5

When you run

sudo rm -rf --no-preserve-root /

Your system will delete every file, one by one. However, this also includes running processes and the operating system itself, eventually deleting rm.

How is Linux able to continue to run if program files are being deleted the operating system is missing critical files?

Additionally, how does rm continue to run if it's deleted?

Jon
  • 153
  • 2
    Deleting all the files is a far cry from formatting. running rm -rf / will delete the files in a file system, but will not delete the file system itself as would happen if you formatted it. – chriscowley Jun 17 '15 at 20:04
  • Don't the system files live on the system? If you were to delete every file, wouldn't that include system files? – Jon Jun 17 '15 at 20:04
  • 2
    filesystem != system files – pericynthion Jun 17 '15 at 20:37
  • You came from Windows. Windows sucks. Incidentally, mkfs -cFF /dev/sda1 (assuming / is /dev/sda1) has a stupendously high chance of success. – Joshua May 04 '16 at 18:45

3 Answers3

6

Despite its name, rm doesn't remove file. It actually unlinks -- removes directory entry referencing file. If there is still hard links for that file, data is kept intact.

When program is executed, Kernel keeps a kind of hard links inside (they all are treated as same inode object), so data will be kept until last process closes unlinked file.

Note how unlink system call is described:

If that name was the last link to a file and no processes have the file open the file is deleted and the space it was using is made available for reuse.

If the name was the last link to a file but any processes still have the file open the file will remain in existence until the last file descriptor referring to it is closed.

For example:

# cp /bin/sleep ./sleep
# ln ./sleep ./sleep2
# ./sleep 1000 &
[1] 24399
# rm ./sleep

At this point, data is still accessible through hardlink, and inode is still known to kernel as (task_struct)->mm->exe_file:

# ls -lh ./sleep2
-rwxr-xr-x 1 myaut users 31K Jun 17 23:10 ./sleep2
# > ls -l /proc/24399/exe 
lrwxrwxrwx 1 myaut users 0 Jun 17 23:11 /proc/24399/exe -> /tmp/test/sleep (deleted)

Even after deletion of second hardlink, data is kept (BTW, if you remove plug and your system loose power at this moment, you will get FS space leakage):

# rm ./sleep2
# ls -l /proc/24399/exe
/proc/24399/exe -> /tmp/test/sleep (deleted)

Now I kill process, and only at this moment disk (or tmpfs) space will be deallocated:

# kill 24399
myaut
  • 1,431
  • 1
    Might want to amend "if you poweroff your system at this moment" to say instead "if your system loses power at this moment" - just to clarify that it wouldn't happen with a graceful shutdown. – godlygeek Jun 17 '15 at 20:34
  • 2
    If you are familiar with memory-managed programming languages like Java, C#, JavaScript, PHP, Ruby, Python, Perl, etc., think of it this way: in Unix, you don't delete files, you remove references to them. The system will garbage collect them, when there are no more references. Having a file open is a reference, therefore open files won't be garbage collected, i.e. deleted. – Jörg W Mittag Jun 17 '15 at 20:49
  • Testing with cp /bin/sleep sleep; cp -l sleep sleep-backup; ./sleep 999 & rm sleep; stat sleep-backup shows a link count of 1, so that doesn't leak on power loss. – o11c Jun 17 '15 at 23:25
2

Almost all programs nowadays have their programs run from memory (RAM) so they don't need to access the disc once loaded. Therefore their image on disc can be deleted without a problem.

Anthon
  • 79,293
  • The entire Linux system runs off ram? – Jon Jun 17 '15 at 20:04
  • They don't run from disc directly, when you run a program, it gets first loaded into memory and run from there. If the program is finished, its memory is released (its more complex than that with caching etc). So the entire system is never in RAM at the same time, but all programs that run, those run from RAM – Anthon Jun 17 '15 at 20:06
  • 1
    This answer is almost entirely incorrect. – godlygeek Jun 17 '15 at 20:11
  • Linux is not able to keep running when things it needs are deleted, unless those things are already in memory. This answer is more or less correct except as Anthon said, it only applies to what is already in memory. Everything 'running' is already in memory. – Baazigar Jun 17 '15 at 20:13
  • @Baazigar Linux is able to keep running when things it needs are deleted, even if those things are not already in memory, as long as they're already running. Those processes can be swapped out to disk, rather than in memory, for instance, and are able to be brought back into memory later and run properly. And that will work even if the swap file has been rmd, because even after it's been rmd it hasn't been removed. See my answer or myaut's. – godlygeek Jun 17 '15 at 20:33
  • In fact, note that you can even start new processes even after every file has been rmd - an already running process could fork, even if its binary had been rmd. The forked child could read and write to any files that the parent had open, because the file handles would be inherited. – godlygeek Jun 17 '15 at 21:14
  • @godlygeek: it is true that a running process keeps an open file handle to the program image, but it's also true that the actual process' code is almost always is completely in RAM and the OS doesn't need to re-read it from disk ever again, especially in the case of a small active binary on a system which is not severely memory-restricted. Imagine running rm -rf / from a thumb drive and unplugging the drive while the command is running - it'll be able to finish even without the physical device it has been started from – Sergey Jun 17 '15 at 23:09
  • @Sergey Yes, it's true that the code of a running process is almost always completely in RAM, but it's also mostly irrelevant to the question. It's even a useful answer to a different question - why, as you note, the command could continue running even if the disk the program was on disappeared. But for this question, note that commands would continue running even if the system is severely memory restricted, and even if it's paging, and even if the page file is rmd while it's running. Things usually fit in memory, but the system would keep running through an rm -rf / even if they didn't. – godlygeek Jun 18 '15 at 17:04
2

When you rm a file, the file isn't immediately deleted. rm internally invokes the unlink() system call to complete its file-removing job, and to quote the man page for unlink() (see man 2 unlink to read it in its entirety):

   unlink()  deletes  a  name  from the filesystem. If that name was the
   last link to a file and no processes have the file open the  file  is
   deleted and the space it was using is made available for reuse.

   If  the name was the last link to a file but any processes still have
   the file open the file will remain in existence until the  last  file
   descriptor referring to it is closed.

That's the answer. If a program has a handle to a file that gets rmed, that file will still exist on the filesystem as an unnamed blob. It no longer has a path, but it still exists and is still taking up space. The program can continue reading from and writing to it. Only when all handles to that file are gone (either because the programs close the file handle or the program itself exits) do the files actually get removed from the filesystem.

godlygeek
  • 8,053