Wie man die CPU- und RAM-Auslastung eines Prozesses mit Cgroups unter Ubuntu begrenzt

Unter Ubuntu ist die sicherste Methode, die Arbeitslast mithilfe von Cgroups zu begrenzen, die Erstellung und Verwaltung der Kontrollgruppe durch systemd zu überlassen. Verwenden Sie diese Methode systemd-runfür einen Befehl, den Sie gerade starten, oder konfigurieren Sie einen systemd-Dienst, wenn die Begrenzung auch nach Neustarts erhalten bleiben soll. Legen Sie CPUQuota=eine feste Obergrenze für die CPU-Zeit fest und wählen Sie zwischen einer MemoryHigh=Begrenzung für die Auslastung und MemoryMax=einer festen Speicherbegrenzung. Diese Grenzwerte gelten für die Unit und ihre Kindprozesse gemeinsam.

Eine Cgroup (Kontrollgruppe) ist ein Mechanismus des Linux-Kernels, der Prozesse so organisiert, dass das System deren Ressourcennutzung erfassen und steuern kann. Ubuntus systemd ordnet Dienste bereits Cgroups zu, sodass die meisten Benutzer keine Verzeichnisse manuell erstellen müssen /sys/fs/cgroup. Die folgenden Beispiele verwenden die Ressourcenkontrollschnittstelle von systemd und sollten mit der auf Ihrer Ubuntu-Version installierten systemd-Version verglichen werden.

Ein Terminal-Mockup im Ubuntu-Stil, das die systemd-Version und den Mount-Typ cgroup2fs überprüft, bevor Ressourcenlimits festgelegt werden.
Beispielhafte Terminal-Umgebung zur Überprüfung von systemd und der cgroup v2-Einbindung. Die angezeigte Version und Ausgabe dienen als Beispiele und stellen kein Testergebnis dar.

Wählen Sie das Steuerelement, das zum Problem passt.

VerfahrenWas es kontrolliertOptimale PassformHauptkompromisse
systemd-runvorübergehender BereichCPU-Kontingent und Speichergrenzen für einen neu gestarteten Befehl und seine NachfolgerEin Build-, Skript-, Import- oder einmaliger Batch-JobDer Geltungsbereich ist temporär und endet mit der Arbeitslast; er bindet sich nicht an einen beliebigen, bereits laufenden Prozess an.
systemd-DiensteinstellungenRessourcen für die Cgroup des Dienstes, einschließlich untergeordneter ProzesseEin Daemon oder eine Anwendung, die nach einem Neustart die gleichen Grenzwerte beibehalten soll.Erfordert eine Servicekonfiguration und in der Regel einen Neustart, um die neuen Einstellungen anzuwenden.
Direkte cgroup v2-DateienKernel-Controller wie cpu.maxz. B.memory.maxContainer-Laufzeitumgebungen, delegierte Cgroup-Manager oder spezialisierte AdministrationMehr manuelle Vorgehensweise; systemd kontrolliert einen Großteil der Ubuntu-Hierarchie, und das Schreiben in seinen verwalteten Baum kann mit systemd in Konflikt geraten oder aufgrund von Berechtigungen und Delegierung fehlschlagen.
niceoderCPUWeight=Relative CPU-Priorität bei GruppenwettbewerbHintergrundprozesse mit niedrigerer Priorität bearbeiten, ihnen aber gleichzeitig die Nutzung ungenutzter CPU-Leistung ermöglichen.Dies ist keine feste CPU-Begrenzung und der Arbeitsspeicher ist nicht eingeschränkt.

Für die meisten interaktiven Ubuntu-Systeme ist ein temporärer Gültigkeitsbereich die schnellste reversible Option. Verwenden Sie für einen Produktionsdienst die Service-Unit, damit die Richtlinie dokumentiert und beim Systemstart wiederhergestellt wird. Verwenden Sie direkte Cgroup-Dateien nur dann, wenn Sie bewusst eine delegierte Hierarchie verwalten oder einen Container-/Laufzeit-Workflow erstellen.

