UNPKG

webpack

Version:

Packs ECMAScript/CommonJs/AMD modules for the browser. Allows you to split your codebase into multiple bundles, which can be loaded on demand. Supports loaders to preprocess files, i.e. json, jsx, es7, css, less, ... and your custom stuff.

7,980 lines • 269 kB
/*
	MIT License http://www.opensource.org/licenses/mit-license.php
	Author sheo13666q @sheo13666q
*/

// GENERATED by tooling/generate-css-data.js — do not edit.
// Sources: mdn-data, color-name and @mdn/browser-compat-data, at the versions yarn.lock pins.

"use strict";

/** @typedef {(sums: Map<string, number>[]) => [string, number[]] | null} MathArgumentReader */
/** @typedef {(values: number[], strategy: string, table: Map<number, number>) => number | null} MathOperation */

// WHY: The arithmetic the math-function descriptors at the end of this file bind to.
// It knows nothing of CSS beyond the shape of an evaluated argument, and names
// no math function: which one uses which is the descriptors' business, and
// `lib/css/syntax.js` only drives the binding.
/**
 * Add two doubles, or decline when the sum carries rounding of its own.
 * @param {number} a one term
 * @param {number} b the other
 * @returns {number | null} their exact sum, or `null`
 */
const exactAdd = (a, b) => {
	const sum = a + b;
	return sum - b === a && sum - a === b ? sum : null;
};

/**
 * Multiply, or decline, on the same terms.
 * @param {number} a the value
 * @param {number} k the factor
 * @returns {number | null} their exact product, or `null`
 */
const exactMultiply = (a, k) => {
	const product = a * k;
	if (!Number.isFinite(product)) return null;
	if (a === 0 || k === 0) return product;
	return product / k === a ? product : null;
};

/**
 * Add two doubles. Every sum a stylesheet can write is finite, and one that is
 * not is no value to print.
 * @param {number} a one term
 * @param {number} b the other
 * @returns {number | null} their sum, or `null`
 */
const foldAdd = (a, b) => {
	const sum = a + b;
	return Number.isFinite(sum) ? sum : null;
};

/**
 * @param {number} a the value
 * @param {number} k the factor
 * @returns {number | null} their product, or `null`
 */
const foldMultiply = (a, k) => {
	const product = a * k;
	return Number.isFinite(product) ? product : null;
};

/**
 * @param {number} a the value
 * @param {number} k the divisor
 * @returns {number | null} their quotient, or `null` where there is none
 */
const foldDivide = (a, k) => {
	if (k === 0) return null;
	const quotient = a / k;
	return Number.isFinite(quotient) ? quotient : null;
};

/**
 * `floor(value / step)` for a positive step, checked against the step exactly.
 * The double quotient can land an ulp either side of an integer, which would put
 * the multiple a whole step out, so the candidate is verified by multiplying
 * back and nudged at most once either way.
 * @param {number} value the dividend
 * @param {number} step the divisor, greater than zero
 * @returns {number | null} the floor, or `null` when it cannot be pinned down
 */
const exactFloorDivide = (value, step) => {
	let n = Math.floor(value / step);
	if (!Number.isFinite(n)) return null;
	for (let attempt = 0; attempt < 3; attempt++) {
		const at = exactMultiply(n, step);
		const next = exactMultiply(n + 1, step);
		if (at === null || next === null) return null;
		if (at > value) {
			n--;
			continue;
		}
		if (next <= value) {
			n++;
			continue;
		}
		return n;
	}
	return null;
};

/**
 * One evaluated argument list, read as a shared unit and its coefficients. A
 * percentage is refused: its basis can be negative (a `background-position`
 * against an image wider than its box), and comparing two of them depends on
 * that sign in a way `calc()`'s arithmetic does not — scaling a percentage is
 * linear, picking the smaller of two is not.
 * @param {Map<string, number>[]} sums the evaluated arguments
 * @returns {[string, number[]] | null} the shared unit and the coefficients
 */
const readSameUnit = (sums) => {
	/** @type {string | null} */
	let shared = null;
	/** @type {number[]} */
	const values = [];
	for (const sum of sums) {
		if (sum.size !== 1) return null;
		const [[key, coefficient]] = sum;
		if (key === "%") return null;
		if (shared === null) shared = key;
		else if (shared !== key) return null;
		values.push(coefficient);
	}
	return shared === null ? null : [shared, values];
};

/**
 * The same, narrowed to arguments that reduced to a plain `<number>`.
 * @param {Map<string, number>[]} sums the evaluated arguments
 * @returns {[string, number[]] | null} the unit (always `""`) and the numbers
 */
const readNumber = (sums) => {
	const shared = readSameUnit(sums);
	return shared === null || shared[0] !== "" ? null : shared;
};

/**
 * Read a trigonometric function's one argument as degrees. A bare number is
 * radians (CSS Values 4 §10.6), and an angle is the unit it was written in;
 * either way what the fold needs is the one measure the tables are keyed by.
 * @param {Map<string, number>} quarterTurnAngle a quarter turn in each unit that spells one exactly
 * @returns {MathArgumentReader} the reader
 */
const angleReader = (quarterTurnAngle) => (sums) => {
	const shared = readSameUnit(sums);
	if (shared === null) return null;
	const [unit, [angle]] = shared;
	// A radian is what a bare number is read as, and the one angle unit that
	// spells no quarter turn exactly — so the table states none for it.
	if (unit === "" || unit === "rad") return ["", [(angle * 180) / Math.PI]];
	const quarter = quarterTurnAngle.get(unit);
	if (quarter === undefined) return null;
	return ["", [(angle * 90) / quarter]];
};

/**
 * @param {number[]} values the coefficients
 * @returns {number} the smallest
 */
const minimum = (values) => Math.min(...values);

/**
 * @param {number[]} values the coefficients
 * @returns {number} the largest
 */
const maximum = (values) => Math.max(...values);

/**
 * CSS Values 4 §10.4: the lower bound wins a contradictory pair.
 * @param {number[]} values the lower bound, the value and the upper bound
 * @returns {number} the value held between them
 */
const clamp = ([lower, value, upper]) =>
	Math.max(lower, Math.min(value, upper));

/**
 * @param {number[]} values the one coefficient
 * @returns {number} its magnitude
 */
const absolute = ([value]) => Math.abs(value);

/**
 * The one operation whose answer changes unit: a sign is a `<number>`. Every
 * unit reaching here scales by a positive factor, so the coefficient's sign is
 * the value's even where the factor is not known.
 * @param {number[]} values the one coefficient
 * @returns {number} its sign
 */
const sign = ([value]) => Math.sign(value);

/**
 * @param {number[]} values the coefficients
 * @returns {number | null} the root of their squares, or `null`
 */
const hypotenuse = (values) => {
	const total = Math.hypot(...values);
	return Number.isFinite(total) ? total : null;
};

/**
 * The multiple of `step` that `strategy` rounds `value` to, as CSS Values 4
 * §10.6 defines them and headless Chromium confirms: `nearest` breaks a tie
 * toward positive infinity, and the other three are the ceiling, the floor and
 * the truncation. A step of zero is NaN per the spec and engines do not agree
 * on what that renders as; a negative one is left alone rather than reasoned
 * about.
 * @param {number[]} values the value and the step
 * @param {string} strategy one of the grammar's rounding strategies
 * @returns {number | null} the rounded multiple, or `null`
 */
const round = ([value, step], strategy) => {
	if (!(step > 0)) return null;
	const below = exactFloorDivide(value, step);
	if (below === null) return null;
	const at = /** @type {number} */ (exactMultiply(below, step));
	// WHY: Exactly on a step is where engines stop agreeing: these are step functions,
	// so an ulp of error in the engine's own conversion moves the answer a whole
	// step. Headless Chromium reads `round(down,10cm,2cm)` as `8cm` and
	// `round(down,-7cm,.5cm)` as `-7.5cm`. Away from a boundary the gap is orders
	// of magnitude wider than any such error, so only the boundary is refused.
	if (at === value) return null;
	let multiple;
	if (strategy === "down") {
		multiple = below;
	} else if (strategy === "up") {
		multiple = below + 1;
	} else if (strategy === "to-zero") {
		multiple = value < 0 ? below + 1 : below;
	} else {
		// The remainder is in `[0, step)`, so twice it against the step is the
		// comparison, and an exact half rounds up — toward positive infinity.
		const remainder = exactAdd(value, -at);
		if (remainder === null) return null;
		const doubled = exactMultiply(remainder, 2);
		if (doubled === null) return null;
		multiple = doubled >= step ? below + 1 : below;
	}
	return exactMultiply(multiple, step);
};

/**
 * The remainder carrying the divisor's sign.
 * @param {number[]} values the dividend and the divisor
 * @returns {number | null} the remainder, or `null`
 */
const modulus = ([value, divisor]) => {
	if (divisor === 0) return null;
	const remainder = value % divisor;
	// A zero remainder is the boundary these two share with `round()`, and engines
	// do not agree on it: headless Chromium reads `mod(10px,-2px)` and
	// `mod(-9px,3px)` as the divisor where both are zero.
	if (remainder === 0) return null;
	// A remainder on the other side of zero is brought back across it.
	return remainder < 0 === divisor < 0
		? remainder
		: exactAdd(remainder, divisor);
};

/**
 * The remainder carrying the dividend's sign, which is what `%` already does.
 * @param {number[]} values the dividend and the divisor
 * @returns {number | null} the remainder, or `null`
 */
const remainder = ([value, divisor]) => {
	if (divisor === 0) return null;
	// The same zero boundary `modulus` declines.
	const rest = value % divisor;
	return rest === 0 ? null : rest;
};

/**
 * @param {number[]} values the one radicand
 * @returns {number | null} its root, or `null` where there is none
 */
const squareRoot = ([value]) => (value >= 0 ? Math.sqrt(value) : null);

/**
 * @param {number[]} values the base and the exponent
 * @returns {number | null} the power, or `null`
 */
const power = ([base, exponent]) => {
	const raised = base ** exponent;
	return Number.isFinite(raised) ? raised : null;
};

/**
 * @param {number[]} values the value and, optionally, the base
 * @returns {number | null} the logarithm, or `null` where there is none
 */
const logarithm = ([value, base]) => {
	if (!(value > 0)) return null;
	if (base === undefined) return Math.log(value);
	// A base of one divides by zero and a negative one has no logarithm at all;
	// both leave a quotient that is not a number.
	const quotient = Math.log(value) / Math.log(base);
	return Number.isFinite(quotient) ? quotient : null;
};

/**
 * @param {number[]} values the one exponent
 * @returns {number | null} `e` raised to it, or `null`
 */
const exponential = ([value]) => {
	const raised = Math.exp(value);
	return Number.isFinite(raised) ? raised : null;
};

/**
 * The value a table gives at a whole number of eighth turns, where a real
 * computation would answer an ulp away from it — `Math.sin(Math.PI)` is 1.2e-16
 * rather than the zero the table states.
 * @param {number} degrees the angle
 * @param {Map<number, number>} table the function's eighth-turn table
 * @returns {number | undefined} the stated value, or undefined
 */
const eighthTurn = (degrees, table) => {
	const eighths = degrees / 45;
	return Number.isInteger(eighths)
		? table.get(((eighths % 8) + 8) % 8)
		: undefined;
};

/**
 * An inverse trigonometric function answers with an angle, and an angle is the
 * one thing the printer does not round — a `rotate()` runs it back through trig,
 * where a truncated digit is a different matrix. So only the arguments the table
 * states are taken: everywhere else the real answer carries digits that are
 * noise (`asin(.5)` is 30.000000000000004 degrees) and no shorter than the call.
 * @param {number[]} values the one argument
 * @param {string} keyword unused
 * @param {Map<number, number>} table the arguments the table states
 * @returns {number | null} the angle in degrees, or `null`
 */
const statedAngle = ([value], keyword, table) => {
	const stated = table.get(value);
	return stated === undefined ? null : stated;
};

/**
 * Tangent, which has an asymptote an odd quarter turn from zero: the table
 * states no value there because there is none, and a double still answers with
 * a very large one.
 * @param {number[]} values the angle in degrees
 * @param {string} keyword unused
 * @param {Map<number, number>} table the eighth-turn table
 * @returns {number | null} its tangent, or `null` at an asymptote
 */
const tangent = ([degrees], keyword, table) => {
	const stated = eighthTurn(degrees, table);
	if (stated !== undefined) return stated;
	const quarters = degrees / 90;
	if (Number.isInteger(quarters) && ((quarters % 2) + 2) % 2 === 1) return null;
	return Math.tan((degrees * Math.PI) / 180);
};

/**
 * @param {number[]} values the angle in degrees
 * @param {string} keyword unused
 * @param {Map<number, number>} table the eighth-turn table
 * @returns {number | null} its cosine
 */
const cosine = ([degrees], keyword, table) => {
	const stated = eighthTurn(degrees, table);
	return stated === undefined ? Math.cos((degrees * Math.PI) / 180) : stated;
};

/**
 * @param {number[]} values the angle in degrees
 * @param {string} keyword unused
 * @param {Map<number, number>} table the eighth-turn table
 * @returns {number | null} its sine
 */
const sine = ([degrees], keyword, table) => {
	const stated = eighthTurn(degrees, table);
	return stated === undefined ? Math.sin((degrees * Math.PI) / 180) : stated;
};

/**
 * The eight directions the arc tangent of a ratio is a whole number of degrees
 * in, an eighth turn apart. Both zero is refused: the spec leaves it to the
 * engine.
 * @param {number[]} values the two coordinates
 * @returns {number | null} the angle in degrees, or `null`
 */
const arcTangent2 = ([y, x]) => {
	if (y === 0 && x === 0) return null;
	if (y === 0) return x > 0 ? 0 : 180;
	if (x === 0) return y > 0 ? 90 : -90;
	if (Math.abs(y) !== Math.abs(x)) return null;
	if (x > 0) return y > 0 ? 45 : -45;
	return y > 0 ? 135 : -135;
};

// WHY: Properties whose value is CSS's `{1,4}` box notation, where an omitted value
// is copied from the opposite side. That makes a repeated value redundant:
// `margin:1px 1px 1px 1px` is `margin:1px`. `border-radius` collapses each side
// of its `/` independently.
const BOX_SHORTHANDS = new Set([
	"border-color",
	"border-image-outset",
	"border-image-width",
	"border-radius",
	"border-style",
	"border-width",
	"corner-shape",
	"inset",
	"margin",
	"mask-border-outset",
	"mask-border-width",
	"padding",
	"scroll-margin",
	"scroll-padding"
]);

// The subset carrying a second box after a `/`, which collapses on its own.
const SLASH_BOX_SHORTHANDS = new Set(["border-radius"]);

// WHY: The four longhands each box shorthand sets, in the order `{1,4}` writes them:
// `top right bottom left`, or clockwise from the top left for a corner family.
// Only the families whose longhands are those four: merging those into the
// shorthand sets exactly the same properties, resetting nothing extra.
// prettier-ignore
const BOX_LONGHANDS = new Map([
	["border-color", ["border-top-color", "border-right-color", "border-bottom-color", "border-left-color"]],
	["border-radius", ["border-top-left-radius", "border-top-right-radius", "border-bottom-right-radius", "border-bottom-left-radius"]],
	["border-style", ["border-top-style", "border-right-style", "border-bottom-style", "border-left-style"]],
	["border-width", ["border-top-width", "border-right-width", "border-bottom-width", "border-left-width"]],
	["corner-shape", ["corner-top-left-shape", "corner-top-right-shape", "corner-bottom-right-shape", "corner-bottom-left-shape"]],
	["inset", ["top", "right", "bottom", "left"]],
	["margin", ["margin-top", "margin-right", "margin-bottom", "margin-left"]],
	["padding", ["padding-top", "padding-right", "padding-bottom", "padding-left"]],
	["scroll-margin", ["scroll-margin-top", "scroll-margin-right", "scroll-margin-bottom", "scroll-margin-left"]],
	["scroll-padding", ["scroll-padding-top", "scroll-padding-right", "scroll-padding-bottom", "scroll-padding-left"]]
]);

// The shorthands setting exactly two longhands, positionally — the same merge
// as the box families, two values wide. Only these: a shorthand gathering a
// whole family resets longhands `computed` does not name.
const PAIR_LONGHANDS = new Map([
	[
		"border-block-color",
		["border-block-start-color", "border-block-end-color"]
	],
	[
		"border-block-style",
		["border-block-start-style", "border-block-end-style"]
	],
	[
		"border-block-width",
		["border-block-start-width", "border-block-end-width"]
	],
	[
		"border-inline-color",
		["border-inline-start-color", "border-inline-end-color"]
	],
	[
		"border-inline-style",
		["border-inline-start-style", "border-inline-end-style"]
	],
	[
		"border-inline-width",
		["border-inline-start-width", "border-inline-end-width"]
	],
	[
		"contain-intrinsic-size",
		["contain-intrinsic-width", "contain-intrinsic-height"]
	],
	[
		"corner-block-end-shape",
		["corner-end-start-shape", "corner-end-end-shape"]
	],
	[
		"corner-block-start-shape",
		["corner-start-start-shape", "corner-start-end-shape"]
	],
	[
		"corner-bottom-shape",
		["corner-bottom-left-shape", "corner-bottom-right-shape"]
	],
	[
		"corner-inline-end-shape",
		["corner-start-end-shape", "corner-end-end-shape"]
	],
	[
		"corner-inline-start-shape",
		["corner-start-start-shape", "corner-end-start-shape"]
	],
	["corner-left-shape", ["corner-top-left-shape", "corner-bottom-left-shape"]],
	[
		"corner-right-shape",
		["corner-top-right-shape", "corner-bottom-right-shape"]
	],
	["corner-top-shape", ["corner-top-left-shape", "corner-top-right-shape"]],
	["gap", ["row-gap", "column-gap"]],
	["inset-block", ["inset-block-start", "inset-block-end"]],
	["inset-inline", ["inset-inline-start", "inset-inline-end"]],
	["interest-delay", ["interest-delay-start", "interest-delay-end"]],
	["margin-block", ["margin-block-start", "margin-block-end"]],
	["margin-inline", ["margin-inline-start", "margin-inline-end"]],
	["overflow", ["overflow-x", "overflow-y"]],
	["overscroll-behavior", ["overscroll-behavior-x", "overscroll-behavior-y"]],
	["padding-block", ["padding-block-start", "padding-block-end"]],
	["padding-inline", ["padding-inline-start", "padding-inline-end"]],
	["place-content", ["align-content", "justify-content"]],
	["place-items", ["align-items", "justify-items"]],
	["place-self", ["align-self", "justify-self"]],
	[
		"scroll-margin-block",
		["scroll-margin-block-start", "scroll-margin-block-end"]
	],
	[
		"scroll-margin-inline",
		["scroll-margin-inline-start", "scroll-margin-inline-end"]
	],
	[
		"scroll-padding-block",
		["scroll-padding-block-start", "scroll-padding-block-end"]
	],
	[
		"scroll-padding-inline",
		["scroll-padding-inline-start", "scroll-padding-inline-end"]
	]
]);

// The subset whose two-value form is newer than the longhands, so only a merge
// collapsing to one value may emit it.
const ONE_VALUE_PAIR_SHORTHANDS = new Set(["overflow"]);

// The pair shorthands the target's `placeShorthand` ability gates, newer than
// the longhands they merge.
const PLACE_SHORTHANDS = new Set([
	"place-content",
	"place-items",
	"place-self"
]);

// The keywords a shorthand's longhands disagree on, so a merge writing one into
// every slot would turn a declaration the engine kept into a shorthand it drops:
// `justify-items` takes `left` and `align-items` does not.
const UNSHARED_LONGHAND_KEYWORDS = new Map([
	["place-content", new Set(["baseline", "first", "last", "left", "right"])],
	["place-items", new Set(["left", "legacy", "right"])],
	["place-self", new Set(["left", "right"])]
]);

// WHY: The shorthands written as an order-free `||` of their own longhands, each
// appearing once, in grammar order. A merge emits every value, so the only
// question is whether each parses back into the longhand it was authored on.
// prettier-ignore
// The properties whose value ends in a family list, out of the grammars: the
// longhand and the shorthands that reference it.
const FAMILY_LIST_PROPERTIES = new Set(["font", "font-family"]);

const FAMILY_LONGHANDS = new Map([
	[
		"border-block-end",
		[
			"border-block-end-width",
			"border-block-end-style",
			"border-block-end-color"
		]
	],
	[
		"border-block-start",
		[
			"border-block-start-width",
			"border-block-start-style",
			"border-block-start-color"
		]
	],
	[
		"border-bottom",
		["border-bottom-width", "border-bottom-style", "border-bottom-color"]
	],
	[
		"border-inline-end",
		[
			"border-inline-end-width",
			"border-inline-end-style",
			"border-inline-end-color"
		]
	],
	[
		"border-inline-start",
		[
			"border-inline-start-width",
			"border-inline-start-style",
			"border-inline-start-color"
		]
	],
	[
		"border-left",
		["border-left-width", "border-left-style", "border-left-color"]
	],
	[
		"border-right",
		["border-right-width", "border-right-style", "border-right-color"]
	],
	["border-top", ["border-top-width", "border-top-style", "border-top-color"]],
	[
		"column-rule",
		["column-rule-width", "column-rule-style", "column-rule-color"]
	],
	["flex-flow", ["flex-direction", "flex-wrap"]],
	[
		"list-style",
		["list-style-type", "list-style-position", "list-style-image"]
	],
	["outline", ["outline-width", "outline-style", "outline-color"]],
	[
		"text-decoration",
		[
			"text-decoration-line",
			"text-decoration-style",
			"text-decoration-color",
			"text-decoration-thickness"
		]
	],
	["text-emphasis", ["text-emphasis-style", "text-emphasis-color"]],
	["text-wrap", ["text-wrap-mode", "text-wrap-style"]]
]);

// The properties whose comma-separated items take a `<custom-ident>`, where a
// vendor spelling is a name the engine parses rather than one it may drop — so a
// later declaration listing an earlier one's items cannot be its fallback.
const CUSTOM_IDENT_LIST_PROPERTIES = new Set([
	"animation",
	"animation-name",
	"animation-trigger",
	"font-family",
	"font-variant",
	"font-variant-alternates",
	"timeline-trigger-name",
	"timeline-trigger-source",
	"transition",
	"transition-property",
	"trigger-scope",
	"will-change"
]);

// The shorthands whose grammar juxtaposes its longhands in a fixed order, so a
// merge writes every value by position rather than reading which slot takes it.
const ORDERED_LONGHANDS = new Map([
	["flex", ["flex-grow", "flex-shrink", "flex-basis"]]
]);

const SLASH_LONGHANDS = new Map([
	[
		"grid-area",
		["grid-row-start", "grid-column-start", "grid-row-end", "grid-column-end"]
	],
	["grid-column", ["grid-column-start", "grid-column-end"]],
	["grid-row", ["grid-row-start", "grid-row-end"]]
]);

// Every longhand each shorthand sets, so one block can be asked whether another
// could shadow it. Not every shorthand prefixes its longhands: `inset` sets `top`.
const SHORTHAND_LONGHANDS = new Map([
	[
		"-moz-outline-radius",
		new Set([
			"-moz-outline-radius-bottomleft",
			"-moz-outline-radius-bottomright",
			"-moz-outline-radius-topleft",
			"-moz-outline-radius-topright"
		])
	],
	[
		"-ms-content-zoom-limit",
		new Set(["-ms-content-zoom-limit-max", "-ms-content-zoom-limit-min"])
	],
	[
		"-ms-content-zoom-snap",
		new Set(["-ms-content-zoom-snap-points", "-ms-content-zoom-snap-type"])
	],
	[
		"-ms-scroll-limit",
		new Set([
			"-ms-scroll-limit-x-max",
			"-ms-scroll-limit-x-min",
			"-ms-scroll-limit-y-max",
			"-ms-scroll-limit-y-min"
		])
	],
	[
		"-ms-scroll-snap-x",
		new Set(["-ms-scroll-snap-points-x", "-ms-scroll-snap-type"])
	],
	[
		"-ms-scroll-snap-y",
		new Set(["-ms-scroll-snap-points-y", "-ms-scroll-snap-type"])
	],
	[
		"-webkit-border-after",
		new Set([
			"border-block-end-color",
			"border-block-end-style",
			"border-block-end-width"
		])
	],
	[
		"-webkit-border-before",
		new Set([
			"border-block-start-color",
			"border-block-start-style",
			"border-block-start-width"
		])
	],
	[
		"-webkit-border-end",
		new Set([
			"border-inline-end-color",
			"border-inline-end-style",
			"border-inline-end-width"
		])
	],
	[
		"-webkit-border-start",
		new Set([
			"border-inline-start-color",
			"border-inline-start-style",
			"border-inline-start-width"
		])
	],
	[
		"-webkit-mask",
		new Set([
			"-webkit-mask-attachment",
			"-webkit-mask-clip",
			"-webkit-mask-image",
			"-webkit-mask-origin",
			"-webkit-mask-position",
			"-webkit-mask-repeat"
		])
	],
	[
		"-webkit-text-stroke",
		new Set(["-webkit-text-stroke-color", "-webkit-text-stroke-width"])
	],
	[
		"animation",
		new Set([
			"animation-delay",
			"animation-direction",
			"animation-duration",
			"animation-fill-mode",
			"animation-iteration-count",
			"animation-name",
			"animation-play-state",
			"animation-timeline",
			"animation-timing-function"
		])
	],
	[
		"animation-range",
		new Set(["animation-range-end", "animation-range-start"])
	],
	[
		"background",
		new Set([
			"background-attachment",
			"background-clip",
			"background-color",
			"background-image",
			"background-origin",
			"background-position",
			"background-position-x",
			"background-position-y",
			"background-repeat",
			"background-size"
		])
	],
	[
		"background-position",
		new Set(["background-position-x", "background-position-y"])
	],
	[
		"border",
		new Set([
			"border-bottom-color",
			"border-bottom-style",
			"border-bottom-width",
			"border-color",
			"border-left-color",
			"border-left-style",
			"border-left-width",
			"border-right-color",
			"border-right-style",
			"border-right-width",
			"border-style",
			"border-top-color",
			"border-top-style",
			"border-top-width",
			"border-width"
		])
	],
	[
		"border-block",
		new Set([
			"border-block-color",
			"border-block-end-color",
			"border-block-end-style",
			"border-block-end-width",
			"border-block-start-color",
			"border-block-start-style",
			"border-block-start-width",
			"border-block-style",
			"border-block-width"
		])
	],
	[
		"border-block-color",
		new Set(["border-block-end-color", "border-block-start-color"])
	],
	[
		"border-block-end",
		new Set([
			"border-block-end-color",
			"border-block-end-style",
			"border-block-end-width"
		])
	],
	[
		"border-block-start",
		new Set([
			"border-block-start-color",
			"border-block-start-style",
			"border-block-start-width"
		])
	],
	[
		"border-block-style",
		new Set(["border-block-end-style", "border-block-start-style"])
	],
	[
		"border-block-width",
		new Set(["border-block-end-width", "border-block-start-width"])
	],
	[
		"border-bottom",
		new Set([
			"border-bottom-color",
			"border-bottom-style",
			"border-bottom-width"
		])
	],
	[
		"border-color",
		new Set([
			"border-bottom-color",
			"border-left-color",
			"border-right-color",
			"border-top-color"
		])
	],
	[
		"border-image",
		new Set([
			"border-image-outset",
			"border-image-repeat",
			"border-image-slice",
			"border-image-source",
			"border-image-width"
		])
	],
	[
		"border-inline",
		new Set([
			"border-inline-color",
			"border-inline-end-color",
			"border-inline-end-style",
			"border-inline-end-width",
			"border-inline-start-color",
			"border-inline-start-style",
			"border-inline-start-width",
			"border-inline-style",
			"border-inline-width"
		])
	],
	[
		"border-inline-color",
		new Set(["border-inline-end-color", "border-inline-start-color"])
	],
	[
		"border-inline-end",
		new Set([
			"border-inline-end-color",
			"border-inline-end-style",
			"border-inline-end-width"
		])
	],
	[
		"border-inline-start",
		new Set([
			"border-inline-start-color",
			"border-inline-start-style",
			"border-inline-start-width"
		])
	],
	[
		"border-inline-style",
		new Set(["border-inline-end-style", "border-inline-start-style"])
	],
	[
		"border-inline-width",
		new Set(["border-inline-end-width", "border-inline-start-width"])
	],
	[
		"border-left",
		new Set(["border-left-color", "border-left-style", "border-left-width"])
	],
	[
		"border-radius",
		new Set([
			"border-bottom-left-radius",
			"border-bottom-right-radius",
			"border-top-left-radius",
			"border-top-right-radius"
		])
	],
	[
		"border-right",
		new Set(["border-right-color", "border-right-style", "border-right-width"])
	],
	[
		"border-style",
		new Set([
			"border-bottom-style",
			"border-left-style",
			"border-right-style",
			"border-top-style"
		])
	],
	[
		"border-top",
		new Set(["border-top-color", "border-top-style", "border-top-width"])
	],
	[
		"border-width",
		new Set([
			"border-bottom-width",
			"border-left-width",
			"border-right-width",
			"border-top-width"
		])
	],
	["caret", new Set(["caret-animation", "caret-color", "caret-shape"])],
	[
		"column-rule",
		new Set(["column-rule-color", "column-rule-style", "column-rule-width"])
	],
	["columns", new Set(["column-count", "column-height", "column-width"])],
	[
		"contain-intrinsic-size",
		new Set(["contain-intrinsic-height", "contain-intrinsic-width"])
	],
	["container", new Set(["container-name", "container-type"])],
	[
		"corner-block-end-shape",
		new Set(["corner-end-end-shape", "corner-end-start-shape"])
	],
	[
		"corner-block-start-shape",
		new Set(["corner-start-end-shape", "corner-start-start-shape"])
	],
	[
		"corner-bottom-shape",
		new Set(["corner-bottom-left-shape", "corner-bottom-right-shape"])
	],
	[
		"corner-inline-end-shape",
		new Set(["corner-end-end-shape", "corner-start-end-shape"])
	],
	[
		"corner-inline-start-shape",
		new Set(["corner-start-end-shape", "corner-start-start-shape"])
	],
	[
		"corner-left-shape",
		new Set(["corner-bottom-left-shape", "corner-top-left-shape"])
	],
	[
		"corner-right-shape",
		new Set(["corner-bottom-right-shape", "corner-top-right-shape"])
	],
	[
		"corner-shape",
		new Set([
			"corner-bottom-left-shape",
			"corner-bottom-right-shape",
			"corner-top-left-shape",
			"corner-top-right-shape"
		])
	],
	[
		"corner-top-shape",
		new Set(["corner-top-left-shape", "corner-top-right-shape"])
	],
	["flex", new Set(["flex-basis", "flex-grow", "flex-shrink"])],
	["flex-flow", new Set(["flex-direction", "flex-wrap"])],
	[
		"font",
		new Set([
			"font-family",
			"font-size",
			"font-stretch",
			"font-style",
			"font-variant",
			"font-weight",
			"line-height"
		])
	],
	["gap", new Set(["column-gap", "row-gap"])],
	[
		"grid",
		new Set([
			"column-gap",
			"grid-auto-columns",
			"grid-auto-flow",
			"grid-auto-rows",
			"grid-column-gap",
			"grid-row-gap",
			"grid-template-areas",
			"grid-template-columns",
			"grid-template-rows",
			"row-gap"
		])
	],
	[
		"grid-area",
		new Set([
			"grid-column-end",
			"grid-column-start",
			"grid-row-end",
			"grid-row-start"
		])
	],
	["grid-column", new Set(["grid-column-end", "grid-column-start"])],
	["grid-gap", new Set(["grid-column-gap", "grid-row-gap"])],
	["grid-row", new Set(["grid-row-end", "grid-row-start"])],
	[
		"grid-template",
		new Set([
			"grid-template-areas",
			"grid-template-columns",
			"grid-template-rows"
		])
	],
	["inset", new Set(["bottom", "left", "right", "top"])],
	["inset-block", new Set(["inset-block-end", "inset-block-start"])],
	["inset-inline", new Set(["inset-inline-end", "inset-inline-start"])],
	["interest-delay", new Set(["interest-delay-end", "interest-delay-start"])],
	[
		"list-style",
		new Set(["list-style-image", "list-style-position", "list-style-type"])
	],
	[
		"margin",
		new Set(["margin-bottom", "margin-left", "margin-right", "margin-top"])
	],
	["margin-block", new Set(["margin-block-end", "margin-block-start"])],
	["margin-inline", new Set(["margin-inline-end", "margin-inline-start"])],
	[
		"mask",
		new Set([
			"mask-clip",
			"mask-composite",
			"mask-image",
			"mask-mode",
			"mask-origin",
			"mask-position",
			"mask-repeat",
			"mask-size"
		])
	],
	[
		"mask-border",
		new Set([
			"mask-border-mode",
			"mask-border-outset",
			"mask-border-repeat",
			"mask-border-slice",
			"mask-border-source",
			"mask-border-width"
		])
	],
	[
		"offset",
		new Set([
			"offset-anchor",
			"offset-distance",
			"offset-path",
			"offset-position",
			"offset-rotate"
		])
	],
	["outline", new Set(["outline-color", "outline-style", "outline-width"])],
	["overflow", new Set(["overflow-x", "overflow-y"])],
	[
		"overscroll-behavior",
		new Set(["overscroll-behavior-x", "overscroll-behavior-y"])
	],
	[
		"padding",
		new Set(["padding-bottom", "padding-left", "padding-right", "padding-top"])
	],
	["padding-block", new Set(["padding-block-end", "padding-block-start"])],
	["padding-inline", new Set(["padding-inline-end", "padding-inline-start"])],
	["place-content", new Set(["align-content", "justify-content"])],
	["place-items", new Set(["align-items", "justify-items"])],
	["place-self", new Set(["align-self", "justify-self"])],
	["position-try", new Set(["position-try-fallbacks", "position-try-order"])],
	[
		"scroll-margin",
		new Set([
			"scroll-margin-bottom",
			"scroll-margin-left",
			"scroll-margin-right",
			"scroll-margin-top"
		])
	],
	[
		"scroll-margin-block",
		new Set(["scroll-margin-block-end", "scroll-margin-block-start"])
	],
	[
		"scroll-margin-inline",
		new Set(["scroll-margin-inline-end", "scroll-margin-inline-start"])
	],
	[
		"scroll-padding",
		new Set([
			"scroll-padding-bottom",
			"scroll-padding-left",
			"scroll-padding-right",
			"scroll-padding-top"
		])
	],
	[
		"scroll-padding-block",
		new Set(["scroll-padding-block-end", "scroll-padding-block-start"])
	],
	[
		"scroll-padding-inline",
		new Set(["scroll-padding-inline-end", "scroll-padding-inline-start"])
	],
	[
		"scroll-timeline",
		new Set(["scroll-timeline-axis", "scroll-timeline-name"])
	],
	[
		"text-decoration",
		new Set([
			"text-decoration-color",
			"text-decoration-line",
			"text-decoration-style",
			"text-decoration-thickness"
		])
	],
	["text-emphasis", new Set(["text-emphasis-color", "text-emphasis-style"])],
	["text-wrap", new Set(["text-wrap-mode", "text-wrap-style"])],
	[
		"timeline-trigger",
		new Set([
			"timeline-trigger-activation-range",
			"timeline-trigger-activation-range-end",
			"timeline-trigger-activation-range-start",
			"timeline-trigger-active-range",
			"timeline-trigger-active-range-end",
			"timeline-trigger-active-range-start",
			"timeline-trigger-name",
			"timeline-trigger-source"
		])
	],
	[
		"timeline-trigger-activation-range",
		new Set([
			"timeline-trigger-activation-range-end",
			"timeline-trigger-activation-range-start"
		])
	],
	[
		"timeline-trigger-active-range",
		new Set([
			"timeline-trigger-active-range-end",
			"timeline-trigger-active-range-start"
		])
	],
	[
		"transition",
		new Set([
			"transition-behavior",
			"transition-delay",
			"transition-duration",
			"transition-property",
			"transition-timing-function"
		])
	],
	["view-timeline", new Set(["view-timeline-axis", "view-timeline-name"])]
]);

// WHY: Every longhand the three merge tables above can consume, so a block is asked
// once whether it holds anything mergeable at all. Two of them have to be
// present before any shorthand can be written, and almost no block holds one,
// which is what keeps the merge off the declarations it cannot serve.
const MERGE_LONGHANDS = new Set([
	"align-content",
	"align-items",
	"align-self",
	"border-block-end-color",
	"border-block-end-style",
	"border-block-end-width",
	"border-block-start-color",
	"border-block-start-style",
	"border-block-start-width",
	"border-bottom-color",
	"border-bottom-left-radius",
	"border-bottom-right-radius",
	"border-bottom-style",
	"border-bottom-width",
	"border-inline-end-color",
	"border-inline-end-style",
	"border-inline-end-width",
	"border-inline-start-color",
	"border-inline-start-style",
	"border-inline-start-width",
	"border-left-color",
	"border-left-style",
	"border-left-width",
	"border-right-color",
	"border-right-style",
	"border-right-width",
	"border-top-color",
	"border-top-left-radius",
	"border-top-right-radius",
	"border-top-style",
	"border-top-width",
	"bottom",
	"column-gap",
	"column-rule-color",
	"column-rule-style",
	"column-rule-width",
	"contain-intrinsic-height",
	"contain-intrinsic-width",
	"corner-bottom-left-shape",
	"corner-bottom-right-shape",
	"corner-end-end-shape",
	"corner-end-start-shape",
	"corner-start-end-shape",
	"corner-start-start-shape",
	"corner-top-left-shape",
	"corner-top-right-shape",
	"flex-basis",
	"flex-direction",
	"flex-grow",
	"flex-shrink",
	"flex-wrap",
	"grid-column-end",
	"grid-column-start",
	"grid-row-end",
	"grid-row-start",
	"inset-block-end",
	"inset-block-start",
	"inset-inline-end",
	"inset-inline-start",
	"interest-delay-end",
	"interest-delay-start",
	"justify-content",
	"justify-items",
	"justify-self",
	"left",
	"list-style-image",
	"list-style-position",
	"list-style-type",
	"margin-block-end",
	"margin-block-start",
	"margin-bottom",
	"margin-inline-end",
	"margin-inline-start",
	"margin-left",
	"margin-right",
	"margin-top",
	"outline-color",
	"outline-style",
	"outline-width",
	"overflow-x",
	"overflow-y",
	"overscroll-behavior-x",
	"overscroll-behavior-y",
	"padding-block-end",
	"padding-block-start",
	"padding-bottom",
	"padding-inline-end",
	"padding-inline-start",
	"padding-left",
	"padding-right",
	"padding-top",
	"right",
	"row-gap",
	"scroll-margin-block-end",
	"scroll-margin-block-start",
	"scroll-margin-bottom",
	"scroll-margin-inline-end",
	"scroll-margin-inline-start",
	"scroll-margin-left",
	"scroll-margin-right",
	"scroll-margin-top",
	"scroll-padding-block-end",
	"scroll-padding-block-start",
	"scroll-padding-bottom",
	"scroll-padding-inline-end",
	"scroll-padding-inline-start",
	"scroll-padding-left",
	"scroll-padding-right",
	"scroll-padding-top",
	"text-decoration-color",
	"text-decoration-line",
	"text-decoration-style",
	"text-decoration-thickness",
	"text-emphasis-color",
	"text-emphasis-style",
	"text-wrap-mode",
	"text-wrap-style",
	"top"
]);

// WHY: The initial keyword each of these may drop when another component stands
// beside it: omitting the group it belongs to leaves exactly that keyword. The
// second half is every keyword that group offers — a value naming two of them
// (`grid-auto-flow:row dense column`) fills the slot twice and is invalid, so
// dropping the initial there would print a value the author never wrote.
/** @type {Map<string, [string, string[]]>} */
// prettier-ignore
const OMITTABLE_INITIAL_KEYWORDS = new Map([["grid-auto-flow", ["row", ["column","row"]]]]);

// WHY: What each of those longhands accepts as a whole value: the keywords it names,
// and the value classes it reaches. A value acceptable to a second slot is what
// makes the merge ambiguous, and `FAMILY_SLOT_CLASSES` names a type the printer
// cannot classify as readily as one it can, so an unknown one declines.
// prettier-ignore
const FAMILY_SLOT_KEYWORDS = new Map([["border-block-end-width", ["medium","thick","thin"]], ["border-block-end-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-block-end-color", []], ["border-block-start-width", ["medium","thick","thin"]], ["border-block-start-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-block-start-color", []], ["border-bottom-width", ["medium","thick","thin"]], ["border-bottom-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-bottom-color", []], ["border-inline-end-width", ["medium","thick","thin"]], ["border-inline-end-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-inline-end-color", []], ["border-inline-start-width", ["medium","thick","thin"]], ["border-inline-start-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-inline-start-color", []], ["border-left-width", ["medium","thick","thin"]], ["border-left-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-left-color", []], ["border-right-width", ["medium","thick","thin"]], ["border-right-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-right-color", []], ["border-top-width", ["medium","thick","thin"]], ["border-top-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["border-top-color", []], ["column-rule-width", ["medium","thick","thin"]], ["column-rule-style", ["dashed","dotted","double","groove","hidden","inset","none","outset","ridge","solid"]], ["column-rule-color", []], ["flex-direction", ["column","column-reverse","row","row-reverse"]], ["flex-wrap", ["nowrap","wrap","wrap-reverse"]], ["list-style-type", ["none"]], ["list-style-position", ["inside","outside"]], ["list-style-image", ["none"]], ["outline-width", ["medium","thick","thin"]], ["outline-style", ["auto","dashed","dotted","double","groove","inset","none","outset","ridge","solid"]], ["outline-color", ["auto"]], ["text-decoration-line", ["blink","grammar-error","line-through","none","overline","spelling-error","underline"]], ["text-decoration-style", ["dashed","dotted","double","solid","wavy"]], ["text-decoration-color", []], ["text-decoration-thickness", ["auto","from-font"]], ["text-emphasis-style", ["circle","dot","double-circle","filled","none","open","sesame","triangle"]], ["text-emphasis-color", []], ["text-wrap-mode", ["nowrap","wrap"]], ["text-wrap-style", ["auto","balance","pretty","stable"]]]);

// prettier-ignore
const FAMILY_SLOT_CLASSES = new Map([["border-block-end-width", ["length"]], ["border-block-end-style", []], ["border-block-end-color", ["color"]], ["border-block-start-width", ["length"]], ["border-block-start-style", []], ["border-block-start-color", ["color"]], ["border-bottom-width", ["length"]], ["border-bottom-style", []], ["border-bottom-color", ["color"]], ["border-inline-end-width", ["length"]], ["border-inline-end-style", []], ["border-inline-end-color", ["color"]], ["border-inline-start-width", ["length"]], ["border-inline-start-style", []], ["border-inline-start-color", ["color"]], ["border-left-width", ["length"]], ["border-left-style", []], ["border-left-color", ["color"]], ["border-right-width", ["length"]], ["border-right-style", []], ["border-right-color", ["color"]], ["border-top-width", ["length"]], ["border-top-style", []], ["border-top-color", ["color"]], ["column-rule-width", ["length"]], ["column-rule-style", []], ["column-rule-color", ["color"]], ["flex-direction", []], ["flex-wrap", []], ["list-style-type", ["custom-ident","string"]], ["list-style-position", []], ["list-style-image", ["image"]], ["outline-width", ["length"]], ["outline-style", []], ["outline-color", ["color"]], ["text-decoration-line", []], ["text-decoration-style", []], ["text-decoration-color", ["color"]], ["text-decoration-thickness", ["length","percentage"]], ["text-emphasis-style", ["string"]], ["text-emphasis-color", ["color"]], ["text-wrap-mode", []], ["text-wrap-style", []]]);

// WHY: The identifiers that are a `<color>` on their own — named, system and the two
// context-dependent ones. Read off the `<color>` grammar outside any function,
// so a channel keyword like the `none` in `hsl(0 none 0)` is not among them.
// cspell:ignore accentcolor accentcolortext activeborder activecaption activetext aliceblue antiquewhite appworkspace aqua aquamarine azure background beige bisque black blanchedalmond blue blueviolet brown burlywood buttonborder buttonface buttonhighlight buttonshadow buttontext cadetblue canvas canvastext captiontext chartreuse chocolate coral cornflowerblue cornsilk crimson currentcolor cyan darkblue darkcyan darkgoldenrod darkgray darkgreen darkgrey darkkhaki darkmagenta darkolivegreen darkorange darkorchid darkred darksalmon darkseagreen darkslateblue darkslategray darkslategrey darkturquoise darkviolet deeppink deepskyblue dimgray dimgrey dodgerblue field fieldtext firebrick floralwhite forestgreen fuchsia gainsboro ghostwhite gold goldenrod gray graytext green greenyellow grey highlight highlighttext honeydew hotpink inactiveborder inactivecaption inactivecaptiontext indianred indigo infobackground infotext ivory khaki lavender lavenderblush lawngreen lemonchiffon lightblue lightcoral lightcyan lightgoldenrodyellow lightgray lightgreen lightgrey lightpink lightsalmon lightseagreen lightskyblue lightslategray lightslategrey lightsteelblue lightyellow lime limegreen linen linktext magenta mark marktext maroon mediumaquamarine mediumblue mediumorchid mediumpurple mediumseagreen mediumslateblue mediumspringgreen mediumturquoise mediumvioletred menu menutext midnightblue mintcream mistyrose moccasin navajowhite navy oldlace olive olivedrab orange orangered orchid palegoldenrod palegreen paleturquoise palevioletred papayawhip peachpuff peru pink plum powderblue purple rebeccapurple red rosybrown royalblue saddlebrown salmon sandybrown scrollbar seagreen seashell selecteditem selecteditemtext sienna silver skyblue slateblue slategray slategrey snow springgreen steelblue tan teal thistle threeddarkshadow threedface threedhighlight threedlightshadow threedshadow tomato transparent turquoise violet visitedtext wheat white whitesmoke window windowframe windowtext yellow yellowgreen
const COLOR_KEYWORDS = new Set([
	"accentcolor",
	"accentcolortext",
	"activeborder",
	"activecaption",
	"activetext",
	"aliceblue",
	"antiquewhite",
	"appworkspace",
	"aqua",
	"aquamarine",
	"azure",
	"background",
	"beige",
	"bisque",
	"black",
	"blanchedalmond",
	"blue",
	"blueviolet",
	"brown",
	"burlywood",
	"buttonborder",
	"buttonface",
	"buttonhighlight",
	"buttonshadow",
	"buttontext",
	"cadetblue",
	"canvas",
	"canvastext",
	"captiontext",
	"chartreuse",
	"chocolate",
	"coral",
	"cornflowerblue",
	"cornsilk",
	"crimson",
	"currentcolor",
	"cyan",
	"darkblue",
	"darkcyan",
	"darkgoldenrod",
	"darkgray",
	"darkgreen",
	"darkgrey",
	"darkkhaki",
	"darkmagenta",
	"darkolivegreen",
	"darkorange",
	"darkorchid",
	"darkred",
	"darksalmon",
	"darkseagreen",
	"darkslateblue",
	"darkslategray",
	"darkslategrey",
	"darkturquoise",
	"darkviolet",
	"deeppink",
	"deepskyblue",
	"dimgray",
	"dimgrey",
	"dodgerblue",
	"field",
	"fieldtext",
	"firebrick",
	"floralwhite",
	"forestgreen",
	"fuchsia",
	"gainsboro",
	"ghostwhite",
	"gold",
	"goldenrod",
	"gray",
	"graytext",
	"green",
	"greenyellow",
	"grey",
	"highlight",
	"highlighttext",
	"honeydew",
	"hotpink",
	"inactiveborder",
	"inactivecaption",
	"inactivecaptiontext",
	"indianred",
	"indigo",
	"infobackground",
	"infotext",
	"ivory",
	"khaki",
	"lavender",
	"lavenderblush",
	"lawngreen",
	"lemonchiffon",
	"lightblue",
	"lightcoral",
	"lightcyan",
	"lightgoldenrodyellow",
	"lightgray",
	"lightgreen",
	"lightgrey",
	"lightpink",
	"lightsalmon",
	"lightseagreen",
	"lightskyblue",
	"lightslategray",
	"lightslategrey",
	"lightsteelblue",
	"lightyellow",
	"lime",
	"limegreen",
	"linen",
	"linktext",
	"magenta",
	"mark",
	"marktext",
	"maroon",
	"mediumaquamarine",
	"mediumblue",
	"mediumorchid",
	"mediumpurple",
	"mediumseagreen",
	"mediumslateblue",
	"mediumspringgreen",
	"mediumturquoise",
	"mediumvioletred",
	"menu",
	"menutext",
	"midnightblue",
	"mintcream",
	"mistyrose",
	"moccasin",
	"navajowhite",
	"navy",
	"oldlace",
	"olive",
	"olivedrab",
	"orange",
	"orangered",
	"orchid",
	"palegoldenrod",
	"palegreen",
	"paleturquoise",
	"palevioletred",
	"papayawhip",
	"peachpuff",
	"peru",
	"pink",
	"plum",
	"powderblue",
	"purple",
	"rebeccapurple",
	"red",
	"rosybrown",
	"royalblue",
	"saddlebrown",
	"salmon",
	"sandybrown",
	"scrollbar",
	"seagreen",
	"seashell",
	"selecteditem",
	"selecteditemtext",
	"sienna",
	"silver",
	"skyblue",
	"slateblue",
	"slategray",
	"slategrey",
	"snow",
	"springgreen",
	"steelblue",
	"tan",
	"teal",
	"thistle",
	"threeddarkshadow",
	"threedface",
	"threedhighlight",
	"threedlightshadow",
	"threedshadow",
	"tomato",
	"transparent",
	"turquoise",
	"violet",
	"visitedtext",
	"wheat",
	"white",
	"whitesmoke",
	"window",
	"windowframe",
	"windowtext",
	"yellow",
	"yellowgreen"
]);

// WHY: The name prefix a declaration between two box longhands must not carry for the
// merge to step over it. The shorthand's first segment, which is deliberately
// wider than the family: `border-color` blocks every `border*` property, since
// `border`, `border-top` and `border-block-start-color` all write its longhands
// and `mdn-data`'s `computed` lists only some of them.
const BOX_FAMILY_PREFIX = new Map([
	["border-color", "border"],
	["border-radius", "border"],
	["border-style", "border"],
	["border-width", "border"],
	["corner-shape", "corner"],
	["inset", "inset"],
	["margin", "margin"],
	["padding", "padding"],
	["scroll-margin", "scroll"],
	["scroll-padding", "scroll"]
]);

// Functions that take a `<color>` directly, so a hash among their arguments is a
// hex color rather than a case-sensitive reference (`element(#id)`). Only direct
// arguments: a gradient nested in `image-set()` is matched as the gradient.
const COLOR_ARGUMENT_FUNCTIONS = new Set([
	"alpha",
	"color",
	"color-mix",
	"conic-gradient",
	"cross-fade",
	"drop-shadow",
	"image",
	"light-dark",
	"linear-gradient",
	"radial-gradient",
	"repeating-conic-gradient",
	"repeating-linear-gradient",
	"repeating-radial-gradient"
]);

// The functions that are a color rather than take one, out of `<color>`'s own
// grammar — what says a call fills a slot a color fills.
const COLOR_FUNCTIONS = new Set([
	"color",
	"color-mix",
	"hsl",
	"hsla",
	"hwb",
	"lab",
	"lch",
	"light-dark",
	"oklab",
	"oklch",
	"rgb",
	"rgba"
]);

// Functions that substitute an arbitrary token sequence, so two identical
// references need not be one repeated value: with `--x:1px 2px`,
// `margin:var(--x) var(--x)` is four values, not two.
const SUBSTITUTION_FUNCTIONS = new Set([
	"attr",
	"env",
	"first-valid",
	"if",
	"inherit",
	"paint",
	"param",
	"random-item",
	"var"
]);

// The pseudo-class functions whose argument is An+B, where `2n+1` is the
// notation `odd` names in one byte less.
const NTH_PSEUDO_FUNCTIONS = new Set([
	"nth-child",
	"nth-last-child",
	"nth-last-of-type",
	"nth-of-type"
]);

// Each An+B pseudo-class whose one-element case has a name of its own:
// `:nth-child(1)` is what `:first-child` selects, in fewer bytes.
const NTH_NAMED_EQUIVALENTS = new Map([
	["nth-child", "first-child"],
	["nth-last-child", "last-child"],
	["nth-last-of-type", "last-of-type"],
	["nth-of-type", "first-of-type"]
]);

// The properties taking a color and never an identifier of the author's own, so
// a named color written in one is that color and may be spelled the shortest way.
const COLOR_ONLY_PROPERTIES = new Set([
	"-moz-border-bottom-colors",
	"-moz-border-left-colors",
	"-moz-border-right-colors",
	"-moz-border-top-colors",
	"-ms-scrollbar-3dlight-color",
	"-ms-scrollbar-arrow-color",
	"-ms-scrollbar-base-color",
	"-ms-scrollbar-darkshadow-color",
	"-ms-scrollbar-face-color",
	"-ms-scrollbar-highlight-color",
	"-ms-scrollbar-shadow-color",
	"-ms-scrollbar-track-color",
	"-webkit-border-after",
	"-webkit-border-after-color",
	"-webkit-border-before",
	"-webkit-border-before-color",
	"-webkit-border-end",
	"-webkit-border-end-color",
	"-webkit-border-start",
	"-webkit-border-start-color",
	"-webkit-tap-highlight-color",
	"-webkit-text-fill-color",
	"-webkit-text-stroke",
	"-webkit-text-stroke-color",
	"accent-color",
	"backdrop-filter",
	"background-color",
	"border",
	"border-block",
	"border-block-color",
	"border-block-end",
	"border-block-end-color",
	"border-block-start",
	"border-block-start-color",
	"border-bottom",
	"border-bottom-color",
	"border-color",
	"border-inline",
	"border-inline-color",
	"border-inline-end",
	"border-inline-end-color",
	"border-inline-start",
	"border-inline-start-color",
	"border-left",
	"border-left-color",
	"border-right",
	"border-right-color",
	"border-top",
	"border-top-color",
	"box-shadow",
	"caret",
	"caret-color",
	"color",
	"column-rule",
	"column-rule-color",
	"fill",
	"filter",
	"flood-color",
	"lighting-color",
	"outline",
	"outline-color",
	"scrollbar-color",
	"stop-color",
	"stroke",
	"stroke-color",
	"text-decoration",
	"text-decoration-color",
	"text-emphasis",
	"text-emphasis-color",
	"text-shadow"
]);

// WHY: The properties whose value is keywords alone, so an identifier standing
// directly in one is a keyword rather than a name of the author's — and matches
// ASCII case-insensitively. A call's arguments are read against the function's
// own grammar, so they are not covered.
const KEYWORD_ONLY_PROPERTIES = new Set([
	"-moz-appearance",
	"-moz-context-properties",
	"-moz-float-edge",
	"-moz-force-broken-image-icon",
	"-moz-orient",
	"-moz-stack-sizing",
	"-moz-text-blink",
	"-moz-user-focus",
	"-moz-user-input",
	"-moz-user-modify",
	"-moz-window-dragging",
	"-moz-window-shadow",
	"-ms-accelerator",
	"-ms-block-progression",
	"-ms-content-zoom-chaining",
	"-ms-content-zoom-snap",
	"-ms-content-zoom-snap-type",
	"-ms-content-zooming",
	"-ms-high-contrast-adjust",
	"-ms-ime-align",
	"-ms-overflow-style",
	"-ms-scroll-chaining",
	"-ms-scroll-rails",
	"-ms-scroll-snap-type",
	"-ms-scroll-snap-x",
	"-ms-scroll-snap-y",
	"-ms-scroll-translation",
	"-ms-text-autospace",
	"-ms-touch-select",
	"-ms-user-select",
	"-ms-wrap-flow",
	"-ms-wrap-through",
	"-webkit-appearance",
	"-webkit-border-after-style",
	"-webkit-border-before-style",
	"-webkit-border-end-style",
	"-webkit-border-start-style",
	"-webkit-mask-attachment",
	"-webkit-mask-clip",
	"-webkit-mask-composite",
	"-webkit-mask-origin",
	"-webkit-mask-repeat",
	"-webkit-mask-repeat-x",
	"-webkit-mask-repeat-y",
	"-webkit-overflow-scrolling",
	"-webkit-touch-callout",
	"-webkit-user-modify",
	"-webkit-user-select",
	"align-content",
	"align-items",
	"align-self",
	"align-tracks",
	"alignment-baseline",
	"all",
	"animation-composition",
	"animation-direction",
	"animation-fill-mode",
	"animation-play-state",
	"animation-timing-function",
	"appearance",
	"backface-visibility",
	"background-attachment",
	"background-blend-mode",
	"background-clip",
	"background-origin",
	"background-repeat",
	"baseline-source",
	"border-block-end-style",
	"border-block-start-style",
	"border-block-style",
	"border-bottom-style",
	"border-collapse",
	"border-image-repeat",
	"border-inline-end-style",
	"border-inline-start-style",
	"border-inline-style",
	"border-left-style",
	"border-right-style",
	"border-shape",
	"border-style",
	"border-top-style",
	"box-align",
	"box-decoration-break",
	"box-direction",
	"box-lines",
	"box-orient",
	"box-pack",
	"box-sizing",
	"break-after",
	"break-before",
	"break-inside",
	"caption-side",
	"caret-animation",
	"caret-shape",
	"clear",
	"clip",
	"clip-rule",
	"color-interpolation-filters",
	"column-fill",
	"column-rule-style",
	"column-span",
	"column-wrap",
	"contain",
	"container-type",
	"content-visibility",
	"corner-block-end-shape",
	"corner-block-start-shape",
	"corner-bottom-left-shape",
	"corner-bottom-right-shape",
	"corner-bottom-shape",
	"corner-end-end-shape",
	"corner-end-start-shape",
	"corner-inline-end-shape",
	"corner-inline-start-shape",
	"corner-left-shape",
	"corner-right-shape",
	"corner-shape",
	"corner-start-end-shape",
	"corner-start-start-shape",
	"corner-top-left-shape",
	"corner-top-right-shape",
	"corner-top-shape",
	"d",
	"direction",
	"display",
	"dominant-baseline",
	"dynamic-range-limit",
	"empty-cells",
	"field-sizing",
	"fill-rule",
	"flex-direction",
	"flex-flow",
	"flex-wrap",
	"float",
	"font-kerning",
	"font-optical-sizing",
	"font-synthesis",
	"font-synthesis-position",
	"font-synthesis-small-caps",
	"font-synthesis-style",
	"font-synthesis-weight",
	"font-variant",
	"font-variant-alternates",
	"font-variant-caps",
	"font-variant-east-asian",
	"font-variant-emoji",
	"font-variant-ligatures",
	"font-variant-numeric",
	"font-variant-position",
	"forced-color-adjust",
	"frame-sizing",
	"grid-auto-flow",
	"hanging-punctuation",
	"hyphens",
	"image-rendering",
	"ime-mode",
	"initial-letter-align",
	"interactivity",
	"interpolate-size",
	"isolation",
	"justify-content",
	"justify-items",
	"justify-self",
	"justify-tracks",
	"line-break",
	"list-style-position",
	"margin-trim",
	"mask-border-mode",
	"mask-border-repeat",
	"mask-clip",
	"mask-composite",
	"mask-mode",
	"mask-origin",
	"mask-repeat",
	"mask-type",
	"masonry-auto-flow",
	"math-shift",
	"math-style",
	"mix-blend-mode",
	"object-fit",
	"object-view-box",
	"outline-style",
	"overflow",
	"overflow-anchor",
	"overflow-block",
	"overflow-clip-box",
	"overflow-inline",
	"overflow-wrap",
	"overflow-x",
	"overflow-y",
	"overlay",
	"overscroll-behavior",
	"overscroll-behavior-block",
	"overscroll-behavior-inline",
	"overscroll-behavior-x",
	"overscroll-behavior-y",
	"page-break-after",
	"page-break-before",
	"page-break-inside",
	"paint-order",
	"place-content",
	"place-items",
	"place-self",
	"pointer-events",
	"position",
	"position-area",
	"position-try-order",
	"position-visibility",
	"print-color-adjust",
	"reading-flow",
	"resize",
	"ruby-align",
	"ruby-merge",
	"ruby-overhang",
	"ruby-position",
	"scroll-behavior",
	"scroll-initial-target",
	"scroll-marker-group",
	"scroll-snap-align",
	"scroll-snap-points-x",
	"scroll-snap-points-y",
	"scroll-snap-stop",
	"scroll-snap-type",
	"scroll-snap-type-x",
	"scroll-snap-type-y",
	"scroll-target-group",
	"scroll-timeline-axis",
	"scrollbar-gutter",
	"scrollbar-width",
	"shape-rendering",
	"speak-as",
	"stroke-linecap",
	"stroke-linejoin",
	"table-layout",
	"text-align",
	"text-align-last",
	"text-anchor",
	"text-box",
	"text-box-edge",
	"text-box-trim",
	"text-decoration-line",
	"text-decoration-skip",
	"text-decoration-skip-ink",
	"text-decoration-style",
	"text-emphasis-position",
	"text-justify",
	"text-orientation",
	"text-rendering",
	"text-spacing-trim",
	"text-transform",
	"text-underline-position",
	"text-wrap",
	"text-wrap-mode",
	"text-wrap-style",
	"touch-action",
	"transform",
	"transform-box",
	"transform-style",
	"transition-behavior",
	"transition-timing-function",
	"unicode-bidi",
	"user-select",
	"vector-effect",
	"view-timeline-axis",
	"view-transition-scope",
	"visibility",
	"white-space",
	"white-space-collapse",
	"word-break",
	"word-wrap",
	"writing-mode"
]);

// Each two-keyword `display` -> the single keyword naming the same box.
const DISPLAY_SHORT_FORMS = new Map([
	["block flex", "flex"],
	["block flow", "block"],
	["block flow-root", "flow-root"],
	["block grid", "grid"],
	["block table", "table"],
	["inline flex", "inline-flex"],
	["inline flow", "inline"],
	["inline flow-root", "inline-block"],
	["inline grid", "inline-grid"],
	["inline ruby", "ruby"],
	["inline table", "inline-table"],
	["run-in flow", "run-in"]
]);

// Each property whose value is a list of shadows -> the count of lengths a
// shadow cannot go below, past which a trailing zero is already implied.
const SHADOW_PROPERTIES = new Map([
	["box-shadow", 2],
	["text-shadow", 2]
]);

// WHY: Each shorthand -> the keywords one of its values may drop, each with every
// spelling its own slot takes: the slot's keywords, and each function it
// accepts written `name()`. A sibling out of that set means the value fills the
// slot twice, which is a declaration the engine drops.
const SHORTHAND_INITIAL_KEYWORDS = new Map([
	[
		"animation",
		new Map([
			[
				"ease",
				{
					spellings: new Set([
						"cubic-bezier()",
						"ease",
						"ease-in",
						"ease-in-out",
						"ease-out",
						"linear",
						"linear()",
						"step-end",
						"step-start",
						"steps()"
					]),
					classes: new Set()
				}
			],
			[
				"normal",
				{
					spellings: new Set([
						"alternate",
						"alternate-reverse",
						"normal",
						"reverse"
					]),
					classes: new Set()
				}
			],
			[
				"running",
				{ spellings: new Set(["paused", "running"]), classes: new Set() }
			]
		])
	],
	[
		"background",
		new Map([
			[
				"none",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"conic-gradient()",
						"cross-fade()",
						"element()",
						"hsl()",
						"hsla()",
						"hwb()",
						"image()",
						"image-set()",
						"lab()",
						"lch()",
						"light-dark()",
						"linear-gradient()",
						"none",
						"oklab()",
						"oklch()",
						"paint()",
						"radial-gradient()",
						"repeating-conic-gradient()",
						"repeating-linear-gradient()",
						"repeating-radial-gradient()",
						"rgb()",
						"rgba()",
						"src()",
						"type()",
						"url()"
					]),
					classes: new Set()
				}
			],
			[
				"repeat",
				{
					spellings: new Set([
						"no-repeat",
						"repeat",
						"repeat-x",
						"repeat-y",
						"round",
						"space"
					]),
					classes: new Set()
				}
			],
			[
				"scroll",
				{ spellings: new Set(["fixed", "local", "scroll"]), classes: new Set() }
			],
			[
				"transparent",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			]
		])
	],
	[
		"border",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"border-bottom",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"border-image",
		new Map([
			[
				"none",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"conic-gradient()",
						"cross-fade()",
						"element()",
						"hsl()",
						"hsla()",
						"hwb()",
						"image()",
						"image-set()",
						"lab()",
						"lch()",
						"light-dark()",
						"linear-gradient()",
						"none",
						"oklab()",
						"oklch()",
						"paint()",
						"radial-gradient()",
						"repeating-conic-gradient()",
						"repeating-linear-gradient()",
						"repeating-radial-gradient()",
						"rgb()",
						"rgba()",
						"src()",
						"type()",
						"url()"
					]),
					classes: new Set()
				}
			],
			[
				"stretch",
				{
					spellings: new Set(["repeat", "round", "space", "stretch"]),
					classes: new Set()
				}
			]
		])
	],
	[
		"border-left",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"border-right",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"border-top",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"column-rule",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"dashed",
						"dotted",
						"double",
						"groove",
						"hidden",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"flex-flow",
		new Map([
			[
				"nowrap",
				{
					spellings: new Set(["balance", "nowrap", "wrap", "wrap-reverse"]),
					classes: new Set()
				}
			],
			[
				"row",
				{
					spellings: new Set([
						"column",
						"column-reverse",
						"row",
						"row-reverse"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"list-style",
		new Map([
			[
				"outside",
				{ spellings: new Set(["inside", "outside"]), classes: new Set() }
			]
		])
	],
	[
		"mask",
		new Map([
			[
				"add",
				{
					spellings: new Set(["add", "exclude", "intersect", "subtract"]),
					classes: new Set()
				}
			],
			[
				"match-source",
				{
					spellings: new Set(["alpha", "luminance", "match-source"]),
					classes: new Set()
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"conic-gradient()",
						"cross-fade()",
						"element()",
						"hsl()",
						"hsla()",
						"hwb()",
						"image()",
						"image-set()",
						"lab()",
						"lch()",
						"light-dark()",
						"linear-gradient()",
						"none",
						"oklab()",
						"oklch()",
						"paint()",
						"radial-gradient()",
						"repeating-conic-gradient()",
						"repeating-linear-gradient()",
						"repeating-radial-gradient()",
						"rgb()",
						"rgba()",
						"src()",
						"type()",
						"url()"
					]),
					classes: new Set()
				}
			],
			[
				"repeat",
				{
					spellings: new Set([
						"no-repeat",
						"repeat",
						"repeat-x",
						"repeat-y",
						"round",
						"space"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"mask-border",
		new Map([
			[
				"alpha",
				{ spellings: new Set(["alpha", "luminance"]), classes: new Set() }
			],
			[
				"none",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"conic-gradient()",
						"cross-fade()",
						"element()",
						"hsl()",
						"hsla()",
						"hwb()",
						"image()",
						"image-set()",
						"lab()",
						"lch()",
						"light-dark()",
						"linear-gradient()",
						"none",
						"oklab()",
						"oklch()",
						"paint()",
						"radial-gradient()",
						"repeating-conic-gradient()",
						"repeating-linear-gradient()",
						"repeating-radial-gradient()",
						"rgb()",
						"rgba()",
						"src()",
						"type()",
						"url()"
					]),
					classes: new Set()
				}
			],
			[
				"stretch",
				{
					spellings: new Set(["repeat", "round", "space", "stretch"]),
					classes: new Set()
				}
			]
		])
	],
	[
		"outline",
		new Map([
			[
				"medium",
				{
					spellings: new Set(["medium", "thick", "thin"]),
					classes: new Set(["length"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"auto",
						"dashed",
						"dotted",
						"double",
						"groove",
						"inset",
						"none",
						"outset",
						"ridge",
						"solid"
					]),
					classes: new Set()
				}
			]
		])
	],
	[
		"text-decoration",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"blink",
						"grammar-error",
						"line-through",
						"none",
						"overline",
						"spelling-error",
						"underline"
					]),
					classes: new Set()
				}
			],
			[
				"solid",
				{
					spellings: new Set(["dashed", "dotted", "double", "solid", "wavy"]),
					classes: new Set()
				}
			]
		])
	],
	[
		"text-emphasis",
		new Map([
			[
				"currentcolor",
				{
					spellings: new Set([
						"color()",
						"color-mix()",
						"hsl()",
						"hsla()",
						"hwb()",
						"lab()",
						"lch()",
						"light-dark()",
						"oklab()",
						"oklch()",
						"rgb()",
						"rgba()"
					]),
					classes: new Set(["color"])
				}
			],
			[
				"none",
				{
					spellings: new Set([
						"circle",
						"dot",
						"double-circle",
						"filled",
						"none",
						"open",
						"sesame",
						"triangle"
					]),
					classes: new Set(["string"])
				}
			]
		])
	],
	[
		"transition",
		new Map([
			[
				"all",
				{
					spellings: new Set(["all", "none"]),
					classes: new Set(["custom-ident"])
				}
			],
			[
				"ease",
				{
					spellings: new Set([
						"cubic-bezier()",
						"ease",
						"ease-in",
						"ease-in-out",
						"ease-out",
						"linear",
						"linear()",
						"step-end",
						"step-start",
						"steps()"
					]),
					classes: new Set()
				}
			],
			[
				"normal",
				{ spellings: new Set(["allow-discrete", "normal"]), classes: new Set() }
			]
		])
	]
]);

// Each `font-stretch` keyword -> the percentage it names, which is the same
// value in fewer bytes.
const FONT_STRETCH_PERCENTAGES = new Map([
	["ultra-condensed", "50%"],
	["extra-condensed", "62.5%"],
	["condensed", "75%"],
	["semi-condensed", "87.5%"],
	["normal", "100%"],
	["semi-expanded", "112.5%"],
	["expanded", "125%"],
	["extra-expanded", "150%"],
	["ultra-expanded", "200%"]
]);

// Each `<filter-function>` with an optional argument -> the amount an omitted
// one means, which is what writing that amount already says.
const FILTER_FUNCTION_OMITTED = new Map([
	["blur", "0"],
	["brightness", "1"],
	["contrast", "1"],
	["grayscale", "1"],
	["hue-rotate", "0"],
	["invert", "1"],
	["opacity", "1"],
	["saturate", "1"],
	["sepia", "1"]
]);

// The generic font families: an unquoted one of these names the generic rather
// than a family called that, so a quoted family spelled like one keeps its quotes.
const GENERIC_FONT_FAMILIES = new Set([
	"cursive",
	"emoji",
	"fangsong",
	"fantasy",
	"math",
	"monospace",
	"sans-serif",
	"serif",
	"system-ui",
	"ui-monospace",
	"ui-rounded",
	"ui-sans-serif",
	"ui-serif"
]);

// The `font` size slot's keywords: `<absolute-size>` and `<relative-size>`.
const FONT_SIZE_KEYWORDS = new Set([
	"large",
	"larger",
	"medium",
	"small",
	"smaller",
	"x-large",
	"x-small",
	"xx-large",
	"xx-small",
	"xxx-large"
]);

// The `<easing-function>` spellings that are a keyword rather than a function.
const EASING_KEYWORDS = new Set([
	"ease",
	"ease-in",
	"ease-in-out",
	"ease-out",
	"linear",
	"step-end",
	"step-start"
]);

// What `transition-behavior` accepts, the slot of a `transition` that is
// neither a time, an easing nor the property name.
const TRANSITION_BEHAVIORS = new Set(["allow-discrete", "normal"]);

// The linear gradients, whose flow a `<side-or-corner>` or angle states.
const LINEAR_GRADIENTS = new Set([
	"linear-gradient",
	"repeating-linear-gradient"
]);

// A size whose omitted second value is `auto`, not the first repeated.
const AUTO_SECOND_VALUE_PROPERTIES = new Set(["background-size", "mask-size"]);

// The direction each unprefixed linear gradient already starts from. A
// `-webkit-` one measures its angle the other way, so it keeps what it says.
const DEFAULT_GRADIENT_DIRECTIONS = new Set(["to bottom", "180deg", "0.5turn"]);

// A name CSS matches ASCII case-insensitively but spells with a capital ->
// that spelling, so lowercasing a name normalizes its case without printing
// `translatey` or `1q` for what everything else writes `translateY` and `1Q`.
const CANONICAL_NAMES = new Map([
	["hz", "Hz"],
	["khz", "kHz"],
	["q", "Q"],
	["rotatex", "rotateX"],
	["rotatey", "rotateY"],
	["rotatez", "rotateZ"],
	["scalex", "scaleX"],
	["scaley", "scaleY"],
	["scalez", "scaleZ"],
	["skewx", "skewX"],
	["skewy", "skewY"],
	["translatex", "translateX"],
	["translatey", "translateY"],
	["translatez", "translateZ"]
]);

// A transform along x only -> the pair spelling whose second component is the
// 0 the one-axis call already means.
const X_AXIS_TRANSFORMS = new Map([
	["translatex", "translate"],
	["skewx", "skew"]
]);

// Each gradient function -> the positions its last color stop already means, so
// writing one of them there says nothing (CSS Images 3 §3.4.3).
const GRADIENT_LAST_POSITIONS = new Map([
	["conic-gradient", new Set(["100%", "360deg", "1turn"])],
	["linear-gradient", new Set(["100%"])],
	["radial-gradient", new Set(["100%"])],
	["repeating-conic-gradient", new Set(["100%", "360deg", "1turn"])],
	["repeating-linear-gradient", new Set(["100%"])],
	["repeating-radial-gradient", new Set(["100%"])]
]);

// The properties whose value is a position, where each edge keyword names the
// percentage that axis resolves to.
const POSITION_PROPERTIES = new Set([
	"-webkit-mask-position",
	"background-position",
	"mask-position",
	"object-position",
	"offset-anchor",
	"offset-position",
	"perspective-origin",
	"scroll-snap-coordinate",
	"scroll-snap-destination",
	"transform-origin"
]);

// Each keyword one axis of a `<position>` accepts -> the percentage it resolves
// to. A keyword both maps carry (`center`) names whichever axis is still free,
// and every free axis is `50%` anyway.
const POSITION_X_KEYWORDS = new Map([
	["center", "50%"],
	["left", "0%"],
	["right", "100%"]
]);

const POSITION_Y_KEYWORDS = new Map([
	["bottom", "100%"],
	["center", "50%"],
	["top", "0%"]
]);

// The keywords one `<repeat-style>` axis can be: a pair only collapses where
// both halves are one of these.
const REPEAT_STYLE_KEYWORDS = new Set([
	"no-repeat",
	"repeat",
	"round",
	"space"
]);

// The properties whose value is a `<repeat-style>`, where one value already
// says what two equal ones do.
const REPEAT_STYLE_PROPERTIES = new Set([
	"-webkit-mask",
	"-webkit-mask-repeat",
	"background",
	"background-repeat",
	"mask",
	"mask-repeat"
]);

