// CWDE : EAX <- signExtend(AX) void CONVERT::sCWDE(THREADID tid, ADDRINT regAXValue, ADDRINT insAddress) { TaintManager_Thread *pTmgrTls = getTmgrInTls(tid); if (pTmgrTls->isRegisterTainted<16>(REG_AX)) { _LOGTAINT(tid, insAddress, "CWDE"); // affectation à EAX (enregistrement du TaintDword) pTmgrTls->updateTaintRegister<32>(REG_EAX, std::make_shared<TaintDword>( X_SIGNEXTEND, ObjectSource(pTmgrTls->getRegisterTaint<16>(REG_AX, regAXValue)))); } else pTmgrTls->unTaintRegister<32>(REG_EAX); // démarquage EAX } // cCWDE
void CONVERT::sCBW(THREADID tid, ADDRINT insAddress) { TaintManager_Thread *pTmgrTls = getTmgrInTls(tid); REGINDEX regIndex = getRegIndex(REG_AL); if (pTmgrTls->isRegisterPartTainted(regIndex, 0)) { _LOGTAINT(tid, insAddress, "CBW"); // affectation à AX (enregistrement du TaintWord) pTmgrTls->updateTaintRegister<16>(REG_AX, std::make_shared<TaintWord>( X_SIGNEXTEND, ObjectSource(pTmgrTls->getRegisterPartTaint(regIndex, 0)))); } else pTmgrTls->unTaintRegisterPart(regIndex, 1); // simple démarquage AH (AL l'est déjà) } // cCBW
// CWD : DX:AX <- signExtend(AX) void CONVERT::sCWD(THREADID tid, ADDRINT regAXValue, ADDRINT insAddress) { TaintManager_Thread *pTmgrTls = getTmgrInTls(tid); if (pTmgrTls->isRegisterTainted<16>(REG_AX)) { _LOGTAINT(tid, insAddress, "CWD"); // construction du résultat TaintDwordPtr tdwPtr = std::make_shared<TaintDword>( X_SIGNEXTEND, ObjectSource(pTmgrTls->getRegisterTaint<16>(REG_AX, regAXValue))); // marquage de la destination (DX:AX) // les 2 octets faibles du résultat => inchangés, aucun traitement // les 2 octets forts du résultat => marquage sur DX // extraction depuis le résultat du TaintWord d'index 1 pTmgrTls->updateTaintRegister<16>(REG_DX, std::make_shared<TaintWord>( EXTRACT, ObjectSource(tdwPtr), ObjectSource(8, 1))); } else pTmgrTls->unTaintRegister<16>(REG_DX); // démarquage DX (AX l'est déjà) } // cCWD
void SEMAPHORE::sCMPXCHG16B(THREADID tid, ADDRINT address, ADDRINT regRAXValue, ADDRINT regRDXValue, ADDRINT insAddress) { TaintManager_Thread *pTmgrTls = getTmgrInTls(tid); // 1ere partie de CMPXCHG16B : // CMP_RM entre RDX:RAX et m128. // Procédure spécifique (impossible de faire appel à BINARY::sCMP_RM) bool isMemTainted = pTmgrGlobal->isMemoryTainted<128>(address); ADDRINT srcMemLowValue = getMemoryValue<64>(address); ADDRINT srcMemHighValue = getMemoryValue<64>(address + 8); bool isRAXTainted = pTmgrTls->isRegisterTainted<64>(REG_EAX); bool isRDXTainted = pTmgrTls->isRegisterTainted<64>(REG_EDX); // marquage flags : seul ZF est affecté, les autres (O/S/A/P/C) sont inchangés if ( !(isMemTainted || isRAXTainted || isRDXTainted)) pTmgrTls->unTaintAllFlags(); else { _LOGTAINT(tid, insAddress, "CMPXCHG16B - FLAG MARQUE"); // pour représenter RDX:RAX et la mémoire il n'est pas possible de faire une concaténation // car cela ne pourra pas traiter le cas ou les deux registres sont démarqués // cf CMPXCHG16B ObjectSource srcMemLow = (pTmgrGlobal->isMemoryTainted<64>(address)) ? ObjectSource(pTmgrGlobal->getMemoryTaint<64>(address)) : ObjectSource(64, srcMemLowValue); ObjectSource srcMemHigh = (pTmgrGlobal->isMemoryTainted<64>(address + 8)) ? ObjectSource(pTmgrGlobal->getMemoryTaint<64>(address + 8)) : ObjectSource(64, srcMemHighValue); ObjectSource srcRAX = (isRAXTainted) ? ObjectSource(pTmgrTls->getRegisterTaint<64>(REG_RAX, regRAXValue)) : ObjectSource(64, regRAXValue); ObjectSource srcRDX = (isRDXTainted) ? ObjectSource(pTmgrTls->getRegisterTaint<64>(REG_RDX, regRDXValue)) : ObjectSource(64, regRDXValue); // marquage flags : seul ZF est affecté, les autres (O/S/A/P/C) sont inchangés pTmgrTls->updateTaintCarryFlag(std::make_shared<TaintBit>( F_CMPXCHG_8B16B, srcMemHigh, srcMemLow, srcRDX, srcRAX)); } /**** 2EME PARTIE : ECHANGE (INDEPENDANT DU MARQUAGE DE ZF) ***/ // si mem128 == RDX:RAX, alors mem <- RCX:RBX // on fera ici un MOVRM de RBX dans addr (traitement partie basse) // puis un MOVRM de RCX dans addr + 8 (tr. partie haute) if ((srcMemLowValue == regRAXValue) && (srcMemHighValue == regRDXValue)) { DATAXFER::sMOV_RM<64>(tid, REG_RBX, address , insAddress); DATAXFER::sMOV_RM<64>(tid, REG_RCX, (address + 8), insAddress); } // sinon RDX:RAX <- mem // on fera un MOVMR de addr dans RAX (partie basse) // puis un MOVMR de addr + 3 dans RDX (partie haute) else { DATAXFER::sMOV_MR<64>(tid, address, REG_RAX, insAddress); DATAXFER::sMOV_MR<64>(tid, (address + 8), REG_RCX, insAddress); } } // sCMPXCHG16B
// SIMULATE void SEMAPHORE::sCMPXCHG8B(THREADID tid, ADDRINT address, ADDRINT regEAXValue, ADDRINT regEDXValue, ADDRINT insAddress) { TaintManager_Thread *pTmgrTls = getTmgrInTls(tid); // 1ere partie de CMPXCHG8B : // CMP_RM entre EDX:EAX et m64. // Procédure spécifique (impossible de faire appel à BINARY::sCMP_RM) bool isMemTainted = pTmgrGlobal->isMemoryTainted<64>(address); ADDRINT srcMemLowValue = getMemoryValue<32>(address); ADDRINT srcMemHighValue = getMemoryValue<32>(address + 4); bool isEAXTainted = pTmgrTls->isRegisterTainted<32>(REG_EAX); bool isEDXTainted = pTmgrTls->isRegisterTainted<32>(REG_EDX); // marquage flags : seul ZF est affecté, les autres (O/S/A/P/C) sont inchangés if ( !(isMemTainted || isEAXTainted || isEDXTainted)) pTmgrTls->unTaintZeroFlag(); else { _LOGTAINT(tid, insAddress, "CMPXCHG8B - FLAG MARQUE"); // pour représenter EDX:EAX et la mémoire il n'est pas possible de faire une concaténation // car cela ne pourra pas traiter le cas ou les deux registres sont démarqués // on pourrait envisager de faire un ObjectSource d'1 valeur de 64bits // mais afin d'uniformiser la procédure avec CMPXCHG16B (128bits) // on utilisera donc une relation spécifique pour CMPXCHG 8B et 16B // on prendra 4 arguments : memLow, memHigh, EAX, EDX. ObjectSource srcMemLow = (pTmgrGlobal->isMemoryTainted<32>(address)) ? ObjectSource(pTmgrGlobal->getMemoryTaint<32>(address)) : ObjectSource(32, srcMemLowValue); ObjectSource srcMemHigh = (pTmgrGlobal->isMemoryTainted<32>(address + 4)) ? ObjectSource(pTmgrGlobal->getMemoryTaint<32>(address + 4)) : ObjectSource(32, srcMemHighValue); ObjectSource srcEAX = (isEAXTainted) ? ObjectSource(pTmgrTls->getRegisterTaint<32>(REG_EAX, regEAXValue)) : ObjectSource(32, regEAXValue); ObjectSource srcEDX = (isEDXTainted) ? ObjectSource(pTmgrTls->getRegisterTaint<32>(REG_EDX, regEDXValue)) : ObjectSource(32, regEDXValue); pTmgrTls->updateTaintCarryFlag(std::make_shared<TaintBit>( F_CMPXCHG_8B16B, srcMemHigh, srcMemLow, srcEDX, srcEAX)); } /**** 2EME PARTIE : ECHANGE (INDEPENDANT DU MARQUAGE DE ZF) ***/ // si mem64 == EDX:EAX, alors mem <- ECX:EBX // on fera ici un MOVRM de EBX dans addr (traitement partie basse) // puis un MOVRM de ECX dans addr + 3 (tr. partie haute) if ((srcMemLowValue == regEAXValue) && (srcMemHighValue == regEDXValue)) { DATAXFER::sMOV_RM<32>(tid, REG_EBX, address , insAddress); DATAXFER::sMOV_RM<32>(tid, REG_ECX, (address + 4), insAddress); } // sinon EDX:EAX <- mem // on fera un MOVMR de addr dans EAX (partie basse) // puis un MOVMR de addr + 3 dans EDX (partie haute) else { DATAXFER::sMOV_MR<32>(tid, address, REG_EAX, insAddress); DATAXFER::sMOV_MR<32>(tid, (address + 4), REG_ECX, insAddress); } }// sCMPXCHG8B