source: webkit/trunk/Source/JavaScriptCore/parser/Lexer.h

Last change on this file was 284075, checked in by [email protected], 4 years ago

Use std::variant instead of WTF::Variant
https://bugs.webkit.org/show_bug.cgi?id=231629

by Alex Christensen <[email protected]> on 2021-10-12
Reviewed by Chris Dumez.

Source/JavaScriptCore:

  • bytecode/StructureStubClearingWatchpoint.h:
  • dfg/DFGSpeculativeJIT.cpp:

(JSC::DFG::SpeculativeJIT::compileCallDOM):

  • jit/AssemblyHelpers.cpp:

(JSC::AssemblyHelpers::branchIfValue):

  • jit/AssemblyHelpers.h:

(JSC::AssemblyHelpers::branchIfTruthy):
(JSC::AssemblyHelpers::branchIfFalsey):

  • jit/SnippetReg.h:
  • jsc.cpp:
  • parser/Lexer.h:
  • parser/VariableEnvironment.h:
  • runtime/BytecodeCacheError.h:
  • runtime/CachePayload.cpp:

(JSC::CachePayload::CachePayload):

  • runtime/CachePayload.h:
  • runtime/CacheUpdate.h:
  • runtime/ISO8601.cpp:

(JSC::ISO8601::parseTimeZoneBracketedAnnotation):

  • runtime/ISO8601.h:
  • wasm/WasmLLIntGenerator.cpp:

Source/WebCore:

  • Modules/async-clipboard/ClipboardItemBindingsDataSource.h:
  • Modules/cache/DOMCacheEngine.h:
  • Modules/fetch/Fetcdy.h:
  • Modules/fetch/FetcdyOwner.h:
  • Modules/fetch/FetchHeaders.h:
  • Modules/fetch/FetchRequest.h:
  • Modules/fetch/FetchResponse.h:
  • Modules/indexeddb/IDBCursor.h:
  • Modules/indexeddb/IDBDatabase.h:
  • Modules/indexeddb/IDBKey.h:
  • Modules/indexeddb/IDBKeyData.h:
  • Modules/indexeddb/IDBKeyPath.h:
  • Modules/indexeddb/IDBRequest.h:
  • Modules/mediacontrols/MediaControlsHost.cpp:

(WebCore::MediaControlsHost::showMediaControlsContextMenu):

  • Modules/mediacontrols/MediaControlsHost.h:
  • Modules/mediastream/MediaDevices.cpp:

(WebCore::createMediaConstraints):

  • Modules/mediastream/MediaDevices.h:
  • Modules/mediastream/MediaTrackConstraints.h:
  • Modules/mediastream/RTCIceServer.h:
  • Modules/mediastream/RTCPeerConnection.h:
  • Modules/mediastream/RTCRtpTransform.h:
  • Modules/mediastream/libwebrtc/LibWebRTCDataChannelHandler.h:
  • Modules/mediastream/libwebrtc/LibWebRTCRtpSenderBackend.h:
  • Modules/paymentrequest/PaymentMethodChangeEvent.h:
  • Modules/paymentrequest/PaymentRequest.h:
  • Modules/push-api/PushEventInit.h:
  • Modules/push-api/PushSubscriptionOptionsInit.h:
  • Modules/speech/SpeechRecognitionUpdate.h:
  • Modules/webaudio/AudioContextOptions.h:
  • Modules/webaudio/AudioNode.h:
  • Modules/webxr/WebXRWebGLLayer.h:
  • accessibility/AXObjectCache.h:
  • accessibility/AccessibilityObjectInterface.h:
  • accessibility/isolatedtree/AXIsolatedTree.h:
  • animation/EffectTiming.h:
  • animation/KeyframeEffect.cpp:

(WebCore::KeyframeEffect::create):

  • animation/KeyframeEffect.h:
  • animation/OptionalEffectTiming.h:
  • bindings/IDLTypes.h:
  • bindings/js/BufferSource.h:
  • bindings/js/JSValueInWrappedObject.h:
  • crypto/CryptoAlgorithm.h:
  • crypto/CryptoKey.h:
  • crypto/SubtleCrypto.h:
  • crypto/parameters/CryptoAlgorithmEcdsaParams.h:
  • crypto/parameters/CryptoAlgorithmHkdfParams.h:
  • crypto/parameters/CryptoAlgorithmHmacKeyParams.h:
  • crypto/parameters/CryptoAlgorithmPbkdf2Params.h:
  • crypto/parameters/CryptoAlgorithmRsaHashedImportParams.h:
  • crypto/parameters/CryptoAlgorithmRsaHashedParams.h:
  • css/CSSCustomPropertyValue.h:
  • css/DOMMatrix.cpp:

(WebCore::DOMMatrix::create):

  • css/DOMMatrix.h:
  • css/DOMMatrixReadOnly.cpp:

(WebCore::DOMMatrixReadOnly::create):

  • css/DOMMatrixReadOnly.h:
  • css/FontFace.h:
  • css/StyleRule.h:
  • css/parser/CSSPropertyParserHelpers.h:
  • css/typedom/CSSNumericValue.h:
  • css/typedom/CSSUnparsedValue.h:
  • dom/Document.h:
  • dom/DocumentMarker.h:
  • dom/Element.cpp:

(WebCore::Element::scrollIntoView):
(WebCore::Element::animate):

  • dom/Element.h:
  • dom/EventTarget.h:
  • dom/MessageEvent.h:
  • dom/Node.h:
  • editing/AlternativeTextController.h:
  • editing/TextCheckingHelper.cpp:

(WebCore::TextCheckingHelper::findFirstMisspelledWordOrUngrammaticalPhrase const):

  • editing/TextCheckingHelper.h:
  • editing/TextManipulationController.h:
  • fileapi/Blob.h:
  • fileapi/FileReader.cpp:

(WebCore::FileReader::result const):

  • fileapi/FileReader.h:
  • fileapi/NetworkSendQueue.h:
  • html/DOMFormData.h:
  • html/HTMLAllCollection.cpp:

(WebCore::HTMLAllCollection::namedOrIndexedItemOrItems const):
(WebCore::HTMLAllCollection::namedItemOrItems const):

  • html/HTMLAllCollection.h:
  • html/HTMLDocument.cpp:

(WebCore::HTMLDocument::namedItem):

  • html/HTMLDocument.h:
  • html/HTMLFormControlsCollection.cpp:

(WebCore::HTMLFormControlsCollection::namedItemOrItems const):

  • html/HTMLFormControlsCollection.h:
  • html/HTMLFormElement.cpp:

(WebCore::HTMLFormElement::namedItem):

  • html/HTMLFormElement.h:
  • html/HTMLMediaElement.h:
  • html/HTMLOptionsCollection.h:
  • html/HTMLSelectElement.h:
  • html/ImageBitmap.h:
  • html/OffscreenCanvas.h:
  • html/URLSearchParams.cpp:

(WebCore::URLSearchParams::create):

  • html/URLSearchParams.h:
  • html/canvas/CanvasRenderingContext2DBase.h:
  • html/canvas/CanvasStyle.h:
  • html/canvas/WebGL2RenderingContext.h:
  • html/canvas/WebGLAny.h:
  • html/canvas/WebGLMultiDraw.h:
  • html/canvas/WebGLRenderingContextBase.h:
  • html/track/TrackEvent.h:
  • html/track/VTTCue.h:
  • inspector/InspectorCanvas.h:
  • inspector/InspectorShaderProgram.h:
  • layout/integration/InlineIteratorBox.h:
  • layout/integration/InlineIteratorLine.h:
  • page/DiagnosticLoggingClient.h:
  • page/IntersectionObserver.h:
  • page/Page.h:
  • page/Performance.h:
  • page/PerformanceMeasureOptions.h:
  • page/PerformanceUserTiming.cpp:

(WebCore::PerformanceUserTiming::convertMarkToTimestamp const):

  • page/PerformanceUserTiming.h:
  • page/scrolling/ScrollingCoordinator.h:
  • platform/PasteboardCustomData.cpp:

(WebCore::copyPlatformData):
(WebCore::PasteboardCustomData::forEachPlatformStringOrBuffer const):

  • platform/PasteboardCustomData.h:
  • platform/SharedBuffer.h:
  • platform/audio/AudioStreamDescription.h:
  • platform/encryptedmedia/CDMProxy.h:
  • platform/graphics/DecodingOptions.h:
  • platform/graphics/FontCascadeDescription.h:
  • platform/graphics/Gradient.h:
  • platform/graphics/InlinePathData.h:
  • platform/graphics/cocoa/SourceBufferParser.h:
  • platform/graphics/cocoa/SourceBufferParserWebM.h:
  • platform/graphics/displaylists/DisplayListResourceHeap.h:
  • platform/mediastream/mac/DisplayCaptureSourceMac.h:
  • platform/mock/MockMediaDevice.h:
  • platform/network/DNS.h:
  • platform/network/FormData.h:
  • platform/sql/SQLValue.h:
  • platform/xr/PlatformXR.h:
  • rendering/RenderBlockFlow.h:
  • testing/TypeConversions.h:
  • workers/SharedWorker.cpp:

(WebCore::SharedWorker::SharedWorker):

  • workers/SharedWorker.h:
  • workers/service/ExtendableMessageEvent.h:
  • workers/service/ServiceWorkerTypes.h:
  • xml/XMLHttpRequest.h:

Source/WebKit:

  • NetworkProcess/NetworkLoadChecker.h:
  • NetworkProcess/cache/NetworkCacheData.h:
  • Platform/IPC/ArgumentCoders.h:

(IPC::VariantCoder::encode):
(IPC::VariantCoder::decode):

  • Platform/IPC/Attachment.h:
  • Platform/IPC/MessageReceiveQueueMap.h:
  • Shared/SessionState.h:
  • Shared/WebCoreArgumentCoders.h:
  • Shared/WebPreferencesStore.h:
  • Shared/mac/MediaFormatReader/MediaSampleCursor.h:
  • UIProcess/API/APIWebAuthenticationPanel.h:
  • UIProcess/API/C/WKMockMediaDevice.cpp:

(WKAddMockMediaDevice):

  • UIProcess/API/Cocoa/WKWebView.mm:

(-[WKWebView _showSafeBrowsingWarning:completionHandler:]):
(-[WKWebView _showSafeBrowsingWarningWithURL:title:warning:detailsWithLinks:completionHandler:]):

  • UIProcess/API/Cocoa/WKWebViewInternal.h:
  • UIProcess/API/Cocoa/_WKWebAuthenticationPanel.mm:

(-[_WKWebAuthenticationPanel makeCredentialWithChallenge:origin:options:completionHandler:]):
(-[_WKWebAuthenticationPanel getAssertionWithChallenge:origin:options:completionHandler:]):

  • UIProcess/Automation/SimulatedInputDiser.h:
  • UIProcess/Automation/WebAutomationSession.cpp:

(WebKit::WebAutomationSession::simulateKeyboardInteraction):

  • UIProcess/Automation/WebAutomationSession.h:
  • UIProcess/Automation/ios/WebAutomationSessionIOS.mm:

(WebKit::WebAutomationSession::platformSimulateKeyboardInteraction):

  • UIProcess/Automation/mac/WebAutomationSessionMac.mm:

(WebKit::WebAutomationSession::platformSimulateKeyboardInteraction):

  • UIProcess/Cocoa/SOAuthorization/SubFrameSOAuthorizationSession.h:
  • UIProcess/Cocoa/WKSafeBrowsingWarning.h:
  • UIProcess/Cocoa/WKSafeBrowsingWarning.mm:

(-[WKSafeBrowsingWarning initWithFrame:safeBrowsingWarning:completionHandler:]):

  • UIProcess/Cocoa/WebViewImpl.h:
  • UIProcess/Cocoa/WebViewImpl.mm:

(WebKit::WebViewImpl::showSafeBrowsingWarning):

  • UIProcess/PageClient.h:

