关于 c : 当一个库被杀死时自动删除它创建的文件

Automatically delete files created by a library when it is killed

我有一个必须创建临时文件的 Linux 动态库。这些文件必须有一个文件名——它们不能被创建并立即取消链接。我也无法拦截像 SIGINTSIGKILL 这样的信号,因为这是一个被其他程序使用的库。

当创建文件的进程被杀死时,是否有一种理智的方法可以自动删除文件?

澄清:

  • 这些确实是我的限制。当我刚刚在问题中说我不能 unlink() 时,请不要回答说"你可以 unlink()"。
  • 我意识到这将需要操作系统支持——显然,当我的程序被杀死时,它本身就不能运行任何代码来删除文件。但是可能有一些方法可以标记文件,以便操作系统删除它们。
  • 例如,Windows 有一个"关闭时删除"选项,这意味着当您的程序被杀死时,它所拥有的任何打开的文件都会被关闭并自动删除(我认为;我没有尝试过)。如果在某个地方存在这样的功能,那么理论上在 Linux 上这样的事情显然是可能的。我只想知道有没有。


    创建一个文件,然后将 /proc/self/fd/X 传递给 LLVM,其中 X 是您的文件描述符。您现在可以取消链接(正如 Basile 建议的那样),

    由于 /proc/self 仅在您的程序关闭时才会消失,因此名称和文件的寿命足够长。


    虽然这不是特别明智,但 Linux 允许您通过 /proc/$pid/fd/$number 传递已删除文件的名称。


    另一个可能的解决方案是 fork() 一个子进程。然后通过某种机制将所有临时文件名发送到此进程。

    子进程可以像这样注册以知道其父进程何时被杀死:

    1
    2
    3
    4
    5
    #include <sys/prctl.h>
    int ret;
    ret = prctl (PR_SET_PDEATHSIG, SIGUSR1);
    if (ret)
            perror ("prctl");

    然后它会在父级被杀死时收到SIGUSR1。此时就可以正常删除文件了。


    不,在使用您的库的程序没有运行后,您不能删除这些,因为使用它的程序不再运行。

    相反,您可能应该

    • 在库的正常操作中检查过时/过大/剩余的临时文件(下次运行时清理)
    • 创建一个单独的程序来为您管理这些(定期清理)

    这感觉像是一个相当普遍的问题(我当然有过),但它源于对您的程序可能发生的事情的误解。 SIGKILL 将在您的程序可以处理的范围之外立即终止它,并且不会运行它的进一步操作。 (一些特殊的可以继续运行)

    正如这篇关于这个主题的帖子所说的那样

    SIGKILL pulls the rug out from your running process, terminating it immediately.


    I have a Linux dynamic library that has to create temporary files.

    您可以使用 atexit(3) 注册一个处理程序,该处理程序将在 exit(3) 时间(或 main 的正常终止)删除所有这些临时文件。当然,这不适用于信号。

    您可以在一些 tmpfs 文件系统中创建这些文件。然后它们将在关机时被删除。

    如果您遵循有关这些文件的一些命名约定,您还可以使用一些清理脚本(由一些 crontab 条目触发)发布您的库。

    Is there a sane way to have the files automatically deleted when the process that created them is killed?

    一般来说不是(并且不可能有一个具有 POSIX 文件语义的)。您可能会编写一个清理程序(可能使用 inotify(7) 工具)以从外部运行(例如,作为 crontab 作业或某个守护进程)。

    您还可以在创建后(使用 opencreat)取消链接(2)每个此类临时文件,并为其保留文件描述符。然后,当进程终止时,或者当它 close-s 那个文件描述符时,文件资源被回收。 tmpfile(3) 使用了这个技巧。

    顺便说一句,如果你使用 LLVM 作为 JIT 翻译器,你可以考虑使用 libgccjit。它能够在没有任何输入文件的情况下生成代码。

    这样的临时文件不能被自动删除,因为其他一些进程可以打开它们(通过它们的名字)——在任意时刻。这就是为什么 Linux 不能"关闭时删除"(相反,据传 Windows 只允许单个进程写入给定文件)。

    But there may be some way to mark the files so that the OS deletes them.

    不,不在 Linux 或 POSIX 上。该功能应由应用程序代码提供。