it-swarm.com.de

Finden Sie heraus, wo Inodes verwendet werden

Daher erhielt ich von unserem Überwachungssystem auf einer unserer Boxen eine Warnung, dass die Anzahl der freien Inodes in einem Dateisystem immer geringer wird.

df -i Ausgabe zeigt dies:

Filesystem       Inodes  IUsed    IFree IUse% Mounted on
/dev/xvda1       524288 422613   101675   81% /

Wie Sie sehen können, werden auf der Root-Partition 81% der Inodes verwendet.
Ich vermute, dass sie alle in einem einzigen Verzeichnis verwendet werden. Aber wie kann ich herausfinden, wo das ist?

201
Patrick

Ich habe diese Frage über Stackoverflow gesehen, aber mir hat keine der Antworten gefallen, und es ist wirklich eine Frage, die sowieso hier bei U & L sein sollte.

Grundsätzlich wird für jede Datei im Dateisystem ein Inode verwendet. Wenn Sie also keine Inodes mehr haben, liegen im Allgemeinen viele kleine Dateien herum. Die Frage lautet also wirklich: "In welchem ​​Verzeichnis befindet sich eine große Anzahl von Dateien?"

In diesem Fall ist das Dateisystem, das uns interessiert, das Root-Dateisystem /, Daher können wir den folgenden Befehl verwenden:

find / -xdev -printf '%h\n' | sort | uniq -c | sort -k 1 -n

Dadurch wird eine Liste aller Verzeichnisse im Dateisystem ausgegeben, denen die Anzahl der Dateien (und Unterverzeichnisse) in diesem Verzeichnis vorangestellt ist. Somit befindet sich das Verzeichnis mit der größten Anzahl von Dateien unten.

In meinem Fall ergibt sich Folgendes:

   1202 /usr/share/man/man1
   2714 /usr/share/man/man3
   2826 /var/lib/dpkg/info
 306588 /var/spool/postfix/maildrop

Im Grunde genommen verbraucht /var/spool/postfix/maildrop Alle Inodes.

Beachten Sie, dass diese Antwort drei Einschränkungen enthält, die mir einfallen. Mit Zeilenumbrüchen im Pfad wird nichts richtig behandelt. Ich weiß, dass mein Dateisystem keine Dateien mit Zeilenumbrüchen enthält, und da dies nur für den menschlichen Verzehr verwendet wird, lohnt es sich nicht, das potenzielle Problem zu lösen (und man kann immer \n Durch \0 Und ersetzen benutze oben sort -z). Es wird auch nicht behandelt, wenn die Dateien auf eine große Anzahl von Verzeichnissen verteilt sind. Dies ist jedoch nicht wahrscheinlich, daher halte ich das Risiko für akzeptabel. Es werden auch mehrmals feste Links zu derselben Datei gezählt (also nur ein Inode verwendet). Auch hier ist es unwahrscheinlich, dass falsch positive Ergebnisse erzielt werden


Der Hauptgrund, warum mir die Antworten auf die Stackoverflow-Antwort nicht gefallen haben, ist, dass sie alle die Grenzen des Dateisystems überschreiten. Da sich mein Problem im Root-Dateisystem befand, bedeutet dies, dass jedes einzelne gemountete Dateisystem durchlaufen wird. Das Werfen von -xdev Auf die Suchbefehle würde nicht einmal richtig funktionieren.
Die am besten bewertete Antwort lautet beispielsweise:

for i in `find . -type d `; do echo `ls -a $i | wc -l` $i; done | sort -n

Wenn wir dies stattdessen ändern zu

for i in `find . -xdev -type d `; do echo `ls -a $i | wc -l` $i; done | sort -n

obwohl /mnt/foo ein Mount ist, ist es auch ein Verzeichnis im Root-Dateisystem, sodass es in find . -mount -type d angezeigt wird und dann an ls -a $i, die in den Berg eintauchen wird.

Das find in meiner Antwort listet stattdessen das Verzeichnis jeder einzelnen Datei auf dem Mount auf. Also im Grunde mit einer Dateistruktur wie:

/foo/bar
/foo/baz
/pop/tart

wir enden mit

/foo
/foo
/pop

Wir müssen also nur die Anzahl der doppelten Zeilen zählen.

223
Patrick

Dies wird von hier auf Geheiß des Fragestellers neu gepostet:

du --inodes -S | sort -rh | sed -n \
        '1,50{/^.\{71\}/s/^\(.\{30\}\).*\(.\{37\}\)$/\1...\2/;p}'

Und wenn Sie im selben Dateisystem bleiben möchten, tun Sie Folgendes:

du --inodes -xS

Hier einige Beispielausgaben:

15K     /usr/share/man/man3
4.0K    /usr/lib
3.6K    /usr/bin
2.4K    /usr/share/man/man1
1.9K    /usr/share/fonts/75dpi
...
519     /usr/lib/python2.7/site-packages/bzrlib
516     /usr/include/KDE
498     /usr/include/qt/QtCore
487     /usr/lib/modules/3.13.6-2-MANJARO/build/include/config
484     /usr/src/linux-3.12.14-2-MANJARO/include/config

JETZT MIT LS:

Einige Leute gaben an, dass sie keine aktuellen Coreutils haben und die Option --inodes ihnen nicht zur Verfügung steht. Also, hier ist ls:

ls ~/test -AiR1U | 
sed -rn '/^[./]/{h;n;};G;
    s|^ *([0-9][0-9]*)[^0-9][^/]*([~./].*):|\1:\2|p' | 
sort -t : -uk1.1,1n |
cut -d: -f2 | sort -V |
uniq -c |sort -rn | head -n10

Wenn Sie neugierig sind, ersetzt das Herz und die Seele dieses langweiligen Teils von regex das filename in jedem von ls's rekursive Suchergebnisse mit dem Verzeichnisnamen, in dem sie gefunden wurden. Von dort aus müssen nur noch wiederholte Inode-Nummern gequetscht, dann wiederholte Verzeichnisnamen gezählt und entsprechend sortiert werden.

Das -U Option ist besonders hilfreich bei der Sortierung, da sie speziell nicht sortiert und stattdessen die Verzeichnisliste in der ursprünglichen Reihenfolge anzeigt - oder mit anderen Worten , durch inode Nummer.

Und natürlich -1 ist insofern unglaublich hilfreich, als es ein einzelnes Ergebnis pro Zeile sicherstellt, unabhängig von möglicherweise enthaltenen Zeilenumbrüchen in Dateinamen oder anderen spektakulär unglücklichen Problemen, die auftreten können, wenn Sie versuchen, eine Liste zu analysieren.

Und natürlich -A für alle und -i für Inode und -R für rekursiv und das ist das lange und kurze davon.

Die zugrunde liegende Methode dazu ist, dass ich jeden Dateinamen von ls durch den enthaltenen Verzeichnisnamen in sed ersetze. Darauf folgend ... Nun, ich bin selbst ein bisschen verschwommen. Ich bin mir ziemlich sicher, dass die Dateien genau gezählt werden, wie Sie hier sehen können:

% _ls_i ~/test
> 100 /home/mikeserv/test/realdir
>   2 /home/mikeserv/test
>   1 /home/mikeserv/test/linkdir

Dies liefert mir ziemlich identische Ergebnisse wie der Befehl du:

DU:

15K     /usr/share/man/man3
4.0K    /usr/lib
3.6K    /usr/bin
2.4K    /usr/share/man/man1
1.9K    /usr/share/fonts/75dpi
1.9K    /usr/share/fonts/100dpi
1.9K    /usr/share/doc/Arch-wiki-markdown
1.6K    /usr/share/fonts/TTF
1.6K    /usr/share/dolphin-emu/sys/GameSettings
1.6K    /usr/share/doc/efl/html

LS:

14686   /usr/share/man/man3:
4322    /usr/lib:
3653    /usr/bin:
2457    /usr/share/man/man1:
1897    /usr/share/fonts/100dpi:
1897    /usr/share/fonts/75dpi:
1890    /usr/share/doc/Arch-wiki-markdown:
1613    /usr/include:
1575    /usr/share/doc/efl/html:
1556    /usr/share/dolphin-emu/sys/GameSettings:

Ich denke, das include hängt nur davon ab, in welchem ​​Verzeichnis sich das Programm zuerst befindet - denn es sind dieselben Dateien und fest verknüpft. Ein bisschen wie die Sache oben. Ich könnte mich jedoch irren - und ich begrüße die Korrektur ...

DU DEMO

% du --version
> du (GNU coreutils) 8.22

Erstellen Sie ein Testverzeichnis:

% mkdir ~/test ; cd ~/test
% du --inodes -S
> 1       .

Einige Kinderverzeichnisse:

% mkdir ./realdir ./linkdir
% du --inodes -S
> 1       ./realdir
> 1       ./linkdir
> 1       .

Machen Sie einige Dateien:

% printf 'touch ./realdir/file%s\n' `seq 1 100` | . /dev/stdin
% du --inodes -S
> 101     ./realdir
> 1       ./linkdir
> 1       .

Einige Hardlinks:

% printf 'n="%s" ; ln ./realdir/file$n ./linkdir/link$n\n' `seq 1 100` | 
    . /dev/stdin
% du --inodes -S
> 101     ./realdir
> 1       ./linkdir
> 1       .

Schauen Sie sich die Hardlinks an:

% cd ./linkdir
% du --inodes -S
> 101

% cd ../realdir
% du --inodes -S
> 101

Sie werden alleine gezählt, aber gehen Sie ein Verzeichnis nach oben ...

% cd ..
% du --inodes -S
> 101     ./realdir
> 1       ./linkdir
> 1       .

Dann habe ich mein Skript von unten ausgeführt und:

> 100     /home/mikeserv/test/realdir
> 100     /home/mikeserv/test/linkdir
> 2       /home/mikeserv/test

Und Graemes:

> 101 ./realdir
> 101 ./linkdir
> 3 ./

Ich denke, dies zeigt, dass die einzige Möglichkeit, Inodes zu zählen, die Inode ist. Und weil das Zählen von Dateien das Zählen von Inodes bedeutet, können Sie Inodes nicht doppelt zählen - um Dateien genau zu zählen, können Inodes nicht mehr als einmal gezählt werden.

27
mikeserv

Ich habe diese Antwort von SO Q & A mit dem Titel: Wo werden alle meine Inodes verwendet? verwendet, als unser NAS ungefähr 2 Jahre abgelaufen ist vor:

$ find . -type d -print0 \
    | while IFS= read -rd '' i; do echo $(ls -a "$i" | wc -l) "$i"; done \
    | sort -n

Beispiel

$ find . -type d -print0 \
    | while IFS= read -rd '' i; do echo $(ls -a "$i" | wc -l) "$i"; done \
    | sort -n
...
110 ./MISC/nodejs/node-v0.8.12/out/Release/obj.target/v8_base/deps/v8/src
120 ./MISC/nodejs/node-v0.8.12/doc/api
123 ./apps_archive/monitoring/nagios/nagios-check_sip-1.3/usr/lib64/nagios
208 ./MISC/nodejs/node-v0.8.12/deps/openssl/openssl/doc/crypto
328 ./MISC/nodejs/node-v0.8.12/deps/v8/src
453 ./MISC/nodejs/node-v0.8.12/test/simple

Überprüfen der Inodes des Geräts

Abhängig von Ihrem NAS bietet es möglicherweise keinen voll funktionsfähigen df -Befehl. In diesen Fällen können Sie stattdessen auf tune2fs Zurückgreifen:

$ Sudo tune2fs -l /dev/sda1 |grep -i inode
Filesystem features:      has_journal ext_attr resize_inode dir_index filetype needs_recovery extent flex_bg sparse_super huge_file uninit_bg dir_nlink extra_isize
Inode count:              128016
Free inodes:              127696
Inodes per group:         2032
Inode blocks per group:   254
First inode:              11
Inode size:           128
Journal inode:            8
Journal backup:           inode blocks

Dateisystemgrenzen überschreiten

Sie können den Schalter -xdev Verwenden, um find so zu steuern, dass die Suche nur auf das Gerät beschränkt wird, auf dem Sie die Suche starten.

Beispiel

Angenommen, ich habe mein /home - Verzeichnis, das über NFS-Freigaben von meinem NAS, dessen Name mulder ist, automatisch bereitgestellt wird.

$ df -h /home/sam 
Filesystem            Size  Used Avail Use% Mounted on
mulder:/export/raid1/home/sam
                      917G  572G  299G  66% /home/sam

Beachten Sie, dass der Einhängepunkt immer noch als systemlokal betrachtet wird.

$ df -h /home/ .
Filesystem            Size  Used Avail Use% Mounted on
-                        0     0     0   -  /home
/dev/mapper/VolGroup00-LogVol00
                      222G  159G   52G  76% /

Wenn ich jetzt find initiiere:

$ find / -xdev  | grep '^/home'
/home

Es wurde /home Gefunden, aber keiner der automatisch bereitgestellten Inhalte, da sie sich auf einem anderen Gerät befinden!

Dateisystemtypen

Sie können den Schalter auf find, -fstype Verwenden, um zu steuern, welche Arten von Dateisystemen find untersucht werden.

   -fstype type
          File is on a filesystem of type type.  The valid filesystem types 
          vary among different versions of Unix; an incomplete list of 
          filesystem  types that are accepted on some version of Unix or 
          another is: ufs, 4.2, 4.3, nfs, tmp, mfs, S51K, S52K.  You can use 
          -printf with the %F directive to see the types of your
          filesystems.

Beispiel

Welche Dateisysteme habe ich?

$ find . -printf "%F\n" | sort -u
ext3

Damit können Sie die Kreuzung steuern:

nur ext3

$ find . -fstype ext3 | head -5
.
./gdcm
./gdcm/gdcm-2.0.16
./gdcm/gdcm-2.0.16/Wrapping
./gdcm/gdcm-2.0.16/Wrapping/CMakeLists.txt

nur nfs

$ find . -fstype nfs | head -5
$ 

ext3 & ext4

$ find . -fstype ext3 -o -fstype ext4 | head -5
.
./gdcm
./gdcm/gdcm-2.0.16
./gdcm/gdcm-2.0.16/Wrapping
./gdcm/gdcm-2.0.16/Wrapping/CMakeLists.txt
6
slm

Befehl zum Suchen des verwendeten Inodes:

for i in /*; do echo $i; find $i |wc -l | sort ; done
5
Ashish Karpe

Ich finde es schneller und einfacher, mit dem folgenden Befehl einen Drilldown durchzuführen:

$ Sudo du -s --inodes * | sort -rn

170202  var
157325  opt
103134  usr
53383   tmp
<snip>

Sie können dann zum Beispiel zu var gehen und sehen, was der große Inode mithilfe von Verzeichnissen dort ist.

4
JonoB

So listen Sie die detaillierte Inode-Verwendung für /, benutze den folgenden Befehl:

echo "Detailed Inode usage for: $(pwd)" ; for d in `find -maxdepth 1 -type d |cut -d\/ -f2 |grep -xv . |sort`; do c=$(find $d |wc -l) ; printf "$c\t\t- $d\n" ; done ; printf "Total: \t\t$(find $(pwd) | wc -l)\n" 
3
user108434

Auf jeden Fall mit maximaler Gegenstimme antworten, um das Konzept der Inodes unter Linux und Unix zu verstehen. Es hilft jedoch nicht wirklich, das eigentliche Problem des Löschens oder Entfernens der Inodes von der Festplatte zu lösen. Eine einfachere Möglichkeit, dies auf Ubuntu-basierten Systemen zu tun, besteht darin, unerwünschte Linux-Kernel-Header und -Bilder zu entfernen.

Sudo apt-get autoremove

Würde das für dich tun. In meinem Fall lag die Inodes-Nutzung bei 78%, aufgrund derer ich benachrichtigt wurde.

$ df -i
Filesystem     Inodes  IUsed  IFree IUse% Mounted on
/dev/xvda1     524288 407957 116331   78% /
none           957443      2 957441    1% /sys/fs/cgroup
udev           956205    388 955817    1% /dev
tmpfs          957443    320 957123    1% /run
none           957443      1 957442    1% /run/lock
none           957443      1 957442    1% /run/shm
none           957443      5 957438    1% /run/user

Nach dem Rennen Sudo apt-get autoremove Befehl war es auf 29% gesunken

$ df -i
Filesystem     Inodes  IUsed  IFree IUse% Mounted on
/dev/xvda1     524288 150472 373816   29% /
none           957443      2 957441    1% /sys/fs/cgroup
udev           956205    388 955817    1% /dev
tmpfs          957443    320 957123    1% /run
none           957443      1 957442    1% /run/lock
none           957443      1 957442    1% /run/shm
none           957443      5 957438    1% /run/user

Dies war nur meine Beobachtung, die mir Zeit sparte. Die Leute finden vielleicht eine bessere Lösung als diese.

2
Shailesh Sutar

Bei jeder bisherigen Antwort wird davon ausgegangen, dass das Problem darin besteht, dass sich viele Dateien in einem einzigen Verzeichnis befinden, anstatt dass viele Unterverzeichnisse zum Problem beitragen. Glücklicherweise besteht die Lösung darin, einfach weniger Flags zu verwenden.

# du --inodes --one-file-system /var | sort --numeric-sort
...
2265    /var/cache/salt/minion
3818    /var/lib/dpkg/info
3910    /var/lib/dpkg
4000    /var/cache/salt/master/gitfs/refs
4489    /var/lib
5709    /var/cache/salt/master/gitfs/hash
12954   /var/cache/salt/master/gitfs
225058  /var/cache/salt/master/jobs
241678  /var/cache/salt/master
243944  /var/cache/salt
244078  /var/cache
248949  /var

Oder mit kürzeren Optionen: du --inodes -x | sort -n. Leider haben nicht alle Versionen von du die Option inodes.

0
OrangeDog