drivers: fix attach sleep locking

attach/detach can be multiple invoked. Therefore lock/unlock deep sleep
only for the very first time it is invoked (when callbacks
are actually changed).
pull/4912/head
Martin Kojtal 2017-08-18 10:06:40 +01:00
parent e57f0bcd26
commit 5b33d2583d
3 changed files with 10 additions and 3 deletions

View File

@ -123,7 +123,10 @@ void CAN::attach(Callback<void()> func, IrqType type) {
_irq[(CanIrqType)type] = func;
can_irq_set(&_can, (CanIrqType)type, 1);
} else {
sleep_manager_unlock_deep_sleep();
// unlock deep sleep only the first time
if (_irq[(CanIrqType)type] != callback(donothing)) {
sleep_manager_unlock_deep_sleep();
}
_irq[(CanIrqType)type] = callback(donothing);
can_irq_set(&_can, (CanIrqType)type, 0);
}

View File

@ -129,11 +129,11 @@ void I2C::unlock() {
int I2C::transfer(int address, const char *tx_buffer, int tx_length, char *rx_buffer, int rx_length, const event_callback_t& callback, int event, bool repeated)
{
lock();
sleep_manager_lock_deep_sleep();
if (i2c_active(&_i2c)) {
unlock();
return -1; // transaction ongoing
}
sleep_manager_lock_deep_sleep();
aquire();
_callback = callback;

View File

@ -84,7 +84,10 @@ void SerialBase::attach(Callback<void()> func, IrqType type) {
_irq[type] = func;
serial_irq_set(&_serial, (SerialIrq)type, 1);
} else {
sleep_manager_unlock_deep_sleep();
// unlock deep sleep only the first time
if (_irq[type] != donothing) {
sleep_manager_unlock_deep_sleep();
}
_irq[type] = donothing;
serial_irq_set(&_serial, (SerialIrq)type, 0);
}
@ -248,6 +251,7 @@ void SerialBase::start_read(void *buffer, int buffer_size, char buffer_width, co
{
_rx_callback = callback;
_thunk_irq.callback(&SerialBase::interrupt_handler_asynch);
sleep_manager_lock_deep_sleep();
serial_rx_asynch(&_serial, buffer, buffer_size, buffer_width, _thunk_irq.entry(), event, char_match, _rx_usage);
}