【问题标题】:Boost asio networking separate send and receive [closed]Boost asio网络分离发送和接收[关闭]
【发布时间】:2016-02-13 11:53:04
【问题描述】:
  • 服务器可以随时向客户端发送数据。例如,服务器包含某种发送函数,另一个类可能会调用它。
  • 服务器永远异步读取
  • 客户端也是如此。

我对 boost::asio 中的网络还很陌生。我了解 TCP 异步服务器和客户端的示例,但这些是回显客户端/服务器。如果服务器收到数据,它会立即发回。但我需要服务器接收数据,为另一个类做一些其他操作,然后发送给特定的客户端(服务器将有多个客户端连接到它)。并且此发送可能在 1 秒或任何给定时间之后。

在使用 GNU 库的套接字编程中,我已经实现了这个。服务器中有一个线程用于侦听,另一个线程用于发送。对客户端也一样。我在 boost:Asio 中研究过这种方法,但只是不知道如何实现它。任何人都可以指出正确的方向吗?

【问题讨论】:

    标签: c++ multithreading sockets boost network-programming


    【解决方案1】:

    全双工套接字不需要多个线程。事实上,如果你不这样做会更容易。

    如果您有多个线程,则必须使用链来协调套接字上的所有异步操作。

    除此之外,真的就是这么简单:

    最简单的例子:

    Live On Coliru

    #include <boost/asio.hpp>
    #include <memory>
    #include <iostream>
    
    namespace io = boost::asio;
    using tcp = io::ip::tcp;
    using boost::system::error_code;
    
    struct session : std::enable_shared_from_this<session> {
    
        session(io::io_service& svc) : _sock(svc), _tim(svc) {}
    
        void run() {
            ping_loop();
            receive_loop();
        }
    
      private:
        friend class server;
        tcp::socket        _sock;
        io::deadline_timer _tim;
        io::streambuf      _buf;
    
        void receive_loop() {
            auto This = shared_from_this();
            io::async_read_until(_sock, _buf, "\n", [This,this](error_code ec, size_t) {
                    if (ec)
                        std::cerr << "Receive error: " << ec.message() << "\n";
                    else {
                        std::cout << "Received '" << &_buf << "'\n";
    
                        // chain
                        receive_loop();
                    }
                });
        }
    
        std::string _ping = "ping\n";
    
        void ping_loop() {
            _tim.expires_from_now(boost::posix_time::millisec(100));
            auto This = shared_from_this();
    
            _tim.async_wait([This,this](error_code ec) {
                    if (!ec) {
                        io::async_write(_sock, io::buffer(_ping), [This,this](error_code,size_t) {});
    
                        // chain
                        ping_loop();
                    }
                });
        }
    };
    
    class server {
      public:
    
        void start() {
            _acc.bind({ io::ip::address_v4{}, 6768 });
            _acc.listen(5);
            accept_loop();
    
            _svc.run(); // TODO thread? shutdown?
        }
    
      private:
    
        void accept_loop() {
            auto sess = std::make_shared<session>(_svc);
    
            _acc.async_accept(sess->_sock, [this,sess](error_code ec){
                    if (ec) {
                        std::cerr << "Accept error: " << ec.message() << "\n";
                    } else {
                        sess->run();
    
                        // chain
                        accept_loop();
                    }
                });
        }
    
        io::io_service _svc;
        tcp::acceptor _acc { _svc, tcp::v4() };
    };
    
    int main() {
        server s;
        s.start();
    }
    

    当像这样运行客户端/客户端时:

    while sleep 1; do date; done | nc localhost 6767
    

    服务器输出如下:

    Received 'Thu Nov 12 10:24:08 CET 2015
    '
    Received 'Thu Nov 12 10:24:09 CET 2015
    '
    Received 'Thu Nov 12 10:24:10 CET 2015
    '
    Received 'Thu Nov 12 10:24:11 CET 2015
    '
    Received 'Thu Nov 12 10:24:12 CET 2015
    '
    Received 'Thu Nov 12 10:24:13 CET 2015
    '
    Received 'Thu Nov 12 10:24:14 CET 2015
    '
    Received 'Thu Nov 12 10:24:15 CET 2015
    '
    Receive error: End of file
    

    当客户端连续接收时

    ping
    ping
    ...
    

    【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-10-13
    • 2016-05-21
    • 1970-01-01
    • 1970-01-01
    • 2014-11-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多