#include "cbor/c/cbor.h" #include "thespian/c/handle.h" #include #include using std::string_view; extern "C" { void thespian_receive(thespian_receiver r, thespian_behaviour_state s, thespian_receiver_dtor dtor) { struct receiver_wrapper { thespian_receiver r; thespian_behaviour_state s; thespian_receiver_dtor dtor; ~receiver_wrapper() { dtor(s); } }; auto wrapper = std::make_shared(r, s, dtor); thespian::receive([wrapper](auto from, cbor::buffer msg) -> thespian::result { thespian_handle from_handle = reinterpret_cast( // NOLINT &from); auto *ret = wrapper->r(wrapper->s, from_handle, {msg.data(), msg.size()}); if (ret) { auto err = cbor::buffer(); const uint8_t *data = ret->base; std::copy(data, data + ret->len, back_inserter(err)); // NOLINT return thespian::to_error(err); } return thespian::ok(); }); } auto thespian_get_trap() -> bool { return thespian::trap(); } auto thespian_set_trap(bool on) -> bool { return thespian::trap(on); } void thespian_link(thespian_handle h) { thespian::handle *h_{ reinterpret_cast( // NOLINT(*-reinterpret-cast) h)}; thespian::link(*h_); } auto thespian_self() -> thespian_handle { auto &self = thespian::self_ref(); return reinterpret_cast(&self); // NOLINT(*-reinterpret-cast) } auto thespian_spawn_link(thespian_behaviour b, thespian_behaviour_state s, const char *name, thespian_env env, thespian_handle *handle) -> int { const thespian::env_t empty_env_{}; thespian::env_t env_ = env ? *reinterpret_cast(env) : empty_env_; // NOLINT auto ret = spawn_link( [b, s]() -> thespian::result { auto *ret = b(s); if (ret) { auto err = cbor::buffer(); const uint8_t *data = ret->base; // NOLINT std::copy(data, data + ret->len, back_inserter(err)); // NOLINT return thespian::to_error(err); } return thespian::ok(); }, string_view(name), std::move(env_)); if (!ret) return -1; *handle = reinterpret_cast( // NOLINT new thespian::handle{ret.value()}); return 0; } }