it-swarm-ko.tech

'kill -9'가 작동하지 않으면 어떻게합니까?

kill -9 <pid>로 죽일 수없는 프로세스가 있습니다. 특히 내가 그 프로세스의 소유자이기 때문에 그러한 경우의 문제는 무엇입니까? 나는 그 kill 옵션을 피할 수 없다고 생각했다.

491
tshepang

kill -9 ( SIGKILL )는 프로세스를 강제 종료 할 권한이있는 경우 항상 작동합니다. 기본적으로 프로세스는 setuid 또는 setgid가 아니어야 시작하거나 루트 여야합니다. 한 가지 예외가 있습니다. root조차도 치명적인 신호를 PID 1 (init 프로세스)에 보낼 수 없습니다.

그러나 kill -9즉시 작동하지 않을 수 있습니다. SIGKILL을 포함한 모든 신호는 비동기 적으로 전달됩니다. 커널이 신호를 전달하는 데 시간이 걸릴 수 있습니다. 일반적으로 신호를 전달하는 데 최대 몇 마이크로 초가 걸리며, 대상이 시간 조각을 얻는 데 걸리는 시간입니다. 그러나 대상에 신호가 차단됨 인 경우 대상이 차단을 해제 할 때까지 신호가 대기됩니다.

일반적으로 프로세스는 SIGKILL을 차단할 수 없습니다. 그러나 커널 코드는 system calls 를 호출 할 때 커널 코드를 실행할 수 있으며 프로세스는 커널 코드를 실행합니다. 커널 호출은 시스템 호출을 방해 할 때 모든 신호를 차단하여 커널 어딘가에 데이터 구조가 잘못 형성되거나보다 일반적으로 일부 커널 불변이 위반 될 수 있습니다. 따라서 (버그 또는 잘못된 설계로 인해) 시스템 호출이 무기한으로 차단되면 프로세스를 종료시킬 수있는 방법이 사실상 없을 수 있습니다. (그러나 시스템 호출을 완료하면 프로세스 will 종료됩니다.)

시스템 호출에서 차단 된 프로세스는 ninterruptible sleep 에 있습니다. ps 또는 top 명령은 (대부분의 유니스에서) 상태를 D (원래“ d isk”라고 생각합니다.).

중단없는 긴 휴면 상태의 전형적인 경우는 서버가 응답하지 않을 때 NFS 이상의 파일에 액세스하는 프로세스입니다. 현대적인 구현에서는 무정전 절전 모드를 적용하지 않는 경향이 있습니다 (예 : Linux에서 intr 마운트 옵션을 사용하면 신호가 NFS 파일 액세스를 방해 할 수 있습니다).

Z 또는 H 출력에서 ​​ps (또는 Linux의 경우 top로 구분 된 항목을 알 수 없음)로 표시된 항목이 표시 될 수 있습니다. 이들은 기술적으로 프로세스가 아니며 좀비 프로세스이며 프로세스 테이블의 항목에 불과하므로 부모 프로세스가 자식의 죽음을 알 수 있습니다. 부모 프로세스가 주의를 기울이는 (또는 죽을 때) 사라질 것입니다.

때때로 프로세스가 존재하며 다음으로 인해 종료 될 수 없습니다.

  • 좀비입니다. 즉 부모가 종료 상태를 읽지 않은 프로세스. 이러한 프로세스는 PID 입력 이외의 리소스를 사용하지 않습니다. top에서 Z 신호
  • 잘못된 무정전 수면. 버그 커널 코드 및/또는 버그 하드웨어의 조합으로 발생해서는 안됩니다. 유일한 방법은 재부팅하거나 기다리는 것입니다. top에서는 D로 표시됩니다.
101
Maciej Piechotka

좀비 프로세스 가있는 것 같습니다. 이것은 해롭지 않습니다. 좀비 프로세스가 소비하는 유일한 리소스는 프로세스 테이블의 항목입니다. 부모 프로세스가 죽거나 아이의 죽음에 반응하면 사라집니다.

top 또는 다음 명령을 사용하여 프로세스가 좀비인지 확인할 수 있습니다.

ps aux | awk '$8=="Z" {print $2}'
32
Josh

