recv是socket程式設計中最常用的函式之一,在阻塞狀態的recv有時候會返回不同的值,而對於錯誤值也有相應的錯誤碼,分別對應不同的狀態,下面是我針對常見的幾種網路狀態的簡單總結。 首先阻塞接收的recv有時候會返回0,這僅在對端已經關閉TCP連線時才會發生。 而當拔掉裝置網線的時候,recv並不會發生變化,仍然阻塞,如果在這個拔網線階段,socket被關掉了,後果可能就是recv永久的阻塞了。 所以一般對於阻塞的socket都會用setsockopt來設定recv超時。 當超時時間到達後,recv會返回錯誤,也就是-1,而此時的錯誤碼是EAGAIN或者EWOULDBLOCK,POSIX.1-2001上允許兩個任意一個出現都行,所以建議在判斷錯誤碼上兩個都寫上。 如果socket是被對方用linger為0的形式關掉,也就是直接發RST的方式關閉的時候,recv也會返回錯誤,錯誤碼是ENOENT 還有一種經常在程式碼中常見的錯誤碼,那就是EINTER,意思是系統在接收的時候因為收到其他中斷訊號而被迫返回,不算socket故障,應該繼續接收。但是這種情況非常難再現,我嘗試過一邊一直在不停的發訊號,一邊用recv接收資料,也沒有出現過。這種異常錯誤我附近只有一個朋友在用write的時候見到過一次,但是總是會有機率出現的,所以作為完善的程式必須對此錯誤進行特殊處理。一般設定超時的阻塞recv常用的方法都如下:while(1){ cnt = (int)recv(m_socket, pBuf,RECVSIZE, 0); if( cnt >0 ) { //正常處理資料 } else { if((cnt0 接收到資料大小。Linux環境下,須如下定義:struct timeval timeout = {3,0}; //設定傳送超時setsockopt(socket,SOL_SOCKET,SO_SNDTIMEO,(char *)&timeout,sizeof(struct timeval));//設定接收超時setsockopt(socket,SOL_SOCKET,SO_RCVTIMEO,(char *)&timeout,sizeof(struct timeval));
recv是socket程式設計中最常用的函式之一,在阻塞狀態的recv有時候會返回不同的值,而對於錯誤值也有相應的錯誤碼,分別對應不同的狀態,下面是我針對常見的幾種網路狀態的簡單總結。 首先阻塞接收的recv有時候會返回0,這僅在對端已經關閉TCP連線時才會發生。 而當拔掉裝置網線的時候,recv並不會發生變化,仍然阻塞,如果在這個拔網線階段,socket被關掉了,後果可能就是recv永久的阻塞了。 所以一般對於阻塞的socket都會用setsockopt來設定recv超時。 當超時時間到達後,recv會返回錯誤,也就是-1,而此時的錯誤碼是EAGAIN或者EWOULDBLOCK,POSIX.1-2001上允許兩個任意一個出現都行,所以建議在判斷錯誤碼上兩個都寫上。 如果socket是被對方用linger為0的形式關掉,也就是直接發RST的方式關閉的時候,recv也會返回錯誤,錯誤碼是ENOENT 還有一種經常在程式碼中常見的錯誤碼,那就是EINTER,意思是系統在接收的時候因為收到其他中斷訊號而被迫返回,不算socket故障,應該繼續接收。但是這種情況非常難再現,我嘗試過一邊一直在不停的發訊號,一邊用recv接收資料,也沒有出現過。這種異常錯誤我附近只有一個朋友在用write的時候見到過一次,但是總是會有機率出現的,所以作為完善的程式必須對此錯誤進行特殊處理。一般設定超時的阻塞recv常用的方法都如下:while(1){ cnt = (int)recv(m_socket, pBuf,RECVSIZE, 0); if( cnt >0 ) { //正常處理資料 } else { if((cnt0 接收到資料大小。Linux環境下,須如下定義:struct timeval timeout = {3,0}; //設定傳送超時setsockopt(socket,SOL_SOCKET,SO_SNDTIMEO,(char *)&timeout,sizeof(struct timeval));//設定接收超時setsockopt(socket,SOL_SOCKET,SO_RCVTIMEO,(char *)&timeout,sizeof(struct timeval));