為什麼會有超時接受?
一般地,我們經常習慣使用阻塞io。
當沒有資料到達的時候,它就會一直阻塞,有資料的時候就會讀取。
因為有可能出現,就是一直等待,等不到結果還繼續等待。所以超時接受可以解決。
如何實現超時控制?
1、實現多路復用
2、 設定套接字的屬性為超時接收。
方法1:
select函式的作用是監聽集合中哪個元素有資料到達
select(xx,***,xx,xx,null); -> 無限等待集合中的資料
-> -> 如果集合中的檔案描述符有資料到達,則函式就會返回。
-> 如果集合中的檔案描述符沒有資料到達在,則函式就會一直阻塞。
每次select之前都要重置時間
select(xx,***,xx,xx,5s); -> 只會在5s內阻塞等待,5s後就會返回。
-> 5s內有資料到達,則函式返回就緒的檔案描述符個數。
-> 5s內沒有資料到達,則5s內會阻塞。
-> 5s後,這個函式就會返回0,不會繼續監聽這個集合。
時間結構體:
struct timeval
例如設定5秒
struct timeval v;
v.tv_sec = 5;
v.tv_usec = 0;
例題: 寫乙個tcp協議伺服器,使用select函式去監聽客戶端的訊息,如果客戶端在5s內沒有資料到達,則列印一句"timeout",如果有資料,就列印客戶端所說的話。
//自定義標頭檔案
#include
"head.h"
intmain
(int argc,
char
*ar**)
// //5. 使用多路復用讀取套接字上資料
fd_set set;
struct timeval v;
int ret;
char buf[
100]
;while(1
)if(ret ==0)
if(ret >0)
}}//5. 阻塞讀取套接字上的資料
/* char buf[100];
while(1) }
*///6. **tcp套接字的資源
close
(sockfd)
;close
(connfd)
;return0;
}
方法2
給套接字設定為超時的屬性
1)機制如何?
如果不給套接字設定屬性,那麼讀取套接字上的資料時預設為阻塞狀態
如果設定超時接收屬性給套接字,那麼讀取套接字資料時,就會有時間的限制。 -> 前一段時間阻塞,時間過了就會返回。
設定超時接收屬性給connfd
recv(connfd); -> 在規定時間內,就會阻塞讀取,超過了時間,這個recv函式就會返回失敗。
int setsockopt(int sockfd, int level, int optname,const void *optval, socklen_t optlen);
sockfd:套接字
level: 優先順序
sol_socket:套接字
ipproto_ip:ip優先順序
ippro_tcp:tcp優先順序
optname:選項名字
optval: 值,使能為1,不使能為0
optlen: 值型別大小
返回值:
成功:0
失敗:-1
例題:寫乙個tcp伺服器,使用recv函式接收客戶端的訊息,如果伺服器在5s內,沒有資料到達,就列印timeout。
#include
"head.h"
intmain
(int argc,
char
*ar**)
// ./rose 50000
//5. 設定超時屬性給connfd。
struct timeval v;
v.tv_sec =5;
v.tv_usec =0;
setsockopt
(connfd,sol_socket,so_rcvtimeo,
&v,sizeof
(v))
;//6. 不斷讀取connfd的內容。
char buf[
100]=;
while(1
)elseif(
strncmp
(buf,
"quit",4
)==0)
}close
(connfd)
;close
(sockfd)
;return0;
}
socket實現TCP通訊
tcp是一種可靠的,面向連線的協議。在socket中,建立tcp連線的過程大致如下 伺服器端 1.初始化套接字 2.建立伺服器socket 3.將本機位址與伺服器socket繫結在一起 4.伺服器開始監聽 5.伺服器確認請求 確認之前時一種阻塞的狀態 accept 函式生成乙個新的socket。6....
如何在socket程式設計的Tcp連線中實現心跳協議
跳包之所以叫心跳包是因為 它像心跳一樣每隔固定時間發一次,以此來告訴伺服器,這個客戶端還活著。事實上這是為了保持長連線,至於這個包的內容,是沒有什麼特別規定的,不過一般都是很小的包,或者只包含包頭的乙個空包。在tcp的機制裡面,本身是存在有心跳包的機制的,也就是tcp的選項 so keepalive...
程式設計實現基於tcp的socket程式設計
server端 public class server socket.shutdowninput 關閉輸入流 4 獲取輸出流,響應客戶端的請求 outputstream os socket.getoutputstream printwriter pw new printwriter os 包裝為列印...