⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 processor.cc

📁 Linux下比较早的基于命令行的DVD播放器
💻 CC
📖 第 1 页 / 共 3 页
字号:
      case Instruction::JUMPVTS_TT:        if (targetPosition.enterVTSTitle(instruction->operand2.getTTN())) {            scheduler.addStartPGC(targetPosition);        } else {            scheduler.addFirstPlayPGC();        }        break;      case Instruction::JUMPVTS_PTT:        if (targetPosition.enterVTSTitle(instruction->operand2.getTTN(),                                         instruction->operand1.getPTTN())) {            scheduler.addStartPGC(targetPosition);        } else {            scheduler.addFirstPlayPGC();        }        break;      case Instruction::JUMPSS:        executeJumpSS(instruction);        break;      case Instruction::CALLSS:        executeCallSS(instruction);        break;      default:        Log::error("dvd::vm::Processor::executeJumpCall: invalid jump/call command: %u\n",                    (unsigned)instruction->getJumpCallCmd());        scheduler.addFirstPlayPGC();        break;      case Instruction::NOP:        --numberOfBranches;        scheduler.addStep();        break;    }}//------------------------------------------------------------------------------void Processor::executeJumpCallSS(const Instruction* instruction, bool isJump){    bool failed = false;    TargetPosition targetPosition(state.getPosition());    switch(instruction->operand2.getJumpCallType()) {      case Operand2::FP:        scheduler.addFirstPlayPGC();        break;      case Operand2::VMGM_MENU:        if (targetPosition.enterVMGMenu(instruction->operand2.getMenu())) {            scheduler.addStartPGC(targetPosition);        } else {            scheduler.addFirstPlayPGC();        }        break;      case Operand2::VTSM:        if (isJump) {            if (instruction->operand2.getVTS()>0) {                if (!targetPosition.enterVTS(instruction->operand2.getVTS(),                                             instruction->operand1.getTTN())) {                    failed = true;                }            } else {                if (!targetPosition.enterVTSTitle(instruction->operand1.getTTN())) {                    failed = true;                }            }        }        if (!failed && targetPosition.enterMenu(instruction->operand2.getMenu())) {            scheduler.addStartPGC(targetPosition);        } else {            scheduler.addFirstPlayPGC();        }        break;      case Operand2::VMGM_PGCN:        if (targetPosition.enterVMGPGC(instruction->operand1.getPGCN())) {            scheduler.addStartPGC(targetPosition);        } else {            scheduler.addFirstPlayPGC();        }        break;      default:        Log::error("dvd::vm::Processor::executeJumpCallSS: invalid jump/call type: %u!\n",                     (unsigned)instruction->operand2.getJumpCallType());        scheduler.addFirstPlayPGC();        break;    }}//------------------------------------------------------------------------------void Processor::executeJumpSS(const Instruction* instruction){    executeJumpCallSS(instruction, true);}//------------------------------------------------------------------------------void Processor::executeCallSS(const Instruction* instruction){    state.save(instruction->operand2.getRSMCell());    executeJumpCallSS(instruction, false);}//------------------------------------------------------------------------------void Processor::executeSetSysReg(const Instruction* instruction){    if (!evaluateSetSysRegCondition(instruction)) {        scheduler.addStep();        return;    }    // FIXME: check if these register settings should appear somehow    // (e.g. when setting the highlighted button number, shall we    // change it on screen)?    switch(instruction->getSetType()) {      case Instruction::STN:        if (instruction->operand1.isAF()) {            unsigned value =                 instruction->isDirect() ?                 instruction->operand1.getAVAL() :                state.getGPRValue(instruction->operand1.getSR1());            state.setSPRValue(SPRM::audioStreamNumber, value);        }        if (instruction->operand2.isSF()) {            unsigned value =                 instruction->isDirect() ?                 instruction->operand2.getSVAL() :                state.getGPRValue(instruction->operand2.getSR2());            state.setSPRValue(SPRM::subPictureStreamNumber, value);        }        if (instruction->operand2.isNF()) {            unsigned value =                 instruction->isDirect() ?                 instruction->operand2.getNVAL() :                state.getGPRValue(instruction->operand2.getSR3());            state.setSPRValue(SPRM::angleNumber, value);        }        break;      case Instruction::NVTMR:        state.setSPRValue(SPRM::navigationTimer,                          instruction->isDirect() ?                          instruction->operand1.getSVAL() :                          state.getValue(instruction->operand1.getSRS()));        state.setSPRValue(SPRM::pgcForNavTimer, instruction->operand2.getPGCN());        break;      case Instruction::GPRMMD:        {        GPR& gpr =            state.getGPRM().getRegister(instruction->operand2.getSRD());        gpr.setValue(instruction->isDirect() ?                      instruction->operand1.getSVAL() :                     state.getValue(instruction->operand1.getSRS()));        if (instruction->operand2.isMF()) {            gpr.setCounter();        } else {            gpr.clearCounter();        }        }        break;      case Instruction::AMXMD:        state.setSPRValue(SPRM::audioMixingMode,                          instruction->isDirect() ?                          instruction->operand2.getValue() :                          state.getGPRValue(instruction->operand2.getSRS()));        break;      case Instruction::HL_BTNN:        state.setSPRValue(SPRM::highlightedButtonNumber,                          instruction->isDirect() ?                          instruction->operand2.getValue() :                          state.getGPRValue(instruction->operand2.getSRS()));        break;      default:        scheduler.addFirstPlayPGC();        Log::error("dvd::vm::Processor::executeSetSysReg: Invalid set type: %u\n",                     (unsigned)instruction->getSetType());        return;    }    executeLinkUnconditionally(instruction);}//------------------------------------------------------------------------------void Processor::executeSet(const Instruction* instruction){    if (!evaluateSetCondition(instruction)) {        scheduler.addStep();        return;    }    GPR& destRegister =        state.getGPRM().getRegister(instruction->operand1.getSRD());    unsigned sourceValue = 0;    Register* sourceRegister = 0;        if (instruction->isDirect()) {        sourceValue = instruction->operand2.getValue();    } else {        sourceRegister =             &(state.getRegister(instruction->operand2.getSRS()));        sourceValue = sourceRegister->getValue();    }    if (executeSet(instruction, destRegister,                    sourceValue, sourceRegister))    {        executeLinkUnconditionally(instruction);    }}//------------------------------------------------------------------------------bool Processor::executeSet(const Instruction* instruction,                            GPR& destRegister,                           unsigned sourceValue, Register* sourceRegister){    unsigned destValue = destRegister.getValue();    switch(instruction->getSetOp()) {      case Instruction::MOV:        destValue = sourceValue;        break;      case Instruction::SWP:        if (sourceRegister!=0) {            sourceRegister->setValue(destValue);            destValue = sourceValue;        } else {            Log::error("dvd::vm::Processor::executeSet: SWAP instruction with no source register!\n");            scheduler.addFirstPlayPGC();            return false;        }        break;      case Instruction::ADD:        destValue += sourceValue;        if (destValue>Register::maxValue) destValue=Register::maxValue;        break;      case Instruction::SUB:        destValue -= sourceValue;        if (destValue>Register::maxValue) destValue=0;        break;      case Instruction::MUL:        destValue *= sourceValue;        if (destValue>Register::maxValue) destValue=Register::maxValue;        break;      case Instruction::DIV:        if (sourceValue>0) destValue /= sourceValue;        else destValue = 0;        break;      case Instruction::MOD:        if (sourceValue>0) destValue %= sourceValue;        else destValue = 0;        break;      case Instruction::RND:        // FIXME: add a srand somewhere!        destValue = (unsigned)((double)sourceValue * rand() / (1.0 + RAND_MAX));        break;      case Instruction::AND:        destValue &= sourceValue;        break;      case Instruction::OR:        destValue |= sourceValue;        break;      case Instruction::XOR:        destValue ^= sourceValue;        break;      default:        Log::error("dvd::vm::Processor::executeSet: invalid set operation: %u!\n",                     (unsigned)instruction->getSetOp());        scheduler.addFirstPlayPGC();        return false;      case Instruction::SET_NONE:        break;    }    destRegister.setValue(destValue);    return true;}//------------------------------------------------------------------------------void Processor::executeSetCLnk(const Instruction* instruction){    if (!executeSetWithLink(instruction)) return;        if (!evaluateSetCLnkCondition(instruction)) {        scheduler.addStep();        return;    }        executeLinkSubset(instruction);}//------------------------------------------------------------------------------bool Processor::executeSetWithLink(const Instruction* instruction){    if (instruction->getSetOp()==Instruction::SET_NONE) return true;    GPR& destRegister =        state.getGPRM().getRegister(instruction->getSRD());    unsigned sourceValue = 0;    Register* sourceRegister = 0;        if (instruction->isDirect()) {        sourceValue = instruction->operand1.getSVAL();    } else {        sourceRegister =             &(state.getRegister(instruction->operand1.getSRS()));        sourceValue = sourceRegister->getValue();    }        return executeSet(instruction, destRegister,                      sourceValue, sourceRegister);}//------------------------------------------------------------------------------void Processor::executeCSetCLnk(const Instruction* instruction){    if (!evaluateCSetCLnkCondition(instruction)) {        scheduler.addStep();        return;    }        if (!executeSetWithLink(instruction)) return;        executeLinkSubset(instruction);}//------------------------------------------------------------------------------void Processor::executeCmpSetLnk(const Instruction* instruction){    if (evaluateCmpSetLnkCondition(instruction)) {        if (!executeSetWithLink(instruction)) return;    }        executeLinkSubset(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateConditionV1(const Instruction* instruction) const{    Instruction::cmpOp_t cmpOp = instruction->getCmpOp();    if (cmpOp==Instruction::CMP_NONE) return true;    unsigned value1 =        state.getValue(instruction->operand1.getCR1());    unsigned value2 =        instruction->isCmpDirect() ?         instruction->operand2.getValue() :         state.getValue(instruction->operand2.getCR2());    return evaluateComparison(cmpOp, value1, value2);}//------------------------------------------------------------------------------bool Processor::evaluateConditionV2(const Instruction* instruction) const{    Instruction::cmpOp_t cmpOp = instruction->getCmpOp();    if (cmpOp==Instruction::CMP_NONE) return true;    unsigned value1 =        state.getValue(instruction->operand3.getCR1());    unsigned value2 =        state.getValue(instruction->operand3.getCR2());    return evaluateComparison(cmpOp, value1, value2);}//------------------------------------------------------------------------------bool Processor::evaluateConditionV3(const Instruction* instruction) const{    Instruction::cmpOp_t cmpOp = instruction->getCmpOp();    if (cmpOp==Instruction::CMP_NONE) return true;    unsigned value1 =        state.getValue(instruction->operand1.getSetCR1());    unsigned value2 =        instruction->isCmpDirect() ?         instruction->operand3.getCVAL() :         state.getValue(instruction->operand3.getCR2());    return evaluateComparison(cmpOp, value1, value2);}//------------------------------------------------------------------------------bool Processor::evaluateConditionV4(const Instruction* instruction) const{    Instruction::cmpOp_t cmpOp = instruction->getCmpOp();    if (cmpOp==Instruction::CMP_NONE) return true;    unsigned value1 =        state.getValue(instruction->getCR1());    unsigned value2 =        instruction->isCmpDirect() ?         instruction->operand2.getCVAL() :         state.getValue(instruction->operand2.getCR2());    return evaluateComparison(cmpOp, value1, value2);}//------------------------------------------------------------------------------bool Processor::evaluateSpecialCondition(const Instruction* instruction) const{    return evaluateConditionV1(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateLinkCondition(const Instruction* instruction) const{    return evaluateConditionV1(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateJumpCallCondition(const Instruction* instruction) const{    return evaluateConditionV2(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateSetSysRegCondition(const Instruction* instruction) const{    return evaluateConditionV2(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateSetCondition(const Instruction* instruction) const{    return evaluateConditionV3(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateSetCLnkCondition(const Instruction* instruction) const{    return evaluateConditionV4(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateCSetCLnkCondition(const Instruction* instruction) const{    return evaluateConditionV4(instruction);}//------------------------------------------------------------------------------bool Processor::evaluateCmpSetLnkCondition(const Instruction* instruction) const{    return evaluateConditionV4(instruction);}//------------------------------------------------------------------------------//------------------------------------------------------------------------------

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -