Skip to content

Commit e232fb1

Browse files
committed
split implementations of functions out to eventloop.cpp
1 parent 8e69c44 commit e232fb1

File tree

4 files changed

+132
-99
lines changed

4 files changed

+132
-99
lines changed

build/Jamfile

+1
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ lib boost_python
6868
import.cpp
6969
exec.cpp
7070
object/function_doc_signature.cpp
71+
eventloop.cpp
7172
: # requirements
7273
<link>static:<define>BOOST_PYTHON_STATIC_LIB
7374
<define>BOOST_PYTHON_SOURCE

include/boost/python/eventloop.hpp

+18-98
Original file line numberDiff line numberDiff line change
@@ -9,11 +9,8 @@
99
# ifndef EVENT_LOOP_PY2021_H_
1010
# define EVENT_LOOP_PY2021_H_
1111

12-
#include <mutex>
13-
#include <functional>
1412
#include <unordered_map>
1513
#include <boost/asio.hpp>
16-
#include <boost/bind.hpp>
1714
#include <boost/python.hpp>
1815

1916
namespace a = boost::asio;
@@ -32,40 +29,8 @@ class EventLoop
3229
std::unordered_map<int, std::unique_ptr<a::posix::stream_descriptor>> _descriptor_map;
3330
std::chrono::steady_clock::time_point _created_time;
3431

35-
void _add_reader_or_writer(int fd, py::object f, int key)
36-
{
37-
// add descriptor
38-
if (_descriptor_map.find(key) == _descriptor_map.end())
39-
{
40-
_descriptor_map.emplace(key,
41-
std::move(std::make_unique<a::posix::stream_descriptor>(_strand.context(), fd))
42-
);
43-
}
44-
45-
_descriptor_map.find(key)->second->async_wait(a::posix::descriptor::wait_type::wait_read,
46-
a::bind_executor(_strand, [key, f, loop=this] (const boost::system::error_code& ec)
47-
{
48-
// move descriptor
49-
auto iter = loop->_descriptor_map.find(key);
50-
if (iter != loop->_descriptor_map.end())
51-
{
52-
iter->second->release();
53-
loop->_descriptor_map.erase(iter);
54-
}
55-
loop->call_soon(f);
56-
}));
57-
return;
58-
}
59-
60-
void _remove_reader_or_writer(int key)
61-
{
62-
auto iter = _descriptor_map.find(key);
63-
if (iter != _descriptor_map.end())
64-
{
65-
iter->second->release();
66-
_descriptor_map.erase(iter);
67-
}
68-
}
32+
void _add_reader_or_writer(int fd, py::object f, int key);
33+
void _remove_reader_or_writer(int key);
6934

7035
public:
7136
EventLoop(a::io_context& ctx):
@@ -83,98 +48,53 @@ class EventLoop
8348
}
8449

8550
// TODO: implement this
86-
void call_soon_thread_safe(py::object f)
87-
{
88-
return;
89-
}
51+
inline void call_soon_thread_safe(py::object f) {};
9052

9153
// Schedule callback to be called after the given delay number of seconds
9254
// TODO: An instance of asyncio.Handle is returned, which can be used later to cancel the callback.
93-
void call_later(double delay, py::object f)
94-
{
95-
// add timer
96-
_id_to_timer_map.emplace(_timer_id,
97-
std::move(std::make_unique<a::steady_timer>(_strand.context(),
98-
std::chrono::steady_clock::now() + std::chrono::nanoseconds(int64_t(delay * 1e9))))
99-
);
100-
101-
_id_to_timer_map.find(_timer_id)->second->async_wait(
102-
// remove timer
103-
a::bind_executor(_strand, [id=_timer_id, f, loop=this] (const boost::system::error_code& ec)
104-
{
105-
loop->_id_to_timer_map.erase(id);
106-
loop->call_soon(f);
107-
}));
108-
_timer_id++;
109-
}
55+
void call_later(double delay, py::object f);
11056

111-
void call_at(double when, py::object f)
112-
{
113-
double diff = when - time();
114-
if (diff > 0)
115-
return call_later(diff, f);
116-
return call_soon(f);
117-
}
57+
void call_at(double when, py::object f);
11858

119-
double time()
59+
inline double time()
12060
{
121-
auto now = std::chrono::steady_clock::now();
122-
std::chrono::duration<double> diff = now - _created_time;
123-
return diff.count();
61+
return static_cast<std::chrono::duration<double>>(std::chrono::steady_clock::now() - _created_time).count();
12462
}
12563

12664
// week 2 ......start......
12765

128-
void add_reader(int fd, py::object f)
66+
inline void add_reader(int fd, py::object f)
12967
{
13068
_add_reader_or_writer(fd, f, fd * 2);
13169
}
13270

133-
void remove_reader(int fd)
71+
inline void remove_reader(int fd)
13472
{
13573
_remove_reader_or_writer(fd * 2);
13674
}
13775

138-
void add_writer(int fd, py::object f)
76+
inline void add_writer(int fd, py::object f)
13977
{
14078
_add_reader_or_writer(fd, f, fd * 2 + 1);
14179
}
14280

