Kiedy powinienem używać / dev / shm / a kiedy powinienem używać / tmp /?

139

Kiedy powinienem /dev/shm/i kiedy powinienem /tmp/? Czy zawsze mogę polegać na tym, że oboje są na Unices?

Usunięte
źródło

Odpowiedzi:

101

/dev/shmto system plików tymczasowego przechowywania plików, tj. tmpfs , który wykorzystuje pamięć RAM do przechowywania kopii zapasowych. Może działać jako implementacja pamięci współużytkowanej, która ułatwia IPC .

Z Wikipedii :

Ostatnie kompilacje jądra Linuksa 2.6 zaczęły oferować / dev / shm jako pamięć współdzieloną w postaci ramdysku, a dokładniej jako katalog do zapisu na świecie, który jest przechowywany w pamięci ze zdefiniowanym limitem w / etc / default / tmpfs.  Obsługa / dev / shm jest całkowicie opcjonalna w pliku konfiguracyjnym jądra.   Jest domyślnie dołączany zarówno do dystrybucji Fedora, jak i Ubuntu, gdzie jest najczęściej wykorzystywany przez aplikację Pulseaudio.             (Podkreślenie dodane.)

/tmpto lokalizacja plików tymczasowych zgodnie z definicją w standardzie hierarchii systemów plików , po której znajdują się prawie wszystkie dystrybucje Uniksa i Linuksa.

Ponieważ pamięć RAM jest znacznie szybsza niż pamięć dyskowa, można jej użyć /dev/shmzamiast /tmpdo zwiększenia wydajności , jeśli proces wymaga intensywnych operacji we / wy i intensywnie wykorzystuje pliki tymczasowe.

Aby odpowiedzieć na twoje pytania: Nie, nie zawsze możesz polegać na /dev/shmobecności, z pewnością nie na maszynach przywiązanych do pamięci. Powinieneś używać, /tmpchyba że masz bardzo dobry powód do używania /dev/shm.

Pamiętaj, że /tmpmoże być częścią /systemu plików zamiast osobnego montowania, a zatem może rosnąć w miarę potrzeb. Rozmiar pliku /dev/shmjest ograniczony nadmiarem pamięci RAM w systemie, dlatego jest większe prawdopodobieństwo, że zabraknie miejsca w tym systemie plików.

nagul
źródło
1
Będę go używał do przekierowania wyjścia ze standardowego wyjścia błędu polecenia do pliku. Następnie przeczytam ten plik i przetworzę go. Zrobię to kilka tysięcy razy (jest to część warunku konstrukcji pętli). Myślałem, że pamięć będzie miła w tym przypadku. Ale chcę też, żeby był przenośny. Myślę, że sprawdzę, czy /dev/shmistnieje, użyję go, jeśli tak, lub wrócę do /tmp. Czy to brzmi dobrze?
Usunięte
1
Dodałbym również sprawdzenie minimalnego rozmiaru i bieżącego poziomu użytkowania / dev / shm, aby uchronić się przed przypadkowym zapełnieniem go.
nagul
4
W Linuksie 2.6 i nowszych wymagane jest podłączenie / dev / shm, aby wywołania systemowe pamięci współużytkowanej POSIX, takie jak shm_open (), działały. Innymi słowy, niektóre programy ulegną awarii, jeśli nie zostaną zamontowane - tak powinno być. To nie tylko dysk RAM. Więc powinieneś upewnić się, że część / dev / shm jest darmowa.
EdH
7
Używanie nie powoduje zwiększenia wydajności /dev/shm. /dev/shmto pamięć (tmpfs) wspierana przez dysk (swap). /var/tmpto pamięć (pamięć podręczna dysku) wspierana przez dysk (system plików na dysku). W praktyce wydajność jest prawie taka sama (tmpfs ma niewielką przewagę, ale nie wystarcza, aby mieć znaczenie). /tmpmoże być tmpfs lub nie, w zależności od tego, jak skonfigurował go administrator. Nie ma dobrego powodu, aby używać /dev/shmw swoich skryptach.
Gilles
3
@GaretClaborn Istnieje wiele dobrych powodów, aby używać pamięci wspartej przez swap, ale to się nazywa normalna pamięć procesu. Jeśli używasz pliku, nazywa się to systemem plików, a wszystkie systemy plików to pamięć (cache), która jest wspierana przez swap, jeśli system plików jest podobny do tmpfs. Przydzielanie miejsca na dysku między obszarami wymiany i innymi obszarami pamięci zwykle należy do administratora. Jeśli aplikacja chce plików, które zwykle pozostają w pamięci RAM, /tmpjest to normalna lokalizacja (z $TMPDIRprzesłonięciem). Wybór, aby wykonać /tmpkopię zapasową, inną przestrzeń dyskową lub nic, należy do administratora.
Gilles
61

