| Index: src/runtime.cc
|
| diff --git a/src/runtime.cc b/src/runtime.cc
|
| index fefe1e46844afb06f030832e58452b60eddbfda1..02be8a66a3eb3f09b2407ba217c3bd261973d6a3 100644
|
| --- a/src/runtime.cc
|
| +++ b/src/runtime.cc
|
| @@ -153,25 +153,13 @@ namespace internal {
|
| PropertyDetails name = PropertyDetails(Smi::cast(args[index]));
|
|
|
|
|
| -// Assert that the given argument has a valid value for a StrictModeFlag
|
| -// and store it in a StrictModeFlag variable with the given name.
|
| +// Assert that the given argument has a valid value for a StrictMode
|
| +// and store it in a StrictMode variable with the given name.
|
| #define CONVERT_STRICT_MODE_ARG_CHECKED(name, index) \
|
| RUNTIME_ASSERT(args[index]->IsSmi()); \
|
| - RUNTIME_ASSERT(args.smi_at(index) == kStrictMode || \
|
| - args.smi_at(index) == kNonStrictMode); \
|
| - StrictModeFlag name = \
|
| - static_cast<StrictModeFlag>(args.smi_at(index));
|
| -
|
| -
|
| -// Assert that the given argument has a valid value for a LanguageMode
|
| -// and store it in a LanguageMode variable with the given name.
|
| -#define CONVERT_LANGUAGE_MODE_ARG(name, index) \
|
| - ASSERT(args[index]->IsSmi()); \
|
| - ASSERT(args.smi_at(index) == CLASSIC_MODE || \
|
| - args.smi_at(index) == STRICT_MODE || \
|
| - args.smi_at(index) == EXTENDED_MODE); \
|
| - LanguageMode name = \
|
| - static_cast<LanguageMode>(args.smi_at(index));
|
| + RUNTIME_ASSERT(args.smi_at(index) == STRICT || \
|
| + args.smi_at(index) == SLOPPY); \
|
| + StrictMode name = static_cast<StrictMode>(args.smi_at(index));
|
|
|
|
|
| static Handle<Map> ComputeObjectLiteralMap(
|
| @@ -298,7 +286,7 @@ static Handle<Object> CreateObjectLiteralBoilerplate(
|
| if (Handle<String>::cast(key)->AsArrayIndex(&element_index)) {
|
| // Array index as string (uint32).
|
| result = JSObject::SetOwnElement(
|
| - boilerplate, element_index, value, kNonStrictMode);
|
| + boilerplate, element_index, value, SLOPPY);
|
| } else {
|
| Handle<String> name(String::cast(*key));
|
| ASSERT(!name->AsArrayIndex(&element_index));
|
| @@ -309,7 +297,7 @@ static Handle<Object> CreateObjectLiteralBoilerplate(
|
| } else if (key->ToArrayIndex(&element_index)) {
|
| // Array index (uint32).
|
| result = JSObject::SetOwnElement(
|
| - boilerplate, element_index, value, kNonStrictMode);
|
| + boilerplate, element_index, value, SLOPPY);
|
| } else {
|
| // Non-uint32 number.
|
| ASSERT(key->IsNumber());
|
| @@ -964,6 +952,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_TypedArrayInitializeFromArrayLike) {
|
| Runtime::ArrayIdToTypeAndSize(arrayId, &array_type, &element_size);
|
|
|
| Handle<JSArrayBuffer> buffer = isolate->factory()->NewJSArrayBuffer();
|
| + if (source->IsJSTypedArray() &&
|
| + JSTypedArray::cast(*source)->type() == array_type) {
|
| + length_obj = Handle<Object>(JSTypedArray::cast(*source)->length(), isolate);
|
| + }
|
| size_t length = NumberToSize(isolate, *length_obj);
|
|
|
| if ((length > static_cast<unsigned>(Smi::kMaxValue)) ||
|
| @@ -1621,7 +1613,8 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetPrototype) {
|
| !isolate->MayNamedAccessWrapper(Handle<JSObject>::cast(obj),
|
| isolate->factory()->proto_string(),
|
| v8::ACCESS_GET)) {
|
| - isolate->ReportFailedAccessCheck(JSObject::cast(*obj), v8::ACCESS_GET);
|
| + isolate->ReportFailedAccessCheckWrapper(Handle<JSObject>::cast(obj),
|
| + v8::ACCESS_GET);
|
| RETURN_IF_SCHEDULED_EXCEPTION(isolate);
|
| return isolate->heap()->undefined_value();
|
| }
|
| @@ -1648,7 +1641,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_SetPrototype) {
|
| ASSERT(args.length() == 2);
|
| CONVERT_ARG_HANDLE_CHECKED(JSObject, obj, 0);
|
| CONVERT_ARG_HANDLE_CHECKED(Object, prototype, 1);
|
| - if (FLAG_harmony_observation && obj->map()->is_observed()) {
|
| + if (obj->map()->is_observed()) {
|
| Handle<Object> old_value(
|
| GetPrototypeSkipHiddenPrototypes(isolate, *obj), isolate);
|
|
|
| @@ -1747,7 +1740,7 @@ static AccessCheckResult CheckPropertyAccess(Handle<JSObject> obj,
|
| return ACCESS_ALLOWED;
|
| }
|
|
|
| - obj->GetIsolate()->ReportFailedAccessCheck(*obj, access_type);
|
| + obj->GetIsolate()->ReportFailedAccessCheckWrapper(obj, access_type);
|
| return ACCESS_FORBIDDEN;
|
| }
|
|
|
| @@ -1786,7 +1779,7 @@ static AccessCheckResult CheckPropertyAccess(Handle<JSObject> obj,
|
| break;
|
| }
|
|
|
| - isolate->ReportFailedAccessCheck(*obj, access_type);
|
| + isolate->ReportFailedAccessCheckWrapper(obj, access_type);
|
| return ACCESS_FORBIDDEN;
|
| }
|
|
|
| @@ -1820,7 +1813,7 @@ static Handle<Object> GetOwnProperty(Isolate* isolate,
|
| case ACCESS_ABSENT: return factory->undefined_value();
|
| }
|
|
|
| - PropertyAttributes attrs = obj->GetLocalPropertyAttribute(*name);
|
| + PropertyAttributes attrs = JSReceiver::GetLocalPropertyAttribute(obj, name);
|
| if (attrs == ABSENT) {
|
| RETURN_HANDLE_IF_SCHEDULED_EXCEPTION(isolate, Object);
|
| return factory->undefined_value();
|
| @@ -2063,17 +2056,12 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) {
|
| // value of the variable if the property is already there.
|
| // Do the lookup locally only, see ES5 erratum.
|
| LookupResult lookup(isolate);
|
| - if (FLAG_es52_globals) {
|
| - global->LocalLookup(*name, &lookup, true);
|
| - } else {
|
| - global->Lookup(*name, &lookup);
|
| - }
|
| + global->LocalLookup(*name, &lookup, true);
|
| if (lookup.IsFound()) {
|
| // We found an existing property. Unless it was an interceptor
|
| // that claims the property is absent, skip this declaration.
|
| if (!lookup.IsInterceptor()) continue;
|
| - PropertyAttributes attributes = global->GetPropertyAttribute(*name);
|
| - if (attributes != ABSENT) continue;
|
| + if (JSReceiver::GetPropertyAttribute(global, name) != ABSENT) continue;
|
| // Fall-through and introduce the absent property by using
|
| // SetProperty.
|
| }
|
| @@ -2102,7 +2090,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) {
|
| attr |= READ_ONLY;
|
| }
|
|
|
| - LanguageMode language_mode = DeclareGlobalsLanguageMode::decode(flags);
|
| + StrictMode strict_mode = DeclareGlobalsStrictMode::decode(flags);
|
|
|
| if (!lookup.IsFound() || is_function) {
|
| // If the local property exists, check that we can reconfigure it
|
| @@ -2124,7 +2112,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareGlobals) {
|
| RETURN_IF_EMPTY_HANDLE(isolate,
|
| JSObject::SetProperty(
|
| global, name, value, static_cast<PropertyAttributes>(attr),
|
| - language_mode == CLASSIC_MODE ? kNonStrictMode : kStrictMode));
|
| + strict_mode));
|
| }
|
| }
|
|
|
| @@ -2180,8 +2168,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareContextSlot) {
|
| Handle<JSObject> object = Handle<JSObject>::cast(holder);
|
| RETURN_IF_EMPTY_HANDLE(
|
| isolate,
|
| - JSReceiver::SetProperty(object, name, initial_value, mode,
|
| - kNonStrictMode));
|
| + JSReceiver::SetProperty(object, name, initial_value, mode, SLOPPY));
|
| }
|
| }
|
|
|
| @@ -2227,7 +2214,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareContextSlot) {
|
| JSObject::SetLocalPropertyIgnoreAttributes(object, name, value, mode));
|
| } else {
|
| RETURN_IF_EMPTY_HANDLE(isolate,
|
| - JSReceiver::SetProperty(object, name, value, mode, kNonStrictMode));
|
| + JSReceiver::SetProperty(object, name, value, mode, SLOPPY));
|
| }
|
| }
|
|
|
| @@ -2248,9 +2235,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) {
|
|
|
| CONVERT_ARG_HANDLE_CHECKED(String, name, 0);
|
| RUNTIME_ASSERT(args[1]->IsSmi());
|
| - CONVERT_LANGUAGE_MODE_ARG(language_mode, 1);
|
| - StrictModeFlag strict_mode_flag = (language_mode == CLASSIC_MODE)
|
| - ? kNonStrictMode : kStrictMode;
|
| + CONVERT_STRICT_MODE_ARG_CHECKED(strict_mode, 1);
|
|
|
| // According to ECMA-262, section 12.2, page 62, the property must
|
| // not be deletable.
|
| @@ -2266,15 +2251,15 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) {
|
| LookupResult lookup(isolate);
|
| isolate->context()->global_object()->LocalLookup(*name, &lookup, true);
|
| if (lookup.IsInterceptor()) {
|
| + Handle<JSObject> holder(lookup.holder());
|
| PropertyAttributes intercepted =
|
| - lookup.holder()->GetPropertyAttribute(*name);
|
| + JSReceiver::GetPropertyAttribute(holder, name);
|
| if (intercepted != ABSENT && (intercepted & READ_ONLY) == 0) {
|
| // Found an interceptor that's not read only.
|
| if (assign) {
|
| CONVERT_ARG_HANDLE_CHECKED(Object, value, 2);
|
| Handle<Object> result = JSObject::SetPropertyForResult(
|
| - handle(lookup.holder()), &lookup, name, value, attributes,
|
| - strict_mode_flag);
|
| + holder, &lookup, name, value, attributes, strict_mode);
|
| RETURN_IF_EMPTY_HANDLE(isolate, result);
|
| return *result;
|
| } else {
|
| @@ -2287,7 +2272,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeVarGlobal) {
|
| CONVERT_ARG_HANDLE_CHECKED(Object, value, 2);
|
| Handle<GlobalObject> global(isolate->context()->global_object());
|
| Handle<Object> result = JSReceiver::SetProperty(
|
| - global, name, value, attributes, strict_mode_flag);
|
| + global, name, value, attributes, strict_mode);
|
| RETURN_IF_EMPTY_HANDLE(isolate, result);
|
| return *result;
|
| }
|
| @@ -2338,11 +2323,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeConstGlobal) {
|
| // BUG 1213575: Handle the case where we have to set a read-only
|
| // property through an interceptor and only do it if it's
|
| // uninitialized, e.g. the hole. Nirk...
|
| - // Passing non-strict mode because the property is writable.
|
| + // Passing sloppy mode because the property is writable.
|
| RETURN_IF_EMPTY_HANDLE(
|
| isolate,
|
| - JSReceiver::SetProperty(global, name, value, attributes,
|
| - kNonStrictMode));
|
| + JSReceiver::SetProperty(global, name, value, attributes, SLOPPY));
|
| return *value;
|
| }
|
|
|
| @@ -2412,7 +2396,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeConstContextSlot) {
|
| // Strict mode not needed (const disallowed in strict mode).
|
| RETURN_IF_EMPTY_HANDLE(
|
| isolate,
|
| - JSReceiver::SetProperty(global, name, value, NONE, kNonStrictMode));
|
| + JSReceiver::SetProperty(global, name, value, NONE, SLOPPY));
|
| return *value;
|
| }
|
|
|
| @@ -2463,8 +2447,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_InitializeConstContextSlot) {
|
| // Strict mode not needed (const disallowed in strict mode).
|
| RETURN_IF_EMPTY_HANDLE(
|
| isolate,
|
| - JSReceiver::SetProperty(object, name, value, attributes,
|
| - kNonStrictMode));
|
| + JSReceiver::SetProperty(object, name, value, attributes, SLOPPY));
|
| }
|
| }
|
|
|
| @@ -2544,7 +2527,6 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_RegExpConstructResult) {
|
|
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_RegExpInitializeObject) {
|
| HandleScope scope(isolate);
|
| - DisallowHeapAllocation no_allocation;
|
| ASSERT(args.length() == 5);
|
| CONVERT_ARG_HANDLE_CHECKED(JSRegExp, regexp, 0);
|
| CONVERT_ARG_HANDLE_CHECKED(String, source, 1);
|
| @@ -2625,7 +2607,7 @@ static Handle<JSFunction> InstallBuiltin(Isolate* isolate,
|
| code,
|
| false);
|
| optimized->shared()->DontAdaptArguments();
|
| - JSReceiver::SetProperty(holder, key, optimized, NONE, kStrictMode);
|
| + JSReceiver::SetProperty(holder, key, optimized, NONE, STRICT);
|
| return optimized;
|
| }
|
|
|
| @@ -2647,7 +2629,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_SpecialArrayFunctions) {
|
| }
|
|
|
|
|
| -RUNTIME_FUNCTION(MaybeObject*, Runtime_IsClassicModeFunction) {
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_IsSloppyModeFunction) {
|
| SealHandleScope shs(isolate);
|
| ASSERT(args.length() == 1);
|
| CONVERT_ARG_CHECKED(JSReceiver, callable, 0);
|
| @@ -2661,7 +2643,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_IsClassicModeFunction) {
|
| }
|
| JSFunction* function = JSFunction::cast(callable);
|
| SharedFunctionInfo* shared = function->shared();
|
| - return isolate->heap()->ToBoolean(shared->is_classic_mode());
|
| + return isolate->heap()->ToBoolean(shared->strict_mode() == SLOPPY);
|
| }
|
|
|
|
|
| @@ -2681,7 +2663,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetDefaultReceiver) {
|
| JSFunction* function = JSFunction::cast(callable);
|
|
|
| SharedFunctionInfo* shared = function->shared();
|
| - if (shared->native() || !shared->is_classic_mode()) {
|
| + if (shared->native() || shared->strict_mode() == STRICT) {
|
| return isolate->heap()->undefined_value();
|
| }
|
| // Returns undefined for strict or native functions, or
|
| @@ -2947,6 +2929,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_SetCode) {
|
| // Set the code, scope info, formal parameter count, and the length
|
| // of the target shared function info.
|
| target_shared->ReplaceCode(source_shared->code());
|
| + target_shared->set_feedback_vector(source_shared->feedback_vector());
|
| target_shared->set_scope_info(source_shared->scope_info());
|
| target_shared->set_length(source_shared->length());
|
| target_shared->set_formal_parameter_count(
|
| @@ -4950,8 +4933,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_KeyedGetProperty) {
|
| int offset = result.GetFieldIndex().field_index();
|
| // Do not track double fields in the keyed lookup cache. Reading
|
| // double values requires boxing.
|
| - if (!FLAG_track_double_fields ||
|
| - !result.representation().IsDouble()) {
|
| + if (!result.representation().IsDouble()) {
|
| keyed_lookup_cache->Update(receiver_map, key, offset);
|
| }
|
| return receiver->FastPropertyAt(result.representation(), offset);
|
| @@ -5086,7 +5068,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DefineOrRedefineDataProperty) {
|
| name,
|
| obj_value,
|
| handle(lookup.holder()),
|
| - kStrictMode);
|
| + STRICT);
|
| RETURN_IF_EMPTY_HANDLE(isolate, result_object);
|
| return *result_object;
|
| }
|
| @@ -5159,7 +5141,7 @@ Handle<Object> Runtime::SetObjectProperty(Isolate* isolate,
|
| Handle<Object> key,
|
| Handle<Object> value,
|
| PropertyAttributes attr,
|
| - StrictModeFlag strict_mode) {
|
| + StrictMode strict_mode) {
|
| SetPropertyMode set_mode = attr == NONE ? SET_PROPERTY : DEFINE_PROPERTY;
|
|
|
| if (object->IsUndefined() || object->IsNull()) {
|
| @@ -5277,7 +5259,7 @@ Handle<Object> Runtime::ForceSetObjectProperty(Isolate* isolate,
|
| return value;
|
| }
|
|
|
| - return JSObject::SetElement(js_object, index, value, attr, kNonStrictMode,
|
| + return JSObject::SetElement(js_object, index, value, attr, SLOPPY,
|
| false,
|
| DEFINE_PROPERTY);
|
| }
|
| @@ -5285,7 +5267,7 @@ Handle<Object> Runtime::ForceSetObjectProperty(Isolate* isolate,
|
| if (key->IsName()) {
|
| Handle<Name> name = Handle<Name>::cast(key);
|
| if (name->AsArrayIndex(&index)) {
|
| - return JSObject::SetElement(js_object, index, value, attr, kNonStrictMode,
|
| + return JSObject::SetElement(js_object, index, value, attr, SLOPPY,
|
| false,
|
| DEFINE_PROPERTY);
|
| } else {
|
| @@ -5303,7 +5285,7 @@ Handle<Object> Runtime::ForceSetObjectProperty(Isolate* isolate,
|
| Handle<String> name = Handle<String>::cast(converted);
|
|
|
| if (name->AsArrayIndex(&index)) {
|
| - return JSObject::SetElement(js_object, index, value, attr, kNonStrictMode,
|
| + return JSObject::SetElement(js_object, index, value, attr, SLOPPY,
|
| false,
|
| DEFINE_PROPERTY);
|
| } else {
|
| @@ -5356,6 +5338,17 @@ MaybeObject* Runtime::DeleteObjectProperty(Isolate* isolate,
|
| }
|
|
|
|
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_SetHiddenProperty) {
|
| + HandleScope scope(isolate);
|
| + RUNTIME_ASSERT(args.length() == 3);
|
| +
|
| + CONVERT_ARG_HANDLE_CHECKED(JSObject, object, 0);
|
| + CONVERT_ARG_HANDLE_CHECKED(String, key, 1);
|
| + CONVERT_ARG_HANDLE_CHECKED(Object, value, 2);
|
| + return *JSObject::SetHiddenProperty(object, key, value);
|
| +}
|
| +
|
| +
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_SetProperty) {
|
| HandleScope scope(isolate);
|
| RUNTIME_ASSERT(args.length() == 4 || args.length() == 5);
|
| @@ -5370,10 +5363,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_SetProperty) {
|
| PropertyAttributes attributes =
|
| static_cast<PropertyAttributes>(unchecked_attributes);
|
|
|
| - StrictModeFlag strict_mode = kNonStrictMode;
|
| + StrictMode strict_mode = SLOPPY;
|
| if (args.length() == 5) {
|
| - CONVERT_STRICT_MODE_ARG_CHECKED(strict_mode_flag, 4);
|
| - strict_mode = strict_mode_flag;
|
| + CONVERT_STRICT_MODE_ARG_CHECKED(strict_mode_arg, 4);
|
| + strict_mode = strict_mode_arg;
|
| }
|
|
|
| Handle<Object> result = Runtime::SetObjectProperty(isolate, object, key,
|
| @@ -5552,7 +5545,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeleteProperty) {
|
| CONVERT_ARG_HANDLE_CHECKED(JSReceiver, object, 0);
|
| CONVERT_ARG_HANDLE_CHECKED(Name, key, 1);
|
| CONVERT_STRICT_MODE_ARG_CHECKED(strict_mode, 2);
|
| - JSReceiver::DeleteMode delete_mode = (strict_mode == kStrictMode)
|
| + JSReceiver::DeleteMode delete_mode = strict_mode == STRICT
|
| ? JSReceiver::STRICT_DELETION : JSReceiver::NORMAL_DELETION;
|
| Handle<Object> result = JSReceiver::DeleteProperty(object, key, delete_mode);
|
| RETURN_IF_EMPTY_HANDLE(isolate, result);
|
| @@ -5650,13 +5643,13 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_HasElement) {
|
|
|
|
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_IsPropertyEnumerable) {
|
| - SealHandleScope shs(isolate);
|
| + HandleScope scope(isolate);
|
| ASSERT(args.length() == 2);
|
|
|
| - CONVERT_ARG_CHECKED(JSObject, object, 0);
|
| - CONVERT_ARG_CHECKED(Name, key, 1);
|
| + CONVERT_ARG_HANDLE_CHECKED(JSObject, object, 0);
|
| + CONVERT_ARG_HANDLE_CHECKED(Name, key, 1);
|
|
|
| - PropertyAttributes att = object->GetLocalPropertyAttribute(key);
|
| + PropertyAttributes att = JSReceiver::GetLocalPropertyAttribute(object, key);
|
| if (att == ABSENT || (att & DONT_ENUM) != 0) {
|
| RETURN_IF_SCHEDULED_EXCEPTION(isolate);
|
| return isolate->heap()->false_value();
|
| @@ -5737,10 +5730,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetLocalPropertyNames) {
|
| if (obj->IsJSGlobalProxy()) {
|
| // Only collect names if access is permitted.
|
| if (obj->IsAccessCheckNeeded() &&
|
| - !isolate->MayNamedAccess(*obj,
|
| - isolate->heap()->undefined_value(),
|
| - v8::ACCESS_KEYS)) {
|
| - isolate->ReportFailedAccessCheck(*obj, v8::ACCESS_KEYS);
|
| + !isolate->MayNamedAccessWrapper(obj,
|
| + isolate->factory()->undefined_value(),
|
| + v8::ACCESS_KEYS)) {
|
| + isolate->ReportFailedAccessCheckWrapper(obj, v8::ACCESS_KEYS);
|
| RETURN_IF_SCHEDULED_EXCEPTION(isolate);
|
| return *isolate->factory()->NewJSArray(0);
|
| }
|
| @@ -5757,10 +5750,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetLocalPropertyNames) {
|
| for (int i = 0; i < length; i++) {
|
| // Only collect names if access is permitted.
|
| if (jsproto->IsAccessCheckNeeded() &&
|
| - !isolate->MayNamedAccess(*jsproto,
|
| - isolate->heap()->undefined_value(),
|
| - v8::ACCESS_KEYS)) {
|
| - isolate->ReportFailedAccessCheck(*jsproto, v8::ACCESS_KEYS);
|
| + !isolate->MayNamedAccessWrapper(jsproto,
|
| + isolate->factory()->undefined_value(),
|
| + v8::ACCESS_KEYS)) {
|
| + isolate->ReportFailedAccessCheckWrapper(jsproto, v8::ACCESS_KEYS);
|
| RETURN_IF_SCHEDULED_EXCEPTION(isolate);
|
| return *isolate->factory()->NewJSArray(0);
|
| }
|
| @@ -5804,7 +5797,9 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetLocalPropertyNames) {
|
| }
|
| }
|
| next_copy_index += local_property_count[i];
|
| - if (jsproto->HasHiddenProperties()) {
|
| +
|
| + // Hidden properties only show up if the filter does not skip strings.
|
| + if ((filter & STRING) == 0 && JSObject::HasHiddenProperties(jsproto)) {
|
| hidden_strings++;
|
| }
|
| if (i < length - 1) {
|
| @@ -5908,9 +5903,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_LocalKeys) {
|
| if (object->IsJSGlobalProxy()) {
|
| // Do access checks before going to the global object.
|
| if (object->IsAccessCheckNeeded() &&
|
| - !isolate->MayNamedAccess(*object, isolate->heap()->undefined_value(),
|
| - v8::ACCESS_KEYS)) {
|
| - isolate->ReportFailedAccessCheck(*object, v8::ACCESS_KEYS);
|
| + !isolate->MayNamedAccessWrapper(object,
|
| + isolate->factory()->undefined_value(),
|
| + v8::ACCESS_KEYS)) {
|
| + isolate->ReportFailedAccessCheckWrapper(object, v8::ACCESS_KEYS);
|
| RETURN_IF_SCHEDULED_EXCEPTION(isolate);
|
| return *isolate->factory()->NewJSArray(0);
|
| }
|
| @@ -5994,7 +5990,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetArgumentsProperty) {
|
| if (key->Equals(isolate->heap()->length_string())) return Smi::FromInt(n);
|
| if (key->Equals(isolate->heap()->callee_string())) {
|
| JSFunction* function = frame->function();
|
| - if (!function->shared()->is_classic_mode()) {
|
| + if (function->shared()->strict_mode() == STRICT) {
|
| return isolate->Throw(*isolate->factory()->NewTypeError(
|
| "strict_arguments_callee", HandleVector<Object>(NULL, 0)));
|
| }
|
| @@ -6245,38 +6241,27 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StringParseFloat) {
|
| template <class Converter>
|
| MUST_USE_RESULT static MaybeObject* ConvertCaseHelper(
|
| Isolate* isolate,
|
| - String* s,
|
| - String::Encoding result_encoding,
|
| - int length,
|
| - int input_string_length,
|
| + String* string,
|
| + SeqString* result,
|
| + int result_length,
|
| unibrow::Mapping<Converter, 128>* mapping) {
|
| + DisallowHeapAllocation no_gc;
|
| // We try this twice, once with the assumption that the result is no longer
|
| // than the input and, if that assumption breaks, again with the exact
|
| // length. This may not be pretty, but it is nicer than what was here before
|
| // and I hereby claim my vaffel-is.
|
| //
|
| - // Allocate the resulting string.
|
| - //
|
| // NOTE: This assumes that the upper/lower case of an ASCII
|
| // character is also ASCII. This is currently the case, but it
|
| // might break in the future if we implement more context and locale
|
| // dependent upper/lower conversions.
|
| - Object* o;
|
| - { MaybeObject* maybe_o = result_encoding == String::ONE_BYTE_ENCODING
|
| - ? isolate->heap()->AllocateRawOneByteString(length)
|
| - : isolate->heap()->AllocateRawTwoByteString(length);
|
| - if (!maybe_o->ToObject(&o)) return maybe_o;
|
| - }
|
| - String* result = String::cast(o);
|
| bool has_changed_character = false;
|
|
|
| - DisallowHeapAllocation no_gc;
|
| -
|
| // Convert all characters to upper case, assuming that they will fit
|
| // in the buffer
|
| Access<ConsStringIteratorOp> op(
|
| isolate->runtime_state()->string_iterator());
|
| - StringCharacterStream stream(s, op.value());
|
| + StringCharacterStream stream(string, op.value());
|
| unibrow::uchar chars[Converter::kMaxWidth];
|
| // We can assume that the string is not empty
|
| uc32 current = stream.GetNext();
|
| @@ -6284,7 +6269,7 @@ MUST_USE_RESULT static MaybeObject* ConvertCaseHelper(
|
| // when converting to uppercase.
|
| static const uc32 yuml_code = 0xff;
|
| bool ignore_yuml = result->IsSeqTwoByteString() || Converter::kIsToLower;
|
| - for (int i = 0; i < length;) {
|
| + for (int i = 0; i < result_length;) {
|
| bool has_next = stream.HasMore();
|
| uc32 next = has_next ? stream.GetNext() : 0;
|
| int char_length = mapping->get(current, next, chars);
|
| @@ -6298,7 +6283,7 @@ MUST_USE_RESULT static MaybeObject* ConvertCaseHelper(
|
| result->Set(i, chars[0]);
|
| has_changed_character = true;
|
| i++;
|
| - } else if (length == input_string_length) {
|
| + } else if (result_length == string->length()) {
|
| bool found_yuml = (current == yuml_code);
|
| // We've assumed that the result would be as long as the
|
| // input but here is a character that converts to several
|
| @@ -6352,7 +6337,7 @@ MUST_USE_RESULT static MaybeObject* ConvertCaseHelper(
|
| // we simple return the result and let the converted string
|
| // become garbage; there is no reason to keep two identical strings
|
| // alive.
|
| - return s;
|
| + return string;
|
| }
|
| }
|
|
|
| @@ -6383,7 +6368,7 @@ static inline uintptr_t AsciiRangeMask(uintptr_t w, char m, char n) {
|
|
|
| #ifdef DEBUG
|
| static bool CheckFastAsciiConvert(char* dst,
|
| - char* src,
|
| + const char* src,
|
| int length,
|
| bool changed,
|
| bool is_to_lower) {
|
| @@ -6406,12 +6391,12 @@ static bool CheckFastAsciiConvert(char* dst,
|
|
|
| template<class Converter>
|
| static bool FastAsciiConvert(char* dst,
|
| - char* src,
|
| + const char* src,
|
| int length,
|
| bool* changed_out) {
|
| #ifdef DEBUG
|
| char* saved_dst = dst;
|
| - char* saved_src = src;
|
| + const char* saved_src = src;
|
| #endif
|
| DisallowHeapAllocation no_gc;
|
| // We rely on the distance between upper and lower case letters
|
| @@ -6422,12 +6407,12 @@ static bool FastAsciiConvert(char* dst,
|
| static const char hi = Converter::kIsToLower ? 'Z' + 1 : 'z' + 1;
|
| bool changed = false;
|
| uintptr_t or_acc = 0;
|
| - char* const limit = src + length;
|
| + const char* const limit = src + length;
|
| #ifdef V8_HOST_CAN_READ_UNALIGNED
|
| // Process the prefix of the input that requires no conversion one
|
| // (machine) word at a time.
|
| while (src <= limit - sizeof(uintptr_t)) {
|
| - uintptr_t w = *reinterpret_cast<uintptr_t*>(src);
|
| + const uintptr_t w = *reinterpret_cast<const uintptr_t*>(src);
|
| or_acc |= w;
|
| if (AsciiRangeMask(w, lo, hi) != 0) {
|
| changed = true;
|
| @@ -6440,7 +6425,7 @@ static bool FastAsciiConvert(char* dst,
|
| // Process the remainder of the input performing conversion when
|
| // required one word at a time.
|
| while (src <= limit - sizeof(uintptr_t)) {
|
| - uintptr_t w = *reinterpret_cast<uintptr_t*>(src);
|
| + const uintptr_t w = *reinterpret_cast<const uintptr_t*>(src);
|
| or_acc |= w;
|
| uintptr_t m = AsciiRangeMask(w, lo, hi);
|
| // The mask has high (7th) bit set in every byte that needs
|
| @@ -6483,13 +6468,12 @@ MUST_USE_RESULT static MaybeObject* ConvertCase(
|
| Arguments args,
|
| Isolate* isolate,
|
| unibrow::Mapping<Converter, 128>* mapping) {
|
| - SealHandleScope shs(isolate);
|
| - CONVERT_ARG_CHECKED(String, s, 0);
|
| - s = s->TryFlattenGetString();
|
| -
|
| - const int length = s->length();
|
| + HandleScope handle_scope(isolate);
|
| + CONVERT_ARG_HANDLE_CHECKED(String, s, 0);
|
| + s = FlattenGetString(s);
|
| + int length = s->length();
|
| // Assume that the string is not empty; we need this assumption later
|
| - if (length == 0) return s;
|
| + if (length == 0) return *s;
|
|
|
| // Simpler handling of ASCII strings.
|
| //
|
| @@ -6497,42 +6481,43 @@ MUST_USE_RESULT static MaybeObject* ConvertCase(
|
| // character is also ASCII. This is currently the case, but it
|
| // might break in the future if we implement more context and locale
|
| // dependent upper/lower conversions.
|
| - if (s->IsSeqOneByteString()) {
|
| - Object* o;
|
| - { MaybeObject* maybe_o = isolate->heap()->AllocateRawOneByteString(length);
|
| - if (!maybe_o->ToObject(&o)) return maybe_o;
|
| - }
|
| - SeqOneByteString* result = SeqOneByteString::cast(o);
|
| + if (s->IsOneByteRepresentationUnderneath()) {
|
| + Handle<SeqOneByteString> result =
|
| + isolate->factory()->NewRawOneByteString(length);
|
| +
|
| + DisallowHeapAllocation no_gc;
|
| + String::FlatContent flat_content = s->GetFlatContent();
|
| + ASSERT(flat_content.IsFlat());
|
| bool has_changed_character = false;
|
| bool is_ascii = FastAsciiConvert<Converter>(
|
| reinterpret_cast<char*>(result->GetChars()),
|
| - reinterpret_cast<char*>(SeqOneByteString::cast(s)->GetChars()),
|
| + reinterpret_cast<const char*>(flat_content.ToOneByteVector().start()),
|
| length,
|
| &has_changed_character);
|
| // If not ASCII, we discard the result and take the 2 byte path.
|
| - if (is_ascii) {
|
| - return has_changed_character ? result : s;
|
| - }
|
| + if (is_ascii) return has_changed_character ? *result : *s;
|
| }
|
|
|
| - String::Encoding result_encoding = s->IsOneByteRepresentation()
|
| - ? String::ONE_BYTE_ENCODING : String::TWO_BYTE_ENCODING;
|
| - Object* answer;
|
| - { MaybeObject* maybe_answer = ConvertCaseHelper(
|
| - isolate, s, result_encoding, length, length, mapping);
|
| - if (!maybe_answer->ToObject(&answer)) return maybe_answer;
|
| + Handle<SeqString> result;
|
| + if (s->IsOneByteRepresentation()) {
|
| + result = isolate->factory()->NewRawOneByteString(length);
|
| + } else {
|
| + result = isolate->factory()->NewRawTwoByteString(length);
|
| }
|
| - if (answer->IsSmi()) {
|
| - int new_length = Smi::cast(answer)->value();
|
| - if (new_length < 0) {
|
| - result_encoding = String::TWO_BYTE_ENCODING;
|
| - new_length = -new_length;
|
| - }
|
| - MaybeObject* maybe_answer = ConvertCaseHelper(
|
| - isolate, s, result_encoding, new_length, length, mapping);
|
| - if (!maybe_answer->ToObject(&answer)) return maybe_answer;
|
| + MaybeObject* maybe = ConvertCaseHelper(isolate, *s, *result, length, mapping);
|
| + Object* answer;
|
| + if (!maybe->ToObject(&answer)) return maybe;
|
| + if (answer->IsString()) return answer;
|
| +
|
| + ASSERT(answer->IsSmi());
|
| + length = Smi::cast(answer)->value();
|
| + if (s->IsOneByteRepresentation() && length > 0) {
|
| + result = isolate->factory()->NewRawOneByteString(length);
|
| + } else {
|
| + if (length < 0) length = -length;
|
| + result = isolate->factory()->NewRawTwoByteString(length);
|
| }
|
| - return answer;
|
| + return ConvertCaseHelper(isolate, *s, *result, length, mapping);
|
| }
|
|
|
|
|
| @@ -7670,94 +7655,32 @@ RUNTIME_UNARY_MATH(log)
|
| #undef RUNTIME_UNARY_MATH
|
|
|
|
|
| -// Cube root approximation, refer to: http://metamerist.com/cbrt/cbrt.htm
|
| -// Using initial approximation adapted from Kahan's cbrt and 4 iterations
|
| -// of Newton's method.
|
| -inline double CubeRootNewtonIteration(double approx, double x) {
|
| - return (1.0 / 3.0) * (x / (approx * approx) + 2 * approx);
|
| -}
|
| -
|
| -
|
| -inline double CubeRoot(double x) {
|
| - static const uint64_t magic = V8_2PART_UINT64_C(0x2A9F7893, 00000000);
|
| - uint64_t xhigh = double_to_uint64(x);
|
| - double approx = uint64_to_double(xhigh / 3 + magic);
|
| -
|
| - approx = CubeRootNewtonIteration(approx, x);
|
| - approx = CubeRootNewtonIteration(approx, x);
|
| - approx = CubeRootNewtonIteration(approx, x);
|
| - return CubeRootNewtonIteration(approx, x);
|
| -}
|
| -
|
| -
|
| -RUNTIME_FUNCTION(MaybeObject*, Runtime_Math_cbrt) {
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_DoubleHi) {
|
| SealHandleScope shs(isolate);
|
| ASSERT(args.length() == 1);
|
| CONVERT_DOUBLE_ARG_CHECKED(x, 0);
|
| - if (x == 0 || std::isinf(x)) return args[0];
|
| - double result = (x > 0) ? CubeRoot(x) : -CubeRoot(-x);
|
| - return isolate->heap()->AllocateHeapNumber(result);
|
| + uint64_t integer = double_to_uint64(x);
|
| + integer = (integer >> 32) & 0xFFFFFFFFu;
|
| + return isolate->heap()->NumberFromDouble(static_cast<int32_t>(integer));
|
| }
|
|
|
|
|
| -RUNTIME_FUNCTION(MaybeObject*, Runtime_Math_log1p) {
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_DoubleLo) {
|
| SealHandleScope shs(isolate);
|
| ASSERT(args.length() == 1);
|
| CONVERT_DOUBLE_ARG_CHECKED(x, 0);
|
| -
|
| - double x_abs = std::fabs(x);
|
| - // Use Taylor series to approximate. With y = x + 1;
|
| - // log(y) at 1 == log(1) + log'(1)(y-1)/1! + log''(1)(y-1)^2/2! + ...
|
| - // == 0 + x - x^2/2 + x^3/3 ...
|
| - // The closer x is to 0, the fewer terms are required.
|
| - static const double threshold_2 = 1.0 / 0x00800000;
|
| - static const double threshold_3 = 1.0 / 0x00008000;
|
| - static const double threshold_7 = 1.0 / 0x00000080;
|
| -
|
| - double result;
|
| - if (x_abs < threshold_2) {
|
| - result = x * (1.0/1.0 - x * 1.0/2.0);
|
| - } else if (x_abs < threshold_3) {
|
| - result = x * (1.0/1.0 - x * (1.0/2.0 - x * (1.0/3.0)));
|
| - } else if (x_abs < threshold_7) {
|
| - result = x * (1.0/1.0 - x * (1.0/2.0 - x * (
|
| - 1.0/3.0 - x * (1.0/4.0 - x * (
|
| - 1.0/5.0 - x * (1.0/6.0 - x * (
|
| - 1.0/7.0)))))));
|
| - } else { // Use regular log if not close enough to 0.
|
| - result = std::log(1.0 + x);
|
| - }
|
| - return isolate->heap()->AllocateHeapNumber(result);
|
| + return isolate->heap()->NumberFromDouble(
|
| + static_cast<int32_t>(double_to_uint64(x) & 0xFFFFFFFFu));
|
| }
|
|
|
|
|
| -RUNTIME_FUNCTION(MaybeObject*, Runtime_Math_expm1) {
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_ConstructDouble) {
|
| SealHandleScope shs(isolate);
|
| - ASSERT(args.length() == 1);
|
| - CONVERT_DOUBLE_ARG_CHECKED(x, 0);
|
| -
|
| - double x_abs = std::fabs(x);
|
| - // Use Taylor series to approximate.
|
| - // exp(x) - 1 at 0 == -1 + exp(0) + exp'(0)*x/1! + exp''(0)*x^2/2! + ...
|
| - // == x/1! + x^2/2! + x^3/3! + ...
|
| - // The closer x is to 0, the fewer terms are required.
|
| - static const double threshold_2 = 1.0 / 0x00400000;
|
| - static const double threshold_3 = 1.0 / 0x00004000;
|
| - static const double threshold_6 = 1.0 / 0x00000040;
|
| -
|
| - double result;
|
| - if (x_abs < threshold_2) {
|
| - result = x * (1.0/1.0 + x * (1.0/2.0));
|
| - } else if (x_abs < threshold_3) {
|
| - result = x * (1.0/1.0 + x * (1.0/2.0 + x * (1.0/6.0)));
|
| - } else if (x_abs < threshold_6) {
|
| - result = x * (1.0/1.0 + x * (1.0/2.0 + x * (
|
| - 1.0/6.0 + x * (1.0/24.0 + x * (
|
| - 1.0/120.0 + x * (1.0/720.0))))));
|
| - } else { // Use regular exp if not close enough to 0.
|
| - result = std::exp(x) - 1.0;
|
| - }
|
| - return isolate->heap()->AllocateHeapNumber(result);
|
| + ASSERT(args.length() == 2);
|
| + CONVERT_NUMBER_CHECKED(uint32_t, hi, Uint32, args[0]);
|
| + CONVERT_NUMBER_CHECKED(uint32_t, lo, Uint32, args[1]);
|
| + uint64_t result = (static_cast<uint64_t>(hi) << 32) | lo;
|
| + return isolate->heap()->AllocateHeapNumber(uint64_to_double(result));
|
| }
|
|
|
|
|
| @@ -7979,11 +7902,11 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_NewArgumentsFast) {
|
| Handle<FixedArray> parameter_map =
|
| isolate->factory()->NewFixedArray(mapped_count + 2, NOT_TENURED);
|
| parameter_map->set_map(
|
| - isolate->heap()->non_strict_arguments_elements_map());
|
| + isolate->heap()->sloppy_arguments_elements_map());
|
|
|
| Handle<Map> old_map(result->map());
|
| Handle<Map> new_map = isolate->factory()->CopyMap(old_map);
|
| - new_map->set_elements_kind(NON_STRICT_ARGUMENTS_ELEMENTS);
|
| + new_map->set_elements_kind(SLOPPY_ARGUMENTS_ELEMENTS);
|
|
|
| result->set_map(*new_map);
|
| result->set_elements(*parameter_map);
|
| @@ -8555,10 +8478,10 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_ClearFunctionTypeFeedback) {
|
| HandleScope scope(isolate);
|
| ASSERT(args.length() == 1);
|
| CONVERT_ARG_HANDLE_CHECKED(JSFunction, function, 0);
|
| + function->shared()->ClearTypeFeedbackInfo(isolate->heap());
|
| Code* unoptimized = function->shared()->code();
|
| if (unoptimized->kind() == Code::FUNCTION) {
|
| unoptimized->ClearInlineCaches();
|
| - unoptimized->ClearTypeFeedbackInfo(isolate->heap());
|
| }
|
| return isolate->heap()->undefined_value();
|
| }
|
| @@ -8800,7 +8723,9 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CompileForOnStackReplacement) {
|
| PrintF(" at AST id %d]\n", ast_id.ToInt());
|
| }
|
|
|
| - function->ReplaceCode(function->shared()->code());
|
| + if (!function->IsOptimized()) {
|
| + function->ReplaceCode(function->shared()->code());
|
| + }
|
| return NULL;
|
| }
|
|
|
| @@ -9114,7 +9039,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareModules) {
|
| case VAR:
|
| case LET:
|
| case CONST:
|
| - case CONST_HARMONY: {
|
| + case CONST_LEGACY: {
|
| PropertyAttributes attr =
|
| IsImmutableVariableMode(mode) ? FROZEN : SEALED;
|
| Handle<AccessorInfo> info =
|
| @@ -9127,7 +9052,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DeclareModules) {
|
| case MODULE: {
|
| Object* referenced_context = Context::cast(host_context)->get(index);
|
| Handle<JSModule> value(Context::cast(referenced_context)->module());
|
| - JSReceiver::SetProperty(module, name, value, FROZEN, kStrictMode);
|
| + JSReceiver::SetProperty(module, name, value, FROZEN, STRICT);
|
| break;
|
| }
|
| case INTERNAL:
|
| @@ -9350,9 +9275,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StoreContextSlot) {
|
| Handle<Object> value(args[0], isolate);
|
| CONVERT_ARG_HANDLE_CHECKED(Context, context, 1);
|
| CONVERT_ARG_HANDLE_CHECKED(String, name, 2);
|
| - CONVERT_LANGUAGE_MODE_ARG(language_mode, 3);
|
| - StrictModeFlag strict_mode = (language_mode == CLASSIC_MODE)
|
| - ? kNonStrictMode : kStrictMode;
|
| + CONVERT_STRICT_MODE_ARG_CHECKED(strict_mode, 3);
|
|
|
| int index;
|
| PropertyAttributes attributes;
|
| @@ -9379,7 +9302,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StoreContextSlot) {
|
| if ((attributes & READ_ONLY) == 0) {
|
| // Context is a fixed array and set cannot fail.
|
| context->set(index, *value);
|
| - } else if (strict_mode == kStrictMode) {
|
| + } else if (strict_mode == STRICT) {
|
| // Setting read only property in strict mode.
|
| Handle<Object> error =
|
| isolate->factory()->NewTypeError("strict_cannot_assign",
|
| @@ -9401,25 +9324,25 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StoreContextSlot) {
|
| // The property was not found.
|
| ASSERT(attributes == ABSENT);
|
|
|
| - if (strict_mode == kStrictMode) {
|
| + if (strict_mode == STRICT) {
|
| // Throw in strict mode (assignment to undefined variable).
|
| Handle<Object> error =
|
| isolate->factory()->NewReferenceError(
|
| "not_defined", HandleVector(&name, 1));
|
| return isolate->Throw(*error);
|
| }
|
| - // In non-strict mode, the property is added to the global object.
|
| + // In sloppy mode, the property is added to the global object.
|
| attributes = NONE;
|
| object = Handle<JSReceiver>(isolate->context()->global_object());
|
| }
|
|
|
| // Set the property if it's not read only or doesn't yet exist.
|
| if ((attributes & READ_ONLY) == 0 ||
|
| - (object->GetLocalPropertyAttribute(*name) == ABSENT)) {
|
| + (JSReceiver::GetLocalPropertyAttribute(object, name) == ABSENT)) {
|
| RETURN_IF_EMPTY_HANDLE(
|
| isolate,
|
| JSReceiver::SetProperty(object, name, value, NONE, strict_mode));
|
| - } else if (strict_mode == kStrictMode && (attributes & READ_ONLY) != 0) {
|
| + } else if (strict_mode == STRICT && (attributes & READ_ONLY) != 0) {
|
| // Setting read only property in strict mode.
|
| Handle<Object> error =
|
| isolate->factory()->NewTypeError(
|
| @@ -9660,8 +9583,8 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DateLocalTimezone) {
|
| ASSERT(args.length() == 1);
|
|
|
| CONVERT_DOUBLE_ARG_CHECKED(x, 0);
|
| - int64_t time = isolate->date_cache()->EquivalentTime(static_cast<int64_t>(x));
|
| - const char* zone = OS::LocalTimezone(static_cast<double>(time));
|
| + const char* zone =
|
| + isolate->date_cache()->LocalTimezone(static_cast<int64_t>(x));
|
| return isolate->heap()->AllocateStringFromUtf8(CStrVector(zone));
|
| }
|
|
|
| @@ -9677,6 +9600,28 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DateToUTC) {
|
| }
|
|
|
|
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_DateCacheVersion) {
|
| + HandleScope hs(isolate);
|
| + ASSERT(args.length() == 0);
|
| + if (!isolate->eternal_handles()->Exists(EternalHandles::DATE_CACHE_VERSION)) {
|
| + Handle<FixedArray> date_cache_version =
|
| + isolate->factory()->NewFixedArray(1, TENURED);
|
| + date_cache_version->set(0, Smi::FromInt(0));
|
| + isolate->eternal_handles()->CreateSingleton(
|
| + isolate, *date_cache_version, EternalHandles::DATE_CACHE_VERSION);
|
| + }
|
| + Handle<FixedArray> date_cache_version =
|
| + Handle<FixedArray>::cast(isolate->eternal_handles()->GetSingleton(
|
| + EternalHandles::DATE_CACHE_VERSION));
|
| + // Return result as a JS array.
|
| + Handle<JSObject> result =
|
| + isolate->factory()->NewJSObject(isolate->array_function());
|
| + isolate->factory()->SetContent(Handle<JSArray>::cast(result),
|
| + date_cache_version);
|
| + return *result;
|
| +}
|
| +
|
| +
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_GlobalReceiver) {
|
| SealHandleScope shs(isolate);
|
| ASSERT(args.length() == 1);
|
| @@ -9758,7 +9703,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CompileString) {
|
| ParseRestriction restriction = function_literal_only
|
| ? ONLY_SINGLE_FUNCTION_LITERAL : NO_PARSE_RESTRICTION;
|
| Handle<JSFunction> fun = Compiler::GetFunctionFromEval(
|
| - source, context, CLASSIC_MODE, restriction, RelocInfo::kNoPosition);
|
| + source, context, SLOPPY, restriction, RelocInfo::kNoPosition);
|
| RETURN_IF_EMPTY_HANDLE(isolate, fun);
|
| return *fun;
|
| }
|
| @@ -9767,7 +9712,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_CompileString) {
|
| static ObjectPair CompileGlobalEval(Isolate* isolate,
|
| Handle<String> source,
|
| Handle<Object> receiver,
|
| - LanguageMode language_mode,
|
| + StrictMode strict_mode,
|
| int scope_position) {
|
| Handle<Context> context = Handle<Context>(isolate->context());
|
| Handle<Context> native_context = Handle<Context>(context->native_context());
|
| @@ -9787,7 +9732,7 @@ static ObjectPair CompileGlobalEval(Isolate* isolate,
|
| // and return the compiled function bound in the local context.
|
| static const ParseRestriction restriction = NO_PARSE_RESTRICTION;
|
| Handle<JSFunction> compiled = Compiler::GetFunctionFromEval(
|
| - source, context, language_mode, restriction, scope_position);
|
| + source, context, strict_mode, restriction, scope_position);
|
| RETURN_IF_EMPTY_HANDLE_VALUE(isolate, compiled,
|
| MakePair(Failure::Exception(), NULL));
|
| return MakePair(*compiled, *receiver);
|
| @@ -9810,12 +9755,14 @@ RUNTIME_FUNCTION(ObjectPair, Runtime_ResolvePossiblyDirectEval) {
|
| return MakePair(*callee, isolate->heap()->undefined_value());
|
| }
|
|
|
| - CONVERT_LANGUAGE_MODE_ARG(language_mode, 3);
|
| + ASSERT(args[3]->IsSmi());
|
| + ASSERT(args.smi_at(3) == SLOPPY || args.smi_at(3) == STRICT);
|
| + StrictMode strict_mode = static_cast<StrictMode>(args.smi_at(3));
|
| ASSERT(args[4]->IsSmi());
|
| return CompileGlobalEval(isolate,
|
| args.at<String>(1),
|
| args.at<Object>(2),
|
| - language_mode,
|
| + strict_mode,
|
| args.smi_at(4));
|
| }
|
|
|
| @@ -9880,7 +9827,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_PushIfAbsent) {
|
| // Strict not needed. Used for cycle detection in Array join implementation.
|
| RETURN_IF_EMPTY_HANDLE(isolate, JSObject::SetFastElement(array, length,
|
| element,
|
| - kNonStrictMode,
|
| + SLOPPY,
|
| true));
|
| return isolate->heap()->true_value();
|
| }
|
| @@ -10065,7 +10012,7 @@ static uint32_t EstimateElementCount(Handle<JSArray> array) {
|
| }
|
| break;
|
| }
|
| - case NON_STRICT_ARGUMENTS_ELEMENTS:
|
| + case SLOPPY_ARGUMENTS_ELEMENTS:
|
| #define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
|
| case EXTERNAL_##TYPE##_ELEMENTS: \
|
| case TYPE##_ELEMENTS: \
|
| @@ -10564,6 +10511,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GlobalPrint) {
|
| // and are followed by non-existing element. Does not change the length
|
| // property.
|
| // Returns the number of non-undefined elements collected.
|
| +// Returns -1 if hole removal is not supported by this method.
|
| RUNTIME_FUNCTION(MaybeObject*, Runtime_RemoveArrayHoles) {
|
| HandleScope scope(isolate);
|
| ASSERT(args.length() == 2);
|
| @@ -11352,7 +11300,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetFrameDetails) {
|
| // THE FRAME ITERATOR TO WRAP THE RECEIVER.
|
| Handle<Object> receiver(it.frame()->receiver(), isolate);
|
| if (!receiver->IsJSObject() &&
|
| - shared->is_classic_mode() &&
|
| + shared->strict_mode() == SLOPPY &&
|
| !function->IsBuiltin()) {
|
| // If the receiver is not a JSObject and the function is not a
|
| // builtin or strict-mode we have hit an optimization where a
|
| @@ -11404,8 +11352,7 @@ static Handle<JSObject> MaterializeStackLocalsWithFrameInspector(
|
|
|
| RETURN_IF_EMPTY_HANDLE_VALUE(
|
| isolate,
|
| - Runtime::SetObjectProperty(
|
| - isolate, target, name, value, NONE, kNonStrictMode),
|
| + Runtime::SetObjectProperty(isolate, target, name, value, NONE, SLOPPY),
|
| Handle<JSObject>());
|
| }
|
|
|
| @@ -11417,8 +11364,7 @@ static Handle<JSObject> MaterializeStackLocalsWithFrameInspector(
|
|
|
| RETURN_IF_EMPTY_HANDLE_VALUE(
|
| isolate,
|
| - Runtime::SetObjectProperty(
|
| - isolate, target, name, value, NONE, kNonStrictMode),
|
| + Runtime::SetObjectProperty(isolate, target, name, value, NONE, SLOPPY),
|
| Handle<JSObject>());
|
| }
|
|
|
| @@ -11501,7 +11447,7 @@ static Handle<JSObject> MaterializeLocalContext(Isolate* isolate,
|
| key,
|
| GetProperty(isolate, ext, key),
|
| NONE,
|
| - kNonStrictMode),
|
| + SLOPPY),
|
| Handle<JSObject>());
|
| }
|
| }
|
| @@ -11602,8 +11548,7 @@ static bool SetLocalVariableValue(Isolate* isolate,
|
| // We don't expect this to do anything except replacing
|
| // property value.
|
| Runtime::SetObjectProperty(isolate, ext, variable_name, new_value,
|
| - NONE,
|
| - kNonStrictMode);
|
| + NONE, SLOPPY);
|
| return true;
|
| }
|
| }
|
| @@ -11651,8 +11596,7 @@ static Handle<JSObject> MaterializeClosure(Isolate* isolate,
|
| isolate,
|
| Runtime::SetObjectProperty(isolate, closure_scope, key,
|
| GetProperty(isolate, ext, key),
|
| - NONE,
|
| - kNonStrictMode),
|
| + NONE, SLOPPY),
|
| Handle<JSObject>());
|
| }
|
| }
|
| @@ -11684,8 +11628,7 @@ static bool SetClosureVariableValue(Isolate* isolate,
|
| if (JSReceiver::HasProperty(ext, variable_name)) {
|
| // We don't expect this to do anything except replacing property value.
|
| Runtime::SetObjectProperty(isolate, ext, variable_name, new_value,
|
| - NONE,
|
| - kNonStrictMode);
|
| + NONE, SLOPPY);
|
| return true;
|
| }
|
| }
|
| @@ -11707,8 +11650,7 @@ static Handle<JSObject> MaterializeCatchScope(Isolate* isolate,
|
| RETURN_IF_EMPTY_HANDLE_VALUE(
|
| isolate,
|
| Runtime::SetObjectProperty(isolate, catch_scope, name, thrown_object,
|
| - NONE,
|
| - kNonStrictMode),
|
| + NONE, SLOPPY),
|
| Handle<JSObject>());
|
| return catch_scope;
|
| }
|
| @@ -12221,7 +12163,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetStepInPositions) {
|
| Smi* position_value = Smi::FromInt(break_location_iterator.position());
|
| JSObject::SetElement(array, len,
|
| Handle<Object>(position_value, isolate),
|
| - NONE, kNonStrictMode);
|
| + NONE, SLOPPY);
|
| len++;
|
| }
|
| }
|
| @@ -12241,7 +12183,7 @@ static const int kScopeDetailsObjectIndex = 1;
|
| static const int kScopeDetailsSize = 2;
|
|
|
|
|
| -static MaybeObject* MaterializeScopeDetails(Isolate* isolate,
|
| +static Handle<JSObject> MaterializeScopeDetails(Isolate* isolate,
|
| ScopeIterator* it) {
|
| // Calculate the size of the result.
|
| int details_size = kScopeDetailsSize;
|
| @@ -12250,10 +12192,10 @@ static MaybeObject* MaterializeScopeDetails(Isolate* isolate,
|
| // Fill in scope details.
|
| details->set(kScopeDetailsTypeIndex, Smi::FromInt(it->Type()));
|
| Handle<JSObject> scope_object = it->ScopeObject();
|
| - RETURN_IF_EMPTY_HANDLE(isolate, scope_object);
|
| + RETURN_IF_EMPTY_HANDLE_VALUE(isolate, scope_object, Handle<JSObject>());
|
| details->set(kScopeDetailsObjectIndex, *scope_object);
|
|
|
| - return *isolate->factory()->NewJSArrayWithElements(details);
|
| + return isolate->factory()->NewJSArrayWithElements(details);
|
| }
|
|
|
|
|
| @@ -12294,7 +12236,51 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetScopeDetails) {
|
| if (it.Done()) {
|
| return isolate->heap()->undefined_value();
|
| }
|
| - return MaterializeScopeDetails(isolate, &it);
|
| + Handle<JSObject> details = MaterializeScopeDetails(isolate, &it);
|
| + RETURN_IF_EMPTY_HANDLE(isolate, details);
|
| + return *details;
|
| +}
|
| +
|
| +
|
| +// Return an array of scope details
|
| +// args[0]: number: break id
|
| +// args[1]: number: frame index
|
| +// args[2]: number: inlined frame index
|
| +//
|
| +// The array returned contains arrays with the following information:
|
| +// 0: Scope type
|
| +// 1: Scope object
|
| +RUNTIME_FUNCTION(MaybeObject*, Runtime_GetAllScopesDetails) {
|
| + HandleScope scope(isolate);
|
| + ASSERT(args.length() == 3);
|
| +
|
| + // Check arguments.
|
| + Object* check;
|
| + { MaybeObject* maybe_check = Runtime_CheckExecutionState(
|
| + RUNTIME_ARGUMENTS(isolate, args));
|
| + if (!maybe_check->ToObject(&check)) return maybe_check;
|
| + }
|
| + CONVERT_SMI_ARG_CHECKED(wrapped_id, 1);
|
| + CONVERT_NUMBER_CHECKED(int, inlined_jsframe_index, Int32, args[2]);
|
| +
|
| + // Get the frame where the debugging is performed.
|
| + StackFrame::Id id = UnwrapFrameId(wrapped_id);
|
| + JavaScriptFrameIterator frame_it(isolate, id);
|
| + JavaScriptFrame* frame = frame_it.frame();
|
| +
|
| + List<Handle<JSObject> > result(4);
|
| + ScopeIterator it(isolate, frame, inlined_jsframe_index);
|
| + for (; !it.Done(); it.Next()) {
|
| + Handle<JSObject> details = MaterializeScopeDetails(isolate, &it);
|
| + RETURN_IF_EMPTY_HANDLE(isolate, details);
|
| + result.Add(details);
|
| + }
|
| +
|
| + Handle<FixedArray> array = isolate->factory()->NewFixedArray(result.length());
|
| + for (int i = 0; i < result.length(); ++i) {
|
| + array->set(i, *result[i]);
|
| + }
|
| + return *isolate->factory()->NewJSArrayWithElements(array);
|
| }
|
|
|
|
|
| @@ -12333,7 +12319,9 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_GetFunctionScopeDetails) {
|
| return isolate->heap()->undefined_value();
|
| }
|
|
|
| - return MaterializeScopeDetails(isolate, &it);
|
| + Handle<JSObject> details = MaterializeScopeDetails(isolate, &it);
|
| + RETURN_IF_EMPTY_HANDLE(isolate, details);
|
| + return *details;
|
| }
|
|
|
|
|
| @@ -12730,7 +12718,7 @@ static Handle<JSObject> MaterializeArgumentsObject(
|
| isolate->factory()->arguments_string(),
|
| arguments,
|
| ::NONE,
|
| - kNonStrictMode);
|
| + SLOPPY);
|
| return target;
|
| }
|
|
|
| @@ -12750,7 +12738,7 @@ static MaybeObject* DebugEvaluate(Isolate* isolate,
|
| Handle<JSFunction> eval_fun =
|
| Compiler::GetFunctionFromEval(source,
|
| context,
|
| - CLASSIC_MODE,
|
| + SLOPPY,
|
| NO_PARSE_RESTRICTION,
|
| RelocInfo::kNoPosition);
|
| RETURN_IF_EMPTY_HANDLE(isolate, eval_fun);
|
| @@ -13008,7 +12996,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_DebugReferencedBy) {
|
|
|
| // Get the constructor function for context extension and arguments array.
|
| JSObject* arguments_boilerplate =
|
| - isolate->context()->native_context()->arguments_boilerplate();
|
| + isolate->context()->native_context()->sloppy_arguments_boilerplate();
|
| JSFunction* arguments_function =
|
| JSFunction::cast(arguments_boilerplate->map()->constructor());
|
|
|
| @@ -14528,8 +14516,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_ListNatives) {
|
| #define COUNT_ENTRY(Name, argc, ressize) + 1
|
| int entry_count = 0
|
| RUNTIME_FUNCTION_LIST(COUNT_ENTRY)
|
| - INLINE_FUNCTION_LIST(COUNT_ENTRY)
|
| - INLINE_RUNTIME_FUNCTION_LIST(COUNT_ENTRY);
|
| + INLINE_FUNCTION_LIST(COUNT_ENTRY);
|
| #undef COUNT_ENTRY
|
| Factory* factory = isolate->factory();
|
| Handle<FixedArray> elements = factory->NewFixedArray(entry_count);
|
| @@ -14557,7 +14544,6 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_ListNatives) {
|
| RUNTIME_FUNCTION_LIST(ADD_ENTRY)
|
| inline_runtime_functions = true;
|
| INLINE_FUNCTION_LIST(ADD_ENTRY)
|
| - INLINE_RUNTIME_FUNCTION_LIST(ADD_ENTRY)
|
| #undef ADD_ENTRY
|
| ASSERT_EQ(index, entry_count);
|
| Handle<JSArray> result = factory->NewJSArrayWithElements(elements);
|
| @@ -14598,7 +14584,7 @@ ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(FastSmiOrObjectElements)
|
| ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(FastDoubleElements)
|
| ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(FastHoleyElements)
|
| ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(DictionaryElements)
|
| -ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(NonStrictArgumentsElements)
|
| +ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(SloppyArgumentsElements)
|
| ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(ExternalArrayElements)
|
| // Properties test sitting with elements tests - not fooling anyone.
|
| ELEMENTS_KIND_CHECK_RUNTIME_FUNCTION(FastProperties)
|
| @@ -14735,12 +14721,13 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_IsAccessAllowedForObserver) {
|
| ASSERT(args.length() == 3);
|
| CONVERT_ARG_HANDLE_CHECKED(JSFunction, observer, 0);
|
| CONVERT_ARG_HANDLE_CHECKED(JSObject, object, 1);
|
| - ASSERT(object->IsAccessCheckNeeded());
|
| + ASSERT(object->map()->is_access_check_needed());
|
| Handle<Object> key = args.at<Object>(2);
|
| SaveContext save(isolate);
|
| isolate->set_context(observer->context());
|
| - if (!isolate->MayNamedAccess(*object, isolate->heap()->undefined_value(),
|
| - v8::ACCESS_KEYS)) {
|
| + if (!isolate->MayNamedAccessWrapper(object,
|
| + isolate->factory()->undefined_value(),
|
| + v8::ACCESS_KEYS)) {
|
| return isolate->heap()->false_value();
|
| }
|
| bool access_allowed = false;
|
| @@ -14748,11 +14735,12 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_IsAccessAllowedForObserver) {
|
| if (key->ToArrayIndex(&index) ||
|
| (key->IsString() && String::cast(*key)->AsArrayIndex(&index))) {
|
| access_allowed =
|
| - isolate->MayIndexedAccess(*object, index, v8::ACCESS_GET) &&
|
| - isolate->MayIndexedAccess(*object, index, v8::ACCESS_HAS);
|
| + isolate->MayIndexedAccessWrapper(object, index, v8::ACCESS_GET) &&
|
| + isolate->MayIndexedAccessWrapper(object, index, v8::ACCESS_HAS);
|
| } else {
|
| - access_allowed = isolate->MayNamedAccess(*object, *key, v8::ACCESS_GET) &&
|
| - isolate->MayNamedAccess(*object, *key, v8::ACCESS_HAS);
|
| + access_allowed =
|
| + isolate->MayNamedAccessWrapper(object, key, v8::ACCESS_GET) &&
|
| + isolate->MayNamedAccessWrapper(object, key, v8::ACCESS_HAS);
|
| }
|
| return isolate->heap()->ToBoolean(access_allowed);
|
| }
|
| @@ -14790,8 +14778,26 @@ static MaybeObject* ArrayConstructorCommon(Isolate* isolate,
|
| site->SetElementsKind(to_kind);
|
| }
|
|
|
| - maybe_array = isolate->heap()->AllocateJSObjectWithAllocationSite(
|
| - *constructor, site);
|
| + // We should allocate with an initial map that reflects the allocation site
|
| + // advice. Therefore we use AllocateJSObjectFromMap instead of passing
|
| + // the constructor.
|
| + Map* initial_map = constructor->initial_map();
|
| + if (to_kind != initial_map->elements_kind()) {
|
| + MaybeObject* maybe_new_map = initial_map->AsElementsKind(to_kind);
|
| + if (!maybe_new_map->To(&initial_map)) return maybe_new_map;
|
| + }
|
| +
|
| + // If we don't care to track arrays of to_kind ElementsKind, then
|
| + // don't emit a memento for them.
|
| + AllocationSite* allocation_site =
|
| + (AllocationSite::GetMode(to_kind) == TRACK_ALLOCATION_SITE)
|
| + ? *site
|
| + : NULL;
|
| +
|
| + maybe_array = isolate->heap()->AllocateJSObjectFromMap(initial_map,
|
| + NOT_TENURED,
|
| + true,
|
| + allocation_site);
|
| if (!maybe_array->To(&array)) return maybe_array;
|
| } else {
|
| maybe_array = isolate->heap()->AllocateJSObject(*constructor);
|
| @@ -14848,7 +14854,8 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_ArrayConstructor) {
|
|
|
| Handle<AllocationSite> site;
|
| if (!type_info.is_null() &&
|
| - *type_info != isolate->heap()->undefined_value()) {
|
| + !type_info.is_identical_to(
|
| + TypeFeedbackInfo::MegamorphicSentinel(isolate))) {
|
| site = Handle<AllocationSite>::cast(type_info);
|
| ASSERT(!site->SitePointsToLiteral());
|
| }
|
| @@ -14903,9 +14910,11 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_MaxSmi) {
|
| static const Runtime::Function kIntrinsicFunctions[] = {
|
| RUNTIME_FUNCTION_LIST(F)
|
| INLINE_FUNCTION_LIST(I)
|
| - INLINE_RUNTIME_FUNCTION_LIST(I)
|
| };
|
|
|
| +#undef I
|
| +#undef F
|
| +
|
|
|
| MaybeObject* Runtime::InitializeIntrinsicFunctionNames(Heap* heap,
|
| Object* dictionary) {
|
|
|