Überprüfen Sie das Ubuntu-System, bevor Sie Grenzwerte festlegen.

Prüfen Sie zunächst, ob systemd verfügbar ist und ob das cgroup-Dateisystem unified v2 ist:

systemctl --version
stat -fc %T /sys/fs/cgroup

Das Ergebnis cgroup2fsdes zweiten Befehls zeigt das einheitliche cgroup-v2-Dateisystem an. Ubuntu-Versionen und angepasste Systeme können sich unterscheiden. Gehen Sie daher nicht davon aus, dass jede Maschine dieselbe Hierarchie oder dieselben systemd-Funktionen aufweist. Mit dem ersten Befehl können Sie die aktuelle systemd-Version überprüfen. Wenn die cgroup-Einbindung nicht v2 ist, können einige Ressourceneigenschaften oder das Verhalten des Controllers abweichen. Konsultieren Sie die Ubuntu-Handbuchseite für die installierte Version, bevor Sie eine Konfiguration kopieren.

Wählen Sie die Werte erst nach der Messung der Arbeitslast. Lassen Sie ausreichend Spielraum für das restliche System und beachten Sie, dass die für einen Benutzerdienst festgelegten Grenzwerte auch durch die Grenzwerte seines übergeordneten Slices beschränkt sind. Eine untergeordnete Cgroup kann nicht mehr Ressourcen erhalten, als ihr übergeordneter Slice zulässt.

Beschränken Sie einen Befehl, den Sie gleich starten werden

Um einen Befehl in Ihrer eigenen Benutzersitzung auszuführen, starten Sie ihn in einem temporären Gültigkeitsbereich mit systemd-run --user --scope. Zum Beispiel:

Ein Terminal-Mockup im Ubuntu-Stil, das einen Python-Worker mit einer CPU-Auslastung von 50 Prozent und Speicherschwellen von 700 MB und 900 MB startet.
Beispielhafte Terminaldarstellung eines einmaligen systemd-run-Befehls mit CPU-Kontingent, Speicherauslastungsschwelle und fester Speicherobergrenze.
systemd-run --user --scope --unit=worker-capped \
  -p CPUQuota=50% \
  -p MemoryHigh=700M \
  -p MemoryMax=900M \
  -- python3 /opt/worker.py

Ersetzen Sie den Python-Befehl durch das Programm, das Sie tatsächlich ausführen möchten. Dieses Beispiel weist der Cgroup eine maximale CPU-Bandbreite entsprechend der Hälfte einer CPU zu, beginnt die Speicherdruckbehandlung bei etwa 700 MiB und legt ein maximales Speicherlimit von 900 MiB fest. Die Speicherwerte basieren auf systemd-Einheiten (Basis 1024). Ein Kontingent von 0 MiB 100%entspricht der Rechenzeit einer CPU; 200%bei Verfügbarkeit kann die Rechenzeit von bis zu zwei CPUs genutzt werden. Es stellt keinen Prozentsatz aller Kerne des Computers dar.

Der Befehl wird im Vordergrund ausgeführt, da es sich um einen Gültigkeitsbereich handelt. Nach Beendigung des Befehls wird die temporäre Einheit entfernt. Entfernen Sie sie --usernur, wenn Sie den Systemmanager verwenden und über die erforderlichen Berechtigungen verfügen. Für eine systemweite temporäre Einheit führen Sie den Befehl mit sudoden entsprechenden Befehlsoptionen aus. Ressourceneinstellungen werden möglicherweise abgelehnt, wenn der Manager oder der Cgroup-Controller diese nicht unterstützt.

Legen Sie Grenzen für einen persistenten systemd-Dienst fest

