You need to enable JavaScript to run this app. 程序自拷贝重启后GetCurrentDirectoryA返回值不变该如何解决?
优惠活动
大模型
产品
解决方案
定价
更多

程序自拷贝重启后GetCurrentDirectoryA返回值不变该如何解决?

问题核心原因

你碰到的死循环本质是混淆了Windows系统中两个完全不同的路径概念:

  • GetCurrentDirectoryA返回的是进程当前工作目录:这个值是进程启动时由父进程指定的动态值,和你exe文件本身存放在哪个位置没有必然关联,也不会随exe文件的物理位置变化自动更新。
  • 你实际需要判断的是exe自身的物理存放目录,需要用专门的API获取。

修复方案

把你判断路径的逻辑从读取GetCurrentDirectoryA的返回值,替换成读取自身exe的实际路径,步骤如下:

  1. 调用GetModuleFileNameA接口,传入NULL作为模块句柄,就能拿到当前运行的exe的完整绝对路径
  2. 切割路径去掉末尾的exe文件名,得到exe所在的目录
  3. 和GetWindowsDirectoryA返回的系统目录做对比,一致就跳过自拷贝逻辑,不一致再执行拷贝+重启操作

参考代码示例

#include <windows.h>
#include <shlwapi.h>
#pragma comment(lib, "shlwapi.lib")

BOOL IsRunningInWindowsDir() {
    // 获取自身exe完整路径
    char szExeFullPath[MAX_PATH] = {0};
    if (!GetModuleFileNameA(NULL, szExeFullPath, MAX_PATH)) {
        return FALSE;
    }
    // 移除文件名,保留所在目录
    if (!PathRemoveFileSpecA(szExeFullPath)) {
        return FALSE;
    }
    // 获取Windows系统目录
    char szWinDir[MAX_PATH] = {0};
    if (!GetWindowsDirectoryA(szWinDir, MAX_PATH)) {
        return FALSE;
    }
    // Windows路径不区分大小写,用不区分大小写的对比逻辑
    return lstrcmpiA(szExeFullPath, szWinDir) == 0;
}

// 业务逻辑入口调用
int main() {
    if (!IsRunningInWindowsDir()) {
        // 1. 执行自身、关联资源到Windows目录的拷贝逻辑
        // 2. 用绝对路径启动Windows目录下的新exe
        char szTargetExePath[MAX_PATH] = {0};
        GetWindowsDirectoryA(szTargetExePath, MAX_PATH);
        PathAppendA(szTargetExePath, "你的程序名.exe");
        ShellExecuteA(NULL, "open", szTargetExePath, NULL, NULL, SW_SHOWNORMAL);
        // 3. 退出当前旧进程
        ExitProcess(0);
    }
    // 后续正常业务逻辑
    return 0;
}

额外优化建议

  • 写入Windows目录需要程序持有管理员权限,你需要在程序的manifest配置中添加requireAdministrator权限声明,否则拷贝操作会被系统拦截
  • 如果你只是需要多个组件共享固定路径,更推荐选择C:\ProgramData\你的程序自定义目录作为存储位置,不需要修改系统目录,权限要求更低,也能实现全局所有组件都能访问到固定路径的需求

内容的提问来源于stack exchange,提问作者брат волк

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.15 01:36:03