diff --git a/cmake/dts.cmake b/cmake/dts.cmake index b182eeabf09..18d7ef4a27a 100644 --- a/cmake/dts.cmake +++ b/cmake/dts.cmake @@ -21,6 +21,7 @@ set(ZEPHYR_DTS ${PROJECT_BINARY_DIR}/zephyr.dts) # and should not be made part of the documentation. set(EDT_PICKLE ${PROJECT_BINARY_DIR}/edt.pickle) set(DEVICETREE_UNFIXED_H ${PROJECT_BINARY_DIR}/include/generated/devicetree_unfixed.h) +set(DEVICE_EXTERN_H ${PROJECT_BINARY_DIR}/include/generated/device_extern.h) set(DTS_POST_CPP ${PROJECT_BINARY_DIR}/${BOARD}.dts.pre.tmp) set_ifndef(DTS_SOURCE ${BOARD_DIR}/${BOARD}.dts) @@ -214,6 +215,7 @@ if(SUPPORTS_DTS) --dtc-flags '${EXTRA_DTC_FLAGS}' --bindings-dirs ${DTS_ROOT_BINDINGS} --header-out ${DEVICETREE_UNFIXED_H} + --device-header-out ${DEVICE_EXTERN_H} --dts-out ${ZEPHYR_DTS} # As a debugging aid --edt-pickle-out ${EDT_PICKLE} ) @@ -228,6 +230,7 @@ if(SUPPORTS_DTS) else() message(STATUS "Generated zephyr.dts: ${ZEPHYR_DTS}") message(STATUS "Generated devicetree_unfixed.h: ${DEVICETREE_UNFIXED_H}") + message(STATUS "Generated device_extern.h: ${DEVICE_EXTERN_H}") endif() # A file that used to be generated by 'dtc'. zephyr.dts is the new @@ -237,4 +240,5 @@ if(SUPPORTS_DTS) else() file(WRITE ${DEVICETREE_UNFIXED_H} "/* WARNING. THIS FILE IS AUTO-GENERATED. DO NOT MODIFY! */") + file(WRITE ${DEVICE_EXTERN_H} "/* WARNING. THIS FILE IS AUTO-GENERATED. DO NOT MODIFY! */") endif(SUPPORTS_DTS) diff --git a/include/device.h b/include/device.h index 6a790f50eb9..bcd7fee8423 100644 --- a/include/device.h +++ b/include/device.h @@ -767,6 +767,9 @@ static inline int device_pm_put_sync(const struct device *dev) { return -ENOTSUP } #endif +/* device_extern is generated base on devicetree nodes */ +#include + #include #endif /* ZEPHYR_INCLUDE_DEVICE_H_ */ diff --git a/scripts/dts/gen_defines.py b/scripts/dts/gen_defines.py index 3dd613857b0..2fd6ba14ba8 100755 --- a/scripts/dts/gen_defines.py +++ b/scripts/dts/gen_defines.py @@ -110,9 +110,35 @@ def main(): write_chosen(edt) write_global_compat_info(edt) + write_device_extern_header(args.device_header_out, edt) + if args.edt_pickle_out: write_pickled_edt(edt, args.edt_pickle_out) + +def write_device_extern_header(device_header_out, edt): + # Generate header that will extern devicetree struct device's + + with open(device_header_out, "w", encoding="utf-8") as dev_header_file: + print("#ifndef DEVICE_EXTERN_GEN_H", file=dev_header_file) + print("#define DEVICE_EXTERN_GEN_H", file=dev_header_file) + print("", file=dev_header_file) + print("#ifdef __cplusplus", file=dev_header_file) + print('extern "C" {', file=dev_header_file) + print("#endif", file=dev_header_file) + print("", file=dev_header_file) + + for node in sorted(edt.nodes, key=lambda node: node.dep_ordinal): + print(f"extern const struct device DEVICE_DT_NAME_GET(DT_{node.z_path_id});", file=dev_header_file) + + print("", file=dev_header_file) + print("#ifdef __cplusplus", file=dev_header_file) + print("}", file=dev_header_file) + print("#endif", file=dev_header_file) + print("", file=dev_header_file) + print("#endif /* DEVICE_EXTERN_GEN_H */", file=dev_header_file) + + def setup_edtlib_logging(): # The edtlib module emits logs using the standard 'logging' module. # Configure it so that warnings and above are printed to stderr, @@ -159,6 +185,8 @@ def parse_args(): parser.add_argument("--dts-out", required=True, help="path to write merged DTS source code to (e.g. " "as a debugging aid)") + parser.add_argument("--device-header-out", required=True, + help="path to write device struct extern header to") parser.add_argument("--edt-pickle-out", help="path to write pickled edtlib.EDT object to")