Für einen Dienst wie diesen worker.serviceerstellen Sie eine Drop-in-Datei, anstatt die Lieferanteneinheitsdatei zu bearbeiten. Führen Sie den Befehl aus sudo systemctl edit worker.serviceund fügen Sie Folgendes hinzu:

Ein Konfigurationsmodell für einen systemd-Dienst, das die Einstellungen CPUQuota, MemoryHigh und MemoryMax enthält.
Beispielhafte systemd-Dienstkonfiguration mit persistenter CPU- und Speichersteuerung. Verwenden Sie den tatsächlichen Dienstnamen und die für Ihre Arbeitslast passenden Werte.
[Service]
CPUQuota=50%
MemoryHigh=700M
MemoryMax=900M

Speichern Sie das Drop-in, laden Sie anschließend die Unit-Definitionen von systemd neu und starten Sie den Dienst neu, damit der Prozess gemäß der geänderten Richtlinie gestartet wird:

sudo systemctl daemon-reload
sudo systemctl restart worker.service

Setzen Sie eine vorsichtige Speicherobergrenze. Kann der Dienst nicht genügend Speicher unterhalb dieser Grenze freigeben MemoryMax, kann der Kernel den Speicherkiller innerhalb der entsprechenden Cgroup aufrufen. Dies kann einen oder mehrere Prozesse in der Dienstgruppe beenden und die Arbeit unterbrechen. Ein sichereres Vorgehen ist oft, die Speicherobergrenze zunächst MemoryHighauf einen Wert festzulegen, bei dem Speicherfreigabe und Drosselung akzeptabel sind, und sie dann MemoryMaxals endgültige Grenze höher zu setzen. Testen Sie unter realistischen Spitzenlasten, bevor Sie strenge Obergrenzen festlegen.

Überprüfen Sie das Gerät und beobachten Sie sein Verhalten.

Überprüfen Sie für den transienten Bereich dessen Status anhand des von Ihnen angegebenen Gerätenamens:

Ein Terminal-Mockup, das den Status von systemctl und die Überwachung eines vorübergehenden Arbeitslastbereichs durch systemd-cgtop anzeigt.
Beispielhafte Status- und Cgroup-Monitoransicht. Die hier gezeigten Beispielwerte für CPU und Speicher stammen nicht aus einem realen Testlauf.
systemctl --user status worker-capped.scope
systemd-cgtop

Bei einem Systemdienst lassen Sie --userden Parameter im Statusbefehl weg. Die Statusansicht bestätigt, dass die Einheit existiert und aktiv ist; systemd-cgtopsie zeigt die aktuelle Ressourcennutzung durch die Steuerungsgruppe an. Um konfigurierte Eigenschaften zu überprüfen, fragen Sie die Einheit direkt ab, zum Beispiel:

systemctl --user show worker-capped.scope \
  -p CPUQuotaPerSecUSec -p MemoryHigh -p MemoryMax

Der für eine Cgroup gemeldete Speicherverbrauch entspricht nicht unbedingt dem residenten Speicherverbrauch eines einzelnen Prozesses: Er umfasst den der Gruppe zugewiesenen Speicher und kann auch die Nachkommen der Workload einschließen. Betrachten Sie die Überwachung als Indikator für das Verhalten dieser Workload im Zeitverlauf und nicht als einzelne Kennzahl, die blind optimiert werden soll.

Was passiert, wenn der Prozess bereits läuft?

systemd-runEs wird ein neuer Befehl in einer neuen Unit gestartet; dabei wird keine beliebige bestehende Prozess-ID (PID) verwendet, um sie in diesen Gültigkeitsbereich zu verschieben. Gehört der Prozess zu einem systemd-Dienst, werden die Einstellungen diesem Dienst per Drop-in zugewiesen oder, für eine temporäre Änderung, mit der entsprechenden Methode sudo systemctl set-property --runtime worker.service CPUQuota=50% MemoryHigh=700M MemoryMax=900M. Die --runtimeForm ist temporär und ersetzt keine dauerhafte Dienstkonfiguration.

