CYFROWY BARON • PROGRAMOWANIE • Zobacz wątek - GetParentProcess

GetParentProcess

dział ogólny

GetParentProcess

Nowy postprzez mckri » czwartek, 29 grudnia 2011, 22:21

Witam.
Czy znacie sposób na pobranie informacji o tym jaki proces (rodzic) uruchomił bieżący proces (własny program)?
Np. Na pulpicie mam program Project1.exe, uruchamiam go, rodzicem procesu jest explorer.exe. W innym przypadku, gdy uruchamiana jest usługa, rodzicem jest wininit.exe->services.exe.
Bardzo dobrze widać powiązanie między procesami w programie Process Explorer firmy Sysinternals (teraz M$) http://technet.microsoft.com/pl-pl/sysinternals/bb896653
Czy informację o procesie-rodzicu można uzyskać dla własnego programu?
Avatar użytkownika
mckri
Intelektryk
Intelektryk
 
Posty: 160
Dołączył(a): piątek, 15 sierpnia 2008, 13:48
Podziękował : 10
Otrzymał podziękowań: 2
System operacyjny: Windows Vista SP2
Kompilator: BCB 5/2007/2009
    Windows VistaInternet Explorer 9

Re: GetParentProcess

Nowy postprzez Cyfrowy Baron » piątek, 30 grudnia 2011, 09:44

Zapewne zapoznałeś się z poradą: ► patrz serwis: Cyfrowy Baron dział: porady -> api -> zamykanie procesów Znajduje się tam przykład takiej funkcji:

KOD cpp:     UKRYJ  
#include <tlhelp32.h>
void __fastcall GetProcess(TStrings *ProcList)
{
 HWND Snap;
 PROCESSENTRY32 proces;

 Snap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
 proces.dwSize = sizeof(PROCESSENTRY32);

 if(Process32First(Snap, &proces))
 {
  do
  {
   if(proces.szExeFile[0] != '[')
   {
    ProcList->Add((String)proces.szExeFile + "=" + (String)proces.th32ProcessID);
   }
  }
  while(Process32Next(Snap , &proces));
 }
 CloseHandle(Snap);
}


Jak widzisz jest tutaj struktura PROCESSENTRY32, która posiada element th32ParentProcessID. W tym przykładowym kodzie tego elementu nie ma, ale możesz go sobie dodać. W pliku pomocy można przeczytać, że: th32ParentProcessID - Process identifier of the process that created this process (its parent process). Modyfikując kod:

KOD cpp:     UKRYJ  
   if(proces.szExeFile[0] != '[')
   {
    ProcList->Add( (String)proces.th32ParentProcessID );
   }


Otrzymasz identyfikator rodzica procesu. Znając ID możesz sobie sprawdzić co to za program o ile ten program wciąż jest uruchomiony.
Avatar użytkownika
Cyfrowy Baron
Administrator
Administrator
 
Posty: 4716
Dołączył(a): niedziela, 13 lipca 2008, 15:17
Podziękował : 12
Otrzymał podziękowań: 442
System operacyjny: Windows 7 x64 SP1
Kompilator: Embarcadero RAD Studio XE2
C++ Builder XE2 Update 4
SKYPE: cyfbar
Gadu Gadu: 0
    Windows XPFirefox

Re: GetParentProcess

Nowy postprzez Cyfrowy Baron » piątek, 30 grudnia 2011, 12:20

Tak naprędce skleciłem taki oto kod:

KOD cpp:     UKRYJ  
#include <tlhelp32.h>
#include <stdio.h>