(WebKit::PageClient::showSafeBrowsingWarning):

  • UIProcess/ProcessThrottler.h:
  • UIProcess/WebAuthentication/Authenticator.h:
  • UIProcess/WebAuthentication/AuthenticatorManager.cpp:

(WebKit::WebCore::getRpId):
(WebKit::WebCore::getUserName):

  • UIProcess/WebAuthentication/AuthenticatorManager.h:
  • UIProcess/WebAuthentication/WebAuthenticationRequestData.cpp:

(WebKit::getClientDataType):
(WebKit::getUserVerificationRequirement):

  • UIProcess/WebAuthentication/WebAuthenticationRequestData.h:
  • UIProcess/WebAuthentication/WebAuthenticatorCoordinatorProxy.cpp:

(WebKit::WebAuthenticatorCoordinatorProxy::handleRequest):

  • UIProcess/WebPageProxy.cpp:

(WebKit::WebPageProxy::receivedPolicyDecision):

  • UIProcess/WebPageProxy.h:
  • UIProcess/ios/PageClientImplIOS.h:
  • UIProcess/ios/PageClientImplIOS.mm:

(WebKit::PageClientImpl::showSafeBrowsingWarning):

  • UIProcess/mac/PageClientImplMac.h:
  • UIProcess/mac/PageClientImplMac.mm:

(WebKit::PageClientImpl::showSafeBrowsingWarning):

  • WebAuthnProcess/WebAuthnConnectionToWebProcess.cpp:

(WebKit::WebAuthnConnectionToWebProcess::handleRequest):

  • WebProcess/GPU/graphics/ImageBufferBackendHandle.h:
  • WebProcess/Storage/WebServiceWorkerFetchTaskClient.h:
  • WebProcess/WebPage/RemoteLayerTree/PlatformCAAnimationRemote.h:

Source/WebKitLegacy/mac:

  • DOM/DOMHTMLSelectElement.mm:

(-[DOMHTMLSelectElement add:before:]):

Source/WTF:

  • wtf/LikelyDenseUnsignedIntegerSet.h:
  • wtf/SmallSet.h:
  • wtf/text/TextBreakIterator.cpp:

(WTF::mapModeToBackingIterator):

  • wtf/text/TextBreakIterator.h:
  • wtf/text/cocoa/TextBreakIteratorInternalICUCocoa.cpp:

(WTF::mapModeToBackingIterator):

  • Property svn:eol-style set to native
