import winim, strutils var someCode: array[0x10, uint8] codeAddr: pointer = addr(someCode) # some dummy testing code for PoC purposes someCode[0] = 0x90 # NOP someCode[1] = 0x90 # NOP someCode[2] = 0x90 # NOP someCode[3] = 0xc3 # RETN # note: repr(ptr) will show the addr and reference echo "placed code at address 0x" & cast[int](codeAddr).toHex # allocate memory # https://msdn.microsoft.com/en-us/library/windows/desktop/aa366887(v=vs.85).aspx # # VirtualAlloc( # _In_opt_ LPVOID lpAddress, # _In_ SIZE_T dwSize, # _In_ DWORD flAllocationType, # _In_ DWORD flProtect); # # winim: # proc VirtualAlloc*(P1: PVOID, P2: DWORD, P3: DWORD, P4: DWORD): PVOID # {.winapi, dynlib: "kernel32", importc.} var lpvAddr: LPVOID lpvAddr = VirtualAlloc(nil, DWORD(sizeof(someCode)), MEM_COMMIT, PAGE_READWRITE) echo "VirtualAlloc returned 0x" & cast[int](lpvAddr).toHex # copy code to allocated memory copyMem(lpvAddr, codeAddr, sizeof(someCode)) # create a thread # https://msdn.microsoft.com/en-us/library/windows/desktop/ms682453(v=vs.85).aspx # # CreateThread( # _In_opt_ LPSECURITY_ATTRIBUTES lpThreadAttributes, # _In_ SIZE_T dwStackSize, # _In_ LPTHREAD_START_ROUTINE lpStartAddress, # _In_opt_ LPVOID lpParameter, # _In_ DWORD dwCreationFlags, # _Out_opt_ LPDWORD lpThreadId); # # winim: # proc CreateThread*(P1: LPSECURITY_ATTRIBUTES, P2: DWORD, P3: LPTHREAD_START_ROUTINE, # P4: PVOID, P5: DWORD, P6: PDWORD): HANDLE {.winapi, dynlib: "kernel32", importc.} var dummyThreadId: PDWORD thread: HANDLE thread = CreateThread(nil, DWORD(0), lpvAddr, nil, DWORD(0), dummyThreadId) # COMPILE/RUN RESULT: # win_test.nim(55, 22) Error: type mismatch: got (nil, DWORD, LPVOID, nil, DWORD, PDWORD) # but expected one of: # proc CreateThread(self: DEBUG_EVENT): CREATE_THREAD_DEBUG_INFO # proc CreateThread(P1: LPSECURITY_ATTRIBUTES; P2: DWORD; P3: LPTHREAD_START_ROUTINE; # P4: PVOID; P5: DWORD; P6: PDWORD): HANDLE