Bug 1165053 - Part 0.2: Inline PossiblyWrappedArrayBufferByteLength self-hosting intrinsic. r=jwalden

This commit is contained in:
Tooru Fujisawa 2016-03-05 18:56:36 +09:00
parent 2e027fb88d
commit 863f2c7e9c
6 changed files with 97 additions and 1 deletions

View File

@ -0,0 +1,41 @@
var PossiblyWrappedArrayBufferByteLength = getSelfHostedValue("PossiblyWrappedArrayBufferByteLength");
setJitCompilerOption("ion.warmup.trigger", 50);
function testBasic() {
var arr = [1, 2, 3];
var tarr = new Int32Array(arr);
var abuf = tarr.buffer;
var arrLength = arr.length;
var bytesPerElement = Int32Array.BYTES_PER_ELEMENT;
var f = function() {
assertEq(PossiblyWrappedArrayBufferByteLength(abuf), arrLength * bytesPerElement);
};
do {
f();
} while (!inIon());
}
testBasic();
function testWrapped() {
var g = newGlobal();
g.eval(`
var arr = [1, 2, 3];
var tarr = new Int32Array(arr);
var abuf = tarr.buffer;
`);
var abuf = g.abuf;
var arrLength = g.arr.length;
var bytesPerElement = g.Int32Array.BYTES_PER_ELEMENT;
var f = function() {
assertEq(PossiblyWrappedArrayBufferByteLength(abuf), arrLength * bytesPerElement);
};
do {
f();
} while (!inIon());
}
testWrapped();

View File

@ -111,6 +111,8 @@
\
_(IntrinsicGetNextMapEntryForIterator) \
\
_(IntrinsicPossiblyWrappedArrayBufferByteLength) \
\
_(IntrinsicIsTypedArray) \
_(IntrinsicIsPossiblyWrappedTypedArray) \
_(IntrinsicTypedArrayLength) \

View File

@ -9500,6 +9500,15 @@ IonBuilder::jsop_getelem_dense(MDefinition* obj, MDefinition* index, JSValueType
return pushTypeBarrier(load, types, barrier);
}
MInstruction*
IonBuilder::addArrayBufferByteLength(MDefinition* obj)
{
MLoadFixedSlot* ins = MLoadFixedSlot::New(alloc(), obj, ArrayBufferObject::BYTE_LENGTH_SLOT);
current->add(ins);
ins->setResultType(MIRType_Int32);
return ins;
}
void
IonBuilder::addTypedArrayLengthAndData(MDefinition* obj,
BoundsChecking checking,

View File

@ -623,6 +623,8 @@ class IonBuilder
enum BoundsChecking { DoBoundsCheck, SkipBoundsCheck };
MInstruction* addArrayBufferByteLength(MDefinition* obj);
// Add instructions to compute a typed array's length and data. Also
// optionally convert |*index| into a bounds-checked definition, if
// requested.
@ -844,6 +846,9 @@ class IonBuilder
// Map intrinsics.
InliningStatus inlineGetNextMapEntryForIterator(CallInfo& callInfo);
// ArrayBuffer intrinsics.
InliningStatus inlinePossiblyWrappedArrayBufferByteLength(CallInfo& callInfo);
// TypedArray intrinsics.
enum WrappingBehavior { AllowWrappedTypedArrays, RejectWrappedTypedArrays };
InliningStatus inlineIsTypedArrayHelper(CallInfo& callInfo, WrappingBehavior wrappingBehavior);

View File

@ -264,6 +264,10 @@ IonBuilder::inlineNativeCall(CallInfo& callInfo, JSFunction* target)
case InlinableNative::IntrinsicGetNextMapEntryForIterator:
return inlineGetNextMapEntryForIterator(callInfo);
// ArrayBuffer intrinsics.
case InlinableNative::IntrinsicPossiblyWrappedArrayBufferByteLength:
return inlinePossiblyWrappedArrayBufferByteLength(callInfo);
// TypedArray intrinsics.
case InlinableNative::IntrinsicIsTypedArray:
return inlineIsTypedArray(callInfo);
@ -2234,6 +2238,40 @@ IonBuilder::inlineGetNextMapEntryForIterator(CallInfo& callInfo)
return InliningStatus_Inlined;
}
static bool
IsArrayBufferObject(CompilerConstraintList* constraints, MDefinition* def)
{
MOZ_ASSERT(def->type() == MIRType_Object);
TemporaryTypeSet* types = def->resultTypeSet();
if (!types)
return false;
return types->getKnownClass(constraints) == &ArrayBufferObject::class_;
}
IonBuilder::InliningStatus
IonBuilder::inlinePossiblyWrappedArrayBufferByteLength(CallInfo& callInfo)
{
MOZ_ASSERT(!callInfo.constructing());
MOZ_ASSERT(callInfo.argc() == 1);
MDefinition* objArg = callInfo.getArg(0);
if (objArg->type() != MIRType_Object)
return InliningStatus_NotInlined;
if (getInlineReturnType() != MIRType_Int32)
return InliningStatus_NotInlined;
if (!IsArrayBufferObject(constraints(), objArg))
return InliningStatus_NotInlined;
MInstruction* ins = addArrayBufferByteLength(objArg);
current->push(ins);
callInfo.setImplicitlyUsedUnchecked();
return InliningStatus_Inlined;
}
IonBuilder::InliningStatus
IonBuilder::inlineIsTypedArrayHelper(CallInfo& callInfo, WrappingBehavior wrappingBehavior)
{

View File

@ -2169,7 +2169,8 @@ static const JSFunctionSpec intrinsic_functions[] = {
intrinsic_IsInstanceOfBuiltin<SharedArrayBufferObject>, 1,0),
JS_FN("ArrayBufferByteLength", intrinsic_ArrayBufferByteLength, 1,0),
JS_FN("PossiblyWrappedArrayBufferByteLength", intrinsic_PossiblyWrappedArrayBufferByteLength, 1,0),
JS_INLINABLE_FN("PossiblyWrappedArrayBufferByteLength", intrinsic_PossiblyWrappedArrayBufferByteLength, 1,0,
IntrinsicPossiblyWrappedArrayBufferByteLength),
JS_FN("ArrayBufferCopyData", intrinsic_ArrayBufferCopyData, 4,0),
JS_FN("IsUint8TypedArray", intrinsic_IsUint8TypedArray, 1,0),