1.select服务器2.poll客户端

1.

服务器

#include <stdio.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <sys/types.h>
#include <string.h>
#include <unistd.h>
#include <pthread.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/select.h>
#define IP "192.168.124.234"
#define PORT 8999
int connect_bn(struct sockaddr_in *savecin, int lfd, fd_set *readfds, int *maxfd)
{
    printf("服务器连接事件\n");
    struct sockaddr_in cin;
    socklen_t len = sizeof(cin);
    int newfd = accept(lfd, (struct sockaddr *)&cin, &len);
    if (newfd < 0)
    {
        perror("accept");
        return -1;
    }
    savecin[newfd - 3] = cin;
    printf("服务器连接了,ip是%s,端口是%d,文件描述符是%d\n", inet_ntoa(cin.sin_addr), ntohs(cin.sin_port), newfd);
    FD_SET(newfd, readfds);
    *maxfd = newfd > *maxfd ? newfd : *maxfd;
    printf("%d\n",*maxfd);
    return 0;
}
int jieshou(int i,fd_set* readfds,int* maxfd,struct sockaddr_in* savecin)
{
    char buf[255]={0};
    bzero(buf,sizeof(buf));
    int r = recv(i, buf, sizeof(buf), 0);
    if (r < 0)
    {
        perror("recv");
        return -1;
    }
    else if (r == 0)
    {
        printf("客户端下线了ip是%s,端口是%d\n", inet_ntoa(savecin[i - 3].sin_addr), ntohs(savecin[i - 3].sin_port));
        close(i);
        FD_CLR(i, readfds);
        while (FD_ISSET(*maxfd, readfds) == 0 && (maxfd--) > 0)
            ;
        return -1;
    }
    printf("%s...  ip是%s,端口是%d,文件描述符是%d\n", buf, inet_ntoa(savecin[i - 3].sin_addr), ntohs(savecin[i - 3].sin_port), i);
    // printf("服务器连接了,ip是%s,端口是%d\n", inet_ntoa(cin.sin_addr), ntohs(cin.sin_port));
    bzero(buf, sizeof(buf));
    // send(i, "hellow", 7, 0);
}
int mesgsend(fd_set *readfds)
{
    printf("键盘事件\n");
    char buf[255] = {0};
    /*bzero(buf, sizeof(buf));
    fgets(buf, sizeof(buf), stdin);
    buf[strlen(buf) - 1] = 0;
    printf("%s\n", buf);
    bzero(buf, sizeof(buf));*/
    bzero(buf, sizeof(buf));
    int sendfd = -1;
    int res = scanf("%d %s", &sendfd, buf);
    while (getchar()!='\n');
    
    if (0 > sendfd || 1023 < sendfd || FD_ISSET(sendfd, readfds) == 0)
    {
        printf("输入不合法\n");
        return -1;
    }
    if (res != 2)
    {
        printf("不合法");
        return -1;
    }
    if (send(sendfd, buf, strlen(buf), 0) < 0)
    {
        perror("send");
        return -1;
    }
    return 0;
}
int main(void)
{
    int lfd = socket(AF_INET, SOCK_STREAM, 0);
    if (lfd < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("socket");
        return -1;
    }
    printf("创建套接字\n");
    struct sockaddr_in sin;
    sin.sin_family = AF_INET;
    sin.sin_port = htons(PORT);
    sin.sin_addr.s_addr = inet_addr(IP);
    int reuse = 1;
    if (setsockopt(lfd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) < 0)
    {
        fprintf(stderr, "line:%d  ", __LINE__);
        perror("setsockopt");
        return -1;
    }
    int bi = bind(lfd, (struct sockaddr *)&sin, sizeof(sin));
    if (bi < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("bind");
        return -1;
    }
    int m = listen(lfd, 300);
    if (m < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("bind");
        return -1;
    }
    struct sockaddr_in cin;
    // socklen_t len = sizeof(cin);
    struct sockaddr_in savecin[1024 - 3];
    int afd = 0;
    fd_set readfds;
    FD_ZERO(&readfds);
    FD_SET(lfd, &readfds);
    FD_SET(afd, &readfds);
    int newfd;
    fd_set temp_readfds;
    char buf[128] = {0};
    int maxfd = lfd;
    while (1)
    {
        temp_readfds = readfds;
        select(maxfd + 1, &temp_readfds, NULL, NULL, NULL);
        for (int i = 0; i <= maxfd; i++)
        {
            if (FD_ISSET(i, &temp_readfds) == 0)
            {
                continue;
            }
            if (i == afd)
            {
                mesgsend(&readfds);
            }
            else if (i == lfd)
            {
                connect_bn(savecin, lfd, &readfds, &maxfd);
            }
            else
            {
                jieshou(i,&readfds,&maxfd,savecin);
            }
        }
    }
    close(lfd);

    return 0;
}

客户端