// Each property whose initial value is a keyword shorter than `initial` -> that
// keyword, which is the same declaration written in fewer bytes.
const INITIAL_VALUE_KEYWORDS = new Map([
	["-moz-binding", "none"],
	["-moz-border-bottom-colors", "none"],
	["-moz-border-left-colors", "none"],
	["-moz-border-right-colors", "none"],
	["-moz-border-top-colors", "none"],
	["-moz-context-properties", "none"],
	["-moz-orient", "inline"],
	["-moz-text-blink", "none"],
	["-moz-user-focus", "none"],
	["-moz-user-input", "auto"],
	["-moz-window-dragging", "drag"],
	["-ms-accelerator", "false"],
	["-ms-block-progression", "tb"],
	["-ms-content-zoom-chaining", "none"],
	["-ms-content-zoom-snap-type", "none"],
	["-ms-flow-from", "none"],
	["-ms-flow-into", "none"],
	["-ms-grid-columns", "none"],
	["-ms-grid-rows", "none"],
	["-ms-high-contrast-adjust", "auto"],
	["-ms-hyphenate-limit-chars", "auto"],
	["-ms-ime-align", "auto"],
	["-ms-overflow-style", "auto"],
	["-ms-scroll-limit-x-max", "auto"],
	["-ms-scroll-limit-y-max", "auto"],
	["-ms-scroll-rails", "railed"],
	["-ms-scroll-snap-type", "none"],
	["-ms-scroll-translation", "none"],
	["-ms-text-autospace", "none"],
	["-ms-user-select", "text"],
	["-ms-wrap-flow", "auto"],
	["-ms-wrap-through", "wrap"],
	["-webkit-border-after-style", "none"],
	["-webkit-border-before-style", "none"],
	["-webkit-border-end-style", "none"],
	["-webkit-border-start-style", "none"],
	["-webkit-line-clamp", "none"],
	["-webkit-mask-attachment", "scroll"],
	["-webkit-mask-clip", "border"],
	["-webkit-mask-image", "none"],
	["-webkit-mask-repeat", "repeat"],
	["-webkit-mask-repeat-x", "repeat"],
	["-webkit-mask-repeat-y", "repeat"],
	["-webkit-overflow-scrolling", "auto"],
	["-webkit-user-select", "auto"],
	["accent-color", "auto"],
	["align-content", "normal"],
	["align-items", "normal"],
	["align-self", "auto"],
	["align-tracks", "normal"],
	["anchor-name", "none"],
	["anchor-scope", "none"],
	["animation-direction", "normal"],
	["animation-fill-mode", "none"],
	["animation-name", "none"],
	["animation-range-end", "normal"],
	["animation-range-start", "normal"],
	["animation-timeline", "auto"],
	["animation-timing-function", "ease"],
	["animation-trigger", "none"],
	["appearance", "none"],
	["aspect-ratio", "auto"],
	["backdrop-filter", "none"],
	["background-attachment", "scroll"],
	["background-blend-mode", "normal"],
	["background-image", "none"],
	["background-repeat", "repeat"],
	["baseline-source", "auto"],
	["block-size", "auto"],
	["border-block-end-style", "none"],
	["border-block-start-style", "none"],
	["border-bottom-style", "none"],
	["border-image-source", "none"],
	["border-inline-end-style", "none"],
	["border-inline-start-style", "none"],
	["border-left-style", "none"],
	["border-right-style", "none"],
	["border-shape", "none"],
	["border-top-style", "none"],
	["bottom", "auto"],
	["box-decoration-break", "slice"],
	["box-direction", "normal"],
	["box-lines", "single"],
	["box-pack", "start"],
	["box-shadow", "none"],
	["break-after", "auto"],
	["break-before", "auto"],
	["break-inside", "auto"],
	["caption-side", "top"],
	["caret-animation", "auto"],
	["caret-color", "auto"],
	["caret-shape", "auto"],
	["clear", "none"],
	["clip", "auto"],
	["clip-path", "none"],
	["color-scheme", "normal"],
	["column-count", "auto"],
	["column-gap", "normal"],
	["column-height", "auto"],
	["column-rule-style", "none"],
	["column-span", "none"],
	["column-width", "auto"],
	["column-wrap", "auto"],
	["contain", "none"],
	["contain-intrinsic-block-size", "none"],
	["contain-intrinsic-height", "none"],
	["contain-intrinsic-inline-size", "none"],
	["contain-intrinsic-width", "none"],
	["container-name", "none"],
	["container-type", "normal"],
	["content", "normal"],
	["corner-bottom-left-shape", "round"],
	["corner-bottom-right-shape", "round"],
	["corner-end-end-shape", "round"],
	["corner-end-start-shape", "round"],
	["corner-start-end-shape", "round"],
	["corner-start-start-shape", "round"],
	["corner-top-left-shape", "round"],
	["corner-top-right-shape", "round"],
	["counter-increment", "none"],
	["counter-reset", "none"],
	["counter-set", "none"],
	["cursor", "auto"],
	["d", "none"],
	["direction", "ltr"],
	["display", "inline"],
	["dominant-baseline", "auto"],
	["empty-cells", "show"],
	["field-sizing", "fixed"],
	["filter", "none"],
	["flex-basis", "auto"],
	["flex-direction", "row"],
	["flex-wrap", "nowrap"],
	["float", "none"],
	["font-feature-settings", "normal"],
	["font-kerning", "auto"],
	["font-language-override", "normal"],
	["font-optical-sizing", "auto"],
	["font-palette", "normal"],
	["font-size-adjust", "none"],
	["font-smooth", "auto"],
	["font-stretch", "normal"],
	["font-style", "normal"],
	["font-synthesis-position", "none"],
	["font-synthesis-small-caps", "auto"],
	["font-synthesis-style", "auto"],
	["font-synthesis-weight", "auto"],
	["font-variant", "normal"],
	["font-variant-alternates", "normal"],
	["font-variant-caps", "normal"],
	["font-variant-east-asian", "normal"],
	["font-variant-emoji", "normal"],
	["font-variant-ligatures", "normal"],
	["font-variant-numeric", "normal"],
	["font-variant-position", "normal"],
	["font-variation-settings", "normal"],
	["font-weight", "normal"],
	["font-width", "normal"],
	["forced-color-adjust", "auto"],
	["frame-sizing", "auto"],
	["grid-auto-columns", "auto"],
	["grid-auto-flow", "row"],
	["grid-auto-rows", "auto"],
	["grid-column-end", "auto"],
	["grid-column-start", "auto"],
	["grid-row-end", "auto"],
	["grid-row-start", "auto"],
	["grid-template-areas", "none"],
	["grid-template-columns", "none"],
	["grid-template-rows", "none"],
	["hanging-punctuation", "none"],
	["height", "auto"],
	["hyphenate-character", "auto"],
	["hyphenate-limit-chars", "auto"],
	["hyphens", "manual"],
	["image-rendering", "auto"],
	["ime-mode", "auto"],
	["initial-letter", "normal"],
	["initial-letter-align", "auto"],
	["inline-size", "auto"],
	["inset-block-end", "auto"],
	["inset-block-start", "auto"],
	["inset-inline-end", "auto"],
	["inset-inline-start", "auto"],
	["interactivity", "auto"],
	["interest-delay-end", "normal"],
	["interest-delay-start", "normal"],
	["isolation", "auto"],
	["justify-content", "normal"],
	["justify-items", "legacy"],
	["justify-self", "auto"],
	["justify-tracks", "normal"],
	["left", "auto"],
	["letter-spacing", "normal"],
	["line-break", "auto"],
	["line-clamp", "none"],
	["line-height", "normal"],
	["link-parameters", "none"],
	["list-style-image", "none"],
	["margin-trim", "none"],
	["marker-end", "none"],
	["marker-mid", "none"],
	["marker-start", "none"],
	["mask-border-mode", "alpha"],
	["mask-border-source", "none"],
	["mask-border-width", "auto"],
	["mask-composite", "add"],
	["mask-image", "none"],
	["mask-repeat", "repeat"],
	["mask-size", "auto"],
	["masonry-auto-flow", "pack"],
	["math-shift", "normal"],
	["math-style", "normal"],
	["max-block-size", "none"],
	["max-height", "none"],
	["max-inline-size", "none"],
	["max-lines", "none"],
	["max-width", "none"],
	["min-height", "auto"],
	["min-width", "auto"],
	["mix-blend-mode", "normal"],
	["object-fit", "fill"],
	["object-view-box", "none"],
	["offset-anchor", "auto"],
	["offset-path", "none"],
	["offset-position", "normal"],
	["offset-rotate", "auto"],
	["outline-style", "none"],
	["overflow-anchor", "auto"],
	["overflow-wrap", "normal"],
	["overlay", "none"],
	["overscroll-behavior", "auto"],
	["overscroll-behavior-block", "auto"],
	["overscroll-behavior-inline", "auto"],
	["overscroll-behavior-x", "auto"],
	["overscroll-behavior-y", "auto"],
	["page", "auto"],
	["page-break-after", "auto"],
	["page-break-before", "auto"],
	["page-break-inside", "auto"],
	["paint-order", "normal"],
	["path-length", "none"],
	["perspective", "none"],
	["pointer-events", "auto"],
	["position", "static"],
	["position-anchor", "normal"],
	["position-area", "none"],
	["position-try-fallbacks", "none"],
	["position-try-order", "normal"],
	["reading-flow", "normal"],
	["resize", "none"],
	["right", "auto"],
	["rotate", "none"],
	["row-gap", "normal"],
	["ruby-overhang", "auto"],
	["rx", "auto"],
	["ry", "auto"],
	["scale", "none"],
	["scroll-behavior", "auto"],
	["scroll-initial-target", "none"],
	["scroll-marker-group", "none"],
	["scroll-padding-block-end", "auto"],
	["scroll-padding-block-start", "auto"],
	["scroll-padding-bottom", "auto"],
	["scroll-padding-inline-end", "auto"],
	["scroll-padding-inline-start", "auto"],
	["scroll-padding-left", "auto"],
	["scroll-padding-right", "auto"],
	["scroll-padding-top", "auto"],
	["scroll-snap-align", "none"],
	["scroll-snap-coordinate", "none"],
	["scroll-snap-points-x", "none"],
	["scroll-snap-points-y", "none"],
	["scroll-snap-stop", "normal"],
	["scroll-snap-type", "none"],
	["scroll-snap-type-x", "none"],
	["scroll-snap-type-y", "none"],
	["scroll-target-group", "none"],
	["scroll-timeline-axis", "block"],
	["scroll-timeline-name", "none"],
	["scrollbar-color", "auto"],
	["scrollbar-gutter", "auto"],
	["scrollbar-width", "auto"],
	["shape-outside", "none"],
	["shape-rendering", "auto"],
	["stroke-dasharray", "none"],
	["stroke-linecap", "butt"],
	["stroke-linejoin", "miter"],
	["table-layout", "auto"],
	["text-align", "start"],
	["text-align-last", "auto"],
	["text-anchor", "start"],
	["text-box", "normal"],
	["text-box-edge", "auto"],
	["text-box-trim", "none"],
	["text-combine-upright", "none"],
	["text-decoration-line", "none"],
	["text-decoration-skip-ink", "auto"],
	["text-decoration-style", "solid"],
	["text-decoration-thickness", "auto"],
	["text-emphasis-style", "none"],
	["text-fit", "none"],
	["text-justify", "auto"],
	["text-orientation", "mixed"],
	["text-overflow", "clip"],
	["text-rendering", "auto"],
	["text-shadow", "none"],
	["text-spacing-trim", "normal"],
	["text-transform", "none"],
	["text-underline-offset", "auto"],
	["text-underline-position", "auto"],
	["text-wrap", "wrap"],
	["text-wrap-mode", "wrap"],
	["text-wrap-style", "auto"],
	["timeline-scope", "none"],
	["timeline-trigger-activation-range-end", "normal"],
	["timeline-trigger-activation-range-start", "normal"],
	["timeline-trigger-active-range-end", "auto"],
	["timeline-trigger-active-range-start", "auto"],
	["timeline-trigger-name", "none"],
	["timeline-trigger-source", "auto"],
	["top", "auto"],
	["touch-action", "auto"],
	["transform", "none"],
	["transform-style", "flat"],
	["transition-behavior", "normal"],
	["transition-property", "all"],
	["transition-timing-function", "ease"],
	["translate", "none"],
	["trigger-scope", "none"],
	["unicode-bidi", "normal"],
	["user-select", "auto"],
	["vector-effect", "none"],
	["view-timeline-axis", "block"],
	["view-timeline-inset", "auto"],
	["view-timeline-name", "none"],
	["view-transition-class", "none"],
	["view-transition-name", "none"],
	["view-transition-scope", "none"],
	["white-space", "normal"],
	["width", "auto"],
	["will-change", "auto"],
	["word-break", "normal"],
	["word-spacing", "normal"],
	["word-wrap", "normal"],
	["z-index", "auto"]
]);

// Each named color a shorter spelling beats -> that spelling, so a name written
// where a color is unambiguous prints as the shortest text for the same value.
const COLOR_NAME_TO_SHORTEST = new Map([
	["aliceblue", "#f0f8ff"],
	["antiquewhite", "#faebd7"],
	["aquamarine", "#7fffd4"],
	["black", "#000"],
	["blanchedalmond", "#ffebcd"],
	["blueviolet", "#8a2be2"],
	["burlywood", "#deb887"],
	["cadetblue", "#5f9ea0"],
	["chartreuse", "#7fff00"],
	["chocolate", "#d2691e"],
	["cornflowerblue", "#6495ed"],
	["cornsilk", "#fff8dc"],
	["darkblue", "#00008b"],
	["darkcyan", "#008b8b"],
	["darkgoldenrod", "#b8860b"],
	["darkgray", "#a9a9a9"],
	["darkgreen", "#006400"],
	["darkgrey", "#a9a9a9"],
	["darkkhaki", "#bdb76b"],
	["darkmagenta", "#8b008b"],
	["darkolivegreen", "#556b2f"],
	["darkorange", "#ff8c00"],
	["darkorchid", "#9932cc"],
	["darksalmon", "#e9967a"],
	["darkseagreen", "#8fbc8f"],
	["darkslateblue", "#483d8b"],
	["darkslategray", "#2f4f4f"],
	["darkslategrey", "#2f4f4f"],
	["darkturquoise", "#00ced1"],
	["darkviolet", "#9400d3"],
	["deeppink", "#ff1493"],
	["deepskyblue", "#00bfff"],
	["dodgerblue", "#1e90ff"],
	["firebrick", "#b22222"],
	["floralwhite", "#fffaf0"],
	["forestgreen", "#228b22"],
	["fuchsia", "#f0f"],
	["gainsboro", "#dcdcdc"],
	["ghostwhite", "#f8f8ff"],
	["goldenrod", "#daa520"],
	["greenyellow", "#adff2f"],
	["honeydew", "#f0fff0"],
	["indianred", "#cd5c5c"],
	["lavender", "#e6e6fa"],
	["lavenderblush", "#fff0f5"],
	["lawngreen", "#7cfc00"],
	["lemonchiffon", "#fffacd"],
	["lightblue", "#add8e6"],
	["lightcoral", "#f08080"],
	["lightcyan", "#e0ffff"],
	["lightgoldenrodyellow", "#fafad2"],
	["lightgray", "#d3d3d3"],
	["lightgreen", "#90ee90"],
	["lightgrey", "#d3d3d3"],
	["lightpink", "#ffb6c1"],
	["lightsalmon", "#ffa07a"],
	["lightseagreen", "#20b2aa"],
	["lightskyblue", "#87cefa"],
	["lightslategray", "#789"],
	["lightslategrey", "#789"],
	["lightsteelblue", "#b0c4de"],
	["lightyellow", "#ffffe0"],
	["limegreen", "#32cd32"],
	["magenta", "#f0f"],
	["mediumaquamarine", "#66cdaa"],
	["mediumblue", "#0000cd"],
	["mediumorchid", "#ba55d3"],
	["mediumpurple", "#9370db"],
	["mediumseagreen", "#3cb371"],
	["mediumslateblue", "#7b68ee"],
	["mediumspringgreen", "#00fa9a"],
	["mediumturquoise", "#48d1cc"],
	["mediumvioletred", "#c71585"],
	["midnightblue", "#191970"],
	["mintcream", "#f5fffa"],
	["mistyrose", "#ffe4e1"],
	["moccasin", "#ffe4b5"],
	["navajowhite", "#ffdead"],
	["olivedrab", "#6b8e23"],
	["orangered", "#ff4500"],
	["palegoldenrod", "#eee8aa"],
	["palegreen", "#98fb98"],
	["paleturquoise", "#afeeee"],
	["palevioletred", "#db7093"],
	["papayawhip", "#ffefd5"],
	["peachpuff", "#ffdab9"],
	["powderblue", "#b0e0e6"],
	["rebeccapurple", "#639"],
	["rosybrown", "#bc8f8f"],
	["royalblue", "#4169e1"],
	["saddlebrown", "#8b4513"],
	["sandybrown", "#f4a460"],
	["seagreen", "#2e8b57"],
	["seashell", "#fff5ee"],
	["slateblue", "#6a5acd"],
	["slategray", "#708090"],
	["slategrey", "#708090"],
	["springgreen", "#00ff7f"],
	["steelblue", "#4682b4"],
	["turquoise", "#40e0d0"],
	["white", "#fff"],
	["whitesmoke", "#f5f5f5"],
	["yellow", "#ff0"],
	["yellowgreen", "#9acd32"]
]);

// The functions whose argument is a selector, so a `>` / `+` / `~` inside one
// is a combinator and needs no whitespace around it.
const SELECTOR_FUNCTIONS = new Set([
	"cue",
	"element",
	"has",
	"host",
	"host-context",
	"is",
	"not",
	"nth-child",
	"nth-last-child",
	"selector",
	"slotted",
	"where"
]);

// The functions every argument of which is an angle, so a zero one needs no
// unit wherever it stands.
const ZERO_ANGLE_FUNCTIONS = new Set([
	"hue-rotate",
	"rotate",
	"rotatex",
	"rotatey",
	"rotatez",
	"skew",
	"skewx",
	"skewy"
]);

// CSS Values 4's math functions: everything inside one is a math expression, so
// `*` and `/` there are operators, and the whitespace around them carries nothing.
const MATH_FUNCTIONS = new Set([
	"abs",
	"acos",
	"asin",
	"atan",
	"atan2",
	"calc",
	"calc-size",
	"clamp",
	"cos",
	"exp",
	"hypot",
	"log",
	"max",
	"min",
	"mod",
	"pow",
	"rem",
	"round",
	"sign",
	"sin",
	"sqrt",
	"tan"
]);

// WHY: How many `<calc-sum>` arguments each of them takes, off its own grammar. A
// function whose arguments are not all expressions (`round()` leads with a
// strategy, `calc-size()` with a basis) is absent, and absence is what the
// folding reads as "leave this one alone".
/** @type {Map<string, [number, number]>} */
const MATH_FUNCTION_ARITY = new Map([
	["abs", [1, 1]],
	["acos", [1, 1]],
	["asin", [1, 1]],
	["atan", [1, 1]],
	["atan2", [2, 2]],
	["calc", [1, 1]],
	["clamp", [3, 3]],
	["cos", [1, 1]],
	["exp", [1, 1]],
	["hypot", [1, Infinity]],
	["log", [1, 2]],
	["max", [1, Infinity]],
	["min", [1, Infinity]],
	["mod", [2, 2]],
	["pow", [2, 2]],
	["rem", [2, 2]],
	["round", [2, 2]],
	["sign", [1, 1]],
	["sin", [1, 1]],
	["sqrt", [1, 1]],
	["tan", [1, 1]]
]);

// The optional keyword a math function may lead with, for the ones whose
// grammar offers a choice of them (`round( <rounding-strategy>?, … )`). Read
// off that production, so a strategy joining it needs no edit here.
/** @type {Map<string, string[]>} */
const MATH_FUNCTION_KEYWORDS = new Map([
	["round", ["down", "nearest", "to-zero", "up"]]
]);

// Where a function the fold cannot read as a whole still takes a `<calc-sum>`,
// so that argument reduces on its own. Keyed by name to the argument positions.
/** @type {Map<string, number[]>} */
const MATH_FUNCTION_SUM_ARGUMENTS = new Map([["calc-size", [1]]]);

// A CSS-wide keyword is only valid as the whole value, so a box repeating one is
// invalid and already discarded — collapsing it would switch the declaration on.
const CSS_WIDE_KEYWORDS = new Set([
	"inherit",
	"initial",
	"revert",
	"revert-layer",
	"unset"
]);

// `<easing-function>` argument lists that are exactly a shorter keyword, keyed
// by the arguments as `Number` prints them.
const CUBIC_BEZIER_KEYWORDS = new Map([
	["0.25,0.1,0.25,1", "ease"],
	["0,0,1,1", "linear"],
	["0.42,0,1,1", "ease-in"],
	["0,0,0.58,1", "ease-out"],
	["0.42,0,0.58,1", "ease-in-out"]
]);

// The two `flex` values CSS Flexbox 7.1.1 gives a keyword spelling.
const FLEX_KEYWORDS = new Map([
	["0 0 auto", "none"],
	["1 1 auto", "auto"]
]);

// The `font-weight` keywords CSS Fonts 4 §2.2 defines as a number, which is what
// `getComputedStyle().fontWeight` reports either way.
const FONT_WEIGHT_NUMBERS = new Map([
	["normal", "400"],
	["bold", "700"]
]);

// Selectors 4 §3.3: the pseudo-elements engines must also accept with one colon,
// so their second colon carries nothing.
const LEGACY_PSEUDO_ELEMENTS = new Set([
	"before",
	"after",
	"first-line",
	"first-letter"
]);

// What may follow the `*` a compound selector implies: another simple selector
// in the same compound. A separator between them would be a descendant
// combinator instead, and `|` makes the `*` a namespace's, not a redundant one.
const COMPOUND_CONTINUATIONS = new Set([":", ".", "#", "["]);

// The pseudo-classes selecting a featureless element, which matches no type or
// universal selector — so an implied `*` before one is what makes the selector
// match nothing, and dropping it would bring the rule to life.
const FEATURELESS_PSEUDO_CLASSES = new Set(["host", "host-context"]);

// The properties whose zero length keeps its unit: those whose own grammar
// offers a bare number beside the length, so the unit is what picks the
// reading, and the two an engine reads its own way.
const ZERO_UNIT_KEEPING_PROPERTIES = new Set([
	"border-image",
	"border-image-outset",
	"border-image-width",
	"columns",
	"flex",
	"flex-basis",
	"font",
	"line-height",
	"mask-border",
	"mask-border-outset",
	"mask-border-width",
	"overflow-clip-margin",
	"stroke-dasharray",
	"stroke-dashoffset",
	"stroke-width",
	"tab-size"
]);

// The properties an engine takes no `calc()` in, so one stays as written
// rather than folding to the value it equals.
const CALC_REJECTING_PROPERTIES = new Set(["overflow-clip-margin"]);

// The range a `calc()` is clamped to where the literal outside it is invalid,
// keyed by property: `[unit, min, max]`.
/** @type {Map<string, [string, number, number]>} */
const CLAMPED_VALUE_RANGES = new Map([["font-style", ["deg", -90, 90]]]);

// At-rules whose empty block is inert, so dropping it changes nothing.
const DROPPABLE_WHEN_EMPTY_AT_RULES = new Set([
	"media",
	"supports",
	"container",
	"starting-style"
]);

// At-rules whose block holds rules and whose prelude states a condition, so two
// adjacent blocks with the same prelude are the one block they resolve to.
const MERGEABLE_AT_RULES = new Set([
	"container",
	"document",
	"layer",
	"media",
	"scope",
	"starting-style",
	"supports"
]);

// The math functions whose result steps with their arguments, so a value inside
// one keeps the unit and the digits it was written with.
const STEPPED_FUNCTIONS = new Set(["mod", "rem", "round"]);

// The units fixed against each other (CSS Values 4 §6.2, §8), as
// `unit -> [group, how many of the group's base unit one is]`. Two units in the
// same group convert into each other exactly when the ratio is binary-exact.
/** @type {Map<string, [string, number]>} */
const ABSOLUTE_UNIT_SCALE = new Map([
	["px", ["length", 381]],
	["pc", ["length", 6096]],
	["pt", ["length", 508]],
	["in", ["length", 36576]],
	["cm", ["length", 14400]],
	["mm", ["length", 1440]],
	["q", ["length", 360]],
	["ms", ["time", 1]],
	["s", ["time", 1000]]
]);

// Each convertible group's reference unit, as `group -> [unit, scale]`. A sum
// counted in the group's base unit divides by the scale to get back to a unit
// that can be written down.
/** @type {Map<string, [string, number]>} */
const UNIT_GROUP_BASE = new Map([
	["length", ["px", 381]],
	["time", ["ms", 1]]
]);

// The units a conversion may emit. Every one is CSS 2.1's, so rewriting into it
// cannot outrun what an engine reading the stylesheet already parses.
const UNIT_CONVERSION_TARGETS = new Set([
	"px",
	"pc",
	"pt",
	"in",
	"cm",
	"mm",
	"ms",
	"s"
]);

// WHY: How each predefined color space is read back to sRGB: the matrix taking its
// linear-light components to linear-light sRGB, and the function that reads one
// stored component back to linear light. Both derived from the primaries,
// white point and transfer function CSS Color 4 §10 states.
/**
 * A component already stored linearly.
 * @param {number} c the stored component
 * @returns {number} the same component
 */
const linearTransfer = (c) => c;

/**
 * The sRGB transfer function, which Display P3 shares.
 * @param {number} c the stored component
 * @returns {number} the linear-light component
 */
const srgbTransfer = (c) => {
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs <= 0.04045 ? c / 12.92 : sign * ((abs + 0.055) / 1.055) ** 2.4;
};

/**
 * Adobe RGB (1998)'s pure gamma of 563/256.
 * @param {number} c the stored component
 * @returns {number} the linear-light component
 */
const a98Transfer = (c) => {
	const sign = c < 0 ? -1 : 1;
	return sign * Math.abs(c) ** (563 / 256);
};

/**
 * ProPhoto RGB's gamma of 1.8, with the linear segment below 16/512.
 * @param {number} c the stored component
 * @returns {number} the linear-light component
 */
const prophotoTransfer = (c) => {
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs <= 16 / 512 ? c / 16 : sign * abs ** 1.8;
};

/**
 * Rec. 2020's transfer function, with the constants ITU-R BT.2020 states.
 * @param {number} c the stored component
 * @returns {number} the linear-light component
 */
const rec2020Transfer = (c) => {
	const alpha = 1.09929682680944;
	const beta = 0.018053968510807;
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs < beta * 4.5
		? c / 4.5
		: sign * ((abs + alpha - 1) / alpha) ** (1 / 0.45);
};

// What a color read in one space passes through on its way to a byte: nothing at
// all, the sRGB transfer, or a matrix as well. `lib/css/syntax.js` reads how far
// its answer can sit from an engine's from this.
const ENCODED_ALREADY = 0;
const THROUGH_TRANSFER = 1;
const THROUGH_MATRIX = 2;
const ENGINE_TRANSFER_DIFFERS = 3;

/** @type {Map<string, { toSrgb: number[], transfer: (c: number) => number, conversion: number }>} */
const PREDEFINED_COLOR_SPACES = new Map([
	[
		"srgb",
		{
			toSrgb: [1, 0, 0, 0, 1, 0, 0, 0, 1],
			transfer: srgbTransfer,
			conversion: 0
		}
	],
	[
		"srgb-linear",
		{
			toSrgb: [1, 0, 0, 0, 1, 0, 0, 0, 1],
			transfer: linearTransfer,
			conversion: 1
		}
	],
	[
		"display-p3",
		{
			toSrgb: [
				1.2249401762805596, -0.22494017628055984, 0, -0.04205695470968812,
				1.042056954709688, -2.0816681711721685e-17, -0.019637554590334425,
				-0.0786360455506318, 1.0982736001409665
			],
			transfer: srgbTransfer,
			conversion: 2
		}
	],
	[
		"a98-rgb",
		{
			toSrgb: [
				1.3983557439607786, -0.39835574396077855, 5.551115123125783e-17,
				-1.4072944198861848e-16, 1, -2.0816681711721685e-17,
				1.734723475976807e-17, -0.04292898929447317, 1.042928989294473
			],
			transfer: a98Transfer,
			conversion: 3
		}
	],
	[
		"prophoto-rgb",
		{
			toSrgb: [
				2.034380836302867, -0.7276360137172471, -0.3067448320015419,
				-0.228825697964331, 1.2317426727787788, -0.0029169277200310345,
				-0.008558858080647581, -0.15326675125999153, 1.161825549670178
			],
			transfer: prophotoTransfer,
			conversion: 3
		}
	],
	[
		"rec2020",
		{
			toSrgb: [
				1.6604910021084347, -0.5876411387885495, -0.07284986331988486,
				-0.12455047452159063, 1.1328998971259596, -0.008349422604369508,
				-0.018150763354905206, -0.10057889800800737, 1.1187296613629127
			],
			transfer: rec2020Transfer,
			conversion: 2
		}
	],
	[
		"xyz",
		{
			toSrgb: [
				3.2409699419045226, -1.537383177570094, -0.4986107602930034,
				-0.9692436362808796, 1.8759675015077202, 0.04155505740717559,
				0.05563007969699366, -0.20397695888897652, 1.0569715142428786
			],
			transfer: linearTransfer,
			conversion: 2
		}
	],
	[
		"xyz-d65",
		{
			toSrgb: [
				3.2409699419045226, -1.537383177570094, -0.4986107602930034,
				-0.9692436362808796, 1.8759675015077202, 0.04155505740717559,
				0.05563007969699366, -0.20397695888897652, 1.0569715142428786
			],
			transfer: linearTransfer,
			conversion: 2
		}
	],
	[
		"xyz-d50",
		{
			toSrgb: [
				3.1341359569958707, -1.6173863321612538, -0.4906619460083532,
				-0.978795502912089, 1.9162545672595237, 0.03344273116131948,
				0.07195537988411684, -0.22897682641583222, 1.4053860583241256
			],
			transfer: linearTransfer,
			conversion: 2
		}
	]
]);

// Linear-light sRGB -> linear-light Display P3, the inverse of the matrix above
// it: a color outside sRGB keeps its gamut in a `color(display-p3 …)` fallback
// wherever the target reads one.
const LINEAR_SRGB_TO_P3 = [
	0.8224619687143625, 0.17753803128563775, 3.3650564745655794e-18,
	0.0331941988509616, 0.9668058011490385, 1.8324840583423322e-17,
	0.017082630721120023, 0.07239744066396339, 0.9105199286149164
];

// WHY: The interpolation spaces a `color-mix()` or a relative color is read in, each
// as the pair taking linear-light sRGB to its components and back, and which
// component is an angle (`-1` for none). Every one derived from the primaries,
// matrices and definitions the generator states.
/**
 * A 3x3 matrix, laid out row by row, times a column.
 * @param {number[]} m the matrix
 * @param {number[]} c the column
 * @returns {number[]} the product
 */
const applyModel = (m, c) =>
	[0, 3, 6].map((row) => m[row] * c[0] + m[row + 1] * c[1] + m[row + 2] * c[2]);

/**
 * @param {number} c a linear component
 * @returns {number} the same component
 */
const linearEncode = (c) => c;

/**
 * @param {number} c a linear component
 * @returns {number} the sRGB-encoded component
 */
const srgbEncode = (c) => {
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs > 0.0031308
		? sign * (1.055 * abs ** (1 / 2.4) - 0.055)
		: 12.92 * c;
};

/**
 * @param {number} c a linear component
 * @returns {number} the Adobe RGB (1998) component
 */
const a98Encode = (c) => {
	const sign = c < 0 ? -1 : 1;
	return sign * Math.abs(c) ** (256 / 563);
};

/**
 * @param {number} c a linear component
 * @returns {number} the ProPhoto RGB component
 */
const prophotoEncode = (c) => {
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs >= 1 / 512 ? sign * abs ** (1 / 1.8) : 16 * c;
};

/**
 * @param {number} c a linear component
 * @returns {number} the Rec. 2020 component
 */
const rec2020Encode = (c) => {
	const alpha = 1.09929682680944;
	const beta = 0.018053968510807;
	const abs = Math.abs(c);
	const sign = c < 0 ? -1 : 1;
	return abs > beta ? sign * (alpha * abs ** 0.45 - (alpha - 1)) : 4.5 * c;
};

// The D50 white point Lab is defined against (CSS Color 4 §12), as XYZ.
const LAB_WHITE = [0.3457 / 0.3585, 1, (1 - 0.3457 - 0.3585) / 0.3585];
const LAB_EPSILON = 216 / 24389;
const LAB_KAPPA = 24389 / 27;

/**
 * Linear-light sRGB -> CIE Lab, through XYZ at Lab's own white point.
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[L, a, b]`, L in 0..100
 */
const toLab = (c) => {
	const xyz = toXyzD50(c);
	const f = xyz.map((value, at) => {
		const t = value / LAB_WHITE[at];
		return t > LAB_EPSILON ? Math.cbrt(t) : (LAB_KAPPA * t + 16) / 116;
	});
	return [116 * f[1] - 16, 500 * (f[0] - f[1]), 200 * (f[1] - f[2])];
};

/**
 * CIE Lab -> linear-light sRGB.
 * @param {number[]} c `[L, a, b]`
 * @returns {number[]} the linear-light components
 */
const fromLab = (c) => {
	const fy = (c[0] + 16) / 116;
	const fx = c[1] / 500 + fy;
	const fz = fy - c[2] / 200;
	return fromXyzD50([
		(fx ** 3 > LAB_EPSILON ? fx ** 3 : (116 * fx - 16) / LAB_KAPPA) *
			LAB_WHITE[0],
		(c[0] > LAB_KAPPA * LAB_EPSILON ? fy ** 3 : c[0] / LAB_KAPPA) *
			LAB_WHITE[1],
		(fz ** 3 > LAB_EPSILON ? fz ** 3 : (116 * fz - 16) / LAB_KAPPA) *
			LAB_WHITE[2]
	]);
};

/**
 * Linear-light sRGB -> Oklab.
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[L, a, b]`, L in 0..1
 */
const toOklab = (c) => applyModel(OKLAB_M, applyModel(LMS_M, c).map(Math.cbrt));

/**
 * Oklab -> linear-light sRGB.
 * @param {number[]} c `[L, a, b]`
 * @returns {number[]} the linear-light components
 */
const fromOklab = (c) =>
	applyModel(
		LMS_I,
		applyModel(OKLAB_I, c).map((value) => value ** 3)
	);

/**
 * A rectangular pair as chroma and hue, and back — the one relation `lch` has
 * to `lab` and `oklch` to `oklab`.
 * @param {number[]} c `[L, a, b]`
 * @returns {number[]} `[L, C, H]`, H in degrees
 */
const toPolar = (c) => {
	const chroma = Math.hypot(c[1], c[2]);
	let hue = (Math.atan2(c[2], c[1]) * 180) / Math.PI;
	if (hue < 0) hue += 360;
	return [c[0], chroma, chroma === 0 ? 0 : hue];
};

/**
 * @param {number[]} c `[L, C, H]`, H in degrees
 * @returns {number[]} `[L, a, b]`
 */
const fromPolar = (c) => {
	const hue = (c[2] * Math.PI) / 180;
	return [c[0], c[1] * Math.cos(hue), c[1] * Math.sin(hue)];
};

/**
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[L, C, H]`
 */
const toLch = (c) => toPolar(toLab(c));

/**
 * @param {number[]} c `[L, C, H]`
 * @returns {number[]} the linear-light components
 */
const fromLch = (c) => fromLab(fromPolar(c));

/**
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[L, C, H]`
 */
const toOklch = (c) => toPolar(toOklab(c));

/**
 * @param {number[]} c `[L, C, H]`
 * @returns {number[]} the linear-light components
 */
const fromOklch = (c) => fromOklab(fromPolar(c));

/**
 * Linear-light sRGB -> HSL (CSS Color 4 §7.1), through sRGB.
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[H, S, L]`, H in degrees and the rest 0..1
 */
const toHsl = (c) => {
	const [r, g, b] = c.map(srgbEncode);
	const max = Math.max(r, g, b);
	const min = Math.min(r, g, b);
	const light = (min + max) / 2;
	const range = max - min;
	if (range === 0) return [0, 0, light];
	let hue;
	if (max === r) hue = ((g - b) / range) % 6;
	else if (max === g) hue = (b - r) / range + 2;
	else hue = (r - g) / range + 4;
	hue *= 60;
	if (hue < 0) hue += 360;
	return [hue, range / (1 - Math.abs(2 * light - 1)), light];
};

/**
 * HSL -> linear-light sRGB.
 * @param {number[]} c `[H, S, L]`
 * @returns {number[]} the linear-light components
 */
const fromHsl = (c) => {
	let hue = c[0] % 360;
	if (hue < 0) hue += 360;
	const amount = c[1] * Math.min(c[2], 1 - c[2]);
	return [0, 8, 4]
		.map((n) => {
			const k = (n + hue / 30) % 12;
			return c[2] - amount * Math.max(-1, Math.min(k - 3, 9 - k, 1));
		})
		.map(srgbTransfer);
};

/**
 * Linear-light sRGB -> HWB (CSS Color 4 §7.2).
 * @param {number[]} c the linear-light components
 * @returns {number[]} `[H, W, B]`
 */
const toHwb = (c) => {
	const srgb = c.map(srgbEncode);
	return [
		toHsl(c)[0],
		Math.min(srgb[0], srgb[1], srgb[2]),
		1 - Math.max(srgb[0], srgb[1], srgb[2])
	];
};

/**
 * HWB -> linear-light sRGB.
 * @param {number[]} c `[H, W, B]`
 * @returns {number[]} the linear-light components
 */
const fromHwb = (c) => {
	if (c[1] + c[2] >= 1) {
		const gray = c[1] / (c[1] + c[2]);
		return [gray, gray, gray].map(srgbTransfer);
	}
	return fromHsl([c[0], 1, 0.5]).map((value) =>
		srgbTransfer(srgbEncode(value) * (1 - c[1] - c[2]) + c[1])
	);
};

const SRGB_M = [1, 0, 0, 0, 1, 0, 0, 0, 1];
const SRGB_I = [1, 0, 0, 0, 1, 0, 0, 0, 1];
/** @type {(c: number[]) => number[]} */
const toSrgb = (c) => applyModel(SRGB_M, c).map(srgbEncode);
/** @type {(c: number[]) => number[]} */
const fromSrgb = (c) => applyModel(SRGB_I, c.map(srgbTransfer));
const SRGB_LINEAR_M = [1, 0, 0, 0, 1, 0, 0, 0, 1];
const SRGB_LINEAR_I = [1, 0, 0, 0, 1, 0, 0, 0, 1];
/** @type {(c: number[]) => number[]} */
const toSrgbLinear = (c) => applyModel(SRGB_LINEAR_M, c).map(linearEncode);
/** @type {(c: number[]) => number[]} */
const fromSrgbLinear = (c) => applyModel(SRGB_LINEAR_I, c.map(linearTransfer));
const DISPLAY_P3_M = [
	0.8224619687143625, 0.17753803128563775, 3.3650564745655794e-18,
	0.0331941988509616, 0.9668058011490385, 1.8324840583423322e-17,
	0.017082630721120023, 0.07239744066396339, 0.9105199286149164
];
const DISPLAY_P3_I = [
	1.2249401762805596, -0.22494017628055984, 0, -0.04205695470968812,
	1.042056954709688, -2.0816681711721685e-17, -0.019637554590334425,
	-0.0786360455506318, 1.0982736001409665
];
/** @type {(c: number[]) => number[]} */
const toDisplayP3 = (c) => applyModel(DISPLAY_P3_M, c).map(srgbEncode);
/** @type {(c: number[]) => number[]} */
const fromDisplayP3 = (c) => applyModel(DISPLAY_P3_I, c.map(srgbTransfer));
const A98_RGB_M = [
	0.7151256068556245, 0.2848743931443755, -3.237737802690131e-17,
	1.0063922760456419e-16, 1, 1.9959826532201272e-17, -7.752312519259058e-18,
	0.04116194845011838, 0.9588380515498818
];
const A98_RGB_I = [
	1.3983557439607786, -0.39835574396077855, 5.551115123125783e-17,
	-1.4072944198861848e-16, 1, -2.0816681711721685e-17, 1.734723475976807e-17,
	-0.04292898929447317, 1.042928989294473
];
/** @type {(c: number[]) => number[]} */
const toA98Rgb = (c) => applyModel(A98_RGB_M, c).map(a98Encode);
/** @type {(c: number[]) => number[]} */
const fromA98Rgb = (c) => applyModel(A98_RGB_I, c.map(a98Transfer));
const PROPHOTO_RGB_M = [
	0.5292769842583223, 0.3301545636252504, 0.14056844993940584,
	0.09836583745016964, 0.8734706333869527, 0.028163490634021324,
	0.016875355289046535, 0.1176594475769436, 0.8654652433945142
];
const PROPHOTO_RGB_I = [
	2.034380836302867, -0.7276360137172471, -0.3067448320015419,
	-0.228825697964331, 1.2317426727787788, -0.0029169277200310345,
	-0.008558858080647581, -0.15326675125999153, 1.161825549670178
];
/** @type {(c: number[]) => number[]} */
const toProphotoRgb = (c) => applyModel(PROPHOTO_RGB_M, c).map(prophotoEncode);
/** @type {(c: number[]) => number[]} */
const fromProphotoRgb = (c) =>
	applyModel(PROPHOTO_RGB_I, c.map(prophotoTransfer));
