1.用socket()函式建立socket,返回值為socket的識別符號sockfd,這個識別符號在後面都會用到
2.用結構體sockaddr_in去儲存伺服器資訊(協議,埠,ip)
聯合體成員:struct sockaddr_in sever_addr
3.用bind()函式繫結資訊
注意:第二個引數要強轉成(struct sockaddr *)型別
4.用sockaddr_in函式儲存客戶端資訊
6.在while迴圈裡面用recvfrom()函式不停的接收資訊並列印
7.用close函式關閉socket
伺服器**:
#include
#include
/* see notes */
#include
#include
#include
#include
#include
#include
intmain()
struct sockaddr_in server_addr;
//用於儲存伺服器資訊
memset
(&server_addr,0,
sizeof
(server_addr));
//清零
server_addr.sin_family = af_inet;
//協議
server_addr.sin_port =
8000
;//埠
server_addr.sin_addr.s_addr =
inet_addr
("127.0.0.1");
//ip位址
//繫結資訊
int ret =
bind
(sockfd,
(struct sockaddr *
)&server_addr,
sizeof
(server_addr));
if(-1
== ret)
char buf[32]
=;struct sockaddr_in client_addr;
//用於儲存客戶端資訊
int length =
sizeof
(client_addr)
;while(1
)printf
("接收%d : %s\n"
, client_addr.sin_port, buf)
;memset
(buf,0,
sizeof
(buf));
}return0;
}
1.用socket()函式建立socket,返回值為socket的識別符號sockfd,後面都會用到識別符號
2.用sockaddr_in 結構體儲存伺服器資訊
3.在while迴圈裡面
4.用sendto()函式不停的傳送資訊
5.用close函式關掉socket
客戶端**:
#include
#include
/* see notes */
#include
#include
#include
#include
#include
#include
intmain()
char buf[32]
=;struct sockaddr_in server_addr;
memset
(&server_addr,0,
sizeof
(server_addr));
server_addr.sin_family = af_inet;
server_addr.sin_port =
8000
; server_addr.sin_addr.s_addr =
inet_addr
("127.0.0.1");
int length =
sizeof
(server_addr)
;while(1
)if(!
strcmp
(buf,
"bye"))
memset
(buf,0,
sizeof
(buf));
}close
(sockfd)
;return0;
}
函式原型:函式原型:ssize_t recvfrom(int sockfd,void *buf,int len,unsigned int flags, struct sockaddr *from,socket_t *fromlen); ssize_t 相當於 int,socket_t 相當於int ,這裡用這個名字為的是提高**的自說明性。
功能:經socket接收資料
引數:
sockfd:標識乙個已連線套介面的描述字。
buf:接收資料緩衝區。
len:緩衝區長度。
返回值:成功則返回接收到的字元數,失敗返回-1.
函式原型:ssize_t sendto(int sockfd, const void *buf, size_t len, int flags, const struct sockaddr *dest_addr, socklen_t addrlen);
功能:使用指定的 sockfd,將指定位元組數的資料傳送到指定的終結點。
引數:
sockfd:正在監聽埠的套介面檔案描述符,通過socket獲得
buf:傳送緩衝區,往往是使用者定義的陣列,該陣列裝有要傳送的資料
len:傳送緩衝區的大小,單位是位元組
flags:填0即可
dest_addr:指向接收資料的主機位址資訊的結構體,也就是該引數指定資料要傳送到哪個主機哪個程序
addrlen:表示第五個引數所指向內容的長度
返回值:成功返回傳送成功的資料長度,失敗返回-1
函式原型:int socket(int sockfd, int type, int protocol);
功能:用於建立乙個socket描述符(socket descriptor),它唯一標識乙個socket。這個socket描述字跟檔案描述字一樣,後續的操作都有用到它,把它作為引數,通過它來進行一些讀寫操作。
引數:
第乙個引數:即協議域,又稱為協議族(family)。常用的協議族有,af_inet、af_inet6、af_local(或稱af_unix,unix域socket)、af_route等等。協議族決定了socket的位址型別,在通訊中必須採用對應的位址,如af_inet決定了要用ipv4位址(32位的)與埠號(16位的)的組合、af_unix決定了要用乙個絕對路徑名作為位址。
第二個引數:指定socket型別。常用的socket型別有,sock_stream、sock_dgram、sock_raw、sock_packet、sock_seqpacket等等(socket的型別有哪些?)。
第三個引數(預設為0):指定協議。常用的協議有,ipproto_tcp、ipptoto_udp、ipproto_sctp、ipproto_tipc等,它們分別對應tcp傳輸協議、udp傳輸協議、stcp傳輸協議、tipc傳輸協議。
注意: 並不是上面的type和protocol可以隨意組合的,如sock_stream不可以跟ipproto_udp組合。當protocol為0時,會自動選擇type型別對應的預設協議。
返回值:成功的話返回socket的標示符sockid,失敗的話返回-1;
函式原型:int bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
功能:把乙個位址族中的特定位址賦給socket。當我們呼叫socket建立乙個socket時,返回的socket描述字它存在於協議族(address family,af_***)空間中,但沒有乙個具體的位址。如果想要給它賦值乙個位址,就必須呼叫bind()函式,否則就當呼叫connect()、listen()時系統會自動隨機分配乙個埠。
引數:
第乙個引數:即socket描述字,它是通過socket()函式建立了,唯一標識乙個socket。bind()函式就是將給這個描述字繫結乙個名字。
第二個引數:乙個const struct sockaddr *指標,指向要繫結給sockfd的協議位址。這個位址結構根據位址建立socket時的位址協議族的不同而不同,如ipv4對應的是:
struct sockaddr_in server_addr;
注意要強轉成struct sockaddr型別
返回值:成功返回0,失敗返回-1;
通常伺服器在啟動的時候都會繫結乙個眾所周知的位址(如ip位址+埠號),用於提供服務,客戶就可以通過它來接連伺服器;而客戶端就不用指定,有系統自動分配乙個埠號和自身的ip位址組合。這就是為什麼通常伺服器端在listen之前會呼叫bind(),而客戶端就不會呼叫,而是在connect()時由系統隨機生成乙個。
就好像操作完開啟的檔案要呼叫fclose關閉開啟的檔案,在讀寫完成之後最後關閉檔案。
函式原型:int close(int fd);
引數:套接字描述符 socket函式和accept函式的返回值;
Linux系統程式設計之網路程式設計一
tcp面向連線 如打 要先撥號建立連線 udp是無連線的,即傳送資料之前,不需要建立連線。tcp提供可靠的服務,也就是說,通過tcp連線傳送的資料,無差錯,不丟失,不重複,且按序到達 udp盡最大努力交付,即不保證可靠交付 每一條tcp連線只能是點到點的 udp支援一對一,一對多,多對一和多對多的互...
系統程式設計之檔案系統程式設計
系統呼叫 所有的作業系統都提供多種服務的入口點,程式由此向核心請求服務。這些可直接進入核心的入口點被稱為系統呼叫。不同作業系統提供了自己的一套系統呼叫,所以系統呼叫無法實現跨平台使用。而且頻繁地系統呼叫,在使用者態和核心態之間切換,很耗費資源,效率不高。c標準庫提供了操作檔案的標準i o函式庫,與系...
系統程式設計之執行緒
pthread t tid 建立執行緒號,多個執行緒可以用陣列來實現,如pthread t tid 3 函式原型 int pthread create pthread t tid,const pthread attr t restrict attr,void start rtn void void ...