【问题标题】:Identify process/exe which was passed specific command line arguments识别传递特定命令行参数的进程/exe
【发布时间】:2014-06-11 06:01:05
【问题描述】:

有两个基于命令行参数执行任务的exe/程序,我们称之为Profile。用户可以使用特定配置文件运行这些 exe 的多个实例。

我们遇到了这样一种情况,如果一个 exe 使用配置文件运行,另一个不应使用相同的配置文件运行,或者一个 exe 不能使用相同的配置文件实例化两次。为此,我们需要识别具有相同配置文件的正在运行的进程。

一种可能性是记录,但如果进程/exe 终止,它可能会失败。

编辑

我需要通过向他/她显示进程的窗口/表单标题来通知用户。由于我的 exes 是基于表单的,所以每个进程都会根据配置文件有自己的标题。基于 WMI 的解决方案,在下面作为我的答案发布,只能找到带有文件名的进程,WMI 没有任何列出窗口/表单标题的功能,所以我决定使用 Win32 API。

我使用了Code sample from this post,因为我只有 PID,但没有句柄。代码示例不返回任何标题。我检查了以下步骤

  1. 在传递来自 WMI 的 ProcessID 时未返回任何标题。
  2. ParentProcessID 时返回正确的父 exe 标题 来自 WMI 已通过。
  3. 当 form.hwnd 被返回时,子 exe 的正确标题被返回 从另一个 exe 传递。

看起来代码示例不适用于子 exe(我的 exe 是从另一个 exe 调用的,即我的 exe 是孩子,而调用者是父母)。 EnumCallBack 找到的句柄不等于表单的 hWnd,这就是它不返回标题的原因。

