Chinaunix首页 | 论坛 | 博客
  • 博客访问: 96628
  • 博文数量: 31
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 380
  • 用 户 组: 普通用户
  • 注册时间: 2014-02-24 22:04
文章分类

全部博文(31)

文章存档

2014年(31)

我的朋友

分类: C/C++

2014-08-04 10:47:29


main
|-----.....
|-----tracker_mem_init
|-----socketServer
|-----tcpsetserveropt
|-----.....

socketServer函数在main函数中被调用的代码:

点击(此处)折叠或打开

  1. sock = socketServer(bind_addr, g_server_port, &result);//创建socket,绑定,监听
  2.     if (sock < 0)
  3.     {
  4.         log_destroy();
  5.         return result;
  6.     

socketServer函数代码:

点击(此处)折叠或打开

  1. int socketServer(const char *bind_ipaddr, const int port, int *err_no)
  2. {
  3.     int sock;
  4.     int result;
  5.     //创建socket,AF_INET:ipv4因特网,SOCK_STREAM:有序,可靠,双向的面向链接的字节流
  6.     //0表示按照给定的域和套接字类型选择默认的协议
  7.     sock = socket(AF_INET, SOCK_STREAM, 0);//创建socket,AF_INET:ipv4因特网
  8.     if (sock < 0)
  9.     {
  10.         *err_no = errno != 0 ? errno : EMFILE;
  11.         logError("file: "__FILE__", line: %d, " \
  12.             "socket create failed, errno: %d, error info: %s", \
  13.             __LINE__, errno, STRERROR(errno));
  14.         return -1;
  15.     }

  16.     result = 1;
  17.     //SO_REUSEADDR:表示如果result为非0,则重用bind中的地址
  18.     //SOL_SOCKET:表示通用的套接字层
  19.     if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &result, sizeof(int))<0)
  20.     {
  21.         *err_no = errno != 0 ? errno : ENOMEM;
  22.         logError("file: "__FILE__", line: %d, " \
  23.             "setsockopt failed, errno: %d, error info: %s", \
  24.             __LINE__, errno, STRERROR(errno));
  25.         close(sock);
  26.         return -2;
  27.     }
  28.     //绑定sock到指定的ip地址与端口上
  29.     if ((*err_no=socketBind(sock, bind_ipaddr, port)) != 0)
  30.     {
  31.         close(sock);
  32.         return -3;
  33.     }
  34.     
  35.     if (listen(sock, 1024) < 0)//服务器监听,1024表示请求队列的大小
  36.     {
  37.         *err_no = errno != 0 ? errno : EINVAL;
  38.         logError("file: "__FILE__", line: %d, " \
  39.             "listen port %d failed, " \
  40.             "errno: %d, error info: %s", \
  41.             __LINE__, port, errno, STRERROR(errno));
  42.         close(sock);
  43.         return -4;
  44.     }

  45.     *err_no = 0;
  46.     return sock;
  47. }

socketSever函数执行步骤:
(1) 调用socket函数,创建socket,并获得socket id
(2) 调用setsockopt函数,设定socket选项
(3) 调用socketBind绑定socket到特定ip地址
(4) 调用listen函数,监听socket
上述步骤中,socket,setsockopt,listen函数均为系统调用


socketBind函数代码:

点击(此处)折叠或打开

  1. int socketBind(int sock, const char *bind_ipaddr, const int port)
  2. {
  3.     struct sockaddr_in bindaddr; //sockaddr_in表示英特网sock结构

  4.     bindaddr.sin_family = AF_INET;
  5.     bindaddr.sin_port = htons(port);//主机字节序转换成网络字节序,l表示32位,s表示16位
  6.     if (bind_ipaddr == NULL || *bind_ipaddr == '\0')
  7.     {
  8.         bindaddr.sin_addr.s_addr = INADDR_ANY;
  9.     }
  10.     else
  11.     {
  12.         //把ip字符串转换成ip地址
  13.         if (inet_aton(bind_ipaddr, &bindaddr.sin_addr) == 0)
  14.         {
  15.             logError("file: "__FILE__", line: %d, " \
  16.                 "invalid ip addr %s", \
  17.                 __LINE__, bind_ipaddr);
  18.             return EINVAL;
  19.         }
  20.     }
  21.     //绑定socket
  22.     if (bind(sock, (struct sockaddr*)&bindaddr, sizeof(bindaddr)) < 0)
  23.     {
  24.         logError("file: "__FILE__", line: %d, " \
  25.             "bind port %d failed, " \
  26.             "errno: %d, error info: %s.", \
  27.             __LINE__, port, errno, STRERROR(errno));
  28.         return errno != 0 ? errno : ENOMEM;
  29.     }

  30.     return 0;
  31. }
socketBind执行步骤:
(1) 调用honts函数,先把端口转换成网络字节序
(2) 调用inet_aton函数,把ip地址字符串转换成ip地址结构
(3) 调用bind函数,绑定socket到特定ip地址







阅读(827) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~