• 转:sock_ev——linux平台socket事件框架(基于字节流的测试程序) .


    原文:http://blog.csdn.net/gdutliuyun827/article/details/8257186

    由于工作与学习的需要,写了一个socket的事件处理框架,在公司写的已经使用了一段时间,下班后回家抽出时间又重写了一下,并进行了完善,起名为:sock_ev;

    最近正在调试阶段,源代码暂且不提供,以防误人子弟,会尽快提供出来;先把最基本的测试程序贴上来,让感兴趣的同仁可以有个感性的认识,希望大家多加关注
     
    支持以下功能:
    1、三种事件监听方式:select、poll、epoll
    2、对读、写事件进行监控
    3、实现了inet域、unix域的通信
    4、支持字节流、数据包两种方式
     
    地址格式采取以下形式:
    stream://192.168.2.10:8080
    dgram://192.168.2.10:8080
    stream://unix.domain.ipc
    dgram://unix.domain.ipc

    注:地址形式采取字符串的形式;stream与dgram分别表示收发数据时采用字节流与数据报的形式。在inet域进行数据传输时要指定ip地址与端口号,注意ip地址与端口号之间用“:”分割,我是用冒号区分的inet域还是unix域;在unix域传输数据时指定一个合法的路径(不要求路径真是存在,我会把它放在/proc下面)。对于inet域服务器端的ip地址支持“*”(i.e: stream://*:8888).

     
    基于字节流的client端测试程序:
    /***************************************************************************************
    ****************************************************************************************
    * FILE        : client_test.h
    * Description    :
    *            
    * Copyright (c) 2012 by Liu Yanyun(E-mail:liuyun827@foxmail.com). All Rights Reserved.
    * Without permission, shall not be used for any commercial purpose
    *
    * History:
    * Version        Name         Date            Description
       0.1        Liu Yanyun        2012/12/03        Initial Version


    ****************************************************************************************
    ****************************************************************************************/

    #include "socket.h"
    #include "log_trace.h"
    #include "socket_addr.h"
    #include "socket_base.h"
    #include <iostream>

    using namespace std;

    int main()
    {
      Socket *clt = Socket::create();//Socket类封装的socket相关的操作,创建一个Socket
      bool ret = clt->connect("stream://192.168.2.10:8080");//向服务器发起连接
      ret = ret;

      char buf[100] = {0};
      clt->recv(buf, sizeof(buf));//发送数据到server端
      cout<<buf<<endl;

      sprintf(buf, "%s", "hello too");
      clt->send(buf, strlen(buf));//接受server发送来的数据

      sleep(20);

      Socket::destroy(clt);//通讯结束销毁创建的Socket

      return 0;
    }

    server端测试程序:

    /***************************************************************************************
    ****************************************************************************************
    * FILE        : server_test.cc
    * Description    :
    *            
    * Copyright (c) 2012 by Liu Yanyun(E-mail:liuyun827@foxmail.com). All Rights Reserved.
    * Without permission, shall not be used for any commercial purpose
    *
    * History:
    * Version        Name         Date            Description
       0.1        Liu Yanyun        2012/12/03        Initial Version

    ****************************************************************************************
    ****************************************************************************************/

    #include "socket.h"
    #include "log_trace.h"
    #include "socket_addr.h"
    #include "socket_base.h"
    #include "event_loop.h"
    #include <iostream>

    using namespace std;

    //有可读事件发生(有数据发送过)调用的callback
    void readCb(EventLoop *loop_, Socket *sock_, EventType evt_, void *arg_)
    {
      char buf[100] = {0};
      int ret = sock_->recv(buf, sizeof(buf));
      if(0 == ret)
      {
        loop_->removeEvt(sock_, evRead);
        Socket::destroy(sock_);
        printf("the other is connection is closed,destroy it ");
      }

      printf("buf:%s;arg:%s ", buf, (char*)arg_);
    }

    /*
    接受新的连接请求的callback;loop_:所在的监听loop,sock_此处是server的Socket,evt_触发的事件,
    arg_注册callback是传递的参数,类似于pthread_create()
    */
    void acceptCb(EventLoop *loop_, Socket *sock_, EventType evt_, void *arg_)
    {
      printf("accept callback trigger:%s ", (char*)arg_);
      Socket *conn = Socket::create();
      sock_->accept(conn);//接受客户端的连接,
      char *test = "test arg sock read";
      loop_->addEvt(conn, readCb, evRead, test);

      char buf[100] = {"hello"};
      conn->send(buf, strlen(buf));
    }

    int main()
    {
      EventLoop loop;//EventLoop用于管理监听的事件,实现了select poll epoll
      loop.initialize(pollLoop);//此处使用poll方式; epollLoop:epoll; selectLoop:select

      Socket *ser = Socket::create();
      bool ret = ser->open("stream://192.168.2.10:8080");//在这个地址打开监听端口,可以用;stream://*:8080

      /*
       添加到事件监听框架中,采取使用callback的形式,下面注册的是read事件,最后的参数是当callback调用的时候回传递过去。
      */
      char *test = "test arg accept";
      loop.addEvt(ser, acceptCb, evRead, test);

      loop.listen(3000);//此处是循环监听事件的,内部会调用select、poll或epoll;有事件触发,会调用注册的callback

      Socket::destroy(ser);

      return 0;
    }
    上面的例子是inet域的数据传输,假如换成unix域的只需要把"stream://192.168.2.10:8080"修改为:"stream://unixDomainTest"即可。

  • 相关阅读:
    研究SandHook
    MYSQL 事务与锁
    Java创造者詹姆斯·高斯林采访
    mybatis like 模糊查询
    【科普】彻底搞清楚什么是交换机什么是路由器。程序员基本功哦
    MinIO的简单使用实践
    如何将微信公众号的文章怎么保存转化为word文档?
    如何在recoil中主动刷新seloctor中缓存的值
    【译文】探索Recoil中的异步请求
    魅族云相册批量下载方案
  • 原文地址:https://www.cnblogs.com/skyofbitbit/p/3672860.html
Copyright © 2020-2023  润新知