| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "config.h" | 5 #include "config.h" |
| 6 #include "core/css/parser/CSSTokenizer.h" | 6 #include "core/css/parser/CSSTokenizer.h" |
| 7 | 7 |
| 8 namespace blink { | 8 namespace blink { |
| 9 #include "core/CSSTokenizerCodepoints.cpp" | 9 #include "core/CSSTokenizerCodepoints.cpp" |
| 10 } | 10 } |
| (...skipping 13 matching lines...) Expand all Loading... |
| 24 return true; | 24 return true; |
| 25 return !isASCII(c); | 25 return !isASCII(c); |
| 26 } | 26 } |
| 27 | 27 |
| 28 // http://dev.w3.org/csswg/css-syntax/#name-code-point | 28 // http://dev.w3.org/csswg/css-syntax/#name-code-point |
| 29 static bool isNameChar(UChar c) | 29 static bool isNameChar(UChar c) |
| 30 { | 30 { |
| 31 return isNameStart(c) || isASCIIDigit(c) || c == '-'; | 31 return isNameStart(c) || isASCIIDigit(c) || c == '-'; |
| 32 } | 32 } |
| 33 | 33 |
| 34 static bool isNewLine(UChar cc) |
| 35 { |
| 36 // We check \r and \f here, since we have no preprocessing stage |
| 37 return (cc == '\r' || cc == '\n' || cc == '\f'); |
| 38 } |
| 39 |
| 34 // http://dev.w3.org/csswg/css-syntax/#check-if-two-code-points-are-a-valid-esca
pe | 40 // http://dev.w3.org/csswg/css-syntax/#check-if-two-code-points-are-a-valid-esca
pe |
| 35 static bool twoCharsAreValidEscape(UChar first, UChar second) | 41 static bool twoCharsAreValidEscape(UChar first, UChar second) |
| 36 { | 42 { |
| 37 return ((first == '\\') && (second != '\n') && (second != kEndOfFileMarker))
; | 43 return first == '\\' && !isNewLine(second) && second != kEndOfFileMarker; |
| 38 } | 44 } |
| 39 | 45 |
| 40 CSSTokenizer::CSSTokenizer(CSSTokenizerInputStream& inputStream) | 46 CSSTokenizer::CSSTokenizer(CSSTokenizerInputStream& inputStream) |
| 41 : m_input(inputStream) | 47 : m_input(inputStream) |
| 42 { | 48 { |
| 43 } | 49 } |
| 44 | 50 |
| 45 void CSSTokenizer::reconsume(UChar c) | 51 void CSSTokenizer::reconsume(UChar c) |
| 46 { | 52 { |
| 47 m_input.pushBack(c); | 53 m_input.pushBack(c); |
| (...skipping 298 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 346 // http://www.w3.org/TR/css3-syntax/#consume-an-ident-like-token | 352 // http://www.w3.org/TR/css3-syntax/#consume-an-ident-like-token |
| 347 CSSParserToken CSSTokenizer::consumeIdentLikeToken() | 353 CSSParserToken CSSTokenizer::consumeIdentLikeToken() |
| 348 { | 354 { |
| 349 String name = consumeName(); | 355 String name = consumeName(); |
| 350 if (consumeIfNext('(')) { | 356 if (consumeIfNext('(')) { |
| 351 return blockStart(LeftParenthesisToken, FunctionToken, name); | 357 return blockStart(LeftParenthesisToken, FunctionToken, name); |
| 352 } | 358 } |
| 353 return CSSParserToken(IdentToken, name); | 359 return CSSParserToken(IdentToken, name); |
| 354 } | 360 } |
| 355 | 361 |
| 356 static bool isNewLine(UChar cc) | |
| 357 { | |
| 358 // We check \r and \f here, since we have no preprocessing stage | |
| 359 return (cc == '\r' || cc == '\n' || cc == '\f'); | |
| 360 } | |
| 361 | |
| 362 // http://dev.w3.org/csswg/css-syntax/#consume-a-string-token | 362 // http://dev.w3.org/csswg/css-syntax/#consume-a-string-token |
| 363 CSSParserToken CSSTokenizer::consumeStringTokenUntil(UChar endingCodePoint) | 363 CSSParserToken CSSTokenizer::consumeStringTokenUntil(UChar endingCodePoint) |
| 364 { | 364 { |
| 365 StringBuilder output; | 365 StringBuilder output; |
| 366 while (true) { | 366 while (true) { |
| 367 UChar cc = consume(); | 367 UChar cc = consume(); |
| 368 if (cc == endingCodePoint || cc == kEndOfFileMarker) { | 368 if (cc == endingCodePoint || cc == kEndOfFileMarker) { |
| 369 // The "reconsume" here deviates from the spec, but is required to a
void consuming past the EOF | 369 // The "reconsume" here deviates from the spec, but is required to a
void consuming past the EOF |
| 370 if (cc == kEndOfFileMarker) | 370 if (cc == kEndOfFileMarker) |
| 371 reconsume(cc); | 371 reconsume(cc); |
| 372 return CSSParserToken(StringToken, output.toString()); | 372 return CSSParserToken(StringToken, output.toString()); |
| 373 } | 373 } |
| 374 if (isNewLine(cc)) { | 374 if (isNewLine(cc)) { |
| 375 reconsume(cc); | 375 reconsume(cc); |
| 376 return CSSParserToken(BadStringToken); | 376 return CSSParserToken(BadStringToken); |
| 377 } | 377 } |
| 378 if (cc == '\\') { | 378 if (cc == '\\') { |
| 379 if (m_input.nextInputChar() == kEndOfFileMarker) | 379 if (m_input.nextInputChar() == kEndOfFileMarker) |
| 380 continue; | 380 continue; |
| 381 if (isNewLine(m_input.nextInputChar())) | 381 if (isNewLine(m_input.nextInputChar())) |
| 382 consume(); | 382 consumeSingleWhitespaceIfNext(); // This handles \r\n for us |
| 383 else | 383 else |
| 384 output.append(consumeEscape()); | 384 output.append(consumeEscape()); |
| 385 } else { | 385 } else { |
| 386 output.append(cc); | 386 output.append(cc); |
| 387 } | 387 } |
| 388 } | 388 } |
| 389 } | 389 } |
| 390 | 390 |
| 391 void CSSTokenizer::consumeUntilNonWhitespace() | 391 void CSSTokenizer::consumeUntilNonWhitespace() |
| 392 { | 392 { |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 449 } | 449 } |
| 450 reconsume(cc); | 450 reconsume(cc); |
| 451 return result.toString(); | 451 return result.toString(); |
| 452 } | 452 } |
| 453 } | 453 } |
| 454 | 454 |
| 455 // http://dev.w3.org/csswg/css-syntax/#consume-an-escaped-code-point | 455 // http://dev.w3.org/csswg/css-syntax/#consume-an-escaped-code-point |
| 456 UChar CSSTokenizer::consumeEscape() | 456 UChar CSSTokenizer::consumeEscape() |
| 457 { | 457 { |
| 458 UChar cc = consume(); | 458 UChar cc = consume(); |
| 459 ASSERT(cc != '\n'); | 459 ASSERT(!isNewLine(cc)); |
| 460 if (isASCIIHexDigit(cc)) { | 460 if (isASCIIHexDigit(cc)) { |
| 461 unsigned consumedHexDigits = 1; | 461 unsigned consumedHexDigits = 1; |
| 462 StringBuilder hexChars; | 462 StringBuilder hexChars; |
| 463 hexChars.append(cc); | 463 hexChars.append(cc); |
| 464 while (consumedHexDigits < 6 && isASCIIHexDigit(m_input.nextInputChar())
) { | 464 while (consumedHexDigits < 6 && isASCIIHexDigit(m_input.nextInputChar())
) { |
| 465 cc = consume(); | 465 cc = consume(); |
| 466 hexChars.append(cc); | 466 hexChars.append(cc); |
| 467 consumedHexDigits++; | 467 consumedHexDigits++; |
| 468 }; | 468 }; |
| 469 consumeSingleWhitespaceIfNext(); | 469 consumeSingleWhitespaceIfNext(); |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 526 | 526 |
| 527 bool CSSTokenizer::nextCharsAreIdentifier() | 527 bool CSSTokenizer::nextCharsAreIdentifier() |
| 528 { | 528 { |
| 529 UChar first = consume(); | 529 UChar first = consume(); |
| 530 bool areIdentifier = nextCharsAreIdentifier(first); | 530 bool areIdentifier = nextCharsAreIdentifier(first); |
| 531 reconsume(first); | 531 reconsume(first); |
| 532 return areIdentifier; | 532 return areIdentifier; |
| 533 } | 533 } |
| 534 | 534 |
| 535 } // namespace blink | 535 } // namespace blink |
| OLD | NEW |