epoll实现TCP服务器和客户端收发数据

应用程序代码

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include

#define ERR_MSG(msg) do{\
    printf("line: %d\n", __LINE__); \
    perror(msg);\
}while(0)

#define PORT 6666   //端口号的网络字节序 1024~49151
#define IP "192.168.250.100" //ifconfig查看本机IP

int main(int argc, const char *argv[])
{
    //创建流式套接字
    int sfd = socket(AF_INET, SOCK_STREAM, 0);
    if(sfd < 0)
    {
        ERR_MSG("socket");
        return -1;
    }
    printf("socket create success sfd=%d __%d__\n", sfd, __LINE__);

    //功能:允许端口快速被重用,快速被复用
    int reuse =1;
    if(setsockopt(sfd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) < 0)
    {
        ERR_MSG("setsockopt");
        return -1;
    }

    //填充服务器自身的地址信息结构体,
    //真实的地址信息结构体根据地址族制定 AF_INET: man 7 ip
    struct sockaddr_in sin;
    sin.sin_family      = AF_INET;      //必须填充AF_INET;
    sin.sin_port        = htons(PORT);  //端口号的网络字节序 1024~49151
    sin.sin_addr.s_addr = inet_addr(IP);    //ifconfig查看本机IP

    //将IP地址和端口号绑定到指定的套接字文件描述符上
    if(bind(sfd, (struct sockaddr*)&sin, sizeof(sin)) < 0)
    {
        ERR_MSG("bind");
        return -1;
    }
    printf("bind success __%d__\n", __LINE__);

    //功能:将通讯套接字设置为被动监听状态。用于监听是否有客户端连接;
    //listen函数会让内核维护两个队列:未完成连接的队列, 已完成连接的队列
    if(listen(sfd, 128) < 0)
    {
        ERR_MSG("listen");
        return -1;
    }
    printf("listen success __%d__\n", __LINE__);

    int s_res = 0;
    struct sockaddr_in cin;     //存储客户端信息
    socklen_t len = sizeof(cin);

    struct sockaddr_in savecin[1024];   //0 1 2 sfd肯定不会有对应客户端

    int newfd = -1;
    ssize_t res = 0;

    struct epoll_event event;
    struct epoll_event events[10];//存放就绪事件描述符的数组
    char buf[128] = {0};

    //创建epoll句柄
    int epfd = epoll_create(1);
    if(epfd < 0)
    {
        printf("epoll_create failed\n");
        exit(-1);
    }

    //添加准备就绪事件进入epoll;
    event.events=EPOLLIN;//读事件
    event.data.fd=sfd;
    if(epoll_ctl(epfd,EPOLL_CTL_ADD,sfd,&event)<0)
    {
        printf("epoll_ctl add filed\n");
    }
    event.events=EPOLLIN;//读事件
    event.data.fd=0;
    if(epoll_ctl(epfd,EPOLL_CTL_ADD,0,&event)<0)
    {
        printf("epoll_ctl add filed\n");
    }
   //监听事件是否发生
   while(1)
   {
    //如果成功,ret接收返回的事件个数,把就绪的事件放在events数组中
        int ret=epoll_wait(epfd,events,10,-1);
        if(ret<0)
        {
            printf("epoll_wait filed\n");
            exit(-1);
        }
        int i;
        //循环遍历数组,做事件的处理
        for(i=0;i

你可能感兴趣的:(tcp/ip,服务器,vscode)