I did a big oops, but the file is still open and in use.
Following (Link to a specific inode),
copying from the /proc/###/fd/###
to a new file is not useful because:
- the file is changing
- The filesize is 40G and the disk is full (150MB free)
I am attempting to relink it to the filesystem (undelete it).
COMMAND PID USER FD TYPE DEVICE SIZE NODE NA开发者_如何学编程ME
vmware-vm 4281 root 126u REG 253,0 40020664320 10928132 /var/mnt/partial.img
I held the file open with a "wc /proc/4281/fd/126", then suspended it.
I created a link on the filesystem by using debugfs (inspired from dag wieers) then edited the directory entry to set the deleted time to 0, update the link count. reboot and run fsck all is well.
This is a kernel mod to do it, I have not tested it yet.
The best way I know is to use gdb
and attach to the process that still has the file open, then manually call library functions from inside gdb
to open a new file and copy the file contents to the new file.
It took a little bit to figure out what you were asking.
There is no user land API to do this that I know of. It would be nice to be able to create a link with an open file descriptor, which, of course, would fail if the file descriptor was anything not on disk or if the newpath did not reside on the same disk as that file, but I don't know of anything like that.
Part of the reason for this is that in reality the file no longer has to actually be on disk. It can live completely (or partially) in the file system's cache. The OS could decide not to flush changes to that file to disk because it may think that doing so won't matter (unless it needs to free up some RAM).
The syscall you want, the idea - link file descriptor to a new name - was proposed and rejected several times in past (discussions pop-up on LKML time after time) due to security reasons: if a file was deleted then it was deleted, period. (See Edit1 below.)
Lots of security oriented application depend on the behavior that the file they have deleted yet they keep file descriptor open, cannot be reopened ever again. To accomplish that, on one side there are the overly restrictive permissions on the /proc/*/fd/*
links (only owner may only read) and on the other side is the missing syscall.
I am attempting to undelete it.
1. the file is changing
2. 40G and the disk is full
You are out of luck. You can't give new name to a deleted (yet open) file. Learn to use rm -i
(I hated the default RedHat's aliases for root shell, but eventually learned to love them).
Edit1 Comment to another response here by @ephemient, pulling the refernces I was lazy to look up myself:
A user land API has been brought up before and shot down several times in the Linux world; the justifications have been security-related, not filesystem disk format-related. lkml.org/lkml/1998/3/8/1 lkml.org/lkml/2002/1/19/16 lkml.org/lkml/2003/4/6/112 et al.
It is not part of the base kernel, but there is a module out there http://fdlink.svn.sourceforge.net/viewvc/fdlink/trunk/flink/ which is supposed to do it. I think that using debugfs is easier but the kernel mod might be cleaner.
精彩评论