예제 #1
0
파일: VM.cpp 프로젝트: EdgarHz/webkit
void VM::throwException(ExecState* exec, Exception* exception)
{
    if (Options::breakOnThrow()) {
        dataLog("In call frame ", RawPointer(exec), " for code block ", *exec->codeBlock(), "\n");
        CRASH();
    }

    ASSERT(exec == topCallFrame || exec == exec->lexicalGlobalObject()->globalExec() || exec == exec->vmEntryGlobalObject()->globalExec());

    interpreter->notifyDebuggerOfExceptionToBeThrown(exec, exception);

    setException(exception);
}
예제 #2
0
static const char *symbolLookupCallback(
    void* opaque, uint64_t referenceValue, uint64_t* referenceType, uint64_t referencePC,
    const char** referenceName)
{
    // Set this if you want to debug an unexpected reference type. Currently we only encounter these
    // if we try to disassemble garbage, since our code generator never uses them. These include things
    // like PC-relative references.
    static const bool crashOnUnexpected = false;
    
    char* symbolString = static_cast<char*>(opaque);
    
    switch (*referenceType) {
    case LLVMDisassembler_ReferenceType_InOut_None:
        return 0;
    case LLVMDisassembler_ReferenceType_In_Branch:
        *referenceName = 0;
        *referenceType = LLVMDisassembler_ReferenceType_InOut_None;
        snprintf(
            symbolString, symbolStringSize, "0x%lx",
            static_cast<unsigned long>(referenceValue));
        return symbolString;
    default:
        if (crashOnUnexpected) {
            dataLog("referenceValue = ", referenceValue, "\n");
            dataLog("referenceType = ", RawPointer(referenceType), ", *referenceType = ", *referenceType, "\n");
            dataLog("referencePC = ", referencePC, "\n");
            dataLog("referenceName = ", RawPointer(referenceName), "\n");
            
            RELEASE_ASSERT_NOT_REACHED();
        }
        
        *referenceName = "unimplemented reference type!";
        *referenceType = LLVMDisassembler_ReferenceType_InOut_None;
        snprintf(
            symbolString, symbolStringSize, "unimplemented:0x%lx",
            static_cast<unsigned long>(referenceValue));
        return symbolString;
    }
}
void Worklist::enqueue(PassRefPtr<Plan> passedPlan)
{
    RefPtr<Plan> plan = passedPlan;
    MutexLocker locker(m_lock);
    if (Options::verboseCompilationQueue()) {
        dump(locker, WTF::dataFile());
        dataLog(": Enqueueing plan to optimize ", plan->key(), "\n");
    }
    ASSERT(m_plans.find(plan->key()) == m_plans.end());
    m_plans.add(plan->key(), plan);
    m_queue.append(plan);
    m_planEnqueued.signal();
}
void JITToDFGDeferredCompilationCallback::compilationDidComplete(
    CodeBlock* codeBlock, CompilationResult result)
{
    ASSERT(codeBlock->alternative()->jitType() == JITCode::BaselineJIT);
    
    if (Options::verboseOSR())
        dataLog("Optimizing compilation of ", *codeBlock, " result: ", result, "\n");
    
    if (result == CompilationSuccessful)
        codeBlock->install();
    
    codeBlock->alternative()->setOptimizationThresholdBasedOnCompilationResult(result);
}
    void coalesce()
    {
        unsigned moveIndex = m_worklistMoves.takeLastMove();
        const MoveOperands& moveOperands = m_coalescingCandidates[moveIndex];
        IndexType u = getAlias(moveOperands.srcIndex);
        IndexType v = getAlias(moveOperands.dstIndex);

        if (isPrecolored(v))
            std::swap(u, v);

        if (traceDebug)
            dataLog("Coalescing move at index", moveIndex, " u = ", u, " v = ", v, "\n");

        if (u == v) {
            addWorkList(u);

            if (traceDebug)
                dataLog("    Coalesced\n");
        } else if (isPrecolored(v) || m_interferenceEdges.contains(InterferenceEdge(u, v))) {
            addWorkList(u);
            addWorkList(v);

            if (traceDebug)
                dataLog("    Constrained\n");
        } else if (canBeSafelyCoalesced(u, v)) {
            combine(u, v);
            addWorkList(u);
            m_hasCoalescedNonTrivialMove = true;

            if (traceDebug)
                dataLog("    Safe Coalescing\n");
        } else {
            m_activeMoves.quickSet(moveIndex);

            if (traceDebug)
                dataLog("    Failed coalescing, added to active moves.\n");
        }
    }
