[modular] Prevent basemgr from shutting down twice.
This happens as a race condition during CQ when a test times out *and*
completes at the same time; in this instance, dev_base_shell calls
BaseShellContext::Shutdown() twice. basemgr should be resilient against
this race.
Testing=ran tests with a smaller timeout and saw that two-time-shutdown
doesn't happen.
Change-Id: I867dc3f84e37eba0eae84c1713206a416b728af1
diff --git a/bin/basemgr/basemgr_impl.cc b/bin/basemgr/basemgr_impl.cc
index 9b50d90..891c5e8 100644
--- a/bin/basemgr/basemgr_impl.cc
+++ b/bin/basemgr/basemgr_impl.cc
@@ -251,12 +251,13 @@
}
void BasemgrImpl::Shutdown() {
- // TODO(mesch): Some of these could be done in parallel too.
- // fuchsia::modular::UserProvider must go first, but the order after user
- // provider is for now rather arbitrary. We terminate base shell last so
- // that in tests testing::Teardown() is invoked at the latest possible time.
- // Right now it just demonstrates that AppTerminate() works as we like it
- // to.
+ // Prevent the shutdown sequence from running twice.
+ if (state_ == State::TERMINATING) {
+ return;
+ }
+
+ state_ = State::TERMINATING;
+
FXL_DLOG(INFO) << "fuchsia::modular::BaseShellContext::Shutdown()";
if (settings_.test) {
@@ -267,6 +268,12 @@
<< "======================== [" << settings_.test_name << "] Done";
}
+ // TODO(mesch): Some of these could be done in parallel too.
+ // fuchsia::modular::UserProvider must go first, but the order after user
+ // provider is for now rather arbitrary. We terminate base shell last so
+ // that in tests testing::Teardown() is invoked at the latest possible time.
+ // Right now it just demonstrates that AppTerminate() works as we like it
+ // to.
user_provider_impl_.Teardown(kUserProviderTimeout, [this] {
FXL_DLOG(INFO) << "- fuchsia::modular::UserProvider down";
StopAccountProvider()->Then([this] {
diff --git a/bin/basemgr/basemgr_impl.h b/bin/basemgr/basemgr_impl.h
index c1196af..2eb063a 100644
--- a/bin/basemgr/basemgr_impl.h
+++ b/bin/basemgr/basemgr_impl.h
@@ -155,6 +155,15 @@
std::vector<SessionShellSettings>::size_type active_session_shell_index_{};
+ enum class State {
+ // normal mode of operation
+ RUNNING,
+ // basemgr is shutting down.
+ TERMINATING
+ };
+
+ State state_ = State::RUNNING;
+
FXL_DISALLOW_COPY_AND_ASSIGN(BasemgrImpl);
};