win socket的server的編寫流程:
1、定義win socket 結構和地址結構:SOCKET ServerSocket,ClientSocket;struct sockaddr_in SocketAddress,ClientAddr;
2、載入socket動態連結程式庫:WSAStartup(MAKEWORD(1,1),&WsaData)
3、填寫地址結構:
SocketAddress.sin_family=AF_INET;
SocketAddress.sin_port=htons (servport);
SocketAddress.sin_addr.S_un.S_addr=htonl(INADDR_ANY);
4、將IP地址及連接埠和定義好的socket進行綁定:
bind(ServerSocket,(const sockaddr*)&SocketAddress,sizeof(SocketAddress))
5、將socket設定為監聽狀態:
listen(ServerSocket,5)
6、接受請求,發送應答:
ClientSocket = accept(ServerSocket,(struct sockaddr*)&ClientAddr,&len)
send(ClientSocket,buffer,strlen(buffer),0)
7、例子:
//server端原代碼
#include <winsock.h>
#include <stdlib.h>
#include <iostream>
using namespace std;
int main()
{
//定義socket;
SOCKET ServerSocket,ClientSocket;
//socket 地址結構
struct sockaddr_in SocketAddress;
struct sockaddr_in ClientAddress;
int len;
int ServerPort=5555;//定義伺服器的連接埠
char buff[256];
for(int i=0;i<256;i++)
{
buff[i]='a';
cout<<buff[i];
}
cout<<"/nthese the world in buff"<<endl;
//以下結構儲存windows的socket的詳細資料
WSADATA wsd;
//servport=atoi("servport");//使用者自訂的連接埠
//調用WSAStartup函數來載入指定版本的socket動態連結程式庫,載入之後,socket中的一些函數
WSAStartup(MAKEWORD(1,1),&wsd);//Initialize
ServerSocket=socket(AF_INET,SOCK_STREAM,0);// Creat socket
//server address struct
memset(&SocketAddress,0,sizeof(SocketAddress));
SocketAddress.sin_family=AF_INET;//TCP/IP協議族
SocketAddress.sin_port=htons(ServerPort);//將機器子節順序轉換為TCP/IP網路子節順序
SocketAddress.sin_addr.S_un.S_addr=htonl(INADDR_ANY);//轉換IP,任何網段上的服務程式都可以與該素主機器通訊
bind(ServerSocket,(const sockaddr*)&SocketAddress,sizeof(SocketAddress));//bind address
listen(ServerSocket,5);//listening
//receive looply
while(1)
{
cout<<"waiting .../n";
len=sizeof(ClientAddress);
ClientSocket=accept(ServerSocket,(struct sockaddr*)&ClientAddress,&len);
cout<<"accept client:"<<inet_ntoa(ClientAddress.sin_addr)<<" "<<ntohs(ClientAddress.sin_port)<<endl;
//send....
send(ClientSocket,buff,strlen(buff),0);
closesocket(ClientSocket);
cout<<"[server OK]"<<endl;
}
closesocket(ServerSocket);
WSACleanup();
return 0;
}
SOCKET socket(int af,int type,int protocol);
af用於指定網路類型,一般取AF_INET,表示該通訊端在Internet域中進行通訊,type用於指定通訊端類型,若取SOCK_STREAM表示要建立的是流通訊端,若取SOCK_STREAM表示建立的是資料通訊端,參數protocol用於指定網路通訊協定,一般是0表示預設為TCP/IP協議。 成功返回指向通訊端的控制代碼SOCKET
int bind(SOCKET s,const sockaddr* name,int namelen);
s標識一個未捆綁通訊端的控制代碼,用來等待客戶機的串連,name是賦予通訊端的地址,它由struct sockaddr結構表示,該結構的格式如下:
struct sockaddr
{
u_short sa_family;
char sa_data[4];
};
該結構地址隨選擇的協議的不同而變換,因此一般情況下另一個與該地址結構大小相同的sockaddr_in結構更為常用,socket_in結構用來表示TCP/IP協議下的地址,在TCP/IP協議下,可以方便的通過強制類型轉換把sockaddr_in結構轉換為sockaddr結構。sockaddr_in結構的格式如下:
struct sockaddr_in
{
short sin_family;
unsigned short sin_port;
struct in_addr sin_addr;
char sin_zero[8];
};
sin_family欄位必須設定為AF_INET,表示socket處於Internet域,sin_port欄位用於指定伺服器連接埠,sin_addr用於把一個IP地址儲存為一個4位元組的數。sin_zero充當填充項的職責。IP地址為INADDR_ANY時,容許伺服器應用監聽主機電腦上面每個網路介面上的客戶機活動。
當隊一個已經綁定的通訊端調用bind,會返回WSAEFFAULT的錯誤。
int listen(SOCKET s,int backlog)
s標識一個已捆綁未串連的通訊端描述符。