【问题标题】:Directory of running program on Linux?Linux 上运行程序的目录?
【发布时间】:2019-05-04 07:14:08
【问题描述】:

嘿,我一直在编写一个程序(一种电子书查看类型的东西),它从可执行文件所在文件夹中的文件夹加载文本文件。这给我带来了一些问题,因为如果我使用命令“./folder/folder/program”从另一个目录运行程序,例如,我的程序将找不到文本,因为工作目录不正确。我不能有一个绝对目录,因为我希望程序是可移植的。有没有办法获得可执行文件运行的精确目录,即使它是从不同的目录运行的。我听说可以结合 argc[0] 和 getcwd() 但是当目录中有空格时 argc 会被截断,(我认为?)所以我想尽可能避免这种情况。

我在 Linux 上使用 g++,提前谢谢

【问题讨论】:

  • argc 是参数计数; argv 是参数向量(指向字符串的指针数组)。 argv[0] 不会被空格截断; argv[0] 由启动程序的程序选择,不一定与程序的路径有任何关系。如果 argv[0] 以 '/' 开头,则不要添加 getcwd()。
  • 你可以访问 boost 库吗?
  • 等一下。您需要“可执行路径”还是“运行可执行文件的目录”?

标签: c++ linux unix


【解决方案1】:

你可以通过阅读命令行获取运行程序的路径。在 linux 中,您可以通过将 /proc 文件夹读取为 /proc/PID/CommandLine 来获取命令行

【讨论】:

    【解决方案2】:

    当您将一本书添加到您的图书馆时,您可以记住它的绝对路径。
    当您的程序依赖于它将从工作目录而不是从其他某个目录启动的事实时,这还不错。这就是为什么会有各种带有“工作目录”参数的“链接”。

    您不必以您想要的方式处理此类情况。只需检查所有必要的文件和目录结构是否到位,如果没有,请在说明中记录错误。

    或者每次当您的程序启动并且没有找到必要的文件时,程序可以要求将路径指向图书库。

    我仍然不明白知道您当前目录名称的原因。

    #include <boost/filesystem/convenience.hpp>
    
    #include <iostream>
    #include <ostream>
    
    int main(int argc, char** argv)
    {
        boost::filesystem::path argvPath( argv[0] );
        boost::filesystem::path executablePath( argvPath.parent_path() );
        boost::filesystem::path runPath( boost::filesystem::initial_path() );
    
        std::cout << executablePath << std::endl;
        std::cout << runPath << std::endl;
        return 0;
    }
    

    【讨论】:

      【解决方案3】:

      编辑 - 不要使用 getcwd(),它只是用户不在可执行文件所在的位置。

      here for details

      在 linux 上 /proc//exe 或 /proc/self/exe 应该是指向可执行文件的符号链接。和其他人一样,我认为更重要的问题是“你为什么需要这个?”使用可执行路径查找辅助文件并不是真正的 UNIX 形式。相反,您使用环境变量或默认位置,或遵循其他约定之一来查找辅助文件的位置(即 ~/.rc)。

      【讨论】:

      • "...这不是真正的 UNIX 形式..." 它是哪种形式?我以为它不是真正的 ANY_OS_FORM。
      • 按照 plinth 的建议:为用户/系统添加配置文件/目录并搜索完整路径。例如,全局配置文件应该放在 /etc 中,而用户配置文件通常放在 ~/.rc 中的文件或 ~/. 目录下。
      • Mykola - 它更像是 1980 年代的 Macintosh/Windows 形式。我的应用程序位于一个文件夹中,它的支持文件与其相关。要查找支持文件,首先要找到应用所在的位置。
      • @plinth:可能需要它的一个原因是,例如,一个可以安装到/usr/usr/local/opt$HOME/app$HOME/.local/ 或其他任何地方。如果您随后需要加载支持文件,您如何决定在哪里查找? 更糟糕的是,如果它被移动了怎么办?查找可执行文件的路径可以让您在不知道将放置在哪里的情况下打包应用程序。这是我当前的用例。
      【解决方案4】:

      argv[0] 在有空格时不会被截断。但是,当从 PATH 环境变量中列出的目录运行程序时,它将只有程序名称而不是路径。

      无论如何,您在这里尝试做的对于 Unix/Linux 程序来说并不是一个好的设计。数据文件不与程序文件存储在同一目录中,因为这样做会导致难以应用适当的安全策略。

      在我看来,获得所需内容的最佳方法是使用 shell 脚本来启动实际程序。这与 Firefox 在 Linux 系统上的启动方式非常相似。 shell 将脚本的名称放入$0,并且该变量将始终具有路径。然后您可以使用环境变量或命令行参数为您的程序提供数据文件的位置,如下所示:

      dir=`dirname "$0"`
      cd "$dir/../data/"
      "$dir/real-program"
      

      我会安排你的程序,使它的文件有点像这样:

      install-dir/bin/program
      install-dir/bin/real-program
      install-dir/etc/config
      install-dir/data/book-file.mobi
      

      【讨论】:

        猜你喜欢
        • 2013-04-29
        • 2011-04-11
        • 2011-10-20
        • 1970-01-01
        • 2013-12-28
        • 2021-10-02
        • 2014-02-16
        • 1970-01-01
        相关资源
        最近更新 更多