Gildas 7 лет назад
Родитель
Сommit
dc5126fc49
1 измененных файлов с 102 добавлено и 238 удалено
  1. 102 238
      lib/single-file/css-declarations-parser.js

+ 102 - 238
lib/single-file/css-declarations-parser.js

@@ -64,6 +64,41 @@ this.parseCss = this.parseCss || (() => {
 		return String.fromCharCode(lead) + String.fromCharCode(trail);
 	}
 
+	const BAD_STRING_TOKEN_TYPE = "BADSTRING";
+	const BAD_URL_TOKEN_TYPE = "BADURL";
+	const WHITESPACE_TOKEN_TYPE = "WHITESPACE";
+	const CDO_TOKEN_TYPE = "CDO";
+	const CDC_TOKEN_TYPE = "CDO";
+	const COLON_TOKEN_TYPE = ":";
+	const SEMICOLON_TOKEN_TYPE = ";";
+	const COMMA_TOKEN_TYPE = ",";
+	const OPEN_CURLY_TOKEN_TYPE = "{";
+	const CLOSE_CURLY_TOKEN_TYPE = "}";
+	const OPEN_SQUARE_TOKEN_TYPE = "[";
+	const CLOSE_SQUARE_TOKEN_TYPE = "]";
+	const OPEN_PAREN_TOKEN_TYPE = "(";
+	const CLOSE_PAREN_TOKEN_TYPE = ";";
+	const INCLUDE_MATCH_TOKEN_TYPE = "~=";
+	const DASH_MATCH_TOKEN_TYPE = "|=";
+	const PREFIX_MATCH_TOKEN_TYPE = "^=";
+	const SUFFIX_MATCH_TOKEN_TYPE = "$=";
+	const SUBSTRING_MATCH_TOKEN_TYPE = "*=";
+	const COLUMN_TOKEN_TYPE = "||";
+	const EOF_TOKEN_TYPE = "EOF";
+	const DELIM_TOKEN_TYPE = "DELIM";
+	const IDENT_TOKEN_TYPE = "IDENT";
+	const FUNCTION_TOKEN_TYPE = "FUNCTION";
+	const HASH_TOKEN_TYPE = "HASH";
+	const STRING_TOKEN_TYPE = "STRING";
+	const URL_TOKEN_TYPE = "URL";
+	const NUMBER_TOKEN_TYPE = "NUMBER";
+	const PERCENTAGE_TOKEN_TYPE = "PERCENTAGE";
+	const DIMENSION_TOKEN_TYPE = "DIMENSION";
+
+	function ASCIIMatch(str) {
+		return this.value.toLowerCase() == str.toLowerCase();
+	}
+
 	function tokenize(str) {
 		str = preprocess(str);
 		let i = -1;
@@ -129,36 +164,36 @@ this.parseCss = this.parseCss || (() => {
 			consume();
 			if (whitespace(code)) {
 				while (whitespace(next())) consume();
-				return new WhitespaceToken;
+				return new Token(WHITESPACE_TOKEN_TYPE);
 			}
 			else if (code == 0x22) return consumeAStringToken();
 			else if (code == 0x23) {
 				if (namechar(next()) || areAValidEscape(next(1), next(2))) {
-					const token = new HashToken();
+					const token = new Token(HASH_TOKEN_TYPE);
 					if (wouldStartAnIdentifier(next(1), next(2), next(3))) token.type = "id";
 					token.value = consumeAName();
 					return token;
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (code == 0x24) {
 				if (next() == 0x3d) {
 					consume();
-					return new SuffixMatchToken();
+					return new Token(SUFFIX_MATCH_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (code == 0x27) return consumeAStringToken();
-			else if (code == 0x28) return new OpenParenToken();
-			else if (code == 0x29) return new CloseParenToken();
+			else if (code == 0x28) return new Token(OPEN_PAREN_TOKEN_TYPE);
+			else if (code == 0x29) return new Token(CLOSE_PAREN_TOKEN_TYPE);
 			else if (code == 0x2a) {
 				if (next() == 0x3d) {
 					consume();
-					return new SubstringMatchToken();
+					return new Token(SUBSTRING_MATCH_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (code == 0x2b) {
@@ -166,22 +201,22 @@ this.parseCss = this.parseCss || (() => {
 					reconsume();
 					return consumeANumericToken();
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
-			else if (code == 0x2c) return new CommaToken();
+			else if (code == 0x2c) return new Token(COMMA_TOKEN_TYPE);
 			else if (code == 0x2d) {
 				if (startsWithANumber()) {
 					reconsume();
 					return consumeANumericToken();
 				} else if (next(1) == 0x2d && next(2) == 0x3e) {
 					consume(2);
-					return new CDCToken();
+					return new Token(CDC_TOKEN_TYPE);
 				} else if (startsWithAnIdentifier()) {
 					reconsume();
 					return consumeAnIdentlikeToken();
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (code == 0x2e) {
@@ -189,60 +224,60 @@ this.parseCss = this.parseCss || (() => {
 					reconsume();
 					return consumeANumericToken();
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
-			else if (code == 0x3a) return new ColonToken;
-			else if (code == 0x3b) return new SemicolonToken;
+			else if (code == 0x3a) return new Token(COLON_TOKEN_TYPE);
+			else if (code == 0x3b) return new Token(SEMICOLON_TOKEN_TYPE);
 			else if (code == 0x3c) {
 				if (next(1) == 0x21 && next(2) == 0x2d && next(3) == 0x2d) {
 					consume(3);
-					return new CDOToken();
+					return new Token(CDO_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (code == 0x40) {
-				return new DelimToken(code);
+				return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 			}
-			else if (code == 0x5b) return new OpenSquareToken();
+			else if (code == 0x5b) new Token(OPEN_SQUARE_TOKEN_TYPE);
 			else if (code == 0x5c) {
 				if (startsWithAValidEscape()) {
 					reconsume();
 					return consumeAnIdentlikeToken();
 				} else {
 					parseerror();
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
-			else if (code == 0x5d) return new CloseSquareToken();
+			else if (code == 0x5d) new Token(CLOSE_SQUARE_TOKEN_TYPE);
 			else if (code == 0x5e) {
 				if (next() == 0x3d) {
 					consume();
-					return new PrefixMatchToken();
+					return new Token(PREFIX_MATCH_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
-			else if (code == 0x7b) return new OpenCurlyToken();
+			else if (code == 0x7b) return new Token(OPEN_CURLY_TOKEN_TYPE);
 			else if (code == 0x7c) {
 				if (next() == 0x3d) {
 					consume();
-					return new DashMatchToken();
+					return new Token(DASH_MATCH_TOKEN_TYPE);
 				} else if (next() == 0x7c) {
 					consume();
-					return new ColumnToken();
+					return new Token(COLUMN_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
-			else if (code == 0x7d) return new CloseCurlyToken();
+			else if (code == 0x7d) return new Token(CLOSE_CURLY_TOKEN_TYPE);
 			else if (code == 0x7e) {
 				if (next() == 0x3d) {
 					consume();
-					return new IncludeMatchToken();
+					return new Token(INCLUDE_MATCH_TOKEN_TYPE);
 				} else {
-					return new DelimToken(code);
+					return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 				}
 			}
 			else if (digit(code)) {
@@ -253,8 +288,8 @@ this.parseCss = this.parseCss || (() => {
 				reconsume();
 				return consumeAnIdentlikeToken();
 			}
-			else if (eof()) return new EOFToken();
-			else return new DelimToken(code);
+			else if (eof()) return new Token(EOF_TOKEN_TYPE);
+			else return new Token(DELIM_TOKEN_TYPE, stringFromCode(code));
 		};
 
 		const consumeComments = function () {
@@ -276,21 +311,19 @@ this.parseCss = this.parseCss || (() => {
 		const consumeANumericToken = function () {
 			const num = consumeANumber();
 			if (wouldStartAnIdentifier(next(1), next(2), next(3))) {
-				const token = new DimensionToken();
-				token.value = num.value;
+				const token = new Token(DIMENSION_TOKEN_TYPE, num.value);
 				token.repr = num.repr;
 				token.type = num.type;
 				token.unit = consumeAName();
 				return token;
 			} else if (next() == 0x25) {
 				consume();
-				const token = new PercentageToken();
-				token.value = num.value;
+				const token = new Token(PERCENTAGE_TOKEN_TYPE, num.value);
 				token.repr = num.repr;
 				return token;
 			} else {
-				const token = new NumberToken();
-				token.value = num.value;
+				const token = new Token(NUMBER_TOKEN_TYPE, num.value);
+				token.type = "integer";
 				token.repr = num.repr;
 				token.type = num.type;
 				return token;
@@ -303,17 +336,19 @@ this.parseCss = this.parseCss || (() => {
 				consume();
 				while (whitespace(next(1)) && whitespace(next(2))) consume();
 				if (next() == 0x22 || next() == 0x27) {
-					return new FunctionToken(str);
+					return new Token(FUNCTION_TOKEN_TYPE, str);
 				} else if (whitespace(next()) && (next(2) == 0x22 || next(2) == 0x27)) {
-					return new FunctionToken(str);
+					return new Token(FUNCTION_TOKEN_TYPE, str);
 				} else {
 					return consumeAURLToken();
 				}
 			} else if (next() == 0x28) {
 				consume();
-				return new FunctionToken(str);
+				return new Token(FUNCTION_TOKEN_TYPE, str);
 			} else {
-				return new IdentToken(str);
+				const token = new Token(IDENT_TOKEN_TYPE, str);
+				token.ASCIIMatch = ASCIIMatch;
+				return token;
 			}
 		};
 
@@ -322,11 +357,11 @@ this.parseCss = this.parseCss || (() => {
 			let string = "";
 			while (consume()) {
 				if (code == endingCodePoint || eof()) {
-					return new StringToken(string);
+					return new Token(STRING_TOKEN_TYPE, string);
 				} else if (newline(code)) {
 					parseerror();
 					reconsume();
-					return new BadStringToken();
+					return new Token(BAD_STRING_TOKEN_TYPE);
 				} else if (code == 0x5c) {
 					if (eof(next())) {
 						donothing();
@@ -342,7 +377,7 @@ this.parseCss = this.parseCss || (() => {
 		};
 
 		const consumeAURLToken = function () {
-			const token = new URLToken("");
+			const token = new Token(URL_TOKEN_TYPE, "");
 			while (whitespace(next())) consume();
 			if (eof(next())) return token;
 			while (consume()) {
@@ -355,19 +390,19 @@ this.parseCss = this.parseCss || (() => {
 						return token;
 					} else {
 						consumeTheRemnantsOfABadURL();
-						return new BadURLToken();
+						return new Token(BAD_URL_TOKEN_TYPE);
 					}
 				} else if (code == 0x22 || code == 0x27 || code == 0x28 || nonprintable(code)) {
 					parseerror();
 					consumeTheRemnantsOfABadURL();
-					return new BadURLToken();
+					return new Token(BAD_URL_TOKEN_TYPE);
 				} else if (code == 0x5c) {
 					if (startsWithAValidEscape()) {
 						token.value += stringFromCode(consumeEscape());
 					} else {
 						parseerror();
 						consumeTheRemnantsOfABadURL();
-						return new BadURLToken();
+						return new Token(BAD_URL_TOKEN_TYPE);
 					}
 				} else {
 					token.value += stringFromCode(code);
@@ -536,177 +571,10 @@ this.parseCss = this.parseCss || (() => {
 		return tokens;
 	}
 
-	function CSSParserToken() { }
-	CSSParserToken.prototype.toString = function () { return this.tokenType; };
-
-	function BadStringToken() { return this; }
-	BadStringToken.prototype = Object.create(CSSParserToken.prototype);
-	BadStringToken.prototype.tokenType = "BADSTRING";
-
-	function BadURLToken() { return this; }
-	BadURLToken.prototype = Object.create(CSSParserToken.prototype);
-	BadURLToken.prototype.tokenType = "BADURL";
-
-	function WhitespaceToken() { return this; }
-	WhitespaceToken.prototype = Object.create(CSSParserToken.prototype);
-	WhitespaceToken.prototype.tokenType = "WHITESPACE";
-	WhitespaceToken.prototype.toString = function () { return "WS"; };
-
-	function CDOToken() { return this; }
-	CDOToken.prototype = Object.create(CSSParserToken.prototype);
-	CDOToken.prototype.tokenType = "CDO";
-
-	function CDCToken() { return this; }
-	CDCToken.prototype = Object.create(CSSParserToken.prototype);
-	CDCToken.prototype.tokenType = "CDC";
-
-	function ColonToken() { return this; }
-	ColonToken.prototype = Object.create(CSSParserToken.prototype);
-	ColonToken.prototype.tokenType = ":";
-
-	function SemicolonToken() { return this; }
-	SemicolonToken.prototype = Object.create(CSSParserToken.prototype);
-	SemicolonToken.prototype.tokenType = ";";
-
-	function CommaToken() { return this; }
-	CommaToken.prototype = Object.create(CSSParserToken.prototype);
-	CommaToken.prototype.tokenType = ",";
-
-	function GroupingToken() { throw "Abstract Base Class"; }
-	GroupingToken.prototype = Object.create(CSSParserToken.prototype);
-
-	function OpenCurlyToken() { this.value = "{"; this.mirror = "}"; return this; }
-	OpenCurlyToken.prototype = Object.create(GroupingToken.prototype);
-	OpenCurlyToken.prototype.tokenType = "{";
-
-	function CloseCurlyToken() { this.value = "}"; this.mirror = "{"; return this; }
-	CloseCurlyToken.prototype = Object.create(GroupingToken.prototype);
-	CloseCurlyToken.prototype.tokenType = "}";
-
-	function OpenSquareToken() { this.value = "["; this.mirror = "]"; return this; }
-	OpenSquareToken.prototype = Object.create(GroupingToken.prototype);
-	OpenSquareToken.prototype.tokenType = "[";
-
-	function CloseSquareToken() { this.value = "]"; this.mirror = "["; return this; }
-	CloseSquareToken.prototype = Object.create(GroupingToken.prototype);
-	CloseSquareToken.prototype.tokenType = "]";
-
-	function OpenParenToken() { this.value = "("; this.mirror = ")"; return this; }
-	OpenParenToken.prototype = Object.create(GroupingToken.prototype);
-	OpenParenToken.prototype.tokenType = "(";
-
-	function CloseParenToken() { this.value = ")"; this.mirror = "("; return this; }
-	CloseParenToken.prototype = Object.create(GroupingToken.prototype);
-	CloseParenToken.prototype.tokenType = ")";
-
-	function IncludeMatchToken() { return this; }
-	IncludeMatchToken.prototype = Object.create(CSSParserToken.prototype);
-	IncludeMatchToken.prototype.tokenType = "~=";
-
-	function DashMatchToken() { return this; }
-	DashMatchToken.prototype = Object.create(CSSParserToken.prototype);
-	DashMatchToken.prototype.tokenType = "|=";
-
-	function PrefixMatchToken() { return this; }
-	PrefixMatchToken.prototype = Object.create(CSSParserToken.prototype);
-	PrefixMatchToken.prototype.tokenType = "^=";
-
-	function SuffixMatchToken() { return this; }
-	SuffixMatchToken.prototype = Object.create(CSSParserToken.prototype);
-	SuffixMatchToken.prototype.tokenType = "$=";
-
-	function SubstringMatchToken() { return this; }
-	SubstringMatchToken.prototype = Object.create(CSSParserToken.prototype);
-	SubstringMatchToken.prototype.tokenType = "*=";
-
-	function ColumnToken() { return this; }
-	ColumnToken.prototype = Object.create(CSSParserToken.prototype);
-	ColumnToken.prototype.tokenType = "||";
-
-	function EOFToken() { return this; }
-	EOFToken.prototype = Object.create(CSSParserToken.prototype);
-	EOFToken.prototype.tokenType = "EOF";
-
-	function DelimToken(code) {
-		this.value = stringFromCode(code);
-		return this;
-	}
-	DelimToken.prototype = Object.create(CSSParserToken.prototype);
-	DelimToken.prototype.tokenType = "DELIM";
-	DelimToken.prototype.toString = function () { return "DELIM(" + this.value + ")"; };
-
-	function StringValuedToken() { throw "Abstract Base Class"; }
-	StringValuedToken.prototype = Object.create(CSSParserToken.prototype);
-	StringValuedToken.prototype.ASCIIMatch = function (str) {
-		return this.value.toLowerCase() == str.toLowerCase();
-	};
-
-	function IdentToken(val) {
-		this.value = val;
+	function Token(tokenType, value) {
+		this.tokenType = tokenType;
+		this.value = value;
 	}
-	IdentToken.prototype = Object.create(StringValuedToken.prototype);
-	IdentToken.prototype.tokenType = "IDENT";
-	IdentToken.prototype.toString = function () { return "IDENT(" + this.value + ")"; };
-
-	function FunctionToken(val) {
-		this.value = val;
-		this.mirror = ")";
-	}
-	FunctionToken.prototype = Object.create(StringValuedToken.prototype);
-	FunctionToken.prototype.tokenType = "FUNCTION";
-	FunctionToken.prototype.toString = function () { return "FUNCTION(" + this.value + ")"; };
-
-	function HashToken(val) {
-		this.value = val;
-		this.type = "unrestricted";
-	}
-	HashToken.prototype = Object.create(StringValuedToken.prototype);
-	HashToken.prototype.tokenType = "HASH";
-	HashToken.prototype.toString = function () { return "HASH(" + this.value + ")"; };
-
-	function StringToken(val) {
-		this.value = val;
-	}
-	StringToken.prototype = Object.create(StringValuedToken.prototype);
-	StringToken.prototype.tokenType = "STRING";
-
-	function URLToken(val) {
-		this.value = val;
-	}
-	URLToken.prototype = Object.create(StringValuedToken.prototype);
-	URLToken.prototype.tokenType = "URL";
-	URLToken.prototype.toString = function () { return "URL(" + this.value + ")"; };
-
-	function NumberToken() {
-		this.value = null;
-		this.type = "integer";
-		this.repr = "";
-	}
-	NumberToken.prototype = Object.create(CSSParserToken.prototype);
-	NumberToken.prototype.tokenType = "NUMBER";
-	NumberToken.prototype.toString = function () {
-		if (this.type == "integer")
-			return "INT(" + this.value + ")";
-		return "NUMBER(" + this.value + ")";
-	};
-
-	function PercentageToken() {
-		this.value = null;
-		this.repr = "";
-	}
-	PercentageToken.prototype = Object.create(CSSParserToken.prototype);
-	PercentageToken.prototype.tokenType = "PERCENTAGE";
-	PercentageToken.prototype.toString = function () { return "PERCENTAGE(" + this.value + ")"; };
-
-	function DimensionToken() {
-		this.value = null;
-		this.type = "integer";
-		this.repr = "";
-		this.unit = "";
-	}
-	DimensionToken.prototype = Object.create(CSSParserToken.prototype);
-	DimensionToken.prototype.tokenType = "DIMENSION";
-	DimensionToken.prototype.toString = function () { return "DIM(" + this.value + "," + this.unit + ")"; };
 
 	// ---
 	function TokenStream(tokens) {
@@ -717,7 +585,7 @@ this.parseCss = this.parseCss || (() => {
 	TokenStream.prototype.tokenAt = function (i) {
 		if (i < this.tokens.length)
 			return this.tokens[i];
-		return new EOFToken();
+		return { tokenType: EOF_TOKEN_TYPE };
 	};
 	TokenStream.prototype.consume = function (num) {
 		if (num === undefined) num = 1;
@@ -741,20 +609,20 @@ this.parseCss = this.parseCss || (() => {
 	function consumeAListOfDeclarations(s) {
 		const decls = [];
 		while (s.consume()) {
-			if (s.token instanceof WhitespaceToken || s.token instanceof SemicolonToken) {
+			if (s.token.tokenType == WHITESPACE_TOKEN_TYPE || s.token.tokenType == SEMICOLON_TOKEN_TYPE) {
 				donothing();
-			} else if (s.token instanceof EOFToken) {
+			} else if (s.token.tokenType == EOF_TOKEN_TYPE) {
 				return decls;
-			} else if (s.token instanceof IdentToken) {
+			} else if (s.token.tokenType == IDENT_TOKEN_TYPE) {
 				const temp = [s.token];
-				while (!(s.next() instanceof SemicolonToken || s.next() instanceof EOFToken))
+				while (!(s.next().tokenType == SEMICOLON_TOKEN_TYPE || s.next().tokenType == EOF_TOKEN_TYPE))
 					temp.push(consumeAComponentValue(s));
 				let decl = consumeADeclaration(new TokenStream(temp));
 				if (decl) decls.push(decl);
 			} else {
 				parseerror(s);
 				s.reconsume();
-				while (!(s.next() instanceof SemicolonToken || s.next() instanceof EOFToken))
+				while (!(s.next().tokenType == SEMICOLON_TOKEN_TYPE || s.next().tokenType == EOF_TOKEN_TYPE))
 					consumeAComponentValue(s);
 			}
 		}
@@ -764,23 +632,23 @@ this.parseCss = this.parseCss || (() => {
 		// Assumes that the next input token will be an ident token.
 		s.consume();
 		const decl = new Declaration(s.token.value);
-		while (s.next() instanceof WhitespaceToken) s.consume();
-		if (!(s.next() instanceof ColonToken)) {
+		while (s.next().tokenType == WHITESPACE_TOKEN_TYPE) s.consume();
+		if (!(s.next().tokenType == COLON_TOKEN_TYPE)) {
 			parseerror(s);
 			return;
 		} else {
 			s.consume();
 		}
-		while (!(s.next() instanceof EOFToken)) {
+		while (!(s.next().tokenType == EOF_TOKEN_TYPE)) {
 			decl.value.push(consumeAComponentValue(s));
 		}
 		let foundImportant = false;
 		for (let i = decl.value.length - 1; i >= 0; i--) {
-			if (decl.value[i] instanceof WhitespaceToken) {
+			if (decl.value[i].tokenType == WHITESPACE_TOKEN_TYPE) {
 				continue;
-			} else if (decl.value[i] instanceof IdentToken && decl.value[i].ASCIIMatch("important")) {
+			} else if (decl.value[i].tokenType == IDENT_TOKEN_TYPE && decl.value[i].ASCIIMatch("important")) {
 				foundImportant = true;
-			} else if (foundImportant && decl.value[i] instanceof DelimToken && decl.value[i].value == "!") {
+			} else if (foundImportant && decl.value[i].tokenType == DELIM_TOKEN_TYPE && decl.value[i].value == "!") {
 				decl.value.splice(i, decl.value.length);
 				decl.important = true;
 				break;
@@ -793,7 +661,7 @@ this.parseCss = this.parseCss || (() => {
 
 	function consumeAComponentValue(s) {
 		s.consume();
-		if (s.token instanceof FunctionToken)
+		if (s.token.tokenType == FUNCTION_TOKEN_TYPE)
 			return consumeAFunction(s);
 		return s.token;
 	}
@@ -801,7 +669,7 @@ this.parseCss = this.parseCss || (() => {
 	function consumeAFunction(s) {
 		const func = new Func(s.token.value);
 		while (s.consume()) {
-			if (s.token instanceof EOFToken || s.token instanceof CloseParenToken)
+			if (s.token.tokenType == EOF_TOKEN_TYPE || s.token.tokenType == CLOSE_PAREN_TOKEN_TYPE)
 				return func;
 			else {
 				s.reconsume();
@@ -821,15 +689,12 @@ this.parseCss = this.parseCss || (() => {
 		return consumeAListOfDeclarations(s);
 	}
 
-	function CSSParserRule() { throw "Abstract Base Class"; }
-
 	function Declaration(name) {
 		this.name = name;
 		this.value = [];
 		this.important = false;
 		return this;
 	}
-	Declaration.prototype = Object.create(CSSParserRule.prototype);
 	Declaration.prototype.type = "DECLARATION";
 
 	function Func(name) {
@@ -837,13 +702,12 @@ this.parseCss = this.parseCss || (() => {
 		this.value = [];
 		return this;
 	}
-	Func.prototype = Object.create(CSSParserRule.prototype);
 	Func.prototype.type = "FUNCTION";
 
 	// Exportation.
 
 	return {
-		parseAListOfDeclarations: parseAListOfDeclarations
+		parseAListOfDeclarations
 	};
 
 })();