UDP畅聊系统简单版本

带有数据存储的模型图

总体的框架

server中

udp_server.h

其中add_user函数为添加新上线用户信息

 1 #pragma once
  2 #include <iostream>
  3 #include <map>
  4 using namespace std;
  5 #include "data_pool.h"
  6 #include <pthread.h>
  7 #include <stdlib.h>
  8 class udp_server
  9 {
 10 public:
 11     udp_server(const std::string &ip="192.168.137.129",const short &port=808    0);
 12     ~udp_server();
 13     void init();
 14     int recv_data();
 15     int send_data(struct sockaddr_in& client,socklen_t len,string& msg);
 16     int broadcast();
 17 protected:
 18     void add_user(string& key_ip,struct sockaddr_in& client);
 19 protected:
 20     string _ip;
 21     short _port;
 22     int _sock; 
 23     std::map<string,struct sockaddr_in> _online_user;
 24     pool_data _pool_data;
 25 };

udp_server.cpp

  1 #include "udp_server.h"
  2 #include "comm.h"
  3 #include "data_pool.h"
  4 
  5 udp_server::udp_server(const std::string &default_ip,const short &default_po    rt)
  6     :_ip(default_ip)
  7     ,_port(default_port)
  8     ,_sock(-1)
  9 {}
 10 
 11 udp_server::~udp_server()
 12 {
 13     if(_sock > 0)
 14         close(_sock);
 15 }
 16 
 17 void udp_server::init()
 18 {
 19     _sock=socket(AF_INET,SOCK_DGRAM,0);
 20     if(_sock <0)
 21     {
 22         print_log(strerror(errno),__FUNCTION__,__LINE__);
  23         exit(1);
 24     }
 25     struct sockaddr_in local;
 26     socklen_t len=sizeof(local);
 27     local.sin_family=AF_INET;
 28     local.sin_port=htons(_port);
 29     if(_ip.c_str()=="any")
 30     {
 31         local.sin_addr.s_addr=htonl(INADDR_ANY);
 32     }
 33     else
 34         local.sin_addr.s_addr=inet_addr(_ip.c_str());
 35     if(bind(_sock,(struct sockaddr*)&local,len)<0)
 36     {
 37         print_log(strerror(errno),__FUNCTION__,__LINE__);
 38         exit(2);
 39     }
 40 }   
  41 
 42 int udp_server::recv_data()
 43 {
 44     std::string _out;
 45     struct sockaddr_in client;
 46     socklen_t len=sizeof(client);
 47     char buf[_SIZE_];
 48     buf[0]=‘\0‘;
 49     ssize_t _size=recvfrom(_sock,buf,sizeof(buf)-1,0,(struct sockaddr*)&clie    nt,&len);
 50     if(_size < 0)
 51     {
 52         print_log(strerror(errno),__FUNCTION__,__LINE__);
 53     }
 54     else if(_size == 0)
 55     {
 56         const char *msg="client closed...";
 57         print_log(msg,__FUNCTION__,__LINE__);
 58     }
 59     else
 60     {
 61         buf[_size]=‘\0‘;
  62         _out=buf;
 63         string key_ip=inet_ntoa(client.sin_addr);
 64         print_log(key_ip.c_str(),__FUNCTION__,__LINE__);
 65         add_user(key_ip,client);
 66         _pool_data.put_data(_out);
 67     }
 68     return _size;
 69 }
 70 
 71 void udp_server::add_user(string &key_ip,struct sockaddr_in &client)
 72 {
 73     std::map<std::string,struct sockaddr_in>::iterator _iter=_online_user.f    ind(key_ip);
 74     if(_iter==_online_user.end())
 75     {
 76         _online_user.insert(std::pair<std::string,struct sockaddr_in>(key_i    p,client));
 77     }
 78     else
 79         return;
  80 }
 81 
 82 int udp_server::send_data(struct sockaddr_in &client,socklen_t len,std::str    ing& msg)
 83 {
 84     ssize_t _size=sendto(_sock,msg.c_str(),msg.size(),0,(struct sockaddr*)&    client,len);
 85     if( _size <0)
 86     {
 87         print_log(strerror(errno),__FUNCTION__,__LINE__);
 88         exit(1);
 89     }
 90    
 91     return _size;
 92 }
 93 int udp_server::broadcast()
 94 {
 95     std::string _in;
 96     std::map<std::string,struct sockaddr_in>::iterator _iter=_online_user.b    egin();
 97     while(_iter!=_online_user.end())
 98     {
 99         //send_data(_iter->second,sizeof(_iter->second),_in);
100         _pool_data.get_data(_in);
101         _iter++;
102     }
103     return 0;
104 }

