From 62ca18dad4b1c3f50767e5b904a59bb7481f66f9 Mon Sep 17 00:00:00 2001 From: TOKITA Hiroshi Date: Sun, 4 Aug 2024 11:16:13 +0900 Subject: [PATCH] libraries: SPI: handle multiple SPI instances Create multiple SPI instances if the `spis` array contains plural elements. Declare these as 'SPI1', 'SPI2', ..., from the second element of the array. (The first element is already declared as 'SPI'.) If `spis` is not defined but the DTS already defines `arduino-spi` and, use it to define the first SPI instance. The `arduion-spi` is usually defined with arduino_header in boards definitions. Signed-off-by: TOKITA Hiroshi --- libraries/SPI/SPI.cpp | 25 +++++++++++++++++++++++-- libraries/SPI/SPI.h | 17 +++++++++++++++++ 2 files changed, 40 insertions(+), 2 deletions(-) diff --git a/libraries/SPI/SPI.cpp b/libraries/SPI/SPI.cpp index 81b42481..d47d84cc 100644 --- a/libraries/SPI/SPI.cpp +++ b/libraries/SPI/SPI.cpp @@ -121,5 +121,26 @@ void arduino::ZephyrSPI::begin() {} void arduino::ZephyrSPI::end() {} -arduino::ZephyrSPI - SPI(DEVICE_DT_GET(DT_PHANDLE_BY_IDX(DT_PATH(zephyr_user), spis, 0))); +#if DT_NODE_HAS_PROP(DT_PATH(zephyr_user), spis) +#if (DT_PROP_LEN(DT_PATH(zephyr_user), spis) > 1) +#define ARDUINO_SPI_DEFINED_0 1 +#define DECL_SPI_0(n, p, i) arduino::ZephyrSPI SPI(DEVICE_DT_GET(DT_PHANDLE_BY_IDX(n, p, i))); +#define DECL_SPI_N(n, p, i) arduino::ZephyrSPI SPI##i(DEVICE_DT_GET(DT_PHANDLE_BY_IDX(n, p, i))); +#define DECLARE_SPI_N(n, p, i) \ + COND_CODE_1(ARDUINO_SPI_DEFINED_##i, (DECL_SPI_0(n, p, i)), (DECL_SPI_N(n, p, i))) + +/* Declare SPI, SPI1, SPI2, ... */ +DT_FOREACH_PROP_ELEM(DT_PATH(zephyr_user), spis, DECLARE_SPI_N) + +#undef DECLARE_SPI_N +#undef DECL_SPI_N +#undef DECL_SPI_0 +#undef ARDUINO_SPI_DEFINED_0 +#else // PROP_LEN(spis) > 1 +/* When PROP_LEN(spis) == 1, DT_FOREACH_PROP_ELEM work not correctly. */ +arduino::ZephyrSPI SPI(DEVICE_DT_GET(DT_PHANDLE_BY_IDX(DT_PATH(zephyr_user), spis, 0))); +#endif // HAS_PORP(spis) +/* If spis node is not defined, tries to use arduino_spi */ +#elif DT_NODE_EXISTS(DT_NODELABEL(arduino_spi)) +arduino::ZephyrSPI SPI(DEVICE_DT_GET(DT_NODELABEL(arduino_spi))); +#endif diff --git a/libraries/SPI/SPI.h b/libraries/SPI/SPI.h index ff9d96ba..5d448d7a 100644 --- a/libraries/SPI/SPI.h +++ b/libraries/SPI/SPI.h @@ -56,7 +56,24 @@ class ZephyrSPI : public HardwareSPI { } // namespace arduino +#if DT_NODE_HAS_PROP(DT_PATH(zephyr_user), spis) && (DT_PROP_LEN(DT_PATH(zephyr_user), spis) > 1) +#define ARDUINO_SPI_DEFINED_0 1 +#define DECL_EXTERN_SPI_0(i) extern arduino::ZephyrSPI SPI +#define DECL_EXTERN_SPI_N(i) extern arduino::ZephyrSPI SPI##i +#define DECLARE_EXTERN_SPI_N(n, p, i) \ + COND_CODE_1(ARDUINO_SPI_DEFINED_##i, (DECL_EXTERN_SPI_0(i);), (DECL_EXTERN_SPI_N(i);)) + +/* Declare SPI, SPI1, SPI2, ... */ +DT_FOREACH_PROP_ELEM(DT_PATH(zephyr_user), spis, DECLARE_EXTERN_SPI_N) + +#undef DECLARE_EXTERN_SPI_N +#undef DECL_EXTERN_SPI_N +#undef DECL_EXTERN_SPI_0 +#undef ARDUINO_SPI_DEFINED_0 +#else extern arduino::ZephyrSPI SPI; +#endif + /* Serial Peripheral Control Register */ extern uint8_t SPCR;