aboutsummaryrefslogtreecommitdiff
path: root/deps/v8/src/compiler/access-info.cc
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/compiler/access-info.cc')
-rw-r--r--deps/v8/src/compiler/access-info.cc118
1 files changed, 72 insertions, 46 deletions
diff --git a/deps/v8/src/compiler/access-info.cc b/deps/v8/src/compiler/access-info.cc
index 97de25bd4c..329cb93fe5 100644
--- a/deps/v8/src/compiler/access-info.cc
+++ b/deps/v8/src/compiler/access-info.cc
@@ -7,10 +7,10 @@
#include "src/accessors.h"
#include "src/compilation-dependencies.h"
#include "src/compiler/access-info.h"
+#include "src/compiler/type-cache.h"
#include "src/field-index-inl.h"
#include "src/field-type.h"
#include "src/objects-inl.h"
-#include "src/type-cache.h"
namespace v8 {
namespace internal {
@@ -79,9 +79,12 @@ PropertyAccessInfo PropertyAccessInfo::DataConstant(
// static
PropertyAccessInfo PropertyAccessInfo::DataField(
- MapList const& receiver_maps, FieldIndex field_index, Type* field_type,
- MaybeHandle<JSObject> holder, MaybeHandle<Map> transition_map) {
- return PropertyAccessInfo(holder, transition_map, field_index, field_type,
+ MapList const& receiver_maps, FieldIndex field_index,
+ MachineRepresentation field_representation, Type* field_type,
+ MaybeHandle<Map> field_map, MaybeHandle<JSObject> holder,
+ MaybeHandle<Map> transition_map) {
+ return PropertyAccessInfo(holder, transition_map, field_index,
+ field_representation, field_type, field_map,
receiver_maps);
}
@@ -93,13 +96,16 @@ PropertyAccessInfo PropertyAccessInfo::AccessorConstant(
}
PropertyAccessInfo::PropertyAccessInfo()
- : kind_(kInvalid), field_type_(Type::None()) {}
+ : kind_(kInvalid),
+ field_representation_(MachineRepresentation::kNone),
+ field_type_(Type::None()) {}
PropertyAccessInfo::PropertyAccessInfo(MaybeHandle<JSObject> holder,
MapList const& receiver_maps)
: kind_(kNotFound),
receiver_maps_(receiver_maps),
holder_(holder),
+ field_representation_(MachineRepresentation::kNone),
field_type_(Type::None()) {}
PropertyAccessInfo::PropertyAccessInfo(Kind kind, MaybeHandle<JSObject> holder,
@@ -109,18 +115,21 @@ PropertyAccessInfo::PropertyAccessInfo(Kind kind, MaybeHandle<JSObject> holder,
receiver_maps_(receiver_maps),
constant_(constant),
holder_(holder),
+ field_representation_(MachineRepresentation::kNone),
field_type_(Type::Any()) {}
-PropertyAccessInfo::PropertyAccessInfo(MaybeHandle<JSObject> holder,
- MaybeHandle<Map> transition_map,
- FieldIndex field_index, Type* field_type,
- MapList const& receiver_maps)
+PropertyAccessInfo::PropertyAccessInfo(
+ MaybeHandle<JSObject> holder, MaybeHandle<Map> transition_map,
+ FieldIndex field_index, MachineRepresentation field_representation,
+ Type* field_type, MaybeHandle<Map> field_map, MapList const& receiver_maps)
: kind_(kDataField),
receiver_maps_(receiver_maps),
transition_map_(transition_map),
holder_(holder),
field_index_(field_index),
- field_type_(field_type) {}
+ field_representation_(field_representation),
+ field_type_(field_type),
+ field_map_(field_map) {}
bool PropertyAccessInfo::Merge(PropertyAccessInfo const* that) {
if (this->kind_ != that->kind_) return false;
@@ -138,7 +147,8 @@ bool PropertyAccessInfo::Merge(PropertyAccessInfo const* that) {
if (this->transition_map_.address() == that->transition_map_.address() &&
this->field_index_ == that->field_index_ &&
this->field_type_->Is(that->field_type_) &&
- that->field_type_->Is(this->field_type_)) {
+ that->field_type_->Is(this->field_type_) &&
+ this->field_representation_ == that->field_representation_) {
this->receiver_maps_.insert(this->receiver_maps_.end(),
that->receiver_maps_.begin(),
that->receiver_maps_.end());
@@ -283,41 +293,45 @@ bool AccessInfoFactory::ComputePropertyAccessInfo(
}
case DATA: {
int index = descriptors->GetFieldIndex(number);
- Representation field_representation = details.representation();
+ Representation details_representation = details.representation();
FieldIndex field_index = FieldIndex::ForPropertyIndex(
- *map, index, field_representation.IsDouble());
- Type* field_type = Type::Tagged();
- if (field_representation.IsSmi()) {
+ *map, index, details_representation.IsDouble());
+ Type* field_type = Type::NonInternal();
+ MachineRepresentation field_representation =
+ MachineRepresentation::kTagged;
+ MaybeHandle<Map> field_map;
+ if (details_representation.IsSmi()) {
field_type = type_cache_.kSmi;
- } else if (field_representation.IsDouble()) {
+ field_representation = MachineRepresentation::kTaggedSigned;
+ } else if (details_representation.IsDouble()) {
field_type = type_cache_.kFloat64;
- } else if (field_representation.IsHeapObject()) {
+ field_representation = MachineRepresentation::kFloat64;
+ } else if (details_representation.IsHeapObject()) {
// Extract the field type from the property details (make sure its
// representation is TaggedPointer to reflect the heap object case).
- field_type = Type::Intersect(
- descriptors->GetFieldType(number)->Convert(zone()),
- Type::TaggedPointer(), zone());
- if (field_type->Is(Type::None())) {
+ field_representation = MachineRepresentation::kTaggedPointer;
+ Handle<FieldType> descriptors_field_type(
+ descriptors->GetFieldType(number), isolate());
+ if (descriptors_field_type->IsNone()) {
// Store is not safe if the field type was cleared.
if (access_mode == AccessMode::kStore) return false;
// The field type was cleared by the GC, so we don't know anything
// about the contents now.
- // TODO(bmeurer): It would be awesome to make this saner in the
- // runtime/GC interaction.
- field_type = Type::TaggedPointer();
- } else if (!Type::Any()->Is(field_type)) {
+ } else if (descriptors_field_type->IsClass()) {
// Add proper code dependencies in case of stable field map(s).
Handle<Map> field_owner_map(map->FindFieldOwner(number),
isolate());
dependencies()->AssumeFieldType(field_owner_map);
- }
- if (access_mode == AccessMode::kLoad) {
- field_type = Type::Any();
+
+ // Remember the field map, and try to infer a useful type.
+ field_type = Type::For(descriptors_field_type->AsClass());
+ field_map = descriptors_field_type->AsClass();
}
}
*access_info = PropertyAccessInfo::DataField(
- MapList{receiver_map}, field_index, field_type, holder);
+ MapList{receiver_map}, field_index, field_representation,
+ field_type, field_map, holder);
return true;
}
case ACCESSOR_CONSTANT: {
@@ -423,12 +437,14 @@ bool AccessInfoFactory::LookupSpecialFieldAccessor(
int offset;
if (Accessors::IsJSObjectFieldAccessor(map, name, &offset)) {
FieldIndex field_index = FieldIndex::ForInObjectOffset(offset);
- Type* field_type = Type::Tagged();
+ Type* field_type = Type::NonInternal();
+ MachineRepresentation field_representation = MachineRepresentation::kTagged;
if (map->IsStringMap()) {
DCHECK(Name::Equals(factory()->length_string(), name));
// The String::length property is always a smi in the range
// [0, String::kMaxLength].
field_type = type_cache_.kStringLengthType;
+ field_representation = MachineRepresentation::kTaggedSigned;
} else if (map->IsJSArrayMap()) {
DCHECK(Name::Equals(factory()->length_string(), name));
// The JSArray::length property is a smi in the range
@@ -438,14 +454,16 @@ bool AccessInfoFactory::LookupSpecialFieldAccessor(
// case of other arrays.
if (IsFastDoubleElementsKind(map->elements_kind())) {
field_type = type_cache_.kFixedDoubleArrayLengthType;
+ field_representation = MachineRepresentation::kTaggedSigned;
} else if (IsFastElementsKind(map->elements_kind())) {
field_type = type_cache_.kFixedArrayLengthType;
+ field_representation = MachineRepresentation::kTaggedSigned;
} else {
field_type = type_cache_.kJSArrayLengthType;
}
}
- *access_info =
- PropertyAccessInfo::DataField(MapList{map}, field_index, field_type);
+ *access_info = PropertyAccessInfo::DataField(
+ MapList{map}, field_index, field_representation, field_type);
return true;
}
return false;
@@ -468,35 +486,43 @@ bool AccessInfoFactory::LookupTransition(Handle<Map> map, Handle<Name> name,
// TODO(bmeurer): Handle transition to data constant?
if (details.type() != DATA) return false;
int const index = details.field_index();
- Representation field_representation = details.representation();
+ Representation details_representation = details.representation();
FieldIndex field_index = FieldIndex::ForPropertyIndex(
- *transition_map, index, field_representation.IsDouble());
- Type* field_type = Type::Tagged();
- if (field_representation.IsSmi()) {
+ *transition_map, index, details_representation.IsDouble());
+ Type* field_type = Type::NonInternal();
+ MaybeHandle<Map> field_map;
+ MachineRepresentation field_representation = MachineRepresentation::kTagged;
+ if (details_representation.IsSmi()) {
field_type = type_cache_.kSmi;
- } else if (field_representation.IsDouble()) {
+ field_representation = MachineRepresentation::kTaggedSigned;
+ } else if (details_representation.IsDouble()) {
field_type = type_cache_.kFloat64;
- } else if (field_representation.IsHeapObject()) {
+ field_representation = MachineRepresentation::kFloat64;
+ } else if (details_representation.IsHeapObject()) {
// Extract the field type from the property details (make sure its
// representation is TaggedPointer to reflect the heap object case).
- field_type = Type::Intersect(
- transition_map->instance_descriptors()->GetFieldType(number)->Convert(
- zone()),
- Type::TaggedPointer(), zone());
- if (field_type->Is(Type::None())) {
+ field_representation = MachineRepresentation::kTaggedPointer;
+ Handle<FieldType> descriptors_field_type(
+ transition_map->instance_descriptors()->GetFieldType(number),
+ isolate());
+ if (descriptors_field_type->IsNone()) {
// Store is not safe if the field type was cleared.
return false;
- } else if (!Type::Any()->Is(field_type)) {
+ } else if (descriptors_field_type->IsClass()) {
// Add proper code dependencies in case of stable field map(s).
Handle<Map> field_owner_map(transition_map->FindFieldOwner(number),
isolate());
dependencies()->AssumeFieldType(field_owner_map);
+
+ // Remember the field map, and try to infer a useful type.
+ field_type = Type::For(descriptors_field_type->AsClass());
+ field_map = descriptors_field_type->AsClass();
}
- DCHECK(field_type->Is(Type::TaggedPointer()));
}
dependencies()->AssumeMapNotDeprecated(transition_map);
*access_info = PropertyAccessInfo::DataField(
- MapList{map}, field_index, field_type, holder, transition_map);
+ MapList{map}, field_index, field_representation, field_type, field_map,
+ holder, transition_map);
return true;
}
return false;