将 %APPDATA% 与 CreateProcessW 一起使用

Posted

技术标签:

【中文标题】将 %APPDATA% 与 CreateProcessW 一起使用【英文标题】:Using %APPDATA% with CreateProcessW 【发布时间】:2018-12-12 10:14:42 【问题描述】:

我有一个简单的代码,它使用 system() 使用变量 %APPDATA% 将文件下载到 AppData,我想使用 CreateProcessW 而不是系统,但由于某种原因,当我在 CreatProcess 下使用相同的命令时,它会查找“Working Dir”\%APPDATA% 而不是实际的 AppData 目录,并引发异常。

System() 工作代码:

system("powershell.exe -command Invoke-WebRequest https://the.earth.li/~sgtatham/putty/latest/w32/putty.exe -OutFile '%APPDATA%\\putty.exe'");

CreateProcessW 代码:

wchar_t cmdArgs[] = L"powershell.exe -command Invoke-WebRequest https://the.earth.li/~sgtatham/putty/latest/w32/putty.exe -OutFile '%APPDATA%\\putty.exe'";
CreateProcessW(NULL, cmdArgs, nullptr, nullptr, false, 0, nullptr, nullptr, &si, &pi)

例外:

Invoke-WebRequest:找不到路径“G:\Projects\C++\PS_Tries\PS_Tries\%APPDATA%\putty.exe”的一部分。 在行:1 字符:1 + 调用 WebRequest https://the.earth.li/~sgtatham/putty/latest/w32/put ... + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : NotSpecified: (:) [Invoke-WebRequest], DirectoryNotFoundException + FullyQualifiedErrorId:System.IO.DirectoryNotFoundException,Microsoft.PowerShell.Commands.InvokeWebRequestCommand

如何使它像 system() 一样扩展 %APPDATA% ?

【问题讨论】:

你可以使用ExpandEnvironmentStrings @VTT 我试过使用它,但我不知道如何将输出添加到 CreateProcess 那将是另一个问题。 扩展%APPDATA% 是查找文件夹的错误方法。你应该使用SHGetKnownFolderPath 您只需将+std::wstring 一起使用。所有这些糟糕的 C 字符串的东西,你不必这样生活。 【参考方案1】:

您可以使用_wdupenv_s 函数获取appdata 路径,然后使用您的参数concatenate

wchar_t *w_app_data_path;
size_t sz = 0;
errno_t err = _wdupenv_s(&w_app_data_path, &sz, L"APPDATA");
wchar_t cmdArgs[2048] 0 ;
wsprintfW(cmdArgs, L"powershell.exe -command Invoke-WebRequest https://the.earth.li/~sgtatham/putty/latest/w32/putty.exe -OutFile '%s\\putty.exe'", w_app_data_path);
free(w_app_data_path);
CreateProcessW(NULL, cmdArgs, nullptr, nullptr, false, 0, nullptr, nullptr, &si, &pi)

【讨论】:

您有内存泄漏。您不应该将已分配的缓冲区传递给_wdupenv_s。相反,该函数会为您分配一个缓冲区,当您完成使用它时,您必须 free @zett42 我已经更新了关于你的评论的代码

以上是关于将 %APPDATA% 与 CreateProcessW 一起使用的主要内容,如果未能解决你的问题,请参考以下文章

在T-SQL中使用LIKE与存储过程完全匹配?

我正在尝试将所有 npm 模块安装在 ../AppData/Roaming 文件夹中。但每次它失败并显示错误代码 - 4068

MSIX 默认安装到 AppData,而不是 ProgramFiles

如何正确引用/检索在 AppData 中创建的临时文件以将文件上传到服务器?

管理员是不是可以限制 %AppData% 的使用?

将Git添加到PATH变量 - 在AppData / Local下找不到GitHub