Handelt es sich bei dem Prozess um ein reguläres Programm in Ihrer Desktop-Sitzung, ist die sicherste und einfachste Methode in der Regel, ihn zu beenden und unter einem anderen System neu zu starten systemd-run. Die Anwendung einer Eigenschaft auf einen größeren Bereich, beispielsweise Ihren gesamten Benutzerbereich, kann viele unabhängige Anwendungen beeinträchtigen. Das Verschieben eines Prozesses durch Schreiben seiner Prozess-ID (PID) in eine Cgroup-Datei erfordert die Kontrolle über die entsprechende delegierte Hierarchie und muss die Regeln für die Prozessplatzierung von Cgroup v2 beachten; schreiben Sie nicht einfach nach Gefühl in von Systemd verwaltete Verzeichnisse.

Wie man eine CPU- und Speicherstrategie auswählt

  • Benötigen Sie eine feste CPU-Obergrenze? Wählen Sie diese Option CPUQuota=. Niedrigere Werte reduzieren die maximale CPU-Auslastung, können aber die Fertigstellung verlangsamen und die Wartezeit erhöhen.
  • Benötigen Sie nur eine niedrigere Priorität?CPUWeight= Dann sollten Sie anstelle einer Quote eine gewichtete Verteilung in Betracht ziehen . Diese verteilt die CPU relativ zur jeweiligen Auslastung; sie reserviert keinen festen Prozentsatz und verhindert nicht die Nutzung ungenutzter CPU-Leistung.
  • Benötigen Sie Speicherdruck ohne sofortigen Stopp? Legen Sie MemoryHigh=den Hauptdruckschwellenwert fest und beobachten Sie Latenz und Speicherrückgewinnungsverhalten.
  • Benötigen Sie eine endgültige Begrenzung? Planen Sie MemoryMax=ausreichend Spielraum für normale Spitzenwerte ein. Seien Sie auf einen Speichermangel vorbereitet, wenn die Begrenzung nicht eingehalten werden kann.
  • Sie verwenden bereits einen Container? Dann bevorzugen Sie die vom Container-Manager unterstützten CPU- und Speicherflags, die Cgroups für diesen Container konfigurieren und zu seinem Lebenszyklus passen.

Es gibt keine allgemeingültige optimale Grenze für jede Arbeitslast. Ein Desktop-Batch-Job kommt möglicherweise mit einem niedrigen Kontingent und einer moderaten Speicherbegrenzung aus; ein latenzempfindlicher Dienst benötigt unter Umständen mehr CPU-Spielraum und eine höhere Speicherbegrenzung, MemoryHighum durch Speicherbereinigung bedingte Pausen zu vermeiden. Beginnen Sie mit einer konservativen Einstellung, überwachen Sie das System während einer typischen Spitzenlast und passen Sie jeweils nur eine Einstellung an.

Referenzen

Einen Kommentar hinterlassen

Wie man ein entferntes SSHFS-Verzeichnis beim Systemstart in Debian automatisch einbindet

Wie man ein entferntes SSHFS-Verzeichnis beim Systemstart in Debian automatisch einbindet

Automatisches Einbinden eines entfernten SSHFS-Verzeichnisses beim Systemstart in Debian mittels schlüsselbasiertem SSH, /etc/fstab, systemd-Netzwerkoptionen, automatischem Einbinden und Verifizierungsschritten.

Behebung des Fehlers „Speicher kann nicht zugewiesen werden“ während eines SLES-System-Upgrades

Behebung des Fehlers „Speicher kann nicht zugewiesen werden“ während eines SLES-System-Upgrades

Beheben Sie den Fehler „Speicher kann nicht zugewiesen werden“ während eines SLES-Upgrades. Überprüfen Sie RAM, Swap-Speicher, OOM-Protokolle und Prozesslimits und beheben Sie das Problem, ohne die Pakettransaktionen zu unterbrechen.

