Jaka jest różnica między vmalloc a kmalloc?

Poszperałem w googlach i znalazłem większość ludzi opowiadających się za używaniem kmalloc, ponieważ masz gwarancję, że dostaniesz sąsiadujące ze sobą fizyczne bloki pamięci. Jednak wydaje się również, że kmalloc może się nie udać, jeśli nie można znaleźć sąsiedniego fizycznego bloku, którego chcesz.
Jakie są zalety posiadania sąsiedniego bloku pamięci? W szczególności, dlaczego miałbym mieć przylegający fizycznyblok pamięci w wywołaniu systemowym ? Czy jest jakiś powód, dla którego nie mógłbym użyć vmalloc?
Na koniec, gdybym miał przydzielać pamięć podczas obsługi wywołania systemowego, czy powinienem podać GFP_ATOMIC? Czy wywołanie systemowe jest wykonywane w kontekście atomowym?

GFP_ATOMIC
Przydział ma wysoki priorytet i nie śpi. To jest flaga do zastosowanie w programach obsługi przerwań, dolna połówki i inne sytuacje, w których nie mogę spać.

GFP_KERNEL Jest to normalny przydział i może zablokować. To jest flaga do użycia w kodzie kontekstu procesu, gdy jest to bezpieczne dla śpij.

Author: Sam Protsenko, 2008-09-22

7 answers

Musisz się martwić tylko o użycie fizycznie przylegającej pamięci, jeśli bufor będzie dostępny przez urządzenie DMA na fizycznie adresowanej magistrali (np. PCI). Problem polega na tym, że wiele wywołań systemowych nie ma możliwości sprawdzenia, czy ich bufor zostanie ostatecznie przekazany do urządzenia DMA: po przekazaniu bufora do innego podsystemu jądra, naprawdę nie możesz wiedzieć, dokąd zmierza. Nawet jeśli jądro nie używa bufora dla DMA dzisiaj, przyszły rozwój może więc.

Vmalloc jest często wolniejszy niż kmalloc, ponieważ może być konieczne przekształcenie przestrzeni bufora w praktycznie przylegający zakres. kmalloc nigdy się nie powtarza, chociaż jeśli nie zostanie wywołany z GFP_ATOMIC, kmalloc może zablokować.

Kmalloc jest ograniczony rozmiarem bufora, który może dostarczyć: 128 KBytes*). Jeśli potrzebujesz naprawdę dużego bufora, musisz użyć vmalloc lub innego mechanizmu, takiego jak rezerwowanie dużej pamięci podczas rozruchu.

*)tak było w przypadku wcześniejszych jąder. On najnowsze kernele (testowałem to na 2.6.33.2), maksymalny rozmiar pojedynczego kmalloc wynosi do 4 MB! (Napisałem dość szczegółowy post na ten.)- kaiwan

Dla wywołania systemowego nie musisz przekazywać GFP_ATOMIC do kmalloc (), możesz użyć GFP_KERNEL. Nie jesteś obsługą przerwań: kod aplikacji wchodzi do kontekstu jądra za pomocą pułapki, nie jest to przerwanie.

 81
Author: DGentry,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-09-02 08:14:29

Krótka odpowiedź: pobierz Sterowniki urządzeń Linuksowych i przeczytaj rozdział na temat zarządzania pamięcią.

Poważnie, jest wiele subtelnych kwestii związanych z zarządzaniem pamięcią jądra, które musisz zrozumieć - spędzam dużo czasu na debugowaniu problemów z nim.

Vmalloc () jest bardzo rzadko używane, ponieważ jądro rzadko używa pamięci wirtualnej. kmalloc() jest tym, co jest zazwyczaj używane, ale musisz wiedzieć, jakie są konsekwencje różnych flag i potrzebujesz strategii za radzenie sobie z tym, co się dzieje, gdy się nie powiedzie - szczególnie jeśli jesteś w programie obsługi przerwań, tak jak sugerowałeś.

 16
Author: Mike Heinz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-09-22 18:05:11

Rozwój jądra Linuksa Robert Love (Rozdział 12, strona 244 w trzeciej edycji) odpowiada na to bardzo wyraźnie.

