@@ -167,7 +167,7 @@ typedef int16_t device_handle_t;
167
167
#define DEVICE_DEFINE (dev_id , name , init_fn , pm , data , config , level , prio , \
168
168
api ) \
169
169
Z_DEVICE_STATE_DEFINE(dev_id); \
170
- Z_DEVICE_DEFINE(DT_INVALID_NODE, dev_id, name, init_fn, pm, data, \
170
+ Z_DEVICE_DEFINE(DT_INVALID_NODE, dev_id, name, init_fn, 0U, pm, data, \
171
171
config, level, prio, api, \
172
172
&Z_DEVICE_STATE_NAME(dev_id))
173
173
@@ -230,8 +230,9 @@ typedef int16_t device_handle_t;
230
230
...) \
231
231
Z_DEVICE_STATE_DEFINE(Z_DEVICE_DT_DEV_ID(node_id)); \
232
232
Z_DEVICE_DEFINE(node_id, Z_DEVICE_DT_DEV_ID(node_id), \
233
- DEVICE_DT_NAME(node_id), init_fn, pm, data, config, \
234
- level, prio, api, \
233
+ DEVICE_DT_NAME(node_id), init_fn, \
234
+ Z_DEVICE_DT_FLAGS(node_id), pm, data, config, level, \
235
+ prio, api, \
235
236
&Z_DEVICE_STATE_NAME(Z_DEVICE_DT_DEV_ID(node_id)), \
236
237
__VA_ARGS__)
237
238
@@ -447,6 +448,19 @@ struct device_dt_metadata;
447
448
#define Z_DEVICE_DEPS_CONST const
448
449
#endif
449
450
451
+ /** Device flags */
452
+ typedef uint8_t device_flags_t ;
453
+
454
+ /**
455
+ * @name Device flags
456
+ * @{
457
+ */
458
+
459
+ /** Device initialization is deferred */
460
+ #define DEVICE_FLAG_INIT_DEFERRED BIT(0)
461
+
462
+ /** @} */
463
+
450
464
/**
451
465
* @brief Runtime device structure (in ROM) per driver instance
452
466
*/
@@ -463,6 +477,8 @@ struct device {
463
477
void * data ;
464
478
/** Initialization function (optional) */
465
479
int (* init_fn )(const struct device * );
480
+ /** Device flags */
481
+ device_flags_t flags ;
466
482
#if defined(CONFIG_DEVICE_DEPS ) || defined(__DOXYGEN__ )
467
483
/**
468
484
* Optional pointer to dependencies associated with the device.
@@ -843,6 +859,14 @@ __syscall int device_init(const struct device *dev);
843
859
static Z_DECL_ALIGN(struct device_state) Z_DEVICE_STATE_NAME(dev_id) \
844
860
__attribute__((__section__(".z_devstate")))
845
861
862
+ /**
863
+ * @brief Device flags obtained from DT.
864
+ *
865
+ * @param node_id Devicetree node identifier.
866
+ */
867
+ #define Z_DEVICE_DT_FLAGS (node_id ) \
868
+ (DT_PROP(node_id, zephyr_deferred_init) * DEVICE_FLAG_INIT_DEFERRED)
869
+
846
870
#if defined(CONFIG_DEVICE_DEPS ) || defined(__DOXYGEN__ )
847
871
848
872
/**
@@ -1058,6 +1082,7 @@ device_get_dt_nodelabels(const struct device *dev)
1058
1082
*
1059
1083
* @param name_ Name of the device.
1060
1084
* @param init_fn_ Init function (optional).
1085
+ * @param flags_ Device flags.
1061
1086
* @param pm_ Reference to @ref pm_device_base (optional).
1062
1087
* @param data_ Reference to device data.
1063
1088
* @param config_ Reference to device config.
@@ -1067,15 +1092,16 @@ device_get_dt_nodelabels(const struct device *dev)
1067
1092
* @param node_id_ Devicetree node identifier
1068
1093
* @param dev_id_ Device identifier token, as passed to Z_DEVICE_BASE_DEFINE
1069
1094
*/
1070
- #define Z_DEVICE_INIT (name_ , init_fn_ , pm_ , data_ , config_ , api_ , state_ , deps_ , \
1071
- node_id_ , dev_id_ ) \
1095
+ #define Z_DEVICE_INIT (name_ , init_fn_ , flags_ , pm_ , data_ , config_ , api_ , state_ , \
1096
+ deps_ , node_id_ , dev_id_ ) \
1072
1097
{ \
1073
1098
.name = name_, \
1074
1099
.config = (config_), \
1075
1100
.api = (api_), \
1076
1101
.state = (state_), \
1077
1102
.data = (data_), \
1078
1103
.init_fn = (init_fn_), \
1104
+ .flags = (flags_), \
1079
1105
IF_ENABLED(CONFIG_DEVICE_DEPS, (.deps = (deps_),)) /**/ \
1080
1106
IF_ENABLED (CONFIG_PM_DEVICE , Z_DEVICE_INIT_PM_BASE (pm_ )) /**/ \
1081
1107
IF_ENABLED (CONFIG_DEVICE_DT_METADATA , \
@@ -1112,6 +1138,7 @@ device_get_dt_nodelabels(const struct device *dev)
1112
1138
* @param dev_id Device identifier (used to name the defined @ref device).
1113
1139
* @param name Name of the device.
1114
1140
* @param init_fn Init function.
1141
+ * @param flags Device flags.
1115
1142
* @param pm Reference to @ref pm_device_base associated with the device.
1116
1143
* (optional).
1117
1144
* @param data Reference to device data.
@@ -1121,14 +1148,15 @@ device_get_dt_nodelabels(const struct device *dev)
1121
1148
* @param api Reference to device API.
1122
1149
* @param ... Optional dependencies, manually specified.
1123
1150
*/
1124
- #define Z_DEVICE_BASE_DEFINE (node_id , dev_id , name , init_fn , pm , data , config , level , prio , api , \
1125
- state , deps ) \
1151
+ #define Z_DEVICE_BASE_DEFINE (node_id , dev_id , name , init_fn , flags , pm , data , config , level , prio , \
1152
+ api , state , deps ) \
1126
1153
COND_CODE_1(DT_NODE_EXISTS(node_id), (), (static)) \
1127
1154
COND_CODE_1(Z_DEVICE_IS_MUTABLE(node_id), (), (const)) \
1128
1155
STRUCT_SECTION_ITERABLE_NAMED_ALTERNATE( \
1129
1156
device, COND_CODE_1(Z_DEVICE_IS_MUTABLE(node_id), (device_mutable), (device)), \
1130
1157
Z_DEVICE_SECTION_NAME(level, prio), DEVICE_NAME_GET(dev_id)) = \
1131
- Z_DEVICE_INIT(name, init_fn, pm, data, config, api, state, deps, node_id, dev_id)
1158
+ Z_DEVICE_INIT(name, init_fn, flags, pm, data, config, api, state, deps, node_id, \
1159
+ dev_id)
1132
1160
1133
1161
/**
1134
1162
* @brief Issue an error if the given init level is not supported.
@@ -1159,13 +1187,6 @@ device_get_dt_nodelabels(const struct device *dev)
1159
1187
.dev = (const struct device *)&DEVICE_NAME_GET(dev_id) \
1160
1188
}
1161
1189
1162
- #define Z_DEFER_DEVICE_INIT_ENTRY_DEFINE (node_id , dev_id ) \
1163
- static const Z_DECL_ALIGN(struct init_entry) __used __noasan \
1164
- __attribute__((__section__(".z_deferred_init"))) \
1165
- Z_INIT_ENTRY_NAME(DEVICE_NAME_GET(dev_id)) = { \
1166
- .dev = (const struct device *)&DEVICE_NAME_GET(dev_id) \
1167
- }
1168
-
1169
1190
/**
1170
1191
* @brief Define a @ref device and all other required objects.
1171
1192
*
@@ -1177,6 +1198,7 @@ device_get_dt_nodelabels(const struct device *dev)
1177
1198
* @param dev_id Device identifier (used to name the defined @ref device).
1178
1199
* @param name Name of the device.
1179
1200
* @param init_fn Device init function.
1201
+ * @param flags Device flags.
1180
1202
* @param pm Reference to @ref pm_device_base associated with the device.
1181
1203
* (optional).
1182
1204
* @param data Reference to device data.
@@ -1187,7 +1209,7 @@ device_get_dt_nodelabels(const struct device *dev)
1187
1209
* @param state Reference to device state.
1188
1210
* @param ... Optional dependencies, manually specified.
1189
1211
*/
1190
- #define Z_DEVICE_DEFINE (node_id , dev_id , name , init_fn , pm , data , config , \
1212
+ #define Z_DEVICE_DEFINE (node_id , dev_id , name , init_fn , flags , pm , data , config ,\
1191
1213
level , prio , api , state , ...) \
1192
1214
Z_DEVICE_NAME_CHECK(name); \
1193
1215
\
@@ -1198,11 +1220,12 @@ device_get_dt_nodelabels(const struct device *dev)
1198
1220
(IF_ENABLED(DT_NODE_EXISTS(node_id), \
1199
1221
(Z_DEVICE_DT_METADATA_DEFINE(node_id, dev_id);))))\
1200
1222
\
1201
- Z_DEVICE_BASE_DEFINE(node_id, dev_id, name, init_fn, pm, data, config, \
1202
- level, prio, api, state, Z_DEVICE_DEPS_NAME(dev_id)); \
1203
- COND_CODE_1(DEVICE_DT_DEFER(node_id), \
1204
- (Z_DEFER_DEVICE_INIT_ENTRY_DEFINE(node_id, dev_id)), \
1205
- (Z_DEVICE_INIT_ENTRY_DEFINE(node_id, dev_id, level, prio)));\
1223
+ Z_DEVICE_BASE_DEFINE(node_id, dev_id, name, init_fn, flags, pm, data, \
1224
+ config, level, prio, api, state, \
1225
+ Z_DEVICE_DEPS_NAME(dev_id)); \
1226
+ \
1227
+ Z_DEVICE_INIT_ENTRY_DEFINE(node_id, dev_id, level, prio); \
1228
+ \
1206
1229
IF_ENABLED(CONFIG_LLEXT_EXPORT_DEVICES, \
1207
1230
(IF_ENABLED(DT_NODE_EXISTS(node_id), \
1208
1231
(Z_DEVICE_EXPORT(node_id);))))
0 commit comments