Uccidi molte istanze di un processo in esecuzione con un solo comando


75

Supponiamo di avere un migliaio o più di istanze di qualsiasi processo (ad esempio, vi) in esecuzione. Come posso ucciderli tutti in un colpo singolo / comando a una riga / comando singolo?


3
Non è chiaro per quali sistemi si intende che funzioni. Ad esempio, su Linux utilizzo pkilldal procpspacchetto.
Deer Hunter,

La domanda è stata posta da un punto di vista generale. Conoscevo solo due processi come killall e tramite awk / sed. Ma volevo sapere se ci sono altri modi per raggiungere questo obiettivo. Se è fatto diversamente in sistemi diversi, allora voglio sapere in cosa. È molto ingombrante per Google, invece ho pensato di discutere con tutti voi ragazzi esperti.
The Dark Knight,

Risposte:


97

Cosa c'è che non va nel buon vecchio,

for pid in $(ps -ef | grep "some search" | awk '{print $2}'); do kill -9 $pid; done

Ci sono modi per renderlo più efficiente,

for pid in $(ps -ef | awk '/some search/ {print $2}'); do kill -9 $pid; done

e altre varianti, ma a livello base, ha sempre funzionato per me.


1
Su votato, conosceva solo la prima variante. Il secondo sembra più efficiente, grazie.
The Dark Knight,

5
@TheDarkKnight Il problema con questo metodo è che spesso finisci per uccidere più del previsto. Scrivere una "ricerca" affidabile è difficile. Sotto Linux, usa pkill , che gestisce la maggior parte delle sottigliezze.
Gilles 'SO- smetti di essere malvagio' l'

Non sono sicuro che sia così complicato, se stai cercando un binario specifico può essere abbastanza affidabile. Lo eseguo sempre come echo kill -9 $pidprima, quindi so cosa sto ricevendo. Non sono sicuro che AIX abbia pkill, che è il mio pane e burro UNIX. Ed è davvero abbastanza brutto da essere votato in basso - strano.
EightBitTony,

1
Se non assolutamente necessario, è necessario inviare il processo SIGTERM anziché SIGKILL.

Dovrei aggiungere che questi 2 metodi non funzioneranno in tutte le shell, per esempio non funzioneràcsh
non sequitor

38

Usa killall,

killall vi

Questo ucciderà tutti i comandi chiamati 'vi'

Potresti anche aggiungere un segnale, ad esempio SIGKILL

killall -9 vi


Esatto, puoi anche aggiungere il segnale che vuoi, tipokillall -9 vi
Hola Soy Edu Feliz Navidad,

1
Non credo che killall sia il naswer: uccidere per file funziona solo con file eseguibili che vengono tenuti aperti durante l'esecuzione, vale a dire che gli eseguibili impuri non possono essere uccisi in questo modo. Digitare il nome killall potrebbe non avere l'effetto desiderato su sistemi non Linux, specialmente se fatto da un utente privilegiato. Cosa succede se sto cercando di eliminare molte istanze di un processo non Linux? killall -w non rileva se un processo scompare e viene sostituito da un nuovo processo con lo stesso PID tra le scansioni. Se i processi cambiano il loro nome, killall potrebbe non essere in grado di abbinarli correttamente.
The Dark Knight,

13
Si noti che questo funziona solo su Linux e BSD. Su Solaris e altri sistemi killallfa esattamente ciò che suggerisce il nome ... uccide il processo di init.
Bobby,

2
Su AIX, "annulla tutti i processi che hai avviato, ad eccezione di quelli che producono il processo killall".
EightBitTony,

31

pkillè ciò che raccomando, se disponibile ( Linux , FreeBSD , NetBSD , OpenBSD , Solaris ). È possibile specificare i processi in base al nome del comando, alla riga di comando completa o ad altri criteri. Ad esempio, pkill viuccide tutti i programmi il cui nome comando contiene la sottostringa vi. Per uccidere solo i processi chiamati vi, utilizzare pkill -x vi. Per uccidere solo i processi chiamati vicon un ultimo argomento che termina con .conf, usare pkill -fx 'vi.*\.conf'.

Per vedere l'elenco dei PID a cui pkillinviare un segnale, utilizzare pgrep, che ha esattamente la stessa sintassi tranne per il fatto che non accetta un nome o un numero di segnale. Per visualizzare ulteriori informazioni su questi processi, eseguire