143-
void remove_writer(int fd)
81+
inline void remove_writer(int fd)
14482
{
14583
_remove_reader_or_writer(fd * 2 + 1);
14684
}
14785

14886

149-
void sock_recv()
150-
{
151-
152-
}
153-
154-
void sock_recv_into()
155-
{
156-
157-
}
158-
159-
void sock_sendall()
160-
{
87+
void sock_recv(py::object sock, int bytes);
16188

162-
}
89+
void sock_recv_into(py::object sock, py::object buffer);
16390

164-
void sock_connect()
165-
{
91+
void sock_sendall(py::object sock, py::object data);
16692

167-
}
168-
169-
void sock_accept()
170-
{
93+
void sock_connect(py::object sock, py::object address);
17194

172-
}
173-
174-
void sock_sendfile()
175-
{
176-
177-
}
95+
void sock_accept(py::object sock);
96+
97+
void sock_sendfile(py::object sock, py::object file, int offset = 0, int count = 0, bool fallback = true);
17898

17999
// week 2 ......end......
180100

src/eventloop.cpp

+111
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
// Copyright Pan Yue 2021.
2+
// Distributed under the Boost Software License, Version 1.0. (See
3+
// accompanying file LICENSE_1_0.txt or copy at
4+
// http://www.boost.org/LICENSE_1_0.txt)
5+
6+
// TODO:
7+
// 1. posix::stream_descriptor need windows version
8+
// 2. call_* need return async.Handle
9+
10+
#include <boost/asio.hpp>
11+
#include <boost/bind.hpp>
12+
#include <boost/python.hpp>
13+
14+
namespace a = boost::asio;
15+
namespace c = std::chrono;
16+
namespace py = boost::python;
17+
18+
namespace boost { namespace python { namespace eventloop {
19+
20+
void EventLoop::_add_reader_or_writer(int fd, py::object f, int key)
21+
{
22+
// add descriptor
23+
if (_descriptor_map.find(key) == _descriptor_map.end())
24+
{
25+
_descriptor_map.emplace(key,
26+
std::move(std::make_unique<a::posix::stream_descriptor>(_strand.context(), fd))
27+
);
28+
}
29+
30+
_descriptor_map.find(key)->second->async_wait(a::posix::descriptor::wait_type::wait_read,
31+
a::bind_executor(_strand, [key, f, loop=this] (const boost::system::error_code& ec)
32+
{
33+
// move descriptor
34+
auto iter = loop->_descriptor_map.find(key);
35+
if (iter != loop->_descriptor_map.end())
36+
{
37+
iter->second->release();
38+
loop->_descriptor_map.erase(iter);
39+
}
40+
loop->call_soon(f);
41+
}));
42+
return;
43+
}
44+
45+
void EventLoop::_remove_reader_or_writer(int key)
46+
{
47+
auto iter = _descriptor_map.find(key);
48+
if (iter != _descriptor_map.end())
49+
{
50+
iter->second->release();
51+
_descriptor_map.erase(iter);
52+
}
53+
}
54+
55+
void EventLoop::call_later(double delay, py::object f)
56+
{
57+
// add timer
58+
_id_to_timer_map.emplace(_timer_id,
59+
std::move(std::make_unique<a::steady_timer>(_strand.context(),
60+
std::chrono::steady_clock::now() + std::chrono::nanoseconds(int64_t(delay * 1e9))))
61+
);
62+
63+
_id_to_timer_map.find(_timer_id)->second->async_wait(
64+
// remove timer
65+
a::bind_executor(_strand, [id=_timer_id, f, loop=this] (const boost::system::error_code& ec)
66+
{
67+
loop->_id_to_timer_map.erase(id);
68+
loop->call_soon(f);
69+
}));
70+
_timer_id++;
71+
}
72+
73+
void EventLoop::call_at(double when, py::object f)
74+
{
75+
double diff = when - time();
76+
if (diff > 0)
77+
return call_later(diff, f);
78+
return call_soon(f);
79+
}
80+
81+
void EventLoop::sock_recv(py::object sock, int bytes)
82+
{
83+
84+
}
85+
86+
void EventLoop::sock_recv_into(py::object sock, py::object buffer)
87+
{
88+
89+
}
90+
91+
void EventLoop::sock_sendall(py::object sock, py::object data)
92+
{
93+
94+
}
95+
96+
void EventLoop::sock_connect(py::object sock, py::object address)
97+
{
98+
99+
}
100+
101+
void EventLoop::sock_accept(py::object sock)
102+
{
103+
104+
}
105+
106+
void EventLoop::sock_sendfile(py::object sock, py::object file, int offset, int count, bool fallback)
107+
{
108+
109+
}
110+
111+
}}}

src/fabscript

+2-1
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,8 @@ bpl = library('boost_python' + root.py_suffix,
4040
'wrapper.cpp',
4141
'import.cpp',
4242
'exec.cpp',
43-
'object/function_doc_signature.cpp'],
43+
'object/function_doc_signature.cpp',
44+
'eventloop.cpp'],
4445
dependencies=root.config,
4546
features=features + define('BOOST_PYTHON_SOURCE'))
4647

0 commit comments

Comments
 (0)