/* * Register operations happen here * */ void Operation(Operators op) { GetToken(); int i; if(IsRegister()) { for(i = 0;i < 5;i++) { if(TokenType(RegList[i])) break; } } else { printf("Expected register, not %s or %d\n", Look->value.string, Look->value.number); exit(1); } GetToken(); if(IsNumber()) { switch(op) { case ADD: Register[i] += Look->value.number; break; case SUB: Register[i] -= Look->value.number; break; case SHL: Register[i] = Register[i] << Look->value.number; break; case SHR: Register[i] = Register[i] >> Look->value.number; break; case SET: Register[i] = Look->value.number; break; case AND: Register[i] = Register[i] & Look->value.number; break; case OR: Register[i] = Register[i] | Look->value.number; break; default: printf(" opcode: %d",op); } } else if(IsRegister())
//안태훈 수정 시작 //(For Performance)(0.2) BOOL CTagManager::IsRegister(const char *name) { return IsRegister(std::string(name)); }
void Permutator::__CreateGraph(BYTE* sectionData, _OffsetType blockOffset, DWORD dwSectionSize, _OffsetType parentOffset) { _DecodeResult res; unsigned int decodedInstructionsCount = 0; _DecodeType dt = Decode32Bits; _OffsetType offsetEnd; _DecodedInst decodedInstructions[MAX_INSTRUCTIONS]; unsigned int i; QWORD tmpOffset = blockOffset; std::string mnemonic, operand; std::vector<Block> targets; std::queue<Block> blockQueue; bool skipFlag; bool disasmStopFlag; Block block; block.offset = blockOffset; block.parentOffset = parentOffset; blockQueue.push(block); while (!blockQueue.empty()) { skipFlag = false; Block currentBlock = blockQueue.front(); blockQueue.pop(); for (std::vector<Block>::iterator it = targets.begin(); it != targets.end(); ++it) { if (((*it).offset == currentBlock.offset) && (*it).parentOffset == currentBlock.parentOffset) { skipFlag = true; break; } } if (skipFlag) continue; // Disassembly part while (1) { disasmStopFlag = false; res = distorm_decode(currentBlock.offset, (const unsigned char*)(sectionData + currentBlock.offset), (DWORD)(dwSectionSize - currentBlock.offset), dt, decodedInstructions, MAX_INSTRUCTIONS, &decodedInstructionsCount); if (res == DECRES_INPUTERR) { free(sectionData); return; } for (i = 0; i < decodedInstructionsCount; ++i) { mnemonic = (reinterpret_cast<char*>(decodedInstructions[i].mnemonic.p)); if (IsJump(mnemonic) || mnemonic.compare("RET") == 0 || mnemonic.compare("RETN") == 0 || mnemonic.substr(0, 2).compare("DB") == 0) { disasmStopFlag = true; break; } if (mnemonic.compare("CALL") == 0) { std::string functionOperand = reinterpret_cast<char*> (decodedInstructions[i].operands.p); if (IsRegister(functionOperand) || !IsFunctionOperandValid(functionOperand)) continue; QWORD functionOffset = std::stoll(functionOperand, nullptr, 0); graph.AddFunctionOffset(tmpOffset, functionOffset - tmpOffset); } tmpOffset += decodedInstructions[i].size; } if (disasmStopFlag) break; } offsetEnd = decodedInstructions[i].offset; DWORD blockSize = (DWORD)(offsetEnd + decodedInstructions[i].size - currentBlock.offset); currentBlock.blockSize = blockSize; // Set 1 to block places in dataBytes for (DWORD j = 0; j < blockSize; ++j) { dataBytes[currentBlock.offset + j] = 1; } targets.push_back(currentBlock); if (mnemonic.compare("RET") == 0 || mnemonic.compare("RETN") == 0 || mnemonic.substr(0, 2).compare("DB") == 0) continue; operand = reinterpret_cast<char*>(decodedInstructions[i].operands.p); operand.resize(decodedInstructions[i].operands.length); if (IsRegister(operand)) continue; QWORD newOffset = std::stoll(operand, nullptr, 0); if (!CheckRange(newOffset)) { std::cerr << "Offset out of CODE section!" << std::endl; continue; } Block positiveJumpBlock; positiveJumpBlock.offset = newOffset; positiveJumpBlock.parentOffset = currentBlock.offset; blockQueue.push(positiveJumpBlock); if (mnemonic.compare("JMP") == 0) continue; QWORD jumpFalseOffset = offsetEnd + decodedInstructions[i].size; if (!CheckRange(newOffset)) { std::cerr << "Offset out of CODE section!" << std::endl; continue; } Block negativeJumpBlock; negativeJumpBlock.offset = jumpFalseOffset; negativeJumpBlock.parentOffset = currentBlock.offset; blockQueue.push(negativeJumpBlock); } // Graph creation for (DWORD i = 0; i < targets.size(); ++i) { Block b = targets.at(i); Node* n = new Node(); n->SetOffset((DWORD) b.offset); n->SetInstructions((BYTE*)(sectionData + b.offset), b.blockSize); graph.AddNode(n, (DWORD)b.parentOffset); } return; }
void Permutator::_CreateGraph(BYTE* sectionData, _OffsetType blockOffset, DWORD dwSectionSize, _OffsetType parentOffset, std::vector<Block>& targets) { _DecodeResult res; unsigned int decodedInstructionsCount = 0; _DecodeType dt = Decode32Bits; _OffsetType offset = blockOffset; _OffsetType offsetEnd; _DecodedInst decodedInstructions[MAX_INSTRUCTIONS]; unsigned int i; QWORD tmpOffset = blockOffset; std::string mnemonic, operand; bool skipFlag; while (1) { res = distorm_decode(offset, (const unsigned char*)sectionData, dwSectionSize, dt, decodedInstructions, MAX_INSTRUCTIONS, &decodedInstructionsCount); if (res == DECRES_INPUTERR) { free(sectionData); return; } for (i = 0; i < decodedInstructionsCount; ++i) { mnemonic = (reinterpret_cast<char*>(decodedInstructions[i].mnemonic.p)); if (IsJump(mnemonic) || mnemonic.compare("RET") == 0 || mnemonic.compare("RETN") == 0 || mnemonic.substr(0, 2).compare("DB") == 0) { break; } if (mnemonic.compare("CALL") == 0) { std::string functionOperand = reinterpret_cast<char*> (decodedInstructions[i].operands.p); if (IsRegister(functionOperand) || !IsFunctionOperandValid(functionOperand)) continue; QWORD functionOffset = std::stoll(functionOperand, nullptr, 0); graph.AddFunctionOffset(tmpOffset, functionOffset - tmpOffset); } tmpOffset += decodedInstructions[i].size; } // Main part of graph creation offsetEnd = decodedInstructions[i].offset; DWORD blockSize = (DWORD)(offsetEnd + decodedInstructions[i].size - offset); Node* node = new Node(); // Set 1 to block places in dataBytes for (DWORD j = 0; j < blockSize; ++j) { dataBytes[blockOffset + j] = 1; } node->SetOffset((DWORD)offset); node->SetInstructions(sectionData, blockSize); // Newly added code skipFlag = false; for (std::vector<Block>::iterator it = targets.begin(); it != targets.end(); ++it) { if (((*it).offset == node->GetOffset()) && (*it).parentOffset == parentOffset) { skipFlag = true; break; } } if (skipFlag) return; Block b; b.offset = node->GetOffset(); b.parentOffset = parentOffset; targets.push_back(b); if (graph.AddNode(node, (DWORD)parentOffset)) { return; } if (mnemonic.compare("RET") == 0 || mnemonic.compare("RETN") == 0 || mnemonic.substr(0, 2).compare("DB") == 0) return; operand = reinterpret_cast<char*>(decodedInstructions[i].operands.p); operand.resize(decodedInstructions[i].operands.length); if (IsRegister(operand)) return; QWORD newOffset = std::stoll(operand, nullptr, 0); if (!CheckRange(newOffset)) { std::cerr << "Offset out of CODE section!" << std::endl; return; } _CreateGraph(sectionData + blockSize + (newOffset - offsetEnd - decodedInstructions[i].size), newOffset, dwSectionSize - (DWORD)newOffset + (DWORD)offset, node->GetOffset(), targets); if (mnemonic.compare("JMP") == 0) return; QWORD jumpFalseOffset = offsetEnd + decodedInstructions[i].size; _CreateGraph(sectionData + jumpFalseOffset - offset, jumpFalseOffset, dwSectionSize - (DWORD)jumpFalseOffset + (DWORD)offset, node->GetOffset(), targets); break; } }