Common core of every hardware device: controllers, buses and the peripherals on them.
More...
Common core of every hardware device: controllers, buses and the peripherals on them.
A device class embeds struct pbl_device, a driver embeds the class struct, and container_of() walks back out. Devices are const and live in flash; the only RAM is the state they point to.
Instances are defined with the PBL_<DRIVER>_DEFINE() macro of their driver, built from PBL_DEVICE_STATE_DEFINE(), PBL_DEVICE_INIT() and PBL_DEVICE_REGISTER(). pbl_device_init_all() brings every registered device up, dependencies first: a device's parent and deps are initialized before it, and a driver's init calls pbl_device_init() on the devices it uses.
An init returning -ENODEV means the device is not present: that is not logged as an error.
struct foo {
uint8_t addr;
};
static int prv_foo_init(
const struct pbl_device *dev) {
const struct foo *foo =
container_of(dev,
const struct foo, dev);
return prv_probe(foo->addr) ? 0 : -ENODEV;
}
static const struct foo s_foo = {
.addr = 0x18,
};
#define PBL_DEVICE_STATE_DEFINE(sym)
Define the runtime state of device instance sym.
Definition device.h:89
#define PBL_DEVICE_INIT(sym, _name, _init, _parent, _deps)
Initializer for the struct pbl_device of device instance sym.
Definition device.h:100
#define PBL_DEVICE_REGISTER(sym, dev)
Add a device to the table pbl_device_init_all() walks.
Definition device.h:121
#define PBL_DEVICE_DEPS(...)
Static dependency list for struct pbl_device::deps.
Definition device.h:82
#define container_of(ptr, type, member)
Get the structure that contains a member.
Definition misc.h:44
A hardware device.
Definition device.h:68
◆ pbl_device_state
Runtime state of a device.
| Data Fields |
|
int |
res |
Result of the initialization. |
|
uint8_t |
status |
One of pbl_device_status. |
◆ PBL_DEVICE_DEPS
| #define PBL_DEVICE_DEPS |
( |
|
... | ) |
((const struct pbl_device *const[]){__VA_ARGS__, nullptr}) |
◆ PBL_DEVICE_INIT
| #define PBL_DEVICE_INIT |
( |
|
sym, |
|
|
|
_name, |
|
|
|
_init, |
|
|
|
_parent, |
|
|
|
_deps |
|
) |
| |
Value: { \
.name = (_name), \
.init = (_init), \
.parent = (_parent), \
.deps = (_deps), \
.state = &sym##_device_state, \
}
Initializer for the struct pbl_device of device instance sym.
- Parameters
-
◆ PBL_DEVICE_REGISTER
◆ PBL_DEVICE_STATE_DEFINE
| #define PBL_DEVICE_STATE_DEFINE |
( |
|
sym | ) |
static struct pbl_device_state sym##_device_state |
Define the runtime state of device instance sym.
- Parameters
-
| sym | Symbol of the device instance. |
◆ PBL_DEVICE_TABLE_SECTION
| #define PBL_DEVICE_TABLE_SECTION PBL_SECTION(".pbl_devices") |
◆ pbl_device_status
Device status.
| Enumerator |
|---|
| PBL_DEVICE_UNINIT | Not initialized yet.
|
| PBL_DEVICE_INITIALIZING | Initialization in progress.
|
| PBL_DEVICE_READY | Initialized.
|
| PBL_DEVICE_FAILED | Initialization failed, or the device is not present.
|
◆ pbl_device_init()
| int pbl_device_init |
( |
const struct pbl_device * |
dev | ) |
|
Initialize a device, its parent and deps first.
A no-op once the device is ready or has failed. A dependency cycle asserts.
- Parameters
-
- Returns
- 0, the error its init returned, or
-ENODEV if its parent or a dep failed.
◆ pbl_device_init_all()
| int pbl_device_init_all |
( |
void |
| ) |
|
Initialize every registered device.
- Returns
- Number of devices that failed or are not present.
◆ pbl_device_init_children()
| int pbl_device_init_children |
( |
const struct pbl_device * |
parent | ) |
|
Initialize every registered device whose parent is parent.
For a multi-function device to bring its functions up from its own init.
- Parameters
-
- Returns
- Number of devices that failed or are not present.
◆ pbl_device_is_ready()
| bool pbl_device_is_ready |
( |
const struct pbl_device * |
dev | ) |
|
Check whether a device is initialized.
- Parameters
-
- Returns
- True if the device is ready.