fix [3237242] sensormanager sensor active count gets out of sync

whether a physical sensor needed to be active or not was managed by
a simpe reference counter; unfortunatelly nothing prevented it to
get out of sync if a sensor was disabled more than once.

sensorservice already maintainted a list of all the "clients"
connected to a physical sensor; we now use that list to determine if
a sensor should be enabled. This can never be "out-of-sync" since
this is the only data structure linking a sensor to a user of that
sensor.

also removed the isEnabled() method, which was never used and
implemented wrongly (since it didn't take into account that a sensor
could be disabled for a client but not of another).

Change-Id: I789affb877728ca957e99f7ba749def37c4db1c7
This commit is contained in:
Mathias Agopian
2010-11-29 17:26:51 -08:00
parent 186b68b744
commit b483d5cd13
10 changed files with 22 additions and 54 deletions

View File

@@ -29,7 +29,7 @@ namespace android {
GravitySensor::GravitySensor(sensor_t const* list, size_t count) GravitySensor::GravitySensor(sensor_t const* list, size_t count)
: mSensorDevice(SensorDevice::getInstance()), : mSensorDevice(SensorDevice::getInstance()),
mEnabled(false), mAccTime(0), mAccTime(0),
mLowPass(M_SQRT1_2, 1.5f), mLowPass(M_SQRT1_2, 1.5f),
mX(mLowPass), mY(mLowPass), mZ(mLowPass) mX(mLowPass), mY(mLowPass), mZ(mLowPass)
@@ -71,15 +71,9 @@ bool GravitySensor::process(sensors_event_t* outEvent,
} }
return false; return false;
} }
bool GravitySensor::isEnabled() const {
return mEnabled;
}
status_t GravitySensor::activate(void* ident, bool enabled) { status_t GravitySensor::activate(void* ident, bool enabled) {
status_t err = mSensorDevice.activate(this, mAccelerometer.getHandle(), enabled); status_t err = mSensorDevice.activate(this, mAccelerometer.getHandle(), enabled);
if (err == NO_ERROR) { if (err == NO_ERROR) {
mEnabled = enabled;
if (enabled) { if (enabled) {
mAccTime = 0; mAccTime = 0;
} }

View File

@@ -33,7 +33,6 @@ namespace android {
class GravitySensor : public SensorInterface { class GravitySensor : public SensorInterface {
SensorDevice& mSensorDevice; SensorDevice& mSensorDevice;
Sensor mAccelerometer; Sensor mAccelerometer;
bool mEnabled;
double mAccTime; double mAccTime;
SecondOrderLowPassFilter mLowPass; SecondOrderLowPassFilter mLowPass;
@@ -43,7 +42,6 @@ public:
GravitySensor(sensor_t const* list, size_t count); GravitySensor(sensor_t const* list, size_t count);
virtual bool process(sensors_event_t* outEvent, virtual bool process(sensors_event_t* outEvent,
const sensors_event_t& event); const sensors_event_t& event);
virtual bool isEnabled() const;
virtual status_t activate(void* ident, bool enabled); virtual status_t activate(void* ident, bool enabled);
virtual status_t setDelay(void* ident, int handle, int64_t ns); virtual status_t setDelay(void* ident, int handle, int64_t ns);
virtual Sensor getSensor() const; virtual Sensor getSensor() const;

View File

@@ -53,10 +53,6 @@ bool LinearAccelerationSensor::process(sensors_event_t* outEvent,
return result; return result;
} }
bool LinearAccelerationSensor::isEnabled() const {
return mGravitySensor.isEnabled();
}
status_t LinearAccelerationSensor::activate(void* ident, bool enabled) { status_t LinearAccelerationSensor::activate(void* ident, bool enabled) {
return mGravitySensor.activate(ident, enabled); return mGravitySensor.activate(ident, enabled);
} }

View File

@@ -40,7 +40,6 @@ class LinearAccelerationSensor : public SensorInterface {
const sensors_event_t& event); const sensors_event_t& event);
public: public:
LinearAccelerationSensor(sensor_t const* list, size_t count); LinearAccelerationSensor(sensor_t const* list, size_t count);
virtual bool isEnabled() const;
virtual status_t activate(void* ident, bool enabled); virtual status_t activate(void* ident, bool enabled);
virtual status_t setDelay(void* ident, int handle, int64_t ns); virtual status_t setDelay(void* ident, int handle, int64_t ns);
virtual Sensor getSensor() const; virtual Sensor getSensor() const;

View File

@@ -34,7 +34,6 @@ static inline T clamp(T v) {
RotationVectorSensor::RotationVectorSensor(sensor_t const* list, size_t count) RotationVectorSensor::RotationVectorSensor(sensor_t const* list, size_t count)
: mSensorDevice(SensorDevice::getInstance()), : mSensorDevice(SensorDevice::getInstance()),
mEnabled(false),
mALowPass(M_SQRT1_2, 5.0f), mALowPass(M_SQRT1_2, 5.0f),
mAX(mALowPass), mAY(mALowPass), mAZ(mALowPass), mAX(mALowPass), mAY(mALowPass), mAZ(mALowPass),
mMLowPass(M_SQRT1_2, 2.5f), mMLowPass(M_SQRT1_2, 2.5f),
@@ -133,19 +132,12 @@ bool RotationVectorSensor::process(sensors_event_t* outEvent,
return false; return false;
} }
bool RotationVectorSensor::isEnabled() const {
return mEnabled;
}
status_t RotationVectorSensor::activate(void* ident, bool enabled) { status_t RotationVectorSensor::activate(void* ident, bool enabled) {
if (mEnabled != enabled) { mSensorDevice.activate(this, mAcc.getHandle(), enabled);
mSensorDevice.activate(this, mAcc.getHandle(), enabled); mSensorDevice.activate(this, mMag.getHandle(), enabled);
mSensorDevice.activate(this, mMag.getHandle(), enabled); if (enabled) {
mEnabled = enabled; mMagTime = 0;
if (enabled) { mAccTime = 0;
mMagTime = 0;
mAccTime = 0;
}
} }
return NO_ERROR; return NO_ERROR;
} }

View File

@@ -34,7 +34,6 @@ class RotationVectorSensor : public SensorInterface {
SensorDevice& mSensorDevice; SensorDevice& mSensorDevice;
Sensor mAcc; Sensor mAcc;
Sensor mMag; Sensor mMag;
bool mEnabled;
float mMagData[3]; float mMagData[3];
double mAccTime; double mAccTime;
double mMagTime; double mMagTime;
@@ -47,7 +46,6 @@ public:
RotationVectorSensor(sensor_t const* list, size_t count); RotationVectorSensor(sensor_t const* list, size_t count);
virtual bool process(sensors_event_t* outEvent, virtual bool process(sensors_event_t* outEvent,
const sensors_event_t& event); const sensors_event_t& event);
virtual bool isEnabled() const;
virtual status_t activate(void* ident, bool enabled); virtual status_t activate(void* ident, bool enabled);
virtual status_t setDelay(void* ident, int handle, int64_t ns); virtual status_t setDelay(void* ident, int handle, int64_t ns);
virtual Sensor getSensor() const; virtual Sensor getSensor() const;

View File

@@ -137,9 +137,8 @@ void SensorDevice::dump(String8& result, char* buffer, size_t SIZE)
Mutex::Autolock _l(mLock); Mutex::Autolock _l(mLock);
for (size_t i=0 ; i<size_t(count) ; i++) { for (size_t i=0 ; i<size_t(count) ; i++) {
snprintf(buffer, SIZE, "handle=0x%08x, active-count=%d / %d\n", snprintf(buffer, SIZE, "handle=0x%08x, active-count=%d\n",
list[i].handle, list[i].handle,
mActivationCount.valueFor(list[i].handle).count,
mActivationCount.valueFor(list[i].handle).rates.size()); mActivationCount.valueFor(list[i].handle).rates.size());
result.append(buffer); result.append(buffer);
} }
@@ -167,22 +166,25 @@ status_t SensorDevice::activate(void* ident, int handle, int enabled)
bool actuateHardware = false; bool actuateHardware = false;
Info& info( mActivationCount.editValueFor(handle) ); Info& info( mActivationCount.editValueFor(handle) );
int32_t& count(info.count);
if (enabled) { if (enabled) {
if (android_atomic_inc(&count) == 0) {
actuateHardware = true;
}
Mutex::Autolock _l(mLock); Mutex::Autolock _l(mLock);
if (info.rates.indexOfKey(ident) < 0) { if (info.rates.indexOfKey(ident) < 0) {
info.rates.add(ident, DEFAULT_EVENTS_PERIOD); info.rates.add(ident, DEFAULT_EVENTS_PERIOD);
actuateHardware = true;
} else {
// sensor was already activated for this ident
} }
} else { } else {
if (android_atomic_dec(&count) == 1) {
actuateHardware = true;
}
Mutex::Autolock _l(mLock); Mutex::Autolock _l(mLock);
info.rates.removeItem(ident); if (info.rates.removeItem(ident) >= 0) {
if (info.rates.size() == 0) {
actuateHardware = true;
}
} else {
// sensor wasn't enabled for this ident
}
} }
if (actuateHardware) { if (actuateHardware) {
err = mSensorDevice->activate(mSensorDevice, handle, enabled); err = mSensorDevice->activate(mSensorDevice, handle, enabled);
if (enabled) { if (enabled) {

View File

@@ -40,8 +40,7 @@ class SensorDevice : public Singleton<SensorDevice> {
Mutex mLock; // protect mActivationCount[].rates Mutex mLock; // protect mActivationCount[].rates
// fixed-size array after construction // fixed-size array after construction
struct Info { struct Info {
Info() : count(0) { } Info() { }
int32_t count;
KeyedVector<void*, nsecs_t> rates; KeyedVector<void*, nsecs_t> rates;
}; };
DefaultKeyedVector<int, Info> mActivationCount; DefaultKeyedVector<int, Info> mActivationCount;

View File

@@ -32,7 +32,7 @@ SensorInterface::~SensorInterface()
HardwareSensor::HardwareSensor(const sensor_t& sensor) HardwareSensor::HardwareSensor(const sensor_t& sensor)
: mSensorDevice(SensorDevice::getInstance()), : mSensorDevice(SensorDevice::getInstance()),
mSensor(&sensor), mEnabled(false) mSensor(&sensor)
{ {
LOGI("%s", sensor.name); LOGI("%s", sensor.name);
} }
@@ -46,15 +46,8 @@ bool HardwareSensor::process(sensors_event_t* outEvent,
return true; return true;
} }
bool HardwareSensor::isEnabled() const { status_t HardwareSensor::activate(void* ident, bool enabled) {
return mEnabled; return mSensorDevice.activate(ident, mSensor.getHandle(), enabled);
}
status_t HardwareSensor::activate(void* ident,bool enabled) {
status_t err = mSensorDevice.activate(ident, mSensor.getHandle(), enabled);
if (err == NO_ERROR)
mEnabled = enabled;
return err;
} }
status_t HardwareSensor::setDelay(void* ident, int handle, int64_t ns) { status_t HardwareSensor::setDelay(void* ident, int handle, int64_t ns) {

View File

@@ -38,7 +38,6 @@ public:
virtual bool process(sensors_event_t* outEvent, virtual bool process(sensors_event_t* outEvent,
const sensors_event_t& event) = 0; const sensors_event_t& event) = 0;
virtual bool isEnabled() const = 0;
virtual status_t activate(void* ident, bool enabled) = 0; virtual status_t activate(void* ident, bool enabled) = 0;
virtual status_t setDelay(void* ident, int handle, int64_t ns) = 0; virtual status_t setDelay(void* ident, int handle, int64_t ns) = 0;
virtual Sensor getSensor() const = 0; virtual Sensor getSensor() const = 0;
@@ -51,7 +50,6 @@ class HardwareSensor : public SensorInterface
{ {
SensorDevice& mSensorDevice; SensorDevice& mSensorDevice;
Sensor mSensor; Sensor mSensor;
bool mEnabled;
public: public:
HardwareSensor(const sensor_t& sensor); HardwareSensor(const sensor_t& sensor);
@@ -61,7 +59,6 @@ public:
virtual bool process(sensors_event_t* outEvent, virtual bool process(sensors_event_t* outEvent,
const sensors_event_t& event); const sensors_event_t& event);
virtual bool isEnabled() const;
virtual status_t activate(void* ident, bool enabled); virtual status_t activate(void* ident, bool enabled);
virtual status_t setDelay(void* ident, int handle, int64_t ns); virtual status_t setDelay(void* ident, int handle, int64_t ns);
virtual Sensor getSensor() const; virtual Sensor getSensor() const;