mirror of
https://github.com/dart-lang/sdk
synced 2024-09-05 00:13:50 +00:00
[parser] Parse record type return type for operators
Change-Id: I23b5ef38a9bfd58c327303198e59d9b50ace323b Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/262681 Reviewed-by: Johnni Winther <johnniwinther@google.com> Commit-Queue: Jens Johansen <jensj@google.com> Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
This commit is contained in:
parent
575ae24207
commit
97cdb043da
|
@ -736,6 +736,10 @@ class ComplexTypeInfo implements TypeInfo {
|
|||
// TODO(jensj): A setter would need parenthesis so technically
|
||||
// couldn't look like this, but I don't think any other valid thing
|
||||
// could either. Should we handle that specifically?
|
||||
} else if (optional("operator", next) &&
|
||||
afterIdentifier.isUserDefinableOperator) {
|
||||
// E.g.
|
||||
// `(int, int) operator [](int foo) {}`
|
||||
} else {
|
||||
// This could for instance be `(int x, int y) async {`.
|
||||
return noType;
|
||||
|
|
|
@ -0,0 +1,11 @@
|
|||
class Foo {
|
||||
(int, int) operator [](int foo) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
||||
|
||||
class Bar {
|
||||
(int, int)? operator [](int bar) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,126 @@
|
|||
beginCompilationUnit(class)
|
||||
beginMetadataStar(class)
|
||||
endMetadataStar(0)
|
||||
beginClassOrMixinOrNamedMixinApplicationPrelude(class)
|
||||
handleIdentifier(Foo, classOrMixinDeclaration)
|
||||
handleNoTypeVariables({)
|
||||
beginClassDeclaration(class, null, null, null, Foo)
|
||||
handleNoType(Foo)
|
||||
handleClassExtends(null, 1)
|
||||
handleClassNoWithClause()
|
||||
handleImplements(null, 0)
|
||||
handleClassHeader(class, class, null)
|
||||
beginClassOrMixinOrExtensionBody(DeclarationKind.Class, {)
|
||||
beginMetadataStar(()
|
||||
endMetadataStar(0)
|
||||
beginMember()
|
||||
beginMethod(DeclarationKind.Class, null, null, null, null, null, null, operator)
|
||||
beginRecordType(()
|
||||
beginRecordTypeEntry()
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments(,)
|
||||
handleType(int, null)
|
||||
handleNoName(,)
|
||||
endRecordTypeEntry()
|
||||
beginRecordTypeEntry()
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments())
|
||||
handleType(int, null)
|
||||
handleNoName())
|
||||
endRecordTypeEntry()
|
||||
endRecordType((, null, 2, false)
|
||||
handleOperatorName(operator, [])
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.NonStaticMethod)
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
beginFormalParameter(int, MemberKind.NonStaticMethod, null, null, null)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments(foo)
|
||||
handleType(int, null)
|
||||
handleIdentifier(foo, formalParameterDeclaration)
|
||||
handleFormalParameterWithoutValue())
|
||||
endFormalParameter(null, null, null, foo, null, null, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
endFormalParameters(1, (, ), MemberKind.NonStaticMethod)
|
||||
handleNoInitializers()
|
||||
handleAsyncModifier(null, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginReturnStatement(return)
|
||||
beginParenthesizedExpressionOrRecordLiteral(()
|
||||
handleLiteralInt(42)
|
||||
handleLiteralInt(42)
|
||||
endRecordLiteral((, 2, null)
|
||||
endReturnStatement(true, return, ;)
|
||||
endBlockFunctionBody(1, {, })
|
||||
endClassMethod(null, (, (, null, })
|
||||
endMember()
|
||||
endClassOrMixinOrExtensionBody(DeclarationKind.Class, 1, {, })
|
||||
endClassDeclaration(class, })
|
||||
endTopLevelDeclaration(class)
|
||||
beginMetadataStar(class)
|
||||
endMetadataStar(0)
|
||||
beginClassOrMixinOrNamedMixinApplicationPrelude(class)
|
||||
handleIdentifier(Bar, classOrMixinDeclaration)
|
||||
handleNoTypeVariables({)
|
||||
beginClassDeclaration(class, null, null, null, Bar)
|
||||
handleNoType(Bar)
|
||||
handleClassExtends(null, 1)
|
||||
handleClassNoWithClause()
|
||||
handleImplements(null, 0)
|
||||
handleClassHeader(class, class, null)
|
||||
beginClassOrMixinOrExtensionBody(DeclarationKind.Class, {)
|
||||
beginMetadataStar(()
|
||||
endMetadataStar(0)
|
||||
beginMember()
|
||||
beginMethod(DeclarationKind.Class, null, null, null, null, null, null, operator)
|
||||
beginRecordType(()
|
||||
beginRecordTypeEntry()
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments(,)
|
||||
handleType(int, null)
|
||||
handleNoName(,)
|
||||
endRecordTypeEntry()
|
||||
beginRecordTypeEntry()
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments())
|
||||
handleType(int, null)
|
||||
handleNoName())
|
||||
endRecordTypeEntry()
|
||||
endRecordType((, ?, 2, false)
|
||||
handleOperatorName(operator, [])
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.NonStaticMethod)
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
beginFormalParameter(int, MemberKind.NonStaticMethod, null, null, null)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments(bar)
|
||||
handleType(int, null)
|
||||
handleIdentifier(bar, formalParameterDeclaration)
|
||||
handleFormalParameterWithoutValue())
|
||||
endFormalParameter(null, null, null, bar, null, null, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
endFormalParameters(1, (, ), MemberKind.NonStaticMethod)
|
||||
handleNoInitializers()
|
||||
handleAsyncModifier(null, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginReturnStatement(return)
|
||||
beginParenthesizedExpressionOrRecordLiteral(()
|
||||
handleLiteralInt(42)
|
||||
handleLiteralInt(42)
|
||||
endRecordLiteral((, 2, null)
|
||||
endReturnStatement(true, return, ;)
|
||||
endBlockFunctionBody(1, {, })
|
||||
endClassMethod(null, (, (, null, })
|
||||
endMember()
|
||||
endClassOrMixinOrExtensionBody(DeclarationKind.Class, 1, {, })
|
||||
endClassDeclaration(class, })
|
||||
endTopLevelDeclaration()
|
||||
endCompilationUnit(2, )
|
|
@ -0,0 +1,246 @@
|
|||
parseUnit(class)
|
||||
skipErrorTokens(class)
|
||||
listener: beginCompilationUnit(class)
|
||||
syntheticPreviousToken(class)
|
||||
parseTopLevelDeclarationImpl(, Instance of 'DirectiveContext')
|
||||
parseMetadataStar()
|
||||
listener: beginMetadataStar(class)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelKeywordDeclaration(, class, null, Instance of 'DirectiveContext')
|
||||
parseClassOrNamedMixinApplication(null, null, null, class)
|
||||
listener: beginClassOrMixinOrNamedMixinApplicationPrelude(class)
|
||||
ensureIdentifier(class, classOrMixinDeclaration)
|
||||
listener: handleIdentifier(Foo, classOrMixinDeclaration)
|
||||
listener: handleNoTypeVariables({)
|
||||
listener: beginClassDeclaration(class, null, null, null, Foo)
|
||||
parseClass(Foo, class, class, Foo)
|
||||
parseClassHeaderOpt(Foo, class, class)
|
||||
parseClassExtendsOpt(Foo)
|
||||
listener: handleNoType(Foo)
|
||||
listener: handleClassExtends(null, 1)
|
||||
parseClassWithClauseOpt(Foo)
|
||||
listener: handleClassNoWithClause()
|
||||
parseClassOrMixinOrEnumImplementsOpt(Foo)
|
||||
listener: handleImplements(null, 0)
|
||||
listener: handleClassHeader(class, class, null)
|
||||
parseClassOrMixinOrExtensionBody(Foo, DeclarationKind.Class, Foo)
|
||||
listener: beginClassOrMixinOrExtensionBody(DeclarationKind.Class, {)
|
||||
notEofOrValue(}, ()
|
||||
parseClassOrMixinOrExtensionOrEnumMemberImpl({, DeclarationKind.Class, Foo)
|
||||
parseMetadataStar({)
|
||||
listener: beginMetadataStar(()
|
||||
listener: endMetadataStar(0)
|
||||
listener: beginMember()
|
||||
parseMethod({, null, null, null, null, null, null, null, {, Instance of 'ComplexTypeInfo', null, operator, DeclarationKind.Class, Foo, false)
|
||||
listener: beginMethod(DeclarationKind.Class, null, null, null, null, null, null, operator)
|
||||
parseRecordType((, {)
|
||||
listener: beginRecordType(()
|
||||
parseRecordTypeField((, identifierIsOptional: true)
|
||||
listener: beginRecordTypeEntry()
|
||||
parseMetadataStar(()
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments(,)
|
||||
listener: handleType(int, null)
|
||||
listener: handleNoName(,)
|
||||
listener: endRecordTypeEntry()
|
||||
parseRecordTypeField(,, identifierIsOptional: true)
|
||||
listener: beginRecordTypeEntry()
|
||||
parseMetadataStar(,)
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments())
|
||||
listener: handleType(int, null)
|
||||
listener: handleNoName())
|
||||
listener: endRecordTypeEntry()
|
||||
listener: endRecordType((, null, 2, false)
|
||||
parseOperatorName())
|
||||
listener: handleOperatorName(operator, [])
|
||||
parseMethodTypeVar([])
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters([], operator, false, MemberKind.NonStaticMethod)
|
||||
parseFormalParameters([], MemberKind.NonStaticMethod)
|
||||
parseFormalParametersRest((, MemberKind.NonStaticMethod)
|
||||
listener: beginFormalParameters((, MemberKind.NonStaticMethod)
|
||||
parseFormalParameter((, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
parseMetadataStar(()
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: beginFormalParameter(int, MemberKind.NonStaticMethod, null, null, null)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments(foo)
|
||||
listener: handleType(int, null)
|
||||
ensureIdentifier(int, formalParameterDeclaration)
|
||||
listener: handleIdentifier(foo, formalParameterDeclaration)
|
||||
listener: handleFormalParameterWithoutValue())
|
||||
listener: endFormalParameter(null, null, null, foo, null, null, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
listener: endFormalParameters(1, (, ), MemberKind.NonStaticMethod)
|
||||
parseInitializersOpt())
|
||||
listener: handleNoInitializers()
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(null, null)
|
||||
inPlainSync()
|
||||
inPlainSync()
|
||||
parseFunctionBody(), false, true)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, return)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseReturnStatement({)
|
||||
listener: beginReturnStatement(return)
|
||||
parseExpression(return)
|
||||
parsePrecedenceExpression(return, 1, true)
|
||||
parseUnaryExpression(return, true)
|
||||
parsePrimary(return, expression)
|
||||
parseParenthesizedExpressionFunctionLiteralOrRecordLiteral(return)
|
||||
parseParenthesizedExpressionOrRecordLiteral(return, null)
|
||||
listener: beginParenthesizedExpressionOrRecordLiteral(()
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseLiteralInt(()
|
||||
listener: handleLiteralInt(42)
|
||||
parseExpression(,)
|
||||
parsePrecedenceExpression(,, 1, true)
|
||||
parseUnaryExpression(,, true)
|
||||
parsePrimary(,, expression)
|
||||
parseLiteralInt(,)
|
||||
listener: handleLiteralInt(42)
|
||||
ensureCloseParen(42, ()
|
||||
listener: endRecordLiteral((, 2, null)
|
||||
ensureSemicolon())
|
||||
listener: endReturnStatement(true, return, ;)
|
||||
inGenerator()
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(1, {, })
|
||||
listener: endClassMethod(null, (, (, null, })
|
||||
listener: endMember()
|
||||
notEofOrValue(}, })
|
||||
listener: endClassOrMixinOrExtensionBody(DeclarationKind.Class, 1, {, })
|
||||
listener: endClassDeclaration(class, })
|
||||
listener: endTopLevelDeclaration(class)
|
||||
parseTopLevelDeclarationImpl(}, Instance of 'DirectiveContext')
|
||||
parseMetadataStar(})
|
||||
listener: beginMetadataStar(class)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelKeywordDeclaration(}, class, null, Instance of 'DirectiveContext')
|
||||
parseClassOrNamedMixinApplication(null, null, null, class)
|
||||
listener: beginClassOrMixinOrNamedMixinApplicationPrelude(class)
|
||||
ensureIdentifier(class, classOrMixinDeclaration)
|
||||
listener: handleIdentifier(Bar, classOrMixinDeclaration)
|
||||
listener: handleNoTypeVariables({)
|
||||
listener: beginClassDeclaration(class, null, null, null, Bar)
|
||||
parseClass(Bar, class, class, Bar)
|
||||
parseClassHeaderOpt(Bar, class, class)
|
||||
parseClassExtendsOpt(Bar)
|
||||
listener: handleNoType(Bar)
|
||||
listener: handleClassExtends(null, 1)
|
||||
parseClassWithClauseOpt(Bar)
|
||||
listener: handleClassNoWithClause()
|
||||
parseClassOrMixinOrEnumImplementsOpt(Bar)
|
||||
listener: handleImplements(null, 0)
|
||||
listener: handleClassHeader(class, class, null)
|
||||
parseClassOrMixinOrExtensionBody(Bar, DeclarationKind.Class, Bar)
|
||||
listener: beginClassOrMixinOrExtensionBody(DeclarationKind.Class, {)
|
||||
notEofOrValue(}, ()
|
||||
parseClassOrMixinOrExtensionOrEnumMemberImpl({, DeclarationKind.Class, Bar)
|
||||
parseMetadataStar({)
|
||||
listener: beginMetadataStar(()
|
||||
listener: endMetadataStar(0)
|
||||
listener: beginMember()
|
||||
parseMethod({, null, null, null, null, null, null, null, {, Instance of 'ComplexTypeInfo', null, operator, DeclarationKind.Class, Bar, false)
|
||||
listener: beginMethod(DeclarationKind.Class, null, null, null, null, null, null, operator)
|
||||
parseRecordType((, {)
|
||||
listener: beginRecordType(()
|
||||
parseRecordTypeField((, identifierIsOptional: true)
|
||||
listener: beginRecordTypeEntry()
|
||||
parseMetadataStar(()
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments(,)
|
||||
listener: handleType(int, null)
|
||||
listener: handleNoName(,)
|
||||
listener: endRecordTypeEntry()
|
||||
parseRecordTypeField(,, identifierIsOptional: true)
|
||||
listener: beginRecordTypeEntry()
|
||||
parseMetadataStar(,)
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments())
|
||||
listener: handleType(int, null)
|
||||
listener: handleNoName())
|
||||
listener: endRecordTypeEntry()
|
||||
listener: endRecordType((, ?, 2, false)
|
||||
parseOperatorName(?)
|
||||
listener: handleOperatorName(operator, [])
|
||||
parseMethodTypeVar([])
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters([], operator, false, MemberKind.NonStaticMethod)
|
||||
parseFormalParameters([], MemberKind.NonStaticMethod)
|
||||
parseFormalParametersRest((, MemberKind.NonStaticMethod)
|
||||
listener: beginFormalParameters((, MemberKind.NonStaticMethod)
|
||||
parseFormalParameter((, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
parseMetadataStar(()
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: beginFormalParameter(int, MemberKind.NonStaticMethod, null, null, null)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments(bar)
|
||||
listener: handleType(int, null)
|
||||
ensureIdentifier(int, formalParameterDeclaration)
|
||||
listener: handleIdentifier(bar, formalParameterDeclaration)
|
||||
listener: handleFormalParameterWithoutValue())
|
||||
listener: endFormalParameter(null, null, null, bar, null, null, FormalParameterKind.requiredPositional, MemberKind.NonStaticMethod)
|
||||
listener: endFormalParameters(1, (, ), MemberKind.NonStaticMethod)
|
||||
parseInitializersOpt())
|
||||
listener: handleNoInitializers()
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(null, null)
|
||||
inPlainSync()
|
||||
inPlainSync()
|
||||
parseFunctionBody(), false, true)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, return)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseReturnStatement({)
|
||||
listener: beginReturnStatement(return)
|
||||
parseExpression(return)
|
||||
parsePrecedenceExpression(return, 1, true)
|
||||
parseUnaryExpression(return, true)
|
||||
parsePrimary(return, expression)
|
||||
parseParenthesizedExpressionFunctionLiteralOrRecordLiteral(return)
|
||||
parseParenthesizedExpressionOrRecordLiteral(return, null)
|
||||
listener: beginParenthesizedExpressionOrRecordLiteral(()
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseLiteralInt(()
|
||||
listener: handleLiteralInt(42)
|
||||
parseExpression(,)
|
||||
parsePrecedenceExpression(,, 1, true)
|
||||
parseUnaryExpression(,, true)
|
||||
parsePrimary(,, expression)
|
||||
parseLiteralInt(,)
|
||||
listener: handleLiteralInt(42)
|
||||
ensureCloseParen(42, ()
|
||||
listener: endRecordLiteral((, 2, null)
|
||||
ensureSemicolon())
|
||||
listener: endReturnStatement(true, return, ;)
|
||||
inGenerator()
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(1, {, })
|
||||
listener: endClassMethod(null, (, (, null, })
|
||||
listener: endMember()
|
||||
notEofOrValue(}, })
|
||||
listener: endClassOrMixinOrExtensionBody(DeclarationKind.Class, 1, {, })
|
||||
listener: endClassDeclaration(class, })
|
||||
listener: endTopLevelDeclaration()
|
||||
reportAllErrorTokens(class)
|
||||
listener: endCompilationUnit(2, )
|
|
@ -0,0 +1,25 @@
|
|||
class Foo {
|
||||
(int, int) operator [](int foo) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
||||
|
||||
class Bar {
|
||||
(int, int)? operator [](int bar) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class[KeywordToken] Foo[StringToken] {[BeginToken]
|
||||
([BeginToken]int[StringToken],[SimpleToken] int[StringToken])[SimpleToken] operator[KeywordToken] [][SimpleToken]([BeginToken]int[StringToken] foo[StringToken])[SimpleToken] {[BeginToken]
|
||||
return[KeywordToken] ([BeginToken]42[StringToken],[SimpleToken] 42[StringToken])[SimpleToken];[SimpleToken]
|
||||
}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
|
||||
class[KeywordToken] Bar[StringToken] {[BeginToken]
|
||||
([BeginToken]int[StringToken],[SimpleToken] int[StringToken])[SimpleToken]?[SimpleToken] operator[KeywordToken] [][SimpleToken]([BeginToken]int[StringToken] bar[StringToken])[SimpleToken] {[BeginToken]
|
||||
return[KeywordToken] ([BeginToken]42[StringToken],[SimpleToken] 42[StringToken])[SimpleToken];[SimpleToken]
|
||||
}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
|
@ -0,0 +1,25 @@
|
|||
class Foo {
|
||||
(int, int) operator [](int foo) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
||||
|
||||
class Bar {
|
||||
(int, int)? operator [](int bar) {
|
||||
return (42, 42);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class[KeywordToken] Foo[StringToken] {[BeginToken]
|
||||
([BeginToken]int[StringToken],[SimpleToken] int[StringToken])[SimpleToken] operator[KeywordToken] [][SimpleToken]([BeginToken]int[StringToken] foo[StringToken])[SimpleToken] {[BeginToken]
|
||||
return[KeywordToken] ([BeginToken]42[StringToken],[SimpleToken] 42[StringToken])[SimpleToken];[SimpleToken]
|
||||
}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
|
||||
class[KeywordToken] Bar[StringToken] {[BeginToken]
|
||||
([BeginToken]int[StringToken],[SimpleToken] int[StringToken])[SimpleToken]?[SimpleToken] operator[KeywordToken] [][SimpleToken]([BeginToken]int[StringToken] bar[StringToken])[SimpleToken] {[BeginToken]
|
||||
return[KeywordToken] ([BeginToken]42[StringToken],[SimpleToken] 42[StringToken])[SimpleToken];[SimpleToken]
|
||||
}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
Loading…
Reference in a new issue