MH2 | Add restart logic in HalProxy::initialize method.
Bug: 136511617
Test: None yet
Change-Id: I389a7243d3612586aae4e8a802afda92af8dcc6d
diff --git a/sensors/2.0/multihal/HalProxy.cpp b/sensors/2.0/multihal/HalProxy.cpp
index d667218..fe2b98b 100644
--- a/sensors/2.0/multihal/HalProxy.cpp
+++ b/sensors/2.0/multihal/HalProxy.cpp
@@ -65,15 +65,7 @@
}
HalProxy::~HalProxy() {
- mThreadsRun.store(false);
- mWakelockCV.notify_one();
- mEventQueueWriteCV.notify_one();
- if (mPendingWritesThread.joinable()) {
- mPendingWritesThread.join();
- }
- if (mWakelockThread.joinable()) {
- mWakelockThread.join();
- }
+ stopThreads();
}
Return<void> HalProxy::getSensorsList(getSensorsList_cb _hidl_cb) {
@@ -119,8 +111,18 @@
const sp<ISensorsCallback>& sensorsCallback) {
Result result = Result::OK;
- // TODO: clean up sensor requests, if not already done elsewhere through a death recipient, and
- // clean up any other resources that exist (FMQs, flags, threads, etc.)
+ stopThreads();
+ resetSharedWakelock();
+
+ // So that the pending write events queue can be cleared safely and when we start threads
+ // again we do not get new events until after initialize resets the subhals.
+ disableAllSensors();
+
+ // Clears the queue if any events were pending write before.
+ mPendingWriteEventsQueue = std::queue<std::pair<std::vector<Event>, size_t>>();
+
+ // Clears previously connected dynamic sensors
+ mDynamicSensors.clear();
mDynamicSensorsCallback = sensorsCallback;
@@ -128,21 +130,29 @@
mEventQueue =
std::make_unique<EventMessageQueue>(eventQueueDescriptor, true /* resetPointers */);
- // Create the EventFlag that is used to signal to the framework that sensor events have been
- // written to the Event FMQ
- if (EventFlag::createEventFlag(mEventQueue->getEventFlagWord(), &mEventQueueFlag) != OK) {
- result = Result::BAD_VALUE;
- }
-
// Create the Wake Lock FMQ that is used by the framework to communicate whenever WAKE_UP
// events have been successfully read and handled by the framework.
mWakeLockQueue =
std::make_unique<WakeLockMessageQueue>(wakeLockDescriptor, true /* resetPointers */);
+ if (mEventQueueFlag != nullptr) {
+ EventFlag::deleteEventFlag(&mEventQueueFlag);
+ }
+ if (mWakelockQueueFlag != nullptr) {
+ EventFlag::deleteEventFlag(&mWakelockQueueFlag);
+ }
+ if (EventFlag::createEventFlag(mEventQueue->getEventFlagWord(), &mEventQueueFlag) != OK) {
+ result = Result::BAD_VALUE;
+ }
+ if (EventFlag::createEventFlag(mWakeLockQueue->getEventFlagWord(), &mWakelockQueueFlag) != OK) {
+ result = Result::BAD_VALUE;
+ }
if (!mDynamicSensorsCallback || !mEventQueue || !mWakeLockQueue || mEventQueueFlag == nullptr) {
result = Result::BAD_VALUE;
}
+ mThreadsRun.store(true);
+
mPendingWritesThread = std::thread(startPendingWritesThread, this);
mWakelockThread = std::thread(startWakelockThread, this);
@@ -157,6 +167,8 @@
}
}
+ mCurrentOperationMode = OperationMode::NORMAL;
+
return result;
}
@@ -331,6 +343,41 @@
initializeSensorList();
}
+void HalProxy::stopThreads() {
+ mThreadsRun.store(false);
+ if (mEventQueueFlag != nullptr && mEventQueue != nullptr) {
+ size_t numToRead = mEventQueue->availableToRead();
+ std::vector<Event> events(numToRead);
+ mEventQueue->read(events.data(), numToRead);
+ mEventQueueFlag->wake(static_cast<uint32_t>(EventQueueFlagBits::EVENTS_READ));
+ }
+ if (mWakelockQueueFlag != nullptr && mWakeLockQueue != nullptr) {
+ uint32_t kZero = 0;
+ mWakeLockQueue->write(&kZero);
+ mWakelockQueueFlag->wake(static_cast<uint32_t>(WakeLockQueueFlagBits::DATA_WRITTEN));
+ }
+ mWakelockCV.notify_one();
+ mEventQueueWriteCV.notify_one();
+ if (mPendingWritesThread.joinable()) {
+ mPendingWritesThread.join();
+ }
+ if (mWakelockThread.joinable()) {
+ mWakelockThread.join();
+ }
+}
+
+void HalProxy::disableAllSensors() {
+ for (const auto& sensorEntry : mSensors) {
+ int32_t sensorHandle = sensorEntry.first;
+ activate(sensorHandle, false /* enabled */);
+ }
+ std::lock_guard<std::mutex> dynamicSensorsLock(mDynamicSensorsMutex);
+ for (const auto& sensorEntry : mDynamicSensors) {
+ int32_t sensorHandle = sensorEntry.first;
+ activate(sensorHandle, false /* enabled */);
+ }
+}
+
void HalProxy::startPendingWritesThread(HalProxy* halProxy) {
halProxy->handlePendingWrites();
}
@@ -347,8 +394,6 @@
size_t eventQueueSize = mEventQueue->getQuantumCount();
size_t numToWrite = std::min(pendingWriteEvents.size(), eventQueueSize);
lock.unlock();
- // TODO: Find a way to interrup writeBlocking if the thread should exit
- // so we don't have to wait for timeout on framework restarts.
if (!mEventQueue->writeBlocking(
pendingWriteEvents.data(), numToWrite,
static_cast<uint32_t>(EventQueueFlagBits::EVENTS_READ),