Project Overview
A solved cybersecurity lab case study explaining the getscore buffer overflow requirements, GDB crash analysis, EIP offset discovery, privilege escalation result, defenses and the extra credit command injection finding.
This case study describes an authorised university lab using a deliberately vulnerable legacy virtual machine. Exact shellcode bytes, the reusable jump address and the command-injection payload are intentionally omitted from the public article.
Requirement → Solution Map
The lab is organised into four stages: prepare the virtual machine, compile and configure the getscore program, deliberately trigger and inspect a segmentation fault, and then use the crash evidence to reason about a controlled buffer overflow in the authorised lab environment.
Grading Breakdown
The submitted report must include detailed screenshots for each stage and a detailed explanation of how the result for each stage was obtained.
Step-by-Step Assignment Solution
The completed solution followed the same four-stage structure and documented the evidence required to move from a normal program run to a confirmed stack overwrite and finally to successful privilege escalation inside the supplied legacy VM.
Setup the VM
Import the supplied Red Hat virtual machine and prepare the getscore.c and score.txt files in the lab environment.
gcc getscore.c -o getscore | chmod 755 getscore; chmod u+s getscore; chmod 600 score.txt
getscore (setuid root) on a Red Hat Linux VM
The solution compiled getscore, applied the required permissions and verified that the setuid bit caused the program to execute with root effective privileges even when it was launched by the guest user.
Compile and Configure getscore
Compile getscore, set the required executable and setuid permissions, protect score.txt, then verify that the program behaves differently when executed by the guest account.
The solution compiled getscore, applied the required permissions and verified that the setuid bit caused the program to execute with root effective privileges even when it was launched by the guest user.
The program was compiled, the required permissions were applied and the guest account was used to verify the setuid behaviour.
This proves why a later memory-safety failure has a much larger security impact: the vulnerable program executes with root effective privileges.
View the setup commands used in this lab
Compile the supplied program
gcc getscore.c -o getscore
Apply the lab permissions
chmod 755 getscore; chmod u+s getscore; chmod 600 score.txt
Trigger the Crash and Inspect GDB Evidence
Provide oversized input to cause a segmentation fault, enable a core dump and use GDB to inspect registers and stack memory.
EIP = 0x41414141
gdb -c core.xxxx | info registers $eip | info registers $esp | x/100x $esp-200
The key turning point in the solution was the GDB evidence. First, EIP became 0x41414141 after the repeated A input. The cyclic-pattern run then identified the exact saved-EIP position as 134 bytes. This answered the assignment question about where EIP must be overwritten without guessing the offset.
View the GDB evidence commands
Open a core dump in GDB
gdb -c core.xxxx
Inspect the saved instruction pointer
info registers $eip
Inspect the stack pointer
info registers $esp
Inspect stack memory
x/100x $esp-200
The key turning point in the solution was the GDB evidence. First, EIP became 0x41414141 after the repeated A input. The cyclic-pattern run then identified the exact saved-EIP position as 134 bytes. This answered the assignment question about where EIP must be overwritten without guessing the offset.
Build and Validate the Lab Exploit
Determine how long the input must be, where the saved EIP is located in the input and what kind of return target is needed for the lab exploit.
The final report records successful privilege escalation from guest (uid=500) to root (uid=0) in the authorised Red Hat VM.
The final report records successful privilege escalation from guest (uid=500) to root (uid=0) in the authorised Red Hat VM.
Conceptually, the final lab payload contained controlled padding up to the saved return address, a lab-specific control-flow redirection, additional landing space and the supplied shellcode. The important academic point is how the crash evidence was converted into a reproducible payload layout, not the memorisation of one address or byte string.
Conceptually, the final lab payload contained controlled padding up to the saved return address, a lab-specific control-flow redirection, additional landing space and the supplied shellcode. The important academic point is how the crash evidence was converted into a reproducible payload layout, not the memorisation of one address or byte string.
Need help with a similar assignment or project?
Send your assignment brief, marking rubric or existing work for originality-focused support, technical review, troubleshooting and project guidance tailored to your requirements.
Why the Exploit Worked
Unbounded copy
The vulnerable getscore program copies user-controlled data into a fixed-size stack buffer without adequate bounds checking, allowing the saved return address to be overwritten.
Known EIP offset
The cyclic-pattern analysis established the exact position of the saved EIP at 134 bytes.
Controlled redirection
A JMP ESP technique redirected execution toward attacker-controlled data on the stack inside the lab VM.
Setuid root context
Because the binary runs with root effective privileges, successful code execution inherits that elevated privilege in the lab.
Legacy mitigations
The report notes that the supplied environment lacked modern protections such as stack canaries, ASLR and NX, making the demonstration reliable.
Defenses That Would Have Prevented It
Detects a return-address overwrite and aborts execution.
Randomizes the C library location so a fixed control-flow target is no longer reliable.
Marks stack memory non-executable, preventing injected stack code from running.
Bounds-checked copying prevents the original buffer overwrite.
Reducing privileges means a successful memory-safety exploit does not automatically become a root shell.
Extra Credit: OS Command Injection Vulnerability
The extra-credit analysis identified a second vulnerability in getscore: OS Command Injection in the error-logging path. When authentication fails, the program formats user-controlled name and SSN values into a shell command and executes that command with system().
sprintf(command,
"echo \"%s: Invalid user name or SSN: %s,%s\"|cat >> error.log",
ctime(¤t_time), argv[1], argv[2]);
if (system(command)) {
perror("Logging");
}
User-controlled values are inserted into a shell command and then passed to system().
The supplied analysis also notes that main() sets both real and effective UIDs to root. That means an injected command in this path would execute with root privileges. The public case study omits the exploit payload and command sequence and focuses on the vulnerability cause and privilege impact.
What Students Should Learn From This Project
Start with the assignment requirements and collect evidence for each required step instead of jumping directly to exploitation.
Use the segmentation fault and core dump as evidence. The overwritten EIP value proves control of the return address.
Use a cyclic pattern to calculate the exact offset rather than estimating where EIP is stored.
Explain why setuid changes the security impact of the same memory-safety bug.
A strong report connects screenshots and command output to interpretation, then finishes with practical mitigations.
Separate the primary buffer-overflow finding from the extra-credit command-injection finding because they arise from different vulnerable code paths.