提升asio:是否可以将接受的tcp套接字转换为basic_socket_iostream(或以某种方式从中获取)?

时间:2011-11-04 00:36:21

标签: c++ sockets boost tcp boost-asio

所以这是我的问题:我们已经有accepted一个提升asio tcp套接字。我们所有的API都使用它。我们只需要在一个函数中执行“timeouted read”。

可以执行here所示的'timeouted read'。但我从我的API获得了提升asio tcp套接字,所以我想知道是否有可能将Boost :: asio socket转换为basic_socket_iostream。怎么做?

3 个答案:

答案 0 :(得分:4)

  

我想知道是否有可能将Boost :: asio socket转换为   basic_socket_iostream。怎么做?

您可以使用tcp::iostream::rdbuf()获取指向socket::basic_socket_streambuf然后assign()描述符的指针。

#include <boost/asio.hpp>

int
main()
{
    boost::asio::io_service io_service;
    boost::asio::ip::tcp::socket socket( io_service );
    boost::asio::ip::tcp::iostream stream;
    stream.rdbuf()->assign( boost::asio::ip::tcp::v4(), socket.native_handle() );
}

虽然这是非常错综复杂,但我强烈建议不要走这条路。如Ralf's answer所示,以及my answer建议的关联问题,您确实应该使用deadline_timer

答案 1 :(得分:2)

您没有说明是否要求不使用异步API,所以这可能对您有所帮助,也许不会:

除非我误解了你,否则我认为你提到的SO答案正在考虑一个不同的用例,即使用tcp :: iostream超时。如果您只是想在读取时添加超时,请查看timeout examples in the asio documentation吗?这是超时套接字操作的标准方法。

答案 2 :(得分:1)

对于任何会遇到这个问题的人来说,在尝试让这个工作几个小时后,我决定使用Boost&#34; Devices&#34;来编写一个简单的包装器类: http://www.boost.org/doc/libs/1_64_0/libs/iostreams/doc/tutorial/container_source.html

#include <iostream>
#include <boost/smart_ptr.hpp>
#include <boost/asio.hpp>
#include <boost/iostreams/stream.hpp>
#include <boost/iostreams/concepts.hpp> 

using boost::asio::ip::tcp;

typedef boost::shared_ptr<tcp::socket> socket_ptr;

class my_source : public boost::iostreams::source
{
public:
    my_source(socket_ptr sock) : _sock(sock)
    {

    }

    std::streamsize read(char* s, std::streamsize n)
    {
        return _sock->read_some(boost::asio::buffer(s, n));
    }

private:
    socket_ptr _sock;

};

用法示例:

boost::iostreams::stream<my_source> in(sock);

for (;;) {
    std::getline(in, line);
    if (line.length() > 0)
        std::cout << line << std::endl;
    else
        break;
}