Unverified Commit 1b29bf10 authored by Noir's avatar Noir Committed by GitHub

Merge pull request #1231

Fix logging of actor constructor arguments
parents 6dc7bf42 5d61ec64
......@@ -23,6 +23,9 @@ is based on [Keep a Changelog](https://keepachangelog.com).
- The handle type `typed_actor` now can construct from a `typed_actor_pointer`.
This resolves a compiler error when trying to initialize a handle for
`my_handle` from a self pointer of type `my_handle::pointer_view` (#1218).
- Passing a function reference to the constructor of an actor caused a compiler
error when building with logging enabled. CAF now properly handles this edge
case and logs such constructor arguments as `<unprintable>` (#1229).
## [0.18.0] - 2021-01-25
......
......@@ -287,7 +287,15 @@ bool save(Inspector& f, T& x) {
template <class Inspector, class T>
bool save(Inspector& f, const T& x) {
return save(f, as_mutable_ref(x), inspect_access_type<Inspector, T>());
if constexpr (!std::is_function<T>::value) {
return save(f, as_mutable_ref(x), inspect_access_type<Inspector, T>());
} else {
// Only inspector such as the stringification_inspector are going to accept
// function pointers. Most other inspectors are going to trigger a static
// assertion when passing `inspector_access_type::none`.
auto fptr = std::add_pointer_t<T>{x};
return save(f, fptr, inspector_access_type::none{});
}
}
template <class Inspector, class T>
......
......@@ -124,30 +124,45 @@ CAF_TEST(states with static C string names override the default name) {
test_name<named_state>("testee");
}
namespace {
int32_t add_operation(int32_t x, int32_t y) {
return x + y;
}
} // namespace
CAF_TEST(states can accept constructor arguments and provide a behavior) {
struct state_type {
int x;
int y;
state_type(int x, int y) : x(x), y(y) {
using operation_type = int32_t (*)(int32_t, int32_t);
int32_t x;
int32_t y;
operation_type f;
state_type(int32_t x, int32_t y, operation_type f) : x(x), y(y), f(f) {
// nop
}
behavior make_behavior() {
return {
[=](int x, int y) {
[=](int32_t x, int32_t y) {
this->x = x;
this->y = y;
},
[=](get_atom) { return f(x, y); },
};
}
};
using actor_type = stateful_actor<state_type>;
auto testee = sys.spawn<actor_type>(10, 20);
auto testee = sys.spawn<actor_type>(10, 20, add_operation);
auto& state = deref<actor_type>(testee).state;
CAF_CHECK_EQUAL(state.x, 10);
CAF_CHECK_EQUAL(state.y, 20);
inject((int, int), to(testee).with(1, 2));
inject((get_atom), from(self).to(testee).with(get_atom_v));
expect((int32_t), from(testee).to(self).with(30));
inject((int32_t, int32_t), to(testee).with(1, 2));
CAF_CHECK_EQUAL(state.x, 1);
CAF_CHECK_EQUAL(state.y, 2);
inject((get_atom), from(self).to(testee).with(get_atom_v));
expect((int32_t), from(testee).to(self).with(3));
}
CAF_TEST(states optionally take the self pointer as first argument) {
......
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