Get path of executable

前端 未结 23 2090
清歌不尽
清歌不尽 2020-11-22 07:04

I know this question has been asked before but I still haven\'t seen a satisfactory answer, or a definitive \"no, this cannot be done\", so I\'ll ask again!

All I wa

23条回答
  •  半阙折子戏
    2020-11-22 07:30

    This was my solution in Windows. It is called like this:

    std::wstring sResult = GetPathOfEXE(64);
    

    Where 64 is the minimum size you think the path will be. GetPathOfEXE calls itself recursively, doubling the size of the buffer each time until it gets a big enough buffer to get the whole path without truncation.

    std::wstring GetPathOfEXE(DWORD dwSize)
    {
        WCHAR* pwcharFileNamePath;
        DWORD dwLastError;
        HRESULT hrError;
        std::wstring wsResult;
        DWORD dwCount;
    
        pwcharFileNamePath = new WCHAR[dwSize];
    
        dwCount = GetModuleFileNameW(
            NULL,
            pwcharFileNamePath,
            dwSize
        );
    
        dwLastError = GetLastError();
    
        if (ERROR_SUCCESS == dwLastError)
        {
            hrError = PathCchRemoveFileSpec(
                pwcharFileNamePath,
                dwCount
            );
    
            if (S_OK == hrError)
            {
                wsResult = pwcharFileNamePath;
    
                if (pwcharFileNamePath)
                {
                    delete pwcharFileNamePath;
                }
    
                return wsResult;
            }
            else if(S_FALSE == hrError)
            {
                wsResult = pwcharFileNamePath;
    
                if (pwcharFileNamePath)
                {
                    delete pwcharFileNamePath;
                }
    
                //there was nothing to truncate off the end of the path
                //returning something better than nothing in this case for the user
                return wsResult;
            }
            else
            {
                if (pwcharFileNamePath)
                {
                    delete pwcharFileNamePath;
                }
    
                std::ostringstream oss;
                oss << "could not get file name and path of executing process. error truncating file name off path. last error : " << hrError;
                throw std::runtime_error(oss.str().c_str());
            }
        }
        else if (ERROR_INSUFFICIENT_BUFFER == dwLastError)
        {
            if (pwcharFileNamePath)
            {
                delete pwcharFileNamePath;
            }
    
            return GetPathOfEXE(
                dwSize * 2
            );
        }
        else
        {
            if (pwcharFileNamePath)
            {
                delete pwcharFileNamePath;
            }
    
            std::ostringstream oss;
            oss << "could not get file name and path of executing process. last error : " << dwLastError;
            throw std::runtime_error(oss.str().c_str());
        }
    }
    

提交回复
热议问题