2017-07-25 3 views
8

Ich habe eine Datenstruktur, die ich nach Bedarf on-demand auslagern möchte. mmap scheint eine einfache Möglichkeit zu sein, erste Experimente durchzuführen. Allerdings möchte ich die Menge an Puffer-Cache, die mmap verwendet, begrenzen. Die Maschine verfügt über genügend Speicher, um die gesamte Datenstruktur in den Cache zu stellen, aber aus Testgründen (und auch aus produktionstechnischen Gründen) möchte ich das nicht erlauben.Limit-Puffer-Cache für mmap

Gibt es eine Möglichkeit, den von mmap verwendeten Pufferspeicher zu begrenzen?

Alternativ könnte auch eine mmap Alternative, die etwas Ähnliches erreichen und die Speicherauslastung begrenzen kann, ebenfalls funktionieren.

+2

Puffer-Cache wird vom Kernel automatisch hervorragend gepflegt. An sich wird es keine Speicherfehler verursachen. Warum willst du es selbst kontrollieren? – fukanchik

+0

@fukanchik Aufgrund meiner Umgebung muss ich genau wissen, wie viel Speicher mein Prozess verwendet, und ich beschränke mich darauf. Außerdem habe ich eine Maschine mit 100 GB Arbeitsspeicher, aber ich möchte die Software testen, als ob die Maschine nur 1 GB Arbeitsspeicher hat. – JaredC

+0

Ich denke, Ihre beste Wette ist nicht, dies in der Anwendung, sondern auf Betriebssystemebene statt. Hier ist ein guter Ausgangspunkt: https://unix.stackexchange.com/questions/44985/limit-memory-usage-for-a-single-linux-process – Frank

Antwort

3

Aus meinem Verständnis ist es nicht möglich. Die Speicherzuordnung wird vom Betriebssystem gesteuert. Der Kernel wird die Entscheidungen treffen, wie der verfügbare Speicher am besten genutzt wird, aber er betrachtet das System insgesamt. Ich bin mir nicht bewusst, dass Quoten für Caches auf Prozessebene unterstützt werden (zumindest habe ich solche APIs in Linux oder BSD nicht gesehen).

Es gibt madvise, um den Kernel Hinweise zu geben, aber es unterstützt nicht den Cache für einen Prozess zu begrenzen. Sie können ihm Hinweise wie MADV_DONTNEED geben, die den Druck auf den Cache anderer Anwendungen reduzieren, aber ich würde erwarten, dass es mehr schadet als nützt, da es höchstwahrscheinlich Caching weniger effizient macht, was zu mehr IO-Last führen wird auf dem System insgesamt.

Ich sehe nur zwei Alternativen. On versucht, das Problem auf Betriebssystemebene zu lösen, und das andere ist, es auf Anwendungsebene zu lösen.

Auf der OS-Ebene sehe ich zwei Möglichkeiten:

  1. Sie eine virtuelle Maschine laufen konnte, aber wahrscheinlich ist dies nicht das, was Sie wollen. Ich würde auch erwarten, dass es die Gesamtsystemleistung nicht verbessern wird. Dennoch wäre es zumindest eine Möglichkeit, Obergrenzen für den Speicherverbrauch festzulegen.
  2. Docker ist die andere Idee, die in den Sinn kommt, auch auf Betriebssystemebene funktioniert, aber nach meinem besten Wissen unterstützt es nicht, Quoten auf den Cache zu definieren. Ich denke nicht, dass es funktionieren wird.

Das lässt nur eine Option, die auf der Anwendungsebene zu sehen ist. Anstatt Speicherabbilddateien zu verwenden, können Sie explizite Dateisystemoperationen verwenden. Wenn Sie die volle Kontrolle über den Puffer haben müssen, denke ich, dass dies die einzige praktische Option ist. Es ist mehr Arbeit als Speicherzuordnung, und es ist auch nicht garantiert, dass die Leistung besser ist.

Wenn Sie bei der Speicherzuordnung bleiben möchten, können Sie auch nur Teile der Datei im Speicher abbilden und die Zuordnung anderer Teile aufheben, wenn Sie Ihr Speicherkontingent überschreiten. Es hat auch das gleiche Problem wie die expliziten Datei-IO-Operationen (mehr Implementierungsarbeit und nicht-triviales Tuning, um eine gute Cache-Strategie zu finden).

Wenn Sie das gesagt haben, könnten Sie die Anforderung in Frage stellen, die Cache-Speicher-Nutzung zu begrenzen. Ich würde erwarten, dass der Kernel eine ziemlich gute Arbeit bei der Zuweisung von Speicherressourcen auf eine gute Weise leistet. Zumindest wird es wahrscheinlich besser als die Lösungen, die ich skizziert habe. (Explizite Datei-E/A, plus einen internen Cache, könnte schnell sein, aber es ist nicht trivial zu implementieren und abzustimmen. Hier ist ein Vergleich der Kompromisse: mmap() vs. reading blocks.)

Während des Tests können Sie die Anwendung ausführen mit ionice -c 3 und nice -n 20, um die Auswirkungen auf die anderen produktiven Anwendungen etwas zu reduzieren. Es gibt auch ein Tool namens nocache.Ich habe es nie benutzt, aber beim Durchlesen seiner Dokumentation scheint es etwas mit deiner Frage zu tun zu haben.

0

Es könnte möglich sein, dies von mmap() durch die Verwendung zu erreichen und Linux Control Groups (allgemeinen here oder here). Nach der Installation haben Sie die Möglichkeit, willkürliche Grenzwerte für den Umfang des physischen Speichers, der von einem Prozess verwendet wird, zu erstellen. Als Beispiel hier beschränken wir den physischen Speicher auf 128 MB und Swap-Speicher auf 256 MB:

cgcreate -g memory:/limitMemory 
echo $((128 * 1024 * 1024)) > /sys/fs/cgroup/memory/limitMemory/memory.limit_in_bytes 
echo $((256 * 1024 * 1024)) > /sys/fs/cgroup/memory/limitMemory/memory.memsw.limit_in_bytes 
1

ich zu einer Zeit, die Strecke von nur Karte Teilen der Datei gehen würde, damit Sie sich auf genau die volle Kontrolle behalten können Wie viel Speicher wird verwendet?

-1

Sie können IPC Shared Memory-Segment verwenden, werden Sie der Master Ihrer Speichersegmente sein.