예제 #6
0
void CallLinkInfo::visitWeak(RepatchBuffer& repatchBuffer)
{
    auto handleSpecificCallee = [&] (JSFunction* callee) {
        if (Heap::isMarked(callee->executable()))
            m_hasSeenClosure = true;
        else
            m_clearedByGC = true;
    };
    
    if (isLinked()) {
        if (stub()) {
            if (!stub()->visitWeak(repatchBuffer)) {
                if (Options::verboseOSR()) {
                    dataLog(
                        "Clearing closure call from ", *repatchBuffer.codeBlock(), " to ",
                        listDump(stub()->variants()), ", stub routine ", RawPointer(stub()),
                        ".\n");
                }
                unlink(repatchBuffer);
                m_clearedByGC = true;
            }
        } else if (!Heap::isMarked(m_callee.get())) {
            if (Options::verboseOSR()) {
                dataLog(
                    "Clearing call from ", *repatchBuffer.codeBlock(), " to ",
                    RawPointer(m_callee.get()), " (",
                    m_callee.get()->executable()->hashFor(specializationKind()),
                    ").\n");
            }
            handleSpecificCallee(m_callee.get());
            unlink(repatchBuffer);
        }
    }
    if (haveLastSeenCallee() && !Heap::isMarked(lastSeenCallee())) {
        handleSpecificCallee(lastSeenCallee());
        clearLastSeenCallee();
    }
}
예제 #7
0
int main(int argc, char** argv)
{
    WTF::initializeThreading();
    
    if (argc != 8
        || !parseValue(argv[2], &numThreadGroups)
        || !parseValue(argv[3], &numThreadsPerGroup)
        || !parseValue(argv[4], &workPerCriticalSection)
        || !parseValue(argv[5], &workBetweenCriticalSections)
        || !parseValue(argv[6], &toyLockSpinLimit)
        || sscanf(argv[7], "%lf", &secondsPerTest) != 1)
        usage();
    
    if (rangeVariable) {
        dataLog("Running with rangeMin = ", rangeMin, ", rangeMax = ", rangeMax, ", rangeStep = ", rangeStep, "\n");
        for (unsigned value = rangeMin; value <= rangeMax; value += rangeStep) {
            dataLog("Running with value = ", value, "\n");
            *rangeVariable = value;
            runEverything<Benchmark>(argv[1]);
        }
    } else
        runEverything<Benchmark>(argv[1]);
    
    for (auto& entry : results) {
        printf("%s = {", entry.key.data());
        bool first = true;
        for (double value : entry.value) {
            if (first)
                first = false;
            else
                printf(", ");
            printf("%.3lf", value);
        }
        printf("};\n");
    }

    return 0;
}
예제 #8
0
JSValue ModuleLoaderObject::evaluate(ExecState* exec, JSValue key, JSValue moduleRecordValue)
{
    if (Options::dumpModuleLoadingState())
        dataLog("Loader [evaluate] ", printableModuleKey(exec, key), "\n");

    JSGlobalObject* globalObject = exec->lexicalGlobalObject();
    if (globalObject->globalObjectMethodTable()->moduleLoaderEvaluate)
        return globalObject->globalObjectMethodTable()->moduleLoaderEvaluate(globalObject, exec, key, moduleRecordValue);

    JSModuleRecord* moduleRecord = jsDynamicCast<JSModuleRecord*>(moduleRecordValue);
    if (!moduleRecord)
        return jsUndefined();
    return moduleRecord->evaluate(exec);
}
예제 #9
0
파일: Heap.cpp 프로젝트: allsmy/webkit
void Heap::visitException(HeapRootVisitor& visitor)
{
    GCPHASE(MarkingException);
    if (!m_vm->exception() && !m_vm->lastException())
        return;

    visitor.visit(m_vm->addressOfException());
    visitor.visit(m_vm->addressOfLastException());

    if (Options::logGC() == GCLogging::Verbose)
        dataLog("Exceptions:\n", m_slotVisitor);

    m_slotVisitor.donateAndDrain();
}
예제 #10
0
void BlockDirectory::stopAllocatingForGood()
{
    if (false)
        dataLog(RawPointer(this), ": BlockDirectory::stopAllocatingForGood!\n");
    
    m_localAllocators.forEach(
        [&] (LocalAllocator* allocator) {
            allocator->stopAllocatingForGood();
        });

    auto locker = holdLock(m_localAllocatorsLock);
    while (!m_localAllocators.isEmpty())
        m_localAllocators.begin()->remove();
}
예제 #11
0
void BytecodeLivenessAnalysis::dumpResults()
{
    CodeBlock* codeBlock = m_graph.codeBlock();
    dataLog("\nDumping bytecode liveness for ", *codeBlock, ":\n");
    Interpreter* interpreter = codeBlock->vm()->interpreter;
    Instruction* instructionsBegin = codeBlock->instructions().begin();
    unsigned i = 0;
    for (BytecodeBasicBlock* block : m_graph) {
        dataLogF("\nBytecode basic block %u: %p (offset: %u, length: %u)\n", i++, block, block->leaderOffset(), block->totalLength());
        dataLogF("Successors: ");
        for (unsigned j = 0; j < block->successors().size(); j++) {
            BytecodeBasicBlock* successor = block->successors()[j];
            dataLogF("%p ", successor);
        }
        dataLogF("\n");
        if (block->isEntryBlock()) {
            dataLogF("Entry block %p\n", block);
            continue;
        }
        if (block->isExitBlock()) {
            dataLogF("Exit block: %p\n", block);
            continue;
        }
        for (unsigned bytecodeOffset = block->leaderOffset(); bytecodeOffset < block->leaderOffset() + block->totalLength();) {
            const Instruction* currentInstruction = &instructionsBegin[bytecodeOffset];

            dataLogF("Live variables: ");
            FastBitVector liveBefore = getLivenessInfoAtBytecodeOffset(bytecodeOffset);
            for (unsigned j = 0; j < liveBefore.numBits(); j++) {
                if (liveBefore.get(j))
                    dataLogF("%u ", j);
            }
            dataLogF("\n");
            codeBlock->dumpBytecode(WTF::dataFile(), codeBlock->globalObject()->globalExec(), instructionsBegin, currentInstruction);

            OpcodeID opcodeID = interpreter->getOpcodeID(instructionsBegin[bytecodeOffset].u.opcode);
            unsigned opcodeLength = opcodeLengths[opcodeID];
            bytecodeOffset += opcodeLength;
        }

        dataLogF("Live variables: ");
        FastBitVector liveAfter = block->out();
        for (unsigned j = 0; j < liveAfter.numBits(); j++) {
            if (liveAfter.get(j))
                dataLogF("%u ", j);
        }
        dataLogF("\n");
    }
}
예제 #12
0
void MarkedAllocator::stopAllocating()
{
    if (false)
        dataLog(RawPointer(this), ": MarkedAllocator::stopAllocating!\n");
    ASSERT(!m_lastActiveBlock);
    if (!m_currentBlock) {
        ASSERT(!m_freeList);
        return;
    }
    
    m_currentBlock->stopAllocating(m_freeList);
    m_lastActiveBlock = m_currentBlock;
    m_currentBlock = 0;
    m_freeList = FreeList();
}
예제 #13
0
void ToFTLDeferredCompilationCallback::compilationDidComplete(
    CodeBlock* codeBlock, CompilationResult result)
{
    if (Options::verboseOSR()) {
        dataLog(
            "Optimizing compilation of ", *codeBlock, " (for ", *m_dfgCodeBlock,
            ") result: ", result, "\n");
    }
    
    if (result == CompilationSuccessful)
        codeBlock->install();
    
    m_dfgCodeBlock->jitCode()->dfg()->setOptimizationThresholdBasedOnCompilationResult(
        m_dfgCodeBlock.get(), result);
}
예제 #14
0
void UnlinkedCodeBlock::dumpExpressionRangeInfo()
{
    Vector<ExpressionRangeInfo>& expressionInfo = m_expressionInfo;

    size_t size = m_expressionInfo.size();
    dataLogF("UnlinkedCodeBlock %p expressionRangeInfo[%zu] {\n", this, size);
    for (size_t i = 0; i < size; i++) {
        ExpressionRangeInfo& info = expressionInfo[i];
        unsigned line;
        unsigned column;
        getLineAndColumn(info, line, column);
        dumpLineColumnEntry(i, instructions(), info.instructionOffset, line, column);
    }
    dataLog("}\n");
}
예제 #15
0
void ArrayProfile::computeUpdatedPrediction(CodeBlock* codeBlock, OperationInProgress operation)
{
    const bool verbose = false;
    
    if (m_lastSeenStructure) {
        m_observedArrayModes |= arrayModeFromStructure(m_lastSeenStructure);
        m_mayInterceptIndexedAccesses |=
            m_lastSeenStructure->typeInfo().interceptsGetOwnPropertySlotByIndexEvenWhenLengthIsNotZero();
        if (!codeBlock->globalObject()->isOriginalArrayStructure(m_lastSeenStructure))
            m_usesOriginalArrayStructures = false;
        if (!structureIsPolymorphic()) {
            if (!m_expectedStructure)
                m_expectedStructure = m_lastSeenStructure;
            else if (m_expectedStructure != m_lastSeenStructure) {
                if (verbose)
                    dataLog(*codeBlock, " bc#", m_bytecodeOffset, ": making structure polymorphic because ", RawPointer(m_expectedStructure), " (", m_expectedStructure->classInfo()->className, ") != ", RawPointer(m_lastSeenStructure), " (", m_lastSeenStructure->classInfo()->className, ")\n");
                m_expectedStructure = polymorphicStructure();
            }
        }
        m_lastSeenStructure = 0;
    }
    
    if (hasTwoOrMoreBitsSet(m_observedArrayModes)) {
        if (verbose)
            dataLog(*codeBlock, " bc#", m_bytecodeOffset, ": making structure polymorphic because two or more bits are set in m_observedArrayModes\n");
        m_expectedStructure = polymorphicStructure();
    }
    
    if (operation == Collection
        && expectedStructure()
        && !Heap::isMarked(m_expectedStructure)) {
        if (verbose)
            dataLog(*codeBlock, " bc#", m_bytecodeOffset, ": making structure during GC\n");
        m_expectedStructure = polymorphicStructure();
    }
}
예제 #16
0
void Graph::predictArgumentTypes()
{
    ASSERT(m_codeBlock->numParameters() >= 1);
    for (size_t arg = 0; arg < static_cast<size_t>(m_codeBlock->numParameters()); ++arg) {
        ValueProfile* profile = m_profiledBlock->valueProfileForArgument(arg);
        if (!profile)
            continue;
        
        at(m_arguments[arg]).variableAccessData()->predict(profile->computeUpdatedPrediction());
        
#if DFG_ENABLE(DEBUG_VERBOSE)
        dataLog("Argument [%zu] prediction: %s\n", arg, speculationToString(at(m_arguments[arg]).variableAccessData()->prediction()));
#endif
    }
}
예제 #17
0
EncodedJSValue JSC_HOST_CALL moduleLoaderObjectModuleDeclarationInstantiation(ExecState* exec)
{
    JSModuleRecord* moduleRecord = jsDynamicCast<JSModuleRecord*>(exec->argument(0));
    if (!moduleRecord)
        return JSValue::encode(jsUndefined());

    if (Options::dumpModuleLoadingState())
        dataLog("Loader [link] ", moduleRecord->moduleKey(), "\n");

    moduleRecord->link(exec);
    if (exec->hadException())
        return JSValue::encode(jsUndefined());

    return JSValue::encode(jsUndefined());
}
예제 #18
0
EncodedJSValue JSC_HOST_CALL moduleLoaderPrototypeModuleDeclarationInstantiation(ExecState* exec)
{
    VM& vm = exec->vm();
    auto scope = DECLARE_THROW_SCOPE(vm);
    JSModuleRecord* moduleRecord = jsDynamicCast<JSModuleRecord*>(vm, exec->argument(0));
    if (!moduleRecord)
        return JSValue::encode(jsUndefined());

    if (Options::dumpModuleLoadingState())
        dataLog("Loader [link] ", moduleRecord->moduleKey(), "\n");

    moduleRecord->link(exec);
    RETURN_IF_EXCEPTION(scope, encodedJSValue());

    return JSValue::encode(jsUndefined());
}
예제 #19
0
    void performBlockCFA(BlockIndex blockIndex)
    {
        BasicBlock* block = m_graph.m_blocks[blockIndex].get();
        if (!block)
            return;
        if (!block->cfaShouldRevisit)
            return;
#if DFG_ENABLE(DEBUG_PROPAGATION_VERBOSE)
        dataLog("   Block #%u (bc#%u):\n", blockIndex, block->bytecodeBegin);
#endif
        m_state.beginBasicBlock(block);
#if DFG_ENABLE(DEBUG_PROPAGATION_VERBOSE)
        dataLog("      head vars: ");
        dumpOperands(block->valuesAtHead, WTF::dataFile());
        dataLog("\n");
#endif
        for (unsigned i = 0; i < block->size(); ++i) {
            NodeIndex nodeIndex = block->at(i);
            if (!m_graph[nodeIndex].shouldGenerate())
                continue;
#if DFG_ENABLE(DEBUG_PROPAGATION_VERBOSE)
            dataLog("      %s @%u: ", Graph::opName(m_graph[nodeIndex].op()), nodeIndex);
            m_state.dump(WTF::dataFile());
            dataLog("\n");
#endif
            if (!m_state.execute(i))
                break;
        }
#if DFG_ENABLE(DEBUG_PROPAGATION_VERBOSE)
        dataLog("      tail regs: ");
        m_state.dump(WTF::dataFile());
        dataLog("\n");
#endif
        m_changed |= m_state.endBasicBlock(AbstractState::MergeToSuccessors);
#if DFG_ENABLE(DEBUG_PROPAGATION_VERBOSE)
        dataLog("      tail vars: ");
        dumpOperands(block->valuesAtTail, WTF::dataFile());
        dataLog("\n");
#endif
    }
