Changeset 33329

Show
Ignore:
Timestamp:
05/12/08 23:03:35 (6 months ago)
Author:
mrowe@apple.com
Message:

2008-05-03 Geoffrey Garen <ggaren@apple.com>

Reviewed by Sam Weinig.

Update ExecState::m_scopeChain when switching scope chains inside the
machine.

This fixes uses of lexicalGlobalObject, such as, in a subframe

alert(top.makeArray() instanceof Array ? "FAIL" : "PASS");

and a bunch of the security failures listed in
https://bugs.webkit.org/show_bug.cgi?id=18870. (Those tests still fail,
seemingly because of regressions in exception messages).

SunSpider reports no change.

  • VM/Machine.cpp: Factored out scope chain updating into a common function that takes care to update ExecState::m_scopeChain, too.
  • kjs/ExecState.h: I made Machine a friend of ExecState so that Machine could update ExecState::m_scopeChain, even though that value is read-only for everyone else.
  • kjs/JSGlobalObject.h: (KJS::JSGlobalObject::JSGlobalObjectData::JSGlobalObjectData): Changed this client to be a little friendlier to ExecState's internal storage type for scope chain data.
Location:
branches/squirrelfish/JavaScriptCore
Files:
8 modified

Legend:

Unmodified
Added
Removed
  • branches/squirrelfish/JavaScriptCore/ChangeLog

    r33328 r33329  
     12008-05-03  Geoffrey Garen  <ggaren@apple.com> 
     2 
     3        Reviewed by Sam Weinig. 
     4         
     5        Update ExecState::m_scopeChain when switching scope chains inside the 
     6        machine. 
     7         
     8        This fixes uses of lexicalGlobalObject, such as, in a subframe 
     9 
     10            alert(top.makeArray() instanceof Array ? "FAIL" : "PASS"); 
     11         
     12        and a bunch of the security failures listed in 
     13        https://bugs.webkit.org/show_bug.cgi?id=18870. (Those tests still fail, 
     14        seemingly because of regressions in exception messages). 
     15         
     16        SunSpider reports no change. 
     17 
     18        * VM/Machine.cpp: Factored out scope chain updating into a common 
     19        function that takes care to update ExecState::m_scopeChain, too. 
     20 
     21        * kjs/ExecState.h: I made Machine a friend of ExecState so that Machine 
     22        could update ExecState::m_scopeChain, even though that value is 
     23        read-only for everyone else. 
     24 
     25        * kjs/JSGlobalObject.h: 
     26        (KJS::JSGlobalObject::JSGlobalObjectData::JSGlobalObjectData): Changed 
     27        this client to be a little friendlier to ExecState's internal 
     28        storage type for scope chain data. 
     29 
    1302008-05-03  Geoffrey Garen  <ggaren@apple.com> 
    231 
  • branches/squirrelfish/JavaScriptCore/JavaScriptCore.exp

    r33327 r33329  
    208208__ZN3KJS9Collector7protectEPNS_7JSValueE 
    209209__ZN3KJS9Collector9unprotectEPNS_7JSValueE 
    210 __ZN3KJS9ExecStateC1EPNS_14JSGlobalObjectEPNS_8JSObjectERNS_10ScopeChainE 
     210__ZN3KJS9ExecStateC1EPNS_14JSGlobalObjectEPNS_8JSObjectEPNS_14ScopeChainNodeE 
    211211__ZN3KJSeqERKNS_7UStringEPKc 
    212212__ZN3WTF10fastCallocEmm 
  • branches/squirrelfish/JavaScriptCore/VM/Machine.cpp

    r33328 r33329  
    503503    while (scopeDelta--) 
    504504        sc.pop(); 
    505     scopeChain = sc.node(); 
     505    setScopeChain(exec, scopeChain, sc.node()); 
    506506 
    507507    return handlerVPC; 
     
    567567    if (codeBlock->needsFullScopeChain) 
    568568        scopeChain = scopeChain->copy(); 
     569     
     570    ExecState newExec(exec, scopeChain); 
    569571 
    570572    m_reentryDepth++; 
    571     JSValue* result = privateExecute(Normal, exec, registerFile, r, scopeChain, codeBlock, exception); 
     573    JSValue* result = privateExecute(Normal, &newExec, registerFile, r, scopeChain, codeBlock, exception); 
    572574    m_reentryDepth--; 
    573575 
     
    620622    scopeChain = scopeChainForCall(functionBodyNode, newCodeBlock, scopeChain, callFrame, registerBase, r);             
    621623 
     624    ExecState newExec(exec, scopeChain); 
     625 
    622626    m_reentryDepth++; 
    623     JSValue* result = privateExecute(Normal, exec, registerFile, r, scopeChain, newCodeBlock, exception); 
     627    JSValue* result = privateExecute(Normal, &newExec, registerFile, r, scopeChain, newCodeBlock, exception); 
    624628    m_reentryDepth--; 
    625629 
     
    671675        scopeChain = scopeChain->copy(); 
    672676 
     677    ExecState newExec(exec, scopeChain); 
     678 
    673679    m_reentryDepth++; 
    674     JSValue* result = privateExecute(Normal, exec, registerFile, r, scopeChain, codeBlock, exception); 
     680    JSValue* result = privateExecute(Normal, &newExec, registerFile, r, scopeChain, codeBlock, exception); 
    675681    m_reentryDepth--; 
    676682 
     
    683689    RegisterFile* registerFile = registerFileStack->current(); 
    684690    return Machine::execute(evalNode, exec, thisObj, registerFile, registerFile->size(), scopeChain, exception); 
     691} 
     692 
     693ALWAYS_INLINE void Machine::setScopeChain(ExecState* exec, ScopeChainNode*& scopeChain, ScopeChainNode* newScopeChain) 
     694{ 
     695    scopeChain = newScopeChain; 
     696    exec->m_scopeChain = newScopeChain; 
    685697} 
    686698 
     
    14801492            codeBlock = newCodeBlock; 
    14811493            callFrame = (*registerBase) + callFrameOffset; // registerBase may have moved, recompute callFrame 
    1482             scopeChain = scopeChainForCall(functionBodyNode, codeBlock, callDataScopeChain, callFrame, registerBase, r);             
     1494            setScopeChain(exec, scopeChain, scopeChainForCall(functionBodyNode, codeBlock, callDataScopeChain, callFrame, registerBase, r)); 
    14831495            k = codeBlock->jsValues.data(); 
    14841496            vPC = codeBlock->instructions.begin(); 
     
    15391551        k = codeBlock->jsValues.data(); 
    15401552        vPC = callFrame[ReturnVPC].u.vPC; 
    1541         scopeChain = callFrame[CallerScopeChain].u.scopeChain; 
     1553        setScopeChain(exec, scopeChain, callFrame[CallerScopeChain].u.scopeChain); 
    15421554        r = (*registerBase) + callFrame[CallerRegisterOffset].u.i; 
    15431555        int r0 = callFrame[ReturnValueRegister].u.i; 
     
    15861598            codeBlock = newCodeBlock; 
    15871599            callFrame = (*registerBase) + callFrameOffset; // registerBase may have moved, recompute callFrame 
    1588             scopeChain = scopeChainForCall(functionBodyNode, codeBlock, callDataScopeChain, callFrame, registerBase, r);             
     1600            setScopeChain(exec, scopeChain, scopeChainForCall(functionBodyNode, codeBlock, callDataScopeChain, callFrame, registerBase, r)); 
    15891601            k = codeBlock->jsValues.data(); 
    15901602            vPC = codeBlock->instructions.begin(); 
     
    16181630        VM_CHECK_EXCEPTION(); 
    16191631         
    1620         scopeChain = scopeChain->push(o); 
     1632        setScopeChain(exec, scopeChain, scopeChain->push(o)); 
    16211633 
    16221634        ++vPC; 
     
    16241636    } 
    16251637    BEGIN_OPCODE(op_pop_scope) { 
    1626         scopeChain = scopeChain->pop(); 
     1638        setScopeChain(exec, scopeChain, scopeChain->pop()); 
    16271639 
    16281640        ++vPC; 
     
    16551667        int scopeDelta = (++vPC)->u.operand; 
    16561668        int offset = (++vPC)->u.operand; 
     1669         
     1670        ScopeChainNode* tmp = scopeChain; 
    16571671        while (scopeDelta--) 
    1658             scopeChain = scopeChain->pop(); 
     1672            tmp = tmp->pop(); 
     1673        setScopeChain(exec, scopeChain, tmp); 
     1674             
    16591675        vPC += offset; 
    16601676        NEXT_OPCODE; 
  • branches/squirrelfish/JavaScriptCore/VM/Machine.h

    r33306 r33329  
    9393        typedef enum { Normal, InitializeAndReturn } ExecutionFlag; 
    9494 
     95        ALWAYS_INLINE void setScopeChain(ExecState* exec, ScopeChainNode*&, ScopeChainNode*); 
     96 
    9597        NEVER_INLINE bool unwindCallFrame(Register**, const Instruction*&, CodeBlock*&, JSValue**&, ScopeChainNode*&, Register*&); 
    9698        NEVER_INLINE Instruction* throwException(ExecState*, JSValue*, Register**, const Instruction*, CodeBlock*&, JSValue**&, ScopeChainNode*&, Register*&); 
  • branches/squirrelfish/JavaScriptCore/kjs/ExecState.cpp

    r33318 r33329  
    3232namespace KJS { 
    3333 
    34 ExecState::ExecState(JSGlobalObject* globalObject, JSObject* globalThisValue, ScopeChain& globalScopeChain) 
    35     : m_globalObject(globalObject) 
     34ExecState::ExecState(JSGlobalObject* globalObject, JSObject* globalThisValue, ScopeChainNode* globalScopeChain) 
     35    : m_prev(0) 
     36    , m_globalObject(globalObject) 
    3637    , m_globalThisValue(globalThisValue) 
    3738    , m_exception(0) 
    3839    , m_exceptionSource(0) 
    3940    , m_perThreadData(globalObject->perThreadData()) 
    40     , m_scopeChain(globalScopeChain.node()) 
     41    , m_scopeChain(globalScopeChain) 
    4142{ 
     43} 
     44 
     45ExecState::ExecState(ExecState* exec, ScopeChainNode* scopeChain) 
     46    : m_prev(exec) 
     47    , m_globalObject(exec->m_globalObject) 
     48    , m_globalThisValue(exec->m_globalThisValue) 
     49    , m_exception(0) 
     50    , m_exceptionSource(0) 
     51    , m_perThreadData(exec->m_globalObject->perThreadData()) 
     52    , m_scopeChain(scopeChain) 
     53{ 
     54    ASSERT(!exec->m_exception); 
     55    ASSERT(!exec->m_exceptionSource); 
    4256} 
    4357 
  • branches/squirrelfish/JavaScriptCore/kjs/ExecState.h

    r33324 r33329  
    6363    // Passed as the first argument to most functions. 
    6464    class ExecState : Noncopyable { 
     65        friend class Machine; 
     66 
    6567    public: 
    66         ExecState(JSGlobalObject*, JSObject* globalThisValue, ScopeChain& globalScopeChain); 
     68        ExecState(JSGlobalObject*, JSObject* globalThisValue, ScopeChainNode* globalScopeChain); 
    6769 
    6870        // Global object in which execution began. 
     
    101103 
    102104    private: 
     105        ExecState(ExecState*, ScopeChainNode*); 
     106 
    103107        bool isGlobalObject(JSObject*) const; 
     108         
     109        ExecState* m_prev; 
    104110     
    105111        JSGlobalObject* m_globalObject; 
     
    111117        const PerThreadData* m_perThreadData; 
    112118 
    113         const ScopeChainNode* m_scopeChain; 
     119        ScopeChainNode* m_scopeChain; 
    114120    }; 
    115121 
  • branches/squirrelfish/JavaScriptCore/kjs/JSGlobalObject.cpp

    r33306 r33329  
    208208    d()->perThreadData.propertyNames = CommonIdentifiers::shared(); 
    209209 
    210     d()->globalExec.set(new ExecState(this, thisValue, d()->globalScopeChain)); 
     210    d()->globalExec.set(new ExecState(this, thisValue, d()->globalScopeChain.node())); 
    211211 
    212212    d()->pageGroupIdentifier = 0; 
  • branches/squirrelfish/JavaScriptCore/kjs/JSGlobalObject.h

    r33327 r33329  
    8383                : JSVariableObjectData(&symbolTable, registerFileStack.globalBasePointer(), 0) 
    8484                , globalScopeChain(globalObject) 
    85                 , globalExec(new ExecState(globalObject, thisValue, globalScopeChain)) 
     85                , globalExec(new ExecState(globalObject, thisValue, globalScopeChain.node())) 
    8686            { 
    8787            }