| OLD | NEW |
| 1 // This code was auto-generated, is not intended to be edited, and is subject to | 1 // This code was auto-generated, is not intended to be edited, and is subject to |
| 2 // significant change. Please see the README file for more information. | 2 // significant change. Please see the README file for more information. |
| 3 library engine.parser; | 3 library engine.parser; |
| 4 import 'dart:collection'; | 4 import 'dart:collection'; |
| 5 import 'java_core.dart'; | 5 import 'java_core.dart'; |
| 6 import 'java_engine.dart'; | 6 import 'java_engine.dart'; |
| 7 import 'instrumentation.dart'; | 7 import 'instrumentation.dart'; |
| 8 import 'error.dart'; | 8 import 'error.dart'; |
| 9 import 'source.dart'; | 9 import 'source.dart'; |
| 10 import 'scanner.dart'; | 10 import 'scanner.dart'; |
| 11 import 'ast.dart'; | 11 import 'ast.dart'; |
| 12 import 'utilities_dart.dart'; | 12 import 'utilities_dart.dart'; |
| 13 /** | 13 /** |
| 14 * Instances of the class `CommentAndMetadata` implement a simple data-holder fo
r a method | 14 * Instances of the class `CommentAndMetadata` implement a simple data-holder fo
r a method |
| 15 * that needs to return multiple values. | 15 * that needs to return multiple values. |
| 16 * |
| 16 * @coverage dart.engine.parser | 17 * @coverage dart.engine.parser |
| 17 */ | 18 */ |
| 18 class CommentAndMetadata { | 19 class CommentAndMetadata { |
| 19 | 20 |
| 20 /** | 21 /** |
| 21 * The documentation comment that was parsed, or `null` if none was given. | 22 * The documentation comment that was parsed, or `null` if none was given. |
| 22 */ | 23 */ |
| 23 Comment _comment; | 24 Comment _comment; |
| 24 | 25 |
| 25 /** | 26 /** |
| 26 * The metadata that was parsed. | 27 * The metadata that was parsed. |
| 27 */ | 28 */ |
| 28 List<Annotation> _metadata; | 29 List<Annotation> _metadata; |
| 29 | 30 |
| 30 /** | 31 /** |
| 31 * Initialize a newly created holder with the given data. | 32 * Initialize a newly created holder with the given data. |
| 33 * |
| 32 * @param comment the documentation comment that was parsed | 34 * @param comment the documentation comment that was parsed |
| 33 * @param metadata the metadata that was parsed | 35 * @param metadata the metadata that was parsed |
| 34 */ | 36 */ |
| 35 CommentAndMetadata(Comment comment, List<Annotation> metadata) { | 37 CommentAndMetadata(Comment comment, List<Annotation> metadata) { |
| 36 this._comment = comment; | 38 this._comment = comment; |
| 37 this._metadata = metadata; | 39 this._metadata = metadata; |
| 38 } | 40 } |
| 39 | 41 |
| 40 /** | 42 /** |
| 41 * Return the documentation comment that was parsed, or `null` if none was giv
en. | 43 * Return the documentation comment that was parsed, or `null` if none was giv
en. |
| 44 * |
| 42 * @return the documentation comment that was parsed | 45 * @return the documentation comment that was parsed |
| 43 */ | 46 */ |
| 44 Comment get comment => _comment; | 47 Comment get comment => _comment; |
| 45 | 48 |
| 46 /** | 49 /** |
| 47 * Return the metadata that was parsed. If there was no metadata, then the lis
t will be empty. | 50 * Return the metadata that was parsed. If there was no metadata, then the lis
t will be empty. |
| 51 * |
| 48 * @return the metadata that was parsed | 52 * @return the metadata that was parsed |
| 49 */ | 53 */ |
| 50 List<Annotation> get metadata => _metadata; | 54 List<Annotation> get metadata => _metadata; |
| 51 } | 55 } |
| 52 /** | 56 /** |
| 53 * Instances of the class `FinalConstVarOrType` implement a simple data-holder f
or a method | 57 * Instances of the class `FinalConstVarOrType` implement a simple data-holder f
or a method |
| 54 * that needs to return multiple values. | 58 * that needs to return multiple values. |
| 59 * |
| 55 * @coverage dart.engine.parser | 60 * @coverage dart.engine.parser |
| 56 */ | 61 */ |
| 57 class FinalConstVarOrType { | 62 class FinalConstVarOrType { |
| 58 | 63 |
| 59 /** | 64 /** |
| 60 * The 'final', 'const' or 'var' keyword, or `null` if none was given. | 65 * The 'final', 'const' or 'var' keyword, or `null` if none was given. |
| 61 */ | 66 */ |
| 62 Token _keyword; | 67 Token _keyword; |
| 63 | 68 |
| 64 /** | 69 /** |
| 65 * The type, of `null` if no type was specified. | 70 * The type, of `null` if no type was specified. |
| 66 */ | 71 */ |
| 67 TypeName _type; | 72 TypeName _type; |
| 68 | 73 |
| 69 /** | 74 /** |
| 70 * Initialize a newly created holder with the given data. | 75 * Initialize a newly created holder with the given data. |
| 76 * |
| 71 * @param keyword the 'final', 'const' or 'var' keyword | 77 * @param keyword the 'final', 'const' or 'var' keyword |
| 72 * @param type the type | 78 * @param type the type |
| 73 */ | 79 */ |
| 74 FinalConstVarOrType(Token keyword, TypeName type) { | 80 FinalConstVarOrType(Token keyword, TypeName type) { |
| 75 this._keyword = keyword; | 81 this._keyword = keyword; |
| 76 this._type = type; | 82 this._type = type; |
| 77 } | 83 } |
| 78 | 84 |
| 79 /** | 85 /** |
| 80 * Return the 'final', 'const' or 'var' keyword, or `null` if none was given. | 86 * Return the 'final', 'const' or 'var' keyword, or `null` if none was given. |
| 87 * |
| 81 * @return the 'final', 'const' or 'var' keyword | 88 * @return the 'final', 'const' or 'var' keyword |
| 82 */ | 89 */ |
| 83 Token get keyword => _keyword; | 90 Token get keyword => _keyword; |
| 84 | 91 |
| 85 /** | 92 /** |
| 86 * Return the type, of `null` if no type was specified. | 93 * Return the type, of `null` if no type was specified. |
| 94 * |
| 87 * @return the type | 95 * @return the type |
| 88 */ | 96 */ |
| 89 TypeName get type => _type; | 97 TypeName get type => _type; |
| 90 } | 98 } |
| 91 /** | 99 /** |
| 92 * Instances of the class `Modifiers` implement a simple data-holder for a metho
d that needs | 100 * Instances of the class `Modifiers` implement a simple data-holder for a metho
d that needs |
| 93 * to return multiple values. | 101 * to return multiple values. |
| 102 * |
| 94 * @coverage dart.engine.parser | 103 * @coverage dart.engine.parser |
| 95 */ | 104 */ |
| 96 class Modifiers { | 105 class Modifiers { |
| 97 | 106 |
| 98 /** | 107 /** |
| 99 * The token representing the keyword 'abstract', or `null` if the keyword was
not found. | 108 * The token representing the keyword 'abstract', or `null` if the keyword was
not found. |
| 100 */ | 109 */ |
| 101 Token _abstractKeyword; | 110 Token _abstractKeyword; |
| 102 | 111 |
| 103 /** | 112 /** |
| (...skipping 22 matching lines...) Expand all Loading... |
| 126 Token _staticKeyword; | 135 Token _staticKeyword; |
| 127 | 136 |
| 128 /** | 137 /** |
| 129 * The token representing the keyword 'var', or `null` if the keyword was not
found. | 138 * The token representing the keyword 'var', or `null` if the keyword was not
found. |
| 130 */ | 139 */ |
| 131 Token _varKeyword; | 140 Token _varKeyword; |
| 132 | 141 |
| 133 /** | 142 /** |
| 134 * Return the token representing the keyword 'abstract', or `null` if the keyw
ord was not | 143 * Return the token representing the keyword 'abstract', or `null` if the keyw
ord was not |
| 135 * found. | 144 * found. |
| 145 * |
| 136 * @return the token representing the keyword 'abstract' | 146 * @return the token representing the keyword 'abstract' |
| 137 */ | 147 */ |
| 138 Token get abstractKeyword => _abstractKeyword; | 148 Token get abstractKeyword => _abstractKeyword; |
| 139 | 149 |
| 140 /** | 150 /** |
| 141 * Return the token representing the keyword 'const', or `null` if the keyword
was not | 151 * Return the token representing the keyword 'const', or `null` if the keyword
was not |
| 142 * found. | 152 * found. |
| 153 * |
| 143 * @return the token representing the keyword 'const' | 154 * @return the token representing the keyword 'const' |
| 144 */ | 155 */ |
| 145 Token get constKeyword => _constKeyword; | 156 Token get constKeyword => _constKeyword; |
| 146 | 157 |
| 147 /** | 158 /** |
| 148 * Return the token representing the keyword 'external', or `null` if the keyw
ord was not | 159 * Return the token representing the keyword 'external', or `null` if the keyw
ord was not |
| 149 * found. | 160 * found. |
| 161 * |
| 150 * @return the token representing the keyword 'external' | 162 * @return the token representing the keyword 'external' |
| 151 */ | 163 */ |
| 152 Token get externalKeyword => _externalKeyword; | 164 Token get externalKeyword => _externalKeyword; |
| 153 | 165 |
| 154 /** | 166 /** |
| 155 * Return the token representing the keyword 'factory', or `null` if the keywo
rd was not | 167 * Return the token representing the keyword 'factory', or `null` if the keywo
rd was not |
| 156 * found. | 168 * found. |
| 169 * |
| 157 * @return the token representing the keyword 'factory' | 170 * @return the token representing the keyword 'factory' |
| 158 */ | 171 */ |
| 159 Token get factoryKeyword => _factoryKeyword; | 172 Token get factoryKeyword => _factoryKeyword; |
| 160 | 173 |
| 161 /** | 174 /** |
| 162 * Return the token representing the keyword 'final', or `null` if the keyword
was not | 175 * Return the token representing the keyword 'final', or `null` if the keyword
was not |
| 163 * found. | 176 * found. |
| 177 * |
| 164 * @return the token representing the keyword 'final' | 178 * @return the token representing the keyword 'final' |
| 165 */ | 179 */ |
| 166 Token get finalKeyword => _finalKeyword; | 180 Token get finalKeyword => _finalKeyword; |
| 167 | 181 |
| 168 /** | 182 /** |
| 169 * Return the token representing the keyword 'static', or `null` if the keywor
d was not | 183 * Return the token representing the keyword 'static', or `null` if the keywor
d was not |
| 170 * found. | 184 * found. |
| 185 * |
| 171 * @return the token representing the keyword 'static' | 186 * @return the token representing the keyword 'static' |
| 172 */ | 187 */ |
| 173 Token get staticKeyword => _staticKeyword; | 188 Token get staticKeyword => _staticKeyword; |
| 174 | 189 |
| 175 /** | 190 /** |
| 176 * Return the token representing the keyword 'var', or `null` if the keyword w
as not found. | 191 * Return the token representing the keyword 'var', or `null` if the keyword w
as not found. |
| 192 * |
| 177 * @return the token representing the keyword 'var' | 193 * @return the token representing the keyword 'var' |
| 178 */ | 194 */ |
| 179 Token get varKeyword => _varKeyword; | 195 Token get varKeyword => _varKeyword; |
| 180 | 196 |
| 181 /** | 197 /** |
| 182 * Set the token representing the keyword 'abstract' to the given token. | 198 * Set the token representing the keyword 'abstract' to the given token. |
| 199 * |
| 183 * @param abstractKeyword the token representing the keyword 'abstract' | 200 * @param abstractKeyword the token representing the keyword 'abstract' |
| 184 */ | 201 */ |
| 185 void set abstractKeyword(Token abstractKeyword2) { | 202 void set abstractKeyword(Token abstractKeyword2) { |
| 186 this._abstractKeyword = abstractKeyword2; | 203 this._abstractKeyword = abstractKeyword2; |
| 187 } | 204 } |
| 188 | 205 |
| 189 /** | 206 /** |
| 190 * Set the token representing the keyword 'const' to the given token. | 207 * Set the token representing the keyword 'const' to the given token. |
| 208 * |
| 191 * @param constKeyword the token representing the keyword 'const' | 209 * @param constKeyword the token representing the keyword 'const' |
| 192 */ | 210 */ |
| 193 void set constKeyword(Token constKeyword2) { | 211 void set constKeyword(Token constKeyword2) { |
| 194 this._constKeyword = constKeyword2; | 212 this._constKeyword = constKeyword2; |
| 195 } | 213 } |
| 196 | 214 |
| 197 /** | 215 /** |
| 198 * Set the token representing the keyword 'external' to the given token. | 216 * Set the token representing the keyword 'external' to the given token. |
| 217 * |
| 199 * @param externalKeyword the token representing the keyword 'external' | 218 * @param externalKeyword the token representing the keyword 'external' |
| 200 */ | 219 */ |
| 201 void set externalKeyword(Token externalKeyword2) { | 220 void set externalKeyword(Token externalKeyword2) { |
| 202 this._externalKeyword = externalKeyword2; | 221 this._externalKeyword = externalKeyword2; |
| 203 } | 222 } |
| 204 | 223 |
| 205 /** | 224 /** |
| 206 * Set the token representing the keyword 'factory' to the given token. | 225 * Set the token representing the keyword 'factory' to the given token. |
| 226 * |
| 207 * @param factoryKeyword the token representing the keyword 'factory' | 227 * @param factoryKeyword the token representing the keyword 'factory' |
| 208 */ | 228 */ |
| 209 void set factoryKeyword(Token factoryKeyword2) { | 229 void set factoryKeyword(Token factoryKeyword2) { |
| 210 this._factoryKeyword = factoryKeyword2; | 230 this._factoryKeyword = factoryKeyword2; |
| 211 } | 231 } |
| 212 | 232 |
| 213 /** | 233 /** |
| 214 * Set the token representing the keyword 'final' to the given token. | 234 * Set the token representing the keyword 'final' to the given token. |
| 235 * |
| 215 * @param finalKeyword the token representing the keyword 'final' | 236 * @param finalKeyword the token representing the keyword 'final' |
| 216 */ | 237 */ |
| 217 void set finalKeyword(Token finalKeyword2) { | 238 void set finalKeyword(Token finalKeyword2) { |
| 218 this._finalKeyword = finalKeyword2; | 239 this._finalKeyword = finalKeyword2; |
| 219 } | 240 } |
| 220 | 241 |
| 221 /** | 242 /** |
| 222 * Set the token representing the keyword 'static' to the given token. | 243 * Set the token representing the keyword 'static' to the given token. |
| 244 * |
| 223 * @param staticKeyword the token representing the keyword 'static' | 245 * @param staticKeyword the token representing the keyword 'static' |
| 224 */ | 246 */ |
| 225 void set staticKeyword(Token staticKeyword2) { | 247 void set staticKeyword(Token staticKeyword2) { |
| 226 this._staticKeyword = staticKeyword2; | 248 this._staticKeyword = staticKeyword2; |
| 227 } | 249 } |
| 228 | 250 |
| 229 /** | 251 /** |
| 230 * Set the token representing the keyword 'var' to the given token. | 252 * Set the token representing the keyword 'var' to the given token. |
| 253 * |
| 231 * @param varKeyword the token representing the keyword 'var' | 254 * @param varKeyword the token representing the keyword 'var' |
| 232 */ | 255 */ |
| 233 void set varKeyword(Token varKeyword2) { | 256 void set varKeyword(Token varKeyword2) { |
| 234 this._varKeyword = varKeyword2; | 257 this._varKeyword = varKeyword2; |
| 235 } | 258 } |
| 236 String toString() { | 259 String toString() { |
| 237 JavaStringBuilder builder = new JavaStringBuilder(); | 260 JavaStringBuilder builder = new JavaStringBuilder(); |
| 238 bool needsSpace = appendKeyword(builder, false, _abstractKeyword); | 261 bool needsSpace = appendKeyword(builder, false, _abstractKeyword); |
| 239 needsSpace = appendKeyword(builder, needsSpace, _constKeyword); | 262 needsSpace = appendKeyword(builder, needsSpace, _constKeyword); |
| 240 needsSpace = appendKeyword(builder, needsSpace, _externalKeyword); | 263 needsSpace = appendKeyword(builder, needsSpace, _externalKeyword); |
| 241 needsSpace = appendKeyword(builder, needsSpace, _factoryKeyword); | 264 needsSpace = appendKeyword(builder, needsSpace, _factoryKeyword); |
| 242 needsSpace = appendKeyword(builder, needsSpace, _finalKeyword); | 265 needsSpace = appendKeyword(builder, needsSpace, _finalKeyword); |
| 243 needsSpace = appendKeyword(builder, needsSpace, _staticKeyword); | 266 needsSpace = appendKeyword(builder, needsSpace, _staticKeyword); |
| 244 appendKeyword(builder, needsSpace, _varKeyword); | 267 appendKeyword(builder, needsSpace, _varKeyword); |
| 245 return builder.toString(); | 268 return builder.toString(); |
| 246 } | 269 } |
| 247 | 270 |
| 248 /** | 271 /** |
| 249 * If the given keyword is not `null`, append it to the given builder, prefixi
ng it with a | 272 * If the given keyword is not `null`, append it to the given builder, prefixi
ng it with a |
| 250 * space if needed. | 273 * space if needed. |
| 274 * |
| 251 * @param builder the builder to which the keyword will be appended | 275 * @param builder the builder to which the keyword will be appended |
| 252 * @param needsSpace `true` if the keyword needs to be prefixed with a space | 276 * @param needsSpace `true` if the keyword needs to be prefixed with a space |
| 253 * @param keyword the keyword to be appended | 277 * @param keyword the keyword to be appended |
| 254 * @return `true` if subsequent keywords need to be prefixed with a space | 278 * @return `true` if subsequent keywords need to be prefixed with a space |
| 255 */ | 279 */ |
| 256 bool appendKeyword(JavaStringBuilder builder, bool needsSpace, Token keyword)
{ | 280 bool appendKeyword(JavaStringBuilder builder, bool needsSpace, Token keyword)
{ |
| 257 if (keyword != null) { | 281 if (keyword != null) { |
| 258 if (needsSpace) { | 282 if (needsSpace) { |
| 259 builder.appendChar(0x20); | 283 builder.appendChar(0x20); |
| 260 } | 284 } |
| 261 builder.append(keyword.lexeme); | 285 builder.append(keyword.lexeme); |
| 262 return true; | 286 return true; |
| 263 } | 287 } |
| 264 return needsSpace; | 288 return needsSpace; |
| 265 } | 289 } |
| 266 } | 290 } |
| 267 /** | 291 /** |
| 268 * Instances of the class `Parser` are used to parse tokens into an AST structur
e. | 292 * Instances of the class `Parser` are used to parse tokens into an AST structur
e. |
| 293 * |
| 269 * @coverage dart.engine.parser | 294 * @coverage dart.engine.parser |
| 270 */ | 295 */ |
| 271 class Parser { | 296 class Parser { |
| 272 | 297 |
| 273 /** | 298 /** |
| 274 * The source being parsed. | 299 * The source being parsed. |
| 275 */ | 300 */ |
| 276 Source _source; | 301 Source _source; |
| 277 | 302 |
| 278 /** | 303 /** |
| (...skipping 16 matching lines...) Expand all Loading... |
| 295 */ | 320 */ |
| 296 bool _inSwitch = false; | 321 bool _inSwitch = false; |
| 297 static String _HIDE = "hide"; | 322 static String _HIDE = "hide"; |
| 298 static String _OF = "of"; | 323 static String _OF = "of"; |
| 299 static String _ON = "on"; | 324 static String _ON = "on"; |
| 300 static String _SHOW = "show"; | 325 static String _SHOW = "show"; |
| 301 static String _NATIVE = "native"; | 326 static String _NATIVE = "native"; |
| 302 | 327 |
| 303 /** | 328 /** |
| 304 * Initialize a newly created parser. | 329 * Initialize a newly created parser. |
| 330 * |
| 305 * @param source the source being parsed | 331 * @param source the source being parsed |
| 306 * @param errorListener the error listener that will be informed of any errors
that are found | 332 * @param errorListener the error listener that will be informed of any errors
that are found |
| 307 * during the parse | 333 * during the parse |
| 308 */ | 334 */ |
| 309 Parser(Source source, AnalysisErrorListener errorListener) { | 335 Parser(Source source, AnalysisErrorListener errorListener) { |
| 310 this._source = source; | 336 this._source = source; |
| 311 this._errorListener = errorListener; | 337 this._errorListener = errorListener; |
| 312 } | 338 } |
| 313 | 339 |
| 314 /** | 340 /** |
| 315 * Parse a compilation unit, starting with the given token. | 341 * Parse a compilation unit, starting with the given token. |
| 342 * |
| 316 * @param token the first token of the compilation unit | 343 * @param token the first token of the compilation unit |
| 317 * @return the compilation unit that was parsed | 344 * @return the compilation unit that was parsed |
| 318 */ | 345 */ |
| 319 CompilationUnit parseCompilationUnit(Token token) { | 346 CompilationUnit parseCompilationUnit(Token token) { |
| 320 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseCompilationUnit"); | 347 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseCompilationUnit"); |
| 321 try { | 348 try { |
| 322 _currentToken = token; | 349 _currentToken = token; |
| 323 return parseCompilationUnit2(); | 350 return parseCompilationUnit2(); |
| 324 } finally { | 351 } finally { |
| 325 instrumentation.log(); | 352 instrumentation.log(); |
| 326 } | 353 } |
| 327 } | 354 } |
| 328 | 355 |
| 329 /** | 356 /** |
| 330 * Parse an expression, starting with the given token. | 357 * Parse an expression, starting with the given token. |
| 358 * |
| 331 * @param token the first token of the expression | 359 * @param token the first token of the expression |
| 332 * @return the expression that was parsed, or `null` if the tokens do not repr
esent a | 360 * @return the expression that was parsed, or `null` if the tokens do not repr
esent a |
| 333 * recognizable expression | 361 * recognizable expression |
| 334 */ | 362 */ |
| 335 Expression parseExpression(Token token) { | 363 Expression parseExpression(Token token) { |
| 336 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseExpression"); | 364 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseExpression"); |
| 337 try { | 365 try { |
| 338 _currentToken = token; | 366 _currentToken = token; |
| 339 return parseExpression2(); | 367 return parseExpression2(); |
| 340 } finally { | 368 } finally { |
| 341 instrumentation.log(); | 369 instrumentation.log(); |
| 342 } | 370 } |
| 343 } | 371 } |
| 344 | 372 |
| 345 /** | 373 /** |
| 346 * Parse a statement, starting with the given token. | 374 * Parse a statement, starting with the given token. |
| 375 * |
| 347 * @param token the first token of the statement | 376 * @param token the first token of the statement |
| 348 * @return the statement that was parsed, or `null` if the tokens do not repre
sent a | 377 * @return the statement that was parsed, or `null` if the tokens do not repre
sent a |
| 349 * recognizable statement | 378 * recognizable statement |
| 350 */ | 379 */ |
| 351 Statement parseStatement(Token token) { | 380 Statement parseStatement(Token token) { |
| 352 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseStatement"); | 381 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseStatement"); |
| 353 try { | 382 try { |
| 354 _currentToken = token; | 383 _currentToken = token; |
| 355 return parseStatement2(); | 384 return parseStatement2(); |
| 356 } finally { | 385 } finally { |
| 357 instrumentation.log(); | 386 instrumentation.log(); |
| 358 } | 387 } |
| 359 } | 388 } |
| 360 | 389 |
| 361 /** | 390 /** |
| 362 * Parse a sequence of statements, starting with the given token. | 391 * Parse a sequence of statements, starting with the given token. |
| 392 * |
| 363 * @param token the first token of the sequence of statement | 393 * @param token the first token of the sequence of statement |
| 364 * @return the statements that were parsed, or `null` if the tokens do not rep
resent a | 394 * @return the statements that were parsed, or `null` if the tokens do not rep
resent a |
| 365 * recognizable sequence of statements | 395 * recognizable sequence of statements |
| 366 */ | 396 */ |
| 367 List<Statement> parseStatements(Token token) { | 397 List<Statement> parseStatements(Token token) { |
| 368 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseStatements"); | 398 InstrumentationBuilder instrumentation = Instrumentation.builder2("dart.engi
ne.Parser.parseStatements"); |
| 369 try { | 399 try { |
| 370 _currentToken = token; | 400 _currentToken = token; |
| 371 return parseStatements2(); | 401 return parseStatements2(); |
| 372 } finally { | 402 } finally { |
| 373 instrumentation.log(); | 403 instrumentation.log(); |
| 374 } | 404 } |
| 375 } | 405 } |
| 376 void set currentToken(Token currentToken2) { | 406 void set currentToken(Token currentToken2) { |
| 377 this._currentToken = currentToken2; | 407 this._currentToken = currentToken2; |
| 378 } | 408 } |
| 379 | 409 |
| 380 /** | 410 /** |
| 381 * Advance to the next token in the token stream. | 411 * Advance to the next token in the token stream. |
| 382 */ | 412 */ |
| 383 void advance() { | 413 void advance() { |
| 384 _currentToken = _currentToken.next; | 414 _currentToken = _currentToken.next; |
| 385 } | 415 } |
| 386 | 416 |
| 387 /** | 417 /** |
| 388 * Append the character equivalent of the given scalar value to the given buil
der. Use the start | 418 * Append the character equivalent of the given scalar value to the given buil
der. Use the start |
| 389 * and end indices to report an error, and don't append anything to the builde
r, if the scalar | 419 * and end indices to report an error, and don't append anything to the builde
r, if the scalar |
| 390 * value is invalid. | 420 * value is invalid. |
| 421 * |
| 391 * @param builder the builder to which the scalar value is to be appended | 422 * @param builder the builder to which the scalar value is to be appended |
| 392 * @param escapeSequence the escape sequence that was parsed to produce the sc
alar value | 423 * @param escapeSequence the escape sequence that was parsed to produce the sc
alar value |
| 393 * @param scalarValue the value to be appended | 424 * @param scalarValue the value to be appended |
| 394 * @param startIndex the index of the first character representing the scalar
value | 425 * @param startIndex the index of the first character representing the scalar
value |
| 395 * @param endIndex the index of the last character representing the scalar val
ue | 426 * @param endIndex the index of the last character representing the scalar val
ue |
| 396 */ | 427 */ |
| 397 void appendScalarValue(JavaStringBuilder builder, String escapeSequence, int s
calarValue, int startIndex, int endIndex) { | 428 void appendScalarValue(JavaStringBuilder builder, String escapeSequence, int s
calarValue, int startIndex, int endIndex) { |
| 398 if (scalarValue < 0 || scalarValue > Character.MAX_CODE_POINT || (scalarValu
e >= 0xD800 && scalarValue <= 0xDFFF)) { | 429 if (scalarValue < 0 || scalarValue > Character.MAX_CODE_POINT || (scalarValu
e >= 0xD800 && scalarValue <= 0xDFFF)) { |
| 399 reportError7(ParserErrorCode.INVALID_CODE_POINT, [escapeSequence]); | 430 reportError7(ParserErrorCode.INVALID_CODE_POINT, [escapeSequence]); |
| 400 return; | 431 return; |
| 401 } | 432 } |
| 402 if (scalarValue < Character.MAX_VALUE) { | 433 if (scalarValue < Character.MAX_VALUE) { |
| 403 builder.appendChar((scalarValue as int)); | 434 builder.appendChar((scalarValue as int)); |
| 404 } else { | 435 } else { |
| 405 builder.append(Character.toChars(scalarValue)); | 436 builder.append(Character.toChars(scalarValue)); |
| 406 } | 437 } |
| 407 } | 438 } |
| 408 | 439 |
| 409 /** | 440 /** |
| 410 * Compute the content of a string with the given literal representation. | 441 * Compute the content of a string with the given literal representation. |
| 442 * |
| 411 * @param lexeme the literal representation of the string | 443 * @param lexeme the literal representation of the string |
| 412 * @return the actual value of the string | 444 * @return the actual value of the string |
| 413 */ | 445 */ |
| 414 String computeStringValue(String lexeme) { | 446 String computeStringValue(String lexeme) { |
| 415 if (lexeme.startsWith("r\"\"\"") || lexeme.startsWith("r'''")) { | 447 if (lexeme.startsWith("r\"\"\"") || lexeme.startsWith("r'''")) { |
| 416 if (lexeme.length > 4) { | 448 if (lexeme.length > 4) { |
| 417 return lexeme.substring(4, lexeme.length - 3); | 449 return lexeme.substring(4, lexeme.length - 3); |
| 418 } | 450 } |
| 419 } else if (lexeme.startsWith("r\"") || lexeme.startsWith("r'")) { | 451 } else if (lexeme.startsWith("r\"") || lexeme.startsWith("r'")) { |
| 420 if (lexeme.length > 2) { | 452 if (lexeme.length > 2) { |
| (...skipping 15 matching lines...) Expand all Loading... |
| 436 JavaStringBuilder builder = new JavaStringBuilder(); | 468 JavaStringBuilder builder = new JavaStringBuilder(); |
| 437 int index = start; | 469 int index = start; |
| 438 while (index < end) { | 470 while (index < end) { |
| 439 index = translateCharacter(builder, lexeme, index); | 471 index = translateCharacter(builder, lexeme, index); |
| 440 } | 472 } |
| 441 return builder.toString(); | 473 return builder.toString(); |
| 442 } | 474 } |
| 443 | 475 |
| 444 /** | 476 /** |
| 445 * Convert the given method declaration into the nearest valid top-level funct
ion declaration. | 477 * Convert the given method declaration into the nearest valid top-level funct
ion declaration. |
| 478 * |
| 446 * @param method the method to be converted | 479 * @param method the method to be converted |
| 447 * @return the function declaration that most closely captures the components
of the given method | 480 * @return the function declaration that most closely captures the components
of the given method |
| 448 * declaration | 481 * declaration |
| 449 */ | 482 */ |
| 450 FunctionDeclaration convertToFunctionDeclaration(MethodDeclaration method) =>
new FunctionDeclaration.full(method.documentationComment, method.metadata, metho
d.externalKeyword, method.returnType, method.propertyKeyword, method.name, new F
unctionExpression.full(method.parameters, method.body)); | 483 FunctionDeclaration convertToFunctionDeclaration(MethodDeclaration method) =>
new FunctionDeclaration.full(method.documentationComment, method.metadata, metho
d.externalKeyword, method.returnType, method.propertyKeyword, method.name, new F
unctionExpression.full(method.parameters, method.body)); |
| 451 | 484 |
| 452 /** | 485 /** |
| 453 * Return `true` if the current token could be the start of a compilation unit
member. This | 486 * Return `true` if the current token could be the start of a compilation unit
member. This |
| 454 * method is used for recovery purposes to decide when to stop skipping tokens
after finding an | 487 * method is used for recovery purposes to decide when to stop skipping tokens
after finding an |
| 455 * error while parsing a compilation unit member. | 488 * error while parsing a compilation unit member. |
| 489 * |
| 456 * @return `true` if the current token could be the start of a compilation uni
t member | 490 * @return `true` if the current token could be the start of a compilation uni
t member |
| 457 */ | 491 */ |
| 458 bool couldBeStartOfCompilationUnitMember() { | 492 bool couldBeStartOfCompilationUnitMember() { |
| 459 if ((matches(Keyword.IMPORT) || matches(Keyword.EXPORT) || matches(Keyword.L
IBRARY) || matches(Keyword.PART)) && !matches4(peek(), TokenType.PERIOD) && !mat
ches4(peek(), TokenType.LT)) { | 493 if ((matches(Keyword.IMPORT) || matches(Keyword.EXPORT) || matches(Keyword.L
IBRARY) || matches(Keyword.PART)) && !matches4(peek(), TokenType.PERIOD) && !mat
ches4(peek(), TokenType.LT)) { |
| 460 return true; | 494 return true; |
| 461 } else if (matches(Keyword.CLASS)) { | 495 } else if (matches(Keyword.CLASS)) { |
| 462 return true; | 496 return true; |
| 463 } else if (matches(Keyword.TYPEDEF) && !matches4(peek(), TokenType.PERIOD) &
& !matches4(peek(), TokenType.LT)) { | 497 } else if (matches(Keyword.TYPEDEF) && !matches4(peek(), TokenType.PERIOD) &
& !matches4(peek(), TokenType.LT)) { |
| 464 return true; | 498 return true; |
| 465 } else if (matches(Keyword.VOID) || ((matches(Keyword.GET) || matches(Keywor
d.SET)) && matchesIdentifier2(peek())) || (matches(Keyword.OPERATOR) && isOperat
or(peek()))) { | 499 } else if (matches(Keyword.VOID) || ((matches(Keyword.GET) || matches(Keywor
d.SET)) && matchesIdentifier2(peek())) || (matches(Keyword.OPERATOR) && isOperat
or(peek()))) { |
| 466 return true; | 500 return true; |
| 467 } else if (matchesIdentifier()) { | 501 } else if (matchesIdentifier()) { |
| 468 if (matches4(peek(), TokenType.OPEN_PAREN)) { | 502 if (matches4(peek(), TokenType.OPEN_PAREN)) { |
| 469 return true; | 503 return true; |
| 470 } | 504 } |
| 471 Token token = skipReturnType(_currentToken); | 505 Token token = skipReturnType(_currentToken); |
| 472 if (token == null) { | 506 if (token == null) { |
| 473 return false; | 507 return false; |
| 474 } | 508 } |
| 475 if (matches(Keyword.GET) || matches(Keyword.SET) || (matches(Keyword.OPERA
TOR) && isOperator(peek())) || matchesIdentifier()) { | 509 if (matches(Keyword.GET) || matches(Keyword.SET) || (matches(Keyword.OPERA
TOR) && isOperator(peek())) || matchesIdentifier()) { |
| 476 return true; | 510 return true; |
| 477 } | 511 } |
| 478 } | 512 } |
| 479 return false; | 513 return false; |
| 480 } | 514 } |
| 481 | 515 |
| 482 /** | 516 /** |
| 483 * Create a synthetic identifier. | 517 * Create a synthetic identifier. |
| 518 * |
| 484 * @return the synthetic identifier that was created | 519 * @return the synthetic identifier that was created |
| 485 */ | 520 */ |
| 486 SimpleIdentifier createSyntheticIdentifier() => new SimpleIdentifier.full(crea
teSyntheticToken2(TokenType.IDENTIFIER)); | 521 SimpleIdentifier createSyntheticIdentifier() => new SimpleIdentifier.full(crea
teSyntheticToken2(TokenType.IDENTIFIER)); |
| 487 | 522 |
| 488 /** | 523 /** |
| 489 * Create a synthetic string literal. | 524 * Create a synthetic string literal. |
| 525 * |
| 490 * @return the synthetic string literal that was created | 526 * @return the synthetic string literal that was created |
| 491 */ | 527 */ |
| 492 SimpleStringLiteral createSyntheticStringLiteral() => new SimpleStringLiteral.
full(createSyntheticToken2(TokenType.STRING), ""); | 528 SimpleStringLiteral createSyntheticStringLiteral() => new SimpleStringLiteral.
full(createSyntheticToken2(TokenType.STRING), ""); |
| 493 | 529 |
| 494 /** | 530 /** |
| 495 * Create a synthetic token representing the given keyword. | 531 * Create a synthetic token representing the given keyword. |
| 532 * |
| 496 * @return the synthetic token that was created | 533 * @return the synthetic token that was created |
| 497 */ | 534 */ |
| 498 Token createSyntheticToken(Keyword keyword) => new KeywordToken_10(keyword, _c
urrentToken.offset); | 535 Token createSyntheticToken(Keyword keyword) => new KeywordToken_11(keyword, _c
urrentToken.offset); |
| 499 | 536 |
| 500 /** | 537 /** |
| 501 * Create a synthetic token with the given type. | 538 * Create a synthetic token with the given type. |
| 539 * |
| 502 * @return the synthetic token that was created | 540 * @return the synthetic token that was created |
| 503 */ | 541 */ |
| 504 Token createSyntheticToken2(TokenType type) => new StringToken(type, "", _curr
entToken.offset); | 542 Token createSyntheticToken2(TokenType type) => new StringToken(type, "", _curr
entToken.offset); |
| 505 | 543 |
| 506 /** | 544 /** |
| 507 * Check that the given expression is assignable and report an error if it isn
't. | 545 * Check that the given expression is assignable and report an error if it isn
't. |
| 546 * |
| 508 * <pre> | 547 * <pre> |
| 509 * assignableExpression ::= | 548 * assignableExpression ::= |
| 510 * primary (arguments* assignableSelector)+ | 549 * primary (arguments* assignableSelector)+ |
| 511 * | 'super' assignableSelector | 550 * | 'super' assignableSelector |
| 512 * | identifier | 551 * | identifier |
| 552 * |
| 513 * assignableSelector ::= | 553 * assignableSelector ::= |
| 514 * '\[' expression '\]' | 554 * '[' expression ']' |
| 515 * | '.' identifier | 555 * | '.' identifier |
| 516 * </pre> | 556 * </pre> |
| 557 * |
| 517 * @param expression the expression being checked | 558 * @param expression the expression being checked |
| 518 */ | 559 */ |
| 519 void ensureAssignable(Expression expression) { | 560 void ensureAssignable(Expression expression) { |
| 520 if (expression != null && !expression.isAssignable) { | 561 if (expression != null && !expression.isAssignable) { |
| 521 reportError7(ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, []); | 562 reportError7(ParserErrorCode.ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, []); |
| 522 } | 563 } |
| 523 } | 564 } |
| 524 | 565 |
| 525 /** | 566 /** |
| 526 * If the current token is a keyword matching the given string, return it afte
r advancing to the | 567 * If the current token is a keyword matching the given string, return it afte
r advancing to the |
| 527 * next token. Otherwise report an error and return the current token without
advancing. | 568 * next token. Otherwise report an error and return the current token without
advancing. |
| 569 * |
| 528 * @param keyword the keyword that is expected | 570 * @param keyword the keyword that is expected |
| 529 * @return the token that matched the given type | 571 * @return the token that matched the given type |
| 530 */ | 572 */ |
| 531 Token expect(Keyword keyword) { | 573 Token expect(Keyword keyword) { |
| 532 if (matches(keyword)) { | 574 if (matches(keyword)) { |
| 533 return andAdvance; | 575 return andAdvance; |
| 534 } | 576 } |
| 535 reportError7(ParserErrorCode.EXPECTED_TOKEN, [keyword.syntax]); | 577 reportError7(ParserErrorCode.EXPECTED_TOKEN, [keyword.syntax]); |
| 536 return _currentToken; | 578 return _currentToken; |
| 537 } | 579 } |
| 538 | 580 |
| 539 /** | 581 /** |
| 540 * If the current token has the expected type, return it after advancing to th
e next token. | 582 * If the current token has the expected type, return it after advancing to th
e next token. |
| 541 * Otherwise report an error and return the current token without advancing. | 583 * Otherwise report an error and return the current token without advancing. |
| 584 * |
| 542 * @param type the type of token that is expected | 585 * @param type the type of token that is expected |
| 543 * @return the token that matched the given type | 586 * @return the token that matched the given type |
| 544 */ | 587 */ |
| 545 Token expect2(TokenType type) { | 588 Token expect2(TokenType type) { |
| 546 if (matches5(type)) { | 589 if (matches5(type)) { |
| 547 return andAdvance; | 590 return andAdvance; |
| 548 } | 591 } |
| 549 if (identical(type, TokenType.SEMICOLON)) { | 592 if (identical(type, TokenType.SEMICOLON)) { |
| 550 reportError8(ParserErrorCode.EXPECTED_TOKEN, _currentToken.previous, [type
.lexeme]); | 593 reportError8(ParserErrorCode.EXPECTED_TOKEN, _currentToken.previous, [type
.lexeme]); |
| 551 } else { | 594 } else { |
| 552 reportError7(ParserErrorCode.EXPECTED_TOKEN, [type.lexeme]); | 595 reportError7(ParserErrorCode.EXPECTED_TOKEN, [type.lexeme]); |
| 553 } | 596 } |
| 554 return _currentToken; | 597 return _currentToken; |
| 555 } | 598 } |
| 556 | 599 |
| 557 /** | 600 /** |
| 558 * Search the given list of ranges for a range that contains the given index.
Return the range | 601 * Search the given list of ranges for a range that contains the given index.
Return the range |
| 559 * that was found, or `null` if none of the ranges contain the index. | 602 * that was found, or `null` if none of the ranges contain the index. |
| 603 * |
| 560 * @param ranges the ranges to be searched | 604 * @param ranges the ranges to be searched |
| 561 * @param index the index contained in the returned range | 605 * @param index the index contained in the returned range |
| 562 * @return the range that was found | 606 * @return the range that was found |
| 563 */ | 607 */ |
| 564 List<int> findRange(List<List<int>> ranges, int index) { | 608 List<int> findRange(List<List<int>> ranges, int index) { |
| 565 for (List<int> range in ranges) { | 609 for (List<int> range in ranges) { |
| 566 if (range[0] <= index && index <= range[1]) { | 610 if (range[0] <= index && index <= range[1]) { |
| 567 return range; | 611 return range; |
| 568 } else if (index < range[0]) { | 612 } else if (index < range[0]) { |
| 569 return null; | 613 return null; |
| 570 } | 614 } |
| 571 } | 615 } |
| 572 return null; | 616 return null; |
| 573 } | 617 } |
| 574 | 618 |
| 575 /** | 619 /** |
| 576 * Advance to the next token in the token stream, making it the new current to
ken. | 620 * Advance to the next token in the token stream, making it the new current to
ken. |
| 621 * |
| 577 * @return the token that was current before this method was invoked | 622 * @return the token that was current before this method was invoked |
| 578 */ | 623 */ |
| 579 Token get andAdvance { | 624 Token get andAdvance { |
| 580 Token token = _currentToken; | 625 Token token = _currentToken; |
| 581 advance(); | 626 advance(); |
| 582 return token; | 627 return token; |
| 583 } | 628 } |
| 584 | 629 |
| 585 /** | 630 /** |
| 586 * Return a list of the ranges of characters in the given comment string that
should be treated as | 631 * Return a list of the ranges of characters in the given comment string that
should be treated as |
| 587 * code blocks. | 632 * code blocks. |
| 633 * |
| 588 * @param comment the comment being processed | 634 * @param comment the comment being processed |
| 589 * @return the ranges of characters that should be treated as code blocks | 635 * @return the ranges of characters that should be treated as code blocks |
| 590 */ | 636 */ |
| 591 List<List<int>> getCodeBlockRanges(String comment) { | 637 List<List<int>> getCodeBlockRanges(String comment) { |
| 592 List<List<int>> ranges = new List<List<int>>(); | 638 List<List<int>> ranges = new List<List<int>>(); |
| 593 int length = comment.length; | 639 int length = comment.length; |
| 594 int index = 0; | 640 int index = 0; |
| 595 if (comment.startsWith("/**") || comment.startsWith("///")) { | 641 if (comment.startsWith("/**") || comment.startsWith("///")) { |
| 596 index = 3; | 642 index = 3; |
| 597 } | 643 } |
| (...skipping 22 matching lines...) Expand all Loading... |
| 620 } else { | 666 } else { |
| 621 index = index + 1; | 667 index = index + 1; |
| 622 } | 668 } |
| 623 } | 669 } |
| 624 return ranges; | 670 return ranges; |
| 625 } | 671 } |
| 626 | 672 |
| 627 /** | 673 /** |
| 628 * Return the end token associated with the given begin token, or `null` if ei
ther the given | 674 * Return the end token associated with the given begin token, or `null` if ei
ther the given |
| 629 * token is not a begin token or it does not have an end token associated with
it. | 675 * token is not a begin token or it does not have an end token associated with
it. |
| 676 * |
| 630 * @param beginToken the token that is expected to have an end token associate
d with it | 677 * @param beginToken the token that is expected to have an end token associate
d with it |
| 631 * @return the end token associated with the begin token | 678 * @return the end token associated with the begin token |
| 632 */ | 679 */ |
| 633 Token getEndToken(Token beginToken) { | 680 Token getEndToken(Token beginToken) { |
| 634 if (beginToken is BeginToken) { | 681 if (beginToken is BeginToken) { |
| 635 return ((beginToken as BeginToken)).endToken; | 682 return ((beginToken as BeginToken)).endToken; |
| 636 } | 683 } |
| 637 return null; | 684 return null; |
| 638 } | 685 } |
| 639 | 686 |
| 640 /** | 687 /** |
| 641 * Return `true` if the current token is the first token of a return type that
is followed | 688 * Return `true` if the current token is the first token of a return type that
is followed |
| 642 * by an identifier, possibly followed by a list of type parameters, followed
by a | 689 * by an identifier, possibly followed by a list of type parameters, followed
by a |
| 643 * left-parenthesis. This is used by parseTypeAlias to determine whether or no
t to parse a return | 690 * left-parenthesis. This is used by parseTypeAlias to determine whether or no
t to parse a return |
| 644 * type. | 691 * type. |
| 692 * |
| 645 * @return `true` if we can successfully parse the rest of a type alias if we
first parse a | 693 * @return `true` if we can successfully parse the rest of a type alias if we
first parse a |
| 646 * return type. | 694 * return type. |
| 647 */ | 695 */ |
| 648 bool hasReturnTypeInTypeAlias() { | 696 bool hasReturnTypeInTypeAlias() { |
| 649 Token next = skipReturnType(_currentToken); | 697 Token next = skipReturnType(_currentToken); |
| 650 if (next == null) { | 698 if (next == null) { |
| 651 return false; | 699 return false; |
| 652 } | 700 } |
| 653 return matchesIdentifier2(next); | 701 return matchesIdentifier2(next); |
| 654 } | 702 } |
| 655 | 703 |
| 656 /** | 704 /** |
| 657 * Return `true` if the current token appears to be the beginning of a functio
n declaration. | 705 * Return `true` if the current token appears to be the beginning of a functio
n declaration. |
| 706 * |
| 658 * @return `true` if the current token appears to be the beginning of a functi
on declaration | 707 * @return `true` if the current token appears to be the beginning of a functi
on declaration |
| 659 */ | 708 */ |
| 660 bool isFunctionDeclaration() { | 709 bool isFunctionDeclaration() { |
| 661 if (matches(Keyword.VOID)) { | 710 if (matches(Keyword.VOID)) { |
| 662 return true; | 711 return true; |
| 663 } | 712 } |
| 664 Token afterReturnType = skipTypeName(_currentToken); | 713 Token afterReturnType = skipTypeName(_currentToken); |
| 665 if (afterReturnType == null) { | 714 if (afterReturnType == null) { |
| 666 afterReturnType = _currentToken; | 715 afterReturnType = _currentToken; |
| 667 } | 716 } |
| 668 Token afterIdentifier = skipSimpleIdentifier(afterReturnType); | 717 Token afterIdentifier = skipSimpleIdentifier(afterReturnType); |
| 669 if (afterIdentifier == null) { | 718 if (afterIdentifier == null) { |
| 670 afterIdentifier = skipSimpleIdentifier(_currentToken); | 719 afterIdentifier = skipSimpleIdentifier(_currentToken); |
| 671 } | 720 } |
| 672 if (afterIdentifier == null) { | 721 if (afterIdentifier == null) { |
| 673 return false; | 722 return false; |
| 674 } | 723 } |
| 675 return isFunctionExpression(afterIdentifier); | 724 return isFunctionExpression(afterIdentifier); |
| 676 } | 725 } |
| 677 | 726 |
| 678 /** | 727 /** |
| 679 * Return `true` if the given token appears to be the beginning of a function
expression. | 728 * Return `true` if the given token appears to be the beginning of a function
expression. |
| 729 * |
| 680 * @param startToken the token that might be the start of a function expressio
n | 730 * @param startToken the token that might be the start of a function expressio
n |
| 681 * @return `true` if the given token appears to be the beginning of a function
expression | 731 * @return `true` if the given token appears to be the beginning of a function
expression |
| 682 */ | 732 */ |
| 683 bool isFunctionExpression(Token startToken) { | 733 bool isFunctionExpression(Token startToken) { |
| 684 Token afterParameters = skipFormalParameterList(startToken); | 734 Token afterParameters = skipFormalParameterList(startToken); |
| 685 if (afterParameters == null) { | 735 if (afterParameters == null) { |
| 686 return false; | 736 return false; |
| 687 } | 737 } |
| 688 return matchesAny(afterParameters, [TokenType.OPEN_CURLY_BRACKET, TokenType.
FUNCTION]); | 738 return matchesAny(afterParameters, [TokenType.OPEN_CURLY_BRACKET, TokenType.
FUNCTION]); |
| 689 } | 739 } |
| 690 | 740 |
| 691 /** | 741 /** |
| 692 * Return `true` if the given character is a valid hexadecimal digit. | 742 * Return `true` if the given character is a valid hexadecimal digit. |
| 743 * |
| 693 * @param character the character being tested | 744 * @param character the character being tested |
| 694 * @return `true` if the character is a valid hexadecimal digit | 745 * @return `true` if the character is a valid hexadecimal digit |
| 695 */ | 746 */ |
| 696 bool isHexDigit(int character) => (0x30 <= character && character <= 0x39) ||
(0x41 <= character && character <= 0x46) || (0x61 <= character && character <= 0
x66); | 747 bool isHexDigit(int character) => (0x30 <= character && character <= 0x39) ||
(0x41 <= character && character <= 0x46) || (0x61 <= character && character <= 0
x66); |
| 697 | 748 |
| 698 /** | 749 /** |
| 699 * Return `true` if the current token is the first token in an initialized var
iable | 750 * Return `true` if the current token is the first token in an initialized var
iable |
| 700 * declaration rather than an expression. This method assumes that we have alr
eady skipped past | 751 * declaration rather than an expression. This method assumes that we have alr
eady skipped past |
| 701 * any metadata that might be associated with the declaration. | 752 * any metadata that might be associated with the declaration. |
| 753 * |
| 702 * <pre> | 754 * <pre> |
| 703 * initializedVariableDeclaration ::= | 755 * initializedVariableDeclaration ::= |
| 704 * declaredIdentifier ('=' expression)? (',' initializedIdentifier) | 756 * declaredIdentifier ('=' expression)? (',' initializedIdentifier)* |
| 757 * |
| 705 * declaredIdentifier ::= | 758 * declaredIdentifier ::= |
| 706 * metadata finalConstVarOrType identifier | 759 * metadata finalConstVarOrType identifier |
| 760 * |
| 707 * finalConstVarOrType ::= | 761 * finalConstVarOrType ::= |
| 708 * 'final' type? | 762 * 'final' type? |
| 709 * | 'const' type? | 763 * | 'const' type? |
| 710 * | 'var' | 764 * | 'var' |
| 711 * | type | 765 * | type |
| 766 * |
| 712 * type ::= | 767 * type ::= |
| 713 * qualified typeArguments? | 768 * qualified typeArguments? |
| 769 * |
| 714 * initializedIdentifier ::= | 770 * initializedIdentifier ::= |
| 715 * identifier ('=' expression)? | 771 * identifier ('=' expression)? |
| 716 * </pre> | 772 * </pre> |
| 773 * |
| 717 * @return `true` if the current token is the first token in an initialized va
riable | 774 * @return `true` if the current token is the first token in an initialized va
riable |
| 718 * declaration | 775 * declaration |
| 719 */ | 776 */ |
| 720 bool isInitializedVariableDeclaration() { | 777 bool isInitializedVariableDeclaration() { |
| 721 if (matches(Keyword.FINAL) || matches(Keyword.VAR)) { | 778 if (matches(Keyword.FINAL) || matches(Keyword.VAR)) { |
| 722 return true; | 779 return true; |
| 723 } | 780 } |
| 724 if (matches(Keyword.CONST)) { | 781 if (matches(Keyword.CONST)) { |
| 725 return !matchesAny(peek(), [TokenType.LT, TokenType.OPEN_CURLY_BRACKET, To
kenType.OPEN_SQUARE_BRACKET, TokenType.INDEX]); | 782 return !matchesAny(peek(), [TokenType.LT, TokenType.OPEN_CURLY_BRACKET, To
kenType.OPEN_SQUARE_BRACKET, TokenType.INDEX]); |
| 726 } | 783 } |
| 727 Token token = skipTypeName(_currentToken); | 784 Token token = skipTypeName(_currentToken); |
| 728 if (token == null) { | 785 if (token == null) { |
| 729 return false; | 786 return false; |
| 730 } | 787 } |
| 731 token = skipSimpleIdentifier(token); | 788 token = skipSimpleIdentifier(token); |
| 732 if (token == null) { | 789 if (token == null) { |
| 733 return false; | 790 return false; |
| 734 } | 791 } |
| 735 TokenType type = token.type; | 792 TokenType type = token.type; |
| 736 return identical(type, TokenType.EQ) || identical(type, TokenType.COMMA) ||
identical(type, TokenType.SEMICOLON) || matches3(token, Keyword.IN); | 793 return identical(type, TokenType.EQ) || identical(type, TokenType.COMMA) ||
identical(type, TokenType.SEMICOLON) || matches3(token, Keyword.IN); |
| 737 } | 794 } |
| 738 | 795 |
| 739 /** | 796 /** |
| 740 * Given that we have just found bracketed text within a comment, look to see
whether that text is | 797 * Given that we have just found bracketed text within a comment, look to see
whether that text is |
| 741 * (a) followed by a parenthesized link address, (b) followed by a colon, or (
c) followed by | 798 * (a) followed by a parenthesized link address, (b) followed by a colon, or (
c) followed by |
| 742 * optional whitespace and another square bracket. | 799 * optional whitespace and another square bracket. |
| 743 * | 800 * |
| 744 * This method uses the syntax described by the <a | 801 * This method uses the syntax described by the <a |
| 745 * href="http://daringfireball.net/projects/markdown/syntax">markdown</a> proj
ect. | 802 * href="http://daringfireball.net/projects/markdown/syntax">markdown</a> proj
ect. |
| 803 * |
| 746 * @param comment the comment text in which the bracketed text was found | 804 * @param comment the comment text in which the bracketed text was found |
| 747 * @param rightIndex the index of the right bracket | 805 * @param rightIndex the index of the right bracket |
| 748 * @return `true` if the bracketed text is followed by a link address | 806 * @return `true` if the bracketed text is followed by a link address |
| 749 */ | 807 */ |
| 750 bool isLinkText(String comment, int rightIndex) { | 808 bool isLinkText(String comment, int rightIndex) { |
| 751 int length = comment.length; | 809 int length = comment.length; |
| 752 int index = rightIndex + 1; | 810 int index = rightIndex + 1; |
| 753 if (index >= length) { | 811 if (index >= length) { |
| 754 return false; | 812 return false; |
| 755 } | 813 } |
| 756 int nextChar = comment.codeUnitAt(index); | 814 int nextChar = comment.codeUnitAt(index); |
| 757 if (nextChar == 0x28 || nextChar == 0x3A) { | 815 if (nextChar == 0x28 || nextChar == 0x3A) { |
| 758 return true; | 816 return true; |
| 759 } | 817 } |
| 760 while (Character.isWhitespace(nextChar)) { | 818 while (Character.isWhitespace(nextChar)) { |
| 761 index = index + 1; | 819 index = index + 1; |
| 762 if (index >= length) { | 820 if (index >= length) { |
| 763 return false; | 821 return false; |
| 764 } | 822 } |
| 765 nextChar = comment.codeUnitAt(index); | 823 nextChar = comment.codeUnitAt(index); |
| 766 } | 824 } |
| 767 return nextChar == 0x5B; | 825 return nextChar == 0x5B; |
| 768 } | 826 } |
| 769 | 827 |
| 770 /** | 828 /** |
| 771 * Return `true` if the given token appears to be the beginning of an operator
declaration. | 829 * Return `true` if the given token appears to be the beginning of an operator
declaration. |
| 830 * |
| 772 * @param startToken the token that might be the start of an operator declarat
ion | 831 * @param startToken the token that might be the start of an operator declarat
ion |
| 773 * @return `true` if the given token appears to be the beginning of an operato
r declaration | 832 * @return `true` if the given token appears to be the beginning of an operato
r declaration |
| 774 */ | 833 */ |
| 775 bool isOperator(Token startToken) { | 834 bool isOperator(Token startToken) { |
| 776 if (startToken.isOperator) { | 835 if (startToken.isOperator) { |
| 777 Token token = startToken.next; | 836 Token token = startToken.next; |
| 778 while (token.isOperator) { | 837 while (token.isOperator) { |
| 779 token = token.next; | 838 token = token.next; |
| 780 } | 839 } |
| 781 return matches4(token, TokenType.OPEN_PAREN); | 840 return matches4(token, TokenType.OPEN_PAREN); |
| 782 } | 841 } |
| 783 return false; | 842 return false; |
| 784 } | 843 } |
| 785 | 844 |
| 786 /** | 845 /** |
| 787 * Return `true` if the current token appears to be the beginning of a switch
member. | 846 * Return `true` if the current token appears to be the beginning of a switch
member. |
| 847 * |
| 788 * @return `true` if the current token appears to be the beginning of a switch
member | 848 * @return `true` if the current token appears to be the beginning of a switch
member |
| 789 */ | 849 */ |
| 790 bool isSwitchMember() { | 850 bool isSwitchMember() { |
| 791 Token token = _currentToken; | 851 Token token = _currentToken; |
| 792 while (matches4(token, TokenType.IDENTIFIER) && matches4(token.next, TokenTy
pe.COLON)) { | 852 while (matches4(token, TokenType.IDENTIFIER) && matches4(token.next, TokenTy
pe.COLON)) { |
| 793 token = token.next.next; | 853 token = token.next.next; |
| 794 } | 854 } |
| 795 if (identical(token.type, TokenType.KEYWORD)) { | 855 if (identical(token.type, TokenType.KEYWORD)) { |
| 796 Keyword keyword = ((token as KeywordToken)).keyword; | 856 Keyword keyword = ((token as KeywordToken)).keyword; |
| 797 return identical(keyword, Keyword.CASE) || identical(keyword, Keyword.DEFA
ULT); | 857 return identical(keyword, Keyword.CASE) || identical(keyword, Keyword.DEFA
ULT); |
| 798 } | 858 } |
| 799 return false; | 859 return false; |
| 800 } | 860 } |
| 801 | 861 |
| 802 /** | 862 /** |
| 803 * Compare the given tokens to find the token that appears first in the source
being parsed. That | 863 * Compare the given tokens to find the token that appears first in the source
being parsed. That |
| 804 * is, return the left-most of all of the tokens. The arguments are allowed to
be `null`. | 864 * is, return the left-most of all of the tokens. The arguments are allowed to
be `null`. |
| 805 * Return the token with the smallest offset, or `null` if there are no argume
nts or if all | 865 * Return the token with the smallest offset, or `null` if there are no argume
nts or if all |
| 806 * of the arguments are `null`. | 866 * of the arguments are `null`. |
| 867 * |
| 807 * @param tokens the tokens being compared | 868 * @param tokens the tokens being compared |
| 808 * @return the token with the smallest offset | 869 * @return the token with the smallest offset |
| 809 */ | 870 */ |
| 810 Token lexicallyFirst(List<Token> tokens) { | 871 Token lexicallyFirst(List<Token> tokens) { |
| 811 Token first = null; | 872 Token first = null; |
| 812 int firstOffset = 2147483647; | 873 int firstOffset = 2147483647; |
| 813 for (Token token in tokens) { | 874 for (Token token in tokens) { |
| 814 if (token != null) { | 875 if (token != null) { |
| 815 int offset = token.offset; | 876 int offset = token.offset; |
| 816 if (offset < firstOffset) { | 877 if (offset < firstOffset) { |
| 817 first = token; | 878 first = token; |
| 818 firstOffset = offset; | 879 firstOffset = offset; |
| 819 } | 880 } |
| 820 } | 881 } |
| 821 } | 882 } |
| 822 return first; | 883 return first; |
| 823 } | 884 } |
| 824 | 885 |
| 825 /** | 886 /** |
| 826 * Return `true` if the current token matches the given keyword. | 887 * Return `true` if the current token matches the given keyword. |
| 888 * |
| 827 * @param keyword the keyword that can optionally appear in the current locati
on | 889 * @param keyword the keyword that can optionally appear in the current locati
on |
| 828 * @return `true` if the current token matches the given keyword | 890 * @return `true` if the current token matches the given keyword |
| 829 */ | 891 */ |
| 830 bool matches(Keyword keyword) => matches3(_currentToken, keyword); | 892 bool matches(Keyword keyword) => matches3(_currentToken, keyword); |
| 831 | 893 |
| 832 /** | 894 /** |
| 833 * Return `true` if the current token matches the given identifier. | 895 * Return `true` if the current token matches the given identifier. |
| 896 * |
| 834 * @param identifier the identifier that can optionally appear in the current
location | 897 * @param identifier the identifier that can optionally appear in the current
location |
| 835 * @return `true` if the current token matches the given identifier | 898 * @return `true` if the current token matches the given identifier |
| 836 */ | 899 */ |
| 837 bool matches2(String identifier) => identical(_currentToken.type, TokenType.ID
ENTIFIER) && _currentToken.lexeme == identifier; | 900 bool matches2(String identifier) => identical(_currentToken.type, TokenType.ID
ENTIFIER) && _currentToken.lexeme == identifier; |
| 838 | 901 |
| 839 /** | 902 /** |
| 840 * Return `true` if the given token matches the given keyword. | 903 * Return `true` if the given token matches the given keyword. |
| 904 * |
| 841 * @param token the token being tested | 905 * @param token the token being tested |
| 842 * @param keyword the keyword that is being tested for | 906 * @param keyword the keyword that is being tested for |
| 843 * @return `true` if the given token matches the given keyword | 907 * @return `true` if the given token matches the given keyword |
| 844 */ | 908 */ |
| 845 bool matches3(Token token, Keyword keyword2) => identical(token.type, TokenTyp
e.KEYWORD) && identical(((token as KeywordToken)).keyword, keyword2); | 909 bool matches3(Token token, Keyword keyword2) => identical(token.type, TokenTyp
e.KEYWORD) && identical(((token as KeywordToken)).keyword, keyword2); |
| 846 | 910 |
| 847 /** | 911 /** |
| 848 * Return `true` if the given token has the given type. | 912 * Return `true` if the given token has the given type. |
| 913 * |
| 849 * @param token the token being tested | 914 * @param token the token being tested |
| 850 * @param type the type of token that is being tested for | 915 * @param type the type of token that is being tested for |
| 851 * @return `true` if the given token has the given type | 916 * @return `true` if the given token has the given type |
| 852 */ | 917 */ |
| 853 bool matches4(Token token, TokenType type2) => identical(token.type, type2); | 918 bool matches4(Token token, TokenType type2) => identical(token.type, type2); |
| 854 | 919 |
| 855 /** | 920 /** |
| 856 * Return `true` if the current token has the given type. Note that this metho
d, unlike | 921 * Return `true` if the current token has the given type. Note that this metho
d, unlike |
| 857 * other variants, will modify the token stream if possible to match a wider r
ange of tokens. In | 922 * other variants, will modify the token stream if possible to match a wider r
ange of tokens. In |
| 858 * particular, if we are attempting to match a '>' and the next token is eithe
r a '>>' or '>>>', | 923 * particular, if we are attempting to match a '>' and the next token is eithe
r a '>>' or '>>>', |
| 859 * the token stream will be re-written and `true` will be returned. | 924 * the token stream will be re-written and `true` will be returned. |
| 925 * |
| 860 * @param type the type of token that can optionally appear in the current loc
ation | 926 * @param type the type of token that can optionally appear in the current loc
ation |
| 861 * @return `true` if the current token has the given type | 927 * @return `true` if the current token has the given type |
| 862 */ | 928 */ |
| 863 bool matches5(TokenType type2) { | 929 bool matches5(TokenType type2) { |
| 864 TokenType currentType = _currentToken.type; | 930 TokenType currentType = _currentToken.type; |
| 865 if (currentType != type2) { | 931 if (currentType != type2) { |
| 866 if (identical(type2, TokenType.GT)) { | 932 if (identical(type2, TokenType.GT)) { |
| 867 if (identical(currentType, TokenType.GT_GT)) { | 933 if (identical(currentType, TokenType.GT_GT)) { |
| 868 int offset = _currentToken.offset; | 934 int offset = _currentToken.offset; |
| 869 Token first = new Token(TokenType.GT, offset); | 935 Token first = new Token(TokenType.GT, offset); |
| (...skipping 25 matching lines...) Expand all Loading... |
| 895 return true; | 961 return true; |
| 896 } | 962 } |
| 897 } | 963 } |
| 898 return false; | 964 return false; |
| 899 } | 965 } |
| 900 return true; | 966 return true; |
| 901 } | 967 } |
| 902 | 968 |
| 903 /** | 969 /** |
| 904 * Return `true` if the given token has any one of the given types. | 970 * Return `true` if the given token has any one of the given types. |
| 971 * |
| 905 * @param token the token being tested | 972 * @param token the token being tested |
| 906 * @param types the types of token that are being tested for | 973 * @param types the types of token that are being tested for |
| 907 * @return `true` if the given token has any of the given types | 974 * @return `true` if the given token has any of the given types |
| 908 */ | 975 */ |
| 909 bool matchesAny(Token token, List<TokenType> types) { | 976 bool matchesAny(Token token, List<TokenType> types) { |
| 910 TokenType actualType = token.type; | 977 TokenType actualType = token.type; |
| 911 for (TokenType type in types) { | 978 for (TokenType type in types) { |
| 912 if (identical(actualType, type)) { | 979 if (identical(actualType, type)) { |
| 913 return true; | 980 return true; |
| 914 } | 981 } |
| 915 } | 982 } |
| 916 return false; | 983 return false; |
| 917 } | 984 } |
| 918 | 985 |
| 919 /** | 986 /** |
| 920 * Return `true` if the current token is a valid identifier. Valid identifiers
include | 987 * Return `true` if the current token is a valid identifier. Valid identifiers
include |
| 921 * built-in identifiers (pseudo-keywords). | 988 * built-in identifiers (pseudo-keywords). |
| 989 * |
| 922 * @return `true` if the current token is a valid identifier | 990 * @return `true` if the current token is a valid identifier |
| 923 */ | 991 */ |
| 924 bool matchesIdentifier() => matchesIdentifier2(_currentToken); | 992 bool matchesIdentifier() => matchesIdentifier2(_currentToken); |
| 925 | 993 |
| 926 /** | 994 /** |
| 927 * Return `true` if the given token is a valid identifier. Valid identifiers i
nclude | 995 * Return `true` if the given token is a valid identifier. Valid identifiers i
nclude |
| 928 * built-in identifiers (pseudo-keywords). | 996 * built-in identifiers (pseudo-keywords). |
| 997 * |
| 929 * @return `true` if the given token is a valid identifier | 998 * @return `true` if the given token is a valid identifier |
| 930 */ | 999 */ |
| 931 bool matchesIdentifier2(Token token) => matches4(token, TokenType.IDENTIFIER)
|| (matches4(token, TokenType.KEYWORD) && ((token as KeywordToken)).keyword.isPs
eudoKeyword); | 1000 bool matchesIdentifier2(Token token) => matches4(token, TokenType.IDENTIFIER)
|| (matches4(token, TokenType.KEYWORD) && ((token as KeywordToken)).keyword.isPs
eudoKeyword); |
| 932 | 1001 |
| 933 /** | 1002 /** |
| 934 * If the current token has the given type, then advance to the next token and
return `true`. Otherwise, return `false` without advancing. | 1003 * If the current token has the given type, then advance to the next token and
return `true` |
| 1004 * . Otherwise, return `false` without advancing. |
| 1005 * |
| 935 * @param type the type of token that can optionally appear in the current loc
ation | 1006 * @param type the type of token that can optionally appear in the current loc
ation |
| 936 * @return `true` if the current token has the given type | 1007 * @return `true` if the current token has the given type |
| 937 */ | 1008 */ |
| 938 bool optional(TokenType type) { | 1009 bool optional(TokenType type) { |
| 939 if (matches5(type)) { | 1010 if (matches5(type)) { |
| 940 advance(); | 1011 advance(); |
| 941 return true; | 1012 return true; |
| 942 } | 1013 } |
| 943 return false; | 1014 return false; |
| 944 } | 1015 } |
| 945 | 1016 |
| 946 /** | 1017 /** |
| 947 * Parse an additive expression. | 1018 * Parse an additive expression. |
| 1019 * |
| 948 * <pre> | 1020 * <pre> |
| 949 * additiveExpression ::= | 1021 * additiveExpression ::= |
| 950 * multiplicativeExpression (additiveOperator multiplicativeExpression) | 1022 * multiplicativeExpression (additiveOperator multiplicativeExpression)* |
| 951 * | 'super' (additiveOperator multiplicativeExpression)+ | 1023 * | 'super' (additiveOperator multiplicativeExpression)+ |
| 952 * </pre> | 1024 * </pre> |
| 1025 * |
| 953 * @return the additive expression that was parsed | 1026 * @return the additive expression that was parsed |
| 954 */ | 1027 */ |
| 955 Expression parseAdditiveExpression() { | 1028 Expression parseAdditiveExpression() { |
| 956 Expression expression; | 1029 Expression expression; |
| 957 if (matches(Keyword.SUPER) && _currentToken.next.type.isAdditiveOperator) { | 1030 if (matches(Keyword.SUPER) && _currentToken.next.type.isAdditiveOperator) { |
| 958 expression = new SuperExpression.full(andAdvance); | 1031 expression = new SuperExpression.full(andAdvance); |
| 959 } else { | 1032 } else { |
| 960 expression = parseMultiplicativeExpression(); | 1033 expression = parseMultiplicativeExpression(); |
| 961 } | 1034 } |
| 962 while (_currentToken.type.isAdditiveOperator) { | 1035 while (_currentToken.type.isAdditiveOperator) { |
| 963 Token operator = andAdvance; | 1036 Token operator = andAdvance; |
| 964 expression = new BinaryExpression.full(expression, operator, parseMultipli
cativeExpression()); | 1037 expression = new BinaryExpression.full(expression, operator, parseMultipli
cativeExpression()); |
| 965 } | 1038 } |
| 966 return expression; | 1039 return expression; |
| 967 } | 1040 } |
| 968 | 1041 |
| 969 /** | 1042 /** |
| 970 * Parse an annotation. | 1043 * Parse an annotation. |
| 1044 * |
| 971 * <pre> | 1045 * <pre> |
| 972 * annotation ::= | 1046 * annotation ::= |
| 973 * '@' qualified ('.' identifier)? arguments? | 1047 * '@' qualified ('.' identifier)? arguments? |
| 974 * </pre> | 1048 * </pre> |
| 1049 * |
| 975 * @return the annotation that was parsed | 1050 * @return the annotation that was parsed |
| 976 */ | 1051 */ |
| 977 Annotation parseAnnotation() { | 1052 Annotation parseAnnotation() { |
| 978 Token atSign = expect2(TokenType.AT); | 1053 Token atSign = expect2(TokenType.AT); |
| 979 Identifier name = parsePrefixedIdentifier(); | 1054 Identifier name = parsePrefixedIdentifier(); |
| 980 Token period = null; | 1055 Token period = null; |
| 981 SimpleIdentifier constructorName = null; | 1056 SimpleIdentifier constructorName = null; |
| 982 if (matches5(TokenType.PERIOD)) { | 1057 if (matches5(TokenType.PERIOD)) { |
| 983 period = andAdvance; | 1058 period = andAdvance; |
| 984 constructorName = parseSimpleIdentifier(); | 1059 constructorName = parseSimpleIdentifier(); |
| 985 } | 1060 } |
| 986 ArgumentList arguments = null; | 1061 ArgumentList arguments = null; |
| 987 if (matches5(TokenType.OPEN_PAREN)) { | 1062 if (matches5(TokenType.OPEN_PAREN)) { |
| 988 arguments = parseArgumentList(); | 1063 arguments = parseArgumentList(); |
| 989 } | 1064 } |
| 990 return new Annotation.full(atSign, name, period, constructorName, arguments)
; | 1065 return new Annotation.full(atSign, name, period, constructorName, arguments)
; |
| 991 } | 1066 } |
| 992 | 1067 |
| 993 /** | 1068 /** |
| 994 * Parse an argument. | 1069 * Parse an argument. |
| 1070 * |
| 995 * <pre> | 1071 * <pre> |
| 996 * argument ::= | 1072 * argument ::= |
| 997 * namedArgument | 1073 * namedArgument |
| 998 * | expression | 1074 * | expression |
| 1075 * |
| 999 * namedArgument ::= | 1076 * namedArgument ::= |
| 1000 * label expression | 1077 * label expression |
| 1001 * </pre> | 1078 * </pre> |
| 1079 * |
| 1002 * @return the argument that was parsed | 1080 * @return the argument that was parsed |
| 1003 */ | 1081 */ |
| 1004 Expression parseArgument() { | 1082 Expression parseArgument() { |
| 1005 if (matchesIdentifier() && matches4(peek(), TokenType.COLON)) { | 1083 if (matchesIdentifier() && matches4(peek(), TokenType.COLON)) { |
| 1006 SimpleIdentifier label = new SimpleIdentifier.full(andAdvance); | 1084 SimpleIdentifier label = new SimpleIdentifier.full(andAdvance); |
| 1007 Label name = new Label.full(label, andAdvance); | 1085 Label name = new Label.full(label, andAdvance); |
| 1008 return new NamedExpression.full(name, parseExpression2()); | 1086 return new NamedExpression.full(name, parseExpression2()); |
| 1009 } else { | 1087 } else { |
| 1010 return parseExpression2(); | 1088 return parseExpression2(); |
| 1011 } | 1089 } |
| 1012 } | 1090 } |
| 1013 | 1091 |
| 1014 /** | 1092 /** |
| 1015 * Parse an argument definition test. | 1093 * Parse an argument definition test. |
| 1094 * |
| 1016 * <pre> | 1095 * <pre> |
| 1017 * argumentDefinitionTest ::= | 1096 * argumentDefinitionTest ::= |
| 1018 * '?' identifier | 1097 * '?' identifier |
| 1019 * </pre> | 1098 * </pre> |
| 1099 * |
| 1020 * @return the argument definition test that was parsed | 1100 * @return the argument definition test that was parsed |
| 1021 */ | 1101 */ |
| 1022 ArgumentDefinitionTest parseArgumentDefinitionTest() { | 1102 ArgumentDefinitionTest parseArgumentDefinitionTest() { |
| 1023 Token question = expect2(TokenType.QUESTION); | 1103 Token question = expect2(TokenType.QUESTION); |
| 1024 SimpleIdentifier identifier = parseSimpleIdentifier(); | 1104 SimpleIdentifier identifier = parseSimpleIdentifier(); |
| 1025 return new ArgumentDefinitionTest.full(question, identifier); | 1105 return new ArgumentDefinitionTest.full(question, identifier); |
| 1026 } | 1106 } |
| 1027 | 1107 |
| 1028 /** | 1108 /** |
| 1029 * Parse a list of arguments. | 1109 * Parse a list of arguments. |
| 1110 * |
| 1030 * <pre> | 1111 * <pre> |
| 1031 * arguments ::= | 1112 * arguments ::= |
| 1032 * '(' argumentList? ')' | 1113 * '(' argumentList? ')' |
| 1114 * |
| 1033 * argumentList ::= | 1115 * argumentList ::= |
| 1034 * namedArgument (',' namedArgument) | 1116 * namedArgument (',' namedArgument)* |
| 1035 * | expressionList (',' namedArgument) | 1117 * | expressionList (',' namedArgument)* |
| 1036 * </pre> | 1118 * </pre> |
| 1119 * |
| 1037 * @return the argument list that was parsed | 1120 * @return the argument list that was parsed |
| 1038 */ | 1121 */ |
| 1039 ArgumentList parseArgumentList() { | 1122 ArgumentList parseArgumentList() { |
| 1040 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 1123 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 1041 List<Expression> arguments = new List<Expression>(); | 1124 List<Expression> arguments = new List<Expression>(); |
| 1042 if (matches5(TokenType.CLOSE_PAREN)) { | 1125 if (matches5(TokenType.CLOSE_PAREN)) { |
| 1043 return new ArgumentList.full(leftParenthesis, arguments, andAdvance); | 1126 return new ArgumentList.full(leftParenthesis, arguments, andAdvance); |
| 1044 } | 1127 } |
| 1045 Expression argument = parseArgument(); | 1128 Expression argument = parseArgument(); |
| 1046 arguments.add(argument); | 1129 arguments.add(argument); |
| (...skipping 10 matching lines...) Expand all Loading... |
| 1057 } else if (argument is NamedExpression) { | 1140 } else if (argument is NamedExpression) { |
| 1058 foundNamedArgument = true; | 1141 foundNamedArgument = true; |
| 1059 } | 1142 } |
| 1060 } | 1143 } |
| 1061 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); | 1144 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); |
| 1062 return new ArgumentList.full(leftParenthesis, arguments, rightParenthesis); | 1145 return new ArgumentList.full(leftParenthesis, arguments, rightParenthesis); |
| 1063 } | 1146 } |
| 1064 | 1147 |
| 1065 /** | 1148 /** |
| 1066 * Parse an assert statement. | 1149 * Parse an assert statement. |
| 1150 * |
| 1067 * <pre> | 1151 * <pre> |
| 1068 * assertStatement ::= | 1152 * assertStatement ::= |
| 1069 * 'assert' '(' conditionalExpression ')' ';' | 1153 * 'assert' '(' conditionalExpression ')' ';' |
| 1070 * </pre> | 1154 * </pre> |
| 1155 * |
| 1071 * @return the assert statement | 1156 * @return the assert statement |
| 1072 */ | 1157 */ |
| 1073 AssertStatement parseAssertStatement() { | 1158 AssertStatement parseAssertStatement() { |
| 1074 Token keyword = expect(Keyword.ASSERT); | 1159 Token keyword = expect(Keyword.ASSERT); |
| 1075 Token leftParen = expect2(TokenType.OPEN_PAREN); | 1160 Token leftParen = expect2(TokenType.OPEN_PAREN); |
| 1076 Expression expression = parseConditionalExpression(); | 1161 Expression expression = parseConditionalExpression(); |
| 1077 Token rightParen = expect2(TokenType.CLOSE_PAREN); | 1162 Token rightParen = expect2(TokenType.CLOSE_PAREN); |
| 1078 Token semicolon = expect2(TokenType.SEMICOLON); | 1163 Token semicolon = expect2(TokenType.SEMICOLON); |
| 1079 return new AssertStatement.full(keyword, leftParen, expression, rightParen,
semicolon); | 1164 return new AssertStatement.full(keyword, leftParen, expression, rightParen,
semicolon); |
| 1080 } | 1165 } |
| 1081 | 1166 |
| 1082 /** | 1167 /** |
| 1083 * Parse an assignable expression. | 1168 * Parse an assignable expression. |
| 1169 * |
| 1084 * <pre> | 1170 * <pre> |
| 1085 * assignableExpression ::= | 1171 * assignableExpression ::= |
| 1086 * primary (arguments* assignableSelector)+ | 1172 * primary (arguments* assignableSelector)+ |
| 1087 * | 'super' assignableSelector | 1173 * | 'super' assignableSelector |
| 1088 * | identifier | 1174 * | identifier |
| 1089 * </pre> | 1175 * </pre> |
| 1176 * |
| 1090 * @param primaryAllowed `true` if the expression is allowed to be a primary w
ithout any | 1177 * @param primaryAllowed `true` if the expression is allowed to be a primary w
ithout any |
| 1091 * assignable selector | 1178 * assignable selector |
| 1092 * @return the assignable expression that was parsed | 1179 * @return the assignable expression that was parsed |
| 1093 */ | 1180 */ |
| 1094 Expression parseAssignableExpression(bool primaryAllowed) { | 1181 Expression parseAssignableExpression(bool primaryAllowed) { |
| 1095 if (matches(Keyword.SUPER)) { | 1182 if (matches(Keyword.SUPER)) { |
| 1096 return parseAssignableSelector(new SuperExpression.full(andAdvance), false
); | 1183 return parseAssignableSelector(new SuperExpression.full(andAdvance), false
); |
| 1097 } | 1184 } |
| 1098 Expression expression = parsePrimaryExpression(); | 1185 Expression expression = parsePrimaryExpression(); |
| 1099 bool isOptional = primaryAllowed || expression is SimpleIdentifier; | 1186 bool isOptional = primaryAllowed || expression is SimpleIdentifier; |
| 1100 while (true) { | 1187 while (true) { |
| 1101 while (matches5(TokenType.OPEN_PAREN)) { | 1188 while (matches5(TokenType.OPEN_PAREN)) { |
| (...skipping 21 matching lines...) Expand all Loading... |
| 1123 } | 1210 } |
| 1124 return expression; | 1211 return expression; |
| 1125 } | 1212 } |
| 1126 expression = selectorExpression; | 1213 expression = selectorExpression; |
| 1127 isOptional = true; | 1214 isOptional = true; |
| 1128 } | 1215 } |
| 1129 } | 1216 } |
| 1130 | 1217 |
| 1131 /** | 1218 /** |
| 1132 * Parse an assignable selector. | 1219 * Parse an assignable selector. |
| 1220 * |
| 1133 * <pre> | 1221 * <pre> |
| 1134 * assignableSelector ::= | 1222 * assignableSelector ::= |
| 1135 * '\[' expression '\]' | 1223 * '[' expression ']' |
| 1136 * | '.' identifier | 1224 * | '.' identifier |
| 1137 * </pre> | 1225 * </pre> |
| 1226 * |
| 1138 * @param prefix the expression preceding the selector | 1227 * @param prefix the expression preceding the selector |
| 1139 * @param optional `true` if the selector is optional | 1228 * @param optional `true` if the selector is optional |
| 1140 * @return the assignable selector that was parsed | 1229 * @return the assignable selector that was parsed |
| 1141 */ | 1230 */ |
| 1142 Expression parseAssignableSelector(Expression prefix, bool optional) { | 1231 Expression parseAssignableSelector(Expression prefix, bool optional) { |
| 1143 if (matches5(TokenType.OPEN_SQUARE_BRACKET)) { | 1232 if (matches5(TokenType.OPEN_SQUARE_BRACKET)) { |
| 1144 Token leftBracket = andAdvance; | 1233 Token leftBracket = andAdvance; |
| 1145 Expression index = parseExpression2(); | 1234 Expression index = parseExpression2(); |
| 1146 Token rightBracket = expect2(TokenType.CLOSE_SQUARE_BRACKET); | 1235 Token rightBracket = expect2(TokenType.CLOSE_SQUARE_BRACKET); |
| 1147 return new IndexExpression.forTarget_full(prefix, leftBracket, index, righ
tBracket); | 1236 return new IndexExpression.forTarget_full(prefix, leftBracket, index, righ
tBracket); |
| 1148 } else if (matches5(TokenType.PERIOD)) { | 1237 } else if (matches5(TokenType.PERIOD)) { |
| 1149 Token period = andAdvance; | 1238 Token period = andAdvance; |
| 1150 return new PropertyAccess.full(prefix, period, parseSimpleIdentifier()); | 1239 return new PropertyAccess.full(prefix, period, parseSimpleIdentifier()); |
| 1151 } else { | 1240 } else { |
| 1152 if (!optional) { | 1241 if (!optional) { |
| 1153 reportError7(ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, []); | 1242 reportError7(ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, []); |
| 1154 } | 1243 } |
| 1155 return prefix; | 1244 return prefix; |
| 1156 } | 1245 } |
| 1157 } | 1246 } |
| 1158 | 1247 |
| 1159 /** | 1248 /** |
| 1160 * Parse a bitwise and expression. | 1249 * Parse a bitwise and expression. |
| 1250 * |
| 1161 * <pre> | 1251 * <pre> |
| 1162 * bitwiseAndExpression ::= | 1252 * bitwiseAndExpression ::= |
| 1163 * equalityExpression ('&' equalityExpression) | 1253 * equalityExpression ('&' equalityExpression)* |
| 1164 * | 'super' ('&' equalityExpression)+ | 1254 * | 'super' ('&' equalityExpression)+ |
| 1165 * </pre> | 1255 * </pre> |
| 1256 * |
| 1166 * @return the bitwise and expression that was parsed | 1257 * @return the bitwise and expression that was parsed |
| 1167 */ | 1258 */ |
| 1168 Expression parseBitwiseAndExpression() { | 1259 Expression parseBitwiseAndExpression() { |
| 1169 Expression expression; | 1260 Expression expression; |
| 1170 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.AMPERSAND)) { | 1261 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.AMPERSAND)) { |
| 1171 expression = new SuperExpression.full(andAdvance); | 1262 expression = new SuperExpression.full(andAdvance); |
| 1172 } else { | 1263 } else { |
| 1173 expression = parseEqualityExpression(); | 1264 expression = parseEqualityExpression(); |
| 1174 } | 1265 } |
| 1175 while (matches5(TokenType.AMPERSAND)) { | 1266 while (matches5(TokenType.AMPERSAND)) { |
| 1176 Token operator = andAdvance; | 1267 Token operator = andAdvance; |
| 1177 expression = new BinaryExpression.full(expression, operator, parseEquality
Expression()); | 1268 expression = new BinaryExpression.full(expression, operator, parseEquality
Expression()); |
| 1178 } | 1269 } |
| 1179 return expression; | 1270 return expression; |
| 1180 } | 1271 } |
| 1181 | 1272 |
| 1182 /** | 1273 /** |
| 1183 * Parse a bitwise or expression. | 1274 * Parse a bitwise or expression. |
| 1275 * |
| 1184 * <pre> | 1276 * <pre> |
| 1185 * bitwiseOrExpression ::= | 1277 * bitwiseOrExpression ::= |
| 1186 * bitwiseXorExpression ('|' bitwiseXorExpression) | 1278 * bitwiseXorExpression ('|' bitwiseXorExpression)* |
| 1187 * | 'super' ('|' bitwiseXorExpression)+ | 1279 * | 'super' ('|' bitwiseXorExpression)+ |
| 1188 * </pre> | 1280 * </pre> |
| 1281 * |
| 1189 * @return the bitwise or expression that was parsed | 1282 * @return the bitwise or expression that was parsed |
| 1190 */ | 1283 */ |
| 1191 Expression parseBitwiseOrExpression() { | 1284 Expression parseBitwiseOrExpression() { |
| 1192 Expression expression; | 1285 Expression expression; |
| 1193 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.BAR)) { | 1286 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.BAR)) { |
| 1194 expression = new SuperExpression.full(andAdvance); | 1287 expression = new SuperExpression.full(andAdvance); |
| 1195 } else { | 1288 } else { |
| 1196 expression = parseBitwiseXorExpression(); | 1289 expression = parseBitwiseXorExpression(); |
| 1197 } | 1290 } |
| 1198 while (matches5(TokenType.BAR)) { | 1291 while (matches5(TokenType.BAR)) { |
| 1199 Token operator = andAdvance; | 1292 Token operator = andAdvance; |
| 1200 expression = new BinaryExpression.full(expression, operator, parseBitwiseX
orExpression()); | 1293 expression = new BinaryExpression.full(expression, operator, parseBitwiseX
orExpression()); |
| 1201 } | 1294 } |
| 1202 return expression; | 1295 return expression; |
| 1203 } | 1296 } |
| 1204 | 1297 |
| 1205 /** | 1298 /** |
| 1206 * Parse a bitwise exclusive-or expression. | 1299 * Parse a bitwise exclusive-or expression. |
| 1300 * |
| 1207 * <pre> | 1301 * <pre> |
| 1208 * bitwiseXorExpression ::= | 1302 * bitwiseXorExpression ::= |
| 1209 * bitwiseAndExpression ('^' bitwiseAndExpression) | 1303 * bitwiseAndExpression ('^' bitwiseAndExpression)* |
| 1210 * | 'super' ('^' bitwiseAndExpression)+ | 1304 * | 'super' ('^' bitwiseAndExpression)+ |
| 1211 * </pre> | 1305 * </pre> |
| 1306 * |
| 1212 * @return the bitwise exclusive-or expression that was parsed | 1307 * @return the bitwise exclusive-or expression that was parsed |
| 1213 */ | 1308 */ |
| 1214 Expression parseBitwiseXorExpression() { | 1309 Expression parseBitwiseXorExpression() { |
| 1215 Expression expression; | 1310 Expression expression; |
| 1216 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.CARET)) { | 1311 if (matches(Keyword.SUPER) && matches4(peek(), TokenType.CARET)) { |
| 1217 expression = new SuperExpression.full(andAdvance); | 1312 expression = new SuperExpression.full(andAdvance); |
| 1218 } else { | 1313 } else { |
| 1219 expression = parseBitwiseAndExpression(); | 1314 expression = parseBitwiseAndExpression(); |
| 1220 } | 1315 } |
| 1221 while (matches5(TokenType.CARET)) { | 1316 while (matches5(TokenType.CARET)) { |
| 1222 Token operator = andAdvance; | 1317 Token operator = andAdvance; |
| 1223 expression = new BinaryExpression.full(expression, operator, parseBitwiseA
ndExpression()); | 1318 expression = new BinaryExpression.full(expression, operator, parseBitwiseA
ndExpression()); |
| 1224 } | 1319 } |
| 1225 return expression; | 1320 return expression; |
| 1226 } | 1321 } |
| 1227 | 1322 |
| 1228 /** | 1323 /** |
| 1229 * Parse a block. | 1324 * Parse a block. |
| 1325 * |
| 1230 * <pre> | 1326 * <pre> |
| 1231 * block ::= | 1327 * block ::= |
| 1232 * '{' statements '}' | 1328 * '{' statements '}' |
| 1233 * </pre> | 1329 * </pre> |
| 1330 * |
| 1234 * @return the block that was parsed | 1331 * @return the block that was parsed |
| 1235 */ | 1332 */ |
| 1236 Block parseBlock() { | 1333 Block parseBlock() { |
| 1237 Token leftBracket = expect2(TokenType.OPEN_CURLY_BRACKET); | 1334 Token leftBracket = expect2(TokenType.OPEN_CURLY_BRACKET); |
| 1238 List<Statement> statements = new List<Statement>(); | 1335 List<Statement> statements = new List<Statement>(); |
| 1239 Token statementStart = _currentToken; | 1336 Token statementStart = _currentToken; |
| 1240 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET))
{ | 1337 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET))
{ |
| 1241 Statement statement = parseStatement2(); | 1338 Statement statement = parseStatement2(); |
| 1242 if (statement != null) { | 1339 if (statement != null) { |
| 1243 statements.add(statement); | 1340 statements.add(statement); |
| 1244 } | 1341 } |
| 1245 if (identical(_currentToken, statementStart)) { | 1342 if (identical(_currentToken, statementStart)) { |
| 1246 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); | 1343 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); |
| 1247 advance(); | 1344 advance(); |
| 1248 } | 1345 } |
| 1249 statementStart = _currentToken; | 1346 statementStart = _currentToken; |
| 1250 } | 1347 } |
| 1251 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); | 1348 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); |
| 1252 return new Block.full(leftBracket, statements, rightBracket); | 1349 return new Block.full(leftBracket, statements, rightBracket); |
| 1253 } | 1350 } |
| 1254 | 1351 |
| 1255 /** | 1352 /** |
| 1256 * Parse a break statement. | 1353 * Parse a break statement. |
| 1354 * |
| 1257 * <pre> | 1355 * <pre> |
| 1258 * breakStatement ::= | 1356 * breakStatement ::= |
| 1259 * 'break' identifier? ';' | 1357 * 'break' identifier? ';' |
| 1260 * </pre> | 1358 * </pre> |
| 1359 * |
| 1261 * @return the break statement that was parsed | 1360 * @return the break statement that was parsed |
| 1262 */ | 1361 */ |
| 1263 Statement parseBreakStatement() { | 1362 Statement parseBreakStatement() { |
| 1264 Token breakKeyword = expect(Keyword.BREAK); | 1363 Token breakKeyword = expect(Keyword.BREAK); |
| 1265 SimpleIdentifier label = null; | 1364 SimpleIdentifier label = null; |
| 1266 if (matchesIdentifier()) { | 1365 if (matchesIdentifier()) { |
| 1267 label = parseSimpleIdentifier(); | 1366 label = parseSimpleIdentifier(); |
| 1268 } | 1367 } |
| 1269 if (!_inLoop && !_inSwitch && label == null) { | 1368 if (!_inLoop && !_inSwitch && label == null) { |
| 1270 reportError8(ParserErrorCode.BREAK_OUTSIDE_OF_LOOP, breakKeyword, []); | 1369 reportError8(ParserErrorCode.BREAK_OUTSIDE_OF_LOOP, breakKeyword, []); |
| 1271 } | 1370 } |
| 1272 Token semicolon = expect2(TokenType.SEMICOLON); | 1371 Token semicolon = expect2(TokenType.SEMICOLON); |
| 1273 return new BreakStatement.full(breakKeyword, label, semicolon); | 1372 return new BreakStatement.full(breakKeyword, label, semicolon); |
| 1274 } | 1373 } |
| 1275 | 1374 |
| 1276 /** | 1375 /** |
| 1277 * Parse a cascade section. | 1376 * Parse a cascade section. |
| 1377 * |
| 1278 * <pre> | 1378 * <pre> |
| 1279 * cascadeSection ::= | 1379 * cascadeSection ::= |
| 1280 * '..' (cascadeSelector arguments*) (assignableSelector arguments*)* cascadeA
ssignment? | 1380 * '..' (cascadeSelector arguments*) (assignableSelector arguments*)* casc
adeAssignment? |
| 1381 * |
| 1281 * cascadeSelector ::= | 1382 * cascadeSelector ::= |
| 1282 * '\[' expression '\]' | 1383 * '[' expression ']' |
| 1283 * | identifier | 1384 * | identifier |
| 1385 * |
| 1284 * cascadeAssignment ::= | 1386 * cascadeAssignment ::= |
| 1285 * assignmentOperator expressionWithoutCascade | 1387 * assignmentOperator expressionWithoutCascade |
| 1286 * </pre> | 1388 * </pre> |
| 1389 * |
| 1287 * @return the expression representing the cascaded method invocation | 1390 * @return the expression representing the cascaded method invocation |
| 1288 */ | 1391 */ |
| 1289 Expression parseCascadeSection() { | 1392 Expression parseCascadeSection() { |
| 1290 Token period = expect2(TokenType.PERIOD_PERIOD); | 1393 Token period = expect2(TokenType.PERIOD_PERIOD); |
| 1291 Expression expression = null; | 1394 Expression expression = null; |
| 1292 SimpleIdentifier functionName = null; | 1395 SimpleIdentifier functionName = null; |
| 1293 if (matchesIdentifier()) { | 1396 if (matchesIdentifier()) { |
| 1294 functionName = parseSimpleIdentifier(); | 1397 functionName = parseSimpleIdentifier(); |
| 1295 } else if (identical(_currentToken.type, TokenType.OPEN_SQUARE_BRACKET)) { | 1398 } else if (identical(_currentToken.type, TokenType.OPEN_SQUARE_BRACKET)) { |
| 1296 Token leftBracket = andAdvance; | 1399 Token leftBracket = andAdvance; |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1333 if (_currentToken.type.isAssignmentOperator) { | 1436 if (_currentToken.type.isAssignmentOperator) { |
| 1334 Token operator = andAdvance; | 1437 Token operator = andAdvance; |
| 1335 ensureAssignable(expression); | 1438 ensureAssignable(expression); |
| 1336 expression = new AssignmentExpression.full(expression, operator, parseExpr
essionWithoutCascade()); | 1439 expression = new AssignmentExpression.full(expression, operator, parseExpr
essionWithoutCascade()); |
| 1337 } | 1440 } |
| 1338 return expression; | 1441 return expression; |
| 1339 } | 1442 } |
| 1340 | 1443 |
| 1341 /** | 1444 /** |
| 1342 * Parse a class declaration. | 1445 * Parse a class declaration. |
| 1446 * |
| 1343 * <pre> | 1447 * <pre> |
| 1344 * classDeclaration ::= | 1448 * classDeclaration ::= |
| 1345 * metadata 'abstract'? 'class' name typeParameterList? (extendsClause withCla
use?)? implementsClause? '{' classMembers '}' | 1449 * metadata 'abstract'? 'class' name typeParameterList? (extendsClause wit
hClause?)? implementsClause? '{' classMembers '}' |
| 1346 * </pre> | 1450 * </pre> |
| 1451 * |
| 1347 * @param commentAndMetadata the metadata to be associated with the member | 1452 * @param commentAndMetadata the metadata to be associated with the member |
| 1348 * @param abstractKeyword the token for the keyword 'abstract', or `null` if t
he keyword was | 1453 * @param abstractKeyword the token for the keyword 'abstract', or `null` if t
he keyword was |
| 1349 * not given | 1454 * not given |
| 1350 * @return the class declaration that was parsed | 1455 * @return the class declaration that was parsed |
| 1351 */ | 1456 */ |
| 1352 ClassDeclaration parseClassDeclaration(CommentAndMetadata commentAndMetadata,
Token abstractKeyword) { | 1457 ClassDeclaration parseClassDeclaration(CommentAndMetadata commentAndMetadata,
Token abstractKeyword) { |
| 1353 Token keyword = expect(Keyword.CLASS); | 1458 Token keyword = expect(Keyword.CLASS); |
| 1354 SimpleIdentifier name = parseSimpleIdentifier(); | 1459 SimpleIdentifier name = parseSimpleIdentifier(); |
| 1355 String className = name.name; | 1460 String className = name.name; |
| 1356 TypeParameterList typeParameters = null; | 1461 TypeParameterList typeParameters = null; |
| 1357 if (matches5(TokenType.LT)) { | 1462 if (matches5(TokenType.LT)) { |
| 1358 typeParameters = parseTypeParameterList(); | 1463 typeParameters = parseTypeParameterList(); |
| 1359 } | 1464 } |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1412 } else { | 1517 } else { |
| 1413 leftBracket = createSyntheticToken2(TokenType.OPEN_CURLY_BRACKET); | 1518 leftBracket = createSyntheticToken2(TokenType.OPEN_CURLY_BRACKET); |
| 1414 rightBracket = createSyntheticToken2(TokenType.CLOSE_CURLY_BRACKET); | 1519 rightBracket = createSyntheticToken2(TokenType.CLOSE_CURLY_BRACKET); |
| 1415 reportError7(ParserErrorCode.MISSING_CLASS_BODY, []); | 1520 reportError7(ParserErrorCode.MISSING_CLASS_BODY, []); |
| 1416 } | 1521 } |
| 1417 return new ClassDeclaration.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, abstractKeyword, keyword, name, typeParameters, extendsClause, wit
hClause, implementsClause, leftBracket, members, rightBracket); | 1522 return new ClassDeclaration.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, abstractKeyword, keyword, name, typeParameters, extendsClause, wit
hClause, implementsClause, leftBracket, members, rightBracket); |
| 1418 } | 1523 } |
| 1419 | 1524 |
| 1420 /** | 1525 /** |
| 1421 * Parse a class member. | 1526 * Parse a class member. |
| 1527 * |
| 1422 * <pre> | 1528 * <pre> |
| 1423 * classMemberDefinition ::= | 1529 * classMemberDefinition ::= |
| 1424 * declaration ';' | 1530 * declaration ';' |
| 1425 * | methodSignature functionBody | 1531 * | methodSignature functionBody |
| 1426 * </pre> | 1532 * </pre> |
| 1533 * |
| 1427 * @param className the name of the class containing the member being parsed | 1534 * @param className the name of the class containing the member being parsed |
| 1428 * @return the class member that was parsed, or `null` if what was found was n
ot a valid | 1535 * @return the class member that was parsed, or `null` if what was found was n
ot a valid |
| 1429 * class member | 1536 * class member |
| 1430 */ | 1537 */ |
| 1431 ClassMember parseClassMember(String className) { | 1538 ClassMember parseClassMember(String className) { |
| 1432 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); | 1539 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); |
| 1433 Modifiers modifiers = parseModifiers(); | 1540 Modifiers modifiers = parseModifiers(); |
| 1434 if (matches(Keyword.VOID)) { | 1541 if (matches(Keyword.VOID)) { |
| 1435 TypeName returnType = parseReturnType(); | 1542 TypeName returnType = parseReturnType(); |
| 1436 if (matches(Keyword.GET) && matchesIdentifier2(peek())) { | 1543 if (matches(Keyword.GET) && matchesIdentifier2(peek())) { |
| 1437 validateModifiersForGetterOrSetterOrMethod(modifiers); | 1544 validateModifiersForGetterOrSetterOrMethod(modifiers); |
| 1438 return parseGetter(commentAndMetadata, modifiers.externalKeyword, modifi
ers.staticKeyword, returnType); | 1545 return parseGetter(commentAndMetadata, modifiers.externalKeyword, modifi
ers.staticKeyword, returnType); |
| 1439 } else if (matches(Keyword.SET) && matchesIdentifier2(peek())) { | 1546 } else if (matches(Keyword.SET) && matchesIdentifier2(peek())) { |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1521 } | 1628 } |
| 1522 validateModifiersForGetterOrSetterOrMethod(modifiers); | 1629 validateModifiersForGetterOrSetterOrMethod(modifiers); |
| 1523 validateFormalParameterList(parameters); | 1630 validateFormalParameterList(parameters); |
| 1524 return parseMethodDeclaration2(commentAndMetadata, modifiers.externalKeywo
rd, modifiers.staticKeyword, type, methodName, parameters); | 1631 return parseMethodDeclaration2(commentAndMetadata, modifiers.externalKeywo
rd, modifiers.staticKeyword, type, methodName, parameters); |
| 1525 } | 1632 } |
| 1526 return parseInitializedIdentifierList(commentAndMetadata, modifiers.staticKe
yword, validateModifiersForField(modifiers), type); | 1633 return parseInitializedIdentifierList(commentAndMetadata, modifiers.staticKe
yword, validateModifiersForField(modifiers), type); |
| 1527 } | 1634 } |
| 1528 | 1635 |
| 1529 /** | 1636 /** |
| 1530 * Parse a list of class members. | 1637 * Parse a list of class members. |
| 1638 * |
| 1531 * <pre> | 1639 * <pre> |
| 1532 * classMembers ::= | 1640 * classMembers ::= |
| 1533 * (metadata memberDefinition) | 1641 * (metadata memberDefinition)* |
| 1534 * </pre> | 1642 * </pre> |
| 1643 * |
| 1535 * @param className the name of the class whose members are being parsed | 1644 * @param className the name of the class whose members are being parsed |
| 1536 * @param closingBracket the closing bracket for the class, or `null` if the c
losing bracket | 1645 * @param closingBracket the closing bracket for the class, or `null` if the c
losing bracket |
| 1537 * is missing | 1646 * is missing |
| 1538 * @return the list of class members that were parsed | 1647 * @return the list of class members that were parsed |
| 1539 */ | 1648 */ |
| 1540 List<ClassMember> parseClassMembers(String className, Token closingBracket) { | 1649 List<ClassMember> parseClassMembers(String className, Token closingBracket) { |
| 1541 List<ClassMember> members = new List<ClassMember>(); | 1650 List<ClassMember> members = new List<ClassMember>(); |
| 1542 Token memberStart = _currentToken; | 1651 Token memberStart = _currentToken; |
| 1543 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET)
&& (closingBracket != null || (!matches(Keyword.CLASS) && !matches(Keyword.TYPED
EF)))) { | 1652 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET)
&& (closingBracket != null || (!matches(Keyword.CLASS) && !matches(Keyword.TYPED
EF)))) { |
| 1544 if (matches5(TokenType.SEMICOLON)) { | 1653 if (matches5(TokenType.SEMICOLON)) { |
| 1545 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); | 1654 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); |
| 1546 advance(); | 1655 advance(); |
| 1547 } else { | 1656 } else { |
| 1548 ClassMember member = parseClassMember(className); | 1657 ClassMember member = parseClassMember(className); |
| 1549 if (member != null) { | 1658 if (member != null) { |
| 1550 members.add(member); | 1659 members.add(member); |
| 1551 } | 1660 } |
| 1552 } | 1661 } |
| 1553 if (identical(_currentToken, memberStart)) { | 1662 if (identical(_currentToken, memberStart)) { |
| 1554 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); | 1663 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); |
| 1555 advance(); | 1664 advance(); |
| 1556 } | 1665 } |
| 1557 memberStart = _currentToken; | 1666 memberStart = _currentToken; |
| 1558 } | 1667 } |
| 1559 return members; | 1668 return members; |
| 1560 } | 1669 } |
| 1561 | 1670 |
| 1562 /** | 1671 /** |
| 1563 * Parse a class type alias. | 1672 * Parse a class type alias. |
| 1673 * |
| 1564 * <pre> | 1674 * <pre> |
| 1565 * classTypeAlias ::= | 1675 * classTypeAlias ::= |
| 1566 * identifier typeParameters? '=' 'abstract'? mixinApplication | 1676 * identifier typeParameters? '=' 'abstract'? mixinApplication |
| 1677 * |
| 1567 * mixinApplication ::= | 1678 * mixinApplication ::= |
| 1568 * type withClause implementsClause? ';' | 1679 * type withClause implementsClause? ';' |
| 1569 * </pre> | 1680 * </pre> |
| 1681 * |
| 1570 * @param commentAndMetadata the metadata to be associated with the member | 1682 * @param commentAndMetadata the metadata to be associated with the member |
| 1571 * @param keyword the token representing the 'typedef' keyword | 1683 * @param keyword the token representing the 'typedef' keyword |
| 1572 * @return the class type alias that was parsed | 1684 * @return the class type alias that was parsed |
| 1573 */ | 1685 */ |
| 1574 ClassTypeAlias parseClassTypeAlias(CommentAndMetadata commentAndMetadata, Toke
n keyword) { | 1686 ClassTypeAlias parseClassTypeAlias(CommentAndMetadata commentAndMetadata, Toke
n keyword) { |
| 1575 SimpleIdentifier className = parseSimpleIdentifier(); | 1687 SimpleIdentifier className = parseSimpleIdentifier(); |
| 1576 TypeParameterList typeParameters = null; | 1688 TypeParameterList typeParameters = null; |
| 1577 if (matches5(TokenType.LT)) { | 1689 if (matches5(TokenType.LT)) { |
| 1578 typeParameters = parseTypeParameterList(); | 1690 typeParameters = parseTypeParameterList(); |
| 1579 } | 1691 } |
| (...skipping 23 matching lines...) Expand all Loading... |
| 1603 } else { | 1715 } else { |
| 1604 reportError8(ParserErrorCode.EXPECTED_TOKEN, _currentToken.previous, [To
kenType.SEMICOLON.lexeme]); | 1716 reportError8(ParserErrorCode.EXPECTED_TOKEN, _currentToken.previous, [To
kenType.SEMICOLON.lexeme]); |
| 1605 } | 1717 } |
| 1606 semicolon = createSyntheticToken2(TokenType.SEMICOLON); | 1718 semicolon = createSyntheticToken2(TokenType.SEMICOLON); |
| 1607 } | 1719 } |
| 1608 return new ClassTypeAlias.full(commentAndMetadata.comment, commentAndMetadat
a.metadata, keyword, className, typeParameters, equals, abstractKeyword, supercl
ass, withClause, implementsClause, semicolon); | 1720 return new ClassTypeAlias.full(commentAndMetadata.comment, commentAndMetadat
a.metadata, keyword, className, typeParameters, equals, abstractKeyword, supercl
ass, withClause, implementsClause, semicolon); |
| 1609 } | 1721 } |
| 1610 | 1722 |
| 1611 /** | 1723 /** |
| 1612 * Parse a list of combinators in a directive. | 1724 * Parse a list of combinators in a directive. |
| 1725 * |
| 1613 * <pre> | 1726 * <pre> |
| 1614 * combinator ::= | 1727 * combinator ::= |
| 1615 * 'show' identifier (',' identifier) | 1728 * 'show' identifier (',' identifier)* |
| 1616 * | 'hide' identifier (',' identifier) | 1729 * | 'hide' identifier (',' identifier)* |
| 1617 * </pre> | 1730 * </pre> |
| 1731 * |
| 1618 * @return the combinators that were parsed | 1732 * @return the combinators that were parsed |
| 1619 */ | 1733 */ |
| 1620 List<Combinator> parseCombinators() { | 1734 List<Combinator> parseCombinators() { |
| 1621 List<Combinator> combinators = new List<Combinator>(); | 1735 List<Combinator> combinators = new List<Combinator>(); |
| 1622 while (matches2(_SHOW) || matches2(_HIDE)) { | 1736 while (matches2(_SHOW) || matches2(_HIDE)) { |
| 1623 Token keyword = expect2(TokenType.IDENTIFIER); | 1737 Token keyword = expect2(TokenType.IDENTIFIER); |
| 1624 if (keyword.lexeme == _SHOW) { | 1738 if (keyword.lexeme == _SHOW) { |
| 1625 List<SimpleIdentifier> shownNames = parseIdentifierList(); | 1739 List<SimpleIdentifier> shownNames = parseIdentifierList(); |
| 1626 combinators.add(new ShowCombinator.full(keyword, shownNames)); | 1740 combinators.add(new ShowCombinator.full(keyword, shownNames)); |
| 1627 } else { | 1741 } else { |
| 1628 List<SimpleIdentifier> hiddenNames = parseIdentifierList(); | 1742 List<SimpleIdentifier> hiddenNames = parseIdentifierList(); |
| 1629 combinators.add(new HideCombinator.full(keyword, hiddenNames)); | 1743 combinators.add(new HideCombinator.full(keyword, hiddenNames)); |
| 1630 } | 1744 } |
| 1631 } | 1745 } |
| 1632 return combinators; | 1746 return combinators; |
| 1633 } | 1747 } |
| 1634 | 1748 |
| 1635 /** | 1749 /** |
| 1636 * Parse the documentation comment and metadata preceeding a declaration. This
method allows any | 1750 * Parse the documentation comment and metadata preceeding a declaration. This
method allows any |
| 1637 * number of documentation comments to occur before, after or between the meta
data, but only | 1751 * number of documentation comments to occur before, after or between the meta
data, but only |
| 1638 * returns the last (right-most) documentation comment that is found. | 1752 * returns the last (right-most) documentation comment that is found. |
| 1753 * |
| 1639 * <pre> | 1754 * <pre> |
| 1640 * metadata ::= | 1755 * metadata ::= |
| 1641 * annotation | 1756 * annotation* |
| 1642 * </pre> | 1757 * </pre> |
| 1758 * |
| 1643 * @return the documentation comment and metadata that were parsed | 1759 * @return the documentation comment and metadata that were parsed |
| 1644 */ | 1760 */ |
| 1645 CommentAndMetadata parseCommentAndMetadata() { | 1761 CommentAndMetadata parseCommentAndMetadata() { |
| 1646 Comment comment = parseDocumentationComment(); | 1762 Comment comment = parseDocumentationComment(); |
| 1647 List<Annotation> metadata = new List<Annotation>(); | 1763 List<Annotation> metadata = new List<Annotation>(); |
| 1648 while (matches5(TokenType.AT)) { | 1764 while (matches5(TokenType.AT)) { |
| 1649 metadata.add(parseAnnotation()); | 1765 metadata.add(parseAnnotation()); |
| 1650 Comment optionalComment = parseDocumentationComment(); | 1766 Comment optionalComment = parseDocumentationComment(); |
| 1651 if (optionalComment != null) { | 1767 if (optionalComment != null) { |
| 1652 comment = optionalComment; | 1768 comment = optionalComment; |
| 1653 } | 1769 } |
| 1654 } | 1770 } |
| 1655 return new CommentAndMetadata(comment, metadata); | 1771 return new CommentAndMetadata(comment, metadata); |
| 1656 } | 1772 } |
| 1657 | 1773 |
| 1658 /** | 1774 /** |
| 1659 * Parse a comment reference from the source between square brackets. | 1775 * Parse a comment reference from the source between square brackets. |
| 1776 * |
| 1660 * <pre> | 1777 * <pre> |
| 1661 * commentReference ::= | 1778 * commentReference ::= |
| 1662 * 'new'? prefixedIdentifier | 1779 * 'new'? prefixedIdentifier |
| 1663 * </pre> | 1780 * </pre> |
| 1781 * |
| 1664 * @param referenceSource the source occurring between the square brackets wit
hin a documentation | 1782 * @param referenceSource the source occurring between the square brackets wit
hin a documentation |
| 1665 * comment | 1783 * comment |
| 1666 * @param sourceOffset the offset of the first character of the reference sour
ce | 1784 * @param sourceOffset the offset of the first character of the reference sour
ce |
| 1667 * @return the comment reference that was parsed, or `null` if no reference co
uld be found | 1785 * @return the comment reference that was parsed, or `null` if no reference co
uld be found |
| 1668 */ | 1786 */ |
| 1669 CommentReference parseCommentReference(String referenceSource, int sourceOffse
t) { | 1787 CommentReference parseCommentReference(String referenceSource, int sourceOffse
t) { |
| 1670 if (referenceSource.length == 0) { | 1788 if (referenceSource.length == 0) { |
| 1671 return null; | 1789 return null; |
| 1672 } | 1790 } |
| 1673 try { | 1791 try { |
| 1674 List<bool> errorFound = [false]; | 1792 List<bool> errorFound = [false]; |
| 1675 AnalysisErrorListener listener = new AnalysisErrorListener_11(errorFound); | 1793 AnalysisErrorListener listener = new AnalysisErrorListener_12(errorFound); |
| 1676 StringScanner scanner = new StringScanner(null, referenceSource, listener)
; | 1794 StringScanner scanner = new StringScanner(null, referenceSource, listener)
; |
| 1677 scanner.setSourceStart(1, 1, sourceOffset); | 1795 scanner.setSourceStart(1, 1, sourceOffset); |
| 1678 Token firstToken = scanner.tokenize(); | 1796 Token firstToken = scanner.tokenize(); |
| 1679 if (errorFound[0]) { | 1797 if (errorFound[0]) { |
| 1680 return null; | 1798 return null; |
| 1681 } | 1799 } |
| 1682 Token newKeyword = null; | 1800 Token newKeyword = null; |
| 1683 if (matches3(firstToken, Keyword.NEW)) { | 1801 if (matches3(firstToken, Keyword.NEW)) { |
| 1684 newKeyword = firstToken; | 1802 newKeyword = firstToken; |
| 1685 firstToken = firstToken.next; | 1803 firstToken = firstToken.next; |
| (...skipping 17 matching lines...) Expand all Loading... |
| 1703 } else if (matches3(firstToken, Keyword.THIS) || matches3(firstToken, Keyw
ord.NULL) || matches3(firstToken, Keyword.TRUE) || matches3(firstToken, Keyword.
FALSE)) { | 1821 } else if (matches3(firstToken, Keyword.THIS) || matches3(firstToken, Keyw
ord.NULL) || matches3(firstToken, Keyword.TRUE) || matches3(firstToken, Keyword.
FALSE)) { |
| 1704 return null; | 1822 return null; |
| 1705 } | 1823 } |
| 1706 } catch (exception) { | 1824 } catch (exception) { |
| 1707 } | 1825 } |
| 1708 return null; | 1826 return null; |
| 1709 } | 1827 } |
| 1710 | 1828 |
| 1711 /** | 1829 /** |
| 1712 * Parse all of the comment references occurring in the given array of documen
tation comments. | 1830 * Parse all of the comment references occurring in the given array of documen
tation comments. |
| 1831 * |
| 1713 * <pre> | 1832 * <pre> |
| 1714 * commentReference ::= | 1833 * commentReference ::= |
| 1715 * '\[' 'new'? qualified '\]' libraryReference? | 1834 * '[' 'new'? qualified ']' libraryReference? |
| 1835 * |
| 1716 * libraryReference ::= | 1836 * libraryReference ::= |
| 1717 * '(' stringLiteral ')' | 1837 * '(' stringLiteral ')' |
| 1718 * </pre> | 1838 * </pre> |
| 1839 * |
| 1719 * @param tokens the comment tokens representing the documentation comments to
be parsed | 1840 * @param tokens the comment tokens representing the documentation comments to
be parsed |
| 1720 * @return the comment references that were parsed | 1841 * @return the comment references that were parsed |
| 1721 */ | 1842 */ |
| 1722 List<CommentReference> parseCommentReferences(List<Token> tokens) { | 1843 List<CommentReference> parseCommentReferences(List<Token> tokens) { |
| 1723 List<CommentReference> references = new List<CommentReference>(); | 1844 List<CommentReference> references = new List<CommentReference>(); |
| 1724 for (Token token in tokens) { | 1845 for (Token token in tokens) { |
| 1725 String comment = token.lexeme; | 1846 String comment = token.lexeme; |
| 1726 int length = comment.length; | 1847 int length = comment.length; |
| 1727 List<List<int>> codeBlockRanges = getCodeBlockRanges(comment); | 1848 List<List<int>> codeBlockRanges = getCodeBlockRanges(comment); |
| 1728 int leftIndex = comment.indexOf('['); | 1849 int leftIndex = comment.indexOf('['); |
| (...skipping 21 matching lines...) Expand all Loading... |
| 1750 } | 1871 } |
| 1751 } | 1872 } |
| 1752 } | 1873 } |
| 1753 return references; | 1874 return references; |
| 1754 } | 1875 } |
| 1755 | 1876 |
| 1756 /** | 1877 /** |
| 1757 * Parse a compilation unit. | 1878 * Parse a compilation unit. |
| 1758 * | 1879 * |
| 1759 * Specified: | 1880 * Specified: |
| 1881 * |
| 1760 * <pre> | 1882 * <pre> |
| 1761 * compilationUnit ::= | 1883 * compilationUnit ::= |
| 1762 * scriptTag? directive* topLevelDeclaration | 1884 * scriptTag? directive* topLevelDeclaration* |
| 1763 * </pre> | 1885 * </pre> |
| 1764 * Actual: | 1886 * Actual: |
| 1887 * |
| 1765 * <pre> | 1888 * <pre> |
| 1766 * compilationUnit ::= | 1889 * compilationUnit ::= |
| 1767 * scriptTag? topLevelElement | 1890 * scriptTag? topLevelElement* |
| 1891 * |
| 1768 * topLevelElement ::= | 1892 * topLevelElement ::= |
| 1769 * directive | 1893 * directive |
| 1770 * | topLevelDeclaration | 1894 * | topLevelDeclaration |
| 1771 * </pre> | 1895 * </pre> |
| 1896 * |
| 1772 * @return the compilation unit that was parsed | 1897 * @return the compilation unit that was parsed |
| 1773 */ | 1898 */ |
| 1774 CompilationUnit parseCompilationUnit2() { | 1899 CompilationUnit parseCompilationUnit2() { |
| 1775 Token firstToken = _currentToken; | 1900 Token firstToken = _currentToken; |
| 1776 ScriptTag scriptTag = null; | 1901 ScriptTag scriptTag = null; |
| 1777 if (matches5(TokenType.SCRIPT_TAG)) { | 1902 if (matches5(TokenType.SCRIPT_TAG)) { |
| 1778 scriptTag = new ScriptTag.full(andAdvance); | 1903 scriptTag = new ScriptTag.full(andAdvance); |
| 1779 } | 1904 } |
| 1780 bool libraryDirectiveFound = false; | 1905 bool libraryDirectiveFound = false; |
| 1781 bool partOfDirectiveFound = false; | 1906 bool partOfDirectiveFound = false; |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1841 advance(); | 1966 advance(); |
| 1842 } | 1967 } |
| 1843 } | 1968 } |
| 1844 memberStart = _currentToken; | 1969 memberStart = _currentToken; |
| 1845 } | 1970 } |
| 1846 return new CompilationUnit.full(firstToken, scriptTag, directives, declarati
ons, _currentToken); | 1971 return new CompilationUnit.full(firstToken, scriptTag, directives, declarati
ons, _currentToken); |
| 1847 } | 1972 } |
| 1848 | 1973 |
| 1849 /** | 1974 /** |
| 1850 * Parse a compilation unit member. | 1975 * Parse a compilation unit member. |
| 1976 * |
| 1851 * <pre> | 1977 * <pre> |
| 1852 * compilationUnitMember ::= | 1978 * compilationUnitMember ::= |
| 1853 * classDefinition | 1979 * classDefinition |
| 1854 * | functionTypeAlias | 1980 * | functionTypeAlias |
| 1855 * | external functionSignature | 1981 * | external functionSignature |
| 1856 * | external getterSignature | 1982 * | external getterSignature |
| 1857 * | external setterSignature | 1983 * | external setterSignature |
| 1858 * | functionSignature functionBody | 1984 * | functionSignature functionBody |
| 1859 * | returnType? getOrSet identifier formalParameterList functionBody | 1985 * | returnType? getOrSet identifier formalParameterList functionBody |
| 1860 * | (final | const) type? staticFinalDeclarationList ';' | 1986 * | (final | const) type? staticFinalDeclarationList ';' |
| 1861 * | variableDeclaration ';' | 1987 * | variableDeclaration ';' |
| 1862 * </pre> | 1988 * </pre> |
| 1989 * |
| 1863 * @param commentAndMetadata the metadata to be associated with the member | 1990 * @param commentAndMetadata the metadata to be associated with the member |
| 1864 * @return the compilation unit member that was parsed, or `null` if what was
parsed could | 1991 * @return the compilation unit member that was parsed, or `null` if what was
parsed could |
| 1865 * not be represented as a compilation unit member | 1992 * not be represented as a compilation unit member |
| 1866 */ | 1993 */ |
| 1867 CompilationUnitMember parseCompilationUnitMember(CommentAndMetadata commentAnd
Metadata) { | 1994 CompilationUnitMember parseCompilationUnitMember(CommentAndMetadata commentAnd
Metadata) { |
| 1868 Modifiers modifiers = parseModifiers(); | 1995 Modifiers modifiers = parseModifiers(); |
| 1869 if (matches(Keyword.CLASS)) { | 1996 if (matches(Keyword.CLASS)) { |
| 1870 return parseClassDeclaration(commentAndMetadata, validateModifiersForClass
(modifiers)); | 1997 return parseClassDeclaration(commentAndMetadata, validateModifiersForClass
(modifiers)); |
| 1871 } else if (matches(Keyword.TYPEDEF) && !matches4(peek(), TokenType.PERIOD) &
& !matches4(peek(), TokenType.LT)) { | 1998 } else if (matches(Keyword.TYPEDEF) && !matches4(peek(), TokenType.PERIOD) &
& !matches4(peek(), TokenType.LT)) { |
| 1872 validateModifiersForTypedef(modifiers); | 1999 validateModifiersForTypedef(modifiers); |
| 1873 return parseTypeAlias(commentAndMetadata); | 2000 return parseTypeAlias(commentAndMetadata); |
| 1874 } | 2001 } |
| 1875 if (matches(Keyword.VOID)) { | 2002 if (matches(Keyword.VOID)) { |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1924 } | 2051 } |
| 1925 if (matchesAny(peek(), [TokenType.OPEN_PAREN, TokenType.FUNCTION, TokenType.
OPEN_CURLY_BRACKET])) { | 2052 if (matchesAny(peek(), [TokenType.OPEN_PAREN, TokenType.FUNCTION, TokenType.
OPEN_CURLY_BRACKET])) { |
| 1926 validateModifiersForTopLevelFunction(modifiers); | 2053 validateModifiersForTopLevelFunction(modifiers); |
| 1927 return parseFunctionDeclaration(commentAndMetadata, modifiers.externalKeyw
ord, returnType); | 2054 return parseFunctionDeclaration(commentAndMetadata, modifiers.externalKeyw
ord, returnType); |
| 1928 } | 2055 } |
| 1929 return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, comm
entAndMetadata.metadata, parseVariableDeclarationList2(null, validateModifiersFo
rTopLevelVariable(modifiers), returnType), expect2(TokenType.SEMICOLON)); | 2056 return new TopLevelVariableDeclaration.full(commentAndMetadata.comment, comm
entAndMetadata.metadata, parseVariableDeclarationList2(null, validateModifiersFo
rTopLevelVariable(modifiers), returnType), expect2(TokenType.SEMICOLON)); |
| 1930 } | 2057 } |
| 1931 | 2058 |
| 1932 /** | 2059 /** |
| 1933 * Parse a conditional expression. | 2060 * Parse a conditional expression. |
| 2061 * |
| 1934 * <pre> | 2062 * <pre> |
| 1935 * conditionalExpression ::= | 2063 * conditionalExpression ::= |
| 1936 * logicalOrExpression ('?' expressionWithoutCascade ':' expressionWithoutCasc
ade)? | 2064 * logicalOrExpression ('?' expressionWithoutCascade ':' expressionWithout
Cascade)? |
| 1937 * </pre> | 2065 * </pre> |
| 2066 * |
| 1938 * @return the conditional expression that was parsed | 2067 * @return the conditional expression that was parsed |
| 1939 */ | 2068 */ |
| 1940 Expression parseConditionalExpression() { | 2069 Expression parseConditionalExpression() { |
| 1941 Expression condition = parseLogicalOrExpression(); | 2070 Expression condition = parseLogicalOrExpression(); |
| 1942 if (!matches5(TokenType.QUESTION)) { | 2071 if (!matches5(TokenType.QUESTION)) { |
| 1943 return condition; | 2072 return condition; |
| 1944 } | 2073 } |
| 1945 Token question = andAdvance; | 2074 Token question = andAdvance; |
| 1946 Expression thenExpression = parseExpressionWithoutCascade(); | 2075 Expression thenExpression = parseExpressionWithoutCascade(); |
| 1947 Token colon = expect2(TokenType.COLON); | 2076 Token colon = expect2(TokenType.COLON); |
| 1948 Expression elseExpression = parseExpressionWithoutCascade(); | 2077 Expression elseExpression = parseExpressionWithoutCascade(); |
| 1949 return new ConditionalExpression.full(condition, question, thenExpression, c
olon, elseExpression); | 2078 return new ConditionalExpression.full(condition, question, thenExpression, c
olon, elseExpression); |
| 1950 } | 2079 } |
| 1951 | 2080 |
| 1952 /** | 2081 /** |
| 1953 * Parse a const expression. | 2082 * Parse a const expression. |
| 2083 * |
| 1954 * <pre> | 2084 * <pre> |
| 1955 * constExpression ::= | 2085 * constExpression ::= |
| 1956 * instanceCreationExpression | 2086 * instanceCreationExpression |
| 1957 * | listLiteral | 2087 * | listLiteral |
| 1958 * | mapLiteral | 2088 * | mapLiteral |
| 1959 * </pre> | 2089 * </pre> |
| 2090 * |
| 1960 * @return the const expression that was parsed | 2091 * @return the const expression that was parsed |
| 1961 */ | 2092 */ |
| 1962 Expression parseConstExpression() { | 2093 Expression parseConstExpression() { |
| 1963 Token keyword = expect(Keyword.CONST); | 2094 Token keyword = expect(Keyword.CONST); |
| 1964 if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.INDEX)) { | 2095 if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.INDEX)) { |
| 1965 return parseListLiteral(keyword, null); | 2096 return parseListLiteral(keyword, null); |
| 1966 } else if (matches5(TokenType.OPEN_CURLY_BRACKET)) { | 2097 } else if (matches5(TokenType.OPEN_CURLY_BRACKET)) { |
| 1967 return parseMapLiteral(keyword, null); | 2098 return parseMapLiteral(keyword, null); |
| 1968 } else if (matches5(TokenType.LT)) { | 2099 } else if (matches5(TokenType.LT)) { |
| 1969 return parseListOrMapLiteral(keyword); | 2100 return parseListOrMapLiteral(keyword); |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2015 } else if (!bodyAllowed) { | 2146 } else if (!bodyAllowed) { |
| 2016 reportError(ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY, body, []); | 2147 reportError(ParserErrorCode.EXTERNAL_CONSTRUCTOR_WITH_BODY, body, []); |
| 2017 } | 2148 } |
| 2018 } | 2149 } |
| 2019 } | 2150 } |
| 2020 return new ConstructorDeclaration.full(commentAndMetadata.comment, commentAn
dMetadata.metadata, externalKeyword, constKeyword, factoryKeyword, returnType, p
eriod, name, parameters, separator, initializers, redirectedConstructor, body); | 2151 return new ConstructorDeclaration.full(commentAndMetadata.comment, commentAn
dMetadata.metadata, externalKeyword, constKeyword, factoryKeyword, returnType, p
eriod, name, parameters, separator, initializers, redirectedConstructor, body); |
| 2021 } | 2152 } |
| 2022 | 2153 |
| 2023 /** | 2154 /** |
| 2024 * Parse a field initializer within a constructor. | 2155 * Parse a field initializer within a constructor. |
| 2156 * |
| 2025 * <pre> | 2157 * <pre> |
| 2026 * fieldInitializer: | 2158 * fieldInitializer: |
| 2027 * ('this' '.')? identifier '=' conditionalExpression cascadeSection | 2159 * ('this' '.')? identifier '=' conditionalExpression cascadeSection* |
| 2028 * </pre> | 2160 * </pre> |
| 2161 * |
| 2029 * @return the field initializer that was parsed | 2162 * @return the field initializer that was parsed |
| 2030 */ | 2163 */ |
| 2031 ConstructorFieldInitializer parseConstructorFieldInitializer() { | 2164 ConstructorFieldInitializer parseConstructorFieldInitializer() { |
| 2032 Token keyword = null; | 2165 Token keyword = null; |
| 2033 Token period = null; | 2166 Token period = null; |
| 2034 if (matches(Keyword.THIS)) { | 2167 if (matches(Keyword.THIS)) { |
| 2035 keyword = andAdvance; | 2168 keyword = andAdvance; |
| 2036 period = expect2(TokenType.PERIOD); | 2169 period = expect2(TokenType.PERIOD); |
| 2037 } | 2170 } |
| 2038 SimpleIdentifier fieldName = parseSimpleIdentifier(); | 2171 SimpleIdentifier fieldName = parseSimpleIdentifier(); |
| 2039 Token equals = expect2(TokenType.EQ); | 2172 Token equals = expect2(TokenType.EQ); |
| 2040 Expression expression = parseConditionalExpression(); | 2173 Expression expression = parseConditionalExpression(); |
| 2041 TokenType tokenType = _currentToken.type; | 2174 TokenType tokenType = _currentToken.type; |
| 2042 if (identical(tokenType, TokenType.PERIOD_PERIOD)) { | 2175 if (identical(tokenType, TokenType.PERIOD_PERIOD)) { |
| 2043 List<Expression> cascadeSections = new List<Expression>(); | 2176 List<Expression> cascadeSections = new List<Expression>(); |
| 2044 while (identical(tokenType, TokenType.PERIOD_PERIOD)) { | 2177 while (identical(tokenType, TokenType.PERIOD_PERIOD)) { |
| 2045 Expression section = parseCascadeSection(); | 2178 Expression section = parseCascadeSection(); |
| 2046 if (section != null) { | 2179 if (section != null) { |
| 2047 cascadeSections.add(section); | 2180 cascadeSections.add(section); |
| 2048 } | 2181 } |
| 2049 tokenType = _currentToken.type; | 2182 tokenType = _currentToken.type; |
| 2050 } | 2183 } |
| 2051 expression = new CascadeExpression.full(expression, cascadeSections); | 2184 expression = new CascadeExpression.full(expression, cascadeSections); |
| 2052 } | 2185 } |
| 2053 return new ConstructorFieldInitializer.full(keyword, period, fieldName, equa
ls, expression); | 2186 return new ConstructorFieldInitializer.full(keyword, period, fieldName, equa
ls, expression); |
| 2054 } | 2187 } |
| 2055 | 2188 |
| 2056 /** | 2189 /** |
| 2057 * Parse the name of a constructor. | 2190 * Parse the name of a constructor. |
| 2191 * |
| 2058 * <pre> | 2192 * <pre> |
| 2059 * constructorName: | 2193 * constructorName: |
| 2060 * type ('.' identifier)? | 2194 * type ('.' identifier)? |
| 2061 * </pre> | 2195 * </pre> |
| 2196 * |
| 2062 * @return the constructor name that was parsed | 2197 * @return the constructor name that was parsed |
| 2063 */ | 2198 */ |
| 2064 ConstructorName parseConstructorName() { | 2199 ConstructorName parseConstructorName() { |
| 2065 TypeName type = parseTypeName(); | 2200 TypeName type = parseTypeName(); |
| 2066 Token period = null; | 2201 Token period = null; |
| 2067 SimpleIdentifier name = null; | 2202 SimpleIdentifier name = null; |
| 2068 if (matches5(TokenType.PERIOD)) { | 2203 if (matches5(TokenType.PERIOD)) { |
| 2069 period = andAdvance; | 2204 period = andAdvance; |
| 2070 name = parseSimpleIdentifier(); | 2205 name = parseSimpleIdentifier(); |
| 2071 } | 2206 } |
| 2072 return new ConstructorName.full(type, period, name); | 2207 return new ConstructorName.full(type, period, name); |
| 2073 } | 2208 } |
| 2074 | 2209 |
| 2075 /** | 2210 /** |
| 2076 * Parse a continue statement. | 2211 * Parse a continue statement. |
| 2212 * |
| 2077 * <pre> | 2213 * <pre> |
| 2078 * continueStatement ::= | 2214 * continueStatement ::= |
| 2079 * 'continue' identifier? ';' | 2215 * 'continue' identifier? ';' |
| 2080 * </pre> | 2216 * </pre> |
| 2217 * |
| 2081 * @return the continue statement that was parsed | 2218 * @return the continue statement that was parsed |
| 2082 */ | 2219 */ |
| 2083 Statement parseContinueStatement() { | 2220 Statement parseContinueStatement() { |
| 2084 Token continueKeyword = expect(Keyword.CONTINUE); | 2221 Token continueKeyword = expect(Keyword.CONTINUE); |
| 2085 if (!_inLoop && !_inSwitch) { | 2222 if (!_inLoop && !_inSwitch) { |
| 2086 reportError8(ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP, continueKeyword, []
); | 2223 reportError8(ParserErrorCode.CONTINUE_OUTSIDE_OF_LOOP, continueKeyword, []
); |
| 2087 } | 2224 } |
| 2088 SimpleIdentifier label = null; | 2225 SimpleIdentifier label = null; |
| 2089 if (matchesIdentifier()) { | 2226 if (matchesIdentifier()) { |
| 2090 label = parseSimpleIdentifier(); | 2227 label = parseSimpleIdentifier(); |
| 2091 } | 2228 } |
| 2092 if (_inSwitch && !_inLoop && label == null) { | 2229 if (_inSwitch && !_inLoop && label == null) { |
| 2093 reportError8(ParserErrorCode.CONTINUE_WITHOUT_LABEL_IN_CASE, continueKeywo
rd, []); | 2230 reportError8(ParserErrorCode.CONTINUE_WITHOUT_LABEL_IN_CASE, continueKeywo
rd, []); |
| 2094 } | 2231 } |
| 2095 Token semicolon = expect2(TokenType.SEMICOLON); | 2232 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2096 return new ContinueStatement.full(continueKeyword, label, semicolon); | 2233 return new ContinueStatement.full(continueKeyword, label, semicolon); |
| 2097 } | 2234 } |
| 2098 | 2235 |
| 2099 /** | 2236 /** |
| 2100 * Parse a directive. | 2237 * Parse a directive. |
| 2238 * |
| 2101 * <pre> | 2239 * <pre> |
| 2102 * directive ::= | 2240 * directive ::= |
| 2103 * exportDirective | 2241 * exportDirective |
| 2104 * | libraryDirective | 2242 * | libraryDirective |
| 2105 * | importDirective | 2243 * | importDirective |
| 2106 * | partDirective | 2244 * | partDirective |
| 2107 * </pre> | 2245 * </pre> |
| 2246 * |
| 2108 * @param commentAndMetadata the metadata to be associated with the directive | 2247 * @param commentAndMetadata the metadata to be associated with the directive |
| 2109 * @return the directive that was parsed | 2248 * @return the directive that was parsed |
| 2110 */ | 2249 */ |
| 2111 Directive parseDirective(CommentAndMetadata commentAndMetadata) { | 2250 Directive parseDirective(CommentAndMetadata commentAndMetadata) { |
| 2112 if (matches(Keyword.IMPORT)) { | 2251 if (matches(Keyword.IMPORT)) { |
| 2113 return parseImportDirective(commentAndMetadata); | 2252 return parseImportDirective(commentAndMetadata); |
| 2114 } else if (matches(Keyword.EXPORT)) { | 2253 } else if (matches(Keyword.EXPORT)) { |
| 2115 return parseExportDirective(commentAndMetadata); | 2254 return parseExportDirective(commentAndMetadata); |
| 2116 } else if (matches(Keyword.LIBRARY)) { | 2255 } else if (matches(Keyword.LIBRARY)) { |
| 2117 return parseLibraryDirective(commentAndMetadata); | 2256 return parseLibraryDirective(commentAndMetadata); |
| 2118 } else if (matches(Keyword.PART)) { | 2257 } else if (matches(Keyword.PART)) { |
| 2119 return parsePartDirective(commentAndMetadata); | 2258 return parsePartDirective(commentAndMetadata); |
| 2120 } else { | 2259 } else { |
| 2121 throw new IllegalStateException("parseDirective invoked in an invalid stat
e; currentToken = ${_currentToken}"); | 2260 throw new IllegalStateException("parseDirective invoked in an invalid stat
e; currentToken = ${_currentToken}"); |
| 2122 } | 2261 } |
| 2123 } | 2262 } |
| 2124 | 2263 |
| 2125 /** | 2264 /** |
| 2126 * Parse a documentation comment. | 2265 * Parse a documentation comment. |
| 2266 * |
| 2127 * <pre> | 2267 * <pre> |
| 2128 * documentationComment ::= | 2268 * documentationComment ::= |
| 2129 * multiLineComment? | 2269 * multiLineComment? |
| 2130 * | singleLineComment | 2270 * | singleLineComment* |
| 2131 * </pre> | 2271 * </pre> |
| 2272 * |
| 2132 * @return the documentation comment that was parsed, or `null` if there was n
o comment | 2273 * @return the documentation comment that was parsed, or `null` if there was n
o comment |
| 2133 */ | 2274 */ |
| 2134 Comment parseDocumentationComment() { | 2275 Comment parseDocumentationComment() { |
| 2135 List<Token> commentTokens = new List<Token>(); | 2276 List<Token> commentTokens = new List<Token>(); |
| 2136 Token commentToken = _currentToken.precedingComments; | 2277 Token commentToken = _currentToken.precedingComments; |
| 2137 while (commentToken != null) { | 2278 while (commentToken != null) { |
| 2138 if (identical(commentToken.type, TokenType.SINGLE_LINE_COMMENT)) { | 2279 if (identical(commentToken.type, TokenType.SINGLE_LINE_COMMENT)) { |
| 2139 if (commentToken.lexeme.startsWith("///")) { | 2280 if (commentToken.lexeme.startsWith("///")) { |
| 2140 if (commentTokens.length == 1 && commentTokens[0].lexeme.startsWith("/
**")) { | 2281 if (commentTokens.length == 1 && commentTokens[0].lexeme.startsWith("/
**")) { |
| 2141 commentTokens.clear(); | 2282 commentTokens.clear(); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 2153 if (commentTokens.isEmpty) { | 2294 if (commentTokens.isEmpty) { |
| 2154 return null; | 2295 return null; |
| 2155 } | 2296 } |
| 2156 List<Token> tokens = new List.from(commentTokens); | 2297 List<Token> tokens = new List.from(commentTokens); |
| 2157 List<CommentReference> references = parseCommentReferences(tokens); | 2298 List<CommentReference> references = parseCommentReferences(tokens); |
| 2158 return Comment.createDocumentationComment2(tokens, references); | 2299 return Comment.createDocumentationComment2(tokens, references); |
| 2159 } | 2300 } |
| 2160 | 2301 |
| 2161 /** | 2302 /** |
| 2162 * Parse a do statement. | 2303 * Parse a do statement. |
| 2304 * |
| 2163 * <pre> | 2305 * <pre> |
| 2164 * doStatement ::= | 2306 * doStatement ::= |
| 2165 * 'do' statement 'while' '(' expression ')' ';' | 2307 * 'do' statement 'while' '(' expression ')' ';' |
| 2166 * </pre> | 2308 * </pre> |
| 2309 * |
| 2167 * @return the do statement that was parsed | 2310 * @return the do statement that was parsed |
| 2168 */ | 2311 */ |
| 2169 Statement parseDoStatement() { | 2312 Statement parseDoStatement() { |
| 2170 bool wasInLoop = _inLoop; | 2313 bool wasInLoop = _inLoop; |
| 2171 _inLoop = true; | 2314 _inLoop = true; |
| 2172 try { | 2315 try { |
| 2173 Token doKeyword = expect(Keyword.DO); | 2316 Token doKeyword = expect(Keyword.DO); |
| 2174 Statement body = parseStatement2(); | 2317 Statement body = parseStatement2(); |
| 2175 Token whileKeyword = expect(Keyword.WHILE); | 2318 Token whileKeyword = expect(Keyword.WHILE); |
| 2176 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 2319 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 2177 Expression condition = parseExpression2(); | 2320 Expression condition = parseExpression2(); |
| 2178 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); | 2321 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); |
| 2179 Token semicolon = expect2(TokenType.SEMICOLON); | 2322 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2180 return new DoStatement.full(doKeyword, body, whileKeyword, leftParenthesis
, condition, rightParenthesis, semicolon); | 2323 return new DoStatement.full(doKeyword, body, whileKeyword, leftParenthesis
, condition, rightParenthesis, semicolon); |
| 2181 } finally { | 2324 } finally { |
| 2182 _inLoop = wasInLoop; | 2325 _inLoop = wasInLoop; |
| 2183 } | 2326 } |
| 2184 } | 2327 } |
| 2185 | 2328 |
| 2186 /** | 2329 /** |
| 2187 * Parse an empty statement. | 2330 * Parse an empty statement. |
| 2331 * |
| 2188 * <pre> | 2332 * <pre> |
| 2189 * emptyStatement ::= | 2333 * emptyStatement ::= |
| 2190 * ';' | 2334 * ';' |
| 2191 * </pre> | 2335 * </pre> |
| 2336 * |
| 2192 * @return the empty statement that was parsed | 2337 * @return the empty statement that was parsed |
| 2193 */ | 2338 */ |
| 2194 Statement parseEmptyStatement() => new EmptyStatement.full(andAdvance); | 2339 Statement parseEmptyStatement() => new EmptyStatement.full(andAdvance); |
| 2195 | 2340 |
| 2196 /** | 2341 /** |
| 2197 * Parse an equality expression. | 2342 * Parse an equality expression. |
| 2343 * |
| 2198 * <pre> | 2344 * <pre> |
| 2199 * equalityExpression ::= | 2345 * equalityExpression ::= |
| 2200 * relationalExpression (equalityOperator relationalExpression)? | 2346 * relationalExpression (equalityOperator relationalExpression)? |
| 2201 * | 'super' equalityOperator relationalExpression | 2347 * | 'super' equalityOperator relationalExpression |
| 2202 * </pre> | 2348 * </pre> |
| 2349 * |
| 2203 * @return the equality expression that was parsed | 2350 * @return the equality expression that was parsed |
| 2204 */ | 2351 */ |
| 2205 Expression parseEqualityExpression() { | 2352 Expression parseEqualityExpression() { |
| 2206 Expression expression; | 2353 Expression expression; |
| 2207 if (matches(Keyword.SUPER) && _currentToken.next.type.isEqualityOperator) { | 2354 if (matches(Keyword.SUPER) && _currentToken.next.type.isEqualityOperator) { |
| 2208 expression = new SuperExpression.full(andAdvance); | 2355 expression = new SuperExpression.full(andAdvance); |
| 2209 } else { | 2356 } else { |
| 2210 expression = parseRelationalExpression(); | 2357 expression = parseRelationalExpression(); |
| 2211 } | 2358 } |
| 2212 while (_currentToken.type.isEqualityOperator) { | 2359 while (_currentToken.type.isEqualityOperator) { |
| 2213 Token operator = andAdvance; | 2360 Token operator = andAdvance; |
| 2214 expression = new BinaryExpression.full(expression, operator, parseRelation
alExpression()); | 2361 expression = new BinaryExpression.full(expression, operator, parseRelation
alExpression()); |
| 2215 } | 2362 } |
| 2216 return expression; | 2363 return expression; |
| 2217 } | 2364 } |
| 2218 | 2365 |
| 2219 /** | 2366 /** |
| 2220 * Parse an export directive. | 2367 * Parse an export directive. |
| 2368 * |
| 2221 * <pre> | 2369 * <pre> |
| 2222 * exportDirective ::= | 2370 * exportDirective ::= |
| 2223 * metadata 'export' stringLiteral combinator*';' | 2371 * metadata 'export' stringLiteral combinator*';' |
| 2224 * </pre> | 2372 * </pre> |
| 2373 * |
| 2225 * @param commentAndMetadata the metadata to be associated with the directive | 2374 * @param commentAndMetadata the metadata to be associated with the directive |
| 2226 * @return the export directive that was parsed | 2375 * @return the export directive that was parsed |
| 2227 */ | 2376 */ |
| 2228 ExportDirective parseExportDirective(CommentAndMetadata commentAndMetadata) { | 2377 ExportDirective parseExportDirective(CommentAndMetadata commentAndMetadata) { |
| 2229 Token exportKeyword = expect(Keyword.EXPORT); | 2378 Token exportKeyword = expect(Keyword.EXPORT); |
| 2230 StringLiteral libraryUri = parseStringLiteral(); | 2379 StringLiteral libraryUri = parseStringLiteral(); |
| 2231 List<Combinator> combinators = parseCombinators(); | 2380 List<Combinator> combinators = parseCombinators(); |
| 2232 Token semicolon = expect2(TokenType.SEMICOLON); | 2381 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2233 return new ExportDirective.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, exportKeyword, libraryUri, combinators, semicolon); | 2382 return new ExportDirective.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, exportKeyword, libraryUri, combinators, semicolon); |
| 2234 } | 2383 } |
| 2235 | 2384 |
| 2236 /** | 2385 /** |
| 2237 * Parse an expression that does not contain any cascades. | 2386 * Parse an expression that does not contain any cascades. |
| 2387 * |
| 2238 * <pre> | 2388 * <pre> |
| 2239 * expression ::= | 2389 * expression ::= |
| 2240 * assignableExpression assignmentOperator expression | 2390 * assignableExpression assignmentOperator expression |
| 2241 * | conditionalExpression cascadeSection | 2391 * | conditionalExpression cascadeSection* |
| 2242 * | throwExpression | 2392 * | throwExpression |
| 2243 * </pre> | 2393 * </pre> |
| 2394 * |
| 2244 * @return the expression that was parsed | 2395 * @return the expression that was parsed |
| 2245 */ | 2396 */ |
| 2246 Expression parseExpression2() { | 2397 Expression parseExpression2() { |
| 2247 if (matches(Keyword.THROW)) { | 2398 if (matches(Keyword.THROW)) { |
| 2248 return parseThrowExpression(); | 2399 return parseThrowExpression(); |
| 2249 } else if (matches(Keyword.RETHROW)) { | 2400 } else if (matches(Keyword.RETHROW)) { |
| 2250 return parseRethrowExpression(); | 2401 return parseRethrowExpression(); |
| 2251 } | 2402 } |
| 2252 Expression expression = parseConditionalExpression(); | 2403 Expression expression = parseConditionalExpression(); |
| 2253 TokenType tokenType = _currentToken.type; | 2404 TokenType tokenType = _currentToken.type; |
| (...skipping 10 matching lines...) Expand all Loading... |
| 2264 } else if (tokenType.isAssignmentOperator) { | 2415 } else if (tokenType.isAssignmentOperator) { |
| 2265 Token operator = andAdvance; | 2416 Token operator = andAdvance; |
| 2266 ensureAssignable(expression); | 2417 ensureAssignable(expression); |
| 2267 return new AssignmentExpression.full(expression, operator, parseExpression
2()); | 2418 return new AssignmentExpression.full(expression, operator, parseExpression
2()); |
| 2268 } | 2419 } |
| 2269 return expression; | 2420 return expression; |
| 2270 } | 2421 } |
| 2271 | 2422 |
| 2272 /** | 2423 /** |
| 2273 * Parse a list of expressions. | 2424 * Parse a list of expressions. |
| 2425 * |
| 2274 * <pre> | 2426 * <pre> |
| 2275 * expressionList ::= | 2427 * expressionList ::= |
| 2276 * expression (',' expression) | 2428 * expression (',' expression)* |
| 2277 * </pre> | 2429 * </pre> |
| 2430 * |
| 2278 * @return the expression that was parsed | 2431 * @return the expression that was parsed |
| 2279 */ | 2432 */ |
| 2280 List<Expression> parseExpressionList() { | 2433 List<Expression> parseExpressionList() { |
| 2281 List<Expression> expressions = new List<Expression>(); | 2434 List<Expression> expressions = new List<Expression>(); |
| 2282 expressions.add(parseExpression2()); | 2435 expressions.add(parseExpression2()); |
| 2283 while (optional(TokenType.COMMA)) { | 2436 while (optional(TokenType.COMMA)) { |
| 2284 expressions.add(parseExpression2()); | 2437 expressions.add(parseExpression2()); |
| 2285 } | 2438 } |
| 2286 return expressions; | 2439 return expressions; |
| 2287 } | 2440 } |
| 2288 | 2441 |
| 2289 /** | 2442 /** |
| 2290 * Parse an expression that does not contain any cascades. | 2443 * Parse an expression that does not contain any cascades. |
| 2444 * |
| 2291 * <pre> | 2445 * <pre> |
| 2292 * expressionWithoutCascade ::= | 2446 * expressionWithoutCascade ::= |
| 2293 * assignableExpression assignmentOperator expressionWithoutCascade | 2447 * assignableExpression assignmentOperator expressionWithoutCascade |
| 2294 * | conditionalExpression | 2448 * | conditionalExpression |
| 2295 * | throwExpressionWithoutCascade | 2449 * | throwExpressionWithoutCascade |
| 2296 * </pre> | 2450 * </pre> |
| 2451 * |
| 2297 * @return the expression that was parsed | 2452 * @return the expression that was parsed |
| 2298 */ | 2453 */ |
| 2299 Expression parseExpressionWithoutCascade() { | 2454 Expression parseExpressionWithoutCascade() { |
| 2300 if (matches(Keyword.THROW)) { | 2455 if (matches(Keyword.THROW)) { |
| 2301 return parseThrowExpressionWithoutCascade(); | 2456 return parseThrowExpressionWithoutCascade(); |
| 2302 } else if (matches(Keyword.RETHROW)) { | 2457 } else if (matches(Keyword.RETHROW)) { |
| 2303 return parseRethrowExpression(); | 2458 return parseRethrowExpression(); |
| 2304 } | 2459 } |
| 2305 Expression expression = parseConditionalExpression(); | 2460 Expression expression = parseConditionalExpression(); |
| 2306 if (_currentToken.type.isAssignmentOperator) { | 2461 if (_currentToken.type.isAssignmentOperator) { |
| 2307 Token operator = andAdvance; | 2462 Token operator = andAdvance; |
| 2308 ensureAssignable(expression); | 2463 ensureAssignable(expression); |
| 2309 expression = new AssignmentExpression.full(expression, operator, parseExpr
essionWithoutCascade()); | 2464 expression = new AssignmentExpression.full(expression, operator, parseExpr
essionWithoutCascade()); |
| 2310 } | 2465 } |
| 2311 return expression; | 2466 return expression; |
| 2312 } | 2467 } |
| 2313 | 2468 |
| 2314 /** | 2469 /** |
| 2315 * Parse a class extends clause. | 2470 * Parse a class extends clause. |
| 2471 * |
| 2316 * <pre> | 2472 * <pre> |
| 2317 * classExtendsClause ::= | 2473 * classExtendsClause ::= |
| 2318 * 'extends' type | 2474 * 'extends' type |
| 2319 * </pre> | 2475 * </pre> |
| 2476 * |
| 2320 * @return the class extends clause that was parsed | 2477 * @return the class extends clause that was parsed |
| 2321 */ | 2478 */ |
| 2322 ExtendsClause parseExtendsClause() { | 2479 ExtendsClause parseExtendsClause() { |
| 2323 Token keyword = expect(Keyword.EXTENDS); | 2480 Token keyword = expect(Keyword.EXTENDS); |
| 2324 TypeName superclass = parseTypeName(); | 2481 TypeName superclass = parseTypeName(); |
| 2325 return new ExtendsClause.full(keyword, superclass); | 2482 return new ExtendsClause.full(keyword, superclass); |
| 2326 } | 2483 } |
| 2327 | 2484 |
| 2328 /** | 2485 /** |
| 2329 * Parse the 'final', 'const', 'var' or type preceding a variable declaration. | 2486 * Parse the 'final', 'const', 'var' or type preceding a variable declaration. |
| 2487 * |
| 2330 * <pre> | 2488 * <pre> |
| 2331 * finalConstVarOrType ::= | 2489 * finalConstVarOrType ::= |
| 2332 * | 'final' type? | 2490 * | 'final' type? |
| 2333 * | 'const' type? | 2491 * | 'const' type? |
| 2334 * | 'var' | 2492 * | 'var' |
| 2335 * | type | 2493 * | type |
| 2336 * </pre> | 2494 * </pre> |
| 2495 * |
| 2337 * @param optional `true` if the keyword and type are optional | 2496 * @param optional `true` if the keyword and type are optional |
| 2338 * @return the 'final', 'const', 'var' or type that was parsed | 2497 * @return the 'final', 'const', 'var' or type that was parsed |
| 2339 */ | 2498 */ |
| 2340 FinalConstVarOrType parseFinalConstVarOrType(bool optional) { | 2499 FinalConstVarOrType parseFinalConstVarOrType(bool optional) { |
| 2341 Token keyword = null; | 2500 Token keyword = null; |
| 2342 TypeName type = null; | 2501 TypeName type = null; |
| 2343 if (matches(Keyword.FINAL) || matches(Keyword.CONST)) { | 2502 if (matches(Keyword.FINAL) || matches(Keyword.CONST)) { |
| 2344 keyword = andAdvance; | 2503 keyword = andAdvance; |
| 2345 if (matchesIdentifier2(peek()) || matches4(peek(), TokenType.LT) || matche
s3(peek(), Keyword.THIS) || (matches4(peek(), TokenType.PERIOD) && matchesIdenti
fier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3), TokenType
.LT) || matches3(peek2(3), Keyword.THIS)))) { | 2504 if (matchesIdentifier2(peek()) || matches4(peek(), TokenType.LT) || matche
s3(peek(), Keyword.THIS) || (matches4(peek(), TokenType.PERIOD) && matchesIdenti
fier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3), TokenType
.LT) || matches3(peek2(3), Keyword.THIS)))) { |
| 2346 type = parseTypeName(); | 2505 type = parseTypeName(); |
| 2347 } | 2506 } |
| 2348 } else if (matches(Keyword.VAR)) { | 2507 } else if (matches(Keyword.VAR)) { |
| 2349 keyword = andAdvance; | 2508 keyword = andAdvance; |
| 2350 } else { | 2509 } else { |
| 2351 if (matchesIdentifier2(peek()) || matches4(peek(), TokenType.LT) || matche
s3(peek(), Keyword.THIS) || (matches4(peek(), TokenType.PERIOD) && matchesIdenti
fier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3), TokenType
.LT) || matches3(peek2(3), Keyword.THIS)))) { | 2510 if (matchesIdentifier2(peek()) || matches4(peek(), TokenType.LT) || matche
s3(peek(), Keyword.THIS) || (matches4(peek(), TokenType.PERIOD) && matchesIdenti
fier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3), TokenType
.LT) || matches3(peek2(3), Keyword.THIS)))) { |
| 2352 type = parseReturnType(); | 2511 type = parseReturnType(); |
| 2353 } else if (!optional) { | 2512 } else if (!optional) { |
| 2354 reportError7(ParserErrorCode.MISSING_CONST_FINAL_VAR_OR_TYPE, []); | 2513 reportError7(ParserErrorCode.MISSING_CONST_FINAL_VAR_OR_TYPE, []); |
| 2355 } | 2514 } |
| 2356 } | 2515 } |
| 2357 return new FinalConstVarOrType(keyword, type); | 2516 return new FinalConstVarOrType(keyword, type); |
| 2358 } | 2517 } |
| 2359 | 2518 |
| 2360 /** | 2519 /** |
| 2361 * Parse a formal parameter. At most one of `isOptional` and `isNamed` can be`
true`. | 2520 * Parse a formal parameter. At most one of `isOptional` and `isNamed` can be |
| 2521 * `true`. |
| 2522 * |
| 2362 * <pre> | 2523 * <pre> |
| 2363 * defaultFormalParameter ::= | 2524 * defaultFormalParameter ::= |
| 2364 * normalFormalParameter ('=' expression)? | 2525 * normalFormalParameter ('=' expression)? |
| 2526 * |
| 2365 * defaultNamedParameter ::= | 2527 * defaultNamedParameter ::= |
| 2366 * normalFormalParameter (':' expression)? | 2528 * normalFormalParameter (':' expression)? |
| 2367 * </pre> | 2529 * </pre> |
| 2530 * |
| 2368 * @param kind the kind of parameter being expected based on the presence or a
bsence of group | 2531 * @param kind the kind of parameter being expected based on the presence or a
bsence of group |
| 2369 * delimiters | 2532 * delimiters |
| 2370 * @return the formal parameter that was parsed | 2533 * @return the formal parameter that was parsed |
| 2371 */ | 2534 */ |
| 2372 FormalParameter parseFormalParameter(ParameterKind kind) { | 2535 FormalParameter parseFormalParameter(ParameterKind kind) { |
| 2373 NormalFormalParameter parameter = parseNormalFormalParameter(); | 2536 NormalFormalParameter parameter = parseNormalFormalParameter(); |
| 2374 if (matches5(TokenType.EQ)) { | 2537 if (matches5(TokenType.EQ)) { |
| 2375 Token seperator = andAdvance; | 2538 Token seperator = andAdvance; |
| 2376 Expression defaultValue = parseExpression2(); | 2539 Expression defaultValue = parseExpression2(); |
| 2377 if (identical(kind, ParameterKind.NAMED)) { | 2540 if (identical(kind, ParameterKind.NAMED)) { |
| 2378 reportError8(ParserErrorCode.WRONG_SEPARATOR_FOR_NAMED_PARAMETER, sepera
tor, []); | 2541 reportError8(ParserErrorCode.WRONG_SEPARATOR_FOR_NAMED_PARAMETER, sepera
tor, []); |
| 2379 } else if (identical(kind, ParameterKind.REQUIRED)) { | 2542 } else if (identical(kind, ParameterKind.REQUIRED)) { |
| (...skipping 10 matching lines...) Expand all Loading... |
| 2390 } | 2553 } |
| 2391 return new DefaultFormalParameter.full(parameter, kind, seperator, default
Value); | 2554 return new DefaultFormalParameter.full(parameter, kind, seperator, default
Value); |
| 2392 } else if (kind != ParameterKind.REQUIRED) { | 2555 } else if (kind != ParameterKind.REQUIRED) { |
| 2393 return new DefaultFormalParameter.full(parameter, kind, null, null); | 2556 return new DefaultFormalParameter.full(parameter, kind, null, null); |
| 2394 } | 2557 } |
| 2395 return parameter; | 2558 return parameter; |
| 2396 } | 2559 } |
| 2397 | 2560 |
| 2398 /** | 2561 /** |
| 2399 * Parse a list of formal parameters. | 2562 * Parse a list of formal parameters. |
| 2563 * |
| 2400 * <pre> | 2564 * <pre> |
| 2401 * formalParameterList ::= | 2565 * formalParameterList ::= |
| 2402 * '(' ')' | 2566 * '(' ')' |
| 2403 * | '(' normalFormalParameters (',' optionalFormalParameters)? ')' | 2567 * | '(' normalFormalParameters (',' optionalFormalParameters)? ')' |
| 2404 * | '(' optionalFormalParameters ')' | 2568 * | '(' optionalFormalParameters ')' |
| 2569 * |
| 2405 * normalFormalParameters ::= | 2570 * normalFormalParameters ::= |
| 2406 * normalFormalParameter (',' normalFormalParameter) | 2571 * normalFormalParameter (',' normalFormalParameter)* |
| 2572 * |
| 2407 * optionalFormalParameters ::= | 2573 * optionalFormalParameters ::= |
| 2408 * optionalPositionalFormalParameters | 2574 * optionalPositionalFormalParameters |
| 2409 * | namedFormalParameters | 2575 * | namedFormalParameters |
| 2576 * |
| 2410 * optionalPositionalFormalParameters ::= | 2577 * optionalPositionalFormalParameters ::= |
| 2411 * '\[' defaultFormalParameter (',' defaultFormalParameter)* '\]' | 2578 * '[' defaultFormalParameter (',' defaultFormalParameter)* ']' |
| 2579 * |
| 2412 * namedFormalParameters ::= | 2580 * namedFormalParameters ::= |
| 2413 * '{' defaultNamedParameter (',' defaultNamedParameter)* '}' | 2581 * '{' defaultNamedParameter (',' defaultNamedParameter)* '}' |
| 2414 * </pre> | 2582 * </pre> |
| 2583 * |
| 2415 * @return the formal parameters that were parsed | 2584 * @return the formal parameters that were parsed |
| 2416 */ | 2585 */ |
| 2417 FormalParameterList parseFormalParameterList() { | 2586 FormalParameterList parseFormalParameterList() { |
| 2418 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 2587 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 2419 if (matches5(TokenType.CLOSE_PAREN)) { | 2588 if (matches5(TokenType.CLOSE_PAREN)) { |
| 2420 return new FormalParameterList.full(leftParenthesis, null, null, null, and
Advance); | 2589 return new FormalParameterList.full(leftParenthesis, null, null, null, and
Advance); |
| 2421 } | 2590 } |
| 2422 List<FormalParameter> parameters = new List<FormalParameter>(); | 2591 List<FormalParameter> parameters = new List<FormalParameter>(); |
| 2423 List<FormalParameter> normalParameters = new List<FormalParameter>(); | 2592 List<FormalParameter> normalParameters = new List<FormalParameter>(); |
| 2424 List<FormalParameter> positionalParameters = new List<FormalParameter>(); | 2593 List<FormalParameter> positionalParameters = new List<FormalParameter>(); |
| 2425 List<FormalParameter> namedParameters = new List<FormalParameter>(); | 2594 List<FormalParameter> namedParameters = new List<FormalParameter>(); |
| 2426 List<FormalParameter> currentParameters = normalParameters; | 2595 List<FormalParameter> currentParameters = normalParameters; |
| 2427 Token leftSquareBracket = null; | 2596 Token leftSquareBracket = null; |
| 2428 Token rightSquareBracket = null; | 2597 Token rightSquareBracket = null; |
| 2429 Token leftCurlyBracket = null; | 2598 Token leftCurlyBracket = null; |
| 2430 Token rightCurlyBracket = null; | 2599 Token rightCurlyBracket = null; |
| 2431 ParameterKind kind = ParameterKind.REQUIRED; | 2600 ParameterKind kind = ParameterKind.REQUIRED; |
| 2432 bool firstParameter = true; | 2601 bool firstParameter = true; |
| 2433 bool reportedMuliplePositionalGroups = false; | 2602 bool reportedMuliplePositionalGroups = false; |
| 2434 bool reportedMulipleNamedGroups = false; | 2603 bool reportedMulipleNamedGroups = false; |
| 2435 bool reportedMixedGroups = false; | 2604 bool reportedMixedGroups = false; |
| 2605 bool wasOptionalParameter = false; |
| 2436 Token initialToken = null; | 2606 Token initialToken = null; |
| 2437 do { | 2607 do { |
| 2438 if (firstParameter) { | 2608 if (firstParameter) { |
| 2439 firstParameter = false; | 2609 firstParameter = false; |
| 2440 } else if (!optional(TokenType.COMMA)) { | 2610 } else if (!optional(TokenType.COMMA)) { |
| 2441 if (getEndToken(leftParenthesis) != null) { | 2611 if (getEndToken(leftParenthesis) != null) { |
| 2442 reportError7(ParserErrorCode.EXPECTED_TOKEN, [TokenType.COMMA.lexeme])
; | 2612 reportError7(ParserErrorCode.EXPECTED_TOKEN, [TokenType.COMMA.lexeme])
; |
| 2443 } else { | 2613 } else { |
| 2444 reportError8(ParserErrorCode.MISSING_CLOSING_PARENTHESIS, _currentToke
n.previous, []); | 2614 reportError8(ParserErrorCode.MISSING_CLOSING_PARENTHESIS, _currentToke
n.previous, []); |
| 2445 break; | 2615 break; |
| 2446 } | 2616 } |
| 2447 } | 2617 } |
| 2448 initialToken = _currentToken; | 2618 initialToken = _currentToken; |
| 2449 if (matches5(TokenType.OPEN_SQUARE_BRACKET)) { | 2619 if (matches5(TokenType.OPEN_SQUARE_BRACKET)) { |
| 2620 wasOptionalParameter = true; |
| 2450 if (leftSquareBracket != null && !reportedMuliplePositionalGroups) { | 2621 if (leftSquareBracket != null && !reportedMuliplePositionalGroups) { |
| 2451 reportError7(ParserErrorCode.MULTIPLE_POSITIONAL_PARAMETER_GROUPS, [])
; | 2622 reportError7(ParserErrorCode.MULTIPLE_POSITIONAL_PARAMETER_GROUPS, [])
; |
| 2452 reportedMuliplePositionalGroups = true; | 2623 reportedMuliplePositionalGroups = true; |
| 2453 } | 2624 } |
| 2454 if (leftCurlyBracket != null && !reportedMixedGroups) { | 2625 if (leftCurlyBracket != null && !reportedMixedGroups) { |
| 2455 reportError7(ParserErrorCode.MIXED_PARAMETER_GROUPS, []); | 2626 reportError7(ParserErrorCode.MIXED_PARAMETER_GROUPS, []); |
| 2456 reportedMixedGroups = true; | 2627 reportedMixedGroups = true; |
| 2457 } | 2628 } |
| 2458 leftSquareBracket = andAdvance; | 2629 leftSquareBracket = andAdvance; |
| 2459 currentParameters = positionalParameters; | 2630 currentParameters = positionalParameters; |
| 2460 kind = ParameterKind.POSITIONAL; | 2631 kind = ParameterKind.POSITIONAL; |
| 2461 } else if (matches5(TokenType.OPEN_CURLY_BRACKET)) { | 2632 } else if (matches5(TokenType.OPEN_CURLY_BRACKET)) { |
| 2633 wasOptionalParameter = true; |
| 2462 if (leftCurlyBracket != null && !reportedMulipleNamedGroups) { | 2634 if (leftCurlyBracket != null && !reportedMulipleNamedGroups) { |
| 2463 reportError7(ParserErrorCode.MULTIPLE_NAMED_PARAMETER_GROUPS, []); | 2635 reportError7(ParserErrorCode.MULTIPLE_NAMED_PARAMETER_GROUPS, []); |
| 2464 reportedMulipleNamedGroups = true; | 2636 reportedMulipleNamedGroups = true; |
| 2465 } | 2637 } |
| 2466 if (leftSquareBracket != null && !reportedMixedGroups) { | 2638 if (leftSquareBracket != null && !reportedMixedGroups) { |
| 2467 reportError7(ParserErrorCode.MIXED_PARAMETER_GROUPS, []); | 2639 reportError7(ParserErrorCode.MIXED_PARAMETER_GROUPS, []); |
| 2468 reportedMixedGroups = true; | 2640 reportedMixedGroups = true; |
| 2469 } | 2641 } |
| 2470 leftCurlyBracket = andAdvance; | 2642 leftCurlyBracket = andAdvance; |
| 2471 currentParameters = namedParameters; | 2643 currentParameters = namedParameters; |
| 2472 kind = ParameterKind.NAMED; | 2644 kind = ParameterKind.NAMED; |
| 2473 } | 2645 } |
| 2474 FormalParameter parameter = parseFormalParameter(kind); | 2646 FormalParameter parameter = parseFormalParameter(kind); |
| 2475 parameters.add(parameter); | 2647 parameters.add(parameter); |
| 2476 currentParameters.add(parameter); | 2648 currentParameters.add(parameter); |
| 2649 if (identical(kind, ParameterKind.REQUIRED) && wasOptionalParameter) { |
| 2650 reportError(ParserErrorCode.NORMAL_BEFORE_OPTIONAL_PARAMETERS, parameter
, []); |
| 2651 } |
| 2477 if (matches5(TokenType.CLOSE_SQUARE_BRACKET)) { | 2652 if (matches5(TokenType.CLOSE_SQUARE_BRACKET)) { |
| 2478 rightSquareBracket = andAdvance; | 2653 rightSquareBracket = andAdvance; |
| 2479 currentParameters = normalParameters; | 2654 currentParameters = normalParameters; |
| 2480 if (leftSquareBracket == null) { | 2655 if (leftSquareBracket == null) { |
| 2481 if (leftCurlyBracket != null) { | 2656 if (leftCurlyBracket != null) { |
| 2482 reportError7(ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP, [
"}"]); | 2657 reportError7(ParserErrorCode.WRONG_TERMINATOR_FOR_PARAMETER_GROUP, [
"}"]); |
| 2483 rightCurlyBracket = rightSquareBracket; | 2658 rightCurlyBracket = rightSquareBracket; |
| 2484 rightSquareBracket = null; | 2659 rightSquareBracket = null; |
| 2485 } else { | 2660 } else { |
| 2486 reportError7(ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GRO
UP, ["["]); | 2661 reportError7(ParserErrorCode.UNEXPECTED_TERMINATOR_FOR_PARAMETER_GRO
UP, ["["]); |
| (...skipping 26 matching lines...) Expand all Loading... |
| 2513 leftSquareBracket = leftCurlyBracket; | 2688 leftSquareBracket = leftCurlyBracket; |
| 2514 } | 2689 } |
| 2515 if (rightSquareBracket == null) { | 2690 if (rightSquareBracket == null) { |
| 2516 rightSquareBracket = rightCurlyBracket; | 2691 rightSquareBracket = rightCurlyBracket; |
| 2517 } | 2692 } |
| 2518 return new FormalParameterList.full(leftParenthesis, parameters, leftSquareB
racket, rightSquareBracket, rightParenthesis); | 2693 return new FormalParameterList.full(leftParenthesis, parameters, leftSquareB
racket, rightSquareBracket, rightParenthesis); |
| 2519 } | 2694 } |
| 2520 | 2695 |
| 2521 /** | 2696 /** |
| 2522 * Parse a for statement. | 2697 * Parse a for statement. |
| 2698 * |
| 2523 * <pre> | 2699 * <pre> |
| 2524 * forStatement ::= | 2700 * forStatement ::= |
| 2525 * 'for' '(' forLoopParts ')' statement | 2701 * 'for' '(' forLoopParts ')' statement |
| 2702 * |
| 2526 * forLoopParts ::= | 2703 * forLoopParts ::= |
| 2527 * forInitializerStatement expression? ';' expressionList? | 2704 * forInitializerStatement expression? ';' expressionList? |
| 2528 * | declaredIdentifier 'in' expression | 2705 * | declaredIdentifier 'in' expression |
| 2529 * | identifier 'in' expression | 2706 * | identifier 'in' expression |
| 2707 * |
| 2530 * forInitializerStatement ::= | 2708 * forInitializerStatement ::= |
| 2531 * localVariableDeclaration ';' | 2709 * localVariableDeclaration ';' |
| 2532 * | expression? ';' | 2710 * | expression? ';' |
| 2533 * </pre> | 2711 * </pre> |
| 2712 * |
| 2534 * @return the for statement that was parsed | 2713 * @return the for statement that was parsed |
| 2535 */ | 2714 */ |
| 2536 Statement parseForStatement() { | 2715 Statement parseForStatement() { |
| 2537 bool wasInLoop = _inLoop; | 2716 bool wasInLoop = _inLoop; |
| 2538 _inLoop = true; | 2717 _inLoop = true; |
| 2539 try { | 2718 try { |
| 2540 Token forKeyword = expect(Keyword.FOR); | 2719 Token forKeyword = expect(Keyword.FOR); |
| 2541 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 2720 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 2542 VariableDeclarationList variableList = null; | 2721 VariableDeclarationList variableList = null; |
| 2543 Expression initialization = null; | 2722 Expression initialization = null; |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2588 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); | 2767 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); |
| 2589 Statement body = parseStatement2(); | 2768 Statement body = parseStatement2(); |
| 2590 return new ForStatement.full(forKeyword, leftParenthesis, variableList, in
itialization, leftSeparator, condition, rightSeparator, updaters, rightParenthes
is, body); | 2769 return new ForStatement.full(forKeyword, leftParenthesis, variableList, in
itialization, leftSeparator, condition, rightSeparator, updaters, rightParenthes
is, body); |
| 2591 } finally { | 2770 } finally { |
| 2592 _inLoop = wasInLoop; | 2771 _inLoop = wasInLoop; |
| 2593 } | 2772 } |
| 2594 } | 2773 } |
| 2595 | 2774 |
| 2596 /** | 2775 /** |
| 2597 * Parse a function body. | 2776 * Parse a function body. |
| 2777 * |
| 2598 * <pre> | 2778 * <pre> |
| 2599 * functionBody ::= | 2779 * functionBody ::= |
| 2600 * '=>' expression ';' | 2780 * '=>' expression ';' |
| 2601 * | block | 2781 * | block |
| 2782 * |
| 2602 * functionExpressionBody ::= | 2783 * functionExpressionBody ::= |
| 2603 * '=>' expression | 2784 * '=>' expression |
| 2604 * | block | 2785 * | block |
| 2605 * </pre> | 2786 * </pre> |
| 2787 * |
| 2606 * @param mayBeEmpty `true` if the function body is allowed to be empty | 2788 * @param mayBeEmpty `true` if the function body is allowed to be empty |
| 2607 * @param emptyErrorCode the error code to report if function body expecte, bu
t not found | 2789 * @param emptyErrorCode the error code to report if function body expecte, bu
t not found |
| 2608 * @param inExpression `true` if the function body is being parsed as part of
an expression | 2790 * @param inExpression `true` if the function body is being parsed as part of
an expression |
| 2609 * and therefore does not have a terminating semicolon | 2791 * and therefore does not have a terminating semicolon |
| 2610 * @return the function body that was parsed | 2792 * @return the function body that was parsed |
| 2611 */ | 2793 */ |
| 2612 FunctionBody parseFunctionBody(bool mayBeEmpty, ParserErrorCode emptyErrorCode
, bool inExpression) { | 2794 FunctionBody parseFunctionBody(bool mayBeEmpty, ParserErrorCode emptyErrorCode
, bool inExpression) { |
| 2613 bool wasInLoop = _inLoop; | 2795 bool wasInLoop = _inLoop; |
| 2614 bool wasInSwitch = _inSwitch; | 2796 bool wasInSwitch = _inSwitch; |
| 2615 _inLoop = false; | 2797 _inLoop = false; |
| 2616 _inSwitch = false; | 2798 _inSwitch = false; |
| 2617 try { | 2799 try { |
| 2618 if (matches5(TokenType.SEMICOLON)) { | 2800 if (matches5(TokenType.SEMICOLON)) { |
| 2619 if (!mayBeEmpty) { | 2801 if (!mayBeEmpty) { |
| (...skipping 22 matching lines...) Expand all Loading... |
| 2642 return new EmptyFunctionBody.full(createSyntheticToken2(TokenType.SEMICO
LON)); | 2824 return new EmptyFunctionBody.full(createSyntheticToken2(TokenType.SEMICO
LON)); |
| 2643 } | 2825 } |
| 2644 } finally { | 2826 } finally { |
| 2645 _inLoop = wasInLoop; | 2827 _inLoop = wasInLoop; |
| 2646 _inSwitch = wasInSwitch; | 2828 _inSwitch = wasInSwitch; |
| 2647 } | 2829 } |
| 2648 } | 2830 } |
| 2649 | 2831 |
| 2650 /** | 2832 /** |
| 2651 * Parse a function declaration. | 2833 * Parse a function declaration. |
| 2834 * |
| 2652 * <pre> | 2835 * <pre> |
| 2653 * functionDeclaration ::= | 2836 * functionDeclaration ::= |
| 2654 * functionSignature functionBody | 2837 * functionSignature functionBody |
| 2655 * | returnType? getOrSet identifier formalParameterList functionBody | 2838 * | returnType? getOrSet identifier formalParameterList functionBody |
| 2656 * </pre> | 2839 * </pre> |
| 2840 * |
| 2657 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 2841 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 2658 * declaration | 2842 * declaration |
| 2659 * @param externalKeyword the 'external' keyword, or `null` if the function is
not external | 2843 * @param externalKeyword the 'external' keyword, or `null` if the function is
not external |
| 2660 * @param returnType the return type, or `null` if there is no return type | 2844 * @param returnType the return type, or `null` if there is no return type |
| 2661 * @param isStatement `true` if the function declaration is being parsed as a
statement | 2845 * @param isStatement `true` if the function declaration is being parsed as a
statement |
| 2662 * @return the function declaration that was parsed | 2846 * @return the function declaration that was parsed |
| 2663 */ | 2847 */ |
| 2664 FunctionDeclaration parseFunctionDeclaration(CommentAndMetadata commentAndMeta
data, Token externalKeyword, TypeName returnType) { | 2848 FunctionDeclaration parseFunctionDeclaration(CommentAndMetadata commentAndMeta
data, Token externalKeyword, TypeName returnType) { |
| 2665 Token keyword = null; | 2849 Token keyword = null; |
| 2666 bool isGetter = false; | 2850 bool isGetter = false; |
| 2667 if (matches(Keyword.GET) && !matches4(peek(), TokenType.OPEN_PAREN)) { | 2851 if (matches(Keyword.GET) && !matches4(peek(), TokenType.OPEN_PAREN)) { |
| 2668 keyword = andAdvance; | 2852 keyword = andAdvance; |
| (...skipping 18 matching lines...) Expand all Loading... |
| 2687 if (externalKeyword == null) { | 2871 if (externalKeyword == null) { |
| 2688 body = parseFunctionBody(false, ParserErrorCode.MISSING_FUNCTION_BODY, fal
se); | 2872 body = parseFunctionBody(false, ParserErrorCode.MISSING_FUNCTION_BODY, fal
se); |
| 2689 } else { | 2873 } else { |
| 2690 body = new EmptyFunctionBody.full(expect2(TokenType.SEMICOLON)); | 2874 body = new EmptyFunctionBody.full(expect2(TokenType.SEMICOLON)); |
| 2691 } | 2875 } |
| 2692 return new FunctionDeclaration.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, externalKeyword, returnType, keyword, name, new FunctionExpress
ion.full(parameters, body)); | 2876 return new FunctionDeclaration.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, externalKeyword, returnType, keyword, name, new FunctionExpress
ion.full(parameters, body)); |
| 2693 } | 2877 } |
| 2694 | 2878 |
| 2695 /** | 2879 /** |
| 2696 * Parse a function declaration statement. | 2880 * Parse a function declaration statement. |
| 2881 * |
| 2697 * <pre> | 2882 * <pre> |
| 2698 * functionDeclarationStatement ::= | 2883 * functionDeclarationStatement ::= |
| 2699 * functionSignature functionBody | 2884 * functionSignature functionBody |
| 2700 * </pre> | 2885 * </pre> |
| 2886 * |
| 2701 * @return the function declaration statement that was parsed | 2887 * @return the function declaration statement that was parsed |
| 2702 */ | 2888 */ |
| 2703 Statement parseFunctionDeclarationStatement() => parseFunctionDeclarationState
ment2(parseCommentAndMetadata(), parseOptionalReturnType()); | 2889 Statement parseFunctionDeclarationStatement() { |
| 2890 Modifiers modifiers = parseModifiers(); |
| 2891 validateModifiersForFunctionDeclarationStatement(modifiers); |
| 2892 return parseFunctionDeclarationStatement2(parseCommentAndMetadata(), parseOp
tionalReturnType()); |
| 2893 } |
| 2704 | 2894 |
| 2705 /** | 2895 /** |
| 2706 * Parse a function declaration statement. | 2896 * Parse a function declaration statement. |
| 2897 * |
| 2707 * <pre> | 2898 * <pre> |
| 2708 * functionDeclarationStatement ::= | 2899 * functionDeclarationStatement ::= |
| 2709 * functionSignature functionBody | 2900 * functionSignature functionBody |
| 2710 * </pre> | 2901 * </pre> |
| 2902 * |
| 2711 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 2903 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 2712 * declaration | 2904 * declaration |
| 2713 * @param returnType the return type, or `null` if there is no return type | 2905 * @param returnType the return type, or `null` if there is no return type |
| 2714 * @return the function declaration statement that was parsed | 2906 * @return the function declaration statement that was parsed |
| 2715 */ | 2907 */ |
| 2716 Statement parseFunctionDeclarationStatement2(CommentAndMetadata commentAndMeta
data, TypeName returnType) => new FunctionDeclarationStatement.full(parseFunctio
nDeclaration(commentAndMetadata, null, returnType)); | 2908 Statement parseFunctionDeclarationStatement2(CommentAndMetadata commentAndMeta
data, TypeName returnType) => new FunctionDeclarationStatement.full(parseFunctio
nDeclaration(commentAndMetadata, null, returnType)); |
| 2717 | 2909 |
| 2718 /** | 2910 /** |
| 2719 * Parse a function expression. | 2911 * Parse a function expression. |
| 2912 * |
| 2720 * <pre> | 2913 * <pre> |
| 2721 * functionExpression ::= | 2914 * functionExpression ::= |
| 2722 * formalParameterList functionExpressionBody | 2915 * formalParameterList functionExpressionBody |
| 2723 * </pre> | 2916 * </pre> |
| 2917 * |
| 2724 * @return the function expression that was parsed | 2918 * @return the function expression that was parsed |
| 2725 */ | 2919 */ |
| 2726 FunctionExpression parseFunctionExpression() { | 2920 FunctionExpression parseFunctionExpression() { |
| 2727 FormalParameterList parameters = parseFormalParameterList(); | 2921 FormalParameterList parameters = parseFormalParameterList(); |
| 2728 validateFormalParameterList(parameters); | 2922 validateFormalParameterList(parameters); |
| 2729 FunctionBody body = parseFunctionBody(false, ParserErrorCode.MISSING_FUNCTIO
N_BODY, true); | 2923 FunctionBody body = parseFunctionBody(false, ParserErrorCode.MISSING_FUNCTIO
N_BODY, true); |
| 2730 return new FunctionExpression.full(parameters, body); | 2924 return new FunctionExpression.full(parameters, body); |
| 2731 } | 2925 } |
| 2732 | 2926 |
| 2733 /** | 2927 /** |
| 2734 * Parse a function type alias. | 2928 * Parse a function type alias. |
| 2929 * |
| 2735 * <pre> | 2930 * <pre> |
| 2736 * functionTypeAlias ::= | 2931 * functionTypeAlias ::= |
| 2737 * functionPrefix typeParameterList? formalParameterList ';' | 2932 * functionPrefix typeParameterList? formalParameterList ';' |
| 2933 * |
| 2738 * functionPrefix ::= | 2934 * functionPrefix ::= |
| 2739 * returnType? name | 2935 * returnType? name |
| 2740 * </pre> | 2936 * </pre> |
| 2937 * |
| 2741 * @param commentAndMetadata the metadata to be associated with the member | 2938 * @param commentAndMetadata the metadata to be associated with the member |
| 2742 * @param keyword the token representing the 'typedef' keyword | 2939 * @param keyword the token representing the 'typedef' keyword |
| 2743 * @return the function type alias that was parsed | 2940 * @return the function type alias that was parsed |
| 2744 */ | 2941 */ |
| 2745 FunctionTypeAlias parseFunctionTypeAlias(CommentAndMetadata commentAndMetadata
, Token keyword) { | 2942 FunctionTypeAlias parseFunctionTypeAlias(CommentAndMetadata commentAndMetadata
, Token keyword) { |
| 2746 TypeName returnType = null; | 2943 TypeName returnType = null; |
| 2747 if (hasReturnTypeInTypeAlias()) { | 2944 if (hasReturnTypeInTypeAlias()) { |
| 2748 returnType = parseReturnType(); | 2945 returnType = parseReturnType(); |
| 2749 } | 2946 } |
| 2750 SimpleIdentifier name = parseSimpleIdentifier(); | 2947 SimpleIdentifier name = parseSimpleIdentifier(); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 2762 return new FunctionTypeAlias.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, keyword, returnType, name, typeParameters, new FormalParameterL
ist.full(createSyntheticToken2(TokenType.OPEN_PAREN), null, null, null, createSy
ntheticToken2(TokenType.CLOSE_PAREN)), createSyntheticToken2(TokenType.SEMICOLON
)); | 2959 return new FunctionTypeAlias.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, keyword, returnType, name, typeParameters, new FormalParameterL
ist.full(createSyntheticToken2(TokenType.OPEN_PAREN), null, null, null, createSy
ntheticToken2(TokenType.CLOSE_PAREN)), createSyntheticToken2(TokenType.SEMICOLON
)); |
| 2763 } | 2960 } |
| 2764 FormalParameterList parameters = parseFormalParameterList(); | 2961 FormalParameterList parameters = parseFormalParameterList(); |
| 2765 validateFormalParameterList(parameters); | 2962 validateFormalParameterList(parameters); |
| 2766 Token semicolon = expect2(TokenType.SEMICOLON); | 2963 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2767 return new FunctionTypeAlias.full(commentAndMetadata.comment, commentAndMeta
data.metadata, keyword, returnType, name, typeParameters, parameters, semicolon)
; | 2964 return new FunctionTypeAlias.full(commentAndMetadata.comment, commentAndMeta
data.metadata, keyword, returnType, name, typeParameters, parameters, semicolon)
; |
| 2768 } | 2965 } |
| 2769 | 2966 |
| 2770 /** | 2967 /** |
| 2771 * Parse a getter. | 2968 * Parse a getter. |
| 2969 * |
| 2772 * <pre> | 2970 * <pre> |
| 2773 * getter ::= | 2971 * getter ::= |
| 2774 * getterSignature functionBody? | 2972 * getterSignature functionBody? |
| 2973 * |
| 2775 * getterSignature ::= | 2974 * getterSignature ::= |
| 2776 * 'external'? 'static'? returnType? 'get' identifier | 2975 * 'external'? 'static'? returnType? 'get' identifier |
| 2777 * </pre> | 2976 * </pre> |
| 2977 * |
| 2778 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 2978 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 2779 * declaration | 2979 * declaration |
| 2780 * @param externalKeyword the 'external' token | 2980 * @param externalKeyword the 'external' token |
| 2781 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic | 2981 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic |
| 2782 * @param the return type that has already been parsed, or `null` if there was
no return | 2982 * @param the return type that has already been parsed, or `null` if there was
no return |
| 2783 * type | 2983 * type |
| 2784 * @return the getter that was parsed | 2984 * @return the getter that was parsed |
| 2785 */ | 2985 */ |
| 2786 MethodDeclaration parseGetter(CommentAndMetadata commentAndMetadata, Token ext
ernalKeyword, Token staticKeyword, TypeName returnType) { | 2986 MethodDeclaration parseGetter(CommentAndMetadata commentAndMetadata, Token ext
ernalKeyword, Token staticKeyword, TypeName returnType) { |
| 2787 Token propertyKeyword = expect(Keyword.GET); | 2987 Token propertyKeyword = expect(Keyword.GET); |
| 2788 SimpleIdentifier name = parseSimpleIdentifier(); | 2988 SimpleIdentifier name = parseSimpleIdentifier(); |
| 2789 if (matches5(TokenType.OPEN_PAREN) && matches4(peek(), TokenType.CLOSE_PAREN
)) { | 2989 if (matches5(TokenType.OPEN_PAREN) && matches4(peek(), TokenType.CLOSE_PAREN
)) { |
| 2790 reportError7(ParserErrorCode.GETTER_WITH_PARAMETERS, []); | 2990 reportError7(ParserErrorCode.GETTER_WITH_PARAMETERS, []); |
| 2791 advance(); | 2991 advance(); |
| 2792 advance(); | 2992 advance(); |
| 2793 } | 2993 } |
| 2794 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.STATIC_GETTER_WITHOUT_BODY, false); | 2994 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.STATIC_GETTER_WITHOUT_BODY, false); |
| 2795 if (externalKeyword != null && body is! EmptyFunctionBody) { | 2995 if (externalKeyword != null && body is! EmptyFunctionBody) { |
| 2796 reportError7(ParserErrorCode.EXTERNAL_GETTER_WITH_BODY, []); | 2996 reportError7(ParserErrorCode.EXTERNAL_GETTER_WITH_BODY, []); |
| 2797 } | 2997 } |
| 2798 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, propertyKeyword, null
, name, null, body); | 2998 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, propertyKeyword, null
, name, null, body); |
| 2799 } | 2999 } |
| 2800 | 3000 |
| 2801 /** | 3001 /** |
| 2802 * Parse a list of identifiers. | 3002 * Parse a list of identifiers. |
| 3003 * |
| 2803 * <pre> | 3004 * <pre> |
| 2804 * identifierList ::= | 3005 * identifierList ::= |
| 2805 * identifier (',' identifier) | 3006 * identifier (',' identifier)* |
| 2806 * </pre> | 3007 * </pre> |
| 3008 * |
| 2807 * @return the list of identifiers that were parsed | 3009 * @return the list of identifiers that were parsed |
| 2808 */ | 3010 */ |
| 2809 List<SimpleIdentifier> parseIdentifierList() { | 3011 List<SimpleIdentifier> parseIdentifierList() { |
| 2810 List<SimpleIdentifier> identifiers = new List<SimpleIdentifier>(); | 3012 List<SimpleIdentifier> identifiers = new List<SimpleIdentifier>(); |
| 2811 identifiers.add(parseSimpleIdentifier()); | 3013 identifiers.add(parseSimpleIdentifier()); |
| 2812 while (matches5(TokenType.COMMA)) { | 3014 while (matches5(TokenType.COMMA)) { |
| 2813 advance(); | 3015 advance(); |
| 2814 identifiers.add(parseSimpleIdentifier()); | 3016 identifiers.add(parseSimpleIdentifier()); |
| 2815 } | 3017 } |
| 2816 return identifiers; | 3018 return identifiers; |
| 2817 } | 3019 } |
| 2818 | 3020 |
| 2819 /** | 3021 /** |
| 2820 * Parse an if statement. | 3022 * Parse an if statement. |
| 3023 * |
| 2821 * <pre> | 3024 * <pre> |
| 2822 * ifStatement ::= | 3025 * ifStatement ::= |
| 2823 * 'if' '(' expression ')' statement ('else' statement)? | 3026 * 'if' '(' expression ')' statement ('else' statement)? |
| 2824 * </pre> | 3027 * </pre> |
| 3028 * |
| 2825 * @return the if statement that was parsed | 3029 * @return the if statement that was parsed |
| 2826 */ | 3030 */ |
| 2827 Statement parseIfStatement() { | 3031 Statement parseIfStatement() { |
| 2828 Token ifKeyword = expect(Keyword.IF); | 3032 Token ifKeyword = expect(Keyword.IF); |
| 2829 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 3033 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 2830 Expression condition = parseExpression2(); | 3034 Expression condition = parseExpression2(); |
| 2831 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); | 3035 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); |
| 2832 Statement thenStatement = parseStatement2(); | 3036 Statement thenStatement = parseStatement2(); |
| 2833 Token elseKeyword = null; | 3037 Token elseKeyword = null; |
| 2834 Statement elseStatement = null; | 3038 Statement elseStatement = null; |
| 2835 if (matches(Keyword.ELSE)) { | 3039 if (matches(Keyword.ELSE)) { |
| 2836 elseKeyword = andAdvance; | 3040 elseKeyword = andAdvance; |
| 2837 elseStatement = parseStatement2(); | 3041 elseStatement = parseStatement2(); |
| 2838 } | 3042 } |
| 2839 return new IfStatement.full(ifKeyword, leftParenthesis, condition, rightPare
nthesis, thenStatement, elseKeyword, elseStatement); | 3043 return new IfStatement.full(ifKeyword, leftParenthesis, condition, rightPare
nthesis, thenStatement, elseKeyword, elseStatement); |
| 2840 } | 3044 } |
| 2841 | 3045 |
| 2842 /** | 3046 /** |
| 2843 * Parse an implements clause. | 3047 * Parse an implements clause. |
| 3048 * |
| 2844 * <pre> | 3049 * <pre> |
| 2845 * implementsClause ::= | 3050 * implementsClause ::= |
| 2846 * 'implements' type (',' type) | 3051 * 'implements' type (',' type)* |
| 2847 * </pre> | 3052 * </pre> |
| 3053 * |
| 2848 * @return the implements clause that was parsed | 3054 * @return the implements clause that was parsed |
| 2849 */ | 3055 */ |
| 2850 ImplementsClause parseImplementsClause() { | 3056 ImplementsClause parseImplementsClause() { |
| 2851 Token keyword = expect(Keyword.IMPLEMENTS); | 3057 Token keyword = expect(Keyword.IMPLEMENTS); |
| 2852 List<TypeName> interfaces = new List<TypeName>(); | 3058 List<TypeName> interfaces = new List<TypeName>(); |
| 2853 interfaces.add(parseTypeName()); | 3059 interfaces.add(parseTypeName()); |
| 2854 while (optional(TokenType.COMMA)) { | 3060 while (optional(TokenType.COMMA)) { |
| 2855 interfaces.add(parseTypeName()); | 3061 interfaces.add(parseTypeName()); |
| 2856 } | 3062 } |
| 2857 return new ImplementsClause.full(keyword, interfaces); | 3063 return new ImplementsClause.full(keyword, interfaces); |
| 2858 } | 3064 } |
| 2859 | 3065 |
| 2860 /** | 3066 /** |
| 2861 * Parse an import directive. | 3067 * Parse an import directive. |
| 3068 * |
| 2862 * <pre> | 3069 * <pre> |
| 2863 * importDirective ::= | 3070 * importDirective ::= |
| 2864 * metadata 'import' stringLiteral ('as' identifier)? combinator*';' | 3071 * metadata 'import' stringLiteral ('as' identifier)? combinator*';' |
| 2865 * </pre> | 3072 * </pre> |
| 3073 * |
| 2866 * @param commentAndMetadata the metadata to be associated with the directive | 3074 * @param commentAndMetadata the metadata to be associated with the directive |
| 2867 * @return the import directive that was parsed | 3075 * @return the import directive that was parsed |
| 2868 */ | 3076 */ |
| 2869 ImportDirective parseImportDirective(CommentAndMetadata commentAndMetadata) { | 3077 ImportDirective parseImportDirective(CommentAndMetadata commentAndMetadata) { |
| 2870 Token importKeyword = expect(Keyword.IMPORT); | 3078 Token importKeyword = expect(Keyword.IMPORT); |
| 2871 StringLiteral libraryUri = parseStringLiteral(); | 3079 StringLiteral libraryUri = parseStringLiteral(); |
| 2872 Token asToken = null; | 3080 Token asToken = null; |
| 2873 SimpleIdentifier prefix = null; | 3081 SimpleIdentifier prefix = null; |
| 2874 if (matches(Keyword.AS)) { | 3082 if (matches(Keyword.AS)) { |
| 2875 asToken = andAdvance; | 3083 asToken = andAdvance; |
| 2876 prefix = parseSimpleIdentifier(); | 3084 prefix = parseSimpleIdentifier(); |
| 2877 } | 3085 } |
| 2878 List<Combinator> combinators = parseCombinators(); | 3086 List<Combinator> combinators = parseCombinators(); |
| 2879 Token semicolon = expect2(TokenType.SEMICOLON); | 3087 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2880 return new ImportDirective.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, importKeyword, libraryUri, asToken, prefix, combinators, semicolon)
; | 3088 return new ImportDirective.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, importKeyword, libraryUri, asToken, prefix, combinators, semicolon)
; |
| 2881 } | 3089 } |
| 2882 | 3090 |
| 2883 /** | 3091 /** |
| 2884 * Parse a list of initialized identifiers. | 3092 * Parse a list of initialized identifiers. |
| 3093 * |
| 2885 * <pre> | 3094 * <pre> |
| 2886 * ?? ::= | 3095 * ?? ::= |
| 2887 * 'static'? ('var' | type) initializedIdentifierList ';' | 3096 * 'static'? ('var' | type) initializedIdentifierList ';' |
| 2888 * | 'final' type? initializedIdentifierList ';' | 3097 * | 'final' type? initializedIdentifierList ';' |
| 3098 * |
| 2889 * initializedIdentifierList ::= | 3099 * initializedIdentifierList ::= |
| 2890 * initializedIdentifier (',' initializedIdentifier) | 3100 * initializedIdentifier (',' initializedIdentifier)* |
| 3101 * |
| 2891 * initializedIdentifier ::= | 3102 * initializedIdentifier ::= |
| 2892 * identifier ('=' expression)? | 3103 * identifier ('=' expression)? |
| 2893 * </pre> | 3104 * </pre> |
| 3105 * |
| 2894 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 3106 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 2895 * declaration | 3107 * declaration |
| 2896 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic | 3108 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic |
| 2897 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if | 3109 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if |
| 2898 * there is no keyword | 3110 * there is no keyword |
| 2899 * @param type the type that has already been parsed, or `null` if 'var' was p
rovided | 3111 * @param type the type that has already been parsed, or `null` if 'var' was p
rovided |
| 2900 * @return the getter that was parsed | 3112 * @return the getter that was parsed |
| 2901 */ | 3113 */ |
| 2902 FieldDeclaration parseInitializedIdentifierList(CommentAndMetadata commentAndM
etadata, Token staticKeyword, Token keyword, TypeName type) { | 3114 FieldDeclaration parseInitializedIdentifierList(CommentAndMetadata commentAndM
etadata, Token staticKeyword, Token keyword, TypeName type) { |
| 2903 VariableDeclarationList fieldList = parseVariableDeclarationList2(null, keyw
ord, type); | 3115 VariableDeclarationList fieldList = parseVariableDeclarationList2(null, keyw
ord, type); |
| 2904 return new FieldDeclaration.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, staticKeyword, fieldList, expect2(TokenType.SEMICOLON)); | 3116 return new FieldDeclaration.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, staticKeyword, fieldList, expect2(TokenType.SEMICOLON)); |
| 2905 } | 3117 } |
| 2906 | 3118 |
| 2907 /** | 3119 /** |
| 2908 * Parse an instance creation expression. | 3120 * Parse an instance creation expression. |
| 3121 * |
| 2909 * <pre> | 3122 * <pre> |
| 2910 * instanceCreationExpression ::= | 3123 * instanceCreationExpression ::= |
| 2911 * ('new' | 'const') type ('.' identifier)? argumentList | 3124 * ('new' | 'const') type ('.' identifier)? argumentList |
| 2912 * </pre> | 3125 * </pre> |
| 3126 * |
| 2913 * @param keyword the 'new' or 'const' keyword that introduces the expression | 3127 * @param keyword the 'new' or 'const' keyword that introduces the expression |
| 2914 * @return the instance creation expression that was parsed | 3128 * @return the instance creation expression that was parsed |
| 2915 */ | 3129 */ |
| 2916 InstanceCreationExpression parseInstanceCreationExpression(Token keyword) { | 3130 InstanceCreationExpression parseInstanceCreationExpression(Token keyword) { |
| 2917 ConstructorName constructorName = parseConstructorName(); | 3131 ConstructorName constructorName = parseConstructorName(); |
| 2918 ArgumentList argumentList = parseArgumentList(); | 3132 ArgumentList argumentList = parseArgumentList(); |
| 2919 return new InstanceCreationExpression.full(keyword, constructorName, argumen
tList); | 3133 return new InstanceCreationExpression.full(keyword, constructorName, argumen
tList); |
| 2920 } | 3134 } |
| 2921 | 3135 |
| 2922 /** | 3136 /** |
| 2923 * Parse a library directive. | 3137 * Parse a library directive. |
| 3138 * |
| 2924 * <pre> | 3139 * <pre> |
| 2925 * libraryDirective ::= | 3140 * libraryDirective ::= |
| 2926 * metadata 'library' identifier ';' | 3141 * metadata 'library' identifier ';' |
| 2927 * </pre> | 3142 * </pre> |
| 3143 * |
| 2928 * @param commentAndMetadata the metadata to be associated with the directive | 3144 * @param commentAndMetadata the metadata to be associated with the directive |
| 2929 * @return the library directive that was parsed | 3145 * @return the library directive that was parsed |
| 2930 */ | 3146 */ |
| 2931 LibraryDirective parseLibraryDirective(CommentAndMetadata commentAndMetadata)
{ | 3147 LibraryDirective parseLibraryDirective(CommentAndMetadata commentAndMetadata)
{ |
| 2932 Token keyword = expect(Keyword.LIBRARY); | 3148 Token keyword = expect(Keyword.LIBRARY); |
| 2933 LibraryIdentifier libraryName = parseLibraryName(ParserErrorCode.MISSING_NAM
E_IN_LIBRARY_DIRECTIVE, keyword); | 3149 LibraryIdentifier libraryName = parseLibraryName(ParserErrorCode.MISSING_NAM
E_IN_LIBRARY_DIRECTIVE, keyword); |
| 2934 Token semicolon = expect2(TokenType.SEMICOLON); | 3150 Token semicolon = expect2(TokenType.SEMICOLON); |
| 2935 return new LibraryDirective.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, keyword, libraryName, semicolon); | 3151 return new LibraryDirective.full(commentAndMetadata.comment, commentAndMetad
ata.metadata, keyword, libraryName, semicolon); |
| 2936 } | 3152 } |
| 2937 | 3153 |
| 2938 /** | 3154 /** |
| 2939 * Parse a library identifier. | 3155 * Parse a library identifier. |
| 3156 * |
| 2940 * <pre> | 3157 * <pre> |
| 2941 * libraryIdentifier ::= | 3158 * libraryIdentifier ::= |
| 2942 * identifier ('.' identifier) | 3159 * identifier ('.' identifier)* |
| 2943 * </pre> | 3160 * </pre> |
| 3161 * |
| 2944 * @return the library identifier that was parsed | 3162 * @return the library identifier that was parsed |
| 2945 */ | 3163 */ |
| 2946 LibraryIdentifier parseLibraryIdentifier() { | 3164 LibraryIdentifier parseLibraryIdentifier() { |
| 2947 List<SimpleIdentifier> components = new List<SimpleIdentifier>(); | 3165 List<SimpleIdentifier> components = new List<SimpleIdentifier>(); |
| 2948 components.add(parseSimpleIdentifier()); | 3166 components.add(parseSimpleIdentifier()); |
| 2949 while (matches5(TokenType.PERIOD)) { | 3167 while (matches5(TokenType.PERIOD)) { |
| 2950 advance(); | 3168 advance(); |
| 2951 components.add(parseSimpleIdentifier()); | 3169 components.add(parseSimpleIdentifier()); |
| 2952 } | 3170 } |
| 2953 return new LibraryIdentifier.full(components); | 3171 return new LibraryIdentifier.full(components); |
| 2954 } | 3172 } |
| 2955 | 3173 |
| 2956 /** | 3174 /** |
| 2957 * Parse a library name. | 3175 * Parse a library name. |
| 3176 * |
| 2958 * <pre> | 3177 * <pre> |
| 2959 * libraryName ::= | 3178 * libraryName ::= |
| 2960 * libraryIdentifier | 3179 * libraryIdentifier |
| 2961 * </pre> | 3180 * </pre> |
| 3181 * |
| 2962 * @param missingNameError the error code to be used if the library name is mi
ssing | 3182 * @param missingNameError the error code to be used if the library name is mi
ssing |
| 2963 * @param missingNameToken the token associated with the error produced if the
library name is | 3183 * @param missingNameToken the token associated with the error produced if the
library name is |
| 2964 * missing | 3184 * missing |
| 2965 * @return the library name that was parsed | 3185 * @return the library name that was parsed |
| 2966 */ | 3186 */ |
| 2967 LibraryIdentifier parseLibraryName(ParserErrorCode missingNameError, Token mis
singNameToken) { | 3187 LibraryIdentifier parseLibraryName(ParserErrorCode missingNameError, Token mis
singNameToken) { |
| 2968 if (matchesIdentifier()) { | 3188 if (matchesIdentifier()) { |
| 2969 return parseLibraryIdentifier(); | 3189 return parseLibraryIdentifier(); |
| 2970 } else if (matches5(TokenType.STRING)) { | 3190 } else if (matches5(TokenType.STRING)) { |
| 2971 StringLiteral string = parseStringLiteral(); | 3191 StringLiteral string = parseStringLiteral(); |
| 2972 reportError(ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME, string, []); | 3192 reportError(ParserErrorCode.NON_IDENTIFIER_LIBRARY_NAME, string, []); |
| 2973 } else { | 3193 } else { |
| 2974 reportError8(missingNameError, missingNameToken, []); | 3194 reportError8(missingNameError, missingNameToken, []); |
| 2975 } | 3195 } |
| 2976 List<SimpleIdentifier> components = new List<SimpleIdentifier>(); | 3196 List<SimpleIdentifier> components = new List<SimpleIdentifier>(); |
| 2977 components.add(createSyntheticIdentifier()); | 3197 components.add(createSyntheticIdentifier()); |
| 2978 return new LibraryIdentifier.full(components); | 3198 return new LibraryIdentifier.full(components); |
| 2979 } | 3199 } |
| 2980 | 3200 |
| 2981 /** | 3201 /** |
| 2982 * Parse a list literal. | 3202 * Parse a list literal. |
| 3203 * |
| 2983 * <pre> | 3204 * <pre> |
| 2984 * listLiteral ::= | 3205 * listLiteral ::= |
| 2985 * 'const'? typeArguments? '\[' (expressionList ','?)? '\]' | 3206 * 'const'? typeArguments? '[' (expressionList ','?)? ']' |
| 2986 * </pre> | 3207 * </pre> |
| 3208 * |
| 2987 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is | 3209 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is |
| 2988 * no modifier | 3210 * no modifier |
| 2989 * @param typeArguments the type arguments appearing before the literal, or `n
ull` if there | 3211 * @param typeArguments the type arguments appearing before the literal, or `n
ull` if there |
| 2990 * are no type arguments | 3212 * are no type arguments |
| 2991 * @return the list literal that was parsed | 3213 * @return the list literal that was parsed |
| 2992 */ | 3214 */ |
| 2993 ListLiteral parseListLiteral(Token modifier, TypeArgumentList typeArguments) { | 3215 ListLiteral parseListLiteral(Token modifier, TypeArgumentList typeArguments) { |
| 2994 if (matches5(TokenType.INDEX)) { | 3216 if (matches5(TokenType.INDEX)) { |
| 2995 BeginToken leftBracket = new BeginToken(TokenType.OPEN_SQUARE_BRACKET, _cu
rrentToken.offset); | 3217 BeginToken leftBracket = new BeginToken(TokenType.OPEN_SQUARE_BRACKET, _cu
rrentToken.offset); |
| 2996 Token rightBracket = new Token(TokenType.CLOSE_SQUARE_BRACKET, _currentTok
en.offset + 1); | 3218 Token rightBracket = new Token(TokenType.CLOSE_SQUARE_BRACKET, _currentTok
en.offset + 1); |
| 2997 leftBracket.endToken = rightBracket; | 3219 leftBracket.endToken = rightBracket; |
| 2998 rightBracket.setNext(_currentToken.next); | 3220 rightBracket.setNext(_currentToken.next); |
| 2999 leftBracket.setNext(rightBracket); | 3221 leftBracket.setNext(rightBracket); |
| 3000 _currentToken.previous.setNext(leftBracket); | 3222 _currentToken.previous.setNext(leftBracket); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 3012 return new ListLiteral.full(modifier, typeArguments, leftBracket, elemen
ts, andAdvance); | 3234 return new ListLiteral.full(modifier, typeArguments, leftBracket, elemen
ts, andAdvance); |
| 3013 } | 3235 } |
| 3014 elements.add(parseExpression2()); | 3236 elements.add(parseExpression2()); |
| 3015 } | 3237 } |
| 3016 Token rightBracket = expect2(TokenType.CLOSE_SQUARE_BRACKET); | 3238 Token rightBracket = expect2(TokenType.CLOSE_SQUARE_BRACKET); |
| 3017 return new ListLiteral.full(modifier, typeArguments, leftBracket, elements,
rightBracket); | 3239 return new ListLiteral.full(modifier, typeArguments, leftBracket, elements,
rightBracket); |
| 3018 } | 3240 } |
| 3019 | 3241 |
| 3020 /** | 3242 /** |
| 3021 * Parse a list or map literal. | 3243 * Parse a list or map literal. |
| 3244 * |
| 3022 * <pre> | 3245 * <pre> |
| 3023 * listOrMapLiteral ::= | 3246 * listOrMapLiteral ::= |
| 3024 * listLiteral | 3247 * listLiteral |
| 3025 * | mapLiteral | 3248 * | mapLiteral |
| 3026 * </pre> | 3249 * </pre> |
| 3250 * |
| 3027 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is | 3251 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is |
| 3028 * no modifier | 3252 * no modifier |
| 3029 * @return the list or map literal that was parsed | 3253 * @return the list or map literal that was parsed |
| 3030 */ | 3254 */ |
| 3031 TypedLiteral parseListOrMapLiteral(Token modifier) { | 3255 TypedLiteral parseListOrMapLiteral(Token modifier) { |
| 3032 TypeArgumentList typeArguments = null; | 3256 TypeArgumentList typeArguments = null; |
| 3033 if (matches5(TokenType.LT)) { | 3257 if (matches5(TokenType.LT)) { |
| 3034 typeArguments = parseTypeArgumentList(); | 3258 typeArguments = parseTypeArgumentList(); |
| 3035 } | 3259 } |
| 3036 if (matches5(TokenType.OPEN_CURLY_BRACKET)) { | 3260 if (matches5(TokenType.OPEN_CURLY_BRACKET)) { |
| 3037 return parseMapLiteral(modifier, typeArguments); | 3261 return parseMapLiteral(modifier, typeArguments); |
| 3038 } else if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.IND
EX)) { | 3262 } else if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.IND
EX)) { |
| 3039 return parseListLiteral(modifier, typeArguments); | 3263 return parseListLiteral(modifier, typeArguments); |
| 3040 } | 3264 } |
| 3041 reportError7(ParserErrorCode.EXPECTED_LIST_OR_MAP_LITERAL, []); | 3265 reportError7(ParserErrorCode.EXPECTED_LIST_OR_MAP_LITERAL, []); |
| 3042 return new ListLiteral.full(modifier, typeArguments, createSyntheticToken2(T
okenType.OPEN_SQUARE_BRACKET), null, createSyntheticToken2(TokenType.CLOSE_SQUAR
E_BRACKET)); | 3266 return new ListLiteral.full(modifier, typeArguments, createSyntheticToken2(T
okenType.OPEN_SQUARE_BRACKET), null, createSyntheticToken2(TokenType.CLOSE_SQUAR
E_BRACKET)); |
| 3043 } | 3267 } |
| 3044 | 3268 |
| 3045 /** | 3269 /** |
| 3046 * Parse a logical and expression. | 3270 * Parse a logical and expression. |
| 3271 * |
| 3047 * <pre> | 3272 * <pre> |
| 3048 * logicalAndExpression ::= | 3273 * logicalAndExpression ::= |
| 3049 * bitwiseOrExpression ('&&' bitwiseOrExpression) | 3274 * bitwiseOrExpression ('&&' bitwiseOrExpression)* |
| 3050 * </pre> | 3275 * </pre> |
| 3276 * |
| 3051 * @return the logical and expression that was parsed | 3277 * @return the logical and expression that was parsed |
| 3052 */ | 3278 */ |
| 3053 Expression parseLogicalAndExpression() { | 3279 Expression parseLogicalAndExpression() { |
| 3054 Expression expression = parseBitwiseOrExpression(); | 3280 Expression expression = parseBitwiseOrExpression(); |
| 3055 while (matches5(TokenType.AMPERSAND_AMPERSAND)) { | 3281 while (matches5(TokenType.AMPERSAND_AMPERSAND)) { |
| 3056 Token operator = andAdvance; | 3282 Token operator = andAdvance; |
| 3057 expression = new BinaryExpression.full(expression, operator, parseBitwiseO
rExpression()); | 3283 expression = new BinaryExpression.full(expression, operator, parseBitwiseO
rExpression()); |
| 3058 } | 3284 } |
| 3059 return expression; | 3285 return expression; |
| 3060 } | 3286 } |
| 3061 | 3287 |
| 3062 /** | 3288 /** |
| 3063 * Parse a logical or expression. | 3289 * Parse a logical or expression. |
| 3290 * |
| 3064 * <pre> | 3291 * <pre> |
| 3065 * logicalOrExpression ::= | 3292 * logicalOrExpression ::= |
| 3066 * logicalAndExpression ('||' logicalAndExpression) | 3293 * logicalAndExpression ('||' logicalAndExpression)* |
| 3067 * </pre> | 3294 * </pre> |
| 3295 * |
| 3068 * @return the logical or expression that was parsed | 3296 * @return the logical or expression that was parsed |
| 3069 */ | 3297 */ |
| 3070 Expression parseLogicalOrExpression() { | 3298 Expression parseLogicalOrExpression() { |
| 3071 Expression expression = parseLogicalAndExpression(); | 3299 Expression expression = parseLogicalAndExpression(); |
| 3072 while (matches5(TokenType.BAR_BAR)) { | 3300 while (matches5(TokenType.BAR_BAR)) { |
| 3073 Token operator = andAdvance; | 3301 Token operator = andAdvance; |
| 3074 expression = new BinaryExpression.full(expression, operator, parseLogicalA
ndExpression()); | 3302 expression = new BinaryExpression.full(expression, operator, parseLogicalA
ndExpression()); |
| 3075 } | 3303 } |
| 3076 return expression; | 3304 return expression; |
| 3077 } | 3305 } |
| 3078 | 3306 |
| 3079 /** | 3307 /** |
| 3080 * Parse a map literal. | 3308 * Parse a map literal. |
| 3309 * |
| 3081 * <pre> | 3310 * <pre> |
| 3082 * mapLiteral ::= | 3311 * mapLiteral ::= |
| 3083 * 'const'? typeArguments? '{' (mapLiteralEntry (',' mapLiteralEntry)* ','?)?
'}' | 3312 * 'const'? typeArguments? '{' (mapLiteralEntry (',' mapLiteralEntry)* ','
?)? '}' |
| 3084 * </pre> | 3313 * </pre> |
| 3314 * |
| 3085 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is | 3315 * @param modifier the 'const' modifier appearing before the literal, or `null
` if there is |
| 3086 * no modifier | 3316 * no modifier |
| 3087 * @param typeArguments the type arguments that were declared, or `null` if th
ere are no | 3317 * @param typeArguments the type arguments that were declared, or `null` if th
ere are no |
| 3088 * type arguments | 3318 * type arguments |
| 3089 * @return the map literal that was parsed | 3319 * @return the map literal that was parsed |
| 3090 */ | 3320 */ |
| 3091 MapLiteral parseMapLiteral(Token modifier, TypeArgumentList typeArguments) { | 3321 MapLiteral parseMapLiteral(Token modifier, TypeArgumentList typeArguments) { |
| 3092 if (typeArguments != null) { | 3322 if (typeArguments != null) { |
| 3093 int num = typeArguments.arguments.length; | 3323 int num = typeArguments.arguments.length; |
| 3094 if (num != 2) { | 3324 if (num != 2) { |
| 3095 reportError(ParserErrorCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS, typeArgumen
ts, [num]); | 3325 reportError(ParserErrorCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS, typeArgumen
ts, [num]); |
| 3096 } | 3326 } |
| 3097 } | 3327 } |
| 3098 Token leftBracket = expect2(TokenType.OPEN_CURLY_BRACKET); | 3328 Token leftBracket = expect2(TokenType.OPEN_CURLY_BRACKET); |
| 3099 List<MapLiteralEntry> entries = new List<MapLiteralEntry>(); | 3329 List<MapLiteralEntry> entries = new List<MapLiteralEntry>(); |
| 3100 if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { | 3330 if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { |
| 3101 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries,
andAdvance); | 3331 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries,
andAdvance); |
| 3102 } | 3332 } |
| 3103 entries.add(parseMapLiteralEntry()); | 3333 entries.add(parseMapLiteralEntry()); |
| 3104 while (optional(TokenType.COMMA)) { | 3334 while (optional(TokenType.COMMA)) { |
| 3105 if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { | 3335 if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { |
| 3106 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries
, andAdvance); | 3336 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries
, andAdvance); |
| 3107 } | 3337 } |
| 3108 entries.add(parseMapLiteralEntry()); | 3338 entries.add(parseMapLiteralEntry()); |
| 3109 } | 3339 } |
| 3110 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); | 3340 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); |
| 3111 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries, ri
ghtBracket); | 3341 return new MapLiteral.full(modifier, typeArguments, leftBracket, entries, ri
ghtBracket); |
| 3112 } | 3342 } |
| 3113 | 3343 |
| 3114 /** | 3344 /** |
| 3115 * Parse a map literal entry. | 3345 * Parse a map literal entry. |
| 3346 * |
| 3116 * <pre> | 3347 * <pre> |
| 3117 * mapLiteralEntry ::= | 3348 * mapLiteralEntry ::= |
| 3118 * expression ':' expression | 3349 * expression ':' expression |
| 3119 * </pre> | 3350 * </pre> |
| 3351 * |
| 3120 * @return the map literal entry that was parsed | 3352 * @return the map literal entry that was parsed |
| 3121 */ | 3353 */ |
| 3122 MapLiteralEntry parseMapLiteralEntry() { | 3354 MapLiteralEntry parseMapLiteralEntry() { |
| 3123 Expression key = parseExpression2(); | 3355 Expression key = parseExpression2(); |
| 3124 Token separator = expect2(TokenType.COLON); | 3356 Token separator = expect2(TokenType.COLON); |
| 3125 Expression value = parseExpression2(); | 3357 Expression value = parseExpression2(); |
| 3126 return new MapLiteralEntry.full(key, separator, value); | 3358 return new MapLiteralEntry.full(key, separator, value); |
| 3127 } | 3359 } |
| 3128 | 3360 |
| 3129 /** | 3361 /** |
| 3130 * Parse a method declaration. | 3362 * Parse a method declaration. |
| 3363 * |
| 3131 * <pre> | 3364 * <pre> |
| 3132 * functionDeclaration ::= | 3365 * functionDeclaration ::= |
| 3133 * 'external'? 'static'? functionSignature functionBody | 3366 * 'external'? 'static'? functionSignature functionBody |
| 3134 * | 'external'? functionSignature ';' | 3367 * | 'external'? functionSignature ';' |
| 3135 * </pre> | 3368 * </pre> |
| 3369 * |
| 3136 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 3370 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 3137 * declaration | 3371 * declaration |
| 3138 * @param externalKeyword the 'external' token | 3372 * @param externalKeyword the 'external' token |
| 3139 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic | 3373 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic |
| 3140 * @param returnType the return type of the method | 3374 * @param returnType the return type of the method |
| 3141 * @return the method declaration that was parsed | 3375 * @return the method declaration that was parsed |
| 3142 */ | 3376 */ |
| 3143 MethodDeclaration parseMethodDeclaration(CommentAndMetadata commentAndMetadata
, Token externalKeyword, Token staticKeyword, TypeName returnType) { | 3377 MethodDeclaration parseMethodDeclaration(CommentAndMetadata commentAndMetadata
, Token externalKeyword, Token staticKeyword, TypeName returnType) { |
| 3144 SimpleIdentifier methodName = parseSimpleIdentifier(); | 3378 SimpleIdentifier methodName = parseSimpleIdentifier(); |
| 3145 FormalParameterList parameters = parseFormalParameterList(); | 3379 FormalParameterList parameters = parseFormalParameterList(); |
| 3146 validateFormalParameterList(parameters); | 3380 validateFormalParameterList(parameters); |
| 3147 return parseMethodDeclaration2(commentAndMetadata, externalKeyword, staticKe
yword, returnType, methodName, parameters); | 3381 return parseMethodDeclaration2(commentAndMetadata, externalKeyword, staticKe
yword, returnType, methodName, parameters); |
| 3148 } | 3382 } |
| 3149 | 3383 |
| 3150 /** | 3384 /** |
| 3151 * Parse a method declaration. | 3385 * Parse a method declaration. |
| 3386 * |
| 3152 * <pre> | 3387 * <pre> |
| 3153 * functionDeclaration ::= | 3388 * functionDeclaration ::= |
| 3154 * ('external' 'static'?)? functionSignature functionBody | 3389 * ('external' 'static'?)? functionSignature functionBody |
| 3155 * | 'external'? functionSignature ';' | 3390 * | 'external'? functionSignature ';' |
| 3156 * </pre> | 3391 * </pre> |
| 3392 * |
| 3157 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 3393 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 3158 * declaration | 3394 * declaration |
| 3159 * @param externalKeyword the 'external' token | 3395 * @param externalKeyword the 'external' token |
| 3160 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic | 3396 * @param staticKeyword the static keyword, or `null` if the getter is not sta
tic |
| 3161 * @param returnType the return type of the method | 3397 * @param returnType the return type of the method |
| 3162 * @param name the name of the method | 3398 * @param name the name of the method |
| 3163 * @param parameters the parameters to the method | 3399 * @param parameters the parameters to the method |
| 3164 * @return the method declaration that was parsed | 3400 * @return the method declaration that was parsed |
| 3165 */ | 3401 */ |
| 3166 MethodDeclaration parseMethodDeclaration2(CommentAndMetadata commentAndMetadat
a, Token externalKeyword, Token staticKeyword, TypeName returnType, SimpleIdenti
fier name, FormalParameterList parameters) { | 3402 MethodDeclaration parseMethodDeclaration2(CommentAndMetadata commentAndMetadat
a, Token externalKeyword, Token staticKeyword, TypeName returnType, SimpleIdenti
fier name, FormalParameterList parameters) { |
| 3167 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.MISSING_FUNCTION_BODY, false); | 3403 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.MISSING_FUNCTION_BODY, false); |
| 3168 if (externalKeyword != null) { | 3404 if (externalKeyword != null) { |
| 3169 if (body is! EmptyFunctionBody) { | 3405 if (body is! EmptyFunctionBody) { |
| 3170 reportError(ParserErrorCode.EXTERNAL_METHOD_WITH_BODY, body, []); | 3406 reportError(ParserErrorCode.EXTERNAL_METHOD_WITH_BODY, body, []); |
| 3171 } | 3407 } |
| 3172 } else if (staticKeyword != null) { | 3408 } else if (staticKeyword != null) { |
| 3173 if (body is EmptyFunctionBody) { | 3409 if (body is EmptyFunctionBody) { |
| 3174 reportError(ParserErrorCode.ABSTRACT_STATIC_METHOD, body, []); | 3410 reportError(ParserErrorCode.ABSTRACT_STATIC_METHOD, body, []); |
| 3175 } | 3411 } |
| 3176 } | 3412 } |
| 3177 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, null, null, name, par
ameters, body); | 3413 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, null, null, name, par
ameters, body); |
| 3178 } | 3414 } |
| 3179 | 3415 |
| 3180 /** | 3416 /** |
| 3181 * Parse the modifiers preceding a declaration. This method allows the modifie
rs to appear in any | 3417 * Parse the modifiers preceding a declaration. This method allows the modifie
rs to appear in any |
| 3182 * order but does generate errors for duplicated modifiers. Checks for other p
roblems, such as | 3418 * order but does generate errors for duplicated modifiers. Checks for other p
roblems, such as |
| 3183 * having the modifiers appear in the wrong order or specifying both 'const' a
nd 'final', are | 3419 * having the modifiers appear in the wrong order or specifying both 'const' a
nd 'final', are |
| 3184 * reported in one of the methods whose name is prefixed with `validateModifie
rsFor`. | 3420 * reported in one of the methods whose name is prefixed with `validateModifie
rsFor`. |
| 3421 * |
| 3185 * <pre> | 3422 * <pre> |
| 3186 * modifiers ::= | 3423 * modifiers ::= |
| 3187 * ('abstract' | 'const' | 'external' | 'factory' | 'final' | 'static' | 'var'
) | 3424 * ('abstract' | 'const' | 'external' | 'factory' | 'final' | 'static' | '
var')* |
| 3188 * </pre> | 3425 * </pre> |
| 3426 * |
| 3189 * @return the modifiers that were parsed | 3427 * @return the modifiers that were parsed |
| 3190 */ | 3428 */ |
| 3191 Modifiers parseModifiers() { | 3429 Modifiers parseModifiers() { |
| 3192 Modifiers modifiers = new Modifiers(); | 3430 Modifiers modifiers = new Modifiers(); |
| 3193 bool progress = true; | 3431 bool progress = true; |
| 3194 while (progress) { | 3432 while (progress) { |
| 3195 if (matches(Keyword.ABSTRACT) && !matches4(peek(), TokenType.PERIOD) && !m
atches4(peek(), TokenType.LT)) { | 3433 if (matches(Keyword.ABSTRACT) && !matches4(peek(), TokenType.PERIOD) && !m
atches4(peek(), TokenType.LT)) { |
| 3196 if (modifiers.abstractKeyword != null) { | 3434 if (modifiers.abstractKeyword != null) { |
| 3197 reportError7(ParserErrorCode.DUPLICATED_MODIFIER, [_currentToken.lexem
e]); | 3435 reportError7(ParserErrorCode.DUPLICATED_MODIFIER, [_currentToken.lexem
e]); |
| 3198 advance(); | 3436 advance(); |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3243 } | 3481 } |
| 3244 } else { | 3482 } else { |
| 3245 progress = false; | 3483 progress = false; |
| 3246 } | 3484 } |
| 3247 } | 3485 } |
| 3248 return modifiers; | 3486 return modifiers; |
| 3249 } | 3487 } |
| 3250 | 3488 |
| 3251 /** | 3489 /** |
| 3252 * Parse a multiplicative expression. | 3490 * Parse a multiplicative expression. |
| 3491 * |
| 3253 * <pre> | 3492 * <pre> |
| 3254 * multiplicativeExpression ::= | 3493 * multiplicativeExpression ::= |
| 3255 * unaryExpression (multiplicativeOperator unaryExpression) | 3494 * unaryExpression (multiplicativeOperator unaryExpression)* |
| 3256 * | 'super' (multiplicativeOperator unaryExpression)+ | 3495 * | 'super' (multiplicativeOperator unaryExpression)+ |
| 3257 * </pre> | 3496 * </pre> |
| 3497 * |
| 3258 * @return the multiplicative expression that was parsed | 3498 * @return the multiplicative expression that was parsed |
| 3259 */ | 3499 */ |
| 3260 Expression parseMultiplicativeExpression() { | 3500 Expression parseMultiplicativeExpression() { |
| 3261 Expression expression; | 3501 Expression expression; |
| 3262 if (matches(Keyword.SUPER) && _currentToken.next.type.isMultiplicativeOperat
or) { | 3502 if (matches(Keyword.SUPER) && _currentToken.next.type.isMultiplicativeOperat
or) { |
| 3263 expression = new SuperExpression.full(andAdvance); | 3503 expression = new SuperExpression.full(andAdvance); |
| 3264 } else { | 3504 } else { |
| 3265 expression = parseUnaryExpression(); | 3505 expression = parseUnaryExpression(); |
| 3266 } | 3506 } |
| 3267 while (_currentToken.type.isMultiplicativeOperator) { | 3507 while (_currentToken.type.isMultiplicativeOperator) { |
| 3268 Token operator = andAdvance; | 3508 Token operator = andAdvance; |
| 3269 expression = new BinaryExpression.full(expression, operator, parseUnaryExp
ression()); | 3509 expression = new BinaryExpression.full(expression, operator, parseUnaryExp
ression()); |
| 3270 } | 3510 } |
| 3271 return expression; | 3511 return expression; |
| 3272 } | 3512 } |
| 3273 | 3513 |
| 3274 /** | 3514 /** |
| 3275 * Parse a new expression. | 3515 * Parse a new expression. |
| 3516 * |
| 3276 * <pre> | 3517 * <pre> |
| 3277 * newExpression ::= | 3518 * newExpression ::= |
| 3278 * instanceCreationExpression | 3519 * instanceCreationExpression |
| 3279 * </pre> | 3520 * </pre> |
| 3521 * |
| 3280 * @return the new expression that was parsed | 3522 * @return the new expression that was parsed |
| 3281 */ | 3523 */ |
| 3282 InstanceCreationExpression parseNewExpression() => parseInstanceCreationExpres
sion(expect(Keyword.NEW)); | 3524 InstanceCreationExpression parseNewExpression() => parseInstanceCreationExpres
sion(expect(Keyword.NEW)); |
| 3283 | 3525 |
| 3284 /** | 3526 /** |
| 3285 * Parse a non-labeled statement. | 3527 * Parse a non-labeled statement. |
| 3528 * |
| 3286 * <pre> | 3529 * <pre> |
| 3287 * nonLabeledStatement ::= | 3530 * nonLabeledStatement ::= |
| 3288 * block | 3531 * block |
| 3289 * | assertStatement | 3532 * | assertStatement |
| 3290 * | breakStatement | 3533 * | breakStatement |
| 3291 * | continueStatement | 3534 * | continueStatement |
| 3292 * | doStatement | 3535 * | doStatement |
| 3293 * | forStatement | 3536 * | forStatement |
| 3294 * | ifStatement | 3537 * | ifStatement |
| 3295 * | returnStatement | 3538 * | returnStatement |
| 3296 * | switchStatement | 3539 * | switchStatement |
| 3297 * | tryStatement | 3540 * | tryStatement |
| 3298 * | whileStatement | 3541 * | whileStatement |
| 3299 * | variableDeclarationList ';' | 3542 * | variableDeclarationList ';' |
| 3300 * | expressionStatement | 3543 * | expressionStatement |
| 3301 * | functionSignature functionBody | 3544 * | functionSignature functionBody |
| 3302 * </pre> | 3545 * </pre> |
| 3546 * |
| 3303 * @return the non-labeled statement that was parsed | 3547 * @return the non-labeled statement that was parsed |
| 3304 */ | 3548 */ |
| 3305 Statement parseNonLabeledStatement() { | 3549 Statement parseNonLabeledStatement() { |
| 3306 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); | 3550 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); |
| 3307 if (matches5(TokenType.OPEN_CURLY_BRACKET)) { | 3551 if (matches5(TokenType.OPEN_CURLY_BRACKET)) { |
| 3308 if (matches4(peek(), TokenType.STRING)) { | 3552 if (matches4(peek(), TokenType.STRING)) { |
| 3309 Token afterString = skipStringLiteral(_currentToken.next); | 3553 Token afterString = skipStringLiteral(_currentToken.next); |
| 3310 if (afterString != null && identical(afterString.type, TokenType.COLON))
{ | 3554 if (afterString != null && identical(afterString.type, TokenType.COLON))
{ |
| 3311 return new ExpressionStatement.full(parseExpression2(), expect2(TokenT
ype.SEMICOLON)); | 3555 return new ExpressionStatement.full(parseExpression2(), expect2(TokenT
ype.SEMICOLON)); |
| 3312 } | 3556 } |
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3383 } else if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { | 3627 } else if (matches5(TokenType.CLOSE_CURLY_BRACKET)) { |
| 3384 reportError7(ParserErrorCode.MISSING_STATEMENT, []); | 3628 reportError7(ParserErrorCode.MISSING_STATEMENT, []); |
| 3385 return new EmptyStatement.full(createSyntheticToken2(TokenType.SEMICOLON))
; | 3629 return new EmptyStatement.full(createSyntheticToken2(TokenType.SEMICOLON))
; |
| 3386 } else { | 3630 } else { |
| 3387 return new ExpressionStatement.full(parseExpression2(), expect2(TokenType.
SEMICOLON)); | 3631 return new ExpressionStatement.full(parseExpression2(), expect2(TokenType.
SEMICOLON)); |
| 3388 } | 3632 } |
| 3389 } | 3633 } |
| 3390 | 3634 |
| 3391 /** | 3635 /** |
| 3392 * Parse a normal formal parameter. | 3636 * Parse a normal formal parameter. |
| 3637 * |
| 3393 * <pre> | 3638 * <pre> |
| 3394 * normalFormalParameter ::= | 3639 * normalFormalParameter ::= |
| 3395 * functionSignature | 3640 * functionSignature |
| 3396 * | fieldFormalParameter | 3641 * | fieldFormalParameter |
| 3397 * | simpleFormalParameter | 3642 * | simpleFormalParameter |
| 3643 * |
| 3398 * functionSignature: | 3644 * functionSignature: |
| 3399 * metadata returnType? identifier formalParameterList | 3645 * metadata returnType? identifier formalParameterList |
| 3646 * |
| 3400 * fieldFormalParameter ::= | 3647 * fieldFormalParameter ::= |
| 3401 * metadata finalConstVarOrType? 'this' '.' identifier | 3648 * metadata finalConstVarOrType? 'this' '.' identifier |
| 3649 * |
| 3402 * simpleFormalParameter ::= | 3650 * simpleFormalParameter ::= |
| 3403 * declaredIdentifier | 3651 * declaredIdentifier |
| 3404 * | metadata identifier | 3652 * | metadata identifier |
| 3405 * </pre> | 3653 * </pre> |
| 3654 * |
| 3406 * @return the normal formal parameter that was parsed | 3655 * @return the normal formal parameter that was parsed |
| 3407 */ | 3656 */ |
| 3408 NormalFormalParameter parseNormalFormalParameter() { | 3657 NormalFormalParameter parseNormalFormalParameter() { |
| 3409 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); | 3658 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); |
| 3410 FinalConstVarOrType holder = parseFinalConstVarOrType(true); | 3659 FinalConstVarOrType holder = parseFinalConstVarOrType(true); |
| 3411 Token thisKeyword = null; | 3660 Token thisKeyword = null; |
| 3412 Token period = null; | 3661 Token period = null; |
| 3413 if (matches(Keyword.THIS)) { | 3662 if (matches(Keyword.THIS)) { |
| 3414 thisKeyword = andAdvance; | 3663 thisKeyword = andAdvance; |
| 3415 period = expect2(TokenType.PERIOD); | 3664 period = expect2(TokenType.PERIOD); |
| (...skipping 10 matching lines...) Expand all Loading... |
| 3426 reportError8(ParserErrorCode.VOID_PARAMETER, type.name.beginToken, []); | 3675 reportError8(ParserErrorCode.VOID_PARAMETER, type.name.beginToken, []); |
| 3427 } | 3676 } |
| 3428 if (thisKeyword != null) { | 3677 if (thisKeyword != null) { |
| 3429 return new FieldFormalParameter.full(commentAndMetadata.comment, commentAn
dMetadata.metadata, holder.keyword, holder.type, thisKeyword, period, identifier
); | 3678 return new FieldFormalParameter.full(commentAndMetadata.comment, commentAn
dMetadata.metadata, holder.keyword, holder.type, thisKeyword, period, identifier
); |
| 3430 } | 3679 } |
| 3431 return new SimpleFormalParameter.full(commentAndMetadata.comment, commentAnd
Metadata.metadata, holder.keyword, holder.type, identifier); | 3680 return new SimpleFormalParameter.full(commentAndMetadata.comment, commentAnd
Metadata.metadata, holder.keyword, holder.type, identifier); |
| 3432 } | 3681 } |
| 3433 | 3682 |
| 3434 /** | 3683 /** |
| 3435 * Parse an operator declaration. | 3684 * Parse an operator declaration. |
| 3685 * |
| 3436 * <pre> | 3686 * <pre> |
| 3437 * operatorDeclaration ::= | 3687 * operatorDeclaration ::= |
| 3438 * operatorSignature (';' | functionBody) | 3688 * operatorSignature (';' | functionBody) |
| 3689 * |
| 3439 * operatorSignature ::= | 3690 * operatorSignature ::= |
| 3440 * 'external'? returnType? 'operator' operator formalParameterList | 3691 * 'external'? returnType? 'operator' operator formalParameterList |
| 3441 * </pre> | 3692 * </pre> |
| 3693 * |
| 3442 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 3694 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 3443 * declaration | 3695 * declaration |
| 3444 * @param externalKeyword the 'external' token | 3696 * @param externalKeyword the 'external' token |
| 3445 * @param the return type that has already been parsed, or `null` if there was
no return | 3697 * @param the return type that has already been parsed, or `null` if there was
no return |
| 3446 * type | 3698 * type |
| 3447 * @return the operator declaration that was parsed | 3699 * @return the operator declaration that was parsed |
| 3448 */ | 3700 */ |
| 3449 MethodDeclaration parseOperator(CommentAndMetadata commentAndMetadata, Token e
xternalKeyword, TypeName returnType) { | 3701 MethodDeclaration parseOperator(CommentAndMetadata commentAndMetadata, Token e
xternalKeyword, TypeName returnType) { |
| 3450 Token operatorKeyword; | 3702 Token operatorKeyword; |
| 3451 if (matches(Keyword.OPERATOR)) { | 3703 if (matches(Keyword.OPERATOR)) { |
| 3452 operatorKeyword = andAdvance; | 3704 operatorKeyword = andAdvance; |
| 3453 } else { | 3705 } else { |
| 3454 reportError8(ParserErrorCode.MISSING_KEYWORD_OPERATOR, _currentToken, []); | 3706 reportError8(ParserErrorCode.MISSING_KEYWORD_OPERATOR, _currentToken, []); |
| 3455 operatorKeyword = createSyntheticToken(Keyword.OPERATOR); | 3707 operatorKeyword = createSyntheticToken(Keyword.OPERATOR); |
| 3456 } | 3708 } |
| (...skipping 12 matching lines...) Expand all Loading... |
| 3469 validateFormalParameterList(parameters); | 3721 validateFormalParameterList(parameters); |
| 3470 FunctionBody body = parseFunctionBody(true, ParserErrorCode.MISSING_FUNCTION
_BODY, false); | 3722 FunctionBody body = parseFunctionBody(true, ParserErrorCode.MISSING_FUNCTION
_BODY, false); |
| 3471 if (externalKeyword != null && body is! EmptyFunctionBody) { | 3723 if (externalKeyword != null && body is! EmptyFunctionBody) { |
| 3472 reportError7(ParserErrorCode.EXTERNAL_OPERATOR_WITH_BODY, []); | 3724 reportError7(ParserErrorCode.EXTERNAL_OPERATOR_WITH_BODY, []); |
| 3473 } | 3725 } |
| 3474 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, null, returnType, null, operatorKeyword, name, p
arameters, body); | 3726 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, null, returnType, null, operatorKeyword, name, p
arameters, body); |
| 3475 } | 3727 } |
| 3476 | 3728 |
| 3477 /** | 3729 /** |
| 3478 * Parse a return type if one is given, otherwise return `null` without advanc
ing. | 3730 * Parse a return type if one is given, otherwise return `null` without advanc
ing. |
| 3731 * |
| 3479 * @return the return type that was parsed | 3732 * @return the return type that was parsed |
| 3480 */ | 3733 */ |
| 3481 TypeName parseOptionalReturnType() { | 3734 TypeName parseOptionalReturnType() { |
| 3482 if (matches(Keyword.VOID)) { | 3735 if (matches(Keyword.VOID)) { |
| 3483 return parseReturnType(); | 3736 return parseReturnType(); |
| 3484 } else if (matchesIdentifier() && !matches(Keyword.GET) && !matches(Keyword.
SET) && !matches(Keyword.OPERATOR) && (matchesIdentifier2(peek()) || matches4(pe
ek(), TokenType.LT))) { | 3737 } else if (matchesIdentifier() && !matches(Keyword.GET) && !matches(Keyword.
SET) && !matches(Keyword.OPERATOR) && (matchesIdentifier2(peek()) || matches4(pe
ek(), TokenType.LT))) { |
| 3485 return parseReturnType(); | 3738 return parseReturnType(); |
| 3486 } else if (matchesIdentifier() && matches4(peek(), TokenType.PERIOD) && matc
hesIdentifier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3),
TokenType.LT))) { | 3739 } else if (matchesIdentifier() && matches4(peek(), TokenType.PERIOD) && matc
hesIdentifier2(peek2(2)) && (matchesIdentifier2(peek2(3)) || matches4(peek2(3),
TokenType.LT))) { |
| 3487 return parseReturnType(); | 3740 return parseReturnType(); |
| 3488 } | 3741 } |
| 3489 return null; | 3742 return null; |
| 3490 } | 3743 } |
| 3491 | 3744 |
| 3492 /** | 3745 /** |
| 3493 * Parse a part or part-of directive. | 3746 * Parse a part or part-of directive. |
| 3747 * |
| 3494 * <pre> | 3748 * <pre> |
| 3495 * partDirective ::= | 3749 * partDirective ::= |
| 3496 * metadata 'part' stringLiteral ';' | 3750 * metadata 'part' stringLiteral ';' |
| 3751 * |
| 3497 * partOfDirective ::= | 3752 * partOfDirective ::= |
| 3498 * metadata 'part' 'of' identifier ';' | 3753 * metadata 'part' 'of' identifier ';' |
| 3499 * </pre> | 3754 * </pre> |
| 3755 * |
| 3500 * @param commentAndMetadata the metadata to be associated with the directive | 3756 * @param commentAndMetadata the metadata to be associated with the directive |
| 3501 * @return the part or part-of directive that was parsed | 3757 * @return the part or part-of directive that was parsed |
| 3502 */ | 3758 */ |
| 3503 Directive parsePartDirective(CommentAndMetadata commentAndMetadata) { | 3759 Directive parsePartDirective(CommentAndMetadata commentAndMetadata) { |
| 3504 Token partKeyword = expect(Keyword.PART); | 3760 Token partKeyword = expect(Keyword.PART); |
| 3505 if (matches2(_OF)) { | 3761 if (matches2(_OF)) { |
| 3506 Token ofKeyword = andAdvance; | 3762 Token ofKeyword = andAdvance; |
| 3507 LibraryIdentifier libraryName = parseLibraryName(ParserErrorCode.MISSING_N
AME_IN_PART_OF_DIRECTIVE, ofKeyword); | 3763 LibraryIdentifier libraryName = parseLibraryName(ParserErrorCode.MISSING_N
AME_IN_PART_OF_DIRECTIVE, ofKeyword); |
| 3508 Token semicolon = expect2(TokenType.SEMICOLON); | 3764 Token semicolon = expect2(TokenType.SEMICOLON); |
| 3509 return new PartOfDirective.full(commentAndMetadata.comment, commentAndMeta
data.metadata, partKeyword, ofKeyword, libraryName, semicolon); | 3765 return new PartOfDirective.full(commentAndMetadata.comment, commentAndMeta
data.metadata, partKeyword, ofKeyword, libraryName, semicolon); |
| 3510 } | 3766 } |
| 3511 StringLiteral partUri = parseStringLiteral(); | 3767 StringLiteral partUri = parseStringLiteral(); |
| 3512 Token semicolon = expect2(TokenType.SEMICOLON); | 3768 Token semicolon = expect2(TokenType.SEMICOLON); |
| 3513 return new PartDirective.full(commentAndMetadata.comment, commentAndMetadata
.metadata, partKeyword, partUri, semicolon); | 3769 return new PartDirective.full(commentAndMetadata.comment, commentAndMetadata
.metadata, partKeyword, partUri, semicolon); |
| 3514 } | 3770 } |
| 3515 | 3771 |
| 3516 /** | 3772 /** |
| 3517 * Parse a postfix expression. | 3773 * Parse a postfix expression. |
| 3774 * |
| 3518 * <pre> | 3775 * <pre> |
| 3519 * postfixExpression ::= | 3776 * postfixExpression ::= |
| 3520 * assignableExpression postfixOperator | 3777 * assignableExpression postfixOperator |
| 3521 * | primary selector | 3778 * | primary selector* |
| 3779 * |
| 3522 * selector ::= | 3780 * selector ::= |
| 3523 * assignableSelector | 3781 * assignableSelector |
| 3524 * | argumentList | 3782 * | argumentList |
| 3525 * </pre> | 3783 * </pre> |
| 3784 * |
| 3526 * @return the postfix expression that was parsed | 3785 * @return the postfix expression that was parsed |
| 3527 */ | 3786 */ |
| 3528 Expression parsePostfixExpression() { | 3787 Expression parsePostfixExpression() { |
| 3529 Expression operand = parseAssignableExpression(true); | 3788 Expression operand = parseAssignableExpression(true); |
| 3530 if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.PERIOD) ||
matches5(TokenType.OPEN_PAREN)) { | 3789 if (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.PERIOD) ||
matches5(TokenType.OPEN_PAREN)) { |
| 3531 do { | 3790 do { |
| 3532 if (matches5(TokenType.OPEN_PAREN)) { | 3791 if (matches5(TokenType.OPEN_PAREN)) { |
| 3533 ArgumentList argumentList = parseArgumentList(); | 3792 ArgumentList argumentList = parseArgumentList(); |
| 3534 if (operand is PropertyAccess) { | 3793 if (operand is PropertyAccess) { |
| 3535 PropertyAccess access = operand as PropertyAccess; | 3794 PropertyAccess access = operand as PropertyAccess; |
| 3536 operand = new MethodInvocation.full(access.target, access.operator,
access.propertyName, argumentList); | 3795 operand = new MethodInvocation.full(access.target, access.operator,
access.propertyName, argumentList); |
| 3537 } else { | 3796 } else { |
| 3538 operand = new FunctionExpressionInvocation.full(operand, argumentLis
t); | 3797 operand = new FunctionExpressionInvocation.full(operand, argumentLis
t); |
| 3539 } | 3798 } |
| 3540 } else { | 3799 } else { |
| 3541 operand = parseAssignableSelector(operand, true); | 3800 operand = parseAssignableSelector(operand, true); |
| 3542 } | 3801 } |
| 3543 } while (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.PER
IOD) || matches5(TokenType.OPEN_PAREN)); | 3802 } while (matches5(TokenType.OPEN_SQUARE_BRACKET) || matches5(TokenType.PER
IOD) || matches5(TokenType.OPEN_PAREN)); |
| 3544 return operand; | 3803 return operand; |
| 3545 } | 3804 } |
| 3546 if (!_currentToken.type.isIncrementOperator) { | 3805 if (!_currentToken.type.isIncrementOperator) { |
| 3547 return operand; | 3806 return operand; |
| 3548 } | 3807 } |
| 3549 if (operand is FunctionExpressionInvocation) { | 3808 if (operand is Literal || operand is FunctionExpressionInvocation) { |
| 3550 reportError7(ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, []); | 3809 reportError7(ParserErrorCode.MISSING_ASSIGNABLE_SELECTOR, []); |
| 3551 } | 3810 } |
| 3552 Token operator = andAdvance; | 3811 Token operator = andAdvance; |
| 3553 return new PostfixExpression.full(operand, operator); | 3812 return new PostfixExpression.full(operand, operator); |
| 3554 } | 3813 } |
| 3555 | 3814 |
| 3556 /** | 3815 /** |
| 3557 * Parse a prefixed identifier. | 3816 * Parse a prefixed identifier. |
| 3817 * |
| 3558 * <pre> | 3818 * <pre> |
| 3559 * prefixedIdentifier ::= | 3819 * prefixedIdentifier ::= |
| 3560 * identifier ('.' identifier)? | 3820 * identifier ('.' identifier)? |
| 3561 * </pre> | 3821 * </pre> |
| 3822 * |
| 3562 * @return the prefixed identifier that was parsed | 3823 * @return the prefixed identifier that was parsed |
| 3563 */ | 3824 */ |
| 3564 Identifier parsePrefixedIdentifier() { | 3825 Identifier parsePrefixedIdentifier() { |
| 3565 SimpleIdentifier qualifier = parseSimpleIdentifier(); | 3826 SimpleIdentifier qualifier = parseSimpleIdentifier(); |
| 3566 if (!matches5(TokenType.PERIOD)) { | 3827 if (!matches5(TokenType.PERIOD)) { |
| 3567 return qualifier; | 3828 return qualifier; |
| 3568 } | 3829 } |
| 3569 Token period = andAdvance; | 3830 Token period = andAdvance; |
| 3570 SimpleIdentifier qualified = parseSimpleIdentifier(); | 3831 SimpleIdentifier qualified = parseSimpleIdentifier(); |
| 3571 return new PrefixedIdentifier.full(qualifier, period, qualified); | 3832 return new PrefixedIdentifier.full(qualifier, period, qualified); |
| 3572 } | 3833 } |
| 3573 | 3834 |
| 3574 /** | 3835 /** |
| 3575 * Parse a primary expression. | 3836 * Parse a primary expression. |
| 3837 * |
| 3576 * <pre> | 3838 * <pre> |
| 3577 * primary ::= | 3839 * primary ::= |
| 3578 * thisExpression | 3840 * thisExpression |
| 3579 * | 'super' assignableSelector | 3841 * | 'super' assignableSelector |
| 3580 * | functionExpression | 3842 * | functionExpression |
| 3581 * | literal | 3843 * | literal |
| 3582 * | identifier | 3844 * | identifier |
| 3583 * | newExpression | 3845 * | newExpression |
| 3584 * | constObjectExpression | 3846 * | constObjectExpression |
| 3585 * | '(' expression ')' | 3847 * | '(' expression ')' |
| 3586 * | argumentDefinitionTest | 3848 * | argumentDefinitionTest |
| 3849 * |
| 3587 * literal ::= | 3850 * literal ::= |
| 3588 * nullLiteral | 3851 * nullLiteral |
| 3589 * | booleanLiteral | 3852 * | booleanLiteral |
| 3590 * | numericLiteral | 3853 * | numericLiteral |
| 3591 * | stringLiteral | 3854 * | stringLiteral |
| 3592 * | mapLiteral | 3855 * | mapLiteral |
| 3593 * | listLiteral | 3856 * | listLiteral |
| 3594 * </pre> | 3857 * </pre> |
| 3858 * |
| 3595 * @return the primary expression that was parsed | 3859 * @return the primary expression that was parsed |
| 3596 */ | 3860 */ |
| 3597 Expression parsePrimaryExpression() { | 3861 Expression parsePrimaryExpression() { |
| 3598 if (matches(Keyword.THIS)) { | 3862 if (matches(Keyword.THIS)) { |
| 3599 return new ThisExpression.full(andAdvance); | 3863 return new ThisExpression.full(andAdvance); |
| 3600 } else if (matches(Keyword.SUPER)) { | 3864 } else if (matches(Keyword.SUPER)) { |
| 3601 return parseAssignableSelector(new SuperExpression.full(andAdvance), false
); | 3865 return parseAssignableSelector(new SuperExpression.full(andAdvance), false
); |
| 3602 } else if (matches(Keyword.NULL)) { | 3866 } else if (matches(Keyword.NULL)) { |
| 3603 return new NullLiteral.full(andAdvance); | 3867 return new NullLiteral.full(andAdvance); |
| 3604 } else if (matches(Keyword.FALSE)) { | 3868 } else if (matches(Keyword.FALSE)) { |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3658 advance(); | 3922 advance(); |
| 3659 return parsePrimaryExpression(); | 3923 return parsePrimaryExpression(); |
| 3660 } else { | 3924 } else { |
| 3661 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); | 3925 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); |
| 3662 return createSyntheticIdentifier(); | 3926 return createSyntheticIdentifier(); |
| 3663 } | 3927 } |
| 3664 } | 3928 } |
| 3665 | 3929 |
| 3666 /** | 3930 /** |
| 3667 * Parse a redirecting constructor invocation. | 3931 * Parse a redirecting constructor invocation. |
| 3932 * |
| 3668 * <pre> | 3933 * <pre> |
| 3669 * redirectingConstructorInvocation ::= | 3934 * redirectingConstructorInvocation ::= |
| 3670 * 'this' ('.' identifier)? arguments | 3935 * 'this' ('.' identifier)? arguments |
| 3671 * </pre> | 3936 * </pre> |
| 3937 * |
| 3672 * @return the redirecting constructor invocation that was parsed | 3938 * @return the redirecting constructor invocation that was parsed |
| 3673 */ | 3939 */ |
| 3674 RedirectingConstructorInvocation parseRedirectingConstructorInvocation() { | 3940 RedirectingConstructorInvocation parseRedirectingConstructorInvocation() { |
| 3675 Token keyword = expect(Keyword.THIS); | 3941 Token keyword = expect(Keyword.THIS); |
| 3676 Token period = null; | 3942 Token period = null; |
| 3677 SimpleIdentifier constructorName = null; | 3943 SimpleIdentifier constructorName = null; |
| 3678 if (matches5(TokenType.PERIOD)) { | 3944 if (matches5(TokenType.PERIOD)) { |
| 3679 period = andAdvance; | 3945 period = andAdvance; |
| 3680 constructorName = parseSimpleIdentifier(); | 3946 constructorName = parseSimpleIdentifier(); |
| 3681 } | 3947 } |
| 3682 ArgumentList argumentList = parseArgumentList(); | 3948 ArgumentList argumentList = parseArgumentList(); |
| 3683 return new RedirectingConstructorInvocation.full(keyword, period, constructo
rName, argumentList); | 3949 return new RedirectingConstructorInvocation.full(keyword, period, constructo
rName, argumentList); |
| 3684 } | 3950 } |
| 3685 | 3951 |
| 3686 /** | 3952 /** |
| 3687 * Parse a relational expression. | 3953 * Parse a relational expression. |
| 3954 * |
| 3688 * <pre> | 3955 * <pre> |
| 3689 * relationalExpression ::= | 3956 * relationalExpression ::= |
| 3690 * shiftExpression ('is' '!'? type | 'as' type | relationalOperator shiftExpre
ssion)? | 3957 * shiftExpression ('is' '!'? type | 'as' type | relationalOperator shiftE
xpression)? |
| 3691 * | 'super' relationalOperator shiftExpression | 3958 * | 'super' relationalOperator shiftExpression |
| 3692 * </pre> | 3959 * </pre> |
| 3960 * |
| 3693 * @return the relational expression that was parsed | 3961 * @return the relational expression that was parsed |
| 3694 */ | 3962 */ |
| 3695 Expression parseRelationalExpression() { | 3963 Expression parseRelationalExpression() { |
| 3696 if (matches(Keyword.SUPER) && _currentToken.next.type.isRelationalOperator)
{ | 3964 if (matches(Keyword.SUPER) && _currentToken.next.type.isRelationalOperator)
{ |
| 3697 Expression expression = new SuperExpression.full(andAdvance); | 3965 Expression expression = new SuperExpression.full(andAdvance); |
| 3698 Token operator = andAdvance; | 3966 Token operator = andAdvance; |
| 3699 expression = new BinaryExpression.full(expression, operator, parseShiftExp
ression()); | 3967 expression = new BinaryExpression.full(expression, operator, parseShiftExp
ression()); |
| 3700 return expression; | 3968 return expression; |
| 3701 } | 3969 } |
| 3702 Expression expression = parseShiftExpression(); | 3970 Expression expression = parseShiftExpression(); |
| 3703 if (matches(Keyword.AS)) { | 3971 if (matches(Keyword.AS)) { |
| 3704 Token asOperator = andAdvance; | 3972 Token asOperator = andAdvance; |
| 3705 expression = new AsExpression.full(expression, asOperator, parseTypeName()
); | 3973 expression = new AsExpression.full(expression, asOperator, parseTypeName()
); |
| 3706 } else if (matches(Keyword.IS)) { | 3974 } else if (matches(Keyword.IS)) { |
| 3707 Token isOperator = andAdvance; | 3975 Token isOperator = andAdvance; |
| 3708 Token notOperator = null; | 3976 Token notOperator = null; |
| 3709 if (matches5(TokenType.BANG)) { | 3977 if (matches5(TokenType.BANG)) { |
| 3710 notOperator = andAdvance; | 3978 notOperator = andAdvance; |
| 3711 } | 3979 } |
| 3712 expression = new IsExpression.full(expression, isOperator, notOperator, pa
rseTypeName()); | 3980 expression = new IsExpression.full(expression, isOperator, notOperator, pa
rseTypeName()); |
| 3713 } else if (_currentToken.type.isRelationalOperator) { | 3981 } else if (_currentToken.type.isRelationalOperator) { |
| 3714 Token operator = andAdvance; | 3982 Token operator = andAdvance; |
| 3715 expression = new BinaryExpression.full(expression, operator, parseShiftExp
ression()); | 3983 expression = new BinaryExpression.full(expression, operator, parseShiftExp
ression()); |
| 3716 } | 3984 } |
| 3717 return expression; | 3985 return expression; |
| 3718 } | 3986 } |
| 3719 | 3987 |
| 3720 /** | 3988 /** |
| 3721 * Parse a rethrow expression. | 3989 * Parse a rethrow expression. |
| 3990 * |
| 3722 * <pre> | 3991 * <pre> |
| 3723 * rethrowExpression ::= | 3992 * rethrowExpression ::= |
| 3724 * 'rethrow' | 3993 * 'rethrow' |
| 3725 * </pre> | 3994 * </pre> |
| 3995 * |
| 3726 * @return the rethrow expression that was parsed | 3996 * @return the rethrow expression that was parsed |
| 3727 */ | 3997 */ |
| 3728 Expression parseRethrowExpression() => new RethrowExpression.full(expect(Keywo
rd.RETHROW)); | 3998 Expression parseRethrowExpression() => new RethrowExpression.full(expect(Keywo
rd.RETHROW)); |
| 3729 | 3999 |
| 3730 /** | 4000 /** |
| 3731 * Parse a return statement. | 4001 * Parse a return statement. |
| 4002 * |
| 3732 * <pre> | 4003 * <pre> |
| 3733 * returnStatement ::= | 4004 * returnStatement ::= |
| 3734 * 'return' expression? ';' | 4005 * 'return' expression? ';' |
| 3735 * </pre> | 4006 * </pre> |
| 4007 * |
| 3736 * @return the return statement that was parsed | 4008 * @return the return statement that was parsed |
| 3737 */ | 4009 */ |
| 3738 Statement parseReturnStatement() { | 4010 Statement parseReturnStatement() { |
| 3739 Token returnKeyword = expect(Keyword.RETURN); | 4011 Token returnKeyword = expect(Keyword.RETURN); |
| 3740 if (matches5(TokenType.SEMICOLON)) { | 4012 if (matches5(TokenType.SEMICOLON)) { |
| 3741 return new ReturnStatement.full(returnKeyword, null, andAdvance); | 4013 return new ReturnStatement.full(returnKeyword, null, andAdvance); |
| 3742 } | 4014 } |
| 3743 Expression expression = parseExpression2(); | 4015 Expression expression = parseExpression2(); |
| 3744 Token semicolon = expect2(TokenType.SEMICOLON); | 4016 Token semicolon = expect2(TokenType.SEMICOLON); |
| 3745 return new ReturnStatement.full(returnKeyword, expression, semicolon); | 4017 return new ReturnStatement.full(returnKeyword, expression, semicolon); |
| 3746 } | 4018 } |
| 3747 | 4019 |
| 3748 /** | 4020 /** |
| 3749 * Parse a return type. | 4021 * Parse a return type. |
| 4022 * |
| 3750 * <pre> | 4023 * <pre> |
| 3751 * returnType ::= | 4024 * returnType ::= |
| 3752 * 'void' | 4025 * 'void' |
| 3753 * | type | 4026 * | type |
| 3754 * </pre> | 4027 * </pre> |
| 4028 * |
| 3755 * @return the return type that was parsed | 4029 * @return the return type that was parsed |
| 3756 */ | 4030 */ |
| 3757 TypeName parseReturnType() { | 4031 TypeName parseReturnType() { |
| 3758 if (matches(Keyword.VOID)) { | 4032 if (matches(Keyword.VOID)) { |
| 3759 return new TypeName.full(new SimpleIdentifier.full(andAdvance), null); | 4033 return new TypeName.full(new SimpleIdentifier.full(andAdvance), null); |
| 3760 } else { | 4034 } else { |
| 3761 return parseTypeName(); | 4035 return parseTypeName(); |
| 3762 } | 4036 } |
| 3763 } | 4037 } |
| 3764 | 4038 |
| 3765 /** | 4039 /** |
| 3766 * Parse a setter. | 4040 * Parse a setter. |
| 4041 * |
| 3767 * <pre> | 4042 * <pre> |
| 3768 * setter ::= | 4043 * setter ::= |
| 3769 * setterSignature functionBody? | 4044 * setterSignature functionBody? |
| 4045 * |
| 3770 * setterSignature ::= | 4046 * setterSignature ::= |
| 3771 * 'external'? 'static'? returnType? 'set' identifier formalParameterList | 4047 * 'external'? 'static'? returnType? 'set' identifier formalParameterList |
| 3772 * </pre> | 4048 * </pre> |
| 4049 * |
| 3773 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the | 4050 * @param commentAndMetadata the documentation comment and metadata to be asso
ciated with the |
| 3774 * declaration | 4051 * declaration |
| 3775 * @param externalKeyword the 'external' token | 4052 * @param externalKeyword the 'external' token |
| 3776 * @param staticKeyword the static keyword, or `null` if the setter is not sta
tic | 4053 * @param staticKeyword the static keyword, or `null` if the setter is not sta
tic |
| 3777 * @param the return type that has already been parsed, or `null` if there was
no return | 4054 * @param the return type that has already been parsed, or `null` if there was
no return |
| 3778 * type | 4055 * type |
| 3779 * @return the setter that was parsed | 4056 * @return the setter that was parsed |
| 3780 */ | 4057 */ |
| 3781 MethodDeclaration parseSetter(CommentAndMetadata commentAndMetadata, Token ext
ernalKeyword, Token staticKeyword, TypeName returnType) { | 4058 MethodDeclaration parseSetter(CommentAndMetadata commentAndMetadata, Token ext
ernalKeyword, Token staticKeyword, TypeName returnType) { |
| 3782 Token propertyKeyword = expect(Keyword.SET); | 4059 Token propertyKeyword = expect(Keyword.SET); |
| 3783 SimpleIdentifier name = parseSimpleIdentifier(); | 4060 SimpleIdentifier name = parseSimpleIdentifier(); |
| 3784 FormalParameterList parameters = parseFormalParameterList(); | 4061 FormalParameterList parameters = parseFormalParameterList(); |
| 3785 validateFormalParameterList(parameters); | 4062 validateFormalParameterList(parameters); |
| 3786 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.STATIC_SETTER_WITHOUT_BODY, false); | 4063 FunctionBody body = parseFunctionBody(externalKeyword != null || staticKeywo
rd == null, ParserErrorCode.STATIC_SETTER_WITHOUT_BODY, false); |
| 3787 if (externalKeyword != null && body is! EmptyFunctionBody) { | 4064 if (externalKeyword != null && body is! EmptyFunctionBody) { |
| 3788 reportError7(ParserErrorCode.EXTERNAL_SETTER_WITH_BODY, []); | 4065 reportError7(ParserErrorCode.EXTERNAL_SETTER_WITH_BODY, []); |
| 3789 } | 4066 } |
| 3790 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, propertyKeyword, null
, name, parameters, body); | 4067 return new MethodDeclaration.full(commentAndMetadata.comment, commentAndMeta
data.metadata, externalKeyword, staticKeyword, returnType, propertyKeyword, null
, name, parameters, body); |
| 3791 } | 4068 } |
| 3792 | 4069 |
| 3793 /** | 4070 /** |
| 3794 * Parse a shift expression. | 4071 * Parse a shift expression. |
| 4072 * |
| 3795 * <pre> | 4073 * <pre> |
| 3796 * shiftExpression ::= | 4074 * shiftExpression ::= |
| 3797 * additiveExpression (shiftOperator additiveExpression) | 4075 * additiveExpression (shiftOperator additiveExpression)* |
| 3798 * | 'super' (shiftOperator additiveExpression)+ | 4076 * | 'super' (shiftOperator additiveExpression)+ |
| 3799 * </pre> | 4077 * </pre> |
| 4078 * |
| 3800 * @return the shift expression that was parsed | 4079 * @return the shift expression that was parsed |
| 3801 */ | 4080 */ |
| 3802 Expression parseShiftExpression() { | 4081 Expression parseShiftExpression() { |
| 3803 Expression expression; | 4082 Expression expression; |
| 3804 if (matches(Keyword.SUPER) && _currentToken.next.type.isShiftOperator) { | 4083 if (matches(Keyword.SUPER) && _currentToken.next.type.isShiftOperator) { |
| 3805 expression = new SuperExpression.full(andAdvance); | 4084 expression = new SuperExpression.full(andAdvance); |
| 3806 } else { | 4085 } else { |
| 3807 expression = parseAdditiveExpression(); | 4086 expression = parseAdditiveExpression(); |
| 3808 } | 4087 } |
| 3809 while (_currentToken.type.isShiftOperator) { | 4088 while (_currentToken.type.isShiftOperator) { |
| 3810 Token operator = andAdvance; | 4089 Token operator = andAdvance; |
| 3811 expression = new BinaryExpression.full(expression, operator, parseAdditive
Expression()); | 4090 expression = new BinaryExpression.full(expression, operator, parseAdditive
Expression()); |
| 3812 } | 4091 } |
| 3813 return expression; | 4092 return expression; |
| 3814 } | 4093 } |
| 3815 | 4094 |
| 3816 /** | 4095 /** |
| 3817 * Parse a simple identifier. | 4096 * Parse a simple identifier. |
| 4097 * |
| 3818 * <pre> | 4098 * <pre> |
| 3819 * identifier ::= | 4099 * identifier ::= |
| 3820 * IDENTIFIER | 4100 * IDENTIFIER |
| 3821 * </pre> | 4101 * </pre> |
| 4102 * |
| 3822 * @return the simple identifier that was parsed | 4103 * @return the simple identifier that was parsed |
| 3823 */ | 4104 */ |
| 3824 SimpleIdentifier parseSimpleIdentifier() { | 4105 SimpleIdentifier parseSimpleIdentifier() { |
| 3825 if (matchesIdentifier()) { | 4106 if (matchesIdentifier()) { |
| 3826 return new SimpleIdentifier.full(andAdvance); | 4107 return new SimpleIdentifier.full(andAdvance); |
| 3827 } | 4108 } |
| 3828 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); | 4109 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); |
| 3829 return createSyntheticIdentifier(); | 4110 return createSyntheticIdentifier(); |
| 3830 } | 4111 } |
| 3831 | 4112 |
| 3832 /** | 4113 /** |
| 3833 * Parse a statement. | 4114 * Parse a statement. |
| 4115 * |
| 3834 * <pre> | 4116 * <pre> |
| 3835 * statement ::= | 4117 * statement ::= |
| 3836 * label* nonLabeledStatement | 4118 * label* nonLabeledStatement |
| 3837 * </pre> | 4119 * </pre> |
| 4120 * |
| 3838 * @return the statement that was parsed | 4121 * @return the statement that was parsed |
| 3839 */ | 4122 */ |
| 3840 Statement parseStatement2() { | 4123 Statement parseStatement2() { |
| 3841 List<Label> labels = new List<Label>(); | 4124 List<Label> labels = new List<Label>(); |
| 3842 while (matchesIdentifier() && matches4(peek(), TokenType.COLON)) { | 4125 while (matchesIdentifier() && matches4(peek(), TokenType.COLON)) { |
| 3843 SimpleIdentifier label = parseSimpleIdentifier(); | 4126 SimpleIdentifier label = parseSimpleIdentifier(); |
| 3844 Token colon = expect2(TokenType.COLON); | 4127 Token colon = expect2(TokenType.COLON); |
| 3845 labels.add(new Label.full(label, colon)); | 4128 labels.add(new Label.full(label, colon)); |
| 3846 } | 4129 } |
| 3847 Statement statement = parseNonLabeledStatement(); | 4130 Statement statement = parseNonLabeledStatement(); |
| 3848 if (labels.isEmpty) { | 4131 if (labels.isEmpty) { |
| 3849 return statement; | 4132 return statement; |
| 3850 } | 4133 } |
| 3851 return new LabeledStatement.full(labels, statement); | 4134 return new LabeledStatement.full(labels, statement); |
| 3852 } | 4135 } |
| 3853 | 4136 |
| 3854 /** | 4137 /** |
| 3855 * Parse a list of statements within a switch statement. | 4138 * Parse a list of statements within a switch statement. |
| 4139 * |
| 3856 * <pre> | 4140 * <pre> |
| 3857 * statements ::= | 4141 * statements ::= |
| 3858 * statement | 4142 * statement* |
| 3859 * </pre> | 4143 * </pre> |
| 4144 * |
| 3860 * @return the statements that were parsed | 4145 * @return the statements that were parsed |
| 3861 */ | 4146 */ |
| 3862 List<Statement> parseStatements2() { | 4147 List<Statement> parseStatements2() { |
| 3863 List<Statement> statements = new List<Statement>(); | 4148 List<Statement> statements = new List<Statement>(); |
| 3864 Token statementStart = _currentToken; | 4149 Token statementStart = _currentToken; |
| 3865 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET)
&& !isSwitchMember()) { | 4150 while (!matches5(TokenType.EOF) && !matches5(TokenType.CLOSE_CURLY_BRACKET)
&& !isSwitchMember()) { |
| 3866 statements.add(parseStatement2()); | 4151 statements.add(parseStatement2()); |
| 3867 if (identical(_currentToken, statementStart)) { | 4152 if (identical(_currentToken, statementStart)) { |
| 3868 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); | 4153 reportError8(ParserErrorCode.UNEXPECTED_TOKEN, _currentToken, [_currentT
oken.lexeme]); |
| 3869 advance(); | 4154 advance(); |
| 3870 } | 4155 } |
| 3871 statementStart = _currentToken; | 4156 statementStart = _currentToken; |
| 3872 } | 4157 } |
| 3873 return statements; | 4158 return statements; |
| 3874 } | 4159 } |
| 3875 | 4160 |
| 3876 /** | 4161 /** |
| 3877 * Parse a string literal that contains interpolations. | 4162 * Parse a string literal that contains interpolations. |
| 4163 * |
| 3878 * @return the string literal that was parsed | 4164 * @return the string literal that was parsed |
| 3879 */ | 4165 */ |
| 3880 StringInterpolation parseStringInterpolation(Token string) { | 4166 StringInterpolation parseStringInterpolation(Token string) { |
| 3881 List<InterpolationElement> elements = new List<InterpolationElement>(); | 4167 List<InterpolationElement> elements = new List<InterpolationElement>(); |
| 3882 elements.add(new InterpolationString.full(string, computeStringValue(string.
lexeme))); | 4168 elements.add(new InterpolationString.full(string, computeStringValue(string.
lexeme))); |
| 3883 while (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION) || matches5(Token
Type.STRING_INTERPOLATION_IDENTIFIER)) { | 4169 while (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION) || matches5(Token
Type.STRING_INTERPOLATION_IDENTIFIER)) { |
| 3884 if (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION)) { | 4170 if (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION)) { |
| 3885 Token openToken = andAdvance; | 4171 Token openToken = andAdvance; |
| 3886 Expression expression = parseExpression2(); | 4172 Expression expression = parseExpression2(); |
| 3887 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); | 4173 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); |
| (...skipping 11 matching lines...) Expand all Loading... |
| 3899 if (matches5(TokenType.STRING)) { | 4185 if (matches5(TokenType.STRING)) { |
| 3900 string = andAdvance; | 4186 string = andAdvance; |
| 3901 elements.add(new InterpolationString.full(string, computeStringValue(str
ing.lexeme))); | 4187 elements.add(new InterpolationString.full(string, computeStringValue(str
ing.lexeme))); |
| 3902 } | 4188 } |
| 3903 } | 4189 } |
| 3904 return new StringInterpolation.full(elements); | 4190 return new StringInterpolation.full(elements); |
| 3905 } | 4191 } |
| 3906 | 4192 |
| 3907 /** | 4193 /** |
| 3908 * Parse a string literal. | 4194 * Parse a string literal. |
| 4195 * |
| 3909 * <pre> | 4196 * <pre> |
| 3910 * stringLiteral ::= | 4197 * stringLiteral ::= |
| 3911 * MULTI_LINE_STRING+ | 4198 * MULTI_LINE_STRING+ |
| 3912 * | SINGLE_LINE_STRING+ | 4199 * | SINGLE_LINE_STRING+ |
| 3913 * </pre> | 4200 * </pre> |
| 4201 * |
| 3914 * @return the string literal that was parsed | 4202 * @return the string literal that was parsed |
| 3915 */ | 4203 */ |
| 3916 StringLiteral parseStringLiteral() { | 4204 StringLiteral parseStringLiteral() { |
| 3917 List<StringLiteral> strings = new List<StringLiteral>(); | 4205 List<StringLiteral> strings = new List<StringLiteral>(); |
| 3918 while (matches5(TokenType.STRING)) { | 4206 while (matches5(TokenType.STRING)) { |
| 3919 Token string = andAdvance; | 4207 Token string = andAdvance; |
| 3920 if (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION) || matches5(TokenT
ype.STRING_INTERPOLATION_IDENTIFIER)) { | 4208 if (matches5(TokenType.STRING_INTERPOLATION_EXPRESSION) || matches5(TokenT
ype.STRING_INTERPOLATION_IDENTIFIER)) { |
| 3921 strings.add(parseStringInterpolation(string)); | 4209 strings.add(parseStringInterpolation(string)); |
| 3922 } else { | 4210 } else { |
| 3923 strings.add(new SimpleStringLiteral.full(string, computeStringValue(stri
ng.lexeme))); | 4211 strings.add(new SimpleStringLiteral.full(string, computeStringValue(stri
ng.lexeme))); |
| 3924 } | 4212 } |
| 3925 } | 4213 } |
| 3926 if (strings.length < 1) { | 4214 if (strings.length < 1) { |
| 3927 reportError7(ParserErrorCode.EXPECTED_STRING_LITERAL, []); | 4215 reportError7(ParserErrorCode.EXPECTED_STRING_LITERAL, []); |
| 3928 return createSyntheticStringLiteral(); | 4216 return createSyntheticStringLiteral(); |
| 3929 } else if (strings.length == 1) { | 4217 } else if (strings.length == 1) { |
| 3930 return strings[0]; | 4218 return strings[0]; |
| 3931 } else { | 4219 } else { |
| 3932 return new AdjacentStrings.full(strings); | 4220 return new AdjacentStrings.full(strings); |
| 3933 } | 4221 } |
| 3934 } | 4222 } |
| 3935 | 4223 |
| 3936 /** | 4224 /** |
| 3937 * Parse a super constructor invocation. | 4225 * Parse a super constructor invocation. |
| 4226 * |
| 3938 * <pre> | 4227 * <pre> |
| 3939 * superConstructorInvocation ::= | 4228 * superConstructorInvocation ::= |
| 3940 * 'super' ('.' identifier)? arguments | 4229 * 'super' ('.' identifier)? arguments |
| 3941 * </pre> | 4230 * </pre> |
| 4231 * |
| 3942 * @return the super constructor invocation that was parsed | 4232 * @return the super constructor invocation that was parsed |
| 3943 */ | 4233 */ |
| 3944 SuperConstructorInvocation parseSuperConstructorInvocation() { | 4234 SuperConstructorInvocation parseSuperConstructorInvocation() { |
| 3945 Token keyword = expect(Keyword.SUPER); | 4235 Token keyword = expect(Keyword.SUPER); |
| 3946 Token period = null; | 4236 Token period = null; |
| 3947 SimpleIdentifier constructorName = null; | 4237 SimpleIdentifier constructorName = null; |
| 3948 if (matches5(TokenType.PERIOD)) { | 4238 if (matches5(TokenType.PERIOD)) { |
| 3949 period = andAdvance; | 4239 period = andAdvance; |
| 3950 constructorName = parseSimpleIdentifier(); | 4240 constructorName = parseSimpleIdentifier(); |
| 3951 } | 4241 } |
| 3952 ArgumentList argumentList = parseArgumentList(); | 4242 ArgumentList argumentList = parseArgumentList(); |
| 3953 return new SuperConstructorInvocation.full(keyword, period, constructorName,
argumentList); | 4243 return new SuperConstructorInvocation.full(keyword, period, constructorName,
argumentList); |
| 3954 } | 4244 } |
| 3955 | 4245 |
| 3956 /** | 4246 /** |
| 3957 * Parse a switch statement. | 4247 * Parse a switch statement. |
| 4248 * |
| 3958 * <pre> | 4249 * <pre> |
| 3959 * switchStatement ::= | 4250 * switchStatement ::= |
| 3960 * 'switch' '(' expression ')' '{' switchCase* defaultCase? '}' | 4251 * 'switch' '(' expression ')' '{' switchCase* defaultCase? '}' |
| 4252 * |
| 3961 * switchCase ::= | 4253 * switchCase ::= |
| 3962 * label* ('case' expression ':') statements | 4254 * label* ('case' expression ':') statements |
| 4255 * |
| 3963 * defaultCase ::= | 4256 * defaultCase ::= |
| 3964 * label* 'default' ':' statements | 4257 * label* 'default' ':' statements |
| 3965 * </pre> | 4258 * </pre> |
| 4259 * |
| 3966 * @return the switch statement that was parsed | 4260 * @return the switch statement that was parsed |
| 3967 */ | 4261 */ |
| 3968 SwitchStatement parseSwitchStatement() { | 4262 SwitchStatement parseSwitchStatement() { |
| 3969 bool wasInSwitch = _inSwitch; | 4263 bool wasInSwitch = _inSwitch; |
| 3970 _inSwitch = true; | 4264 _inSwitch = true; |
| 3971 try { | 4265 try { |
| 3972 Set<String> definedLabels = new Set<String>(); | 4266 Set<String> definedLabels = new Set<String>(); |
| 3973 Token keyword = expect(Keyword.SWITCH); | 4267 Token keyword = expect(Keyword.SWITCH); |
| 3974 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 4268 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 3975 Expression expression = parseExpression2(); | 4269 Expression expression = parseExpression2(); |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4014 } | 4308 } |
| 4015 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); | 4309 Token rightBracket = expect2(TokenType.CLOSE_CURLY_BRACKET); |
| 4016 return new SwitchStatement.full(keyword, leftParenthesis, expression, righ
tParenthesis, leftBracket, members, rightBracket); | 4310 return new SwitchStatement.full(keyword, leftParenthesis, expression, righ
tParenthesis, leftBracket, members, rightBracket); |
| 4017 } finally { | 4311 } finally { |
| 4018 _inSwitch = wasInSwitch; | 4312 _inSwitch = wasInSwitch; |
| 4019 } | 4313 } |
| 4020 } | 4314 } |
| 4021 | 4315 |
| 4022 /** | 4316 /** |
| 4023 * Parse a throw expression. | 4317 * Parse a throw expression. |
| 4318 * |
| 4024 * <pre> | 4319 * <pre> |
| 4025 * throwExpression ::= | 4320 * throwExpression ::= |
| 4026 * 'throw' expression | 4321 * 'throw' expression |
| 4027 * </pre> | 4322 * </pre> |
| 4323 * |
| 4028 * @return the throw expression that was parsed | 4324 * @return the throw expression that was parsed |
| 4029 */ | 4325 */ |
| 4030 Expression parseThrowExpression() { | 4326 Expression parseThrowExpression() { |
| 4031 Token keyword = expect(Keyword.THROW); | 4327 Token keyword = expect(Keyword.THROW); |
| 4032 if (matches5(TokenType.SEMICOLON) || matches5(TokenType.CLOSE_PAREN)) { | 4328 if (matches5(TokenType.SEMICOLON) || matches5(TokenType.CLOSE_PAREN)) { |
| 4033 reportError8(ParserErrorCode.MISSING_EXPRESSION_IN_THROW, _currentToken, [
]); | 4329 reportError8(ParserErrorCode.MISSING_EXPRESSION_IN_THROW, _currentToken, [
]); |
| 4034 return new ThrowExpression.full(keyword, createSyntheticIdentifier()); | 4330 return new ThrowExpression.full(keyword, createSyntheticIdentifier()); |
| 4035 } | 4331 } |
| 4036 Expression expression = parseExpression2(); | 4332 Expression expression = parseExpression2(); |
| 4037 return new ThrowExpression.full(keyword, expression); | 4333 return new ThrowExpression.full(keyword, expression); |
| 4038 } | 4334 } |
| 4039 | 4335 |
| 4040 /** | 4336 /** |
| 4041 * Parse a throw expression. | 4337 * Parse a throw expression. |
| 4338 * |
| 4042 * <pre> | 4339 * <pre> |
| 4043 * throwExpressionWithoutCascade ::= | 4340 * throwExpressionWithoutCascade ::= |
| 4044 * 'throw' expressionWithoutCascade | 4341 * 'throw' expressionWithoutCascade |
| 4045 * </pre> | 4342 * </pre> |
| 4343 * |
| 4046 * @return the throw expression that was parsed | 4344 * @return the throw expression that was parsed |
| 4047 */ | 4345 */ |
| 4048 Expression parseThrowExpressionWithoutCascade() { | 4346 Expression parseThrowExpressionWithoutCascade() { |
| 4049 Token keyword = expect(Keyword.THROW); | 4347 Token keyword = expect(Keyword.THROW); |
| 4050 if (matches5(TokenType.SEMICOLON) || matches5(TokenType.CLOSE_PAREN)) { | 4348 if (matches5(TokenType.SEMICOLON) || matches5(TokenType.CLOSE_PAREN)) { |
| 4051 reportError8(ParserErrorCode.MISSING_EXPRESSION_IN_THROW, _currentToken, [
]); | 4349 reportError8(ParserErrorCode.MISSING_EXPRESSION_IN_THROW, _currentToken, [
]); |
| 4052 return new ThrowExpression.full(keyword, createSyntheticIdentifier()); | 4350 return new ThrowExpression.full(keyword, createSyntheticIdentifier()); |
| 4053 } | 4351 } |
| 4054 Expression expression = parseExpressionWithoutCascade(); | 4352 Expression expression = parseExpressionWithoutCascade(); |
| 4055 return new ThrowExpression.full(keyword, expression); | 4353 return new ThrowExpression.full(keyword, expression); |
| 4056 } | 4354 } |
| 4057 | 4355 |
| 4058 /** | 4356 /** |
| 4059 * Parse a try statement. | 4357 * Parse a try statement. |
| 4358 * |
| 4060 * <pre> | 4359 * <pre> |
| 4061 * tryStatement ::= | 4360 * tryStatement ::= |
| 4062 * 'try' block (onPart+ finallyPart? | finallyPart) | 4361 * 'try' block (onPart+ finallyPart? | finallyPart) |
| 4362 * |
| 4063 * onPart ::= | 4363 * onPart ::= |
| 4064 * catchPart block | 4364 * catchPart block |
| 4065 * | 'on' type catchPart? block | 4365 * | 'on' type catchPart? block |
| 4366 * |
| 4066 * catchPart ::= | 4367 * catchPart ::= |
| 4067 * 'catch' '(' identifier (',' identifier)? ')' | 4368 * 'catch' '(' identifier (',' identifier)? ')' |
| 4369 * |
| 4068 * finallyPart ::= | 4370 * finallyPart ::= |
| 4069 * 'finally' block | 4371 * 'finally' block |
| 4070 * </pre> | 4372 * </pre> |
| 4373 * |
| 4071 * @return the try statement that was parsed | 4374 * @return the try statement that was parsed |
| 4072 */ | 4375 */ |
| 4073 Statement parseTryStatement() { | 4376 Statement parseTryStatement() { |
| 4074 Token tryKeyword = expect(Keyword.TRY); | 4377 Token tryKeyword = expect(Keyword.TRY); |
| 4075 Block body = parseBlock(); | 4378 Block body = parseBlock(); |
| 4076 List<CatchClause> catchClauses = new List<CatchClause>(); | 4379 List<CatchClause> catchClauses = new List<CatchClause>(); |
| 4077 Block finallyClause = null; | 4380 Block finallyClause = null; |
| 4078 while (matches2(_ON) || matches(Keyword.CATCH)) { | 4381 while (matches2(_ON) || matches(Keyword.CATCH)) { |
| 4079 Token onKeyword = null; | 4382 Token onKeyword = null; |
| 4080 TypeName exceptionType = null; | 4383 TypeName exceptionType = null; |
| (...skipping 27 matching lines...) Expand all Loading... |
| 4108 } else { | 4411 } else { |
| 4109 if (catchClauses.isEmpty) { | 4412 if (catchClauses.isEmpty) { |
| 4110 reportError7(ParserErrorCode.MISSING_CATCH_OR_FINALLY, []); | 4413 reportError7(ParserErrorCode.MISSING_CATCH_OR_FINALLY, []); |
| 4111 } | 4414 } |
| 4112 } | 4415 } |
| 4113 return new TryStatement.full(tryKeyword, body, catchClauses, finallyKeyword,
finallyClause); | 4416 return new TryStatement.full(tryKeyword, body, catchClauses, finallyKeyword,
finallyClause); |
| 4114 } | 4417 } |
| 4115 | 4418 |
| 4116 /** | 4419 /** |
| 4117 * Parse a type alias. | 4420 * Parse a type alias. |
| 4421 * |
| 4118 * <pre> | 4422 * <pre> |
| 4119 * typeAlias ::= | 4423 * typeAlias ::= |
| 4120 * 'typedef' typeAliasBody | 4424 * 'typedef' typeAliasBody |
| 4425 * |
| 4121 * typeAliasBody ::= | 4426 * typeAliasBody ::= |
| 4122 * classTypeAlias | 4427 * classTypeAlias |
| 4123 * | functionTypeAlias | 4428 * | functionTypeAlias |
| 4429 * |
| 4124 * classTypeAlias ::= | 4430 * classTypeAlias ::= |
| 4125 * identifier typeParameters? '=' 'abstract'? mixinApplication | 4431 * identifier typeParameters? '=' 'abstract'? mixinApplication |
| 4432 * |
| 4126 * mixinApplication ::= | 4433 * mixinApplication ::= |
| 4127 * qualified withClause implementsClause? ';' | 4434 * qualified withClause implementsClause? ';' |
| 4435 * |
| 4128 * functionTypeAlias ::= | 4436 * functionTypeAlias ::= |
| 4129 * functionPrefix typeParameterList? formalParameterList ';' | 4437 * functionPrefix typeParameterList? formalParameterList ';' |
| 4438 * |
| 4130 * functionPrefix ::= | 4439 * functionPrefix ::= |
| 4131 * returnType? name | 4440 * returnType? name |
| 4132 * </pre> | 4441 * </pre> |
| 4442 * |
| 4133 * @param commentAndMetadata the metadata to be associated with the member | 4443 * @param commentAndMetadata the metadata to be associated with the member |
| 4134 * @return the type alias that was parsed | 4444 * @return the type alias that was parsed |
| 4135 */ | 4445 */ |
| 4136 TypeAlias parseTypeAlias(CommentAndMetadata commentAndMetadata) { | 4446 TypeAlias parseTypeAlias(CommentAndMetadata commentAndMetadata) { |
| 4137 Token keyword = expect(Keyword.TYPEDEF); | 4447 Token keyword = expect(Keyword.TYPEDEF); |
| 4138 if (matchesIdentifier()) { | 4448 if (matchesIdentifier()) { |
| 4139 Token next = peek(); | 4449 Token next = peek(); |
| 4140 if (matches4(next, TokenType.LT)) { | 4450 if (matches4(next, TokenType.LT)) { |
| 4141 next = skipTypeParameterList(next); | 4451 next = skipTypeParameterList(next); |
| 4142 if (next != null && matches4(next, TokenType.EQ)) { | 4452 if (next != null && matches4(next, TokenType.EQ)) { |
| 4143 return parseClassTypeAlias(commentAndMetadata, keyword); | 4453 return parseClassTypeAlias(commentAndMetadata, keyword); |
| 4144 } | 4454 } |
| 4145 } else if (matches4(next, TokenType.EQ)) { | 4455 } else if (matches4(next, TokenType.EQ)) { |
| 4146 return parseClassTypeAlias(commentAndMetadata, keyword); | 4456 return parseClassTypeAlias(commentAndMetadata, keyword); |
| 4147 } | 4457 } |
| 4148 } | 4458 } |
| 4149 return parseFunctionTypeAlias(commentAndMetadata, keyword); | 4459 return parseFunctionTypeAlias(commentAndMetadata, keyword); |
| 4150 } | 4460 } |
| 4151 | 4461 |
| 4152 /** | 4462 /** |
| 4153 * Parse a list of type arguments. | 4463 * Parse a list of type arguments. |
| 4464 * |
| 4154 * <pre> | 4465 * <pre> |
| 4155 * typeArguments ::= | 4466 * typeArguments ::= |
| 4156 * '<' typeList '>' | 4467 * '<' typeList '>' |
| 4468 * |
| 4157 * typeList ::= | 4469 * typeList ::= |
| 4158 * type (',' type) | 4470 * type (',' type)* |
| 4159 * </pre> | 4471 * </pre> |
| 4472 * |
| 4160 * @return the type argument list that was parsed | 4473 * @return the type argument list that was parsed |
| 4161 */ | 4474 */ |
| 4162 TypeArgumentList parseTypeArgumentList() { | 4475 TypeArgumentList parseTypeArgumentList() { |
| 4163 Token leftBracket = expect2(TokenType.LT); | 4476 Token leftBracket = expect2(TokenType.LT); |
| 4164 List<TypeName> arguments = new List<TypeName>(); | 4477 List<TypeName> arguments = new List<TypeName>(); |
| 4165 arguments.add(parseTypeName()); | 4478 arguments.add(parseTypeName()); |
| 4166 while (optional(TokenType.COMMA)) { | 4479 while (optional(TokenType.COMMA)) { |
| 4167 arguments.add(parseTypeName()); | 4480 arguments.add(parseTypeName()); |
| 4168 } | 4481 } |
| 4169 Token rightBracket = expect2(TokenType.GT); | 4482 Token rightBracket = expect2(TokenType.GT); |
| 4170 return new TypeArgumentList.full(leftBracket, arguments, rightBracket); | 4483 return new TypeArgumentList.full(leftBracket, arguments, rightBracket); |
| 4171 } | 4484 } |
| 4172 | 4485 |
| 4173 /** | 4486 /** |
| 4174 * Parse a type name. | 4487 * Parse a type name. |
| 4488 * |
| 4175 * <pre> | 4489 * <pre> |
| 4176 * type ::= | 4490 * type ::= |
| 4177 * qualified typeArguments? | 4491 * qualified typeArguments? |
| 4178 * </pre> | 4492 * </pre> |
| 4493 * |
| 4179 * @return the type name that was parsed | 4494 * @return the type name that was parsed |
| 4180 */ | 4495 */ |
| 4181 TypeName parseTypeName() { | 4496 TypeName parseTypeName() { |
| 4182 Identifier typeName; | 4497 Identifier typeName; |
| 4183 if (matches(Keyword.VAR)) { | 4498 if (matches(Keyword.VAR)) { |
| 4184 reportError7(ParserErrorCode.VAR_AS_TYPE_NAME, []); | 4499 reportError7(ParserErrorCode.VAR_AS_TYPE_NAME, []); |
| 4185 typeName = new SimpleIdentifier.full(andAdvance); | 4500 typeName = new SimpleIdentifier.full(andAdvance); |
| 4186 } else if (matchesIdentifier()) { | 4501 } else if (matchesIdentifier()) { |
| 4187 typeName = parsePrefixedIdentifier(); | 4502 typeName = parsePrefixedIdentifier(); |
| 4188 } else { | 4503 } else { |
| 4189 typeName = createSyntheticIdentifier(); | 4504 typeName = createSyntheticIdentifier(); |
| 4190 reportError7(ParserErrorCode.EXPECTED_TYPE_NAME, []); | 4505 reportError7(ParserErrorCode.EXPECTED_TYPE_NAME, []); |
| 4191 } | 4506 } |
| 4192 TypeArgumentList typeArguments = null; | 4507 TypeArgumentList typeArguments = null; |
| 4193 if (matches5(TokenType.LT)) { | 4508 if (matches5(TokenType.LT)) { |
| 4194 typeArguments = parseTypeArgumentList(); | 4509 typeArguments = parseTypeArgumentList(); |
| 4195 } | 4510 } |
| 4196 return new TypeName.full(typeName, typeArguments); | 4511 return new TypeName.full(typeName, typeArguments); |
| 4197 } | 4512 } |
| 4198 | 4513 |
| 4199 /** | 4514 /** |
| 4200 * Parse a type parameter. | 4515 * Parse a type parameter. |
| 4516 * |
| 4201 * <pre> | 4517 * <pre> |
| 4202 * typeParameter ::= | 4518 * typeParameter ::= |
| 4203 * metadata name ('extends' bound)? | 4519 * metadata name ('extends' bound)? |
| 4204 * </pre> | 4520 * </pre> |
| 4521 * |
| 4205 * @return the type parameter that was parsed | 4522 * @return the type parameter that was parsed |
| 4206 */ | 4523 */ |
| 4207 TypeParameter parseTypeParameter() { | 4524 TypeParameter parseTypeParameter() { |
| 4208 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); | 4525 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); |
| 4209 SimpleIdentifier name = parseSimpleIdentifier(); | 4526 SimpleIdentifier name = parseSimpleIdentifier(); |
| 4210 if (matches(Keyword.EXTENDS)) { | 4527 if (matches(Keyword.EXTENDS)) { |
| 4211 Token keyword = andAdvance; | 4528 Token keyword = andAdvance; |
| 4212 TypeName bound = parseTypeName(); | 4529 TypeName bound = parseTypeName(); |
| 4213 return new TypeParameter.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, name, keyword, bound); | 4530 return new TypeParameter.full(commentAndMetadata.comment, commentAndMetada
ta.metadata, name, keyword, bound); |
| 4214 } | 4531 } |
| 4215 return new TypeParameter.full(commentAndMetadata.comment, commentAndMetadata
.metadata, name, null, null); | 4532 return new TypeParameter.full(commentAndMetadata.comment, commentAndMetadata
.metadata, name, null, null); |
| 4216 } | 4533 } |
| 4217 | 4534 |
| 4218 /** | 4535 /** |
| 4219 * Parse a list of type parameters. | 4536 * Parse a list of type parameters. |
| 4537 * |
| 4220 * <pre> | 4538 * <pre> |
| 4221 * typeParameterList ::= | 4539 * typeParameterList ::= |
| 4222 * '<' typeParameter (',' typeParameter)* '>' | 4540 * '<' typeParameter (',' typeParameter)* '>' |
| 4223 * </pre> | 4541 * </pre> |
| 4542 * |
| 4224 * @return the list of type parameters that were parsed | 4543 * @return the list of type parameters that were parsed |
| 4225 */ | 4544 */ |
| 4226 TypeParameterList parseTypeParameterList() { | 4545 TypeParameterList parseTypeParameterList() { |
| 4227 Token leftBracket = expect2(TokenType.LT); | 4546 Token leftBracket = expect2(TokenType.LT); |
| 4228 List<TypeParameter> typeParameters = new List<TypeParameter>(); | 4547 List<TypeParameter> typeParameters = new List<TypeParameter>(); |
| 4229 typeParameters.add(parseTypeParameter()); | 4548 typeParameters.add(parseTypeParameter()); |
| 4230 while (optional(TokenType.COMMA)) { | 4549 while (optional(TokenType.COMMA)) { |
| 4231 typeParameters.add(parseTypeParameter()); | 4550 typeParameters.add(parseTypeParameter()); |
| 4232 } | 4551 } |
| 4233 Token rightBracket = expect2(TokenType.GT); | 4552 Token rightBracket = expect2(TokenType.GT); |
| 4234 return new TypeParameterList.full(leftBracket, typeParameters, rightBracket)
; | 4553 return new TypeParameterList.full(leftBracket, typeParameters, rightBracket)
; |
| 4235 } | 4554 } |
| 4236 | 4555 |
| 4237 /** | 4556 /** |
| 4238 * Parse a unary expression. | 4557 * Parse a unary expression. |
| 4558 * |
| 4239 * <pre> | 4559 * <pre> |
| 4240 * unaryExpression ::= | 4560 * unaryExpression ::= |
| 4241 * prefixOperator unaryExpression | 4561 * prefixOperator unaryExpression |
| 4242 * | postfixExpression | 4562 * | postfixExpression |
| 4243 * | unaryOperator 'super' | 4563 * | unaryOperator 'super' |
| 4244 * | '-' 'super' | 4564 * | '-' 'super' |
| 4245 * | incrementOperator assignableExpression | 4565 * | incrementOperator assignableExpression |
| 4246 * </pre> | 4566 * </pre> |
| 4567 * |
| 4247 * @return the unary expression that was parsed | 4568 * @return the unary expression that was parsed |
| 4248 */ | 4569 */ |
| 4249 Expression parseUnaryExpression() { | 4570 Expression parseUnaryExpression() { |
| 4250 if (matches5(TokenType.MINUS) || matches5(TokenType.BANG) || matches5(TokenT
ype.TILDE)) { | 4571 if (matches5(TokenType.MINUS) || matches5(TokenType.BANG) || matches5(TokenT
ype.TILDE)) { |
| 4251 Token operator = andAdvance; | 4572 Token operator = andAdvance; |
| 4252 if (matches(Keyword.SUPER)) { | 4573 if (matches(Keyword.SUPER)) { |
| 4253 if (matches4(peek(), TokenType.OPEN_SQUARE_BRACKET) || matches4(peek(),
TokenType.PERIOD)) { | 4574 if (matches4(peek(), TokenType.OPEN_SQUARE_BRACKET) || matches4(peek(),
TokenType.PERIOD)) { |
| 4254 return new PrefixExpression.full(operator, parseUnaryExpression()); | 4575 return new PrefixExpression.full(operator, parseUnaryExpression()); |
| 4255 } | 4576 } |
| 4256 return new PrefixExpression.full(operator, new SuperExpression.full(andA
dvance)); | 4577 return new PrefixExpression.full(operator, new SuperExpression.full(andA
dvance)); |
| (...skipping 21 matching lines...) Expand all Loading... |
| 4278 return new PrefixExpression.full(operator, parseAssignableExpression(false
)); | 4599 return new PrefixExpression.full(operator, parseAssignableExpression(false
)); |
| 4279 } else if (matches5(TokenType.PLUS)) { | 4600 } else if (matches5(TokenType.PLUS)) { |
| 4280 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); | 4601 reportError7(ParserErrorCode.MISSING_IDENTIFIER, []); |
| 4281 return createSyntheticIdentifier(); | 4602 return createSyntheticIdentifier(); |
| 4282 } | 4603 } |
| 4283 return parsePostfixExpression(); | 4604 return parsePostfixExpression(); |
| 4284 } | 4605 } |
| 4285 | 4606 |
| 4286 /** | 4607 /** |
| 4287 * Parse a variable declaration. | 4608 * Parse a variable declaration. |
| 4609 * |
| 4288 * <pre> | 4610 * <pre> |
| 4289 * variableDeclaration ::= | 4611 * variableDeclaration ::= |
| 4290 * identifier ('=' expression)? | 4612 * identifier ('=' expression)? |
| 4291 * </pre> | 4613 * </pre> |
| 4614 * |
| 4292 * @return the variable declaration that was parsed | 4615 * @return the variable declaration that was parsed |
| 4293 */ | 4616 */ |
| 4294 VariableDeclaration parseVariableDeclaration() { | 4617 VariableDeclaration parseVariableDeclaration() { |
| 4295 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); | 4618 CommentAndMetadata commentAndMetadata = parseCommentAndMetadata(); |
| 4296 SimpleIdentifier name = parseSimpleIdentifier(); | 4619 SimpleIdentifier name = parseSimpleIdentifier(); |
| 4297 Token equals = null; | 4620 Token equals = null; |
| 4298 Expression initializer = null; | 4621 Expression initializer = null; |
| 4299 if (matches5(TokenType.EQ)) { | 4622 if (matches5(TokenType.EQ)) { |
| 4300 equals = andAdvance; | 4623 equals = andAdvance; |
| 4301 initializer = parseExpression2(); | 4624 initializer = parseExpression2(); |
| 4302 } | 4625 } |
| 4303 return new VariableDeclaration.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, name, equals, initializer); | 4626 return new VariableDeclaration.full(commentAndMetadata.comment, commentAndMe
tadata.metadata, name, equals, initializer); |
| 4304 } | 4627 } |
| 4305 | 4628 |
| 4306 /** | 4629 /** |
| 4307 * Parse a variable declaration list. | 4630 * Parse a variable declaration list. |
| 4631 * |
| 4308 * <pre> | 4632 * <pre> |
| 4309 * variableDeclarationList ::= | 4633 * variableDeclarationList ::= |
| 4310 * finalConstVarOrType variableDeclaration (',' variableDeclaration) | 4634 * finalConstVarOrType variableDeclaration (',' variableDeclaration)* |
| 4311 * </pre> | 4635 * </pre> |
| 4636 * |
| 4312 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration list | 4637 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration list |
| 4313 * @return the variable declaration list that was parsed | 4638 * @return the variable declaration list that was parsed |
| 4314 */ | 4639 */ |
| 4315 VariableDeclarationList parseVariableDeclarationList(CommentAndMetadata commen
tAndMetadata) { | 4640 VariableDeclarationList parseVariableDeclarationList(CommentAndMetadata commen
tAndMetadata) { |
| 4316 FinalConstVarOrType holder = parseFinalConstVarOrType(false); | 4641 FinalConstVarOrType holder = parseFinalConstVarOrType(false); |
| 4317 return parseVariableDeclarationList2(commentAndMetadata, holder.keyword, hol
der.type); | 4642 return parseVariableDeclarationList2(commentAndMetadata, holder.keyword, hol
der.type); |
| 4318 } | 4643 } |
| 4319 | 4644 |
| 4320 /** | 4645 /** |
| 4321 * Parse a variable declaration list. | 4646 * Parse a variable declaration list. |
| 4647 * |
| 4322 * <pre> | 4648 * <pre> |
| 4323 * variableDeclarationList ::= | 4649 * variableDeclarationList ::= |
| 4324 * finalConstVarOrType variableDeclaration (',' variableDeclaration) | 4650 * finalConstVarOrType variableDeclaration (',' variableDeclaration)* |
| 4325 * </pre> | 4651 * </pre> |
| 4326 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration list, or`null` if there is no attempt at parsing the comment and meta
data | 4652 * |
| 4653 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration list, or |
| 4654 * `null` if there is no attempt at parsing the comment and metadata |
| 4327 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if | 4655 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if |
| 4328 * there is no keyword | 4656 * there is no keyword |
| 4329 * @param type the type of the variables in the list | 4657 * @param type the type of the variables in the list |
| 4330 * @return the variable declaration list that was parsed | 4658 * @return the variable declaration list that was parsed |
| 4331 */ | 4659 */ |
| 4332 VariableDeclarationList parseVariableDeclarationList2(CommentAndMetadata comme
ntAndMetadata, Token keyword, TypeName type) { | 4660 VariableDeclarationList parseVariableDeclarationList2(CommentAndMetadata comme
ntAndMetadata, Token keyword, TypeName type) { |
| 4333 List<VariableDeclaration> variables = new List<VariableDeclaration>(); | 4661 List<VariableDeclaration> variables = new List<VariableDeclaration>(); |
| 4334 variables.add(parseVariableDeclaration()); | 4662 variables.add(parseVariableDeclaration()); |
| 4335 while (matches5(TokenType.COMMA)) { | 4663 while (matches5(TokenType.COMMA)) { |
| 4336 advance(); | 4664 advance(); |
| 4337 variables.add(parseVariableDeclaration()); | 4665 variables.add(parseVariableDeclaration()); |
| 4338 } | 4666 } |
| 4339 return new VariableDeclarationList.full(commentAndMetadata != null ? comment
AndMetadata.comment : null, commentAndMetadata != null ? commentAndMetadata.meta
data : null, keyword, type, variables); | 4667 return new VariableDeclarationList.full(commentAndMetadata != null ? comment
AndMetadata.comment : null, commentAndMetadata != null ? commentAndMetadata.meta
data : null, keyword, type, variables); |
| 4340 } | 4668 } |
| 4341 | 4669 |
| 4342 /** | 4670 /** |
| 4343 * Parse a variable declaration statement. | 4671 * Parse a variable declaration statement. |
| 4672 * |
| 4344 * <pre> | 4673 * <pre> |
| 4345 * variableDeclarationStatement ::= | 4674 * variableDeclarationStatement ::= |
| 4346 * variableDeclarationList ';' | 4675 * variableDeclarationList ';' |
| 4347 * </pre> | 4676 * </pre> |
| 4677 * |
| 4348 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration | 4678 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration |
| 4349 * statement, or `null` if there is no attempt at parsing the comment and meta
data | 4679 * statement, or `null` if there is no attempt at parsing the comment
and metadata |
| 4350 * @return the variable declaration statement that was parsed | 4680 * @return the variable declaration statement that was parsed |
| 4351 */ | 4681 */ |
| 4352 VariableDeclarationStatement parseVariableDeclarationStatement(CommentAndMetad
ata commentAndMetadata) { | 4682 VariableDeclarationStatement parseVariableDeclarationStatement(CommentAndMetad
ata commentAndMetadata) { |
| 4353 VariableDeclarationList variableList = parseVariableDeclarationList(commentA
ndMetadata); | 4683 VariableDeclarationList variableList = parseVariableDeclarationList(commentA
ndMetadata); |
| 4354 Token semicolon = expect2(TokenType.SEMICOLON); | 4684 Token semicolon = expect2(TokenType.SEMICOLON); |
| 4355 return new VariableDeclarationStatement.full(variableList, semicolon); | 4685 return new VariableDeclarationStatement.full(variableList, semicolon); |
| 4356 } | 4686 } |
| 4357 | 4687 |
| 4358 /** | 4688 /** |
| 4359 * Parse a variable declaration statement. | 4689 * Parse a variable declaration statement. |
| 4690 * |
| 4360 * <pre> | 4691 * <pre> |
| 4361 * variableDeclarationStatement ::= | 4692 * variableDeclarationStatement ::= |
| 4362 * variableDeclarationList ';' | 4693 * variableDeclarationList ';' |
| 4363 * </pre> | 4694 * </pre> |
| 4695 * |
| 4364 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration | 4696 * @param commentAndMetadata the metadata to be associated with the variable d
eclaration |
| 4365 * statement, or `null` if there is no attempt at parsing the comment and meta
data | 4697 * statement, or `null` if there is no attempt at parsing the comment
and metadata |
| 4366 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if | 4698 * @param keyword the token representing the 'final', 'const' or 'var' keyword
, or `null` if |
| 4367 * there is no keyword | 4699 * there is no keyword |
| 4368 * @param type the type of the variables in the list | 4700 * @param type the type of the variables in the list |
| 4369 * @return the variable declaration statement that was parsed | 4701 * @return the variable declaration statement that was parsed |
| 4370 */ | 4702 */ |
| 4371 VariableDeclarationStatement parseVariableDeclarationStatement2(CommentAndMeta
data commentAndMetadata, Token keyword, TypeName type) { | 4703 VariableDeclarationStatement parseVariableDeclarationStatement2(CommentAndMeta
data commentAndMetadata, Token keyword, TypeName type) { |
| 4372 VariableDeclarationList variableList = parseVariableDeclarationList2(comment
AndMetadata, keyword, type); | 4704 VariableDeclarationList variableList = parseVariableDeclarationList2(comment
AndMetadata, keyword, type); |
| 4373 Token semicolon = expect2(TokenType.SEMICOLON); | 4705 Token semicolon = expect2(TokenType.SEMICOLON); |
| 4374 return new VariableDeclarationStatement.full(variableList, semicolon); | 4706 return new VariableDeclarationStatement.full(variableList, semicolon); |
| 4375 } | 4707 } |
| 4376 | 4708 |
| 4377 /** | 4709 /** |
| 4378 * Parse a while statement. | 4710 * Parse a while statement. |
| 4711 * |
| 4379 * <pre> | 4712 * <pre> |
| 4380 * whileStatement ::= | 4713 * whileStatement ::= |
| 4381 * 'while' '(' expression ')' statement | 4714 * 'while' '(' expression ')' statement |
| 4382 * </pre> | 4715 * </pre> |
| 4716 * |
| 4383 * @return the while statement that was parsed | 4717 * @return the while statement that was parsed |
| 4384 */ | 4718 */ |
| 4385 Statement parseWhileStatement() { | 4719 Statement parseWhileStatement() { |
| 4386 bool wasInLoop = _inLoop; | 4720 bool wasInLoop = _inLoop; |
| 4387 _inLoop = true; | 4721 _inLoop = true; |
| 4388 try { | 4722 try { |
| 4389 Token keyword = expect(Keyword.WHILE); | 4723 Token keyword = expect(Keyword.WHILE); |
| 4390 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); | 4724 Token leftParenthesis = expect2(TokenType.OPEN_PAREN); |
| 4391 Expression condition = parseExpression2(); | 4725 Expression condition = parseExpression2(); |
| 4392 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); | 4726 Token rightParenthesis = expect2(TokenType.CLOSE_PAREN); |
| 4393 Statement body = parseStatement2(); | 4727 Statement body = parseStatement2(); |
| 4394 return new WhileStatement.full(keyword, leftParenthesis, condition, rightP
arenthesis, body); | 4728 return new WhileStatement.full(keyword, leftParenthesis, condition, rightP
arenthesis, body); |
| 4395 } finally { | 4729 } finally { |
| 4396 _inLoop = wasInLoop; | 4730 _inLoop = wasInLoop; |
| 4397 } | 4731 } |
| 4398 } | 4732 } |
| 4399 | 4733 |
| 4400 /** | 4734 /** |
| 4401 * Parse a with clause. | 4735 * Parse a with clause. |
| 4736 * |
| 4402 * <pre> | 4737 * <pre> |
| 4403 * withClause ::= | 4738 * withClause ::= |
| 4404 * 'with' typeName (',' typeName) | 4739 * 'with' typeName (',' typeName)* |
| 4405 * </pre> | 4740 * </pre> |
| 4741 * |
| 4406 * @return the with clause that was parsed | 4742 * @return the with clause that was parsed |
| 4407 */ | 4743 */ |
| 4408 WithClause parseWithClause() { | 4744 WithClause parseWithClause() { |
| 4409 Token with2 = expect(Keyword.WITH); | 4745 Token with2 = expect(Keyword.WITH); |
| 4410 List<TypeName> types = new List<TypeName>(); | 4746 List<TypeName> types = new List<TypeName>(); |
| 4411 types.add(parseTypeName()); | 4747 types.add(parseTypeName()); |
| 4412 while (optional(TokenType.COMMA)) { | 4748 while (optional(TokenType.COMMA)) { |
| 4413 types.add(parseTypeName()); | 4749 types.add(parseTypeName()); |
| 4414 } | 4750 } |
| 4415 return new WithClause.full(with2, types); | 4751 return new WithClause.full(with2, types); |
| 4416 } | 4752 } |
| 4417 | 4753 |
| 4418 /** | 4754 /** |
| 4419 * Return the token that is immediately after the current token. This is equiv
alent to[peek]. | 4755 * Return the token that is immediately after the current token. This is equiv
alent to |
| 4756 * [peek]. |
| 4757 * |
| 4420 * @return the token that is immediately after the current token | 4758 * @return the token that is immediately after the current token |
| 4421 */ | 4759 */ |
| 4422 Token peek() => _currentToken.next; | 4760 Token peek() => _currentToken.next; |
| 4423 | 4761 |
| 4424 /** | 4762 /** |
| 4425 * Return the token that is the given distance after the current token. | 4763 * Return the token that is the given distance after the current token. |
| 4426 * @param distance the number of tokens to look ahead, where `0` is the curren
t token,`1` is the next token, etc. | 4764 * |
| 4765 * @param distance the number of tokens to look ahead, where `0` is the curren
t token, |
| 4766 * `1` is the next token, etc. |
| 4427 * @return the token that is the given distance after the current token | 4767 * @return the token that is the given distance after the current token |
| 4428 */ | 4768 */ |
| 4429 Token peek2(int distance) { | 4769 Token peek2(int distance) { |
| 4430 Token token = _currentToken; | 4770 Token token = _currentToken; |
| 4431 for (int i = 0; i < distance; i++) { | 4771 for (int i = 0; i < distance; i++) { |
| 4432 token = token.next; | 4772 token = token.next; |
| 4433 } | 4773 } |
| 4434 return token; | 4774 return token; |
| 4435 } | 4775 } |
| 4436 | 4776 |
| 4437 /** | 4777 /** |
| 4438 * Report an error with the given error code and arguments. | 4778 * Report an error with the given error code and arguments. |
| 4779 * |
| 4439 * @param errorCode the error code of the error to be reported | 4780 * @param errorCode the error code of the error to be reported |
| 4440 * @param node the node specifying the location of the error | 4781 * @param node the node specifying the location of the error |
| 4441 * @param arguments the arguments to the error, used to compose the error mess
age | 4782 * @param arguments the arguments to the error, used to compose the error mess
age |
| 4442 */ | 4783 */ |
| 4443 void reportError(ParserErrorCode errorCode, ASTNode node, List<Object> argumen
ts) { | 4784 void reportError(ParserErrorCode errorCode, ASTNode node, List<Object> argumen
ts) { |
| 4444 _errorListener.onError(new AnalysisError.con2(_source, node.offset, node.len
gth, errorCode, arguments)); | 4785 _errorListener.onError(new AnalysisError.con2(_source, node.offset, node.len
gth, errorCode, arguments)); |
| 4445 } | 4786 } |
| 4446 | 4787 |
| 4447 /** | 4788 /** |
| 4448 * Report an error with the given error code and arguments. | 4789 * Report an error with the given error code and arguments. |
| 4790 * |
| 4449 * @param errorCode the error code of the error to be reported | 4791 * @param errorCode the error code of the error to be reported |
| 4450 * @param arguments the arguments to the error, used to compose the error mess
age | 4792 * @param arguments the arguments to the error, used to compose the error mess
age |
| 4451 */ | 4793 */ |
| 4452 void reportError7(ParserErrorCode errorCode, List<Object> arguments) { | 4794 void reportError7(ParserErrorCode errorCode, List<Object> arguments) { |
| 4453 reportError8(errorCode, _currentToken, arguments); | 4795 reportError8(errorCode, _currentToken, arguments); |
| 4454 } | 4796 } |
| 4455 | 4797 |
| 4456 /** | 4798 /** |
| 4457 * Report an error with the given error code and arguments. | 4799 * Report an error with the given error code and arguments. |
| 4800 * |
| 4458 * @param errorCode the error code of the error to be reported | 4801 * @param errorCode the error code of the error to be reported |
| 4459 * @param token the token specifying the location of the error | 4802 * @param token the token specifying the location of the error |
| 4460 * @param arguments the arguments to the error, used to compose the error mess
age | 4803 * @param arguments the arguments to the error, used to compose the error mess
age |
| 4461 */ | 4804 */ |
| 4462 void reportError8(ParserErrorCode errorCode, Token token, List<Object> argumen
ts) { | 4805 void reportError8(ParserErrorCode errorCode, Token token, List<Object> argumen
ts) { |
| 4463 _errorListener.onError(new AnalysisError.con2(_source, token.offset, token.l
ength, errorCode, arguments)); | 4806 _errorListener.onError(new AnalysisError.con2(_source, token.offset, token.l
ength, errorCode, arguments)); |
| 4464 } | 4807 } |
| 4465 | 4808 |
| 4466 /** | 4809 /** |
| 4467 * Parse the 'final', 'const', 'var' or type preceding a variable declaration,
starting at the | 4810 * Parse the 'final', 'const', 'var' or type preceding a variable declaration,
starting at the |
| 4468 * given token, without actually creating a type or changing the current token
. Return the token | 4811 * given token, without actually creating a type or changing the current token
. Return the token |
| 4469 * following the type that was parsed, or `null` if the given token is not the
first token | 4812 * following the type that was parsed, or `null` if the given token is not the
first token |
| 4470 * in a valid type. | 4813 * in a valid type. |
| 4814 * |
| 4471 * <pre> | 4815 * <pre> |
| 4472 * finalConstVarOrType ::= | 4816 * finalConstVarOrType ::= |
| 4473 * | 'final' type? | 4817 * | 'final' type? |
| 4474 * | 'const' type? | 4818 * | 'const' type? |
| 4475 * | 'var' | 4819 * | 'var' |
| 4476 * | type | 4820 * | type |
| 4477 * </pre> | 4821 * </pre> |
| 4822 * |
| 4478 * @param startToken the token at which parsing is to begin | 4823 * @param startToken the token at which parsing is to begin |
| 4479 * @return the token following the type that was parsed | 4824 * @return the token following the type that was parsed |
| 4480 */ | 4825 */ |
| 4481 Token skipFinalConstVarOrType(Token startToken) { | 4826 Token skipFinalConstVarOrType(Token startToken) { |
| 4482 if (matches3(startToken, Keyword.FINAL) || matches3(startToken, Keyword.CONS
T)) { | 4827 if (matches3(startToken, Keyword.FINAL) || matches3(startToken, Keyword.CONS
T)) { |
| 4483 Token next = startToken.next; | 4828 Token next = startToken.next; |
| 4484 if (matchesIdentifier2(next.next) || matches4(next.next, TokenType.LT) ||
matches3(next.next, Keyword.THIS)) { | 4829 if (matchesIdentifier2(next.next) || matches4(next.next, TokenType.LT) ||
matches3(next.next, Keyword.THIS)) { |
| 4485 return skipTypeName(next); | 4830 return skipTypeName(next); |
| 4486 } | 4831 } |
| 4487 } else if (matches3(startToken, Keyword.VAR)) { | 4832 } else if (matches3(startToken, Keyword.VAR)) { |
| (...skipping 13 matching lines...) Expand all Loading... |
| 4501 * parameter list that was parsed, or `null` if the given token is not the fir
st token in a | 4846 * parameter list that was parsed, or `null` if the given token is not the fir
st token in a |
| 4502 * valid list of formal parameter. | 4847 * valid list of formal parameter. |
| 4503 * | 4848 * |
| 4504 * Note that unlike other skip methods, this method uses a heuristic. In the w
orst case, the | 4849 * Note that unlike other skip methods, this method uses a heuristic. In the w
orst case, the |
| 4505 * parameters could be prefixed by metadata, which would require us to be able
to skip arbitrary | 4850 * parameters could be prefixed by metadata, which would require us to be able
to skip arbitrary |
| 4506 * expressions. Rather than duplicate the logic of most of the parse methods w
e simply look for | 4851 * expressions. Rather than duplicate the logic of most of the parse methods w
e simply look for |
| 4507 * something that is likely to be a list of parameters and then skip to return
ing the token after | 4852 * something that is likely to be a list of parameters and then skip to return
ing the token after |
| 4508 * the closing parenthesis. | 4853 * the closing parenthesis. |
| 4509 * | 4854 * |
| 4510 * This method must be kept in sync with [parseFormalParameterList]. | 4855 * This method must be kept in sync with [parseFormalParameterList]. |
| 4856 * |
| 4511 * <pre> | 4857 * <pre> |
| 4512 * formalParameterList ::= | 4858 * formalParameterList ::= |
| 4513 * '(' ')' | 4859 * '(' ')' |
| 4514 * | '(' normalFormalParameters (',' optionalFormalParameters)? ')' | 4860 * | '(' normalFormalParameters (',' optionalFormalParameters)? ')' |
| 4515 * | '(' optionalFormalParameters ')' | 4861 * | '(' optionalFormalParameters ')' |
| 4862 * |
| 4516 * normalFormalParameters ::= | 4863 * normalFormalParameters ::= |
| 4517 * normalFormalParameter (',' normalFormalParameter) | 4864 * normalFormalParameter (',' normalFormalParameter)* |
| 4865 * |
| 4518 * optionalFormalParameters ::= | 4866 * optionalFormalParameters ::= |
| 4519 * optionalPositionalFormalParameters | 4867 * optionalPositionalFormalParameters |
| 4520 * | namedFormalParameters | 4868 * | namedFormalParameters |
| 4869 * |
| 4521 * optionalPositionalFormalParameters ::= | 4870 * optionalPositionalFormalParameters ::= |
| 4522 * '\[' defaultFormalParameter (',' defaultFormalParameter)* '\]' | 4871 * '[' defaultFormalParameter (',' defaultFormalParameter)* ']' |
| 4872 * |
| 4523 * namedFormalParameters ::= | 4873 * namedFormalParameters ::= |
| 4524 * '{' defaultNamedParameter (',' defaultNamedParameter)* '}' | 4874 * '{' defaultNamedParameter (',' defaultNamedParameter)* '}' |
| 4525 * </pre> | 4875 * </pre> |
| 4876 * |
| 4526 * @param startToken the token at which parsing is to begin | 4877 * @param startToken the token at which parsing is to begin |
| 4527 * @return the token following the formal parameter list that was parsed | 4878 * @return the token following the formal parameter list that was parsed |
| 4528 */ | 4879 */ |
| 4529 Token skipFormalParameterList(Token startToken) { | 4880 Token skipFormalParameterList(Token startToken) { |
| 4530 if (!matches4(startToken, TokenType.OPEN_PAREN)) { | 4881 if (!matches4(startToken, TokenType.OPEN_PAREN)) { |
| 4531 return null; | 4882 return null; |
| 4532 } | 4883 } |
| 4533 Token next = startToken.next; | 4884 Token next = startToken.next; |
| 4534 if (matches4(next, TokenType.CLOSE_PAREN)) { | 4885 if (matches4(next, TokenType.CLOSE_PAREN)) { |
| 4535 return next.next; | 4886 return next.next; |
| (...skipping 13 matching lines...) Expand all Loading... |
| 4549 } | 4900 } |
| 4550 if (skipSimpleIdentifier(afterType) == null) { | 4901 if (skipSimpleIdentifier(afterType) == null) { |
| 4551 return null; | 4902 return null; |
| 4552 } | 4903 } |
| 4553 return skipPastMatchingToken(startToken); | 4904 return skipPastMatchingToken(startToken); |
| 4554 } | 4905 } |
| 4555 | 4906 |
| 4556 /** | 4907 /** |
| 4557 * If the given token is a begin token with an associated end token, then retu
rn the token | 4908 * If the given token is a begin token with an associated end token, then retu
rn the token |
| 4558 * following the end token. Otherwise, return `null`. | 4909 * following the end token. Otherwise, return `null`. |
| 4910 * |
| 4559 * @param startToken the token that is assumed to be a being token | 4911 * @param startToken the token that is assumed to be a being token |
| 4560 * @return the token following the matching end token | 4912 * @return the token following the matching end token |
| 4561 */ | 4913 */ |
| 4562 Token skipPastMatchingToken(Token startToken) { | 4914 Token skipPastMatchingToken(Token startToken) { |
| 4563 if (startToken is! BeginToken) { | 4915 if (startToken is! BeginToken) { |
| 4564 return null; | 4916 return null; |
| 4565 } | 4917 } |
| 4566 Token closeParen = ((startToken as BeginToken)).endToken; | 4918 Token closeParen = ((startToken as BeginToken)).endToken; |
| 4567 if (closeParen == null) { | 4919 if (closeParen == null) { |
| 4568 return null; | 4920 return null; |
| 4569 } | 4921 } |
| 4570 return closeParen.next; | 4922 return closeParen.next; |
| 4571 } | 4923 } |
| 4572 | 4924 |
| 4573 /** | 4925 /** |
| 4574 * Parse a prefixed identifier, starting at the given token, without actually
creating a prefixed | 4926 * Parse a prefixed identifier, starting at the given token, without actually
creating a prefixed |
| 4575 * identifier or changing the current token. Return the token following the pr
efixed identifier | 4927 * identifier or changing the current token. Return the token following the pr
efixed identifier |
| 4576 * that was parsed, or `null` if the given token is not the first token in a v
alid prefixed | 4928 * that was parsed, or `null` if the given token is not the first token in a v
alid prefixed |
| 4577 * identifier. | 4929 * identifier. |
| 4578 * | 4930 * |
| 4579 * This method must be kept in sync with [parsePrefixedIdentifier]. | 4931 * This method must be kept in sync with [parsePrefixedIdentifier]. |
| 4932 * |
| 4580 * <pre> | 4933 * <pre> |
| 4581 * prefixedIdentifier ::= | 4934 * prefixedIdentifier ::= |
| 4582 * identifier ('.' identifier)? | 4935 * identifier ('.' identifier)? |
| 4583 * </pre> | 4936 * </pre> |
| 4937 * |
| 4584 * @param startToken the token at which parsing is to begin | 4938 * @param startToken the token at which parsing is to begin |
| 4585 * @return the token following the prefixed identifier that was parsed | 4939 * @return the token following the prefixed identifier that was parsed |
| 4586 */ | 4940 */ |
| 4587 Token skipPrefixedIdentifier(Token startToken) { | 4941 Token skipPrefixedIdentifier(Token startToken) { |
| 4588 Token token = skipSimpleIdentifier(startToken); | 4942 Token token = skipSimpleIdentifier(startToken); |
| 4589 if (token == null) { | 4943 if (token == null) { |
| 4590 return null; | 4944 return null; |
| 4591 } else if (!matches4(token, TokenType.PERIOD)) { | 4945 } else if (!matches4(token, TokenType.PERIOD)) { |
| 4592 return token; | 4946 return token; |
| 4593 } | 4947 } |
| 4594 return skipSimpleIdentifier(token.next); | 4948 return skipSimpleIdentifier(token.next); |
| 4595 } | 4949 } |
| 4596 | 4950 |
| 4597 /** | 4951 /** |
| 4598 * Parse a return type, starting at the given token, without actually creating
a return type or | 4952 * Parse a return type, starting at the given token, without actually creating
a return type or |
| 4599 * changing the current token. Return the token following the return type that
was parsed, or`null` if the given token is not the first token in a valid retur
n type. | 4953 * changing the current token. Return the token following the return type that
was parsed, or |
| 4954 * `null` if the given token is not the first token in a valid return type. |
| 4600 * | 4955 * |
| 4601 * This method must be kept in sync with [parseReturnType]. | 4956 * This method must be kept in sync with [parseReturnType]. |
| 4957 * |
| 4602 * <pre> | 4958 * <pre> |
| 4603 * returnType ::= | 4959 * returnType ::= |
| 4604 * 'void' | 4960 * 'void' |
| 4605 * | type | 4961 * | type |
| 4606 * </pre> | 4962 * </pre> |
| 4963 * |
| 4607 * @param startToken the token at which parsing is to begin | 4964 * @param startToken the token at which parsing is to begin |
| 4608 * @return the token following the return type that was parsed | 4965 * @return the token following the return type that was parsed |
| 4609 */ | 4966 */ |
| 4610 Token skipReturnType(Token startToken) { | 4967 Token skipReturnType(Token startToken) { |
| 4611 if (matches3(startToken, Keyword.VOID)) { | 4968 if (matches3(startToken, Keyword.VOID)) { |
| 4612 return startToken.next; | 4969 return startToken.next; |
| 4613 } else { | 4970 } else { |
| 4614 return skipTypeName(startToken); | 4971 return skipTypeName(startToken); |
| 4615 } | 4972 } |
| 4616 } | 4973 } |
| 4617 | 4974 |
| 4618 /** | 4975 /** |
| 4619 * Parse a simple identifier, starting at the given token, without actually cr
eating a simple | 4976 * Parse a simple identifier, starting at the given token, without actually cr
eating a simple |
| 4620 * identifier or changing the current token. Return the token following the si
mple identifier that | 4977 * identifier or changing the current token. Return the token following the si
mple identifier that |
| 4621 * was parsed, or `null` if the given token is not the first token in a valid
simple | 4978 * was parsed, or `null` if the given token is not the first token in a valid
simple |
| 4622 * identifier. | 4979 * identifier. |
| 4623 * | 4980 * |
| 4624 * This method must be kept in sync with [parseSimpleIdentifier]. | 4981 * This method must be kept in sync with [parseSimpleIdentifier]. |
| 4982 * |
| 4625 * <pre> | 4983 * <pre> |
| 4626 * identifier ::= | 4984 * identifier ::= |
| 4627 * IDENTIFIER | 4985 * IDENTIFIER |
| 4628 * </pre> | 4986 * </pre> |
| 4987 * |
| 4629 * @param startToken the token at which parsing is to begin | 4988 * @param startToken the token at which parsing is to begin |
| 4630 * @return the token following the simple identifier that was parsed | 4989 * @return the token following the simple identifier that was parsed |
| 4631 */ | 4990 */ |
| 4632 Token skipSimpleIdentifier(Token startToken) { | 4991 Token skipSimpleIdentifier(Token startToken) { |
| 4633 if (matches4(startToken, TokenType.IDENTIFIER) || (matches4(startToken, Toke
nType.KEYWORD) && ((startToken as KeywordToken)).keyword.isPseudoKeyword)) { | 4992 if (matches4(startToken, TokenType.IDENTIFIER) || (matches4(startToken, Toke
nType.KEYWORD) && ((startToken as KeywordToken)).keyword.isPseudoKeyword)) { |
| 4634 return startToken.next; | 4993 return startToken.next; |
| 4635 } | 4994 } |
| 4636 return null; | 4995 return null; |
| 4637 } | 4996 } |
| 4638 | 4997 |
| 4639 /** | 4998 /** |
| 4640 * Parse a string literal that contains interpolations, starting at the given
token, without | 4999 * Parse a string literal that contains interpolations, starting at the given
token, without |
| 4641 * actually creating a string literal or changing the current token. Return th
e token following | 5000 * actually creating a string literal or changing the current token. Return th
e token following |
| 4642 * the string literal that was parsed, or `null` if the given token is not the
first token | 5001 * the string literal that was parsed, or `null` if the given token is not the
first token |
| 4643 * in a valid string literal. | 5002 * in a valid string literal. |
| 4644 * | 5003 * |
| 4645 * This method must be kept in sync with [parseStringInterpolation]. | 5004 * This method must be kept in sync with [parseStringInterpolation]. |
| 5005 * |
| 4646 * @param startToken the token at which parsing is to begin | 5006 * @param startToken the token at which parsing is to begin |
| 4647 * @return the string literal that was parsed | 5007 * @return the string literal that was parsed |
| 4648 */ | 5008 */ |
| 4649 Token skipStringInterpolation(Token startToken) { | 5009 Token skipStringInterpolation(Token startToken) { |
| 4650 Token token = startToken; | 5010 Token token = startToken; |
| 4651 TokenType type = token.type; | 5011 TokenType type = token.type; |
| 4652 while (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION) || identic
al(type, TokenType.STRING_INTERPOLATION_IDENTIFIER)) { | 5012 while (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION) || identic
al(type, TokenType.STRING_INTERPOLATION_IDENTIFIER)) { |
| 4653 if (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION)) { | 5013 if (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION)) { |
| 4654 token = token.next; | 5014 token = token.next; |
| 4655 type = token.type; | 5015 type = token.type; |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4688 } | 5048 } |
| 4689 return token; | 5049 return token; |
| 4690 } | 5050 } |
| 4691 | 5051 |
| 4692 /** | 5052 /** |
| 4693 * Parse a string literal, starting at the given token, without actually creat
ing a string literal | 5053 * Parse a string literal, starting at the given token, without actually creat
ing a string literal |
| 4694 * or changing the current token. Return the token following the string litera
l that was parsed, | 5054 * or changing the current token. Return the token following the string litera
l that was parsed, |
| 4695 * or `null` if the given token is not the first token in a valid string liter
al. | 5055 * or `null` if the given token is not the first token in a valid string liter
al. |
| 4696 * | 5056 * |
| 4697 * This method must be kept in sync with [parseStringLiteral]. | 5057 * This method must be kept in sync with [parseStringLiteral]. |
| 5058 * |
| 4698 * <pre> | 5059 * <pre> |
| 4699 * stringLiteral ::= | 5060 * stringLiteral ::= |
| 4700 * MULTI_LINE_STRING+ | 5061 * MULTI_LINE_STRING+ |
| 4701 * | SINGLE_LINE_STRING+ | 5062 * | SINGLE_LINE_STRING+ |
| 4702 * </pre> | 5063 * </pre> |
| 5064 * |
| 4703 * @param startToken the token at which parsing is to begin | 5065 * @param startToken the token at which parsing is to begin |
| 4704 * @return the token following the string literal that was parsed | 5066 * @return the token following the string literal that was parsed |
| 4705 */ | 5067 */ |
| 4706 Token skipStringLiteral(Token startToken) { | 5068 Token skipStringLiteral(Token startToken) { |
| 4707 Token token = startToken; | 5069 Token token = startToken; |
| 4708 while (token != null && matches4(token, TokenType.STRING)) { | 5070 while (token != null && matches4(token, TokenType.STRING)) { |
| 4709 token = token.next; | 5071 token = token.next; |
| 4710 TokenType type = token.type; | 5072 TokenType type = token.type; |
| 4711 if (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION) || identica
l(type, TokenType.STRING_INTERPOLATION_IDENTIFIER)) { | 5073 if (identical(type, TokenType.STRING_INTERPOLATION_EXPRESSION) || identica
l(type, TokenType.STRING_INTERPOLATION_IDENTIFIER)) { |
| 4712 token = skipStringInterpolation(token); | 5074 token = skipStringInterpolation(token); |
| 4713 } | 5075 } |
| 4714 } | 5076 } |
| 4715 if (identical(token, startToken)) { | 5077 if (identical(token, startToken)) { |
| 4716 return null; | 5078 return null; |
| 4717 } | 5079 } |
| 4718 return token; | 5080 return token; |
| 4719 } | 5081 } |
| 4720 | 5082 |
| 4721 /** | 5083 /** |
| 4722 * Parse a list of type arguments, starting at the given token, without actual
ly creating a type argument list | 5084 * Parse a list of type arguments, starting at the given token, without actual
ly creating a type argument list |
| 4723 * or changing the current token. Return the token following the type argument
list that was parsed, | 5085 * or changing the current token. Return the token following the type argument
list that was parsed, |
| 4724 * or `null` if the given token is not the first token in a valid type argumen
t list. | 5086 * or `null` if the given token is not the first token in a valid type argumen
t list. |
| 4725 * | 5087 * |
| 4726 * This method must be kept in sync with [parseTypeArgumentList]. | 5088 * This method must be kept in sync with [parseTypeArgumentList]. |
| 5089 * |
| 4727 * <pre> | 5090 * <pre> |
| 4728 * typeArguments ::= | 5091 * typeArguments ::= |
| 4729 * '<' typeList '>' | 5092 * '<' typeList '>' |
| 5093 * |
| 4730 * typeList ::= | 5094 * typeList ::= |
| 4731 * type (',' type) | 5095 * type (',' type)* |
| 4732 * </pre> | 5096 * </pre> |
| 5097 * |
| 4733 * @param startToken the token at which parsing is to begin | 5098 * @param startToken the token at which parsing is to begin |
| 4734 * @return the token following the type argument list that was parsed | 5099 * @return the token following the type argument list that was parsed |
| 4735 */ | 5100 */ |
| 4736 Token skipTypeArgumentList(Token startToken) { | 5101 Token skipTypeArgumentList(Token startToken) { |
| 4737 Token token = startToken; | 5102 Token token = startToken; |
| 4738 if (!matches4(token, TokenType.LT)) { | 5103 if (!matches4(token, TokenType.LT)) { |
| 4739 return null; | 5104 return null; |
| 4740 } | 5105 } |
| 4741 token = skipTypeName(token.next); | 5106 token = skipTypeName(token.next); |
| 4742 if (token == null) { | 5107 if (token == null) { |
| (...skipping 10 matching lines...) Expand all Loading... |
| 4753 } else if (identical(token.type, TokenType.GT_GT)) { | 5118 } else if (identical(token.type, TokenType.GT_GT)) { |
| 4754 Token second = new Token(TokenType.GT, token.offset + 1); | 5119 Token second = new Token(TokenType.GT, token.offset + 1); |
| 4755 second.setNextWithoutSettingPrevious(token.next); | 5120 second.setNextWithoutSettingPrevious(token.next); |
| 4756 return second; | 5121 return second; |
| 4757 } | 5122 } |
| 4758 return null; | 5123 return null; |
| 4759 } | 5124 } |
| 4760 | 5125 |
| 4761 /** | 5126 /** |
| 4762 * Parse a type name, starting at the given token, without actually creating a
type name or | 5127 * Parse a type name, starting at the given token, without actually creating a
type name or |
| 4763 * changing the current token. Return the token following the type name that w
as parsed, or`null` if the given token is not the first token in a valid type na
me. | 5128 * changing the current token. Return the token following the type name that w
as parsed, or |
| 5129 * `null` if the given token is not the first token in a valid type name. |
| 4764 * | 5130 * |
| 4765 * This method must be kept in sync with [parseTypeName]. | 5131 * This method must be kept in sync with [parseTypeName]. |
| 5132 * |
| 4766 * <pre> | 5133 * <pre> |
| 4767 * type ::= | 5134 * type ::= |
| 4768 * qualified typeArguments? | 5135 * qualified typeArguments? |
| 4769 * </pre> | 5136 * </pre> |
| 5137 * |
| 4770 * @param startToken the token at which parsing is to begin | 5138 * @param startToken the token at which parsing is to begin |
| 4771 * @return the token following the type name that was parsed | 5139 * @return the token following the type name that was parsed |
| 4772 */ | 5140 */ |
| 4773 Token skipTypeName(Token startToken) { | 5141 Token skipTypeName(Token startToken) { |
| 4774 Token token = skipPrefixedIdentifier(startToken); | 5142 Token token = skipPrefixedIdentifier(startToken); |
| 4775 if (token == null) { | 5143 if (token == null) { |
| 4776 return null; | 5144 return null; |
| 4777 } | 5145 } |
| 4778 if (matches4(token, TokenType.LT)) { | 5146 if (matches4(token, TokenType.LT)) { |
| 4779 token = skipTypeArgumentList(token); | 5147 token = skipTypeArgumentList(token); |
| 4780 } | 5148 } |
| 4781 return token; | 5149 return token; |
| 4782 } | 5150 } |
| 4783 | 5151 |
| 4784 /** | 5152 /** |
| 4785 * Parse a list of type parameters, starting at the given token, without actua
lly creating a type | 5153 * Parse a list of type parameters, starting at the given token, without actua
lly creating a type |
| 4786 * parameter list or changing the current token. Return the token following th
e type parameter | 5154 * parameter list or changing the current token. Return the token following th
e type parameter |
| 4787 * list that was parsed, or `null` if the given token is not the first token i
n a valid type | 5155 * list that was parsed, or `null` if the given token is not the first token i
n a valid type |
| 4788 * parameter list. | 5156 * parameter list. |
| 4789 * | 5157 * |
| 4790 * This method must be kept in sync with [parseTypeParameterList]. | 5158 * This method must be kept in sync with [parseTypeParameterList]. |
| 5159 * |
| 4791 * <pre> | 5160 * <pre> |
| 4792 * typeParameterList ::= | 5161 * typeParameterList ::= |
| 4793 * '<' typeParameter (',' typeParameter)* '>' | 5162 * '<' typeParameter (',' typeParameter)* '>' |
| 4794 * </pre> | 5163 * </pre> |
| 5164 * |
| 4795 * @param startToken the token at which parsing is to begin | 5165 * @param startToken the token at which parsing is to begin |
| 4796 * @return the token following the type parameter list that was parsed | 5166 * @return the token following the type parameter list that was parsed |
| 4797 */ | 5167 */ |
| 4798 Token skipTypeParameterList(Token startToken) { | 5168 Token skipTypeParameterList(Token startToken) { |
| 4799 if (!matches4(startToken, TokenType.LT)) { | 5169 if (!matches4(startToken, TokenType.LT)) { |
| 4800 return null; | 5170 return null; |
| 4801 } | 5171 } |
| 4802 int depth = 1; | 5172 int depth = 1; |
| 4803 Token next = startToken.next; | 5173 Token next = startToken.next; |
| 4804 while (depth > 0) { | 5174 while (depth > 0) { |
| (...skipping 23 matching lines...) Expand all Loading... |
| 4828 depth -= 2; | 5198 depth -= 2; |
| 4829 } | 5199 } |
| 4830 next = next.next; | 5200 next = next.next; |
| 4831 } | 5201 } |
| 4832 return next; | 5202 return next; |
| 4833 } | 5203 } |
| 4834 | 5204 |
| 4835 /** | 5205 /** |
| 4836 * Translate the characters at the given index in the given string, appending
the translated | 5206 * Translate the characters at the given index in the given string, appending
the translated |
| 4837 * character to the given builder. The index is assumed to be valid. | 5207 * character to the given builder. The index is assumed to be valid. |
| 5208 * |
| 4838 * @param builder the builder to which the translated character is to be appen
ded | 5209 * @param builder the builder to which the translated character is to be appen
ded |
| 4839 * @param lexeme the string containing the character(s) to be translated | 5210 * @param lexeme the string containing the character(s) to be translated |
| 4840 * @param index the index of the character to be translated | 5211 * @param index the index of the character to be translated |
| 4841 * @return the index of the next character to be translated | 5212 * @return the index of the next character to be translated |
| 4842 */ | 5213 */ |
| 4843 int translateCharacter(JavaStringBuilder builder, String lexeme, int index) { | 5214 int translateCharacter(JavaStringBuilder builder, String lexeme, int index) { |
| 4844 int currentChar = lexeme.codeUnitAt(index); | 5215 int currentChar = lexeme.codeUnitAt(index); |
| 4845 if (currentChar != 0x5C) { | 5216 if (currentChar != 0x5C) { |
| 4846 builder.appendChar(currentChar); | 5217 builder.appendChar(currentChar); |
| 4847 return index + 1; | 5218 return index + 1; |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4933 return currentIndex + 4; | 5304 return currentIndex + 4; |
| 4934 } | 5305 } |
| 4935 } else { | 5306 } else { |
| 4936 builder.appendChar(currentChar); | 5307 builder.appendChar(currentChar); |
| 4937 } | 5308 } |
| 4938 return currentIndex + 1; | 5309 return currentIndex + 1; |
| 4939 } | 5310 } |
| 4940 | 5311 |
| 4941 /** | 5312 /** |
| 4942 * Validate that the given parameter list does not contain any field initializ
ers. | 5313 * Validate that the given parameter list does not contain any field initializ
ers. |
| 5314 * |
| 4943 * @param parameterList the parameter list to be validated | 5315 * @param parameterList the parameter list to be validated |
| 4944 */ | 5316 */ |
| 4945 void validateFormalParameterList(FormalParameterList parameterList) { | 5317 void validateFormalParameterList(FormalParameterList parameterList) { |
| 4946 for (FormalParameter parameter in parameterList.parameters) { | 5318 for (FormalParameter parameter in parameterList.parameters) { |
| 4947 if (parameter is FieldFormalParameter) { | 5319 if (parameter is FieldFormalParameter) { |
| 4948 reportError(ParserErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, ((par
ameter as FieldFormalParameter)).identifier, []); | 5320 reportError(ParserErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, ((par
ameter as FieldFormalParameter)).identifier, []); |
| 4949 } | 5321 } |
| 4950 } | 5322 } |
| 4951 } | 5323 } |
| 4952 | 5324 |
| 4953 /** | 5325 /** |
| 4954 * Validate that the given set of modifiers is appropriate for a class and ret
urn the 'abstract' | 5326 * Validate that the given set of modifiers is appropriate for a class and ret
urn the 'abstract' |
| 4955 * keyword if there is one. | 5327 * keyword if there is one. |
| 5328 * |
| 4956 * @param modifiers the modifiers being validated | 5329 * @param modifiers the modifiers being validated |
| 4957 */ | 5330 */ |
| 4958 Token validateModifiersForClass(Modifiers modifiers) { | 5331 Token validateModifiersForClass(Modifiers modifiers) { |
| 4959 validateModifiersForTopLevelDeclaration(modifiers); | 5332 validateModifiersForTopLevelDeclaration(modifiers); |
| 4960 if (modifiers.constKeyword != null) { | 5333 if (modifiers.constKeyword != null) { |
| 4961 reportError8(ParserErrorCode.CONST_CLASS, modifiers.constKeyword, []); | 5334 reportError8(ParserErrorCode.CONST_CLASS, modifiers.constKeyword, []); |
| 4962 } | 5335 } |
| 4963 if (modifiers.externalKeyword != null) { | 5336 if (modifiers.externalKeyword != null) { |
| 4964 reportError8(ParserErrorCode.EXTERNAL_CLASS, modifiers.externalKeyword, []
); | 5337 reportError8(ParserErrorCode.EXTERNAL_CLASS, modifiers.externalKeyword, []
); |
| 4965 } | 5338 } |
| 4966 if (modifiers.finalKeyword != null) { | 5339 if (modifiers.finalKeyword != null) { |
| 4967 reportError8(ParserErrorCode.FINAL_CLASS, modifiers.finalKeyword, []); | 5340 reportError8(ParserErrorCode.FINAL_CLASS, modifiers.finalKeyword, []); |
| 4968 } | 5341 } |
| 4969 if (modifiers.varKeyword != null) { | 5342 if (modifiers.varKeyword != null) { |
| 4970 reportError8(ParserErrorCode.VAR_CLASS, modifiers.varKeyword, []); | 5343 reportError8(ParserErrorCode.VAR_CLASS, modifiers.varKeyword, []); |
| 4971 } | 5344 } |
| 4972 return modifiers.abstractKeyword; | 5345 return modifiers.abstractKeyword; |
| 4973 } | 5346 } |
| 4974 | 5347 |
| 4975 /** | 5348 /** |
| 4976 * Validate that the given set of modifiers is appropriate for a constructor a
nd return the | 5349 * Validate that the given set of modifiers is appropriate for a constructor a
nd return the |
| 4977 * 'const' keyword if there is one. | 5350 * 'const' keyword if there is one. |
| 5351 * |
| 4978 * @param modifiers the modifiers being validated | 5352 * @param modifiers the modifiers being validated |
| 4979 * @return the 'const' or 'final' keyword associated with the constructor | 5353 * @return the 'const' or 'final' keyword associated with the constructor |
| 4980 */ | 5354 */ |
| 4981 Token validateModifiersForConstructor(Modifiers modifiers) { | 5355 Token validateModifiersForConstructor(Modifiers modifiers) { |
| 4982 if (modifiers.abstractKeyword != null) { | 5356 if (modifiers.abstractKeyword != null) { |
| 4983 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); | 5357 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); |
| 4984 } | 5358 } |
| 4985 if (modifiers.finalKeyword != null) { | 5359 if (modifiers.finalKeyword != null) { |
| 4986 reportError8(ParserErrorCode.FINAL_CONSTRUCTOR, modifiers.finalKeyword, []
); | 5360 reportError8(ParserErrorCode.FINAL_CONSTRUCTOR, modifiers.finalKeyword, []
); |
| 4987 } | 5361 } |
| (...skipping 11 matching lines...) Expand all Loading... |
| 4999 } | 5373 } |
| 5000 if (externalKeyword != null && factoryKeyword != null && factoryKeyword.offs
et < externalKeyword.offset) { | 5374 if (externalKeyword != null && factoryKeyword != null && factoryKeyword.offs
et < externalKeyword.offset) { |
| 5001 reportError8(ParserErrorCode.EXTERNAL_AFTER_FACTORY, externalKeyword, []); | 5375 reportError8(ParserErrorCode.EXTERNAL_AFTER_FACTORY, externalKeyword, []); |
| 5002 } | 5376 } |
| 5003 return constKeyword; | 5377 return constKeyword; |
| 5004 } | 5378 } |
| 5005 | 5379 |
| 5006 /** | 5380 /** |
| 5007 * Validate that the given set of modifiers is appropriate for a field and ret
urn the 'final', | 5381 * Validate that the given set of modifiers is appropriate for a field and ret
urn the 'final', |
| 5008 * 'const' or 'var' keyword if there is one. | 5382 * 'const' or 'var' keyword if there is one. |
| 5383 * |
| 5009 * @param modifiers the modifiers being validated | 5384 * @param modifiers the modifiers being validated |
| 5010 * @return the 'final', 'const' or 'var' keyword associated with the field | 5385 * @return the 'final', 'const' or 'var' keyword associated with the field |
| 5011 */ | 5386 */ |
| 5012 Token validateModifiersForField(Modifiers modifiers) { | 5387 Token validateModifiersForField(Modifiers modifiers) { |
| 5013 if (modifiers.abstractKeyword != null) { | 5388 if (modifiers.abstractKeyword != null) { |
| 5014 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); | 5389 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); |
| 5015 } | 5390 } |
| 5016 if (modifiers.externalKeyword != null) { | 5391 if (modifiers.externalKeyword != null) { |
| 5017 reportError8(ParserErrorCode.EXTERNAL_FIELD, modifiers.externalKeyword, []
); | 5392 reportError8(ParserErrorCode.EXTERNAL_FIELD, modifiers.externalKeyword, []
); |
| 5018 } | 5393 } |
| (...skipping 21 matching lines...) Expand all Loading... |
| 5040 if (staticKeyword != null && finalKeyword.offset < staticKeyword.offset) { | 5415 if (staticKeyword != null && finalKeyword.offset < staticKeyword.offset) { |
| 5041 reportError8(ParserErrorCode.STATIC_AFTER_FINAL, staticKeyword, []); | 5416 reportError8(ParserErrorCode.STATIC_AFTER_FINAL, staticKeyword, []); |
| 5042 } | 5417 } |
| 5043 } else if (varKeyword != null && staticKeyword != null && varKeyword.offset
< staticKeyword.offset) { | 5418 } else if (varKeyword != null && staticKeyword != null && varKeyword.offset
< staticKeyword.offset) { |
| 5044 reportError8(ParserErrorCode.STATIC_AFTER_VAR, staticKeyword, []); | 5419 reportError8(ParserErrorCode.STATIC_AFTER_VAR, staticKeyword, []); |
| 5045 } | 5420 } |
| 5046 return lexicallyFirst([constKeyword, finalKeyword, varKeyword]); | 5421 return lexicallyFirst([constKeyword, finalKeyword, varKeyword]); |
| 5047 } | 5422 } |
| 5048 | 5423 |
| 5049 /** | 5424 /** |
| 5425 * Validate that the given set of modifiers is appropriate for a local functio
n. |
| 5426 * |
| 5427 * @param modifiers the modifiers being validated |
| 5428 */ |
| 5429 void validateModifiersForFunctionDeclarationStatement(Modifiers modifiers) { |
| 5430 if (modifiers.abstractKeyword != null || modifiers.constKeyword != null || m
odifiers.externalKeyword != null || modifiers.factoryKeyword != null || modifier
s.finalKeyword != null || modifiers.staticKeyword != null || modifiers.varKeywor
d != null) { |
| 5431 reportError7(ParserErrorCode.LOCAL_FUNCTION_DECLARATION_MODIFIER, []); |
| 5432 } |
| 5433 } |
| 5434 |
| 5435 /** |
| 5050 * Validate that the given set of modifiers is appropriate for a getter, sette
r, or method. | 5436 * Validate that the given set of modifiers is appropriate for a getter, sette
r, or method. |
| 5437 * |
| 5051 * @param modifiers the modifiers being validated | 5438 * @param modifiers the modifiers being validated |
| 5052 */ | 5439 */ |
| 5053 void validateModifiersForGetterOrSetterOrMethod(Modifiers modifiers) { | 5440 void validateModifiersForGetterOrSetterOrMethod(Modifiers modifiers) { |
| 5054 if (modifiers.abstractKeyword != null) { | 5441 if (modifiers.abstractKeyword != null) { |
| 5055 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); | 5442 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); |
| 5056 } | 5443 } |
| 5057 if (modifiers.constKeyword != null) { | 5444 if (modifiers.constKeyword != null) { |
| 5058 reportError8(ParserErrorCode.CONST_METHOD, modifiers.constKeyword, []); | 5445 reportError8(ParserErrorCode.CONST_METHOD, modifiers.constKeyword, []); |
| 5059 } | 5446 } |
| 5060 if (modifiers.factoryKeyword != null) { | 5447 if (modifiers.factoryKeyword != null) { |
| 5061 reportError8(ParserErrorCode.NON_CONSTRUCTOR_FACTORY, modifiers.factoryKey
word, []); | 5448 reportError8(ParserErrorCode.NON_CONSTRUCTOR_FACTORY, modifiers.factoryKey
word, []); |
| 5062 } | 5449 } |
| 5063 if (modifiers.finalKeyword != null) { | 5450 if (modifiers.finalKeyword != null) { |
| 5064 reportError8(ParserErrorCode.FINAL_METHOD, modifiers.finalKeyword, []); | 5451 reportError8(ParserErrorCode.FINAL_METHOD, modifiers.finalKeyword, []); |
| 5065 } | 5452 } |
| 5066 if (modifiers.varKeyword != null) { | 5453 if (modifiers.varKeyword != null) { |
| 5067 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); | 5454 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); |
| 5068 } | 5455 } |
| 5069 Token externalKeyword = modifiers.externalKeyword; | 5456 Token externalKeyword = modifiers.externalKeyword; |
| 5070 Token staticKeyword = modifiers.staticKeyword; | 5457 Token staticKeyword = modifiers.staticKeyword; |
| 5071 if (externalKeyword != null && staticKeyword != null && staticKeyword.offset
< externalKeyword.offset) { | 5458 if (externalKeyword != null && staticKeyword != null && staticKeyword.offset
< externalKeyword.offset) { |
| 5072 reportError8(ParserErrorCode.EXTERNAL_AFTER_STATIC, externalKeyword, []); | 5459 reportError8(ParserErrorCode.EXTERNAL_AFTER_STATIC, externalKeyword, []); |
| 5073 } | 5460 } |
| 5074 } | 5461 } |
| 5075 | 5462 |
| 5076 /** | 5463 /** |
| 5077 * Validate that the given set of modifiers is appropriate for a getter, sette
r, or method. | 5464 * Validate that the given set of modifiers is appropriate for a getter, sette
r, or method. |
| 5465 * |
| 5078 * @param modifiers the modifiers being validated | 5466 * @param modifiers the modifiers being validated |
| 5079 */ | 5467 */ |
| 5080 void validateModifiersForOperator(Modifiers modifiers) { | 5468 void validateModifiersForOperator(Modifiers modifiers) { |
| 5081 if (modifiers.abstractKeyword != null) { | 5469 if (modifiers.abstractKeyword != null) { |
| 5082 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); | 5470 reportError7(ParserErrorCode.ABSTRACT_CLASS_MEMBER, []); |
| 5083 } | 5471 } |
| 5084 if (modifiers.constKeyword != null) { | 5472 if (modifiers.constKeyword != null) { |
| 5085 reportError8(ParserErrorCode.CONST_METHOD, modifiers.constKeyword, []); | 5473 reportError8(ParserErrorCode.CONST_METHOD, modifiers.constKeyword, []); |
| 5086 } | 5474 } |
| 5087 if (modifiers.factoryKeyword != null) { | 5475 if (modifiers.factoryKeyword != null) { |
| 5088 reportError8(ParserErrorCode.NON_CONSTRUCTOR_FACTORY, modifiers.factoryKey
word, []); | 5476 reportError8(ParserErrorCode.NON_CONSTRUCTOR_FACTORY, modifiers.factoryKey
word, []); |
| 5089 } | 5477 } |
| 5090 if (modifiers.finalKeyword != null) { | 5478 if (modifiers.finalKeyword != null) { |
| 5091 reportError8(ParserErrorCode.FINAL_METHOD, modifiers.finalKeyword, []); | 5479 reportError8(ParserErrorCode.FINAL_METHOD, modifiers.finalKeyword, []); |
| 5092 } | 5480 } |
| 5093 if (modifiers.staticKeyword != null) { | 5481 if (modifiers.staticKeyword != null) { |
| 5094 reportError8(ParserErrorCode.STATIC_OPERATOR, modifiers.staticKeyword, [])
; | 5482 reportError8(ParserErrorCode.STATIC_OPERATOR, modifiers.staticKeyword, [])
; |
| 5095 } | 5483 } |
| 5096 if (modifiers.varKeyword != null) { | 5484 if (modifiers.varKeyword != null) { |
| 5097 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); | 5485 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); |
| 5098 } | 5486 } |
| 5099 } | 5487 } |
| 5100 | 5488 |
| 5101 /** | 5489 /** |
| 5102 * Validate that the given set of modifiers is appropriate for a top-level dec
laration. | 5490 * Validate that the given set of modifiers is appropriate for a top-level dec
laration. |
| 5491 * |
| 5103 * @param modifiers the modifiers being validated | 5492 * @param modifiers the modifiers being validated |
| 5104 */ | 5493 */ |
| 5105 void validateModifiersForTopLevelDeclaration(Modifiers modifiers) { | 5494 void validateModifiersForTopLevelDeclaration(Modifiers modifiers) { |
| 5106 if (modifiers.factoryKeyword != null) { | 5495 if (modifiers.factoryKeyword != null) { |
| 5107 reportError8(ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION, modifiers.fact
oryKeyword, []); | 5496 reportError8(ParserErrorCode.FACTORY_TOP_LEVEL_DECLARATION, modifiers.fact
oryKeyword, []); |
| 5108 } | 5497 } |
| 5109 if (modifiers.staticKeyword != null) { | 5498 if (modifiers.staticKeyword != null) { |
| 5110 reportError8(ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION, modifiers.stati
cKeyword, []); | 5499 reportError8(ParserErrorCode.STATIC_TOP_LEVEL_DECLARATION, modifiers.stati
cKeyword, []); |
| 5111 } | 5500 } |
| 5112 } | 5501 } |
| 5113 | 5502 |
| 5114 /** | 5503 /** |
| 5115 * Validate that the given set of modifiers is appropriate for a top-level fun
ction. | 5504 * Validate that the given set of modifiers is appropriate for a top-level fun
ction. |
| 5505 * |
| 5116 * @param modifiers the modifiers being validated | 5506 * @param modifiers the modifiers being validated |
| 5117 */ | 5507 */ |
| 5118 void validateModifiersForTopLevelFunction(Modifiers modifiers) { | 5508 void validateModifiersForTopLevelFunction(Modifiers modifiers) { |
| 5119 validateModifiersForTopLevelDeclaration(modifiers); | 5509 validateModifiersForTopLevelDeclaration(modifiers); |
| 5120 if (modifiers.abstractKeyword != null) { | 5510 if (modifiers.abstractKeyword != null) { |
| 5121 reportError7(ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION, []); | 5511 reportError7(ParserErrorCode.ABSTRACT_TOP_LEVEL_FUNCTION, []); |
| 5122 } | 5512 } |
| 5123 if (modifiers.constKeyword != null) { | 5513 if (modifiers.constKeyword != null) { |
| 5124 reportError8(ParserErrorCode.CONST_CLASS, modifiers.constKeyword, []); | 5514 reportError8(ParserErrorCode.CONST_CLASS, modifiers.constKeyword, []); |
| 5125 } | 5515 } |
| 5126 if (modifiers.finalKeyword != null) { | 5516 if (modifiers.finalKeyword != null) { |
| 5127 reportError8(ParserErrorCode.FINAL_CLASS, modifiers.finalKeyword, []); | 5517 reportError8(ParserErrorCode.FINAL_CLASS, modifiers.finalKeyword, []); |
| 5128 } | 5518 } |
| 5129 if (modifiers.varKeyword != null) { | 5519 if (modifiers.varKeyword != null) { |
| 5130 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); | 5520 reportError8(ParserErrorCode.VAR_RETURN_TYPE, modifiers.varKeyword, []); |
| 5131 } | 5521 } |
| 5132 } | 5522 } |
| 5133 | 5523 |
| 5134 /** | 5524 /** |
| 5135 * Validate that the given set of modifiers is appropriate for a field and ret
urn the 'final', | 5525 * Validate that the given set of modifiers is appropriate for a field and ret
urn the 'final', |
| 5136 * 'const' or 'var' keyword if there is one. | 5526 * 'const' or 'var' keyword if there is one. |
| 5527 * |
| 5137 * @param modifiers the modifiers being validated | 5528 * @param modifiers the modifiers being validated |
| 5138 * @return the 'final', 'const' or 'var' keyword associated with the field | 5529 * @return the 'final', 'const' or 'var' keyword associated with the field |
| 5139 */ | 5530 */ |
| 5140 Token validateModifiersForTopLevelVariable(Modifiers modifiers) { | 5531 Token validateModifiersForTopLevelVariable(Modifiers modifiers) { |
| 5141 validateModifiersForTopLevelDeclaration(modifiers); | 5532 validateModifiersForTopLevelDeclaration(modifiers); |
| 5142 if (modifiers.abstractKeyword != null) { | 5533 if (modifiers.abstractKeyword != null) { |
| 5143 reportError7(ParserErrorCode.ABSTRACT_TOP_LEVEL_VARIABLE, []); | 5534 reportError7(ParserErrorCode.ABSTRACT_TOP_LEVEL_VARIABLE, []); |
| 5144 } | 5535 } |
| 5145 if (modifiers.externalKeyword != null) { | 5536 if (modifiers.externalKeyword != null) { |
| 5146 reportError8(ParserErrorCode.EXTERNAL_FIELD, modifiers.externalKeyword, []
); | 5537 reportError8(ParserErrorCode.EXTERNAL_FIELD, modifiers.externalKeyword, []
); |
| (...skipping 12 matching lines...) Expand all Loading... |
| 5159 if (varKeyword != null) { | 5550 if (varKeyword != null) { |
| 5160 reportError8(ParserErrorCode.FINAL_AND_VAR, varKeyword, []); | 5551 reportError8(ParserErrorCode.FINAL_AND_VAR, varKeyword, []); |
| 5161 } | 5552 } |
| 5162 } | 5553 } |
| 5163 return lexicallyFirst([constKeyword, finalKeyword, varKeyword]); | 5554 return lexicallyFirst([constKeyword, finalKeyword, varKeyword]); |
| 5164 } | 5555 } |
| 5165 | 5556 |
| 5166 /** | 5557 /** |
| 5167 * Validate that the given set of modifiers is appropriate for a class and ret
urn the 'abstract' | 5558 * Validate that the given set of modifiers is appropriate for a class and ret
urn the 'abstract' |
| 5168 * keyword if there is one. | 5559 * keyword if there is one. |
| 5560 * |
| 5169 * @param modifiers the modifiers being validated | 5561 * @param modifiers the modifiers being validated |
| 5170 */ | 5562 */ |
| 5171 void validateModifiersForTypedef(Modifiers modifiers) { | 5563 void validateModifiersForTypedef(Modifiers modifiers) { |
| 5172 validateModifiersForTopLevelDeclaration(modifiers); | 5564 validateModifiersForTopLevelDeclaration(modifiers); |
| 5173 if (modifiers.abstractKeyword != null) { | 5565 if (modifiers.abstractKeyword != null) { |
| 5174 reportError8(ParserErrorCode.ABSTRACT_TYPEDEF, modifiers.abstractKeyword,
[]); | 5566 reportError8(ParserErrorCode.ABSTRACT_TYPEDEF, modifiers.abstractKeyword,
[]); |
| 5175 } | 5567 } |
| 5176 if (modifiers.constKeyword != null) { | 5568 if (modifiers.constKeyword != null) { |
| 5177 reportError8(ParserErrorCode.CONST_TYPEDEF, modifiers.constKeyword, []); | 5569 reportError8(ParserErrorCode.CONST_TYPEDEF, modifiers.constKeyword, []); |
| 5178 } | 5570 } |
| 5179 if (modifiers.externalKeyword != null) { | 5571 if (modifiers.externalKeyword != null) { |
| 5180 reportError8(ParserErrorCode.EXTERNAL_TYPEDEF, modifiers.externalKeyword,
[]); | 5572 reportError8(ParserErrorCode.EXTERNAL_TYPEDEF, modifiers.externalKeyword,
[]); |
| 5181 } | 5573 } |
| 5182 if (modifiers.finalKeyword != null) { | 5574 if (modifiers.finalKeyword != null) { |
| 5183 reportError8(ParserErrorCode.FINAL_TYPEDEF, modifiers.finalKeyword, []); | 5575 reportError8(ParserErrorCode.FINAL_TYPEDEF, modifiers.finalKeyword, []); |
| 5184 } | 5576 } |
| 5185 if (modifiers.varKeyword != null) { | 5577 if (modifiers.varKeyword != null) { |
| 5186 reportError8(ParserErrorCode.VAR_TYPEDEF, modifiers.varKeyword, []); | 5578 reportError8(ParserErrorCode.VAR_TYPEDEF, modifiers.varKeyword, []); |
| 5187 } | 5579 } |
| 5188 } | 5580 } |
| 5189 } | 5581 } |
| 5190 class KeywordToken_10 extends KeywordToken { | 5582 class KeywordToken_11 extends KeywordToken { |
| 5191 KeywordToken_10(Keyword arg0, int arg1) : super(arg0, arg1); | 5583 KeywordToken_11(Keyword arg0, int arg1) : super(arg0, arg1); |
| 5192 int get length => 0; | 5584 int get length => 0; |
| 5193 } | 5585 } |
| 5194 class AnalysisErrorListener_11 implements AnalysisErrorListener { | 5586 class AnalysisErrorListener_12 implements AnalysisErrorListener { |
| 5195 List<bool> errorFound; | 5587 List<bool> errorFound; |
| 5196 AnalysisErrorListener_11(this.errorFound); | 5588 AnalysisErrorListener_12(this.errorFound); |
| 5197 void onError(AnalysisError error) { | 5589 void onError(AnalysisError error) { |
| 5198 errorFound[0] = true; | 5590 errorFound[0] = true; |
| 5199 } | 5591 } |
| 5200 } | 5592 } |
| 5201 /** | 5593 /** |
| 5202 * The enumeration `ParserErrorCode` defines the error codes used for errors det
ected by the | 5594 * The enumeration `ParserErrorCode` defines the error codes used for errors det
ected by the |
| 5203 * parser. The convention for this class is for the name of the error code to in
dicate the problem | 5595 * parser. The convention for this class is for the name of the error code to in
dicate the problem |
| 5204 * that caused the error to be generated and for the error message to explain wh
at is wrong and, | 5596 * that caused the error to be generated and for the error message to explain wh
at is wrong and, |
| 5205 * when appropriate, how the problem can be corrected. | 5597 * when appropriate, how the problem can be corrected. |
| 5598 * |
| 5206 * @coverage dart.engine.parser | 5599 * @coverage dart.engine.parser |
| 5207 */ | 5600 */ |
| 5208 class ParserErrorCode implements Comparable<ParserErrorCode>, ErrorCode { | 5601 class ParserErrorCode implements Comparable<ParserErrorCode>, ErrorCode { |
| 5209 static final ParserErrorCode ABSTRACT_CLASS_MEMBER = new ParserErrorCode.con2(
'ABSTRACT_CLASS_MEMBER', 0, "Members of classes cannot be declared to be 'abstra
ct'"); | 5602 static final ParserErrorCode ABSTRACT_CLASS_MEMBER = new ParserErrorCode.con2(
'ABSTRACT_CLASS_MEMBER', 0, "Members of classes cannot be declared to be 'abstra
ct'"); |
| 5210 static final ParserErrorCode ABSTRACT_STATIC_METHOD = new ParserErrorCode.con2
('ABSTRACT_STATIC_METHOD', 1, "Static methods cannot be declared to be 'abstract
'"); | 5603 static final ParserErrorCode ABSTRACT_STATIC_METHOD = new ParserErrorCode.con2
('ABSTRACT_STATIC_METHOD', 1, "Static methods cannot be declared to be 'abstract
'"); |
| 5211 static final ParserErrorCode ABSTRACT_TOP_LEVEL_FUNCTION = new ParserErrorCode
.con2('ABSTRACT_TOP_LEVEL_FUNCTION', 2, "Top-level functions cannot be declared
to be 'abstract'"); | 5604 static final ParserErrorCode ABSTRACT_TOP_LEVEL_FUNCTION = new ParserErrorCode
.con2('ABSTRACT_TOP_LEVEL_FUNCTION', 2, "Top-level functions cannot be declared
to be 'abstract'"); |
| 5212 static final ParserErrorCode ABSTRACT_TOP_LEVEL_VARIABLE = new ParserErrorCode
.con2('ABSTRACT_TOP_LEVEL_VARIABLE', 3, "Top-level variables cannot be declared
to be 'abstract'"); | 5605 static final ParserErrorCode ABSTRACT_TOP_LEVEL_VARIABLE = new ParserErrorCode
.con2('ABSTRACT_TOP_LEVEL_VARIABLE', 3, "Top-level variables cannot be declared
to be 'abstract'"); |
| 5213 static final ParserErrorCode ABSTRACT_TYPEDEF = new ParserErrorCode.con2('ABST
RACT_TYPEDEF', 4, "Type aliases cannot be declared to be 'abstract'"); | 5606 static final ParserErrorCode ABSTRACT_TYPEDEF = new ParserErrorCode.con2('ABST
RACT_TYPEDEF', 4, "Type aliases cannot be declared to be 'abstract'"); |
| 5214 static final ParserErrorCode BREAK_OUTSIDE_OF_LOOP = new ParserErrorCode.con2(
'BREAK_OUTSIDE_OF_LOOP', 5, "A break statement cannot be used outside of a loop
or switch statement"); | 5607 static final ParserErrorCode BREAK_OUTSIDE_OF_LOOP = new ParserErrorCode.con2(
'BREAK_OUTSIDE_OF_LOOP', 5, "A break statement cannot be used outside of a loop
or switch statement"); |
| 5215 static final ParserErrorCode CONST_AND_FINAL = new ParserErrorCode.con2('CONST
_AND_FINAL', 6, "Members cannot be declared to be both 'const' and 'final'"); | 5608 static final ParserErrorCode CONST_AND_FINAL = new ParserErrorCode.con2('CONST
_AND_FINAL', 6, "Members cannot be declared to be both 'const' and 'final'"); |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5260 static final ParserErrorCode IMPLEMENTS_BEFORE_WITH = new ParserErrorCode.con2
('IMPLEMENTS_BEFORE_WITH', 51, "The with clause must be before the implements cl
ause"); | 5653 static final ParserErrorCode IMPLEMENTS_BEFORE_WITH = new ParserErrorCode.con2
('IMPLEMENTS_BEFORE_WITH', 51, "The with clause must be before the implements cl
ause"); |
| 5261 static final ParserErrorCode IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE = new Parse
rErrorCode.con2('IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE', 52, "Import directives
must preceed part directives"); | 5654 static final ParserErrorCode IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE = new Parse
rErrorCode.con2('IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE', 52, "Import directives
must preceed part directives"); |
| 5262 static final ParserErrorCode INITIALIZED_VARIABLE_IN_FOR_EACH = new ParserErro
rCode.con2('INITIALIZED_VARIABLE_IN_FOR_EACH', 53, "The loop variable in a for-e
ach loop cannot be initialized"); | 5655 static final ParserErrorCode INITIALIZED_VARIABLE_IN_FOR_EACH = new ParserErro
rCode.con2('INITIALIZED_VARIABLE_IN_FOR_EACH', 53, "The loop variable in a for-e
ach loop cannot be initialized"); |
| 5263 static final ParserErrorCode INVALID_CODE_POINT = new ParserErrorCode.con2('IN
VALID_CODE_POINT', 54, "The escape sequence '%s' is not a valid code point"); | 5656 static final ParserErrorCode INVALID_CODE_POINT = new ParserErrorCode.con2('IN
VALID_CODE_POINT', 54, "The escape sequence '%s' is not a valid code point"); |
| 5264 static final ParserErrorCode INVALID_COMMENT_REFERENCE = new ParserErrorCode.c
on2('INVALID_COMMENT_REFERENCE', 55, "Comment references should contain a possib
ly prefixed identifier and can start with 'new', but should not contain anything
else"); | 5657 static final ParserErrorCode INVALID_COMMENT_REFERENCE = new ParserErrorCode.c
on2('INVALID_COMMENT_REFERENCE', 55, "Comment references should contain a possib
ly prefixed identifier and can start with 'new', but should not contain anything
else"); |
| 5265 static final ParserErrorCode INVALID_HEX_ESCAPE = new ParserErrorCode.con2('IN
VALID_HEX_ESCAPE', 56, "An escape sequence starting with '\\x' must be followed
by 2 hexidecimal digits"); | 5658 static final ParserErrorCode INVALID_HEX_ESCAPE = new ParserErrorCode.con2('IN
VALID_HEX_ESCAPE', 56, "An escape sequence starting with '\\x' must be followed
by 2 hexidecimal digits"); |
| 5266 static final ParserErrorCode INVALID_OPERATOR = new ParserErrorCode.con2('INVA
LID_OPERATOR', 57, "The string '%s' is not a valid operator"); | 5659 static final ParserErrorCode INVALID_OPERATOR = new ParserErrorCode.con2('INVA
LID_OPERATOR', 57, "The string '%s' is not a valid operator"); |
| 5267 static final ParserErrorCode INVALID_OPERATOR_FOR_SUPER = new ParserErrorCode.
con2('INVALID_OPERATOR_FOR_SUPER', 58, "The operator '%s' cannot be used with 's
uper'"); | 5660 static final ParserErrorCode INVALID_OPERATOR_FOR_SUPER = new ParserErrorCode.
con2('INVALID_OPERATOR_FOR_SUPER', 58, "The operator '%s' cannot be used with 's
uper'"); |
| 5268 static final ParserErrorCode INVALID_UNICODE_ESCAPE = new ParserErrorCode.con2
('INVALID_UNICODE_ESCAPE', 59, "An escape sequence starting with '\\u' must be f
ollowed by 4 hexidecimal digits or from 1 to 6 digits between '{' and '}'"); | 5661 static final ParserErrorCode INVALID_UNICODE_ESCAPE = new ParserErrorCode.con2
('INVALID_UNICODE_ESCAPE', 59, "An escape sequence starting with '\\u' must be f
ollowed by 4 hexidecimal digits or from 1 to 6 digits between '{' and '}'"); |
| 5269 static final ParserErrorCode LIBRARY_DIRECTIVE_NOT_FIRST = new ParserErrorCode
.con2('LIBRARY_DIRECTIVE_NOT_FIRST', 60, "The library directive must appear befo
re all other directives"); | 5662 static final ParserErrorCode LIBRARY_DIRECTIVE_NOT_FIRST = new ParserErrorCode
.con2('LIBRARY_DIRECTIVE_NOT_FIRST', 60, "The library directive must appear befo
re all other directives"); |
| 5270 static final ParserErrorCode MISSING_ASSIGNABLE_SELECTOR = new ParserErrorCode
.con2('MISSING_ASSIGNABLE_SELECTOR', 61, "Missing selector such as \".<identifie
r>\" or \"[0]\""); | 5663 static final ParserErrorCode LOCAL_FUNCTION_DECLARATION_MODIFIER = new ParserE
rrorCode.con2('LOCAL_FUNCTION_DECLARATION_MODIFIER', 61, "Local function declara
tions cannot specify any modifier"); |
| 5271 static final ParserErrorCode MISSING_CATCH_OR_FINALLY = new ParserErrorCode.co
n2('MISSING_CATCH_OR_FINALLY', 62, "A try statement must have either a catch or
finally clause"); | 5664 static final ParserErrorCode MISSING_ASSIGNABLE_SELECTOR = new ParserErrorCode
.con2('MISSING_ASSIGNABLE_SELECTOR', 62, "Missing selector such as \".<identifie
r>\" or \"[0]\""); |
| 5272 static final ParserErrorCode MISSING_CLASS_BODY = new ParserErrorCode.con2('MI
SSING_CLASS_BODY', 63, "A class definition must have a body, even if it is empty
"); | 5665 static final ParserErrorCode MISSING_CATCH_OR_FINALLY = new ParserErrorCode.co
n2('MISSING_CATCH_OR_FINALLY', 63, "A try statement must have either a catch or
finally clause"); |
| 5273 static final ParserErrorCode MISSING_CLOSING_PARENTHESIS = new ParserErrorCode
.con2('MISSING_CLOSING_PARENTHESIS', 64, "The closing parenthesis is missing"); | 5666 static final ParserErrorCode MISSING_CLASS_BODY = new ParserErrorCode.con2('MI
SSING_CLASS_BODY', 64, "A class definition must have a body, even if it is empty
"); |
| 5274 static final ParserErrorCode MISSING_CONST_FINAL_VAR_OR_TYPE = new ParserError
Code.con2('MISSING_CONST_FINAL_VAR_OR_TYPE', 65, "Variables must be declared usi
ng the keywords 'const', 'final', 'var' or a type name"); | 5667 static final ParserErrorCode MISSING_CLOSING_PARENTHESIS = new ParserErrorCode
.con2('MISSING_CLOSING_PARENTHESIS', 65, "The closing parenthesis is missing"); |
| 5275 static final ParserErrorCode MISSING_EXPRESSION_IN_THROW = new ParserErrorCode
.con2('MISSING_EXPRESSION_IN_THROW', 66, "Throw expressions must compute the obj
ect to be thrown"); | 5668 static final ParserErrorCode MISSING_CONST_FINAL_VAR_OR_TYPE = new ParserError
Code.con2('MISSING_CONST_FINAL_VAR_OR_TYPE', 66, "Variables must be declared usi
ng the keywords 'const', 'final', 'var' or a type name"); |
| 5276 static final ParserErrorCode MISSING_FUNCTION_BODY = new ParserErrorCode.con2(
'MISSING_FUNCTION_BODY', 67, "A function body must be provided"); | 5669 static final ParserErrorCode MISSING_EXPRESSION_IN_THROW = new ParserErrorCode
.con2('MISSING_EXPRESSION_IN_THROW', 67, "Throw expressions must compute the obj
ect to be thrown"); |
| 5277 static final ParserErrorCode MISSING_FUNCTION_PARAMETERS = new ParserErrorCode
.con2('MISSING_FUNCTION_PARAMETERS', 68, "Functions must have an explicit list o
f parameters"); | 5670 static final ParserErrorCode MISSING_FUNCTION_BODY = new ParserErrorCode.con2(
'MISSING_FUNCTION_BODY', 68, "A function body must be provided"); |
| 5278 static final ParserErrorCode MISSING_IDENTIFIER = new ParserErrorCode.con2('MI
SSING_IDENTIFIER', 69, "Expected an identifier"); | 5671 static final ParserErrorCode MISSING_FUNCTION_PARAMETERS = new ParserErrorCode
.con2('MISSING_FUNCTION_PARAMETERS', 69, "Functions must have an explicit list o
f parameters"); |
| 5279 static final ParserErrorCode MISSING_KEYWORD_OPERATOR = new ParserErrorCode.co
n2('MISSING_KEYWORD_OPERATOR', 70, "Operator declarations must be preceeded by t
he keyword 'operator'"); | 5672 static final ParserErrorCode MISSING_IDENTIFIER = new ParserErrorCode.con2('MI
SSING_IDENTIFIER', 70, "Expected an identifier"); |
| 5280 static final ParserErrorCode MISSING_NAME_IN_LIBRARY_DIRECTIVE = new ParserErr
orCode.con2('MISSING_NAME_IN_LIBRARY_DIRECTIVE', 71, "Library directives must in
clude a library name"); | 5673 static final ParserErrorCode MISSING_KEYWORD_OPERATOR = new ParserErrorCode.co
n2('MISSING_KEYWORD_OPERATOR', 71, "Operator declarations must be preceeded by t
he keyword 'operator'"); |
| 5281 static final ParserErrorCode MISSING_NAME_IN_PART_OF_DIRECTIVE = new ParserErr
orCode.con2('MISSING_NAME_IN_PART_OF_DIRECTIVE', 72, "Library directives must in
clude a library name"); | 5674 static final ParserErrorCode MISSING_NAME_IN_LIBRARY_DIRECTIVE = new ParserErr
orCode.con2('MISSING_NAME_IN_LIBRARY_DIRECTIVE', 72, "Library directives must in
clude a library name"); |
| 5282 static final ParserErrorCode MISSING_STATEMENT = new ParserErrorCode.con2('MIS
SING_STATEMENT', 73, "Expected a statement"); | 5675 static final ParserErrorCode MISSING_NAME_IN_PART_OF_DIRECTIVE = new ParserErr
orCode.con2('MISSING_NAME_IN_PART_OF_DIRECTIVE', 73, "Library directives must in
clude a library name"); |
| 5283 static final ParserErrorCode MISSING_TERMINATOR_FOR_PARAMETER_GROUP = new Pars
erErrorCode.con2('MISSING_TERMINATOR_FOR_PARAMETER_GROUP', 74, "There is no '%s'
to close the parameter group"); | 5676 static final ParserErrorCode MISSING_STATEMENT = new ParserErrorCode.con2('MIS
SING_STATEMENT', 74, "Expected a statement"); |
| 5284 static final ParserErrorCode MISSING_TYPEDEF_PARAMETERS = new ParserErrorCode.
con2('MISSING_TYPEDEF_PARAMETERS', 75, "Type aliases for functions must have an
explicit list of parameters"); | 5677 static final ParserErrorCode MISSING_TERMINATOR_FOR_PARAMETER_GROUP = new Pars
erErrorCode.con2('MISSING_TERMINATOR_FOR_PARAMETER_GROUP', 75, "There is no '%s'
to close the parameter group"); |
| 5285 static final ParserErrorCode MISSING_VARIABLE_IN_FOR_EACH = new ParserErrorCod
e.con2('MISSING_VARIABLE_IN_FOR_EACH', 76, "A loop variable must be declared in
a for-each loop before the 'in', but none were found"); | 5678 static final ParserErrorCode MISSING_TYPEDEF_PARAMETERS = new ParserErrorCode.
con2('MISSING_TYPEDEF_PARAMETERS', 76, "Type aliases for functions must have an
explicit list of parameters"); |
| 5286 static final ParserErrorCode MIXED_PARAMETER_GROUPS = new ParserErrorCode.con2
('MIXED_PARAMETER_GROUPS', 77, "Cannot have both positional and named parameters
in a single parameter list"); | 5679 static final ParserErrorCode MISSING_VARIABLE_IN_FOR_EACH = new ParserErrorCod
e.con2('MISSING_VARIABLE_IN_FOR_EACH', 77, "A loop variable must be declared in
a for-each loop before the 'in', but none were found"); |
| 5287 static final ParserErrorCode MULTIPLE_EXTENDS_CLAUSES = new ParserErrorCode.co
n2('MULTIPLE_EXTENDS_CLAUSES', 78, "Each class definition can have at most one e
xtends clause"); | 5680 static final ParserErrorCode MIXED_PARAMETER_GROUPS = new ParserErrorCode.con2
('MIXED_PARAMETER_GROUPS', 78, "Cannot have both positional and named parameters
in a single parameter list"); |
| 5288 static final ParserErrorCode MULTIPLE_IMPLEMENTS_CLAUSES = new ParserErrorCode
.con2('MULTIPLE_IMPLEMENTS_CLAUSES', 79, "Each class definition can have at most
one implements clause"); | 5681 static final ParserErrorCode MULTIPLE_EXTENDS_CLAUSES = new ParserErrorCode.co
n2('MULTIPLE_EXTENDS_CLAUSES', 79, "Each class definition can have at most one e
xtends clause"); |
| 5289 static final ParserErrorCode MULTIPLE_LIBRARY_DIRECTIVES = new ParserErrorCode
.con2('MULTIPLE_LIBRARY_DIRECTIVES', 80, "Only one library directive may be decl
ared in a file"); | 5682 static final ParserErrorCode MULTIPLE_IMPLEMENTS_CLAUSES = new ParserErrorCode
.con2('MULTIPLE_IMPLEMENTS_CLAUSES', 80, "Each class definition can have at most
one implements clause"); |
| 5290 static final ParserErrorCode MULTIPLE_NAMED_PARAMETER_GROUPS = new ParserError
Code.con2('MULTIPLE_NAMED_PARAMETER_GROUPS', 81, "Cannot have multiple groups of
named parameters in a single parameter list"); | 5683 static final ParserErrorCode MULTIPLE_LIBRARY_DIRECTIVES = new ParserErrorCode
.con2('MULTIPLE_LIBRARY_DIRECTIVES', 81, "Only one library directive may be decl
ared in a file"); |
| 5291 static final ParserErrorCode MULTIPLE_PART_OF_DIRECTIVES = new ParserErrorCode
.con2('MULTIPLE_PART_OF_DIRECTIVES', 82, "Only one part-of directive may be decl
ared in a file"); | 5684 static final ParserErrorCode MULTIPLE_NAMED_PARAMETER_GROUPS = new ParserError
Code.con2('MULTIPLE_NAMED_PARAMETER_GROUPS', 82, "Cannot have multiple groups of
named parameters in a single parameter list"); |
| 5292 static final ParserErrorCode MULTIPLE_POSITIONAL_PARAMETER_GROUPS = new Parser
ErrorCode.con2('MULTIPLE_POSITIONAL_PARAMETER_GROUPS', 83, "Cannot have multiple
groups of positional parameters in a single parameter list"); | 5685 static final ParserErrorCode MULTIPLE_PART_OF_DIRECTIVES = new ParserErrorCode
.con2('MULTIPLE_PART_OF_DIRECTIVES', 83, "Only one part-of directive may be decl
ared in a file"); |
| 5293 static final ParserErrorCode MULTIPLE_VARIABLES_IN_FOR_EACH = new ParserErrorC
ode.con2('MULTIPLE_VARIABLES_IN_FOR_EACH', 84, "A single loop variable must be d
eclared in a for-each loop before the 'in', but %s were found"); | 5686 static final ParserErrorCode MULTIPLE_POSITIONAL_PARAMETER_GROUPS = new Parser
ErrorCode.con2('MULTIPLE_POSITIONAL_PARAMETER_GROUPS', 84, "Cannot have multiple
groups of positional parameters in a single parameter list"); |
| 5294 static final ParserErrorCode MULTIPLE_WITH_CLAUSES = new ParserErrorCode.con2(
'MULTIPLE_WITH_CLAUSES', 85, "Each class definition can have at most one with cl
ause"); | 5687 static final ParserErrorCode MULTIPLE_VARIABLES_IN_FOR_EACH = new ParserErrorC
ode.con2('MULTIPLE_VARIABLES_IN_FOR_EACH', 85, "A single loop variable must be d
eclared in a for-each loop before the 'in', but %s were found"); |
| 5295 static final ParserErrorCode NAMED_FUNCTION_EXPRESSION = new ParserErrorCode.c
on2('NAMED_FUNCTION_EXPRESSION', 86, "Function expressions cannot be named"); | 5688 static final ParserErrorCode MULTIPLE_WITH_CLAUSES = new ParserErrorCode.con2(
'MULTIPLE_WITH_CLAUSES', 86, "Each class definition can have at most one with cl
ause"); |
| 5296 static final ParserErrorCode NAMED_PARAMETER_OUTSIDE_GROUP = new ParserErrorCo
de.con2('NAMED_PARAMETER_OUTSIDE_GROUP', 87, "Named parameters must be enclosed
in curly braces ('{' and '}')"); | 5689 static final ParserErrorCode NAMED_FUNCTION_EXPRESSION = new ParserErrorCode.c
on2('NAMED_FUNCTION_EXPRESSION', 87, "Function expressions cannot be named"); |
| 5297 static final ParserErrorCode NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE = new Parser
ErrorCode.con2('NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE', 88, "Native functions can
only be declared in the SDK and code that is loaded through native extensions")
; | 5690 static final ParserErrorCode NAMED_PARAMETER_OUTSIDE_GROUP = new ParserErrorCo
de.con2('NAMED_PARAMETER_OUTSIDE_GROUP', 88, "Named parameters must be enclosed
in curly braces ('{' and '}')"); |
| 5298 static final ParserErrorCode NON_CONSTRUCTOR_FACTORY = new ParserErrorCode.con
2('NON_CONSTRUCTOR_FACTORY', 89, "Only constructors can be declared to be a 'fac
tory'"); | 5691 static final ParserErrorCode NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE = new Parser
ErrorCode.con2('NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE', 89, "Native functions can
only be declared in the SDK and code that is loaded through native extensions")
; |
| 5299 static final ParserErrorCode NON_IDENTIFIER_LIBRARY_NAME = new ParserErrorCode
.con2('NON_IDENTIFIER_LIBRARY_NAME', 90, "The name of a library must be an ident
ifier"); | 5692 static final ParserErrorCode NON_CONSTRUCTOR_FACTORY = new ParserErrorCode.con
2('NON_CONSTRUCTOR_FACTORY', 90, "Only constructors can be declared to be a 'fac
tory'"); |
| 5300 static final ParserErrorCode NON_PART_OF_DIRECTIVE_IN_PART = new ParserErrorCo
de.con2('NON_PART_OF_DIRECTIVE_IN_PART', 91, "The part-of directive must be the
only directive in a part"); | 5693 static final ParserErrorCode NON_IDENTIFIER_LIBRARY_NAME = new ParserErrorCode
.con2('NON_IDENTIFIER_LIBRARY_NAME', 91, "The name of a library must be an ident
ifier"); |
| 5301 static final ParserErrorCode NON_USER_DEFINABLE_OPERATOR = new ParserErrorCode
.con2('NON_USER_DEFINABLE_OPERATOR', 92, "The operator '%s' is not user definabl
e"); | 5694 static final ParserErrorCode NON_PART_OF_DIRECTIVE_IN_PART = new ParserErrorCo
de.con2('NON_PART_OF_DIRECTIVE_IN_PART', 92, "The part-of directive must be the
only directive in a part"); |
| 5302 static final ParserErrorCode POSITIONAL_AFTER_NAMED_ARGUMENT = new ParserError
Code.con2('POSITIONAL_AFTER_NAMED_ARGUMENT', 93, "Positional arguments must occu
r before named arguments"); | 5695 static final ParserErrorCode NON_USER_DEFINABLE_OPERATOR = new ParserErrorCode
.con2('NON_USER_DEFINABLE_OPERATOR', 93, "The operator '%s' is not user definabl
e"); |
| 5303 static final ParserErrorCode POSITIONAL_PARAMETER_OUTSIDE_GROUP = new ParserEr
rorCode.con2('POSITIONAL_PARAMETER_OUTSIDE_GROUP', 94, "Positional parameters mu
st be enclosed in square brackets ('[' and ']')"); | 5696 static final ParserErrorCode NORMAL_BEFORE_OPTIONAL_PARAMETERS = new ParserErr
orCode.con2('NORMAL_BEFORE_OPTIONAL_PARAMETERS', 94, "Normal parameters must occ
ur before optional parameters"); |
| 5304 static final ParserErrorCode STATIC_AFTER_CONST = new ParserErrorCode.con2('ST
ATIC_AFTER_CONST', 95, "The modifier 'static' should be before the modifier 'con
st'"); | 5697 static final ParserErrorCode POSITIONAL_AFTER_NAMED_ARGUMENT = new ParserError
Code.con2('POSITIONAL_AFTER_NAMED_ARGUMENT', 95, "Positional arguments must occu
r before named arguments"); |
| 5305 static final ParserErrorCode STATIC_AFTER_FINAL = new ParserErrorCode.con2('ST
ATIC_AFTER_FINAL', 96, "The modifier 'static' should be before the modifier 'fin
al'"); | 5698 static final ParserErrorCode POSITIONAL_PARAMETER_OUTSIDE_GROUP = new ParserEr
rorCode.con2('POSITIONAL_PARAMETER_OUTSIDE_GROUP', 96, "Positional parameters mu
st be enclosed in square brackets ('[' and ']')"); |
| 5306 static final ParserErrorCode STATIC_AFTER_VAR = new ParserErrorCode.con2('STAT
IC_AFTER_VAR', 97, "The modifier 'static' should be before the modifier 'var'"); | 5699 static final ParserErrorCode STATIC_AFTER_CONST = new ParserErrorCode.con2('ST
ATIC_AFTER_CONST', 97, "The modifier 'static' should be before the modifier 'con
st'"); |
| 5307 static final ParserErrorCode STATIC_CONSTRUCTOR = new ParserErrorCode.con2('ST
ATIC_CONSTRUCTOR', 98, "Constructors cannot be static"); | 5700 static final ParserErrorCode STATIC_AFTER_FINAL = new ParserErrorCode.con2('ST
ATIC_AFTER_FINAL', 98, "The modifier 'static' should be before the modifier 'fin
al'"); |
| 5308 static final ParserErrorCode STATIC_GETTER_WITHOUT_BODY = new ParserErrorCode.
con2('STATIC_GETTER_WITHOUT_BODY', 99, "A 'static' getter must have a body"); | 5701 static final ParserErrorCode STATIC_AFTER_VAR = new ParserErrorCode.con2('STAT
IC_AFTER_VAR', 99, "The modifier 'static' should be before the modifier 'var'"); |
| 5309 static final ParserErrorCode STATIC_OPERATOR = new ParserErrorCode.con2('STATI
C_OPERATOR', 100, "Operators cannot be static"); | 5702 static final ParserErrorCode STATIC_CONSTRUCTOR = new ParserErrorCode.con2('ST
ATIC_CONSTRUCTOR', 100, "Constructors cannot be static"); |
| 5310 static final ParserErrorCode STATIC_SETTER_WITHOUT_BODY = new ParserErrorCode.
con2('STATIC_SETTER_WITHOUT_BODY', 101, "A 'static' setter must have a body"); | 5703 static final ParserErrorCode STATIC_GETTER_WITHOUT_BODY = new ParserErrorCode.
con2('STATIC_GETTER_WITHOUT_BODY', 101, "A 'static' getter must have a body"); |
| 5311 static final ParserErrorCode STATIC_TOP_LEVEL_DECLARATION = new ParserErrorCod
e.con2('STATIC_TOP_LEVEL_DECLARATION', 102, "Top-level declarations cannot be de
clared to be 'static'"); | 5704 static final ParserErrorCode STATIC_OPERATOR = new ParserErrorCode.con2('STATI
C_OPERATOR', 102, "Operators cannot be static"); |
| 5312 static final ParserErrorCode SWITCH_HAS_CASE_AFTER_DEFAULT_CASE = new ParserEr
rorCode.con2('SWITCH_HAS_CASE_AFTER_DEFAULT_CASE', 103, "The 'default' case shou
ld be the last case in a switch statement"); | 5705 static final ParserErrorCode STATIC_SETTER_WITHOUT_BODY = new ParserErrorCode.
con2('STATIC_SETTER_WITHOUT_BODY', 103, "A 'static' setter must have a body"); |
| 5313 static final ParserErrorCode SWITCH_HAS_MULTIPLE_DEFAULT_CASES = new ParserErr
orCode.con2('SWITCH_HAS_MULTIPLE_DEFAULT_CASES', 104, "The 'default' case can on
ly be declared once"); | 5706 static final ParserErrorCode STATIC_TOP_LEVEL_DECLARATION = new ParserErrorCod
e.con2('STATIC_TOP_LEVEL_DECLARATION', 104, "Top-level declarations cannot be de
clared to be 'static'"); |
| 5314 static final ParserErrorCode TOP_LEVEL_OPERATOR = new ParserErrorCode.con2('TO
P_LEVEL_OPERATOR', 105, "Operators must be declared within a class"); | 5707 static final ParserErrorCode SWITCH_HAS_CASE_AFTER_DEFAULT_CASE = new ParserEr
rorCode.con2('SWITCH_HAS_CASE_AFTER_DEFAULT_CASE', 105, "The 'default' case shou
ld be the last case in a switch statement"); |
| 5315 static final ParserErrorCode UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP = new P
arserErrorCode.con2('UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP', 106, "There is
no '%s' to open a parameter group"); | 5708 static final ParserErrorCode SWITCH_HAS_MULTIPLE_DEFAULT_CASES = new ParserErr
orCode.con2('SWITCH_HAS_MULTIPLE_DEFAULT_CASES', 106, "The 'default' case can on
ly be declared once"); |
| 5316 static final ParserErrorCode UNEXPECTED_TOKEN = new ParserErrorCode.con2('UNEX
PECTED_TOKEN', 107, "Unexpected token '%s'"); | 5709 static final ParserErrorCode TOP_LEVEL_OPERATOR = new ParserErrorCode.con2('TO
P_LEVEL_OPERATOR', 107, "Operators must be declared within a class"); |
| 5317 static final ParserErrorCode WITH_BEFORE_EXTENDS = new ParserErrorCode.con2('W
ITH_BEFORE_EXTENDS', 108, "The extends clause must be before the with clause"); | 5710 static final ParserErrorCode UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP = new P
arserErrorCode.con2('UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP', 108, "There is
no '%s' to open a parameter group"); |
| 5318 static final ParserErrorCode WITH_WITHOUT_EXTENDS = new ParserErrorCode.con2('
WITH_WITHOUT_EXTENDS', 109, "The with clause cannot be used without an extends c
lause"); | 5711 static final ParserErrorCode UNEXPECTED_TOKEN = new ParserErrorCode.con2('UNEX
PECTED_TOKEN', 109, "Unexpected token '%s'"); |
| 5319 static final ParserErrorCode WRONG_SEPARATOR_FOR_NAMED_PARAMETER = new ParserE
rrorCode.con2('WRONG_SEPARATOR_FOR_NAMED_PARAMETER', 110, "The default value of
a named parameter should be preceeded by ':'"); | 5712 static final ParserErrorCode WITH_BEFORE_EXTENDS = new ParserErrorCode.con2('W
ITH_BEFORE_EXTENDS', 110, "The extends clause must be before the with clause"); |
| 5320 static final ParserErrorCode WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER = new Pa
rserErrorCode.con2('WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER', 111, "The default
value of a positional parameter should be preceeded by '='"); | 5713 static final ParserErrorCode WITH_WITHOUT_EXTENDS = new ParserErrorCode.con2('
WITH_WITHOUT_EXTENDS', 111, "The with clause cannot be used without an extends c
lause"); |
| 5321 static final ParserErrorCode WRONG_TERMINATOR_FOR_PARAMETER_GROUP = new Parser
ErrorCode.con2('WRONG_TERMINATOR_FOR_PARAMETER_GROUP', 112, "Expected '%s' to cl
ose parameter group"); | 5714 static final ParserErrorCode WRONG_SEPARATOR_FOR_NAMED_PARAMETER = new ParserE
rrorCode.con2('WRONG_SEPARATOR_FOR_NAMED_PARAMETER', 112, "The default value of
a named parameter should be preceeded by ':'"); |
| 5322 static final ParserErrorCode VAR_AS_TYPE_NAME = new ParserErrorCode.con2('VAR_
AS_TYPE_NAME', 113, "The keyword 'var' cannot be used as a type name"); | 5715 static final ParserErrorCode WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER = new Pa
rserErrorCode.con2('WRONG_SEPARATOR_FOR_POSITIONAL_PARAMETER', 113, "The default
value of a positional parameter should be preceeded by '='"); |
| 5323 static final ParserErrorCode VAR_CLASS = new ParserErrorCode.con2('VAR_CLASS',
114, "Classes cannot be declared to be 'var'"); | 5716 static final ParserErrorCode WRONG_TERMINATOR_FOR_PARAMETER_GROUP = new Parser
ErrorCode.con2('WRONG_TERMINATOR_FOR_PARAMETER_GROUP', 114, "Expected '%s' to cl
ose parameter group"); |
| 5324 static final ParserErrorCode VAR_RETURN_TYPE = new ParserErrorCode.con2('VAR_R
ETURN_TYPE', 115, "The return type cannot be 'var'"); | 5717 static final ParserErrorCode VAR_AS_TYPE_NAME = new ParserErrorCode.con2('VAR_
AS_TYPE_NAME', 115, "The keyword 'var' cannot be used as a type name"); |
| 5325 static final ParserErrorCode VAR_TYPEDEF = new ParserErrorCode.con2('VAR_TYPED
EF', 116, "Type aliases cannot be declared to be 'var'"); | 5718 static final ParserErrorCode VAR_CLASS = new ParserErrorCode.con2('VAR_CLASS',
116, "Classes cannot be declared to be 'var'"); |
| 5326 static final ParserErrorCode VOID_PARAMETER = new ParserErrorCode.con2('VOID_P
ARAMETER', 117, "Parameters cannot have a type of 'void'"); | 5719 static final ParserErrorCode VAR_RETURN_TYPE = new ParserErrorCode.con2('VAR_R
ETURN_TYPE', 117, "The return type cannot be 'var'"); |
| 5327 static final ParserErrorCode VOID_VARIABLE = new ParserErrorCode.con2('VOID_VA
RIABLE', 118, "Variables cannot have a type of 'void'"); | 5720 static final ParserErrorCode VAR_TYPEDEF = new ParserErrorCode.con2('VAR_TYPED
EF', 118, "Type aliases cannot be declared to be 'var'"); |
| 5328 static final List<ParserErrorCode> values = [ABSTRACT_CLASS_MEMBER, ABSTRACT_S
TATIC_METHOD, ABSTRACT_TOP_LEVEL_FUNCTION, ABSTRACT_TOP_LEVEL_VARIABLE, ABSTRACT
_TYPEDEF, BREAK_OUTSIDE_OF_LOOP, CONST_AND_FINAL, CONST_AND_VAR, CONST_CLASS, CO
NST_CONSTRUCTOR_WITH_BODY, CONST_FACTORY, CONST_METHOD, CONST_TYPEDEF, CONSTRUCT
OR_WITH_RETURN_TYPE, CONTINUE_OUTSIDE_OF_LOOP, CONTINUE_WITHOUT_LABEL_IN_CASE, D
EPRECATED_ARGUMENT_DEFINITION_TEST, DIRECTIVE_AFTER_DECLARATION, DUPLICATE_LABEL
_IN_SWITCH_STATEMENT, DUPLICATED_MODIFIER, EXPECTED_CASE_OR_DEFAULT, EXPECTED_CL
ASS_MEMBER, EXPECTED_EXECUTABLE, EXPECTED_LIST_OR_MAP_LITERAL, EXPECTED_STRING_L
ITERAL, EXPECTED_TOKEN, EXPECTED_TWO_MAP_TYPE_ARGUMENTS, EXPECTED_TYPE_NAME, EXP
ORT_DIRECTIVE_AFTER_PART_DIRECTIVE, EXTERNAL_AFTER_CONST, EXTERNAL_AFTER_FACTORY
, EXTERNAL_AFTER_STATIC, EXTERNAL_CLASS, EXTERNAL_CONSTRUCTOR_WITH_BODY, EXTERNA
L_FIELD, EXTERNAL_GETTER_WITH_BODY, EXTERNAL_METHOD_WITH_BODY, EXTERNAL_OPERATOR
_WITH_BODY, EXTERNAL_SETTER_WITH_BODY, EXTERNAL_TYPEDEF, FACTORY_TOP_LEVEL_DECLA
RATION, FACTORY_WITHOUT_BODY, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_AND_V
AR, FINAL_CLASS, FINAL_CONSTRUCTOR, FINAL_METHOD, FINAL_TYPEDEF, GETTER_WITH_PAR
AMETERS, ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, IMPLEMENTS_BEFORE_EXTENDS, IMPLEM
ENTS_BEFORE_WITH, IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, INITIALIZED_VARIABLE_IN
_FOR_EACH, INVALID_CODE_POINT, INVALID_COMMENT_REFERENCE, INVALID_HEX_ESCAPE, IN
VALID_OPERATOR, INVALID_OPERATOR_FOR_SUPER, INVALID_UNICODE_ESCAPE, LIBRARY_DIRE
CTIVE_NOT_FIRST, MISSING_ASSIGNABLE_SELECTOR, MISSING_CATCH_OR_FINALLY, MISSING_
CLASS_BODY, MISSING_CLOSING_PARENTHESIS, MISSING_CONST_FINAL_VAR_OR_TYPE, MISSIN
G_EXPRESSION_IN_THROW, MISSING_FUNCTION_BODY, MISSING_FUNCTION_PARAMETERS, MISSI
NG_IDENTIFIER, MISSING_KEYWORD_OPERATOR, MISSING_NAME_IN_LIBRARY_DIRECTIVE, MISS
ING_NAME_IN_PART_OF_DIRECTIVE, MISSING_STATEMENT, MISSING_TERMINATOR_FOR_PARAMET
ER_GROUP, MISSING_TYPEDEF_PARAMETERS, MISSING_VARIABLE_IN_FOR_EACH, MIXED_PARAME
TER_GROUPS, MULTIPLE_EXTENDS_CLAUSES, MULTIPLE_IMPLEMENTS_CLAUSES, MULTIPLE_LIBR
ARY_DIRECTIVES, MULTIPLE_NAMED_PARAMETER_GROUPS, MULTIPLE_PART_OF_DIRECTIVES, MU
LTIPLE_POSITIONAL_PARAMETER_GROUPS, MULTIPLE_VARIABLES_IN_FOR_EACH, MULTIPLE_WIT
H_CLAUSES, NAMED_FUNCTION_EXPRESSION, NAMED_PARAMETER_OUTSIDE_GROUP, NATIVE_FUNC
TION_BODY_IN_NON_SDK_CODE, NON_CONSTRUCTOR_FACTORY, NON_IDENTIFIER_LIBRARY_NAME,
NON_PART_OF_DIRECTIVE_IN_PART, NON_USER_DEFINABLE_OPERATOR, POSITIONAL_AFTER_NA
MED_ARGUMENT, POSITIONAL_PARAMETER_OUTSIDE_GROUP, STATIC_AFTER_CONST, STATIC_AFT
ER_FINAL, STATIC_AFTER_VAR, STATIC_CONSTRUCTOR, STATIC_GETTER_WITHOUT_BODY, STAT
IC_OPERATOR, STATIC_SETTER_WITHOUT_BODY, STATIC_TOP_LEVEL_DECLARATION, SWITCH_HA
S_CASE_AFTER_DEFAULT_CASE, SWITCH_HAS_MULTIPLE_DEFAULT_CASES, TOP_LEVEL_OPERATOR
, UNEXPECTED_TERMINATOR_FOR_PARAMETER_GROUP, UNEXPECTED_TOKEN, WITH_BEFORE_EXTEN
DS, WITH_WITHOUT_EXTENDS, WRONG_SEPARATOR_FOR_NAMED_PARAMETER, WRONG_SEPARATOR_F
OR_POSITIONAL_PARAMETER, WRONG_TERMINATOR_FOR_PARAMETER_GROUP, VAR_AS_TYPE_NAME,
VAR_CLASS, VAR_RETURN_TYPE, VAR_TYPEDEF, VOID_PARAMETER, VOID_VARIABLE]; | 5721 static final ParserErrorCode VOID_PARAMETER = new ParserErrorCode.con2('VOID_P
ARAMETER', 119, "Parameters cannot have a type of 'void'"); |
| 5722 static final ParserErrorCode VOID_VARIABLE = new ParserErrorCode.con2('VOID_VA
RIABLE', 120, "Variables cannot have a type of 'void'"); |
| 5723 static final List<ParserErrorCode> values = [ABSTRACT_CLASS_MEMBER, ABSTRACT_S
TATIC_METHOD, ABSTRACT_TOP_LEVEL_FUNCTION, ABSTRACT_TOP_LEVEL_VARIABLE, ABSTRACT
_TYPEDEF, BREAK_OUTSIDE_OF_LOOP, CONST_AND_FINAL, CONST_AND_VAR, CONST_CLASS, CO
NST_CONSTRUCTOR_WITH_BODY, CONST_FACTORY, CONST_METHOD, CONST_TYPEDEF, CONSTRUCT
OR_WITH_RETURN_TYPE, CONTINUE_OUTSIDE_OF_LOOP, CONTINUE_WITHOUT_LABEL_IN_CASE, D
EPRECATED_ARGUMENT_DEFINITION_TEST, DIRECTIVE_AFTER_DECLARATION, DUPLICATE_LABEL
_IN_SWITCH_STATEMENT, DUPLICATED_MODIFIER, EXPECTED_CASE_OR_DEFAULT, EXPECTED_CL
ASS_MEMBER, EXPECTED_EXECUTABLE, EXPECTED_LIST_OR_MAP_LITERAL, EXPECTED_STRING_L
ITERAL, EXPECTED_TOKEN, EXPECTED_TWO_MAP_TYPE_ARGUMENTS, EXPECTED_TYPE_NAME, EXP
ORT_DIRECTIVE_AFTER_PART_DIRECTIVE, EXTERNAL_AFTER_CONST, EXTERNAL_AFTER_FACTORY
, EXTERNAL_AFTER_STATIC, EXTERNAL_CLASS, EXTERNAL_CONSTRUCTOR_WITH_BODY, EXTERNA
L_FIELD, EXTERNAL_GETTER_WITH_BODY, EXTERNAL_METHOD_WITH_BODY, EXTERNAL_OPERATOR
_WITH_BODY, EXTERNAL_SETTER_WITH_BODY, EXTERNAL_TYPEDEF, FACTORY_TOP_LEVEL_DECLA
RATION, FACTORY_WITHOUT_BODY, FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, FINAL_AND_V
AR, FINAL_CLASS, FINAL_CONSTRUCTOR, FINAL_METHOD, FINAL_TYPEDEF, GETTER_WITH_PAR
AMETERS, ILLEGAL_ASSIGNMENT_TO_NON_ASSIGNABLE, IMPLEMENTS_BEFORE_EXTENDS, IMPLEM
ENTS_BEFORE_WITH, IMPORT_DIRECTIVE_AFTER_PART_DIRECTIVE, INITIALIZED_VARIABLE_IN
_FOR_EACH, INVALID_CODE_POINT, INVALID_COMMENT_REFERENCE, INVALID_HEX_ESCAPE, IN
VALID_OPERATOR, INVALID_OPERATOR_FOR_SUPER, INVALID_UNICODE_ESCAPE, LIBRARY_DIRE
CTIVE_NOT_FIRST, LOCAL_FUNCTION_DECLARATION_MODIFIER, MISSING_ASSIGNABLE_SELECTO
R, MISSING_CATCH_OR_FINALLY, MISSING_CLASS_BODY, MISSING_CLOSING_PARENTHESIS, MI
SSING_CONST_FINAL_VAR_OR_TYPE, MISSING_EXPRESSION_IN_THROW, MISSING_FUNCTION_BOD
Y, MISSING_FUNCTION_PARAMETERS, MISSING_IDENTIFIER, MISSING_KEYWORD_OPERATOR, MI
SSING_NAME_IN_LIBRARY_DIRECTIVE, MISSING_NAME_IN_PART_OF_DIRECTIVE, MISSING_STAT
EMENT, MISSING_TERMINATOR_FOR_PARAMETER_GROUP, MISSING_TYPEDEF_PARAMETERS, MISSI
NG_VARIABLE_IN_FOR_EACH, MIXED_PARAMETER_GROUPS, MULTIPLE_EXTENDS_CLAUSES, MULTI
PLE_IMPLEMENTS_CLAUSES, MULTIPLE_LIBRARY_DIRECTIVES, MULTIPLE_NAMED_PARAMETER_GR
OUPS, MULTIPLE_PART_OF_DIRECTIVES, MULTIPLE_POSITIONAL_PARAMETER_GROUPS, MULTIPL
E_VARIABLES_IN_FOR_EACH, MULTIPLE_WITH_CLAUSES, NAMED_FUNCTION_EXPRESSION, NAMED
_PARAMETER_OUTSIDE_GROUP, NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE, NON_CONSTRUCTOR_
FACTORY, NON_IDENTIFIER_LIBRARY_NAME, NON_PART_OF_DIRECTIVE_IN_PART, NON_USER_DE
FINABLE_OPERATOR, NORMAL_BEFORE_OPTIONAL_PARAMETERS, POSITIONAL_AFTER_NAMED_ARGU
MENT, POSITIONAL_PARAMETER_OUTSIDE_GROUP, STATIC_AFTER_CONST, STATIC_AFTER_FINAL
, STATIC_AFTER_VAR, STATIC_CONSTRUCTOR, STATIC_GETTER_WITHOUT_BODY, STATIC_OPERA
TOR, STATIC_SETTER_WITHOUT_BODY, STATIC_TOP_LEVEL_DECLARATION, SWITCH_HAS_CASE_A
FTER_DEFAULT_CASE, SWITCH_HAS_MULTIPLE_DEFAULT_CASES, TOP_LEVEL_OPERATOR, UNEXPE
CTED_TERMINATOR_FOR_PARAMETER_GROUP, UNEXPECTED_TOKEN, WITH_BEFORE_EXTENDS, WITH
_WITHOUT_EXTENDS, WRONG_SEPARATOR_FOR_NAMED_PARAMETER, WRONG_SEPARATOR_FOR_POSIT
IONAL_PARAMETER, WRONG_TERMINATOR_FOR_PARAMETER_GROUP, VAR_AS_TYPE_NAME, VAR_CLA
SS, VAR_RETURN_TYPE, VAR_TYPEDEF, VOID_PARAMETER, VOID_VARIABLE]; |
| 5329 | 5724 |
| 5330 /// The name of this enum constant, as declared in the enum declaration. | 5725 /// The name of this enum constant, as declared in the enum declaration. |
| 5331 final String name; | 5726 final String name; |
| 5332 | 5727 |
| 5333 /// The position in the enum declaration. | 5728 /// The position in the enum declaration. |
| 5334 final int ordinal; | 5729 final int ordinal; |
| 5335 | 5730 |
| 5336 /** | 5731 /** |
| 5337 * The severity of this error. | 5732 * The severity of this error. |
| 5338 */ | 5733 */ |
| 5339 ErrorSeverity _severity; | 5734 ErrorSeverity _severity; |
| 5340 | 5735 |
| 5341 /** | 5736 /** |
| 5342 * The message template used to create the message to be displayed for this er
ror. | 5737 * The message template used to create the message to be displayed for this er
ror. |
| 5343 */ | 5738 */ |
| 5344 String _message; | 5739 String _message; |
| 5345 | 5740 |
| 5346 /** | 5741 /** |
| 5347 * Initialize a newly created error code to have the given severity and messag
e. | 5742 * Initialize a newly created error code to have the given severity and messag
e. |
| 5743 * |
| 5348 * @param severity the severity of the error | 5744 * @param severity the severity of the error |
| 5349 * @param message the message template used to create the message to be displa
yed for the error | 5745 * @param message the message template used to create the message to be displa
yed for the error |
| 5350 */ | 5746 */ |
| 5351 ParserErrorCode.con1(this.name, this.ordinal, ErrorSeverity severity2, String
message2) { | 5747 ParserErrorCode.con1(this.name, this.ordinal, ErrorSeverity severity2, String
message2) { |
| 5352 _jtd_constructor_311_impl(severity2, message2); | 5748 _jtd_constructor_311_impl(severity2, message2); |
| 5353 } | 5749 } |
| 5354 _jtd_constructor_311_impl(ErrorSeverity severity2, String message2) { | 5750 _jtd_constructor_311_impl(ErrorSeverity severity2, String message2) { |
| 5355 this._severity = severity2; | 5751 this._severity = severity2; |
| 5356 this._message = message2; | 5752 this._message = message2; |
| 5357 } | 5753 } |
| 5358 | 5754 |
| 5359 /** | 5755 /** |
| 5360 * Initialize a newly created error code to have the given message and a sever
ity of ERROR. | 5756 * Initialize a newly created error code to have the given message and a sever
ity of ERROR. |
| 5757 * |
| 5361 * @param message the message template used to create the message to be displa
yed for the error | 5758 * @param message the message template used to create the message to be displa
yed for the error |
| 5362 */ | 5759 */ |
| 5363 ParserErrorCode.con2(this.name, this.ordinal, String message) { | 5760 ParserErrorCode.con2(this.name, this.ordinal, String message) { |
| 5364 _jtd_constructor_312_impl(message); | 5761 _jtd_constructor_312_impl(message); |
| 5365 } | 5762 } |
| 5366 _jtd_constructor_312_impl(String message) { | 5763 _jtd_constructor_312_impl(String message) { |
| 5367 _jtd_constructor_311_impl(ErrorSeverity.ERROR, message); | 5764 _jtd_constructor_311_impl(ErrorSeverity.ERROR, message); |
| 5368 } | 5765 } |
| 5369 ErrorSeverity get errorSeverity => _severity; | 5766 ErrorSeverity get errorSeverity => _severity; |
| 5370 String get message => _message; | 5767 String get message => _message; |
| (...skipping 11 matching lines...) Expand all Loading... |
| 5382 /** | 5779 /** |
| 5383 * The writer to which the source is to be written. | 5780 * The writer to which the source is to be written. |
| 5384 */ | 5781 */ |
| 5385 PrintWriter _writer; | 5782 PrintWriter _writer; |
| 5386 int _indentLevel = 0; | 5783 int _indentLevel = 0; |
| 5387 String _indentString = ""; | 5784 String _indentString = ""; |
| 5388 | 5785 |
| 5389 /** | 5786 /** |
| 5390 * Initialize a newly created visitor to write source code representing the vi
sited nodes to the | 5787 * Initialize a newly created visitor to write source code representing the vi
sited nodes to the |
| 5391 * given writer. | 5788 * given writer. |
| 5789 * |
| 5392 * @param writer the writer to which the source is to be written | 5790 * @param writer the writer to which the source is to be written |
| 5393 */ | 5791 */ |
| 5394 ToFormattedSourceVisitor(PrintWriter writer) { | 5792 ToFormattedSourceVisitor(PrintWriter writer) { |
| 5395 this._writer = writer; | 5793 this._writer = writer; |
| 5396 } | 5794 } |
| 5397 Object visitAdjacentStrings(AdjacentStrings node) { | 5795 Object visitAdjacentStrings(AdjacentStrings node) { |
| 5398 visitList5(node.strings, " "); | 5796 visitList5(node.strings, " "); |
| 5399 return null; | 5797 return null; |
| 5400 } | 5798 } |
| 5401 Object visitAnnotation(Annotation node) { | 5799 Object visitAnnotation(Annotation node) { |
| (...skipping 744 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6146 void nl() { | 6544 void nl() { |
| 6147 _writer.print("\n"); | 6545 _writer.print("\n"); |
| 6148 } | 6546 } |
| 6149 void nl2() { | 6547 void nl2() { |
| 6150 nl(); | 6548 nl(); |
| 6151 indent(); | 6549 indent(); |
| 6152 } | 6550 } |
| 6153 | 6551 |
| 6154 /** | 6552 /** |
| 6155 * Safely visit the given node. | 6553 * Safely visit the given node. |
| 6554 * |
| 6156 * @param node the node to be visited | 6555 * @param node the node to be visited |
| 6157 */ | 6556 */ |
| 6158 void visit(ASTNode node) { | 6557 void visit(ASTNode node) { |
| 6159 if (node != null) { | 6558 if (node != null) { |
| 6160 node.accept(this); | 6559 node.accept(this); |
| 6161 } | 6560 } |
| 6162 } | 6561 } |
| 6163 | 6562 |
| 6164 /** | 6563 /** |
| 6165 * Safely visit the given node, printing the suffix after the node if it is no
n-<code>null</code>. | 6564 * Safely visit the given node, printing the suffix after the node if it is no
n-<code>null</code>. |
| 6565 * |
| 6166 * @param suffix the suffix to be printed if there is a node to visit | 6566 * @param suffix the suffix to be printed if there is a node to visit |
| 6167 * @param node the node to be visited | 6567 * @param node the node to be visited |
| 6168 */ | 6568 */ |
| 6169 void visit6(ASTNode node, String suffix) { | 6569 void visit6(ASTNode node, String suffix) { |
| 6170 if (node != null) { | 6570 if (node != null) { |
| 6171 node.accept(this); | 6571 node.accept(this); |
| 6172 _writer.print(suffix); | 6572 _writer.print(suffix); |
| 6173 } | 6573 } |
| 6174 } | 6574 } |
| 6175 | 6575 |
| 6176 /** | 6576 /** |
| 6177 * Safely visit the given node, printing the prefix before the node if it is n
on-<code>null</code> | 6577 * Safely visit the given node, printing the prefix before the node if it is n
on-<code>null</code> |
| 6178 * . | 6578 * . |
| 6579 * |
| 6179 * @param prefix the prefix to be printed if there is a node to visit | 6580 * @param prefix the prefix to be printed if there is a node to visit |
| 6180 * @param node the node to be visited | 6581 * @param node the node to be visited |
| 6181 */ | 6582 */ |
| 6182 void visit7(String prefix, ASTNode node) { | 6583 void visit7(String prefix, ASTNode node) { |
| 6183 if (node != null) { | 6584 if (node != null) { |
| 6184 _writer.print(prefix); | 6585 _writer.print(prefix); |
| 6185 node.accept(this); | 6586 node.accept(this); |
| 6186 } | 6587 } |
| 6187 } | 6588 } |
| 6188 | 6589 |
| 6189 /** | 6590 /** |
| 6190 * Safely visit the given node, printing the suffix after the node if it is no
n-<code>null</code>. | 6591 * Safely visit the given node, printing the suffix after the node if it is no
n-<code>null</code>. |
| 6592 * |
| 6191 * @param suffix the suffix to be printed if there is a node to visit | 6593 * @param suffix the suffix to be printed if there is a node to visit |
| 6192 * @param node the node to be visited | 6594 * @param node the node to be visited |
| 6193 */ | 6595 */ |
| 6194 void visit8(Token token, String suffix) { | 6596 void visit8(Token token, String suffix) { |
| 6195 if (token != null) { | 6597 if (token != null) { |
| 6196 _writer.print(token.lexeme); | 6598 _writer.print(token.lexeme); |
| 6197 _writer.print(suffix); | 6599 _writer.print(suffix); |
| 6198 } | 6600 } |
| 6199 } | 6601 } |
| 6200 | 6602 |
| 6201 /** | 6603 /** |
| 6202 * Print a list of nodes without any separation. | 6604 * Print a list of nodes without any separation. |
| 6605 * |
| 6203 * @param nodes the nodes to be printed | 6606 * @param nodes the nodes to be printed |
| 6204 * @param separator the separator to be printed between adjacent nodes | 6607 * @param separator the separator to be printed between adjacent nodes |
| 6205 */ | 6608 */ |
| 6206 void visitList(NodeList<ASTNode> nodes) { | 6609 void visitList(NodeList<ASTNode> nodes) { |
| 6207 visitList5(nodes, ""); | 6610 visitList5(nodes, ""); |
| 6208 } | 6611 } |
| 6209 | 6612 |
| 6210 /** | 6613 /** |
| 6211 * Print a list of nodes, separated by the given separator. | 6614 * Print a list of nodes, separated by the given separator. |
| 6615 * |
| 6212 * @param nodes the nodes to be printed | 6616 * @param nodes the nodes to be printed |
| 6213 * @param separator the separator to be printed between adjacent nodes | 6617 * @param separator the separator to be printed between adjacent nodes |
| 6214 */ | 6618 */ |
| 6215 void visitList5(NodeList<ASTNode> nodes, String separator) { | 6619 void visitList5(NodeList<ASTNode> nodes, String separator) { |
| 6216 if (nodes != null) { | 6620 if (nodes != null) { |
| 6217 int size = nodes.length; | 6621 int size = nodes.length; |
| 6218 for (int i = 0; i < size; i++) { | 6622 for (int i = 0; i < size; i++) { |
| 6219 if ("\n" == separator) { | 6623 if ("\n" == separator) { |
| 6220 _writer.print("\n"); | 6624 _writer.print("\n"); |
| 6221 indent(); | 6625 indent(); |
| 6222 } else if (i > 0) { | 6626 } else if (i > 0) { |
| 6223 _writer.print(separator); | 6627 _writer.print(separator); |
| 6224 } | 6628 } |
| 6225 nodes[i].accept(this); | 6629 nodes[i].accept(this); |
| 6226 } | 6630 } |
| 6227 } | 6631 } |
| 6228 } | 6632 } |
| 6229 | 6633 |
| 6230 /** | 6634 /** |
| 6231 * Print a list of nodes, separated by the given separator. | 6635 * Print a list of nodes, separated by the given separator. |
| 6636 * |
| 6232 * @param nodes the nodes to be printed | 6637 * @param nodes the nodes to be printed |
| 6233 * @param separator the separator to be printed between adjacent nodes | 6638 * @param separator the separator to be printed between adjacent nodes |
| 6234 * @param suffix the suffix to be printed if the list is not empty | 6639 * @param suffix the suffix to be printed if the list is not empty |
| 6235 */ | 6640 */ |
| 6236 void visitList6(NodeList<ASTNode> nodes, String separator, String suffix) { | 6641 void visitList6(NodeList<ASTNode> nodes, String separator, String suffix) { |
| 6237 if (nodes != null) { | 6642 if (nodes != null) { |
| 6238 int size = nodes.length; | 6643 int size = nodes.length; |
| 6239 if (size > 0) { | 6644 if (size > 0) { |
| 6240 for (int i = 0; i < size; i++) { | 6645 for (int i = 0; i < size; i++) { |
| 6241 if (i > 0) { | 6646 if (i > 0) { |
| 6242 _writer.print(separator); | 6647 _writer.print(separator); |
| 6243 } | 6648 } |
| 6244 nodes[i].accept(this); | 6649 nodes[i].accept(this); |
| 6245 } | 6650 } |
| 6246 _writer.print(suffix); | 6651 _writer.print(suffix); |
| 6247 } | 6652 } |
| 6248 } | 6653 } |
| 6249 } | 6654 } |
| 6250 | 6655 |
| 6251 /** | 6656 /** |
| 6252 * Print a list of nodes, separated by the given separator. | 6657 * Print a list of nodes, separated by the given separator. |
| 6658 * |
| 6253 * @param prefix the prefix to be printed if the list is not empty | 6659 * @param prefix the prefix to be printed if the list is not empty |
| 6254 * @param nodes the nodes to be printed | 6660 * @param nodes the nodes to be printed |
| 6255 * @param separator the separator to be printed between adjacent nodes | 6661 * @param separator the separator to be printed between adjacent nodes |
| 6256 */ | 6662 */ |
| 6257 void visitList7(String prefix, NodeList<ASTNode> nodes, String separator) { | 6663 void visitList7(String prefix, NodeList<ASTNode> nodes, String separator) { |
| 6258 if (nodes != null) { | 6664 if (nodes != null) { |
| 6259 int size = nodes.length; | 6665 int size = nodes.length; |
| 6260 if (size > 0) { | 6666 if (size > 0) { |
| 6261 _writer.print(prefix); | 6667 _writer.print(prefix); |
| 6262 for (int i = 0; i < size; i++) { | 6668 for (int i = 0; i < size; i++) { |
| 6263 if (i > 0) { | 6669 if (i > 0) { |
| 6264 _writer.print(separator); | 6670 _writer.print(separator); |
| 6265 } | 6671 } |
| 6266 nodes[i].accept(this); | 6672 nodes[i].accept(this); |
| 6267 } | 6673 } |
| 6268 } | 6674 } |
| 6269 } | 6675 } |
| 6270 } | 6676 } |
| 6271 } | 6677 } |
| OLD | NEW |