|
| WIN32 API, help to capture env variables of another running proces |
 |
Thu, 20 Mar 2008 19:30:00 -070 |
I need some help with capturing the environemnt variables from a current
running process. My process has no relationship to the process id to be
query. The code below gets me to the process memory, and I can get the
command line that the original process was launched with but I am completely
lost on how to go after the environment variables. Nothing special here, no
.net, platform is Windows XP SP2, the original application is a traditional
win32 api application that is started with a batch file and has a command
(console) window. Using VS2003 IDE, not 2005 yet. At GM we are usually 3 to
5 years behind the current OS/Software releases. Any help is alway
appreciated!
Regards.
typedef long NTSTATUS;
#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
typedef enum _PROCESSINFOCLASS PROCESSINFOCLASS;
typedef struct _INFOBLOCK
{
unsigned long dwFiller[16];
unsigned short wLength;
unsigned short wMaxLength;
const unsigned short *dwCmdLineAddress;
const unsigned short *env;
} INFOBLOCK, *PINFOBLOCK;
typedef struct _PEB
{
unsigned long dwFiller[4];
PINFOBLOCK dwInfoBlockAddress;
} PEB, *PPEB;
typedef struct _PROCESS_BASIC_INFORMATION
{
NTSTATUS ExitStatus;
PPEB PebBaseAddress;
unsigned long AffinityMask;
long BasePriority;
unsigned long UniqueProcessId;
unsigned long InheritedFromUniqueProcessId;
} PBI;
typedef NTSTATUS (NTAPI *ZWQueryInformationProcessW)(HANDLE,
PROCESSINFOCLASS, PVOID, ULONG, PULONG);
void Get(HANDLE hProcess)
{
ZWQueryInformationProcessW ZwQueryInformationProcessA;
HMODULE hModule = GetModuleHandle(_T("ntdll"));
ZwQueryInformationProcessA =
(ZWQueryInformationProcessW)GetProcAddress(hModule,
"ZwQueryInformationProcess");
if (ZwQueryInformationProcessA == NULL) exit(1);
PBI ProcInfo;
PEB ProcPEB;
INFOBLOCK ProcBlock;
unsigned long ReturnLength;
//HANDLE hProcess;
unsigned short *pszCmdLine = NULL;
int bSuccess;
//hProcess = GetCurrentProcess();
//hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ,
FALSE, 2780);
if (! NT_SUCCESS(ZwQueryInformationProcessA(hProcess,
ProcessBasicInformation, &ProcInfo, sizeof(ProcInfo), &ReturnLength)))
exit(1);
bSuccess = ReadProcessMemory(hProcess, (const void
*)ProcInfo.PebBaseAddress, &ProcPEB, sizeof(ProcPEB), &ReturnLength);
if (bSuccess != false)
{
bSuccess = ReadProcessMemory(hProcess, (const void
*)ProcPEB.dwInfoBlockAddress, &ProcBlock, sizeof(ProcBlock),
&ReturnLength);
pszCmdLine = (unsigned short *) new BYTE[ProcBlock.wMaxLength];
}
if (bSuccess != false)
{
bSuccess = ReadProcessMemory(hProcess, ProcBlock.dwCmdLineAddress,
pszCmdLine, ProcBlock.wMaxLength, &ReturnLength);
}
_tprintf(TEXT("%S\n"),pszCmdLine);
if (NULL != pszCmdLine) delete [] pszCmdLine;
// CloseHandle(hProcess);
return;
}
int main()
{
// Get the list of process identifiers.
unsigned long processID[1024];
unsigned long size;
unsigned long n_processID;
char szProcessName[MAX_PATH] = TEXT("<unknown>");
HANDLE hProcess;
HMODULE hModule;
std::vector<std::pair<unsigned long, std::string> > processes;
if (! EnumProcesses(processID, sizeof(processID), &size)) return -1;
// Calculate how many process identifiers were returned.
n_processID = size / sizeof(unsigned long);
// Print the name and process identifier for each process.
for (unsigned ii = 0; ii < n_processID; ++ii)
{
if (processID[ii] == 0) continue;
// Get a handle to the process.
hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, false,
processID[ii]);
// Get the process name.
if (hProcess == NULL) continue;
if (EnumProcessModules(hProcess, &hModule, sizeof(hModule), &size))
{
GetModuleBaseName(hProcess, hModule, szProcessName,
sizeof(szProcessName)/sizeof(char));
processes.push_back(std::make_pair(processID[ii], szProcessName));
}
if (! stricmp(szProcessName, "cmd.exe"))
{
Get(hProcess);
std::cout << "Found PID: " << processID[ii] <<
std::endl;
}
//_tprintf(TEXT("%s (PID: %u)\n"), szProcessName, processID[ii]);
CloseHandle(hProcess);
}
std::sort(processes.begin(), processes.end());
return 0;
|
| Post Reply
|
| Re: WIN32 API, help to capture env variables of another running proces |
 |
