缓冲区溢出漏洞利用失败排查及exploit3.c代码疑问
Let’s break down your two questions clearly, starting with why you’re not getting the expected /bin/sh shell.
1. Why isn’t /bin/sh being executed?
There are a few key issues causing your exploit to fail:
a. Incorrect Return Address Calculation
Your exploit uses get_sp() - offset to determine the target jump address, but this value is tied to the exploit process’s stack pointer, not the vulnerable process’s stack layout. When you launch ./vulnerable $EGG, the shell forks a new process and executes vulnerable, which resets the stack structure (including positions of argv arguments, environment variables, and stack frames). The address calculated in the exploit won’t match the actual location of your shellcode/NOP sled in the vulnerable process’s stack.
Looking at your vulnerable.c assembly:
- The
xbuffbuffer lives atebp-0x208 - The return address is stored at
ebp+4(sinceebpis pushed to the stack before the return address)
This means you need 524 bytes (0x208 + 4) to fill the buffer and overwrite the base pointer before hitting the return address. Your 612-byte buffer is sufficient in size, but the jump address is pointing to the wrong location.
b. Stack Layout Mismatch
When you pass $EGG as an argument to vulnerable, the shell expands the environment variable into a string and copies it to the vulnerable process’s argv stack region—not the environment variable region. The address you calculated using get_sp() refers to the exploit’s stack, which is completely separate from vulnerable’s argv stack area.
c. Potential ASLR Interference
If Address Space Layout Randomization (ASLR) is enabled on your system, the stack address of vulnerable will change every time it runs, making your hardcoded address calculation useless.
Fixes to Try:
- Debug to find the correct address: Use gdb to run
vulnerablewith a test payload (e.g.,./vulnerable $(python -c 'print "A"*612')), then inspect the stack to find the actual starting address of the argv[1] string. Use this address (plus an offset into your NOP sled) as the return address. - Adjust the offset parameter: Try running the exploit with different offset values (e.g.,
./exploit3 612 100,./exploit3 612 200) to fine-tune the jump address into your NOP sled. - Disable ASLR: Temporarily turn off address randomization with
echo 0 > /proc/sys/kernel/randomize_va_space(requires root) to eliminate stack address variability.
2. Why does the exploit end with system("/bin/bash")?
This line spawns a new bash shell that inherits the exploit’s environment variables. Here’s why it’s necessary:
- When you call
putenv(buff), you add theEGGvariable to the exploit’s local environment. If the exploit exited immediately, this environment variable would be destroyed (environment variables are process-specific). - The new shell launched by
system("/bin/bash")keeps theEGGvariable alive. When you run./vulnerable $EGGin this new shell, the shell can expand the$EGGvariable into your payload string and pass it tovulnerableas an argument. Without this step, the original shell wouldn’t have theEGGvariable, and$EGGwould resolve to an empty string—making the overflow impossible.
内容的提问来源于stack exchange,提问作者wafaa

