5

Okay, some time ago I found what seems to be a bug in nautilus.

/tmp$ mkdir test/
/tmp$ mkdir test2/
/tmp$ echo "very important stuff" > test/important-file.txt
/tmp$ ln -s /tmp/test/ test2/test

If you try to mv test2/test . bash is smart enough to answer :

mv: «test2/test» and «./test» identify the same file

I created a symbolic link to test (a directory containing a file) in another location, and then I moved the symbolic link to the place where the directory was

But then , nautilus gets into the game:

Moving symbolic link to the location where de directory is in nautilus

Nautilus understands that the symbolic link is a directory, and it kindly offers me to merge them:

enter image description here

Now, I merged them (I obviously thought it was two different directories). And as a result...

tmp$ ls -la
lrwxrwxrwx  1 cool-user  best-group-ever      9 août  26 23:51 test -> /tmp/test

Okay. So I lost my directory (which is normal, because I overwrote it) and ended up with a useless circular symbolic link, but... what happened with my important-file.txt ? It had an inode, that's not referenced by any directory in my system anymore.

Obviously, I didn't write that inode in a post-it... so, where is it ?. Is there any way to find every file with an inode which is not referenced by any dir?

And as a bonus question: Is this the expecteb behaviour of nautilus, or is it a bug?

Why and how this happened to me is a long story, but I had some really important (and confidential) files within my directory that I would like to get back

  • 1
    You probably have an excessive cd command on line 4 of the snippet – kos Sep 18 '15 at 10:02
  • 3
    However it's definetly a bug, and I've got the feeling that the file will be gone after this. Here's the post of an user reporting the same thing on Launchpad, in a bug report probably related to the same "main" Nautilus' internal issue – kos Sep 18 '15 at 10:56
  • It seems to be easy if important-file.txt is still opened by another process, so you can find out the inode by listing all open files (lsof | grep important-file.txt) and then re-link it. See serverfault.com/questions/168909/relinking-a-deleted-file and barricane.com/undelete-open-file-from-inode - but I guess your file is not opened any more, so it could also probably be overwritten already... – Byte Commander Sep 18 '15 at 11:56
  • Besides that, you can look for the standard data recovery methods of deleted files. Make sure you don't boot from or writeable mount the disk any more though! superuser.com/q/170857/418736 or askubuntu.com/questions/217606/undelete-files-on-ext4 or askubuntu.com/questions/41601/… - GOOD LUCK! :-) – Byte Commander Sep 18 '15 at 12:06
  • Well, I tried at the time without succeeding, but it was long ago. Actually, that's why I thought the file hadn't been deleted, as his inode should still be listed by the device, but not referenced anywhere. Those utilities do the opposite, the look for file data that's not referenced by an active inode. – Luis Sieira Sep 18 '15 at 12:17
3
+25

Not sure that's possible. After all, all your of your free space is a list of inodes.

See however the Orphan File feature of ext4.

  • This sounds really interesting, could you link something about what free space is ? Is it always the case for Unix systems ? – Luis Sieira Sep 18 '15 at 12:11
  • If you can point me to some documentation detailing that; the bounty is yours :-) – Luis Sieira Sep 19 '15 at 19:52
  • 1
    ext2/3/4 all use broadly the same approach to storing files. As Serban says, free space is a list of inodes. If a file is actually deleted. the chain of inodes that were the file, join the list of inodes that are free space. If the disk gets corrupted, such that the inodes are neither in a file, or free space, then after running fsck they will (or at least used to) appear in the lost+found folder in the root of the mounted filesystem (so /usr/lost+found if you mounted /usr or /lost+found, for the / mount point) – sibaz Sep 23 '15 at 16:29
0

I'll post my answer, but I'm not accepting it, since it doesn't seem to be by any meanings a good one (at least in terms of efficiency or completeness).

This would require a program (I'd write it in C) that recursivelly walks the entire directory tree, registers every referencied inode in an ordered list (avoiding duplicates), and then diffs it against the actual inode list.

The difference are the missing files

  • unfortunately unreferenced inode = deleted. So it comes down to undelete files. – user448115 Sep 19 '15 at 16:59
  • I knew deleting a file in use could leave orphan inodes hanging around, but I didn't know that a file was considered as deleted if it's inode was not referenced by any directory... Do you know about any documentation concerning that? – Luis Sieira Sep 19 '15 at 19:51
  • 2
    Check unlink system call manual page (man 2 unlink). Anyway - found the source of the problem. Conflict dialog sees the source as a folder and presents the option to merge, but the code responsible for performing the copy/move sees it as a file. Also merge internaly = overwrite. So by clicking merge, target folder is removed recursively (using remove_target_recursively) and the new file takes it's place. This is the case for every link to a folder. i.e. every link to folder named 'test' will overwrite any folder named 'test'. – user448115 Sep 20 '15 at 11:48
  • @adonis Can you post that as an answer so I can reward you the bounty? – Luis Sieira Sep 20 '15 at 18:51
  • 1
    There is an existing program (written in C) that recursively walks the entire filesystem, registers every referencied inode in an ordered list (avoiding duplicates), and then diffs it against the actual inode list. It's called fsck and leaves the orphaned inodes in a directory called lost+found. – Stephen M. Webb Sep 24 '15 at 10:34

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.