在程序终止(C / C ++)保证文件删除 [英] Guaranteed file deletion upon program termination (C/C++)

查看:156
本文介绍了在程序终止(C / C ++)保证文件删除的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

的Win32的 的CreateFile 具有 FILE_FLAG_DELETE_ON_CLOSE ,但我在Linux上。

Win32's CreateFile has FILE_FLAG_DELETE_ON_CLOSE, but I'm on Linux.

我想打开这将永远在程序终止删除临时文件。我能理解,在程序的情况下崩溃,可能是不实际的,以保证这一点,但在其他情况下,我想它的工作。

I want to open a temporary file which will always be deleted upon program termination. I could understand that in the case of a program crash it may not be practical to guarantee this, but in any other case I'd like it to work.

我知道RAII。我知道信号。我知道的atexit(3)。我知道我可以打开该文件,并立即删除它,直到关闭文件,文件将保持可访问(甚至处理崩溃)。这些都不似乎是一个完整的,直接的解决方案:

I know about RAII. I know about signals. I know about atexit(3). I know I can open the file and delete it immediately and the file will remain accessible until the file descriptor is closed (which even handles a crash). None of these seem like a complete and straightforward solution:


  1. RAII:在那里,这样做:我有一个对象的析构函数删除该文件,但如果该程序是由信号终止析构函数不叫

  2. 的信号:我正在写一个低级别的库,这使得注册一个信号处理一个棘手的命题。例如,如果应用程序使用什么样的信号本身?我不想踩脚趾的任何。我可能会考虑一些聪明的使用的sigaction(2)来应对......但还没有投入足够的思想 - 这种可能性呢。

  3. 的atexit(3):显然是没用的,因为它不是异常终止(例如,通过信号)中调用

  4. preemptive 的unlink(2):这是pretty好,只是我需要的文件保留在文件系统中可见的(否则系统更难监测/故障诊断)。

  1. RAII: been there, done that: I have an object whose destructor deletes the file, but the destructor is not called if the program is terminated by a signal.
  2. signals: I'm writing a low-level library which makes registering a signal handler a tricky proposition. For example, what if the application uses signals itself? I don't want to step on any toes. I might consider some clever use of sigaction(2) to cope...but haven't put enough thought into this possibility yet.
  3. atexit(3): apparently useless, since it isn't called during abnormal termination (e.g. via a signal).
  4. preemptive unlink(2): this is pretty good except that I need the file to remain visible in the filesystem (otherwise the system is harder to monitor/troubleshoot).

你会做什么吗?

新解

我在原来的职位,我现在意识到我应该包括省略了一个细节。 文件在这种情况下是不是严格意义上的正常文件,而是一个POSIX消息队列。我通过 mq_open创建它()。它可以通过 mq_close被关闭()的close()(前者是后者我的系统上的别名)。它可以从系统中通过 mq_unlink被删除()。所有这一切都使得它类似于一个普通文件,的除了的,我不能选择文件所在的目录。这使得当前最流行的答案(将文件中的 / tmp目录)行不通的,因为是由系统中的虚拟文件系统容量非常有限创建的文件。 (我已经安装在的/ dev / mqueue中的虚拟文件系统,继男人mq_overview的例子)。

I elided one detail in my original post which I now realize I should have included. The "file" in this case is not strictly a normal file, but rather is a POSIX Message Queue. I create it via mq_open(). It can be closed via mq_close() or close() (the former is an alias for the latter on my system). It can be removed from the system via mq_unlink(). All of this makes it analogous to a regular file, except that I cannot choose the directory in which the file resides. This makes the current most popular answer (placing the file in /tmp) unworkable, because the "file" is created by the system in a virtual filesystem with very limited capacity. (I've mounted the virtual filesystem in /dev/mqueue, following the example in man mq_overview) .

这也解释了为什么我需要的名称保持可见(使即刻取消链接的方法行不通):文件必须两个或多个进程之间共享

This also explains why I need the name to remain visible (making the immediate-unlink approach unworkable): the "file" must be shared between two or more processes.

推荐答案

这名在过程运行时仍然可见要求使得这个难以实现。你可以重温这一要求?

The requirement that the name remains visible while the process is running makes this hard to achieve. Can you revisit that requirement?

如果没有,那么有可能不是一个完美的解决方案。我会考虑结合卡米尔什么建议Kisiel的信号处理策略。你可以跟踪安装在信号处理程序在安装信号处理程序之前。如果默认的处理程序是SIG_IGN,你通常不会安装自己的处理程序;如果是SIG_DFL,你会记得;如果是别的东西 - 一个用户定义的信号处理程序 - 你会记得这个指针,并安装你自己的。当你的处理程序调用时,你会做你需要做的,然后调用想起处理程序,从而链接的处理程序。您也将安装的atexit()处理。您也将记录您做到这一点,信号为你做到这一点。

If not, then there probably isn't a perfect solution. I would consider combining a signal handling strategy with what Kamil Kisiel suggests. You could keep track of the signal handlers installed before you install your signal handlers. If the default handler is SIG_IGN, you wouldn't normally install your own handler; if it is SIG_DFL, you would remember that; if it is something else - a user-defined signal handler - you would remember that pointer, and install your own. When your handler was called, you'd do whatever you need to do, and then call the remembered handler, thus chaining the handlers. You would also install an atexit() handler. You would also document that you do this, and the signals for which you do it.

需要注意的是信号处理是一个不完美的策略; SIGKILL不能被捕获,和的atexit()处理程序不会被调用,文件将围绕离开了。

Note that signal handling is an imperfect strategy; SIGKILL cannot be caught, and the atexit() handler won't be called, and the file will be left around.

大卫Segond的建议 - 一个临时文件名守护 - 很有趣。对于简单的过程,这是不够的;如果进程请求临时文件叉子和期望孩子以后自己的文件(退出)则守护进程有一个问题,当使用它的最后一道工序模具检测 - 因为它不会自动知道有它打开的进程。

David Segond's suggestion - a temporary file name daemon - is interesting. For simple processes, it is sufficient; if the process requesting the temporary file forks and expects the child to own the file thereafter (and exits) then the daemon has a problem detecting when the last process using it dies - because it doesn't automatically know the processes that have it open.

这篇关于在程序终止(C / C ++)保证文件删除的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