Winapi Windows API-CreateProcess()路径,带空格

Winapi Windows API-CreateProcess()路径,带空格,winapi,Winapi,如何将带有空格的路径传递给CreateProcess()函数 以下作品 STARTUPINFO si; PROCESS_INFORMATION pi; ZeroMemory( &si, sizeof(si) ); si.cb = sizeof(si); ZeroMemory( &pi, sizeof(pi) ); if( !CreateProcess(_T(

如何将带有空格的路径传递给CreateProcess()函数

以下作品

STARTUPINFO si;
            PROCESS_INFORMATION pi;

            ZeroMemory( &si, sizeof(si) );
            si.cb = sizeof(si);
            ZeroMemory( &pi, sizeof(pi) );

            if( !CreateProcess(_T("c:\\installer\\ew3d.exe"),    // No module name (use command line)
                _T("c:\\installer\\ew3d.exe /qr"),//argv[1],        // Command line
                NULL,           // Process handle not inheritable
                NULL,           // Thread handle not inheritable
                FALSE,          // Set handle inheritance to FALSE
                0,              // No creation flags
                NULL,           // Use parent's environment block
                NULL,           // Use parent's starting directory 
                &si,            // Pointer to STARTUPINFO structure
                &pi )           // Pointer to PROCESS_INFORMATION structure
                ) 
            {
                printf( "CreateProcess failed (%d).\n", GetLastError() );
                return false;
            }

            //Wait until child process exits.
            WaitForSingleObject( pi.hProcess, INFINITE );

            // Close process and thread handles. 
            CloseHandle( pi.hProcess );
            CloseHandle( pi.hThread );
但是,如果我使用一个路径和下面的代码一样有空格,它就不起作用了

CreateProcess(_T("c:\\master installer\\ew3d.exe"),    // No module name (use command line)
                    _T("c:\\master installer\\ew3d.exe /qr"),//argv[1],        // Command line
                    NULL,           // Process handle not inheritable
                    NULL,           // Thread handle not inheritable
                    FALSE,          // Set handle inheritance to FALSE
                    0,              // No creation flags
                    NULL,           // Use parent's environment block
                    NULL,           // Use parent's starting directory 
                    &si,            // Pointer to STARTUPINFO structure
                    &pi )           // Pointer to PROCESS_INFORMATION structure
                    ) 
引用下面这样的命令也没有帮助

CreateProcess(_T("\"c:\\master installer\\ew3d.exe\""),    // No module name (use command line)
                    _T("\"c:\\master installer\\ew3d.exe\" /qr"),//argv[1],        // Command line
                    NULL,           // Process handle not inheritable
                    NULL,           // Thread handle not inheritable
                    FALSE,          // Set handle inheritance to FALSE
                    0,              // No creation flags
                    NULL,           // Use parent's environment block
                    NULL,           // Use parent's starting directory 
                    &si,            // Pointer to STARTUPINFO structure
                    &pi )           // Pointer to PROCESS_INFORMATION structure
                    ) 

传递带有空格的路径的正确方法是什么?

不需要在第一个和第二个参数中指定应用程序路径。根据MSDN,如果在第一个参数中列出应用程序名称,则第二个参数应仅为命令行参数。否则,请将第一个参数设置为
NULL
,然后在第二个参数中,如果应用程序名称包含空格,请将其括在引号中。不确定您的上一个列表为什么不起作用。

您的第三个代码片段是正确的,不确定您为什么有问题。在这里,拥有GetLastError()返回值是很有价值的。但是请注意CreateProcess的第二个参数是LPTSTR,而不是LPCTSTR。换句话说,Windows可以写回字符串。很恐怖,不是吗?可能有足够的理由改用ShellExecuteEx()。

文档不清楚,但如果包含空格,则可能必须允许param 2定义完整路径

lpApplicationName参数可以是 无效的在这种情况下,模块名 一定是第一个白人 空格–中以空格分隔的标记 lpCommandLine字符串。如果您正在使用 一个长文件名,其中包含 空格,使用带引号的字符串表示 文件名的结尾和 争论开始了;否则,文件将被删除 名称不明确

你试过这种变体吗

CreateProcess(NULL,    // No module name (use command line)
              _T("\"c:\\master installer\\ew3d.exe\" /qr"),//argv[1],        // Command line
              NULL,           // Process handle not inheritable
              NULL,           // Thread handle not inheritable
              FALSE,          // Set handle inheritance to FALSE
              0,              // No creation flags
              NULL,           // Use parent's environment block
              NULL,           // Use parent's starting directory 
              &si,            // Pointer to STARTUPINFO structure
              &pi )           // Pointer to PROCESS_INFORMATION structure
             ) 
