Snažím se vytvořit procesní kontejner. Kontejner spustí další programy. Například – bash skript, který spouští běžící úlohy na pozadí s použitím „&“.
Jde mi o to, že když zabiju kontejner, mělo by být zabito vše, co se pod ním vytvořilo. Nejen přímé děti, ale i jejich potomci.
Když jsem s tímto projektem začínal, mylně jsem se domníval, že když zabijete proces, jeho děti budou automaticky zabity také. Hledal jsem radu od lidí, kteří měli stejný nesprávný nápad. I když je možné zachytit signál a předat zabití dětem, to není to, co zde hledám.
Věřím, že to, co chci, bude dosažitelné, protože když zavřete xterm, vše, co v něm běželo, je zabito, pokud to nebylo nohup’d. To zahrnuje osiřelé procesy. To je to, co chci znovu vytvořit.
Mám představu, že to, co hledám, zahrnuje unixové relace.
Pokud by existoval spolehlivý způsob, jak identifikovat všechny potomky procesu, bylo by užitečné jim také posílat libovolné signály. např. SIGUSR1.
Přijatá odpověď:
Pokud vyšlete signál procesu, tento proces bude zabit. Zajímalo by mě, jak se zrodily fámy, že zabití procesu zabije i jiné procesy, zdá se to být obzvláště kontraintuitivní.
Existují však způsoby, jak zabít více než jeden proces. Ale nevyšlete signál jednomu procesu. Celou skupinu procesů můžete zabít odesláním signálu na -1234, kde 1234 je PGID (ID skupiny procesů), což je PID vedoucího skupiny procesů. Když spustíte kanál, celý kanál začíná jako skupina procesů (aplikace to mohou změnit voláním setpgid
nebo setpgrp
).
Když spustíte procesy na pozadí (foo &
), jsou ve své vlastní procesní skupině. Skupiny procesů se používají ke správě přístupu k terminálu; normálně má přístup k terminálu pouze skupina procesů na popředí. Úlohy na pozadí zůstávají ve stejné relaci, ale není zde žádný prostředek, který by celou relaci ukončil nebo dokonce vyjmenoval skupiny procesů nebo procesy v relaci, takže to moc nepomůže.
Když zavřete terminál, jádro pošle signál SIGHUP
všem procesům, které jej mají jako řídící terminál. Tyto procesy tvoří relaci, ale ne všechny relace mají řídicí terminál. Jednou z možností pro váš projekt je proto spustit všechny procesy v jejich vlastním terminálu, vytvořeném skriptem, obrazovkou atd. Zabijte proces emulátoru terminálu, abyste zabili obsažené procesy (za předpokladu, že se neoddělily pomocí setsid ).
Můžete poskytnout větší izolaci spuštěním procesů jako jejich vlastní uživatel, který nedělá nic jiného. Pak je snadné zabít všechny procesy:spusťte kill
(systémové volání nebo obslužný program) jako tohoto uživatele a použijte -1 jako argument PID k ukončení, což znamená „všechny procesy tohoto uživatele“.
Spuštěním obsažených procesů ve skutečném kontejneru můžete zajistit ještě větší izolaci, ale s podstatně větším nastavením.