x64内存执行



我已将可执行文件中的内存执行用作test_x86.exe作为文件并正常工作:

/* In memory execution example */
/*
Author: Amit Malik
http://www.securityxploded.com
Compile in Dev C++
*/
#include 
#include 
#include 
#define DEREF_32( name )*(DWORD *)(name)
int main()
{
     char file[20];
     HANDLE handle;
     PVOID vpointer;
     HINSTANCE laddress;
     LPSTR libname;
     DWORD size;
     DWORD EntryAddr;
     int state;
     DWORD byteread;
     PIMAGE_NT_HEADERS nt;
     PIMAGE_SECTION_HEADER section;
     DWORD dwValueA;
     DWORD dwValueB;
     DWORD dwValueC;
     DWORD dwValueD; 
     printf("Enter file name: ");
     scanf("%s",&file);
     // read the file
     printf("Reading file..n");
     handle = CreateFile(file,GENERIC_READ,0,0,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0);
     // get the file size
     size = GetFileSize(handle,NULL);
     // Allocate the space 
     vpointer = VirtualAlloc(NULL,size,MEM_COMMIT,PAGE_READWRITE);
     // read file on the allocated space
     state = ReadFile(handle,vpointer,size,&byteread,NULL);
     CloseHandle(handle);
     printf("You can delete the file now!n");
     system("pause");
     // read NT header of the file
     nt = PIMAGE_NT_HEADERS(PCHAR(vpointer) + PIMAGE_DOS_HEADER(vpointer)->e_lfanew);
     handle = GetCurrentProcess();
     // get VA of entry point
     EntryAddr = nt->OptionalHeader.ImageBase + nt->OptionalHeader.AddressOfEntryPoint;
     // Allocate the space with Imagebase as a desired address allocation request
     PVOID memalloc = VirtualAllocEx(
                                     handle, 
                                     PVOID(nt->OptionalHeader.ImageBase), 
                                     nt->OptionalHeader.SizeOfImage, 
                                     MEM_RESERVE | MEM_COMMIT, 
                                     PAGE_EXECUTE_READWRITE
                                     );
     // Write headers on the allocated space
     WriteProcessMemory(handle, 
     memalloc, 
     vpointer, 
     nt->OptionalHeader.SizeOfHeaders, 
     0
     );
     // write sections on the allocated space
     section = IMAGE_FIRST_SECTION(nt);
     for (ULONG i = 0; i < nt->FileHeader.NumberOfSections; i++) 
     {
         WriteProcessMemory(
                           handle, 
                           PCHAR(memalloc) + section[i].VirtualAddress, 
                           PCHAR(vpointer) + section[i].PointerToRawData, 
                           section[i].SizeOfRawData, 
                           0
                           );
     }
     // read import dirctory    
     dwValueB = (DWORD) &(nt->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT]);
     // get the VA 
     dwValueC = (DWORD)(nt->OptionalHeader.ImageBase) + 
                          ((PIMAGE_DATA_DIRECTORY)dwValueB)->VirtualAddress;

     while(((PIMAGE_IMPORT_DESCRIPTOR)dwValueC)->Name)
     {
            // get DLL name
            libname = (LPSTR)(nt->OptionalHeader.ImageBase + 
                              ((PIMAGE_IMPORT_DESCRIPTOR)dwValueC)->Name);
            // Load dll
            laddress = LoadLibrary(libname);
            // get first thunk, it will become our IAT
            dwValueA = nt->OptionalHeader.ImageBase + 
                                  ((PIMAGE_IMPORT_DESCRIPTOR)dwValueC)->FirstThunk;
            // resolve function addresses
            while(DEREF_32(dwValueA))
            {
                dwValueD = nt->OptionalHeader.ImageBase + DEREF_32(dwValueA);
                // get function name 
                LPSTR Fname = (LPSTR)((PIMAGE_IMPORT_BY_NAME)dwValueD)->Name;
                // get function addresses
                DEREF_32(dwValueA) = (DWORD)GetProcAddress(laddress,Fname);
                dwValueA += 4;
            }
            dwValueC += sizeof( IMAGE_IMPORT_DESCRIPTOR );
     }
     // call the entry point :: here we assume that everything is ok.
     ((void(*)(void))EntryAddr)();
}    

但是,当我将此代码用作test_x64.exe的Release-x64作为文件时,我会在此行中违反访问:

// get the VA    
dwValueC = (DWORD)(nt->OptionalHeader.ImageBase) + ((PIMAGE_DATA_DIRECTORY)dwValueB)->VirtualAddress;

我不知道为什么。

可能是x64指针而不是dword size:

DWORD dwValueB;
...
dwValueB = (DWORD) &(nt->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT]);

在我的minwindef.h中,我有:

typedef unsigned long       DWORD;

sizeof(DWORD)给我4,但是sizeof(void*)给出8。

最新更新