| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 import 'package:front_end/src/base/errors.dart'; | 5 import 'package:front_end/src/base/errors.dart'; |
| 6 import 'package:front_end/src/fasta/fasta_codes.dart'; | 6 import 'package:front_end/src/fasta/fasta_codes.dart'; |
| 7 import 'package:front_end/src/fasta/scanner/error_token.dart'; | 7 import 'package:front_end/src/fasta/scanner/error_token.dart'; |
| 8 import 'package:front_end/src/scanner/token.dart' show Token; | 8 import 'package:front_end/src/scanner/token.dart' show Token, TokenType; |
| 9 import 'package:front_end/src/fasta/scanner/token_constants.dart'; | 9 import 'package:front_end/src/fasta/scanner/token_constants.dart'; |
| 10 | 10 |
| 11 /** | 11 /** |
| 12 * The error codes used for errors detected by the scanner. | 12 * The error codes used for errors detected by the scanner. |
| 13 */ | 13 */ |
| 14 class ScannerErrorCode extends ErrorCode { | 14 class ScannerErrorCode extends ErrorCode { |
| 15 /** | 15 /** |
| 16 * Parameters: | 16 * Parameters: |
| 17 * 0: the token that was expected but not found |
| 18 */ |
| 19 static const ScannerErrorCode EXPECTED_TOKEN = |
| 20 const ScannerErrorCode('EXPECTED_TOKEN', "Expected to find '{0}'."); |
| 21 |
| 22 /** |
| 23 * Parameters: |
| 17 * 0: the illegal character | 24 * 0: the illegal character |
| 18 */ | 25 */ |
| 19 static const ScannerErrorCode ILLEGAL_CHARACTER = | 26 static const ScannerErrorCode ILLEGAL_CHARACTER = |
| 20 const ScannerErrorCode('ILLEGAL_CHARACTER', "Illegal character '{0}'."); | 27 const ScannerErrorCode('ILLEGAL_CHARACTER', "Illegal character '{0}'."); |
| 21 | 28 |
| 22 static const ScannerErrorCode MISSING_DIGIT = | 29 static const ScannerErrorCode MISSING_DIGIT = |
| 23 const ScannerErrorCode('MISSING_DIGIT', "Decimal digit expected."); | 30 const ScannerErrorCode('MISSING_DIGIT', "Decimal digit expected."); |
| 24 | 31 |
| 25 static const ScannerErrorCode MISSING_HEX_DIGIT = const ScannerErrorCode( | 32 static const ScannerErrorCode MISSING_HEX_DIGIT = const ScannerErrorCode( |
| 26 'MISSING_HEX_DIGIT', "Hexidecimal digit expected."); | 33 'MISSING_HEX_DIGIT', "Hexidecimal digit expected."); |
| 27 | 34 |
| 35 static const ScannerErrorCode MISSING_IDENTIFIER = |
| 36 const ScannerErrorCode('MISSING_IDENTIFIER', "Expected an identifier."); |
| 37 |
| 28 static const ScannerErrorCode MISSING_QUOTE = | 38 static const ScannerErrorCode MISSING_QUOTE = |
| 29 const ScannerErrorCode('MISSING_QUOTE', "Expected quote (' or \")."); | 39 const ScannerErrorCode('MISSING_QUOTE', "Expected quote (' or \")."); |
| 30 | 40 |
| 31 /** | 41 /** |
| 32 * Parameters: | 42 * Parameters: |
| 33 * 0: the path of the file that cannot be read | 43 * 0: the path of the file that cannot be read |
| 34 */ | 44 */ |
| 35 static const ScannerErrorCode UNABLE_GET_CONTENT = const ScannerErrorCode( | 45 static const ScannerErrorCode UNABLE_GET_CONTENT = const ScannerErrorCode( |
| 36 'UNABLE_GET_CONTENT', "Unable to get content of '{0}'."); | 46 'UNABLE_GET_CONTENT', "Unable to get content of '{0}'."); |
| 37 | 47 |
| (...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 112 case "MISSING_HEX_DIGIT": | 122 case "MISSING_HEX_DIGIT": |
| 113 // TODO(paulberry,ahe): Fasta reports the error location as the entire | 123 // TODO(paulberry,ahe): Fasta reports the error location as the entire |
| 114 // number; analyzer expects the end of the number. | 124 // number; analyzer expects the end of the number. |
| 115 charOffset = endOffset - 1; | 125 charOffset = endOffset - 1; |
| 116 return _makeError(ScannerErrorCode.MISSING_HEX_DIGIT, null); | 126 return _makeError(ScannerErrorCode.MISSING_HEX_DIGIT, null); |
| 117 | 127 |
| 118 case "ILLEGAL_CHARACTER": | 128 case "ILLEGAL_CHARACTER": |
| 119 return _makeError(ScannerErrorCode.ILLEGAL_CHARACTER, [token.character]); | 129 return _makeError(ScannerErrorCode.ILLEGAL_CHARACTER, [token.character]); |
| 120 | 130 |
| 121 default: | 131 default: |
| 122 if (errorCode == codeUnmatchedToken || | 132 if (errorCode == codeUnmatchedToken) { |
| 123 errorCode == codeUnexpectedDollarInString) { | 133 TokenType type = token.begin?.type; |
| 124 return null; | 134 if (type == TokenType.OPEN_CURLY_BRACKET || |
| 135 type == TokenType.STRING_INTERPOLATION_EXPRESSION) { |
| 136 return _makeError(ScannerErrorCode.EXPECTED_TOKEN, ['}']); |
| 137 } |
| 138 if (type == TokenType.OPEN_SQUARE_BRACKET) { |
| 139 return _makeError(ScannerErrorCode.EXPECTED_TOKEN, [']']); |
| 140 } |
| 141 if (type == TokenType.OPEN_PAREN) { |
| 142 return _makeError(ScannerErrorCode.EXPECTED_TOKEN, [')']); |
| 143 } |
| 144 } else if (errorCode == codeUnexpectedDollarInString) { |
| 145 return _makeError(ScannerErrorCode.MISSING_IDENTIFIER, null); |
| 125 } | 146 } |
| 126 throw new UnimplementedError('$errorCode'); | 147 throw new UnimplementedError('$errorCode'); |
| 127 } | 148 } |
| 128 } | 149 } |
| 129 | 150 |
| 130 /** | 151 /** |
| 131 * Determines whether the given [charOffset], which came from the non-EOF token | 152 * Determines whether the given [charOffset], which came from the non-EOF token |
| 132 * [token], represents the end of the input. | 153 * [token], represents the end of the input. |
| 133 */ | 154 */ |
| 134 bool _isAtEnd(Token token, int charOffset) { | 155 bool _isAtEnd(Token token, int charOffset) { |
| 135 while (true) { | 156 while (true) { |
| 136 // Skip to the next token. | 157 // Skip to the next token. |
| 137 token = token.next; | 158 token = token.next; |
| 138 // If we've found an EOF token, its charOffset indicates where the end of | 159 // If we've found an EOF token, its charOffset indicates where the end of |
| 139 // the input is. | 160 // the input is. |
| 140 if (token.isEof) return token.charOffset == charOffset; | 161 if (token.isEof) return token.charOffset == charOffset; |
| 141 // If we've found a non-error token, then we know there is additional input | 162 // If we've found a non-error token, then we know there is additional input |
| 142 // text after [charOffset]. | 163 // text after [charOffset]. |
| 143 if (token.type.kind != BAD_INPUT_TOKEN) return false; | 164 if (token.type.kind != BAD_INPUT_TOKEN) return false; |
| 144 // Otherwise keep looking. | 165 // Otherwise keep looking. |
| 145 } | 166 } |
| 146 } | 167 } |
| OLD | NEW |