C++学习_udp协议(socket)的封装

C++学习笔记第一天,关于UDP(socket)的封装实现
1.配置QT下的pro文件


  1. TEMPLATE = app
  2. CONFIG += console
  3. CONFIG -= app_bundle
  4. CONFIG -= qt
  5.  
  6. LIBS += -lWs2_32 ##标示使用window下的Ws2_32.lib,-l表示要链接后面的库
  7. #-lWs2_32,link Ws2_32.lib
  8.  
  9. SOURCES += main.cpp \
  10.     udp.cpp

  11. include(deployment.pri)
  12. qtcAddDeployment()

  13.  
  14. HEADERS += \
  15.     udp.h
2. 编写udp . h文件


  1. #ifndef UDP_H
  2. #define UDP_H

  3. #ifdef MYLINUX

  4. #include <unistd.h>
  5. #include <arpa/inet.h>
  6. #include <sys/types.h> /* See NOTES */
  7. #include <sys/socket.h>

  8. #define SOCKET int

  9. #else
  10. #include <winsock2.h>
  11. #endif

  12. class myudp
  13. {
  14. private:
  15.     SOCKET st;//类的内部成员一般是不暴露在外面的
  16. public:
  17.     myudp();
  18.     ~myudp();

  19. int socket_send(const char * IP,const char *buf, int len);
  20. int socket_recv(char *buf, int len, char * srcIP);
  21. int socket_bind(short int port);
  22. };

  23. #endif // UDP_H
3 . 编写udp . cpp
  1. #include <string.h>
  2. #include <stdio.h>
  3. #include "udp.h"

  4. //#define MYLINUX ---- linux 下 makefile文件定义 -DMYLINUX





  5. int myudp::socket_send(const char * IP,const char *buf, int len)
  6. {

  7.     st = socket(AF_INET, SOCK_DGRAM, 0);
  8.     //建立一个socket,第一个参数是指定socket要用哪个协议,AF_INET代表要用TCP/IP协议
  9.     //第二个参数SOCK_DGRAM意思是要用UDP协议
  10.     //第三个参数一般默认填0
  11.     struct sockaddr_in addr;
  12.     memset(&addr, 0, sizeof(addr));//初始化结构addr
  13.     addr.sin_family = AF_INET;//代表要使用一个TCP/IP的地址
  14.     addr.sin_port = htons(8080);//host to net short
  15.     addr.sin_addr.s_addr = inet_addr(IP);
  16.     //IP地址解析
  17.     //unsigned long laddr = inet_addr("192.168.6.200");
  18.     //unsigned char *p = &laddr;
  19.     //printf("%u, %u, %u, %u\n", *(p), *(p+1), *(p+2), *(p+3));

  20.     size_t rc = 0;

  21.     //发送udp数据
  22.     rc = sendto(st,buf,len,0,(struct sockaddr *)&addr,sizeof(addr));

  23.     return rc;
  24. }

  25. int myudp::socket_recv(char *buf, int len, char * srcIP)
  26. {
  27.     struct sockaddr_in sendaddr;//来自发送方的IP地址
  28.     memset(&sendaddr,0,sizeof(sendaddr));

  29. #ifdef MYLINUX
  30.     socklen_t len;
  31. #else
  32.     int addrlen;
  33. #endif
  34.     addrlen = sizeof(sendaddr);


  35.     memset(buf,0,len);
  36.     size_t rc = recvfrom(st,buf,len,0,(struct sockaddr *)&sendaddr,&addrlen);
  37.     //inet_ntoa(sendaddr.sin_addr);//这个函数是不可重入函数
  38.     //多线程调用,这个函数会出问题
  39.     if(srcIP)
  40.         strcpy(srcIP,inet_ntoa(sendaddr.sin_addr));
  41.     //printf("%s:\n%s\n", srcIP, buf);
  42. return rc;
  43. }

  44. myudp::myudp()
  45. {
  46. #ifndef MYLINUX
  47.     //初始化socket
  48.     DWORD ver;
  49.     WSADATA wsaData;
  50.     ver = MAKEWORD(1,1);//在调用WASStartup要告诉windows,我用什么版本的socket
  51.     WSAStartup(ver, &wsaData);//windows要求,只要用socket,第一步,必须调用这个函数
  52.     //初始化完成
  53. #endif

  54.     st = socket(AF_INET,SOCK_DGRAM,0);//定义一个socket

  55. }


  56. myudp::~myudp()
  57. {
  58. #ifdef MYLINUX
  59.     close(st);
  60. #else
  61.     closesocket(st);//关闭socket
  62.     WSACleanup();//释放win socket内部的相关资源
  63. #endif
  64. }


  65. int myudp::socket_bind(short port)
  66. {
  67.     struct sockaddr_in addr;
  68.     memset(&addr,0,sizeof(addr));//初始化addr
  69.     addr.sin_family = AF_INET;//代表要使用一个TCP/IP的地址
  70.     addr.sin_port = htons(port);
  71.     addr.sin_addr.s_addr = htonl(INADDR_ANY);//作为接收方,不需要指定具体的IP地址,接受的主机是什么IP,我就在什么IP接受数据
  72.     //addr.sin_addr.s_addr = inet_addr("192.168.2.100");

  73.     return bind(st, (struct sockaddr *)&addr, sizeof(addr)); //将端口号和程序绑定
  74. }
4 . main . c的实现代码
  1. #include <iostream>
  2. #include "udp.h"

  3. using namespace std;

  4. int main(int argc, char *args[])
  5. {
  6.     if(argc > 1)
  7.     {
  8.         myudp udp;
  9.         char buf[1024] = {0};
  10.         while(1)
  11.         {
  12.             memset(buf, 0, sizeof(buf));
  13.             gets(buf);
  14.             udp.socket_send(args[1],buf, strlen(buf));
  15.             if (strcmp(buf, "exit") == 0)
  16.                 break;
  17.         }

  18.     }else
  19.     {
  20.         myudp udp;
  21.         char buf[1024] = {0};
  22.         if(udp.socket_bind(8080) > -1)
  23.         {
  24.             char ip[100] = {0};
  25.             while(1)
  26.             {
  27.                 memset(buf, 0, sizeof(buf));
  28.                 memset(ip, 0, sizeof(ip));
  29.                 udp.socket_recv(buf,sizeof(buf), ip);
  30.                 if (strncmp(buf, "exit", 4) == 0)
  31.                         break;
  32.                 cout << ip << endl;
  33.                 cout << buf << endl;
  34.             }
  35.         }
  36.     }

  37.     cout << "over" << endl;
  38.     return 0;
  39. }


来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/31532105/viewspace-2153075/,如需转载,请注明出处,否则将追究法律责任。

转载于:http://blog.itpub.net/31532105/viewspace-2153075/

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值