VirtualAllocEx failing with ERROR_ACCESS_DENIED code

195 Views Asked by At

My program (LibInjector) tries to allocate memory in another process (Recipient) and fails, GetLastError() returns 5(ERROR_ACCESS_DENIED). Usually it works (for recipients such as my other program or notepad.exe), and I don't know why VirtualAllocEx doesn't work in this particular case.

#include <stdio.h>
#include <stdlib.h>
#include <Windows.h>
int main(int argc, char* argv[])
{

    if (argc != 3)
    {
        printf("Usage: LibInjector [receiver process ID] [dll name]!\n");
        return 1;
    }
    int iProcessId = atoi(argv[1]);
    if (!iProcessId)
    {
        printf("Failed to parse process ID! Current process ID will be used.\n");
        iProcessId = GetCurrentProcessId();
    }
    const char* psDllName = argv[2];
    printf("Receiver process id: %d\n", iProcessId);
    //PROCESS_CREATE_THREAD | PROCESS_VM_OPERATION | PROCESS_VM_WRITE | PROCESS_VM_READ | PROCESS_QUERY_INFORMATION
    HANDLE hTargetProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, iProcessId);
    if (hTargetProcess == NULL)
    {
        printf("OpenProcess failed with code %d !\n", GetLastError());
        return 2;
    }
    SIZE_T stDllNameLen = strlen(psDllName);
    LPVOID lpDllNameAddress = VirtualAllocEx(hTargetProcess, NULL, stDllNameLen + 1, MEM_COMMIT, PAGE_READWRITE);
    if (lpDllNameAddress == NULL)
    {
        printf("VirtualAllocEx failed with code %d !\n", GetLastError());
        return 3;
    }
        //unreachable
}
  • The platforms of both processes (LibInjector and Recipient) are 32 bit;
  • Both processes running by the same user;
  • Both processes has elevated privileges;
  • Process explorer (running elevated) shows an empty Protection field for recipient;
  • Recipient's exe file had digital signature, I set VirtualAddress and Size of Security Directory in Optional PE Header to 0. Now there is no Digital Signature tab in Recipient's exe file properties, but VirtualAllocEx still throws the same ERROR_ACCESS_DENIED.

UPD:

  • RtlGetLastNtStatus also returns 0xC0000022, which means {Access Denied} A process has requested access to an object but has not been granted those access rights.
  • calling GetSecurityInfo(hTargetProcess, SE_KERNEL_OBJECT, DACL_SECURITY_INFORMATION | SACL_SECURITY_INFORMATION, NULL, NULL, &dacl, &sacl, &pSecDesc); returns 5
0

There are 0 best solutions below