#include <windows.h> #include <stdio.h> #define ProcessBasicInformation 0 typedef struct { USHORT Length; USHORT MaximumLength; PWSTR Buffer; } UNICODE_STRING, *PUNICODE_STRING; typedef struct { ULONG AllocationSize; ULONG ActualSize; ULONG Flags; ULONG Unknown1; UNICODE_STRING Unknown2; HANDLE InputHandle; HANDLE OutputHandle; HANDLE ErrorHandle; UNICODE_STRING CurrentDirectory; HANDLE CurrentDirectoryHandle; UNICODE_STRING SearchPaths; UNICODE_STRING ApplicationName; UNICODE_STRING CommandLine; PVOID EnvironmentBlock; ULONG Unknown[9]; UNICODE_STRING Unknown3; UNICODE_STRING Unknown4; UNICODE_STRING Unknown5; UNICODE_STRING Unknown6; } PROCESS_PARAMETERS, *PPROCESS_PARAMETERS; typedef struct { ULONG AllocationSize; ULONG Unknown1; HINSTANCE ProcessHinstance; PVOID ListDlls; PPROCESS_PARAMETERS ProcessParameters; ULONG Unknown2; HANDLE Heap; } PEB, *PPEB; typedef struct { DWORD ExitStatus; PPEB PebBaseAddress; DWORD AffinityMask; DWORD BasePriority; ULONG UniqueProcessId; ULONG InheritedFromUniqueProcessId; } PROCESS_BASIC_INFORMATION; // ntdll!NtQueryInformationProcess (NT specific!) // // The function copies the process information of the // specified type into a buffer // // NTSYSAPI // NTSTATUS // NTAPI // NtQueryInformationProcess( // IN HANDLE ProcessHandle, // handle to process // IN PROCESSINFOCLASS InformationClass, // information type // OUT PVOID ProcessInformation, // pointer to buffer // IN ULONG ProcessInformationLength, // buffer size in bytes // OUT PULONG ReturnLength OPTIONAL // pointer to a 32-bit // // variable that receives // // the number of bytes // // written to the buffer // ); typedef LONG (WINAPI *PROCNTQSIP)(HANDLE,UINT,PVOID,ULONG,PULONG); PROCNTQSIP NtQueryInformationProcess; BOOL GetProcessCmdLine(DWORD dwId,LPWSTR wBuf,DWORD dwBufLen); void main(int argc, char* argv[]) { if (argc<2) { printf("Usage: cmdline.exe ProcId "); return; } NtQueryInformationProcess = (PROCNTQSIP)GetProcAddress( GetModuleHandleA("ntdll"), "NtQueryInformationProcess" ); if (!NtQueryInformationProcess) return; DWORD dwId; sscanf(argv[1],"%lu",&dwId); WCHAR wstr[255] = {0}; if (GetProcessCmdLine(dwId,wstr,sizeof(wstr))) wprintf(L"Command line for process %lu is: %s ",dwId,wstr); else wprintf(L"Could not get command line!"); system("pause"); } BOOL GetProcessCmdLine(DWORD dwId,LPWSTR wBuf,DWORD dwBufLen) { LONG status; HANDLE hProcess; PROCESS_BASIC_INFORMATION pbi; PEB Peb; PROCESS_PARAMETERS ProcParam; DWORD dwDummy; DWORD dwSize; LPVOID lpAddress; BOOL bRet = FALSE; // Get process handle hProcess = OpenProcess(PROCESS_QUERY_INFORMATION|PROCESS_VM_READ,FALSE,dwId); if (!hProcess) return FALSE; // Retrieve information status = NtQueryInformationProcess( hProcess, ProcessBasicInformation, (PVOID)&pbi, sizeof(PROCESS_BASIC_INFORMATION), NULL ); if (status) goto cleanup; if (!ReadProcessMemory( hProcess, pbi.PebBaseAddress, &Peb, sizeof(PEB), &dwDummy ) ) goto cleanup; if (!ReadProcessMemory( hProcess, Peb.ProcessParameters, &ProcParam, sizeof(PROCESS_PARAMETERS), &dwDummy ) ) goto cleanup; lpAddress = ProcParam.CommandLine.Buffer; dwSize = ProcParam.CommandLine.Length; if (dwBufLen<dwSize) goto cleanup; if (!ReadProcessMemory( hProcess, lpAddress, wBuf, dwSize, &dwDummy ) ) goto cleanup; bRet = TRUE; cleanup: CloseHandle (hProcess); return bRet; }
原文转自:http://blog.donews.com/zwell/archive/2004/09/30/114988.aspx