const REC2020_M = [
	0.6274038959346989, 0.32928303837788375, 0.04331306568741721,
	0.06909728935823205, 0.9195403950754593, 0.011362315566309202,
	0.016391438875150217, 0.08801330787722576, 0.8955952532476239
];
const REC2020_I = [
	1.6604910021084347, -0.5876411387885495, -0.07284986331988486,
	-0.12455047452159063, 1.1328998971259596, -0.008349422604369508,
	-0.018150763354905206, -0.10057889800800737, 1.1187296613629127
];
/** @type {(c: number[]) => number[]} */
const toRec2020 = (c) => applyModel(REC2020_M, c).map(rec2020Encode);
/** @type {(c: number[]) => number[]} */
const fromRec2020 = (c) => applyModel(REC2020_I, c.map(rec2020Transfer));
const XYZ_M = [
	0.41239079926595934, 0.357584339383878, 0.18048078840183424,
	0.21263900587151027, 0.7151686787677561, 0.07219231536073371,
	0.01933081871559181, 0.11919477979462595, 0.9505321522496607
];
const XYZ_I = [
	3.2409699419045226, -1.537383177570094, -0.4986107602930034,
	-0.9692436362808796, 1.8759675015077202, 0.04155505740717559,
	0.05563007969699366, -0.20397695888897652, 1.0569715142428786
];
const XYZ_D50_M = [
	0.436065749632219, 0.3851515490648008, 0.14307837223757391,
	0.22249316329879926, 0.7168869742512141, 0.06061983440080464,
	0.01392393331799153, 0.09708135172457436, 0.7140993556376494
];
const XYZ_D50_I = [
	3.1341359569958707, -1.6173863321612538, -0.4906619460083532,
	-0.978795502912089, 1.9162545672595237, 0.03344273116131948,
	0.07195537988411684, -0.22897682641583222, 1.4053860583241256
];
/** @type {(c: number[]) => number[]} */
const toXyz = (c) => applyModel(XYZ_M, c);
/** @type {(c: number[]) => number[]} */
const fromXyz = (c) => applyModel(XYZ_I, c);
/** @type {(c: number[]) => number[]} */
const toXyzD50 = (c) => applyModel(XYZ_D50_M, c);
/** @type {(c: number[]) => number[]} */
const fromXyzD50 = (c) => applyModel(XYZ_D50_I, c);
const LMS_M = [
	0.4122214708, 0.5363325363, 0.0514459929, 0.2119034982, 0.6806995451,
	0.1073969566, 0.0883024619, 0.2817188376, 0.6299787005
];
const LMS_I = [
	4.076741661347994, -3.3077115904081933, 0.23096992872942784,
	-1.268438004092176, 2.6097574006633715, -0.34131939631021946,
	-0.004196086541837046, -0.7034186144594494, 1.7076147009309446
];
const OKLAB_M = [
	0.2104542553, 0.793617785, -0.0040720468, 1.9779984951, -2.428592205,
	0.4505937099, 0.0259040371, 0.7827717662, -0.808675766
];
const OKLAB_I = [
	0.9999999984505199, 0.39633779217376786, 0.2158037580607588,
	1.0000000088817607, -0.10556134232365634, -0.0638541747717059,
	1.000000054672411, -0.08948418209496577, -1.291485537864092
];
/**
 * @param {number[]} c a color's components in Oklch
 * @returns {boolean} true where an engine may read the hue as missing
 */
const uncertainOklchHue = (c) => Math.abs(c[1]) < 0.03;

// The space a hex and an `rgb()` state their components in.
const SRGB_SPACE = "srgb";

/** @typedef {{ to: (c: number[]) => number[], from: (c: number[]) => number[], hue: number, conversion: number, written: { open: string, scale: number[], percent: boolean[], feature: string }, uncertainHue: ((c: number[]) => boolean) | null }} ColorSpaceModel */

