Fabric: Proper failCallback handling in EventBeatBasedExecutor

Summary: That's why we need the previous three diffs. Synchonous executor deadlocks if the beat is missing.

Reviewed By: sahrens

Differential Revision: D10081501

fbshipit-source-id: 9986d0a1844e642048b6f37a1fcb5f623a267663
This commit is contained in:
Valentin Shergin 2018-10-08 14:34:25 -07:00 committed by Facebook Github Bot
parent 02d2e85af3
commit 5f4aa6ae42
3 changed files with 10 additions and 4 deletions

View File

@ -46,6 +46,9 @@ void MessageQueueEventBeat::induce() const {
// If `wasExecuted` was destroyed before set to `true`, // If `wasExecuted` was destroyed before set to `true`,
// it means that the execution block was deallocated not being executed. // it means that the execution block was deallocated not being executed.
// This indicates that `messageQueueThread_` is being deallocated. // This indicates that `messageQueueThread_` is being deallocated.
// This trick is quite expensive due to deallocation and messing with atomic
// counters. Seems we need this only for making hot-reloading mechanism
// thread-safe. Hence, let's leave it to be DEBUG-only for now.
auto wasExecuted = std::shared_ptr<bool>(new bool {false}, [this](bool *wasExecuted) { auto wasExecuted = std::shared_ptr<bool>(new bool {false}, [this](bool *wasExecuted) {
if (!*wasExecuted && failCallback_) { if (!*wasExecuted && failCallback_) {
failCallback_(); failCallback_();

View File

@ -19,7 +19,8 @@ using Mode = EventBeatBasedExecutor::Mode;
EventBeatBasedExecutor::EventBeatBasedExecutor(std::unique_ptr<EventBeat> eventBeat): EventBeatBasedExecutor::EventBeatBasedExecutor(std::unique_ptr<EventBeat> eventBeat):
eventBeat_(std::move(eventBeat)) { eventBeat_(std::move(eventBeat)) {
eventBeat_->setBeatCallback(std::bind(&EventBeatBasedExecutor::onBeat, this)); eventBeat_->setBeatCallback(std::bind(&EventBeatBasedExecutor::onBeat, this, true));
eventBeat_->setFailCallback(std::bind(&EventBeatBasedExecutor::onBeat, this, false));
} }
void EventBeatBasedExecutor::operator()(Routine routine, Mode mode) const { void EventBeatBasedExecutor::operator()(Routine routine, Mode mode) const {
@ -52,7 +53,7 @@ void EventBeatBasedExecutor::execute(Task task) const {
eventBeat_->induce(); eventBeat_->induce();
} }
void EventBeatBasedExecutor::onBeat() const { void EventBeatBasedExecutor::onBeat(bool success) const {
std::vector<Task> tasks; std::vector<Task> tasks;
{ {
@ -67,7 +68,9 @@ void EventBeatBasedExecutor::onBeat() const {
} }
for (const auto task : tasks) { for (const auto task : tasks) {
if (success) {
task.routine(); task.routine();
}
if (task.callback) { if (task.callback) {
task.callback(); task.callback();

View File

@ -43,7 +43,7 @@ public:
void operator()(Routine routine, Mode mode = Mode::Asynchronous) const; void operator()(Routine routine, Mode mode = Mode::Asynchronous) const;
private: private:
void onBeat() const; void onBeat(bool success = true) const;
void execute(Task task) const; void execute(Task task) const;
std::unique_ptr<EventBeat> eventBeat_; std::unique_ptr<EventBeat> eventBeat_;