1. 程式人生 > >TCP client和server 程式例子(轉)

TCP client和server 程式例子(轉)

tcp和udp的程式就不貼了,網上例程太多,放在附件裡。下面分別說一下流程和細節
tcp服務端流程:
1、建立socket(socket函式)
2、設定服務端sockaddr_in結構體,並繫結到第一步的socket(bind函式)
3、設定客戶端資訊佇列長度,也就是已經建立連線的客戶端和未連線上客戶端的最大數量,並把socket設為偵聽狀態(listen函式)
4、等待客戶端連線,並得到與該客戶端繫結的socket(accept函式)
5、收發資料(sendrecv函式
6、關閉繫結客戶端的socket,關閉偵聽socket(close函式)
tcp客戶端流程:

1、建立socket

2、

設定要連線的伺服器ip地址和埠到sockaddr_in結構體

3、連線伺服器(connect函式)

4、收發資料

5、關閉客戶端socket
tcp連線時的三次握手:
客戶端connect時發出syn訊號給服務端,服務端收到後返回ack訊號和syn訊號,客戶端收到後傳送ack訊號給服務端。
可以用兩個人線上語音形象的描述三次握手
我對你說:能聽到我說話嗎(syn)?你聽到後跟我說:能聽到(ack),那你能聽到我說話嗎(syn)?我聽到後跟你說:能聽到(ack)。這就確保了訊號在你和我之間的雙向連通
tcp斷開時的四次握手:
A端發出fin訊號,B端收到後返回ack訊號,B端再發fin訊號,A端收到後返回ack訊號。這裡的fin只是代表單邊結束,因為tcp是全雙工,所以必須兩端都斷開才斷開。斷開之後在read會得到一個數據長度0的包,可以用來處理斷開之後的事情


細節:
主要是網路位元組序的問題,需要把sockaddr_in中的ip和port轉換為網路位元組序也就是大端模式,例如:htons(port_number),在sockaddr_in中的埠號是一個short型別,因此是htons(host to net short)。
轉換ip的函式有inet_addr、inet_aton、inet_pton,其中inet_pton比較新,ipv6也可以用,具體使用方法看man手冊。

UDP服務端:

1、建立socket
2、設定服務端sockaddr_in結構體,並繫結到第一步的socket(bind函式)
3、等待客戶端連線,獲得客戶端sockaddr結構體從而知道ip和埠

4、收發資料recvfromsendto函式)
5、關閉服務端socket
UDP
客戶端

1、建立socket
2、設定要連線的伺服器ip地址和埠到sockaddr_in結構體
3、收發資料
4、關閉客戶端socket
細節:
除了網路位元組序最主要的點就是recvfrom這個函數出錯返回後perror打印出的的invalid argument錯誤,原因是ssize_t recvfrom(int sockfd, void *buf, size_t len, int flags,struct sockaddr *src_addr, socklen_t *addrlen)這個函式裡面的addrlen在使用之前必須先初始化為sockaddr結構體的長度,函式執行之後會變成src_addr的真實長 度。如果不初始化,程式能不能執行全憑運氣...
man recvfrom中關於addrlen引數的說明:
If  src_addr  is  not  NULL,  and  the underlying protocol provides the
source address, this source address is filled  in.   When  src_addr  is
NULL,  nothing  is  filled  in;  in this case, addrlen is not used, and
should also be NULL.  The argument addrlen is a value-result  argument,
which  the  caller should initialize before the call to the size of the
buffer associated with src_addr, and modified on return to indicate the
actual  size  of the source address.  The returned address is truncated
if the buffer provided is too small; in this case, addrlen will  return

a value greater than was supplied to the call.