Sat, 22 Mar 2008 14:20:01 -070 |
There is no documented way to access that piece of information
across processes.
The undocumented way begins with
RTL_USER_PROCESS_PARAMETERS::Environment
--
--
This posting is provided "AS IS" with no warranties, and confers no
rights.
Use of any included script samples are subject to the terms specified at
http://www.microsoft.com/info/cpyright.htm
"Shawn" <Shawn@discussions.microsoft.com> wrote in message
news:93372DF0-9734-4DB3-A23A-E0CE63A87519@microsoft.com...
>I need some help with capturing the environemnt variables from a current
> running process. My process has no relationship to the process id to be
> query. The code below gets me to the process memory, and I can get the
> command line that the original process was launched with but I am
> completely
> lost on how to go after the environment variables. Nothing special here,
> no
> .net, platform is Windows XP SP2, the original application is a
> traditional
> win32 api application that is started with a batch file and has a command
> (console) window. Using VS2003 IDE, not 2005 yet. At GM we are usually 3
> to
> 5 years behind the current OS/Software releases. Any help is alway
> appreciated!
>
> Regards.
>
>
> typedef long NTSTATUS;
>
> #define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
>
> typedef enum _PROCESSINFOCLASS
> PROCESSINFOCLASS;
>
> typedef struct _INFOBLOCK
> {
> unsigned long dwFiller[16];
> unsigned short wLength;
> unsigned short wMaxLength;
> const unsigned short *dwCmdLineAddress;
> const unsigned short *env;
> } INFOBLOCK, *PINFOBLOCK;
>
> typedef struct _PEB
> {
> unsigned long dwFiller[4];
> PINFOBLOCK dwInfoBlockAddress;
> } PEB, *PPEB;
>
> typedef struct _PROCESS_BASIC_INFORMATION
> {
> NTSTATUS ExitStatus;
> PPEB PebBaseAddress;
> unsigned long AffinityMask;
> long BasePriority;
> unsigned long UniqueProcessId;
> unsigned long InheritedFromUniqueProcessId;
> } PBI;
>
> typedef NTSTATUS (NTAPI *ZWQueryInformationProcessW)(HANDLE,
> PROCESSINFOCLASS, PVOID, ULONG, PULONG);
>
>
> void Get(HANDLE hProcess)
> {
> ZWQueryInformationProcessW ZwQueryInformationProcessA;
>
> HMODULE hModule = GetModuleHandle(_T("ntdll"));
>
> ZwQueryInformationProcessA =
> (ZWQueryInformationProcessW)GetProcAddress(hModule,
> "ZwQueryInformationProcess");
>
> if (ZwQueryInformationProcessA == NULL) exit(1);
>
> PBI ProcInfo;
> PEB ProcPEB;
> INFOBLOCK ProcBlock;
> unsigned long ReturnLength;
> //HANDLE hProcess;
> unsigned short *pszCmdLine = NULL;
> int bSuccess;
>
> //hProcess = GetCurrentProcess();
> //hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ,
> FALSE, 2780);
>
> if (! NT_SUCCESS(ZwQueryInformationProcessA(hProcess,
> ProcessBasicInformation, &ProcInfo, sizeof(ProcInfo),
&ReturnLength)))
> exit(1);
>
> bSuccess = ReadProcessMemory(hProcess, (const void
> *)ProcInfo.PebBaseAddress, &ProcPEB, sizeof(ProcPEB),
&ReturnLength);
>
> if (bSuccess != false)
> {
> bSuccess = ReadProcessMemory(hProcess, (const void
> *)ProcPEB.dwInfoBlockAddress, &ProcBlock, sizeof(ProcBlock),
> &ReturnLength);
>
> pszCmdLine = (unsigned short *) new BYTE[ProcBlock.wMaxLength];
> }
>
> if (bSuccess != false)
> {
> bSuccess = ReadProcessMemory(hProcess, ProcBlock.dwCmdLineAddress,
> pszCmdLine, ProcBlock.wMaxLength, &ReturnLength);
> }
>
> _tprintf(TEXT("%S\n"),pszCmdLine);
>
> if (NULL != pszCmdLine) delete [] pszCmdLine;
>
> // CloseHandle(hProcess);
>
> return;
> }
>
>
> int main()
> {
> // Get the list of process identifiers.
> unsigned long processID[1024];
> unsigned long size;
> unsigned long n_processID;
> char szProcessName[MAX_PATH] = TEXT("<unknown>");
> HANDLE hProcess;
> HMODULE hModule;
> std::vector<std::pair<unsigned long, std::string> > processes;
>
> if (! EnumProcesses(processID, sizeof(processID), &size)) return -1;
>
> // Calculate how many process identifiers were returned.
> n_processID = size / sizeof(unsigned long);
>
> // Print the name and process identifier for each process.
> for (unsigned ii = 0; ii < n_processID; ++ii)
> {
> if (processID[ii] == 0) continue;
>
> // Get a handle to the process.
> hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, false,
> processID[ii]);
>
> // Get the process name.
> if (hProcess == NULL) continue;
>
> if (EnumProcessModules(hProcess, &hModule, sizeof(hModule),
&size))
> {
> GetModuleBaseName(hProcess, hModule, szProcessName,
> sizeof(szProcessName)/sizeof(char));
>
> processes.push_back(std::make_pair(processID[ii], szProcessName));
> }
>
> if (! stricmp(szProcessName, "cmd.exe"))
> {
> Get(hProcess);
>
> std::cout << "Found PID: " << processID[ii] <<
std::endl;
> }
>
> //_tprintf(TEXT("%s (PID: %u)\n"), szProcessName,
processID[ii]);
>
> CloseHandle(hProcess);
> }
>
> std::sort(processes.begin(), processes.end());
>
> return 0;
> }
|
| Post Reply
|
| Re: WIN32 API, help to capture env variables of another running pr |
 |