W kolejności malejącej tmpfsprawdopodobieństwa:

┌───────────┬──────────────┬────────────────┐
│ /dev/shm  │ always tmpfs │ Linux specific │
├───────────┼──────────────┼────────────────┤
│ /tmp      │ can be tmpfs │ FHS 1.0        │
├───────────┼──────────────┼────────────────┤
│ /var/tmp  │ never tmpfs  │ FHS 1.0        │
└───────────┴──────────────┴────────────────┘

Ponieważ pytasz o punkt montowania tmpfs specyficzny dla Linuksa w porównaniu z katalogiem przenośnym, którym może być tmpfs (w zależności od twojego sysadmin i tego, co jest domyślne dla twojej dystrybucji), twoje pytanie ma dwa aspekty, na które inne odpowiedzi podkreślały inaczej:

  1. Kiedy korzystać z tych katalogów w oparciu o dobre praktyki
  2. Kiedy właściwe jest użycie tmpfs

Dobre praktyki

Edycja konserwatywna (połączenie konwencji z FHS i powszechnego użytku):

  • W razie wątpliwości użyj /tmp.
  • Używaj /var/tmpdo dużych danych, które nie mogą łatwo zmieścić się w pamięci RAM.
  • Użyj /var/tmpdo danych, które są korzystne dla ponownego uruchamiania (np. Pamięci podręcznej).
  • Użyj /dev/shmjako efekt uboczny połączenia shm_open(). Docelowi odbiorcy są ograniczonymi buforami, które są w nieskończoność nadpisywane. Tak jest w przypadku plików długowiecznych, których zawartość jest niestabilna i niezbyt duża.
  • W razie wątpliwości podaj sposób na zastąpienie przez użytkownika. Na przykład mktempprogram honoruje TMPDIRzmienną środowiskową.

Edycja pragmatyczna:

Użyj, /dev/shmgdy ważne jest użycie tmpfs, /var/tmpgdy ważne jest, aby nie, w przeciwnym razie /tmp.

Gdzie tmpfs przoduje

fsyncjest zakazem działania na tmpfs. To wywołanie systemowe jest największym wrogiem wydajności (IO) (i długowieczności flash, jeśli ci na tym zależy), chociaż jeśli używasz tmpfs (lub eatmydata) tylko po to, aby pokonać fsync, a następnie (lub inny programista w łańcuchu) robisz coś złego. Oznacza to, że transakcje dotyczące urządzenia pamięci masowej są niepotrzebnie drobiazgowe dla twojego celu - wyraźnie chcesz pominąć niektóre punkty zapisu dla wydajności, ponieważ doszedłeś do skrajności sabotowania ich wszystkich - rzadko najlepszy kompromis. Również tutaj, w krainie wydajności transakcji, znajdują się jedne z największych zalet posiadania dysku SSD - każdy porządny dysk SSD będzie działał nie z tego świata w porównaniu z tym, co może wziąć wirujący dysk (7200 obr./min = 120 Hz , jeśli tylko inne osoby mają do niego dostęp), nie wspominając już o kartach pamięci flash, które różnią się znacznie w zależności od tego wskaźnika (zwłaszcza dlatego, że jest to kompromis z wydajnością sekwencyjną, według której są oceniane, np. ocena klasy karty SD). Więc strzeżcie się,

Chcesz usłyszeć śmieszną historię? Moja pierwsza fsynclekcja: Miałem zadanie polegające na rutynowym „uaktualnianiu” kilku baz danych Sqlite (przechowywanych jako skrzynki testowe) do ciągle zmieniającego się bieżącego formatu. Struktura „upgrade” uruchamiałaby wiele skryptów, wykonujących co najmniej jedną transakcję, aby zaktualizować jedną bazę danych. Oczywiście zaktualizowałem swoje bazy danych równolegle (8 równolegle, ponieważ zostałem pobłogosławiony potężnym 8-rdzeniowym procesorem). Ale jak się dowiedziałem, nie było żadnego przyspieszenia równoległości (raczej niewielkie trafienie ), ponieważ proces był całkowicie związany z IO. Zabawne jest to, że zawijanie frameworka aktualizacji w skrypcie, który kopiował każdą bazę danych /dev/shm, uaktualniało ją tam i kopiowało z powrotem na dysk było 100 razy szybsze (wciąż z 8 równolegle). Jako bonus, komputer był użyteczny podczas aktualizacji baz danych.

