| OLD | NEW |
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 10 matching lines...) Expand all Loading... |
| 21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | 21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
| 22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, | 22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
| 23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | 23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
| 24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | 25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
| 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 27 | 27 |
| 28 | 28 |
| 29 // ------------------------------------------------------------------- | 29 // ------------------------------------------------------------------- |
| 30 // | 30 // |
| 31 // Matches Script::Type from objects.h | |
| 32 var TYPE_NATIVE = 0; | |
| 33 var TYPE_EXTENSION = 1; | |
| 34 var TYPE_NORMAL = 2; | |
| 35 | |
| 36 // Matches Script::CompilationType from objects.h | |
| 37 var COMPILATION_TYPE_HOST = 0; | |
| 38 var COMPILATION_TYPE_EVAL = 1; | |
| 39 var COMPILATION_TYPE_JSON = 2; | |
| 40 | |
| 41 // Matches Messages::kNoLineNumberInfo from v8.h | |
| 42 var kNoLineNumberInfo = 0; | |
| 43 | |
| 44 // If this object gets passed to an error constructor the error will | 31 // If this object gets passed to an error constructor the error will |
| 45 // get an accessor for .message that constructs a descriptive error | 32 // get an accessor for .message that constructs a descriptive error |
| 46 // message on access. | 33 // message on access. |
| 47 var kAddMessageAccessorsMarker = { }; | 34 const kAddMessageAccessorsMarker = { }; |
| 48 | 35 |
| 49 var kMessages = 0; | 36 // This will be lazily initialized when first needed (and forcibly |
| 50 | 37 // overwritten even though it's const). |
| 51 var kReplacementMarkers = [ "%0", "%1", "%2", "%3" ]; | 38 const kMessages = 0; |
| 52 | 39 |
| 53 function FormatString(format, message) { | 40 function FormatString(format, message) { |
| 54 var args = %MessageGetArguments(message); | 41 var args = %MessageGetArguments(message); |
| 55 var result = ""; | 42 var result = ""; |
| 56 var arg_num = 0; | 43 var arg_num = 0; |
| 57 for (var i = 0; i < format.length; i++) { | 44 for (var i = 0; i < format.length; i++) { |
| 58 var str = format[i]; | 45 var str = format[i]; |
| 59 for (arg_num = 0; arg_num < kReplacementMarkers.length; arg_num++) { | 46 if (str.length == 2 && %_StringCharCodeAt(str, 0) == 0x25) { |
| 60 if (str == kReplacementMarkers[arg_num]) { | 47 // Two-char string starts with "%". |
| 48 var arg_num = (%_StringCharCodeAt(str, 1) - 0x30) >>> 0; |
| 49 if (arg_num < 4) { |
| 50 // str is one of %0, %1, %2 or %3. |
| 61 try { | 51 try { |
| 62 str = ToDetailString(args[arg_num]); | 52 str = ToDetailString(args[arg_num]); |
| 63 } catch (e) { | 53 } catch (e) { |
| 64 str = "#<error>"; | 54 str = "#<error>"; |
| 65 } | 55 } |
| 66 break; | |
| 67 } | 56 } |
| 68 } | 57 } |
| 69 result += str; | 58 result += str; |
| 70 } | 59 } |
| 71 return result; | 60 return result; |
| 72 } | 61 } |
| 73 | 62 |
| 74 | 63 |
| 75 // To check if something is a native error we need to check the | 64 // To check if something is a native error we need to check the |
| 76 // concrete native error types. It is not enough to check "obj | 65 // concrete native error types. It is not enough to check "obj |
| (...skipping 18 matching lines...) Expand all Loading... |
| 95 function ToStringCheckErrorObject(obj) { | 84 function ToStringCheckErrorObject(obj) { |
| 96 if (IsNativeErrorObject(obj)) { | 85 if (IsNativeErrorObject(obj)) { |
| 97 return %_CallFunction(obj, errorToString); | 86 return %_CallFunction(obj, errorToString); |
| 98 } else { | 87 } else { |
| 99 return ToString(obj); | 88 return ToString(obj); |
| 100 } | 89 } |
| 101 } | 90 } |
| 102 | 91 |
| 103 | 92 |
| 104 function ToDetailString(obj) { | 93 function ToDetailString(obj) { |
| 105 if (obj != null && IS_OBJECT(obj) && | 94 if (obj != null && IS_OBJECT(obj) && obj.toString === ObjectToString) { |
| 106 obj.toString === $Object.prototype.toString) { | |
| 107 var constructor = obj.constructor; | 95 var constructor = obj.constructor; |
| 108 if (!constructor) return ToStringCheckErrorObject(obj); | 96 if (typeof constructor == "function") { |
| 109 var constructorName = constructor.name; | 97 var constructorName = constructor.name; |
| 110 if (!constructorName || !IS_STRING(constructorName)) { | 98 if (IS_STRING(constructorName) && constructorName !== "") { |
| 111 return ToStringCheckErrorObject(obj); | 99 return "#<" + constructorName + ">"; |
| 100 } |
| 112 } | 101 } |
| 113 return "#<" + constructorName + ">"; | |
| 114 } else { | |
| 115 return ToStringCheckErrorObject(obj); | |
| 116 } | 102 } |
| 103 return ToStringCheckErrorObject(obj); |
| 117 } | 104 } |
| 118 | 105 |
| 119 | 106 |
| 120 function MakeGenericError(constructor, type, args) { | 107 function MakeGenericError(constructor, type, args) { |
| 121 if (IS_UNDEFINED(args)) { | 108 if (IS_UNDEFINED(args)) { |
| 122 args = []; | 109 args = []; |
| 123 } | 110 } |
| 124 var e = new constructor(kAddMessageAccessorsMarker); | 111 var e = new constructor(kAddMessageAccessorsMarker); |
| 125 e.type = type; | 112 e.type = type; |
| 126 e.arguments = args; | 113 e.arguments = args; |
| 127 return e; | 114 return e; |
| 128 } | 115 } |
| 129 | 116 |
| 130 | 117 |
| 131 /** | 118 /** |
| 132 * Setup the Script function and constructor. | 119 * Set up the Script function and constructor. |
| 133 */ | 120 */ |
| 134 %FunctionSetInstanceClassName(Script, 'Script'); | 121 %FunctionSetInstanceClassName(Script, 'Script'); |
| 135 %SetProperty(Script.prototype, 'constructor', Script, DONT_ENUM); | 122 %SetProperty(Script.prototype, 'constructor', Script, |
| 123 DONT_ENUM | DONT_DELETE | READ_ONLY); |
| 136 %SetCode(Script, function(x) { | 124 %SetCode(Script, function(x) { |
| 137 // Script objects can only be created by the VM. | 125 // Script objects can only be created by the VM. |
| 138 throw new $Error("Not supported"); | 126 throw new $Error("Not supported"); |
| 139 }); | 127 }); |
| 140 | 128 |
| 141 | 129 |
| 142 // Helper functions; called from the runtime system. | 130 // Helper functions; called from the runtime system. |
| 143 function FormatMessage(message) { | 131 function FormatMessage(message) { |
| 144 if (kMessages === 0) { | 132 if (kMessages === 0) { |
| 145 kMessages = { | 133 var messagesDictionary = [ |
| 146 // Error | 134 // Error |
| 147 cyclic_proto: ["Cyclic __proto__ value"], | 135 "cyclic_proto", ["Cyclic __proto__ value"], |
| 148 code_gen_from_strings: ["Code generation from strings disallowed fo
r this context"], | 136 "code_gen_from_strings", ["Code generation from strings disallowed
for this context"], |
| 149 // TypeError | 137 // TypeError |
| 150 unexpected_token: ["Unexpected token ", "%0"], | 138 "unexpected_token", ["Unexpected token ", "%0"], |
| 151 unexpected_token_number: ["Unexpected number"], | 139 "unexpected_token_number", ["Unexpected number"], |
| 152 unexpected_token_string: ["Unexpected string"], | 140 "unexpected_token_string", ["Unexpected string"], |
| 153 unexpected_token_identifier: ["Unexpected identifier"], | 141 "unexpected_token_identifier", ["Unexpected identifier"], |
| 154 unexpected_reserved: ["Unexpected reserved word"], | 142 "unexpected_reserved", ["Unexpected reserved word"], |
| 155 unexpected_strict_reserved: ["Unexpected strict mode reserved word"], | 143 "unexpected_strict_reserved", ["Unexpected strict mode reserved word"], |
| 156 unexpected_eos: ["Unexpected end of input"], | 144 "unexpected_eos", ["Unexpected end of input"], |
| 157 malformed_regexp: ["Invalid regular expression: /", "%0", "/:
", "%1"], | 145 "malformed_regexp", ["Invalid regular expression: /", "%0", "/
: ", "%1"], |
| 158 unterminated_regexp: ["Invalid regular expression: missing /"], | 146 "unterminated_regexp", ["Invalid regular expression: missing /"], |
| 159 regexp_flags: ["Cannot supply flags when constructing one
RegExp from another"], | 147 "regexp_flags", ["Cannot supply flags when constructing on
e RegExp from another"], |
| 160 incompatible_method_receiver: ["Method ", "%0", " called on incompatible r
eceiver ", "%1"], | 148 "incompatible_method_receiver", ["Method ", "%0", " called on incompatible
receiver ", "%1"], |
| 161 invalid_lhs_in_assignment: ["Invalid left-hand side in assignment"], | 149 "invalid_lhs_in_assignment", ["Invalid left-hand side in assignment"], |
| 162 invalid_lhs_in_for_in: ["Invalid left-hand side in for-in"], | 150 "invalid_lhs_in_for_in", ["Invalid left-hand side in for-in"], |
| 163 invalid_lhs_in_postfix_op: ["Invalid left-hand side expression in postf
ix operation"], | 151 "invalid_lhs_in_postfix_op", ["Invalid left-hand side expression in pos
tfix operation"], |
| 164 invalid_lhs_in_prefix_op: ["Invalid left-hand side expression in prefi
x operation"], | 152 "invalid_lhs_in_prefix_op", ["Invalid left-hand side expression in pre
fix operation"], |
| 165 multiple_defaults_in_switch: ["More than one default clause in switch sta
tement"], | 153 "multiple_defaults_in_switch", ["More than one default clause in switch s
tatement"], |
| 166 newline_after_throw: ["Illegal newline after throw"], | 154 "newline_after_throw", ["Illegal newline after throw"], |
| 167 redeclaration: ["%0", " '", "%1", "' has already been decla
red"], | 155 "redeclaration", ["%0", " '", "%1", "' has already been dec
lared"], |
| 168 no_catch_or_finally: ["Missing catch or finally after try"], | 156 "no_catch_or_finally", ["Missing catch or finally after try"], |
| 169 unknown_label: ["Undefined label '", "%0", "'"], | 157 "unknown_label", ["Undefined label '", "%0", "'"], |
| 170 uncaught_exception: ["Uncaught ", "%0"], | 158 "uncaught_exception", ["Uncaught ", "%0"], |
| 171 stack_trace: ["Stack Trace:\n", "%0"], | 159 "stack_trace", ["Stack Trace:\n", "%0"], |
| 172 called_non_callable: ["%0", " is not a function"], | 160 "called_non_callable", ["%0", " is not a function"], |
| 173 undefined_method: ["Object ", "%1", " has no method '", "%0",
"'"], | 161 "undefined_method", ["Object ", "%1", " has no method '", "%0"
, "'"], |
| 174 property_not_function: ["Property '", "%0", "' of object ", "%1", "
is not a function"], | 162 "property_not_function", ["Property '", "%0", "' of object ", "%1",
" is not a function"], |
| 175 cannot_convert_to_primitive: ["Cannot convert object to primitive value"]
, | 163 "cannot_convert_to_primitive", ["Cannot convert object to primitive value
"], |
| 176 not_constructor: ["%0", " is not a constructor"], | 164 "not_constructor", ["%0", " is not a constructor"], |
| 177 not_defined: ["%0", " is not defined"], | 165 "not_defined", ["%0", " is not defined"], |
| 178 non_object_property_load: ["Cannot read property '", "%0", "' of ", "%
1"], | 166 "non_object_property_load", ["Cannot read property '", "%0", "' of ",
"%1"], |
| 179 non_object_property_store: ["Cannot set property '", "%0", "' of ", "%1
"], | 167 "non_object_property_store", ["Cannot set property '", "%0", "' of ", "
%1"], |
| 180 non_object_property_call: ["Cannot call method '", "%0", "' of ", "%1"
], | 168 "non_object_property_call", ["Cannot call method '", "%0", "' of ", "%
1"], |
| 181 with_expression: ["%0", " has no properties"], | 169 "with_expression", ["%0", " has no properties"], |
| 182 illegal_invocation: ["Illegal invocation"], | 170 "illegal_invocation", ["Illegal invocation"], |
| 183 no_setter_in_callback: ["Cannot set property ", "%0", " of ", "%1",
" which has only a getter"], | 171 "no_setter_in_callback", ["Cannot set property ", "%0", " of ", "%1
", " which has only a getter"], |
| 184 apply_non_function: ["Function.prototype.apply was called on ",
"%0", ", which is a ", "%1", " and not a function"], | 172 "apply_non_function", ["Function.prototype.apply was called on "
, "%0", ", which is a ", "%1", " and not a function"], |
| 185 apply_wrong_args: ["Function.prototype.apply: Arguments list h
as wrong type"], | 173 "apply_wrong_args", ["Function.prototype.apply: Arguments list
has wrong type"], |
| 186 invalid_in_operator_use: ["Cannot use 'in' operator to search for '",
"%0", "' in ", "%1"], | 174 "invalid_in_operator_use", ["Cannot use 'in' operator to search for '
", "%0", "' in ", "%1"], |
| 187 instanceof_function_expected: ["Expecting a function in instanceof check,
but got ", "%0"], | 175 "instanceof_function_expected", ["Expecting a function in instanceof check
, but got ", "%0"], |
| 188 instanceof_nonobject_proto: ["Function has non-object prototype '", "%0"
, "' in instanceof check"], | 176 "instanceof_nonobject_proto", ["Function has non-object prototype '", "%
0", "' in instanceof check"], |
| 189 null_to_object: ["Cannot convert null to object"], | 177 "null_to_object", ["Cannot convert null to object"], |
| 190 reduce_no_initial: ["Reduce of empty array with no initial valu
e"], | 178 "reduce_no_initial", ["Reduce of empty array with no initial va
lue"], |
| 191 getter_must_be_callable: ["Getter must be a function: ", "%0"], | 179 "getter_must_be_callable", ["Getter must be a function: ", "%0"], |
| 192 setter_must_be_callable: ["Setter must be a function: ", "%0"], | 180 "setter_must_be_callable", ["Setter must be a function: ", "%0"], |
| 193 value_and_accessor: ["Invalid property. A property cannot both
have accessors and be writable or have a value: ", "%0"], | 181 "value_and_accessor", ["Invalid property. A property cannot bot
h have accessors and be writable or have a value, ", "%0"], |
| 194 proto_object_or_null: ["Object prototype may only be an Object or
null"], | 182 "proto_object_or_null", ["Object prototype may only be an Object o
r null"], |
| 195 property_desc_object: ["Property description must be an object: ",
"%0"], | 183 "property_desc_object", ["Property description must be an object:
", "%0"], |
| 196 redefine_disallowed: ["Cannot redefine property: ", "%0"], | 184 "redefine_disallowed", ["Cannot redefine property: ", "%0"], |
| 197 define_disallowed: ["Cannot define property:", "%0", ", object
is not extensible."], | 185 "define_disallowed", ["Cannot define property:", "%0", ", objec
t is not extensible."], |
| 198 non_extensible_proto: ["%0", " is not extensible"], | 186 "non_extensible_proto", ["%0", " is not extensible"], |
| 199 handler_non_object: ["Proxy.", "%0", " called with non-object as
handler"], | 187 "handler_non_object", ["Proxy.", "%0", " called with non-object
as handler"], |
| 200 handler_trap_missing: ["Proxy handler ", "%0", " has no '", "%1",
"' trap"], | 188 "handler_trap_missing", ["Proxy handler ", "%0", " has no '", "%1"
, "' trap"], |
| 201 handler_trap_must_be_callable: ["Proxy handler ", "%0", " has non-callable
'", "%1", "' trap"], | 189 "handler_trap_must_be_callable", ["Proxy handler ", "%0", " has non-callab
le '", "%1", "' trap"], |
| 202 handler_returned_false: ["Proxy handler ", "%0", " returned false fo
r '", "%1", "' trap"], | 190 "handler_returned_false", ["Proxy handler ", "%0", " returned false
for '", "%1", "' trap"], |
| 203 handler_returned_undefined: ["Proxy handler ", "%0", " returned undefine
d for '", "%1", "' trap"], | 191 "handler_returned_undefined", ["Proxy handler ", "%0", " returned undefi
ned for '", "%1", "' trap"], |
| 204 proxy_prop_not_configurable: ["Trap ", "%1", " of proxy handler ", "%0",
" returned non-configurable descriptor for property ", "%2"], | 192 "proxy_prop_not_configurable", ["Trap ", "%1", " of proxy handler ", "%0"
, " returned non-configurable descriptor for property ", "%2"], |
| 205 proxy_non_object_prop_names: ["Trap ", "%1", " returned non-object ", "%0
"], | 193 "proxy_non_object_prop_names", ["Trap ", "%1", " returned non-object ", "
%0"], |
| 206 proxy_repeated_prop_name: ["Trap ", "%1", " returned repeated property
name ", "%2"], | 194 "proxy_repeated_prop_name", ["Trap ", "%1", " returned repeated proper
ty name ", "%2"], |
| 207 invalid_weakmap_key: ["Invalid value used as weak map key"], | 195 "invalid_weakmap_key", ["Invalid value used as weak map key"], |
| 208 // RangeError | 196 // RangeError |
| 209 invalid_array_length: ["Invalid array length"], | 197 "invalid_array_length", ["Invalid array length"], |
| 210 stack_overflow: ["Maximum call stack size exceeded"], | 198 "stack_overflow", ["Maximum call stack size exceeded"], |
| 211 // SyntaxError | 199 // SyntaxError |
| 212 unable_to_parse: ["Parse error"], | 200 "unable_to_parse", ["Parse error"], |
| 213 invalid_regexp_flags: ["Invalid flags supplied to RegExp construct
or '", "%0", "'"], | 201 "invalid_regexp_flags", ["Invalid flags supplied to RegExp constru
ctor '", "%0", "'"], |
| 214 invalid_regexp: ["Invalid RegExp pattern /", "%0", "/"], | 202 "invalid_regexp", ["Invalid RegExp pattern /", "%0", "/"], |
| 215 illegal_break: ["Illegal break statement"], | 203 "illegal_break", ["Illegal break statement"], |
| 216 illegal_continue: ["Illegal continue statement"], | 204 "illegal_continue", ["Illegal continue statement"], |
| 217 illegal_return: ["Illegal return statement"], | 205 "illegal_return", ["Illegal return statement"], |
| 218 error_loading_debugger: ["Error loading debugger"], | 206 "error_loading_debugger", ["Error loading debugger"], |
| 219 no_input_to_regexp: ["No input to ", "%0"], | 207 "no_input_to_regexp", ["No input to ", "%0"], |
| 220 invalid_json: ["String '", "%0", "' is not valid JSON"], | 208 "invalid_json", ["String '", "%0", "' is not valid JSON"], |
| 221 circular_structure: ["Converting circular structure to JSON"], | 209 "circular_structure", ["Converting circular structure to JSON"], |
| 222 obj_ctor_property_non_object: ["Object.", "%0", " called on non-object"], | 210 "obj_ctor_property_non_object", ["Object.", "%0", " called on non-object"]
, |
| 223 called_on_null_or_undefined: ["%0", " called on null or undefined"], | 211 "called_on_null_or_undefined", ["%0", " called on null or undefined"], |
| 224 array_indexof_not_defined: ["Array.getIndexOf: Argument undefined"], | 212 "array_indexof_not_defined", ["Array.getIndexOf: Argument undefined"], |
| 225 object_not_extensible: ["Can't add property ", "%0", ", object is n
ot extensible"], | 213 "object_not_extensible", ["Can't add property ", "%0", ", object is
not extensible"], |
| 226 illegal_access: ["Illegal access"], | 214 "illegal_access", ["Illegal access"], |
| 227 invalid_preparser_data: ["Invalid preparser data for function ", "%0
"], | 215 "invalid_preparser_data", ["Invalid preparser data for function ", "
%0"], |
| 228 strict_mode_with: ["Strict mode code may not include a with st
atement"], | 216 "strict_mode_with", ["Strict mode code may not include a with
statement"], |
| 229 strict_catch_variable: ["Catch variable may not be eval or argument
s in strict mode"], | 217 "strict_catch_variable", ["Catch variable may not be eval or argume
nts in strict mode"], |
| 230 too_many_arguments: ["Too many arguments in function call (only
32766 allowed)"], | 218 "too_many_arguments", ["Too many arguments in function call (onl
y 32766 allowed)"], |
| 231 too_many_parameters: ["Too many parameters in function definition
(only 32766 allowed)"], | 219 "too_many_parameters", ["Too many parameters in function definiti
on (only 32766 allowed)"], |
| 232 too_many_variables: ["Too many variables declared (only 32767 al
lowed)"], | 220 "too_many_variables", ["Too many variables declared (only 32767
allowed)"], |
| 233 strict_param_name: ["Parameter name eval or arguments is not al
lowed in strict mode"], | 221 "strict_param_name", ["Parameter name eval or arguments is not
allowed in strict mode"], |
| 234 strict_param_dupe: ["Strict mode function may not have duplicat
e parameter names"], | 222 "strict_param_dupe", ["Strict mode function may not have duplic
ate parameter names"], |
| 235 strict_var_name: ["Variable name may not be eval or arguments
in strict mode"], | 223 "strict_var_name", ["Variable name may not be eval or argumen
ts in strict mode"], |
| 236 strict_function_name: ["Function name may not be eval or arguments
in strict mode"], | 224 "strict_function_name", ["Function name may not be eval or argumen
ts in strict mode"], |
| 237 strict_octal_literal: ["Octal literals are not allowed in strict m
ode."], | 225 "strict_octal_literal", ["Octal literals are not allowed in strict
mode."], |
| 238 strict_duplicate_property: ["Duplicate data property in object literal
not allowed in strict mode"], | 226 "strict_duplicate_property", ["Duplicate data property in object litera
l not allowed in strict mode"], |
| 239 accessor_data_property: ["Object literal may not have data and acces
sor property with the same name"], | 227 "accessor_data_property", ["Object literal may not have data and acc
essor property with the same name"], |
| 240 accessor_get_set: ["Object literal may not have multiple get/s
et accessors with the same name"], | 228 "accessor_get_set", ["Object literal may not have multiple get
/set accessors with the same name"], |
| 241 strict_lhs_assignment: ["Assignment to eval or arguments is not all
owed in strict mode"], | 229 "strict_lhs_assignment", ["Assignment to eval or arguments is not a
llowed in strict mode"], |
| 242 strict_lhs_postfix: ["Postfix increment/decrement may not have e
val or arguments operand in strict mode"], | 230 "strict_lhs_postfix", ["Postfix increment/decrement may not have
eval or arguments operand in strict mode"], |
| 243 strict_lhs_prefix: ["Prefix increment/decrement may not have ev
al or arguments operand in strict mode"], | 231 "strict_lhs_prefix", ["Prefix increment/decrement may not have
eval or arguments operand in strict mode"], |
| 244 strict_reserved_word: ["Use of future reserved word in strict mode
"], | 232 "strict_reserved_word", ["Use of future reserved word in strict mo
de"], |
| 245 strict_delete: ["Delete of an unqualified identifier in str
ict mode."], | 233 "strict_delete", ["Delete of an unqualified identifier in s
trict mode."], |
| 246 strict_delete_property: ["Cannot delete property '", "%0", "' of ",
"%1"], | 234 "strict_delete_property", ["Cannot delete property '", "%0", "' of "
, "%1"], |
| 247 strict_const: ["Use of const in strict mode."], | 235 "strict_const", ["Use of const in strict mode."], |
| 248 strict_function: ["In strict mode code, functions can only be
declared at top level or immediately within another function." ], | 236 "strict_function", ["In strict mode code, functions can only
be declared at top level or immediately within another function." ], |
| 249 strict_read_only_property: ["Cannot assign to read only property '", "%
0", "' of ", "%1"], | 237 "strict_read_only_property", ["Cannot assign to read only property '",
"%0", "' of ", "%1"], |
| 250 strict_cannot_assign: ["Cannot assign to read only '", "%0", "' in
strict mode"], | 238 "strict_cannot_assign", ["Cannot assign to read only '", "%0", "'
in strict mode"], |
| 251 strict_poison_pill: ["'caller', 'callee', and 'arguments' proper
ties may not be accessed on strict mode functions or the arguments objects for c
alls to them"], | 239 "strict_poison_pill", ["'caller', 'callee', and 'arguments' prop
erties may not be accessed on strict mode functions or the arguments objects for
calls to them"], |
| 252 strict_caller: ["Illegal access to a strict mode caller fun
ction."], | 240 "strict_caller", ["Illegal access to a strict mode caller f
unction."], |
| 253 unprotected_let: ["Illegal let declaration in unprotected sta
tement context."], | 241 "unprotected_let", ["Illegal let declaration in unprotected s
tatement context."], |
| 254 }; | 242 ]; |
| 243 var messages = { __proto__ : null }; |
| 244 var desc = new PropertyDescriptor(); |
| 245 desc.setConfigurable(false); |
| 246 desc.setEnumerable(false); |
| 247 desc.setWritable(false); |
| 248 for (var i = 0; i < messagesDictionary.length; i += 2) { |
| 249 var key = messagesDictionary[i]; |
| 250 var format = messagesDictionary[i + 1]; |
| 251 ObjectFreeze(format); |
| 252 desc.setValue(format); |
| 253 DefineOwnProperty(messages, key, desc); |
| 254 } |
| 255 %PreventExtensions(messages); |
| 256 %IgnoreAttributesAndSetProperty(builtins, "kMessages", |
| 257 messages, |
| 258 DONT_DELETE | DONT_ENUM | READ_ONLY); |
| 255 } | 259 } |
| 256 var message_type = %MessageGetType(message); | 260 var message_type = %MessageGetType(message); |
| 257 var format = kMessages[message_type]; | 261 var format = kMessages[message_type]; |
| 258 if (!format) return "<unknown message " + message_type + ">"; | 262 if (!format) return "<unknown message " + message_type + ">"; |
| 259 return FormatString(format, message); | 263 return FormatString(format, message); |
| 260 } | 264 } |
| 261 | 265 |
| 262 | 266 |
| 263 function GetLineNumber(message) { | 267 function GetLineNumber(message) { |
| 264 var start_position = %MessageGetStartPosition(message); | 268 var start_position = %MessageGetStartPosition(message); |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 310 function MakeError(type, args) { | 314 function MakeError(type, args) { |
| 311 return MakeGenericError($Error, type, args); | 315 return MakeGenericError($Error, type, args); |
| 312 } | 316 } |
| 313 | 317 |
| 314 /** | 318 /** |
| 315 * Find a line number given a specific source position. | 319 * Find a line number given a specific source position. |
| 316 * @param {number} position The source position. | 320 * @param {number} position The source position. |
| 317 * @return {number} 0 if input too small, -1 if input too large, | 321 * @return {number} 0 if input too small, -1 if input too large, |
| 318 else the line number. | 322 else the line number. |
| 319 */ | 323 */ |
| 320 Script.prototype.lineFromPosition = function(position) { | 324 function ScriptLineFromPosition(position) { |
| 321 var lower = 0; | 325 var lower = 0; |
| 322 var upper = this.lineCount() - 1; | 326 var upper = this.lineCount() - 1; |
| 323 var line_ends = this.line_ends; | 327 var line_ends = this.line_ends; |
| 324 | 328 |
| 325 // We'll never find invalid positions so bail right away. | 329 // We'll never find invalid positions so bail right away. |
| 326 if (position > line_ends[upper]) { | 330 if (position > line_ends[upper]) { |
| 327 return -1; | 331 return -1; |
| 328 } | 332 } |
| 329 | 333 |
| 330 // This means we don't have to safe-guard indexing line_ends[i - 1]. | 334 // This means we don't have to safe-guard indexing line_ends[i - 1]. |
| (...skipping 18 matching lines...) Expand all Loading... |
| 349 } | 353 } |
| 350 | 354 |
| 351 /** | 355 /** |
| 352 * Get information on a specific source position. | 356 * Get information on a specific source position. |
| 353 * @param {number} position The source position | 357 * @param {number} position The source position |
| 354 * @param {boolean} include_resource_offset Set to true to have the resource | 358 * @param {boolean} include_resource_offset Set to true to have the resource |
| 355 * offset added to the location | 359 * offset added to the location |
| 356 * @return {SourceLocation} | 360 * @return {SourceLocation} |
| 357 * If line is negative or not in the source null is returned. | 361 * If line is negative or not in the source null is returned. |
| 358 */ | 362 */ |
| 359 Script.prototype.locationFromPosition = function (position, | 363 function ScriptLocationFromPosition(position, |
| 360 include_resource_offset) { | 364 include_resource_offset) { |
| 361 var line = this.lineFromPosition(position); | 365 var line = this.lineFromPosition(position); |
| 362 if (line == -1) return null; | 366 if (line == -1) return null; |
| 363 | 367 |
| 364 // Determine start, end and column. | 368 // Determine start, end and column. |
| 365 var line_ends = this.line_ends; | 369 var line_ends = this.line_ends; |
| 366 var start = line == 0 ? 0 : line_ends[line - 1] + 1; | 370 var start = line == 0 ? 0 : line_ends[line - 1] + 1; |
| 367 var end = line_ends[line]; | 371 var end = line_ends[line]; |
| 368 if (end > 0 && %_CallFunction(this.source, end - 1, StringCharAt) == '\r') end
--; | 372 if (end > 0 && %_CallFunction(this.source, end - 1, StringCharAt) == '\r') { |
| 373 end--; |
| 374 } |
| 369 var column = position - start; | 375 var column = position - start; |
| 370 | 376 |
| 371 // Adjust according to the offset within the resource. | 377 // Adjust according to the offset within the resource. |
| 372 if (include_resource_offset) { | 378 if (include_resource_offset) { |
| 373 line += this.line_offset; | 379 line += this.line_offset; |
| 374 if (line == this.line_offset) { | 380 if (line == this.line_offset) { |
| 375 column += this.column_offset; | 381 column += this.column_offset; |
| 376 } | 382 } |
| 377 } | 383 } |
| 378 | 384 |
| 379 return new SourceLocation(this, position, line, column, start, end); | 385 return new SourceLocation(this, position, line, column, start, end); |
| 380 }; | 386 }; |
| 381 | 387 |
| 382 | 388 |
| 383 /** | 389 /** |
| 384 * Get information on a specific source line and column possibly offset by a | 390 * Get information on a specific source line and column possibly offset by a |
| 385 * fixed source position. This function is used to find a source position from | 391 * fixed source position. This function is used to find a source position from |
| 386 * a line and column position. The fixed source position offset is typically | 392 * a line and column position. The fixed source position offset is typically |
| 387 * used to find a source position in a function based on a line and column in | 393 * used to find a source position in a function based on a line and column in |
| 388 * the source for the function alone. The offset passed will then be the | 394 * the source for the function alone. The offset passed will then be the |
| 389 * start position of the source for the function within the full script source. | 395 * start position of the source for the function within the full script source. |
| 390 * @param {number} opt_line The line within the source. Default value is 0 | 396 * @param {number} opt_line The line within the source. Default value is 0 |
| 391 * @param {number} opt_column The column in within the line. Default value is 0 | 397 * @param {number} opt_column The column in within the line. Default value is 0 |
| 392 * @param {number} opt_offset_position The offset from the begining of the | 398 * @param {number} opt_offset_position The offset from the begining of the |
| 393 * source from where the line and column calculation starts. Default value i
s 0 | 399 * source from where the line and column calculation starts. |
| 400 * Default value is 0 |
| 394 * @return {SourceLocation} | 401 * @return {SourceLocation} |
| 395 * If line is negative or not in the source null is returned. | 402 * If line is negative or not in the source null is returned. |
| 396 */ | 403 */ |
| 397 Script.prototype.locationFromLine = function (opt_line, opt_column, opt_offset_p
osition) { | 404 function ScriptLocationFromLine(opt_line, opt_column, opt_offset_position) { |
| 398 // Default is the first line in the script. Lines in the script is relative | 405 // Default is the first line in the script. Lines in the script is relative |
| 399 // to the offset within the resource. | 406 // to the offset within the resource. |
| 400 var line = 0; | 407 var line = 0; |
| 401 if (!IS_UNDEFINED(opt_line)) { | 408 if (!IS_UNDEFINED(opt_line)) { |
| 402 line = opt_line - this.line_offset; | 409 line = opt_line - this.line_offset; |
| 403 } | 410 } |
| 404 | 411 |
| 405 // Default is first column. If on the first line add the offset within the | 412 // Default is first column. If on the first line add the offset within the |
| 406 // resource. | 413 // resource. |
| 407 var column = opt_column || 0; | 414 var column = opt_column || 0; |
| (...skipping 21 matching lines...) Expand all Loading... |
| 429 /** | 436 /** |
| 430 * Get a slice of source code from the script. The boundaries for the slice is | 437 * Get a slice of source code from the script. The boundaries for the slice is |
| 431 * specified in lines. | 438 * specified in lines. |
| 432 * @param {number} opt_from_line The first line (zero bound) in the slice. | 439 * @param {number} opt_from_line The first line (zero bound) in the slice. |
| 433 * Default is 0 | 440 * Default is 0 |
| 434 * @param {number} opt_to_column The last line (zero bound) in the slice (non | 441 * @param {number} opt_to_column The last line (zero bound) in the slice (non |
| 435 * inclusive). Default is the number of lines in the script | 442 * inclusive). Default is the number of lines in the script |
| 436 * @return {SourceSlice} The source slice or null of the parameters where | 443 * @return {SourceSlice} The source slice or null of the parameters where |
| 437 * invalid | 444 * invalid |
| 438 */ | 445 */ |
| 439 Script.prototype.sourceSlice = function (opt_from_line, opt_to_line) { | 446 function ScriptSourceSlice(opt_from_line, opt_to_line) { |
| 440 var from_line = IS_UNDEFINED(opt_from_line) ? this.line_offset : opt_from_line
; | 447 var from_line = IS_UNDEFINED(opt_from_line) ? this.line_offset : opt_from_line
; |
| 441 var to_line = IS_UNDEFINED(opt_to_line) ? this.line_offset + this.lineCount()
: opt_to_line | 448 var to_line = IS_UNDEFINED(opt_to_line) ? this.line_offset + this.lineCount()
: opt_to_line |
| 442 | 449 |
| 443 // Adjust according to the offset within the resource. | 450 // Adjust according to the offset within the resource. |
| 444 from_line -= this.line_offset; | 451 from_line -= this.line_offset; |
| 445 to_line -= this.line_offset; | 452 to_line -= this.line_offset; |
| 446 if (from_line < 0) from_line = 0; | 453 if (from_line < 0) from_line = 0; |
| 447 if (to_line > this.lineCount()) to_line = this.lineCount(); | 454 if (to_line > this.lineCount()) to_line = this.lineCount(); |
| 448 | 455 |
| 449 // Check parameters. | 456 // Check parameters. |
| 450 if (from_line >= this.lineCount() || | 457 if (from_line >= this.lineCount() || |
| 451 to_line < 0 || | 458 to_line < 0 || |
| 452 from_line > to_line) { | 459 from_line > to_line) { |
| 453 return null; | 460 return null; |
| 454 } | 461 } |
| 455 | 462 |
| 456 var line_ends = this.line_ends; | 463 var line_ends = this.line_ends; |
| 457 var from_position = from_line == 0 ? 0 : line_ends[from_line - 1] + 1; | 464 var from_position = from_line == 0 ? 0 : line_ends[from_line - 1] + 1; |
| 458 var to_position = to_line == 0 ? 0 : line_ends[to_line - 1] + 1; | 465 var to_position = to_line == 0 ? 0 : line_ends[to_line - 1] + 1; |
| 459 | 466 |
| 460 // Return a source slice with line numbers re-adjusted to the resource. | 467 // Return a source slice with line numbers re-adjusted to the resource. |
| 461 return new SourceSlice(this, from_line + this.line_offset, to_line + this.line
_offset, | 468 return new SourceSlice(this, from_line + this.line_offset, to_line + this.line
_offset, |
| 462 from_position, to_position); | 469 from_position, to_position); |
| 463 } | 470 } |
| 464 | 471 |
| 465 | 472 |
| 466 Script.prototype.sourceLine = function (opt_line) { | 473 function ScriptSourceLine(opt_line) { |
| 467 // Default is the first line in the script. Lines in the script are relative | 474 // Default is the first line in the script. Lines in the script are relative |
| 468 // to the offset within the resource. | 475 // to the offset within the resource. |
| 469 var line = 0; | 476 var line = 0; |
| 470 if (!IS_UNDEFINED(opt_line)) { | 477 if (!IS_UNDEFINED(opt_line)) { |
| 471 line = opt_line - this.line_offset; | 478 line = opt_line - this.line_offset; |
| 472 } | 479 } |
| 473 | 480 |
| 474 // Check parameter. | 481 // Check parameter. |
| 475 if (line < 0 || this.lineCount() <= line) { | 482 if (line < 0 || this.lineCount() <= line) { |
| 476 return null; | 483 return null; |
| 477 } | 484 } |
| 478 | 485 |
| 479 // Return the source line. | 486 // Return the source line. |
| 480 var line_ends = this.line_ends; | 487 var line_ends = this.line_ends; |
| 481 var start = line == 0 ? 0 : line_ends[line - 1] + 1; | 488 var start = line == 0 ? 0 : line_ends[line - 1] + 1; |
| 482 var end = line_ends[line]; | 489 var end = line_ends[line]; |
| 483 return %_CallFunction(this.source, start, end, StringSubstring); | 490 return %_CallFunction(this.source, start, end, StringSubstring); |
| 484 } | 491 } |
| 485 | 492 |
| 486 | 493 |
| 487 /** | 494 /** |
| 488 * Returns the number of source lines. | 495 * Returns the number of source lines. |
| 489 * @return {number} | 496 * @return {number} |
| 490 * Number of source lines. | 497 * Number of source lines. |
| 491 */ | 498 */ |
| 492 Script.prototype.lineCount = function() { | 499 function ScriptLineCount() { |
| 493 // Return number of source lines. | 500 // Return number of source lines. |
| 494 return this.line_ends.length; | 501 return this.line_ends.length; |
| 495 }; | 502 }; |
| 496 | 503 |
| 497 | 504 |
| 498 /** | 505 /** |
| 499 * Returns the name of script if available, contents of sourceURL comment | 506 * Returns the name of script if available, contents of sourceURL comment |
| 500 * otherwise. See | 507 * otherwise. See |
| 501 * http://fbug.googlecode.com/svn/branches/firebug1.1/docs/ReleaseNotes_1.1.txt | 508 * http://fbug.googlecode.com/svn/branches/firebug1.1/docs/ReleaseNotes_1.1.txt |
| 502 * for details on using //@ sourceURL comment to identify scritps that don't | 509 * for details on using //@ sourceURL comment to identify scritps that don't |
| 503 * have name. | 510 * have name. |
| 504 * | 511 * |
| 505 * @return {?string} script name if present, value for //@ sourceURL comment | 512 * @return {?string} script name if present, value for //@ sourceURL comment |
| 506 * otherwise. | 513 * otherwise. |
| 507 */ | 514 */ |
| 508 Script.prototype.nameOrSourceURL = function() { | 515 function ScriptNameOrSourceURL() { |
| 509 if (this.name) | 516 if (this.name) { |
| 510 return this.name; | 517 return this.name; |
| 518 } |
| 511 // TODO(608): the spaces in a regexp below had to be escaped as \040 | 519 // TODO(608): the spaces in a regexp below had to be escaped as \040 |
| 512 // because this file is being processed by js2c whose handling of spaces | 520 // because this file is being processed by js2c whose handling of spaces |
| 513 // in regexps is broken. Also, ['"] are excluded from allowed URLs to | 521 // in regexps is broken. Also, ['"] are excluded from allowed URLs to |
| 514 // avoid matches against sources that invoke evals with sourceURL. | 522 // avoid matches against sources that invoke evals with sourceURL. |
| 515 // A better solution would be to detect these special comments in | 523 // A better solution would be to detect these special comments in |
| 516 // the scanner/parser. | 524 // the scanner/parser. |
| 517 var source = ToString(this.source); | 525 var source = ToString(this.source); |
| 518 var sourceUrlPos = %StringIndexOf(source, "sourceURL=", 0); | 526 var sourceUrlPos = %StringIndexOf(source, "sourceURL=", 0); |
| 519 if (sourceUrlPos > 4) { | 527 if (sourceUrlPos > 4) { |
| 520 var sourceUrlPattern = | 528 var sourceUrlPattern = |
| 521 /\/\/@[\040\t]sourceURL=[\040\t]*([^\s\'\"]*)[\040\t]*$/gm; | 529 /\/\/@[\040\t]sourceURL=[\040\t]*([^\s\'\"]*)[\040\t]*$/gm; |
| 522 // Don't reuse lastMatchInfo here, so we create a new array with room | 530 // Don't reuse lastMatchInfo here, so we create a new array with room |
| 523 // for four captures (array with length one longer than the index | 531 // for four captures (array with length one longer than the index |
| 524 // of the fourth capture, where the numbering is zero-based). | 532 // of the fourth capture, where the numbering is zero-based). |
| 525 var matchInfo = new InternalArray(CAPTURE(3) + 1); | 533 var matchInfo = new InternalArray(CAPTURE(3) + 1); |
| 526 var match = | 534 var match = |
| 527 %_RegExpExec(sourceUrlPattern, source, sourceUrlPos - 4, matchInfo); | 535 %_RegExpExec(sourceUrlPattern, source, sourceUrlPos - 4, matchInfo); |
| 528 if (match) { | 536 if (match) { |
| 529 return SubString(source, matchInfo[CAPTURE(2)], matchInfo[CAPTURE(3)]); | 537 return SubString(source, matchInfo[CAPTURE(2)], matchInfo[CAPTURE(3)]); |
| 530 } | 538 } |
| 531 } | 539 } |
| 532 return this.name; | 540 return this.name; |
| 533 } | 541 } |
| 534 | 542 |
| 535 | 543 |
| 544 SetUpLockedPrototype(Script, |
| 545 $Array("source", "name", "line_ends", "line_offset", "column_offset"), |
| 546 $Array( |
| 547 "lineFromPosition", ScriptLineFromPosition, |
| 548 "locationFromPosition", ScriptLocationFromPosition, |
| 549 "locationFromLine", ScriptLocationFromLine, |
| 550 "sourceSlice", ScriptSourceSlice, |
| 551 "sourceLine", ScriptSourceLine, |
| 552 "lineCount", ScriptLineCount, |
| 553 "nameOrSourceURL", ScriptNameOrSourceURL |
| 554 ) |
| 555 ); |
| 556 |
| 557 |
| 536 /** | 558 /** |
| 537 * Class for source location. A source location is a position within some | 559 * Class for source location. A source location is a position within some |
| 538 * source with the following properties: | 560 * source with the following properties: |
| 539 * script : script object for the source | 561 * script : script object for the source |
| 540 * line : source line number | 562 * line : source line number |
| 541 * column : source column within the line | 563 * column : source column within the line |
| 542 * position : position within the source | 564 * position : position within the source |
| 543 * start : position of start of source context (inclusive) | 565 * start : position of start of source context (inclusive) |
| 544 * end : position of end of source context (not inclusive) | 566 * end : position of end of source context (not inclusive) |
| 545 * Source text for the source context is the character interval [start, end[. In | 567 * Source text for the source context is the character interval [start, end[. In |
| (...skipping 10 matching lines...) Expand all Loading... |
| 556 */ | 578 */ |
| 557 function SourceLocation(script, position, line, column, start, end) { | 579 function SourceLocation(script, position, line, column, start, end) { |
| 558 this.script = script; | 580 this.script = script; |
| 559 this.position = position; | 581 this.position = position; |
| 560 this.line = line; | 582 this.line = line; |
| 561 this.column = column; | 583 this.column = column; |
| 562 this.start = start; | 584 this.start = start; |
| 563 this.end = end; | 585 this.end = end; |
| 564 } | 586 } |
| 565 | 587 |
| 566 SourceLocation.prototype.__proto__ = null; | |
| 567 | |
| 568 const kLineLengthLimit = 78; | 588 const kLineLengthLimit = 78; |
| 569 | 589 |
| 570 /** | 590 /** |
| 571 * Restrict source location start and end positions to make the source slice | 591 * Restrict source location start and end positions to make the source slice |
| 572 * no more that a certain number of characters wide. | 592 * no more that a certain number of characters wide. |
| 573 * @param {number} opt_limit The with limit of the source text with a default | 593 * @param {number} opt_limit The with limit of the source text with a default |
| 574 * of 78 | 594 * of 78 |
| 575 * @param {number} opt_before The number of characters to prefer before the | 595 * @param {number} opt_before The number of characters to prefer before the |
| 576 * position with a default value of 10 less that the limit | 596 * position with a default value of 10 less that the limit |
| 577 */ | 597 */ |
| 578 SourceLocation.prototype.restrict = function (opt_limit, opt_before) { | 598 function SourceLocationRestrict(opt_limit, opt_before) { |
| 579 // Find the actual limit to use. | 599 // Find the actual limit to use. |
| 580 var limit; | 600 var limit; |
| 581 var before; | 601 var before; |
| 582 if (!IS_UNDEFINED(opt_limit)) { | 602 if (!IS_UNDEFINED(opt_limit)) { |
| 583 limit = opt_limit; | 603 limit = opt_limit; |
| 584 } else { | 604 } else { |
| 585 limit = kLineLengthLimit; | 605 limit = kLineLengthLimit; |
| 586 } | 606 } |
| 587 if (!IS_UNDEFINED(opt_before)) { | 607 if (!IS_UNDEFINED(opt_before)) { |
| 588 before = opt_before; | 608 before = opt_before; |
| (...skipping 26 matching lines...) Expand all Loading... |
| 615 } | 635 } |
| 616 } | 636 } |
| 617 }; | 637 }; |
| 618 | 638 |
| 619 | 639 |
| 620 /** | 640 /** |
| 621 * Get the source text for a SourceLocation | 641 * Get the source text for a SourceLocation |
| 622 * @return {String} | 642 * @return {String} |
| 623 * Source text for this location. | 643 * Source text for this location. |
| 624 */ | 644 */ |
| 625 SourceLocation.prototype.sourceText = function () { | 645 function SourceLocationSourceText() { |
| 626 return %_CallFunction(this.script.source, this.start, this.end, StringSubstrin
g); | 646 return %_CallFunction(this.script.source, this.start, this.end, StringSubstrin
g); |
| 627 }; | 647 }; |
| 628 | 648 |
| 629 | 649 |
| 650 SetUpLockedPrototype(SourceLocation, |
| 651 $Array("script", "position", "line", "column", "start", "end"), |
| 652 $Array( |
| 653 "restrict", SourceLocationRestrict, |
| 654 "sourceText", SourceLocationSourceText |
| 655 ) |
| 656 ); |
| 657 |
| 658 |
| 630 /** | 659 /** |
| 631 * Class for a source slice. A source slice is a part of a script source with | 660 * Class for a source slice. A source slice is a part of a script source with |
| 632 * the following properties: | 661 * the following properties: |
| 633 * script : script object for the source | 662 * script : script object for the source |
| 634 * from_line : line number for the first line in the slice | 663 * from_line : line number for the first line in the slice |
| 635 * to_line : source line number for the last line in the slice | 664 * to_line : source line number for the last line in the slice |
| 636 * from_position : position of the first character in the slice | 665 * from_position : position of the first character in the slice |
| 637 * to_position : position of the last character in the slice | 666 * to_position : position of the last character in the slice |
| 638 * The to_line and to_position are not included in the slice, that is the lines | 667 * The to_line and to_position are not included in the slice, that is the lines |
| 639 * in the slice are [from_line, to_line[. Likewise the characters in the slice | 668 * in the slice are [from_line, to_line[. Likewise the characters in the slice |
| 640 * are [from_position, to_position[. | 669 * are [from_position, to_position[. |
| 641 * @param {Script} script The Script object for the source slice | 670 * @param {Script} script The Script object for the source slice |
| 642 * @param {number} from_line | 671 * @param {number} from_line |
| 643 * @param {number} to_line | 672 * @param {number} to_line |
| 644 * @param {number} from_position | 673 * @param {number} from_position |
| 645 * @param {number} to_position | 674 * @param {number} to_position |
| 646 * @constructor | 675 * @constructor |
| 647 */ | 676 */ |
| 648 function SourceSlice(script, from_line, to_line, from_position, to_position) { | 677 function SourceSlice(script, from_line, to_line, from_position, to_position) { |
| 649 this.script = script; | 678 this.script = script; |
| 650 this.from_line = from_line; | 679 this.from_line = from_line; |
| 651 this.to_line = to_line; | 680 this.to_line = to_line; |
| 652 this.from_position = from_position; | 681 this.from_position = from_position; |
| 653 this.to_position = to_position; | 682 this.to_position = to_position; |
| 654 } | 683 } |
| 655 | 684 |
| 656 SourceSlice.prototype.__proto__ = null; | |
| 657 | |
| 658 /** | 685 /** |
| 659 * Get the source text for a SourceSlice | 686 * Get the source text for a SourceSlice |
| 660 * @return {String} Source text for this slice. The last line will include | 687 * @return {String} Source text for this slice. The last line will include |
| 661 * the line terminating characters (if any) | 688 * the line terminating characters (if any) |
| 662 */ | 689 */ |
| 663 SourceSlice.prototype.sourceText = function () { | 690 function SourceSliceSourceText() { |
| 664 return %_CallFunction(this.script.source, | 691 return %_CallFunction(this.script.source, |
| 665 this.from_position, | 692 this.from_position, |
| 666 this.to_position, | 693 this.to_position, |
| 667 StringSubstring); | 694 StringSubstring); |
| 668 }; | 695 }; |
| 669 | 696 |
| 697 SetUpLockedPrototype(SourceSlice, |
| 698 $Array("script", "from_line", "to_line", "from_position", "to_position"), |
| 699 $Array("sourceText", SourceSliceSourceText) |
| 700 ); |
| 701 |
| 670 | 702 |
| 671 // Returns the offset of the given position within the containing | 703 // Returns the offset of the given position within the containing |
| 672 // line. | 704 // line. |
| 673 function GetPositionInLine(message) { | 705 function GetPositionInLine(message) { |
| 674 var script = %MessageGetScript(message); | 706 var script = %MessageGetScript(message); |
| 675 var start_position = %MessageGetStartPosition(message); | 707 var start_position = %MessageGetStartPosition(message); |
| 676 var location = script.locationFromPosition(start_position, false); | 708 var location = script.locationFromPosition(start_position, false); |
| 677 if (location == null) return -1; | 709 if (location == null) return -1; |
| 678 location.restrict(); | 710 location.restrict(); |
| 679 return start_position - location.start; | 711 return start_position - location.start; |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 714 desc = ToPropertyDescriptor(desc); | 746 desc = ToPropertyDescriptor(desc); |
| 715 DefineOwnProperty(obj, name, desc, true); | 747 DefineOwnProperty(obj, name, desc, true); |
| 716 } | 748 } |
| 717 | 749 |
| 718 function CallSite(receiver, fun, pos) { | 750 function CallSite(receiver, fun, pos) { |
| 719 this.receiver = receiver; | 751 this.receiver = receiver; |
| 720 this.fun = fun; | 752 this.fun = fun; |
| 721 this.pos = pos; | 753 this.pos = pos; |
| 722 } | 754 } |
| 723 | 755 |
| 724 CallSite.prototype.__proto__ = null; | 756 function CallSiteGetThis() { |
| 725 | |
| 726 CallSite.prototype.getThis = function () { | |
| 727 return this.receiver; | 757 return this.receiver; |
| 728 }; | 758 }; |
| 729 | 759 |
| 730 CallSite.prototype.getTypeName = function () { | 760 function CallSiteGetTypeName() { |
| 731 var constructor = this.receiver.constructor; | 761 var constructor = this.receiver.constructor; |
| 732 if (!constructor) { | 762 if (!constructor) { |
| 733 return %_CallFunction(this.receiver, ObjectToString); | 763 return %_CallFunction(this.receiver, ObjectToString); |
| 734 } | 764 } |
| 735 var constructorName = constructor.name; | 765 var constructorName = constructor.name; |
| 736 if (!constructorName) { | 766 if (!constructorName) { |
| 737 return %_CallFunction(this.receiver, ObjectToString); | 767 return %_CallFunction(this.receiver, ObjectToString); |
| 738 } | 768 } |
| 739 return constructorName; | 769 return constructorName; |
| 740 }; | 770 }; |
| 741 | 771 |
| 742 CallSite.prototype.isToplevel = function () { | 772 function CallSiteIsToplevel() { |
| 743 if (this.receiver == null) { | 773 if (this.receiver == null) { |
| 744 return true; | 774 return true; |
| 745 } | 775 } |
| 746 return IS_GLOBAL(this.receiver); | 776 return IS_GLOBAL(this.receiver); |
| 747 }; | 777 }; |
| 748 | 778 |
| 749 CallSite.prototype.isEval = function () { | 779 function CallSiteIsEval() { |
| 750 var script = %FunctionGetScript(this.fun); | 780 var script = %FunctionGetScript(this.fun); |
| 751 return script && script.compilation_type == COMPILATION_TYPE_EVAL; | 781 return script && script.compilation_type == COMPILATION_TYPE_EVAL; |
| 752 }; | 782 }; |
| 753 | 783 |
| 754 CallSite.prototype.getEvalOrigin = function () { | 784 function CallSiteGetEvalOrigin() { |
| 755 var script = %FunctionGetScript(this.fun); | 785 var script = %FunctionGetScript(this.fun); |
| 756 return FormatEvalOrigin(script); | 786 return FormatEvalOrigin(script); |
| 757 }; | 787 }; |
| 758 | 788 |
| 759 CallSite.prototype.getScriptNameOrSourceURL = function () { | 789 function CallSiteGetScriptNameOrSourceURL() { |
| 760 var script = %FunctionGetScript(this.fun); | 790 var script = %FunctionGetScript(this.fun); |
| 761 return script ? script.nameOrSourceURL() : null; | 791 return script ? script.nameOrSourceURL() : null; |
| 762 }; | 792 }; |
| 763 | 793 |
| 764 CallSite.prototype.getFunction = function () { | 794 function CallSiteGetFunction() { |
| 765 return this.fun; | 795 return this.fun; |
| 766 }; | 796 }; |
| 767 | 797 |
| 768 CallSite.prototype.getFunctionName = function () { | 798 function CallSiteGetFunctionName() { |
| 769 // See if the function knows its own name | 799 // See if the function knows its own name |
| 770 var name = this.fun.name; | 800 var name = this.fun.name; |
| 771 if (name) { | 801 if (name) { |
| 772 return name; | 802 return name; |
| 773 } else { | 803 } else { |
| 774 return %FunctionGetInferredName(this.fun); | 804 return %FunctionGetInferredName(this.fun); |
| 775 } | 805 } |
| 776 // Maybe this is an evaluation? | 806 // Maybe this is an evaluation? |
| 777 var script = %FunctionGetScript(this.fun); | 807 var script = %FunctionGetScript(this.fun); |
| 778 if (script && script.compilation_type == COMPILATION_TYPE_EVAL) { | 808 if (script && script.compilation_type == COMPILATION_TYPE_EVAL) { |
| 779 return "eval"; | 809 return "eval"; |
| 780 } | 810 } |
| 781 return null; | 811 return null; |
| 782 }; | 812 }; |
| 783 | 813 |
| 784 CallSite.prototype.getMethodName = function () { | 814 function CallSiteGetMethodName() { |
| 785 // See if we can find a unique property on the receiver that holds | 815 // See if we can find a unique property on the receiver that holds |
| 786 // this function. | 816 // this function. |
| 787 var ownName = this.fun.name; | 817 var ownName = this.fun.name; |
| 788 if (ownName && this.receiver && | 818 if (ownName && this.receiver && |
| 789 (%_CallFunction(this.receiver, ownName, ObjectLookupGetter) === this.fun |
| | 819 (%_CallFunction(this.receiver, ownName, ObjectLookupGetter) === this.fun |
| |
| 790 %_CallFunction(this.receiver, ownName, ObjectLookupSetter) === this.fun |
| | 820 %_CallFunction(this.receiver, ownName, ObjectLookupSetter) === this.fun |
| |
| 791 this.receiver[ownName] === this.fun)) { | 821 this.receiver[ownName] === this.fun)) { |
| 792 // To handle DontEnum properties we guess that the method has | 822 // To handle DontEnum properties we guess that the method has |
| 793 // the same name as the function. | 823 // the same name as the function. |
| 794 return ownName; | 824 return ownName; |
| 795 } | 825 } |
| 796 var name = null; | 826 var name = null; |
| 797 for (var prop in this.receiver) { | 827 for (var prop in this.receiver) { |
| 798 if (this.receiver.__lookupGetter__(prop) === this.fun || | 828 if (this.receiver.__lookupGetter__(prop) === this.fun || |
| 799 this.receiver.__lookupSetter__(prop) === this.fun || | 829 this.receiver.__lookupSetter__(prop) === this.fun || |
| 800 (!this.receiver.__lookupGetter__(prop) && this.receiver[prop] === this.f
un)) { | 830 (!this.receiver.__lookupGetter__(prop) && this.receiver[prop] === this.f
un)) { |
| 801 // If we find more than one match bail out to avoid confusion. | 831 // If we find more than one match bail out to avoid confusion. |
| 802 if (name) { | 832 if (name) { |
| 803 return null; | 833 return null; |
| 804 } | 834 } |
| 805 name = prop; | 835 name = prop; |
| 806 } | 836 } |
| 807 } | 837 } |
| 808 if (name) { | 838 if (name) { |
| 809 return name; | 839 return name; |
| 810 } | 840 } |
| 811 return null; | 841 return null; |
| 812 }; | 842 }; |
| 813 | 843 |
| 814 CallSite.prototype.getFileName = function () { | 844 function CallSiteGetFileName() { |
| 815 var script = %FunctionGetScript(this.fun); | 845 var script = %FunctionGetScript(this.fun); |
| 816 return script ? script.name : null; | 846 return script ? script.name : null; |
| 817 }; | 847 }; |
| 818 | 848 |
| 819 CallSite.prototype.getLineNumber = function () { | 849 function CallSiteGetLineNumber() { |
| 820 if (this.pos == -1) { | 850 if (this.pos == -1) { |
| 821 return null; | 851 return null; |
| 822 } | 852 } |
| 823 var script = %FunctionGetScript(this.fun); | 853 var script = %FunctionGetScript(this.fun); |
| 824 var location = null; | 854 var location = null; |
| 825 if (script) { | 855 if (script) { |
| 826 location = script.locationFromPosition(this.pos, true); | 856 location = script.locationFromPosition(this.pos, true); |
| 827 } | 857 } |
| 828 return location ? location.line + 1 : null; | 858 return location ? location.line + 1 : null; |
| 829 }; | 859 }; |
| 830 | 860 |
| 831 CallSite.prototype.getColumnNumber = function () { | 861 function CallSiteGetColumnNumber() { |
| 832 if (this.pos == -1) { | 862 if (this.pos == -1) { |
| 833 return null; | 863 return null; |
| 834 } | 864 } |
| 835 var script = %FunctionGetScript(this.fun); | 865 var script = %FunctionGetScript(this.fun); |
| 836 var location = null; | 866 var location = null; |
| 837 if (script) { | 867 if (script) { |
| 838 location = script.locationFromPosition(this.pos, true); | 868 location = script.locationFromPosition(this.pos, true); |
| 839 } | 869 } |
| 840 return location ? location.column + 1: null; | 870 return location ? location.column + 1: null; |
| 841 }; | 871 }; |
| 842 | 872 |
| 843 CallSite.prototype.isNative = function () { | 873 function CallSiteIsNative() { |
| 844 var script = %FunctionGetScript(this.fun); | 874 var script = %FunctionGetScript(this.fun); |
| 845 return script ? (script.type == TYPE_NATIVE) : false; | 875 return script ? (script.type == TYPE_NATIVE) : false; |
| 846 }; | 876 }; |
| 847 | 877 |
| 848 CallSite.prototype.getPosition = function () { | 878 function CallSiteGetPosition() { |
| 849 return this.pos; | 879 return this.pos; |
| 850 }; | 880 }; |
| 851 | 881 |
| 852 CallSite.prototype.isConstructor = function () { | 882 function CallSiteIsConstructor() { |
| 853 var constructor = this.receiver ? this.receiver.constructor : null; | 883 var constructor = this.receiver ? this.receiver.constructor : null; |
| 854 if (!constructor) { | 884 if (!constructor) { |
| 855 return false; | 885 return false; |
| 856 } | 886 } |
| 857 return this.fun === constructor; | 887 return this.fun === constructor; |
| 858 }; | 888 }; |
| 859 | 889 |
| 890 SetUpLockedPrototype(CallSite, $Array("receiver", "fun", "pos"), $Array( |
| 891 "getThis", CallSiteGetThis, |
| 892 "getTypeName", CallSiteGetTypeName, |
| 893 "isToplevel", CallSiteIsToplevel, |
| 894 "isEval", CallSiteIsEval, |
| 895 "getEvalOrigin", CallSiteGetEvalOrigin, |
| 896 "getScriptNameOrSourceURL", CallSiteGetScriptNameOrSourceURL, |
| 897 "getFunction", CallSiteGetFunction, |
| 898 "getFunctionName", CallSiteGetFunctionName, |
| 899 "getMethodName", CallSiteGetMethodName, |
| 900 "getFileName", CallSiteGetFileName, |
| 901 "getLineNumber", CallSiteGetLineNumber, |
| 902 "getColumnNumber", CallSiteGetColumnNumber, |
| 903 "isNative", CallSiteIsNative, |
| 904 "getPosition", CallSiteGetPosition, |
| 905 "isConstructor", CallSiteIsConstructor |
| 906 )); |
| 907 |
| 908 |
| 860 function FormatEvalOrigin(script) { | 909 function FormatEvalOrigin(script) { |
| 861 var sourceURL = script.nameOrSourceURL(); | 910 var sourceURL = script.nameOrSourceURL(); |
| 862 if (sourceURL) { | 911 if (sourceURL) { |
| 863 return sourceURL; | 912 return sourceURL; |
| 864 } | 913 } |
| 865 | 914 |
| 866 var eval_origin = "eval at "; | 915 var eval_origin = "eval at "; |
| 867 if (script.eval_from_function_name) { | 916 if (script.eval_from_function_name) { |
| 868 eval_origin += script.eval_from_function_name; | 917 eval_origin += script.eval_from_function_name; |
| 869 } else { | 918 } else { |
| (...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 991 var pos = %FunctionGetPositionForOffset(code, pc); | 1040 var pos = %FunctionGetPositionForOffset(code, pc); |
| 992 frames.push(new CallSite(recv, fun, pos)); | 1041 frames.push(new CallSite(recv, fun, pos)); |
| 993 } | 1042 } |
| 994 if (IS_FUNCTION($Error.prepareStackTrace)) { | 1043 if (IS_FUNCTION($Error.prepareStackTrace)) { |
| 995 return $Error.prepareStackTrace(error, frames); | 1044 return $Error.prepareStackTrace(error, frames); |
| 996 } else { | 1045 } else { |
| 997 return FormatStackTrace(error, frames); | 1046 return FormatStackTrace(error, frames); |
| 998 } | 1047 } |
| 999 } | 1048 } |
| 1000 | 1049 |
| 1001 function DefineError(f) { | |
| 1002 // Store the error function in both the global object | |
| 1003 // and the runtime object. The function is fetched | |
| 1004 // from the runtime object when throwing errors from | |
| 1005 // within the runtime system to avoid strange side | |
| 1006 // effects when overwriting the error functions from | |
| 1007 // user code. | |
| 1008 var name = f.name; | |
| 1009 %SetProperty(global, name, f, DONT_ENUM); | |
| 1010 this['$' + name] = f; | |
| 1011 // Configure the error function. | |
| 1012 if (name == 'Error') { | |
| 1013 // The prototype of the Error object must itself be an error. | |
| 1014 // However, it can't be an instance of the Error object because | |
| 1015 // it hasn't been properly configured yet. Instead we create a | |
| 1016 // special not-a-true-error-but-close-enough object. | |
| 1017 function ErrorPrototype() {} | |
| 1018 %FunctionSetPrototype(ErrorPrototype, $Object.prototype); | |
| 1019 %FunctionSetInstanceClassName(ErrorPrototype, 'Error'); | |
| 1020 %FunctionSetPrototype(f, new ErrorPrototype()); | |
| 1021 } else { | |
| 1022 %FunctionSetPrototype(f, new $Error()); | |
| 1023 } | |
| 1024 %FunctionSetInstanceClassName(f, 'Error'); | |
| 1025 %SetProperty(f.prototype, 'constructor', f, DONT_ENUM); | |
| 1026 // The name property on the prototype of error objects is not | |
| 1027 // specified as being read-one and dont-delete. However, allowing | |
| 1028 // overwriting allows leaks of error objects between script blocks | |
| 1029 // in the same context in a browser setting. Therefore we fix the | |
| 1030 // name. | |
| 1031 %SetProperty(f.prototype, "name", name, DONT_ENUM | DONT_DELETE | READ_ONLY); | |
| 1032 %SetCode(f, function(m) { | |
| 1033 if (%_IsConstructCall()) { | |
| 1034 // Define all the expected properties directly on the error | |
| 1035 // object. This avoids going through getters and setters defined | |
| 1036 // on prototype objects. | |
| 1037 %IgnoreAttributesAndSetProperty(this, 'stack', void 0, DONT_ENUM); | |
| 1038 %IgnoreAttributesAndSetProperty(this, 'arguments', void 0, DONT_ENUM); | |
| 1039 %IgnoreAttributesAndSetProperty(this, 'type', void 0, DONT_ENUM); | |
| 1040 if (m === kAddMessageAccessorsMarker) { | |
| 1041 // DefineOneShotAccessor always inserts a message property and | |
| 1042 // ignores setters. | |
| 1043 DefineOneShotAccessor(this, 'message', function (obj) { | |
| 1044 return FormatMessage(%NewMessageObject(obj.type, obj.arguments)); | |
| 1045 }); | |
| 1046 } else if (!IS_UNDEFINED(m)) { | |
| 1047 %IgnoreAttributesAndSetProperty(this, | |
| 1048 'message', | |
| 1049 ToString(m), | |
| 1050 DONT_ENUM); | |
| 1051 } | |
| 1052 captureStackTrace(this, f); | |
| 1053 } else { | |
| 1054 return new f(m); | |
| 1055 } | |
| 1056 }); | |
| 1057 } | |
| 1058 | 1050 |
| 1059 function captureStackTrace(obj, cons_opt) { | 1051 function captureStackTrace(obj, cons_opt) { |
| 1060 var stackTraceLimit = $Error.stackTraceLimit; | 1052 var stackTraceLimit = $Error.stackTraceLimit; |
| 1061 if (!stackTraceLimit || !IS_NUMBER(stackTraceLimit)) return; | 1053 if (!stackTraceLimit || !IS_NUMBER(stackTraceLimit)) return; |
| 1062 if (stackTraceLimit < 0 || stackTraceLimit > 10000) { | 1054 if (stackTraceLimit < 0 || stackTraceLimit > 10000) { |
| 1063 stackTraceLimit = 10000; | 1055 stackTraceLimit = 10000; |
| 1064 } | 1056 } |
| 1065 var raw_stack = %CollectStackTrace(cons_opt | 1057 var raw_stack = %CollectStackTrace(cons_opt |
| 1066 ? cons_opt | 1058 ? cons_opt |
| 1067 : captureStackTrace, stackTraceLimit); | 1059 : captureStackTrace, stackTraceLimit); |
| 1068 DefineOneShotAccessor(obj, 'stack', function (obj) { | 1060 DefineOneShotAccessor(obj, 'stack', function (obj) { |
| 1069 return FormatRawStackTrace(obj, raw_stack); | 1061 return FormatRawStackTrace(obj, raw_stack); |
| 1070 }); | 1062 }); |
| 1071 }; | 1063 }; |
| 1072 | 1064 |
| 1073 $Math.__proto__ = global.Object.prototype; | |
| 1074 | 1065 |
| 1075 // DefineError is a native function. Use explicit receiver. Otherwise | 1066 function SetUpError() { |
| 1076 // the receiver will be 'undefined'. | 1067 // Define special error type constructors. |
| 1077 this.DefineError(function Error() { }); | 1068 |
| 1078 this.DefineError(function TypeError() { }); | 1069 function DefineError(f) { |
| 1079 this.DefineError(function RangeError() { }); | 1070 // Store the error function in both the global object |
| 1080 this.DefineError(function SyntaxError() { }); | 1071 // and the runtime object. The function is fetched |
| 1081 this.DefineError(function ReferenceError() { }); | 1072 // from the runtime object when throwing errors from |
| 1082 this.DefineError(function EvalError() { }); | 1073 // within the runtime system to avoid strange side |
| 1083 this.DefineError(function URIError() { }); | 1074 // effects when overwriting the error functions from |
| 1075 // user code. |
| 1076 var name = f.name; |
| 1077 %SetProperty(global, name, f, DONT_ENUM); |
| 1078 %SetProperty(builtins, '$' + name, f, DONT_ENUM | DONT_DELETE | READ_ONLY); |
| 1079 // Configure the error function. |
| 1080 if (name == 'Error') { |
| 1081 // The prototype of the Error object must itself be an error. |
| 1082 // However, it can't be an instance of the Error object because |
| 1083 // it hasn't been properly configured yet. Instead we create a |
| 1084 // special not-a-true-error-but-close-enough object. |
| 1085 function ErrorPrototype() {} |
| 1086 %FunctionSetPrototype(ErrorPrototype, $Object.prototype); |
| 1087 %FunctionSetInstanceClassName(ErrorPrototype, 'Error'); |
| 1088 %FunctionSetPrototype(f, new ErrorPrototype()); |
| 1089 } else { |
| 1090 %FunctionSetPrototype(f, new $Error()); |
| 1091 } |
| 1092 %FunctionSetInstanceClassName(f, 'Error'); |
| 1093 %SetProperty(f.prototype, 'constructor', f, DONT_ENUM); |
| 1094 // The name property on the prototype of error objects is not |
| 1095 // specified as being read-one and dont-delete. However, allowing |
| 1096 // overwriting allows leaks of error objects between script blocks |
| 1097 // in the same context in a browser setting. Therefore we fix the |
| 1098 // name. |
| 1099 %SetProperty(f.prototype, "name", name, |
| 1100 DONT_ENUM | DONT_DELETE | READ_ONLY) ; |
| 1101 %SetCode(f, function(m) { |
| 1102 if (%_IsConstructCall()) { |
| 1103 // Define all the expected properties directly on the error |
| 1104 // object. This avoids going through getters and setters defined |
| 1105 // on prototype objects. |
| 1106 %IgnoreAttributesAndSetProperty(this, 'stack', void 0, DONT_ENUM); |
| 1107 %IgnoreAttributesAndSetProperty(this, 'arguments', void 0, DONT_ENUM); |
| 1108 %IgnoreAttributesAndSetProperty(this, 'type', void 0, DONT_ENUM); |
| 1109 if (m === kAddMessageAccessorsMarker) { |
| 1110 // DefineOneShotAccessor always inserts a message property and |
| 1111 // ignores setters. |
| 1112 DefineOneShotAccessor(this, 'message', function (obj) { |
| 1113 return FormatMessage(%NewMessageObject(obj.type, obj.arguments)); |
| 1114 }); |
| 1115 } else if (!IS_UNDEFINED(m)) { |
| 1116 %IgnoreAttributesAndSetProperty(this, |
| 1117 'message', |
| 1118 ToString(m), |
| 1119 DONT_ENUM); |
| 1120 } |
| 1121 captureStackTrace(this, f); |
| 1122 } else { |
| 1123 return new f(m); |
| 1124 } |
| 1125 }); |
| 1126 } |
| 1127 |
| 1128 DefineError(function Error() { }); |
| 1129 DefineError(function TypeError() { }); |
| 1130 DefineError(function RangeError() { }); |
| 1131 DefineError(function SyntaxError() { }); |
| 1132 DefineError(function ReferenceError() { }); |
| 1133 DefineError(function EvalError() { }); |
| 1134 DefineError(function URIError() { }); |
| 1135 } |
| 1136 |
| 1137 SetUpError(); |
| 1084 | 1138 |
| 1085 $Error.captureStackTrace = captureStackTrace; | 1139 $Error.captureStackTrace = captureStackTrace; |
| 1086 | 1140 |
| 1087 // Setup extra properties of the Error.prototype object. | 1141 %SetProperty($Error.prototype, 'message', '', DONT_ENUM); |
| 1088 function setErrorMessage() { | |
| 1089 var desc = {value: '', | |
| 1090 enumerable: false, | |
| 1091 configurable: true, | |
| 1092 writable: true }; | |
| 1093 DefineOwnProperty($Error.prototype, | |
| 1094 'message', | |
| 1095 ToPropertyDescriptor(desc), | |
| 1096 true); | |
| 1097 | |
| 1098 } | |
| 1099 | |
| 1100 setErrorMessage(); | |
| 1101 | 1142 |
| 1102 // Global list of error objects visited during errorToString. This is | 1143 // Global list of error objects visited during errorToString. This is |
| 1103 // used to detect cycles in error toString formatting. | 1144 // used to detect cycles in error toString formatting. |
| 1104 var visited_errors = new $Array(); | 1145 const visited_errors = new InternalArray(); |
| 1105 var cyclic_error_marker = new $Object(); | 1146 const cyclic_error_marker = new $Object(); |
| 1106 | 1147 |
| 1107 function errorToStringDetectCycle() { | 1148 function errorToStringDetectCycle(error) { |
| 1108 if (!%PushIfAbsent(visited_errors, this)) throw cyclic_error_marker; | 1149 if (!%PushIfAbsent(visited_errors, error)) throw cyclic_error_marker; |
| 1109 try { | 1150 try { |
| 1110 var type = this.type; | 1151 var type = error.type; |
| 1111 if (type && !%_CallFunction(this, "message", ObjectHasOwnProperty)) { | 1152 var hasMessage = %_CallFunction(error, "message", ObjectHasOwnProperty); |
| 1112 var formatted = FormatMessage(%NewMessageObject(type, this.arguments)); | 1153 if (type && !hasMessage) { |
| 1113 return this.name + ": " + formatted; | 1154 var formatted = FormatMessage(%NewMessageObject(type, error.arguments)); |
| 1155 return error.name + ": " + formatted; |
| 1114 } | 1156 } |
| 1115 var message = %_CallFunction(this, "message", ObjectHasOwnProperty) | 1157 var message = hasMessage ? (": " + error.message) : ""; |
| 1116 ? (": " + this.message) | 1158 return error.name + message; |
| 1117 : ""; | |
| 1118 return this.name + message; | |
| 1119 } finally { | 1159 } finally { |
| 1120 visited_errors.length = visited_errors.length - 1; | 1160 visited_errors.length = visited_errors.length - 1; |
| 1121 } | 1161 } |
| 1122 } | 1162 } |
| 1123 | 1163 |
| 1124 function errorToString() { | 1164 function errorToString() { |
| 1125 if (IS_NULL_OR_UNDEFINED(this) && !IS_UNDETECTABLE(this)) { | 1165 if (IS_NULL_OR_UNDEFINED(this) && !IS_UNDETECTABLE(this)) { |
| 1126 throw MakeTypeError("called_on_null_or_undefined", | 1166 throw MakeTypeError("called_on_null_or_undefined", |
| 1127 ["Error.prototype.toString"]); | 1167 ["Error.prototype.toString"]); |
| 1128 } | 1168 } |
| 1129 // This helper function is needed because access to properties on | 1169 // This helper function is needed because access to properties on |
| 1130 // the builtins object do not work inside of a catch clause. | 1170 // the builtins object do not work inside of a catch clause. |
| 1131 function isCyclicErrorMarker(o) { return o === cyclic_error_marker; } | 1171 function isCyclicErrorMarker(o) { return o === cyclic_error_marker; } |
| 1132 | 1172 |
| 1133 try { | 1173 try { |
| 1134 return %_CallFunction(this, errorToStringDetectCycle); | 1174 return errorToStringDetectCycle(this); |
| 1135 } catch(e) { | 1175 } catch(e) { |
| 1136 // If this error message was encountered already return the empty | 1176 // If this error message was encountered already return the empty |
| 1137 // string for it instead of recursively formatting it. | 1177 // string for it instead of recursively formatting it. |
| 1138 if (isCyclicErrorMarker(e)) { | 1178 if (isCyclicErrorMarker(e)) { |
| 1139 return ''; | 1179 return ''; |
| 1140 } | 1180 } |
| 1141 throw e; | 1181 throw e; |
| 1142 } | 1182 } |
| 1143 } | 1183 } |
| 1144 | 1184 |
| 1145 | 1185 |
| 1146 InstallFunctions($Error.prototype, DONT_ENUM, ['toString', errorToString]); | 1186 InstallFunctions($Error.prototype, DONT_ENUM, ['toString', errorToString]); |
| 1147 | 1187 |
| 1148 // Boilerplate for exceptions for stack overflows. Used from | 1188 // Boilerplate for exceptions for stack overflows. Used from |
| 1149 // Isolate::StackOverflow(). | 1189 // Isolate::StackOverflow(). |
| 1150 const kStackOverflowBoilerplate = MakeRangeError('stack_overflow', []); | 1190 const kStackOverflowBoilerplate = MakeRangeError('stack_overflow', []); |
| OLD | NEW |