Loading sensors/2.0/default/Sensor.cpp +73 −10 Original line number Diff line number Diff line Loading @@ -16,31 +16,94 @@ #include "Sensor.h" #include <utils/SystemClock.h> namespace android { namespace hardware { namespace sensors { namespace V2_0 { namespace implementation { Sensor::Sensor() : mIsEnabled(false), mSamplingPeriodNs(0) {} using ::android::hardware::sensors::V1_0::SensorStatus; Sensor::Sensor(ISensorsEventCallback* callback) : mIsEnabled(false), mSamplingPeriodNs(0), mLastSampleTimeNs(0), mCallback(callback) { mRunThread = std::thread(startThread, this); } Sensor::~Sensor() { mStopThread = true; mIsEnabled = false; mWaitCV.notify_all(); mRunThread.join(); } const SensorInfo& Sensor::getSensorInfo() const { return mSensorInfo; } bool Sensor::batch(int32_t samplingPeriodNs) { bool success = true; if (samplingPeriodNs >= mSensorInfo.minDelay * 1000 && samplingPeriodNs <= mSensorInfo.maxDelay * 1000) { void Sensor::batch(int32_t samplingPeriodNs) { if (samplingPeriodNs < mSensorInfo.minDelay * 1000) { samplingPeriodNs = mSensorInfo.minDelay * 1000; } else if (samplingPeriodNs > mSensorInfo.maxDelay * 1000) { samplingPeriodNs = mSensorInfo.maxDelay * 1000; } if (mSamplingPeriodNs != samplingPeriodNs) { mSamplingPeriodNs = samplingPeriodNs; } else { success = false; // Wake up the 'run' thread to check if a new event should be generated now mWaitCV.notify_all(); } return success; } void Sensor::activate(bool enable) { if (mIsEnabled != enable) { mIsEnabled = enable; mWaitCV.notify_all(); } } void Sensor::startThread(Sensor* sensor) { sensor->run(); } void Sensor::run() { std::mutex runMutex; std::unique_lock<std::mutex> runLock(runMutex); constexpr int64_t kNanosecondsInSeconds = 1000 * 1000 * 1000; while (!mStopThread) { if (!mIsEnabled) { mWaitCV.wait(runLock, [&] { return mIsEnabled || mStopThread; }); } else { timespec curTime; clock_gettime(CLOCK_REALTIME, &curTime); int64_t now = (curTime.tv_sec * kNanosecondsInSeconds) + curTime.tv_nsec; int64_t nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; if (now >= nextSampleTime) { mLastSampleTimeNs = now; nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; mCallback->postEvents(readEvents()); } mWaitCV.wait_for(runLock, std::chrono::nanoseconds(nextSampleTime - now)); } } } std::vector<Event> Sensor::readEvents() { std::vector<Event> events; Event event; event.sensorHandle = mSensorInfo.sensorHandle; event.sensorType = mSensorInfo.type; event.timestamp = ::android::elapsedRealtimeNano(); event.u.vec3.x = 1; event.u.vec3.y = 2; event.u.vec3.z = 3; event.u.vec3.status = SensorStatus::ACCURACY_HIGH; events.push_back(event); return events; } } // namespace implementation Loading sensors/2.0/default/Sensor.h +28 −3 Original line number Diff line number Diff line Loading @@ -19,7 +19,14 @@ #include <android/hardware/sensors/1.0/types.h> #include <condition_variable> #include <memory> #include <thread> #include <vector> using ::android::hardware::sensors::V1_0::Event; using ::android::hardware::sensors::V1_0::SensorInfo; using ::android::hardware::sensors::V1_0::SensorType; namespace android { namespace hardware { Loading @@ -27,18 +34,36 @@ namespace sensors { namespace V2_0 { namespace implementation { class ISensorsEventCallback { public: virtual ~ISensorsEventCallback(){}; virtual void postEvents(const std::vector<Event>& events) = 0; }; class Sensor { public: Sensor(); Sensor(ISensorsEventCallback* callback); virtual ~Sensor(); const SensorInfo& getSensorInfo() const; bool batch(int32_t samplingPeriodNs); void batch(int32_t samplingPeriodNs); void activate(bool enable); protected: void run(); virtual std::vector<Event> readEvents(); static void startThread(Sensor* sensor); bool mIsEnabled; int64_t mSamplingPeriodNs; int64_t mLastSampleTimeNs; SensorInfo mSensorInfo; std::atomic_bool mStopThread; std::condition_variable mWaitCV; std::thread mRunThread; ISensorsEventCallback* mCallback; }; } // namespace implementation Loading sensors/2.0/default/Sensors.cpp +15 −4 Original line number Diff line number Diff line Loading @@ -100,12 +100,12 @@ Return<Result> Sensors::initialize( Return<Result> Sensors::batch(int32_t sensorHandle, int64_t samplingPeriodNs, int64_t /* maxReportLatencyNs */) { Result result = Result::BAD_VALUE; auto sensor = mSensors.find(sensorHandle); if (sensor != mSensors.end() && sensor->second->batch(samplingPeriodNs)) { result = Result::OK; if (sensor != mSensors.end()) { sensor->second->batch(samplingPeriodNs); return Result::OK; } return result; return Result::BAD_VALUE; } Return<Result> Sensors::flush(int32_t /* sensorHandle */) { Loading Loading @@ -134,6 +134,17 @@ Return<void> Sensors::configDirectReport(int32_t /* sensorHandle */, int32_t /* return Return<void>(); } void Sensors::postEvents(const std::vector<Event>& events) { std::lock_guard<std::mutex> l(mLock); // TODO: read events from the Wake Lock FMQ in the right place std::vector<uint32_t> tmp(mWakeLockQueue->availableToRead()); mWakeLockQueue->read(tmp.data(), mWakeLockQueue->availableToRead()); mEventQueue->write(events.data(), events.size()); mEventQueueFlag->wake(static_cast<uint32_t>(EventQueueFlagBits::READ_AND_PROCESS)); } void Sensors::deleteEventFlag() { status_t status = EventFlag::deleteEventFlag(&mEventQueueFlag); if (status != OK) { Loading sensors/2.0/default/Sensors.h +8 −1 Original line number Diff line number Diff line Loading @@ -43,7 +43,7 @@ using ::android::hardware::MQDescriptor; using ::android::hardware::Return; using ::android::hardware::Void; struct Sensors : public ISensors { struct Sensors : public ISensors, public ISensorsEventCallback { using Event = ::android::hardware::sensors::V1_0::Event; using OperationMode = ::android::hardware::sensors::V1_0::OperationMode; using RateLevel = ::android::hardware::sensors::V1_0::RateLevel; Loading Loading @@ -80,6 +80,8 @@ struct Sensors : public ISensors { Return<void> configDirectReport(int32_t sensorHandle, int32_t channelHandle, RateLevel rate, configDirectReport_cb _hidl_cb) override; void postEvents(const std::vector<Event>& events) override; private: /** * Utility function to delete the Event Flag Loading Loading @@ -113,6 +115,11 @@ struct Sensors : public ISensors { * A map of the available sensors */ std::map<int32_t, std::shared_ptr<Sensor>> mSensors; /** * Lock to protect writes and reads to the FMQs */ std::mutex mLock; }; } // namespace implementation Loading Loading
sensors/2.0/default/Sensor.cpp +73 −10 Original line number Diff line number Diff line Loading @@ -16,31 +16,94 @@ #include "Sensor.h" #include <utils/SystemClock.h> namespace android { namespace hardware { namespace sensors { namespace V2_0 { namespace implementation { Sensor::Sensor() : mIsEnabled(false), mSamplingPeriodNs(0) {} using ::android::hardware::sensors::V1_0::SensorStatus; Sensor::Sensor(ISensorsEventCallback* callback) : mIsEnabled(false), mSamplingPeriodNs(0), mLastSampleTimeNs(0), mCallback(callback) { mRunThread = std::thread(startThread, this); } Sensor::~Sensor() { mStopThread = true; mIsEnabled = false; mWaitCV.notify_all(); mRunThread.join(); } const SensorInfo& Sensor::getSensorInfo() const { return mSensorInfo; } bool Sensor::batch(int32_t samplingPeriodNs) { bool success = true; if (samplingPeriodNs >= mSensorInfo.minDelay * 1000 && samplingPeriodNs <= mSensorInfo.maxDelay * 1000) { void Sensor::batch(int32_t samplingPeriodNs) { if (samplingPeriodNs < mSensorInfo.minDelay * 1000) { samplingPeriodNs = mSensorInfo.minDelay * 1000; } else if (samplingPeriodNs > mSensorInfo.maxDelay * 1000) { samplingPeriodNs = mSensorInfo.maxDelay * 1000; } if (mSamplingPeriodNs != samplingPeriodNs) { mSamplingPeriodNs = samplingPeriodNs; } else { success = false; // Wake up the 'run' thread to check if a new event should be generated now mWaitCV.notify_all(); } return success; } void Sensor::activate(bool enable) { if (mIsEnabled != enable) { mIsEnabled = enable; mWaitCV.notify_all(); } } void Sensor::startThread(Sensor* sensor) { sensor->run(); } void Sensor::run() { std::mutex runMutex; std::unique_lock<std::mutex> runLock(runMutex); constexpr int64_t kNanosecondsInSeconds = 1000 * 1000 * 1000; while (!mStopThread) { if (!mIsEnabled) { mWaitCV.wait(runLock, [&] { return mIsEnabled || mStopThread; }); } else { timespec curTime; clock_gettime(CLOCK_REALTIME, &curTime); int64_t now = (curTime.tv_sec * kNanosecondsInSeconds) + curTime.tv_nsec; int64_t nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; if (now >= nextSampleTime) { mLastSampleTimeNs = now; nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; mCallback->postEvents(readEvents()); } mWaitCV.wait_for(runLock, std::chrono::nanoseconds(nextSampleTime - now)); } } } std::vector<Event> Sensor::readEvents() { std::vector<Event> events; Event event; event.sensorHandle = mSensorInfo.sensorHandle; event.sensorType = mSensorInfo.type; event.timestamp = ::android::elapsedRealtimeNano(); event.u.vec3.x = 1; event.u.vec3.y = 2; event.u.vec3.z = 3; event.u.vec3.status = SensorStatus::ACCURACY_HIGH; events.push_back(event); return events; } } // namespace implementation Loading
sensors/2.0/default/Sensor.h +28 −3 Original line number Diff line number Diff line Loading @@ -19,7 +19,14 @@ #include <android/hardware/sensors/1.0/types.h> #include <condition_variable> #include <memory> #include <thread> #include <vector> using ::android::hardware::sensors::V1_0::Event; using ::android::hardware::sensors::V1_0::SensorInfo; using ::android::hardware::sensors::V1_0::SensorType; namespace android { namespace hardware { Loading @@ -27,18 +34,36 @@ namespace sensors { namespace V2_0 { namespace implementation { class ISensorsEventCallback { public: virtual ~ISensorsEventCallback(){}; virtual void postEvents(const std::vector<Event>& events) = 0; }; class Sensor { public: Sensor(); Sensor(ISensorsEventCallback* callback); virtual ~Sensor(); const SensorInfo& getSensorInfo() const; bool batch(int32_t samplingPeriodNs); void batch(int32_t samplingPeriodNs); void activate(bool enable); protected: void run(); virtual std::vector<Event> readEvents(); static void startThread(Sensor* sensor); bool mIsEnabled; int64_t mSamplingPeriodNs; int64_t mLastSampleTimeNs; SensorInfo mSensorInfo; std::atomic_bool mStopThread; std::condition_variable mWaitCV; std::thread mRunThread; ISensorsEventCallback* mCallback; }; } // namespace implementation Loading
sensors/2.0/default/Sensors.cpp +15 −4 Original line number Diff line number Diff line Loading @@ -100,12 +100,12 @@ Return<Result> Sensors::initialize( Return<Result> Sensors::batch(int32_t sensorHandle, int64_t samplingPeriodNs, int64_t /* maxReportLatencyNs */) { Result result = Result::BAD_VALUE; auto sensor = mSensors.find(sensorHandle); if (sensor != mSensors.end() && sensor->second->batch(samplingPeriodNs)) { result = Result::OK; if (sensor != mSensors.end()) { sensor->second->batch(samplingPeriodNs); return Result::OK; } return result; return Result::BAD_VALUE; } Return<Result> Sensors::flush(int32_t /* sensorHandle */) { Loading Loading @@ -134,6 +134,17 @@ Return<void> Sensors::configDirectReport(int32_t /* sensorHandle */, int32_t /* return Return<void>(); } void Sensors::postEvents(const std::vector<Event>& events) { std::lock_guard<std::mutex> l(mLock); // TODO: read events from the Wake Lock FMQ in the right place std::vector<uint32_t> tmp(mWakeLockQueue->availableToRead()); mWakeLockQueue->read(tmp.data(), mWakeLockQueue->availableToRead()); mEventQueue->write(events.data(), events.size()); mEventQueueFlag->wake(static_cast<uint32_t>(EventQueueFlagBits::READ_AND_PROCESS)); } void Sensors::deleteEventFlag() { status_t status = EventFlag::deleteEventFlag(&mEventQueueFlag); if (status != OK) { Loading
sensors/2.0/default/Sensors.h +8 −1 Original line number Diff line number Diff line Loading @@ -43,7 +43,7 @@ using ::android::hardware::MQDescriptor; using ::android::hardware::Return; using ::android::hardware::Void; struct Sensors : public ISensors { struct Sensors : public ISensors, public ISensorsEventCallback { using Event = ::android::hardware::sensors::V1_0::Event; using OperationMode = ::android::hardware::sensors::V1_0::OperationMode; using RateLevel = ::android::hardware::sensors::V1_0::RateLevel; Loading Loading @@ -80,6 +80,8 @@ struct Sensors : public ISensors { Return<void> configDirectReport(int32_t sensorHandle, int32_t channelHandle, RateLevel rate, configDirectReport_cb _hidl_cb) override; void postEvents(const std::vector<Event>& events) override; private: /** * Utility function to delete the Event Flag Loading Loading @@ -113,6 +115,11 @@ struct Sensors : public ISensors { * A map of the available sensors */ std::map<int32_t, std::shared_ptr<Sensor>> mSensors; /** * Lock to protect writes and reads to the FMQs */ std::mutex mLock; }; } // namespace implementation Loading