To może.
Istnieją dwa różne warunki braku pamięci, które można napotkać w systemie Linux. Spotkanie zależy od wartości sysctl vm.overcommit_memory
( /proc/sys/vm/overcommit_memory
)
Wprowadzenie:
Jądro może wykonywać tak zwane „overcommit pamięci”. To wtedy jądro przydziela programom więcej pamięci, niż jest w rzeczywistości w systemie. Odbywa się to w nadziei, że programy faktycznie nie wykorzystają całej przydzielonej pamięci, ponieważ jest to dość częste zjawisko.
overcommit_memory = 2
Kiedy overcommit_memory
jest ustawiony na 2
, jądro w ogóle nie wykonuje żadnego nadpisywania. Zamiast tego, gdy program ma przydzieloną pamięć, zagwarantowany jest dostęp do tej pamięci. Jeśli system nie ma wystarczającej ilości wolnej pamięci, aby zaspokoić żądanie alokacji, jądro po prostu zwróci błąd dla żądania. Program w pełni wdzięcznie poradzi sobie z sytuacją. Jeśli nie sprawdzi, czy alokacja się powiodła, gdy naprawdę się nie powiodła, aplikacja często napotyka awarię.
W przypadku segfault powinieneś znaleźć taką linię na wyjściu dmesg
:
[1962.987529] myapp[3303]: segfault at 0 ip 00400559 sp 5bc7b1b0 error 6 in myapp[400000+1000]
Te at 0
środki, które aplikacja próbowali uzyskać dostęp do niezainicjowanej wskaźnik, który może być wynikiem nieudanego wezwania alokacji pamięci (ale nie jest to jedyna droga).
overcommit_memory = 0 i 1
Gdy overcommit_memory
jest ustawiony na 0
lub 1
, funkcja overcommit jest włączona, a programy mogą przydzielać więcej pamięci, niż jest w rzeczywistości dostępne.
Jednak, gdy program chce użyć pamięci, która została przydzielona, ale jądro stwierdza, że tak naprawdę nie ma wystarczającej ilości pamięci, aby ją zaspokoić, musi odzyskać trochę pamięci. Najpierw próbuje wykonać różne zadania czyszczenia pamięci, takie jak opróżnianie pamięci podręcznej, ale jeśli to nie wystarczy, przerwie proces. To zakończenie jest wykonywane przez OOM-Killera. OOM-Killer patrzy na system, aby zobaczyć, które programy używają jakiej pamięci, jak długo działały, kto je uruchamia, oraz szereg innych czynników, aby ustalić, który z nich zostanie zabity.
Po tym, jak proces został zabity, używana pamięć zostaje zwolniona, a program, który właśnie spowodował stan braku pamięci, ma teraz potrzebną pamięć.
Jednak nawet w tym trybie programom nadal można odmówić żądania alokacji. Kiedy overcommit_memory
jest 0
, jądro próbuje zgadnąć, kiedy powinien zacząć odrzucać żądania alokacji. Gdy jest ustawiony na 1
, nie jestem pewien, jakiej determinacji używa, aby określić, kiedy powinien odrzucić żądanie, ale może odrzucić bardzo duże żądania.
Możesz sprawdzić, czy OOM-Killer jest zaangażowany, patrząc na wyniki dmesg
i znajdując komunikaty, takie jak:
[11686.043641] Out of memory: Kill process 2603 (flasherav) score 761 or sacrifice child
[11686.043647] Killed process 2603 (flasherav) total-vm:1498536kB, anon-rss:721784kB, file-rss:4228kB