Changeset 245648 in webkit for trunk/Source/JavaScriptCore/parser/Lexer.cpp
- Timestamp:
- May 22, 2019, 2:52:58 PM (6 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/JavaScriptCore/parser/Lexer.cpp
r245634 r245648 814 814 } 815 815 816 template<typename CharacterType>817 static inline bool isASCIIDigitOrSeparator(CharacterType character)818 {819 return isASCIIDigit(character) || character == '_';820 }821 822 template<typename CharacterType>823 static inline bool isASCIIHexDigitOrSeparator(CharacterType character)824 {825 return isASCIIHexDigit(character) || character == '_';826 }827 828 template<typename CharacterType>829 static inline bool isASCIIBinaryDigitOrSeparator(CharacterType character)830 {831 return isASCIIBinaryDigit(character) || character == '_';832 }833 834 template<typename CharacterType>835 static inline bool isASCIIOctalDigitOrSeparator(CharacterType character)836 {837 return isASCIIOctalDigit(character) || character == '_';838 }839 840 816 static inline LChar singleEscape(int c) 841 817 { … … 1515 1491 1516 1492 template <typename T> 1517 ALWAYS_INLINE auto Lexer<T>::parseHex() -> Optional<NumberParseResult> 1518 { 1519 ASSERT(isASCIIHexDigit(m_current)); 1520 1493 ALWAYS_INLINE auto Lexer<T>::parseHex() -> NumberParseResult 1494 { 1521 1495 // Optimization: most hexadecimal values fit into 4 bytes. 1522 1496 uint32_t hexValue = 0; … … 1524 1498 1525 1499 do { 1526 if (m_current == '_') {1527 if (UNLIKELY(!isASCIIHexDigit(peek(1))))1528 return WTF::nullopt;1529 1530 shift();1531 }1532 1533 1500 hexValue = (hexValue << 4) + toASCIIHexValue(m_current); 1534 1501 shift(); 1535 1502 --maximumDigits; 1536 } while (isASCIIHexDigit OrSeparator(m_current) && maximumDigits >= 0);1503 } while (isASCIIHexDigit(m_current) && maximumDigits >= 0); 1537 1504 1538 1505 if (LIKELY(maximumDigits >= 0 && m_current != 'n')) 1539 return NumberParseResult { hexValue };1506 return hexValue; 1540 1507 1541 1508 // No more place in the hexValue buffer. … … 1550 1517 } 1551 1518 1552 while (isASCIIHexDigitOrSeparator(m_current)) { 1553 if (m_current == '_') { 1554 if (UNLIKELY(!isASCIIHexDigit(peek(1)))) 1555 return WTF::nullopt; 1556 1557 shift(); 1558 } 1559 1519 while (isASCIIHexDigit(m_current)) { 1560 1520 record8(m_current); 1561 1521 shift(); … … 1563 1523 1564 1524 if (UNLIKELY(Options::useBigInt() && m_current == 'n')) 1565 return NumberParseResult { makeIdentifier(m_buffer8.data(), m_buffer8.size()) };1525 return makeIdentifier(m_buffer8.data(), m_buffer8.size()); 1566 1526 1567 return NumberParseResult { parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 16) };1527 return parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 16); 1568 1528 } 1569 1529 … … 1571 1531 ALWAYS_INLINE auto Lexer<T>::parseBinary() -> Optional<NumberParseResult> 1572 1532 { 1573 ASSERT(isASCIIBinaryDigit(m_current));1574 1575 1533 // Optimization: most binary values fit into 4 bytes. 1576 1534 uint32_t binaryValue = 0; … … 1582 1540 1583 1541 do { 1584 if (m_current == '_') {1585 if (UNLIKELY(!isASCIIBinaryDigit(peek(1))))1586 return WTF::nullopt;1587 1588 shift();1589 }1590 1591 1542 binaryValue = (binaryValue << 1) + (m_current - '0'); 1592 1543 digits[digit] = m_current; 1593 1544 shift(); 1594 1545 --digit; 1595 } while (isASCIIBinaryDigit OrSeparator(m_current) && digit >= 0);1596 1597 if (LIKELY(!isASCIIDigit OrSeparator(m_current) && digit >= 0 && m_current != 'n'))1598 return NumberParseResult{ binaryValue };1546 } while (isASCIIBinaryDigit(m_current) && digit >= 0); 1547 1548 if (LIKELY(!isASCIIDigit(m_current) && digit >= 0 && m_current != 'n')) 1549 return Variant<double, const Identifier*> { binaryValue }; 1599 1550 1600 1551 for (int i = maximumDigits - 1; i > digit; --i) 1601 1552 record8(digits[i]); 1602 1553 1603 while (isASCIIBinaryDigitOrSeparator(m_current)) { 1604 if (m_current == '_') { 1605 if (UNLIKELY(!isASCIIBinaryDigit(peek(1)))) 1606 return WTF::nullopt; 1607 1608 shift(); 1609 } 1610 1554 while (isASCIIBinaryDigit(m_current)) { 1611 1555 record8(m_current); 1612 1556 shift(); … … 1614 1558 1615 1559 if (UNLIKELY(Options::useBigInt() && m_current == 'n')) 1616 return NumberParseResult{ makeIdentifier(m_buffer8.data(), m_buffer8.size()) };1560 return Variant<double, const Identifier*> { makeIdentifier(m_buffer8.data(), m_buffer8.size()) }; 1617 1561 1618 1562 if (isASCIIDigit(m_current)) 1619 1563 return WTF::nullopt; 1620 1564 1621 return NumberParseResult{ parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 2) };1565 return Variant<double, const Identifier*> { parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 2) }; 1622 1566 } 1623 1567 … … 1625 1569 ALWAYS_INLINE auto Lexer<T>::parseOctal() -> Optional<NumberParseResult> 1626 1570 { 1627 ASSERT(isASCIIOctalDigit(m_current));1628 1629 1571 // Optimization: most octal values fit into 4 bytes. 1630 1572 uint32_t octalValue = 0; … … 1636 1578 1637 1579 do { 1638 if (m_current == '_') {1639 if (UNLIKELY(!isASCIIOctalDigit(peek(1))))1640 return WTF::nullopt;1641 1642 shift();1643 }1644 1645 1580 octalValue = octalValue * 8 + (m_current - '0'); 1646 1581 digits[digit] = m_current; 1647 1582 shift(); 1648 1583 --digit; 1649 } while (isASCIIOctalDigitOrSeparator(m_current) && digit >= 0); 1650 1651 if (LIKELY(!isASCIIDigitOrSeparator(m_current) && digit >= 0 && m_current != 'n')) 1652 return NumberParseResult { octalValue }; 1584 } while (isASCIIOctalDigit(m_current) && digit >= 0); 1585 1586 if (LIKELY(!isASCIIDigit(m_current) && digit >= 0 && m_current != 'n')) 1587 return Variant<double, const Identifier*> { octalValue }; 1588 1653 1589 1654 1590 for (int i = maximumDigits - 1; i > digit; --i) 1655 1591 record8(digits[i]); 1656 1592 1657 while (isASCIIOctalDigitOrSeparator(m_current)) { 1658 if (m_current == '_') { 1659 if (UNLIKELY(!isASCIIOctalDigit(peek(1)))) 1660 return WTF::nullopt; 1661 1662 shift(); 1663 } 1664 1593 while (isASCIIOctalDigit(m_current)) { 1665 1594 record8(m_current); 1666 1595 shift(); … … 1668 1597 1669 1598 if (UNLIKELY(Options::useBigInt() && m_current == 'n')) 1670 return NumberParseResult{ makeIdentifier(m_buffer8.data(), m_buffer8.size()) };1599 return Variant<double, const Identifier*> { makeIdentifier(m_buffer8.data(), m_buffer8.size()) }; 1671 1600 1672 1601 if (isASCIIDigit(m_current)) 1673 1602 return WTF::nullopt; 1674 1603 1675 return NumberParseResult{ parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 8) };1604 return Variant<double, const Identifier*> { parseIntOverflow(m_buffer8.data(), m_buffer8.size(), 8) }; 1676 1605 } 1677 1606 … … 1679 1608 ALWAYS_INLINE auto Lexer<T>::parseDecimal() -> Optional<NumberParseResult> 1680 1609 { 1681 ASSERT(isASCIIDigit(m_current));1682 1683 1610 // Optimization: most decimal values fit into 4 bytes. 1684 1611 uint32_t decimalValue = 0; … … 1694 1621 1695 1622 do { 1696 if (m_current == '_') {1697 if (UNLIKELY(!isASCIIDigit(peek(1))))1698 return WTF::nullopt;1699 1700 shift();1701 }1702 1703 1623 decimalValue = decimalValue * 10 + (m_current - '0'); 1704 1624 digits[digit] = m_current; 1705 1625 shift(); 1706 1626 --digit; 1707 } while (isASCIIDigit OrSeparator(m_current) && digit >= 0);1627 } while (isASCIIDigit(m_current) && digit >= 0); 1708 1628 1709 1629 if (digit >= 0 && m_current != '.' && !isASCIIAlphaCaselessEqual(m_current, 'e') && m_current != 'n') 1710 return NumberParseResult{ decimalValue };1630 return Variant<double, const Identifier*> { decimalValue }; 1711 1631 1712 1632 for (int i = maximumDigits - 1; i > digit; --i) … … 1714 1634 } 1715 1635 1716 while (isASCIIDigitOrSeparator(m_current)) { 1717 if (m_current == '_') { 1718 if (UNLIKELY(!isASCIIDigit(peek(1)))) 1719 return WTF::nullopt; 1720 1721 shift(); 1722 } 1723 1636 while (isASCIIDigit(m_current)) { 1724 1637 record8(m_current); 1725 1638 shift(); … … 1727 1640 1728 1641 if (UNLIKELY(Options::useBigInt() && m_current == 'n')) 1729 return NumberParseResult{ makeIdentifier(m_buffer8.data(), m_buffer8.size()) };1642 return Variant<double, const Identifier*> { makeIdentifier(m_buffer8.data(), m_buffer8.size()) }; 1730 1643 1731 1644 return WTF::nullopt; … … 1733 1646 1734 1647 template <typename T> 1735 ALWAYS_INLINE bool Lexer<T>::parseNumberAfterDecimalPoint() 1736 { 1737 ASSERT(isASCIIDigit(m_current)); 1648 ALWAYS_INLINE void Lexer<T>::parseNumberAfterDecimalPoint() 1649 { 1738 1650 record8('.'); 1739 1740 do { 1741 if (m_current == '_') { 1742 if (UNLIKELY(!isASCIIDigit(peek(1)))) 1743 return false; 1744 1745 shift(); 1746 } 1747 1651 while (isASCIIDigit(m_current)) { 1748 1652 record8(m_current); 1749 1653 shift(); 1750 } while (isASCIIDigitOrSeparator(m_current)); 1751 1752 return true; 1654 } 1753 1655 } 1754 1656 … … 1767 1669 1768 1670 do { 1769 if (m_current == '_') {1770 if (UNLIKELY(!isASCIIDigit(peek(1))))1771 return false;1772 1773 shift();1774 }1775 1776 1671 record8(m_current); 1777 1672 shift(); 1778 } while (isASCIIDigitOrSeparator(m_current)); 1779 1673 } while (isASCIIDigit(m_current)); 1780 1674 return true; 1781 1675 } … … 2197 2091 break; 2198 2092 } 2199 if (UNLIKELY(!parseNumberAfterDecimalPoint())) { 2200 m_lexErrorMessage = "Non-number found after decimal point"_s; 2201 token = INVALID_NUMERIC_LITERAL_ERRORTOK; 2202 goto returnError; 2203 } 2093 parseNumberAfterDecimalPoint(); 2204 2094 token = DOUBLE; 2205 2095 if (isASCIIAlphaCaselessEqual(m_current, 'e')) { … … 2235 2125 2236 2126 auto parseNumberResult = parseHex(); 2237 if (!parseNumberResult) 2238 tokenData->doubleValue = 0; 2239 else if (WTF::holds_alternative<double>(*parseNumberResult)) 2240 tokenData->doubleValue = WTF::get<double>(*parseNumberResult); 2127 if (WTF::holds_alternative<double>(parseNumberResult)) 2128 tokenData->doubleValue = WTF::get<double>(parseNumberResult); 2241 2129 else { 2242 2130 token = BIGINT; 2243 2131 shift(); 2244 tokenData->bigIntString = WTF::get<const Identifier*>( *parseNumberResult);2132 tokenData->bigIntString = WTF::get<const Identifier*>(parseNumberResult); 2245 2133 tokenData->radix = 16; 2246 2134 } … … 2320 2208 m_buffer8.shrink(0); 2321 2209 break; 2322 }2323 2324 if (UNLIKELY(m_current == '_')) {2325 m_lexErrorMessage = "Numeric literals may not begin with 0_"_s;2326 token = UNTERMINATED_OCTAL_NUMBER_ERRORTOK;2327 goto returnError;2328 2210 } 2329 2211 … … 2359 2241 if (m_current == '.') { 2360 2242 shift(); 2361 if (UNLIKELY(isASCIIDigit(m_current) && !parseNumberAfterDecimalPoint())) { 2362 m_lexErrorMessage = "Non-number found after decimal point"_s; 2363 token = INVALID_NUMERIC_LITERAL_ERRORTOK; 2364 goto returnError; 2365 } 2243 parseNumberAfterDecimalPoint(); 2366 2244 token = DOUBLE; 2367 2245 }
Note:
See TracChangeset
for help on using the changeset viewer.