Tworzę dystrybucję Linuksa i teraz potrzebuję programu init. Potrafię dobrze napisać c-c i wiem trochę o Linuksie (niewiele, ale używam arch-linuxa do programowania od 4 lat), więc pomyślałem, że powinienem spróbować napisać własny skrypt skryptowy w C. tylko zastanawiam się, jakie zadania wykonuje init, aby skonfigurować system dla prostej powłoki? (Kiedy pytam „co robi init?”, Wiem, czym jest init i do czego służy. Po prostu nie wiem, jakie zadania wykonuje.)
Nie potrzebuję kodu i prawdopodobnie nie trzeba nawet podstawowych komend, ale ja nie potrzebuję kolejność, w jakiej są one uruchamiane w.
Odpowiedzi:
System 5
init
opowie ci tylko niewielką część historii.Istnieje rodzaj krótkowzroczności, która wpływa na świat Linuksa. Ludzie myślą, że używają czegoś o nazwie „System 5
init
”, i to jest zarówno tradycyjne, jak i najlepsze miejsce na start. W rzeczywistości tak nie jest.Na początek tradycja nie jest tym, co mówią tacy ludzie. System 5
init
i System 5rc
datują się na AT&T UNIX System 5, który był prawie tak daleko od pierwszego UNIX-a, jak obecnie (powiedzmy) po pierwszej wersji Linux-Mandrake.1st Edition UNIX miał tylko
init
. Nie miałrc
. Język asemblerowy 1. edycjiinit
( którego kod został przywrócony i udostępniony przez Warren Toomey i in. ) Bezpośrednio spawnował i odradzał 12getty
procesów, montował 3 wbudowane systemy plików z wbudowanej tabeli i bezpośrednio uruchamiał program z katalogu domowego użytkownik o nazwiemel
.getty
Stół był również bezpośrednio na obrazie programu.Minęła kolejna dekada po UNIX System 5, kiedy pojawił się tak zwany „tradycyjny” system inicjujący Linuksa. W 1992 r. Miquel van Smoorenburg (ponownie) napisał Linux
init
+rc
i powiązane z nim narzędzia, które ludzie nazywają teraz „Systemem 5init
”, mimo że tak naprawdę nie jest to oprogramowanie z systemu UNIX System 5 (i to nie tylkoinit
).System 5
init
/rc
nie jest najlepszym miejscem do rozpoczęcia, a nawet jeśli dodaje się wiedzę o systemd, która nie obejmuje połowy tego, co trzeba wiedzieć. Wiele pracy poświęcono projektowaniu systemu init (dla Linuksa i BSD), co miało miejsce w ciągu ostatnich dwóch dekad. Omawiano, podejmowano, projektowano, wdrażano i praktykowano wszelkiego rodzaju decyzje inżynierskie. Komercyjne Unices też wiele zrobiły.Istniejące systemy do nauki i uczenia się od
Oto niepełna lista niektórych głównych systemów inicjujących innych niż te dwa oraz jeden lub dwa z ich (kilku) istotnych punktów:
init
.getty
spawnowanie i zbieranie zombie) do osobnego menedżera usług oraz po prostu obsługę specyficznych dla systemu operacyjnego urządzeń „API” / dowiązań symbolicznych / katalogów i zdarzeń systemowych./bin/rc.init
zadanie, którego zadaniem jest uruchamianie programów, montowanie systemu plików itp. W tym celu można użyć czegoś takiego jak minirc .Co więcej, około 10 lat temu, nie było dyskusji wśród daemontools użytkowników i innych z użyciem
svscan
jako procesu nr 1, która doprowadziła do projektów takich jak Paul Jarc na svscan jako proces 1 badaniu , pomysłów Gerrit Pape jest i Laurent Bercot na svscan jako proces 1 .Co prowadzi nas do tego, co robią programy nr 1.
Co robią programy nr 1
Pojęcia tego, co proces „1” ma wykonać, są z natury subiektywne. Znaczącym obiektywnym kryterium projektowym jest to, co musi wykonać proces nr 1 . Jądro nakłada na niego kilka wymagań. I zawsze ma do czynienia z różnymi rzeczami specyficznymi dla systemu operacyjnego. Jeśli chodzi o to, co tradycyjnie zrobił proces nr 1 , to nie jesteśmy na tym minimum i nigdy tak naprawdę nie byliśmy.
Jest kilka rzeczy, których różne jądra systemu operacyjnego i inne programy wymagają od procesu nr 1, z których po prostu nie można uciec.
Ludzie powiedzą ci, że
fork()
tworzenie rzeczy i działanie jako rodzic osieroconych procesów jest podstawową funkcją procesu nr 1. Jak na ironię, to nieprawda. Radzenie sobie z osieroconymi procesami jest (z najnowszymi jądrami Linuksa, jak wyjaśniono na https://unix.stackexchange.com/a/177361/5132 ) częścią systemu, który można w dużej mierze uwzględnić poza procesem nr 1 w innych procesach, takich jak dedykowany kierownik serwisu . Wszystkie są menedżerami usług, które działają poza procesem nr 1:srcmstr
, Kontroler zasobów systemowychrunsvdir
z runitusvscan
z daemontools, Adam Sampsonsvscan
z freedt , Bruce Guentersvscan
z daemontools-encore i Laurent Bercots6-svscan
z s6perpd
od sprawcyservice-manager
z noshPodobnie, jak wyjaśniono na https://superuser.com/a/888936/38062 , cały
/dev/initctl
pomysł nie musi znajdować się w pobliżu procesu nr 1. Jak na ironię, jest to wysoce scentralizowany system, który pokazuje, że można go usunąć z procesu nr 1.Odwrotnie, obowiązkowe rzeczy dla
init
, że ludzie zwykle zapomnieć w ich off-the-top-of-the-head wzorów, są rzeczy, takich jak obsługaSIGINT
,SIGPWR
,SIGWINCH
, i tak dalej wysyłane z jądra i przyjmując różne żądania zmiany stanu systemu wysłane z programów, które „wiedzą”, że pewne sygnały do przetworzenia nr 1 oznaczają pewne rzeczy. (Na przykład: Jak wyjaśniono na https://unix.stackexchange.com/a/196471/5132 , zestawy narzędzi BSD „wiedzą”, żeSIGUSR1
mają określone znaczenie.)Istnieją również jednorazowe zadania inicjalizacji i finalizacji, których nie można uciec lub które będą bardzo cierpieć z powodu niewykonania, takie jak montowanie systemów plików „API” lub opróżnianie pamięci podręcznej systemu plików.
Podstawy radzenia sobie z systemami plików „API” niewiele różnią się od działania
init
ROM 1. edycja UNIX: Jeden zawiera listę informacji zapisanych w programie i po prostumount()
wszystkie wpisy na liście. Znajdziesz ten mechanizm w systemach tak różnorodnych jak BSD (sic!)init
, Od noshsystem-manager
, do systemd.„skonfiguruj system dla prostej powłoki”
Jak zauważyłeś,
init=/bin/sh
nie można zamontować systemów plików „API”, ulega awarii w nieładny sposób bez opróżniania pamięci podręcznej, gdy jeden typexit
( https://unix.stackexchange.com/a/195978/5132 ) i ogólnie pozostawia to (super) użytkownikowi, aby ręcznie wykonał czynności, które sprawiają, że system jest minimalnie użyteczny.Aby zobaczyć, co tak naprawdę nie ma innego wyjścia, jak zrobić w programach procesu nr 1, a tym samym ustawić dobry kurs dla podanego celu projektowego, najlepszym rozwiązaniem jest przyjrzenie się nakładaniu się działania Runit Gerrita Pape'a, Felixa von Minit Leitnera i
system-manager
program z pakietu nosh. Dwie poprzednie pokazują dwie próby bycia minimalistą, ale wciąż radzą sobie z rzeczami, których nie można uniknąć.Ta ostatnia jest użyteczna, sugeruję, ze względu na obszerne ręczne wprowadzanie do
system-manager
programu, który szczegółowo opisuje, jakie systemy plików „API” są zamontowane, jakie zadania inicjujące są uruchamiane i jakie sygnały są obsługiwane; w systemie, który z założenia ma menedżera systemu, po prostu spawnują trzy inne rzeczy (menedżer usług, towarzyszący rejestrator i program do uruchamiania zmian stanu) i robią tylko nieuniknione w procesie nr 1.źródło
launchd
. Czasami ludzie całkowicie zapominają, że OSX jest (świetnym) członkiem dużej rodziny * nix.System V init na Debianie (istnieją inne warianty i odmiany) wykonuje następujące czynności:
/etc/rcX.d/S*
kolejności alfanumerycznej, gdzieX
jest poziom działania. Te skrypty powinny skonfigurować poziom działania. Typowa instalacja to uruchamianie demonów i wykonywanie zadań konfiguracji dla tego poziomu uruchamiania. Jest to jednorazowa czynność wykonywana podczas wchodzenia na poziom uruchamiania./etc/inittab
jako wymagające działania podczas tego poziomu uruchamiania. Jeśli te demony przestaną działać, uruchomi je ponownie. Chociaż możesz mieć dowolnego demona, którym chcesz zarządzać, potrzebujeszinit
co najmniej kilkugetty
, abyś mógł się zalogować.getty
Kończy się po zakończeniu logowania, a następnieinit
uruchamia go ponownie, zapewniając ponowne logowanie.init
automatycznie próby utrzymania go w działaniu. Musisz to określić osobno w/etc/inittab
./etc/rcX.d/K*
kolejności alfanumerycznej, gdzieX
jest poziom działania. Sposobem na wdrożenie zamknięcia lub ponownego uruchomienia jest zdefiniowanie poziomu uruchamiania dla tych zdarzeń i wykonanie ostatniego zadania poleceniahalt
lubreboot
.Jeśli chcesz, możesz więc użyć go
init
jako podstawowego menedżera usług, ale obecnie jego głównym zadaniem jest utrzymaniegetty
dostępności, aby użytkownik mógł się zalogować i rozpocząć przejścia na poziomie uruchamiania.Cokolwiek chcesz. Na Debianie w każdym
/etc/rcX.d
katalogu znajduje się dowiązanie symboliczne do skryptu, w/etc/init.d
którym można w pełni dostosować lub usunąć te skrypty. Kolejność ustala poprzedzając każdy skrypt z00
,01
itpMożesz także określić
-b
opcjęinit
(np. Poprzez linię poleceń jądra), jeśli chcesz po prostuinit
odrodzić powłokę. Kiedy wyjdziesz z powłoki,init
umiera, a kiedyinit
umiera, jądro wpadnie w panikę.źródło
Absolutne minimum, które musi wykonać init, to uruchomić przynajmniej jeden inny program i nigdy nie wychodzić. Jeśli init kończy działanie, system ulega awarii. Podejrzewam, że nawet uruchomienie jednego innego programu nie jest absolutnie konieczne, ale jeśli tego nie zrobisz, init musiałby być odpowiedzialny za zrobienie wszystkiego, co powinien zrobić system, albo nie byłoby to bardzo przydatne.
źródło
init
możesz robić co chceszinit jest dowolnym plikiem wykonywalnym wywoływanym przez jądro Linuksa na końcu procesu rozruchu (i jedynym takim plikiem wykonywalnym).
Zwykle jest implementowany jako plik wykonywalny ELF, ale może nawet być skryptem powłoki z
chmod +x
: Init jako skryptem powłokiTypowe implementacje, takie jak sysemd, odczytują pliki konfiguracyjne, ofen
/etc/initrc
, a następnie rozwidlają kilka procesów użytkownika w oparciu o te konfiguracje, aby zaimplementować różne aspekty systemu.Jest to jednak całkowicie specyficzne dla implementacji, dlatego na pytanie nie można odpowiedzieć bez podania konkretnej implementacji. Na przykład bawiłem się
init
procesem, który po prostu wykonujereboot
syscall w celach edukacyjnych.Jądro systemu Linux
/init
domyślnie po prostu szuka pliku wykonywalnego w ścieżce , ale można to zastąpićinit=
parametrem wiersza polecenia jądra systemu Linux.Jednym świetnym sposobem na zabawę
init
jest użycie QEMU, ponieważ można przekazać parametry wiersza polecenia jądra do QEMU z wiersza polecenia QEMU z-append
opcją i bez obawy o uszkodzenie pulpitu.Oto moja minimalna, w pełni zautomatyzowana konfiguracja Buildroot + QEMU, która sprawia, że bardzo łatwo jest bawić się własnymi initami w celu wyjaśnienia sprawy.
źródło
Jeśli jesteś zaangażowany w modułową zasadę „zrób jedną rzecz i zrób to dobrze”,
init
program powinien rozpocząć procesy.Rozpocznij procesy
Powinien zostać wykonany po pomyślnym zdekompresowaniu jądra, dbając o wszystkie podstawowe zadania związane z inicjowaniem wszystkich początkowych procesów wymaganych przez system (takich jak montowanie napędów znalezionych w / etc / fstab, uruchamianie interfejsów sieciowych i wkrótce).
Ponieważ proces uruchamiania i zamykania jest zasadniczo odwrotny względem siebie, program inicjujący często zapewnia również zatrzymanie procesów po wydaniu polecenia zamknięcia.
Zatrzymaj procesy
Oznacza to, że musi zatrzymać procesy zgodnie ze stroną
kill -9
podręcznika tego procesu (innymi słowy, nie tylko rażąco , powinien sprowadzić proces w sposób, w jaki chce się zakończyć), odmontować dyski i ostatecznie wydać polecenie końcowego wyłączenia zasilania .Bibliografia
Dobrym odniesieniem do tego, jak robią to inni, jest przyjrzenie się skryptom /etc/rc.d Slackware , a także prostemu systemowi inicjalizacji, który już istnieje, takim jak ninit (następca minit). Ma nadzór nad procesem (co oznacza, że jeśli proces umrze, zostanie ponownie uruchomiony), co prawdopodobnie nie jest zadaniem init, ale nadal jest dość prosty i łatwy do zrozumienia, szczególnie za pomocą przykładowych skryptów autora.
źródło