/** @type {Map<string, ColorSpaceModel>} */
const COLOR_SPACE_MODEL = new Map([
	[
		"srgb",
		{
			to: toSrgb,
			from: fromSrgb,
			hue: -1,
			conversion: 0,
			written: {
				open: "color(srgb ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"srgb-linear",
		{
			to: toSrgbLinear,
			from: fromSrgbLinear,
			hue: -1,
			conversion: 1,
			written: {
				open: "color(srgb-linear ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"display-p3",
		{
			to: toDisplayP3,
			from: fromDisplayP3,
			hue: -1,
			conversion: 2,
			written: {
				open: "color(display-p3 ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"a98-rgb",
		{
			to: toA98Rgb,
			from: fromA98Rgb,
			hue: -1,
			conversion: 3,
			written: {
				open: "color(a98-rgb ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"prophoto-rgb",
		{
			to: toProphotoRgb,
			from: fromProphotoRgb,
			hue: -1,
			conversion: 3,
			written: {
				open: "color(prophoto-rgb ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"rec2020",
		{
			to: toRec2020,
			from: fromRec2020,
			hue: -1,
			conversion: 2,
			written: {
				open: "color(rec2020 ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"xyz",
		{
			to: toXyz,
			from: fromXyz,
			hue: -1,
			conversion: 2,
			written: {
				open: "color(xyz ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"xyz-d65",
		{
			to: toXyz,
			from: fromXyz,
			hue: -1,
			conversion: 2,
			written: {
				open: "color(xyz-d65 ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"xyz-d50",
		{
			to: toXyzD50,
			from: fromXyzD50,
			hue: -1,
			conversion: 2,
			written: {
				open: "color(xyz-d50 ",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "colorFunction"
			},
			uncertainHue: null
		}
	],
	[
		"lab",
		{
			to: toLab,
			from: fromLab,
			hue: -1,
			conversion: 2,
			written: {
				open: "lab(",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "labColors"
			},
			uncertainHue: null
		}
	],
	[
		"lch",
		{
			to: toLch,
			from: fromLch,
			hue: 2,
			conversion: 2,
			written: {
				open: "lch(",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "labColors"
			},
			uncertainHue: null
		}
	],
	[
		"oklab",
		{
			to: toOklab,
			from: fromOklab,
			hue: -1,
			conversion: 2,
			written: {
				open: "oklab(",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "oklabColors"
			},
			uncertainHue: null
		}
	],
	[
		"oklch",
		{
			to: toOklch,
			from: fromOklch,
			hue: 2,
			conversion: 2,
			written: {
				open: "oklch(",
				scale: [1, 1, 1],
				percent: [false, false, false],
				feature: "oklabColors"
			},
			uncertainHue: uncertainOklchHue
		}
	],
	[
		"hsl",
		{
			to: toHsl,
			from: fromHsl,
			hue: 0,
			conversion: 0,
			written: {
				open: "hsl(",
				scale: [1, 100, 100],
				percent: [false, true, true],
				feature: ""
			},
			uncertainHue: null
		}
	],
	[
		"hwb",
		{
			to: toHwb,
			from: fromHwb,
			hue: 0,
			conversion: 0,
			written: {
				open: "hwb(",
				scale: [1, 100, 100],
				percent: [false, true, true],
				feature: "hwbColors"
			},
			uncertainHue: null
		}
	]
]);

// The named colors an engine may not read while reading the rest, so one says
// nothing about what another takes. Every other name is as old as naming one.
const LATER_COLOR_NAMES = new Set(["rebeccapurple", "transparent"]);

// Every named color as its packed `0xrrggbb` value — what a color a mix or a
// relative reference names resolves through. The two tables above cut this one
// down to the spellings worth rewriting; this one answers for every name.
/** @type {Map<string, number>} */
const COLOR_NAME_TO_RGB = new Map([
	["aliceblue", 15792383],
	["antiquewhite", 16444375],
	["aqua", 65535],
	["aquamarine", 8388564],
	["azure", 15794175],
	["beige", 16119260],
	["bisque", 16770244],
	["black", 0],
	["blanchedalmond", 16772045],
	["blue", 255],
	["blueviolet", 9055202],
	["brown", 10824234],
	["burlywood", 14596231],
	["cadetblue", 6266528],
	["chartreuse", 8388352],
	["chocolate", 13789470],
	["coral", 16744272],
	["cornflowerblue", 6591981],
	["cornsilk", 16775388],
	["crimson", 14423100],
	["cyan", 65535],
	["darkblue", 139],
	["darkcyan", 35723],
	["darkgoldenrod", 12092939],
	["darkgray", 11119017],
	["darkgreen", 25600],
	["darkgrey", 11119017],
	["darkkhaki", 12433259],
	["darkmagenta", 9109643],
	["darkolivegreen", 5597999],
	["darkorange", 16747520],
	["darkorchid", 10040012],
	["darkred", 9109504],
	["darksalmon", 15308410],
	["darkseagreen", 9419919],
	["darkslateblue", 4734347],
	["darkslategray", 3100495],
	["darkslategrey", 3100495],
	["darkturquoise", 52945],
	["darkviolet", 9699539],
	["deeppink", 16716947],
	["deepskyblue", 49151],
	["dimgray", 6908265],
	["dimgrey", 6908265],
	["dodgerblue", 2003199],
	["firebrick", 11674146],
	["floralwhite", 16775920],
	["forestgreen", 2263842],
	["fuchsia", 16711935],
	["gainsboro", 14474460],
	["ghostwhite", 16316671],
	["gold", 16766720],
	["goldenrod", 14329120],
	["gray", 8421504],
	["green", 32768],
	["greenyellow", 11403055],
	["grey", 8421504],
	["honeydew", 15794160],
	["hotpink", 16738740],
	["indianred", 13458524],
	["indigo", 4915330],
	["ivory", 16777200],
	["khaki", 15787660],
	["lavender", 15132410],
	["lavenderblush", 16773365],
	["lawngreen", 8190976],
	["lemonchiffon", 16775885],
	["lightblue", 11393254],
	["lightcoral", 15761536],
	["lightcyan", 14745599],
	["lightgoldenrodyellow", 16448210],
	["lightgray", 13882323],
	["lightgreen", 9498256],
	["lightgrey", 13882323],
	["lightpink", 16758465],
	["lightsalmon", 16752762],
	["lightseagreen", 2142890],
	["lightskyblue", 8900346],
	["lightslategray", 7833753],
	["lightslategrey", 7833753],
	["lightsteelblue", 11584734],
	["lightyellow", 16777184],
	["lime", 65280],
	["limegreen", 3329330],
	["linen", 16445670],
	["magenta", 16711935],
	["maroon", 8388608],
	["mediumaquamarine", 6737322],
	["mediumblue", 205],
	["mediumorchid", 12211667],
	["mediumpurple", 9662683],
	["mediumseagreen", 3978097],
	["mediumslateblue", 8087790],
	["mediumspringgreen", 64154],
	["mediumturquoise", 4772300],
	["mediumvioletred", 13047173],
	["midnightblue", 1644912],
	["mintcream", 16121850],
	["mistyrose", 16770273],
	["moccasin", 16770229],
	["navajowhite", 16768685],
	["navy", 128],
	["oldlace", 16643558],
	["olive", 8421376],
	["olivedrab", 7048739],
	["orange", 16753920],
	["orangered", 16729344],
	["orchid", 14315734],
	["palegoldenrod", 15657130],
	["palegreen", 10025880],
	["paleturquoise", 11529966],
	["palevioletred", 14381203],
	["papayawhip", 16773077],
	["peachpuff", 16767673],
	["peru", 13468991],
	["pink", 16761035],
	["plum", 14524637],
	["powderblue", 11591910],
	["purple", 8388736],
	["rebeccapurple", 6697881],
	["red", 16711680],
	["rosybrown", 12357519],
	["royalblue", 4286945],
	["saddlebrown", 9127187],
	["salmon", 16416882],
	["sandybrown", 16032864],
	["seagreen", 3050327],
	["seashell", 16774638],
	["sienna", 10506797],
	["silver", 12632256],
	["skyblue", 8900331],
	["slateblue", 6970061],
	["slategray", 7372944],
	["slategrey", 7372944],
	["snow", 16775930],
	["springgreen", 65407],
	["steelblue", 4620980],
	["tan", 13808780],
	["teal", 32896],
	["thistle", 14204888],
	["tomato", 16737095],
	["turquoise", 4251856],
	["violet", 15631086],
	["wheat", 16113331],
	["white", 16777215],
	["whitesmoke", 16119285],
	["yellow", 16776960],
	["yellowgreen", 10145074]
]);

// What a layered shorthand's position, size, origin and clip hold when nothing
// writes them, as `[x, y, size, origin, clip]`. A layer holding its own is a
// layer the shorthand says without them.
const LAYER_INITIALS = new Map([
	["background", ["0%", "0%", "auto", "padding-box", "border-box"]],
	["mask", ["0%", "0%", "auto", "border-box", "border-box"]]
]);

// What each slot of a family shorthand holds when nothing writes it. A slot
// holding its own initial says nothing beside the others.
const FAMILY_SLOT_INITIALS = new Map([
	["border-block-end-color", "currentcolor"],
	["border-block-end-style", "none"],
	["border-block-end-width", "medium"],
	["border-block-start-color", "currentcolor"],
	["border-block-start-style", "none"],
	["border-block-start-width", "medium"],
	["border-bottom-color", "currentcolor"],
	["border-bottom-style", "none"],
	["border-bottom-width", "medium"],
	["border-inline-end-color", "currentcolor"],
	["border-inline-end-style", "none"],
	["border-inline-end-width", "medium"],
	["border-inline-start-color", "currentcolor"],
	["border-inline-start-style", "none"],
	["border-inline-start-width", "medium"],
	["border-left-color", "currentcolor"],
	["border-left-style", "none"],
	["border-left-width", "medium"],
	["border-right-color", "currentcolor"],
	["border-right-style", "none"],
	["border-right-width", "medium"],
	["border-top-color", "currentcolor"],
	["border-top-style", "none"],
	["border-top-width", "medium"],
	["column-rule-color", "currentcolor"],
	["column-rule-style", "none"],
	["column-rule-width", "medium"],
	["flex-direction", "row"],
	["flex-wrap", "nowrap"],
	["list-style-image", "none"],
	["list-style-position", "outside"],
	["list-style-type", "disc"],
	["outline-color", "auto"],
	["outline-style", "none"],
	["outline-width", "medium"],
	["text-decoration-color", "currentcolor"],
	["text-decoration-line", "none"],
	["text-decoration-style", "solid"],
	["text-decoration-thickness", "auto"],
	["text-emphasis-color", "currentcolor"],
	["text-emphasis-style", "none"],
	["text-wrap-mode", "wrap"],
	["text-wrap-style", "auto"]
]);

// The font stack `system-ui` names, for a target that does not read the keyword.
const SYSTEM_UI_STACK =
	"system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Noto Sans,Ubuntu,Cantarell,Helvetica Neue";

// The angle units. Excluded from rounding: `rotate()` runs its argument through
// trig, which turns a truncated digit into a different computed matrix.
const ANGLE_UNITS = new Set(["deg", "grad", "rad", "turn"]);

// The constants a calculation may name (CSS Values 4 §10.7), as `name -> value`.
// `infinity` and `NaN` are named with none: no printed number spells either, so
// a calculation naming one is left as it stands.
/** @type {Map<string, number | null>} */
const CALC_CONSTANTS = new Map([
	["e", Math.E],
	["infinity", null],
	["nan", null],
	["pi", Math.PI]
]);

// A quarter turn in each unit that spells it exactly (CSS Values 4 §8.1), as
// `unit -> the count`. It is what a trig function's argument is read as degrees
// through, and the eighths of it are where sine and cosine are rational.
/** @type {Map<string, number>} */
const QUARTER_TURN_ANGLE = new Map([
	["deg", 90],
	["grad", 100],
	["turn", 0.25]
]);

// Sine, cosine and tangent as `eighth turn from zero -> value`. The eighths
// where the value is irrational are absent — sine and cosine on the odd ones,
// tangent on the asymptotes. Cosine is sine a quarter turn along.
/** @type {Map<number, number>} */
const EIGHTH_TURN_SINE = new Map([
	[0, 0],
	[2, 1],
	[4, 0],
	[6, -1]
]);

/** @type {Map<number, number>} */
const EIGHTH_TURN_COSINE = new Map([
	[0, 1],
	[2, 0],
	[4, -1],
	[6, 0]
]);

/** @type {Map<number, number>} */
const EIGHTH_TURN_TANGENT = new Map([
	[0, 0],
	[1, 1],
	[3, -1],
	[4, 0],
	[5, 1],
	[7, -1]
]);

// What each inverse trig function answers, as `argument -> degrees`, by
// inverting the table above it over that function's principal branch. Every
// other argument is transcendental and leaves the call written out.
/** @type {Map<number, number>} */
const ARC_SINE_DEGREES = new Map([
	[-1, -90],
	[0, 0],
	[1, 90]
]);

/** @type {Map<number, number>} */
const ARC_COSINE_DEGREES = new Map([
	[-1, 180],
	[0, 90],
	[1, 0]
]);

/** @type {Map<number, number>} */
const ARC_TANGENT_DEGREES = new Map([
	[-1, -45],
	[0, 0],
	[1, 45]
]);

// The reader that needs a table, built once here — `mathPrimitives` knows how to
// read an angle but not which units spell a quarter turn.
const readAngle = angleReader(QUARTER_TURN_ANGLE);

// The table a function that looks nothing up is handed.
/** @type {Map<number, number>} */
const NO_TABLE = new Map();

// WHY: What folding each math function comes down to, as
// `name -> { read, apply, result, table }`: how its arguments are read, which
// arithmetic runs, and the unit the answer carries. `read` and `apply` are the
// functions themselves, so `lib/css/syntax.js` drives the fold while naming
// neither a math function nor an arithmetic of its own.
/** @type {Map<string, { read: MathArgumentReader, apply: MathOperation, result: string, table: Map<number, number> }>} */
const MATH_FUNCTION_FOLD = new Map([
	[
		"abs",
		{ read: readSameUnit, apply: absolute, result: "same", table: NO_TABLE }
	],
	[
		"acos",
		{
			read: readNumber,
			apply: statedAngle,
			result: "deg",
			table: ARC_COSINE_DEGREES
		}
	],
	[
		"asin",
		{
			read: readNumber,
			apply: statedAngle,
			result: "deg",
			table: ARC_SINE_DEGREES
		}
	],
	[
		"atan",
		{
			read: readNumber,
			apply: statedAngle,
			result: "deg",
			table: ARC_TANGENT_DEGREES
		}
	],
	[
		"atan2",
		{ read: readSameUnit, apply: arcTangent2, result: "deg", table: NO_TABLE }
	],
	[
		"clamp",
		{ read: readSameUnit, apply: clamp, result: "same", table: NO_TABLE }
	],
	[
		"cos",
		{ read: readAngle, apply: cosine, result: "", table: EIGHTH_TURN_COSINE }
	],
	[
		"exp",
		{ read: readNumber, apply: exponential, result: "", table: NO_TABLE }
	],
	[
		"hypot",
		{ read: readSameUnit, apply: hypotenuse, result: "same", table: NO_TABLE }
	],
	["log", { read: readNumber, apply: logarithm, result: "", table: NO_TABLE }],
	[
		"max",
		{ read: readSameUnit, apply: maximum, result: "same", table: NO_TABLE }
	],
	[
		"min",
		{ read: readSameUnit, apply: minimum, result: "same", table: NO_TABLE }
	],
	[
		"mod",
		{ read: readSameUnit, apply: modulus, result: "same", table: NO_TABLE }
	],
	["pow", { read: readNumber, apply: power, result: "", table: NO_TABLE }],
	[
		"rem",
		{ read: readSameUnit, apply: remainder, result: "same", table: NO_TABLE }
	],
	[
		"round",
		{ read: readSameUnit, apply: round, result: "same", table: NO_TABLE }
	],
	["sign", { read: readSameUnit, apply: sign, result: "", table: NO_TABLE }],
	[
		"sin",
		{ read: readAngle, apply: sine, result: "", table: EIGHTH_TURN_SINE }
	],
	[
		"sqrt",
		{ read: readNumber, apply: squareRoot, result: "", table: NO_TABLE }
	],
	[
		"tan",
		{ read: readAngle, apply: tangent, result: "", table: EIGHTH_TURN_TANGENT }
	]
]);

// WHY: Properties whose grammar can reach an `<integer>`. Deliberately wide: a
// non-integer where an integer is expected is rounded rather than dropped
// (`z-index: calc(1.5)` computes to `2`), so this is read to refuse a rewrite,
// and one name too many costs only that rewrite.
const INTEGER_PROPERTIES = new Set([
	"-ms-grid-columns",
	"-ms-grid-rows",
	"-ms-hyphenate-limit-chars",
	"-ms-hyphenate-limit-lines",
	"-webkit-line-clamp",
	"animation",
	"animation-timing-function",
	"box-flex-group",
	"box-ordinal-group",
	"column-count",
	"columns",
	"counter-increment",
	"counter-reset",
	"counter-set",
	"flex-line-count",
	"font-feature-settings",
	"grid",
	"grid-area",
	"grid-column",
	"grid-column-end",
	"grid-column-start",
	"grid-row",
	"grid-row-end",
	"grid-row-start",
	"grid-template",
	"grid-template-columns",
	"grid-template-rows",
	"hyphenate-limit-chars",
	"initial-letter",
	"line-clamp",
	"math-depth",
	"max-lines",
	"order",
	"orphans",
	"reading-order",
	"tab-size",
	"text-combine-upright",
	"transition",
	"transition-timing-function",
	"widows",
	"z-index"
]);

// The properties whose value is one `<number> | <percentage>`, where the
// percentage is the number hundredfold and the two compute to the same thing.
const ALPHA_VALUE_PROPERTIES = new Set(["opacity", "shape-image-threshold"]);

// The properties taking a `<ratio>`, whose second number of `1` is the one an
// omitted denominator means.
const RATIO_PROPERTIES = new Set(["aspect-ratio"]);

// The keywords of every property a `css/module` reads a scoped name out of,
// each mapped to how many times it may be spelled before the next one is the
// name (`Infinity` — never the name). Derived from each property's grammar.
const CSS_MODULES_KEYWORDS = new Map([
	[
		"animation",
		new Map([
			["alternate", 1],
			["alternate-reverse", 1],
			["auto", Infinity],
			["backwards", 1],
			["both", 1],
			["ease", 1],
			["ease-in", 1],
			["ease-in-out", 1],
			["ease-out", 1],
			["forwards", 1],
			["infinite", 1],
			["inherit", Infinity],
			["initial", Infinity],
			["linear", 1],
			["none", Infinity],
			["normal", 1],
			["paused", 1],
			["reverse", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["running", 1],
			["step-end", 1],
			["step-start", 1],
			["unset", Infinity]
		])
	],
	[
		"animation-name",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["none", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"container",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["inline-size", 1],
			["none", Infinity],
			["normal", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["scroll-state", 1],
			["size", 1],
			["unset", Infinity]
		])
	],
	[
		"container-name",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["none", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"list-style",
		new Map([
			["arabic-indic", 1],
			["armenian", 1],
			["bengali", 1],
			["cambodian", 1],
			["circle", 1],
			["cjk-decimal", 1],
			["cjk-earthly-branch", 1],
			["cjk-heavenly-stem", 1],
			["cjk-ideographic", 1],
			["decimal", 1],
			["decimal-leading-zero", 1],
			["devanagari", 1],
			["disc", 1],
			["disclosure-closed", 1],
			["disclosure-open", 1],
			["ethiopic-numeric", 1],
			["georgian", 1],
			["gujarati", 1],
			["gurmukhi", 1],
			["hebrew", 1],
			["hiragana", 1],
			["hiragana-iroha", 1],
			["inherit", Infinity],
			["initial", Infinity],
			["inside", 1],
			["japanese-formal", 1],
			["japanese-informal", 1],
			["kannada", 1],
			["katakana", 1],
			["katakana-iroha", 1],
			["khmer", 1],
			["korean-hangul-formal", 1],
			["korean-hanja-formal", 1],
			["korean-hanja-informal", 1],
			["lao", 1],
			["lower-alpha", 1],
			["lower-armenian", 1],
			["lower-greek", 1],
			["lower-latin", 1],
			["lower-roman", 1],
			["malayalam", 1],
			["mongolian", 1],
			["myanmar", 1],
			["none", Infinity],
			["oriya", 1],
			["outside", 1],
			["persian", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["simp-chinese-formal", 1],
			["simp-chinese-informal", 1],
			["square", 1],
			["tamil", 1],
			["telugu", 1],
			["thai", 1],
			["tibetan", 1],
			["trad-chinese-formal", 1],
			["trad-chinese-informal", 1],
			["unset", Infinity],
			["upper-alpha", 1],
			["upper-armenian", 1],
			["upper-latin", 1],
			["upper-roman", 1]
		])
	],
	[
		"list-style-type",
		new Map([
			["arabic-indic", 1],
			["armenian", 1],
			["bengali", 1],
			["cambodian", 1],
			["circle", 1],
			["cjk-decimal", 1],
			["cjk-earthly-branch", 1],
			["cjk-heavenly-stem", 1],
			["cjk-ideographic", 1],
			["decimal", 1],
			["decimal-leading-zero", 1],
			["devanagari", 1],
			["disc", 1],
			["disclosure-closed", 1],
			["disclosure-open", 1],
			["ethiopic-numeric", 1],
			["georgian", 1],
			["gujarati", 1],
			["gurmukhi", 1],
			["hebrew", 1],
			["hiragana", 1],
			["hiragana-iroha", 1],
			["inherit", Infinity],
			["initial", Infinity],
			["japanese-formal", 1],
			["japanese-informal", 1],
			["kannada", 1],
			["katakana", 1],
			["katakana-iroha", 1],
			["khmer", 1],
			["korean-hangul-formal", 1],
			["korean-hanja-formal", 1],
			["korean-hanja-informal", 1],
			["lao", 1],
			["lower-alpha", 1],
			["lower-armenian", 1],
			["lower-greek", 1],
			["lower-latin", 1],
			["lower-roman", 1],
			["malayalam", 1],
			["mongolian", 1],
			["myanmar", 1],
			["none", Infinity],
			["oriya", 1],
			["persian", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["simp-chinese-formal", 1],
			["simp-chinese-informal", 1],
			["square", 1],
			["tamil", 1],
			["telugu", 1],
			["thai", 1],
			["tibetan", 1],
			["trad-chinese-formal", 1],
			["trad-chinese-informal", 1],
			["unset", Infinity],
			["upper-alpha", 1],
			["upper-armenian", 1],
			["upper-latin", 1],
			["upper-roman", 1]
		])
	],
	[
		"system",
		new Map([
			["additive", 1],
			["alphabetic", 1],
			["arabic-indic", 1],
			["armenian", 1],
			["bengali", 1],
			["cambodian", 1],
			["circle", 1],
			["cjk-decimal", 1],
			["cjk-earthly-branch", 1],
			["cjk-heavenly-stem", 1],
			["cjk-ideographic", 1],
			["cyclic", 1],
			["decimal", 1],
			["decimal-leading-zero", 1],
			["devanagari", 1],
			["disc", 1],
			["disclosure-closed", 1],
			["disclosure-open", 1],
			["ethiopic-numeric", 1],
			["extends", 1],
			["fixed", 1],
			["georgian", 1],
			["gujarati", 1],
			["gurmukhi", 1],
			["hebrew", 1],
			["hiragana", 1],
			["hiragana-iroha", 1],
			["japanese-formal", 1],
			["japanese-informal", 1],
			["kannada", 1],
			["katakana", 1],
			["katakana-iroha", 1],
			["khmer", 1],
			["korean-hangul-formal", 1],
			["korean-hanja-formal", 1],
			["korean-hanja-informal", 1],
			["lao", 1],
			["lower-alpha", 1],
			["lower-armenian", 1],
			["lower-greek", 1],
			["lower-latin", 1],
			["lower-roman", 1],
			["malayalam", 1],
			["mongolian", 1],
			["myanmar", 1],
			["numeric", 1],
			["oriya", 1],
			["persian", 1],
			["simp-chinese-formal", 1],
			["simp-chinese-informal", 1],
			["square", 1],
			["symbolic", 1],
			["tamil", 1],
			["telugu", 1],
			["thai", 1],
			["tibetan", 1],
			["trad-chinese-formal", 1],
			["trad-chinese-informal", 1],
			["upper-alpha", 1],
			["upper-armenian", 1],
			["upper-latin", 1],
			["upper-roman", 1]
		])
	],
	[
		"fallback",
		new Map([
			["arabic-indic", 1],
			["armenian", 1],
			["bengali", 1],
			["cambodian", 1],
			["circle", 1],
			["cjk-decimal", 1],
			["cjk-earthly-branch", 1],
			["cjk-heavenly-stem", 1],
			["cjk-ideographic", 1],
			["decimal", 1],
			["decimal-leading-zero", 1],
			["devanagari", 1],
			["disc", 1],
			["disclosure-closed", 1],
			["disclosure-open", 1],
			["ethiopic-numeric", 1],
			["georgian", 1],
			["gujarati", 1],
			["gurmukhi", 1],
			["hebrew", 1],
			["hiragana", 1],
			["hiragana-iroha", 1],
			["japanese-formal", 1],
			["japanese-informal", 1],
			["kannada", 1],
			["katakana", 1],
			["katakana-iroha", 1],
			["khmer", 1],
			["korean-hangul-formal", 1],
			["korean-hanja-formal", 1],
			["korean-hanja-informal", 1],
			["lao", 1],
			["lower-alpha", 1],
			["lower-armenian", 1],
			["lower-greek", 1],
			["lower-latin", 1],
			["lower-roman", 1],
			["malayalam", 1],
			["mongolian", 1],
			["myanmar", 1],
			["oriya", 1],
			["persian", 1],
			["simp-chinese-formal", 1],
			["simp-chinese-informal", 1],
			["square", 1],
			["tamil", 1],
			["telugu", 1],
			["thai", 1],
			["tibetan", 1],
			["trad-chinese-formal", 1],
			["trad-chinese-informal", 1],
			["upper-alpha", 1],
			["upper-armenian", 1],
			["upper-latin", 1],
			["upper-roman", 1]
		])
	],
	[
		"speak-as",
		new Map([
			["arabic-indic", 1],
			["armenian", 1],
			["auto", Infinity],
			["bengali", 1],
			["bullets", Infinity],
			["cambodian", 1],
			["circle", 1],
			["cjk-decimal", 1],
			["cjk-earthly-branch", 1],
			["cjk-heavenly-stem", 1],
			["cjk-ideographic", 1],
			["decimal", 1],
			["decimal-leading-zero", 1],
			["devanagari", 1],
			["disc", 1],
			["disclosure-closed", 1],
			["disclosure-open", 1],
			["ethiopic-numeric", 1],
			["georgian", 1],
			["gujarati", 1],
			["gurmukhi", 1],
			["hebrew", 1],
			["hiragana", 1],
			["hiragana-iroha", 1],
			["japanese-formal", 1],
			["japanese-informal", 1],
			["kannada", 1],
			["katakana", 1],
			["katakana-iroha", 1],
			["khmer", 1],
			["korean-hangul-formal", 1],
			["korean-hanja-formal", 1],
			["korean-hanja-informal", 1],
			["lao", 1],
			["lower-alpha", 1],
			["lower-armenian", 1],
			["lower-greek", 1],
			["lower-latin", 1],
			["lower-roman", 1],
			["malayalam", 1],
			["mongolian", 1],
			["myanmar", 1],
			["numbers", Infinity],
			["oriya", 1],
			["persian", 1],
			["simp-chinese-formal", 1],
			["simp-chinese-informal", 1],
			["spell-out", Infinity],
			["square", 1],
			["tamil", 1],
			["telugu", 1],
			["thai", 1],
			["tibetan", 1],
			["trad-chinese-formal", 1],
			["trad-chinese-informal", 1],
			["upper-alpha", 1],
			["upper-armenian", 1],
			["upper-latin", 1],
			["upper-roman", 1],
			["words", Infinity]
		])
	],
	[
		"counter-reset",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["list-item", Infinity],
			["none", 1],
			["page", Infinity],
			["pages", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"counter-increment",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["list-item", Infinity],
			["none", 1],
			["page", Infinity],
			["pages", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"counter-set",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["list-item", Infinity],
			["none", 1],
			["page", Infinity],
			["pages", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"view-transition-name",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["match-element", Infinity],
			["none", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"view-transition-group",
		new Map([
			["contain", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["nearest", Infinity],
			["normal", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"view-transition-class",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["none", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid",
		new Map([
			["auto", Infinity],
			["auto-flow", 1],
			["column", 1],
			["dense", 1],
			["inherit", Infinity],
			["initial", Infinity],
			["masonry", 1],
			["max-content", Infinity],
			["min-content", Infinity],
			["none", 2],
			["revert", Infinity],
			["revert-layer", Infinity],
			["row", 1],
			["subgrid", 2],
			["unset", Infinity]
		])
	],
	[
		"grid-area",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-column",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-column-end",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-column-start",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-row",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-row-end",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-row-start",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["revert", Infinity],
			["revert-layer", Infinity],
			["span", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-template",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["masonry", 1],
			["max-content", Infinity],
			["min-content", Infinity],
			["none", 2],
			["revert", Infinity],
			["revert-layer", Infinity],
			["subgrid", 2],
			["unset", Infinity]
		])
	],
	[
		"grid-template-areas",
		new Map([
			["inherit", Infinity],
			["initial", Infinity],
			["none", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["unset", Infinity]
		])
	],
	[
		"grid-template-columns",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["masonry", 1],
			["max-content", Infinity],
			["min-content", Infinity],
			["none", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["subgrid", 1],
			["unset", Infinity]
		])
	],
	[
		"grid-template-rows",
		new Map([
			["auto", Infinity],
			["inherit", Infinity],
			["initial", Infinity],
			["masonry", 1],
			["max-content", Infinity],
			["min-content", Infinity],
			["none", 1],
			["revert", Infinity],
			["revert-layer", Infinity],
			["subgrid", 1],
			["unset", Infinity]
		])
	]
]);

// The parser option gating each of them.
const CSS_MODULES_KEYWORD_OPTIONS = new Map([
	["animation", "animation"],
	["animation-name", "animation"],
	["container", "container"],
	["container-name", "container"],
	["list-style", "customIdents"],
	["list-style-type", "customIdents"],
	["system", "customIdents"],
	["fallback", "customIdents"],
	["speak-as", "customIdents"],
	["counter-reset", "customIdents"],
	["counter-increment", "customIdents"],
	["counter-set", "customIdents"],
	["view-transition-name", "customIdents"],
	["view-transition-group", "customIdents"],
	["view-transition-class", "customIdents"],
	["grid", "grid"],
	["grid-area", "grid"],
	["grid-column", "grid"],
	["grid-column-end", "grid"],
	["grid-column-start", "grid"],
	["grid-row", "grid"],
	["grid-row-end", "grid"],
	["grid-row-start", "grid"],
	["grid-template", "grid"],
	["grid-template-areas", "grid"],
	["grid-template-columns", "grid"],
	["grid-template-rows", "grid"]
]);

// WHY: The properties a negative value is valid on, so `calc(-5px)` may lose its
// parentheses there. Read to permit a rewrite, which is the opposite of
// `INTEGER_PROPERTIES` above: naming one property too many is a bug, naming one
// too few only costs a rewrite.
const NEGATIVE_ACCEPTING_PROPERTIES = new Set([
	"animation-delay",
	"background-position",
	"background-position-x",
	"background-position-y",
	"bottom",
	"inset",
	"inset-block",
	"inset-block-end",
	"inset-block-start",
	"inset-inline",
	"inset-inline-end",
	"inset-inline-start",
	"left",
	"letter-spacing",
	"margin",
	"margin-block",
	"margin-block-end",
	"margin-block-start",
	"margin-bottom",
	"margin-inline",
	"margin-inline-end",
	"margin-inline-start",
	"margin-left",
	"margin-right",
	"margin-top",
	"offset-distance",
	"order",
	"outline-offset",
	"perspective-origin",
	"right",
	"rotate",
	"scroll-margin",
	"scroll-margin-block",
	"scroll-margin-bottom",
	"scroll-margin-inline",
	"scroll-margin-left",
	"scroll-margin-right",
	"scroll-margin-top",
	"stroke-dashoffset",
	"text-indent",
	"text-underline-offset",
	"top",
	"transform-origin",
	"transition-delay",
	"translate",
	"vertical-align",
	"word-spacing",
	"z-index"
]);

// WHY: The functions whose every numeric argument is a length, so a zero inside one
// drops its unit the way a whole component's does. Read to permit a rewrite:
// any other numeric type would make the bare `0` mean something else, or make
// a dropped declaration valid.
const LENGTH_ONLY_FUNCTIONS = new Set([
	"anchor",
	"anchor-size",
	"blur",
	"circle",
	"ellipse",
	"fit-content",
	"inset",
	"perspective",
	"polygon",
	"rect",
	"translate",
	"translate3d",
	"translatex",
	"translatey",
	"translatez",
	"view",
	"xywh"
]);

// Packed `0xrrggbb` -> the shortest named color with that value. Only names that
// can beat `#rrggbb`; anything longer would never be picked.
const RGB_TO_NAME = new Map([
	[0x000080, "navy"],
	[0x008000, "green"],
	[0x008080, "teal"],
	[0x4b0082, "indigo"],
	[0x800000, "maroon"],
	[0x800080, "purple"],
	[0x808000, "olive"],
	[0x808080, "gray"],
	[0xa0522d, "sienna"],
	[0xa52a2a, "brown"],
	[0xc0c0c0, "silver"],
	[0xcd853f, "peru"],
	[0xd2b48c, "tan"],
	[0xda70d6, "orchid"],
	[0xdda0dd, "plum"],
	[0xee82ee, "violet"],
	[0xf0e68c, "khaki"],
	[0xf0ffff, "azure"],
	[0xf5deb3, "wheat"],
	[0xf5f5dc, "beige"],
	[0xfa8072, "salmon"],
	[0xfaf0e6, "linen"],
	[0xff0000, "red"],
	[0xff6347, "tomato"],
	[0xff7f50, "coral"],
	[0xffa500, "orange"],
	[0xffc0cb, "pink"],
	[0xffd700, "gold"],
	[0xffe4c4, "bisque"],
	[0xfffafa, "snow"],
	[0xfffff0, "ivory"]
]);

// WHY: Prefixed constructs the minifier reads back, one table per axis, as `name ->
// [prefix, windowList][]`. Versions are `major * 100000 + minor`; a target
// browser at version V needs the prefix when `prefixedFrom <= V < unprefixedFrom`
// (`NEVER` = never unprefixed). Non-standard-only constructs are absent.
// Every window list laid end to end as `browserSlot, prefixedFrom,
// unprefixedFrom` triples — the slot is the browser's place in
// `SUPPORT_BROWSERS`, so no name is restated. A spelling names its list by
// index, and two thirds of the lists are shared.
const PREFIX_WINDOWS = new Uint32Array([
	3, 2100000, 2900000, 0, 2500000, 2900000, 10, 1500000, 1600000, 9, 1400000,
	1600000, 11, 700000, 900000, 8, 700000, 900000, 12, 100005, 200000, 6,
	1000000, 1100000, 7, 1000000, 1100000, 3, 2100000, 2900000, 0, 2500000,
	2900000, 11, 700000, 900000, 8, 700000, 900000, 12, 100005, 200000, 10,
	1500000, 1600000, 9, 1400000, 1600000, 11, 800000, 1800000, 8, 800000,
	1800000, 3, 300000, 4300000, 0, 1800000, 4300000, 10, 1500000, 3000000, 9,
	1400000, 3000000, 11, 400000, 900000, 8, 300002, 900000, 12, 100000, 400000,
	2, 200000, 4300000, 5, 500000, 1600000, 1, 500000, 1600000, 10, 1200000,
	1500000, 9, 1200000, 1400000, 3, 300000, 4300000, 0, 1800000, 4300000, 10,
	1500000, 3000000, 9, 1400000, 3000000, 11, 400000, 900000, 8, 300002, 900000,
	12, 100000, 400000, 2, 400004, 4300000, 3, 300000, 4300000, 0, 1800000,
	4300000, 10, 1500000, 3000000, 9, 1400000, 3000000, 11, 400000, 900000, 8,
	400002, 900000, 12, 100000, 400000, 2, 200000, 4300000, 3, 300000, 4300000, 0,
	1800000, 4300000, 10, 1500000, 3000000, 9, 1400000, 3000000, 11, 500000,
	900000, 8, 400000, 900000, 12, 100000, 400000, 2, 400004, 4300000, 3, 300000,
	4300000, 0, 1800000, 4300000, 10, 1500000, 3000000, 9, 1400000, 3000000, 11,
	400000, 900000, 8, 200000, 900000, 12, 100000, 400000, 2, 400004, 4300000, 3,
	100000, 8400000, 0, 1800000, 8400000, 4, 1200000, 8400000, 10, 1500000,
	7000000, 9, 1400000, 6000000, 11, 300000, 1500004, 8, 100000, 1500004, 12,
	100000, 1400000, 2, 400004, 8400000, 5, 100000, 8000000, 1, 400000, 8000000,
	4, 1700000, 7900000, 11, 900000, 1800000, 8, 900000, 1800000, 3, 1200000,
	3600000, 0, 1800000, 3600000, 10, 1500000, 2300000, 9, 1400000, 2400000, 11,
	500001, 1500004, 8, 500000, 1500004, 12, 100000, 300000, 2, 300000, 3700000,
	5, 1000000, 1600000, 1, 1000000, 1600000, 5, 100000, 400000, 11, 300000,
	500000, 8, 100000, 500000, 3, 100000, 300000, 11, 300000, 500000, 8, 100000,
	400002, 5, 300006, 400000, 10, 900005, 1000002, 3, 800000, 5700000, 0,
	1800000, 5700000, 10, 1500000, 4400000, 9, 1400000, 4300000, 11, 500001,
	1200001, 8, 500000, 1200002, 12, 100000, 700000, 2, 400004, 5700000, 3,
	100000, 400000, 11, 300000, 500000, 8, 100000, 400002, 3, 700000, 1600000, 11,
	300000, 600000, 8, 200000, 600000, 2, 200000, 400004, 5, 300005, 1500000, 1,
	400000, 1500000, 10, 1000005, 1500000, 9, 1100000, 1400000, 5, 300000,
	4100000, 1, 400000, 4100000, 3, 100000, 400000, 11, 300000, 500000, 8, 100000,
	400002, 2, 200000, 400004, 3, 100000, 1e9, 0, 1800000, 1e9, 4, 1200000, 1e9,
	10, 1500000, 1e9, 9, 1400000, 1e9, 11, 300000, 1e9, 8, 100000, 1e9, 12,
	100000, 1e9, 2, 400004, 1e9, 5, 100000, 1e9, 1, 400000, 1e9, 3, 2200000,
	13000000, 0, 2500000, 13000000, 4, 7900000, 13000000, 10, 1500000, 11500000,
	9, 1400000, 8600000, 11, 700000, 1e9, 8, 700000, 1e9, 12, 100005, 2800000, 2,
	400004, 13000000, 3, 100000, 6700000, 0, 1800000, 6700000, 10, 1500000,
	5500000, 9, 1400000, 4800000, 11, 300000, 1e9, 8, 100000, 1e9, 12, 100000,
	900000, 2, 400004, 6700000, 3, 100000, 1000000, 11, 300000, 500001, 8, 100000,
	500000, 5, 300005, 400000, 3, 100000, 1000000, 11, 300000, 500001, 8, 100000,
	600000, 2, 200000, 400000, 5, 100000, 2900000, 1, 400000, 2900000, 3, 2300000,
	5500000, 0, 2500000, 5500000, 10, 1500000, 4200000, 9, 1400000, 4200000, 11,
	700000, 900001, 8, 700000, 900003, 12, 100005, 600000, 2, 400004, 5500000, 3,
	100000, 5000000, 0, 1800000, 5000000, 10, 1500000, 3700000, 9, 1400000,
	3700000, 11, 300000, 900000, 8, 200000, 900000, 12, 100000, 500000, 2, 400004,
	5000000, 5, 100005, 5200000, 1, 400000, 5200000, 5, 1700000, 5200000, 1,
	1700000, 5200000, 11, 800000, 900000, 8, 800000, 900000, 3, 400000, 5000000,
	11, 300001, 900000, 8, 300002, 900000, 10, 1500000, 3700000, 2, 200001,
	500000, 12, 400000, 500000, 9, 1400000, 3700000, 5, 200000, 5200000, 3,
	100000, 5000000, 0, 1800000, 5000000, 11, 300000, 900000, 8, 100000, 900000,
	12, 100000, 500000, 2, 400004, 5000000, 10, 1500000, 3700000, 9, 1400000,
	3700000, 5, 300005, 5200000, 1, 400000, 5200000, 3, 400000, 5000000, 0,
	1800000, 5000000, 10, 1500000, 3700000, 9, 1400000, 3700000, 11, 300001,
	900000, 8, 300002, 900000, 12, 100000, 500000, 2, 200001, 5000000, 5, 900000,
	5200000, 1, 2200000, 5200000, 11, 300000, 900000, 8, 300002, 900000, 2,
	200000, 5000000, 3, 400000, 5000000, 10, 1500000, 3700000, 12, 400000, 500000,
	9, 1400000, 3700000, 3, 1800000, 5300000, 0, 1800000, 5300000, 10, 1500000,
	4000000, 9, 1400000, 4100000, 11, 600000, 900001, 8, 600000, 900003, 12,
	100000, 600000, 2, 400004, 5300000, 3, 2200000, 2900000, 0, 2500000, 2900000,
	11, 700000, 900000, 8, 700000, 900000, 12, 100005, 200000, 10, 1500000,
	1600000, 9, 1400000, 1600000, 3, 2200000, 2900000, 0, 2500000, 2900000, 11,
	800000, 900000, 8, 800000, 900000, 12, 100005, 200000, 10, 1500000, 1600000,
	9, 1400000, 1600000, 3, 1600000, 4800000, 0, 1800000, 4800000, 10, 1500000,
	3500000, 9, 1400000, 3500000, 12, 100000, 500000, 5, 1500000, 3400000, 1,
	1500000, 3400000, 3, 2900000, 3300000, 0, 2900000, 3300000, 10, 1600000,
	2000000, 9, 1600000, 2000000, 11, 600000, 900001, 8, 600000, 1200000, 12,
	100000, 200000, 5, 400000, 3400000, 1, 400000, 3400000, 3, 3100000, 3400000,
	0, 3100000, 3400000, 10, 1800000, 2100000, 9, 1800000, 2100000, 11, 700000,
	900001, 8, 700000, 900003, 2, 400004, 3700000, 4, 1200000, 7900000, 6,
	1000000, 1e9, 7, 1000000, 1e9, 3, 600000, 10600000, 0, 1800000, 10600000, 4,
	7900000, 10600000, 10, 1500000, 9200000, 9, 1400000, 7200000, 11, 500001,
	1700000, 8, 500000, 1700000, 12, 100000, 2000000, 2, 400004, 10600000, 3,
	1300000, 5500000, 0, 1800000, 5500000, 10, 1500000, 4200000, 9, 1400000,
	4200000, 11, 500001, 1700000, 8, 400002, 1700000, 12, 100000, 600000, 2,
	400004, 5500000, 5, 600000, 4300000, 1, 600000, 4300000, 4, 1200000, 7900000,
	11, 900000, 1e9, 8, 900000, 1e9, 3, 100000, 5800000, 0, 1800000, 5800000, 10,
	1500000, 4500000, 9, 1400000, 4300000, 11, 300000, 1100000, 8, 100000,
	1100000, 12, 100000, 700000, 2, 400004, 5800000, 3, 600000, 1e9, 0, 1800000,
	1e9, 4, 7900000, 1e9, 5, 6800000, 1e9, 1, 6800000, 1e9, 10, 1500000, 1e9, 9,
	1400000, 1e9, 11, 500000, 1e9, 8, 400002, 1e9, 12, 100000, 1e9, 2, 400004,
	1e9, 3, 800000, 6900000, 0, 1800000, 6900000, 10, 1500000, 5600000, 9,
	1400000, 4800000, 11, 500001, 1200001, 8, 500000, 1200002, 12, 100000,
	1000000, 2, 400004, 6900000, 3, 200000, 6900000, 0, 1800000, 6900000, 10,
	1500000, 5600000, 9, 1400000, 4800000, 11, 300000, 1200001, 8, 300000,
	1200002, 12, 100000, 1000000, 2, 200000, 8700000, 3, 100000, 12000000, 0,
	1800000, 12000000, 4, 7900000, 12000000, 10, 1500000, 10600000, 9, 1400000,
	8000000, 11, 300001, 1500004, 8, 200000, 1500004, 12, 100000, 2500000, 2,
	200000, 12000000, 3, 100000, 1e9, 0, 1800000, 1e9, 4, 7900000, 1e9, 10,
	1500000, 1e9, 9, 1400000, 1e9, 11, 300001, 1700002, 8, 200000, 1700002, 12,
	100000, 1e9, 2, 400004, 1e9, 3, 100000, 12000000, 0, 1800000, 12000000, 4,
	7900000, 12000000, 10, 1500000, 10600000, 9, 1400000, 8000000, 11, 400000,
	1500004, 8, 300002, 1500004, 12, 100000, 2500000, 2, 200000, 12000000, 3,
	100000, 12000000, 0, 1800000, 12000000, 4, 7900000, 12000000, 10, 1500000,
	1e9, 9, 1400000, 8000000, 11, 400000, 1500004, 8, 300002, 1500004, 12, 100000,
	2500000, 2, 200000, 12000000, 3, 400000, 12000000, 0, 1800000, 12000000, 4,
	7900000, 12000000, 10, 1500000, 10600000, 9, 1400000, 8000000, 11, 400000,
	1500004, 8, 200000, 1500004, 12, 100000, 2500000, 2, 400004, 12000000, 10,
	1000006, 1500000, 9, 1100000, 1400000, 5, 100000, 300006, 5, 100000, 100005,
	3, 1200000, 3600000, 0, 1800000, 3600000, 10, 1500000, 2300000, 9, 1400000,
	2400000, 11, 400000, 900000, 8, 200000, 900000, 12, 100000, 300000, 2, 300000,
	400004, 3, 1700000, 13600000, 0, 1800000, 13600000, 4, 7900000, 13600000, 10,
	1500000, 12100000, 9, 1400000, 9000000, 11, 600000, 1500004, 8, 600000,
	1500004, 12, 100000, 2900000, 2, 400004, 13600000, 3, 100000, 8400000, 0,
	1800000, 8400000, 4, 7900000, 8400000, 10, 1500000, 7000000, 9, 1400000,
	6000000, 11, 700000, 1800002, 8, 700000, 1800002, 2, 400004, 8400000, 11,
	900000, 1100000, 8, 900000, 1100000, 11, 700001, 1000001, 8, 800000, 1000003,
	5, 400000, 9100000, 1, 400000, 9100000, 5, 1200000, 4900000, 1, 1400000,
	4900000, 4, 1200000, 7900000, 6, 1100000, 1e9, 7, 1100000, 1e9, 5, 600000,
	3600000, 1, 600000, 3600000, 11, 800000, 1200001, 8, 800000, 1200002, 11,
	700000, 1200001, 8, 700000, 1200002, 3, 2500000, 9900000, 0, 2500000, 9900000,
	4, 7900000, 9900000, 10, 1500000, 8500000, 9, 1400000, 6800000, 12, 100005,
	1800000, 2, 400004, 9900000, 3, 1200000, 4800000, 0, 1800000, 4800000, 10,
	1500000, 3500000, 9, 1400000, 3500000, 11, 500001, 1400000, 8, 500000,
	1400000, 12, 100000, 500000, 2, 400004, 4800000, 10, 900000, 1100000, 9,
	1000000, 1200001, 4, 1200000, 7900000, 8, 100000, 1e9, 1, 1400000, 1e9, 5,
	1400000, 1e9, 7, 1000000, 1200000, 4, 1200000, 1900000, 11, 900000, 1200001,
	8, 900000, 1200002, 3, 100000, 3600000, 0, 1800000, 3600000, 10, 1500000,
	2300000, 9, 1400000, 2400000, 11, 300001, 900000, 8, 300002, 900000, 12,
	100000, 300000, 2, 200000, 400004, 5, 300005, 1600000, 1, 400000, 1600000, 6,
	900000, 1000000, 7, 900000, 1000000, 3, 100000, 3600000, 0, 1800000, 3600000,
	10, 1500000, 2300000, 9, 1400000, 2400000, 11, 200000, 900000, 8, 100000,
	900000, 12, 100000, 300000, 2, 400004, 3700000, 3, 100000, 2600000, 0,
	1800000, 2600000, 11, 300001, 900000, 8, 200000, 900000, 12, 100000, 100005,
	2, 200000, 400004, 5, 400000, 1600000, 1, 400000, 1600000, 10, 1000001,
	1200001, 9, 1000001, 1200001, 3, 100000, 2600000, 0, 1800000, 2600000, 11,
	400000, 900000, 8, 200000, 900000, 12, 100000, 100005, 2, 200000, 400004, 10,
	1100006, 1200001, 9, 1200000, 1200001, 10, 1000000, 1200001, 9, 1000001,
	1200001, 3, 100000, 2600000, 0, 1800000, 2600000, 11, 300001, 900000, 8,
	200000, 900000, 12, 100000, 100005, 3, 100000, 1e9, 0, 1800000, 1e9, 4,
	1200000, 1e9, 10, 1500000, 1e9, 9, 1400000, 1e9, 11, 300000, 1e9, 8, 500000,
	1e9, 12, 100000, 1e9, 2, 3700000, 1e9, 5, 100000, 13200000, 1, 400000,
	13200000, 3, 100000, 5400000, 0, 1800000, 5400000, 4, 1200000, 7900000, 10,
	1500000, 4100000, 9, 1400000, 4100000, 11, 300000, 1e9, 8, 300000, 1e9, 12,
	100000, 600000, 2, 400004, 5400000, 5, 100000, 6900000, 1, 400000, 7900000, 3,
	800000, 4800000, 0, 1800000, 4800000, 10, 1500000, 3500000, 9, 1400000,
	3500000, 11, 500001, 1000001, 8, 500000, 1000003, 12, 100000, 500000, 2,
	300000, 4800000, 3, 100000, 6500000, 0, 1800000, 6500000, 10, 1500000,
	5200000, 9, 1400000, 4700000, 11, 300000, 900000, 8, 100000, 900000, 12,
	100000, 900000, 2, 400004, 6500000, 5, 100000, 5000000, 1, 400000, 5000000, 3,
	100000, 11000000, 0, 1800000, 11000000, 4, 7900000, 11000000, 10, 1500000,
	9600000, 9, 1400000, 7400000, 11, 300000, 1500000, 8, 100000, 1500000, 12,
	100000, 2100000, 2, 400004, 11000000, 3, 3200000, 3700000, 0, 3200000,
	3700000, 10, 1900000, 2400000, 9, 1900000, 2400000, 12, 200000, 300000, 2,
	400004, 3700000, 5, 1700000, 4900000, 1, 1700000, 4900000, 3, 100000, 8900000,
	0, 1800000, 8900000, 4, 7900000, 8900000, 10, 1500000, 7500000, 9, 1400000,
	6300000, 11, 300000, 1400001, 8, 100000, 1400005, 12, 100000, 1500000, 2,
	400004, 8900000, 5, 400000, 8500000, 1, 400000, 8500000, 3, 1500000, 7100000,
	0, 1800000, 7100000, 10, 1500000, 5800000, 9, 1400000, 5000000, 11, 600000,
	1600004, 8, 1200000, 1600004, 12, 100000, 1000000, 2, 3700000, 7100000, 5,
	900000, 6400000, 1, 900000, 6400000, 6, 1100000, 1e9, 7, 1100000, 1e9, 3,
	1200000, 8800000, 0, 1800000, 8800000, 4, 7900000, 8800000, 10, 1500000,
	7400000, 9, 1400000, 6300000, 11, 500000, 1400000, 8, 500000, 1400000, 12,
	100000, 1500000, 2, 400004, 8800000, 5, 400000, 7800000, 1, 400000, 7900000,
	3, 600000, 5700000, 0, 1800000, 5700000, 4, 1200000, 7900000, 10, 1500000,
	4400000, 9, 1400000, 4300000, 11, 500000, 1000001, 8, 400002, 1000003, 12,
	100000, 700000, 2, 200000, 5700000, 5, 1900000, 5100000, 1, 1900000, 5100000,
	5, 100005, 7800000, 1, 400000, 7900000, 5, 100000, 6200000, 1, 400000,
	6200000, 5, 400000, 8800000, 1, 400000, 8800000, 5, 100005, 1e9, 1, 400000,
	1e9, 3, 100000, 4300000, 0, 1800000, 4300000, 10, 1500000, 3000000, 9,
	1400000, 3000000, 11, 400000, 900000, 8, 400000, 900000, 12, 100000, 400000,
	2, 400004, 4300000, 5, 300000, 9400000, 1, 400000, 9400000, 11, 700000,
	1100000, 8, 700000, 1100000, 3, 2200000, 4600000, 0, 2500000, 4600000, 12,
	100005, 500000, 2, 400004, 4600000, 10, 1500000, 3300000, 9, 1400000, 3300000,
	5, 300000, 6600000, 1, 400000, 6600000, 11, 900000, 1100000, 8, 900000,
	1100000, 3, 2200000, 4600000, 0, 2500000, 4600000, 10, 1500000, 3300000, 9,
	1400000, 3300000, 12, 100005, 500000, 2, 400004, 4600000, 11, 900000, 1100000,
	8, 900000, 1100000, 3, 2500000, 4600000, 0, 2500000, 4600000, 10, 1500000,
	3300000, 9, 1400000, 3300000, 12, 100005, 500000, 2, 400004, 4600000, 3,
	100000, 6800000, 0, 1800000, 6800000, 10, 1500000, 5500000, 9, 1400000,
	4800000, 11, 400000, 1100000, 12, 100000, 1000000, 2, 400004, 6800000, 5,
	100005, 2700000, 3, 100000, 6800000, 0, 1800000, 6800000, 10, 1500000,
	5500000, 9, 1400000, 4800000, 12, 100000, 1000000, 2, 400004, 6800000, 3,
	100000, 3700000, 0, 1800000, 3700000, 10, 1500000, 2300000, 9, 1400000,
	2400000, 11, 300000, 900000, 12, 100000, 300000, 2, 400004, 3700000, 5,
	100000, 2400000, 6, 800000, 1100000, 7, 800000, 1100000, 5, 2200000, 9400000,
	1, 2200000, 9400000, 5, 2200000, 6600000, 1, 2200000, 6600000, 3, 1300000,
	14800000, 0, 1800000, 14800000, 4, 7900000, 14800000, 10, 1500000, 13200000,
	9, 1400000, 9900000, 11, 600000, 700000, 8, 600000, 700000, 12, 100000, 1e9,
	2, 400004, 14800000, 5, 300006, 6500000, 1, 400000, 6500000, 3, 2500000,
	4600000, 0, 2500000, 4600000, 11, 700000, 1100000, 8, 700000, 1100000, 12,
	100005, 500000, 2, 400004, 4600000, 11, 700000, 1100000, 8, 700000, 1100000,
	3, 2200000, 4600000, 0, 2500000, 4600000, 12, 100005, 500000, 2, 400004,
	4600000, 11, 700000, 1100000, 8, 700000, 1100000, 3, 2500000, 4600000, 0,
	2500000, 4600000, 12, 100005, 500000, 2, 400004, 4600000, 5, 100005, 8100000,
	1, 400000, 8100000, 11, 700000, 1300000, 8, 700000, 1300000, 3, 1600000, 1e9,
	0, 1800000, 1e9, 4, 7900000, 1e9, 10, 1500000, 1e9, 9, 1400000, 1e9, 12,
	100000, 1e9, 3, 1600000, 4800000, 10, 1500000, 3500000, 11, 600000, 1100000,
	8, 600000, 1100000, 5, 1000000, 5000000, 1, 1000000, 5000000, 5, 1700000,
	5000000, 1, 1700000, 5000000, 11, 700000, 1100000, 8, 700000, 1100000, 3,
	1600000, 4800000, 10, 1500000, 3500000, 11, 600000, 1100000, 8, 600000,
	1100000, 3, 1600000, 4800000, 10, 1500000, 3500000, 5, 100000, 300000
]);

// Where each window list begins; the entry after it is where it ends.
const PREFIX_WINDOW_STARTS = new Uint16Array([
	0, 21, 27, 48, 54, 78, 84, 90, 114, 138, 162, 186, 213, 219, 228, 252, 258,
	261, 267, 276, 279, 282, 306, 315, 327, 333, 339, 345, 357, 384, 390, 417,
	441, 450, 453, 465, 471, 495, 519, 525, 531, 537, 558, 561, 585, 591, 615,
	621, 642, 666, 687, 708, 723, 729, 750, 756, 777, 786, 813, 837, 843, 846,
	852, 876, 909, 933, 957, 984, 1011, 1038, 1065, 1092, 1098, 1101, 1104, 1128,
	1155, 1179, 1185, 1191, 1197, 1203, 1212, 1218, 1224, 1230, 1251, 1275, 1281,
	1287, 1293, 1299, 1305, 1329, 1335, 1341, 1365, 1383, 1389, 1395, 1413, 1419,
	1425, 1440, 1467, 1473, 1500, 1506, 1530, 1554, 1560, 1587, 1605, 1611, 1638,
	1644, 1668, 1674, 1680, 1707, 1713, 1740, 1746, 1752, 1758, 1764, 1770, 1794,
	1800, 1824, 1830, 1854, 1878, 1899, 1902, 1920, 1941, 1944, 1950, 1956, 1962,
	1989, 1995, 2013, 2031, 2049, 2055, 2061, 2079, 2091, 2097, 2103, 2115, 2127,
	2130
]);

/** @type {Map<string, [string, number][]>} */
const PREFIXED_PROPERTIES = new Map([
	[
		"align-content",
		[
			["-webkit-align-content", 0],
			["-ms-flex-line-pack", 1]
		]
	],
	[
		"align-items",
		[
			["-webkit-align-items", 0],
			["-ms-flex-align", 1]
		]
	],
	[
		"align-self",
		[
			["-webkit-align-self", 2],
			["-ms-flex-item-align", 1]
		]
	],
	["alt", [["-webkit-alt", 3]]],
	[
		"animation",
		[
			["-webkit-animation", 4],
			["-moz-animation", 5],
			["-o-animation", 6]
		]
	],
	[
		"animation-delay",
		[
			["-webkit-animation-delay", 7],
			["-moz-animation-delay", 5],
			["-o-animation-delay", 6]
		]
	],
	[
		"animation-direction",
		[
			["-webkit-animation-direction", 7],
			["-moz-animation-direction", 5],
			["-o-animation-direction", 6]
		]
	],
	[
		"animation-duration",
		[
			["-webkit-animation-duration", 8],
			["-moz-animation-duration", 5],
			["-o-animation-duration", 6]
		]
	],
	[
		"animation-fill-mode",
		[
			["-webkit-animation-fill-mode", 9],
			["-moz-animation-fill-mode", 5],
			["-o-animation-fill-mode", 6]
		]
	],
	[
		"animation-iteration-count",
		[
			["-webkit-animation-iteration-count", 7],
			["-moz-animation-iteration-count", 5],
			["-o-animation-iteration-count", 6]
		]
	],
	[
		"animation-name",
		[
			["-webkit-animation-name", 7],
			["-moz-animation-name", 5],
			["-o-animation-name", 6]
		]
	],
	[
		"animation-play-state",
		[
			["-webkit-animation-play-state", 10],
			["-moz-animation-play-state", 5],
			["-o-animation-play-state", 6]
		]
	],
	[
		"animation-timing-function",
		[
			["-webkit-animation-timing-function", 7],
			["-moz-animation-timing-function", 5],
			["-o-animation-timing-function", 6]
		]
	],
	[
		"appearance",
		[
			["-webkit-appearance", 11],
			["-moz-appearance", 12]
		]
	],
	["backdrop-filter", [["-webkit-backdrop-filter", 13]]],
	[
		"backface-visibility",
		[
			["-webkit-backface-visibility", 14],
			["-moz-backface-visibility", 15]
		]
	],
	[
		"background-clip",
		[
			["-moz-background-clip", 16],
			["-webkit-background-clip", 17]
		]
	],
	["background-origin", [["-moz-background-origin", 16]]],
	[
		"background-size",
		[
			["-webkit-background-size", 18],
			["-moz-background-size", 19],
			["-o-background-size", 20]
		]
	],
	["block-size", [["-webkit-logical-height", 21]]],
	[
		"border-bottom-left-radius",
		[
			["-webkit-border-bottom-left-radius", 22],
			["-moz-border-radius-bottomleft", 16]
		]
	],
	[
		"border-bottom-right-radius",
		[
			["-webkit-border-bottom-right-radius", 22],
			["-moz-border-radius-bottomright", 16]
		]
	],
	[
		"border-image",
		[
			["-webkit-border-image", 23],
			["-moz-border-image", 24],
			["-o-border-image", 25]
		]
	],
	["border-inline-end-color", [["-moz-border-end-color", 26]]],
	["border-inline-end-style", [["-moz-border-end-style", 26]]],
	["border-inline-end-width", [["-moz-border-end-width", 26]]],
	["border-inline-start-color", [["-moz-border-start-color", 26]]],
	["border-inline-start-style", [["-moz-border-start-style", 26]]],
	[
		"border-radius",
		[
			["-webkit-border-radius", 27],
			["-moz-border-radius", 16]
		]
	],
	[
		"border-top-left-radius",
		[
			["-webkit-border-top-left-radius", 22],
			["-moz-border-radius-topleft", 16]
		]
	],
	[
		"border-top-right-radius",
		[
			["-webkit-border-top-right-radius", 22],
			["-moz-border-radius-topright", 16]
		]
	],
	[
		"box-align",
		[
			["-webkit-box-align", 28],
			["-moz-box-align", 29]
		]
	],
	["box-decoration-break", [["-webkit-box-decoration-break", 30]]],
	[
		"box-direction",
		[
			["-webkit-box-direction", 28],
			["-moz-box-direction", 29]
		]
	],
	[
		"box-flex",
		[
			["-webkit-box-flex", 28],
			["-moz-box-flex", 29]
		]
	],
	["box-flex-group", [["-webkit-box-flex-group", 31]]],
	["box-lines", [["-webkit-box-lines", 31]]],
	[
		"box-ordinal-group",
		[
			["-webkit-box-ordinal-group", 28],
			["-moz-box-ordinal-group", 29]
		]
	],
	[
		"box-orient",
		[
			["-webkit-box-orient", 28],
			["-moz-box-orient", 29]
		]
	],
	[
		"box-pack",
		[
			["-webkit-box-pack", 28],
			["-moz-box-pack", 29]
		]
	],
	[
		"box-shadow",
		[
			["-webkit-box-shadow", 32],
			["-moz-box-shadow", 33]
		]
	],
	[
		"box-sizing",
		[
			["-webkit-box-sizing", 34],
			["-moz-box-sizing", 35]
		]
	],
	["clip-path", [["-webkit-clip-path", 36]]],
	[
		"column-count",
		[
			["-webkit-column-count", 37],
			["-moz-column-count", 38]
		]
	],
	[
		"column-fill",
		[
			["-moz-column-fill", 39],
			["-webkit-column-fill", 40]
		]
	],
	[
		"column-gap",
		[
			["-webkit-column-gap", 41],
			["-moz-column-gap", 42]
		]
	],
	[
		"column-rule",
		[
			["-webkit-column-rule", 43],
			["-moz-column-rule", 44]
		]
	],
	[
		"column-rule-color",
		[
			["-webkit-column-rule-color", 43],
			["-moz-column-rule-color", 44]
		]
	],
	[
		"column-rule-style",
		[
			["-webkit-column-rule-style", 43],
			["-moz-column-rule-style", 44]
		]
	],
	[
		"column-rule-width",
		[
			["-webkit-column-rule-width", 43],
			["-moz-column-rule-width", 44]
		]
	],
	["column-span", [["-webkit-column-span", 45]]],
	[
		"column-width",
		[
			["-webkit-column-width", 43],
			["-moz-column-width", 38]
		]
	],
	[
		"columns",
		[
			["-moz-columns", 46],
			["-webkit-columns", 47]
		]
	],
	["filter", [["-webkit-filter", 48]]],
	[
		"flex",
		[
			["-webkit-flex", 2],
			["-ms-flex", 1]
		]
	],
	[
		"flex-basis",
		[
			["-webkit-flex-basis", 49],
			["-ms-flex-preferred-size", 1]
		]
	],
	[
		"flex-direction",
		[
			["-webkit-flex-direction", 2],
			["-ms-flex-direction", 1]
		]
	],
	[
		"flex-flow",
		[
			["-webkit-flex-flow", 2],
			["-ms-flex-flow", 1]
		]
	],
	[
		"flex-grow",
		[
			["-webkit-flex-grow", 49],
			["-ms-flex-positive", 1]
		]
	],
	[
		"flex-shrink",
		[
			["-webkit-flex-shrink", 50],
			["-ms-flex-negative", 1]
		]
	],
	[
		"flex-wrap",
		[
			["-webkit-flex-wrap", 0],
			["-ms-flex-wrap", 1]
		]
	],
	[
		"font-feature-settings",
		[
			["-webkit-font-feature-settings", 51],
			["-moz-font-feature-settings", 52]
		]
	],
	["font-kerning", [["-webkit-font-kerning", 53]]],
	["font-language-override", [["-moz-font-language-override", 54]]],
	["font-variant-ligatures", [["-webkit-font-variant-ligatures", 55]]],
	["forced-color-adjust", [["-ms-high-contrast-adjust", 56]]],
	["hyphenate-character", [["-webkit-hyphenate-character", 57]]],
	[
		"hyphens",
		[
			["-webkit-hyphens", 58],
			["-ms-hyphens", 56],
			["-moz-hyphens", 59]
		]
	],
	["ime-mode", [["-ms-ime-mode", 60]]],
	["initial-letter", [["-webkit-initial-letter", 61]]],
	["inline-size", [["-webkit-logical-width", 21]]],
	[
		"justify-content",
		[
			["-webkit-justify-content", 2],
			["-ms-flex-pack", 1]
		]
	],
	["line-break", [["-webkit-line-break", 62]]],
	["line-clamp", [["-webkit-line-clamp", 63]]],
	["margin-block-end", [["-webkit-margin-after", 64]]],
	["margin-block-start", [["-webkit-margin-before", 64]]],
	[
		"margin-inline-end",
		[
			["-webkit-margin-end", 65],
			["-moz-margin-end", 26]
		]
	],
	[
		"margin-inline-start",
		[
			["-webkit-margin-start", 65],
			["-moz-margin-start", 26]
		]
	],
	["mask", [["-webkit-mask", 66]]],
	["mask-border", [["-webkit-mask-box-image", 67]]],
	["mask-border-outset", [["-webkit-mask-box-image-outset", 67]]],
	["mask-border-repeat", [["-webkit-mask-box-image-repeat", 67]]],
	["mask-border-slice", [["-webkit-mask-box-image-slice", 67]]],
	["mask-border-source", [["-webkit-mask-box-image-source", 67]]],
	["mask-border-width", [["-webkit-mask-box-image-width", 67]]],
	["mask-clip", [["-webkit-mask-clip", 68]]],
	["mask-image", [["-webkit-mask-image", 69]]],
	["mask-origin", [["-webkit-mask-origin", 68]]],
	["mask-position", [["-webkit-mask-position", 66]]],
	["mask-repeat", [["-webkit-mask-repeat", 66]]],
	["mask-size", [["-webkit-mask-size", 70]]],
	["max-block-size", [["-webkit-max-logical-height", 21]]],
	["max-inline-size", [["-webkit-max-logical-width", 21]]],
	["min-block-size", [["-webkit-min-logical-height", 21]]],
	["min-inline-size", [["-webkit-min-logical-width", 21]]],
	["object-fit", [["-o-object-fit", 71]]],
	["object-position", [["-o-object-position", 71]]],
	[
		"order",
		[
			["-webkit-order", 2],
			["-ms-flex-order", 1]
		]
	],
	["outline", [["-moz-outline", 72]]],
	["outline-color", [["-moz-outline-color", 73]]],
	["outline-style", [["-moz-outline-style", 73]]],
	["outline-width", [["-moz-outline-width", 73]]],
	[
		"padding-inline-end",
		[
			["-webkit-padding-end", 65],
			["-moz-padding-end", 26]
		]
	],
	[
		"padding-inline-start",
		[
			["-webkit-padding-start", 65],
			["-moz-padding-start", 26]
		]
	],
	[
		"perspective",
		[
			["-webkit-perspective", 74],
			["-moz-perspective", 15]
		]
	],
	[
		"perspective-origin",
		[
			["-webkit-perspective-origin", 74],
			["-moz-perspective-origin", 15]
		]
	],
	["print-color-adjust", [["-webkit-print-color-adjust", 75]]],
	["ruby-position", [["-webkit-ruby-position", 76]]],
	[
		"scroll-snap-type",
		[
			["-ms-scroll-snap-type", 56],
			["-webkit-scroll-snap-type", 77]
		]
	],
	["shape-image-threshold", [["-webkit-shape-image-threshold", 78]]],
	["shape-margin", [["-webkit-shape-margin", 78]]],
	["shape-outside", [["-webkit-shape-outside", 78]]],
	[
		"tab-size",
		[
			["-moz-tab-size", 79],
			["-o-tab-size", 25]
		]
	],
	["text-align-last", [["-moz-text-align-last", 80]]],
	["text-combine-upright", [["-ms-text-combine-horizontal", 81]]],
	[
		"text-decoration-color",
		[
			["-moz-text-decoration-color", 82],
			["-webkit-text-decoration-color", 83]
		]
	],
	[
		"text-decoration-line",
		[
			["-moz-text-decoration-line", 82],
			["-webkit-text-decoration-line", 83]
		]
	],
	["text-decoration-skip", [["-webkit-text-decoration-skip", 84]]],
	[
		"text-decoration-style",
		[
			["-moz-text-decoration-style", 82],
			["-webkit-text-decoration-style", 83]
		]
	],
	["text-emphasis", [["-webkit-text-emphasis", 85]]],
	["text-emphasis-color", [["-webkit-text-emphasis-color", 85]]],
	["text-emphasis-position", [["-webkit-text-emphasis-position", 85]]],
	["text-emphasis-style", [["-webkit-text-emphasis-style", 85]]],
	["text-orientation", [["-webkit-text-orientation", 86]]],
	["text-overflow", [["-o-text-overflow", 87]]],
	[
		"text-size-adjust",
		[
			["-webkit-text-size-adjust", 88],
			["-moz-text-size-adjust", 89],
			["-ms-text-size-adjust", 90]
		]
	],
	["text-underline-position", [["-webkit-text-underline-position", 91]]],
	["touch-action", [["-ms-touch-action", 1]]],
	[
		"transform",
		[
			["-webkit-transform", 92],
			["-moz-transform", 93],
			["-ms-transform", 94],
			["-o-transform", 25]
		]
	],
	[
		"transform-origin",
		[
			["-webkit-transform-origin", 95],
			["-moz-transform-origin", 93],
			["-ms-transform-origin", 94],
			["-o-transform-origin", 25]
		]
	],
	[
		"transform-style",
		[
			["-webkit-transform-style", 74],
			["-moz-transform-style", 15]
		]
	],
	[
		"transition",
		[
			["-webkit-transition", 96],
			["-moz-transition", 97],
			["-o-transition", 98]
		]
	],
	[
		"transition-delay",
		[
			["-webkit-transition-delay", 99],
			["-moz-transition-delay", 97],
			["-o-transition-delay", 100]
		]
	],
	[
		"transition-duration",
		[
			["-webkit-transition-duration", 96],
			["-moz-transition-duration", 97],
			["-o-transition-duration", 101]
		]
	],
	[
		"transition-property",
		[
			["-webkit-transition-property", 102],
			["-moz-transition-property", 97],
			["-o-transition-property", 100]
		]
	],
	[
		"transition-timing-function",
		[
			["-webkit-transition-timing-function", 102],
			["-moz-transition-timing-function", 97],
			["-o-transition-timing-function", 100]
		]
	],
	[
		"user-modify",
		[
			["-webkit-user-modify", 103],
			["-moz-user-modify", 104]
		]
	],
	[
		"user-select",
		[
			["-webkit-user-select", 105],
			["-ms-user-select", 56],
			["-moz-user-select", 106]
		]
	],
	["writing-mode", [["-webkit-writing-mode", 107]]]
]);

/** @type {Map<string, [string, number][]>} */
const PREFIXED_SELECTORS = new Map([
	[
		"any-link",
		[
			["-webkit-any-link", 108],
			["-moz-any-link", 109]
		]
	],
	["autofill", [["-webkit-autofill", 110]]],
	[
		"backdrop",
		[
			["-webkit-backdrop", 111],
			["-ms-backdrop", 81]
		]
	],
	["dir", [["-moz-dir", 112]]],
	[
		"file-selector-button",
		[
			["-webkit-file-upload-button", 113],
			["-ms-browse", 56]
		]
	],
	["focus-visible", [["-moz-focusring", 114]]],
	[
		"fullscreen",
		[
			["-webkit-full-screen", 115],
			["-moz-full-screen", 116],
			["-ms-fullscreen", 117]
		]
	],
	[
		"is",
		[
			["-webkit-any", 118],
			["-moz-any", 119]
		]
	],
	[
		"placeholder",
		[
			["-webkit-input-placeholder", 120],
			["-ms-input-placeholder", 60],
			["-moz-placeholder", 121]
		]
	],
	["read-only", [["-moz-read-only", 122]]],
	["read-write", [["-moz-read-write", 122]]],
	["selection", [["-moz-selection", 123]]],
	["user-invalid", [["-moz-ui-invalid", 124]]],
	["user-valid", [["-moz-ui-valid", 124]]]
]);

/** @type {Map<string, [string, number][]>} */
const PREFIXED_AT_RULES = new Map([
	["document", [["-moz-document", 125]]],
	[
		"keyframes",
		[
			["-webkit-keyframes", 126],
			["-moz-keyframes", 5],
			["-o-keyframes", 6]
		]
	]
]);

// WHY: The version a browser that never shipped a construct is given below, and
// the one a spelling still prefixed today is unprefixed at. Finite, a plain
// number and below 2**31, so both version tables are `Uint32Array`s of small
// integers; far past any real version, and past the one Safari TP is read as.
const NEVER = 1e9;

// The browsers every support profile below covers, in the order it states them.
// A selection has an ability when every browser in it is named here and at or
// past the version its profile row gives.
/** @type {string[]} */
const SUPPORT_BROWSERS = [
	"and_chr",
	"and_ff",
	"android",
	"chrome",
	"edge",
	"firefox",
	"ie",
	"ie_mob",
	"ios_saf",
	"op_mob",
	"opera",
	"safari",
	"samsung"
];

// The versions themselves, rows of `SUPPORT_BROWSERS.length` laid end to end,
// one row per distinct profile: a construct names the row it reads rather than
// carrying its own copy of it. `NEVER` is a browser that never shipped it.
const SUPPORT_PROFILES = new Uint32Array([
	6200000, 4900000, 6200000, 6200000, 7900000, 4900000, 1e9, 1e9, 900003,
	4700000, 4900000, 1000000, 800000, 7200000, 8300000, 7200000, 7200000,
	7900000, 8300000, 1e9, 1e9, 1200002, 5100000, 6000000, 1200001, 1100000,
	11500000, 7900000, 11500000, 11500000, 11500000, 7000000, 1e9, 1e9, 1500000,
	7700000, 10100000, 1500000, 2300000, 5600000, 9200000, 5600000, 5600000,
	7900000, 9200000, 1e9, 1e9, 1100000, 4300000, 4300000, 1100000, 600000,
	8800000, 7900000, 8800000, 8800000, 8800000, 7800000, 1e9, 1e9, 1400000,
	6300000, 7400000, 1400000, 1500000, 1e9, 11400000, 1e9, 1e9, 1e9, 11400000,
	1e9, 1e9, 900000, 1e9, 1e9, 900000, 1e9, 8800000, 8400000, 8800000, 8800000,
	8800000, 8400000, 1e9, 1e9, 900000, 1e9, 7400000, 900000, 1500000, 12000000,
	4900000, 12000000, 12000000, 12000000, 4900000, 1e9, 1e9, 1600004, 8000000,
	10600000, 1600004, 2500000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9,
	1e9, 1e9, 1e9, 12000000, 11700000, 12000000, 12000000, 12000000, 11700000,
	1e9, 1e9, 1700002, 8000000, 10600000, 1700002, 2500000, 5700000, 600000,
	5700000, 5700000, 7900000, 600000, 1e9, 1e9, 2600002, 4300000, 4400000,
	2600002, 700000, 8700000, 7900000, 8700000, 8700000, 8700000, 7000000, 1e9,
	1e9, 2600002, 6200000, 7300000, 2600002, 1400000, 11100000, 11300000,
	11100000, 11100000, 11100000, 11300000, 1e9, 1e9, 1500000, 7500000, 9700000,
	1500000, 2200000, 11100000, 11300000, 11100000, 11100000, 11100000, 11300000,
	1e9, 1e9, 1600002, 7500000, 9700000, 1600002, 2200000, 10100000, 9600000,
	10100000, 10100000, 10100000, 9600000, 1e9, 1e9, 1500000, 7000000, 8700000,
	1500000, 1900000, 12300000, 12000000, 12300000, 12300000, 12300000, 12000000,
	1e9, 1e9, 1700005, 8200000, 10900000, 1700005, 2700000, 11100000, 11300000,
	11100000, 11100000, 11100000, 11300000, 1e9, 1e9, 1500004, 7500000, 9700000,
	1500004, 2200000, 8700000, 6600000, 8700000, 8700000, 8700000, 6600000, 1e9,
	1e9, 1400005, 6200000, 7300000, 1400001, 1400000, 10400000, 10200000,
	10400000, 10400000, 10400000, 10200000, 1e9, 1e9, 1600004, 7100000, 9000000,
	1600004, 2000000, 6800000, 6100000, 6800000, 6800000, 7900000, 6100000, 1e9,
	1e9, 1300004, 4800000, 5500000, 1300001, 1000000, 5900000, 4500000, 5900000,
	5900000, 7900000, 4500000, 1e9, 1e9, 1100000, 4300000, 4600000, 1100000,
	700000, 1800000, 400000, 400004, 100000, 1200000, 100005, 900000, 900000,
	300002, 1000001, 700000, 400000, 100000, 3700000, 4700000, 3700000, 3700000,
	7900000, 4700000, 1e9, 1e9, 1500004, 2400000, 2400000, 1500004, 300000,
	1800000, 400000, 400004, 100000, 1200000, 100005, 900000, 900000, 300000,
	1000001, 700000, 400000, 100000, 13300000, 1e9, 13300000, 13300000, 13300000,
	1e9, 1e9, 1e9, 2700000, 8800000, 11800000, 2700000, 2900000, 2600000, 5500000,
	400004, 2600000, 7900000, 5500000, 1e9, 1e9, 700000, 1400000, 1500000, 700000,
	100005, 13100000, 14300000, 13100000, 13100000, 13100000, 14300000, 1e9, 1e9,
	1800004, 8700000, 11600000, 1800004, 2900000, 8900000, 8200000, 8900000,
	8900000, 8900000, 8200000, 1e9, 1e9, 1400005, 6300000, 7500000, 1400001,
	1500000, 1800000, 400000, 3700000, 100000, 1200000, 100000, 900000, 900000,
	100000, 1000001, 700000, 100000, 100000, 1800000, 400000, 400004, 100000,
	1200000, 100000, 900000, 900000, 100000, 1000001, 700000, 100000, 100000,
	12100000, 1e9, 12100000, 12100000, 12100000, 1e9, 1e9, 1e9, 1700004, 8100000,
	10700000, 1700004, 2500000, 10500000, 14900000, 10500000, 10500000, 10500000,
	14900000, 1e9, 1e9, 1700002, 7200000, 9100000, 1700002, 2000000, 8600000,
	6800000, 8600000, 8600000, 8600000, 6800000, 1e9, 1e9, 1100003, 6100000,
	7200000, 1100001, 1400000, 7300000, 7900000, 7300000, 7300000, 7900000,
	7200000, 1e9, 1e9, 1300004, 5200000, 6000000, 1300001, 1100000, 13500000, 1e9,
	13500000, 13500000, 13500000, 1e9, 1e9, 1e9, 2700000, 8900000, 12000000,
	2700000, 2900000, 5700000, 5100000, 5700000, 5700000, 7900000, 5100000, 1e9,
	1e9, 1000003, 4300000, 4400000, 1000001, 700000, 1800000, 6200000, 3700000,
	100000, 1200000, 6200000, 900000, 900000, 1e9, 1400000, 900005, 100001,
	100000, 5000000, 6300000, 5000000, 5000000, 7900000, 6300000, 1e9, 1e9,
	1000000, 3700000, 3700000, 1000000, 500000, 8900000, 13100000, 8900000,
	8900000, 8900000, 13100000, 1e9, 1e9, 1800002, 6300000, 7500000, 1800002,
	1500000, 10900000, 14400000, 10900000, 10900000, 10900000, 14400000, 1e9, 1e9,
	1800000, 7400000, 9500000, 1800000, 2100000, 1800000, 400000, 400004, 100000,
	1200000, 100000, 400000, 400000, 100000, 1000001, 500000, 100000, 100000,
	12500000, 14400000, 12500000, 12500000, 12500000, 14400000, 1e9, 1e9, 1800000,
	8300000, 11100000, 1800000, 2700000, 12500000, 14700000, 12500000, 12500000,
	12500000, 14700000, 1e9, 1e9, 1800002, 8300000, 11100000, 1800002, 2700000,
	6500000, 5000000, 6500000, 6500000, 7900000, 5000000, 1e9, 1e9, 900000,
	4700000, 5200000, 900000, 900000, 11000000, 8600000, 11000000, 11000000,
	11000000, 8600000, 1e9, 1e9, 1500000, 7400000, 9600000, 1500000, 2100000,
	15200000, 15000000, 15200000, 15200000, 15200000, 15000000, 1e9, 1e9, 1500004,
	1e9, 13600000, 1500004, 1e9, 1800000, 400000, 200000, 100000, 1200000, 100000,
	900000, 900000, 200000, 1000001, 900000, 300001, 100000, 1800000, 400000,
	3700000, 1000000, 7900000, 400000, 1e9, 1e9, 500000, 1000001, 1000000, 500000,
	100000, 5400000, 6300000, 5400000, 5400000, 7900000, 6300000, 1e9, 1e9,
	1000000, 4100000, 4100000, 1000000, 600000, 1800000, 400000, 200000, 100000,
	1200000, 100000, 900000, 900000, 200000, 1000001, 900005, 300001, 100000,
	1800000, 11600000, 400004, 1800000, 1200000, 11600000, 800000, 800000, 600000,
	1000001, 900002, 600000, 100000, 1800000, 400000, 400004, 400000, 1200000,
	300000, 700000, 700000, 400000, 1000001, 900005, 300001, 100000, 1800000,
	400000, 200000, 100000, 1200000, 300005, 900000, 900000, 200000, 1000001,
	900005, 300001, 100000, 1800000, 400000, 400004, 100000, 1200000, 100000,
	800000, 800000, 100000, 1000001, 700000, 100000, 100000, 8600000, 8500000,
	8600000, 8600000, 8600000, 8500000, 1e9, 1e9, 1500004, 6100000, 7200000,
	1500004, 1400000, 6000000, 5200000, 6000000, 6000000, 7900000, 5200000, 1e9,
	1e9, 1000003, 4400000, 4700000, 1000001, 800000, 7100000, 6400000, 7100000,
	7100000, 1200000, 6400000, 1e9, 1e9, 1600004, 5000000, 5800000, 1600004,
	1000000, 2500000, 1e9, 400004, 2300000, 7900000, 1e9, 1e9, 1e9, 700000,
	1400000, 1500000, 700000, 100005, 10500000, 12100000, 10500000, 10500000,
	10500000, 12100000, 1e9, 1e9, 1500004, 7200000, 9100000, 1500004, 2000000,
	1e9, 13600000, 1e9, 1e9, 1e9, 13600000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9,
	5400000, 1e9, 5400000, 5400000, 7900000, 1e9, 1e9, 1e9, 1e9, 4100000, 4100000,
	1e9, 600000, 1800000, 400000, 400004, 100000, 1200000, 100000, 400000, 400000,
	100000, 1000001, 400000, 200000, 100000, 1800000, 1600000, 200002, 1000000,
	1300000, 2900000, 1e9, 1e9, 500000, 1100000, 1100000, 500001, 100000, 1800000,
	400000, 400004, 100000, 1200000, 200000, 1000000, 1000000, 100000, 1000001,
	900000, 300000, 100000, 1800000, 400000, 3700000, 1000000, 1200000, 400000,
	1000000, 1000000, 500000, 1000001, 1000000, 500000, 100000, 1800000, 400000,
	400004, 100000, 1200000, 100000, 800000, 800000, 200000, 1000001, 800000,
	300001, 100000, 1800000, 400000, 400004, 100000, 1200000, 100000, 900000,
	900000, 200000, 1000001, 900005, 300001, 100000, 1800000, 1e9, 400004, 600000,
	1200000, 1e9, 800000, 800000, 400002, 1000001, 900002, 500000, 100000,
	1800000, 400000, 100005, 100000, 1200000, 100000, 300000, 300000, 300002,
	1400000, 300005, 100000, 100000, 10500000, 10300000, 10500000, 10500000,
	10500000, 10300000, 1e9, 1e9, 1500006, 7200000, 9100000, 1500006, 2000000,
	1800000, 400000, 400004, 100000, 1200000, 300005, 900000, 900000, 200000,
	1000001, 900005, 300001, 100000, 1800000, 400000, 400004, 400000, 1200000,
	300005, 900000, 900000, 200000, 1000001, 900000, 300001, 100000, 1800000,
	400000, 200000, 400000, 1200000, 300005, 900000, 900000, 200000, 1000001,
	900005, 300001, 100000, 1800000, 400000, 400004, 200000, 1200000, 100005,
	900000, 900000, 200000, 1000001, 900005, 300001, 100000, 13300000, 13600000,
	13300000, 13300000, 13300000, 13600000, 1e9, 1e9, 2600005, 8800000, 11800000,
	2600005, 2900000, 11000000, 1e9, 11000000, 11000000, 11000000, 15300000, 1e9,
	1e9, 1300004, 7400000, 9600000, 1300001, 2100000, 4700000, 5100000, 4700000,
	4700000, 7900000, 5100000, 1e9, 1e9, 900000, 3400000, 3400000, 900000, 500000,
	11400000, 12500000, 11400000, 11400000, 11400000, 12500000, 1e9, 1e9, 1700000,
	7600000, 10000000, 1700000, 2300000, 1800000, 7900000, 400004, 100000,
	1300000, 7800000, 1e9, 1e9, 300002, 1000001, 900000, 400000, 100000, 1800000,
	400000, 400004, 1000000, 1200000, 400000, 1000000, 1000000, 500000, 1000001,
	1000000, 500000, 100000, 1800000, 400000, 3700000, 100000, 1200000, 100000,
	900000, 900000, 100000, 1400000, 900005, 100000, 100000, 2700000, 3200000,
	400004, 2700000, 7900000, 3200000, 1e9, 1e9, 700000, 1500000, 1500000, 700000,
	100005, 12500000, 12600000, 12500000, 12500000, 12500000, 12600000, 1e9, 1e9,
	1e9, 8300000, 11100000, 1700004, 2700000, 1800000, 400000, 200000, 100000,
	1200000, 100000, 900000, 900000, 200000, 1000001, 900005, 100003, 100000,
	11900000, 8800000, 11900000, 11900000, 11900000, 8800000, 1e9, 1e9, 1600005,
	7900000, 10500000, 1600005, 2500000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 400000, 400000, 100000, 1000001, 300005, 100000, 100000, 9300000,
	9200000, 9300000, 9300000, 9300000, 9200000, 1e9, 1e9, 1500004, 6600000,
	7900000, 1500004, 1700000, 2900000, 2800000, 400004, 2900000, 1200000,
	2800000, 1100000, 1100000, 900000, 1600000, 1600000, 900000, 200000, 12500000,
	14700000, 12500000, 12500000, 12500000, 14700000, 1e9, 1e9, 2600000, 8300000,
	11100000, 2600000, 2700000, 2500000, 2800000, 400004, 2100000, 7900000,
	2800000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100005, 1800000,
	15300000, 400004, 100000, 7900000, 15300000, 1e9, 1e9, 500000, 1400000,
	1500000, 500001, 100000, 1800000, 14900000, 400004, 100000, 7900000, 14900000,
	1e9, 1e9, 500000, 1400000, 1500000, 500001, 100000, 1800000, 1e9, 400004,
	100000, 7900000, 1e9, 1e9, 1e9, 500000, 1400000, 1500000, 500001, 100000,
	1800000, 500000, 400004, 300000, 1200000, 500000, 1e9, 1e9, 300002, 1400000,
	1500000, 400000, 100000, 1800000, 500000, 400004, 300000, 7900000, 500000,
	1e9, 1e9, 300002, 1400000, 1500000, 400000, 100000, 11200000, 11500000,
	11200000, 11200000, 11200000, 11500000, 1e9, 1e9, 1600000, 7500000, 9800000,
	1600000, 2300000, 1800000, 500000, 400004, 300000, 1200000, 500000, 1000000,
	1000000, 300002, 1400000, 1500000, 400000, 100000, 2500000, 1600000, 400004,
	1900000, 1200000, 1600000, 1000000, 1000000, 600000, 1200001, 1200001, 600000,
	100005, 11500000, 1e9, 11500000, 11500000, 11500000, 1e9, 1e9, 1e9, 1800004,
	7700000, 10100000, 1800004, 2300000, 1800000, 500000, 400004, 300000, 1200000,
	500000, 1000000, 1000000, 400002, 1400000, 1500000, 500000, 100000, 14600000,
	1e9, 14600000, 14600000, 14600000, 1e9, 1e9, 1e9, 1e9, 9700000, 13000000, 1e9,
	1e9, 8300000, 8000000, 8300000, 8300000, 8300000, 8000000, 1e9, 1e9, 1500004,
	5900000, 6900000, 1500004, 1300000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 1e9, 1e9, 200000, 1400000, 1500000, 300000, 100000, 1800000, 8000000,
	400004, 100000, 1200000, 8000000, 1e9, 1e9, 100000, 1400000, 1500000, 300000,
	100000, 1800000, 5400000, 400004, 100000, 1200000, 5400000, 1e9, 1e9, 300000,
	1400000, 1500000, 300000, 100000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 1e9, 1e9, 100000, 1400000, 1500000, 300000, 100000, 8800000, 8900000,
	8800000, 8800000, 8800000, 8900000, 1e9, 1e9, 1500000, 6300000, 7400000,
	1500000, 1500000, 7600000, 10300000, 7600000, 7600000, 7900000, 10300000, 1e9,
	1e9, 900000, 5400000, 6300000, 900000, 1200000, 1800000, 1000000, 400004,
	1200000, 1200000, 1000000, 1e9, 1e9, 500000, 1400000, 1500000, 500001, 100000,
	3100000, 5000000, 400004, 3100000, 1500000, 5000000, 1e9, 1e9, 900003,
	1800000, 1800000, 900001, 200000, 1800000, 5000000, 400004, 1500000, 1500000,
	5000000, 1e9, 1e9, 900003, 1400000, 1500000, 900001, 100000, 1800000, 400000,
	400004, 100000, 1200000, 100000, 1e9, 1e9, 100000, 1400000, 1500000, 100000,
	100000, 1800000, 400000, 3700000, 100000, 1200000, 200000, 900000, 900000,
	500000, 1400000, 1000005, 1500004, 100000, 1800000, 2500000, 3700000, 100000,
	1200000, 2500000, 900000, 900000, 1500004, 1400000, 1000005, 1500004, 100000,
	1800000, 400000, 400004, 100000, 1200000, 100000, 400000, 400000, 300002,
	1400000, 1500000, 100000, 100000, 15000000, 1e9, 15000000, 15000000, 15000000,
	1e9, 1e9, 1e9, 1800002, 10100000, 13400000, 1800002, 1e9, 1800000, 400000,
	400004, 100000, 1200000, 400000, 900000, 900000, 200000, 1400000, 1500000,
	300000, 100000, 1800000, 400000, 400004, 100000, 1200000, 400000, 900000,
	900000, 100000, 1100000, 1000005, 300000, 100000, 12000000, 4900000, 12000000,
	12000000, 12000000, 4900000, 1e9, 1e9, 1400000, 8000000, 10600000, 1400000,
	2500000, 1800000, 400000, 400004, 100000, 1200000, 100000, 400000, 400000,
	100000, 1400000, 1500000, 100000, 100000, 1800000, 400000, 400000, 100000,
	1200000, 400000, 900000, 900000, 100000, 1100000, 1000005, 300000, 100000,
	1800000, 400000, 400004, 100000, 7900000, 100000, 1e9, 1e9, 100000, 1400000,
	1500000, 100000, 100000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 2600000, 1e9,
	1e9, 2600000, 1e9, 3000000, 4900000, 400004, 3000000, 1200000, 4900000,
	900000, 900000, 800000, 1800000, 1700000, 800000, 200000, 1800000, 400000,
	400004, 100000, 1200000, 300006, 1100000, 1100000, 200000, 1400000, 1500000,
	300000, 100000, 1800000, 400000, 3700000, 300000, 1200000, 300006, 900000,
	900000, 400002, 1400000, 1000000, 500000, 100000, 1800000, 1e9, 400004,
	100000, 7900000, 1e9, 1e9, 1e9, 300002, 1400000, 1500000, 400000, 100000,
	1800000, 14900000, 400004, 100000, 7900000, 14900000, 1e9, 1e9, 300002,
	1400000, 1500000, 400000, 100000, 11100000, 11500000, 11100000, 11100000,
	11100000, 11500000, 1e9, 1e9, 1e9, 7500000, 9700000, 1e9, 2200000, 1800000,
	4100000, 400004, 800000, 7900000, 4100000, 1e9, 1e9, 500000, 1400000, 1500000,
	500001, 100000, 5700000, 9400000, 5700000, 5700000, 7900000, 9400000, 1e9,
	1e9, 1200002, 4300000, 4400000, 1200001, 700000, 5700000, 6600000, 5700000,
	5700000, 7900000, 6600000, 1e9, 1e9, 1200002, 4300000, 4400000, 1200001,
	500000, 6900000, 4100000, 6900000, 6900000, 7900000, 4100000, 1e9, 1e9,
	1200002, 4800000, 5600000, 1200001, 1000000, 1800000, 400000, 400004, 100000,
	7900000, 100000, 1e9, 1e9, 100000, 1400000, 1500000, 100001, 100000, 1800000,
	1500000, 400004, 1600000, 1200000, 1500000, 1100000, 1100000, 600000, 1400000,
	1500000, 600000, 100000, 1800000, 400000, 400004, 1600000, 1200000, 300005,
	1e9, 1e9, 200000, 1400000, 1500000, 300000, 100000, 1800000, 1500000, 400004,
	1500000, 1200000, 1500000, 1100000, 1100000, 900003, 1400000, 1500000, 600000,
	100000, 3000000, 1500000, 400004, 3000000, 1200000, 1500000, 1100000, 1100000,
	900003, 1800000, 1700000, 900001, 200000, 5600000, 5000000, 5600000, 5600000,
	1200000, 5000000, 1100000, 1100000, 900003, 4300000, 4300000, 900001, 600000,
	1800000, 1500000, 400004, 1500000, 1200000, 1500000, 1e9, 1e9, 600000,
	1400000, 1500000, 600000, 100000, 1800000, 1400000, 400004, 100000, 1200000,
	100000, 1e9, 1e9, 100000, 1400000, 1500000, 100000, 100000, 14700000, 1e9,
	14700000, 14700000, 14700000, 1e9, 1e9, 1e9, 1e9, 9800000, 13100000, 1e9, 1e9,
	1800000, 400000, 400004, 100000, 1200000, 100000, 1100000, 1100000, 100000,
	1400000, 1500000, 100000, 100000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 1e9, 1e9, 300000, 1400000, 1500000, 100000, 100000, 13000000, 3200000,
	13000000, 13000000, 13000000, 3200000, 1e9, 1e9, 700000, 8600000, 11500000,
	700000, 2800000, 1800000, 400000, 400004, 100000, 1200000, 300005, 900000,
	900000, 400002, 1400000, 1000005, 500000, 100000, 1800000, 400000, 400004,
	100000, 1200000, 300005, 1e9, 1e9, 200000, 1400000, 1500000, 300000, 100000,
	1800000, 400000, 400004, 100000, 1200000, 100000, 1100000, 1100000, 200000,
	1400000, 1500000, 300000, 100000, 1e9, 6500000, 1e9, 1e9, 1e9, 6500000, 1e9,
	1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 5000000, 6500000, 5000000, 5000000, 7900000,
	6500000, 1e9, 1e9, 1000000, 3700000, 3700000, 1000000, 500000, 5000000, 1e9,
	5000000, 5000000, 7900000, 1e9, 1e9, 1e9, 1e9, 3700000, 3700000, 1e9, 500000,
	5000000, 1e9, 5000000, 5000000, 7900000, 1e9, 1e9, 1e9, 1000000, 3700000,
	3700000, 1000000, 500000, 5000000, 9200000, 5000000, 5000000, 7900000,
	9200000, 1e9, 1e9, 1000000, 3700000, 3700000, 1000000, 500000, 14000000, 1e9,
	14000000, 14000000, 14000000, 1e9, 1e9, 1e9, 1e9, 9200000, 12400000, 1e9,
	3000000, 5700000, 5300000, 5700000, 5700000, 7900000, 5300000, 1e9, 1e9,
	1100003, 4300000, 4400000, 1100001, 700000, 14400000, 1e9, 14400000, 14400000,
	14400000, 1e9, 1e9, 1e9, 1e9, 9500000, 12800000, 1e9, 1e9, 11800000, 5500000,
	11800000, 11800000, 11800000, 5500000, 1e9, 1e9, 1500000, 7900000, 10400000,
	1500000, 2500000, 11900000, 5400000, 11900000, 11900000, 11900000, 5400000,
	1e9, 1e9, 1300000, 7900000, 10500000, 1300000, 2500000, 11900000, 5100000,
	11900000, 11900000, 11900000, 5100000, 1e9, 1e9, 1300004, 7900000, 10500000,
	1300001, 2500000, 11900000, 5400000, 11900000, 11900000, 11900000, 5400000,
	1e9, 1e9, 1300004, 7900000, 10500000, 1300001, 2500000, 1800000, 400000,
	400004, 1500000, 7900000, 300005, 1e9, 1e9, 400002, 1400000, 1500000, 500000,
	100000, 1800000, 400000, 400004, 100000, 7900000, 300000, 1e9, 1e9, 200000,
	1400000, 1500000, 300000, 100000, 2800000, 2200000, 400004, 2800000, 7900000,
	2200000, 1e9, 1e9, 900000, 1500000, 1500000, 900000, 100005, 8100000, 9600000,
	8100000, 8100000, 8100000, 9600000, 1e9, 1e9, 1300000, 5800000, 6800000,
	1300000, 1300000, 9800000, 9600000, 9800000, 9800000, 9800000, 9600000, 1e9,
	1e9, 1300000, 6800000, 8400000, 1300000, 1800000, 1800000, 400000, 400004,
	100000, 1200000, 100005, 1e9, 1e9, 200000, 1400000, 1500000, 300000, 100000,
	5000000, 1700000, 5000000, 5000000, 1200000, 1700000, 1100000, 1100000,
	800000, 3700000, 3700000, 800000, 500000, 1800000, 400000, 400004, 100000,
	1200000, 100005, 1000000, 1000000, 200000, 1100001, 1100001, 300000, 100000,
	14500000, 1e9, 14500000, 14500000, 14500000, 1e9, 1e9, 1e9, 1e9, 9600000,
	12900000, 1e9, 1e9, 1800000, 7900000, 400004, 600000, 1200000, 7100000, 1e9,
	1e9, 500000, 1400000, 1500000, 500001, 100000, 5000000, 2200000, 5000000,
	5000000, 1200000, 900000, 1e9, 1e9, 300002, 3700000, 3700000, 300000, 500000,
	5200000, 7900000, 5200000, 5200000, 7900000, 6900000, 1e9, 1e9, 1500004,
	4100000, 3900000, 1500004, 600000, 10500000, 10100000, 10500000, 10500000,
	10500000, 10100000, 1e9, 1e9, 1600000, 7200000, 9100000, 1600000, 2000000,
	5200000, 10300000, 5200000, 5200000, 7900000, 10300000, 1e9, 1e9, 2700000,
	4100000, 3900000, 2700000, 600000, 9800000, 10700000, 9800000, 9800000,
	9800000, 10700000, 1e9, 1e9, 1700000, 6800000, 8400000, 1700000, 1800000,
	10500000, 11000000, 10500000, 10500000, 10500000, 11000000, 1e9, 1e9, 1600000,
	7200000, 9100000, 1600000, 2000000, 10900000, 11000000, 10900000, 10900000,
	10900000, 11000000, 1e9, 1e9, 1600000, 7400000, 9500000, 1600000, 2100000,
	13300000, 1e9, 13300000, 13300000, 13300000, 1e9, 1e9, 1e9, 1e9, 8800000,
	11800000, 1e9, 2900000, 8500000, 12500000, 8500000, 8500000, 8500000,
	12500000, 1e9, 1e9, 2600000, 6000000, 7100000, 2600000, 1400000, 8500000,
	12500000, 8500000, 8500000, 8500000, 12500000, 1e9, 1e9, 1800000, 6000000,
	7100000, 1800000, 1400000, 13900000, 1e9, 13900000, 13900000, 13900000, 1e9,
	1e9, 1e9, 1e9, 9100000, 12300000, 1e9, 3000000, 1800000, 2500000, 400004,
	200000, 1200000, 100000, 1100000, 1100000, 200000, 1400000, 1500000, 300000,
	100000, 8500000, 6800000, 8500000, 8500000, 8500000, 6800000, 1e9, 1e9,
	1700002, 6000000, 7100000, 1700002, 1400000, 1800000, 9500000, 400004, 100000,
	1200000, 100005, 1000000, 1000000, 1e9, 1400000, 1000006, 300000, 100000,
	1800000, 9500000, 400004, 100000, 1200000, 100005, 600000, 600000, 1e9,
	1400000, 1000006, 300000, 100000, 1800000, 9500000, 400004, 100000, 1200000,
	100000, 400000, 400000, 1300004, 1400000, 700000, 100002, 100000, 1800000,
	9500000, 400004, 100000, 1200000, 100005, 1000000, 1000000, 1300004, 1400000,
	1000006, 300000, 100000, 1800000, 9500000, 400004, 100000, 1200000, 100000,
	400000, 400000, 1e9, 1400000, 700000, 100002, 100000, 6800000, 9500000,
	6800000, 6800000, 1400000, 2700000, 1e9, 1e9, 1e9, 4800000, 5500000, 1100000,
	1000000, 6800000, 9500000, 6800000, 6800000, 7900000, 2700000, 1e9, 1e9, 1e9,
	4800000, 5500000, 1100000, 1000000, 1800000, 9500000, 400004, 500000, 1200000,
	300000, 900000, 900000, 1e9, 1400000, 1500000, 500000, 100000, 1800000,
	9500000, 400004, 100000, 1200000, 100000, 600000, 600000, 1e9, 1400000,
	700000, 100002, 100000, 1800000, 9500000, 400004, 100000, 1200000, 100005,
	1e9, 1e9, 1e9, 1400000, 1000006, 300000, 100000, 3700000, 9500000, 3700000,
	3700000, 1200000, 2400000, 1e9, 1e9, 1e9, 2400000, 2400000, 900000, 300000,
	5200000, 9700000, 5200000, 5200000, 7900000, 9700000, 1e9, 1e9, 1e9, 4100000,
	3900000, 1e9, 600000, 1800000, 400000, 400004, 200000, 1200000, 100000,
	1100000, 1100000, 100000, 1400000, 1500000, 100000, 100000, 1800000, 400000,
	400004, 100000, 1200000, 100000, 400000, 400000, 100000, 1000001, 700000,
	100000, 100000, 6500000, 3700000, 6500000, 6500000, 7900000, 3700000, 1e9,
	1e9, 1100003, 4700000, 5200000, 1100001, 900000, 2900000, 2000000, 400004,
	2900000, 1200000, 2000000, 1100000, 1100000, 900000, 1600000, 1600000, 900000,
	200000, 5800000, 5300000, 5800000, 5800000, 7900000, 5300000, 1e9, 1e9,
	1300000, 4300000, 4500000, 1300000, 700000, 5700000, 5200000, 5700000,
	5700000, 1600000, 5200000, 1e9, 1e9, 1000003, 4300000, 4400000, 1000001,
	600000, 1800000, 400000, 400004, 100000, 1200000, 100000, 800000, 800000,
	100000, 1400000, 700000, 100000, 100000, 1800000, 400000, 400004, 100000,
	1200000, 300000, 800000, 800000, 100000, 1400000, 700000, 100000, 100000,
	1800000, 400000, 400004, 100000, 1200000, 100000, 600000, 600000, 100000,
	1400000, 700000, 100000, 100000, 12100000, 3800000, 12100000, 12100000,
	12100000, 3800000, 700000, 700000, 1e9, 8100000, 10700000, 1e9, 2500000, 1e9,
	3800000, 1e9, 1e9, 1e9, 3800000, 700000, 700000, 1e9, 1e9, 1e9, 1e9, 1e9,
	1800000, 400000, 400004, 100000, 1200000, 100000, 1e9, 1e9, 300002, 1400000,
	1500000, 400000, 100000, 1800000, 400000, 400004, 100000, 7900000, 100000,
	1e9, 1e9, 300002, 1400000, 1500000, 400000, 100000, 1e9, 14900000, 1e9, 1e9,
	1e9, 14900000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 13600000, 1e9, 13600000,
	13600000, 13600000, 1e9, 1e9, 1e9, 1e9, 9000000, 12100000, 1e9, 2900000,
	13600000, 1e9, 13600000, 13600000, 13600000, 1e9, 1e9, 1e9, 2600000, 9000000,
	12100000, 2600000, 2900000, 1800000, 400000, 400004, 100000, 1200000, 100000,
	800000, 800000, 100000, 1000001, 400000, 100002, 100000, 1800000, 400000,
	400004, 100000, 1500000, 300000, 1e9, 1e9, 300002, 1400000, 1500000, 400000,
	100000, 1800000, 3500000, 400004, 1800000, 1200000, 3500000, 1e9, 1e9, 600000,
	1400000, 1500000, 600000, 100000, 2500000, 2200000, 400004, 2100000, 1200000,
	2200000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100005, 9400000, 6100000,
	9400000, 9400000, 9400000, 6100000, 1e9, 1e9, 1500000, 6600000, 8000000,
	1500000, 1700000, 9400000, 9400000, 9400000, 9400000, 9400000, 9400000, 1e9,
	1e9, 1600000, 6600000, 8000000, 1600000, 1700000, 9400000, 6600000, 9400000,
	9400000, 9400000, 6600000, 1e9, 1e9, 1600000, 6600000, 8000000, 1600000,
	1700000, 2500000, 2200000, 400004, 2100000, 1200000, 2200000, 1100000,
	1100000, 700000, 1400000, 1500000, 700000, 100005, 2500000, 2200000, 400004,
	2200000, 1200000, 2200000, 1100000, 1100000, 900000, 1200001, 1200001, 900000,
	100005, 9400000, 6100000, 9400000, 9400000, 9400000, 6100000, 1e9, 1e9,
	1500004, 6600000, 8000000, 1500004, 1700000, 2500000, 8100000, 400004,
	2100000, 1200000, 8100000, 1100000, 1100000, 700000, 1400000, 1500000, 700000,
	100005, 15000000, 1e9, 15000000, 15000000, 15000000, 1e9, 1e9, 1e9, 1e9,
	10100000, 13400000, 1e9, 1e9, 2500000, 2800000, 400004, 2100000, 1200000,
	2800000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100005, 2500000, 2800000,
	400004, 2100000, 1200000, 2800000, 1100000, 1100000, 700000, 1400000, 1500000,
	700000, 100005, 1800000, 400000, 3700000, 100000, 1200000, 100000, 400000,
	400000, 100000, 1400000, 600000, 100000, 100000, 10900000, 14900000, 10900000,
	10900000, 10900000, 14900000, 1e9, 1e9, 2600002, 7400000, 9500000, 2600002,
	2100000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1300004, 1e9, 1e9, 1300001,
	1e9, 1800000, 1500000, 400004, 1600000, 1500000, 1500000, 1100000, 1100000,
	900003, 1400000, 1500000, 900001, 100000, 3300000, 3200000, 400004, 3300000,
	7900000, 3200000, 1e9, 1e9, 900000, 2000000, 2000000, 900000, 200000,
	14300000, 400000, 14300000, 14300000, 14300000, 400000, 1e9, 1e9, 1e9,
	9400000, 12700000, 1e9, 3000000, 7900000, 6200000, 7900000, 7900000, 1700000,
	6200000, 1e9, 1e9, 1300004, 5700000, 6600000, 1300001, 1200000, 10100000,
	10700000, 10100000, 10100000, 10100000, 10700000, 1e9, 1e9, 1500004, 7000000,
	8700000, 1500004, 1900000, 10900000, 11700000, 10900000, 10900000, 10900000,
	11700000, 1e9, 1e9, 2600004, 7400000, 9500000, 2600004, 2100000, 7900000,
	7900000, 7900000, 7900000, 7900000, 7000000, 1e9, 1e9, 1600004, 5700000,
	6600000, 1600004, 1200000, 12700000, 11800000, 12700000, 12700000, 12700000,
	11800000, 1e9, 1e9, 1700000, 8400000, 11300000, 1700000, 2800000, 12700000,
	400000, 12700000, 12700000, 12700000, 300000, 1e9, 1e9, 1600004, 8400000,
	11300000, 1600004, 2800000, 9700000, 3400000, 9700000, 9700000, 9700000,
	3400000, 1e9, 1e9, 900000, 6800000, 8300000, 900000, 1800000, 1e9, 11800000,
	1e9, 1e9, 1e9, 11800000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 9700000, 9300000,
	9700000, 9700000, 9700000, 9300000, 1e9, 1e9, 1000003, 6800000, 8300000,
	1000001, 1800000, 9700000, 3400000, 9700000, 9700000, 9700000, 3400000, 1e9,
	1e9, 1000003, 6800000, 8300000, 1000001, 1800000, 9700000, 11100000, 9700000,
	9700000, 9700000, 11100000, 1e9, 1e9, 1600004, 6800000, 8300000, 1600004,
	1800000, 11100000, 3400000, 11100000, 11100000, 11100000, 3400000, 1e9, 1e9,
	900003, 7500000, 9700000, 900001, 2200000, 5200000, 3400000, 5200000, 5200000,
	7900000, 3400000, 1e9, 1e9, 900000, 4100000, 3900000, 900000, 600000, 5200000,
	3400000, 5200000, 5200000, 7900000, 3400000, 1e9, 1e9, 900003, 4100000,
	3900000, 900001, 600000, 6300000, 3400000, 6300000, 6300000, 7900000, 3400000,
	1e9, 1e9, 900003, 4600000, 5000000, 900001, 800000, 13100000, 14100000,
	13100000, 13100000, 13100000, 14100000, 1e9, 1e9, 1e9, 8700000, 11600000, 1e9,
	2900000, 3100000, 3400000, 400004, 3100000, 7900000, 3400000, 1e9, 1e9,
	700000, 1800000, 1800000, 700000, 200000, 11700000, 3400000, 11700000,
	11700000, 11700000, 3400000, 1e9, 1e9, 900003, 7800000, 10300000, 900001,
	2400000, 6200000, 6200000, 6200000, 6200000, 1700000, 6200000, 1e9, 1e9,
	1100000, 4600000, 4900000, 1100000, 800000, 8900000, 11300000, 8900000,
	8900000, 7900000, 11300000, 1e9, 1e9, 1e9, 6300000, 7500000, 1e9, 1500000,
	10600000, 1e9, 10600000, 10600000, 10600000, 1e9, 1e9, 1e9, 1e9, 7200000,
	9200000, 1e9, 2000000, 5700000, 5200000, 5700000, 5700000, 1600000, 5200000,
	1e9, 1e9, 1000003, 4300000, 4400000, 1000001, 700000, 5700000, 5200000,
	5700000, 5700000, 1600000, 5200000, 1e9, 1e9, 1100000, 4300000, 4400000,
	1100000, 700000, 5700000, 5200000, 5700000, 5700000, 7900000, 5200000, 1e9,
	1e9, 1000003, 4300000, 4400000, 1000001, 700000, 11700000, 7900000, 11700000,
	11700000, 11700000, 7100000, 1e9, 1e9, 1600000, 7800000, 10300000, 1600000,
	2400000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1000000, 1e9, 1e9, 1000000,
	1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1600004, 1e9, 1e9, 1600004, 1e9,
	4600000, 9400000, 4600000, 4600000, 7900000, 9400000, 1e9, 1e9, 1100000,
	3300000, 3300000, 1100000, 500000, 4600000, 6600000, 4600000, 4600000,
	7900000, 6600000, 1e9, 1e9, 1100000, 4300000, 4400000, 1100000, 500000,
	1800000, 9800000, 400004, 600000, 7900000, 9800000, 1e9, 1e9, 500000, 1400000,
	1500000, 500001, 100000, 10900000, 13700000, 10900000, 10900000, 10900000,
	13700000, 1e9, 1e9, 1e9, 7400000, 9500000, 1e9, 2100000, 5500000, 600000,
	5500000, 8800000, 8800000, 600000, 1e9, 1e9, 400002, 4200000, 7400000, 500001,
	600000, 8100000, 2600000, 8100000, 8100000, 8100000, 2600000, 1e9, 1e9,
	1300004, 5800000, 6800000, 1300001, 1300000, 1800000, 400000, 400004, 1300000,
	7900000, 300006, 1e9, 1e9, 600000, 1400000, 1500000, 600000, 100000, 14800000,
	6500000, 14800000, 14800000, 14800000, 6500000, 1e9, 1e9, 700000, 9900000,
	13200000, 700000, 1e9, 4100000, 9300000, 4100000, 4100000, 7900000, 9300000,
	1e9, 1e9, 1000000, 2600000, 2600000, 1000000, 400000, 1e9, 9300000, 1e9, 1e9,
	1e9, 9300000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 11000000, 1e9, 11000000,
	11000000, 11000000, 1e9, 1e9, 1e9, 1e9, 7400000, 9600000, 900000, 2100000,
	5700000, 9400000, 5700000, 5700000, 7900000, 9400000, 1e9, 1e9, 1200002,
	4300000, 4400000, 1200001, 1e9, 8700000, 4100000, 8700000, 8700000, 8700000,
	4100000, 1e9, 1e9, 1400005, 6200000, 7300000, 1400001, 1400000, 13500000, 1e9,
	13500000, 13500000, 13500000, 1e9, 1e9, 1e9, 1e9, 8900000, 12000000, 1e9,
	2900000, 14200000, 1e9, 14200000, 14200000, 14200000, 1e9, 1e9, 1e9, 1e9,
	9300000, 12600000, 1e9, 3000000, 4100000, 3600000, 4100000, 4100000, 7900000,
	3600000, 1e9, 1e9, 800000, 2800000, 2800000, 800000, 400000, 2500000, 2000000,
	400004, 2100000, 7900000, 2000000, 1e9, 1e9, 700000, 1400000, 1500000, 700000,
	100005, 5200000, 2000000, 5200000, 5200000, 7900000, 2000000, 1e9, 1e9,
	900000, 4100000, 3900000, 900000, 600000, 5700000, 4500000, 5700000, 5700000,
	7900000, 4500000, 1e9, 1e9, 1000003, 4300000, 4400000, 1000001, 700000,
	8300000, 7900000, 8300000, 8300000, 8300000, 6900000, 1e9, 1e9, 1300000,
	5900000, 6900000, 1300000, 1300000, 2500000, 7900000, 400004, 2500000,
	7900000, 6900000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100005, 2500000,
	7900000, 400004, 2500000, 7900000, 6900000, 1e9, 1e9, 800000, 1400000,
	1500000, 800000, 100005, 1800000, 7900000, 400004, 100000, 7900000, 6900000,
	1e9, 1e9, 100000, 1400000, 1500000, 200000, 100000, 1e9, 6800000, 1e9, 1e9,
	1e9, 6800000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1800000, 400000, 3700000,
	100000, 1200000, 100000, 600000, 600000, 100000, 1400000, 300005, 100000,
	100000, 12000000, 5300000, 12000000, 12000000, 12000000, 5300000, 1e9, 1e9,
	1e9, 8000000, 10600000, 1e9, 2500000, 12000000, 5300000, 12000000, 12000000,
	12000000, 5300000, 1e9, 1e9, 1500004, 8000000, 10600000, 1500004, 2500000,
	2500000, 3500000, 400004, 2400000, 7900000, 3500000, 1e9, 1e9, 700000,
	1400000, 1500000, 700000, 100005, 10900000, 11700000, 10900000, 10900000,
	10900000, 11700000, 1e9, 1e9, 1400005, 7400000, 9500000, 1400001, 2100000,
	5700000, 4100000, 5700000, 5700000, 7900000, 4100000, 1e9, 1e9, 1200002,
	4300000, 4400000, 1200001, 700000, 4600000, 9400000, 4600000, 4600000,
	7900000, 9400000, 1e9, 1e9, 1100000, 4300000, 4400000, 1100000, 500000,
	1800000, 400000, 400004, 1800000, 1200000, 100000, 1e9, 1e9, 100000, 1400000,
	1500000, 100003, 100000, 5700000, 6600000, 5700000, 5700000, 7900000, 6600000,
	1e9, 1e9, 1200002, 4300000, 4400000, 1200001, 700000, 2500000, 3400000,
	400004, 2100000, 1200000, 3400000, 1e9, 1e9, 700000, 1400000, 1200001, 700000,
	100005, 4600000, 6600000, 4600000, 4600000, 7900000, 6600000, 1e9, 1e9,
	1100000, 3300000, 3300000, 1100000, 500000, 4100000, 3200000, 4100000,
	4100000, 7900000, 3200000, 1e9, 1e9, 1000000, 2800000, 2800000, 1000000,
	400000, 4100000, 3200000, 4100000, 4100000, 7900000, 3200000, 1e9, 1e9,
	800000, 2800000, 2800000, 800000, 400000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9,
	1e9, 900000, 1e9, 1e9, 900000, 1e9, 10000000, 9900000, 10000000, 10000000,
	10000000, 9900000, 1e9, 1e9, 900003, 6900000, 8600000, 900001, 1900000,
	3200000, 3600000, 400004, 3200000, 7900000, 3600000, 1e9, 1e9, 1000000,
	1900000, 1900000, 1000000, 200000, 3200000, 3600000, 400004, 3200000, 1600000,
	3600000, 1e9, 1e9, 1000000, 1900000, 1900000, 1000000, 200000, 11600000,
	12200000, 11600000, 11600000, 11600000, 12200000, 1e9, 1e9, 1600000, 7800000,
	10200000, 1600000, 2400000, 6100000, 7900000, 6100000, 6100000, 7900000,
	7200000, 1e9, 1e9, 1600000, 4500000, 4800000, 1600000, 800000, 11600000,
	12200000, 11600000, 11600000, 11600000, 12200000, 1e9, 1e9, 1700000, 7800000,
	10200000, 1700000, 2400000, 11600000, 7900000, 11600000, 11600000, 11600000,
	7200000, 1e9, 1e9, 1600000, 7800000, 10200000, 1600000, 2400000, 11600000,
	12200000, 11600000, 11600000, 11600000, 12200000, 1e9, 1e9, 1800000, 7800000,
	10200000, 1800000, 2400000, 8000000, 7900000, 8000000, 8000000, 8000000,
	7200000, 1e9, 1e9, 1800000, 5700000, 6700000, 1800000, 1300000, 11600000,
	12200000, 11600000, 11600000, 11600000, 12200000, 1e9, 1e9, 1700002, 7800000,
	10200000, 1700002, 2400000, 4600000, 7900000, 4600000, 4600000, 7900000,
	7200000, 1e9, 1e9, 1600000, 3300000, 3300000, 1600000, 500000, 1800000,
	400000, 400004, 100000, 7900000, 100000, 1e9, 1e9, 100000, 1400000, 1500000,
	100002, 100000, 1800000, 400000, 400004, 100000, 1200000, 100000, 1e9, 1e9,
	100000, 1400000, 1500000, 100002, 100000, 1800000, 400000, 400004, 100000,
	1200000, 100005, 1100000, 1100000, 100000, 1400000, 1500000, 100002, 100000,
	1800000, 400000, 400004, 100000, 1200000, 100000, 1100000, 1100000, 100000,
	1400000, 1500000, 100002, 100000, 9000000, 8100000, 9000000, 9000000, 9000000,
	8100000, 1e9, 1e9, 1600000, 6400000, 7600000, 1600000, 1500000, 5600000,
	6600000, 5600000, 5600000, 7900000, 6600000, 1e9, 1e9, 2700000, 4300000,
	4300000, 2700000, 600000, 13500000, 7900000, 13500000, 13500000, 13500000,
	6900000, 1e9, 1e9, 2600000, 8900000, 12000000, 2600000, 2900000, 13500000,
	8100000, 13500000, 13500000, 13500000, 8100000, 1e9, 1e9, 2600000, 8900000,
	12000000, 2600000, 2900000, 10400000, 14800000, 10400000, 10400000, 10400000,
	14800000, 1e9, 1e9, 1e9, 7100000, 9000000, 1e9, 2000000, 8000000, 6500000,
	8000000, 8000000, 8000000, 6500000, 1e9, 1e9, 1500004, 5700000, 6700000,
	1500004, 1300000, 1800000, 400000, 400004, 100000, 1200000, 300005, 500005,
	500005, 100000, 1100000, 1000005, 100000, 100000, 1800000, 400000, 400004,
	100000, 1200000, 300005, 1100000, 1100000, 100000, 1400000, 1500000, 100000,
	100000, 1800000, 400000, 400004, 100000, 1200000, 300005, 1100000, 1100000,
	200000, 1400000, 1500000, 300000, 100000, 6300000, 5900000, 6300000, 6300000,
	7900000, 5900000, 1e9, 1e9, 1600000, 4600000, 5000000, 1600000, 800000,
	7700000, 7900000, 7700000, 7700000, 7900000, 7300000, 1e9, 1e9, 1600000,
	5500000, 6400000, 1600000, 1200000, 6300000, 5900000, 6300000, 6300000,
	1800000, 5900000, 1e9, 1e9, 1600000, 4600000, 5000000, 1600000, 800000,
	8500000, 11000000, 8500000, 8500000, 8500000, 11000000, 1e9, 1e9, 100000,
	6000000, 7100000, 100000, 1400000, 3500000, 6000000, 3700000, 3500000,
	7900000, 6000000, 1e9, 1e9, 800000, 2200000, 2200000, 800000, 300000, 1800000,
	1000000, 400004, 1200000, 1200000, 1000000, 1100000, 1100000, 300002, 1400000,
	1500000, 400000, 100000, 1800000, 1000000, 400004, 1200000, 1200000, 1000000,
	1000000, 1000000, 200000, 1400000, 1500000, 400000, 100000, 1800000, 400000,
	400004, 100000, 1200000, 100005, 1e9, 1e9, 300002, 1400000, 1500000, 400000,
	100000, 3100000, 5000000, 400004, 3100000, 1200000, 5000000, 1e9, 1e9, 300002,
	1800000, 1800000, 400000, 200000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 700000, 700000, 100000, 1400000, 400000, 100000, 100000, 5600000,
	3200000, 5600000, 5600000, 1600000, 3200000, 1e9, 1e9, 1300000, 4300000,
	4300000, 1300000, 600000, 13600000, 9700000, 13600000, 13600000, 13600000,
	9700000, 1e9, 1e9, 600000, 9000000, 12100000, 600000, 2900000, 8700000,
	7900000, 8700000, 8700000, 8700000, 7000000, 1e9, 1e9, 1400005, 6200000,
	7300000, 1400001, 1400000, 1800000, 400000, 400004, 1100000, 1200000, 100005,
	1100000, 1100000, 900000, 1400000, 1500000, 900000, 100000, 13700000, 1e9,
	13700000, 13700000, 13700000, 1e9, 1e9, 1e9, 1e9, 9000000, 12100000, 1e9,
	3000000, 11800000, 1e9, 11800000, 11800000, 11800000, 6300000, 1e9, 1e9, 1e9,
	7900000, 10400000, 1600000, 2500000, 1800000, 400000, 400004, 100000, 7900000,
	400000, 1e9, 1e9, 1e9, 1400000, 1500000, 300000, 100000, 10400000, 7900000,
	10400000, 10400000, 10400000, 7200000, 1e9, 1e9, 1400005, 7100000, 9000000,
	1400001, 2000000, 4700000, 5200000, 4700000, 4700000, 1600000, 5200000, 1e9,
	1e9, 1000003, 3400000, 3400000, 1000001, 500000, 12800000, 3800000, 12800000,
	12800000, 12800000, 3800000, 1e9, 1e9, 1800002, 8500000, 11400000, 1800002,
	2800000, 15100000, 1e9, 15100000, 15100000, 15100000, 1e9, 1e9, 1e9, 1800002,
	10100000, 13500000, 1800002, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9,
	1800002, 1e9, 1e9, 1800002, 1e9, 1e9, 8800000, 1e9, 1e9, 1e9, 8800000, 1e9,
	1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 8400000, 1e9, 8400000, 8400000, 8400000, 1e9,
	1e9, 1e9, 1800002, 6000000, 7000000, 1800002, 1400000, 8400000, 3800000,
	8400000, 8400000, 8400000, 3800000, 1e9, 1e9, 1800002, 6000000, 7000000,
	1800002, 1400000, 5300000, 7900000, 5300000, 5300000, 7900000, 6900000, 1e9,
	1e9, 1700004, 4100000, 4000000, 1700004, 600000, 6100000, 3600000, 6100000,
	6100000, 7900000, 3600000, 1e9, 1e9, 1500004, 4500000, 4800000, 1500004,
	800000, 6900000, 6800000, 6900000, 6900000, 7900000, 6800000, 1e9, 1e9,
	1100000, 4800000, 5600000, 1100000, 1000000, 6900000, 6800000, 6900000,
	6900000, 7900000, 6800000, 1e9, 1e9, 1500000, 4800000, 5600000, 1500000,
	1000000, 7800000, 6800000, 7800000, 7800000, 7900000, 6800000, 1e9, 1e9,
	1500000, 5600000, 6500000, 1500000, 1200000, 7500000, 10300000, 7500000,
	7500000, 7900000, 10300000, 1e9, 1e9, 1500000, 5400000, 6200000, 1500000,
	1100000, 6900000, 3900000, 6900000, 6900000, 7900000, 3900000, 1e9, 1e9,
	1100000, 4800000, 5600000, 1100000, 1000000, 12100000, 6400000, 1e9, 12100000,
	12100000, 6400000, 1e9, 1e9, 2600002, 8100000, 10700000, 2600002, 2500000,
	9400000, 9700000, 9400000, 9400000, 9400000, 9700000, 1e9, 1e9, 1800002,
	6600000, 8000000, 1800002, 1700000, 12100000, 6400000, 1e9, 12100000,
	12100000, 6400000, 1e9, 1e9, 1800002, 8100000, 10700000, 1800002, 2500000,
	3700000, 6200000, 3700000, 3700000, 7900000, 6200000, 1e9, 1e9, 1000003,
	2400000, 2400000, 1000001, 300000, 1800000, 400000, 400004, 100000, 7900000,
	300000, 1e9, 1e9, 300002, 1400000, 1500000, 400000, 100000, 3100000, 5000000,
	400004, 3100000, 7900000, 5000000, 1e9, 1e9, 300002, 1800000, 1800000, 400000,
	200000, 1800000, 400000, 400004, 100000, 1500000, 100005, 1e9, 1e9, 300002,
	1400000, 1500000, 400000, 100000, 1800000, 400000, 100005, 1400000, 1200000,
	100000, 500000, 500000, 300000, 1000001, 700000, 100000, 100000, 1800000,
	400000, 3700000, 100000, 7900000, 100000, 1e9, 1e9, 200000, 1400000, 1500000,
	300001, 100000, 1e9, 4000000, 3700000, 1e9, 1e9, 4000000, 1e9, 1e9, 1500004,
	1e9, 1e9, 1500004, 1e9, 4700000, 1400000, 4700000, 4700000, 1200000, 1200000,
	1100000, 1100000, 1600000, 3400000, 3400000, 1600000, 500000, 4700000,
	1400000, 4700000, 4700000, 1200000, 1200000, 1e9, 1e9, 1600000, 3400000,
	3400000, 1600000, 500000, 4700000, 1400000, 4700000, 4700000, 7900000,
	1200000, 1e9, 1e9, 1600000, 3400000, 3400000, 1600000, 500000, 1800000,
	400000, 400004, 100000, 1400000, 300000, 1e9, 1e9, 300002, 1400000, 1500000,
	400000, 100000, 1e9, 14500000, 1e9, 1e9, 1e9, 14500000, 1e9, 1e9, 1800004,
	1e9, 1e9, 1800004, 1e9, 14000000, 14500000, 14000000, 14000000, 14000000,
	14500000, 1e9, 1e9, 1800004, 9200000, 12400000, 1800004, 3000000, 13300000,
	15400000, 13300000, 13300000, 13300000, 15400000, 1e9, 1e9, 1800002, 8800000,
	11800000, 1800002, 2900000, 1e9, 15400000, 1e9, 1e9, 1e9, 15400000, 1e9, 1e9,
	1e9, 1e9, 1e9, 1e9, 1e9, 4800000, 4800000, 4800000, 4800000, 7900000, 4800000,
	1e9, 1e9, 1500004, 3500000, 3500000, 1500004, 500000, 3100000, 400000, 400004,
	3100000, 1200000, 300000, 1e9, 1e9, 100000, 1800000, 1800000, 100000, 200000,
	5700000, 5000000, 5700000, 5700000, 7900000, 5000000, 1e9, 1e9, 2600002,
	4300000, 4400000, 2600002, 700000, 12100000, 13700000, 12100000, 12100000,
	12100000, 13700000, 1e9, 1e9, 2600002, 8100000, 10700000, 2600002, 2500000,
	1800000, 400000, 400004, 100000, 1200000, 300000, 1e9, 1e9, 100000, 1400000,
	1500000, 100000, 100000, 1e9, 14600000, 1e9, 1e9, 1e9, 14600000, 1e9, 1e9,
	1e9, 1e9, 1e9, 1e9, 1e9, 5700000, 2600000, 5700000, 5700000, 7900000, 2600000,
	1e9, 1e9, 800000, 4300000, 4400000, 800000, 700000, 5700000, 600000, 5700000,
	5700000, 7900000, 600000, 1e9, 1e9, 800000, 4300000, 4400000, 800000, 700000,
	14800000, 7900000, 14800000, 14800000, 14800000, 7500000, 1e9, 1e9, 1500004,
	9900000, 13200000, 1500004, 1e9, 6400000, 7900000, 6400000, 6400000, 7900000,
	7000000, 1e9, 1e9, 1500004, 4700000, 5100000, 1500004, 900000, 8700000,
	7900000, 8700000, 8700000, 8700000, 7000000, 1e9, 1e9, 1200002, 6200000,
	7300000, 1200001, 1400000, 2500000, 4600000, 400004, 2500000, 7900000,
	4600000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100005, 1e9, 13200000,
	1e9, 1e9, 1e9, 13200000, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 1e9, 6200000, 4600000,
	6200000, 6200000, 7900000, 4600000, 1e9, 1e9, 800000, 4600000, 4900000,
	800000, 800000, 9900000, 10800000, 9900000, 9900000, 9900000, 10800000, 1e9,
	1e9, 700000, 6800000, 8500000, 700000, 1800000, 9900000, 4600000, 9900000,
	9900000, 9900000, 4600000, 1e9, 1e9, 700000, 6800000, 8500000, 700000,
	1800000, 14600000, 12100000, 14600000, 14600000, 14600000, 12100000, 1e9, 1e9,
	1500000, 9700000, 13000000, 1500000, 1e9, 14500000, 5500000, 14500000,
	14500000, 14500000, 5500000, 1e9, 1e9, 1e9, 9600000, 12900000, 1e9, 1e9,
	4800000, 4100000, 4800000, 4800000, 7900000, 4100000, 1e9, 1e9, 1300004,
	3500000, 3500000, 1300001, 500000, 1800000, 4400000, 400004, 1200000, 7900000,
	4400000, 1e9, 1e9, 700000, 1400000, 1500000, 700000, 100000, 1800000, 4100000,
	400004, 1200000, 7900000, 4100000, 1e9, 1e9, 1300004, 1400000, 1500000,
	1300001, 100000, 1800000, 700000, 400004, 100000, 1200000, 700000, 1100000,
	1100000, 100000, 1400000, 1500000, 100003, 100000, 1800000, 4600000, 400004,
	400000, 7900000, 100000, 1e9, 1e9, 400002, 1400000, 1500000, 500000, 100000,
	1800000, 4600000, 400004, 1300000, 7900000, 100000, 1e9, 1e9, 600000, 1400000,
	1500000, 600000, 100000, 3100000, 5000000, 400004, 3100000, 7900000, 5000000,
	1e9, 1e9, 400002, 1800000, 1800000, 500000, 200000, 1800000, 400000, 400004,
	200000, 1200000, 300005, 1e9, 1e9, 100000, 1400000, 1500000, 100001, 100000,
	1800000, 400000, 400004, 100000, 1200000, 100000, 400000, 400000, 100000,
	1100000, 700000, 100000, 100000, 1e9, 6400000, 1e9, 1e9, 1e9, 6400000, 1e9,
	1e9, 1700000, 1e9, 1e9, 1700000, 1e9, 1e9, 1900000, 1e9, 1e9, 1e9, 1900000,
	1e9, 1e9, 1700000, 1e9, 1e9, 1700000, 1e9, 10900000, 11700000, 10900000,
	10900000, 10900000, 11700000, 1e9, 1e9, 1e9, 7400000, 9500000, 1e9, 2100000,
	3300000, 7900000, 400004, 3300000, 7900000, 7400000, 600000, 600000, 1200002,
	2000000, 2000000, 1200001, 200000, 8700000, 7900000, 8700000, 8700000,
	8700000, 7400000, 1e9, 1e9, 1200002, 6200000, 7300000, 1200001, 1400000,
	7100000, 7900000, 7100000, 7100000, 7900000, 7400000, 1e9, 1e9, 1800002,
	5000000, 5800000, 1800002, 1000000, 3300000, 7900000, 400004, 3300000,
	7900000, 7400000, 1e9, 1e9, 1200002, 2000000, 2000000, 1200001, 200000,
	13000000, 12100000, 13000000, 13000000, 13000000, 12100000, 1e9, 1e9, 1700004,
	8600000, 11500000, 1700004, 2800000, 11400000, 12100000, 11400000, 11400000,
	11400000, 12100000, 1e9, 1e9, 1700005, 7600000, 10000000, 1700005, 2300000,
	11400000, 12400000, 11400000, 11400000, 11400000, 12400000, 1e9, 1e9, 1700004,
	7600000, 10000000, 1700004, 2300000, 11700000, 1e9, 11700000, 11700000,
	11700000, 1e9, 1e9, 1e9, 2600000, 7800000, 10300000, 2600000, 2400000,
	13000000, 12100000, 13000000, 13000000, 13000000, 12100000, 1e9, 1e9, 1700005,
	8600000, 11500000, 1700005, 2800000, 13000000, 12400000, 13000000, 13000000,
	13000000, 12400000, 1e9, 1e9, 1700004, 8600000, 11500000, 1700004, 2800000,
	13000000, 12400000, 13000000, 13000000, 13000000, 12400000, 1e9, 1e9, 1700005,
	8600000, 11500000, 1700005, 2800000, 13000000, 1e9, 13000000, 13000000,
	13000000, 1e9, 1e9, 1e9, 2600000, 8600000, 11500000, 2600000, 2800000,
	3600000, 5200000, 3700000, 3600000, 1200000, 5200000, 1100000, 1100000,
	900003, 2400000, 2300000, 1300000, 300000, 3600000, 5200000, 3700000, 3600000,
	1200000, 5200000, 1100000, 1100000, 1300000, 2400000, 2300000, 1300000,
	300000, 5500000, 1e9, 5500000, 5500000, 7900000, 1e9, 1e9, 1e9, 1e9, 4200000,
	4200000, 1e9, 600000, 5600000, 8500000, 5600000, 5600000, 1200000, 8500000,
	1100000, 1100000, 1300000, 4300000, 4300000, 1300000, 600000, 1800000, 400000,
	400004, 100000, 1200000, 300005, 1e9, 1e9, 300002, 1400000, 1500000, 300001,
	100000, 11800000, 5500000, 11800000, 11800000, 11800000, 5500000, 1e9, 1e9,
	1100000, 7900000, 10400000, 1100000, 2500000, 11800000, 12500000, 11800000,
	11800000, 11800000, 12500000, 1e9, 1e9, 1300004, 7900000, 10400000, 1300001,
	2500000, 6400000, 5500000, 6400000, 6400000, 7900000, 5500000, 1e9, 1e9,
	1100000, 4700000, 5100000, 1100000, 900000, 1800000, 400000, 400004, 100000,
	1200000, 300005, 1100000, 1100000, 100000, 1400000, 1500000, 200000, 100000,
	1800000, 1000000, 400004, 1200000, 1200000, 1000000, 1e9, 1e9, 300002,
	1400000, 1500000, 400000, 100000, 1800000, 400000, 400004, 100000, 1200000,
	400000, 1e9, 1e9, 200000, 1400000, 1500000, 300001, 100000, 3700000, 400000,
	3700000, 3700000, 1200000, 400000, 1e9, 1e9, 1000000, 2400000, 2400000,
	1000000, 300000, 11700000, 12900000, 11700000, 11700000, 11700000, 12900000,
	1e9, 1e9, 1700004, 7800000, 10300000, 1700004, 2400000, 1800000, 400000,
	400004, 100000, 1200000, 400000, 1100000, 1100000, 200000, 1400000, 1500000,
	300001, 100000, 1800000, 400000, 400004, 200000, 1200000, 100000, 1100000,
	1100000, 100000, 1400000, 1500000, 100003, 100000, 4800000, 5000000, 4800000,
	4800000, 7900000, 5000000, 1e9, 1e9, 1100000, 3500000, 3500000, 1100000,
	500000, 5300000, 400000, 5300000, 5300000, 7900000, 100000, 1e9, 1e9, 1e9,
	4100000, 4000000, 1600000, 600000, 1800000, 400000, 400004, 100000, 1200000,
	100000, 1000000, 1000000, 1e9, 1400000, 1500000, 200000, 100000, 1800000,
	2100000, 400004, 100000, 1200000, 2100000, 1000000, 1000000, 1e9, 1400000,
	1500000, 200000, 100000, 1800000, 1500000, 400004, 600000, 7900000, 1500000,
	1e9, 1e9, 500000, 1400000, 1500000, 500001, 100000, 12500000, 14400000,
	12500000, 12500000, 12500000, 14400000, 1e9, 1e9, 1800002, 8300000, 11100000,
	1800002, 2700000, 13700000, 14400000, 13700000, 13700000, 13700000, 14400000,
	1e9, 1e9, 1800004, 9000000, 12100000, 1800004, 3000000, 11100000, 14400000,
	11100000, 11100000, 11100000, 14400000, 1e9, 1e9, 1800000, 7500000, 9700000,
	1800000, 2200000, 1800000, 400000, 400004, 100000, 1200000, 100000, 1000000,
	1000000, 100000, 1000001, 400000, 100003, 100000, 7600000, 7900000, 7600000,
	7600000, 7900000, 6900000, 1e9, 1e9, 1300004, 5400000, 6200000, 1300001,
	1200000, 11400000, 12400000, 11400000, 11400000, 11400000, 12400000, 1e9, 1e9,
	1800000, 7600000, 10000000, 1800000, 2300000, 1800000, 400000, 400004, 100000,
	1200000, 100000, 500005, 500005, 100000, 1000001, 400000, 100000, 100000,
	1800000, 400000, 3700000, 100000, 1200000, 100000, 600000, 600000, 100000,
	1400000, 400000, 100000, 100000, 1800000, 400000, 3700000, 100000, 1200000,
	300005, 800000, 800000, 100000, 1400000, 900005, 300000, 100000, 1800000,
	400000, 3700000, 100000, 1200000, 300000, 800000, 800000, 100000, 1400000,
	800000, 300000, 100000, 1e9, 12400000, 1e9, 1e9, 1e9, 12400000, 1e9, 1e9, 1e9,
	1e9, 1e9, 1e9, 1e9, 3600000, 3600000, 3700000, 3600000, 7900000, 3600000, 1e9,
	1e9, 900003, 2400000, 2300000, 900001, 300000, 11900000, 1e9, 11900000,
	11900000, 11900000, 1e9, 1e9, 1e9, 1e9, 7900000, 10500000, 1e9, 2500000,
	1800000, 1500000, 400004, 100000, 1200000, 1500000, 1100000, 1100000, 200000,
	1400000, 1500000, 300000, 100000, 1800000, 6700000, 400004, 100000, 1200000,
	6700000, 1100000, 1100000, 200000, 1400000, 1500000, 300000, 100000, 4400000,
	1500000, 4400000, 4400000, 1200000, 1500000, 500005, 500005, 900000, 3200000,
	3100000, 900000, 400000, 1800000, 400000, 400004, 100000, 1200000, 100000,
	600000, 600000, 100000, 1400000, 300005, 100000, 100000, 4800000, 4300000,
	4800000, 4800000, 1200000, 4300000, 1e9, 1e9, 900000, 3500000, 3500000,
	900000, 500000, 13200000, 4300000, 13200000, 13200000, 13200000, 4300000, 1e9,
	1e9, 1800004, 8700000, 11700000, 1800004, 2900000
]);

/** @type {Map<string, number>} */
const SUPPORTED_FROM = new Map([
	["colorHexAlpha", 0],
	["gradientDoublePosition", 1],
	["displayTwoValues", 2],
	["systemUiFont", 3],
	["isSelector", 4],
	["langArgumentList", 5],
	["notSelectorList", 6],
	["whereSelector", 4],
	["dirSelector", 7],
	["customMedia", 8],
	["nesting", 9],
	["textDecorationColorStyle", 10],
	["textDecorationThickness", 11],
	["colorFunction", 12],
	["colorMix", 13],
	["hwbColors", 14],
	["lightDark", 15],
	["labColors", 12],
	["oklabColors", 16],
	["insetShorthand", 17],
	["mediaQueryRange", 18],
	["overflowTwoValues", 19],
	["placeShorthand", 20]
]);

// When each browser first read a pseudo-class or pseudo-element, by the spelling
// a selector carries. A pseudo missing here is one no target is known to read,
// so it never joins a selector list.
/** @type {Map<string, number>} */
const SELECTOR_SUPPORTED_FROM = new Map([
	["::after", 21],
	["::backdrop", 22],
	["::before", 23],
	["::checkmark", 24],
	["::cue", 25],
	["::details-content", 26],
	["::file-selector-button", 27],
	["::first-letter", 28],
	["::first-line", 29],
	["::grammar-error", 30],
	["::highlight", 31],
	["::marker", 32],
	["::part", 33],
	["::picker", 34],
	["::picker-icon", 24],
	["::placeholder", 35],
	["::selection", 36],
	["::slotted", 37],
	["::spelling-error", 30],
	["::target-text", 38],
	["::view-transition", 39],
	["::view-transition-group", 39],
	["::view-transition-image-pair", 39],
	["::view-transition-new", 39],
	["::view-transition-old", 39],
	[":active", 40],
	[":active-view-transition", 41],
	[":active-view-transition-type", 42],
	[":any-link", 43],
	[":autofill", 44],
	[":buffering", 45],
	[":checked", 46],
	[":default", 47],
	[":defined", 48],
	[":dir", 7],
	[":disabled", 46],
	[":empty", 49],
	[":enabled", 46],
	[":first", 50],
	[":first-child", 51],
	[":first-of-type", 52],
	[":focus", 53],
	[":focus-visible", 54],
	[":focus-within", 55],
	[":fullscreen", 56],
	[":future", 57],
	[":has", 58],
	[":has-slotted", 59],
	[":host", 48],
	[":host-context", 60],
	[":hover", 61],
	[":in-range", 62],
	[":indeterminate", 63],
	[":invalid", 64],
	[":is", 4],
	[":lang", 65],
	[":last-child", 66],
	[":last-of-type", 52],
	[":left", 67],
	[":link", 68],
	[":modal", 69],
	[":muted", 45],
	[":not", 49],
	[":nth-child", 70],
	[":nth-last-child", 71],
	[":nth-last-of-type", 72],
	[":nth-of-type", 52],
	[":only-child", 73],
	[":only-of-type", 52],
	[":open", 74],
	[":optional", 64],
	[":out-of-range", 62],
	[":past", 57],
	[":paused", 45],
	[":picture-in-picture", 75],
	[":placeholder-shown", 76],
	[":playing", 45],
	[":popover-open", 77],
	[":read-only", 78],
	[":read-write", 78],
	[":required", 79],
	[":right", 67],
	[":root", 80],
	[":scope", 81],
	[":seeking", 45],
	[":stalled", 45],
	[":state", 82],
	[":target", 83],
	[":user-invalid", 84],
	[":user-valid", 84],
	[":valid", 64],
	[":visited", 85],
	[":volume-locked", 45],
	[":where", 4]
]);

// When each browser first read a value a declaration may name, as
// `property:keyword index keyword index|...` with the color functions under no
// property. A value missing here is one no target is known to read.
const VALUE_SUPPORT_PACKED =
	"accent-color:auto 86|align-content:normal 87|align-items:anchor-center 88|align-self:anchor-center 88 auto 89 normal 89 stretch 89|alignment-baseline:alphabetic 90 baseline 91 central 90 ideographic 90 mathematical 90 middle 91 text-after-edge 92 text-before-edge 92|animation:alternate 93 alternate-reverse 93 auto 93 backwards 93 both 93 ease 93 ease-in 93 ease-in-out 93 ease-out 93 forwards 93 infinite 93 linear 93 none 93 normal 93 paused 94 reverse 93 running 94 step-end 93 step-start 93|animation-composition:accumulate 95 add 95 replace 95|animation-direction:alternate 96 alternate-reverse 97 normal 96 reverse 97|animation-duration:auto 98|animation-fill-mode:backwards 99 both 99 forwards 99 none 99|animation-iteration-count:infinite 96|animation-name:none 96|animation-play-state:paused 96 running 96|animation-timing-function:ease 93 ease-in 93 ease-in-out 93 ease-out 93 linear 93 step-end 93 step-start 93|animation-trigger:none 100|appearance:auto 101 button 102 checkbox 102 listbox 102 menulist 102 menulist-button 103 meter 102 none 104 progress-bar 102 radio 102 searchfield 102 textarea 102 textfield 105|aspect-ratio:auto 106|backdrop-filter:none 107|backface-visibility:hidden 108 visible 108|background:border-box 109 bottom 109 center 109 content-box 109 fixed 110 left 109 local 111 no-repeat 111 none 111 padding-box 109 repeat 111 repeat-x 111 repeat-y 111 right 109 round 111 scroll 111 space 111 top 109|background-attachment:fixed 112 local 113 scroll 114|background-clip:border-area 115 border-box 116 content-box 117 padding-box 116 text 118|background-image:none 119|background-origin:border-box 116 content-box 120 padding-box 116|background-position:bottom 121 center 121 left 121 right 121 top 121|background-position-x:x-end 122 x-start 122|background-position-y:y-end 122 y-start 122|background-repeat:no-repeat 119 repeat 119 repeat-x 119 repeat-y 119 round 123 space 123|background-size:auto 124 contain 125 cover 125|baseline-shift:baseline 126 sub 127 super 127|baseline-source:auto 128 first 128 last 128|block-size:auto 129 fit-content 130 max-content 131 min-content 131|border:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 medium 111 none 111 outset 111 ridge 111 solid 111 thick 111 thin 111|border-block:dashed 17 dotted 17 double 17 groove 17 hidden 17 inset 17 medium 17 none 17 outset 17 ridge 17 solid 17 thick 17 thin 17|border-block-end:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 medium 132 none 132 outset 132 ridge 132 solid 132 thick 132 thin 132|border-block-end-style:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 none 132 outset 132 ridge 132 solid 132|border-block-end-width:medium 132 thick 132 thin 132|border-block-start:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 medium 132 none 132 outset 132 ridge 132 solid 132 thick 132 thin 132|border-block-start-style:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 none 132 outset 132 ridge 132 solid 132|border-block-start-width:medium 132 thick 132 thin 132|border-block-style:dashed 17 dotted 17 double 17 groove 17 hidden 17 inset 17 none 17 outset 17 ridge 17 solid 17|border-block-width:medium 17 thick 17 thin 17|border-bottom:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 medium 111 none 111 outset 111 ridge 111 solid 111 thick 111 thin 111|border-bottom-style:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 none 111 outset 111 ridge 111 solid 111|border-bottom-width:medium 111 thick 111 thin 111|border-collapse:collapse 133 separate 133|border-image:fill 134 none 135 repeat 135 round 135 space 135 stretch 135|border-image-repeat:repeat 136 round 137 space 138 stretch 136|border-image-source:none 139|border-image-width:auto 134|border-inline:dashed 17 dotted 17 double 17 groove 17 hidden 17 inset 17 medium 17 none 17 outset 17 ridge 17 solid 17 thick 17 thin 17|border-inline-end:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 medium 132 none 132 outset 132 ridge 132 solid 132 thick 132 thin 132|border-inline-end-style:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 none 132 outset 132 ridge 132 solid 132|border-inline-end-width:medium 132 thick 132 thin 132|border-inline-start:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 medium 132 none 132 outset 132 ridge 132 solid 132 thick 132 thin 132|border-inline-start-style:dashed 132 dotted 132 double 132 groove 132 hidden 132 inset 132 none 132 outset 132 ridge 132 solid 132|border-inline-start-width:medium 132 thick 132 thin 132|border-inline-style:dashed 17 dotted 17 double 17 groove 17 hidden 17 inset 17 none 17 outset 17 ridge 17 solid 17|border-inline-width:medium 17 thick 17 thin 17|border-left:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 medium 111 none 111 outset 111 ridge 111 solid 111 thick 111 thin 111|border-left-style:dashed 140 dotted 140 double 140 groove 140 hidden 140 inset 140 none 140 outset 140 ridge 140 solid 140|border-left-width:medium 111 thick 111 thin 111|border-right:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 medium 111 none 111 outset 111 ridge 111 solid 111 thick 111 thin 111|border-right-style:dashed 140 dotted 140 double 140 groove 140 hidden 140 inset 140 none 140 outset 140 ridge 140 solid 140|border-right-width:medium 111 thick 111 thin 111|border-shape:none 141|border-style:dashed 142 dotted 142 double 142 groove 142 hidden 142 inset 142 none 142 outset 142 ridge 142 solid 142|border-top:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 medium 111 none 111 outset 111 ridge 111 solid 111 thick 111 thin 111|border-top-style:dashed 111 dotted 111 double 111 groove 111 hidden 111 inset 111 none 111 outset 111 ridge 111 solid 111|border-top-width:medium 111 thick 111 thin 111|border-width:medium 143 thick 143 thin 143|bottom:auto 142|box-decoration-break:clone 144 slice 144|box-shadow:inset 145 none 146|box-sizing:border-box 147 content-box 147|break-after:always 148 auto 149 avoid 150 avoid-column 151 avoid-page 151 column 151 left 149 page 149 recto 151 right 149 verso 151|break-before:always 148 auto 149 avoid 150 avoid-column 151 avoid-page 151 column 151 left 149 page 149 recto 151 right 149 verso 151|break-inside:auto 149 avoid 149 avoid-column 152 avoid-page 152|caption-side:bottom 121 top 121|caret-animation:auto 153 manual 153|caret-color:auto 154|caret-shape:auto 155 bar 155 block 155 underscore 155|clear:both 142 inline-end 156 inline-start 156 left 142 none 111 right 142|clip-path:border-box 157 content-box 157 fill-box 158 margin-box 157 padding-box 157 stroke-box 158 view-box 159|clip-rule:evenodd 160 nonzero 160|:color 12 color-mix 13 hsl 66 hwb 14 lab 12 lch 12 light-dark 15 oklab 16 oklch 16 rgb 85|color-interpolation-filters:auto 161 linearrgb 162 srgb 162|color-scheme:dark 163 light 163 normal 163 only 164|column-count:auto 165|column-fill:auto 166 balance 166|column-gap:normal 167|column-height:auto 168|column-rule:dashed 146 dotted 146 double 146 groove 146 hidden 146 inset 146 medium 146 none 146 outset 146 ridge 146 solid 146 thick 146 thin 146|column-rule-style:dashed 146 dotted 146 double 146 groove 146 hidden 146 inset 146 none 146 outset 146 ridge 146 solid 146|column-rule-width:medium 146 thick 146 thin 146|column-span:all 169 none 169|column-width:auto 165|column-wrap:auto 168 nowrap 168 wrap 168|columns:auto 170|contain:content 171 inline-size 172 layout 171 none 171 paint 171 size 171 strict 171 style 173|contain-intrinsic-block-size:none 174|contain-intrinsic-height:none 174|contain-intrinsic-inline-size:none 174|contain-intrinsic-size:none 174|contain-intrinsic-width:none 174|container:inline-size 175 none 175 normal 176 scroll-state 175 size 175|container-name:none 175|container-type:inline-size 175 normal 175 scroll-state 177 size 175|content:close-quote 111 no-close-quote 111 no-open-quote 111 none 142 normal 142 open-quote 111|content-visibility:auto 178 hidden 179 visible 179|corner-block-end-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-block-start-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-bottom-left-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-bottom-right-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-bottom-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-end-end-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-end-start-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-inline-end-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-inline-start-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-left-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-right-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-start-end-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-start-start-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-top-left-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-top-right-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|corner-top-shape:bevel 180 notch 180 round 180 scoop 180 square 180 squircle 180|counter-increment:none 181|counter-reset:none 181|counter-set:none 182|cursor:alias 183 all-scroll 184 auto 185 cell 186 col-resize 184 context-menu 183 copy 183 crosshair 187 default 187 e-resize 187 ew-resize 183 grab 188 grabbing 189 help 187 move 187 n-resize 187 ne-resize 187 nesw-resize 183 no-drop 184 none 190 not-allowed 184 ns-resize 183 nw-resize 187 nwse-resize 183 pointer 191 progress 191 row-resize 184 s-resize 187 se-resize 187 sw-resize 187 text 185 vertical-text 192 w-resize 187 wait 187 zoom-in 193 zoom-out 193|d:none 194|direction:ltr 195 rtl 195|display:block 196 contents 197 flex 198 flow-root 199 grid 200 inline 196 inline-block 201 inline-flex 198 inline-grid 200 inline-table 202 list-item 203 none 196 ruby 204 ruby-base 205 ruby-base-container 205 ruby-text 204 ruby-text-container 205 table 201 table-caption 206 table-cell 201 table-column 201 table-column-group 201 table-footer-group 201 table-header-group 201 table-row 201 table-row-group 201|dominant-baseline:alphabetic 207 auto 207 central 207 hanging 207 ideographic 207 mathematical 207 middle 207 text-bottom 208 text-top 208|dynamic-range-limit:constrained 209 no-limit 210 standard 210|empty-cells:hide 211 show 211|fill:none 212|fill-rule:evenodd 212 nonzero 212|filter:none 213|flex:auto 214 content 215 fit-content 216 max-content 217 min-content 217 none 218|flex-basis:auto 219 content 220 fit-content 216 max-content 217 min-content 217|flex-direction:column 218 column-reverse 221 row 218 row-reverse 221|flex-flow:balance 222 column 223 column-reverse 223 nowrap 223 row 223 row-reverse 223 wrap 223 wrap-reverse 223|flex-wrap:balance 222 nowrap 224 wrap 224 wrap-reverse 224|float:inline-end 156 inline-start 156 left 142 none 142 right 142|font:caption 225 icon 225 menu 225 message-box 225 small-caption 225 status-bar 225|font-family:cursive 111 fantasy 111 math 226 monospace 111 sans-serif 111 serif 111 system-ui 3 ui-monospace 227 ui-rounded 227 ui-sans-serif 227 ui-serif 227|font-feature-settings:normal 228|font-kerning:auto 229 none 229 normal 229|font-language-override:normal 230|font-optical-sizing:auto 231 none 231|font-palette:dark 232 light 232 normal 232|font-size:math 233 xxx-large 234|font-size-adjust:from-font 235 none 236|font-style:italic 142 normal 142 oblique 111|font-synthesis:none 237 position 238 small-caps 239 style 240 weight 240|font-synthesis-small-caps:auto 241 none 241|font-synthesis-style:auto 241 none 241|font-synthesis-weight:auto 241 none 241|font-variant:historical-forms 242 none 243 normal 142|font-variant-alternates:historical-forms 242 normal 242|font-variant-caps:all-petite-caps 244 all-small-caps 244 normal 244 petite-caps 244 small-caps 244 titling-caps 244 unicase 244|font-variant-east-asian:full-width 245 jis04 245 jis78 245 jis83 245 jis90 245 normal 245 proportional-width 245 ruby 245 simplified 245 traditional 245|font-variant-emoji:emoji 246 normal 246 text 246 unicode 246|font-variant-ligatures:common-ligatures 247 contextual 247 discretionary-ligatures 247 historical-ligatures 247 no-common-ligatures 247 no-contextual 247 no-discretionary-ligatures 247 no-historical-ligatures 247 none 247 normal 247|font-variant-numeric:diagonal-fractions 244 lining-nums 244 normal 244 oldstyle-nums 244 ordinal 244 proportional-nums 244 slashed-zero 244 stacked-fractions 244 tabular-nums 244|font-variant-position:normal 248 sub 248 super 248|font-variation-settings:normal 249|font-weight:bold 195 bolder 195 lighter 195 normal 195|forced-color-adjust:auto 250 none 250 preserve-parent-color 251|frame-sizing:auto 8 content-block-size 8 content-height 8 content-inline-size 8 content-width 8|gap:normal 252|grid:none 252|grid-area:auto 252|grid-auto-columns:auto 252 max-content 253 min-content 253|grid-auto-flow:column 254 dense 254 row 254|grid-auto-rows:auto 252 max-content 253 min-content 253|grid-column:auto 252|grid-column-end:auto 252|grid-column-start:auto 252|grid-row:auto 252|grid-row-end:auto 252|grid-row-start:auto 252|grid-template:none 254|grid-template-areas:none 254|grid-template-columns:auto 254 max-content 254 min-content 254 none 254 subgrid 255|grid-template-rows:auto 254 max-content 254 min-content 254 none 254 subgrid 255|hanging-punctuation:allow-end 256 first 256 force-end 257 last 256 none 256|height:auto 142 fit-content 258 max-content 259 min-content 259|hyphenate-character:auto 260|hyphenate-limit-chars:auto 261|hyphens:auto 262 manual 262 none 262|image-orientation:from-image 263|image-rendering:auto 264 crisp-edges 265 pixelated 266 smooth 267|initial-letter:normal 268|inline-size:auto 129 fit-content 269 max-content 131 min-content 131|inset:auto 17|inset-block:auto 270|inset-block-end:auto 270|inset-block-start:auto 270|inset-inline:auto 270|inset-inline-end:auto 270|inset-inline-start:auto 270|interactivity:auto 271 inert 271|interest-delay:normal 272|interest-delay-end:normal 272|interest-delay-start:normal 272|isolation:auto 273 isolate 273|justify-content:left 274 normal 274 right 274|justify-items:anchor-center 88 center 275 left 275 legacy 275 right 275|justify-self:anchor-center 88 auto 276 left 276 normal 276 right 276 stretch 276|left:auto 142|letter-spacing:normal 142|line-break:anywhere 277 auto 278 loose 279 normal 280 strict 279|line-clamp:none 281|line-height:normal 142|list-style:inside 111 none 111 outside 111|list-style-image:none 142|list-style-position:inside 142 outside 142|list-style-type:none 142|margin:auto 282|margin-block:auto 17|margin-block-end:auto 132|margin-block-start:auto 132|margin-bottom:auto 282|margin-inline:auto 17|margin-inline-end:auto 132|margin-inline-start:auto 132|margin-left:auto 282|margin-right:auto 282|margin-top:auto 282|marker:none 212|marker-end:none 212|marker-mid:none 212|marker-start:none 212|mask-clip:border-box 283 content-box 283 fill-box 283 no-clip 283 padding-box 283 stroke-box 283 view-box 283|mask-composite:add 284 exclude 284 intersect 284 subtract 284|mask-mode:alpha 284 luminance 284 match-source 284|mask-origin:border-box 283 content-box 283 fill-box 283 padding-box 283 stroke-box 283 view-box 283|mask-type:alpha 285 luminance 285|math-depth:auto-add 233|math-style:compact 286 normal 286|max-block-size:fit-content 269 max-content 131 min-content 131 none 287|max-height:fit-content 288 max-content 259 min-content 259 none 289|max-inline-size:fit-content 269 max-content 290 min-content 290 none 287|max-width:fit-content 288 max-content 259 min-content 259 none 142|min-block-size:auto 287 fit-content 269 max-content 290 min-content 290|min-height:auto 291 fit-content 288 max-content 259 min-content 259|min-inline-size:auto 287 fit-content 269 max-content 290 min-content 290|min-width:auto 291 fit-content 258 max-content 292 min-content 292|mix-blend-mode:color 293 color-burn 294 color-dodge 294 darken 294 difference 294 exclusion 294 hard-light 294 hue 293 lighten 294 luminosity 293 multiply 294 normal 294 overlay 294 plus-darker 295 plus-lighter 296 saturation 293 screen 294 soft-light 294|object-fit:contain 297 cover 297 fill 297 none 297 scale-down 297|object-position:bottom 298 center 298 left 298 right 298 top 298|offset:auto 299 border-box 299 bottom 299 center 299 content-box 299 fill-box 299 left 299 none 300 normal 301 padding-box 299 right 299 stroke-box 299 top 299 view-box 299|offset-anchor:auto 302 bottom 302 center 302 left 302 right 302 top 302|offset-path:border-box 303 content-box 303 fill-box 303 none 304 padding-box 303 stroke-box 303 view-box 303|offset-position:auto 299 bottom 299 center 299 left 299 normal 305 right 299 top 299|offset-rotate:auto 306 reverse 306|outline:auto 307 dashed 308 dotted 308 double 308 groove 308 inset 308 medium 308 none 308 outset 308 ridge 308 solid 308 thick 308 thin 308|outline-style:auto 309 dashed 310 dotted 310 double 310 groove 310 inset 310 none 310 outset 310 ridge 310 solid 310|outline-width:medium 308 thick 308 thin 308|overflow:auto 147 clip 311 hidden 147 scroll 147 visible 147|overflow-anchor:auto 312 none 312|overflow-block:auto 313 clip 314 hidden 313 scroll 313 visible 313|overflow-clip-margin:border-box 315 content-box 315 padding-box 315|overflow-inline:auto 313 clip 314 hidden 313 scroll 313 visible 313|overflow-wrap:anywhere 316 break-word 317 normal 318|overflow-x:auto 319 clip 311 hidden 319 scroll 319 visible 319|overflow-y:auto 319 clip 311 hidden 319 scroll 319 visible 319|overscroll-behavior:auto 320 contain 320 none 320|overscroll-behavior-block:auto 321 contain 321 none 321|overscroll-behavior-inline:auto 321 contain 321 none 321|overscroll-behavior-x:auto 322 contain 322 none 320|overscroll-behavior-y:auto 322 contain 322 none 320|page:auto 323|paint-order:fill 324 markers 324 normal 324 stroke 324|path-length:none 8|perspective:none 325|perspective-origin:bottom 326 center 326 left 326 right 326 top 326|place-items:anchor-center 88|place-self:anchor-center 88|pointer-events:all 327 auto 327 fill 327 none 327 painted 327 stroke 327 visible 327 visiblefill 328 visiblepainted 328 visiblestroke 328|position:absolute 142 fixed 329 relative 142 static 142 sticky 330|print-color-adjust:economy 331 exact 331|quotes:auto 332 none 333|reading-flow:flex-flow 334 flex-visual 334 grid-columns 334 grid-order 334 grid-rows 334 normal 334 source-order 334|resize:block 335 both 336 horizontal 336 inline 335 none 336 vertical 336|right:auto 142|rotate:none 337|row-gap:normal 338|ruby-align:center 339 space-around 339 space-between 339 start 339|ruby-overhang:auto 340 none 341|ruby-position:alternate 342 inter-character 343 over 344 under 344|rx:auto 345|ry:auto 345|scale:none 337|scroll-behavior:auto 346 smooth 346|scroll-marker-group:after 271 before 271 none 271|scroll-padding:auto 347|scroll-padding-block:auto 348|scroll-padding-block-end:auto 348|scroll-padding-block-start:auto 348|scroll-padding-bottom:auto 349|scroll-padding-inline:auto 348|scroll-padding-inline-end:auto 348|scroll-padding-inline-start:auto 348|scroll-padding-left:auto 349|scroll-padding-right:auto 349|scroll-padding-top:auto 349|scroll-snap-align:center 347 end 347 none 347 start 347|scroll-snap-stop:always 350 normal 350|scroll-snap-type:block 347 both 347 inline 347 none 351 x 347 y 347|scroll-target-group:auto 153 none 153|scrollbar-color:auto 352|scrollbar-gutter:auto 353 stable 353|scrollbar-width:auto 354 none 354 thin 354|shape-outside:border-box 355 content-box 355 margin-box 355 none 355 padding-box 355|shape-rendering:auto 356 crispedges 357 geometricprecision 357 optimizespeed 357|stroke:none 358|stroke-dasharray:none 358|stroke-linecap:butt 358 round 358 square 358|stroke-linejoin:bevel 358 miter 358 round 358|table-layout:auto 359 fixed 359|text-align:center 207 end 360 justify 142 left 207 match-parent 361 right 207 start 360|text-align-last:auto 362 center 363 end 364 justify 363 left 363 right 363 start 364|text-anchor:end 365 middle 365 start 365|text-autospace:auto 366 normal 367|text-box:alphabetic 368 auto 368 cap 368 ex 368 ideographic 369 ideographic-ink 369 none 368 normal 368 text 368 trim-both 368 trim-end 368 trim-start 368|text-box-edge:alphabetic 368 auto 368 cap 368 ex 368 ideographic 369 ideographic-ink 369 text 368|text-box-trim:none 368 trim-both 368 trim-end 368 trim-start 368|text-combine-upright:all 370 none 370|text-decoration:auto 11 blink 371 dashed 372 dotted 372 double 372 from-font 11 grammar-error 373 line-through 374 none 374 overline 374 solid 372 spelling-error 373 underline 374 wavy 372|text-decoration-inset:auto 375|text-decoration-line:blink 376 grammar-error 373 line-through 377 none 377 overline 377 spelling-error 373 underline 377|text-decoration-skip-ink:all 378 auto 379 none 379|text-decoration-style:dashed 377 dotted 377 double 377 solid 377 wavy 377|text-decoration-thickness:auto 380 from-font 380|text-emphasis:circle 381 dot 381 double-circle 381 filled 381 none 381 open 381 sesame 381 triangle 381|text-emphasis-position:auto 382 left 383 over 384 right 383 under 384|text-emphasis-style:circle 385 dot 385 double-circle 385 filled 385 none 385 open 385 sesame 385 triangle 385|text-fit:consistent 222 grow 222 none 222 per-line 222 per-line-all 222 shrink 222|text-indent:each-line 386 hanging 386|text-justify:auto 387 inter-character 387 inter-word 387 none 387|text-orientation:mixed 388 sideways 389 upright 390|text-overflow:clip 391 ellipsis 391|text-rendering:auto 392 geometricprecision 393 optimizelegibility 394 optimizespeed 394|text-shadow:none 395|text-transform:capitalize 396 full-size-kana 397 full-width 398 lowercase 142 math-auto 399 none 142 uppercase 142|text-underline-offset:auto 380|text-underline-position:auto 400 from-font 401 left 402 right 402 under 403|text-wrap:auto 404 balance 405 nowrap 406 pretty 407 stable 408 wrap 406|text-wrap-mode:nowrap 409 wrap 409|text-wrap-style:auto 410 balance 410 pretty 411 stable 410|timeline-trigger:auto 100 none 100 normal 100|timeline-trigger-activation-range:normal 100|timeline-trigger-activation-range-end:normal 100|timeline-trigger-activation-range-start:normal 100|timeline-trigger-active-range:auto 100 normal 100|timeline-trigger-active-range-end:auto 100 normal 100|timeline-trigger-active-range-start:auto 100 normal 100|timeline-trigger-name:none 100|timeline-trigger-source:auto 100 none 100|top:auto 142|touch-action:manipulation 412 none 413 pan-down 414 pan-left 414 pan-right 414 pan-up 414 pan-x 413 pan-y 413 pinch-zoom 415|transform:none 416|transform-box:border-box 417 content-box 418 fill-box 419 stroke-box 418 view-box 419|transform-origin:bottom 420 center 420 left 420 right 420 top 420|transform-style:flat 421 preserve-3d 421|transition:all 422 allow-discrete 423 ease 422 ease-in 422 ease-in-out 422 ease-out 422 linear 422 none 422 normal 423 step-end 422 step-start 422|transition-behavior:allow-discrete 424 normal 424|transition-property:all 425 none 425|transition-timing-function:ease 422 ease-in 422 ease-in-out 422 ease-out 422 linear 422 step-end 422 step-start 422|translate:none 337|trigger-scope:all 100 none 100|unicode-bidi:bidi-override 426 embed 426 isolate 427 isolate-override 427 normal 426 plaintext 427|user-select:all 428 auto 429 none 430 text 429|vector-effect:non-scaling-stroke 431 none 431|vertical-align:baseline 142 bottom 142 middle 142 sub 142 super 142 text-bottom 142 text-top 142 top 142|view-transition-class:none 432|view-transition-name:match-element 433 none 434|view-transition-scope:all 141 none 141|visibility:collapse 435 hidden 142 visible 142|white-space:break-spaces 436 collapse 437 normal 142 nowrap 438 pre 439 pre-line 440 pre-wrap 441 preserve 437 preserve-breaks 437 preserve-spaces 442 wrap 437|white-space-collapse:break-spaces 406 collapse 406 preserve 406 preserve-breaks 406 preserve-spaces 442|width:auto 142 fit-content 258 max-content 259 min-content 292|will-change:auto 443 contents 443 scroll-position 443|word-break:auto-phrase 444 break-all 445 break-word 446 keep-all 447 normal 445|word-spacing:normal 448|writing-mode:horizontal-tb 449 sideways-lr 450 sideways-rl 450 vertical-lr 449 vertical-rl 449|z-index:auto 119|zoom:reset 8";

// WHY: The vendor spellings of a property's own keyword values, as `property ->
// keyword -> [spelling, [browserslistBrowser, from, to][]][]` — `display:flex`
// was `display:-webkit-flex`, and `width:max-content` `width:-moz-max-content`.
// Only keywords the property's syntax names are here, so a function whose older
// spelling read its arguments differently is not.
/** @type {Map<string, Map<string, [string, number][]>>} */
const PREFIXED_VALUES = new Map([
	[
		"block-size",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"cursor",
		new Map([
			[
				"grab",
				[
					["-webkit-grab", 132],
					["-moz-grab", 133]
				]
			],
			["grabbing", [["-webkit-grabbing", 134]]],
			[
				"zoom-in",
				[
					["-webkit-zoom-in", 135],
					["-moz-zoom-in", 136]
				]
			],
			[
				"zoom-out",
				[
					["-webkit-zoom-out", 135],
					["-moz-zoom-out", 136]
				]
			]
		])
	],
	[
		"display",
		new Map([
			[
				"flex",
				[
					["-webkit-flex", 0],
					["-ms-flexbox", 137]
				]
			],
			[
				"inline-flex",
				[
					["-webkit-inline-flex", 0],
					["-ms-inline-flexbox", 137]
				]
			]
		])
	],
	[
		"flex-basis",
		new Map([
			["fit-content", [["-moz-fit-content", 138]]],
			["max-content", [["-moz-max-content", 139]]],
			["min-content", [["-moz-min-content", 139]]]
		])
	],
	[
		"height",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"image-rendering",
		new Map([
			[
				"crisp-edges",
				[
					["-webkit-optimize-contrast", 140],
					["-moz-crisp-edges", 141]
				]
			]
		])
	],
	[
		"inline-size",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"max-block-size",
		new Map([
			[
				"fit-content",
				[
					["-webkit-fit-content", 142],
					["-moz-fit-content", 127]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 143]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 144]
				]
			]
		])
	],
	[
		"max-height",
		new Map([
			[
				"fit-content",
				[
					["-webkit-fit-content", 142],
					["-moz-fit-content", 127]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 143]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 144]
				]
			]
		])
	],
	[
		"max-inline-size",
		new Map([
			[
				"fit-content",
				[
					["-webkit-fit-content", 142],
					["-moz-fit-content", 127]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 143]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 144]
				]
			]
		])
	],
	[
		"max-width",
		new Map([
			[
				"fit-content",
				[
					["-webkit-fit-content", 142],
					["-moz-fit-content", 127]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 143]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 144]
				]
			]
		])
	],
	[
		"min-block-size",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"min-height",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"min-inline-size",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	[
		"min-width",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	],
	["overflow", new Map([["clip", [["-moz-hidden-unscrollable", 145]]]])],
	["overflow-block", new Map([["clip", [["-moz-hidden-unscrollable", 145]]]])],
	["overflow-inline", new Map([["clip", [["-moz-hidden-unscrollable", 145]]]])],
	["overflow-x", new Map([["clip", [["-moz-hidden-unscrollable", 145]]]])],
	["overflow-y", new Map([["clip", [["-moz-hidden-unscrollable", 145]]]])],
	["position", new Map([["sticky", [["-webkit-sticky", 146]]]])],
	["text-align", new Map([["match-parent", [["-webkit-match-parent", 147]]]])],
	[
		"unicode-bidi",
		new Map([
			[
				"isolate",
				[
					["-webkit-isolate", 148],
					["-moz-isolate", 149]
				]
			],
			[
				"isolate-override",
				[
					["-moz-isolate-override", 150],
					["-webkit-isolate-override", 151]
				]
			],
			[
				"plaintext",
				[
					["-moz-plaintext", 149],
					["-webkit-plaintext", 152]
				]
			]
		])
	],
	["white-space", new Map([["pre-wrap", [["-moz-pre-wrap", 153]]]])],
	[
		"width",
		new Map([
			[
				"fit-content",
				[
					["-moz-fit-content", 127],
					["-webkit-fit-content", 128]
				]
			],
			[
				"max-content",
				[
					["-moz-max-content", 129],
					["-webkit-max-content", 130]
				]
			],
			[
				"min-content",
				[
					["-moz-min-content", 129],
					["-webkit-min-content", 131]
				]
			]
		])
	]
]);

// WHY: The keywords a vendor spelling reads in place of the standard ones, as
// `spelling -> standard -> legacy` — IE 10's `-ms-flex-pack` reads
// `space-around` as `distribute`. Each map is the older property's whole
// grammar, so a value naming anything it does not is one that property cannot
// read and no copy is written.
/** @type {Map<string, Map<string, string>>} */
const PREFIXED_SPELLING_KEYWORDS = new Map([
	[
		"-ms-flex-align",
		new Map([
			["flex-start", "start"],
			["flex-end", "end"],
			["center", "center"],
			["baseline", "baseline"],
			["stretch", "stretch"]
		])
	],
	[
		"-ms-flex-item-align",
		new Map([
			["auto", "auto"],
			["flex-start", "start"],
			["flex-end", "end"],
			["center", "center"],
			["baseline", "baseline"],
			["stretch", "stretch"]
		])
	],
	[
		"-ms-flex-line-pack",
		new Map([
			["flex-start", "start"],
			["flex-end", "end"],
			["center", "center"],
			["space-between", "justify"],
			["space-around", "distribute"],
			["stretch", "stretch"]
		])
	],
	[
		"-ms-flex-pack",
		new Map([
			["flex-start", "start"],
			["flex-end", "end"],
			["center", "center"],
			["space-between", "justify"],
			["space-around", "distribute"]
		])
	],
	[
		"-webkit-ruby-position",
		new Map([
			["over", "before"],
			["under", "after"]
		])
	],
	[
		"-webkit-text-orientation",
		new Map([
			["mixed", "vertical-right"],
			["upright", "upright"],
			["sideways", "sideways"]
		])
	]
]);

module.exports.ABSOLUTE_UNIT_SCALE = ABSOLUTE_UNIT_SCALE;
module.exports.ALPHA_VALUE_PROPERTIES = ALPHA_VALUE_PROPERTIES;
module.exports.ANGLE_UNITS = ANGLE_UNITS;
module.exports.ARC_COSINE_DEGREES = ARC_COSINE_DEGREES;
module.exports.ARC_SINE_DEGREES = ARC_SINE_DEGREES;
module.exports.ARC_TANGENT_DEGREES = ARC_TANGENT_DEGREES;
module.exports.AUTO_SECOND_VALUE_PROPERTIES = AUTO_SECOND_VALUE_PROPERTIES;
module.exports.BOX_FAMILY_PREFIX = BOX_FAMILY_PREFIX;
module.exports.BOX_LONGHANDS = BOX_LONGHANDS;
module.exports.BOX_SHORTHANDS = BOX_SHORTHANDS;
module.exports.CALC_CONSTANTS = CALC_CONSTANTS;
module.exports.CALC_REJECTING_PROPERTIES = CALC_REJECTING_PROPERTIES;
module.exports.CANONICAL_NAMES = CANONICAL_NAMES;
module.exports.CLAMPED_VALUE_RANGES = CLAMPED_VALUE_RANGES;
module.exports.COLOR_ARGUMENT_FUNCTIONS = COLOR_ARGUMENT_FUNCTIONS;
module.exports.COLOR_FUNCTIONS = COLOR_FUNCTIONS;
module.exports.COLOR_KEYWORDS = COLOR_KEYWORDS;
module.exports.COLOR_NAME_TO_RGB = COLOR_NAME_TO_RGB;
module.exports.COLOR_NAME_TO_SHORTEST = COLOR_NAME_TO_SHORTEST;
module.exports.COLOR_ONLY_PROPERTIES = COLOR_ONLY_PROPERTIES;
module.exports.COLOR_SPACE_MODEL = COLOR_SPACE_MODEL;
module.exports.COMPOUND_CONTINUATIONS = COMPOUND_CONTINUATIONS;
module.exports.CSS_MODULES_KEYWORDS = CSS_MODULES_KEYWORDS;
module.exports.CSS_MODULES_KEYWORD_OPTIONS = CSS_MODULES_KEYWORD_OPTIONS;
module.exports.CSS_WIDE_KEYWORDS = CSS_WIDE_KEYWORDS;
module.exports.CUBIC_BEZIER_KEYWORDS = CUBIC_BEZIER_KEYWORDS;
module.exports.CUSTOM_IDENT_LIST_PROPERTIES = CUSTOM_IDENT_LIST_PROPERTIES;
module.exports.DEFAULT_GRADIENT_DIRECTIONS = DEFAULT_GRADIENT_DIRECTIONS;
module.exports.DISPLAY_SHORT_FORMS = DISPLAY_SHORT_FORMS;
module.exports.DROPPABLE_WHEN_EMPTY_AT_RULES = DROPPABLE_WHEN_EMPTY_AT_RULES;
module.exports.EASING_KEYWORDS = EASING_KEYWORDS;
module.exports.EIGHTH_TURN_COSINE = EIGHTH_TURN_COSINE;
module.exports.EIGHTH_TURN_SINE = EIGHTH_TURN_SINE;
module.exports.EIGHTH_TURN_TANGENT = EIGHTH_TURN_TANGENT;
module.exports.ENCODED_ALREADY = ENCODED_ALREADY;
module.exports.ENGINE_TRANSFER_DIFFERS = ENGINE_TRANSFER_DIFFERS;
module.exports.FAMILY_LIST_PROPERTIES = FAMILY_LIST_PROPERTIES;
module.exports.FAMILY_LONGHANDS = FAMILY_LONGHANDS;
module.exports.FAMILY_SLOT_CLASSES = FAMILY_SLOT_CLASSES;
module.exports.FAMILY_SLOT_INITIALS = FAMILY_SLOT_INITIALS;
module.exports.FAMILY_SLOT_KEYWORDS = FAMILY_SLOT_KEYWORDS;
module.exports.FEATURELESS_PSEUDO_CLASSES = FEATURELESS_PSEUDO_CLASSES;
module.exports.FILTER_FUNCTION_OMITTED = FILTER_FUNCTION_OMITTED;
module.exports.FLEX_KEYWORDS = FLEX_KEYWORDS;
module.exports.FONT_SIZE_KEYWORDS = FONT_SIZE_KEYWORDS;
module.exports.FONT_STRETCH_PERCENTAGES = FONT_STRETCH_PERCENTAGES;
module.exports.FONT_WEIGHT_NUMBERS = FONT_WEIGHT_NUMBERS;
module.exports.GENERIC_FONT_FAMILIES = GENERIC_FONT_FAMILIES;
module.exports.GRADIENT_LAST_POSITIONS = GRADIENT_LAST_POSITIONS;
module.exports.INITIAL_VALUE_KEYWORDS = INITIAL_VALUE_KEYWORDS;
module.exports.INTEGER_PROPERTIES = INTEGER_PROPERTIES;
module.exports.KEYWORD_ONLY_PROPERTIES = KEYWORD_ONLY_PROPERTIES;
module.exports.LATER_COLOR_NAMES = LATER_COLOR_NAMES;
module.exports.LAYER_INITIALS = LAYER_INITIALS;
module.exports.LEGACY_PSEUDO_ELEMENTS = LEGACY_PSEUDO_ELEMENTS;
module.exports.LENGTH_ONLY_FUNCTIONS = LENGTH_ONLY_FUNCTIONS;
module.exports.LINEAR_GRADIENTS = LINEAR_GRADIENTS;
module.exports.LINEAR_SRGB_TO_P3 = LINEAR_SRGB_TO_P3;
module.exports.MATH_FUNCTIONS = MATH_FUNCTIONS;
module.exports.MATH_FUNCTION_ARITY = MATH_FUNCTION_ARITY;
module.exports.MATH_FUNCTION_FOLD = MATH_FUNCTION_FOLD;
module.exports.MATH_FUNCTION_KEYWORDS = MATH_FUNCTION_KEYWORDS;
module.exports.MATH_FUNCTION_SUM_ARGUMENTS = MATH_FUNCTION_SUM_ARGUMENTS;
module.exports.MERGEABLE_AT_RULES = MERGEABLE_AT_RULES;
module.exports.MERGE_LONGHANDS = MERGE_LONGHANDS;
module.exports.NEGATIVE_ACCEPTING_PROPERTIES = NEGATIVE_ACCEPTING_PROPERTIES;
module.exports.NEVER = NEVER;
module.exports.NTH_NAMED_EQUIVALENTS = NTH_NAMED_EQUIVALENTS;
module.exports.NTH_PSEUDO_FUNCTIONS = NTH_PSEUDO_FUNCTIONS;
module.exports.OMITTABLE_INITIAL_KEYWORDS = OMITTABLE_INITIAL_KEYWORDS;
module.exports.ONE_VALUE_PAIR_SHORTHANDS = ONE_VALUE_PAIR_SHORTHANDS;
module.exports.ORDERED_LONGHANDS = ORDERED_LONGHANDS;
module.exports.PAIR_LONGHANDS = PAIR_LONGHANDS;
module.exports.PLACE_SHORTHANDS = PLACE_SHORTHANDS;
module.exports.POSITION_PROPERTIES = POSITION_PROPERTIES;
module.exports.POSITION_X_KEYWORDS = POSITION_X_KEYWORDS;
module.exports.POSITION_Y_KEYWORDS = POSITION_Y_KEYWORDS;
module.exports.PREDEFINED_COLOR_SPACES = PREDEFINED_COLOR_SPACES;
module.exports.PREFIXED_AT_RULES = PREFIXED_AT_RULES;
module.exports.PREFIXED_PROPERTIES = PREFIXED_PROPERTIES;
module.exports.PREFIXED_SELECTORS = PREFIXED_SELECTORS;
module.exports.PREFIXED_SPELLING_KEYWORDS = PREFIXED_SPELLING_KEYWORDS;
module.exports.PREFIXED_VALUES = PREFIXED_VALUES;
module.exports.PREFIX_WINDOWS = PREFIX_WINDOWS;
module.exports.PREFIX_WINDOW_STARTS = PREFIX_WINDOW_STARTS;
module.exports.QUARTER_TURN_ANGLE = QUARTER_TURN_ANGLE;
module.exports.RATIO_PROPERTIES = RATIO_PROPERTIES;
module.exports.REPEAT_STYLE_KEYWORDS = REPEAT_STYLE_KEYWORDS;
module.exports.REPEAT_STYLE_PROPERTIES = REPEAT_STYLE_PROPERTIES;
module.exports.RGB_TO_NAME = RGB_TO_NAME;
module.exports.SELECTOR_FUNCTIONS = SELECTOR_FUNCTIONS;
module.exports.SELECTOR_SUPPORTED_FROM = SELECTOR_SUPPORTED_FROM;
module.exports.SHADOW_PROPERTIES = SHADOW_PROPERTIES;
module.exports.SHORTHAND_INITIAL_KEYWORDS = SHORTHAND_INITIAL_KEYWORDS;
module.exports.SHORTHAND_LONGHANDS = SHORTHAND_LONGHANDS;
module.exports.SLASH_BOX_SHORTHANDS = SLASH_BOX_SHORTHANDS;
module.exports.SLASH_LONGHANDS = SLASH_LONGHANDS;
module.exports.SRGB_SPACE = SRGB_SPACE;
module.exports.STEPPED_FUNCTIONS = STEPPED_FUNCTIONS;
module.exports.SUBSTITUTION_FUNCTIONS = SUBSTITUTION_FUNCTIONS;
module.exports.SUPPORTED_FROM = SUPPORTED_FROM;
module.exports.SUPPORT_BROWSERS = SUPPORT_BROWSERS;
module.exports.SUPPORT_PROFILES = SUPPORT_PROFILES;
module.exports.SYSTEM_UI_STACK = SYSTEM_UI_STACK;
module.exports.THROUGH_MATRIX = THROUGH_MATRIX;
module.exports.THROUGH_TRANSFER = THROUGH_TRANSFER;
module.exports.TRANSITION_BEHAVIORS = TRANSITION_BEHAVIORS;
module.exports.UNIT_CONVERSION_TARGETS = UNIT_CONVERSION_TARGETS;
module.exports.UNIT_GROUP_BASE = UNIT_GROUP_BASE;
module.exports.UNSHARED_LONGHAND_KEYWORDS = UNSHARED_LONGHAND_KEYWORDS;
module.exports.VALUE_SUPPORT_PACKED = VALUE_SUPPORT_PACKED;
module.exports.X_AXIS_TRANSFORMS = X_AXIS_TRANSFORMS;
module.exports.ZERO_ANGLE_FUNCTIONS = ZERO_ANGLE_FUNCTIONS;
module.exports.ZERO_UNIT_KEEPING_PROPERTIES = ZERO_UNIT_KEEPING_PROPERTIES;
// The arithmetic the printer's own evaluator needs. Sorted after the tables:
// `import/order` orders exports by case, uppercase first.
module.exports.foldAdd = foldAdd;
module.exports.foldDivide = foldDivide;
module.exports.foldMultiply = foldMultiply;