mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-09 03:15:11 +00:00
Fix model stack management for catch guards in the decompiler; eliminate related SRC_HIDDEN abusage (375794, r=igor).
This commit is contained in:
parent
60a0ed8c0b
commit
70efc15226
@ -5089,12 +5089,8 @@ js_EmitTree(JSContext *cx, JSCodeGenerator *cg, JSParseNode *pn)
|
||||
* Dup the exception object if there is a guard for rethrowing to use
|
||||
* it later when rethrowing or in other catches.
|
||||
*/
|
||||
if (pn->pn_kid2) {
|
||||
if (js_NewSrcNote(cx, cg, SRC_HIDDEN) < 0 ||
|
||||
js_Emit1(cx, cg, JSOP_DUP) < 0) {
|
||||
return JS_FALSE;
|
||||
}
|
||||
}
|
||||
if (pn->pn_kid2 && js_Emit1(cx, cg, JSOP_DUP) < 0)
|
||||
return JS_FALSE;
|
||||
|
||||
pn2 = pn->pn_kid1;
|
||||
switch (pn2->pn_type) {
|
||||
|
@ -1623,8 +1623,8 @@ Decompile(SprintStack *ss, jsbytecode *pc, intN nb)
|
||||
*/
|
||||
#define ATOM_IS_IDENTIFIER(atom) js_IsIdentifier(ATOM_TO_STRING(atom))
|
||||
#define ATOM_IS_KEYWORD(atom) \
|
||||
(js_CheckKeyword(JSSTRING_CHARS(ATOM_TO_STRING(atom)), \
|
||||
JSSTRING_LENGTH(ATOM_TO_STRING(atom))) != TOK_EOF)
|
||||
(js_CheckKeyword(JSSTRING_CHARS(ATOM_TO_STRING(atom)), \
|
||||
JSSTRING_LENGTH(ATOM_TO_STRING(atom))) != TOK_EOF)
|
||||
|
||||
/*
|
||||
* Given an atom already fetched from jp->script's atom map, quote/escape its
|
||||
@ -2431,18 +2431,31 @@ Decompile(SprintStack *ss, jsbytecode *pc, intN nb)
|
||||
pc += oplen;
|
||||
LOCAL_ASSERT(*pc == JSOP_EXCEPTION);
|
||||
pc += JSOP_EXCEPTION_LENGTH;
|
||||
todo = Sprint(&ss->sprinter, exception_cookie);
|
||||
if (todo < 0 || !PushOff(ss, todo, JSOP_EXCEPTION)) {
|
||||
ok = JS_FALSE;
|
||||
goto enterblock_out;
|
||||
}
|
||||
|
||||
if (*pc == JSOP_DUP) {
|
||||
sn2 = js_GetSrcNote(jp->script, pc);
|
||||
if (sn2 && SN_TYPE(sn2) == SRC_HIDDEN) {
|
||||
if (!sn2 || SN_TYPE(sn2) != SRC_DESTRUCT) {
|
||||
/*
|
||||
* This is a hidden dup to save the exception for
|
||||
* later. It must exist only when the catch has
|
||||
* This is a dup to save the exception for later.
|
||||
* It is emitted only when the catch head contains
|
||||
* an exception guard.
|
||||
*/
|
||||
LOCAL_ASSERT(js_GetSrcNoteOffset(sn, 0) != 0);
|
||||
pc += JSOP_DUP_LENGTH;
|
||||
todo = Sprint(&ss->sprinter, exception_cookie);
|
||||
if (todo < 0 ||
|
||||
!PushOff(ss, todo, JSOP_EXCEPTION)) {
|
||||
ok = JS_FALSE;
|
||||
goto enterblock_out;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if JS_HAS_DESTRUCTURING
|
||||
if (*pc == JSOP_DUP) {
|
||||
pc = DecompileDestructuring(ss, pc, endpc);
|
||||
@ -2459,6 +2472,7 @@ Decompile(SprintStack *ss, jsbytecode *pc, intN nb)
|
||||
LOCAL_ASSERT(*pc == JSOP_SETLOCALPOP);
|
||||
i = GET_UINT16(pc);
|
||||
pc += JSOP_SETLOCALPOP_LENGTH;
|
||||
(void) PopOff(ss, JSOP_NOP);
|
||||
atom = atomv[i - OBJ_BLOCK_DEPTH(cx, obj)];
|
||||
str = ATOM_TO_STRING(atom);
|
||||
if (!QuoteString(&jp->sprinter, str, 0)) {
|
||||
@ -2513,8 +2527,21 @@ Decompile(SprintStack *ss, jsbytecode *pc, intN nb)
|
||||
LOCAL_ASSERT(op == JSOP_LEAVEBLOCK);
|
||||
if (SN_TYPE(sn) == SRC_HIDDEN)
|
||||
break;
|
||||
|
||||
/*
|
||||
* This JSOP_LEAVEBLOCK must be for a catch block. If sn's
|
||||
* offset does not equal the model stack depth, there must
|
||||
* be a copy of the exception value on the stack due to a
|
||||
* catch guard (see above, the JSOP_ENTERBLOCK + SRC_CATCH
|
||||
* case code).
|
||||
*/
|
||||
LOCAL_ASSERT(SN_TYPE(sn) == SRC_CATCH);
|
||||
LOCAL_ASSERT((uintN)js_GetSrcNoteOffset(sn, 0) == ss->top);
|
||||
if ((uintN)js_GetSrcNoteOffset(sn, 0) != ss->top) {
|
||||
LOCAL_ASSERT((uintN)js_GetSrcNoteOffset(sn, 0)
|
||||
== ss->top - 1);
|
||||
rval = POP_STR();
|
||||
LOCAL_ASSERT(strcmp(rval, exception_cookie) == 0);
|
||||
}
|
||||
}
|
||||
top = ss->top;
|
||||
depth = GET_UINT16(pc);
|
||||
|
Loading…
Reference in New Issue
Block a user