Behebung von Touchscreen-Kalibrierungsproblemen auf Harmonica OS-Tablets: Die richtige Linux-Lösung auswählen

Behebung von Touchscreen-Kalibrierungsproblemen auf Harmonica OS-Tablets: Die richtige Linux-Lösung auswählen

Beheben Sie Probleme mit Touch-Offset, Rotation und Display-Mapping auf Harmonica OS (HamoniKR)-Tablets. Vergleichen Sie die Korrekturen von X.Org und libinput, testen Sie sicher und erkennen Sie, wann eine Kalibrierung nicht hilft.

Wie man eine verschlüsselte Swap-Partition unter Debian 12 einrichtet

Wie man eine verschlüsselte Swap-Partition unter Debian 12 einrichtet

Verschlüsseln Sie eine bestehende Debian 12 Swap-Partition mit dm-crypt, einem neuen zufälligen Schlüssel bei jedem Systemstart, /etc/crypttab, /etc/fstab und sicheren Verifizierungsschritten.

Wie man den Zustand von SMART-Laufwerken unter Ubuntu per E-Mail-Benachrichtigung überwacht

Wie man den Zustand von SMART-Laufwerken unter Ubuntu per E-Mail-Benachrichtigung überwacht

Richten Sie smartmontools unter Ubuntu ein, um den Zustand von Laufwerken zu überwachen und SMART-E-Mail-Benachrichtigungen zu versenden. Prüfen Sie die Geräteunterstützung, konfigurieren Sie die E-Mail-Zustellung, testen Sie Benachrichtigungen und beheben Sie Fehler.

Behebung des Fehlers „Kein bootfähiges Gerät gefunden“ nach der Installation von Debian auf einem UEFI-System

Behebung des Fehlers „Kein bootfähiges Gerät gefunden“ nach der Installation von Debian auf einem UEFI-System

Beheben Sie Debian UEFI-Bootfehler, indem Sie den Bootmodus des Installationsprogramms, die EFI-Systempartition, NVRAM-Einträge, GRUB-EFI-Dateien, Secure Boot und Firmware-Fallbacks überprüfen.

Wie man automatisierte Btrfs-Snapshots auf Ubuntu Desktop einrichtet

Wie man automatisierte Btrfs-Snapshots auf Ubuntu Desktop einrichtet

Konfigurieren Sie Snapper so, dass es auf Ubuntu Desktop geplante Btrfs-Snapshots erstellt und löscht. Überprüfen Sie vorher Ihr Subvolume-Layout, aktivieren Sie die Systemd-Timer und stellen Sie die Aufbewahrungsdauer sicher.

Sicheres Beheben von Speicherplatzproblemen bei SUSE Linux Enterprise LVM Thin Provisioning

Sicheres Beheben von Speicherplatzproblemen bei SUSE Linux Enterprise LVM Thin Provisioning

Diagnostizieren und Wiederherstellen eines vollständigen LVM Thin Pools auf SUSE Linux Enterprise durch Unterscheidung von Daten- und Metadatenerschöpfung, Erweiterung des Speichers, Reparatur der Metadaten und Aktivierung der automatischen Erweiterung.

Debian 12 CIS Hardening Guide: A Step-by-Step Server Baseline

Debian 12 CIS Hardening Guide: A Step-by-Step Server Baseline

Harden Debian 12 Bookworm against the current CIS Benchmark v2.0.0 with a safe server workflow for updates, SSH, firewall, AppArmor, auditing, and validation.

So installieren Sie Flatpak- und Snap-Apps auf Gooroom OS

So installieren Sie Flatpak- und Snap-Apps auf Gooroom OS

Installieren Sie Flatpak- und Snap-Apps auf Gooroom OS mit Versionsprüfungen, Terminalbefehlen und einem praktischen Vergleich von Kompatibilität, Sicherheitskontrollen, Updates und Speicherplatz.