您的位置:首页 > 理论基础 > 计算机网络

网络IPC, socket(3): 建立连接

2007-07-12 18:57 330 查看
1. 前提:

如果处理的是面向连接的网络服务(SOCK_STREAM或SOCK_SEQPACKET), 在开始传输数据之前, 需要在客户端和服务器端建立一个连接.

2. 函数介绍:

用connect建立一个连接:

头文件: <sys/socket.h>

原型: int connect(int sockfd, const struct sockaddr *addr, socklen_t len);

返回值: 成功则返回0, 出错则返回-1.

说明: 在connect中所指定的地址是想与之通信的服务器地址.

用listen进行监听(可以接受连接请求):

头文件: <sys/socket.h>

原型: int listen(int sockfd, int backlog);

返回值: 成功则返回0, 出错则返回-1.

参数: backlog提供了一个提示, 用于表示该进程可以入队等待的连接请求数量. 其实际上限值由系统和协议决定. 一旦队列满, 系统会拒绝多余的连接请求, 所以该值应该基于服务器期望负载量和处理能力来选择.

服务器调用了listen以后, socket就可以接收连接请求了.

用accept获得连接请求并建立连接:

头文件: <sys/socket.h>

原型: int accept(int sockfd, struct sockaddr *restrict addr, socklen_t *restrict len);

返回值: 成功则返回socket描述符, 出错则返回-1.

参数: 如果不关心客户端标识, 可以将addr和len设为NULL; 否则, 在调用accept之前, 应确保参数addr的缓冲区有足够大的空间来存放地址, 并且将len设为对应大小.

这个返回的socket与原始的socket(sockfd参数)具有相同的socket类型和地址族, 但并没有关联. 原始socket继续保持可用状态并接受其他连接请求.

如果没有连接请求, accept会阻塞; 如果sockfd处于非阻塞模式, accept会返回-1并将errno设置为EAGAIN或EWOULDBLOCK.

另外, 服务器可以使用poll或select来等待一个请求到来, 在以后的文章中将介绍.

3. 举例:

客户端的连接程序:


#include<sys/types.h>


#include<sys/socket.h>


#include<netinet/in.h>


#include<arpa/inet.h>


#define PORT 1234


#define SERVER_IP “127.0.0.1”




int main()




...{


int s;


struct sockaddr_in addr;


char buffer[256];




if((s = socket(AF_INET,SOCK_STREAM,0))<0)...{


perror(“socket”);


exit(1);


}






/**//* 填写sockaddr_in结构*/


bzero(&addr,sizeof(addr));


addr.sin_family = AF_INET;


addr.sin_port=htons(PORT);


addr.sin_addr.s_addr = inet_addr(SERVER_IP);






/**//* 尝试连线*/




if(connect(s,&addr,sizeof(addr))<0)...{


perror(“connect”);


exit(1);


}


return 0;


}



服务器端的监听程序:


#include<sys/socket.h>


#include<netinet/in.h>


#include<arpa/inet.h>


#define PORT 1234


#define MAXSOCKFD 10




int main()




...{


int sockfd, newsockfd;


struct sockaddr_in addr;


int addr_len = sizeof(struct sockaddr_in);






/**//* 创建socket */




if ((sockfd = socket(AF_INET,SOCK_STREAM,0))<0)...{


perror(“socket”);


exit(1);


}






/**//* 填充addr */


bzero(&addr,sizeof(addr));


addr.sin_family =AF_INET;


addr.sin_port = htons(PORT);


addr.sin_addr.s_addr = htonl(INADDR_ANY);






/**//* 绑定 */




if(bind(sockfd,&addr,sizeof(addr))<0)...{


perror(“connect”);


exit(1);


}






/**//* 监听 */




if(listen(sockfd,3)<0)...{


perror(“listen”);


exit(1);


}






/**//* 接受请求 */




if((newsockfd = accept(sockfd, NULL, NULL)) < 0)...{


perror("accept");


exit(1);


}




return 0;


}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: