Gibt es eine Möglichkeit, die niedrigste und höchste Speicheradresse auszudrucken, die ein Betriebssystem in C adressieren kann?
Antworten
Zu viele Anzeigen?Nein, dies ist keine Funktion von Standard-C. Die Lösung, die Sie benötigen, muss betriebssystemspezifisch sein.
Wenn Sie ein bestimmtes Betriebssystem im Sinn haben, sollten Sie es erwähnen. Aber es fällt mir schwer, mich zu fragen, warum das wichtig sein soll. Es ist nicht erforderlich, C-Programme schreiben zu können, vielleicht können Sie uns aufklären.
Basierend auf Ihrem Kommentar:
Was mich interessiert ist: "Wenn jeder Prozess einen Adressraum im Speicher erhält, kann ich dann die obere und untere Adresse dieses Prozesses ausdrucken?"
Dies hängt wiederum vom Betriebssystem ab. Ihr Adressraum ist nicht unbedingt der physische Speicher, den Sie haben, sondern die Gesamtheit der Stellen, die Sie adressieren können. Ein auf x86 basierendes Betriebssystem kann beispielsweise jedem einzelnen Prozess einen eigenen 4G-Adressraum zuweisen, aber Sie müssen das Betriebssystem um "unterstützenden" Speicher bitten (tatsächlichen realen Speicher, den Sie in diesem Adressraum unterbringen können).
Und ein Teil dieses Adressraums wird von allen Prozessen gemeinsam genutzt (z. B. kann das Betriebssystem eine physische Kopie seines Codes zur Verwendung durch alle Prozesse laden).
Sie müssen bedenken, dass virtueller Speicher und physischer Speicher sehr unterschiedliche Dinge sind.
Unter Linux können Sie die Memory Map für jeden laufenden Prozess abfragen, indem Sie sich /proc/[PID]/maps
; siehe proc(5) . Zum Beispiel:
$ cat /proc/self/maps
08048000-0804f000 r-xp 00000000 03:01 63119 /bin/cat
0804f000-08050000 rw-p 00006000 03:01 63119 /bin/cat
08050000-08071000 rw-p 08050000 00:00 0 [heap]
b7c58000-b7e09000 r--p 00000000 03:05 243564 /usr/lib/locale/locale-archive
b7e09000-b7e0a000 rw-p b7e09000 00:00 0
b7e0a000-b7f39000 r-xp 00000000 03:01 63497 /lib/libc-2.7.so
b7f39000-b7f3a000 r--p 0012f000 03:01 63497 /lib/libc-2.7.so
b7f3a000-b7f3c000 rw-p 00130000 03:01 63497 /lib/libc-2.7.so
b7f3c000-b7f40000 rw-p b7f3c000 00:00 0
b7f5b000-b7f5c000 rw-p b7f5b000 00:00 0
b7f5c000-b7f76000 r-xp 00000000 03:01 63276 /lib/ld-2.7.so
b7f76000-b7f78000 rw-p 00019000 03:01 63276 /lib/ld-2.7.so
bfc83000-bfc98000 rw-p bffeb000 00:00 0 [stack]
ffffe000-fffff000 r-xp 00000000 00:00 0 [vdso]
Für diesen Prozess ist der letzte Eintrag in der Speicherkarte 0xfffff000, also ist das letzte adressierbare Byte 0xfffff000 - 1.
Die einfache Antwort ist, dass bei einem 32-Bit-Adressensystem (zum Beispiel) der Adressbereich wie folgt aussieht [0x00000000, 0xFFFFFFFF]
. Aber das bedeutet nicht, dass Sie tatsächlich Zugang jedes Byte innerhalb dieses Bereichs. Sie müssen wissen, wie das Betriebssystem und der Compiler den Speicher in Ihrem Programm anordnen, d.h. wo sich das statische Datensegment befindet, wo der Heap ist, wo der Stack ist, usw.
Und stellen Sie fest, dass bei jedem beliebigen Programm, das auf einem modernen Betriebssystem läuft, der größte Teil des Adressraums nicht abgebildet ist.
Beim virtuellen Speicher hat jeder Prozess seinen eigenen Adressraum, so dass das Byte an der Adresse 0x0010F444
(zum Beispiel) in einem Prozess ein völlig anderes physikalisches Byte ist als das Byte an derselben Adresse in jedem anderen Prozess.
Auf modernen Betriebssystemen mit virtuellem Speicher und Speicherschutz sind die Grenzen des Adressraums eines Prozesses nicht statisch. Wenn Sie Speicher aus dem Heap zuweisen, kann dies dazu führen, dass das Betriebssystem mehr physischen Speicher in Ihren Adressraum abbildet, so dass dieser Raum wächst.
Das Wichtigste dabei ist, dass Prozessspeicher und Betriebssystemspeicher völlig unterschiedliche Dinge sind. Wenn Sie also von "in C" sprechen, meinen Sie dann wirklich etwas anderes als den Prozessspeicherbereich?
Ich schlage vor ce könnte hilfreich sein oder Ihnen zumindest eine Orientierung geben. Eine andere Sache ist brk(2) / sbrk(2). Diese Mechanismen werden nicht so oft verwendet, wie meine Erfahrung zeigt.