mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 1147216 part 1 - Give JSOP_LINENO a 4-byte instead of 2-byte operand. r=luke
This commit is contained in:
parent
db3b77867f
commit
00300d588d
@ -523,15 +523,26 @@ BytecodeEmitter::checkTypeSet(JSOp op)
|
||||
}
|
||||
|
||||
bool
|
||||
BytecodeEmitter::emitUint16Operand(JSOp op, uint32_t i)
|
||||
BytecodeEmitter::emitUint16Operand(JSOp op, uint32_t operand)
|
||||
{
|
||||
MOZ_ASSERT(i <= UINT16_MAX);
|
||||
if (!emit3(op, UINT16_HI(i), UINT16_LO(i)))
|
||||
MOZ_ASSERT(operand <= UINT16_MAX);
|
||||
if (!emit3(op, UINT16_HI(operand), UINT16_LO(operand)))
|
||||
return false;
|
||||
checkTypeSet(op);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
BytecodeEmitter::emitUint32Operand(JSOp op, uint32_t operand)
|
||||
{
|
||||
ptrdiff_t off;
|
||||
if (!emitN(op, 4, &off))
|
||||
return false;
|
||||
SET_UINT32(code(off), operand);
|
||||
checkTypeSet(op);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
BytecodeEmitter::flushPops(int* npops)
|
||||
{
|
||||
@ -6426,7 +6437,7 @@ BytecodeEmitter::emitCallOrNew(ParseNode* pn)
|
||||
pn->isOp(JSOP_STRICTSPREADEVAL))
|
||||
{
|
||||
uint32_t lineNum = parser->tokenStream.srcCoords.lineNum(pn->pn_pos.begin);
|
||||
if (!emitUint16Operand(JSOP_LINENO, lineNum))
|
||||
if (!emitUint32Operand(JSOP_LINENO, lineNum))
|
||||
return false;
|
||||
}
|
||||
if (pn->pn_xflags & PNX_SETCALL) {
|
||||
|
@ -397,7 +397,10 @@ struct BytecodeEmitter
|
||||
|
||||
// Emit a bytecode followed by an uint16 immediate operand stored in
|
||||
// big-endian order.
|
||||
bool emitUint16Operand(JSOp op, uint32_t i);
|
||||
bool emitUint16Operand(JSOp op, uint32_t operand);
|
||||
|
||||
// Emit a bytecode followed by an uint32 immediate operand.
|
||||
bool emitUint32Operand(JSOp op, uint32_t operand);
|
||||
|
||||
// Emit (1 + extra) bytecodes, for N bytes of op and its immediate operand.
|
||||
bool emitN(JSOp op, size_t extra, ptrdiff_t* offset = nullptr);
|
||||
|
14
js/src/jit-test/tests/basic/bug1147216.js
Normal file
14
js/src/jit-test/tests/basic/bug1147216.js
Normal file
@ -0,0 +1,14 @@
|
||||
// Ensure JSOP_LINENO (emitted after JSOP_EVAL) handles big line
|
||||
// numbers correctly.
|
||||
function f() {
|
||||
var s = "";
|
||||
var stack;
|
||||
for (var i=0; i<66002; i++) {
|
||||
s += "\n";
|
||||
if (i === 66000)
|
||||
s += "eval('stack = Error().stack');";
|
||||
}
|
||||
eval(s);
|
||||
assertEq(stack.indexOf("line 66002") > 0, true);
|
||||
}
|
||||
f();
|
@ -1041,6 +1041,10 @@ js::Disassemble1(JSContext* cx, HandleScript script, jsbytecode* pc,
|
||||
Sprint(sp, " %u", GET_LOCALNO(pc));
|
||||
break;
|
||||
|
||||
case JOF_UINT32:
|
||||
Sprint(sp, " %u", GET_UINT32(pc));
|
||||
break;
|
||||
|
||||
{
|
||||
int i;
|
||||
|
||||
|
@ -48,8 +48,8 @@ enum {
|
||||
JOF_UINT8 = 13, /* uint8_t immediate, e.g. top 8 bits of 24-bit
|
||||
atom index */
|
||||
JOF_INT32 = 14, /* int32_t immediate operand */
|
||||
JOF_OBJECT = 15, /* unsigned 16-bit object index */
|
||||
/* 16 is unused */
|
||||
JOF_UINT32 = 15, /* uint32_t immediate operand */
|
||||
JOF_OBJECT = 16, /* unsigned 16-bit object index */
|
||||
JOF_REGEXP = 17, /* unsigned 32-bit regexp index */
|
||||
JOF_INT8 = 18, /* int8_t immediate operand */
|
||||
JOF_ATOMOBJECT = 19, /* uint16_t constant index + object index */
|
||||
@ -222,8 +222,8 @@ GET_INT8(const jsbytecode* pc)
|
||||
return int8_t(pc[1]);
|
||||
}
|
||||
|
||||
static MOZ_ALWAYS_INLINE int32_t
|
||||
GET_INT32(const jsbytecode* pc)
|
||||
static MOZ_ALWAYS_INLINE uint32_t
|
||||
GET_UINT32(const jsbytecode* pc)
|
||||
{
|
||||
return (uint32_t(pc[1]) << 24) |
|
||||
(uint32_t(pc[2]) << 16) |
|
||||
@ -232,12 +232,24 @@ GET_INT32(const jsbytecode* pc)
|
||||
}
|
||||
|
||||
static MOZ_ALWAYS_INLINE void
|
||||
SET_INT32(jsbytecode* pc, uint32_t i)
|
||||
SET_UINT32(jsbytecode* pc, uint32_t u)
|
||||
{
|
||||
pc[1] = jsbytecode(uint32_t(i) >> 24);
|
||||
pc[2] = jsbytecode(uint32_t(i) >> 16);
|
||||
pc[3] = jsbytecode(uint32_t(i) >> 8);
|
||||
pc[4] = jsbytecode(uint32_t(i));
|
||||
pc[1] = jsbytecode(u >> 24);
|
||||
pc[2] = jsbytecode(u >> 16);
|
||||
pc[3] = jsbytecode(u >> 8);
|
||||
pc[4] = jsbytecode(u);
|
||||
}
|
||||
|
||||
static MOZ_ALWAYS_INLINE int32_t
|
||||
GET_INT32(const jsbytecode* pc)
|
||||
{
|
||||
return static_cast<int32_t>(GET_UINT32(pc));
|
||||
}
|
||||
|
||||
static MOZ_ALWAYS_INLINE void
|
||||
SET_INT32(jsbytecode* pc, int32_t i)
|
||||
{
|
||||
SET_UINT32(pc, static_cast<uint32_t>(i));
|
||||
}
|
||||
|
||||
/* Index limit is determined by SN_4BYTE_OFFSET_FLAG, see frontend/BytecodeEmitter.h. */
|
||||
|
@ -2928,7 +2928,7 @@ js::DescribeScriptedCallerForCompilation(JSContext* cx, MutableHandleScript mayb
|
||||
JSOp(*pc) == JSOP_STRICTSPREADEVAL;
|
||||
MOZ_ASSERT(*(pc + (isSpread ? JSOP_SPREADEVAL_LENGTH : JSOP_EVAL_LENGTH)) == JSOP_LINENO);
|
||||
*file = maybeScript->filename();
|
||||
*linenop = GET_UINT16(pc + (JSOp(*pc) == JSOP_EVAL ? JSOP_EVAL_LENGTH
|
||||
*linenop = GET_UINT32(pc + (JSOp(*pc) == JSOP_EVAL ? JSOP_EVAL_LENGTH
|
||||
: JSOP_SPREADEVAL_LENGTH));
|
||||
*pcOffset = pc - maybeScript->code();
|
||||
*mutedErrors = maybeScript->mutedErrors();
|
||||
|
@ -1166,7 +1166,7 @@
|
||||
* Operands: uint32_t lineno
|
||||
* Stack: =>
|
||||
*/ \
|
||||
macro(JSOP_LINENO, 119,"lineno", NULL, 3, 0, 0, JOF_UINT16) \
|
||||
macro(JSOP_LINENO, 119,"lineno", NULL, 5, 0, 0, JOF_UINT32) \
|
||||
\
|
||||
/*
|
||||
* This no-op appears after the bytecode for EXPR in 'switch (EXPR) {...}'
|
||||
|
@ -29,7 +29,7 @@ namespace js {
|
||||
*
|
||||
* https://developer.mozilla.org/en-US/docs/SpiderMonkey/Internals/Bytecode
|
||||
*/
|
||||
static const uint32_t XDR_BYTECODE_VERSION_SUBTRAHEND = 275;
|
||||
static const uint32_t XDR_BYTECODE_VERSION_SUBTRAHEND = 276;
|
||||
static const uint32_t XDR_BYTECODE_VERSION =
|
||||
uint32_t(0xb973c0de - XDR_BYTECODE_VERSION_SUBTRAHEND);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user