其實這個問題在richard stevens的《unix網路程式設計指南》卷一里有很詳細的
解答(中文版p166-168頁)。這裡我只是寫幾個基本的例子來驗證這個問題。
首先宣告乙個問題:當兩個socket的address和port相衝突,而你又想重用地
址和埠,則舊的socket和新的socket都要已經被設定了so_reuseaddr特性,只
有兩者之一有這個特性還是有問題的。
so_reuseaddr可以用在以下四種情況下。
(摘自《unix網路程式設計》卷一,即unpv1)
1、當有乙個有相同本地位址和埠的socket1處於time_wait狀態時,而你啟
動的程式的socket2要占用該位址和埠,你的程式就要用到該選項。
2、so_reuseaddr允許同一port上啟動同一伺服器的多個例項(多個程序)。但
每個例項繫結的ip位址是不能相同的。在有多塊網絡卡或用ip alias技術的機器可
以測試這種情況。
3、so_reuseaddr允許單個程序繫結相同的埠到多個socket上,但每個soc
ket繫結的ip位址不同。這和2很相似,區別請看unpv1。
4、so_reuseaddr允許完全相同的位址和埠的重複繫結。但這只用於udp的
多播,不用於tcp。
例子1:測試上面第一種情況。
#include in
.h>
#include
#include
#include
#include <
string
.h>
#define
maxline 100
intmain(
intargc,
char
** argv)
bzero(&servaddr,
sizeof
(servaddr));
servaddr.sin_family=af_inet;
servaddr.sin_addr.s_addr=htonl(inaddr_any);
servaddr.sin_port=htons(port);
if( setsockopt(listenfd, sol_socket, so_reuseaddr, &flag, len) == -
1)
if( bind(listenfd,(
struct
sockaddr*)&servaddr,
sizeof
(servaddr)) ==
-1)
else
printf("bind call ok!/n");
if( listen(listenfd,5) == -1)
for(;;) if
( fork() == 0)
/*child process*/
close(connfd);
exit(0);
/* end parent*/
} }
測試:編譯為f1-9d程式,放到乙個自己path環境變數裡的某個路徑裡,例如$ho
me/bin,執行f1-9d,然後telnet localhost 10013看結果。
2、第二種情況我沒有環境測,所以就不給測試程式了,大家有條件的可以自己寫
乙個來測試一下。
3、測試第三種情況的程式
#include in
.h>
#include
#include
#include
#include <
string
.h>
#define
maxline 100
intmain(
intargc,
char
** argv) if
( (fd2=socket(af_inet,sock_stream,0)) == -1)
bzero(&servaddr1,
sizeof
(servaddr1));
bzero(&servaddr2,
sizeof
(servaddr2));
servaddr1.sin_family=af_inet;
servaddr2.sin_family=af_inet;
if( inet_pton(af_inet, "127.0.0.1", &servaddr1.sin_addr) <= 0) if
( inet_pton(af_inet, "128.160.1.230", &servaddr2.sin_addr) <= 0)
servaddr1.sin_port=htons(port);
servaddr2.sin_port=htons(port);
if( setsockopt(fd1, sol_socket, so_reuseaddr, &flag, len) == -1) if
( setsockopt(fd2, sol_socket, so_reuseaddr, &flag, len) == -1) if
( bind(fd1,(
struct
sockaddr*)&servaddr1,
sizeof
(servaddr1)) == -1) if
( bind(fd2,(
struct
sockaddr*)&servaddr2,
sizeof
(servaddr2)) == -1)
printf("bind fd1 and fd2 ok!/n");
/*put other process here*/
getchar();
exit(0);
/* end */}
4、由於第四種情況只用於udp的多播,和tcp的使用沒多大關係,所以就不寫測試
例子了。自己有興趣的可以寫。
以上的程式都是在linux下編譯通過的。也可以在其他unix平台執行。
埠重用開啟cmdshell
要重用的埠是tomcat的預設http埠8080。源 include pragma comment lib,ws2 32.lib define listen port 8080 int main 此時,已經啟動tomcat,可以通過來訪問tomcat主頁。執行此程式時,如果沒有重用埠,繫結到8080...
學習筆記 socket關於埠重用的學習
這兩天想搭建乙個c2c伺服器的模型,一開始是想用c寫,結果c的各種細節寫的人太煩躁了,就換成了python,原來n百行的 瞬間變成了幾十行,世界一下子就清淨了 這是後話,此文主要是記錄一下埠重用的問題。之前寫socket經常在除錯時候,每次重啟服務端都會在bind時候報錯 埠被占用 這是因為bind...
套接字 實現埠重用
假如埠被socket使用過,並且利用socket.close 來關閉連線,但此時埠還沒有釋放,要經過乙個time wait的過程之後才能使用,這是tnn的相當煩銀的,為了實現埠的馬上覆用,可以選擇setsockopt 函式來達到目的。以下是網上找到的一篇文章的一小段相關例子,試用之後,相當有效果,特...