void ShowError( TCHAR* msg )
{
  DWORD eNum;
  TCHAR sysMsg[256];
  TCHAR* p;

  eNum = GetLastError( );
  FormatMessage( FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, eNum, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), sysMsg, 256, NULL );

  p = sysMsg;
  while( ( *p > 31 ) || ( *p == 9 ) )
    ++p;
  do { *p-- = 0; } while( ( p >= sysMsg ) && ( ( *p == '.' ) || ( *p < 33 ) ) );

  TCHAR ShowMsg[UNICODE_STRING_MAX_CHARS];

  swprintf(ShowMsg, L"UWAGA: %s wywołał błąd %d (%s)", msg, eNum, sysMsg );

  ShowMessage( (String)ShowMsg );
}
//---------------------------------------------------------------------------
/* Funkcja wylicza moduły połączone z procesem */
BOOL ListProcessModules( DWORD dwPID, TStrings *Lista)
{
  HANDLE hModuleSnap = INVALID_HANDLE_VALUE;
  MODULEENTRY32 me32;

  hModuleSnap = CreateToolhelp32Snapshot( TH32CS_SNAPMODULE, dwPID );
  if( hModuleSnap == INVALID_HANDLE_VALUE )
  {
         ShowError( L"CreateToolhelp32Snapshot (modułów)" );
         return( FALSE );
  }

  me32.dwSize = sizeof( MODULEENTRY32 );

  if( !Module32First( hModuleSnap, &me32 ) )
  {
        ShowError( L"Module32First" );
        CloseHandle( hModuleSnap );
        return( FALSE );
  }

  do
  {
        Lista->Add( "NAZWA MODUŁU: " + (String)me32.szModule );
        Lista->Add( "Nazwa pliku procesu     = " + (String)me32.szExePath );
        Lista->Add( "PID procesu     = " + (String)me32.th32ProcessID );
        Lista->Add( "ref count (g)  =     " + (String)me32.GlblcntUsage );
        Lista->Add( "ref count (p)  =     " + (String)me32.ProccntUsage );
        Lista->Add( "base address   = " + (String)(DWORD)me32.modBaseAddr );
        Lista->Add( "base size      = " + (String)me32.modBaseSize );

  } while( Module32Next( hModuleSnap, &me32 ) );

  CloseHandle( hModuleSnap );
  return( TRUE );
}
//---------------------------------------------------------------------------
/* Funkcja szukająca rodzica procesu */
BOOL FindParentProces( DWORD dwOwnerPID, TStrings *Lista)
{
  HANDLE hSnap = INVALID_HANDLE_VALUE;
  PROCESSENTRY32 pe32;

  hSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );
  if( hSnap == INVALID_HANDLE_VALUE )
    return( FALSE );

  pe32.dwSize = sizeof( PROCESSENTRY32 );

  if( !Process32First( hSnap, &pe32 ) )
  {
        ShowError( L"Process32First" );
        CloseHandle( hSnap );
    return( FALSE );
  }

  do
  {
        if( pe32.th32ProcessID == dwOwnerPID )
        {
         HANDLE hWnd = OpenProcess(PROCESS_ALL_ACCESS, true, pe32.th32ProcessID);
         if(hWnd)
         {
          Lista->Add( "Parent: " + (String)pe32.szExeFile );
         }
    }
  } while( Process32Next(hSnap, &pe32 ) );

  CloseHandle( hSnap );
  return( TRUE );
}
//---------------------------------------------------------------------------
void __fastcall GetParentProces(String ProcesName, TStrings *Lista)
{
 PROCESSENTRY32 proces;

 HANDLE Snap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
 proces.dwSize = sizeof(PROCESSENTRY32);

 if(Process32First(Snap, &proces))
 {
  do
  {
   if(proces.szExeFile[0] != '[')
   {
        if(SameText((String)proces.szExeFile, ProcesName))
        {
         HANDLE hWnd = OpenProcess(PROCESS_ALL_ACCESS, true, proces.th32ProcessID);
         if(hWnd)
         {
          DWORD pID = proces.th32ProcessID;
          Lista->Add(" *** MODUŁY PROCESU ***");
          ListProcessModules( pID, Lista );
          pID = proces.th32ParentProcessID;
          Lista->Add("---------------");
          Lista->Add(" *** PARENT ***");
          FindParentProces( pID, Lista );
          Lista->Add( "Parent PID: " + (String)pID );
         }
         else return;
         CloseHandle(hWnd);
         return;
        }
   }
  }
  while(Process32Next(Snap , &proces));
 }
 CloseHandle(Snap);
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
 GetParentProces("notepad.exe", ListBox1->Items);
}


Kod działa, ale nie jest optymalnie napisany. Robi więcej niż chciałeś, gdyż wyświetla również wszystkie moduły z których korzysta proces. Możesz więc go bez problemu dostosować do własnych potrzeb.
Kod został opracowany dla środowiska Embarcadero C++ Builder 2010 i operuje na zmiennych UnicodeString i wchar_t, przy mapowaniu ustawionym na wchar_t. Jeżeli korzystasz ze zmiennych AnsiString i char to musisz je odpowiednio zmodyfikować.

Za ten post autor Cyfrowy Baron otrzymał podziękowanie od:
mckri
Avatar użytkownika
Cyfrowy Baron
Administrator
Administrator
 
Posty: 4716
Dołączył(a): niedziela, 13 lipca 2008, 15:17
Podziękował : 12
Otrzymał podziękowań: 442
System operacyjny: Windows 7 x64 SP1
Kompilator: Embarcadero RAD Studio XE2
C++ Builder XE2 Update 4
SKYPE: cyfbar
Gadu Gadu: 0
    Windows XPFirefox

Re: GetParentProcess

Nowy postprzez mckri » niedziela, 1 stycznia 2012, 21:14

Dzięki. Teraz nie mogę, ale wypróbuję wkrótce
Avatar użytkownika
mckri
Intelektryk
Intelektryk
 
Posty: 160
Dołączył(a): piątek, 15 sierpnia 2008, 13:48
Podziękował : 10
Otrzymał podziękowań: 2
System operacyjny: Windows Vista SP2
Kompilator: BCB 5/2007/2009
    Windows VistaOpera


Powrót do Ogólne problemy z programowaniem

Kto przegląda forum

Użytkownicy przeglądający ten dział: Brak zalogowanych użytkowników i 4 gości