Tak, fizycznie przylegająca pamięć nie jest wymagana w wielu przypadkach. Głównym powodem, dla którego kmalloc jest używany bardziej niż vmalloc w jądrze, jest wydajność. W książce wyjaśniono, że gdy duże kawałki pamięci są przydzielane za pomocą vmalloc, jądro musi mapować fizycznie nie sąsiadujące ze sobą kawałki (strony) w jeden sąsiadujący region pamięci wirtualnej. Ponieważ pamięć jest praktycznie przylegająca i fizycznie nie przylegające, kilka wirtualnych do fizycznych mapowań adresów będzie musiało zostać dodanych do tabeli strony. W najgorszym przypadku do tabeli stron zostanie dodana (rozmiar bufora/rozmiar strony) liczba mapowań.

Dodaje to również presję na TLB (wpisy pamięci podręcznej przechowujące Ostatnie mapowania adresów wirtualnych na fizyczne) podczas uzyskiwania dostępu do tego bufora. To może prowadzić do thrashing.

 10
Author: codetwiddler,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-07-11 22:37:55

The kmalloc() & vmalloc() funkcje są prostym interfejsem do uzyskiwania pamięci jądra w kawałkach o wielkości bajtów.

  1. Funkcja kmalloc() gwarantuje, że strony są fizycznie przylegające (i praktycznie przylegające).

  2. Funkcja vmalloc() działa w podobny sposób jak kmalloc(), z tym że przydziela pamięć, która jest tylko praktycznie przylegająca, a niekoniecznie fizycznie przylegająca.

 7
Author: Yogeesh H T,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-07-04 11:41:36

Jakie są zalety posiadania sąsiedniego bloku pamięci? W szczególności, dlaczego miałbym mieć przylegający fizyczny blok pamięci w wywołaniu systemowym? Czy jest jakiś powód, dla którego nie mogłem po prostu użyć vmalloc?

From Google ' S "I' m Feeling Lucky " on vmalloc:

Kmalloc jest preferowaną drogą, o ile nie potrzebujesz bardzo dużych obszarów. Problem w tym, że jeśli chcesz zrobić DMA Z / do jakiegoś urządzenia sprzętowego, musisz użyć kmalloc i prawdopodobnie będziesz potrzebował większego chunk. Rozwiązaniem jest przydzielenie pamięci tak szybko, jak to możliwe, przed pamięć ulega fragmentacji.

 5
Author: Dark Shikari,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2008-09-22 17:48:13

Jedną z innych różnic jest to, że kmalloc zwróci adres logiczny (w przeciwnym razie podasz GPF_HIGHMEM). Adresy logiczne są umieszczane w "małej pamięci" (w pierwszym gigabajcie pamięci fizycznej) i są mapowane bezpośrednio do adresów fizycznych (użyj makra __pa, aby je przekonwertować). Ta właściwość implikuje, że pamięć kmalloced jest pamięcią ciągłą.

Z drugiej strony, Vmalloc jest w stanie zwracać adresy wirtualne z "wysokiej pamięci". Adresy te nie mogą być konwertowane na adresy fizyczne w sposób bezpośredni (musisz użyć funkcji virt_to_page).

 1
Author: Jezz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-03-13 20:52:40

W systemie 32-bitowym, kmalloc () zwraca adres logiczny jądra (jest to jednak adres wirtualny), który ma bezpośrednie mapowanie (w rzeczywistości ze stałym przesunięciem) na adres fizyczny. To bezpośrednie mapowanie zapewnia, że otrzymujemy przylegający fizyczny fragment pamięci RAM. Nadaje się do DMA, gdzie podajemy tylko początkowy wskaźnik i oczekujemy dalszego fizycznego mapowania dla naszej operacji.

Vmalloc () zwraca wirtualny adres jądra, który z kolei może nie mieć przylegającego mapowania na fizycznej pamięci RAM. Przydatne przy dużej alokacji pamięci i w przypadkach, gdy nie dbamy o to, aby pamięć przydzielona do naszego procesu była ciągła również w fizycznej pamięci RAM.

 1
Author: a.saurabh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-11-05 20:13:31