void __stdcall DynLoader()
{
_asm
{
//----------------------------------
DWORD_TYPE(DYN_LOADER_START_MAGIC)
//----------------------------------
Main_0:
PUSHAD // Save the registers context in stack
CALL Main_1
Main_1:
POP EBP
SUB EBP,OFFSET Main_1 // Get Base EBP
MOV EAX,DWORD PTR [EBP+_RO_dwImageBase]
ADD EAX,DWORD PTR [EBP+_RO_dwOrgEntryPoint]
MOV DWORD PTR [ESP+10h],EAX // pStack.Ebx <- EAX
LEA EAX,[EBP+_except_handler1_OEP_Jump]
MOV DWORD PTR [ESP+1Ch],EAX // pStack.Eax <- EAX
POPAD // Restore the first registers context from stack
...
//----------------------------------
DWORD_TYPE(DYN_LOADER_START_DATA1)
//----------------------------------
_RO_dwImageBase: DWORD_TYPE(0xCCCCCCCC)
_RO_dwOrgEntryPoint: DWORD_TYPE(0xCCCCCCCC)
//----------------------------------
DWORD_TYPE(DYN_LOADER_END_MAGIC)
//----------------------------------
}
}
DWORD_TYPE这些只是给二进制代码做标记, 从DWORD_TYPE(DYN_LOADER_START_MAGIC)到DWORD_TYPE(DYN_LOADER_END_MAGIC)之间的二进制将被复制到目标exe中, 目标exe的OEP写在_RO_dwOrgEntryPoint, 通过取这个地址里的内容来完成跳回OEP, 我看不明白的是CALL Main_1, 这个在目标exe能正常执行么?复制过去后地址都变了, 如果可以,那么又何必要算来算去的去取OEP, 直接取_RO_dwOrgEntryPoint不就行了? 难道call 里的标号取的是个相对地址, 与二进制本身的位置无关, 而mov里的标号取的是绝对的地址, 所以不能直接用,要算出实际在目标exe中的地址来..
[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课