【问题标题】:Sharing data between users of a shared-library在共享库的用户之间共享数据
【发布时间】:2011-11-15 18:30:06
【问题描述】:

我有一个共享库,比如 foo.so,其中包含一个名为 initialize() 的函数。有多个可执行文件打开 foo.so,每个都调用 initialize()。我希望initialize() 检查它是否已被另一个可执行文件调用,如果是,则什么也不做。在这些进程之间共享这些信息的最佳方式是什么?是否有一些特殊工具可以共享此类信息,或者我需要使用标准 IPC?

【问题讨论】:

    标签: c++ linux shared-libraries


    【解决方案1】:

    创建一个文件 /var/db/mylibname.如果 open() 返回错误,说明文件已存在,则说明您的库已初始化。

    它需要添加 atexit() 处理程序,该处理程序将在进程退出时删除文件。只有当 open() 返回成功时才必须初始化 Atexit。

    更新:

    如果资源必须只初始化一次并且它们(资源)不依赖于当时使用该库的任何进程的存在,那么最好在 /var 中创建文件/run 目录(以便在系统重新启动后清理)并忘记 atexit()。

    【讨论】:

    • Ew。谁再使用atexit
    • @TomalakGeret'kal 好吧,这取决于。 atexit() 是一种快速而肮脏的方法,但它做得很好。
    • 这可能有问题,请考虑以下顺序:进程 A 启动并初始化。然后进程 B 开始并且没有初始化,因为 A 已经这样做了。 A 现在退出,删除文件。进程 C 现在启动,检查文件是否存在并发现它丢失,所以现在 重新初始化,如果 B 仍在使用来自 A 的先前初始化,则可能会破坏进程中的 B。
    • @awoodland 如果资源必须只初始化一次,并且如果当时是否存在任何使用该库的进程并不重要,那么 atexit() 根本不应该使用。跨度>
    • @awoodland 哦,对,我可能误解了你。 rename() 将很难知道确切的文件名。我认为最好将引用计数存储在文件中并使用文件锁(例如 F_SETLKW)来读取和更新它。当然它不是完全安全的,例如用户进程可以在更新 refcount 的那一刻被 SIGKILL。
    【解决方案2】:

    您需要使用标准 IPC。想到内存映射,但首先要确定是否要按用户和按机器进行初始化。

    【讨论】:

    • 在这种情况下,每台机器只应调用一次初始化。用户信息不是一个因素。
    • @user800133:抱歉,但用户信息一个因素,因为执行 IPC 需要权限。
    • 我的意思是,有多少用户不是一个因素。 Initialize 应该只被调用一次。
    • @user800133:那么每个调用你的库的进程都应该以同一个用户身份运行,即它应该被限制为单个用户或者是 setuid。
    猜你喜欢
    • 1970-01-01
    • 2014-06-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多