• Linux 网络编程一步一步学(四)设置非阻塞方式


        1 #include <stdio.h>                                                                                           
        2 #include <string.h>
        3 #include <errno.h>
        4 #include <sys/socket.h>
        5 #include <resolv.h>
        6 #include <stdlib.h>
        7 #include <netinet/in.h>
        8 #include <arpa/inet.h>
        9 #include <unistd.h>
       10 #include <fcntl.h>
       11 #define MAXBUF 10
       12 int main(int argc, char **argv)
    -  13 {
    |  14     int sockfd, ret, rcvtm = 0;
    |  15     struct sockaddr_in dest, mine;
    |  16     char buffer[MAXBUF + 1];
    -  17     if (argc != 5) {
    2  18         printf("参数格式错误!正确用法如下:\n\t\t%s 对方IP 地址 对方端口 本机IP 地址 本机端口\n\t比如:\t%s 127.0.0.1 82     0\n此程序用来以本机固定的端口从某个 IP 地址的服务器某个端口接收最多MAXBUF 个字节的消息",argv[0], argv[0]);
    2  19     exit(0);
    2  20     }
    |  21     /* 创建一个 socket 用于 tcp 通信 */
    |  22     sockfd = socket(AF_INET, SOCK_STREAM, 0);
    |  23     /* 初始化服务器端(对方)的地址和端口信息 */
    |  24     bzero(&dest, sizeof(dest));
    |  25     dest.sin_family = AF_INET;
    |  26     dest.sin_port = htons(atoi(argv[2]));
    -  27     if (inet_aton(argv[1], (struct in_addr *) &dest.sin_addr.s_addr) == 0) {
    2  28         perror(argv[1]);
    2  29         exit(errno);
    2  30     }
    |  31     /* 初始化自己的地址和端口信息 */
    |  32     bzero(&mine, sizeof(mine));
    |  33     mine.sin_family = AF_INET;
    |  34     mine.sin_port = htons(atoi(argv[4]));
    -  35     if (inet_aton(argv[3], (struct in_addr *) &mine.sin_addr.s_addr) == 0) {
    2  36         perror(argv[3]);
    2  37         exit(errno);
    2  38     }
    |  39     /* 把自己的 IP 地址信息和端口与 socket 绑定 */
    -  40     if (bind(sockfd, (struct sockaddr *) &mine, sizeof(struct sockaddr)) == -1) {
    2  41         perror(argv[3]);
    2  42         exit(errno);
    2  43     }
    |  44     /* 连接服务器 */
    -  45     if (connect(sockfd, (struct sockaddr *) &dest, sizeof(dest)) != 0) {
    2  46         perror("Connect ");
    2  47         exit(errno);
    2  48     }
    |  49     /* 设置 socket 属性为非阻塞方式 */
    -  50     if(fcntl(sockfd, F_SETFL, O_NONBLOCK) == -1) {
    2  51         perror("fcntl");
    2  52         exit(errno);
    2  53     }
    |  54     /* 接收对方发过来的消息,每次最多接收 MAXBUF 个字节,直到把对方发过来的所有消息接收完毕为止 */
    -  55     do {
    2  56         _retry:
    2  57             bzero(buffer, MAXBUF + 1);
    2  58             ret = recv(sockfd, buffer, MAXBUF, 0);
    2  59             if(ret > 0)
    2  60                 printf("读到%d个字节,它们是:'%s'\n", ret, buffer);
    -  61             if(ret < 0) {
    3  62                 if(errno == EAGAIN) {
    3  63                     if(rcvtm)
    3  64                         break;
    3  65                     else {
    3  66                         printf("数据还未到达!\n");
    3  67                         usleep(100000);
    3  68                         goto _retry;
    3  69                     };
    3  70                 };
    3  71                 printf("接收出错了!\n");
    3  72                 perror("recv");
    3  73             }
    2  74             rcvtm++;
    2  75     }while(ret==MAXBUF);
    |  76     /* 关闭连接 */
    |  77     close(sockfd);
    |  78     return 0;
    |  79 }
       80   
  • 相关阅读:
    iOS开发-Scheduler attach ERROR when replacing an existing executor !!! id:88
    多层导航栏下的登陆注销架构
    iOS开发-功能篇-静态库
    iOS开发-UI篇-AutoLayout
    iOS开发-数据篇-sqlite存储
    零碎知识整理-外链应用
    零碎知识整理
    iOS开发-功能篇-国际化|NSUserDefaults
    iOS开发-底层篇-Class详解
    swift可选隐式可选类型
  • 原文地址:https://www.cnblogs.com/liqiu/p/2981240.html
Copyright © 2020-2023  润新知