server_main.cpp中,两个线程处理函数分别处理接收与广播数据

  1 #include "udp_server.h"
  2 
  3 void Usage(const char* proc)
  4 {
  5     cout<<"Usage:"<<proc<<" [ip] [port]"<<endl;
  6 }
  7 
  8 void* recv(void* arg)
  9 {
 10     udp_server* _ser=(udp_server*)arg;
 11     while(1)
 12     {
 13         _ser->recv_data();
 14     }
 15 }
 16 
 17 void* broad_cast(void* arg)
 18 {
 19     udp_server* _ser=(udp_server*)arg;
 20     while(1)
 21     {
 22         _ser->broadcast();
 23     }
  24 }
 25 
 26 int main(int argc,const char* argv[])
 27 {
 28     if(argc!=3)
 29     {
 30         Usage(argv[0]);
 31         exit(1);
 32     }
 33     string ip=argv[1];
 34     int port=atoi(argv[2]);
 35     udp_server _ser(ip,port);
 36     _ser.init();
 37     pthread_t tid1;
 38     pthread_t tid2;
 39     pthread_create(&tid1,NULL,recv,(void*)&_ser);
 40     pthread_create(&tid2,NULL,broad_cast,(void*)&_ser);
 41    
 42     pthread_join(tid1,NULL);
 43     pthread_join(tid2,NULL);
 44 //  while(1)
 45 //  {
 46 //      std::string msg;
 47 //      if(_ser.recv_data(msg)>0)
 48 //      {
 49 //          cout<<"client say:"<<msg;
 50 //          _ser.broadcast(msg);
 51 //      }
 52 //  }   
 53     return 0;
 54 }

client中进行发送消息和接收消息

udp_client.h

 1 #pragma once
  2 
  3 #include <iostream>
  4 using namespace std;
  5 #include <stdio.h>
  6 #include <assert.h>
  7 
  8 class udp_client
  9 {
 10 public:
 11     udp_client(const string &default_ip="192.168.137.129",const short &defa    ult_port=8080);
 12     ~udp_client();
 13     void init();
 14     int recv_data(string& _out);
 15     int send_data(string& _in);
 16 protected:
 17     string _ip;
 18     short _port;
 19     int _sock;
 20 };

udp_client.cpp

 1 #include "udp_client.h"
  2 #include "comm.h"
  3 
  4 udp_client::udp_client(const string &default_ip,const short &default_port)
  5     :_ip(default_ip)
  6     ,_port(default_port)
  7     ,_sock(-1)
  8 {}
  9 
 10 udp_client::~udp_client()
 11 {
 12     if(_sock > 0)
 13         close(_sock);
 14 }
 15 
 16 
 17 void udp_client::init()
 18 {
 19     _sock=socket(AF_INET,SOCK_DGRAM,0);
 20     if(_sock <0)
 21     {
 22         print_log(strerror(errno),__FUNCTION__,__LINE__);
 23         exit(1);
  24     }
 25 }
 26 
 27 int udp_client::recv_data(string &_out)
 28 {
 29     struct sockaddr_in server;
 30     socklen_t len=sizeof(server);
 31     char buf[_SIZE_];
 32     buf[0]=‘\0‘;
 33     ssize_t _size=recvfrom(_sock,buf,sizeof(buf)-1,0,(struct sockaddr*)&ser    ver,&len);
 34     if(_size < 0)
 35     {
 36         print_log(strerror(errno),__FUNCTION__,__LINE__);
 37     }
 38     else if(_size == 0)
 39     {
 40         const char *msg="server closed...";
 41         print_log(msg,__FUNCTION__,__LINE__);
 42     }
 43     else
 44     {
 45         buf[_size]=‘\0‘;
 46         _out=buf;
 47     }
 48     return _size;
 49 }   
 50 
 51 int udp_client::send_data(string& _in)
 52 {
 53     struct sockaddr_in server;
 54     server.sin_family=AF_INET;
 55     server.sin_port=htons(_port);
 56     server.sin_addr.s_addr=inet_addr(_ip.c_str());
 57     socklen_t len=sizeof(server);
 58     ssize_t _size=sendto(_sock,_in.c_str(),_in.size(),0,(struct sockaddr*)&    server,len);
 59     if(_size < 0)
 60     {
 61         print_log(strerror(errno),__FUNCTION__,__LINE__);
 62     }
 63     return _size;
 64 }

