T_GeneratorError C_TaskControl::init () { T_GeneratorError L_error_code ; GEN_DEBUG(0, "C_TaskControl::init() start"); L_error_code = InitProcedure(); if (L_error_code == E_GEN_NO_ERROR) { M_state = C_TaskControl::E_STATE_INIT ; } GEN_DEBUG(0, "C_TaskControl::init() end"); return (L_error_code); }
/* * 获取单个函数帧 * 使用IsProcEnd函数鉴别末尾,不处理中间遇到的CALL指令 */ __INLINE__ PPROCEDURE __INTERNAL_FUNC__ GetProcFrame(__memory pMem, __memory pStart, __integer iBlockMaxSize, PPROGRAM pParents) { PPROCEDURE pProcedure = InitProcedure(pParents); PX86INSTRUCTION pInstructionPrev = NULL, *pInstructionPoint = &(pProcedure->pInstruction); __address ImageBase = pParents->ImageBase; __offset ofOffset = 0; __integer iContinueSize = 0, iInstCount = 0; __bool bPredictProcEnd = FALSE;//是否启用预测函数结尾 ud_t ud_obj; ud_init(&ud_obj); ud_set_mode(&ud_obj, 32); ud_set_input_buffer(&ud_obj, pStart, iBlockMaxSize); ud_set_syntax(&ud_obj, UD_SYN_INTEL); /* * 预测结尾分析 * 可以在为遍历完指令流时,预先知道函数的末尾 */ // 获取整个函数框架 while (ud_disassemble(&ud_obj)) { __memory pCurrent = pStart + ofOffset; // 如果是未知指令,则记录它的数量 if (ud_obj.mnemonic == UD_Iinvalid) (pProcedure->iInvalidOpcodeCount)++; *pInstructionPoint = InitInstruction(pProcedure, pInstructionPrev); AnalyzeInstructionPass1(&ud_obj, pMem, ImageBase, pCurrent, ofOffset, *pInstructionPoint); pInstructionPrev = *pInstructionPoint; // 判断是否到达函数末尾,常规分析 if (IsProcEnd(&ud_obj, pProcedure->pInstruction, *pInstructionPoint, &bPredictProcEnd, &iContinueSize)) { ofOffset += ud_obj.inp_ctr; iInstCount++; goto _end_while; } /* * 如果进入这里则说明当前指令必定是ret指令 */ if (bPredictProcEnd) { // 将反汇编的缓冲区长度设置为 // 从当前指令到预测出的函数结尾 __memory pRetNextInstruction = (*pInstructionPoint)->pCurrFileAddress + ud_obj.inp_ctr;//得到ret指令下一条指令的位置 ofOffset += ud_obj.inp_ctr;//将当前指令的长度加入偏移值内 ud_set_input_buffer(&ud_obj, pRetNextInstruction, (size_t)iContinueSize);//ud_obj会重新初始化 pInstructionPoint = &((*pInstructionPoint)->pNext); iInstCount++; bPredictProcEnd = FALSE; continue;//直接进入下一轮 } // 移动指针 pInstructionPoint = &((*pInstructionPoint)->pNext); ofOffset += ud_obj.inp_ctr; iInstCount++; }/* end while */ _end_while: // 填充函数基本信息 pProcedure->addrMemoryStartAddress = pParents->ImageBase + AnalyzerRaw2Rva(pMem, (__integer)(pStart - pMem)); pProcedure->pFileStartAddress = pStart; pProcedure->iSize = (__integer)ofOffset; pProcedure->iInstCount = iInstCount; pProcedure->pInstructionJmp = GetInstructionJmpListHeader(pProcedure); return pProcedure; }