代码之家  ›  专栏  ›  技术社区  ›  John Gietzen

如何在C/Win32中获取正在运行的进程的DOS路径名?

  •  0
  • John Gietzen  · 技术社区  · 15 年前

    总而言之,我需要这样做:

    12345(hWnd)->“C:\安装程序.exe"


    现在,我正在使用 GetProcessImageFileName 检索进程句柄的内核设备路径。我正在用 OpenProcess GetWindowThreadProcessId

    \设备\硬盘1\安装程序.exe

    此时,我使用枚举系统上的所有驱动器 DriveInfo.GetDrives() QueryDosDevice . 最后,我可以做一些字符串操作魔术,和“ 繁荣 “我有我的路。


    好吧,我的问题是:
    1. 我真正想要的是 QueryFullProcessImageName 在XP上

    2 回复  |  直到 15 年前
        1
  •  2
  •   Jerry Coffin    10 年前

    QueryFullProcessImageName

    最接近于 QueryFullProcessImageName 在XP上可用的可能是 GetModuleFileNameEx QueryFullProcessImageName .

    编辑:While GetModuleFileNameEx模块

    #include <windows.h>
    #include <psapi.h>
    #include <iterator>
    #include <iostream>
    #include <string>
    #include <map>
    
    std::string getfilename(DWORD pid) { 
        HANDLE process = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, false, pid);
        static int winver;
        char path[256]= {0};
        DWORD size = sizeof(path);
    
        if (winver==0) 
            winver = GetVersion() & 0xf; 
    
    #if WINVER >= 0x600
        if (winver >= 6)    
            QueryFullProcessImageName(process, 0, path, &size);
        else
    #endif
        if (!GetModuleFileNameEx(process, NULL, path, sizeof(path)))
            strcpy(path, "Unknown");
        return std::string(path);
    }
    
    typedef std::map<DWORD, std::string> win_map;
    
    namespace std { 
        ostream &operator<<(ostream &os, win_map::value_type const &v) { 
            return os << v.first << ": " << v.second;
        }
    }
    
    BOOL CALLBACK show_info(HWND window, LPARAM lParam) {
        win_map &exes = *(win_map *)lParam;
    
        DWORD pid;
        GetWindowThreadProcessId(window, &pid);
        exes[pid] = getfilename(pid);
        return true;
    }
    
    int main() {
        win_map exes;
        EnumWindows(show_info, (LPARAM)&exes);
        std::copy(exes.begin(), exes.end(), std::ostream_iterator<win_map::value_type>(std::cout, "\n"));
        return 0;
    }
    

    快速测试的结果有些有趣。编译为32位代码,版本使用 找到33个具有顶级窗口的进程,并找到其中31个可执行文件的名称。使用的版本 ,还找到了33个进程,但只找到了21个可执行文件的名称。但是,如果我把它编译成64位代码, 任何一个

    在任何情况下,即使是功能最差的版本(32位/GMFNE)也能找到~2/3的名称 无线电数据系统

        2
  •  1
  •   jamesdlin    15 年前

    必须能够检索到正在运行的进程的文件路径,因为Sysinternals的processexplorer会这样做。当然,processexplorer使用 NtQueryInformationProcess ,该函数不受支持。(另一方面,因为您专门针对XP,并且 QueryFullProcessImageName 在Vista和更高版本上,担心API在未来版本的Windows中不可用可能不是一个问题。)

    CodeProject has an article about how to use NtQueryInformationProcess