Search code examples
windowswinapiwindows-xpwindows-2000nt-native-api

How to open a process by name with NtOpenProcess


MSDN states that on older versions of Windows, NtOpenProcess supports opening a process by name but fails to document that actual syntax of the name string.

In Windows Server 2003, Windows XP, and Windows 2000, the caller has the option of supplying either a client ID or an object name (but not both). If the ObjectName field of the structure pointed to by ObjectAttributes contains a non-NULL pointer to an object name, ClientId must be NULL.

I've tried various versions of %d, %#x and %x, what is the correct syntax for the object name?

HANDLE handle = 0;
WCHAR b[99];
wsprintfW(b, L"Process\\%x", GetCurrentProcessId()); // What is the syntax supposed to be? "Process" is the name of the process object type but I'm not sure if it's required here.
UNICODE_STRING name;
RtlInitUnicodeString(&name, b);
OBJECT_ATTRIBUTES oa;
InitializeObjectAttributes(&oa, &name, 0, NULL, NULL);
NTSTATUS status = NtOpenProcess(&handle, SYNCHRONIZE, &oa, NULL);
_tprintf(_T("%X %p\n"), status, handle);

(I realize this question is outdated by about 20 years but I'm just curious)


Solution

  • With help from RbMm in the comments I was able to get it to work but since you are limited to processes named on purpose and the functions to do that are undocumented the whole feature is rather useless.

    if (LOBYTE(GetVersion()) != 5) return -1;
    UNICODE_STRING name;
    OBJECT_ATTRIBUTES oa;
    RtlInitUnicodeString(&name, L"\\BaseNamedObjects\\HelloWorld");
    NTSTATUS status;
    HANDLE handle = 0;
    InitializeObjectAttributes(&oa, &name, 0, NULL, NULL);
    status = NtCreateProcessEx(&handle, STANDARD_RIGHTS_REQUIRED|SYNCHRONIZE|0x0FFF, &oa, GetCurrentProcess(), 0, NULL, NULL, NULL, 0);
    _tprintf(_T("create %X %p pid=%d\n"), status, handle, status ? 0 : GetProcessId(handle));
    if (status) return status;
        
    status = NtOpenProcess(&handle, SYNCHRONIZE|PROCESS_QUERY_INFORMATION|PROCESS_TERMINATE, &oa, NULL);
    _tprintf(_T("open %X %p pid=%d\n"), status, handle, status ? 0 : GetProcessId(handle));
    if (status) return status;
    Sleep(1000*60);
    TerminateProcess(handle, 0); // Kill zombie child
    

    named process on XP