client_main.cpp

 1 #include "udp_client.h"
  2 #include "comm.h"
  3 
  4 void Usage(const char* proc)
  5 {
  6     assert(proc);
  7     cout<<"Usage:"<<proc<<"[ip] [port]"<<endl;
  8 }
  9 int main(int argc,char* argv[])
 10 {
 11     if(argc!=3)
 12     {
 13         Usage(argv[0]);
 14         exit(1);
 15     }
 16     string ip=argv[1];
 17     int port=atoi(argv[2]);
 18 
 19     std::string msg;
 20     std::string rec;
 21     std::string _in;
 22     char buf[_SIZE_];
 23     udp_client _cli(ip,port);
  24     _cli.init();
 25     _cli.send_data(msg);
 26     while(1)
 27     {
 28         cout<<"please input:";
 29         fflush(stdout);
 30         memset(buf,‘\0‘,sizeof(buf));
 31         ssize_t _s=read(0,buf,sizeof(buf)-1);
 32         if(_s >0)
 33         {
 34             rec=buf;
 35             _cli.send_data(rec);
 36         }
 37         if(buf=="quit")
 38         {
 39             cout<<"no data send"<<endl;
 40             return -1;
 41         }
 42         sleep(2);
 43         if(_cli.recv_data(_in)>0)
 44         {
 45             cout<<"server echo:"<<_in;
 46         }
 47     }
 48     return 0;
 49 }

Makefile

 1 ROOT_PATH=$(shell pwd)
  2 SERVER=$(ROOT_PATH)/server
  3 CLIENT=$(ROOT_PATH)/client
  4 COMM=$(ROOT_PATH)/comm
  5 DATA_POOL=$(ROOT_PATH)/data_pool
    
  8 SERVER_BIN=udp_server
  9 CLIENT_BIN=udp_client
 10 
 11 
 12 INCLUDE=-I$(COMM) -I$(DATA_POOL)
 13 INCLUDE+=-I$(DATA_POOL)
 14 INCLUDE+=-I$(ROOT_PATH)/lib/include
 15 
 16 CC=g++
 17 FLAGS=
 18 LDFLAGS=-lpthread #-static
 19 
 20 SER_SRC=$(shell ls -R $(SERVER) |grep -E ‘*.cpp‘)
 21 SER_SRC+=$(shell ls -R $(COMM) |grep -E ‘*.cpp‘)
 22 SER_SRC+=$(shell ls -R $(DATA_POOL) |grep -E ‘*.cpp‘)
 23 SER_OBJ=$(SER_SRC:.cpp=.o)
  
 25 CLI_SRC=$(shell ls -R $(CLIENT) |grep -E ‘*.cpp‘)
 26 CLI_SRC+=$(shell ls -R $(COMM) |grep -E ‘*.cpp‘)
 27 CLI_OBJ=$(CLI_SRC:.cpp=.o)
 28 
 29 .PHONY:all
 30 all:$(SERVER_BIN) $(CLIENT_BIN)
 31 $(SERVER_BIN):$(SER_OBJ)
 32     @$(CC) -o [email protected] $^ $(LDFLAGS)
 33     @echo "Linking [ $^ ] to [ [email protected] ] ...done"
 34 $(CLIENT_BIN):$(CLI_OBJ)
 35     @$(CC) -o [email protected] $^ $(LDFLAGS)
 36     @echo "Linking [ $^ ] to [ [email protected] ] ...done"
 37 %.o:$(COMM)/%.cpp
 38     @$(CC) -c $< $(INCLUDE) 
 39     @echo "Compling [ $(shell basename $<) ] to [ [email protected] ] ...done"
 40 %.o:$(DATA_POOL)/%.cpp
 41     @$(CC) -c $< $(INCLUDE) 
 42     @echo "Compling [ $(shell basename $<) ] to [ [email protected] ] ...done"
 43 %.o:$(SERVER)/%.cpp
 44     @$(CC) -c $< $(INCLUDE) 
 45     @echo "Compling [ $(shell basename $<) ] to [ [email protected] ] ...done"
 46 %.o:$(CLIENT)/%.cpp
 47     @$(CC) -c $< $(INCLUDE) 
 48     @echo "Compling [ $(shell basename $<) ] to [ [email protected] ] ...done"
 49 
 
 62 .PHONY:clean
 63 clean:
 64     @rm -f *.o $(SERVER_BIN) $(CLIENT_BIN)
 65     @echo "cleaning done..."    
 66 
 67 .PHONY:debug
 68 debug:
 69     @echo $(SER_SRC)    
 70     @echo $(CLI_SRC)
时间: 2024-08-01 15:43:57

UDP畅聊系统简单版本的相关文章

UDP畅聊系统数据的序列化与反序列化

comm中实现基本数据的序列化与反序列化 基于jsoncpp库,由c++编写,用于为网络数据提供序列化及反序列化功能 使用的几个类 Json::Value 可表示所有的类型,int,float,string等 Json::Reader 将json字符串解析到Value中,反序列化,使用Parse函数 Json::Writer 将Value转换成json字符串型,序列化 它的两个子类:Json::FastWriter 和Json::StyledWriter 两种不同的显示风格 Makefile  

