2010-10-16 50 views
8

我有一個red5 server(JAVA)在我的Linux服務器上運行。Linux:如何殺死使用1935端口的程序?

有時,服務器關閉。當我嘗試重新啓動時,出現錯誤:

「綁定錯誤,此端口在使用中」。

所以我儘量殺死killall -9 java的 服務器,並嘗試重新啓動服務器:同樣的錯誤。

我必須等待一段時間(大約2-3分鐘),然後重新啓動它:即有效。

我只需要知道爲什麼當我殺死進程時,我仍然需要等待2-3分鐘,然後我才能再次運行服務器。

有沒有辦法立即殺死這個過程並釋放端口?

+1

我不相信將SIGKILL歸咎於港口失敗清理的答案。操作系統完全知道進程已經結束,並以標準方式放棄其資源。剛關閉的TCP監聽端口的標準方式在一段時間內不能連接到錯誤的服務器。這可以通過使用Justin的答案中提到的SO_REUSEADDR來輕鬆避免。 – 2010-10-16 13:57:58

回答

16

如果你是你的服務器的肯定舊實例持有端口,只需運行jps,找到你的服務器的PID在列表中,然後運行kill -9 my_pid

對於一般非Java的過程中,通常lsof -i :1935對我的作品。再次,採取PID並殺死這個過程。

5

如果可能,應在程序設置其套接字時使用套接字SO_REUSEADDR選項。這樣,您可以在程序重新啓動時立即重新使用套接字,而不必等2-3分鐘。

有關更多信息,請參閱javadoc setReuseAddress。特別是:

When a TCP connection is closed the connection may remain in a timeout state for a period of time after the connection is closed (typically known as the TIME_WAIT state or 2MSL wait state). For applications using a well known socket address or port it may not be possible to bind a socket to the required SocketAddress if there is a connection in the timeout state involving the socket address or port.

Enabling SO_REUSEADDR prior to binding the socket using bind(SocketAddress) allows the socket to be bound even though a previous connection is in a timeout state.

+0

他可以通過調用setReuseAddress http://download.oracle.com/javase/1.4.2/docs/api/java/net/ServerSocket.html – 2010-10-16 12:59:29

+0

來在Java中執行此操作看起來我們都在想同一件事 - 請參閱我的編輯:) – 2010-10-16 13:00:39

9

問題是在殺死。

如果使用SIGKILL(-9)終止進程,則會立即終止進程。所以港口仍然分配,直到(一分鐘後)O.S.注意到問題。在SIGKILL之前嘗試SIGHUP和SIGINT(按順序)。

在任何情況下,請使用netstat -a -t -p來驗證哪個進程已獲取端口。

1

kill -9應該默認使用。該過程無法清理內部事物。 要使用爲例8000端口殺應用程序的PID:

kill $(netstat -nptl | awk '/:8000/{gsub("/.*", ""); print $7}') 
+0

kill:usage:kill [-s sigspec | -n signum | -sigspec] pid | jobspec ...或kill -l [sigspec] – yarek 2010-10-17 14:58:36

+0

似乎這個命令有錯誤:kill:usage:kill [-s sigspec | -n signum | -sigspec] pid | jobspec ...或者kill -l [sigspec] – yarek 2010-10-17 14:59:07

1

這是一個方便的oneliner:

kill $(fuser 1935/tcp) 
7

立即終止進程和端口版本:

fuser -k 1935/tcp