ps -p "$(pgrep …)"

Sotto Linux, ps -p $(pgrep -d, …)invece , è necessario (questo è un bug: Linux psnon è conforme a POSIX).

Un altro modo comune per identificare i processi da uccidere sono i processi che hanno un certo file aperto (che può essere l'eseguibile del processo). Puoi elencarli con fuser; usare fuser -kper inviare loro un segnale. Ad esempio, fuser -k /usr/bin/finduccide tutte le istanze in esecuzione di find.

Se c'è un processo in fuga che continua a biforcarsi, potrebbe essere necessario uccidere l'intero gruppo di processi contemporaneamente. Un gruppo di processi è identificato dal negativo del suo leader, che è il processo antenato di tutti i processi nel gruppo. Per vedere il gruppo di processi a cui appartiene un processo, esegui ps -o pgid(oltre a qualsiasi opzione per selezionare i processi da visualizzare). Se si determina che si vuole uccidere il leader del gruppo di processo 1234 e tutti i suoi figli, correre kill -1234o di kill -HUP -1234o di qualsiasi altro segnale.

Se non riesci a trovare un modo migliore, utilizzare pscon le opzioni appropriate per elencare tutti i processi e filtrarlo con grepo con altri comandi di filtraggio del testo. Fare attenzione a non abbinare accidentalmente altri processi che eseguono un comando con un nome simile o con un argomento che contiene quel nome. Per esempio:

kill $(ps -o pid -o comm | awk '$2 == "vi" {print $1}')

Ricordiamo che il grepo awkcomando stesso può essere elencato nella psproduzione ( pse il comando di filtraggio vengono avviati in parallelo, in modo che verrà visualizzato o non dipende temporizzazione). Ciò è particolarmente importante se gli argomenti del comando sono inclusi psnell'output.


Grazie mille, è davvero fantastico. Quello che hai dato è una specie di tutorial. Grazie ancora . Up ha votato
The Dark Knight il

6

pkillè molto bello qui. Puoi dargli molti parametri per affinare il modello.


Non disponibile su tutti gli UNIX e nessuna menzione di un sistema operativo specifico UNIX o UNIX nella domanda.
EightBitTony,

@EightBitTony pkillè disponibile su Linux, BSD e Solaris - afaik. Quindi ha una diffusione maggiore di killall.
Nils,

Sono d'accordo, ma killall è ancora più problematico perché ci sono più strumenti con lo stesso nome, che sembrano avere comportamenti radicalmente diversi. Non mi piacciono neanche le risposte killall. pkill non esiste su AIX o HP-UX e, nonostante ciò a cui piace credere, esiste ancora una base significativa di UNIX non Linux nel mondo.
EightBitTony,

1
@EightBitTony ecco perché la tua risposta è quella accettata. Ma non lo userei su Solaris (che è anche Unix).
Nils,

6

Il modo più semplice per fare è prima verificare che si ottengano gli ID processo corretti con:

pgrep -f [part_of_a_command]

Se il risultato è come previsto. Vai con:

pkill -f [part_of_a_command]

oppure usa:pgrep -f "command name"
Magne il

3

Interessante nessuno ha menzionato questo. pidof genera pid di processi separati da spazi corrispondenti al nome del processo passato. Come tale, è possibile utilizzare direttamente il suo output con killsenza tubazioni. Su Arch Linux che uso

kill -9 $(pidof <proc name>)

L'aspetto negativo di questa soluzione è che non consente l'uso di espressioni regolari.


0

Ti suggerirei di provare pkill.

Ex: ps -ef | pkill -f command

Per mostrare l'elenco di tutti i processi da uccidere, provare innanzitutto a pgrep:

Ex: ps -ef | pgrep -f command


1
Qual è lo scopo di convogliare l'output di ps -efin pkillo pgrep? Questi comandi non vengono letti dall'input standard.
Kusalananda

0

Puoi uccidere più processi diversi usando il comando seguente

pkill -9 -f "\.\/.+\s\.|process1|process2|process3\[^"

Nota che questo ucciderà il processo che corrisponde allo schema sopra, significa process1abc process2def process3ghianche che verrà ucciso.


-1

pgrep "name-of-application" | xargs kill -9

Era abbastanza semplice da ricordare e ha funzionato bene per me.


-2
$ ps -eaf  | grep "xyz" | grep -v grep | awk 'print $2' | xargs kill

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.