void ToFTLForOSREntryDeferredCompilationCallback::compilationDidComplete(
    CodeBlock* codeBlock, CompilationResult result)
{
    if (Options::verboseOSR()) {
        dataLog(
            "Optimizing compilation of ", *codeBlock, " (for ", *m_dfgCodeBlock,
            ") result: ", result, "\n");
    }

    if (result == CompilationSuccessful)
        m_dfgCodeBlock->jitCode()->dfg()->osrEntryBlock = codeBlock;

    // FIXME: if we failed, we might want to just turn off OSR entry rather than
    // totally turning off tier-up.
    m_dfgCodeBlock->jitCode()->dfg()->setOptimizationThresholdBasedOnCompilationResult(
        m_dfgCodeBlock.get(), result);
}
예제 #21
0
void CodeBlockSet::traceMarked(SlotVisitor& visitor)
{
    if (verbose)
        dataLog("Tracing ", m_currentlyExecuting.size(), " code blocks.\n");

    // We strongly visit the currently executing set because jettisoning code
    // is not valuable once it's on the stack. We're past the point where
    // jettisoning would avoid the cost of OSR exit.
    for (const RefPtr<CodeBlock>& codeBlock : m_currentlyExecuting)
        codeBlock->visitStrongly(visitor);

    // We strongly visit the remembered set because jettisoning old code during
    // Eden GC is unsound. There might be an old object with a strong reference
    // to the code.
    for (const RefPtr<CodeBlock>& codeBlock : m_remembered)
        codeBlock->visitStrongly(visitor);
}
예제 #22
0
JITCode::~JITCode()
{
    if (FTL::shouldDumpDisassembly()) {
        dataLog("Destroying FTL JIT code at ");
        CommaPrinter comma;
#if FTL_USES_B3
        dataLog(comma, m_b3Code);
        dataLog(comma, m_arityCheckEntrypoint);
#else
        for (auto& handle : m_handles)
            dataLog(comma, pointerDump(handle.get()));
        dataLog(comma, pointerDump(m_arityCheckEntrypoint.executableMemory()));
        dataLog(comma, pointerDump(m_exitThunks.executableMemory()));
        dataLog("\n");
#endif
    }
}
예제 #23
0
JSInternalPromise* ModuleLoaderObject::fetch(ExecState* exec, JSValue key)
{
    if (Options::dumpModuleLoadingState())
        dataLog("Loader [fetch] ", printableModuleKey(exec, key), "\n");

    JSGlobalObject* globalObject = exec->lexicalGlobalObject();
    if (globalObject->globalObjectMethodTable()->moduleLoaderFetch)
        return globalObject->globalObjectMethodTable()->moduleLoaderFetch(globalObject, exec, key);
    JSInternalPromiseDeferred* deferred = JSInternalPromiseDeferred::create(exec, globalObject);
    String moduleKey = key.toString(exec)->value(exec);
    if (exec->hadException()) {
        JSValue exception = exec->exception()->value();
        exec->clearException();
        deferred->reject(exec, exception);
        return deferred->promise();
    }
    deferred->reject(exec, createError(exec, makeString("Could not open the module '", moduleKey, "'.")));
    return deferred->promise();
}
void ProfiledCodeBlockJettisoningWatchpoint::fireInternal()
{
    if (DFG::shouldShowDisassembly()) {
        dataLog(
            "Firing profiled watchpoint ", RawPointer(this), " on ", *m_codeBlock, " due to ",
            m_exitKind, " at ", m_codeOrigin, "\n");
    }
    
    baselineCodeBlockForOriginAndBaselineCodeBlock(
        m_codeOrigin, m_codeBlock->baselineVersion())->addFrequentExitSite(
            DFG::FrequentExitSite(m_codeOrigin.bytecodeIndex, m_exitKind));
    
#if ENABLE(JIT)
    m_codeBlock->jettison(CountReoptimization);
#endif

    if (isOnList())
        remove();
}
예제 #25
0
bool Plan::parseAndValidateModule()
{
    MonotonicTime startTime;
    if (verbose || Options::reportCompileTimes())
        startTime = MonotonicTime::now();

    {
        ModuleParser moduleParser(m_vm, m_source, m_sourceLength);
        auto parseResult = moduleParser.parse();
        if (!parseResult) {
            m_errorMessage = parseResult.error();
            return false;
        }
        m_moduleInformation = WTFMove(parseResult->module);
        m_functionLocationInBinary = WTFMove(parseResult->functionLocationInBinary);
        m_moduleSignatureIndicesToUniquedSignatureIndices = WTFMove(parseResult->moduleSignatureIndicesToUniquedSignatureIndices);
    }

    for (unsigned functionIndex = 0; functionIndex < m_functionLocationInBinary.size(); ++functionIndex) {
        if (verbose)
            dataLogLn("Processing function starting at: ", m_functionLocationInBinary[functionIndex].start, " and ending at: ", m_functionLocationInBinary[functionIndex].end);
        const uint8_t* functionStart = m_source + m_functionLocationInBinary[functionIndex].start;
        size_t functionLength = m_functionLocationInBinary[functionIndex].end - m_functionLocationInBinary[functionIndex].start;
        ASSERT(functionLength <= m_sourceLength);
        SignatureIndex signatureIndex = m_moduleInformation->internalFunctionSignatureIndices[functionIndex];
        const Signature* signature = SignatureInformation::get(m_vm, signatureIndex);

        auto validationResult = validateFunction(m_vm, functionStart, functionLength, signature, *m_moduleInformation, m_moduleSignatureIndicesToUniquedSignatureIndices);
        if (!validationResult) {
            if (verbose) {
                for (unsigned i = 0; i < functionLength; ++i)
                    dataLog(RawPointer(reinterpret_cast<void*>(functionStart[i])), ", ");
                dataLogLn();
            }
            m_errorMessage = makeString(validationResult.error(), ", in function at index ", String::number(functionIndex)); // FIXME make this an Expected.
            return false;
        }
    }

    if (verbose || Options::reportCompileTimes())
        dataLogLn("Took ", (MonotonicTime::now() - startTime).microseconds(), " us to validate module");
    return true;
}
예제 #26
0
 void performBlockCFA(BasicBlock* block)
 {
     if (!block)
         return;
     if (!block->cfaShouldRevisit)
         return;
     if (m_verbose)
         dataLog("   Block ", *block, ":\n");
     m_state.beginBasicBlock(block);
     if (m_verbose) {
         dataLog("      head vars: ", block->valuesAtHead, "\n");
         if (m_graph.m_form == SSA)
             dataLog("      head regs: ", nodeValuePairListDump(block->ssa->valuesAtHead), "\n");
     }
     for (unsigned i = 0; i < block->size(); ++i) {
         if (m_verbose) {
             Node* node = block->at(i);
             dataLogF("      %s @%u: ", Graph::opName(node->op()), node->index());
             
             if (!safeToExecute(m_state, m_graph, node))
                 dataLog("(UNSAFE) ");
             
             dataLog(m_state.variables(), " ", m_interpreter);
             
             dataLogF("\n");
         }
         if (!m_interpreter.execute(i)) {
             if (m_verbose)
                 dataLogF("         Expect OSR exit.\n");
             break;
         }
     }
     if (m_verbose) {
         dataLogF("      tail regs: ");
         m_interpreter.dump(WTF::dataFile());
         dataLogF("\n");
     }
     m_changed |= m_state.endBasicBlock();
     
     if (m_verbose) {
         dataLog("      tail vars: ", block->valuesAtTail, "\n");
         if (m_graph.m_form == SSA)
             dataLog("      head regs: ", nodeValuePairListDump(block->ssa->valuesAtTail), "\n");
     }
 }