단서가 있는지 /var/log/kern.log/var/log/dmesg (또는 동등한 항목)를 확인하십시오. 내 경험상 이것은 NFS 마운트의 네트워크 연결이 갑자기 끊어 지거나 장치 드라이버가 충돌했을 때만 발생했습니다. 하드 드라이브가 충돌하면 발생할 수 있다고 생각합니다.

lsof를 사용하여 프로세스가 어떤 장치 파일을 열 었는지 확인할 수 있습니다.

26
LawrenceC

@ Maciej 's 및 @ Gilles 's 답변으로 문제를 해결할 수없고 프로세스를 인식하지 못하는 경우 (그리고 배포판에 어떤 것이 있는지 묻습니다. 답을 찾지 마십시오). 루트킷 및 소유 한 다른 징후 를 확인하십시오. 루트킷은 프로세스를 종료시키지 못하게 할 수 있습니다. 실제로 많은 사람들이 당신이 그들을 보지 못하게 할 수 있습니다. 그러나 1 개의 작은 프로그램을 수정하는 것을 잊어 버린 경우 발견 될 수 있습니다 (예 : top는 수정했지만 htop는 수정하지 않음). 아마도 이것은 사실이 아니지만 미안보다 안전합니다.

17
xenoterracide

킬은 실제로 신호를 보내는 것을 의미합니다. 보낼 수있는 여러 신호가 있습니다. kill -9는 특별한 신호입니다.

신호를 보낼 때 응용 프로그램이 신호를 처리합니다. 그렇지 않으면 커널이 처리합니다. 애플리케이션에 신호를 포착 할 수 있습니다.

그러나 나는 살인 9가 특별하다고 말했다. 응용 프로그램이 얻지 못한다는 점에서 특별합니다. 커널로 직접 이동하여 가능한 첫 번째 기회에서 응용 프로그램을 실제로 종료합니다. 다른 말로하면 죽었다

kill -15는 SIGNAL TERMINATE를 나타내는 SIGTERM 신호를 전송합니다. 즉, 응용 프로그램이 종료되도록 지시합니다. 이것은 응용 프로그램에 종료 시간을 알려주는 친숙한 방법입니다. 그러나 응용 프로그램이 응답하지 않으면 kill -9가 종료합니다.

kill -9가 작동하지 않으면 아마도 커널에 문제가있는 것입니다. 재부팅이 순서대로 이루어집니다. 나는 그 일이 일어났다는 것을 기억할 수 없다.

11
DeveloperChris

먼저 좀비 프로세스가 있는지 확인하십시오 (매우 가능합니다).

ps -Al

다음과 같은 내용이 표시됩니다.

0 Z  1000 24589     1  0  80   0 -     0 exit   ?        00:00:00 soffice.bin <defunct>

(왼쪽의 "Z"참고)

5 번째 열이 1이 아니면 상위 프로세스가 있음을 의미합니다. 부모 프로세스 id를 강제 종료하십시오.

PPID가 1이면 DO N'T KILL IT !!이면 다른 장치 나 프로세스와 관련이있을 수 있습니다.

예를 들어, 마운트 된 장치 또는 Samba를 사용중인 경우 마운트 해제하십시오. 좀비 프로세스가 해제 될 수 있습니다.

NOTE : ps -Al (또는 top)는 "Z"대신 "D"를 표시하며 원격 마운트 (NFS와 같은)와 관련 될 수 있습니다. 내 경험에 따르면 재부팅하는 것이 유일한 방법이지만 해당 사례를 자세히 다루는 다른 답변을 확인할 수 있습니다.

11
lepe

초기화 과정은 SIGKILL에 면역입니다.

이것은 커널 스레드, 즉 PPID가 0 인 "프로세스"에도 적용됩니다.

10
jlliagre

다른 사람들이 언급했듯이, 무정전 수면 과정은 즉시 (또는 경우에 따라) 죽일 수 없습니다. 특정 프로세스, 특히 프로세스가 NFS를 기다리는 일반적인 경우에이 문제를 해결하기 위해 TASK_KILLABLE이라는 다른 프로세스 상태가 추가되었다는 점은 주목할 가치가 있습니다. http://lwn.net/Articles/288056/ 참조

불행히도 이것이 커널의 어느 곳에서나 NFS가 아니라고 생각합니다.

10
user36054

