Commit 2f1d6a3d authored by Dominik Charousset's avatar Dominik Charousset

fix libcppa to work with Boost.Context 1.52

parent a29c423d
...@@ -162,7 +162,7 @@ set(LD_FLAGS ${CMAKE_LD_LIBS} ${PTHREAD_LIBRARIES}) ...@@ -162,7 +162,7 @@ set(LD_FLAGS ${CMAKE_LD_LIBS} ${PTHREAD_LIBRARIES})
if (DISABLE_CONTEXT_SWITCHING) if (DISABLE_CONTEXT_SWITCHING)
# explicitly disabled # explicitly disabled
else (DISABLE_CONTEXT_SWITCHING) else (DISABLE_CONTEXT_SWITCHING)
find_package(Boost COMPONENTS context) find_package(Boost 1.52.0 COMPONENTS context)
# without REQUIRED, find_package(Boost...) returns with Boost_FOUND=FALSE # without REQUIRED, find_package(Boost...) returns with Boost_FOUND=FALSE
if (NOT Boost_FOUND) if (NOT Boost_FOUND)
set(DISABLE_CONTEXT_SWITCHING true) set(DISABLE_CONTEXT_SWITCHING true)
......
...@@ -33,13 +33,13 @@ ...@@ -33,13 +33,13 @@
namespace cppa { namespace util { namespace cppa { namespace util {
struct fiber_impl; class fiber_impl;
class fiber { class fiber {
public: public:
fiber() throw(); fiber();
fiber(void (*func)(void*), void* arg1); fiber(void (*func)(void*), void* arg1);
......
...@@ -57,37 +57,69 @@ namespace cppa { namespace util { ...@@ -57,37 +57,69 @@ namespace cppa { namespace util {
void fiber_trampoline(intptr_t iptr); void fiber_trampoline(intptr_t iptr);
struct fiber_impl { namespace ctx = boost::context;
void* m_arg; class fiber_impl {
bool m_converted;
void (*m_fun)(void*); public:
boost::ctx::fcontext_t m_ctx;
boost::ctx::stack_allocator m_alloc; fiber_impl() : m_ctx(nullptr) { }
fiber_impl() : m_arg(nullptr), m_converted(true), m_fun(nullptr) { } virtual ~fiber_impl() { }
fiber_impl(void (*fun)(void*), void* arg) : m_arg(arg), m_converted(false), m_fun(fun) { virtual void run() { }
auto st = m_alloc.allocate(boost::ctx::minimum_stacksize());
m_ctx.fc_stack.base = st; void swap(fiber_impl* to) {
m_ctx.fc_stack.limit = static_cast<char*>(st) - boost::ctx::minimum_stacksize(); ctx::jump_fcontext(m_ctx, to->m_ctx, (intptr_t) to);
boost::ctx::make_fcontext(&m_ctx, fiber_trampoline);
} }
inline void run() { protected:
m_fun(m_arg);
ctx::fcontext_t* m_ctx;
};
// a fiber representing a thread ('converts' the thread to a fiber)
class converted_fiber : public fiber_impl {
public:
converted_fiber() { m_ctx = &m_ctx_obj; }
private:
ctx::fcontext_t m_ctx_obj;
};
// a fiber executing a function
class fun_fiber : public fiber_impl {
typedef ctx::guarded_stack_allocator allocator;
public:
fun_fiber(void (*fun)(void*), void* arg) : m_arg(arg), m_fun(fun) {
m_size = allocator::minimum_stacksize();
m_ctx = ctx::make_fcontext(m_alloc.allocate(m_size), m_size, fiber_trampoline);
} }
void swap(fiber_impl* to) { ~fun_fiber() {
boost::ctx::jump_fcontext(&m_ctx, &(to->m_ctx), (intptr_t) to); m_alloc.deallocate(m_ctx->fc_stack.sp, m_size);
} }
~fiber_impl() { virtual void run() {
if (m_converted == false) { m_fun(m_arg);
m_alloc.deallocate(m_ctx.fc_stack.base, boost::ctx::minimum_stacksize());
}
} }
private:
void* m_arg;
void (*m_fun)(void*);
size_t m_size;
allocator m_alloc;
}; };
void fiber_trampoline(intptr_t iptr) { void fiber_trampoline(intptr_t iptr) {
...@@ -95,12 +127,9 @@ void fiber_trampoline(intptr_t iptr) { ...@@ -95,12 +127,9 @@ void fiber_trampoline(intptr_t iptr) {
ptr->run(); ptr->run();
} }
fiber::fiber() throw() : m_impl(new fiber_impl) { fiber::fiber() : m_impl(new converted_fiber) { }
}
fiber::fiber(void (*func)(void*), void* arg) fiber::fiber(void (*f)(void*), void* arg) : m_impl(new fun_fiber(f, arg)) { }
: m_impl(new fiber_impl(func, arg)) {
}
void fiber::swap(fiber& from, fiber& to) { void fiber::swap(fiber& from, fiber& to) {
from.m_impl->swap(to.m_impl); from.m_impl->swap(to.m_impl);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment