Was passiert , wenn ich schreibe cat /proc/cpuinfo
. Ist das eine Named Pipe (oder etwas anderes) zum Betriebssystem, die die CPU-Informationen im laufenden Betrieb liest und diesen Text jedes Mal generiert, wenn ich ihn aufrufe?
Was passiert , wenn ich schreibe cat /proc/cpuinfo
. Ist das eine Named Pipe (oder etwas anderes) zum Betriebssystem, die die CPU-Informationen im laufenden Betrieb liest und diesen Text jedes Mal generiert, wenn ich ihn aufrufe?
Antworten:
Wann immer Sie eine Datei lesen, wird ein /proc
Code im Kernel aufgerufen, der den zu lesenden Text als Dateiinhalt berechnet. Die Tatsache, dass der Inhalt im Handumdrehen generiert wird, erklärt, warum für fast alle Dateien die aktuelle Zeit und die Größe 0 angegeben wurde. Hier sollte 0 als „Weiß nicht“ angegeben werden. Im Gegensatz zu gewöhnlichen Dateisystemen lädt das Dateisystem /proc
, das als procfs bezeichnet wird , keine Daten von einer Festplatte oder einem anderen Speichermedium (wie FAT, ext2, zfs,…) oder über das Netzwerk (wie NFS, Samba,…). und ruft keinen Benutzercode auf (im Gegensatz zu FUSE ).
Procfs ist in den meisten Nicht-BSD-Unices vorhanden. Es wurde in den Bell Labs von AT & T in UNIX 8 eingeführt , um Informationen zu Prozessen zu melden (und ps
ist häufig ein sehr nützlicher Drucker, um Informationen durchzulesen /proc
). Die meisten procfs-Implementierungen haben eine Datei oder ein Verzeichnis, die bzw. das aufgerufen wird /proc/123
, um Informationen über den Prozess mit PID 123 zu melden. Linux erweitert das proc-Dateisystem um viele weitere Einträge, die den Status des Systems melden, einschließlich Ihres Beispiels /proc/cpuinfo
.
In der Vergangenheit hat Linux /proc
verschiedene Dateien erworben, die Informationen zu Treibern enthalten. Diese Verwendung wird jetzt jedoch nicht mehr empfohlen /sys
und /proc
entwickelt sich nur langsam. Einträge mögen /proc/bus
und /proc/fs/ext4
bleiben dort, wo sie aus Gründen der Abwärtskompatibilität sind, aber neuere ähnliche Schnittstellen werden unter erstellt /sys
. In dieser Antwort werde ich mich auf Linux konzentrieren.
Ihr erster und zweiter Einstiegspunkt für die Dokumentation /proc
zu Linux sind:
proc(5)
Manpage ;/proc
Dateisystem in der Kerneldokumentation .Ihr dritter Einstiegspunkt, wenn die Dokumentation dies nicht behandelt, ist das Lesen der Quelle . Sie können den Quellcode auf Ihren Computer herunterladen, aber dies ist ein riesiges Programm, und LXR , der Linux-Querverweis, ist eine große Hilfe. (Es gibt viele LXR-Varianten; die lxr.linux.no
mit Abstand beste, aber leider ist die Site häufig nicht erreichbar.) Ein wenig C-Kenntnisse sind erforderlich, aber Sie müssen kein Programmierer sein, um einen mysteriösen Wert aufzuspüren .
Die Kernbehandlung von /proc
Einträgen befindet sich im fs/proc
Verzeichnis. Jeder Fahrer kann Einträge in registrieren /proc
(obwohl dies, wie oben angegeben, jetzt zugunsten von veraltet ist /sys
). Wenn Sie also nicht das finden, wonach Sie suchen fs/proc
, suchen Sie überall anders. Treiber rufen Funktionen auf, die in deklariert sind include/linux/proc_fs.h
. Kernel-Versionen bis 3.9 bieten die Funktionen create_proc_entry
und einige Wrapper (insbesondere create_proc_read_entry
), und Kernel-Versionen 3.10 und höher bieten stattdessen nur proc_create
und proc_create_data
(und einige mehr).
Am /proc/cpuinfo
Beispiel einer Suche nach "cpuinfo"
führt Sie der Aufruf zu proc_create("cpuinfo, …")
in fs/proc/cpuinfo.c
. Sie können sehen, dass es sich bei dem Code so ziemlich um Boilerplate-Code handelt: Da die meisten Dateien /proc
nur Textdaten ausgeben, gibt es dafür Hilfsfunktionen. Es gibt nur eine seq_operations
Struktur, und das eigentliche Fleisch befindet sich in der cpuinfo_op
Datenstruktur, die architekturabhängig ist und normalerweise in arch/<architecture>/kernel/setup.c
(oder manchmal in einer anderen Datei) definiert wird. Am Beispiel von x86 werden wir dazu geführt arch/x86/kernel/cpu/proc.c
. Dort ist die Hauptfunktionshow_cpuinfo
, der den gewünschten Dateiinhalt druckt; Der Rest der Infrastruktur ist dazu da, die Daten mit der von ihr angeforderten Geschwindigkeit an den Leseprozess weiterzuleiten. Sie können die Daten, die im laufenden Betrieb zusammengestellt werden, anhand von Daten in verschiedenen Variablen im Kernel sehen, einschließlich einiger Zahlen, die im laufenden Betrieb berechnet werden, z. B. der CPU-Frequenz .
Ein großer Teil davon /proc
sind die prozessbezogenen Informationen in /proc/<PID>
. Diese Einträge sind fs/proc/base.c
in dem tgid_base_stuff
Array registriert . Einige hier registrierte Funktionen sind in anderen Dateien definiert. Schauen wir uns ein paar Beispiele an, wie diese Einträge generiert werden:
cmdline
wird von proc_pid_cmdline
in derselben Datei generiert . Es findet die Daten im Prozess und druckt sie aus.clear_refs
Im Gegensatz zu den Einträgen, die wir bisher gesehen haben, ist es beschreibbar, aber nicht lesbar. Daher proc_clear_refs_operations
definieren die Strukturen eine clear_refs_write
Funktion, jedoch keine Lesefunktion.cwd
ist ein symbolischer Link (ein leicht magischer), der durch deklariert wird proc_cwd_link
und der das aktuelle Verzeichnis des Prozesses nachschlägt und es als Linkinhalt zurückgibt.fd
ist ein Unterverzeichnis. Die Operationen für das Verzeichnis selbst werden in der proc_fd_operations
Datenstruktur definiert (sie sind mit Ausnahme der Funktion, die die Einträge auflistetproc_readfd
, die die geöffneten Dateien des Prozesses auflistet ), während Operationen für die Einträge in proc_fd_inode_operations enthalten sind .Ein weiterer wichtiger Bereich von /proc
ist /proc/sys
, das eine direkte Schnittstelle zu ist sysctl
. Das Lesen von einem Eintrag in dieser Hierarchie gibt den Wert des entsprechenden Sysctl-Werts zurück, und das Schreiben legt den Sysctl-Wert fest. Die Einstiegspunkte für sysctl befinden sich in fs/proc/proc_sysctl.c
. Sysctls haben ein eigenes Registrierungssystem mit register_sysctl
und mit Freunden.
Wenn Sie versuchen, einen Einblick zu gewinnen, welche Art von Magie sich hinter den Kulissen abspielt, ist Ihr bester Freund strace
. Das Erlernen der Bedienung dieses Tools ist eines der besten Dinge, die Sie tun können, um besser zu verstehen, was verrückte Magie hinter den Kulissen vor sich geht.
$ strace -s 200 -m strace.log cat /proc/cpuinfo
...
read(3, "processor\t: 0\nvendor_id\t: GenuineIntel\ncpu family\t: 6\nmodel\t\t: 37\nmodel name\t: Intel(R) Core(TM) i5 CPU M 560 @ 2.67GHz\nstepping\t: 5\nmicrocode\t: 0x4\ncpu MHz\t\t: 1199.000\ncache size\t: 3072 KB\nphy"..., 65536) = 3464
write(1, "processor\t: 0\nvendor_id\t: GenuineIntel\ncpu family\t: 6\nmodel\t\t: 37\nmodel name\t: Intel(R) Core(TM) i5 CPU M 560 @ 2.67GHz\nstepping\t: 5\nmicrocode\t: 0x4\ncpu MHz\t\t: 1199.000\ncache size\t: 3072 KB\nphy"..., 3464) = 3464
read(3, "", 65536) = 0
close(3) = 0
...
An der obigen Ausgabe können Sie erkennen, dass /proc/cpuinfo
es sich nur um eine reguläre Datei handelt oder zumindest eine solche zu sein scheint. Also lasst uns tiefer graben.
Betrachtet man die Datei selbst, scheint es sich um "nur eine Datei" zu handeln.
$ ls -l /proc/cpuinfo
-r--r--r--. 1 root root 0 Mar 26 22:45 /proc/cpuinfo
Aber schauen Sie genauer hin. Wir bekommen unseren ersten Hinweis, dass es etwas Besonderes ist, beachten Sie, dass die Größe der Datei 0 Bytes beträgt.
# 2 - mit stat ..Wenn wir uns nun die Datei mit ansehen, können stat
wir unseren nächsten Hinweis erhalten, dass etwas Besonderes daran liegt /proc/cpuinfo
.
$ stat /proc/cpuinfo
File: ‘/proc/cpuinfo’
Size: 0 Blocks: 0 IO Block: 1024 regular empty file
Device: 3h/3dInode: 4026532023 Links: 1
Access: (0444/-r--r--r--) Uid: ( 0/ root) Gid: ( 0/ root)
Context: system_u:object_r:proc_t:s0
Access: 2014-03-26 22:46:18.390753719 -0400
Modify: 2014-03-26 22:46:18.390753719 -0400
Change: 2014-03-26 22:46:18.390753719 -0400
Birth: -
Lauf Nr. 2
$ stat /proc/cpuinfo
File: ‘/proc/cpuinfo’
Size: 0 Blocks: 0 IO Block: 1024 regular empty file
Device: 3h/3dInode: 4026532023 Links: 1
Access: (0444/-r--r--r--) Uid: ( 0/ root) Gid: ( 0/ root)
Context: system_u:object_r:proc_t:s0
Access: 2014-03-26 22:46:19.945753704 -0400
Modify: 2014-03-26 22:46:19.945753704 -0400
Change: 2014-03-26 22:46:19.945753704 -0400
Birth: -
Beachten Sie die Zugriffs-, Änderungs- und Änderungszeiten? Sie ändern sich bei jedem Zugriff. Das ist höchst ungewöhnlich, dass sich alle 3 so ändern würden. Die Zeitstempelattribute einer Datei bleiben in der Regel unverändert, es sei denn, sie wurden bearbeitet.
# 3 - mit Datei ..Noch ein Hinweis darauf, dass diese Datei alles andere als eine reguläre Datei ist:
$ file /proc/cpuinfo
/proc/cpuinfo: empty
Wenn es sich um eine Manifestation einer Named Pipe handeln würde, würde sie ähnlich einer der folgenden Dateien angezeigt:
$ ls -l /dev/initctl /dev/zero
prw-------. 1 root root 0 Mar 26 20:09 /dev/initctl
crw-rw-rw-. 1 root root 1, 5 Mar 27 00:39 /dev/zero
$ file /dev/initctl /dev/zero
/dev/initctl: fifo (named pipe)
/dev/zero: character special
Wenn wir eine berühren emptyfile
, /proc/cpuinfo
scheint dies eher eine Datei als eine Pipe zu sein:
$ touch emptyfile
$ ls -l emptyfile
-rw-rw-r--. 1 saml saml 0 Mar 27 07:40 emptyfile
$ file emptyfile
emptyfile: empty
# 4 - mit Montierung ..
An diesem Punkt müssen wir also einen Schritt zurücktreten und etwas herauszoomen. Wir schauen uns eine bestimmte Datei an, aber vielleicht sollten wir uns das Dateisystem ansehen, in dem sich diese Datei befindet. Und dafür können wir den mount
Befehl verwenden.
$ mount | grep " /proc "
proc on /proc type proc (rw,nosuid,nodev,noexec,relatime)
OK, der Dateisystemtyp ist also vom Typ proc
. Es handelt sich also /proc
um einen anderen Dateisystemtyp, das ist unser Hinweis darauf, dass die Dateien darunter etwas /proc
Besonderes sind. Sie sind nicht nur Ihre Lieblingsdateien. Informieren wir uns über die proc
Besonderheiten des Dateisystems.
Schauen Sie sich die mount
Manpage von an:
Das proc-Dateisystem ist keinem speziellen Gerät zugeordnet, und beim Mounten kann anstelle einer Gerätespezifikation ein beliebiges Schlüsselwort wie proc verwendet werden. (Die übliche Wahl none ist weniger glücklich: Die Fehlermeldung none busy von umount kann verwirrend sein.)
Und wenn wir uns die proc
Manpage anschauen :
Das proc-Dateisystem ist ein Pseudodateisystem, das als Schnittstelle zu Kerneldatenstrukturen verwendet wird. Es wird üblicherweise bei / proc montiert. Das meiste davon ist schreibgeschützt, aber in einigen Dateien können Kernelvariablen geändert werden.
Ein bisschen weiter unten in derselben Manpage:
/ proc / cpuinfo
Dies ist eine Sammlung von Elementen, die von der CPU und der Systemarchitektur abhängen. Für jede unterstützte Architektur wird eine andere Liste erstellt. Zwei gebräuchliche Einträge sind Prozessor, der die CPU-Nummer und die Bogomips angibt. Eine Systemkonstante, die während der Kernel-Initialisierung berechnet wird. SMP-Maschinen verfügen über Informationen für jede CPU. Der Befehl lscpu (1) sammelt seine Informationen aus dieser Datei.
Am Ende der Manpage befindet sich ein Verweis auf ein Kerneldokument, das Sie hier mit dem Titel: THE / proc FILESYSTEM finden . Zitat aus diesem Dokument:
Das proc-Dateisystem fungiert als Schnittstelle zu internen Datenstrukturen im Kernel. Es kann verwendet werden, um Informationen über das System zu erhalten und bestimmte Kernelparameter zur Laufzeit zu ändern (sysctl).
Also, was haben wir hier gelernt? Nun /proc
, da dies als Pseudo-Dateisystem und auch als "Schnittstelle zu internen Datenstrukturen" bezeichnet wird, ist es wahrscheinlich sicher anzunehmen, dass die darin enthaltenen Elemente keine tatsächlichen Dateien sind, sondern nur Manifestationen, die wie Dateien aussehen, aber nicht wirklich sind.
Ich werde mit diesem Zitat schließen, das anscheinend in einer früheren Version des man 5 proc
von circa 2004 war, aber aus welchem Grund auch immer nicht mehr enthalten ist. HINWEIS: Ich bin nicht sicher, warum es entfernt wurde, da es sehr gut beschreibt, was /proc
ist:
Das Verzeichnis / proc auf GNU / Linux-Systemen bietet eine dateisystemähnliche Schnittstelle zum Kernel. Auf diese Weise können Anwendungen und Benutzer Informationen aus dem Kernel abrufen und Werte im normalen Dateisystem-E / A-Betrieb festlegen.
Das proc-Dateisystem wird manchmal als Prozessinformations-Pseudodateisystem bezeichnet. Es enthält keine echten Dateien, sondern Informationen zum Laufzeitsystem (z. B. Systemspeicher, gemountete Geräte, Hardwarekonfiguration usw.). Aus diesem Grund kann es als Kontroll- und Informationszentrum für den Kernel angesehen werden. Tatsächlich sind viele Systemdienstprogramme lediglich Aufrufe von Dateien in diesem Verzeichnis. Beispielsweise ist der Befehl lsmod, der die vom Kernel geladenen Module auflistet, im Grunde derselbe wie 'cat / proc / modules', während lspci, der an den PCI-Bus des Systems angeschlossene Geräte auflistet, derselbe ist wie 'cat / proc / pci '. Durch Ändern der Dateien in diesem Verzeichnis können Sie die Kernelparameter ändern, während das System ausgeführt wird.
Quelle: Das proc Pseudo-Dateisystem
strace -o catcpuproc.txt cat /proc/cpuinfo
Die Antwort von @slm ist sehr umfassend, aber ich denke, eine einfachere Erklärung könnte aus einem Perspektivwechsel resultieren.
Im täglichen Gebrauch können wir uns Dateien als physische Dinge vorstellen, z. Datenblöcke, die auf einem Gerät gespeichert sind. Dies macht Dateien wie / proc / cpuinfo sehr mysteriös und verwirrend. Es macht jedoch alles Sinn, wenn wir uns Dateien als Schnittstelle vorstellen. eine Möglichkeit, Daten in ein Programm hinein und aus einem Programm heraus zu senden.
Die Programme, die Daten auf diese Weise senden und empfangen, sind Dateisysteme oder Treiber (je nachdem, wie Sie diese Begriffe definieren, ist eine Definition möglicherweise zu weit oder zu eng). Der wichtige Punkt ist, dass einige dieser Programme ein Hardwaregerät verwenden, um die über diese Schnittstelle gesendeten Daten zu speichern und abzurufen. aber nicht alles.
Einige Beispiele für Dateisysteme, die (zumindest direkt) kein Speichergerät verwenden, sind:
Das Plan9-Betriebssystem ( http://en.wikipedia.org/wiki/Plan_9_from_Bell_Labs ) ist ein extremes Beispiel für die Verwendung von Dateien als allgemeine Programmierschnittstelle.