From cef7b20ec047a2f8763de5875638ec0632d7ebd2 Mon Sep 17 00:00:00 2001 From: "verwaest@chromium.org" Date: Mon, 7 Jul 2014 13:27:37 +0000 Subject: [PATCH] Only create arguments-maps in the bootstrapper, remove now obsolete ValueType flag. TBR=dslomov@chromium.org BUG= Review URL: https://codereview.chromium.org/375503008 git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@22245 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/arm/code-stubs-arm.cc | 32 +++--- src/arm64/code-stubs-arm64.cc | 58 +++++------ src/bootstrapper.cc | 196 +++++++++++++---------------------- src/builtins.cc | 4 +- src/contexts.h | 231 ++++++++++++++++++++---------------------- src/factory.cc | 22 +++- src/factory.h | 2 +- src/heap.cc | 52 ---------- src/heap.h | 4 - src/ia32/code-stubs-ia32.cc | 53 +++++----- src/objects.cc | 49 ++++----- src/objects.h | 20 +--- src/runtime.cc | 27 ++--- src/x64/code-stubs-x64.cc | 38 ++++--- test/cctest/cctest.h | 1 - test/cctest/test-alloc.cc | 1 - 16 files changed, 327 insertions(+), 463 deletions(-) diff --git a/src/arm/code-stubs-arm.cc b/src/arm/code-stubs-arm.cc index 06c1b05..526bc55 100644 --- a/src/arm/code-stubs-arm.cc +++ b/src/arm/code-stubs-arm.cc @@ -2019,12 +2019,12 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { __ Allocate(r9, r0, r3, r4, &runtime, TAG_OBJECT); // r0 = address of new object(s) (tagged) - // r2 = argument count (tagged) + // r2 = argument count (smi-tagged) // Get the arguments boilerplate from the current native context into r4. const int kNormalOffset = - Context::SlotOffset(Context::SLOPPY_ARGUMENTS_BOILERPLATE_INDEX); + Context::SlotOffset(Context::SLOPPY_ARGUMENTS_MAP_INDEX); const int kAliasedOffset = - Context::SlotOffset(Context::ALIASED_ARGUMENTS_BOILERPLATE_INDEX); + Context::SlotOffset(Context::ALIASED_ARGUMENTS_MAP_INDEX); __ ldr(r4, MemOperand(cp, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ ldr(r4, FieldMemOperand(r4, GlobalObject::kNativeContextOffset)); @@ -2034,22 +2034,23 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { // r0 = address of new object (tagged) // r1 = mapped parameter count (tagged) - // r2 = argument count (tagged) - // r4 = address of boilerplate object (tagged) - // Copy the JS object part. - for (int i = 0; i < JSObject::kHeaderSize; i += kPointerSize) { - __ ldr(r3, FieldMemOperand(r4, i)); - __ str(r3, FieldMemOperand(r0, i)); - } + // r2 = argument count (smi-tagged) + // r4 = address of arguments map (tagged) + __ str(r4, FieldMemOperand(r0, JSObject::kMapOffset)); + __ LoadRoot(r3, Heap::kEmptyFixedArrayRootIndex); + __ str(r3, FieldMemOperand(r0, JSObject::kPropertiesOffset)); + __ str(r3, FieldMemOperand(r0, JSObject::kElementsOffset)); // Set up the callee in-object property. STATIC_ASSERT(Heap::kArgumentsCalleeIndex == 1); __ ldr(r3, MemOperand(sp, 2 * kPointerSize)); + __ AssertNotSmi(r3); const int kCalleeOffset = JSObject::kHeaderSize + Heap::kArgumentsCalleeIndex * kPointerSize; __ str(r3, FieldMemOperand(r0, kCalleeOffset)); // Use the length (smi tagged) and set that as an in-object property too. + __ AssertSmi(r2); STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); const int kLengthOffset = JSObject::kHeaderSize + Heap::kArgumentsLengthIndex * kPointerSize; @@ -2203,15 +2204,18 @@ void ArgumentsAccessStub::GenerateNewStrict(MacroAssembler* masm) { // Get the arguments boilerplate from the current native context. __ ldr(r4, MemOperand(cp, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ ldr(r4, FieldMemOperand(r4, GlobalObject::kNativeContextOffset)); - __ ldr(r4, MemOperand(r4, Context::SlotOffset( - Context::STRICT_ARGUMENTS_BOILERPLATE_INDEX))); + __ ldr(r4, MemOperand( + r4, Context::SlotOffset(Context::STRICT_ARGUMENTS_MAP_INDEX))); - // Copy the JS object part. - __ CopyFields(r0, r4, d0, JSObject::kHeaderSize / kPointerSize); + __ str(r4, FieldMemOperand(r0, JSObject::kMapOffset)); + __ LoadRoot(r3, Heap::kEmptyFixedArrayRootIndex); + __ str(r3, FieldMemOperand(r0, JSObject::kPropertiesOffset)); + __ str(r3, FieldMemOperand(r0, JSObject::kElementsOffset)); // Get the length (smi tagged) and set that as an in-object property too. STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); __ ldr(r1, MemOperand(sp, 0 * kPointerSize)); + __ AssertSmi(r1); __ str(r1, FieldMemOperand(r0, JSObject::kHeaderSize + Heap::kArgumentsLengthIndex * kPointerSize)); diff --git a/src/arm64/code-stubs-arm64.cc b/src/arm64/code-stubs-arm64.cc index 6dc564d..0e08907 100644 --- a/src/arm64/code-stubs-arm64.cc +++ b/src/arm64/code-stubs-arm64.cc @@ -2103,41 +2103,42 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { // Get the arguments boilerplate from the current (global) context. - // x0 alloc_obj pointer to allocated objects (param map, backing - // store, arguments) - // x1 mapped_params number of mapped parameters, min(params, args) - // x2 arg_count number of function arguments - // x3 arg_count_smi number of function arguments (smi) - // x4 function function pointer - // x7 param_count number of function parameters - // x11 args_offset offset to args (or aliased args) boilerplate (uninit) - // x14 recv_arg pointer to receiver arguments + // x0 alloc_obj pointer to allocated objects (param map, backing + // store, arguments) + // x1 mapped_params number of mapped parameters, min(params, args) + // x2 arg_count number of function arguments + // x3 arg_count_smi number of function arguments (smi) + // x4 function function pointer + // x7 param_count number of function parameters + // x11 sloppy_args_map offset to args (or aliased args) map (uninit) + // x14 recv_arg pointer to receiver arguments Register global_object = x10; Register global_ctx = x10; - Register args_offset = x11; - Register aliased_args_offset = x10; + Register sloppy_args_map = x11; + Register aliased_args_map = x10; __ Ldr(global_object, GlobalObjectMemOperand()); __ Ldr(global_ctx, FieldMemOperand(global_object, GlobalObject::kNativeContextOffset)); - __ Ldr(args_offset, - ContextMemOperand(global_ctx, - Context::SLOPPY_ARGUMENTS_BOILERPLATE_INDEX)); - __ Ldr(aliased_args_offset, - ContextMemOperand(global_ctx, - Context::ALIASED_ARGUMENTS_BOILERPLATE_INDEX)); + __ Ldr(sloppy_args_map, + ContextMemOperand(global_ctx, Context::SLOPPY_ARGUMENTS_MAP_INDEX)); + __ Ldr(aliased_args_map, + ContextMemOperand(global_ctx, Context::ALIASED_ARGUMENTS_MAP_INDEX)); __ Cmp(mapped_params, 0); - __ CmovX(args_offset, aliased_args_offset, ne); + __ CmovX(sloppy_args_map, aliased_args_map, ne); // Copy the JS object part. - __ CopyFields(alloc_obj, args_offset, CPURegList(x10, x12, x13), - JSObject::kHeaderSize / kPointerSize); + __ Str(sloppy_args_map, FieldMemOperand(alloc_obj, JSObject::kMapOffset)); + __ LoadRoot(x10, Heap::kEmptyFixedArrayRootIndex); + __ Str(x10, FieldMemOperand(alloc_obj, JSObject::kPropertiesOffset)); + __ Str(x10, FieldMemOperand(alloc_obj, JSObject::kElementsOffset)); // Set up the callee in-object property. STATIC_ASSERT(Heap::kArgumentsCalleeIndex == 1); const int kCalleeOffset = JSObject::kHeaderSize + Heap::kArgumentsCalleeIndex * kPointerSize; + __ AssertNotSmi(function); __ Str(function, FieldMemOperand(alloc_obj, kCalleeOffset)); // Use the length and set that as an in-object property. @@ -2338,25 +2339,24 @@ void ArgumentsAccessStub::GenerateNewStrict(MacroAssembler* masm) { // Get the arguments boilerplate from the current (native) context. Register global_object = x10; Register global_ctx = x10; - Register args_offset = x4; + Register strict_args_map = x4; __ Ldr(global_object, GlobalObjectMemOperand()); __ Ldr(global_ctx, FieldMemOperand(global_object, GlobalObject::kNativeContextOffset)); - __ Ldr(args_offset, - ContextMemOperand(global_ctx, - Context::STRICT_ARGUMENTS_BOILERPLATE_INDEX)); + __ Ldr(strict_args_map, + ContextMemOperand(global_ctx, Context::STRICT_ARGUMENTS_MAP_INDEX)); // x0 alloc_obj pointer to allocated objects: parameter array and // arguments object // x1 param_count_smi number of parameters passed to function (smi) // x2 params pointer to parameters // x3 function function pointer - // x4 args_offset offset to arguments boilerplate + // x4 strict_args_map offset to arguments map // x13 param_count number of parameters passed to function - - // Copy the JS object part. - __ CopyFields(alloc_obj, args_offset, CPURegList(x5, x6, x7), - JSObject::kHeaderSize / kPointerSize); + __ Str(strict_args_map, FieldMemOperand(alloc_obj, JSObject::kMapOffset)); + __ LoadRoot(x5, Heap::kEmptyFixedArrayRootIndex); + __ Str(x5, FieldMemOperand(alloc_obj, JSObject::kPropertiesOffset)); + __ Str(x5, FieldMemOperand(alloc_obj, JSObject::kElementsOffset)); // Set the smi-tagged length as an in-object property. STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); diff --git a/src/bootstrapper.cc b/src/bootstrapper.cc index 42e3e69..6051447 100644 --- a/src/bootstrapper.cc +++ b/src/bootstrapper.cc @@ -769,16 +769,17 @@ Handle Genesis::CreateNewGlobals( Handle name = Handle(heap()->empty_string()); Handle code = Handle(isolate()->builtins()->builtin( Builtins::kIllegal)); - js_global_object_function = factory()->NewFunction( - name, code, JS_GLOBAL_OBJECT_TYPE, JSGlobalObject::kSize); - // Change the constructor property of the prototype of the - // hidden global function to refer to the Object function. Handle prototype = - Handle( - JSObject::cast(js_global_object_function->instance_prototype())); - JSObject::SetOwnPropertyIgnoreAttributes( - prototype, factory()->constructor_string(), - isolate()->object_function(), NONE).Check(); + factory()->NewFunctionPrototype(isolate()->object_function()); + js_global_object_function = factory()->NewFunction( + name, code, prototype, JS_GLOBAL_OBJECT_TYPE, JSGlobalObject::kSize); +#ifdef DEBUG + LookupIterator it(prototype, factory()->constructor_string(), + LookupIterator::CHECK_OWN_REAL); + Handle value = JSReceiver::GetProperty(&it).ToHandleChecked(); + ASSERT(it.IsFound()); + ASSERT_EQ(*isolate()->object_function(), *value); +#endif } else { Handle js_global_object_constructor( FunctionTemplateInfo::cast(js_global_object_template->constructor())); @@ -1133,80 +1134,57 @@ void Genesis::InitializeGlobal(Handle global_object, InstallFunction(global, "WeakSet", JS_WEAK_SET_TYPE, JSWeakSet::kSize, isolate->initial_object_prototype(), Builtins::kIllegal); - { // --- arguments_boilerplate_ + { // --- sloppy arguments map // Make sure we can recognize argument objects at runtime. // This is done by introducing an anonymous function with // class_name equals 'Arguments'. Handle arguments_string = factory->InternalizeOneByteString( STATIC_ASCII_VECTOR("Arguments")); Handle code(isolate->builtins()->builtin(Builtins::kIllegal)); - Handle function = factory->NewFunctionWithoutPrototype( arguments_string, code); - ASSERT(!function->has_initial_map()); function->shared()->set_instance_class_name(*arguments_string); - function->shared()->set_expected_nof_properties(2); - function->set_prototype_or_initial_map( - native_context()->object_function()->prototype()); - Handle result = factory->NewJSObject(function); - - native_context()->set_sloppy_arguments_boilerplate(*result); - // Note: length must be added as the first property and - // callee must be added as the second property. - JSObject::AddProperty( - result, factory->length_string(), - factory->undefined_value(), DONT_ENUM, - Object::FORCE_TAGGED, FORCE_FIELD); - JSObject::AddProperty( - result, factory->callee_string(), - factory->undefined_value(), DONT_ENUM, - Object::FORCE_TAGGED, FORCE_FIELD); -#ifdef DEBUG - LookupResult lookup(isolate); - result->LookupOwn(factory->callee_string(), &lookup); - ASSERT(lookup.IsField()); - ASSERT(lookup.GetFieldIndex().property_index() == - Heap::kArgumentsCalleeIndex); - - result->LookupOwn(factory->length_string(), &lookup); - ASSERT(lookup.IsField()); - ASSERT(lookup.GetFieldIndex().property_index() == - Heap::kArgumentsLengthIndex); - - ASSERT(result->map()->inobject_properties() > Heap::kArgumentsCalleeIndex); - ASSERT(result->map()->inobject_properties() > Heap::kArgumentsLengthIndex); - - // Check the state of the object. - ASSERT(result->HasFastProperties()); - ASSERT(result->HasFastObjectElements()); -#endif + Handle map = + factory->NewMap(JS_OBJECT_TYPE, Heap::kSloppyArgumentsObjectSize); + // Create the descriptor array for the arguments object. + Map::EnsureDescriptorSlack(map, 2); + + { // length + FieldDescriptor d(factory->length_string(), Heap::kArgumentsLengthIndex, + DONT_ENUM, Representation::Tagged()); + map->AppendDescriptor(&d); + } + { // callee + FieldDescriptor d(factory->callee_string(), Heap::kArgumentsCalleeIndex, + DONT_ENUM, Representation::Tagged()); + map->AppendDescriptor(&d); + } + + map->set_function_with_prototype(true); + map->set_prototype(native_context()->object_function()->prototype()); + map->set_pre_allocated_property_fields(2); + map->set_inobject_properties(2); + native_context()->set_sloppy_arguments_map(*map); + + ASSERT(!function->has_initial_map()); + function->set_initial_map(*map); + map->set_constructor(*function); + + ASSERT(map->inobject_properties() > Heap::kArgumentsCalleeIndex); + ASSERT(map->inobject_properties() > Heap::kArgumentsLengthIndex); + ASSERT(!map->is_dictionary_map()); + ASSERT(IsFastObjectElementsKind(map->elements_kind())); } - { // --- aliased_arguments_boilerplate_ - // Set up a well-formed parameter map to make assertions happy. - Handle elements = factory->NewFixedArray(2); - elements->set_map(heap->sloppy_arguments_elements_map()); - Handle array; - array = factory->NewFixedArray(0); - elements->set(0, *array); - array = factory->NewFixedArray(0); - elements->set(1, *array); - - Handle old_map( - native_context()->sloppy_arguments_boilerplate()->map()); - Handle new_map = Map::Copy(old_map); - new_map->set_pre_allocated_property_fields(2); - Handle result = factory->NewJSObjectFromMap(new_map); - // Set elements kind after allocating the object because - // NewJSObjectFromMap assumes a fast elements map. - new_map->set_elements_kind(SLOPPY_ARGUMENTS_ELEMENTS); - result->set_elements(*elements); - ASSERT(result->HasSloppyArgumentsElements()); - native_context()->set_aliased_arguments_boilerplate(*result); - } - - { // --- strict mode arguments boilerplate + { // --- aliased arguments map + Handle map = Map::Copy(isolate->sloppy_arguments_map()); + map->set_elements_kind(SLOPPY_ARGUMENTS_ELEMENTS); + ASSERT_EQ(2, map->pre_allocated_property_fields()); + native_context()->set_aliased_arguments_map(*map); + } + + { // --- strict mode arguments map const PropertyAttributes attributes = static_cast(DONT_ENUM | DONT_DELETE | READ_ONLY); @@ -1229,20 +1207,16 @@ void Genesis::InitializeGlobal(Handle global_object, Map::EnsureDescriptorSlack(map, 3); { // length - FieldDescriptor d( - factory->length_string(), 0, DONT_ENUM, Representation::Tagged()); + FieldDescriptor d(factory->length_string(), Heap::kArgumentsLengthIndex, + DONT_ENUM, Representation::Tagged()); map->AppendDescriptor(&d); } { // callee - CallbacksDescriptor d(factory->callee_string(), - callee, - attributes); + CallbacksDescriptor d(factory->callee_string(), callee, attributes); map->AppendDescriptor(&d); } { // caller - CallbacksDescriptor d(factory->caller_string(), - caller, - attributes); + CallbacksDescriptor d(factory->caller_string(), caller, attributes); map->AppendDescriptor(&d); } @@ -1253,29 +1227,13 @@ void Genesis::InitializeGlobal(Handle global_object, // Copy constructor from the sloppy arguments boilerplate. map->set_constructor( - native_context()->sloppy_arguments_boilerplate()->map()->constructor()); - - // Allocate the arguments boilerplate object. - Handle result = factory->NewJSObjectFromMap(map); - native_context()->set_strict_arguments_boilerplate(*result); - -#ifdef DEBUG - LookupResult lookup(isolate); - result->LookupOwn(factory->length_string(), &lookup); - ASSERT(lookup.IsField()); - ASSERT(lookup.GetFieldIndex().property_index() == - Heap::kArgumentsLengthIndex); + native_context()->sloppy_arguments_map()->constructor()); - Handle length_value = Object::GetProperty( - result, factory->length_string()).ToHandleChecked(); - ASSERT_EQ(heap->undefined_value(), *length_value); + native_context()->set_strict_arguments_map(*map); - ASSERT(result->map()->inobject_properties() > Heap::kArgumentsLengthIndex); - - // Check the state of the object. - ASSERT(result->HasFastProperties()); - ASSERT(result->HasFastObjectElements()); -#endif + ASSERT(map->inobject_properties() > Heap::kArgumentsLengthIndex); + ASSERT(!map->is_dictionary_map()); + ASSERT(IsFastObjectElementsKind(map->elements_kind())); } { // --- context extension @@ -2192,33 +2150,27 @@ bool Bootstrapper::InstallExtensions(Handle native_context, bool Genesis::InstallSpecialObjects(Handle native_context) { Isolate* isolate = native_context->GetIsolate(); + // Don't install extensions into the snapshot. + if (isolate->serializer_enabled()) return true; + Factory* factory = isolate->factory(); HandleScope scope(isolate); Handle global(JSGlobalObject::cast( native_context->global_object())); + + Handle Error = Handle::cast( + Object::GetProperty(isolate, global, "Error").ToHandleChecked()); + Handle name = + factory->InternalizeOneByteString(STATIC_ASCII_VECTOR("stackTraceLimit")); + Handle stack_trace_limit(Smi::FromInt(FLAG_stack_trace_limit), isolate); + JSObject::AddProperty(Error, name, stack_trace_limit, NONE); + // Expose the natives in global if a name for it is specified. if (FLAG_expose_natives_as != NULL && strlen(FLAG_expose_natives_as) != 0) { Handle natives = factory->InternalizeUtf8String(FLAG_expose_natives_as); - RETURN_ON_EXCEPTION_VALUE( - isolate, - JSObject::SetOwnPropertyIgnoreAttributes( - global, natives, Handle(global->builtins()), DONT_ENUM), - false); - } - - Handle Error = Object::GetProperty( - isolate, global, "Error").ToHandleChecked(); - if (Error->IsJSObject()) { - Handle name = factory->InternalizeOneByteString( - STATIC_ASCII_VECTOR("stackTraceLimit")); - Handle stack_trace_limit( - Smi::FromInt(FLAG_stack_trace_limit), isolate); - RETURN_ON_EXCEPTION_VALUE( - isolate, - JSObject::SetOwnPropertyIgnoreAttributes( - Handle::cast(Error), name, stack_trace_limit, NONE), - false); + JSObject::AddProperty(global, natives, handle(global->builtins()), + DONT_ENUM); } // Expose the stack trace symbol to native JS. @@ -2246,11 +2198,7 @@ bool Genesis::InstallSpecialObjects(Handle native_context) { Handle debug_string = factory->InternalizeUtf8String(FLAG_expose_debug_as); Handle global_proxy(debug_context->global_proxy(), isolate); - RETURN_ON_EXCEPTION_VALUE( - isolate, - JSObject::SetOwnPropertyIgnoreAttributes( - global, debug_string, global_proxy, DONT_ENUM), - false); + JSObject::AddProperty(global, debug_string, global_proxy, DONT_ENUM); } return true; } diff --git a/src/builtins.cc b/src/builtins.cc index 33bd5df..94ff13e 100644 --- a/src/builtins.cc +++ b/src/builtins.cc @@ -643,8 +643,8 @@ BUILTIN(ArraySlice) { } else { // Array.slice(arguments, ...) is quite a common idiom (notably more // than 50% of invocations in Web apps). Treat it in C++ as well. - Map* arguments_map = isolate->context()->native_context()-> - sloppy_arguments_boilerplate()->map(); + Map* arguments_map = + isolate->context()->native_context()->sloppy_arguments_map(); bool is_arguments_object_with_fast_elements = receiver->IsJSObject() && diff --git a/src/contexts.h b/src/contexts.h index 1ee5a6f..08773b7 100644 --- a/src/contexts.h +++ b/src/contexts.h @@ -73,122 +73,114 @@ enum BindingFlags { // must always be allocated via Heap::AllocateContext() or // Factory::NewContext. -#define NATIVE_CONTEXT_FIELDS(V) \ - V(GLOBAL_PROXY_INDEX, JSObject, global_proxy_object) \ - V(SECURITY_TOKEN_INDEX, Object, security_token) \ - V(BOOLEAN_FUNCTION_INDEX, JSFunction, boolean_function) \ - V(NUMBER_FUNCTION_INDEX, JSFunction, number_function) \ - V(STRING_FUNCTION_INDEX, JSFunction, string_function) \ - V(STRING_FUNCTION_PROTOTYPE_MAP_INDEX, Map, string_function_prototype_map) \ - V(SYMBOL_FUNCTION_INDEX, JSFunction, symbol_function) \ - V(OBJECT_FUNCTION_INDEX, JSFunction, object_function) \ - V(INTERNAL_ARRAY_FUNCTION_INDEX, JSFunction, internal_array_function) \ - V(ARRAY_FUNCTION_INDEX, JSFunction, array_function) \ - V(JS_ARRAY_MAPS_INDEX, Object, js_array_maps) \ - V(DATE_FUNCTION_INDEX, JSFunction, date_function) \ - V(JSON_OBJECT_INDEX, JSObject, json_object) \ - V(REGEXP_FUNCTION_INDEX, JSFunction, regexp_function) \ - V(INITIAL_OBJECT_PROTOTYPE_INDEX, JSObject, initial_object_prototype) \ - V(INITIAL_ARRAY_PROTOTYPE_INDEX, JSObject, initial_array_prototype) \ - V(CREATE_DATE_FUN_INDEX, JSFunction, create_date_fun) \ - V(TO_NUMBER_FUN_INDEX, JSFunction, to_number_fun) \ - V(TO_STRING_FUN_INDEX, JSFunction, to_string_fun) \ - V(TO_DETAIL_STRING_FUN_INDEX, JSFunction, to_detail_string_fun) \ - V(TO_OBJECT_FUN_INDEX, JSFunction, to_object_fun) \ - V(TO_INTEGER_FUN_INDEX, JSFunction, to_integer_fun) \ - V(TO_UINT32_FUN_INDEX, JSFunction, to_uint32_fun) \ - V(TO_INT32_FUN_INDEX, JSFunction, to_int32_fun) \ - V(GLOBAL_EVAL_FUN_INDEX, JSFunction, global_eval_fun) \ - V(INSTANTIATE_FUN_INDEX, JSFunction, instantiate_fun) \ - V(CONFIGURE_INSTANCE_FUN_INDEX, JSFunction, configure_instance_fun) \ - V(ARRAY_BUFFER_FUN_INDEX, JSFunction, array_buffer_fun) \ - V(UINT8_ARRAY_FUN_INDEX, JSFunction, uint8_array_fun) \ - V(INT8_ARRAY_FUN_INDEX, JSFunction, int8_array_fun) \ - V(UINT16_ARRAY_FUN_INDEX, JSFunction, uint16_array_fun) \ - V(INT16_ARRAY_FUN_INDEX, JSFunction, int16_array_fun) \ - V(UINT32_ARRAY_FUN_INDEX, JSFunction, uint32_array_fun) \ - V(INT32_ARRAY_FUN_INDEX, JSFunction, int32_array_fun) \ - V(FLOAT32_ARRAY_FUN_INDEX, JSFunction, float32_array_fun) \ - V(FLOAT64_ARRAY_FUN_INDEX, JSFunction, float64_array_fun) \ - V(UINT8_CLAMPED_ARRAY_FUN_INDEX, JSFunction, uint8_clamped_array_fun) \ - V(INT8_ARRAY_EXTERNAL_MAP_INDEX, Map, int8_array_external_map) \ - V(UINT8_ARRAY_EXTERNAL_MAP_INDEX, Map, uint8_array_external_map) \ - V(INT16_ARRAY_EXTERNAL_MAP_INDEX, Map, int16_array_external_map) \ - V(UINT16_ARRAY_EXTERNAL_MAP_INDEX, Map, uint16_array_external_map) \ - V(INT32_ARRAY_EXTERNAL_MAP_INDEX, Map, int32_array_external_map) \ - V(UINT32_ARRAY_EXTERNAL_MAP_INDEX, Map, uint32_array_external_map) \ - V(FLOAT32_ARRAY_EXTERNAL_MAP_INDEX, Map, float32_array_external_map) \ - V(FLOAT64_ARRAY_EXTERNAL_MAP_INDEX, Map, float64_array_external_map) \ - V(UINT8_CLAMPED_ARRAY_EXTERNAL_MAP_INDEX, Map, \ - uint8_clamped_array_external_map) \ - V(DATA_VIEW_FUN_INDEX, JSFunction, data_view_fun) \ - V(SLOPPY_FUNCTION_MAP_INDEX, Map, sloppy_function_map) \ - V(SLOPPY_FUNCTION_WITH_READONLY_PROTOTYPE_MAP_INDEX, Map, \ - sloppy_function_with_readonly_prototype_map) \ - V(STRICT_FUNCTION_MAP_INDEX, Map, strict_function_map) \ - V(SLOPPY_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, \ - sloppy_function_without_prototype_map) \ - V(STRICT_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, \ - strict_function_without_prototype_map) \ - V(BOUND_FUNCTION_MAP_INDEX, Map, bound_function_map) \ - V(REGEXP_RESULT_MAP_INDEX, Map, regexp_result_map)\ - V(SLOPPY_ARGUMENTS_BOILERPLATE_INDEX, JSObject, \ - sloppy_arguments_boilerplate) \ - V(ALIASED_ARGUMENTS_BOILERPLATE_INDEX, JSObject, \ - aliased_arguments_boilerplate) \ - V(STRICT_ARGUMENTS_BOILERPLATE_INDEX, JSObject, \ - strict_arguments_boilerplate) \ - V(MESSAGE_LISTENERS_INDEX, JSObject, message_listeners) \ - V(MAKE_MESSAGE_FUN_INDEX, JSFunction, make_message_fun) \ - V(GET_STACK_TRACE_LINE_INDEX, JSFunction, get_stack_trace_line_fun) \ - V(CONFIGURE_GLOBAL_INDEX, JSFunction, configure_global_fun) \ - V(FUNCTION_CACHE_INDEX, JSObject, function_cache) \ - V(JSFUNCTION_RESULT_CACHES_INDEX, FixedArray, jsfunction_result_caches) \ - V(NORMALIZED_MAP_CACHE_INDEX, NormalizedMapCache, normalized_map_cache) \ - V(RUNTIME_CONTEXT_INDEX, Context, runtime_context) \ - V(CALL_AS_FUNCTION_DELEGATE_INDEX, JSFunction, call_as_function_delegate) \ - V(CALL_AS_CONSTRUCTOR_DELEGATE_INDEX, JSFunction, \ - call_as_constructor_delegate) \ - V(SCRIPT_FUNCTION_INDEX, JSFunction, script_function) \ - V(OPAQUE_REFERENCE_FUNCTION_INDEX, JSFunction, opaque_reference_function) \ - V(CONTEXT_EXTENSION_FUNCTION_INDEX, JSFunction, context_extension_function) \ - V(MAP_CACHE_INDEX, Object, map_cache) \ - V(EMBEDDER_DATA_INDEX, FixedArray, embedder_data) \ - V(ALLOW_CODE_GEN_FROM_STRINGS_INDEX, Object, allow_code_gen_from_strings) \ - V(ERROR_MESSAGE_FOR_CODE_GEN_FROM_STRINGS_INDEX, Object, \ - error_message_for_code_gen_from_strings) \ - V(IS_PROMISE_INDEX, JSFunction, is_promise) \ - V(PROMISE_CREATE_INDEX, JSFunction, promise_create) \ - V(PROMISE_RESOLVE_INDEX, JSFunction, promise_resolve) \ - V(PROMISE_REJECT_INDEX, JSFunction, promise_reject) \ - V(PROMISE_CHAIN_INDEX, JSFunction, promise_chain) \ - V(PROMISE_CATCH_INDEX, JSFunction, promise_catch) \ - V(PROMISE_THEN_INDEX, JSFunction, promise_then) \ - V(TO_COMPLETE_PROPERTY_DESCRIPTOR_INDEX, JSFunction, \ - to_complete_property_descriptor) \ - V(DERIVED_HAS_TRAP_INDEX, JSFunction, derived_has_trap) \ - V(DERIVED_GET_TRAP_INDEX, JSFunction, derived_get_trap) \ - V(DERIVED_SET_TRAP_INDEX, JSFunction, derived_set_trap) \ - V(PROXY_ENUMERATE_INDEX, JSFunction, proxy_enumerate) \ - V(OBSERVERS_NOTIFY_CHANGE_INDEX, JSFunction, observers_notify_change) \ - V(OBSERVERS_ENQUEUE_SPLICE_INDEX, JSFunction, observers_enqueue_splice) \ - V(OBSERVERS_BEGIN_SPLICE_INDEX, JSFunction, \ - observers_begin_perform_splice) \ - V(OBSERVERS_END_SPLICE_INDEX, JSFunction, \ - observers_end_perform_splice) \ - V(NATIVE_OBJECT_OBSERVE_INDEX, JSFunction, \ - native_object_observe) \ - V(NATIVE_OBJECT_GET_NOTIFIER_INDEX, JSFunction, \ - native_object_get_notifier) \ - V(NATIVE_OBJECT_NOTIFIER_PERFORM_CHANGE, JSFunction, \ - native_object_notifier_perform_change) \ - V(SLOPPY_GENERATOR_FUNCTION_MAP_INDEX, Map, sloppy_generator_function_map) \ - V(STRICT_GENERATOR_FUNCTION_MAP_INDEX, Map, strict_generator_function_map) \ - V(GENERATOR_OBJECT_PROTOTYPE_MAP_INDEX, Map, \ - generator_object_prototype_map) \ - V(ITERATOR_RESULT_MAP_INDEX, Map, iterator_result_map) \ - V(MAP_ITERATOR_MAP_INDEX, Map, map_iterator_map) \ - V(SET_ITERATOR_MAP_INDEX, Map, set_iterator_map) \ +#define NATIVE_CONTEXT_FIELDS(V) \ + V(GLOBAL_PROXY_INDEX, JSObject, global_proxy_object) \ + V(SECURITY_TOKEN_INDEX, Object, security_token) \ + V(BOOLEAN_FUNCTION_INDEX, JSFunction, boolean_function) \ + V(NUMBER_FUNCTION_INDEX, JSFunction, number_function) \ + V(STRING_FUNCTION_INDEX, JSFunction, string_function) \ + V(STRING_FUNCTION_PROTOTYPE_MAP_INDEX, Map, string_function_prototype_map) \ + V(SYMBOL_FUNCTION_INDEX, JSFunction, symbol_function) \ + V(OBJECT_FUNCTION_INDEX, JSFunction, object_function) \ + V(INTERNAL_ARRAY_FUNCTION_INDEX, JSFunction, internal_array_function) \ + V(ARRAY_FUNCTION_INDEX, JSFunction, array_function) \ + V(JS_ARRAY_MAPS_INDEX, Object, js_array_maps) \ + V(DATE_FUNCTION_INDEX, JSFunction, date_function) \ + V(JSON_OBJECT_INDEX, JSObject, json_object) \ + V(REGEXP_FUNCTION_INDEX, JSFunction, regexp_function) \ + V(INITIAL_OBJECT_PROTOTYPE_INDEX, JSObject, initial_object_prototype) \ + V(INITIAL_ARRAY_PROTOTYPE_INDEX, JSObject, initial_array_prototype) \ + V(CREATE_DATE_FUN_INDEX, JSFunction, create_date_fun) \ + V(TO_NUMBER_FUN_INDEX, JSFunction, to_number_fun) \ + V(TO_STRING_FUN_INDEX, JSFunction, to_string_fun) \ + V(TO_DETAIL_STRING_FUN_INDEX, JSFunction, to_detail_string_fun) \ + V(TO_OBJECT_FUN_INDEX, JSFunction, to_object_fun) \ + V(TO_INTEGER_FUN_INDEX, JSFunction, to_integer_fun) \ + V(TO_UINT32_FUN_INDEX, JSFunction, to_uint32_fun) \ + V(TO_INT32_FUN_INDEX, JSFunction, to_int32_fun) \ + V(GLOBAL_EVAL_FUN_INDEX, JSFunction, global_eval_fun) \ + V(INSTANTIATE_FUN_INDEX, JSFunction, instantiate_fun) \ + V(CONFIGURE_INSTANCE_FUN_INDEX, JSFunction, configure_instance_fun) \ + V(ARRAY_BUFFER_FUN_INDEX, JSFunction, array_buffer_fun) \ + V(UINT8_ARRAY_FUN_INDEX, JSFunction, uint8_array_fun) \ + V(INT8_ARRAY_FUN_INDEX, JSFunction, int8_array_fun) \ + V(UINT16_ARRAY_FUN_INDEX, JSFunction, uint16_array_fun) \ + V(INT16_ARRAY_FUN_INDEX, JSFunction, int16_array_fun) \ + V(UINT32_ARRAY_FUN_INDEX, JSFunction, uint32_array_fun) \ + V(INT32_ARRAY_FUN_INDEX, JSFunction, int32_array_fun) \ + V(FLOAT32_ARRAY_FUN_INDEX, JSFunction, float32_array_fun) \ + V(FLOAT64_ARRAY_FUN_INDEX, JSFunction, float64_array_fun) \ + V(UINT8_CLAMPED_ARRAY_FUN_INDEX, JSFunction, uint8_clamped_array_fun) \ + V(INT8_ARRAY_EXTERNAL_MAP_INDEX, Map, int8_array_external_map) \ + V(UINT8_ARRAY_EXTERNAL_MAP_INDEX, Map, uint8_array_external_map) \ + V(INT16_ARRAY_EXTERNAL_MAP_INDEX, Map, int16_array_external_map) \ + V(UINT16_ARRAY_EXTERNAL_MAP_INDEX, Map, uint16_array_external_map) \ + V(INT32_ARRAY_EXTERNAL_MAP_INDEX, Map, int32_array_external_map) \ + V(UINT32_ARRAY_EXTERNAL_MAP_INDEX, Map, uint32_array_external_map) \ + V(FLOAT32_ARRAY_EXTERNAL_MAP_INDEX, Map, float32_array_external_map) \ + V(FLOAT64_ARRAY_EXTERNAL_MAP_INDEX, Map, float64_array_external_map) \ + V(UINT8_CLAMPED_ARRAY_EXTERNAL_MAP_INDEX, Map, \ + uint8_clamped_array_external_map) \ + V(DATA_VIEW_FUN_INDEX, JSFunction, data_view_fun) \ + V(SLOPPY_FUNCTION_MAP_INDEX, Map, sloppy_function_map) \ + V(SLOPPY_FUNCTION_WITH_READONLY_PROTOTYPE_MAP_INDEX, Map, \ + sloppy_function_with_readonly_prototype_map) \ + V(STRICT_FUNCTION_MAP_INDEX, Map, strict_function_map) \ + V(SLOPPY_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, \ + sloppy_function_without_prototype_map) \ + V(STRICT_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX, Map, \ + strict_function_without_prototype_map) \ + V(BOUND_FUNCTION_MAP_INDEX, Map, bound_function_map) \ + V(REGEXP_RESULT_MAP_INDEX, Map, regexp_result_map) \ + V(SLOPPY_ARGUMENTS_MAP_INDEX, Map, sloppy_arguments_map) \ + V(ALIASED_ARGUMENTS_MAP_INDEX, Map, aliased_arguments_map) \ + V(STRICT_ARGUMENTS_MAP_INDEX, Map, strict_arguments_map) \ + V(MESSAGE_LISTENERS_INDEX, JSObject, message_listeners) \ + V(MAKE_MESSAGE_FUN_INDEX, JSFunction, make_message_fun) \ + V(GET_STACK_TRACE_LINE_INDEX, JSFunction, get_stack_trace_line_fun) \ + V(CONFIGURE_GLOBAL_INDEX, JSFunction, configure_global_fun) \ + V(FUNCTION_CACHE_INDEX, JSObject, function_cache) \ + V(JSFUNCTION_RESULT_CACHES_INDEX, FixedArray, jsfunction_result_caches) \ + V(NORMALIZED_MAP_CACHE_INDEX, NormalizedMapCache, normalized_map_cache) \ + V(RUNTIME_CONTEXT_INDEX, Context, runtime_context) \ + V(CALL_AS_FUNCTION_DELEGATE_INDEX, JSFunction, call_as_function_delegate) \ + V(CALL_AS_CONSTRUCTOR_DELEGATE_INDEX, JSFunction, \ + call_as_constructor_delegate) \ + V(SCRIPT_FUNCTION_INDEX, JSFunction, script_function) \ + V(OPAQUE_REFERENCE_FUNCTION_INDEX, JSFunction, opaque_reference_function) \ + V(CONTEXT_EXTENSION_FUNCTION_INDEX, JSFunction, context_extension_function) \ + V(MAP_CACHE_INDEX, Object, map_cache) \ + V(EMBEDDER_DATA_INDEX, FixedArray, embedder_data) \ + V(ALLOW_CODE_GEN_FROM_STRINGS_INDEX, Object, allow_code_gen_from_strings) \ + V(ERROR_MESSAGE_FOR_CODE_GEN_FROM_STRINGS_INDEX, Object, \ + error_message_for_code_gen_from_strings) \ + V(IS_PROMISE_INDEX, JSFunction, is_promise) \ + V(PROMISE_CREATE_INDEX, JSFunction, promise_create) \ + V(PROMISE_RESOLVE_INDEX, JSFunction, promise_resolve) \ + V(PROMISE_REJECT_INDEX, JSFunction, promise_reject) \ + V(PROMISE_CHAIN_INDEX, JSFunction, promise_chain) \ + V(PROMISE_CATCH_INDEX, JSFunction, promise_catch) \ + V(PROMISE_THEN_INDEX, JSFunction, promise_then) \ + V(TO_COMPLETE_PROPERTY_DESCRIPTOR_INDEX, JSFunction, \ + to_complete_property_descriptor) \ + V(DERIVED_HAS_TRAP_INDEX, JSFunction, derived_has_trap) \ + V(DERIVED_GET_TRAP_INDEX, JSFunction, derived_get_trap) \ + V(DERIVED_SET_TRAP_INDEX, JSFunction, derived_set_trap) \ + V(PROXY_ENUMERATE_INDEX, JSFunction, proxy_enumerate) \ + V(OBSERVERS_NOTIFY_CHANGE_INDEX, JSFunction, observers_notify_change) \ + V(OBSERVERS_ENQUEUE_SPLICE_INDEX, JSFunction, observers_enqueue_splice) \ + V(OBSERVERS_BEGIN_SPLICE_INDEX, JSFunction, observers_begin_perform_splice) \ + V(OBSERVERS_END_SPLICE_INDEX, JSFunction, observers_end_perform_splice) \ + V(NATIVE_OBJECT_OBSERVE_INDEX, JSFunction, native_object_observe) \ + V(NATIVE_OBJECT_GET_NOTIFIER_INDEX, JSFunction, native_object_get_notifier) \ + V(NATIVE_OBJECT_NOTIFIER_PERFORM_CHANGE, JSFunction, \ + native_object_notifier_perform_change) \ + V(SLOPPY_GENERATOR_FUNCTION_MAP_INDEX, Map, sloppy_generator_function_map) \ + V(STRICT_GENERATOR_FUNCTION_MAP_INDEX, Map, strict_generator_function_map) \ + V(GENERATOR_OBJECT_PROTOTYPE_MAP_INDEX, Map, generator_object_prototype_map) \ + V(ITERATOR_RESULT_MAP_INDEX, Map, iterator_result_map) \ + V(MAP_ITERATOR_MAP_INDEX, Map, map_iterator_map) \ + V(SET_ITERATOR_MAP_INDEX, Map, set_iterator_map) \ V(ITERATOR_SYMBOL_INDEX, Symbol, iterator_symbol) // JSFunctions are pairs (context, function code), sometimes also called @@ -263,9 +255,9 @@ class Context: public FixedArray { // These slots are only in native contexts. GLOBAL_PROXY_INDEX = MIN_CONTEXT_SLOTS, SECURITY_TOKEN_INDEX, - SLOPPY_ARGUMENTS_BOILERPLATE_INDEX, - ALIASED_ARGUMENTS_BOILERPLATE_INDEX, - STRICT_ARGUMENTS_BOILERPLATE_INDEX, + SLOPPY_ARGUMENTS_MAP_INDEX, + ALIASED_ARGUMENTS_MAP_INDEX, + STRICT_ARGUMENTS_MAP_INDEX, REGEXP_RESULT_MAP_INDEX, SLOPPY_FUNCTION_MAP_INDEX, SLOPPY_FUNCTION_WITH_READONLY_PROTOTYPE_MAP_INDEX, @@ -375,7 +367,6 @@ class Context: public FixedArray { // Total number of slots. NATIVE_CONTEXT_SLOTS, - FIRST_WEAK_SLOT = OPTIMIZED_FUNCTIONS_LIST }; diff --git a/src/factory.cc b/src/factory.cc index a09c784..8c08ba1 100644 --- a/src/factory.cc +++ b/src/factory.cc @@ -4,6 +4,7 @@ #include "src/factory.h" +#include "src/allocation-site-scopes.h" #include "src/conversions.h" #include "src/isolate-inl.h" #include "src/macro-assembler.h" @@ -2086,11 +2087,24 @@ Handle Factory::NewDebugInfo(Handle shared) { } -Handle Factory::NewArgumentsObject(Handle callee, +Handle Factory::NewArgumentsObject(Handle callee, int length) { - CALL_HEAP_FUNCTION( - isolate(), - isolate()->heap()->AllocateArgumentsObject(*callee, length), JSObject); + bool strict_mode_callee = callee->shared()->strict_mode() == STRICT; + Handle map = strict_mode_callee ? isolate()->strict_arguments_map() + : isolate()->sloppy_arguments_map(); + + AllocationSiteUsageContext context(isolate(), Handle(), + false); + ASSERT(!isolate()->has_pending_exception()); + Handle result = NewJSObjectFromMap(map); + Handle value(Smi::FromInt(length), isolate()); + JSReceiver::SetProperty(result, length_string(), value, NONE, STRICT) + .Assert(); + if (!strict_mode_callee) { + JSReceiver::SetProperty(result, callee_string(), callee, NONE, STRICT) + .Assert(); + } + return result; } diff --git a/src/factory.h b/src/factory.h index 3736b4b..b91b246 100644 --- a/src/factory.h +++ b/src/factory.h @@ -361,7 +361,7 @@ class Factory V8_FINAL { return NewJSObjectFromMap(neander_map()); } - Handle NewArgumentsObject(Handle callee, int length); + Handle NewArgumentsObject(Handle callee, int length); // JS objects are pretenured when allocated by the bootstrapper and // runtime. diff --git a/src/heap.cc b/src/heap.cc index d390788..2fa7702 100644 --- a/src/heap.cc +++ b/src/heap.cc @@ -3569,58 +3569,6 @@ AllocationResult Heap::Allocate(Map* map, AllocationSpace space, } -AllocationResult Heap::AllocateArgumentsObject(Object* callee, int length) { - // To get fast allocation and map sharing for arguments objects we - // allocate them based on an arguments boilerplate. - - JSObject* boilerplate; - int arguments_object_size; - bool strict_mode_callee = callee->IsJSFunction() && - JSFunction::cast(callee)->shared()->strict_mode() == STRICT; - if (strict_mode_callee) { - boilerplate = - isolate()->context()->native_context()->strict_arguments_boilerplate(); - arguments_object_size = kStrictArgumentsObjectSize; - } else { - boilerplate = - isolate()->context()->native_context()->sloppy_arguments_boilerplate(); - arguments_object_size = kSloppyArgumentsObjectSize; - } - - // Check that the size of the boilerplate matches our - // expectations. The ArgumentsAccessStub::GenerateNewObject relies - // on the size being a known constant. - ASSERT(arguments_object_size == boilerplate->map()->instance_size()); - - // Do the allocation. - HeapObject* result; - { AllocationResult allocation = - AllocateRaw(arguments_object_size, NEW_SPACE, OLD_POINTER_SPACE); - if (!allocation.To(&result)) return allocation; - } - - // Copy the content. The arguments boilerplate doesn't have any - // fields that point to new space so it's safe to skip the write - // barrier here. - CopyBlock(result->address(), boilerplate->address(), JSObject::kHeaderSize); - - // Set the length property. - JSObject* js_obj = JSObject::cast(result); - js_obj->InObjectPropertyAtPut( - kArgumentsLengthIndex, Smi::FromInt(length), SKIP_WRITE_BARRIER); - // Set the callee property for sloppy mode arguments object only. - if (!strict_mode_callee) { - js_obj->InObjectPropertyAtPut(kArgumentsCalleeIndex, callee); - } - - // Check the state of the object - ASSERT(js_obj->HasFastProperties()); - ASSERT(js_obj->HasFastObjectElements()); - - return js_obj; -} - - void Heap::InitializeJSObjectFromMap(JSObject* obj, FixedArray* properties, Map* map) { diff --git a/src/heap.h b/src/heap.h index 31df853..a6a14f6 100644 --- a/src/heap.h +++ b/src/heap.h @@ -1486,10 +1486,6 @@ class Heap { int length, PretenureFlag pretenure = NOT_TENURED); - // Allocates an arguments object - optionally with an elements array. - MUST_USE_RESULT AllocationResult AllocateArgumentsObject( - Object* callee, int length); - // Copy the code and scope info part of the code object, but insert // the provided data as the relocation information. MUST_USE_RESULT AllocationResult CopyCode(Code* code, diff --git a/src/ia32/code-stubs-ia32.cc b/src/ia32/code-stubs-ia32.cc index 8a05e00..e3f1aa6 100644 --- a/src/ia32/code-stubs-ia32.cc +++ b/src/ia32/code-stubs-ia32.cc @@ -1036,7 +1036,7 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { __ mov(Operand(esp, 2 * kPointerSize), edx); // ebx = parameter count (tagged) - // ecx = argument count (tagged) + // ecx = argument count (smi-tagged) // esp[4] = parameter count (tagged) // esp[8] = address of receiver argument // Compute the mapped parameter count = min(ebx, ecx) in ebx. @@ -1069,47 +1069,52 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { __ Allocate(ebx, eax, edx, edi, &runtime, TAG_OBJECT); // eax = address of new object(s) (tagged) - // ecx = argument count (tagged) + // ecx = argument count (smi-tagged) // esp[0] = mapped parameter count (tagged) // esp[8] = parameter count (tagged) // esp[12] = address of receiver argument - // Get the arguments boilerplate from the current native context into edi. - Label has_mapped_parameters, copy; + // Get the arguments map from the current native context into edi. + Label has_mapped_parameters, instantiate; __ mov(edi, Operand(esi, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ mov(edi, FieldOperand(edi, GlobalObject::kNativeContextOffset)); __ mov(ebx, Operand(esp, 0 * kPointerSize)); __ test(ebx, ebx); __ j(not_zero, &has_mapped_parameters, Label::kNear); - __ mov(edi, Operand(edi, - Context::SlotOffset(Context::SLOPPY_ARGUMENTS_BOILERPLATE_INDEX))); - __ jmp(©, Label::kNear); + __ mov( + edi, + Operand(edi, Context::SlotOffset(Context::SLOPPY_ARGUMENTS_MAP_INDEX))); + __ jmp(&instantiate, Label::kNear); __ bind(&has_mapped_parameters); - __ mov(edi, Operand(edi, - Context::SlotOffset(Context::ALIASED_ARGUMENTS_BOILERPLATE_INDEX))); - __ bind(©); + __ mov( + edi, + Operand(edi, Context::SlotOffset(Context::ALIASED_ARGUMENTS_MAP_INDEX))); + __ bind(&instantiate); // eax = address of new object (tagged) // ebx = mapped parameter count (tagged) - // ecx = argument count (tagged) - // edi = address of boilerplate object (tagged) + // ecx = argument count (smi-tagged) + // edi = address of arguments map (tagged) // esp[0] = mapped parameter count (tagged) // esp[8] = parameter count (tagged) // esp[12] = address of receiver argument // Copy the JS object part. - for (int i = 0; i < JSObject::kHeaderSize; i += kPointerSize) { - __ mov(edx, FieldOperand(edi, i)); - __ mov(FieldOperand(eax, i), edx); - } + __ mov(FieldOperand(eax, JSObject::kMapOffset), edi); + __ mov(FieldOperand(eax, JSObject::kPropertiesOffset), + masm->isolate()->factory()->empty_fixed_array()); + __ mov(FieldOperand(eax, JSObject::kElementsOffset), + masm->isolate()->factory()->empty_fixed_array()); // Set up the callee in-object property. STATIC_ASSERT(Heap::kArgumentsCalleeIndex == 1); __ mov(edx, Operand(esp, 4 * kPointerSize)); + __ AssertNotSmi(edx); __ mov(FieldOperand(eax, JSObject::kHeaderSize + Heap::kArgumentsCalleeIndex * kPointerSize), edx); // Use the length (smi tagged) and set that as an in-object property too. + __ AssertSmi(ecx); STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); __ mov(FieldOperand(eax, JSObject::kHeaderSize + Heap::kArgumentsLengthIndex * kPointerSize), @@ -1266,22 +1271,22 @@ void ArgumentsAccessStub::GenerateNewStrict(MacroAssembler* masm) { // Do the allocation of both objects in one go. __ Allocate(ecx, eax, edx, ebx, &runtime, TAG_OBJECT); - // Get the arguments boilerplate from the current native context. + // Get the arguments map from the current native context. __ mov(edi, Operand(esi, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ mov(edi, FieldOperand(edi, GlobalObject::kNativeContextOffset)); - const int offset = - Context::SlotOffset(Context::STRICT_ARGUMENTS_BOILERPLATE_INDEX); + const int offset = Context::SlotOffset(Context::STRICT_ARGUMENTS_MAP_INDEX); __ mov(edi, Operand(edi, offset)); - // Copy the JS object part. - for (int i = 0; i < JSObject::kHeaderSize; i += kPointerSize) { - __ mov(ebx, FieldOperand(edi, i)); - __ mov(FieldOperand(eax, i), ebx); - } + __ mov(FieldOperand(eax, JSObject::kMapOffset), edi); + __ mov(FieldOperand(eax, JSObject::kPropertiesOffset), + masm->isolate()->factory()->empty_fixed_array()); + __ mov(FieldOperand(eax, JSObject::kElementsOffset), + masm->isolate()->factory()->empty_fixed_array()); // Get the length (smi tagged) and set that as an in-object property too. STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); __ mov(ecx, Operand(esp, 1 * kPointerSize)); + __ AssertSmi(ecx); __ mov(FieldOperand(eax, JSObject::kHeaderSize + Heap::kArgumentsLengthIndex * kPointerSize), ecx); diff --git a/src/objects.cc b/src/objects.cc index ab34acf..3d5987c 100644 --- a/src/objects.cc +++ b/src/objects.cc @@ -1834,7 +1834,6 @@ void JSObject::AddFastProperty(Handle object, Handle value, PropertyAttributes attributes, StoreFromKeyed store_mode, - ValueType value_type, TransitionFlag flag) { ASSERT(!object->IsJSGlobalProxy()); @@ -1844,7 +1843,7 @@ void JSObject::AddFastProperty(Handle object, handle(object->map()), name, value, attributes, flag); } else if (!object->TooManyFastProperties(store_mode)) { Isolate* isolate = object->GetIsolate(); - Representation representation = value->OptimalRepresentation(value_type); + Representation representation = value->OptimalRepresentation(); maybe_map = Map::CopyWithField( handle(object->map(), isolate), name, value->OptimalType(isolate, representation), @@ -1901,7 +1900,6 @@ MaybeHandle JSObject::AddPropertyInternal( StrictMode strict_mode, JSReceiver::StoreFromKeyed store_mode, ExtensibilityCheck extensibility_check, - ValueType value_type, StoreMode mode, TransitionFlag transition_flag) { ASSERT(!object->IsJSGlobalProxy()); @@ -1926,7 +1924,7 @@ MaybeHandle JSObject::AddPropertyInternal( if (object->HasFastProperties()) { AddFastProperty(object, name, value, attributes, store_mode, - value_type, transition_flag); + transition_flag); } if (!object->HasFastProperties()) { @@ -3976,8 +3974,7 @@ MaybeHandle JSObject::SetPropertyUsingTransition( return JSObject::AddPropertyInternal( object, name, value, attributes, SLOPPY, JSReceiver::CERTAINLY_NOT_STORE_FROM_KEYED, - JSReceiver::OMIT_EXTENSIBILITY_CHECK, - JSObject::FORCE_TAGGED, FORCE_FIELD, OMIT_TRANSITION); + JSReceiver::OMIT_EXTENSIBILITY_CHECK, FORCE_FIELD, OMIT_TRANSITION); } // Keep the target CONSTANT if the same value is stored. @@ -4223,7 +4220,6 @@ void JSObject::AddProperty( Handle name, Handle value, PropertyAttributes attributes, - ValueType value_type, StoreMode store_mode) { #ifdef DEBUG uint32_t index; @@ -4234,9 +4230,8 @@ void JSObject::AddProperty( ASSERT(!it.IsFound()); ASSERT(object->map()->is_extensible()); #endif - SetOwnPropertyIgnoreAttributes( - object, name, value, attributes, value_type, store_mode, - OMIT_EXTENSIBILITY_CHECK).Check(); + SetOwnPropertyIgnoreAttributes(object, name, value, attributes, store_mode, + OMIT_EXTENSIBILITY_CHECK).Check(); } @@ -4251,7 +4246,6 @@ MaybeHandle JSObject::SetOwnPropertyIgnoreAttributes( Handle name, Handle value, PropertyAttributes attributes, - ValueType value_type, StoreMode mode, ExtensibilityCheck extensibility_check, StoreFromKeyed store_from_keyed, @@ -4280,8 +4274,9 @@ MaybeHandle JSObject::SetOwnPropertyIgnoreAttributes( Handle proto(object->GetPrototype(), isolate); if (proto->IsNull()) return value; ASSERT(proto->IsJSGlobalObject()); - return SetOwnPropertyIgnoreAttributes(Handle::cast(proto), - name, value, attributes, value_type, mode, extensibility_check); + return SetOwnPropertyIgnoreAttributes(Handle::cast(proto), name, + value, attributes, mode, + extensibility_check); } if (lookup.IsInterceptor() || @@ -4296,7 +4291,8 @@ MaybeHandle JSObject::SetOwnPropertyIgnoreAttributes( ? OMIT_TRANSITION : INSERT_TRANSITION; // Neither properties nor transitions found. return AddPropertyInternal(object, name, value, attributes, SLOPPY, - store_from_keyed, extensibility_check, value_type, mode, flag); + store_from_keyed, extensibility_check, mode, + flag); } Handle old_value = isolate->factory()->the_hole_value(); @@ -5260,12 +5256,8 @@ Handle JSObject::SetHiddenPropertiesHashTable(Handle object, } } - SetOwnPropertyIgnoreAttributes(object, - isolate->factory()->hidden_string(), - value, - DONT_ENUM, - OPTIMAL_REPRESENTATION, - ALLOW_AS_CONSTANT, + SetOwnPropertyIgnoreAttributes(object, isolate->factory()->hidden_string(), + value, DONT_ENUM, ALLOW_AS_CONSTANT, OMIT_EXTENSIBILITY_CHECK).Assert(); return object; } @@ -5610,11 +5602,10 @@ bool JSObject::ReferencesObject(Object* obj) { // For functions check the context. if (IsJSFunction()) { // Get the constructor function for arguments array. - JSObject* arguments_boilerplate = - heap->isolate()->context()->native_context()-> - sloppy_arguments_boilerplate(); + Map* arguments_map = + heap->isolate()->context()->native_context()->sloppy_arguments_map(); JSFunction* arguments_function = - JSFunction::cast(arguments_boilerplate->map()->constructor()); + JSFunction::cast(arguments_map->constructor()); // Get the context and don't check if it is the native context. JSFunction* f = JSFunction::cast(this); @@ -5906,7 +5897,7 @@ MaybeHandle JSObjectWalkVisitor::StructureWalk( Handle object) { Isolate* isolate = this->isolate(); bool copying = this->copying(); - bool shallow = hints_ == JSObject::kObjectIsShallowArray; + bool shallow = hints_ == JSObject::kObjectIsShallow; if (!shallow) { StackLimitCheck check(isolate); @@ -6393,12 +6384,8 @@ MaybeHandle JSReceiver::GetKeys(Handle object, USE(ContainsOnlyValidKeys); Isolate* isolate = object->GetIsolate(); Handle content = isolate->factory()->empty_fixed_array(); - Handle arguments_boilerplate = Handle( - isolate->context()->native_context()->sloppy_arguments_boilerplate(), - isolate); - Handle arguments_function = Handle( - JSFunction::cast(arguments_boilerplate->map()->constructor()), - isolate); + Handle arguments_function( + JSFunction::cast(isolate->sloppy_arguments_map()->constructor())); // Only collect keys if access is permitted. for (Handle p = object; diff --git a/src/objects.h b/src/objects.h index e2d9791..d49e365 100644 --- a/src/objects.h +++ b/src/objects.h @@ -1406,17 +1406,8 @@ class Object { bool ToInt32(int32_t* value); bool ToUint32(uint32_t* value); - // Indicates whether OptimalRepresentation can do its work, or whether it - // always has to return Representation::Tagged(). - enum ValueType { - OPTIMAL_REPRESENTATION, - FORCE_TAGGED - }; - - inline Representation OptimalRepresentation( - ValueType type = OPTIMAL_REPRESENTATION) { + inline Representation OptimalRepresentation() { if (!FLAG_track_fields) return Representation::Tagged(); - if (type == FORCE_TAGGED) return Representation::Tagged(); if (IsSmi()) { return Representation::Smi(); } else if (FLAG_track_double_fields && IsHeapNumber()) { @@ -2167,7 +2158,6 @@ class JSObject: public JSReceiver { Handle key, Handle value, PropertyAttributes attributes, - ValueType value_type = OPTIMAL_REPRESENTATION, StoreMode mode = ALLOW_AS_CONSTANT, ExtensibilityCheck extensibility_check = PERFORM_EXTENSIBILITY_CHECK, StoreFromKeyed store_mode = MAY_BE_STORE_FROM_KEYED, @@ -2177,7 +2167,6 @@ class JSObject: public JSReceiver { Handle key, Handle value, PropertyAttributes attributes, - ValueType value_type = OPTIMAL_REPRESENTATION, StoreMode mode = ALLOW_AS_CONSTANT); // Extend the receiver with a single fast property appeared first in the @@ -2517,10 +2506,7 @@ class JSObject: public JSReceiver { static void SetObserved(Handle object); // Copy object. - enum DeepCopyHints { - kNoHints = 0, - kObjectIsShallowArray = 1 - }; + enum DeepCopyHints { kNoHints = 0, kObjectIsShallow = 1 }; static Handle Copy(Handle object); MUST_USE_RESULT static MaybeHandle DeepCopy( @@ -2785,7 +2771,6 @@ class JSObject: public JSReceiver { StrictMode strict_mode, StoreFromKeyed store_mode = MAY_BE_STORE_FROM_KEYED, ExtensibilityCheck extensibility_check = PERFORM_EXTENSIBILITY_CHECK, - ValueType value_type = OPTIMAL_REPRESENTATION, StoreMode mode = ALLOW_AS_CONSTANT, TransitionFlag flag = INSERT_TRANSITION); @@ -2795,7 +2780,6 @@ class JSObject: public JSReceiver { Handle value, PropertyAttributes attributes, StoreFromKeyed store_mode, - ValueType value_type, TransitionFlag flag); // Add a property to a slow-case object. diff --git a/src/runtime.cc b/src/runtime.cc index d860245..893e31b 100644 --- a/src/runtime.cc +++ b/src/runtime.cc @@ -251,9 +251,6 @@ MUST_USE_RESULT static MaybeHandle CreateObjectLiteralBoilerplate( JSObject::NormalizeProperties( boilerplate, KEEP_INOBJECT_PROPERTIES, length / 2); } - Object::ValueType value_type = should_normalize - ? Object::FORCE_TAGGED : Object::OPTIMAL_REPRESENTATION; - // TODO(verwaest): Support tracking representations in the boilerplate. for (int index = 0; index < length; index +=2) { Handle key(constant_properties->get(index+0), isolate); @@ -283,8 +280,7 @@ MUST_USE_RESULT static MaybeHandle CreateObjectLiteralBoilerplate( Handle name(String::cast(*key)); ASSERT(!name->AsArrayIndex(&element_index)); maybe_result = JSObject::SetOwnPropertyIgnoreAttributes( - boilerplate, name, value, NONE, - value_type, mode); + boilerplate, name, value, NONE, mode); } } else if (key->ToArrayIndex(&element_index)) { // Array index (uint32). @@ -303,7 +299,7 @@ MUST_USE_RESULT static MaybeHandle CreateObjectLiteralBoilerplate( const char* str = DoubleToCString(num, buffer); Handle name = isolate->factory()->NewStringFromAsciiChecked(str); maybe_result = JSObject::SetOwnPropertyIgnoreAttributes( - boilerplate, name, value, NONE, value_type, mode); + boilerplate, name, value, NONE, mode); } // If setting the property on the boilerplate throws an // exception, the exception is converted to an empty handle in @@ -572,8 +568,8 @@ static MaybeHandle CreateArrayLiteralImpl(Isolate* isolate, AllocationSiteUsageContext usage_context(isolate, site, enable_mementos); usage_context.EnterNewScope(); JSObject::DeepCopyHints hints = (flags & ArrayLiteral::kShallowElements) == 0 - ? JSObject::kNoHints - : JSObject::kObjectIsShallowArray; + ? JSObject::kNoHints + : JSObject::kObjectIsShallow; MaybeHandle copy = JSObject::DeepCopy(boilerplate, &usage_context, hints); usage_context.ExitScope(site, boilerplate); @@ -5093,7 +5089,6 @@ RUNTIME_FUNCTION(Runtime_DefineDataPropertyUnchecked) { isolate, result, JSObject::SetOwnPropertyIgnoreAttributes( js_object, name, obj_value, attr, - Object::OPTIMAL_REPRESENTATION, ALLOW_AS_CONSTANT, JSReceiver::PERFORM_EXTENSIBILITY_CHECK, JSReceiver::MAY_BE_STORE_FROM_KEYED, @@ -5249,9 +5244,8 @@ MaybeHandle Runtime::DefineObjectProperty( } else { if (name->IsString()) name = String::Flatten(Handle::cast(name)); return JSObject::SetOwnPropertyIgnoreAttributes( - js_object, name, value, attr, Object::OPTIMAL_REPRESENTATION, - ALLOW_AS_CONSTANT, JSReceiver::PERFORM_EXTENSIBILITY_CHECK, - store_from_keyed); + js_object, name, value, attr, ALLOW_AS_CONSTANT, + JSReceiver::PERFORM_EXTENSIBILITY_CHECK, store_from_keyed); } } @@ -5266,9 +5260,8 @@ MaybeHandle Runtime::DefineObjectProperty( SLOPPY, false, DEFINE_PROPERTY); } else { return JSObject::SetOwnPropertyIgnoreAttributes( - js_object, name, value, attr, Object::OPTIMAL_REPRESENTATION, - ALLOW_AS_CONSTANT, JSReceiver::PERFORM_EXTENSIBILITY_CHECK, - store_from_keyed); + js_object, name, value, attr, ALLOW_AS_CONSTANT, + JSReceiver::PERFORM_EXTENSIBILITY_CHECK, store_from_keyed); } } @@ -13100,10 +13093,8 @@ RUNTIME_FUNCTION(Runtime_DebugReferencedBy) { // Get the constructor function for context extension and arguments array. - Handle arguments_boilerplate( - isolate->sloppy_arguments_boilerplate()); Handle arguments_function( - JSFunction::cast(arguments_boilerplate->map()->constructor())); + JSFunction::cast(isolate->sloppy_arguments_map()->constructor())); // Get the number of referencing objects. int count; diff --git a/src/x64/code-stubs-x64.cc b/src/x64/code-stubs-x64.cc index c08e38b..63b1b8f 100644 --- a/src/x64/code-stubs-x64.cc +++ b/src/x64/code-stubs-x64.cc @@ -922,35 +922,35 @@ void ArgumentsAccessStub::GenerateNewSloppyFast(MacroAssembler* masm) { // rax = address of new object(s) (tagged) // rcx = argument count (untagged) - // Get the arguments boilerplate from the current native context into rdi. - Label has_mapped_parameters, copy; + // Get the arguments map from the current native context into rdi. + Label has_mapped_parameters, instantiate; __ movp(rdi, Operand(rsi, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ movp(rdi, FieldOperand(rdi, GlobalObject::kNativeContextOffset)); __ testp(rbx, rbx); __ j(not_zero, &has_mapped_parameters, Label::kNear); - const int kIndex = Context::SLOPPY_ARGUMENTS_BOILERPLATE_INDEX; + const int kIndex = Context::SLOPPY_ARGUMENTS_MAP_INDEX; __ movp(rdi, Operand(rdi, Context::SlotOffset(kIndex))); - __ jmp(©, Label::kNear); + __ jmp(&instantiate, Label::kNear); - const int kAliasedIndex = Context::ALIASED_ARGUMENTS_BOILERPLATE_INDEX; + const int kAliasedIndex = Context::ALIASED_ARGUMENTS_MAP_INDEX; __ bind(&has_mapped_parameters); __ movp(rdi, Operand(rdi, Context::SlotOffset(kAliasedIndex))); - __ bind(©); + __ bind(&instantiate); // rax = address of new object (tagged) // rbx = mapped parameter count (untagged) // rcx = argument count (untagged) - // rdi = address of boilerplate object (tagged) - // Copy the JS object part. - for (int i = 0; i < JSObject::kHeaderSize; i += kPointerSize) { - __ movp(rdx, FieldOperand(rdi, i)); - __ movp(FieldOperand(rax, i), rdx); - } + // rdi = address of arguments map (tagged) + __ movp(FieldOperand(rax, JSObject::kMapOffset), rdi); + __ LoadRoot(kScratchRegister, Heap::kEmptyFixedArrayRootIndex); + __ movp(FieldOperand(rax, JSObject::kPropertiesOffset), kScratchRegister); + __ movp(FieldOperand(rax, JSObject::kElementsOffset), kScratchRegister); // Set up the callee in-object property. STATIC_ASSERT(Heap::kArgumentsCalleeIndex == 1); __ movp(rdx, args.GetArgumentOperand(0)); + __ AssertNotSmi(rdx); __ movp(FieldOperand(rax, JSObject::kHeaderSize + Heap::kArgumentsCalleeIndex * kPointerSize), rdx); @@ -1140,18 +1140,16 @@ void ArgumentsAccessStub::GenerateNewStrict(MacroAssembler* masm) { // Do the allocation of both objects in one go. __ Allocate(rcx, rax, rdx, rbx, &runtime, TAG_OBJECT); - // Get the arguments boilerplate from the current native context. + // Get the arguments map from the current native context. __ movp(rdi, Operand(rsi, Context::SlotOffset(Context::GLOBAL_OBJECT_INDEX))); __ movp(rdi, FieldOperand(rdi, GlobalObject::kNativeContextOffset)); - const int offset = - Context::SlotOffset(Context::STRICT_ARGUMENTS_BOILERPLATE_INDEX); + const int offset = Context::SlotOffset(Context::STRICT_ARGUMENTS_MAP_INDEX); __ movp(rdi, Operand(rdi, offset)); - // Copy the JS object part. - for (int i = 0; i < JSObject::kHeaderSize; i += kPointerSize) { - __ movp(rbx, FieldOperand(rdi, i)); - __ movp(FieldOperand(rax, i), rbx); - } + __ movp(FieldOperand(rax, JSObject::kMapOffset), rdi); + __ LoadRoot(kScratchRegister, Heap::kEmptyFixedArrayRootIndex); + __ movp(FieldOperand(rax, JSObject::kPropertiesOffset), kScratchRegister); + __ movp(FieldOperand(rax, JSObject::kElementsOffset), kScratchRegister); // Get the length (smi tagged) and set that as an in-object property too. STATIC_ASSERT(Heap::kArgumentsLengthIndex == 0); diff --git a/test/cctest/cctest.h b/test/cctest/cctest.h index 1fadfb7..e1676e5 100644 --- a/test/cctest/cctest.h +++ b/test/cctest/cctest.h @@ -83,7 +83,6 @@ typedef v8::internal::EnumSet CcTestExtensionFlags; // Use this to expose protected methods in i::Heap. class TestHeap : public i::Heap { public: - using i::Heap::AllocateArgumentsObject; using i::Heap::AllocateByteArray; using i::Heap::AllocateFixedArray; using i::Heap::AllocateHeapNumber; diff --git a/test/cctest/test-alloc.cc b/test/cctest/test-alloc.cc index f80e6a5..f26c461 100644 --- a/test/cctest/test-alloc.cc +++ b/test/cctest/test-alloc.cc @@ -50,7 +50,6 @@ static AllocationResult AllocateAfterFailures() { // for specific kinds. heap->AllocateFixedArray(100).ToObjectChecked(); heap->AllocateHeapNumber(0.42).ToObjectChecked(); - heap->AllocateArgumentsObject(Smi::FromInt(87), 10).ToObjectChecked(); Object* object = heap->AllocateJSObject( *CcTest::i_isolate()->object_function()).ToObjectChecked(); heap->CopyJSObject(JSObject::cast(object)).ToObjectChecked(); -- 2.7.4