ROP - Return Oriented Programing
Basiese Inligting
Return-Oriented Programming (ROP) is 'n gevorderde uitbuitingstegniek wat gebruik word om sekuriteitsmaatreëls soos No-Execute (NX) of Data Execution Prevention (DEP) te omseil. In plaas van om shellcode in te spuit en uit te voer, maak 'n aanvaller gebruik van stukke kode wat reeds teenwoordig is in die binêre lêer of in gelaai biblioteke, bekend as "gadgets". Elke gadget eindig tipies met 'n ret
instruksie en voer 'n klein operasie uit, soos die skuif van data tussen registre of die uitvoer van rekenkundige operasies. Deur hierdie gadgets aan mekaar te koppel, kan 'n aanvaller 'n lading bou om arbitrêre operasies uit te voer, wat effektief NX/DEP-beskerming omseil.
Hoe ROP Werk
Beheerstroomkaping: Eerstens moet 'n aanvaller die beheerstroom van 'n program kap, tipies deur 'n buffer-oorvloei te benut om 'n gestoorde terugkeeradres op die stok oor te skryf.
Gadget-ketting: Die aanvaller kies dan sorgvuldig gadgets en koppel hulle aan mekaar om die gewenste aksies uit te voer. Dit kan die opstel van argumente vir 'n funksieoproep behels, die roep van die funksie (bv.,
system("/bin/sh")
), en die hanteer van enige nodige skoonmaak of bykomende operasies.Ladinguitvoering: Wanneer die kwesbare funksie terugkeer, begin dit in plaas van om na 'n wettige plek terug te keer, die ketting van gadgets uitvoer.
Gereedskap
Gewoonlik kan gadgets gevind word met behulp van ROPgadget, ropper of direk vanuit pwntools (ROP).
ROP-ketting in x86 Voorbeeld
x86 (32-bis) Oproepkonvensies
cdecl: Die oproeper maak die stok skoon. Funksie-argumente word in omgekeerde volgorde op die stok gedruk (van regs na links). Argumente word van regs na links op die stok gedruk.
stdcall: Soortgelyk aan cdecl, maar die ontvanger is verantwoordelik vir die skoonmaak van die stok.
Gadgets Vind
Eerstens, laat ons aanneem dat ons die nodige gadgets binne die binêre lêer of sy gelaai biblioteke geïdentifiseer het. Die gadgets waarin ons belangstel, is:
pop eax; ret
: Hierdie gadget skuif die boonste waarde van die stok in dieEAX
-register en keer dan terug, wat ons in staat stel omEAX
te beheer.pop ebx; ret
: Soortgelyk aan die bogenoemde, maar vir dieEBX
-register, wat beheer oorEBX
moontlik maak.mov [ebx], eax; ret
: Skuif die waarde inEAX
na die geheueplek wat deurEBX
aangedui word en keer dan terug. Dit word dikwels 'n write-what-where gadget genoem.Daarbenewens het ons die adres van die
system()
-funksie beskikbaar.
ROP-ketting
Met behulp van pwntools berei ons die stok voor vir die uitvoering van die ROP-ketting soos hieronder gemik om system('/bin/sh')
uit te voer, let op hoe die ketting begin met:
'n
ret
instruksie vir uitlyn doeleindes (opsioneel)Adres van
system
-funksie (onder die veronderstelling dat ASLR uitgeskakel is en bekende libc, meer inligting in Ret2lib)Plekhouer vir die terugkeeradres van
system()
"/bin/sh"
string-adres (parameter vir stelsel funksie)
ROP Ketting in x64 Voorbeeld
x64 (64-bis) Oproepkonvensies
Gebruik die System V AMD64 ABI oproepkonvensie op Unix-soortgelyke stelsels, waar die eerste ses heelgetal- of wysaanwysingsargumente in die register
RDI
,RSI
,RDX
,RCX
,R8
, enR9
oorgedra word. Addisionele argumente word op die stok oorgedra. Die terugvoerwaarde word inRAX
geplaas.Die Windows x64 oproepkonvensie gebruik
RCX
,RDX
,R8
, enR9
vir die eerste vier heelgetal- of wysaanwysingsargumente, met addisionele argumente wat op die stok oorgedra word. Die terugvoerwaarde word inRAX
geplaas.Register: 64-bis register sluit in
RAX
,RBX
,RCX
,RDX
,RSI
,RDI
,RBP
,RSP
, enR8
totR15
.
Vind Gadgets
Vir ons doel, laat ons fokus op gadgets wat ons sal toelaat om die RDI register in te stel (om die "/bin/sh" string as 'n argument aan system() oor te dra) en dan die system() funksie aan te roep. Ons aanvaar dat ons die volgende gadgets geïdentifiseer het:
pop rdi; ret: Haal die boonste waarde van die stok uit in RDI en keer dan terug. Essensieel vir die instelling van ons argument vir system().
ret: 'n Eenvoudige terugkeer, nuttig vir stokuitlyn in sommige scenarios.
En ons weet die adres van die system() funksie.
ROP Ketting
Hieronder is 'n voorbeeld wat pwntools gebruik om 'n ROP-reeks op te stel en uit te voer met die doel om system('/bin/sh') uit te voer op x64:
In hierdie voorbeeld:
Ons maak gebruik van die
pop rdi; ret
instrument omRDI
in te stel op die adres van"/bin/sh"
.Ons spring direk na
system()
nadat onsRDI
ingestel het, met system() se adres in die ketting.ret_gadget
word gebruik vir belyn as die teikenomgewing dit vereis, wat meer algemeen is in x64 om behoorlike stakingsbelyn te verseker voordat funksies geroep word.
Stakingsbelyn
Die x86-64 ABI verseker dat die stapel 16-byte gebelyn is wanneer 'n oproepinstruksie uitgevoer word. LIBC, om prestasie te optimaliseer, gebruik SSE-instruksies (soos movaps) wat hierdie belyn vereis. As die stapel nie behoorlik gebelyn is nie (wat beteken dat RSP nie 'n veelvoud van 16 is nie), sal oproepe na funksies soos system misluk in 'n ROP-ketting. Om dit reg te stel, voeg eenvoudig 'n ret gadget by voordat jy system in jou ROP-ketting aanroep.
x86 vs x64 hoofverskil
Aangesien x64 registers gebruik vir die eerste paar argumente, benodig dit dikwels minder gadgets as x86 vir eenvoudige funksie-oproepe, maar die vind en koppel van die regte gadgets kan meer kompleks wees as gevolg van die verhoogde aantal registers en die groter adresruimte. Die verhoogde aantal registers en die groter adresruimte in x64-argitektuur bied beide geleenthede en uitdagings vir uitbuitontwikkeling, veral in die konteks van Return-Oriented Programming (ROP).
ROP-ketting in ARM64 Voorbeeld
ARM64 Basiese beginsels & Oproepkonvensies
Kyk na die volgende bladsy vir hierdie inligting:
Introduction to ARM64v8Beskerming teen ROP
Stapelkanaries: In geval van 'n BOF, is dit nodig om die stapelkanarie te omseil om terugkeerpunte te oorskryf om 'n ROP-ketting te misbruik.
Gebrek aan Gadgets: As daar nie genoeg gadgets is nie, sal dit nie moontlik wees om 'n ROP-ketting te genereer nie.
ROP-gebaseerde tegnieke
Let daarop dat ROP net 'n tegniek is om arbitrêre kode uit te voer. Gebaseer op ROP is baie Ret2XXX-tegnieke ontwikkel:
Ret2lib: Gebruik ROP om arbitrêre funksies van 'n gelaai biblioteek met arbitrêre parameters aan te roep (gewoonlik iets soos
system('/bin/sh')
.
Ret2Syscall: Gebruik ROP om 'n oproep na 'n syscall voor te berei, bv.
execve
, en maak dit moontlik om arbitrêre bevele uit te voer.
EBP2Ret & EBP Chaining: Die eerste sal EBP misbruik in plaas van EIP om die vloei te beheer en die tweede is soortgelyk aan Ret2lib, maar in hierdie geval word die vloei hoofsaaklik met EBP-adresse beheer (alhoewel dit ook nodig is om EIP te beheer).
Ander Voorbeelde & Verwysings
64 bit, Pie en nx geaktiveer, geen kanarie, oorskryf RIP met 'n
vsyscall
-adres met die enigste doel om terug te keer na die volgende adres in die stapel wat 'n gedeeltelike oorskrywing van die adres sal wees om die deel van die funksie te kry wat die vlag lekarm64, geen ASLR, ROP-gadget om stapel uitvoerbaar te maak en te spring na shellcode in stapel
Last updated