我们可以使用boost.asio创建未命名的套接字来模拟匿名管道吗?

时间:2017-03-18 22:26:57

标签: c++ boost ipc boost-asio

Linux上的

socketpair()允许您创建未命名的套接字。 boost.asio库中有类似的东西吗?我正在尝试使用boost.asio库来模拟匿名管道。我知道boost.process支持这个,但我想使用boost.asio库。顺便说一下为什么在boost.asio中缺少匿名管道?

1 个答案:

答案 0 :(得分:3)

我编写了下面的代码,使用boost.asio库来模拟管道。它唯一的演示代码,没有消息边界检查,错误检查等。

#include <boost/asio.hpp>
#include <boost/bind.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <iostream>
#include <cctype>
#include <boost/array.hpp>

using boost::asio::local::stream_protocol;

int main()
{
    try
    {
        boost::asio::io_service io_service;

        stream_protocol::socket parentSocket(io_service);
        stream_protocol::socket childSocket(io_service);

        //create socket pair
        boost::asio::local::connect_pair(childSocket, parentSocket);
        std::string request("Dad I am your child, hello!");
        std::string dadRequest("Hello son!");

        //Create child process
        pid_t pid = fork();
        if( pid < 0 ){
            std::cerr << "fork() erred\n";
        } else if (pid == 0 ) { //child process
            parentSocket.close(); // no need of parents socket handle, childSocket is bidirectional stream socket unlike pipe that has different handles for read and write
            boost::asio::write(childSocket, boost::asio::buffer(request)); //Send data to the parent

            std::vector<char> dadResponse(dadRequest.size(),0);
            boost::asio::read(childSocket, boost::asio::buffer(dadResponse)); //Wait for parents response

            std::cout << "Dads response: ";
            std::cout.write(&dadResponse[0], dadResponse.size());
            std::cout << std::endl;


        } else { //parent
            childSocket.close(); //Close childSocket here use one bidirectional socket
            std::vector<char> reply(request.size());
            boost::asio::read(parentSocket, boost::asio::buffer(reply)); //Wait for child process to send message

            std::cout << "Child message: ";
            std::cout.write(&reply[0], request.size());
            std::cout << std::endl;

            sleep(5); //Add 5 seconds delay before sending response to parent
            boost::asio::write(parentSocket, boost::asio::buffer(dadRequest)); //Send child process response

        }
    }
    catch (std::exception& e)
    {
        std::cerr << "Exception: " << e.what() << "\n";
        std::exit(1);
    }
}