mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
trace JSOP_CALLELEM (484334, r=mrbkap)
This commit is contained in:
parent
4017bf1be3
commit
9bee45ca8e
@ -640,6 +640,29 @@ static struct {
|
||||
/* 9*/ JSOP_STOP,
|
||||
},
|
||||
};
|
||||
static struct {
|
||||
jsbytecode callprop[12];
|
||||
jsbytecode callelem[12];
|
||||
} callelem_imacros = {
|
||||
{
|
||||
/* 0*/ JSOP_SWAP,
|
||||
/* 1*/ JSOP_DUP,
|
||||
/* 2*/ JSOP_CALLBUILTIN, ((JSBUILTIN_GetProperty) & 0xff00) >> 8, ((JSBUILTIN_GetProperty) & 0xff),
|
||||
/* 5*/ JSOP_PICK, 3,
|
||||
/* 7*/ JSOP_CALL, 0, 1,
|
||||
/*10*/ JSOP_SWAP,
|
||||
/*11*/ JSOP_STOP,
|
||||
},
|
||||
{
|
||||
/* 0*/ JSOP_SWAP,
|
||||
/* 1*/ JSOP_DUP,
|
||||
/* 2*/ JSOP_CALLBUILTIN, ((JSBUILTIN_GetElement) & 0xff00) >> 8, ((JSBUILTIN_GetElement) & 0xff),
|
||||
/* 5*/ JSOP_PICK, 3,
|
||||
/* 7*/ JSOP_CALL, 0, 1,
|
||||
/*10*/ JSOP_SWAP,
|
||||
/*11*/ JSOP_STOP,
|
||||
},
|
||||
};
|
||||
static struct {
|
||||
jsbytecode setprop[15];
|
||||
jsbytecode setelem[15];
|
||||
@ -885,7 +908,7 @@ uint8 js_opcode2extra[JSOP_LIMIT] = {
|
||||
0, /* JSOP_RESETBASE0 */
|
||||
0, /* JSOP_STARTXML */
|
||||
0, /* JSOP_STARTXMLEXPR */
|
||||
0, /* JSOP_CALLELEM */
|
||||
3, /* JSOP_CALLELEM */
|
||||
0, /* JSOP_STOP */
|
||||
0, /* JSOP_GETXPROP */
|
||||
0, /* JSOP_CALLXMLNAME */
|
||||
@ -952,4 +975,5 @@ uint8 js_opcode2extra[JSOP_LIMIT] = {
|
||||
|| x == JSOP_NEXTITER \
|
||||
|| x == JSOP_APPLY \
|
||||
|| x == JSOP_INITELEM \
|
||||
|| x == JSOP_CALLELEM \
|
||||
)
|
||||
|
@ -685,6 +685,30 @@
|
||||
|
||||
.end
|
||||
|
||||
.igroup callelem JSOP_CALLELEM
|
||||
|
||||
.imacro callprop # obj name
|
||||
swap # name obj
|
||||
dup # name obj obj
|
||||
callbuiltin (JSBUILTIN_GetProperty) # name obj fun obj
|
||||
pick 3 # obj fun obj name
|
||||
call 1 # obj propval
|
||||
swap # propval obj
|
||||
stop
|
||||
.end
|
||||
|
||||
.imacro callelem # obj i
|
||||
swap # i obj
|
||||
dup # i obj obj
|
||||
callbuiltin (JSBUILTIN_GetElement) # i obj fun obj
|
||||
pick 3 # obj fun obj i
|
||||
call 1 # obj propval
|
||||
swap # propval obj
|
||||
stop
|
||||
.end
|
||||
|
||||
.end
|
||||
|
||||
.igroup setelem JSOP_SETELEM
|
||||
|
||||
.imacro setprop # obj name val
|
||||
|
@ -6729,11 +6729,10 @@ TraceRecorder::functionCall(bool constructing, uintN argc)
|
||||
LIns* this_ins = get(&tval);
|
||||
|
||||
/*
|
||||
* If this is NULL, this is a shapeless call. If we observe a shapeless call
|
||||
* at recording time, the call at this point will always be shapeless so we
|
||||
* can make the decision based on recording-time introspection of this.
|
||||
* If callee is not constant, it's a shapeless call and we have to guard
|
||||
* explicitly that we will get this callee again at runtime.
|
||||
*/
|
||||
if (tval == JSVAL_NULL && !guardCallee(fval))
|
||||
if (!get(&fval)->isconst() && !guardCallee(fval))
|
||||
return false;
|
||||
|
||||
/*
|
||||
@ -7266,6 +7265,8 @@ JS_DEFINE_TRCINFO_1(GetElement,
|
||||
JS_REQUIRES_STACK bool
|
||||
TraceRecorder::record_JSOP_GETELEM()
|
||||
{
|
||||
bool call = js_GetOpcode(cx, cx->fp->script, cx->fp->regs->pc) == JSOP_CALLELEM;
|
||||
|
||||
jsval& idx = stackval(-1);
|
||||
jsval& lval = stackval(-2);
|
||||
|
||||
@ -7274,6 +7275,8 @@ TraceRecorder::record_JSOP_GETELEM()
|
||||
|
||||
// Special case for array-like access of strings.
|
||||
if (JSVAL_IS_STRING(lval) && isInt32(idx)) {
|
||||
if (call)
|
||||
ABORT_TRACE("JSOP_CALLELEM on a string");
|
||||
int i = asInt32(idx);
|
||||
if (size_t(i) >= JSSTRING_LENGTH(JSVAL_TO_STRING(lval)))
|
||||
ABORT_TRACE("Invalid string index in JSOP_GETELEM");
|
||||
@ -7309,7 +7312,7 @@ TraceRecorder::record_JSOP_GETELEM()
|
||||
if (!guardNotGlobalObject(obj, obj_ins))
|
||||
return false;
|
||||
|
||||
return call_imacro(getelem_imacros.getprop);
|
||||
return call_imacro(call ? callelem_imacros.callprop : getelem_imacros.getprop);
|
||||
}
|
||||
|
||||
// Invalid dense array index or not a dense array.
|
||||
@ -7317,7 +7320,7 @@ TraceRecorder::record_JSOP_GETELEM()
|
||||
if (!guardNotGlobalObject(obj, obj_ins))
|
||||
return false;
|
||||
|
||||
return call_imacro(getelem_imacros.getelem);
|
||||
return call_imacro(call ? callelem_imacros.callelem : getelem_imacros.getelem);
|
||||
}
|
||||
|
||||
// Fast path for dense arrays accessed with a non-negative integer index.
|
||||
@ -7326,6 +7329,8 @@ TraceRecorder::record_JSOP_GETELEM()
|
||||
if (!elem(lval, idx, vp, v_ins, addr_ins))
|
||||
return false;
|
||||
set(&lval, v_ins);
|
||||
if (call)
|
||||
set(&idx, obj_ins);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -9108,7 +9113,7 @@ TraceRecorder::record_JSOP_RESETBASE0()
|
||||
JS_REQUIRES_STACK bool
|
||||
TraceRecorder::record_JSOP_CALLELEM()
|
||||
{
|
||||
return false;
|
||||
return record_JSOP_GETELEM();
|
||||
}
|
||||
|
||||
JS_REQUIRES_STACK bool
|
||||
|
@ -4692,6 +4692,25 @@ testIntUnderflow.jitstats = {
|
||||
};
|
||||
test(testIntUnderflow);
|
||||
|
||||
function testCALLELEM()
|
||||
{
|
||||
function f() {
|
||||
return 5;
|
||||
}
|
||||
|
||||
function g() {
|
||||
return 7;
|
||||
}
|
||||
|
||||
var x = [f,f,f,f,g];
|
||||
var y = 0;
|
||||
for (var i = 0; i < 5; ++i)
|
||||
y = x[i]();
|
||||
return y;
|
||||
}
|
||||
testCALLELEM.expected = 7;
|
||||
test(testCALLELEM);
|
||||
|
||||
/*****************************************************************************
|
||||
* *
|
||||
* _____ _ _ _____ ______ _____ _______ *
|
||||
|
Loading…
Reference in New Issue
Block a user