Gdzie właściwe jest tmpfs

Właściwe użycie tmpfs polega na uniknięciu niepotrzebnego zapisu lotnych danych. Skutecznie wyłącza zapisywanie zwrotne , takie jak ustawienie /proc/sys/vm/dirty_writeback_centisecsnieskończoności w zwykłym systemie plików.

Nie ma to wiele wspólnego z wydajnością, w przeciwnym razie jest to znacznie mniejszy problem niż nadużywanie fsync: Limit czasu zapisu określa, jak leniwie zawartość dysku jest aktualizowana po zawartości pagecache, a domyślnie 5 sekund to długi czas dla komputera - aplikacja może nadpisywać plik tak często, jak chce, w pagecache, ale zawartość dysku jest aktualizowana tylko raz na 5 sekund. Chyba że aplikacja wymusi przejście przez fsync, to znaczy. Zastanów się, ile razy aplikacja może w tym czasie wyprowadzić mały plik, a zobaczysz, dlaczego synchronizacja każdego z nich byłaby o wiele większym problemem.

W czym tmpfs nie może ci pomóc

  • Przeczytaj wyniki. Jeśli twoje dane są gorące (co lepiej, jeśli rozważasz przechowywanie ich w tmpfs), i tak trafisz na pagecache. Różnica polega na tym, że nie uderzasz w pamięć podręczną; w takim przypadku przejdź do „Where tmpfs sux” poniżej.
  • Pliki krótkotrwałe. Mogą żyć całe swoje życie w pamięci podręcznej (jako brudne strony), zanim zostaną zapisane. Chyba że wymusisz to fsyncoczywiście.

Gdzie smp tsfs

Przechowywanie zimnych danych. Możesz mieć pokusę, aby myśleć, że udostępnianie plików bez wymiany jest tak samo wydajne jak normalny system plików, ale istnieje kilka powodów, dla których tak nie jest:

  • Najprostszy powód: nie ma niczego, co współczesne urządzenia pamięci masowej (twarde lub oparte na Flashu) bardziej niż czytają dość sekwencyjne pliki uporządkowane przez odpowiedni system plików. Wymiana bloków 4KiB raczej nie poprawi się.
  • Ukryty koszt: Zamiana na zewnątrz . Tmpfs strony są brudne - muszą być napisane gdzieś (do wymiany), aby być eksmitowany z Obsługi KlientaSchowek, w przeciwieństwie do pliku kopii czystych stron, które mogą być natychmiast spadła. Jest to dodatkowa kara zapisu za wszystko, co konkuruje o pamięć - wpływa na coś innego w innym czasie niż korzystanie z tych stron tmpfs.
użytkownik2394284
źródło
W moim Ubuntu 14.04 / dev / shm znajduje się link do / run / shm, który ma system plików „none” zgodnie z poleceniem df. Rozmiar to jednak około 2G.
jarno
3
@jarno Po pierwsze, oszczędzając liczbę punktów montowania tmpfs, nazwałbym szczegół implementacji. Po drugie, nie pozwól, aby nazwa urządzenia Cię myliła - zajrzyj do / proc / mounts (jest to właściwe miejsce do patrzenia), a zobaczysz, że typem jest „tmpfs”, podczas gdy urządzenie jest tym, czego „nie ma”. Tak, nazwa urządzenia nic nie znaczy w tmpfs - możesz, mount -t tmpfs "jarno is great" /mnt/jarnojeśli chcesz! Po trzecie, domyślny rozmiar to połowa pamięci RAM - założę się, że masz 4 GB pamięci RAM.
user2394284,
1
Czy istnieje opcja, która przydziela stały rozmiar pamięci RAM i obiecuje, że nigdy nie użyje wymiany?
palswim
@palswim: To byłby ramdysk. Nie widzę takiej opcji w tmpfs , poza tym, że poprzednik tmpfs nie obsługiwał zamiany. Procesy mogą blokować swoje strony w pamięci RAM, co jest prawdopodobnie mniej szalone niż blokowanie stron tmpfs w pamięci RAM, biorąc pod uwagę, że zabójca OOM nie jest w stanie zwolnić tych ostatnich, jeśli zabraknie pamięci.
user2394284,
18

