W systemach opartych na RHEL, takich jak CentOS Stream 9, kontrola grup zasobów (cgroups) odgrywa bardzo ważną rolę w zarządzaniu i ograniczaniu wykorzystania zasobów przez aplikacje i usługi. Mechanizm cgroups, dostępny od lat w jądrze Linux, pozwala administratorom systemów kontrolować takie zasoby jak procesor (CPU), pamięć RAM, przepustowość sieci czy operacje wejścia-wyjścia na dyskach. W tym artykule pokaże na przykładzie CentOS Stream 9, działającym na najnowszych fundamentach RHEL 9, gdzie cgroups w wersji 2 (cgroups v2) jest domyślnym systemem, co upraszcza zarządzanie hierarchią i politykami zasobów. Cgroups są szczególnie użyteczne w środowiskach, gdzie wiele aplikacji i usług współdzieli zasoby jednego serwera. Wyobraźmy sobie sytuację, w której na serwerze działa kilka aplikacji webowych, każda zarządzana przez osobne jednostki systemd. Możemy ograniczyć zasoby każdej aplikacji, aby zapobiec sytuacji, w której jedna z nich wykorzystuje całą pamięć RAM lub czas procesora, powodując spowolnienie działania innych.

W tym artykule skupie się na limitowaniu CPU i RAM; warto jednak zaznaczyć, że limitowanie przepustowości sieci to temat o większym stopniu skomplikowania.

Weźmy na przykład typową aplikację, którą większość zna i rozumie dzięki czemu zrozumienie cgoups będzie z pewnością łatwiejsze. W naszym przypadku będzie to klasyczny nginx jako serwer www.

Ustawienie limitowania RAM

Jeśli mamy już zainstalowany nginx wystarczy wydać polecenie edytujące, jeśli nie mamy instalujemy za pomocą dnf’a.

systemctl edit nginx.service

Domyślny plik wygląda mniej więcej tak:

Dodajemy nasz wpis na początku pliku pomiędzy tymi liniami:

[Service]

MemoryMax=500M

Zapisujemy plik i przeładowujemy systemd.

systemctl daemon-reload

Restartujemy serwis nginx’a

systemctl restart nginx

Sprawdzamy czy limity zostały załadowane:

cat /sys/fs/cgroup/system.slice/nginx.service/memory.max

Możemy dla testu zmienić wartość np. Na 600 MB:

Jak widać aktualnie nginx został zlimitowany na maksymalnie 600 MB pamięci RAM i więcej nie będzie mógł zająć.

Ustawienie limitowania CPU

systemctl edit nginx.service

Dopisujemy wartość:

CPUQuota=50%

Zapisujemy, daemon reload i w ten sposób nginx został zlimitowany także na CPU do wartości 50%.

Monitorowanie zużycia zasobów

Do monitorowania zużycia zasobów możemy wykorzystać wiele narzędzie dostępnych w systemie Linux. Jednym z nich będzie „htop” gdzie po włączeniu kolumny cgroups (f2) możemy obserwować aktualne zużycie pamięci dla zadanej grupy.

Możemy też użyć narzędzie, które jest już wbudowane w system:

systemcd-cgtop

Gdzie po odnalezieniu właściwej grupy możemy monitorować na bieżąco zajętość zasobów.

Testowanie limitów

Z pewnością wiele osób zadało sobie pytanie, w jaki sposób przetestować czy te limity faktycznie działają. Z odpowiedzią przyjdą nam systemowe rozwiązania i narzędzia, którymi możemy zarówno testować jak i obserwować co się dzieje z procesem.

Na początek zainstalujemy narzędzie apache benchmark do testowania obciążenia serwera www.

dnf -y install httpd-tools

W skład toolsów od serwera httpd wchodzi między innymi narzędzie o nazwie “ab”, którym możemy przetestować obciążenie serwera, w naszym przypadku nginxa.

Generujemy plik do testów:

dd if=/dev/zero of=/usr/share/nginx/html/plik bs=1M count=20

Uruchamiamy narzędzie benchmarkowe:

ab -n 5000 -c 500 -p /usr/share/nginx/html/plik -T „application/octet-stream” http://127.0.0.1/

Informacje o parametrach:

-n 500: Wysyła 500 żądań.

-c 50: Utrzymuje 50 równoległych połączeń.

-p /usr/share/nginx/html/plik: Wysyła zawartość dużego pliku w każdym żądaniu.

-T „application/octet-stream”: Ustawia nagłówek typu treści na binarny plik.

Powinno to spokojnie obciążyć naszego nginxa do testów.

Sprawdźmy co się dzieje w procesach:

systemd-cgtop

Jak widać nginx zajmuje maksymalną wartość, przydzieloną do tego procesu, 50% czasu procesora.

Zwiększamy testowo wartość CPU limit na 80%

nano /etc/systemd/system/nginx.service.d/override.conf

Zwiększamy wartość CPU do 80%.

Przeładowujemy ponownie serwisy.

systemctl daemon-reload

systemctl restart nginx

Testujemy ponownie przy obciążeniu jak poprzednio.

ab -n 5000 -c 500 -p /usr/share/nginx/html/plik -T „application/octet-stream” http://127.0.0.1/

Wyniki

Jak widać w tym momencie nginx zajmuje już 80% czasu procesora, gdyż tyle przydzieliliśmy. Limity zatem działają poprawnie. Warto zastanowić się nad innymi procesami, użytkownikami, które chcemy limitować w taki sposób, aby zapewnić stabilizację serwera i uniemożliwić jednemu procesowi czy użytkownikowi zajęcie całej mocy obliczeniowej serwera.

Podsumowanie

Stosowanie limitowania zasobów za pomocą cgroups w systemie CentOS, w szczególności w kontekście CPU i pamięci RAM, jest jednym z elementów zarządzania wydajnością i stabilnością serwera, na którym działa wiele różnych usług. Dzięki precyzyjnemu przypisywaniu limitów można zapewnić, że żadna aplikacja lub usługa nie wykorzysta nadmiernej ilości zasobów, co mogłoby doprowadzić do degradacji działania innych procesów lub nawet całego systemu. Na przykład, ograniczenie zużycia procesora za pomocą `CPUQuota` pozwala kontrolować, ile czasu obliczeniowego dana usługa może wykorzystać, zapobiegając sytuacjom, w których intensywne obciążenie jednego procesu spowalnia inne ważne aplikacje. Podobnie, limitowanie pamięci RAM za pomocą `MemoryMax` chroni system przed sytuacjami, w których niewłaściwie zaprojektowana lub błędna aplikacja zużywa całą dostępną pamięć, powodując problemy takie jak ubijanie procesów przez mechanizm OOM (Out of Memory). W serwerach działających w środowiskach współdzielonych, takich jak hosting aplikacji webowych, bazy danych czy przetwarzanie w chmurze, cgroups pozwalają na efektywne alokowanie zasobów, co zwiększa niezawodność i sprawia, że wszystkie usługi działają w sposób przewidywalny. Wprowadzenie takich ograniczeń nie tylko poprawia stabilność systemu, ale również ułatwia diagnozowanie problemów i planowanie zasobów w perspektywie długoterminowej, co jest istotne dla utrzymania wysokiej jakości działania serwera i długoterminowego utrzymania usług na stabilnym poziomie.