Skip to content

Commit

Permalink
add implementations for eventloop functions sock_*
Browse files Browse the repository at this point in the history
  • Loading branch information
philoinovsky committed Jun 28, 2021
1 parent 5747a3a commit 211ae97
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 9 deletions.
6 changes: 3 additions & 3 deletions include/boost/python/eventloop.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,11 +67,11 @@ class event_loop
}


void sock_recv(object sock, int bytes);
object sock_recv(object sock, size_t nbytes);

void sock_recv_into(object sock, object buffer);
size_t sock_recv_into(object sock, object buffer);

void sock_sendall(object sock, object data);
object sock_sendall(object sock, object data);

void sock_connect(object sock, object address);

Expand Down
53 changes: 47 additions & 6 deletions src/eventloop.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,28 @@
#include <boost/bind.hpp>
#include <boost/python.hpp>
#include <boost/python/eventloop.hpp>
#include <boost/mpl/vector.hpp>
#include <Python.h>


namespace boost { namespace python { namespace asio {
namespace
{

void _sock_recv_handler(std::promise<std::vector<char>>& prom, size_t nbytes, int fd, size_t& nbytes_read)
{
std::vector<char> buffer(nbytes);
nbytes_read = read(fd, buffer.data(), nbytes);
prom.set_value(std::move(buffer));
}

void _sock_send_handler(std::promise<size_t>& prom, int fd, const char *py_str, size_t len)
{
size_t nwrite = write(fd, py_str, len);
prom.set_value(nwrite);
}

}

void event_loop::_add_reader_or_writer(int fd, object f, int key)
{
Expand Down Expand Up @@ -76,19 +95,41 @@ void event_loop::call_at(double when, object f)
return call_soon(f);
}

void event_loop::sock_recv(object sock, int bytes)
object event_loop::sock_recv(object sock, size_t nbytes)
{

int fd = extract<int>(sock.attr("fileno")());
std::promise<std::vector<char>> prom;
std::future<std::vector<char>> fut = prom.get_future();
size_t nbytes_read;
add_reader(fd, make_function(bind(_sock_recv_handler, std::ref(prom), nbytes, fd, nbytes_read),
default_call_policies(), boost::mpl::vector<void, object>()));
return object(handle<>(PyBytes_FromStringAndSize(fut.get().data(), nbytes)));
}

void event_loop::sock_recv_into(object sock, object buffer)
size_t event_loop::sock_recv_into(object sock, object buffer)
{

int fd = extract<int>(sock.attr("fileno")());
size_t nbytes = extract<size_t>(buffer.attr("__len__")());
std::promise<std::vector<char>> prom;
std::future<std::vector<char>> fut = prom.get_future();
size_t nbytes_read;
add_reader(fd, make_function(bind(_sock_recv_handler, std::ref(prom), nbytes, fd, nbytes_read),
default_call_policies(), boost::mpl::vector<void, object>()));
buffer = object(handle<>(PyBytes_FromStringAndSize(fut.get().data(), nbytes)));
return nbytes_read;
}

void event_loop::sock_sendall(object sock, object data)
object event_loop::sock_sendall(object sock, object data)
{

int fd = extract<int>(sock.attr("fileno")());
char const* py_str = extract<char const*>(data.attr("decode")());
size_t len = extract<size_t>(data.attr("__len__")());
std::promise<size_t> prom;
std::future<size_t> fut = prom.get_future();
add_writer(fd, make_function(bind(_sock_send_handler, std::ref(prom), fd, py_str, len),
default_call_policies(), boost::mpl::vector<void, object>()));
fut.wait();
return object();
}

void event_loop::sock_connect(object sock, object address)
Expand Down

0 comments on commit 211ae97

Please sign in to comment.