2010-03-28 10 views

risposta

60

WMI è il modo più semplice per farlo in C#. La classe Win32_Process ha la proprietà ParentProcessId. Ecco un esempio:

using System; 
using System.Management; // <=== Add Reference required!! 
using System.Diagnostics; 

class Program { 
    public static void Main() { 
     var myId = Process.GetCurrentProcess().Id; 
     var query = string.Format("SELECT ParentProcessId FROM Win32_Process WHERE ProcessId = {0}", myId); 
     var search = new ManagementObjectSearcher("root\\CIMV2", query); 
     var results = search.Get().GetEnumerator(); 
     results.MoveNext(); 
     var queryObj = results.Current; 
     var parentId = (uint)queryObj["ParentProcessId"]; 
     var parent = Process.GetProcessById((int)parentId); 
     Console.WriteLine("I was started by {0}", parent.ProcessName); 
     Console.ReadLine(); 
    } 
} 

uscita quando eseguito da Visual Studio:

sono stato iniziato da devenv

2

Controllare il membro th32ParentProcessID di un'enumerazione CreateToolhelp32Snapshot.

Per un esempio di come eseguire questa operazione see my post here.

Poiché si utilizza C#, è necessario utilizzare DllImports. Nel post collegato ci sono pagine MSDN per ognuna delle funzioni necessarie. Nella parte inferiore di ogni pagina MSDN hanno il codice per DllImport per C#.

C'è anche solo un codice easier way using managed ma non funziona se si hanno più di un nome di processo avviato da diverse applicazioni.

6

Se si ha il controllo dell'applicazione madre, è possibile modificare il genitore per passare il PID al figlio quando avvia il processo.

+0

Semplicità al suo meglio. Questa è la risposta che stavo cercando. – khargoosh

8

Utilizzando la risposta di Brian R. Bondy come una guida, così come quello che è su PInvoke.net, e qualche uscita Reflector, ho prodotto questo, per l'uso in LinqPad MyExtensions:

public static int ParentProcessId(this Process process) 
{ 
    return ParentProcessId(process.Id); 
} 
public static int ParentProcessId(int Id) 
{ 
    PROCESSENTRY32 pe32 = new PROCESSENTRY32{}; 
    pe32.dwSize = (uint)Marshal.SizeOf(typeof(PROCESSENTRY32)); 
    using(var hSnapshot = CreateToolhelp32Snapshot(SnapshotFlags.Process, (uint)Id)) 
    { 
     if(hSnapshot.IsInvalid) 
      throw new Win32Exception(); 

     if(!Process32First(hSnapshot, ref pe32)) 
     { 
      int errno = Marshal.GetLastWin32Error(); 
      if(errno == ERROR_NO_MORE_FILES) 
       return -1; 
      throw new Win32Exception(errno); 
     }  
     do { 
       if(pe32.th32ProcessID == (uint)Id) 
        return (int)pe32.th32ParentProcessID; 
     } while(Process32Next(hSnapshot, ref pe32)); 
    } 
    return -1; 
} 
private const int ERROR_NO_MORE_FILES = 0x12; 
[DllImport("kernel32.dll", SetLastError=true)] 
private static extern SafeSnapshotHandle CreateToolhelp32Snapshot(SnapshotFlags flags, uint id); 
[DllImport("kernel32.dll", SetLastError=true)] 
private static extern bool Process32First(SafeSnapshotHandle hSnapshot, ref PROCESSENTRY32 lppe); 
[DllImport("kernel32.dll", SetLastError=true)] 
private static extern bool Process32Next(SafeSnapshotHandle hSnapshot, ref PROCESSENTRY32 lppe); 

[Flags] 
private enum SnapshotFlags : uint 
{ 
    HeapList = 0x00000001, 
    Process = 0x00000002, 
    Thread = 0x00000004, 
    Module = 0x00000008, 
    Module32 = 0x00000010, 
    All  = (HeapList | Process | Thread | Module), 
    Inherit = 0x80000000, 
    NoHeaps = 0x40000000 
} 
[StructLayout(LayoutKind.Sequential)] 
private struct PROCESSENTRY32 
{ 
    public uint dwSize; 
    public uint cntUsage; 
    public uint th32ProcessID; 
    public IntPtr th32DefaultHeapID; 
    public uint th32ModuleID; 
    public uint cntThreads; 
    public uint th32ParentProcessID; 
    public int pcPriClassBase; 
    public uint dwFlags; 
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst=260)] public string szExeFile; 
}; 
[SuppressUnmanagedCodeSecurity, HostProtection(SecurityAction.LinkDemand, MayLeakOnAbort=true)] 
internal sealed class SafeSnapshotHandle : SafeHandleMinusOneIsInvalid 
{ 
    internal SafeSnapshotHandle() : base(true) 
    { 
    } 

    [SecurityPermission(SecurityAction.LinkDemand, UnmanagedCode=true)] 
    internal SafeSnapshotHandle(IntPtr handle) : base(true) 
    { 
     base.SetHandle(handle); 
    } 

    protected override bool ReleaseHandle() 
    { 
     return CloseHandle(base.handle); 
    } 

    [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success), DllImport("kernel32.dll", CharSet=CharSet.Auto, SetLastError=true, ExactSpelling=true)] 
    private static extern bool CloseHandle(IntPtr handle); 
} 
Problemi correlati