1、Socket有三種類型:
(1)流式通訊端:SOCK_STREAM。
流式通訊端使用TCP協議,可以提供可靠的、連線導向的通訊流。
(2)資料通訊端: SOCK_DGRAM。
資料通訊端使用UDP協議,定義了一種不需連線的服務
(3)原始通訊端:SOCK_RAW。
原始通訊端直接基於IP協議,主要用於新的網路通訊協定的測試等
2、網路地址:
(1) 在socket程式設計中,struct sockaddr用於記錄網路地址,它的定義是:
struct sockaddr{
u_short sa_family; //協議族,採用“AF_XXX”的形式,如:AF_INET(IP協議族)
char sa_data[14]; //14位元組的特定協議地址
}
(2)實際的應用中,我們記錄網路地址的資料結構是:struct sockaddr_in,它的定義是:
struct sockaddr_in{
short int sin_family; //協議族
unsigned short int sin_port; //連接埠號碼
struct in_addr sin_addr; //協議特定地址
unsigned char sin_zero[8]; //填0
}
使用sockaddr_in代替sockaddr的原因是,它操作起來比較簡單,如上面的定義可以知,sockaddr_in下的資料結構是sockaddr下sa_data[14]的細分:連接埠,地址,沒用的部分,讓他們分別儲存。
(3)在struct sockaddr_in中,又有一個新的資料結構 struct in_addr,它的定義是:
typedef struct in_addr{
union{
struct{
unsigned char s_b1,
s_b2,
s_b3,
s_b4;
}S_un_b;
struct{
unsigned short s_w1,
s_w2;
}S_un_w;
unsigned long S_addr;
}S_un;
}IN_ADDR;
(4)IP地址通常由數字加點(192.168.0.1)的形式表示,而在struct in_addr 中使用的IP地址是由32位的整數表示的,為了完成轉換我們可以使用下面兩個函數:
int inet_aton(const char *cp,struct in_addr * inp);
char * inet_ntoa(struct in_addr in);
函數名中,a代表 ascii,n代表network,inet_aton是將a.b.c.d形式的IP地址轉換為32位的IP,儲存在inp指標裡面。
inet_ntoa是將32位IP轉換為a.b.c.d的格式
3、位元組序轉換
不同類型的CPU對變數的位元組儲存順序有可能不同:有的系統是高位在前,低位在後,而有的系統是低位在前,高位在後。而網路傳輸的資料順序一定要是同意的,所以當內部位元組儲存順序和網路位元組序不同時,就要進行轉換。
位元組序轉換函式:
(1)htons,host to net short,把unsigned short 類型從主機序列轉換到網路序列
(2)htonl,host to net long,把unsigned long類型從主機序列轉換到網路序列
(3)ntohs,net to host short
(4)ntohl, net to host long
其中,(1)(2)在發送資料時使用,(3)(4)在接受時使用
4、IP與主機名稱
在網路中表示一台主機可以用IP地址,也可以使用主機名稱。
struct hostent * gethostbyname(const char * hostname)
struct hostent{ //hostent == hostentry,主機記錄
char * h_name; //主機的正式名稱
char * h_aliases; //主機的別名
int h_addrtype; //主機的地址類型 AF_INET
int h_length; //主機的地址長度
char ** h_addr_list; //主機的IP地址清單
}
#define h_addr h_addr_list[0]; //主機的第一個IP地址
5、Socket編程函數:
(1)socket,建立一個socket
(2)bind,用於綁定IP地址和連接埠號碼到socket
(3)connect,該函數用於與伺服器建立串連
(4)listen,設定伺服器能處理的最大串連要求
(5)accept,用來等待來自用戶端的socket串連請求
(6)send,發送資料
(7)recv,接受資料