좀 더 살펴볼 수 있도록 작은 스크립트를 만들었습니다!

이것을 사용하여 경로에 주어진 이름을 가진 프로세스를 죽일 수 있습니다 (주의하십시오!) 또는 "-u username"매개 변수를 사용하여 주어진 사용자의 프로세스를 죽일 수 있습니다.

#!/bin/bash

if [ "$1" == "-u" ] ; then\n
        PID=`grep "$2" /etc/passwd | cut -d ":" -f3`
        processes=`ps aux | grep "$PID" | egrep -v "PID|ps \-au|killbyname|grep" | awk '{ print $2}'`
        echo "############# Killing all processes of user: $2 ############################"
else
        echo "############# Killing processes by name: $1 ############################"
        processes=`ps aux | grep "$1" | egrep -v "killbyname|grep" | awk '{ print $2}' `
fi


for process in $processes ; do
        # "command" stores the entire commandline of the process that will be killed
        #it may be useful to show it but in some cases it is counter-productive
        #command=`ps aux | grep $process | egrep -v "grep" | awk '{ print $2 }'`
        echo "Killing process: $process"
        echo ""
        kill -9 $process
done
6
user36035

프로세스에 kill -9를 보내더라도 pid는 중지되지만 프로세스는 자동으로 다시 시작됩니다 (예 : gnome-panel, 다시 시작됩니다) : 여기에 해당 될 수 있습니까?

5
dag729

에서 여기서는 원래 :

strace에 아무것도 표시되지 않는지 확인

strace -p <PID>

gdb로 프로세스에 연결해보십시오

gdb <path to binary> <PID>

프로세스가 마운트 해제 할 수있는 장치와 상호 작용하는 경우 커널 모듈을 제거하거나 물리적으로 분리/분리하십시오 ... 그런 다음 시도하십시오.

2
nmz787

나는 이런 종류의 문제가 있었다. 이것은 strace로 시작하여 Ctrl + C으로 중단 된 프로그램입니다. T (추적 또는 중지) 상태가되었습니다. 정확히 어떻게되는지 모르겠지만 SIGKILL로 죽일 수 없었습니다.

간단히 말해서, 나는 gdb로 그것을 죽이는 데 성공했습니다.

gdb -p <PID>
> kill
Kill the program being debugged? (y or n) y
> quit

Gilles의 대답에 대한 단서를 바탕으로 시스템 리소스를 사용하고있는 "Z"( "")로 표시된 프로세스가 있었으며, 포트가 열려 있고 청취 할 수있었습니다. 이것은 kill -9 그 위에. 부모는 "1"(즉, init)이므로 이론적으로 사라져야합니다. 그러나 그것은 달리지 않았지만 주위에 붙어있었습니다.

제 경우에는 좀비이지만 여전히 리소스를 소비하고 있습니다 ... FWIW.

그리고 그것은 kill -9.

그리고 부모는 init이지만 거두지 않았습니다 (정리되지 않았습니다). 즉 init에는 좀비 아이가있었습니다.

그리고 문제를 해결하기 위해 재부팅 할 필요가 없었습니다. 재부팅으로 문제가 해결되었지만 더 빨리 종료되었습니다. 우아하지는 않았지만 여전히 가능했습니다.

그리고 좀비 프로세스가 소유 한 LISTEN 포트였습니다 (로컬 호스트에 로컬 호스트에 연결된 CLOSE_WAIT 상태와 같은 다른 포트도 있습니다). 그리고 그것은 여전히 ​​연결을 받아 들였습니다. 좀비로도. 포트를 정리하지는 않았지만 들어오는 연결은 여전히 ​​TCP 수신 포트의 백 로그에 추가되었지만 수락 될 가능성은 없었습니다.

내부에 스레드가있어 "시스템 호출"(이 인스턴스에서는 ioctl)을 실행하는 데 몇 시간이 걸렸습니다 (예상 됨). 분명히 시스템은 그로부터 돌아올 때까지 "완전히"죽일 수 없습니다. 몇 시간 후 예상대로 소켓이 모두 닫히고 소켓이 모두 닫혔습니다. 그것은 끔찍한 죽음의 시간입니다!

또한 dmesg를 확인하여 커널 패닉 (즉, 커널 버그)이 있는지 확인하십시오.

0
rogerdpack