예제 #27
0
void TypeProfilerLog::processLogEntries(const String& reason)
{
    double before = 0;
    if (verbose) {
        dataLog("Process caller:'", reason, "'");
        before = currentTimeMS();
    }

    LogEntry* entry = m_logStartPtr;
    HashMap<Structure*, RefPtr<StructureShape>> seenShapes;
    while (entry != m_currentLogEntryPtr) {
        StructureID id = entry->structureID;
        RefPtr<StructureShape> shape;
        JSValue value = entry->value;
        Structure* structure = nullptr;
        if (id) {
            structure = Heap::heap(value.asCell())->structureIDTable().get(id);
            auto iter = seenShapes.find(structure);
            if (iter == seenShapes.end()) {
                shape = structure->toStructureShape(value);
                seenShapes.set(structure, shape);
            } else
                shape = iter->value;
        }

        RuntimeType type = runtimeTypeForValue(value);
        TypeLocation* location = entry->location;
        location->m_lastSeenType = type;
        if (location->m_globalTypeSet)
            location->m_globalTypeSet->addTypeInformation(type, shape, structure);
        location->m_instructionTypeSet->addTypeInformation(type, shape, structure);

        entry++;
    }

    m_currentLogEntryPtr = m_logStartPtr;

    if (verbose) {
        double after = currentTimeMS();
        dataLogF(" Processing the log took: '%f' ms\n", after - before);
    }
}
void AdaptiveStructureWatchpoint::fireInternal(const FireDetail& detail)
{
    if (m_key.isWatchable(PropertyCondition::EnsureWatchability)) {
        install();
        return;
    }
    
    if (DFG::shouldDumpDisassembly()) {
        dataLog(
            "Firing watchpoint ", RawPointer(this), " (", m_key, ") on ", *m_codeBlock, "\n");
    }
    
    StringPrintStream out;
    out.print("Adaptation of ", m_key, " failed: ", detail);
    
    StringFireDetail stringDetail(out.toCString().data());
    
    m_codeBlock->jettison(
        Profiler::JettisonDueToUnprofiledWatchpoint, CountReoptimization, &stringDetail);
}
예제 #29
0
파일: VM.cpp 프로젝트: ollie314/webkit
void VM::verifyExceptionCheckNeedIsSatisfied(unsigned recursionDepth, ExceptionEventLocation& location)
{
    if (!Options::validateExceptionChecks())
        return;

    if (UNLIKELY(m_needExceptionCheck)) {
        auto throwDepth = m_simulatedThrowPointRecursionDepth;
        auto& throwLocation = m_simulatedThrowPointLocation;

        dataLog(
            "ERROR: Unchecked JS exception:\n"
            "    This scope can throw a JS exception: ", throwLocation, "\n"
            "        (ExceptionScope::m_recursionDepth was ", throwDepth, ")\n"
            "    But the exception was unchecked as of this scope: ", location, "\n"
            "        (ExceptionScope::m_recursionDepth was ", recursionDepth, ")\n"
            "\n");

        RELEASE_ASSERT(!m_needExceptionCheck);
    }
}
    bool run()
    {
        ASSERT(m_graph.m_form == ThreadedCPS);
        ASSERT(m_graph.m_unificationState == GloballyUnified);
        
        ASSERT(codeBlock()->numParameters() >= 1);
        for (size_t arg = 0; arg < static_cast<size_t>(codeBlock()->numParameters()); ++arg) {
            ValueProfile* profile = profiledBlock()->valueProfileForArgument(arg);
            if (!profile)
                continue;
            
            m_graph.m_arguments[arg]->variableAccessData()->predict(profile->computeUpdatedPrediction());
            
#if DFG_ENABLE(DEBUG_VERBOSE)
            dataLog(
                "Argument [", arg, "] prediction: ",
                SpeculationDump(m_graph.m_arguments[arg]->variableAccessData()->prediction()), "\n");
#endif
        }
        
        for (BlockIndex blockIndex = 0; blockIndex < m_graph.m_blocks.size(); ++blockIndex) {
            BasicBlock* block = m_graph.m_blocks[blockIndex].get();
            if (!block)
                continue;
            if (!block->isOSRTarget)
                continue;
            if (block->bytecodeBegin != m_graph.m_osrEntryBytecodeIndex)
                continue;
            for (size_t i = 0; i < m_graph.m_mustHandleValues.size(); ++i) {
                Node* node = block->variablesAtHead.operand(
                    m_graph.m_mustHandleValues.operandForIndex(i));
                if (!node)
                    continue;
                ASSERT(node->hasLocal());
                node->variableAccessData()->predict(
                    speculationFromValue(m_graph.m_mustHandleValues[i]));
            }
        }
        
        return true;
    }