OK, oto rzeczywistość.

Zarówno tmpfs, jak i normalny system plików są pamięcią podręczną na dysku.

Tmpfs wykorzystuje pamięć i swapspace, ponieważ tworzy kopię zapasową, system plików używa określonego obszaru dysku, żaden z nich nie jest ograniczony wielkością systemu plików, całkiem możliwe jest posiadanie 200 GB tmpfs na maszynie z mniej niż GB pamięci RAM, jeśli masz wystarczająco dużo przestrzeni wymiany.

Różnica polega na tym, kiedy dane są zapisywane na dysku. W przypadku tmpfs dane są zapisywane TYLKO wtedy, gdy pamięć się zapełni lub dane prawdopodobnie nie zostaną wkrótce wykorzystane. OTOH większość normalnych systemów plików Linux jest zaprojektowana tak, aby zawsze mieć mniej lub bardziej spójny zestaw danych na dysku, więc jeśli użytkownik wyciągnie wtyczkę, nie wszystko straci.

Osobiście jestem przyzwyczajony do posiadania systemów operacyjnych, które nie powodują awarii i systemów UPS (np. Baterii laptopów), więc myślę, że systemy plików ext2 / 3 są zbyt paranoiczne z ich 5-10 sekundowym interwałem punktu kontrolnego. System plików ext4 jest lepszy z 10-minutowym punktem kontrolnym, z tym wyjątkiem, że traktuje dane użytkownika jako drugą klasę i nie chroni ich. (ext3 jest taki sam, ale nie zauważasz go z powodu 5-sekundowego punktu kontrolnego)

To częste sprawdzanie oznacza, że ​​niepotrzebne dane są ciągle zapisywane na dysk, nawet dla / tmp.

W rezultacie musisz utworzyć przestrzeń wymiany tak dużą, jak potrzebujesz / tmp (nawet jeśli musisz utworzyć plik wymiany) i użyć tej przestrzeni do zamontowania tmpfs o wymaganym rozmiarze na / tmp.

NIGDY nie używaj / dev / shm.