【问题讨论】:

    标签: shell process vb6 hwnd window-handles


    【解决方案1】:

    感谢 MC ND 确定要使用的 WMI 和 Evripidis

    这是获取所有进程的命令行参数的示例代码

        Dim objWMIService, objProcess, colProcess
        Dim strComputer, strList
    
        strComputer = "."
    
        Set objWMIService = GetObject("winmgmts:" & _
              "{impersonationLevel=impersonate}!\\" & _
               strComputer & "\root\cimv2")
    
        Set colProcess = objWMIService.ExecQuery("Select * from Win32_Process")
    
        For Each objProcess In colProcess
            Debug.Print objProcess.Name & " | " & objProcess.CommandLine
        Next
    

    获取已在命令行参数中传递ABCD 的进程的查询将是

    Set colProcess = objWMIService.ExecQuery("Select * from Win32_Process " & _
                                             " Where CommandLine Like ""%ABCD%"" ")
    

    阅读更多

    编辑:

    为了从 ProcessID 获取窗口/表单标题,我使用了 Evripidis 的以下文章中的源代码

    Get window handlle (hWnd) from process ID

    这里是中心思想

    1. 存储与 PID 相关的所有句柄
    2. 获取可见顶级窗口句柄的文本 在任务栏上

    【讨论】:

      【解决方案2】:

      询问 WMI

      wmic process get name,commandline
      

      【讨论】:

      • @bjan,tasklist /v 是否为您的子进程返回窗口标题?
      【解决方案3】:

      通常单实例程序会创建互斥体。如果可以,则没有其他实例正在运行。如果不能,则切换到前一个实例的窗口,然后退出。

      在 vb6 中,app 对象有一个 PrevInstance 属性,尽管这只会提醒您需要检查参数。

      所以创建一个与您的个人资料同名的互斥锁。

      CreateMutex
      The CreateMutex function creates or opens a named or unnamed mutex object. 
      
      HANDLE CreateMutex(
        LPSECURITY_ATTRIBUTES lpMutexAttributes,  // SD
        BOOL bInitialOwner,                       // initial owner
        LPCTSTR lpName                            // object name
      );
      

      【讨论】:

        【解决方案4】:

        这是一些代码(没有声明,它来自一个表单,因此您需要对其进行编辑)。它列出了系统上每个窗口的所有内容。

        它像这样输出(到 rtfedit 中)。 Level 是显示父子关系的缩进数。

        Order   Level   WindowText  ClassName   HWnd    ParentHWnd  ProcessID   ParentProcessID ThreadID    ModuleNameHWin  EXENameProcess
        1   0   «No Window Text 0»  msvb_lib_tooltips   133318  133318  1648    3876    1944    C:\Windows\system32\MSCOMCTL.OCX    VB6.EXE
        2   0   «No Window Text 0»  msvb_lib_tooltips   133316  133318  1648    3876    1944    C:\Windows\system32\MSCOMCTL.OCX    VB6.EXE
        3   0   «No Window Text 0»  msvb_lib_tooltips   198898  133318  1648    3876    1944    C:\Windows\system32\MSCOMCTL.OCX    VB6.EXE
        4   0   «No Window Text 0»  msvb_lib_tooltips   133276  133318  1648    3876    1944    C:\Windows\system32\MSCOMCTL.OCX    VB6.EXE
        5   0   «No Window Text 0»  tooltips_class32    8585400 133318  1648    3876    1944    C:\Program Files\Microsoft Visual Studio\VB98\vb6.exe   VB6.EXE
        6   0   «No Window Text 0»  tooltips_class32    7341130 133318  1648    3876    1944    C:\Program Files\Microsoft Visual Studio\VB98\vb6.exe   VB6.EXE
        7   0   MSCTFIME UI MSCTFIME UI 8127794 133318  3356    1500    3240    C:\Program Files\Microsoft Visual Studio\VB98\vb6.exe   explorer.exe
        8   0   Default IME IME 721516  133318  3356    1500    3240    «Not Available Error=0» explorer.exe
        9   0   «No Window Text 0»  tooltips_class32    7340808 133318  3356    1500    3240    «Not Available Error=0» explorer.exe
        10  0   «No Window Text 0»  ThumbnailStackClass 4457892 133318  3356    1500    3240    «Not Available Error=0» explorer.exe
        

        这是代码

        Sub mnuInsertWindowList_Click()
        '    WindowChain = 0
            Dim hwnd As Long
                hwnd = GetTopWindow(0)
                If hwnd <> 0 Then
                    AddChildWindows hwnd, 0
                End If
        End Sub
        
        
        Private Function AddChildWindows(ByVal hwndParent As Long, ByVal Level As Long) As String
              Dim gwfnhwnd As Long, X As Long, WT As String, CN As String, Length As Long, hwnd As Long, TID As Long, PID As Long, MN As String, Ret As Long, Parenthwnd As Long
                Static Order As Long
                Static FirstTime As Long
                Parenthwnd = hwndParent
                If Level = 0 Then
                                hwnd = hwndParent
                Else
                    hwnd = GetWindow(hwndParent, GW_CHILD)
                End If
                Do While hwnd <> 0
                         WT = Space(512)
                          Length = GetWindowText(hwnd, WT, 508)
                          WT = Left$(WT, Length)
                          If WT = "" Then WT = Chr(171) & "No Window Text " & Err.LastDllError & Chr(187)
                          CN = Space(512)
                          Length = GetClassName(hwnd, CN, 508)
                          CN = Left$(CN, Length)
                          If CN = "" Then CN = "Error=" & Err.LastDllError
        
        
                          TID = GetWindowThreadProcessId(hwnd, PID)
        
                          MN = Space(512)
                          Length = GetWindowModuleFileName(hwnd, MN, 508)
                          If Length = 0 Then
                            MN = Chr(171) & "Not Available Error=" & Err.LastDllError & Chr(187)
                          Else
                            MN = Left$(MN, Length)
                          End If
        
        
                         Dim f As Long, sname As String, PList As String, PPID As Long
                         Dim hSnap As Long, proc As PROCESSENTRY32, Temp As String
                         hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0)
                         If hSnap = hNull Then Exit Function
                         proc.dwSize = LenB(proc)
                         ' Iterate through the processes
                         f = Process32First(hSnap, proc)
                         Do
                                If PID = proc.th32ProcessID Then
                                    sname = StrZToStr(proc.szExeFile)
                                    PPID = proc.th32ParentProcessID
                                End If
                                f = Process32Next(hSnap, proc)
                         Loop While f = 1
                          Order = Order + 1
        '                  CStr(Order) & " HWnd=" & FormatNumber$(hwnd, 0, vbFalse, vbFalse, vbFalse) & " Parent HWnd=" & FormatNumber$(Parenthwnd, 0, vbFalse, vbFalse, vbFalse) & " Level=" & CStr(Level) & WT & " (" & CN & ")" & " PID=" & FormatNumber$(PID, 0, vbFalse, vbFalse, vbFalse) & " TID=" & FormatNumber$(TID, 0, vbFalse, vbFalse, vbFalse) & " Module Name:" & MN & " ExeName:" & sname & vbCrLf
                        If FirstTime = 0 Then
                            txtNote.SelText = vbCrLf & "Order" & vbTab & "Level" & vbTab & "WindowText" & vbTab & "ClassName" & vbTab & "HWnd" & vbTab & "ParentHWnd" & vbTab & "ProcessID" & vbTab & "ParentProcessID" & vbTab & "ThreadID" & vbTab & "ModuleNameHWin" & vbTab & "EXENameProcess"
                            FirstTime = 1
                        End If
                        txtNote.SelText = vbCrLf & CStr(Order) & vbTab & CStr(Level) & vbTab & WT & vbTab & CN & vbTab & CStr(hwnd) & vbTab & CStr(Parenthwnd) & vbTab & CStr(PID) & vbTab & CStr(PPID) & vbTab & CStr(TID) & vbTab & MN & vbTab & sname
        
                          AddChildWindows hwnd, Level + 1
                          hwnd = GetWindow(hwnd, GW_HWNDNEXT)
                Loop
              End Function
        

        这些是声明。

        Public Declare Function GetTopWindow Lib "user32" (ByVal hwnd As Long) As Long
        Public Declare Function GetWindow Lib "user32" (ByVal hwnd As Long, ByVal wCmd As Long) As Long
        Public Declare Function GetWindowModuleFileName Lib "user32" Alias "GetWindowModuleFileNameA" (ByVal hwnd As Long, ByVal WinModule As String, StringLength As Long) As Long
        Public Declare Function GetWindowRect Lib "user32" (ByVal hwnd As Long, lpRect As RECT) As Long
        Public Declare Function GetWindowText Lib "user32" Alias "GetWindowTextA" (ByVal hwnd As Long, ByVal lpString As String, ByVal cch As Long) As Long
        Public Declare Function GetWindowThreadProcessId Lib "user32" (ByVal hwnd As Long, lpdwProcessId As Long) As Long
        Public Declare Function IsUserAnAdmin Lib "Shell32" () As Boolean
        
          Private Declare Function Process32Next Lib "kernel32" (ByVal hSnapshot As Long, lppe As PROCESSENTRY32) As Long
          Private Declare Function CloseHandle Lib "Kernel32.dll" (ByVal Handle As Long) As Long
          Private Declare Function Process32First Lib "kernel32" (ByVal hSnapshot As Long, lppe As PROCESSENTRY32) As Long
         Private Declare Function CreateToolhelp32Snapshot Lib "kernel32" (ByVal dwFlags As Long, ByVal th32ProcessID As Long) As Long
        
         Private Declare Function GetVersionExA Lib "kernel32" _
             (lpVersionInformation As OSVERSIONINFO) As Integer
        
        
        
          Private Type PROCESSENTRY32
             dwSize As Long
             cntUsage As Long
             th32ProcessID As Long           ' This process
             th32DefaultHeapID As Long
             th32ModuleID As Long            ' Associated exe
             cntThreads As Long
             th32ParentProcessID As Long     ' This process's parent process
             pcPriClassBase As Long          ' Base priority of process threads
             dwFlags As Long
             szExeFile As String * 260 ' MAX_PATH
          End Type
        
          Private Type OSVERSIONINFO
             dwOSVersionInfoSize As Long
             dwMajorVersion As Long
             dwMinorVersion As Long
             dwBuildNumber As Long
             dwPlatformId As Long           '1 = Windows 95 2 = Windows NT
             szCSDVersion As String * 128
          End Type
        
           Private Const PROCESS_QUERY_INFORMATION = 1024
           Private Const PROCESS_VM_READ = 16
           Private Const MAX_PATH = 260
           Private Const STANDARD_RIGHTS_REQUIRED = &HF0000
           Private Const SYNCHRONIZE = &H100000
          'STANDARD_RIGHTS_REQUIRED Or SYNCHRONIZE Or &HFFF
           Private Const PROCESS_ALL_ACCESS = &H1F0FFF
           Private Const TH32CS_SNAPPROCESS = &H2&
           Private Const hNull = 0
           Private Const GW_CHILD = 5
           Private Const GW_HWNDNEXT = 2
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2018-04-29
          • 2011-11-14
          • 1970-01-01
          • 2013-12-27
          • 2016-03-25
          • 1970-01-01
          • 2014-07-14
          • 1970-01-01
          相关资源
          最近更新 更多