畅聊Linux系统运维的未来

畅聊Linux系统运维的未来我想来跟大家聊聊Linux运维这一行业,从几个方面说下行业的现状.如何学好Linux和如何成为专业运维人员以及云服务对运Linux运维的影响. 一.linux行业状况我们都知道从1991年Linux开始火爆全球,蔓延至中国,随着智能中国.网络繁荣发展,众多应用基本都跑在Linux服务器上面,但对于大多数人来说还是不太了解.1.入坑门槛太高Linux属于类UNIX操作系统,从开发之初就不是针对普通大众的,而是专门从事计算机行业的员.Linux主要以命令行的方式操作,而这

openstack(liberty):部署实验平台(二,简单版本软件安装 part1)

软件安装过程中,考虑到现在是一个实验环境,且也考虑到规模不大,还有,网络压力不会大,出于简单考虑,将各个节点的拓扑结构改了一下,主要体现在网络节点和控制节点并在了一起.在一个服务器上安装! 到目前位置,我的这个平台,只有keystone,glance,neutron,dashboard以及nova几个服务.省出的那个服务器,打算也作为计算节点.所以,最新规划topo如下了: 绿色节点表示目前已经安装了openstack的模块软件,灰色部分,表示下一步即将安装的部分. 下面简要说下安装的过程,重点

linux小白-基础篇-系统简单优化

作为一个刚刚接触Linux的小白,通过一段时间的学习,将我自己的部分笔记整理后拿出来,请求大家指点:因为是"0"基础学起很多地方了解的都不够深入,希望各位前辈能够指点一下:予人玫瑰,手留余香,谢谢! 因为条件有限环境是用VM搭建起来的,下文主要是根据"老男孩教育视频"中的内容整理出来的系统简单优化,希望各位前辈看过以后可以给出建议: 已学习进步为目的,不喜勿喷!谢谢! 系统简单优化    命令 一.关闭selinux                         

Ubuntu学习笔记-win7&Ubuntu双系统简单搭建系统指南

win7&Ubuntu双系统简单搭建系统指南 本文是自己老本子折腾Ubuntu的一些记录,主要是搭建了一个能够足够娱乐(不玩游戏)专注练习自己编程能力的内容.只是简单的写了关于系统的安装和一些配置环境的简单搭建.并没有深入探讨系统地各项内容.希望可以给香简单使用的同学参考. 一.准备工作 打开UltraISO ,依次点击"文件"--"打开"--选择Ubuntu14.04系统镜像文件,确认打开后就能在软件界面内看到整个镜像的全部文件信息. 接下来开始制作系统安

基于Struct的云和租房系统(简单房屋出租)

基于Struct的云和租房系统(简单房屋出租) 系统采用javaBean实现ORM对象关系映射,前台纯JSP实现,后台struct映射,适合刚学习J2EE的新手,代码思路清晰,注解详细,数据库用的是mysql5.1,服务器用的tomcat7,JDK版本1.7. 编程软件Eclispe J2EE版本.是典型MVC架构,并且前后台分离,亦可以当做房屋中介房屋出租房屋销售管理系统二手房交易管理系统.具体功能这里不再赘述,请下方看系统详细演示图,如果大家有什么疑问或者什么不懂得可以在下方给我留言,或者你

linux系统原始版本介绍

*/--> pre.src {background-color: Black; color: White;} linux系统原始版本介绍 linux正式对外公布是在1991年 0.11 正是向外公布的内核版本 0.95加入虚拟文件系统思想 0.96加入网络支持和虚拟文件系统VFS 0.97 加入对新的SCSI驱动程序的支持 0.98 改善了对TCP/IP网络的支持 0.99重新设计对内存使用情况的使用分配,每个进程有4GB线性空间

Linux 查看系统的版本信息

在 Linux 中,有多种方法可以查看系统的版本信息. uname 命令 [email protected]:~$ uname -a Linux huey-K42JE 3.5.0-43-generic #66~precise1-Ubuntu SMP Thu Oct 24 14:55:08 UTC 2013 i686 i686 i386 GNU/Linux  lsb_release 命令 [email protected]:~$ lsb_release -a No LSB modules are

Linux下怎么查看当前系统的版本

Linux下怎么查看当前系统的版本: uname -r 功能说明:uname用来获取电脑和操作系统的相关信息. 语 法:uname [-amnrsvpio][--help][--version] 补充说明:uname可显示linux主机所用的操作系统的版本.硬件的名称等基本信息. 参 数: -a或–all     详细输出所有信息,依次为内核名称,主机名,内核版本号,内核版本,硬件名,处理器类型,硬件平台类型,操作系统名称 -m或–machine   显示主机的硬件(CPU)名 -n或-node