全部博文(842)
分类: LINUX
2012-05-17 17:02:30
下面从服务器端完整地叙述一遍服务器端socket创建、监听、与客户端建立连接的过程。
要建立一个处理连接的服务器端程序,首先要调用socket函数创建一个socket,返回一个文件句柄fd,使以后对它的操作就象对普通文件设备一样读写。
由于是服务器端必须对一个端口进行监听其他机器的请求,所以接下去调用bind函数,传入刚才的fd,定义好地址和端口,由于是要接受来自任何host的连接所以应讲sin_addr赋为INADDR_ANY,port为你所设定的端口。
注意:这里的地址和端口是网络字节顺序,所以要调用htonl,htons完成主机字节顺序
到网络字节的转变
当服务器端的Socket对象绑定完成之后,服务器端必须建立一个监听的队列来接收客户端的连接请求。使用listen()函数使服务器端的Socket 进入监听状态,并设定可以建立的最大连接数(目前最大值限制为 5, 最小值为1)。该函数调用成功返回0,否则返回SOCKET_ERROR。
服务器端的Socket调用完listen()后,如果此时客户端调用connect()函数提出连接申请的话,Server 端必须再调用accept() 函数,这样服务器端和客户端才算正式完成通信程序的连接动作。
整个过程就是socket->bind->listen->accpet->Read,write
(而对于客户端则是socket->connect->read,write)
以下附一个简单的例子,实现功能:客户端程序A向服务器端程序B发送一个消息后,服务器将这个消息返回给客户端,在客户端及服务器端分别打印出这个消息。
服务器端代码:#include
#include
#include
#include
#include
#include
#include
#define DEST_IP "127.0.0.1"
#define DEST_PORT 1316
#define MY_PORT 3490
#define BACKLOG 2
void main()
{
int sockfd;
int send_len;
int recv_len;
int new_fd;
char buffer[1024];
struct sockaddr_in my_addr;
struct sockaddr_in other_addr;
sockfd = socket(AF_INET,SOCK_STREAM,0);
my_addr.sin_family = AF_INET;
my_addr.sin_addr.s_addr = INADDR_ANY;//表示服务器可以接受任何客户端的请求
my_addr.sin_port = htons(DEST_PORT);// htons(监听的端口)实现主机字节序到网络字节序的转换
bind(sockfd, (struct sockaddr*)&my_addr,sizeof(my_addr));
listen(sockfd,BACKLOG);
while(1){
new_fd = -1;
socklen_t other_size = sizeof(struct sockaddr_in);
new_fd = accept(sockfd,(struct sockaddr*)&other_addr,&other_size);
recv_len = recv(new_fd, buffer, sizeof(buffer)-1, 0 );
if( recv_len > 0 )
{
buffer[recv_len] = 0;
send(new_fd, buffer, strlen(buffer),0);
printf("%s\n",buffer);
}
close(new_fd);
}
close(sockfd);
}
客户端代码:#include
#include
#include
#include
#include
#include
#include
int main(int agrc, char** argv)
{
int sock_cli;
int sock;
struct sockaddr_in serv_addr;
char buffer[1024];
sock_cli=socket(AF_INET,SOCK_STREAM,0);
bzero(&serv_addr,sizeof(serv_addr));
serv_addr.sin_family=AF_INET;
serv_addr.sin_port=htons(1316);
serv_addr.sin_addr.s_addr=inet_addr("127.0.0.1");
if( (sock=connect(sock_cli,(struct sockaddr *)&serv_addr,sizeof(struct sockaddr))) < 0 )
{
return -1;
}
if( agrc != 2 )
send(sock_cli, "testing", strlen("testing"), 0 );
else
send(sock_cli, argv[1], strlen(argv[1]),0);
int recv_len = recv(sock_cli, buffer, sizeof(buffer)-1, 0 );
buffer[recv_len] = 0;
printf("%s\n",buffer);
close(sock_cli);
}