간단한 데몬을 위한 Python 코드
import socket
import time
import signal
s=socket.socket()
s.bind(('127.0.1.1', 20201))
def stop(*a, **k):
global work
work = False
signal.signal(signal.SIGINT, stop)
signal.signal(signal.SIGTERM, stop)
work = True
while work:
print('working')
time.sleep(1)
s.close()
포트 20201에 바인딩되어 있으므로 인스턴스가 하나만 실행되고 있다고 확신합니다. 다른 인스턴스를 실행하려고 하면 계획대로 오류가 표시됩니다.
Address already in use
하지만 바인딩된 포트에 대한 pid나 기타 정보를 찾는 방법을 찾을 수 없습니다.
netstat -a | grep 20201
아무것도 주지 않았다
lsof -i TCP | grep 20201
아무것도 주어지지 않는다
ss | grep 20201
아무것도 주어지지 않는다
바인딩된 프로세스를 찾는 방법이 있지만 수신 포트는 찾을 수 없나요?
답변1
나는 노력했다 lsof -p <pid of python process>
. 여기에는 다음 줄이 포함됩니다.
python 1834 barmar 3u sock 0,6 0t0 70994705 can't identify protocol
따라서 이러한 방식으로 특정 포트를 바인딩하는 프로세스를 찾을 수 없는 동안 다음을 사용할 수 있습니다.
lsof | grep "can't identify protocol"
포트를 바인딩했지만 연결되지 않았거나 수신 대기 중인 모든 프로세스를 찾습니다. 여러 개가 있는 경우 관심 있는 포트를 사용하고 있는 포트가 무엇인지 알아낼 수 있습니다.
소켓이 이 상태로 들어가는 다른 방법이 있다는 점에 유의하십시오. 위 명령을 실행하면 mysql
오랫동안 유휴 상태였던 프로세스가 나열됩니다. 이는 mysqld
유휴 클라이언트 연결이 시간 초과 후에 닫히기 때문입니다 . mysql
새 쿼리를 보내려고 할 때 이를 감지하고 그 시점에 다시 연결합니다. 그러나 그때까지 클라이언트 프로세스에는 여전히 이전 소켓이 열려 있지만 이와 관련된 TCP 연결은 없습니다.
답변2
귀하의 IP:포트 조합은 다음과 같이 표시될 수 있습니다.고객소켓, 때로는 불운으로 인해 이런 일이 발생합니다(클라이언트 소켓의 로컬 포트는 무작위로 생성된 "임시 포트"입니다). 설정된 TCP 연결을 확인합니다(-l은 청취 소켓을 제한합니다).
ss -tnp |grep :20201
그렇지 않으면 소켓 생성과 바인딩 사이에 소켓 옵션이 적용되고 SO_REUSEADDR
프로세스가 종료된 후 수신 대기 중인 IP:port가 반드시 재사용 가능한 것은 아닙니다(기존 클라이언트 소켓이 기존 IP :port 소스에 연결되어 있지만 TIME_WAIT 상태이기 때문입니다).