Chyba, że ​​używasz go do bardzo małych (prawdopodobnie mmap'd) plików IPC i masz pewność, że istnieje (to nie jest standard), a maszyna ma więcej niż wystarczającą ilość pamięci + wymiany.

Robert
źródło
24
Uzgodniono, z wyjątkiem wniosku „NIGDY nie używaj / dev / shm”. Chcesz użyć / dev / shm w przypadkach, gdy w ogóle nie chcesz, aby plik był zapisywany na dysku i chcesz zminimalizować operacje wejścia / wyjścia na dysku. Na przykład muszę pobrać bardzo duże pliki zip z serwera FTP, rozpakować je, a następnie zaimportować do bazy danych. Rozpakowuję do / dev / shm, więc zarówno dla operacji rozpakowywania, jak i importowania dysk twardy musi wykonać tylko połowę operacji, zamiast przesuwać się w przód iw tył między źródłem a miejscem docelowym. Ogromnie przyspiesza ten proces. To jeden z wielu przykładów, ale zgadzam się, że jest to narzędzie niszowe.
Nathan Stretch,
4

Użyj / tmp / dla plików tymczasowych. Użyj / dev / shm /, jeśli chcesz pamięci współdzielonej (tj. Komunikacja międzyprocesowa poprzez pliki).

Możesz polegać na tym, że / tmp / istnieje, ale / dev / shm / jest stosunkowo nową rzeczą dla Linuksa.

Kapitanie Segfault
źródło
Czy nie ma również aspektu wydajności? Czy / dev / shm jest najczęściej montowany jako wolumin tmpfs i zasadniczo jako dysk RAM?
Usunięte
Możesz także zamontować / tmp jako system plików tmpfs, robię to na moim netbooku, aby przyspieszyć niektóre rzeczy poprzez ograniczenie zapisu na (wolnym) dysku SSD. Są oczywiście wady (głównie użycie pamięci RAM, ale mój netbook ma o wiele więcej pamięci RAM niż zwykle potrzebuje).
David Spillett,
W moim konkretnym przypadku użyłbym go do pewnego rodzaju komunikacji procesowej. Przechwytywam wyjście standardowego błędu z aplikacji i działam na jego zawartości (i wciąż potrzebuję standardowego wyjścia nietkniętego, więc nie mogę tego zrobić 1>/dev/null 2>&1. Zrobiłbym to kilka tysięcy razy, więc tmpfs byłby miły. Jednak jeśli wypuść skrypt, w którym nie mogę polegać na tmpfs, /tmpponieważ myślę, że nie jest to takie powszechne. Jeśli jest bardziej powszechne, /dev/shmto jest to dla mnie lepsze. Ale szukam wskazówek dotyczących przenośności itp.
Usunięte
1

Innym razem, kiedy należy używać / dev / shm (Linux 2.6 i wyżej), gdy trzeba gwarantowana tmpfs systemu plików, ponieważ nie wiem, czy można napisać na dysku.

Znany mi system monitorowania musi zapisywać pliki tymczasowe podczas tworzenia raportu w celu przesłania go na serwer centralny. W praktyce jest o wiele bardziej prawdopodobne, że coś uniemożliwi zapisywanie w systemie plików (brak miejsca na dysku lub podstawowa awaria RAID spowodowała, że ​​system przeszedł w sprzętowy tryb tylko do odczytu), ale nadal można utykać, aby ostrzec o tym, czy coś spiralnie zapełnia całą dostępną pamięć, tak że tmpfs będzie bezużyteczny (a pudełko nie będzie martwe). W takich przypadkach system monitorowania preferuje zapisywanie do pamięci RAM, aby potencjalnie móc wysłać ostrzeżenie o pełnym dysku lub martwym / umierającym sprzęcie.

Japheth Cleaver
źródło
0

/ dev / shm służy do sterowników i programów specyficznych dla systemu pamięci wirtualnej.

Jeśli tworzysz program, który wymaga sterty pamięci wirtualnej, którą należy zamapować na pamięć wirtualną. Jest to dwukrotne, więc jeśli potrzebujesz wielu procesów lub wątków, aby mieć bezpieczny dostęp do tej pamięci.

Faktem jest, że tylko dlatego, że sterownik używa do tego specjalnej wersji tmpfs, nie oznacza to, że powinieneś używać go jako ogólnej partycji tmpfs. Zamiast tego powinieneś po prostu utworzyć kolejną partycję tmpfs, jeśli chcesz ją dla swojego katalogu tymczasowego.

Robert Wm Ruedisueli
źródło
0

W PERL, mając minimum 8 GB na dowolnej maszynie (wszystkie z uruchomioną Linux Mint), uważam, że dobrym nawykiem jest wykonywanie złożonych algorytmów opartych na pliku DB_ (struktura danych w pliku) z milionami odczytów i zapisów przy użyciu / dev / shm

W innych językach, gdzie nie ma miejsca na gigether, aby uniknąć startów i zatrzymań w transferze sieciowym (praca lokalna na pliku znajdującym się na serwerze w atmosferze klient-serwer), używając pliku wsadowego pewnego rodzaju, skopiuję plik cały plik (300-900 MB) do / dev / shm, uruchom program z wyjściem do / dev / shm, zapisz wyniki z powrotem na serwer i usuń z / dev / shm

Oczywiście, gdybym miał mniej pamięci RAM, nie zrobiłbym tego. Zwykle system plików w pamięci / dev / shm odczytuje jako rozmiar stanowiący połowę dostępnej pamięci RAM. Jednak zwykłe użycie pamięci RAM jest stałe. Tak naprawdę nie można tego zrobić na urządzeniu o pojemności 2 GB lub mniejszej. Aby zmienić parafrazę w hiperbolę, w pamięci RAM często występują rzeczy, których nawet system nie zgłasza dobrze.

David Grove
źródło
(Myślę, że jest to w duchu tego, o co pierwotnie pytano.) Mam na myśli w zasadzie to, że czuję się dobrze używając / dev / shm jako dysku RAM, o ile mam wystarczającą ilość pamięci. Jeśli jest to nieefektywne, nie powinno cię to zniechęcać, ale powinno wywołać pytanie typu „Jak mogę mieć dysk RAM na Linuksie?”. Odpowiedź brzmi / dev / shm
David Grove