kernel: device: invert sense of ready bit

The device status ready bit replaced the previous hack of clearing the
device API pointer when initialization of the device failed.  It
inadvertently changed the behavior of device_get_binding() when
invoked before the device was initialized: previously that succeeded
for uninitialized devices, after the change it failed.

Multiple driver initializations rely on being able to get a device
pointer for something they're going to depend on in their init
function, even if that device has not yet been initialized.  Although
this is wrong, and would cause faults if the device failed to
initialize before use, in practice it has been working.

It's not feasible to identify all the situations where this has
occurred, nor to add code to diagnose such cases without changing the
state associated with a device to distinguish initialized from
initialization success/failure.  Restore the previous behavior until a
more holistic solution is developed.

Signed-off-by: Peter Bigot <peter.bigot@nordicsemi.no>
This commit is contained in:
Peter Bigot 2020-09-14 10:51:44 -05:00 committed by Carles Cufí
commit 1a7cd6ddbd

View file

@ -64,9 +64,9 @@ void z_sys_init_run_level(int32_t level)
z_object_init(dev);
}
if ((entry->init(dev) == 0) && (dev != NULL)) {
/* Initialization was successful.
* Set the init status bit so device is declared ready.
if ((entry->init(dev) != 0) && (dev != NULL)) {
/* Initialization failed.
* Set the init status bit so device is not declared ready.
*/
sys_bitfield_set_bit(
(mem_addr_t) __device_init_status_start,
@ -122,7 +122,8 @@ size_t z_device_get_all_static(struct device const **devices)
bool z_device_ready(const struct device *dev)
{
return !!(sys_bitfield_test_bit((mem_addr_t)__device_init_status_start,
/* Set bit indicates device failed initialization */
return !(sys_bitfield_test_bit((mem_addr_t)__device_init_status_start,
(dev - __device_start)));
}