Sat, 22 Mar 2008 15:52:00 -070 |
Thank you for you reply.
I did receive a solution from another forum, similar to what my included
code does, but it does exactly what I was looking for. It captures ALL the
environment variables of a running process ID. It is a perfect solution for
my issue. And it is documented, using GetProcAddress and ReadProcessMemory,
and mining the Process Environment Block of memory.
"Ivan Brugiolo [MSFT]" wrote:
> There is no documented way to access that piece of information
> across processes.
>
> The undocumented way begins with
> RTL_USER_PROCESS_PARAMETERS::Environment
>
>
> --
>
> --
> This posting is provided "AS IS" with no warranties, and confers
no rights.
> Use of any included script samples are subject to the terms specified at
> http://www.microsoft.com/info/cpyright.htm
>
>
> "Shawn" <Shawn@discussions.microsoft.com> wrote in message
> news:93372DF0-9734-4DB3-A23A-E0CE63A87519@microsoft.com...
> >I need some help with capturing the environemnt variables from a
current
> > running process. My process has no relationship to the process id to
be
> > query. The code below gets me to the process memory, and I can get
the
> > command line that the original process was launched with but I am
> > completely
> > lost on how to go after the environment variables. Nothing special
here,
> > no
> > .net, platform is Windows XP SP2, the original application is a
> > traditional
> > win32 api application that is started with a batch file and has a
command
> > (console) window. Using VS2003 IDE, not 2005 yet. At GM we are
usually 3
> > to
> > 5 years behind the current OS/Software releases. Any help is alway
> > appreciated!
> >
> > Regards.
> >
> >
> > typedef long NTSTATUS;
> >
> > #define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
> >
> > typedef enum _PROCESSINFOCLASS
> > PROCESSINFOCLASS;
> >
> > typedef struct _INFOBLOCK
> > {
> > unsigned long dwFiller[16];
> > unsigned short wLength;
> > unsigned short wMaxLength;
> > const unsigned short *dwCmdLineAddress;
> > const unsigned short *env;
> > } INFOBLOCK, *PINFOBLOCK;
> >
> > typedef struct _PEB
> > {
> > unsigned long dwFiller[4];
> > PINFOBLOCK dwInfoBlockAddress;
> > } PEB, *PPEB;
> >
> > typedef struct _PROCESS_BASIC_INFORMATION
> > {
> > NTSTATUS ExitStatus;
> > PPEB PebBaseAddress;
> > unsigned long AffinityMask;
> > long BasePriority;
> > unsigned long UniqueProcessId;
> > unsigned long InheritedFromUniqueProcessId;
> > } PBI;
> >
> > typedef NTSTATUS (NTAPI *ZWQueryInformationProcessW)(HANDLE,
> > PROCESSINFOCLASS, PVOID, ULONG, PULONG);
> >
> >
> > void Get(HANDLE hProcess)
> > {
> > ZWQueryInformationProcessW ZwQueryInformationProcessA;
> >
> > HMODULE hModule = GetModuleHandle(_T("ntdll"));
> >
> > ZwQueryInformationProcessA =
> > (ZWQueryInformationProcessW)GetProcAddress(hModule,
> > "ZwQueryInformationProcess");
> >
> > if (ZwQueryInformationProcessA == NULL) exit(1);
> >
> > PBI ProcInfo;
> > PEB ProcPEB;
> > INFOBLOCK ProcBlock;
> > unsigned long ReturnLength;
> > //HANDLE hProcess;
> > unsigned short *pszCmdLine = NULL;
> > int bSuccess;
> >
> > //hProcess = GetCurrentProcess();
> > //hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ,
> > FALSE, 2780);
> >
> > if (! NT_SUCCESS(ZwQueryInformationProcessA(hProcess,
> > ProcessBasicInformation, &ProcInfo, sizeof(ProcInfo),
&ReturnLength)))
> > exit(1);
> >
> > bSuccess = ReadProcessMemory(hProcess, (const void
> > *)ProcInfo.PebBaseAddress, &ProcPEB, sizeof(ProcPEB),
&ReturnLength);
> >
> > if (bSuccess != false)
> > {
> > bSuccess = ReadProcessMemory(hProcess, (const void
> > *)ProcPEB.dwInfoBlockAddress, &ProcBlock, sizeof(ProcBlock),
> > &ReturnLength);
> >
> > pszCmdLine = (unsigned short *) new BYTE[ProcBlock.wMaxLength];
> > }
> >
> > if (bSuccess != false)
> > {
> > bSuccess = ReadProcessMemory(hProcess, ProcBlock.dwCmdLineAddress,
> > pszCmdLine, ProcBlock.wMaxLength, &ReturnLength);
> > }
> >
> > _tprintf(TEXT("%S\n"),pszCmdLine);
> >
> > if (NULL != pszCmdLine) delete [] pszCmdLine;
> >
> > // CloseHandle(hProcess);
> >
> > return;
> > }
> >
> >
> > int main()
> > {
> > // Get the list of process identifiers.
> > unsigned long processID[1024];
> > unsigned long size;
> > unsigned long n_processID;
> > char szProcessName[MAX_PATH] = TEXT("<unknown>");
> > HANDLE hProcess;
> > HMODULE hModule;
> > std::vector<std::pair<unsigned long, std::string> >
processes;
> >
> > if (! EnumProcesses(processID, sizeof(processID), &size)) return
-1;
> >
> > // Calculate how many process identifiers were returned.
> > n_processID = size / sizeof(unsigned long);
> >
> > // Print the name and process identifier for each process.
> > for (unsigned ii = 0; ii < n_processID; ++ii)
> > {
> > if (processID[ii] == 0) continue;
> >
> > // Get a handle to the process.
> > hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ,
false,
> > processID[ii]);
> >
> > // Get the process name.
> > if (hProcess == NULL) continue;
> >
> > if (EnumProcessModules(hProcess, &hModule, sizeof(hModule),
&size))
> > {
> > GetModuleBaseName(hProcess, hModule, szProcessName,
> > sizeof(szProcessName)/sizeof(char));
> >
> > processes.push_back(std::make_pair(processID[ii], szProcessName));
> > }
> >
> > if (! stricmp(szProcessName, "cmd.exe"))
> > {
> > Get(hProcess);
> >
> > std::cout << "Found PID: " << processID[ii]
<< std::endl;
> > }
> >
> > //_tprintf(TEXT("%s (PID: %u)\n"), szProcessName,
processID[ii]);
> >
> > CloseHandle(hProcess);
> > }
> >
> > std::sort(processes.begin(), processes.end());
> >
> > return 0;
> > }
>
>
|
| Post Reply
|
|
|