Je cours
ln /a/A /b/B
Je voudrais voir dans le dossier a
où le fichier A est pointé par ls
.
Je cours
ln /a/A /b/B
Je voudrais voir dans le dossier a
où le fichier A est pointé par ls
.
Vous pouvez trouver le numéro d'inode pour votre fichier avec
ls -i
et
ls -l
montre le nombre de références (nombre de liens durs vers un inode particulier)
après avoir trouvé le numéro d'inode, vous pouvez rechercher tous les fichiers avec le même inode :
find . -inum NUM
affichera les noms de fichiers pour l'inode NUM dans le répertoire actuel (.)
Il n'y a pas vraiment de réponse bien définie à votre question. Contrairement aux liens symboliques, les liens durs sont indiscernables du "fichier original".
Les entrées du répertoire sont constituées d'un nom de fichier et d'un pointeur vers un inode. L'inode contient à son tour les métadonnées du fichier et (des pointeurs vers) le contenu réel du fichier). La création d'un lien dur crée une autre entrée de répertoire qui fait référence au même inode. Ces références sont unidirectionnelles (dans les systèmes de fichiers typiques, du moins) -- l'inode ne conserve qu'un compte de références. Il n'y a aucun moyen intrinsèque de savoir quel est le nom de fichier "original".
D'ailleurs, c'est pourquoi l'appel système pour "supprimer" un fichier s'appelle unlink
. Il enlève juste un lien dur. L'inode et les données attachées sont supprimés seulement si le nombre de références de l'inode tombe à 0.
La seule façon de trouver les autres références à un inode donné est d'effectuer une recherche exhaustive dans le système de fichiers en vérifiant quels fichiers font référence à l'inode en question. Vous pouvez utiliser 'test A -ef B' à partir du Shell pour effectuer cette vérification.
UNIX a des liens durs et des liens symboliques (faits avec "ln"
y "ln -s"
respectivement). Les liens symboliques sont simplement un fichier qui contient le chemin réel vers un autre fichier et peuvent traverser les systèmes de fichiers.
Les liens durs existent depuis les premiers jours d'UNIX (pour autant que je m'en souvienne, et cela remonte à un certain temps). Il s'agit de deux entrées de répertoire qui font référence au exact mêmes données sous-jacentes. Les données d'un fichier sont spécifiées par son inode
. Chaque fichier d'un système de fichiers pointe vers un inode mais il n'est pas nécessaire que chaque fichier pointe vers un inode unique - c'est de là que viennent les liens durs.
Puisque les inodes ne sont uniques que pour un système de fichiers donné, il y a une limitation que les liens durs doivent être sur le même système de fichiers (contrairement aux liens symboliques). Notez que, contrairement aux liens symboliques, il n'y a pas de fichier privilégié - ils sont tous égaux. La zone de données ne sera libérée que lorsque todo les fichiers utilisant cet inode sont supprimés (et tous les processus le ferment également, mais c'est un autre problème).
Vous pouvez utiliser le "ls -i"
pour obtenir l'inode d'un fichier particulier. Vous pouvez ensuite utiliser la commande "find <filesystemroot> -inum <inode>"
pour trouver tous les fichiers sur le système de fichiers avec cet inode donné.
Voici un script qui fait exactement cela. Vous l'invoquez avec :
findhardlinks ~/jquery.js
et il trouvera tous les fichiers sur ce système de fichiers qui sont des liens directs pour ce fichier :
pax@daemonspawn:~# ./findhardlinks /home/pax/jquery.js
Processing '/home/pax/jquery.js'
'/home/pax/jquery.js' has inode 5211995 on mount point '/'
/home/common/jquery-1.2.6.min.js
/home/pax/jquery.js
Voici le script.
#!/bin/bash
if [[ $# -lt 1 ]] ; then
echo "Usage: findhardlinks <fileOrDirToFindFor> ..."
exit 1
fi
while [[ $# -ge 1 ]] ; do
echo "Processing '$1'"
if [[ ! -r "$1" ]] ; then
echo " '$1' is not accessible"
else
numlinks=$(ls -ld "$1" | awk '{print $2}')
inode=$(ls -id "$1" | awk '{print $1}' | head -1l)
device=$(df "$1" | tail -1l | awk '{print $6}')
echo " '$1' has inode ${inode} on mount point '${device}'"
find ${device} -inum ${inode} 2>/dev/null | sed 's/^/ /'
fi
shift
done
ls -l
La première colonne représentera les permissions. La deuxième colonne sera le nombre de sous-éléments (pour les répertoires) ou le nombre de chemins d'accès aux mêmes données (liens durs, y compris le fichier original) vers le fichier. Ex :
-rw-r--r--@ 2 [username] [group] [timestamp] HardLink
-rw-r--r--@ 2 [username] [group] [timestamp] Original
^ Number of hard links to the data
Que pensez-vous du modèle plus simple suivant ? (Ce dernier pourrait remplacer le long scripts ci-dessus !)
Si vous avez un fichier spécifique <THEFILENAME>
et que vous voulez connaître tous ses hardlinks répartis dans le répertoire <TARGETDIR>
(qui peut même être le système de fichiers entier noté par /
)
find <TARGETDIR> -type f -samefile <THEFILENAME>
En prolongeant la logique, si vous voulez connaître tous les fichiers de l'application <SOURCEDIR>
avoir plusieurs liens durs répartis sur <TARGETDIR>
:
find <SOURCEDIR> -type f -links +1 \
-printf "\n\n %n HardLinks of file : %H/%f \n" \
-exec find <TARGETDIR> -type f -samefile {} \;
SystemesEZ est une communauté de sysadmins où vous pouvez résoudre vos problèmes et vos doutes. Vous pouvez consulter les questions des autres sysadmins, poser vos propres questions ou résoudre celles des autres.