File size: 14.4 KB
Line 
1/*
2* Copyright (C) 1999-2000 Harri Porten ([email protected])
3* Copyright (C) 2002-2019 Apple Inc. All rights reserved.
4* Copyright (C) 2010 Zoltan Herczeg ([email protected])
5*
6* This library is free software; you can redistribute it and/or
7* modify it under the terms of the GNU Library General Public
8* License as published by the Free Software Foundation; either
9* version 2 of the License, or (at your option) any later version.
10*
11* This library is distributed in the hope that it will be useful,
12* but WITHOUT ANY WARRANTY; without even the implied warranty of
13* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14* Library General Public License for more details.
15*
16* You should have received a copy of the GNU Library General Public License
17* along with this library; see the file COPYING.LIB. If not, write to
18* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
19* Boston, MA 02110-1301, USA.
20*
21*/
22
23#pragma once
24
25#include "Lookup.h"
26#include "ParserArena.h"
27#include "ParserModes.h"
28#include "ParserTokens.h"
29#include "SourceCode.h"
30#include <wtf/ASCIICType.h>
31#include <wtf/Vector.h>
32#include <wtf/unicode/CharacterNames.h>
33
34namespace JSC {
35
36struct ParsedUnicodeEscapeValue;
37
38enum class LexerFlags : uint8_t {
39IgnoreReservedWords = 1 << 0,
40DontBuildStrings = 1 << 1,
41DontBuildKeywords = 1 << 2
42};
43
44bool isLexerKeyword(const Identifier&);
45
46template <typename T>
47class Lexer {
48WTF_MAKE_NONCOPYABLE(Lexer);
49WTF_MAKE_FAST_ALLOCATED;
50
51public:
52Lexer(VM&, JSParserBuiltinMode, JSParserScriptMode);
53~Lexer();
54
55// Character manipulation functions.
56static bool isWhiteSpace(T character);
57static bool isLineTerminator(T character);
58static unsigned char convertHex(int c1, int c2);
59static UChar convertUnicode(int c1, int c2, int c3, int c4);
60
61// Functions to set up parsing.
62void setCode(const SourceCode&, ParserArena*);
63void setIsReparsingFunction() { m_isReparsingFunction = true; }
64bool isReparsingFunction() const { return m_isReparsingFunction; }
65
66JSTokenType lex(JSToken*, OptionSet<LexerFlags>, bool strictMode);
67JSTokenType lexWithoutClearingLineTerminator(JSToken*, OptionSet<LexerFlags>, bool strictMode);
68bool nextTokenIsColon();
69int lineNumber() const { return m_lineNumber; }
70ALWAYS_INLINE int currentOffset() const { return offsetFromSourcePtr(m_code); }
71ALWAYS_INLINE int currentLineStartOffset() const { return offsetFromSourcePtr(m_lineStart); }
72ALWAYS_INLINE JSTextPosition currentPosition() const
73{
74return JSTextPosition(m_lineNumber, currentOffset(), currentLineStartOffset());
75}
76JSTextPosition positionBeforeLastNewline() const { return m_positionBeforeLastNewline; }
77JSTokenLocation lastTokenLocation() const { return m_lastTokenLocation; }
78void setLastLineNumber(int lastLineNumber) { m_lastLineNumber = lastLineNumber; }
79int lastLineNumber() const { return m_lastLineNumber; }
80bool hasLineTerminatorBeforeToken() const { return m_hasLineTerminatorBeforeToken; }
81JSTokenType scanRegExp(JSToken*, UChar patternPrefix = 0);
82enum class RawStringsBuildMode { BuildRawStrings, DontBuildRawStrings };
83JSTokenType scanTemplateString(JSToken*, RawStringsBuildMode);
84
85// Functions for use after parsing.
86bool sawError() const { return m_error; }
87void setSawError(bool sawError) { m_error = sawError; }
88String getErrorMessage() const { return m_lexErrorMessage; }
89void setErrorMessage(const String& errorMessage) { m_lexErrorMessage = errorMessage; }
90String sourceURLDirective() const { return m_sourceURLDirective; }
91String sourceMappingURLDirective() const { return m_sourceMappingURLDirective; }
92void clear();
93void setOffset(int offset, int lineStartOffset)
94{
95m_error = 0;
96m_lexErrorMessage = String();
97
98m_code = sourcePtrFromOffset(offset);
99m_lineStart = sourcePtrFromOffset(lineStartOffset);
100ASSERT(currentOffset() >= currentLineStartOffset());
101
102m_buffer8.shrink(0);
103m_buffer16.shrink(0);
104if (LIKELY(m_code < m_codeEnd))
105m_current = *m_code;
106else
107m_current = 0;
108}
109void setLineNumber(int line)
110{
111ASSERT(line >= 0);
112m_lineNumber = line;
113}
114void setHasLineTerminatorBeforeToken(bool terminator)
115{
116m_hasLineTerminatorBeforeToken = terminator;
117}
118
119JSTokenType lexExpectIdentifier(JSToken*, OptionSet<LexerFlags>, bool strictMode);
120
121ALWAYS_INLINE StringView getToken(const JSToken& token)
122{
123SourceProvider* sourceProvider = m_source->provider();
124ASSERT_WITH_MESSAGE(token.m_location.startOffset <= token.m_location.endOffset, "Calling this function with the baked token.");
125return sourceProvider->getRange(token.m_location.startOffset, token.m_location.endOffset);
126}
127
128size_t codeLength() { return m_codeEnd - m_codeStart; }
129
130private:
131void record8(int);
132void append8(const T*, size_t);
133void record16(int);
134void record16(T);
135void recordUnicodeCodePoint(UChar32);
136void append16(const LChar*, size_t);
137void append16(const UChar* characters, size_t length) { m_buffer16.append(characters, length); }
138
139UChar32 currentCodePoint() const;
140ALWAYS_INLINE void shift();
141ALWAYS_INLINE bool atEnd() const;
142ALWAYS_INLINE T peek(int offset) const;
143
144ParsedUnicodeEscapeValue parseUnicodeEscape();
145void shiftLineTerminator();
146
147ALWAYS_INLINE int offsetFromSourcePtr(const T* ptr) const { return ptr - m_codeStart; }
148ALWAYS_INLINE const T* sourcePtrFromOffset(int offset) const { return m_codeStart + offset; }
149
150String invalidCharacterMessage() const;
151ALWAYS_INLINE const T* currentSourcePtr() const;
152
153ALWAYS_INLINE void setCodeStart(StringView);
154
155ALWAYS_INLINE const Identifier* makeIdentifier(const LChar* characters, size_t length);
156ALWAYS_INLINE const Identifier* makeIdentifier(const UChar* characters, size_t length);
157ALWAYS_INLINE const Identifier* makeLCharIdentifier(const LChar* characters, size_t length);
158ALWAYS_INLINE const Identifier* makeLCharIdentifier(const UChar* characters, size_t length);
159ALWAYS_INLINE const Identifier* makeRightSizedIdentifier(const UChar* characters, size_t length, UChar orAllChars);
160ALWAYS_INLINE const Identifier* makeIdentifierLCharFromUChar(const UChar* characters, size_t length);
161ALWAYS_INLINE const Identifier* makeEmptyIdentifier();
162
163ALWAYS_INLINE bool lastTokenWasRestrKeyword() const;
164
165ALWAYS_INLINE void skipWhitespace();
166
167template <int shiftAmount> void internalShift();
168template <bool shouldCreateIdentifier> ALWAYS_INLINE JSTokenType parseKeyword(JSTokenData*);
169template <bool shouldBuildIdentifiers> ALWAYS_INLINE JSTokenType parseIdentifier(JSTokenData*, OptionSet<LexerFlags>, bool strictMode);
170template <bool shouldBuildIdentifiers> NEVER_INLINE JSTokenType parseIdentifierSlowCase(JSTokenData*, OptionSet<LexerFlags>, bool strictMode, const T* identifierStart);
171enum StringParseResult {
172StringParsedSuccessfully,
173StringUnterminated,
174StringCannotBeParsed
175};
176template <bool shouldBuildStrings> ALWAYS_INLINE StringParseResult parseString(JSTokenData*, bool strictMode);
177template <bool shouldBuildStrings> NEVER_INLINE StringParseResult parseStringSlowCase(JSTokenData*, bool strictMode);
178
179
180template <bool shouldBuildStrings> ALWAYS_INLINE StringParseResult parseComplexEscape(bool strictMode);
181ALWAYS_INLINE StringParseResult parseTemplateLiteral(JSTokenData*, RawStringsBuildMode);
182
183using NumberParseResult = std::variant<double, const Identifier*>;
184ALWAYS_INLINE std::optional<NumberParseResult> parseHex();
185ALWAYS_INLINE std::optional<NumberParseResult> parseBinary();
186ALWAYS_INLINE std::optional<NumberParseResult> parseOctal();
187ALWAYS_INLINE std::optional<NumberParseResult> parseDecimal();
188ALWAYS_INLINE bool parseNumberAfterDecimalPoint();
189ALWAYS_INLINE bool parseNumberAfterExponentIndicator();
190ALWAYS_INLINE bool parseMultilineComment();
191
192ALWAYS_INLINE void parseCommentDirective();
193ALWAYS_INLINE String parseCommentDirectiveValue();
194
195template <unsigned length>
196ALWAYS_INLINE bool consume(const char (&input)[length]);
197
198void fillTokenInfo(JSToken*, JSTokenType, int lineNumber, int endOffset, int lineStartOffset, JSTextPosition endPosition);
199
200static constexpr size_t initialReadBufferCapacity = 32;
201
202int m_lineNumber;
203int m_lastLineNumber;
204
205Vector<LChar> m_buffer8;
206Vector<UChar> m_buffer16;
207Vector<UChar> m_bufferForRawTemplateString16;
208bool m_hasLineTerminatorBeforeToken;
209int m_lastToken;
210
211const SourceCode* m_source;
212unsigned m_sourceOffset;
213const T* m_code;
214const T* m_codeStart;
215const T* m_codeEnd;
216const T* m_codeStartPlusOffset;
217const T* m_lineStart;
218JSTextPosition m_positionBeforeLastNewline;
219JSTokenLocation m_lastTokenLocation;
220bool m_isReparsingFunction;
221bool m_atLineStart;
222bool m_error;
223String m_lexErrorMessage;
224
225String m_sourceURLDirective;
226String m_sourceMappingURLDirective;
227
228T m_current;
229
230IdentifierArena* m_arena;
231
232VM& m_vm;
233bool m_parsingBuiltinFunction;
234JSParserScriptMode m_scriptMode;
235};
236
237template <>
238ALWAYS_INLINE bool Lexer<LChar>::isWhiteSpace(LChar ch)
239{
240return ch == ' ' || ch == '\t' || ch == 0xB || ch == 0xC || ch == 0xA0;
241}
242
243template <>
244ALWAYS_INLINE bool Lexer<UChar>::isWhiteSpace(UChar ch)
245{
246return isLatin1(ch) ? Lexer<LChar>::isWhiteSpace(static_cast<LChar>(ch)) : (u_charType(ch) == U_SPACE_SEPARATOR || ch == byteOrderMark);
247}
248
249template <>
250ALWAYS_INLINE bool Lexer<LChar>::isLineTerminator(LChar ch)
251{
252return ch == '\r' || ch == '\n';
253}
254
255template <>
256ALWAYS_INLINE bool Lexer<UChar>::isLineTerminator(UChar ch)
257{
258return ch == '\r' || ch == '\n' || (ch & ~1) == 0x2028;
259}
260
261template <typename T>
262inline unsigned char Lexer<T>::convertHex(int c1, int c2)
263{
264return (toASCIIHexValue(c1) << 4) | toASCIIHexValue(c2);
265}
266
267template <typename T>
268inline UChar Lexer<T>::convertUnicode(int c1, int c2, int c3, int c4)
269{
270return (convertHex(c1, c2) << 8) | convertHex(c3, c4);
271}
272
273template <typename T>
274ALWAYS_INLINE const Identifier* Lexer<T>::makeIdentifier(const LChar* characters, size_t length)
275{
276return &m_arena->makeIdentifier(m_vm, characters, length);
277}
278
279template <typename T>
280ALWAYS_INLINE const Identifier* Lexer<T>::makeIdentifier(const UChar* characters, size_t length)
281{
282return &m_arena->makeIdentifier(m_vm, characters, length);
283}
284
285template <>
286ALWAYS_INLINE const Identifier* Lexer<LChar>::makeRightSizedIdentifier(const UChar* characters, size_t length, UChar)
287{
288return &m_arena->makeIdentifierLCharFromUChar(m_vm, characters, length);
289}
290
291template <>
292ALWAYS_INLINE const Identifier* Lexer<UChar>::makeRightSizedIdentifier(const UChar* characters, size_t length, UChar orAllChars)
293{
294if (!(orAllChars & ~0xff))
295return &m_arena->makeIdentifierLCharFromUChar(m_vm, characters, length);
296
297return &m_arena->makeIdentifier(m_vm, characters, length);
298}
299
300template <typename T>
301ALWAYS_INLINE const Identifier* Lexer<T>::makeEmptyIdentifier()
302{
303return &m_arena->makeEmptyIdentifier(m_vm);
304}
305
306template <>
307ALWAYS_INLINE void Lexer<LChar>::setCodeStart(StringView sourceString)
308{
309ASSERT(sourceString.is8Bit());
310m_codeStart = sourceString.characters8();
311}
312
313template <>
314ALWAYS_INLINE void Lexer<UChar>::setCodeStart(StringView sourceString)
315{
316ASSERT(!sourceString.is8Bit());
317m_codeStart = sourceString.characters16();
318}
319
320template <typename T>
321ALWAYS_INLINE const Identifier* Lexer<T>::makeIdentifierLCharFromUChar(const UChar* characters, size_t length)
322{
323return &m_arena->makeIdentifierLCharFromUChar(m_vm, characters, length);
324}
325
326template <typename T>
327ALWAYS_INLINE const Identifier* Lexer<T>::makeLCharIdentifier(const LChar* characters, size_t length)
328{
329return &m_arena->makeIdentifier(m_vm, characters, length);
330}
331
332template <typename T>
333ALWAYS_INLINE const Identifier* Lexer<T>::makeLCharIdentifier(const UChar* characters, size_t length)
334{
335return &m_arena->makeIdentifierLCharFromUChar(m_vm, characters, length);
336}
337
338#if ASSERT_ENABLED
339bool isSafeBuiltinIdentifier(VM&, const Identifier*);
340#else
341ALWAYS_INLINE bool isSafeBuiltinIdentifier(VM&, const Identifier*) { return true; }
342#endif // ASSERT_ENABLED
343
344template <typename T>
345ALWAYS_INLINE JSTokenType Lexer<T>::lexExpectIdentifier(JSToken* tokenRecord, OptionSet<LexerFlags> lexerFlags, bool strictMode)
346{
347JSTokenData* tokenData = &tokenRecord->m_data;
348JSTokenLocation* tokenLocation = &tokenRecord->m_location;
349ASSERT(lexerFlags.contains(LexerFlags::IgnoreReservedWords));
350const T* start = m_code;
351const T* ptr = start;
352const T* end = m_codeEnd;
353JSTextPosition startPosition = currentPosition();
354if (ptr >= end) {
355ASSERT(ptr == end);
356goto slowCase;
357}
358if (!WTF::isASCIIAlpha(*ptr))
359goto slowCase;
360++ptr;
361while (ptr < end) {
362if (!WTF::isASCIIAlphanumeric(*ptr))
363break;
364++ptr;
365}
366
367// Here's the shift
368if (ptr < end) {
369if ((!WTF::isASCII(*ptr)) || (*ptr == '\\') || (*ptr == '_') || (*ptr == '$'))
370goto slowCase;
371m_current = *ptr;
372} else
373m_current = 0;
374
375m_code = ptr;
376ASSERT(currentOffset() >= currentLineStartOffset());
377
378// Create the identifier if needed
379if (lexerFlags.contains(LexerFlags::DontBuildKeywords)
380#if ASSERT_ENABLED
381&& !m_parsingBuiltinFunction
382#endif
383)
384tokenData->ident = nullptr;
385else
386tokenData->ident = makeLCharIdentifier(start, ptr - start);
387
388tokenLocation->line = m_lineNumber;
389tokenLocation->lineStartOffset = currentLineStartOffset();
390tokenLocation->startOffset = offsetFromSourcePtr(start);
391tokenLocation->endOffset = currentOffset();
392ASSERT(tokenLocation->startOffset >= tokenLocation->lineStartOffset);
393tokenRecord->m_startPosition = startPosition;
394tokenRecord->m_endPosition = currentPosition();
395#if ASSERT_ENABLED
396if (m_parsingBuiltinFunction) {
397if (!isSafeBuiltinIdentifier(m_vm, tokenData->ident))
398return ERRORTOK;
399}
400#endif
401
402m_lastToken = IDENT;
403return IDENT;
404
405slowCase:
406return lex(tokenRecord, lexerFlags, strictMode);
407}
408
409template <typename T>
410ALWAYS_INLINE JSTokenType Lexer<T>::lex(JSToken* tokenRecord, OptionSet<LexerFlags> lexerFlags, bool strictMode)
411{
412m_hasLineTerminatorBeforeToken = false;
413return lexWithoutClearingLineTerminator(tokenRecord, lexerFlags, strictMode);
414}
415
416} // namespace JSC
Note: See TracBrowser for help on using the repository browser.