编辑:以下内容对我有效(dwError为0)。我的项目是用多字节字符集构建的

LPTSTR szCmdLine = _tcsdup(TEXT(
    "\"C:\\Program Files\\adobe\\Reader 8.0\\reader\\acrord32.exe\" /qr"));
CreateProcess(NULL,
              szCmdLine,
              NULL,           // Process handle not inheritable
              NULL,           // Thread handle not inheritable
              FALSE,          // Set handle inheritance to FALSE
              0,              // No creation flags
              NULL,           // Use parent's environment block
              NULL,           // Use parent's starting directory 
              &si,            // Pointer to STARTUPINFO structure
              &pi            // Pointer to PROCESS_INFORMATION structure
             );     // This works. Downcasting of pointer to members in general is fine.

DWORD error = GetLastError();

晚会有点晚了。出于某种原因,我不能投票给执政官,但他是对的。我也遇到了同样的问题,取消应用程序名就可以解决这个问题。我还尝试了appname中的path&第二个参数中的命令行参数,但没有成功

我在Win7 x64上

CreateProcess(空,“\”到exe的路径\”-x-y-z“,…)


对我来说很有用。

对于另一个答案,示例3是不是正确的答案


问题是引号不应该封装作为CreateProcess的第一个参数传递的模块路径名。但是,引号应该将arg0(同样是模块路径)封装为传递给命令行(CreateProcess的第二个参数)

因此,正确的格式副本是:

CreateProcess(_T("c:\\master installer\\ew3d.exe"),    
                    _T("\"c:\\master installer\\ew3d.exe\" /qr"),
                    NULL,           // Process handle not inheritable
                    NULL,           // Thread handle not inheritable
                    FALSE,          // Set handle inheritance to FALSE
                    0,              // No creation flags
                    NULL,           // Use parent's environment block
                    NULL,           // Use parent's starting directory 
                    &si,            // Pointer to STARTUPINFO structure
                    &pi )           // Pointer to PROCESS_INFORMATION structure
                    ) 

我的想法(把两个论点的完整路径)来自。事实上,我对它进行了测试——如果我没有在两个参数中都输入完整路径,它就会失败。对于第三个代码段,GetLastError()返回123,这意味着“文件名、目录名或卷标语法不正确”。这很不寻常。您使用的路径是否与发布的路径完全相同,或者您是否对其进行了修改?完全从我的测试应用程序中复制。是的,我放弃了CreateProcess()并使用了ShellExcuteEx(),它不再存在此问题。但是我有一个非常奇怪的问题,也许你可以看看——问题是引号不应该封装模块路径名(CreateProcess的第一个参数)。这就是为什么错误是路径不存在。但是,您应该继续引用为命令行(CreateProcess的第二个参数)传递的封装arg0(同样是模块路径)。我在下面发布了新的答案。刚刚在编辑中发布的代码对我来说还行-看不出为什么对你来说不行。它在Windows Vista 32上,我使用的是VS 2010。它能在不同的操作系统上工作吗?这是可行的,但不是100%的学究式正确。我的答案(得票最多的一个)解释了全部情况。上面公认的答案是错误的。