#include <stdio.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <sys/types.h>
#include <string.h>
#include <unistd.h>
#include <pthread.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/select.h>
#define IP "192.168.124.234"
#define PORT 8999
int mian()
{
    int fd = socket(AF_INET, SOCK_STREAM, 0);
    if (fd < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("socket");
        return -1;
    }
    printf("创建套接字\n");
    struct sockaddr_in sin;
    sin.sin_family = AF_INET;
    sin.sin_port = htons(PORT);
    sin.sin_addr.s_addr = inet_addr(IP);
    int reuse = 1;
    if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) < 0)
    {
        fprintf(stderr, "line:%d  ", __LINE__);
        perror("setsockopt");
        return -1;
    }
    int bi = bind(fd, (struct sockaddr *)&sin, sizeof(sin));
    if (bi < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("bind");
        return -1;
    }
    // 允许端口号被快速重复使用
    struct sockaddr_in cin;
    cin.sin_family = AF_INET;
    cin.sin_port = htons(8999);
    cin.sin_addr.s_addr = inet_addr("192.168.124.234");
    int sfd = connect(fd, (struct sockaddr *)&cin, sizeof(cin));
    if (sfd < 0)
    {
        perror("connect");
        return -1;
    }
    fd_set readfds;
    FD_ZERO(&readfds);
    FD_SET(0,&readfds);
    FD_SET(fd,&readfds);
    fd_set temp_readfds;
    char buf[255]={0};
    int maxfd=fd;
    int res;
    while (1)
    {
        temp_readfds=readfds;
        select(maxfd+1,&temp_readfds,NULL,NULL,NULL);
        if(FD_ISSET(0,&temp_readfds))
        {
            bzero(buf,sizeof(buf));
            fgets(buf,sizeof(buf),stdin);
            buf[strlen(buf)-1]='\0';
            send(fd,buf,strlen(buf),0);
        }
        if(FD_ISSET(fd,&temp_readfds))
        {
            bzero(buf,sizeof(buf));
            res=recv(fd,buf,sizeof(buf),0);
            if(res==0)
            {
                printf("服务器下线了\n");
                return 0;
            }
            else if(res<0)
            {
                perror("recv");
                return -1;
            }
            printf("%s\n",buf);
        }
        
    }
    close(fd);
    close(sfd);
    return 0;
}

2.

客户端

#include <stdio.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <sys/types.h>
#include <string.h>
#include <unistd.h>
#include <pthread.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/select.h>
#include <poll.h>
#define IP "192.168.124.234"
#define PORT 8999
int mian()
{
    int fd = socket(AF_INET, SOCK_STREAM, 0);
    if (fd < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("socket");
        return -1;
    }
    printf("创建套接字\n");
    struct sockaddr_in sin;
    sin.sin_family = AF_INET;
    sin.sin_port = htons(PORT);
    sin.sin_addr.s_addr = inet_addr(IP);
    int reuse = 1;
    if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) < 0)
    {
        fprintf(stderr, "line:%d  ", __LINE__);
        perror("setsockopt");
        return -1;
    }
    int bi = bind(fd, (struct sockaddr *)&sin, sizeof(sin));
    if (bi < 0)
    {
        fprintf(stderr, "%d", __LINE__);
        perror("bind");
        return -1;
    }
    // 允许端口号被快速重复使用
    struct sockaddr_in cin;
    cin.sin_family = AF_INET;
    cin.sin_port = htons(8999);
    cin.sin_addr.s_addr = inet_addr("192.168.124.234");
    int sfd = connect(fd, (struct sockaddr *)&cin, sizeof(cin));
    if (sfd < 0)
    {
        perror("connect");
        return -1;
    }
    struct pollfd fds[2];
    fds[0].fd=0;
    fds[0].events=POLLIN;
    fds[1].fd=fd;
    fds[1].events=POLLIN;
    char buf[255]={0};
    int pollres;
    int res;
    while (1)
    {
        pollres=poll(fds,2,-1);
        if(pollres<0)
        {
            perror("poll");
            return -1;
        }
        else if(pollres==0)
        {
            printf("超时了\n");
            continue;
        }
        if(fds[0].events&POLLIN)
        {
            bzero(buf,sizeof(buf));
            fgets(buf,sizeof(buf),stdin);
            buf[strlen(buf)-1]=0;
            if(send(fd,buf,strlen(buf),0)<0)
            {
                perror("send");
                return -1;
            }
        }
        if(fds[1].events&POLLIN)
        {
            bzero(buf,sizeof(buf));
            res=recv(fd,buf,sizeof(buf),0);
            if(res<0)
            {
                perror("recv");
                return -1;
            }
            else if(res=0)
            {
                printf("服务器下线\n");
                break;
            }
            printf("%s\n",buf);
        }
    }
    close(fd);
    close(sfd);
    return 0;
}

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值