Actors: destroy events in mailbox in context of actor

GitOrigin-RevId: f3b47e7b80889a65ead6a30e918513409df4c667
This commit is contained in:
Arseny Smirnov 2019-07-30 16:22:43 +03:00
parent a7005ee358
commit 06efc32de9
5 changed files with 58 additions and 5 deletions

View File

@ -70,14 +70,13 @@ inline void ActorInfo::on_actor_moved(Actor *actor_new_ptr) {
inline void ActorInfo::clear() { inline void ActorInfo::clear() {
// LOG_IF(WARNING, !mailbox_.empty()) << "Destroy actor with non-empty mailbox: " << get_name() // LOG_IF(WARNING, !mailbox_.empty()) << "Destroy actor with non-empty mailbox: " << get_name()
// << format::as_array(mailbox_); // << format::as_array(mailbox_);
mailbox_.clear(); CHECK(mailbox_.empty());
CHECK(!actor_);
CHECK(!is_running()); CHECK(!is_running());
CHECK(!is_migrating()); CHECK(!is_migrating());
// NB: must be in non migrating state // NB: must be in non migrating state
// store invalid scheduler id. // store invalid scheduler id.
sched_id_.store((1 << 30) - 1, std::memory_order_relaxed); sched_id_.store((1 << 30) - 1, std::memory_order_relaxed);
destroy_actor();
// Destroy context only after destructor.
context_.reset(); context_.reset();
} }
@ -93,6 +92,7 @@ inline void ActorInfo::destroy_actor() {
break; break;
} }
actor_ = nullptr; actor_ = nullptr;
mailbox_.clear();
} }
template <class ActorT> template <class ActorT>

View File

@ -369,6 +369,7 @@ void Scheduler::do_stop_actor(ActorInfo *actor_info) {
event_context_ptr_->flags = 0; event_context_ptr_->flags = 0;
} else { } else {
owner_ptr = actor_info->get_actor_unsafe()->clear(); owner_ptr = actor_info->get_actor_unsafe()->clear();
actor_info->destroy_actor();
} }
destroy_actor(actor_info); destroy_actor(actor_info);
} }

View File

@ -465,3 +465,55 @@ TEST(Actors, do_after_stop) {
} }
sched.finish(); sched.finish();
} }
class XContext : public ActorContext {
public:
void validate() {
CHECK(x == 1234);
}
~XContext() {
x = 0;
}
int x = 1234;
};
class WithContext : public Actor {
public:
void start_up() override {
set_context(std::make_shared<XContext>());
}
void f(unique_ptr<Guard> guard) {
}
void close() {
stop();
}
private:
};
void check_context() {
auto ptr = static_cast<XContext *>(Scheduler::context());
CHECK(ptr);
ptr->validate();
}
TEST(Actors, context_during_destruction) {
SET_VERBOSITY_LEVEL(VERBOSITY_NAME(ERROR));
ConcurrentScheduler sched;
int threads_n = 0;
sched.init(threads_n);
{
auto guard = sched.get_main_guard();
auto with_context = create_actor<WithContext>("WithContext").release();
send_closure(with_context, &WithContext::f, create_lambda_guard([] { check_context(); }));
send_closure_later(with_context, &WithContext::close);
send_closure(with_context, &WithContext::f, create_lambda_guard([] { check_context(); }));
send_closure(with_context, &WithContext::f, create_lambda_guard([] { Scheduler::instance()->finish(); }));
}
sched.start();
while (sched.run_main(10)) {
// empty
}
sched.finish();
}

View File

@ -4,7 +4,7 @@
// Distributed under the Boost Software License, Version 1.0. (See accompanying // Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
// //
#include "test/data.h" #include "data.h"
namespace td { namespace td {
static const char thumbnail_arr[] = static const char thumbnail_arr[] =
"_9j_4AAQSkZJRgABAQEASABIAAD_2wBDAAICAgICAQICAgIDAgIDAwYEAwMDAwcFBQQGCAcJCAgHCAgJCg0LCQoMCggICw8LDA0ODg8OCQsQERAOEQ" "_9j_4AAQSkZJRgABAQEASABIAAD_2wBDAAICAgICAQICAgIDAgIDAwYEAwMDAwcFBQQGCAcJCAgHCAgJCg0LCQoMCggICw8LDA0ODg8OCQsQERAOEQ"

View File

@ -33,7 +33,7 @@
#include "td/utils/Status.h" #include "td/utils/Status.h"
#include "td/utils/UInt.h" #include "td/utils/UInt.h"
#include "test/data.h" #include "data.h"
#include <algorithm> #include <algorithm>
#include <cstdlib> #include <cstdlib>