| Index: src/deoptimizer.cc
|
| diff --git a/src/deoptimizer.cc b/src/deoptimizer.cc
|
| index 91ab4513a329e2f0190e04af9210ba0951c85fdd..97f82cb3e12950ffc3a04acc1c9879c97f5f849e 100644
|
| --- a/src/deoptimizer.cc
|
| +++ b/src/deoptimizer.cc
|
| @@ -3614,6 +3614,329 @@ void TranslatedState::Prepare(bool has_adapted_arguments,
|
| UpdateFromPreviouslyMaterializedObjects();
|
| }
|
|
|
| +class TranslatedState::CapturedObjectMaterializer {
|
| + public:
|
| + CapturedObjectMaterializer(TranslatedState* state, int frame_index,
|
| + int field_count)
|
| + : state_(state), frame_index_(frame_index), field_count_(field_count) {}
|
| +
|
| + Handle<Object> FieldAt(int* value_index) {
|
| + CHECK(field_count_ > 0);
|
| + --field_count_;
|
| + return state_->MaterializeAt(frame_index_, value_index);
|
| + }
|
| +
|
| + ~CapturedObjectMaterializer() { CHECK_EQ(0, field_count_); }
|
| +
|
| + private:
|
| + TranslatedState* state_;
|
| + int frame_index_;
|
| + int field_count_;
|
| +};
|
| +
|
| +Handle<Object> TranslatedState::MaterializeCapturedObjectAt(
|
| + TranslatedValue* slot, int frame_index, int* value_index) {
|
| + int length = slot->GetChildrenCount();
|
| +
|
| + CapturedObjectMaterializer materializer(this, frame_index, length);
|
| +
|
| + Handle<Object> result;
|
| + if (slot->value_.ToHandle(&result)) {
|
| + // This has been previously materialized, return the previous value.
|
| + // We still need to skip all the nested objects.
|
| + for (int i = 0; i < length; i++) {
|
| + materializer.FieldAt(value_index);
|
| + }
|
| +
|
| + return result;
|
| + }
|
| +
|
| + Handle<Object> map_object = materializer.FieldAt(value_index);
|
| + Handle<Map> map = Map::GeneralizeAllFields(Handle<Map>::cast(map_object));
|
| + switch (map->instance_type()) {
|
| + case MUTABLE_HEAP_NUMBER_TYPE:
|
| + case HEAP_NUMBER_TYPE: {
|
| + // Reuse the HeapNumber value directly as it is already properly
|
| + // tagged and skip materializing the HeapNumber explicitly.
|
| + Handle<Object> object = materializer.FieldAt(value_index);
|
| + slot->value_ = object;
|
| + // On 32-bit architectures, there is an extra slot there because
|
| + // the escape analysis calculates the number of slots as
|
| + // object-size/pointer-size. To account for this, we read out
|
| + // any extra slots.
|
| + for (int i = 0; i < length - 2; i++) {
|
| + materializer.FieldAt(value_index);
|
| + }
|
| + return object;
|
| + }
|
| + case JS_OBJECT_TYPE:
|
| + case JS_ERROR_TYPE:
|
| + case JS_ARGUMENTS_TYPE: {
|
| + Handle<JSObject> object =
|
| + isolate_->factory()->NewJSObjectFromMap(map, NOT_TENURED);
|
| + slot->value_ = object;
|
| + Handle<Object> properties = materializer.FieldAt(value_index);
|
| + Handle<Object> elements = materializer.FieldAt(value_index);
|
| + object->set_properties(FixedArray::cast(*properties));
|
| + object->set_elements(FixedArrayBase::cast(*elements));
|
| + for (int i = 0; i < length - 3; ++i) {
|
| + Handle<Object> value = materializer.FieldAt(value_index);
|
| + FieldIndex index = FieldIndex::ForPropertyIndex(object->map(), i);
|
| + object->FastPropertyAtPut(index, *value);
|
| + }
|
| + return object;
|
| + }
|
| + case JS_TYPED_ARRAY_KEY_ITERATOR_TYPE:
|
| + case JS_FAST_ARRAY_KEY_ITERATOR_TYPE:
|
| + case JS_GENERIC_ARRAY_KEY_ITERATOR_TYPE:
|
| + case JS_UINT8_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT8_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT16_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT16_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FLOAT32_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FLOAT64_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT8_CLAMPED_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_SMI_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_SMI_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_DOUBLE_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_DOUBLE_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_GENERIC_ARRAY_KEY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT8_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT8_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT16_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT16_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT32_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_INT32_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FLOAT32_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FLOAT64_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_UINT8_CLAMPED_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_SMI_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_SMI_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_DOUBLE_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_FAST_HOLEY_DOUBLE_ARRAY_VALUE_ITERATOR_TYPE:
|
| + case JS_GENERIC_ARRAY_VALUE_ITERATOR_TYPE: {
|
| + Handle<JSArrayIterator> object = Handle<JSArrayIterator>::cast(
|
| + isolate_->factory()->NewJSObjectFromMap(map, NOT_TENURED));
|
| + slot->value_ = object;
|
| + Handle<Object> properties = materializer.FieldAt(value_index);
|
| + Handle<Object> elements = materializer.FieldAt(value_index);
|
| + Handle<Object> iterated_object = materializer.FieldAt(value_index);
|
| + Handle<Object> next_index = materializer.FieldAt(value_index);
|
| + Handle<Object> iterated_object_map = materializer.FieldAt(value_index);
|
| + object->set_properties(FixedArray::cast(*properties));
|
| + object->set_elements(FixedArrayBase::cast(*elements));
|
| + object->set_object(*iterated_object);
|
| + object->set_index(*next_index);
|
| + object->set_object_map(*iterated_object_map);
|
| + return object;
|
| + }
|
| + case JS_ARRAY_TYPE: {
|
| + Handle<JSArray> object = Handle<JSArray>::cast(
|
| + isolate_->factory()->NewJSObjectFromMap(map, NOT_TENURED));
|
| + slot->value_ = object;
|
| + Handle<Object> properties = materializer.FieldAt(value_index);
|
| + Handle<Object> elements = materializer.FieldAt(value_index);
|
| + Handle<Object> length = materializer.FieldAt(value_index);
|
| + object->set_properties(FixedArray::cast(*properties));
|
| + object->set_elements(FixedArrayBase::cast(*elements));
|
| + object->set_length(*length);
|
| + return object;
|
| + }
|
| + case JS_FUNCTION_TYPE: {
|
| + Handle<SharedFunctionInfo> temporary_shared =
|
| + isolate_->factory()->NewSharedFunctionInfo(
|
| + isolate_->factory()->empty_string(), MaybeHandle<Code>(), false);
|
| + Handle<JSFunction> object =
|
| + isolate_->factory()->NewFunctionFromSharedFunctionInfo(
|
| + map, temporary_shared, isolate_->factory()->undefined_value(),
|
| + NOT_TENURED);
|
| + slot->value_ = object;
|
| + Handle<Object> properties = materializer.FieldAt(value_index);
|
| + Handle<Object> elements = materializer.FieldAt(value_index);
|
| + Handle<Object> prototype = materializer.FieldAt(value_index);
|
| + Handle<Object> shared = materializer.FieldAt(value_index);
|
| + Handle<Object> context = materializer.FieldAt(value_index);
|
| + Handle<Object> literals = materializer.FieldAt(value_index);
|
| + Handle<Object> entry = materializer.FieldAt(value_index);
|
| + Handle<Object> next_link = materializer.FieldAt(value_index);
|
| + object->ReplaceCode(*isolate_->builtins()->CompileLazy());
|
| + object->set_map(*map);
|
| + object->set_properties(FixedArray::cast(*properties));
|
| + object->set_elements(FixedArrayBase::cast(*elements));
|
| + object->set_prototype_or_initial_map(*prototype);
|
| + object->set_shared(SharedFunctionInfo::cast(*shared));
|
| + object->set_context(Context::cast(*context));
|
| + object->set_literals(LiteralsArray::cast(*literals));
|
| + CHECK(entry->IsNumber()); // Entry to compile lazy stub.
|
| + CHECK(next_link->IsUndefined(isolate_));
|
| + return object;
|
| + }
|
| + case CONS_STRING_TYPE: {
|
| + Handle<ConsString> object = Handle<ConsString>::cast(
|
| + isolate_->factory()
|
| + ->NewConsString(isolate_->factory()->undefined_string(),
|
| + isolate_->factory()->undefined_string())
|
| + .ToHandleChecked());
|
| + slot->value_ = object;
|
| + Handle<Object> hash = materializer.FieldAt(value_index);
|
| + Handle<Object> length = materializer.FieldAt(value_index);
|
| + Handle<Object> first = materializer.FieldAt(value_index);
|
| + Handle<Object> second = materializer.FieldAt(value_index);
|
| + object->set_map(*map);
|
| + object->set_length(Smi::cast(*length)->value());
|
| + object->set_first(String::cast(*first));
|
| + object->set_second(String::cast(*second));
|
| + CHECK(hash->IsNumber()); // The {Name::kEmptyHashField} value.
|
| + return object;
|
| + }
|
| + case CONTEXT_EXTENSION_TYPE: {
|
| + Handle<ContextExtension> object =
|
| + isolate_->factory()->NewContextExtension(
|
| + isolate_->factory()->NewScopeInfo(1),
|
| + isolate_->factory()->undefined_value());
|
| + slot->value_ = object;
|
| + Handle<Object> scope_info = materializer.FieldAt(value_index);
|
| + Handle<Object> extension = materializer.FieldAt(value_index);
|
| + object->set_scope_info(ScopeInfo::cast(*scope_info));
|
| + object->set_extension(*extension);
|
| + return object;
|
| + }
|
| + case FIXED_ARRAY_TYPE: {
|
| + Handle<Object> lengthObject = materializer.FieldAt(value_index);
|
| + int32_t length = 0;
|
| + CHECK(lengthObject->ToInt32(&length));
|
| + Handle<FixedArray> object = isolate_->factory()->NewFixedArray(length);
|
| + // We need to set the map, because the fixed array we are
|
| + // materializing could be a context or an arguments object,
|
| + // in which case we must retain that information.
|
| + object->set_map(*map);
|
| + slot->value_ = object;
|
| + for (int i = 0; i < length; ++i) {
|
| + Handle<Object> value = materializer.FieldAt(value_index);
|
| + object->set(i, *value);
|
| + }
|
| + return object;
|
| + }
|
| + case FIXED_DOUBLE_ARRAY_TYPE: {
|
| + DCHECK_EQ(*map, isolate_->heap()->fixed_double_array_map());
|
| + Handle<Object> lengthObject = materializer.FieldAt(value_index);
|
| + int32_t length = 0;
|
| + CHECK(lengthObject->ToInt32(&length));
|
| + Handle<FixedArrayBase> object =
|
| + isolate_->factory()->NewFixedDoubleArray(length);
|
| + slot->value_ = object;
|
| + if (length > 0) {
|
| + Handle<FixedDoubleArray> double_array =
|
| + Handle<FixedDoubleArray>::cast(object);
|
| + for (int i = 0; i < length; ++i) {
|
| + Handle<Object> value = materializer.FieldAt(value_index);
|
| + CHECK(value->IsNumber());
|
| + double_array->set(i, value->Number());
|
| + }
|
| + }
|
| + return object;
|
| + }
|
| + case STRING_TYPE:
|
| + case ONE_BYTE_STRING_TYPE:
|
| + case CONS_ONE_BYTE_STRING_TYPE:
|
| + case SLICED_STRING_TYPE:
|
| + case SLICED_ONE_BYTE_STRING_TYPE:
|
| + case EXTERNAL_STRING_TYPE:
|
| + case EXTERNAL_ONE_BYTE_STRING_TYPE:
|
| + case EXTERNAL_STRING_WITH_ONE_BYTE_DATA_TYPE:
|
| + case SHORT_EXTERNAL_STRING_TYPE:
|
| + case SHORT_EXTERNAL_ONE_BYTE_STRING_TYPE:
|
| + case SHORT_EXTERNAL_STRING_WITH_ONE_BYTE_DATA_TYPE:
|
| + case INTERNALIZED_STRING_TYPE:
|
| + case ONE_BYTE_INTERNALIZED_STRING_TYPE:
|
| + case EXTERNAL_INTERNALIZED_STRING_TYPE:
|
| + case EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
|
| + case EXTERNAL_INTERNALIZED_STRING_WITH_ONE_BYTE_DATA_TYPE:
|
| + case SHORT_EXTERNAL_INTERNALIZED_STRING_TYPE:
|
| + case SHORT_EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
|
| + case SHORT_EXTERNAL_INTERNALIZED_STRING_WITH_ONE_BYTE_DATA_TYPE:
|
| + case SYMBOL_TYPE:
|
| + case ODDBALL_TYPE:
|
| + case SIMD128_VALUE_TYPE:
|
| + case JS_GLOBAL_OBJECT_TYPE:
|
| + case JS_GLOBAL_PROXY_TYPE:
|
| + case JS_API_OBJECT_TYPE:
|
| + case JS_SPECIAL_API_OBJECT_TYPE:
|
| + case JS_VALUE_TYPE:
|
| + case JS_MESSAGE_OBJECT_TYPE:
|
| + case JS_DATE_TYPE:
|
| + case JS_CONTEXT_EXTENSION_OBJECT_TYPE:
|
| + case JS_GENERATOR_OBJECT_TYPE:
|
| + case JS_MODULE_NAMESPACE_TYPE:
|
| + case JS_ARRAY_BUFFER_TYPE:
|
| + case JS_REGEXP_TYPE:
|
| + case JS_TYPED_ARRAY_TYPE:
|
| + case JS_DATA_VIEW_TYPE:
|
| + case JS_SET_TYPE:
|
| + case JS_MAP_TYPE:
|
| + case JS_SET_ITERATOR_TYPE:
|
| + case JS_MAP_ITERATOR_TYPE:
|
| + case JS_STRING_ITERATOR_TYPE:
|
| + case JS_WEAK_MAP_TYPE:
|
| + case JS_WEAK_SET_TYPE:
|
| + case JS_PROMISE_CAPABILITY_TYPE:
|
| + case JS_PROMISE_TYPE:
|
| + case JS_BOUND_FUNCTION_TYPE:
|
| + case JS_PROXY_TYPE:
|
| + case MAP_TYPE:
|
| + case ALLOCATION_SITE_TYPE:
|
| + case ACCESSOR_INFO_TYPE:
|
| + case SHARED_FUNCTION_INFO_TYPE:
|
| + case FUNCTION_TEMPLATE_INFO_TYPE:
|
| + case ACCESSOR_PAIR_TYPE:
|
| + case BYTE_ARRAY_TYPE:
|
| + case BYTECODE_ARRAY_TYPE:
|
| + case TRANSITION_ARRAY_TYPE:
|
| + case FOREIGN_TYPE:
|
| + case SCRIPT_TYPE:
|
| + case CODE_TYPE:
|
| + case PROPERTY_CELL_TYPE:
|
| + case MODULE_TYPE:
|
| + case MODULE_INFO_ENTRY_TYPE:
|
| + case FREE_SPACE_TYPE:
|
| +#define FIXED_TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
|
| + case FIXED_##TYPE##_ARRAY_TYPE:
|
| + TYPED_ARRAYS(FIXED_TYPED_ARRAY_CASE)
|
| +#undef FIXED_TYPED_ARRAY_CASE
|
| + case FILLER_TYPE:
|
| + case ACCESS_CHECK_INFO_TYPE:
|
| + case INTERCEPTOR_INFO_TYPE:
|
| + case CALL_HANDLER_INFO_TYPE:
|
| + case OBJECT_TEMPLATE_INFO_TYPE:
|
| + case ALLOCATION_MEMENTO_TYPE:
|
| + case TYPE_FEEDBACK_INFO_TYPE:
|
| + case ALIASED_ARGUMENTS_ENTRY_TYPE:
|
| + case BOX_TYPE:
|
| + case PROMISE_RESOLVE_THENABLE_JOB_INFO_TYPE:
|
| + case PROMISE_REACTION_JOB_INFO_TYPE:
|
| + case DEBUG_INFO_TYPE:
|
| + case BREAK_POINT_INFO_TYPE:
|
| + case CELL_TYPE:
|
| + case WEAK_CELL_TYPE:
|
| + case PROTOTYPE_INFO_TYPE:
|
| + case TUPLE2_TYPE:
|
| + case TUPLE3_TYPE:
|
| + case CONSTANT_ELEMENTS_PAIR_TYPE:
|
| + OFStream os(stderr);
|
| + os << "[couldn't handle instance type " << map->instance_type() << "]"
|
| + << std::endl;
|
| + UNREACHABLE();
|
| + break;
|
| + }
|
| + UNREACHABLE();
|
| + return Handle<Object>::null();
|
| +}
|
|
|
| Handle<Object> TranslatedState::MaterializeAt(int frame_index,
|
| int* value_index) {
|
| @@ -3663,198 +3986,11 @@ Handle<Object> TranslatedState::MaterializeAt(int frame_index,
|
| return arguments;
|
| }
|
| case TranslatedValue::kCapturedObject: {
|
| - int length = slot->GetChildrenCount();
|
| -
|
| - class FieldMaterializer {
|
| - public:
|
| - FieldMaterializer(TranslatedState* state, int frame_index,
|
| - int field_count)
|
| - : state_(state),
|
| - frame_index_(frame_index),
|
| - field_count_(field_count) {}
|
| -
|
| - Handle<Object> At(int* value_index) {
|
| - CHECK(field_count_ > 0);
|
| - --field_count_;
|
| - return state_->MaterializeAt(frame_index_, value_index);
|
| - }
|
| -
|
| - ~FieldMaterializer() { CHECK_EQ(0, field_count_); }
|
| -
|
| - private:
|
| - TranslatedState* state_;
|
| - int frame_index_;
|
| - int field_count_;
|
| - };
|
| - FieldMaterializer materializer(this, frame_index, length);
|
| -
|
| // The map must be a tagged object.
|
| CHECK(frame->values_[*value_index].kind() == TranslatedValue::kTagged);
|
| -
|
| - Handle<Object> result;
|
| - if (slot->value_.ToHandle(&result)) {
|
| - // This has been previously materialized, return the previous value.
|
| - // We still need to skip all the nested objects.
|
| - for (int i = 0; i < length; i++) {
|
| - materializer.At(value_index);
|
| - }
|
| -
|
| - return result;
|
| - }
|
| -
|
| - Handle<Object> map_object = materializer.At(value_index);
|
| - Handle<Map> map = Map::GeneralizeAllFields(Handle<Map>::cast(map_object));
|
| - switch (map->instance_type()) {
|
| - case MUTABLE_HEAP_NUMBER_TYPE:
|
| - case HEAP_NUMBER_TYPE: {
|
| - // Reuse the HeapNumber value directly as it is already properly
|
| - // tagged and skip materializing the HeapNumber explicitly.
|
| - Handle<Object> object = materializer.At(value_index);
|
| - slot->value_ = object;
|
| - // On 32-bit architectures, there is an extra slot there because
|
| - // the escape analysis calculates the number of slots as
|
| - // object-size/pointer-size. To account for this, we read out
|
| - // any extra slots.
|
| - for (int i = 0; i < length - 2; i++) {
|
| - materializer.At(value_index);
|
| - }
|
| - return object;
|
| - }
|
| - case JS_OBJECT_TYPE:
|
| - case JS_ERROR_TYPE:
|
| - case JS_ARGUMENTS_TYPE: {
|
| - Handle<JSObject> object =
|
| - isolate_->factory()->NewJSObjectFromMap(map, NOT_TENURED);
|
| - slot->value_ = object;
|
| - Handle<Object> properties = materializer.At(value_index);
|
| - Handle<Object> elements = materializer.At(value_index);
|
| - object->set_properties(FixedArray::cast(*properties));
|
| - object->set_elements(FixedArrayBase::cast(*elements));
|
| - for (int i = 0; i < length - 3; ++i) {
|
| - Handle<Object> value = materializer.At(value_index);
|
| - FieldIndex index = FieldIndex::ForPropertyIndex(object->map(), i);
|
| - object->FastPropertyAtPut(index, *value);
|
| - }
|
| - return object;
|
| - }
|
| - case JS_ARRAY_TYPE: {
|
| - Handle<JSArray> object = Handle<JSArray>::cast(
|
| - isolate_->factory()->NewJSObjectFromMap(map, NOT_TENURED));
|
| - slot->value_ = object;
|
| - Handle<Object> properties = materializer.At(value_index);
|
| - Handle<Object> elements = materializer.At(value_index);
|
| - Handle<Object> length = materializer.At(value_index);
|
| - object->set_properties(FixedArray::cast(*properties));
|
| - object->set_elements(FixedArrayBase::cast(*elements));
|
| - object->set_length(*length);
|
| - return object;
|
| - }
|
| - case JS_FUNCTION_TYPE: {
|
| - Handle<SharedFunctionInfo> temporary_shared =
|
| - isolate_->factory()->NewSharedFunctionInfo(
|
| - isolate_->factory()->empty_string(), MaybeHandle<Code>(),
|
| - false);
|
| - Handle<JSFunction> object =
|
| - isolate_->factory()->NewFunctionFromSharedFunctionInfo(
|
| - map, temporary_shared, isolate_->factory()->undefined_value(),
|
| - NOT_TENURED);
|
| - slot->value_ = object;
|
| - Handle<Object> properties = materializer.At(value_index);
|
| - Handle<Object> elements = materializer.At(value_index);
|
| - Handle<Object> prototype = materializer.At(value_index);
|
| - Handle<Object> shared = materializer.At(value_index);
|
| - Handle<Object> context = materializer.At(value_index);
|
| - Handle<Object> literals = materializer.At(value_index);
|
| - Handle<Object> entry = materializer.At(value_index);
|
| - Handle<Object> next_link = materializer.At(value_index);
|
| - object->ReplaceCode(*isolate_->builtins()->CompileLazy());
|
| - object->set_map(*map);
|
| - object->set_properties(FixedArray::cast(*properties));
|
| - object->set_elements(FixedArrayBase::cast(*elements));
|
| - object->set_prototype_or_initial_map(*prototype);
|
| - object->set_shared(SharedFunctionInfo::cast(*shared));
|
| - object->set_context(Context::cast(*context));
|
| - object->set_literals(LiteralsArray::cast(*literals));
|
| - CHECK(entry->IsNumber()); // Entry to compile lazy stub.
|
| - CHECK(next_link->IsUndefined(isolate_));
|
| - return object;
|
| - }
|
| - case CONS_STRING_TYPE: {
|
| - Handle<ConsString> object = Handle<ConsString>::cast(
|
| - isolate_->factory()
|
| - ->NewConsString(isolate_->factory()->undefined_string(),
|
| - isolate_->factory()->undefined_string())
|
| - .ToHandleChecked());
|
| - slot->value_ = object;
|
| - Handle<Object> hash = materializer.At(value_index);
|
| - Handle<Object> length = materializer.At(value_index);
|
| - Handle<Object> first = materializer.At(value_index);
|
| - Handle<Object> second = materializer.At(value_index);
|
| - object->set_map(*map);
|
| - object->set_length(Smi::cast(*length)->value());
|
| - object->set_first(String::cast(*first));
|
| - object->set_second(String::cast(*second));
|
| - CHECK(hash->IsNumber()); // The {Name::kEmptyHashField} value.
|
| - return object;
|
| - }
|
| - case CONTEXT_EXTENSION_TYPE: {
|
| - Handle<ContextExtension> object =
|
| - isolate_->factory()->NewContextExtension(
|
| - isolate_->factory()->NewScopeInfo(1),
|
| - isolate_->factory()->undefined_value());
|
| - slot->value_ = object;
|
| - Handle<Object> scope_info = materializer.At(value_index);
|
| - Handle<Object> extension = materializer.At(value_index);
|
| - object->set_scope_info(ScopeInfo::cast(*scope_info));
|
| - object->set_extension(*extension);
|
| - return object;
|
| - }
|
| - case FIXED_ARRAY_TYPE: {
|
| - Handle<Object> lengthObject = materializer.At(value_index);
|
| - int32_t length = 0;
|
| - CHECK(lengthObject->ToInt32(&length));
|
| - Handle<FixedArray> object =
|
| - isolate_->factory()->NewFixedArray(length);
|
| - // We need to set the map, because the fixed array we are
|
| - // materializing could be a context or an arguments object,
|
| - // in which case we must retain that information.
|
| - object->set_map(*map);
|
| - slot->value_ = object;
|
| - for (int i = 0; i < length; ++i) {
|
| - Handle<Object> value = materializer.At(value_index);
|
| - object->set(i, *value);
|
| - }
|
| - return object;
|
| - }
|
| - case FIXED_DOUBLE_ARRAY_TYPE: {
|
| - DCHECK_EQ(*map, isolate_->heap()->fixed_double_array_map());
|
| - Handle<Object> lengthObject = materializer.At(value_index);
|
| - int32_t length = 0;
|
| - CHECK(lengthObject->ToInt32(&length));
|
| - Handle<FixedArrayBase> object =
|
| - isolate_->factory()->NewFixedDoubleArray(length);
|
| - slot->value_ = object;
|
| - if (length > 0) {
|
| - Handle<FixedDoubleArray> double_array =
|
| - Handle<FixedDoubleArray>::cast(object);
|
| - for (int i = 0; i < length; ++i) {
|
| - Handle<Object> value = materializer.At(value_index);
|
| - CHECK(value->IsNumber());
|
| - double_array->set(i, value->Number());
|
| - }
|
| - }
|
| - return object;
|
| - }
|
| - default:
|
| - PrintF(stderr, "[couldn't handle instance type %d]\n",
|
| - map->instance_type());
|
| - FATAL("unreachable");
|
| - return Handle<Object>::null();
|
| - }
|
| - UNREACHABLE();
|
| - break;
|
| + CHECK(frame->values_[*value_index].GetValue()->IsMap());
|
| + return MaterializeCapturedObjectAt(slot, frame_index, value_index);
|
| }
|
| -
|
| case TranslatedValue::kDuplicatedObject: {
|
| int object_index = slot->object_index();
|
| TranslatedState::ObjectPosition pos = object_positions_[object_index];
|
| @@ -3884,14 +4020,12 @@ Handle<Object> TranslatedState::MaterializeAt(int frame_index,
|
| return Handle<Object>::null();
|
| }
|
|
|
| -
|
| Handle<Object> TranslatedState::MaterializeObjectAt(int object_index) {
|
| CHECK_LT(static_cast<size_t>(object_index), object_positions_.size());
|
| TranslatedState::ObjectPosition pos = object_positions_[object_index];
|
| return MaterializeAt(pos.frame_index_, &(pos.value_index_));
|
| }
|
|
|
| -
|
| bool TranslatedState::GetAdaptedArguments(Handle<JSObject>* result,
|
| int frame_index) {
|
| if (frame_index == 0) {
|
| @@ -3931,7 +4065,6 @@ bool TranslatedState::GetAdaptedArguments(Handle<JSObject>* result,
|
| }
|
| }
|
|
|
| -
|
| TranslatedFrame* TranslatedState::GetArgumentsInfoFromJSFrameIndex(
|
| int jsframe_index, int* args_count) {
|
| for (size_t i = 0; i < frames_.size(); i++) {
|
| @@ -3940,7 +4073,8 @@ TranslatedFrame* TranslatedState::GetArgumentsInfoFromJSFrameIndex(
|
| if (jsframe_index > 0) {
|
| jsframe_index--;
|
| } else {
|
| - // We have the JS function frame, now check if it has arguments adaptor.
|
| + // We have the JS function frame, now check if it has arguments
|
| + // adaptor.
|
| if (i > 0 &&
|
| frames_[i - 1].kind() == TranslatedFrame::kArgumentsAdaptor) {
|
| *args_count = frames_[i - 1].height();
|
| @@ -4006,7 +4140,6 @@ void TranslatedState::StoreMaterializedValuesAndDeopt(JavaScriptFrame* frame) {
|
| }
|
| }
|
|
|
| -
|
| void TranslatedState::UpdateFromPreviouslyMaterializedObjects() {
|
| MaterializedObjectStore* materialized_store =
|
| isolate_->materialized_object_store();
|
|
|