Bug 1544386 part 1 - Call ElementAccessHasExtraIndexedProperty instead of ArrayPrototypeHasIndexedProperty when inlining array natives. r=tcampbell, a=jcristau
This simplifies the code a bit because ElementAccessHasExtraIndexedProperty
checks for length-overflow and sparse-indexes so the callers don't have to
do that anymore.
Differential Revision:
https://phabricator.services.mozilla.com/D29486
--- a/js/src/jit/MCallOptimize.cpp
+++ b/js/src/jit/MCallOptimize.cpp
@@ -922,19 +922,20 @@ IonBuilder::InliningResult IonBuilder::i
if (clasp != &ArrayObject::class_) {
return InliningStatus_NotInlined;
}
if (thisTypes->hasObjectFlags(constraints(), unhandledFlags)) {
trackOptimizationOutcome(TrackedOutcome::ArrayBadFlags);
return InliningStatus_NotInlined;
}
+ // Watch out for extra indexed properties on the object or its prototype.
bool hasIndexedProperty;
MOZ_TRY_VAR(hasIndexedProperty,
- ArrayPrototypeHasIndexedProperty(this, script()));
+ ElementAccessHasExtraIndexedProperty(this, obj));
if (hasIndexedProperty) {
trackOptimizationOutcome(TrackedOutcome::ProtoIndexedProps);
return InliningStatus_NotInlined;
}
callInfo.setImplicitlyUsedUnchecked();
obj = addMaybeCopyElementsForWrite(obj, /* checkNative = */ false);
@@ -1041,26 +1042,20 @@ IonBuilder::InliningResult IonBuilder::i
TemporaryTypeSet* thisTypes = obj->resultTypeSet();
if (!thisTypes) {
return InliningStatus_NotInlined;
}
const Class* clasp = thisTypes->getKnownClass(constraints());
if (clasp != &ArrayObject::class_) {
return InliningStatus_NotInlined;
}
- if (thisTypes->hasObjectFlags(
- constraints(),
- OBJECT_FLAG_SPARSE_INDEXES | OBJECT_FLAG_LENGTH_OVERFLOW)) {
- trackOptimizationOutcome(TrackedOutcome::ArrayBadFlags);
- return InliningStatus_NotInlined;
- }
bool hasIndexedProperty;
MOZ_TRY_VAR(hasIndexedProperty,
- ArrayPrototypeHasIndexedProperty(this, script()));
+ ElementAccessHasExtraIndexedProperty(this, obj));
if (hasIndexedProperty) {
trackOptimizationOutcome(TrackedOutcome::ProtoIndexedProps);
return InliningStatus_NotInlined;
}
TemporaryTypeSet::DoubleConversion conversion =
thisTypes->convertDoubleElements(constraints());
if (conversion == TemporaryTypeSet::AmbiguousDoubleConversion) {
@@ -1178,27 +1173,21 @@ IonBuilder::InliningResult IonBuilder::i
if (!thisTypes) {
return InliningStatus_NotInlined;
}
const Class* clasp = thisTypes->getKnownClass(constraints());
if (clasp != &ArrayObject::class_) {
return InliningStatus_NotInlined;
}
- if (thisTypes->hasObjectFlags(
- constraints(),
- OBJECT_FLAG_SPARSE_INDEXES | OBJECT_FLAG_LENGTH_OVERFLOW)) {
- trackOptimizationOutcome(TrackedOutcome::ArrayBadFlags);
- return InliningStatus_NotInlined;
- }
-
- // Watch out for indexed properties on the prototype.
+
+ // Watch out for extra indexed properties on the object or its prototype.
bool hasIndexedProperty;
MOZ_TRY_VAR(hasIndexedProperty,
- ArrayPrototypeHasIndexedProperty(this, script()));
+ ElementAccessHasExtraIndexedProperty(this, obj));
if (hasIndexedProperty) {
trackOptimizationOutcome(TrackedOutcome::ProtoIndexedProps);
return InliningStatus_NotInlined;
}
// The group of the result will be dynamically fixed up to match the input
// object, allowing us to handle 'this' objects that might have more than
// one group. Make sure that no singletons can be sliced here.
--- a/js/src/jit/MIR.cpp
+++ b/js/src/jit/MIR.cpp
@@ -5967,26 +5967,16 @@ AbortReasonOr<bool> PrototypeHasIndexedP
if (!builder->alloc().ensureBallast()) {
return builder->abort(AbortReason::Alloc);
}
} while (obj);
return false;
}
-// Whether Array.prototype, or an object on its proto chain, has an indexed
-// property.
-AbortReasonOr<bool> jit::ArrayPrototypeHasIndexedProperty(IonBuilder* builder,
- JSScript* script) {
- if (JSObject* proto = script->global().maybeGetArrayPrototype()) {
- return PrototypeHasIndexedProperty(builder, proto);
- }
- return true;
-}
-
// Whether obj or any of its prototypes have an indexed property.
AbortReasonOr<bool> jit::TypeCanHaveExtraIndexedProperties(
IonBuilder* builder, TemporaryTypeSet* types) {
const Class* clasp = types->getKnownClass(builder->constraints());
// Note: typed arrays have indexed properties not accounted for by type
// information, though these are all in bounds and will be accounted for
// by JIT paths.
--- a/js/src/jit/MIR.h
+++ b/js/src/jit/MIR.h
@@ -12138,18 +12138,16 @@ bool CanWriteProperty(TempAllocator& all
HeapTypeSetKey property, MDefinition* value,
MIRType implicitType = MIRType::None);
bool PropertyWriteNeedsTypeBarrier(TempAllocator& alloc,
CompilerConstraintList* constraints,
MBasicBlock* current, MDefinition** pobj,
PropertyName* name, MDefinition** pvalue,
bool canModify,
MIRType implicitType = MIRType::None);
-AbortReasonOr<bool> ArrayPrototypeHasIndexedProperty(IonBuilder* builder,
- JSScript* script);
AbortReasonOr<bool> TypeCanHaveExtraIndexedProperties(IonBuilder* builder,
TemporaryTypeSet* types);
inline MIRType MIRTypeForTypedArrayRead(Scalar::Type arrayType,
bool observedDouble) {
switch (arrayType) {
case Scalar::Int8:
case Scalar::Uint8: