Le fichier fantôme se manifeste souvent par le fait qu’il occupe 100% d’un filesystem mais on n’arrive pas à le voir. Parfois même le filesystem semble vide. En général il s’agit d’un fichier ouver par un process mais qui a été effacé du FS, par la commande rm par exemple. Ce phénomène s’explique par le fait que unix autorise de supprimer un fichier (en réalité il se contente de supprimer la référence vers ce fichier dans la structure du FS) alors que le fichier est encore utilisé par un process. Il n’est donc en pratique pas libéré physiquement.

Comment donc allons nous faire pour récupérer la place ?

Exemple:

[vincent@sauron 23:22 /u01/FS1] df -k .
Filesystem           1K-blocks      Used Available Use% Mounted on
/u01/Tests/FS1.dd         4838      4838         0 100% /u01/FS1

[vincent@sauron 23:25 /u01/FS1] sudo du -sk .
13 .

[vincent@sauron 23:22 /u01/FS1] ls -la
total 21
drwxr-xr-x 3 root root 1024 2008-11-09 23:22 .
drwxr-xr-x 12 root root 4096 2008-11-09 20:52 ..
drwx------ 2 root root 12288 2008-11-09 20:51 lost+found

La solution du débutant:

Le linuxien de base aura à peine compris l’explication ci dessus, mais suffisamment pour proposer une solution: reboot. Ca marchera, mais on aura besoin d’arrêter une machine qui pourrait être critique, et on génère une interruption de service.

L’admin système:

Il a compris qu’un process utilise le fichier, et c’est cela qui empeche le FS de libérer la place. Il faut donc tuer ce process. Le hic, comment identifier le process fautif ?

la commande lsof peut nous aider, en effet elle liste l’ensemble des fichiers ouverts d’un systeme. En outre elle a le bon goùt de marquer lorsqu’un fichier a été supprimé:
[vincent@sauron 23:34 /u01/FS1] lsof|grep deleted
critique. 28564    vincent    3w      REG    7,0 3849208      12 /u01/FS1/fichier.log (deleted)
[vincent@sauron 23:35 /u01/FS1] ps -ef | grep 28564
vincent  28564 28420  0 23:19 pts/3    00:00:00 /usr/bin/perl ./critique.pl /u01/FS1/fichier.log

On a retrouvé le fichier, un bête fichier de log. On a aussi le process fautif: critique.pl, mais comme son nom l’indique, il est critique, on ne peut donc pas le tuer immédiatement. J’ai longtemps cru qu’on était bloqué ici, mais un collègue m’a montré que non.

Le Gourou:

La solution a ce problème permet à la fois de se passer de lsof (il n’est pas disponible partout, en particulier sur les Solaris) et de répondre à la question de place, en tronquant le fichier.

L’astuce consiste à interroger directement les structures du noyau en passant par le pseudo FS /proc, chaque process y a en effet son entrée, ainsi que la liste des fichiers qu’il a ouverts. L’autre partie de l’astuce consiste à comprendre qu’un fichier effacé se caractérise par le fait d’avoir son nombre de liens à 0.

[root@sauron 23:50 ~] find -L /proc/*/fd -links 0 -ls
find: `/proc/1087/fd/3': Not a directory
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/1272/fd/14
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/25990/fd/14
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/25991/fd/14
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/25992/fd/14
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/25994/fd/14
423618    0 -rw-r--r--   0 root     root            0 Nov  8 18:20 /proc/25998/fd/14
12 3775 -rw-r--r--   0 vincent  root      3849208 Nov  9 23:02 /proc/28564/fd/3

Seul le fichier /proc/28564/fd/3 mérite notre attention a cause de sa taille. En outre on peut vérifier sa nature:

[root@sauron 23:52 ~] ls -l /proc/28564/fd/3
l-wx------ 1 vincent vincent 64 2008-11-09 23:19 /proc/28564/fd/3 -> /u01/FS1/fichier.log (deleted)

Et maintenant, grace à l’entrée dans /proc on peut le tronquer:

[root@sauron 23:52 ~] cat /dev/null > /proc/28564/fd/3
[root@sauron 23:54 ~] df -k /u01/FS1
Filesystem           1K-blocks      Used Available Use% Mounted on
/u01/Tests/FS1.dd         4838      1063      3525  24% /u01/FS1

Merci à Arnaud CORNET à qui je dois cette astuce. J’ajoute que cette astuce marche également avec /proc de solaris.