diff --git a/boards/adi/apard32690/apard32690_max32690_m4.dts b/boards/adi/apard32690/apard32690_max32690_m4.dts index 43575a724ac7b..0e896b561ece9 100644 --- a/boards/adi/apard32690/apard32690_max32690_m4.dts +++ b/boards/adi/apard32690/apard32690_max32690_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include diff --git a/boards/adi/max32655evkit/Kconfig.max32655evkit b/boards/adi/max32655evkit/Kconfig.max32655evkit index 2eed6e48c6089..373327bb652f6 100644 --- a/boards/adi/max32655evkit/Kconfig.max32655evkit +++ b/boards/adi/max32655evkit/Kconfig.max32655evkit @@ -5,3 +5,4 @@ config BOARD_MAX32655EVKIT select SOC_MAX32655_M4 if BOARD_MAX32655EVKIT_MAX32655_M4 + select SOC_MAX32655_RV32 if BOARD_MAX32655EVKIT_MAX32655_RV32 diff --git a/boards/adi/max32655evkit/doc/index.rst b/boards/adi/max32655evkit/doc/index.rst index 9c72155a4d90f..dacf124524c8f 100644 --- a/boards/adi/max32655evkit/doc/index.rst +++ b/boards/adi/max32655evkit/doc/index.rst @@ -154,10 +154,73 @@ Debugging Please refer to the `Flashing`_ section and run the ``west debug`` command instead of ``west flash``. +Dual Core Support +***************** + +An experimental board configuration for the secondary RISC-V core can be found +in +:zephyr_file:`boards/adi/max32655evkit/max32655evkit_max32655_rv32_defconfig`. + +It can boot Zephyr and print "hello world" to a RAM console, but it currently +has significant limitations: + +- **Kernel timer**: The zero-riscy core doesn't implement a machine timer and we + have not yet implemented a Zephyr driver for a system-level timer peripheral + on this SoC, therefore kernel functions that take a :c:type:`k_timeout_t` + argument, such as :c:func:`k_sleep` are not expected to work. + +- **Interrupts**: The zero-riscy core only allows enabling/disabling interrupts + globally and assumes there is an interrupt controller outside of the core. We + have not yet implemented support for a system-level interrupt controller, + therefore kernel interrupt services are not expected to work. + +- **Peripheral drivers**: Without interrupts, the existing UART, GPIO, and + other peripheral drivers won't work. + +The primary Arm core uses Kconfig options, +:kconfig:option:`CONFIG_MAX32_SECONDARY_RV32` and +:kconfig:option:`CONFIG_MAX32_SECONDARY_RV32_BOOT_ADDRESS`, to enable and +configure the boot address for the secondary RISC-V core. The devicetree chosen +node, ``zephyr,code-rv32-partition``, specifies the default value for the boot +address. + +:zephyr:code-sample:`sysbuild_hello_world` supports building the Arm and RISC-V +images: + +.. zephyr-app-commands:: + :zephyr-app: samples/sysbuild/hello_world + :board: max32655evkit/max32655/m4 + :west-args: -T sample.sysbuild.hello_world.max32655evkit_m4_rv32 + :goals: build + :compact: + +The build system hasn't yet been instrumented to merge the two images into one +combined image, so you can use :zephyr_file:`scripts/build/mergehex.py` to +merge them: + +.. code-block:: console + + $ python scripts/build/mergehex.py -o build/merged.hex \ + build/hello_world/zephyr/zephyr.hex build/remote/zephyr/zephyr.hex + +Likewise, west runners aren't aware of combined image, so you can use JLink to +program it to flash: + +.. code-block:: console + + $ JLinkExe -device MAX32655 -if SWD -speed 4000 -autoconnect 1 + + J-Link>loadfile build/merged.hex + References ********** - `MAX32655EVKIT web page`_ +- `zero-riscy user manual`_ + .. _MAX32655EVKIT web page: https://www.analog.com/en/design-center/evaluation-hardware-and-software/evaluation-boards-kits/max32655evkit.html#eb-overview + +.. _zero-riscy user manual: + https://pulp-platform.org/docs/user_manual.pdf diff --git a/boards/adi/max32655evkit/max32655evkit.dtsi b/boards/adi/max32655evkit/max32655evkit.dtsi new file mode 100644 index 0000000000000..5e0cc1a42bed8 --- /dev/null +++ b/boards/adi/max32655evkit/max32655evkit.dtsi @@ -0,0 +1,105 @@ +/* + * Copyright (c) 2023-2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include +#include + +/ { + reserved-memory { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + /* + * Concatenate SRAM0(32KB), SRAM1(32KB) and SRAM2(48KB) for the M4 + */ + m4_sram: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(112)>; + }; + + /* + * Use SRAM3(16KB) for the RV32 + */ + rv32_sram: memory@2001c000 { + compatible = "mmio-sram"; + reg = <0x2001c000 DT_SIZE_K(16)>; + }; + }; + + leds { + compatible = "gpio-leds"; + + led1: led_1 { + gpios = <&gpio0 24 GPIO_ACTIVE_LOW>; + label = "Red LED"; + }; + + led2: led_2 { + gpios = <&gpio0 25 GPIO_ACTIVE_LOW>; + label = "Blue LED"; + }; + }; + + buttons { + compatible = "gpio-keys"; + + pb1: pb1 { + gpios = <&gpio0 18 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; + label = "SW2"; + zephyr,code = ; + }; + + pb2: pb2 { + gpios = <&gpio0 19 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; + label = "SW3"; + zephyr,code = ; + }; + + pb_wakeup: pb_wakeup { + gpios = <&gpio3 1 + (GPIO_PULL_UP | GPIO_ACTIVE_LOW | MAX32_GPIO_VSEL_VDDIOH)>; + label = "Wakeup"; + zephyr,code = ; + }; + }; + + /* These aliases are provided for compatibility with samples */ + aliases { + led0 = &led1; + led1 = &led2; + sw0 = &pb1; + sw1 = &pb2; + watchdog0 = &wdt0; + }; +}; + +&uart0 { + pinctrl-0 = <&uart0a_tx_p0_1 &uart0a_rx_p0_0>; + pinctrl-names = "default"; + current-speed = <115200>; + data-bits = <8>; + parity = "none"; +}; + +&flash0 { + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + m4_partition: partition@10000000 { + label = "image-m4"; + reg = <0x10000000 DT_SIZE_K(256)>; + }; + + rv32_partition: partition@10040000 { + label = "image-rv32"; + reg = <0x10040000 DT_SIZE_K(256)>; + }; + }; +}; diff --git a/boards/adi/max32655evkit/max32655evkit_max32655_m4.dts b/boards/adi/max32655evkit/max32655evkit_max32655_m4.dts index 20c6daf6001f3..97b0e135767c7 100644 --- a/boards/adi/max32655evkit/max32655evkit_max32655_m4.dts +++ b/boards/adi/max32655evkit/max32655evkit_max32655_m4.dts @@ -6,10 +6,8 @@ /dts-v1/; -#include -#include -#include -#include +#include +#include "max32655evkit.dtsi" / { model = "Analog Devices MAX32655EVKIT"; @@ -18,64 +16,48 @@ chosen { zephyr,console = &uart0; zephyr,shell-uart = &uart0; - zephyr,sram = &sram2; - zephyr,flash = &flash0; + zephyr,sram = &m4_sram; + zephyr,flash = &m4_partition; + zephyr,code-rv32-partition = &rv32_partition; }; - leds { - compatible = "gpio-leds"; + aliases { + spi-flash0 = &spi0_cs0_flash; + }; +}; - led1: led_1 { - gpios = <&gpio0 24 GPIO_ACTIVE_LOW>; - label = "Red LED"; - }; +&cpu1 { + pinctrl-0 = <&rv_tck_p1_0 &rv_tms_p1_1 &rv_tdi_p1_2 &rv_tdo_p1_3>; + pinctrl-names = "default"; +}; - led2: led_2 { - gpios = <&gpio0 25 GPIO_ACTIVE_LOW>; - label = "Blue LED"; - }; - }; +&led1 { + status = "okay"; +}; - buttons { - compatible = "gpio-keys"; - - pb1: pb1 { - gpios = <&gpio0 18 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; - label = "SW2"; - zephyr,code = ; - }; - - pb2: pb2 { - gpios = <&gpio0 19 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; - label = "SW3"; - zephyr,code = ; - }; - - pb_wakeup: pb_wakeup { - gpios = <&gpio3 1 - (GPIO_PULL_UP | GPIO_ACTIVE_LOW | MAX32_GPIO_VSEL_VDDIOH)>; - label = "Wakeup"; - zephyr,code = ; - }; - }; +&led2 { + status = "okay"; +}; - /* These aliases are provided for compatibility with samples */ - aliases { - led0 = &led1; - led1 = &led2; - sw0 = &pb1; - sw1 = &pb2; - watchdog0 = &wdt0; - }; +&pb1 { + status = "okay"; +}; + +&pb2 { + status = "okay"; +}; + +&pb_wakeup { + status = "okay"; }; &uart0 { pinctrl-0 = <&uart0a_tx_p0_1 &uart0a_rx_p0_0>; + status = "okay"; pinctrl-names = "default"; current-speed = <115200>; data-bits = <8>; parity = "none"; - status = "okay"; }; &clk_ipo { @@ -123,12 +105,6 @@ status = "okay"; }; -&spi0 { - status = "okay"; - pinctrl-0 = <&spi0_mosi_p0_5 &spi0_miso_p0_6 &spi0_sck_p0_7 &spi0_ss0_p0_4>; - pinctrl-names = "default"; -}; - &w1 { pinctrl-0 = <&owm_io_p0_6 &owm_pe_p0_7>; pinctrl-names = "default"; @@ -151,10 +127,10 @@ }; &spi0 { - status = "okay"; pinctrl-0 = <&spi0_mosi_p0_5 &spi0_miso_p0_6 &spi0_sck_p0_7>; pinctrl-names = "default"; cs-gpios = <&gpio0 4 (GPIO_ACTIVE_LOW | MAX32_GPIO_VSEL_VDDIOH)>; + status = "okay"; spi0_cs0_flash: w25q128@0 { compatible = "jedec,spi-nor"; diff --git a/boards/adi/max32655evkit/max32655evkit_max32655_m4.yaml b/boards/adi/max32655evkit/max32655evkit_max32655_m4.yaml index 97b5b04e28778..2ed16625ff233 100644 --- a/boards/adi/max32655evkit/max32655evkit_max32655_m4.yaml +++ b/boards/adi/max32655evkit/max32655evkit_max32655_m4.yaml @@ -22,4 +22,4 @@ supported: - w1 - flash ram: 48 -flash: 512 +flash: 256 diff --git a/boards/adi/max32655evkit/max32655evkit_max32655_rv32.dts b/boards/adi/max32655evkit/max32655evkit_max32655_rv32.dts new file mode 100644 index 0000000000000..7bd40a9f72c04 --- /dev/null +++ b/boards/adi/max32655evkit/max32655evkit_max32655_rv32.dts @@ -0,0 +1,62 @@ +/* + * Copyright (c) 2023-2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/dts-v1/; + +#include +#include "max32655evkit.dtsi" + +/ { + model = "Analog Devices MAX32655EVKIT"; + compatible = "adi,max32655evkit"; + + chosen { + zephyr,console = &uart3; + zephyr,shell-uart = &uart3; + zephyr,sram = &rv32_sram; + zephyr,flash = &rv32_partition; + }; +}; + +&rv32_sys_timer { + status = "okay"; +}; + +&clk_iso { + status = "okay"; +}; + +/* + * ERTCO is required for counter RTC + */ +&clk_ertco { + status = "okay"; +}; + +&gpio0 { + status = "okay"; +}; + +&gpio1 { + status = "okay"; +}; + +&gpio2 { + status = "okay"; +}; + +&gpio3 { + status = "okay"; +}; + +&uart3 { + pinctrl-0 = <&lpuartb_rx_p2_6 &lpuartb_tx_p2_7>; + status = "okay"; + pinctrl-names = "default"; + current-speed = <115200>; + data-bits = <8>; + parity = "none"; +}; diff --git a/boards/adi/max32655evkit/max32655evkit_max32655_rv32.yaml b/boards/adi/max32655evkit/max32655evkit_max32655_rv32.yaml new file mode 100644 index 0000000000000..ec11981e3e6a2 --- /dev/null +++ b/boards/adi/max32655evkit/max32655evkit_max32655_rv32.yaml @@ -0,0 +1,13 @@ +identifier: max32655evkit/max32655/rv32 +name: max32655evkit rv32 +vendor: adi +type: mcu +arch: riscv +toolchain: + - zephyr +supported: + - gpio + - serial + - flash +ram: 16 +flash: 256 diff --git a/boards/adi/max32655evkit/max32655evkit_max32655_rv32_defconfig b/boards/adi/max32655evkit/max32655evkit_max32655_rv32_defconfig new file mode 100644 index 0000000000000..4e89e4760305b --- /dev/null +++ b/boards/adi/max32655evkit/max32655evkit_max32655_rv32_defconfig @@ -0,0 +1,14 @@ +# Copyright (c) 2023-2024 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +CONFIG_SYS_CLOCK_TICKS_PER_SEC=5000 + +CONFIG_GPIO=y + +# Console +CONFIG_CONSOLE=y +CONFIG_UART_CONSOLE=y + +# Enable UART +CONFIG_SERIAL=y +CONFIG_UART_INTERRUPT_DRIVEN=y diff --git a/boards/adi/max32655fthr/max32655fthr_max32655_m4.dts b/boards/adi/max32655fthr/max32655fthr_max32655_m4.dts index 2c9d5950c9e3e..4bdb3833a51bd 100644 --- a/boards/adi/max32655fthr/max32655fthr_max32655_m4.dts +++ b/boards/adi/max32655fthr/max32655fthr_max32655_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include @@ -18,10 +18,24 @@ chosen { zephyr,console = &uart0; zephyr,shell-uart = &uart0; - zephyr,sram = &sram2; + zephyr,sram = &m4_sram; zephyr,flash = &flash0; }; + reserved-memory { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + /* + * Concatenate SRAM0(32KB), SRAM1(32KB) and SRAM2(48KB) for the M4 + */ + m4_sram: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(112)>; + }; + }; + leds { compatible = "gpio-leds"; diff --git a/boards/adi/max32680evkit/max32680evkit_max32680_m4.dts b/boards/adi/max32680evkit/max32680evkit_max32680_m4.dts index 44b04d719216c..7214a8f90ff21 100644 --- a/boards/adi/max32680evkit/max32680evkit_max32680_m4.dts +++ b/boards/adi/max32680evkit/max32680evkit_max32680_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include diff --git a/boards/adi/max32690evkit/Kconfig.max32690evkit b/boards/adi/max32690evkit/Kconfig.max32690evkit index d475a30f4c894..0a969a05830a8 100644 --- a/boards/adi/max32690evkit/Kconfig.max32690evkit +++ b/boards/adi/max32690evkit/Kconfig.max32690evkit @@ -5,3 +5,4 @@ config BOARD_MAX32690EVKIT select SOC_MAX32690_M4 if BOARD_MAX32690EVKIT_MAX32690_M4 + select SOC_MAX32690_RV32 if BOARD_MAX32690EVKIT_MAX32690_RV32 diff --git a/boards/adi/max32690evkit/max32690evkit.dtsi b/boards/adi/max32690evkit/max32690evkit.dtsi new file mode 100644 index 0000000000000..176867bcb8e84 --- /dev/null +++ b/boards/adi/max32690evkit/max32690evkit.dtsi @@ -0,0 +1,135 @@ +/* + * Copyright (c) 2023-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include +#include + +/ { + model = "Analog Devices MAX32690EVKIT"; + compatible = "adi,max32690evkit"; + + chosen { + zephyr,flash = &flash0; + }; + + reserved-memory { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + /* + * Concatenate SRAM0 through SRAM7 for the M4 + */ + m4_sram: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_M(1)>; + }; + }; + + leds { + compatible = "gpio-leds"; + + red_led: led_0 { + gpios = <&gpio0 14 GPIO_ACTIVE_LOW>; + label = "LED0"; + }; + + green_led: led_1 { + gpios = <&gpio2 12 GPIO_ACTIVE_LOW>; + label = "LED1"; + }; + }; + + buttons { + compatible = "gpio-keys"; + + pb0: pb0 { + gpios = <&gpio4 0 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; + label = "SW2"; + zephyr,code = ; + }; + }; +}; + +&clk_ipo { + status = "okay"; +}; + +&clk_ibro { + status = "okay"; +}; + +&trng { + status = "okay"; +}; + + +&gpio0 { + status = "okay"; +}; + +&gpio1 { + status = "okay"; +}; + +&gpio2 { + status = "okay"; +}; + +&gpio3 { + status = "okay"; +}; + +&gpio4 { + status = "okay"; +}; + +&i2c0 { + status = "okay"; + pinctrl-0 = <&i2c0a_scl_p2_8 &i2c0a_sda_p2_7>; + pinctrl-names = "default"; +}; + +&rtc_counter { + status = "okay"; +}; + +&flash0 { + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + m4_partition: partition@0 { + label = "image-m4"; + reg = <0x0 DT_SIZE_M(1)>; + }; + + storage_partition: partition@100000 { + label = "storage"; + reg = <0x100000 DT_SIZE_K(64)>; + }; + }; +}; + +&flash1 { + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + rv32_partition: rv32_partition@0 { + label = "image-rv32"; + reg = <0x0 DT_SIZE_K(192)>; + }; + + rv32_storage_partition: rv32_partition@30000 { + label = "rv32-storage"; + reg = <0x30000 DT_SIZE_K(64)>; + }; + }; +}; diff --git a/boards/adi/max32690evkit/max32690evkit_max32690_m4.dts b/boards/adi/max32690evkit/max32690evkit_max32690_m4.dts index bcd78bf642f37..ac1b05364be70 100644 --- a/boards/adi/max32690evkit/max32690evkit_max32690_m4.dts +++ b/boards/adi/max32690evkit/max32690evkit_max32690_m4.dts @@ -6,7 +6,9 @@ /dts-v1/; -#include +#include +#include "max32690evkit.dtsi" + #include #include #include @@ -20,36 +22,13 @@ chosen { zephyr,console = &uart2; zephyr,shell-uart = &uart2; - zephyr,sram = &sram0; + zephyr,sram = &m4_sram; zephyr,flash = &flash0; + zephyr,code-rv32-partition = &flash1; zephyr,display = &st7735; zephyr,canbus = &can0; }; - leds { - compatible = "gpio-leds"; - - red_led: led_0 { - gpios = <&gpio0 14 GPIO_ACTIVE_LOW>; - label = "LED0"; - }; - - green_led: led_1 { - gpios = <&gpio2 12 GPIO_ACTIVE_LOW>; - label = "LED1"; - }; - }; - - buttons { - compatible = "gpio-keys"; - - pb0: pb0 { - gpios = <&gpio4 0 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; - label = "SW2"; - zephyr,code = ; - }; - }; - aliases { led0 = &red_led; led1 = &green_led; @@ -110,6 +89,10 @@ }; }; +&dma0 { + status = "okay"; +}; + &hpb { pinctrl-0 = <&hyp_cs0n_p1_11 &hyp_rwds_p1_14 &hyp_d0_p1_12 &hyp_d1_p1_15 &hyp_d2_p1_19 &hyp_d3_p1_20 &hyp_d4_p1_13 @@ -126,34 +109,6 @@ }; }; -&clk_ipo { - status = "okay"; -}; - -&clk_ibro { - status = "okay"; -}; - -&gpio0 { - status = "okay"; -}; - -&gpio1 { - status = "okay"; -}; - -&gpio2 { - status = "okay"; -}; - -&gpio3 { - status = "okay"; -}; - -&gpio4 { - status = "okay"; -}; - &uart2 { clock-source = ; pinctrl-0 = <&uart2a_tx_p1_10 &uart2a_rx_p1_9>; @@ -164,20 +119,6 @@ status = "okay"; }; -&trng { - status = "okay"; -}; - -&i2c0 { - status = "okay"; - pinctrl-0 = <&i2c0a_scl_p2_8 &i2c0a_sda_p2_7>; - pinctrl-names = "default"; -}; - -&dma0 { - status = "okay"; -}; - &wdt0 { status = "okay"; }; @@ -205,4 +146,6 @@ zephyr_udc0: &usbhs { status = "okay"; pinctrl-0 = <&can0b_tx_p2_23 &can0b_rx_p2_22>; pinctrl-names = "default"; + bitrate = <500000>; + sample-point = <800>; }; diff --git a/boards/adi/max32690evkit/max32690evkit_max32690_rv32.dts b/boards/adi/max32690evkit/max32690evkit_max32690_rv32.dts new file mode 100644 index 0000000000000..bc74053cc8585 --- /dev/null +++ b/boards/adi/max32690evkit/max32690evkit_max32690_rv32.dts @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/dts-v1/; + +#include +#include "max32690evkit.dtsi" + +#include +#include +#include +#include +#include + +/ { + model = "Analog Devices MAX32690EVKIT"; + compatible = "adi,max32690evkit"; + + chosen { + zephyr,console = &uart3; + zephyr,shell-uart = &uart3; + zephyr,sram = &sram8; + zephyr,flash = &flash1; + zephyr,settings-partition = &rv32_storage_partition; + }; + + aliases { + watchdog0 = &wdt1; + }; +}; + +&rv32_sys_timer { + status = "okay"; +}; + +&uart3 { + clock-source = ; + pinctrl-0 = <&lpuart0b_rx_p3_0 &lpuart0b_tx_p3_1>; + pinctrl-names = "default"; + current-speed = <115200>; + data-bits = <8>; + parity = "none"; + status = "okay"; +}; + +&flc1 { + status = "okay"; +}; + +&wdt1 { + status = "okay"; +}; diff --git a/boards/adi/max32690evkit/max32690evkit_max32690_rv32.yaml b/boards/adi/max32690evkit/max32690evkit_max32690_rv32.yaml new file mode 100644 index 0000000000000..d067eeba41bfe --- /dev/null +++ b/boards/adi/max32690evkit/max32690evkit_max32690_rv32.yaml @@ -0,0 +1,13 @@ +identifier: max32690evkit/max32690/rv32 +name: max32690evkit rv32 +vendor: adi +type: mcu +arch: riscv +toolchain: + - zephyr +supported: + - gpio + - serial + - flash +ram: 128 +flash: 256 diff --git a/boards/adi/max32690evkit/max32690evkit_max32690_rv32_defconfig b/boards/adi/max32690evkit/max32690evkit_max32690_rv32_defconfig new file mode 100644 index 0000000000000..723411122b0e3 --- /dev/null +++ b/boards/adi/max32690evkit/max32690evkit_max32690_rv32_defconfig @@ -0,0 +1,13 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +# Set supported clock accuracy +CONFIG_SYS_CLOCK_TICKS_PER_SEC=5000 + +# Console +CONFIG_CONSOLE=y +CONFIG_UART_CONSOLE=y + +# Enable UART +CONFIG_SERIAL=y +CONFIG_UART_INTERRUPT_DRIVEN=y diff --git a/boards/adi/max32690fthr/max32690fthr_max32690_m4.dts b/boards/adi/max32690fthr/max32690fthr_max32690_m4.dts index fb2dbc17cc359..3a49a149ec64a 100644 --- a/boards/adi/max32690fthr/max32690fthr_max32690_m4.dts +++ b/boards/adi/max32690fthr/max32690fthr_max32690_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include diff --git a/boards/adi/max78000evkit/max78000evkit_max78000_m4.dts b/boards/adi/max78000evkit/max78000evkit_max78000_m4.dts index 7ddca4a85a398..b22da5e08aee6 100644 --- a/boards/adi/max78000evkit/max78000evkit_max78000_m4.dts +++ b/boards/adi/max78000evkit/max78000evkit_max78000_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include diff --git a/boards/adi/max78000fthr/max78000fthr_max78000_m4.dts b/boards/adi/max78000fthr/max78000fthr_max78000_m4.dts index acbfd93105c7b..862fdedd8be3d 100644 --- a/boards/adi/max78000fthr/max78000fthr_max78000_m4.dts +++ b/boards/adi/max78000fthr/max78000fthr_max78000_m4.dts @@ -6,7 +6,7 @@ /dts-v1/; -#include +#include #include #include #include diff --git a/boards/adi/max78002evkit/Kconfig.max78002evkit b/boards/adi/max78002evkit/Kconfig.max78002evkit index a18aa6b97d954..3fa6d83530d30 100644 --- a/boards/adi/max78002evkit/Kconfig.max78002evkit +++ b/boards/adi/max78002evkit/Kconfig.max78002evkit @@ -5,3 +5,4 @@ config BOARD_MAX78002EVKIT select SOC_MAX78002_M4 if BOARD_MAX78002EVKIT_MAX78002_M4 + select SOC_MAX78002_RV32 if BOARD_MAX78002EVKIT_MAX78002_RV32 diff --git a/boards/adi/max78002evkit/max78002evkit.dtsi b/boards/adi/max78002evkit/max78002evkit.dtsi new file mode 100644 index 0000000000000..535a2155dc7b4 --- /dev/null +++ b/boards/adi/max78002evkit/max78002evkit.dtsi @@ -0,0 +1,174 @@ +/* + * Copyright (c) 2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include +#include + +/ { + model = "Analog Devices MAX78002EVKIT"; + compatible = "adi,max78002evkit"; + + chosen { + zephyr,flash = &flash0; + }; + + reserved-memory { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + /* + * Concatenate SRAM2 through SRAM3 for the M4. + * Avoid SRAM0 since it will not work for noinit data. + */ + m4_sram: memory@20010000 { + compatible = "mmio-sram"; + reg = <0x20010000 DT_SIZE_K(48 + 16)>; + }; + + /* + * Concatenate SRAM4 through SRAM6 for the RV32 + */ + rv32_sram: memory@20030000 { + compatible = "mmio-sram"; + reg = <0x20030000 DT_SIZE_K(176)>; + }; + }; + + leds { + compatible = "gpio-leds"; + + led1: led_1 { + gpios = <&gpio2 4 GPIO_ACTIVE_HIGH>; + label = "Green LED"; + }; + + led2: led_2 { + gpios = <&gpio2 5 GPIO_ACTIVE_HIGH>; + label = "Red LED"; + }; + }; + + buttons { + compatible = "gpio-keys"; + + pb1: pb1 { + gpios = <&gpio2 6 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; + label = "SW2"; + zephyr,code = ; + }; + + pb2: pb2 { + gpios = <&gpio2 7 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; + label = "SW3"; + zephyr,code = ; + }; + + pb_wakeup: pb_wakeup { + gpios = <&gpio3 1 + (GPIO_PULL_UP | GPIO_ACTIVE_LOW | MAX32_GPIO_VSEL_VDDIOH)>; + label = "Wakeup"; + zephyr,code = ; + }; + }; + + /* These aliases are provided for compatibility with samples */ + aliases { + led0 = &led1; + led1 = &led2; + sw0 = &pb1; + sw1 = &pb2; + watchdog0 = &wdt0; + }; +}; + +&clk_ipo { + status = "okay"; +}; + +&clk_ibro { + status = "okay"; +}; + +&uart0 { + pinctrl-0 = <&uart0a_tx_p0_1 &uart0a_rx_p0_0>; + clock-source = ; + pinctrl-names = "default"; + current-speed = <115200>; + data-bits = <8>; + parity = "none"; +}; + +&uart1 { + pinctrl-0 = <&uart1_tx_p0_13 &uart1_rx_p0_12>; + clock-source = ; + pinctrl-names = "default"; + current-speed = <115200>; + data-bits = <8>; + parity = "none"; +}; + +rv32_uart: &uart1 {}; +m4_uart: &uart0 {}; + +&gpio0 { + status = "okay"; +}; + +&gpio1 { + status = "okay"; +}; + +&gpio2 { + status = "okay"; +}; + +&gpio3 { + status = "okay"; +}; + +&trng { + status = "okay"; +}; + +&i2c0 { + status = "okay"; + pinctrl-0 = <&i2c0_scl_p0_10 &i2c0_sda_p0_11>; + pinctrl-names = "default"; +}; + +&rtc_counter { + status = "okay"; +}; + +&flash0 { + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + m4_partition: partition@0 { + label = "image-m4"; + reg = <0x0 DT_SIZE_M(1)>; + }; + + m4_storage_partition: partition@100000 { + label = "storage-m4"; + reg = <0x100000 DT_SIZE_K(256)>; + }; + + rv32_partition: partition@140000 { + label = "image-rv32"; + reg = <0x140000 DT_SIZE_M(1)>; + }; + + rv32_storage_partition: partition@240000 { + label = "storage-rv32"; + reg = <0x240000 DT_SIZE_K(256)>; + }; + }; +}; diff --git a/boards/adi/max78002evkit/max78002evkit_max78002_m4.dts b/boards/adi/max78002evkit/max78002evkit_max78002_m4.dts index a21e71e967a10..0fd68c1c0aa7a 100644 --- a/boards/adi/max78002evkit/max78002evkit_max78002_m4.dts +++ b/boards/adi/max78002evkit/max78002evkit_max78002_m4.dts @@ -6,131 +6,58 @@ /dts-v1/; -#include +#include +#include "max78002evkit.dtsi" + #include -#include -#include / { model = "Analog Devices MAX78002EVKIT"; compatible = "adi,max78002evkit"; chosen { - zephyr,console = &uart0; - zephyr,shell-uart = &uart0; - zephyr,sram = &sram2; - zephyr,flash = &flash0; - }; - - leds { - compatible = "gpio-leds"; - - led1: led_1 { - gpios = <&gpio2 4 GPIO_ACTIVE_HIGH>; - label = "Green LED"; - }; - - led2: led_2 { - gpios = <&gpio2 5 GPIO_ACTIVE_HIGH>; - label = "Red LED"; - }; + zephyr,console = &m4_uart; + zephyr,shell-uart = &m4_uart; + zephyr,sram = &m4_sram; + zephyr,code-partition = &m4_partition; + zephyr,settings-partition = &m4_storage_partition; + zephyr,code-rv32-partition = &rv32_partition; + zephyr,rv32-flash = &flash0; }; - buttons { - compatible = "gpio-keys"; - - pb1: pb1 { - gpios = <&gpio2 6 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; - label = "SW2"; - zephyr,code = ; - }; - - pb2: pb2 { - gpios = <&gpio2 7 (GPIO_PULL_UP | GPIO_ACTIVE_LOW)>; - label = "SW3"; - zephyr,code = ; - }; - - pb_wakeup: pb_wakeup { - gpios = <&gpio3 1 - (GPIO_PULL_UP | GPIO_ACTIVE_LOW | MAX32_GPIO_VSEL_VDDIOH)>; - label = "Wakeup"; - zephyr,code = ; - }; - }; - - /* These aliases are provided for compatibility with samples */ aliases { - led0 = &led1; - led1 = &led2; - sw0 = &pb1; - sw1 = &pb2; watchdog0 = &wdt0; }; }; -&uart0 { - pinctrl-0 = <&uart0a_tx_p0_1 &uart0a_rx_p0_0>; - pinctrl-names = "default"; - current-speed = <115200>; - data-bits = <8>; - parity = "none"; +&flc0 { status = "okay"; }; -&clk_ipo { - status = "okay"; -}; - -&clk_ibro { - status = "okay"; -}; - -&gpio0 { - status = "okay"; -}; - -&gpio1 { - status = "okay"; -}; - -&gpio2 { - status = "okay"; -}; - -&gpio3 { - status = "okay"; +&cpu1 { + pinctrl-0 = <&rv_tck_p1_0 &rv_tms_p1_1 &rv_tdi_p1_2 &rv_tdo_p1_3>; + pinctrl-names = "default"; }; -&trng { +&m4_uart { status = "okay"; }; -&i2c0 { +&spi0 { status = "okay"; - pinctrl-0 = <&i2c0_scl_p0_10 &i2c0_sda_p0_11>; + pinctrl-0 = <&spi0_mosi_p0_5 &spi0_miso_p0_6 &spi0_sck_p0_7 &spi0_ss0_p0_4>; pinctrl-names = "default"; }; -&dma0 { - status = "okay"; -}; - &wdt0 { status = "okay"; }; -&spi0 { +&dma0 { status = "okay"; - pinctrl-0 = <&spi0_mosi_p0_5 &spi0_miso_p0_6 &spi0_sck_p0_7 &spi0_ss0_p0_4>; - pinctrl-names = "default"; }; &w1 { pinctrl-0 = <&owm_io_p0_6 &owm_pe_p0_7>; pinctrl-names = "default"; }; - -&rtc_counter { - status = "okay"; -}; diff --git a/boards/adi/max78002evkit/max78002evkit_max78002_m4_defconfig b/boards/adi/max78002evkit/max78002evkit_max78002_m4_defconfig index 38ffe5e0e7a24..d48537c4171a0 100644 --- a/boards/adi/max78002evkit/max78002evkit_max78002_m4_defconfig +++ b/boards/adi/max78002evkit/max78002evkit_max78002_m4_defconfig @@ -14,3 +14,6 @@ CONFIG_UART_CONSOLE=y # Enable UART CONFIG_SERIAL=y CONFIG_UART_INTERRUPT_DRIVEN=y + +# Load at the correct code partition +CONFIG_USE_DT_CODE_PARTITION=y diff --git a/boards/adi/max78002evkit/max78002evkit_max78002_rv32.dts b/boards/adi/max78002evkit/max78002evkit_max78002_rv32.dts new file mode 100644 index 0000000000000..13b3f496494c6 --- /dev/null +++ b/boards/adi/max78002evkit/max78002evkit_max78002_rv32.dts @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/dts-v1/; + +#include +#include "max78002evkit.dtsi" + +#include + +/ { + model = "Analog Devices MAX78002EVKIT"; + compatible = "adi,max78002evkit"; + + chosen { + zephyr,console = &rv32_uart; + zephyr,shell-uart = &rv32_uart; + zephyr,sram = &rv32_sram; + zephyr,code-partition = &rv32_partition; + zephyr,settings-partition = &rv32_storage_partition; + }; +}; + +&rv32_sys_timer { + status = "okay"; +}; + +&clk_iso { + status = "okay"; +}; + +&rv32_uart { + status = "okay"; +}; diff --git a/boards/adi/max78002evkit/max78002evkit_max78002_rv32.yaml b/boards/adi/max78002evkit/max78002evkit_max78002_rv32.yaml new file mode 100644 index 0000000000000..2c2fcd777488d --- /dev/null +++ b/boards/adi/max78002evkit/max78002evkit_max78002_rv32.yaml @@ -0,0 +1,12 @@ +identifier: max78002evkit/max78002/rv32 +name: max78002evkit rv32 +vendor: adi +type: mcu +arch: riscv +toolchain: + - zephyr +supported: + - gpio + - serial +ram: 112 +flash: 1024 diff --git a/boards/adi/max78002evkit/max78002evkit_max78002_rv32_defconfig b/boards/adi/max78002evkit/max78002evkit_max78002_rv32_defconfig new file mode 100644 index 0000000000000..4dfe4f2d99415 --- /dev/null +++ b/boards/adi/max78002evkit/max78002evkit_max78002_rv32_defconfig @@ -0,0 +1,18 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +# Set supported clock accuracy +CONFIG_SYS_CLOCK_TICKS_PER_SEC=4500 + +# Enable GPIO +CONFIG_GPIO=y + +# Console +CONFIG_CONSOLE=y +CONFIG_UART_CONSOLE=y + +# Enable UART +CONFIG_SERIAL=y +CONFIG_UART_INTERRUPT_DRIVEN=y + +CONFIG_USE_DT_CODE_PARTITION=y diff --git a/boards/common/openocd-adi-max32.boards.cmake b/boards/common/openocd-adi-max32.boards.cmake index c815a0db64f33..95497f18cbd79 100644 --- a/boards/common/openocd-adi-max32.boards.cmake +++ b/boards/common/openocd-adi-max32.boards.cmake @@ -5,7 +5,9 @@ if(CONFIG_ARCH STREQUAL "riscv") set(MAX32_TARGET_CFG "${CONFIG_SOC}_riscv.cfg") - set(MAX32_INTERFACE_CFG "olimex-arm-usb-ocd-h.cfg") + set(MAX32_INTERFACE_CFG "ftdi/olimex-arm-usb-ocd-h.cfg") + set(MAX32_FLASH_TARGET_CFG "${CONFIG_SOC}.cfg") + set(MAX32_FLASH_INTERFACE_CFG "cmsis-dap.cfg") else() set(MAX32_TARGET_CFG "${CONFIG_SOC}.cfg") set(MAX32_INTERFACE_CFG "cmsis-dap.cfg") @@ -22,7 +24,19 @@ board_runner_args(openocd --cmd-pre-init "source [find interface/${MAX32_INTERFA board_runner_args(openocd --cmd-pre-init "source [find target/${MAX32_TARGET_CFG}]") board_runner_args(openocd "--target-handle=_CHIPNAME.cpu") +if(MAX32_FLASH_INTERFACE_CFG) + board_runner_args(openocd --flash-cmd-pre-init "source [find interface/${MAX32_FLASH_INTERFACE_CFG}]") +endif() + +if(MAX32_FLASH_TARGET_CFG) + board_runner_args(openocd --flash-cmd-pre-init "source [find target/${MAX32_FLASH_TARGET_CFG}]") +endif() + if(CONFIG_SOC_FAMILY_MAX32_M4 OR CONFIG_SOC_FAMILY_MAX32_M33) board_runner_args(openocd --cmd-pre-init "allow_low_pwr_dbg") board_runner_args(openocd "--cmd-erase=max32xxx mass_erase 0") endif() + +if(CONFIG_SOC_MAX32690 AND CONFIG_SOC_FAMILY_MAX32_RV32) + board_runner_args(openocd "--cmd-erase=max32xxx mass_erase 1") +endif() diff --git a/drivers/hwinfo/Kconfig.max32 b/drivers/hwinfo/Kconfig.max32 index d66dd9638e339..62ebfb4e10ccf 100644 --- a/drivers/hwinfo/Kconfig.max32 +++ b/drivers/hwinfo/Kconfig.max32 @@ -6,6 +6,7 @@ config HWINFO_MAX32 default y depends on SOC_FAMILY_MAX32 depends on !TRUSTED_EXECUTION_NONSECURE + depends on !SOC_FAMILY_MAX32_RV32 select HWINFO_HAS_DRIVER help Enable MAX32 hwinfo driver. diff --git a/drivers/interrupt_controller/CMakeLists.txt b/drivers/interrupt_controller/CMakeLists.txt index 44a0b7573a81e..07144b2b4887f 100644 --- a/drivers/interrupt_controller/CMakeLists.txt +++ b/drivers/interrupt_controller/CMakeLists.txt @@ -50,6 +50,7 @@ zephyr_library_sources_ifdef(CONFIG_NXP_IRQSTEER intc_nxp_irqsteer.c) zephyr_library_sources_ifdef(CONFIG_INTC_MTK_ADSP intc_mtk_adsp.c) zephyr_library_sources_ifdef(CONFIG_WCH_PFIC intc_wch_pfic.c) zephyr_library_sources_ifdef(CONFIG_WCH_EXTI intc_wch_exti.c) +zephyr_library_sources_ifdef(CONFIG_MAX32_RV32_INTC intc_max32_rv32.c) if(CONFIG_INTEL_VTD_ICTL) zephyr_library_include_directories(${ZEPHYR_BASE}/arch/x86/include) diff --git a/drivers/interrupt_controller/Kconfig b/drivers/interrupt_controller/Kconfig index d3954cc1f3c84..e544ae8642c20 100644 --- a/drivers/interrupt_controller/Kconfig +++ b/drivers/interrupt_controller/Kconfig @@ -125,4 +125,6 @@ source "drivers/interrupt_controller/Kconfig.wch_pfic" source "drivers/interrupt_controller/Kconfig.wch_exti" +source "drivers/interrupt_controller/Kconfig.max32_rv32" + endmenu diff --git a/drivers/interrupt_controller/Kconfig.max32_rv32 b/drivers/interrupt_controller/Kconfig.max32_rv32 new file mode 100644 index 0000000000000..b49491571f38c --- /dev/null +++ b/drivers/interrupt_controller/Kconfig.max32_rv32 @@ -0,0 +1,11 @@ +# ADI MAX32 RV32 IC configuration + +# Copyright (c) 2025 Analog Devices, Inc +# SPDX-License-Identifier: Apache-2.0 + +config MAX32_RV32_INTC + bool "Interrupt Controller Driver for MAX32 RV32 cores" + default y + depends on DT_HAS_ADI_MAX32_RV32_INTC_ENABLED + help + Enable interrupt controller driver for MAX32 RV32 cores. diff --git a/drivers/interrupt_controller/intc_max32_rv32.c b/drivers/interrupt_controller/intc_max32_rv32.c new file mode 100644 index 0000000000000..4435ff3320ed0 --- /dev/null +++ b/drivers/interrupt_controller/intc_max32_rv32.c @@ -0,0 +1,132 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#define DT_DRV_COMPAT adi_max32_rv32_intc + +#include +#include +#include + +typedef struct { + uint32_t enable; /**< \b 0x00:<\tt> */ + uint32_t pending; /**< \b 0x04:<\tt> */ + uint32_t set_pending; /**< \b 0x08:<\tt> */ + uint32_t clear_pending; /**< \b 0x0c:<\tt> */ +} rv32_intc_grp_t; + +typedef struct { + rv32_intc_grp_t intr[2]; + rv32_intc_grp_t event[2]; +} rv32_intc_regs_t; + +static volatile rv32_intc_regs_t *get_intc_regs(void) +{ + return (rv32_intc_regs_t *)DT_INST_REG_ADDR(0); +} + +void arch_irq_enable(unsigned int source) +{ + volatile rv32_intc_regs_t *regs = get_intc_regs(); + uint8_t grp = source / 32; + uint32_t val = source % 32; + volatile rv32_intc_grp_t *int_grp = ®s->intr[grp]; + volatile rv32_intc_grp_t *event_grp = ®s->event[grp]; + unsigned int key; + + key = arch_irq_lock(); + int_grp->enable |= BIT(val); + event_grp->enable |= BIT(val); + arch_irq_unlock(key); +} + +void arch_irq_disable(unsigned int source) +{ + volatile rv32_intc_regs_t *regs = get_intc_regs(); + uint8_t grp = source / 32; + uint32_t val = source % 32; + volatile rv32_intc_grp_t *int_grp = ®s->intr[grp]; + volatile rv32_intc_grp_t *event_grp = ®s->event[grp]; + unsigned int key; + + key = arch_irq_lock(); + int_grp->enable &= ~BIT(val); + event_grp->enable &= ~BIT(val); + arch_irq_unlock(key); +} + +int arch_irq_is_enabled(unsigned int source) +{ + volatile rv32_intc_regs_t *regs = get_intc_regs(); + uint8_t grp = source / 32; + uint32_t val = source % 32; + volatile rv32_intc_grp_t *int_grp = ®s->intr[grp]; + volatile rv32_intc_grp_t *event_grp = ®s->event[grp]; + unsigned int key; + int ret; + + key = arch_irq_lock(); + ret = (int_grp->enable & BIT(val)) & (event_grp->enable & BIT(val)); + arch_irq_unlock(key); + + return ret; +} + +void intc_max32_rv32_irq_clear_pending(int source) +{ + volatile rv32_intc_regs_t *regs = get_intc_regs(); + uint8_t grp = source / 32; + uint32_t val = source % 32; + volatile rv32_intc_grp_t *int_grp = ®s->intr[grp]; + volatile rv32_intc_grp_t *event_grp = ®s->event[grp]; + unsigned int key; + + key = arch_irq_lock(); + int_grp->clear_pending |= BIT(val); + event_grp->clear_pending |= BIT(val); + arch_irq_unlock(key); +} + +uint32_t max32_rv32_intc_get_next_source(void) +{ + volatile rv32_intc_regs_t *regs = get_intc_regs(); + volatile rv32_intc_grp_t *int_grp = ®s->intr[0]; + volatile rv32_intc_grp_t *evt_grp = ®s->event[0]; + uint32_t status; + uint32_t source; + uint32_t clear; + + status = int_grp->pending & int_grp->enable; + + if (status) { + clear = source = __builtin_ffs(status) - 1; + } else { + int_grp = ®s->intr[1]; + evt_grp = ®s->event[1]; + status = int_grp->pending & int_grp->enable; + + if (status) { + clear = __builtin_ffs(status) - 1; + source = (clear + 32); + } else { + clear = 0; + source = 0; + printk("No pending interrupt lines!\n"); + } + } + + int_grp->clear_pending |= BIT(clear); + evt_grp->clear_pending |= BIT(clear); + + return source; +} + +static int max32_rv32_intc_init(const struct device *dev) +{ + return 0; +} + +DEVICE_DT_INST_DEFINE(0, max32_rv32_intc_init, NULL, NULL, NULL, PRE_KERNEL_1, + CONFIG_INTC_INIT_PRIORITY, NULL); diff --git a/drivers/serial/Kconfig.max32 b/drivers/serial/Kconfig.max32 index 31aa5c2f2cb20..df95632acefc8 100644 --- a/drivers/serial/Kconfig.max32 +++ b/drivers/serial/Kconfig.max32 @@ -10,7 +10,7 @@ config UART_MAX32 select SERIAL_HAS_DRIVER select SERIAL_SUPPORT_INTERRUPT select PINCTRL - select SERIAL_SUPPORT_ASYNC if DT_HAS_ADI_MAX32_DMA_ENABLED + select SERIAL_SUPPORT_ASYNC if DT_HAS_ADI_MAX32_DMA_ENABLED && !SOC_FAMILY_MAX32_RV32 select DMA if UART_ASYNC_API help This option enables the UART driver for MAX32 family of diff --git a/drivers/timer/CMakeLists.txt b/drivers/timer/CMakeLists.txt index 0291ce07d2a6b..d9098c2bacf68 100644 --- a/drivers/timer/CMakeLists.txt +++ b/drivers/timer/CMakeLists.txt @@ -21,6 +21,7 @@ zephyr_library_sources_ifdef(CONFIG_ITE_IT51XXX_TIMER ite_it51xxx_timer.c) zephyr_library_sources_ifdef(CONFIG_ITE_IT8XXX2_TIMER ite_it8xxx2_timer.c) zephyr_library_sources_ifdef(CONFIG_LEON_GPTIMER leon_gptimer.c) zephyr_library_sources_ifdef(CONFIG_LITEX_TIMER litex_timer.c) +zephyr_library_sources_ifdef(CONFIG_MAX32_RV32_SYS_TIMER max32_rv32_sys_timer.c) zephyr_library_sources_ifdef(CONFIG_MCHP_XEC_RTOS_TIMER mchp_xec_rtos_timer.c) zephyr_library_sources_ifdef(CONFIG_MCHP_SAM_PIT64B_TIMER mchp_sam_pit64b_timer.c) zephyr_library_sources_ifdef(CONFIG_MCUX_LPTMR_TIMER mcux_lptmr_timer.c) diff --git a/drivers/timer/Kconfig b/drivers/timer/Kconfig index 1ebd267622877..0c26e57dbd9dc 100644 --- a/drivers/timer/Kconfig +++ b/drivers/timer/Kconfig @@ -78,6 +78,7 @@ source "drivers/timer/Kconfig.it51xxx" source "drivers/timer/Kconfig.ite_it8xxx2" source "drivers/timer/Kconfig.leon_gptimer" source "drivers/timer/Kconfig.litex" +source "drivers/timer/Kconfig.max32_rv32_sys_timer" source "drivers/timer/Kconfig.mchp_xec_rtos" source "drivers/timer/Kconfig.mchp_sam" source "drivers/timer/Kconfig.mcux_gpt" diff --git a/drivers/timer/Kconfig.max32_rv32_sys_timer b/drivers/timer/Kconfig.max32_rv32_sys_timer new file mode 100644 index 0000000000000..824aef1ed7e6f --- /dev/null +++ b/drivers/timer/Kconfig.max32_rv32_sys_timer @@ -0,0 +1,12 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +config MAX32_RV32_SYS_TIMER + bool "ADI MAX32 RV32 system timer driver" + default y + select TICKLESS_CAPABLE + depends on DT_HAS_ADI_MAX32_RV32_SYS_TIMER_ENABLED + help + This module implements a kernel device driver for using a MAX32 timer + peripheral as the system clock for the RV32 core. It provides the + standard "system clock driver" interfaces. diff --git a/drivers/timer/max32_rv32_sys_timer.c b/drivers/timer/max32_rv32_sys_timer.c new file mode 100644 index 0000000000000..2c56b3a4649c6 --- /dev/null +++ b/drivers/timer/max32_rv32_sys_timer.c @@ -0,0 +1,200 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#define DT_DRV_COMPAT adi_max32_rv32_sys_timer + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#if defined(CONFIG_TEST) +const int32_t z_sys_timer_irq_for_test = DT_INST_IRQN(0); +#endif + +#define CYC_PER_SEC sys_clock_hw_cycles_per_sec() +#define CYC_PER_TICK (CYC_PER_SEC / CONFIG_SYS_CLOCK_TICKS_PER_SEC / DT_INST_PROP(0, prescaler)) + +static mxc_tmr_regs_t *regs = (mxc_tmr_regs_t *)DT_INST_REG_ADDR(0); + +static const struct max32_perclk perclk = { + .bus = DT_INST_CLOCKS_CELL(0, offset), + .bit = DT_INST_CLOCKS_CELL(0, bit), +}; + +#define TIMER_CLOCK DEVICE_DT_GET(DT_INST_CLOCKS_CTLR(0)) +#define PRESCALER DT_INST_PROP(0, prescaler) + +#define COMPARE_VAL ((CYC_PER_TICK)) +#define MAX_TIMEOUT ((UINT32_MAX / COMPARE_VAL) - 1) + +static struct k_spinlock lock; +static uint32_t last_cycle; +static uint32_t last_tick; +static uint32_t last_elapsed; + +#define CYCLE_DIFF_MAX (~(uint32_t)0) + +#define CYCLES_MAX_1 ((uint64_t)INT32_MAX * (uint64_t)CYC_PER_TICK) +#define CYCLES_MAX_2 ((uint64_t)CYCLE_DIFF_MAX) +#define CYCLES_MAX_3 MIN(CYCLES_MAX_1, CYCLES_MAX_2) +#define CYCLES_MAX_4 (CYCLES_MAX_3 / 2 + CYCLES_MAX_3 / 4) +#define CYCLES_MAX_5 (CYCLES_MAX_4 + LSB_GET(CYCLES_MAX_4)) + +#define CYCLES_MAX CYCLES_MAX_5 + +#if PRESCALER == 0 +#define PRES_VAL TMR_PRES_1 +#else +#define PRES_VAL CONCAT(TMR_PRES_, PRESCALER) +#endif + +static void rv32_sys_timer_irq_handler(const struct device *unused) +{ + ARG_UNUSED(unused); + k_spinlock_key_t key; + + key = k_spin_lock(&lock); + + uint32_t curr_cycle = MXC_TMR_GetCount(regs); + uint32_t delta_cycles = curr_cycle - last_cycle; + uint32_t delta_ticks = (uint32_t)delta_cycles / CYC_PER_TICK; + + last_cycle += (uint32_t)delta_ticks * CYC_PER_TICK; + last_tick += delta_ticks; + last_elapsed = 0; + + MXC_TMR_ClearFlags(regs); + /* The IRQ will re-assert until the flags on the timer are cleared. */ + intc_max32_rv32_irq_clear_pending(DT_INST_IRQN(0)); + +#if !IS_ENABLED(CONFIG_TICKLESS_KERNEL) + MXC_TMR_SetCompare(regs, last_cycle + CYC_PER_TICK); +#endif + + k_spin_unlock(&lock, key); + + sys_clock_announce(IS_ENABLED(CONFIG_TICKLESS_KERNEL) ? delta_ticks : 1); +} + +uint32_t sys_clock_cycle_get_32(void) +{ + return MXC_TMR_GetCount(regs) * DT_INST_PROP(0, prescaler); +} + +uint32_t sys_clock_elapsed(void) +{ + if (!IS_ENABLED(CONFIG_TICKLESS_KERNEL)) { + return 0; + } + + uint32_t curr_cycle = MXC_TMR_GetCount(regs); + k_spinlock_key_t key = k_spin_lock(&lock); + + int32_t delta_cycles = curr_cycle - last_cycle; + int32_t delta_ticks = (uint32_t)delta_cycles / CYC_PER_TICK; + + last_elapsed = delta_ticks; + k_spin_unlock(&lock, key); + + return delta_ticks; +} + +void sys_clock_set_timeout(int32_t ticks, bool idle) +{ + if (!IS_ENABLED(CONFIG_TICKLESS_KERNEL)) { + return; + } + + if (idle && ticks == K_TICKS_FOREVER) { + return; + } + + k_spinlock_key_t key = k_spin_lock(&lock); + uint32_t next_cycle; + uint32_t count; + + if (ticks == INT32_MAX) { + next_cycle = (last_tick * CYC_PER_TICK) + CYCLES_MAX; + } else if (ticks == 0) { + next_cycle = MXC_TMR_GetCount(regs) + (CYC_PER_TICK * 3 / 2); + next_cycle -= (next_cycle % CYC_PER_TICK); + } else { + next_cycle = (last_tick + last_elapsed + ticks) * CYC_PER_TICK; + if ((next_cycle - last_cycle) > CYCLES_MAX) { + next_cycle = (last_tick * CYC_PER_TICK) + CYCLES_MAX; + } else { + count = MXC_TMR_GetCount(regs); + if (next_cycle < count) { + ticks = DIV_ROUND_UP(count - next_cycle, CYC_PER_TICK); + ticks += 1; + next_cycle += ticks * CYC_PER_TICK; + } else if (next_cycle - count < CYC_PER_TICK / 6) { + next_cycle += CYC_PER_TICK; + } + } + } + + MXC_TMR_SetCompare(regs, next_cycle); + k_spin_unlock(&lock, key); +} + +static int sys_clock_driver_init(void) +{ + wrap_mxc_tmr_cfg_t tmr_cfg; + int ret; + + IRQ_CONNECT(DT_INST_IRQN(0), 0, rv32_sys_timer_irq_handler, NULL, 0); + + tmr_cfg.pres = PRES_VAL; + tmr_cfg.mode = TMR_MODE_COMPARE; +#if IS_ENABLED(CONFIG_TICKLESS_KERNEL) + tmr_cfg.cmp_cnt = (MAX_TIMEOUT * COMPARE_VAL); +#else + tmr_cfg.cmp_cnt = COMPARE_VAL; +#endif + + tmr_cfg.bitMode = 0; /* Timer Mode 32 bit */ + tmr_cfg.pol = 0; + + tmr_cfg.clock = Wrap_MXC_TMR_GetClockIndex(DT_INST_PROP(0, clock_source)); + if (tmr_cfg.clock < 0) { + return -ENOTSUP; + } + + MXC_TMR_Shutdown(regs); + + /* enable clock */ + ret = clock_control_on(TIMER_CLOCK, (clock_control_subsys_t)&perclk); + if (ret) { + return ret; + } + + ret = Wrap_MXC_TMR_Init(regs, &tmr_cfg); + if (ret != E_NO_ERROR) { + return ret; + } + + /* Be sure our start point is 0x0, not 0x1 as set on reset. */ + MXC_TMR_SetCount(regs, 0); + + MXC_TMR_ClearFlags(regs); + Wrap_MXC_TMR_EnableInt(regs); + + MXC_TMR_Start(regs); + + irq_enable(DT_INST_IRQN(0)); + + return 0; +} + +SYS_INIT(sys_clock_driver_init, PRE_KERNEL_2, CONFIG_SYSTEM_CLOCK_INIT_PRIORITY); diff --git a/dts/arm/adi/max32/max32650.dtsi b/dts/arm/adi/max32/max32650.dtsi index dda77562b8803..6ee37fa90f602 100644 --- a/dts/arm/adi/max32/max32650.dtsi +++ b/dts/arm/adi/max32/max32650.dtsi @@ -4,8 +4,8 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include &flash0 { @@ -56,6 +56,11 @@ /* MAX32650 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(32)>; + }; + sram1: memory@20008000 { compatible = "mmio-sram"; reg = <0x20008000 DT_SIZE_K(64)>; diff --git a/dts/arm/adi/max32/max32660.dtsi b/dts/arm/adi/max32/max32660.dtsi index 7aa175b7f8645..30fbe01c0f242 100644 --- a/dts/arm/adi/max32/max32660.dtsi +++ b/dts/arm/adi/max32/max32660.dtsi @@ -4,18 +4,14 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include &clk_ipo { clock-frequency = ; }; -&sram0 { - reg = <0x20000000 DT_SIZE_K(16)>; -}; - /delete-node/ &clk_iso; /delete-node/ &clk_ibro; /delete-node/ &clk_erfo; @@ -43,6 +39,11 @@ }; soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(16)>; + }; + sram1: memory@20004000 { compatible = "mmio-sram"; reg = <0x20004000 DT_SIZE_K(16)>; diff --git a/dts/arm/adi/max32/max32662.dtsi b/dts/arm/adi/max32/max32662.dtsi index fc2db2f348c52..88456d1b6c626 100644 --- a/dts/arm/adi/max32/max32662.dtsi +++ b/dts/arm/adi/max32/max32662.dtsi @@ -4,18 +4,14 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include &flash0 { reg = <0x10000000 DT_SIZE_K(256)>; }; -&sram0 { - reg = <0x20000000 DT_SIZE_K(16)>; -}; - /delete-node/ &clk_iso; /delete-node/ &gpio1; @@ -42,6 +38,11 @@ /* MAX32662 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(16)>; + }; + sram1: memory@20004000 { compatible = "mmio-sram"; reg = <0x20004000 DT_SIZE_K(16)>; diff --git a/dts/arm/adi/max32/max32666.dtsi b/dts/arm/adi/max32/max32666.dtsi index f21d13aa955dd..467e2e49c3543 100644 --- a/dts/arm/adi/max32/max32666.dtsi +++ b/dts/arm/adi/max32/max32666.dtsi @@ -4,8 +4,8 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include &clk_ipo { @@ -27,6 +27,11 @@ /* MAX32666 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(32)>; + }; + sram1: memory@20008000 { compatible = "mmio-sram"; reg = <0x20008000 DT_SIZE_K(32)>; diff --git a/dts/arm/adi/max32/max32670.dtsi b/dts/arm/adi/max32/max32670.dtsi index 8739bbbc981bf..136a1df723abb 100644 --- a/dts/arm/adi/max32/max32670.dtsi +++ b/dts/arm/adi/max32/max32670.dtsi @@ -4,14 +4,10 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include -&sram0 { - reg = <0x20000000 DT_SIZE_K(16)>; -}; - &flash0 { reg = <0x10000000 DT_SIZE_K(384)>; }; @@ -29,6 +25,11 @@ /* MAX32670 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(16)>; + }; + sram1: memory@20004000 { compatible = "mmio-sram"; reg = <0x20004000 DT_SIZE_K(16)>; diff --git a/dts/arm/adi/max32/max32672.dtsi b/dts/arm/adi/max32/max32672.dtsi index fa95941982a8b..06fa51eec6f84 100644 --- a/dts/arm/adi/max32/max32672.dtsi +++ b/dts/arm/adi/max32/max32672.dtsi @@ -4,13 +4,10 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include -&sram0 { - reg = <0x20000000 DT_SIZE_K(16)>; -}; &clk_inro { clock-frequency = ; @@ -38,6 +35,11 @@ /* MAX32672 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(16)>; + }; + sram1: memory@20004000 { compatible = "mmio-sram"; reg = <0x20004000 DT_SIZE_K(16)>; diff --git a/dts/arm/adi/max32/max32675.dtsi b/dts/arm/adi/max32/max32675.dtsi index 10065112d0f98..c8b9735240f96 100644 --- a/dts/arm/adi/max32/max32675.dtsi +++ b/dts/arm/adi/max32/max32675.dtsi @@ -4,18 +4,14 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include +#include #include &flash0 { reg = <0x10000000 DT_SIZE_K(384)>; }; -&sram0 { - reg = <0x20000000 DT_SIZE_K(16)>; -}; - &clk_inro { clock-frequency = ; }; @@ -31,6 +27,11 @@ /* MAX32675 extra peripherals. */ / { soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(16)>; + }; + sram1: memory@20004000 { compatible = "mmio-sram"; reg = <0x20004000 DT_SIZE_K(16)>; diff --git a/dts/bindings/cpu/adi,max32-rv32.yaml b/dts/bindings/cpu/adi,max32-rv32.yaml new file mode 100644 index 0000000000000..221791bba12fb --- /dev/null +++ b/dts/bindings/cpu/adi,max32-rv32.yaml @@ -0,0 +1,9 @@ +# Copyright (c) 2025 Analog Devices, Inc +# +# SPDX-License-Identifier: Apache-2.0 + +description: MAX32 RV32 core + +compatible: "adi,max32-rv32" + +include: ["riscv,cpus.yaml", "pinctrl-device.yaml"] diff --git a/dts/bindings/interrupt-controller/adi,max32-rv32-intc.yaml b/dts/bindings/interrupt-controller/adi,max32-rv32-intc.yaml new file mode 100644 index 0000000000000..c93197895898e --- /dev/null +++ b/dts/bindings/interrupt-controller/adi,max32-rv32-intc.yaml @@ -0,0 +1,16 @@ +description: MAX32 RV32 Core Interrupt Controller + +compatible: "adi,max32-rv32-intc" + +include: [base.yaml, interrupt-controller.yaml] + +properties: + reg: + required: true + + "#interrupt-cells": + const: 2 + +interrupt-cells: + - irq + - priority diff --git a/dts/bindings/timer/adi,max32-rv32-sys-timer.yaml b/dts/bindings/timer/adi,max32-rv32-sys-timer.yaml new file mode 100644 index 0000000000000..9a1441f005e76 --- /dev/null +++ b/dts/bindings/timer/adi,max32-rv32-sys-timer.yaml @@ -0,0 +1,18 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +description: ADI MAX32 RV32 system timer + +compatible: "adi,max32-rv32-sys-timer" + +include: ["adi,max32-timer-common.yaml"] + +properties: + clock-source: + enum: [6] + description: | + Clock source to be used by the timer peripheral. The following options + are available: + - 6: "ADI_MAX32_PRPH_CLK_SRC_ISO" Internal Secondary Oscillator + The system timer clock source needs to match the source for the RV32 + core. diff --git a/dts/bindings/timer/adi,max32-timer-common.yaml b/dts/bindings/timer/adi,max32-timer-common.yaml new file mode 100644 index 0000000000000..6636aec7ce153 --- /dev/null +++ b/dts/bindings/timer/adi,max32-timer-common.yaml @@ -0,0 +1,37 @@ +# Copyright (c) 2023-2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +description: ADI MAX32 timer common + +include: [base.yaml, reset-device.yaml] + +properties: + reg: + required: true + + clocks: + description: Source clock controller configuration + + clock-source: + type: int + + prescaler: + type: int + required: true + enum: + - 1 + - 2 + - 4 + - 8 + - 16 + - 32 + - 64 + - 128 + - 256 + - 512 + - 1024 + - 2048 + - 4096 + description: | + The prescaler that divides the timers source clock to set the timers count clock as follows: + F_cnt_clk = F_clock_source / prescaler diff --git a/dts/bindings/timer/adi,max32-timer.yaml b/dts/bindings/timer/adi,max32-timer.yaml index b73fcb907b841..1a0806fcf2f64 100644 --- a/dts/bindings/timer/adi,max32-timer.yaml +++ b/dts/bindings/timer/adi,max32-timer.yaml @@ -5,17 +5,10 @@ description: ADI MAX32 timer compatible: "adi,max32-timer" -include: [base.yaml, reset-device.yaml] +include: ["adi,max32-timer-common.yaml"] properties: - reg: - required: true - - clocks: - description: Source clock controller configuration - clock-source: - type: int enum: [0, 1, 2, 3, 4, 5, 6, 7] description: | Clock source to be used by the WDT peripheral. The following options @@ -30,24 +23,3 @@ properties: - 7: "ADI_MAX32_PRPH_CLK_SRC_IBRO_DIV8" IBRO/8 The target device might not support every option please take a look on target device user guide - - prescaler: - type: int - required: true - enum: - - 1 - - 2 - - 4 - - 8 - - 16 - - 32 - - 64 - - 128 - - 256 - - 512 - - 1024 - - 2048 - - 4096 - description: | - The prescaler that divides the timers source clock to set the timers count clock as follows: - F_cnt_clk = F_clock_source / prescaler diff --git a/dts/vendor/adi/max32/max32655-m4.dtsi b/dts/vendor/adi/max32/max32655-m4.dtsi new file mode 100644 index 0000000000000..c70777fbb358b --- /dev/null +++ b/dts/vendor/adi/max32/max32655-m4.dtsi @@ -0,0 +1,99 @@ +/* + * Copyright (c) 2023-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&gpio2 { + interrupts = <26 0>; +}; + +&gpio3 { + interrupts = <54 0>; +}; + +/* MAX32655 extra peripherals. */ +/ { + cpus { + cpu@0 { + cpu-power-states = <&idle &suspend &standby>; + }; + + power-states { + /* Standby Mode */ + standby: standby { + compatible = "zephyr,power-state"; + power-state-name = "standby"; + min-residency-us = <1000>; + /* Typical value is 14.7us as per of Datasheet */ + exit-latency-us = <30>; + }; + }; + }; + + soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(32)>; + }; + + sram1: memory@20008000 { + compatible = "mmio-sram"; + reg = <0x20008000 DT_SIZE_K(32)>; + }; + + sram2: memory@20010000 { + compatible = "mmio-sram"; + reg = <0x20010000 DT_SIZE_K(48)>; + }; + + spi0: spi@400be000 { + compatible = "adi,max32-spi"; + reg = <0x400be000 0x1000>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; + interrupts = <56 0>; + status = "disabled"; + }; + }; +}; + +&uart3 { + interrupts = <88 0>; +}; + +&wdt1 { + interrupts = <57 0>; +}; + +&spi0 { + interrupts = <56 0>; +}; + +&spi1 { + interrupts = <16 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&lptimer0 { + interrupts = <9 0>; +}; + +&lptimer1 { + interrupts = <10 0>; +}; + +&w1 { + interrupts = <67 0>; +}; + +&wut0 { + interrupts = <53 0>; +}; diff --git a/dts/arm/adi/max32/max32655-pinctrl.dtsi b/dts/vendor/adi/max32/max32655-pinctrl.dtsi similarity index 100% rename from dts/arm/adi/max32/max32655-pinctrl.dtsi rename to dts/vendor/adi/max32/max32655-pinctrl.dtsi diff --git a/dts/vendor/adi/max32/max32655-rv32.dtsi b/dts/vendor/adi/max32/max32655-rv32.dtsi new file mode 100644 index 0000000000000..e3dc497a85d3b --- /dev/null +++ b/dts/vendor/adi/max32/max32655-rv32.dtsi @@ -0,0 +1,48 @@ +/* + * Copyright (c) 2023-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&gpio2 { + interrupts = <27 0>; +}; + +&gpio3 { + interrupts = <6 0>; +}; + +&uart3 { + interrupts = <21 0>; +}; + +&wdt1 { + interrupts = <48 0>; +}; + +&spi1 { + interrupts = <22 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&lptimer0 { + interrupts = <12 0>; +}; + +&lptimer1 { + interrupts = <13 0>; +}; + +&w1 { + interrupts = <54 0>; +}; + +&wut0 { + interrupts = <23 0>; +}; diff --git a/dts/arm/adi/max32/max32655.dtsi b/dts/vendor/adi/max32/max32655.dtsi similarity index 83% rename from dts/arm/adi/max32/max32655.dtsi rename to dts/vendor/adi/max32/max32655.dtsi index 1a2a6e51939fa..916dabbbaf72e 100644 --- a/dts/arm/adi/max32/max32655.dtsi +++ b/dts/vendor/adi/max32/max32655.dtsi @@ -4,7 +4,6 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include #include @@ -33,24 +32,12 @@ /* MAX32655 extra peripherals. */ / { - cpus { - cpu@0 { - cpu-power-states = <&idle &suspend &standby>; - }; - - power-states { - /* Standby Mode */ - standby: standby { - compatible = "zephyr,power-state"; - power-state-name = "standby"; - min-residency-us = <1000>; - /* Typical value is 14.7us as per of Datasheet */ - exit-latency-us = <30>; - }; + soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(32)>; }; - }; - soc { sram1: memory@20008000 { compatible = "mmio-sram"; reg = <0x20008000 DT_SIZE_K(32)>; @@ -94,16 +81,6 @@ status = "disabled"; }; - spi0: spi@400be000 { - compatible = "adi,max32-spi"; - reg = <0x400be000 0x1000>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; - interrupts = <56 0>; - status = "disabled"; - }; - spi1: spi@40046000 { compatible = "adi,max32-spi"; reg = <0x40046000 0x1000>; diff --git a/dts/vendor/adi/max32/max32680-m4.dtsi b/dts/vendor/adi/max32/max32680-m4.dtsi new file mode 100644 index 0000000000000..fca6a63284cb7 --- /dev/null +++ b/dts/vendor/adi/max32/max32680-m4.dtsi @@ -0,0 +1,77 @@ +/* + * Copyright (c) 2024-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +/ { + soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(32)>; + }; + + sram1: memory@20008000 { + compatible = "mmio-sram"; + reg = <0x20008000 DT_SIZE_K(32)>; + }; + + sram2: memory@20010000 { + compatible = "mmio-sram"; + reg = <0x20010000 DT_SIZE_K(48)>; + }; + + spi0: spi@400be000 { + compatible = "adi,max32-spi"; + reg = <0x400be000 0x1000>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; + interrupts = <56 0>; + status = "disabled"; + }; + }; +}; + +&gpio2 { + interrupts = <26 0>; +}; + +&gpio3 { + interrupts = <54 0>; +}; + +&uart3 { + interrupts = <88 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&wdt1 { + interrupts = <57 0>; +}; + +&spi1 { + interrupts = <16 0>; +}; + +&lptimer0 { + interrupts = <9 0>; +}; + +&lptimer1 { + interrupts = <10 0>; +}; + +&w1 { + interrupts = <67 0>; +}; + +&wut0 { + interrupts = <53 0>; +}; diff --git a/dts/arm/adi/max32/max32680-pinctrl.dtsi b/dts/vendor/adi/max32/max32680-pinctrl.dtsi similarity index 100% rename from dts/arm/adi/max32/max32680-pinctrl.dtsi rename to dts/vendor/adi/max32/max32680-pinctrl.dtsi diff --git a/dts/vendor/adi/max32/max32680-rv32.dtsi b/dts/vendor/adi/max32/max32680-rv32.dtsi new file mode 100644 index 0000000000000..a33985c44f4de --- /dev/null +++ b/dts/vendor/adi/max32/max32680-rv32.dtsi @@ -0,0 +1,48 @@ +/* + * Copyright (c) 2024-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&gpio2 { + interrupts = <27 0>; +}; + +&gpio3 { + interrupts = <6 0>; +}; + +&uart3 { + interrupts = <21 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&wdt1 { + interrupts = <48 0>; +}; + +&spi1 { + interrupts = <22 0>; +}; + +&lptimer0 { + interrupts = <12 0>; +}; + +&lptimer1 { + interrupts = <13 0>; +}; + +&w1 { + interrupts = <54 0>; +}; + +&wut0 { + interrupts = <23 0>; +}; diff --git a/dts/arm/adi/max32/max32680.dtsi b/dts/vendor/adi/max32/max32680.dtsi similarity index 77% rename from dts/arm/adi/max32/max32680.dtsi rename to dts/vendor/adi/max32/max32680.dtsi index 154b2025796aa..b70bdc468155a 100644 --- a/dts/arm/adi/max32/max32680.dtsi +++ b/dts/vendor/adi/max32/max32680.dtsi @@ -4,7 +4,6 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include #include @@ -16,7 +15,6 @@ compatible = "adi,max32-gpio"; gpio-controller; #gpio-cells = <2>; - interrupts = <26 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 0>; status = "disabled"; }; @@ -26,23 +24,12 @@ compatible = "adi,max32-gpio"; gpio-controller; #gpio-cells = <2>; - interrupts = <54 0>; status = "disabled"; }; }; / { soc { - sram1: memory@20008000 { - compatible = "mmio-sram"; - reg = <0x20008000 DT_SIZE_K(32)>; - }; - - sram2: memory@20010000 { - compatible = "mmio-sram"; - reg = <0x20010000 DT_SIZE_K(48)>; - }; - sram3: memory@2001c000 { compatible = "mmio-sram"; reg = <0x2001c000 DT_SIZE_K(16)>; @@ -53,7 +40,6 @@ reg = <0x40081400 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 4>; clock-source = ; - interrupts = <88 0>; status = "disabled"; }; @@ -61,7 +47,6 @@ compatible = "adi,max32-dma"; reg = <0x40028000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 5>; - interrupts = <28 0>, <29 0>, <30 0>, <31 0>; dma-channels = <4>; status = "disabled"; #dma-cells = <2>; @@ -70,36 +55,23 @@ wdt1: watchdog@40080800 { compatible = "adi,max32-watchdog"; reg = <0x40080800 0x400>; - interrupts = <57 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 1>; clock-source = ; status = "disabled"; }; - spi0: spi@400be000 { - compatible = "adi,max32-spi"; - reg = <0x400be000 0x1000>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; - interrupts = <56 0>; - status = "disabled"; - }; - spi1: spi@40046000 { compatible = "adi,max32-spi"; reg = <0x40046000 0x1000>; #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 6>; - interrupts = <16 0>; status = "disabled"; }; lptimer0: timer@40080c00 { compatible = "adi,max32-timer"; reg = <0x40080c00 0x400>; - interrupts = <9 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 2>; clock-source = ; @@ -114,7 +86,6 @@ lptimer1: timer@40081000 { compatible = "adi,max32-timer"; reg = <0x40081000 0x400>; - interrupts = <10 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 3>; clock-source = ; @@ -130,14 +101,12 @@ compatible = "adi,max32-w1"; reg = <0x4003d000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 13>; - interrupts = <67 0>; status = "disabled"; }; wut0: timer@40006400 { compatible = "adi,max32-timer"; reg = <0x40006400 0x400>; - interrupts = <53 0>; status = "disabled"; prescaler = <1>; diff --git a/dts/vendor/adi/max32/max32690-m4.dtsi b/dts/vendor/adi/max32/max32690-m4.dtsi new file mode 100644 index 0000000000000..424e904cda95a --- /dev/null +++ b/dts/vendor/adi/max32/max32690-m4.dtsi @@ -0,0 +1,180 @@ +/* + * Copyright (c) 2023-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +/* MAX32690 extra peripherals. */ +/ { + soc { + sram0: memory@20000000 { + compatible = "mmio-sram"; + reg = <0x20000000 DT_SIZE_K(128)>; + }; + + sram1: memory@20020000 { + compatible = "mmio-sram"; + reg = <0x20020000 DT_SIZE_K(128)>; + }; + + sram2: memory@20040000 { + compatible = "mmio-sram"; + reg = <0x20040000 DT_SIZE_K(128)>; + }; + + sram3: memory@20060000 { + compatible = "mmio-sram"; + reg = <0x20060000 DT_SIZE_K(128)>; + }; + + sram4: memory@20080000 { + compatible = "mmio-sram"; + reg = <0x20080000 DT_SIZE_K(128)>; + }; + + sram5: memory@200a0000 { + compatible = "mmio-sram"; + reg = <0x200a0000 DT_SIZE_K(128)>; + }; + + sram6: memory@200c0000 { + compatible = "mmio-sram"; + reg = <0x200c0000 DT_SIZE_K(64)>; + }; + + sram7: memory@200d0000 { + compatible = "mmio-sram"; + reg = <0x200d0000 DT_SIZE_K(64)>; + }; + + spixf: spixf@40027000 { + compatible = "adi,max32-spixf"; + reg = <0x40027000 0x1000>; + + #address-cells = <1>; + #size-cells = <1>; + interrupts = <38 0>; + + clocks = <&gcr ADI_MAX32_CLOCK_BUS0 30>, <&gcr ADI_MAX32_CLOCK_BUS0 31>; + + status = "disabled"; + }; + + hpb: hpb@40039000 { + compatible = "adi,max32-hpb"; + reg = <0x40039000 0x1000>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 4 &gcr ADI_MAX32_CLOCK_BUS1 7>; + status = "disabled"; + }; + + spi3: spi@400be000 { + compatible = "adi,max32-spi"; + reg = <0x400be000 0x400>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; + interrupts = <56 0>; + status = "disabled"; + }; + + spi4: spi@400be400 { + compatible = "adi,max32-spi"; + reg = <0x400be400 0x400>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 17>; + interrupts = <105 0>; + status = "disabled"; + }; + + usbhs: usbhs@400b1000 { + compatible = "adi,max32-usbhs"; + reg = <0x400b1000 0x1000>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS0 3>; + interrupts = <2 0>; + num-bidir-endpoints = <1>; + num-in-endpoints = <6>; + num-out-endpoints = <7>; + maximum-speed = "high-speed"; + status = "disabled"; + }; + }; +}; + +&flash0 { + interrupts = <23 0>; +}; + +&gpio2 { + interrupts = <26 0>; +}; + +&gpio3 { + interrupts = <58 0>; +}; + +&gpio4 { + interrupts = <54 0>; +}; + +&flc1 { + status = "okay"; + interrupts = <87 0>; +}; + +&spi0 { + interrupts = <16 0>; +}; + +&spi1 { + interrupts = <17 0>; +}; + +&spi2 { + interrupts = <18 0>; +}; + +&uart3 { + interrupts = <88 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&wdt1 { + interrupts = <57 0>; +}; + +&lptimer0 { + interrupts = <9 0>; +}; + +&lptimer1 { + interrupts = <10 0>; +}; + +&w1 { + interrupts = <67 0>; +}; + +&can0 { + interrupts = <107 0>; +}; + +&can1 { + interrupts = <108 0>; +}; + +&wut0 { + interrupts = <53 0>; +}; + +&wut1 { + interrupts = <109 0>; +}; diff --git a/dts/arm/adi/max32/max32690-pinctrl.dtsi b/dts/vendor/adi/max32/max32690-pinctrl.dtsi similarity index 100% rename from dts/arm/adi/max32/max32690-pinctrl.dtsi rename to dts/vendor/adi/max32/max32690-pinctrl.dtsi diff --git a/dts/vendor/adi/max32/max32690-rv32.dtsi b/dts/vendor/adi/max32/max32690-rv32.dtsi new file mode 100644 index 0000000000000..207a98e54f402 --- /dev/null +++ b/dts/vendor/adi/max32/max32690-rv32.dtsi @@ -0,0 +1,76 @@ +/* + * Copyright (c) 2023-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&gpio2 { + interrupts = <56 0>; +}; + +&gpio3 { + interrupts = <23 0>; +}; + +&gpio4 { + interrupts = <2 0>; +}; + +&flc1 { + interrupts = <20 0>; +}; + +&spi0 { + interrupts = <18 0>; +}; + +&spi1 { + interrupts = <57 0>; +}; + +&spi2 { + interrupts = <58 0>; +}; + +&uart3 { + interrupts = <21 0>; +}; + +&dma0 { + interrupts = <24 0>, <25 0>, <26 0>, <27 0>; +}; + +&wdt1 { + interrupts = <44 0>; +}; + +&lptimer0 { + interrupts = <8 0>; +}; + +&lptimer1 { + interrupts = <9 0>; +}; + +&w1 { + interrupts = <50 0>; +}; + +&can0 { + interrupts = <54 0>; +}; + +&can1 { + interrupts = <59 0>; +}; + +&wut0 { + interrupts = <1 0>; +}; + +&wut1 { + interrupts = <44 0>; +}; diff --git a/dts/arm/adi/max32/max32690.dtsi b/dts/vendor/adi/max32/max32690.dtsi similarity index 66% rename from dts/arm/adi/max32/max32690.dtsi rename to dts/vendor/adi/max32/max32690.dtsi index 2e49774093d68..362cb384526f0 100644 --- a/dts/arm/adi/max32/max32690.dtsi +++ b/dts/vendor/adi/max32/max32690.dtsi @@ -4,7 +4,6 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include #include @@ -12,10 +11,6 @@ clock-frequency = ; }; -&sram0 { - reg = <0x20000000 DT_SIZE_K(128)>; -}; - &flash0 { reg = <0x10000000 DT_SIZE_M(3)>; erase-block-size = <16384>; @@ -68,61 +63,13 @@ /* MAX32690 extra peripherals. */ / { soc { - sram1: memory@20020000 { - compatible = "mmio-sram"; - reg = <0x20020000 DT_SIZE_K(128)>; - }; - - sram2: memory@20040000 { - compatible = "mmio-sram"; - reg = <0x20040000 DT_SIZE_K(128)>; - }; - - sram3: memory@20060000 { - compatible = "mmio-sram"; - reg = <0x20060000 DT_SIZE_K(128)>; - }; - - sram4: memory@20080000 { - compatible = "mmio-sram"; - reg = <0x20080000 DT_SIZE_K(128)>; - }; - - sram5: memory@200a0000 { - compatible = "mmio-sram"; - reg = <0x200a0000 DT_SIZE_K(128)>; - }; - - sram6: memory@200c0000 { - compatible = "mmio-sram"; - reg = <0x200c0000 DT_SIZE_K(64)>; - }; - - sram7: memory@200d0000 { - compatible = "mmio-sram"; - reg = <0x200d0000 DT_SIZE_K(192)>; - }; - - spixf: spixf@40027000 { - compatible = "adi,max32-spixf"; - reg = <0x40027000 0x1000>; - - #address-cells = <1>; - #size-cells = <1>; - interrupts = <38 0>; - - clocks = <&gcr ADI_MAX32_CLOCK_BUS0 30>, <&gcr ADI_MAX32_CLOCK_BUS0 31>; - - status = "disabled"; - }; - flc1: flash_controller@40029400 { compatible = "adi,max32-flash-controller"; reg = <0x40029400 0x400>; #address-cells = <1>; #size-cells = <1>; - status = "okay"; + status = "disabled"; flash1: flash@10300000 { compatible = "soc-nv-flash"; @@ -132,13 +79,10 @@ }; }; - hpb: hpb@40039000 { - compatible = "adi,max32-hpb"; - reg = <0x40039000 0x1000>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 4 &gcr ADI_MAX32_CLOCK_BUS1 7>; - status = "disabled"; + // SRAM8 is accessible to either core + sram8: memory@20100000 { + compatible = "mmio-sram"; + reg = <0x20100000 DT_SIZE_K(128)>; }; spi0: spi@40046000 { @@ -147,7 +91,6 @@ #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 6>; - interrupts = <16 0>; status = "disabled"; }; @@ -157,7 +100,6 @@ #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 7>; - interrupts = <17 0>; status = "disabled"; }; @@ -167,27 +109,6 @@ #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 8>; - interrupts = <18 0>; - status = "disabled"; - }; - - spi3: spi@400be000 { - compatible = "adi,max32-spi"; - reg = <0x400be000 0x400>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; - interrupts = <56 0>; - status = "disabled"; - }; - - spi4: spi@400be400 { - compatible = "adi,max32-spi"; - reg = <0x400be400 0x400>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 17>; - interrupts = <105 0>; status = "disabled"; }; @@ -196,7 +117,6 @@ reg = <0x40081400 0x400>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 4>; clock-source = ; - interrupts = <88 0>; status = "disabled"; }; @@ -213,7 +133,6 @@ wdt1: watchdog@40080800 { compatible = "adi,max32-watchdog"; reg = <0x40080800 0x400>; - interrupts = <57 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 1>; clock-source = ; status = "disabled"; @@ -222,7 +141,6 @@ lptimer0: timer@40080c00 { compatible = "adi,max32-timer"; reg = <0x40080c00 0x400>; - interrupts = <9 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 2>; clock-source = ; @@ -237,7 +155,6 @@ lptimer1: timer@40081000 { compatible = "adi,max32-timer"; reg = <0x40081000 0x400>; - interrupts = <10 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 3>; clock-source = ; @@ -253,19 +170,6 @@ compatible = "adi,max32-w1"; reg = <0x4003d000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 13>; - interrupts = <67 0>; - status = "disabled"; - }; - - usbhs: usbhs@400b1000 { - compatible = "adi,max32-usbhs"; - reg = <0x400b1000 0x1000>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS0 3>; - interrupts = <2 0>; - num-bidir-endpoints = <1>; - num-in-endpoints = <6>; - num-out-endpoints = <7>; - maximum-speed = "high-speed"; status = "disabled"; }; @@ -273,7 +177,6 @@ compatible = "adi,max32-can"; reg = <0x40064000 0x1000>; status = "disabled"; - interrupts = <107 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 11>; }; @@ -281,14 +184,12 @@ compatible = "adi,max32-can"; reg = <0x40065000 0x1000>; status = "disabled"; - interrupts = <108 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 19>; }; wut0: timer@40006400 { compatible = "adi,max32-timer"; reg = <0x40006400 0x200>; - interrupts = <53 0>; status = "disabled"; prescaler = <1>; @@ -301,7 +202,6 @@ wut1: timer@40006600 { compatible = "adi,max32-timer"; reg = <0x40006600 0x200>; - interrupts = <109 0>; status = "disabled"; prescaler = <1>; diff --git a/dts/vendor/adi/max32/max32xxx-m4.dtsi b/dts/vendor/adi/max32/max32xxx-m4.dtsi new file mode 100644 index 0000000000000..de5dd013bc4a5 --- /dev/null +++ b/dts/vendor/adi/max32/max32xxx-m4.dtsi @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include + +&i2c0 { + interrupts = <13 0>; +}; + +&i2c1 { + interrupts = <36 0>; +}; + +&i2c2 { + interrupts = <62 0>; +}; + +&gpio0 { + interrupts = <24 0>; +}; + +&gpio1 { + interrupts = <25 0>; +}; + +&uart0 { + interrupts = <14 0>; +}; + +&uart1 { + interrupts = <15 0>; +}; + +&uart2 { + interrupts = <34 0>; +}; + +&wdt0 { + interrupts = <1 0>; +}; + +&adc { + interrupts = <20 0>; +}; + +&timer0 { + interrupts = <5 0>; +}; + +&timer1 { + interrupts = <6 0>; +}; + +&timer2 { + interrupts = <7 0>; +}; + +&timer3 { + interrupts = <8 0>; +}; + +&rtc_counter { + interrupts = <3 0>; +}; + +&flc0 { + status = "okay"; +}; + +&nvic { + arm,num-irq-priority-bits = <3>; +}; diff --git a/dts/vendor/adi/max32/max32xxx-rv32.dtsi b/dts/vendor/adi/max32/max32xxx-rv32.dtsi new file mode 100644 index 0000000000000..da79f99ef9053 --- /dev/null +++ b/dts/vendor/adi/max32/max32xxx-rv32.dtsi @@ -0,0 +1,88 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/delete-node/ &cpu0; + +/ { + #address-cells = <1>; + #size-cells = <1>; + + soc { + compatible = "simple-bus"; + + interrupt-parent = <&intc>; + intc: intc@e5070000 { + #address-cells = <1>; + compatible = "adi,max32-rv32-intc"; + reg = <0xe5070000 0x100>; + interrupt-controller; + #interrupt-cells = <2>; + }; + }; +}; + +&i2c0 { + interrupts = <14 0>; +}; + +&i2c1 { + interrupts = <17 0>; +}; + +&i2c2 { + interrupts = <20 0>; +}; + +&gpio0 { + interrupts = <25 0>; +}; + +&gpio1 { + interrupts = <26 0>; +}; + +&uart0 { + interrupts = <15 0>; +}; + +&uart1 { + interrupts = <18 0>; +}; + +&uart2 { + interrupts = <19 0>; +}; + +&wdt0 { + interrupts = <5 0>; +}; + +&adc { + interrupts = <53 0>; +}; + +&timer0 { + interrupts = <8 0>; +}; + +&timer1 { + interrupts = <9 0>; +}; + +&timer2 { + interrupts = <10 0>; +}; + +rv32_sys_timer: &timer3 { + compatible = "adi,max32-rv32-sys-timer"; + interrupts = <11 0>; + prescaler = <1>; + clock-source = <6>; +}; + +&rtc_counter { + interrupts = <7 0>; +}; diff --git a/dts/arm/adi/max32/max32xxx.dtsi b/dts/vendor/adi/max32/max32xxx.dtsi similarity index 93% rename from dts/arm/adi/max32/max32xxx.dtsi rename to dts/vendor/adi/max32/max32xxx.dtsi index d4c7193fd133e..67015968a5420 100644 --- a/dts/arm/adi/max32/max32xxx.dtsi +++ b/dts/vendor/adi/max32/max32xxx.dtsi @@ -29,6 +29,13 @@ cpu-power-states = <&idle &suspend>; }; + cpu1: cpu@1 { + device_type = "cpu"; + compatible = "adi,max32-rv32", "riscv"; + riscv,isa = "rv32imc_zicsr_zifencei"; + reg = <1>; + }; + power-states { /* Sleep Mode */ idle: idle { @@ -95,10 +102,8 @@ }; soc { - sram0: memory@20000000 { - compatible = "mmio-sram"; - reg = <0x20000000 DT_SIZE_K(32)>; - }; + #address-cells = <1>; + #size-cells = <1>; flc0: flash_controller@40029000 { compatible = "adi,max32-flash-controller"; @@ -106,7 +111,7 @@ #address-cells = <1>; #size-cells = <1>; - status = "okay"; + status = "disabled"; flash0: flash@10000000 { compatible = "soc-nv-flash"; @@ -132,7 +137,6 @@ #size-cells = <0>; clock-frequency = ; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 13>; - interrupts = <13 0>; status = "disabled"; }; @@ -143,7 +147,6 @@ #size-cells = <0>; clock-frequency = ; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 28>; - interrupts = <36 0>; status = "disabled"; }; @@ -154,7 +157,6 @@ #size-cells = <0>; clock-frequency = ; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 24>; - interrupts = <62 0>; status = "disabled"; }; @@ -170,7 +172,6 @@ gpio-controller; #gpio-cells = <2>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 0>; - interrupts = <24 0>; status = "disabled"; }; @@ -179,18 +180,24 @@ compatible = "adi,max32-gpio"; gpio-controller; #gpio-cells = <2>; - interrupts = <25 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 1>; status = "disabled"; }; }; + mbox: mbox@4003e000 { + compatible = "adi,mbox-max32-semaphore"; + reg = <0x4003e000 0x1000>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 9>; + #mbox-cells = <1>; + status = "disabled"; + }; + uart0: serial@40042000 { compatible = "adi,max32-uart"; reg = <0x40042000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 9>; clock-source = ; - interrupts = <14 0>; status = "disabled"; }; @@ -199,7 +206,6 @@ reg = <0x40043000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 10>; clock-source = ; - interrupts = <15 0>; status = "disabled"; }; @@ -208,7 +214,6 @@ reg = <0x40044000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 1>; clock-source = ; - interrupts = <34 0>; status = "disabled"; }; @@ -222,7 +227,6 @@ wdt0: watchdog@40003000 { compatible = "adi,max32-watchdog"; reg = <0x40003000 0x400>; - interrupts = <1 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 27>; clock-source = ; status = "disabled"; @@ -234,7 +238,6 @@ clocks = <&gcr ADI_MAX32_CLOCK_BUS0 23>; channel-count = <17>; #io-channel-cells = <1>; - interrupts = <20 0>; resolution = <10>; vref-mv = <1220>; status = "disabled"; @@ -243,7 +246,6 @@ timer0: timer@40010000 { compatible = "adi,max32-timer"; reg = <0x40010000 0x1000>; - interrupts = <5 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 15>; clock-source = ; @@ -264,7 +266,6 @@ timer1: timer@40011000 { compatible = "adi,max32-timer"; reg = <0x40011000 0x1000>; - interrupts = <6 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 16>; clock-source = ; @@ -285,7 +286,6 @@ timer2: timer@40012000 { compatible = "adi,max32-timer"; reg = <0x40012000 0x1000>; - interrupts = <7 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 17>; clock-source = ; @@ -306,7 +306,6 @@ timer3: timer@40013000 { compatible = "adi,max32-timer"; reg = <0x40013000 0x1000>; - interrupts = <8 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 18>; clock-source = ; @@ -327,12 +326,7 @@ rtc_counter: rtc_counter@40006000 { compatible = "adi,max32-rtc-counter"; reg = <0x40006000 0x400>; - interrupts = <3 0>; status = "disabled"; }; }; }; - -&nvic { - arm,num-irq-priority-bits = <3>; -}; diff --git a/dts/vendor/adi/max32/max78000-m4.dtsi b/dts/vendor/adi/max32/max78000-m4.dtsi new file mode 100644 index 0000000000000..3a78977211283 --- /dev/null +++ b/dts/vendor/adi/max32/max78000-m4.dtsi @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&flash0 { + interrupts = <23 0>; + reg = <0x10000000 DT_SIZE_K(512)>; + erase-block-size = <8192>; +}; + +&gpio2 { + interrupts = <26 0>; +}; + +&gpio3 { + interrupts = <54 0>; +}; + +/* MAX78000 extra peripherals. */ +/ { + soc { + sram1: memory@20008000 { + compatible = "mmio-sram"; + reg = <0x20008000 DT_SIZE_K(32)>; + }; + + sram2: memory@20010000 { + compatible = "mmio-sram"; + reg = <0x20010000 DT_SIZE_K(48)>; + }; + + spi0: spi@400be000 { + compatible = "adi,max32-spi"; + reg = <0x400be000 0x400>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; + interrupts = <56 0>; + status = "disabled"; + }; + }; +}; + +&spi1 { + interrupts = <16 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&w1 { + interrupts = <67 0>; +}; + +&wdt1 { + interrupts = <57 0>; +}; + +&lptimer0 { + interrupts = <9 0>; +}; + +&lptimer1 { + interrupts = <10 0>; +}; diff --git a/dts/arm/adi/max32/max78000-pinctrl.dtsi b/dts/vendor/adi/max32/max78000-pinctrl.dtsi similarity index 100% rename from dts/arm/adi/max32/max78000-pinctrl.dtsi rename to dts/vendor/adi/max32/max78000-pinctrl.dtsi diff --git a/dts/vendor/adi/max32/max78000-rv32.dtsi b/dts/vendor/adi/max32/max78000-rv32.dtsi new file mode 100644 index 0000000000000..ba066add0e9fe --- /dev/null +++ b/dts/vendor/adi/max32/max78000-rv32.dtsi @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&flash0 { + interrupts = <24 0>; +}; + +&gpio2 { + interrupts = <27 0>; +}; + +&gpio3 { + interrupts = <6 0>; +}; + +&spi1 { + interrupts = <22 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&w1 { + interrupts = <54 0>; +}; + +&wdt1 { + interrupts = <48 0>; +}; + +&lptimer0 { + interrupts = <12 0>; +}; + +&lptimer1 { + interrupts = <13 0>; +}; diff --git a/dts/arm/adi/max32/max78000.dtsi b/dts/vendor/adi/max32/max78000.dtsi similarity index 82% rename from dts/arm/adi/max32/max78000.dtsi rename to dts/vendor/adi/max32/max78000.dtsi index ceec6ec19b5a8..f66494bdd9cb0 100644 --- a/dts/arm/adi/max32/max78000.dtsi +++ b/dts/vendor/adi/max32/max78000.dtsi @@ -44,16 +44,6 @@ /* MAX78000 extra peripherals. */ / { soc { - sram1: memory@20008000 { - compatible = "mmio-sram"; - reg = <0x20008000 DT_SIZE_K(32)>; - }; - - sram2: memory@20010000 { - compatible = "mmio-sram"; - reg = <0x20010000 DT_SIZE_K(48)>; - }; - sram3: memory@2001c000 { compatible = "mmio-sram"; reg = <0x2001c000 DT_SIZE_K(16)>; @@ -64,17 +54,6 @@ reg = <0x40081400 0x400>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 4>; clock-source = ; - interrupts = <88 0>; - status = "disabled"; - }; - - spi0: spi@400be000 { - compatible = "adi,max32-spi"; - reg = <0x400be000 0x400>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; - interrupts = <56 0>; status = "disabled"; }; @@ -84,7 +63,6 @@ #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 6>; - interrupts = <16 0>; status = "disabled"; }; @@ -92,7 +70,6 @@ compatible = "adi,max32-dma"; reg = <0x40028000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 5>; - interrupts = <28 0>, <29 0>, <30 0>, <31 0>; dma-channels = <4>; status = "disabled"; #dma-cells = <2>; @@ -102,14 +79,12 @@ compatible = "adi,max32-w1"; reg = <0x4003d000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 13>; - interrupts = <67 0>; status = "disabled"; }; wdt1: watchdog@40080800 { compatible = "adi,max32-watchdog"; reg = <0x40080800 0x400>; - interrupts = <57 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 1>; clock-source = ; status = "disabled"; @@ -118,7 +93,6 @@ lptimer0: timer@40080c00 { compatible = "adi,max32-timer"; reg = <0x40080c00 0x400>; - interrupts = <9 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 2>; clock-source = ; @@ -141,7 +115,6 @@ lptimer1: timer@40081000 { compatible = "adi,max32-timer"; reg = <0x40081000 0x400>; - interrupts = <10 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 3>; clock-source = ; diff --git a/dts/vendor/adi/max32/max78002-m4.dtsi b/dts/vendor/adi/max32/max78002-m4.dtsi new file mode 100644 index 0000000000000..c6e72d9eb5eb1 --- /dev/null +++ b/dts/vendor/adi/max32/max78002-m4.dtsi @@ -0,0 +1,82 @@ +/* + * Copyright (c) 2024-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&flash0 { + interrupts = <23 0>; +}; + +&gpio2 { + interrupts = <26 0>; +}; + +&gpio3 { + interrupts = <54 0>; +}; + +/* MAX78002 extra peripherals. */ +/ { + soc { + sram1: memory@20008000 { + compatible = "mmio-sram"; + reg = <0x20008000 DT_SIZE_K(32)>; + }; + + sram2: memory@20010000 { + compatible = "mmio-sram"; + reg = <0x20010000 DT_SIZE_K(64)>; + }; + + sram3: memory@20020000 { + compatible = "mmio-sram"; + reg = <0x20020000 DT_SIZE_K(64)>; + }; + + spi0: spi@400be000 { + compatible = "adi,max32-spi"; + reg = <0x400be000 0x1000>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; + interrupts = <56 0>; + status = "disabled"; + }; + }; +}; + +&uart3 { + interrupts = <88 0>; +}; + +&spi1 { + interrupts = <16 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&wdt1 { + interrupts = <57 0>; +}; + +&lptimer0 { + interrupts = <9 0>; +}; + +&lptimer1 { + interrupts = <10 0>; +}; + +&w1 { + interrupts = <67 0>; +}; + +&wut0 { + interrupts = <53 0>; +}; diff --git a/dts/arm/adi/max32/max78002-pinctrl.dtsi b/dts/vendor/adi/max32/max78002-pinctrl.dtsi similarity index 100% rename from dts/arm/adi/max32/max78002-pinctrl.dtsi rename to dts/vendor/adi/max32/max78002-pinctrl.dtsi diff --git a/dts/vendor/adi/max32/max78002-rv32.dtsi b/dts/vendor/adi/max32/max78002-rv32.dtsi new file mode 100644 index 0000000000000..7d9a166ee8901 --- /dev/null +++ b/dts/vendor/adi/max32/max78002-rv32.dtsi @@ -0,0 +1,52 @@ +/* + * Copyright (c) 2024-2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +&flash0 { + interrupts = <24 0>; +}; + +&gpio2 { + interrupts = <27 0>; +}; + +&gpio3 { + interrupts = <6 0>; +}; + +&uart3 { + interrupts = <21 0>; +}; + +&spi1 { + interrupts = <22 0>; +}; + +&dma0 { + interrupts = <28 0>, <29 0>, <30 0>, <31 0>; +}; + +&wdt1 { + interrupts = <48 0>; +}; + +&lptimer0 { + interrupts = <12 0>; +}; + +&lptimer1 { + interrupts = <13 0>; +}; + +&w1 { + interrupts = <54 0>; +}; + +&wut0 { + interrupts = <23 0>; +}; diff --git a/dts/arm/adi/max32/max78002.dtsi b/dts/vendor/adi/max32/max78002.dtsi similarity index 82% rename from dts/arm/adi/max32/max78002.dtsi rename to dts/vendor/adi/max32/max78002.dtsi index 4c017074a2b45..528ce9ad1d8fc 100644 --- a/dts/arm/adi/max32/max78002.dtsi +++ b/dts/vendor/adi/max32/max78002.dtsi @@ -4,7 +4,6 @@ * SPDX-License-Identifier: Apache-2.0 */ -#include #include #include @@ -50,7 +49,6 @@ compatible = "adi,max32-gpio"; gpio-controller; #gpio-cells = <2>; - interrupts = <26 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 0>; status = "disabled"; }; @@ -60,7 +58,6 @@ compatible = "adi,max32-gpio"; gpio-controller; #gpio-cells = <2>; - interrupts = <54 0>; status = "disabled"; }; }; @@ -79,20 +76,6 @@ /* MAX78002 extra peripherals. */ / { soc { - sram1: memory@20008000 { - compatible = "mmio-sram"; - reg = <0x20008000 DT_SIZE_K(32)>; - }; - - sram2: memory@20010000 { - compatible = "mmio-sram"; - reg = <0x20010000 DT_SIZE_K(64)>; - }; - - sram3: memory@20020000 { - compatible = "mmio-sram"; - reg = <0x20020000 DT_SIZE_K(64)>; - }; sram4: memory@20030000 { compatible = "mmio-sram"; @@ -119,17 +102,6 @@ reg = <0x40081400 0x400>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 4>; clock-source = ; - interrupts = <88 0>; - status = "disabled"; - }; - - spi0: spi@400be000 { - compatible = "adi,max32-spi"; - reg = <0x400be000 0x1000>; - #address-cells = <1>; - #size-cells = <0>; - clocks = <&gcr ADI_MAX32_CLOCK_BUS1 16>; - interrupts = <56 0>; status = "disabled"; }; @@ -139,7 +111,6 @@ #address-cells = <1>; #size-cells = <0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 6>; - interrupts = <16 0>; status = "disabled"; }; @@ -147,7 +118,6 @@ compatible = "adi,max32-dma"; reg = <0x40028000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS0 5>; - interrupts = <28 0>, <29 0>, <30 0>, <31 0>; dma-channels = <4>; status = "disabled"; #dma-cells = <2>; @@ -156,7 +126,6 @@ wdt1: watchdog@40080800 { compatible = "adi,max32-watchdog"; reg = <0x40080800 0x400>; - interrupts = <57 0>; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 1>; clock-source = ; status = "disabled"; @@ -165,7 +134,6 @@ lptimer0: timer@40080c00 { compatible = "adi,max32-timer"; reg = <0x40080c00 0x400>; - interrupts = <9 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 2>; clock-source = ; @@ -186,7 +154,6 @@ lptimer1: timer@40081000 { compatible = "adi,max32-timer"; reg = <0x40081000 0x400>; - interrupts = <10 0>; status = "disabled"; clocks = <&gcr ADI_MAX32_CLOCK_BUS2 3>; clock-source = ; @@ -208,14 +175,12 @@ compatible = "adi,max32-w1"; reg = <0x4003d000 0x1000>; clocks = <&gcr ADI_MAX32_CLOCK_BUS1 13>; - interrupts = <67 0>; status = "disabled"; }; wut0: timer@40006400 { compatible = "adi,max32-timer"; reg = <0x40006400 0x400>; - interrupts = <53 0>; status = "disabled"; prescaler = <1>; diff --git a/include/zephyr/drivers/interrupt_controller/intc_max32_rv32.h b/include/zephyr/drivers/interrupt_controller/intc_max32_rv32.h new file mode 100644 index 0000000000000..0e007e9d4c2c0 --- /dev/null +++ b/include/zephyr/drivers/interrupt_controller/intc_max32_rv32.h @@ -0,0 +1,17 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#ifndef ZEPHYR_DRIVERS_INTERRUPT_CONTROLLER_INTC_MAX32_RV32_H_ +#define ZEPHYR_DRIVERS_INTERRUPT_CONTROLLER_INTC_MAX32_RV32_H_ + +/** + * @brief Clear the pending interrupt line in the controller. + * + * @param source: the IRQ number to clear any pending status for. + */ +void intc_max32_rv32_irq_clear_pending(int source); + +#endif /* ZEPHYR_DRIVERS_INTERRUPT_CONTROLLER_INTC_MAX32_RV32_H_ */ diff --git a/lib/os/spsc_pbuf.c b/lib/os/spsc_pbuf.c index 748be9fc1be0d..53d3f7a41a8bc 100644 --- a/lib/os/spsc_pbuf.c +++ b/lib/os/spsc_pbuf.c @@ -5,6 +5,7 @@ */ #include +#include #include #include #include diff --git a/samples/sysbuild/hello_world/boards/max32655evkit_max32655_m4.conf b/samples/sysbuild/hello_world/boards/max32655evkit_max32655_m4.conf new file mode 100644 index 0000000000000..7d29b0e30f03c --- /dev/null +++ b/samples/sysbuild/hello_world/boards/max32655evkit_max32655_m4.conf @@ -0,0 +1,5 @@ +# Copyright (c) 2024 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +CONFIG_MAX32_SECONDARY_RV32=y +CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY=15000000 diff --git a/samples/sysbuild/hello_world/boards/max32690evkit_max32690_m4.conf b/samples/sysbuild/hello_world/boards/max32690evkit_max32690_m4.conf new file mode 100644 index 0000000000000..a8cfa094c7ad8 --- /dev/null +++ b/samples/sysbuild/hello_world/boards/max32690evkit_max32690_m4.conf @@ -0,0 +1,5 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +CONFIG_MAX32_SECONDARY_RV32=y +CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY=15000000 diff --git a/samples/sysbuild/hello_world/boards/max78002evkit_max78002_m4.conf b/samples/sysbuild/hello_world/boards/max78002evkit_max78002_m4.conf new file mode 100644 index 0000000000000..a8cfa094c7ad8 --- /dev/null +++ b/samples/sysbuild/hello_world/boards/max78002evkit_max78002_m4.conf @@ -0,0 +1,5 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +CONFIG_MAX32_SECONDARY_RV32=y +CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY=15000000 diff --git a/samples/sysbuild/hello_world/sample.yaml b/samples/sysbuild/hello_world/sample.yaml index 86eeea479c6f8..d0d779867e554 100644 --- a/samples/sysbuild/hello_world/sample.yaml +++ b/samples/sysbuild/hello_world/sample.yaml @@ -84,3 +84,27 @@ tests: extra_args: - SB_CONF_FILE=sysbuild/bl54l15u_dvk_nrf54l15_cpuflpr.conf - hello_world_SNIPPET=nordic-flpr + + sample.sysbuild.hello_world.max32655evkit_m4_rv32: + platform_allow: + - max32655evkit/max32655/m4 + integration_platforms: + - max32655evkit/max32655/m4 + extra_args: + - SB_CONF_FILE=sysbuild/max32655evkit_max32655_rv32.conf + + sample.sysbuild.hello_world.max32690evkit_m4_rv32: + platform_allow: + - max32690evkit/max32690/m4 + integration_platforms: + - max32690evkit/max32690/m4 + extra_args: + - SB_CONF_FILE=sysbuild/max32690evkit_max32690_rv32.conf + + sample.sysbuild.hello_world.max78002evkit_m4_rv32: + platform_allow: + - max78002evkit/max78002/m4 + integration_platforms: + - max78002evkit/max78002/m4 + extra_args: + - SB_CONF_FILE=sysbuild/max78002evkit_max78002_rv32.conf diff --git a/samples/sysbuild/hello_world/sysbuild/max32655evkit_max32655_rv32.conf b/samples/sysbuild/hello_world/sysbuild/max32655evkit_max32655_rv32.conf new file mode 100644 index 0000000000000..df3007d7e92f9 --- /dev/null +++ b/samples/sysbuild/hello_world/sysbuild/max32655evkit_max32655_rv32.conf @@ -0,0 +1,4 @@ +# Copyright (c) 2024 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +SB_CONFIG_REMOTE_BOARD="max32655evkit/max32655/rv32" diff --git a/samples/sysbuild/hello_world/sysbuild/max32690evkit_max32690_rv32.conf b/samples/sysbuild/hello_world/sysbuild/max32690evkit_max32690_rv32.conf new file mode 100644 index 0000000000000..14416308f8ba8 --- /dev/null +++ b/samples/sysbuild/hello_world/sysbuild/max32690evkit_max32690_rv32.conf @@ -0,0 +1,4 @@ +# Copyright (c) 2024 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +SB_CONFIG_REMOTE_BOARD="max32690evkit/max32690/rv32" diff --git a/samples/sysbuild/hello_world/sysbuild/max78002evkit_max78002_rv32.conf b/samples/sysbuild/hello_world/sysbuild/max78002evkit_max78002_rv32.conf new file mode 100644 index 0000000000000..2e36bfd2e9760 --- /dev/null +++ b/samples/sysbuild/hello_world/sysbuild/max78002evkit_max78002_rv32.conf @@ -0,0 +1,4 @@ +# Copyright (c) 2025 Analog Devices, Inc. +# SPDX-License-Identifier: Apache-2.0 + +SB_CONFIG_REMOTE_BOARD="max78002evkit/max78002/rv32" diff --git a/scripts/west_commands/runners/openocd.py b/scripts/west_commands/runners/openocd.py index 31014c06d3b07..dba2bc4a142cf 100644 --- a/scripts/west_commands/runners/openocd.py +++ b/scripts/west_commands/runners/openocd.py @@ -48,7 +48,8 @@ def to_num(number): class OpenOcdBinaryRunner(ZephyrBinaryRunner): '''Runner front-end for openocd.''' - def __init__(self, cfg, pre_init=None, reset_halt_cmd=DEFAULT_OPENOCD_RESET_HALT_CMD, + def __init__(self, cfg, pre_init=None, flash_pre_init=None, + reset_halt_cmd=DEFAULT_OPENOCD_RESET_HALT_CMD, pre_load=None, erase_cmd=None, load_cmd=None, verify_cmd=None, post_verify=None, do_verify=False, do_verify_only=False, do_erase=False, tui=None, config=None, serial=None, use_elf=None, @@ -96,6 +97,7 @@ def __init__(self, cfg, pre_init=None, reset_halt_cmd=DEFAULT_OPENOCD_RESET_HALT # openocd doesn't cope with Windows path names, so convert # them to POSIX style just to be sure. self.elf_name = Path(cfg.elf_file).as_posix() if cfg.elf_file else None + self.flash_pre_init = flash_pre_init or [] self.pre_init = pre_init or [] self.reset_halt_cmd = reset_halt_cmd self.pre_load = pre_load or [] @@ -146,6 +148,10 @@ def do_add_parser(cls, parser): parser.add_argument('--cmd-pre-init', action='append', help='''Command to run before calling init; may be given multiple times''') + parser.add_argument('--flash-cmd-pre-init', action='append', + help='''Command to run before calling init when performing a flash; + may be given multiple times; + When set, existing --cmd-pre-init will be ignored when flashing''') parser.add_argument('--cmd-reset-halt', default=DEFAULT_OPENOCD_RESET_HALT_CMD, help=f'''Command to run for resetting and halting the target, defaults to "{DEFAULT_OPENOCD_RESET_HALT_CMD}"''') @@ -206,7 +212,8 @@ def do_add_parser(cls, parser): def do_create(cls, cfg, args): return OpenOcdBinaryRunner( cfg, - pre_init=args.cmd_pre_init, reset_halt_cmd=args.cmd_reset_halt, + pre_init=args.cmd_pre_init, flash_pre_init=args.flash_cmd_pre_init, + reset_halt_cmd=args.cmd_reset_halt, pre_load=args.cmd_pre_load, erase_cmd=args.cmd_erase, load_cmd=args.cmd_load, verify_cmd=args.cmd_verify, post_verify=args.cmd_post_verify, do_verify=args.verify, do_verify_only=args.verify_only, do_erase=args.erase, @@ -288,9 +295,14 @@ def do_flash(self, **kwargs): pre_init_cmd = [] pre_load_cmd = [] post_verify_cmd = [] - for i in self.pre_init: - pre_init_cmd.append("-c") - pre_init_cmd.append(i) + if self.flash_pre_init: + for i in self.flash_pre_init: + pre_init_cmd.append("-c") + pre_init_cmd.append(i) + else: + for i in self.pre_init: + pre_init_cmd.append("-c") + pre_init_cmd.append(i) for i in self.pre_load: pre_load_cmd.append("-c") diff --git a/soc/adi/max32/CMakeLists.txt b/soc/adi/max32/CMakeLists.txt index 74b3b29698bf9..a479c3473a842 100644 --- a/soc/adi/max32/CMakeLists.txt +++ b/soc/adi/max32/CMakeLists.txt @@ -13,4 +13,12 @@ if(CONFIG_SOC_MAX78000 OR CONFIG_SOC_MAX78002) zephyr_linker_sources(SECTIONS max7800x.ld) endif() -set(SOC_LINKER_SCRIPT ${ZEPHYR_BASE}/include/zephyr/arch/arm/cortex_m/scripts/linker.ld CACHE INTERNAL "") +if(CONFIG_ARM) + set(SOC_LINKER_SCRIPT ${ZEPHYR_BASE}/include/zephyr/arch/arm/cortex_m/scripts/linker.ld CACHE INTERNAL "") +elseif(CONFIG_RISCV) + set(SOC_LINKER_SCRIPT ${ZEPHYR_BASE}/include/zephyr/arch/riscv/common/linker.ld CACHE INTERNAL "") + zephyr_sources( + soc_irq_rv32.S + vector_rv32.S + ) +endif() diff --git a/soc/adi/max32/Kconfig b/soc/adi/max32/Kconfig index 7b100cc7134d9..705747603c58d 100644 --- a/soc/adi/max32/Kconfig +++ b/soc/adi/max32/Kconfig @@ -4,7 +4,6 @@ # SPDX-License-Identifier: Apache-2.0 config SOC_FAMILY_MAX32 - select CLOCK_CONTROL select BUILD_OUTPUT_HEX select SOC_EARLY_INIT_HOOK select HAS_SEGGER_RTT if ZEPHYR_SEGGER_MODULE @@ -29,6 +28,20 @@ config SOC_FAMILY_MAX32_M4 select CPU_HAS_ARM_MPU select CPU_HAS_FPU select HAS_PM + select CLOCK_CONTROL + +config SOC_FAMILY_MAX32_RV32 + select RISCV + select RISCV_ISA_RV32I + select RISCV_ISA_EXT_M + select RISCV_ISA_EXT_ZICSR + select RISCV_ISA_EXT_ZIFENCEI + select ATOMIC_OPERATIONS_C + select INCLUDE_RESET_VECTOR + select CLOCK_CONTROL + select HAS_FLASH_LOAD_OFFSET + select ARCH_HAS_RAMFUNC_SUPPORT + imply XIP config SOC_MAX32655_M4 select MAX32_HAS_SECONDARY_RV32 @@ -51,6 +64,7 @@ config MAX32_ON_ENTER_CPU_IDLE_HOOK bool "CPU idle hook enable" default y if !PM imply ARM_ON_ENTER_CPU_IDLE_HOOK + depends on ARM help Enables a hook (z_arm_on_enter_cpu_idle()) that is called when the CPU is made idle (by k_cpu_idle() or k_cpu_atomic_idle()). @@ -60,9 +74,10 @@ config MAX32_ON_ENTER_CPU_IDLE_HOOK config MAX32_HAS_SECONDARY_RV32 bool +if MAX32_HAS_SECONDARY_RV32 + config MAX32_SECONDARY_RV32 bool "Secondary RISC-V core enable" - depends on MAX32_HAS_SECONDARY_RV32 config MAX32_STANDBY_DELAY int "Prevent standby on boot for given ms" @@ -72,13 +87,31 @@ config MAX32_STANDBY_DELAY Prevents the system from entering standby mode for a give number of ms. This is intended to prevent debug lockout when using power management. +if MAX32_SECONDARY_RV32 + DT_CHOSEN_Z_CODE_RV32_PARTITION := zephyr,code-rv32-partition +DT_CHOSEN_Z_RV32_FLASH := zephyr,rv32-flash config MAX32_SECONDARY_RV32_BOOT_ADDRESS hex "Secondary RISC-V core boot address" - default $(dt_chosen_reg_addr_hex,$(DT_CHOSEN_Z_CODE_RV32_PARTITION)) + default $(dt_chosen_reg_addr_hex,$(DT_CHOSEN_Z_RV32_FLASH)) if $(dt_chosen_enabled,$(DT_CHOSEN_Z_RV32_FLASH)) + default 0x0 depends on MAX32_SECONDARY_RV32 +config MAX32_SECONDARY_RV32_BOOT_OFFSET + hex "Secondary RISC-V core boot address offset" + default $(dt_chosen_reg_addr_hex,$(DT_CHOSEN_Z_CODE_RV32_PARTITION)) if $(dt_chosen_enabled,$(DT_CHOSEN_Z_CODE_RV32_PARTITION)) + default 0x0 + depends on MAX32_SECONDARY_RV32 + +config MAX32_SECONDARY_RV32_STARTUP_DELAY + int "Secondary RISC-V core startup delay (in cycles)" + default 0 + +endif # MAX32_SECONDARY_RV32 + +endif # MAX32_HAS_SECONDARY_RV32 + config BUILD_WITH_TFM default y if TRUSTED_EXECUTION_NONSECURE help diff --git a/soc/adi/max32/Kconfig.defconfig b/soc/adi/max32/Kconfig.defconfig index cb0810b7f0093..1de1cdb22cee4 100644 --- a/soc/adi/max32/Kconfig.defconfig +++ b/soc/adi/max32/Kconfig.defconfig @@ -12,4 +12,26 @@ choice PM_PREWAKEUP_CONV_MODE endchoice # PM_PREWAKEUP_CONV_MODE +if SOC_FAMILY_MAX32_RV32 + +config RISCV_TRAP_HANDLER_ALIGNMENT + default 256 + +config ARCH_SW_ISR_TABLE_ALIGN + default 32 + +config RISCV_SOC_CONTEXT_SAVE + default y + +config RISCV_SOC_OFFSETS + default y + +config RISCV_MCAUSE_EXCEPTION_MASK + default 0xFFF + +config ISR_TABLES_LOCAL_DECLARATION_SUPPORTED + default n + +endif + endif # SOC_FAMILY_MAX32 diff --git a/soc/adi/max32/Kconfig.defconfig.max32655 b/soc/adi/max32/Kconfig.defconfig.max32655 index 8a9ef445f95df..3b3fe974fd47f 100644 --- a/soc/adi/max32/Kconfig.defconfig.max32655 +++ b/soc/adi/max32/Kconfig.defconfig.max32655 @@ -5,10 +5,37 @@ if SOC_MAX32655 +if SOC_MAX32655_M4 + config SYS_CLOCK_HW_CYCLES_PER_SEC default $(dt_node_int_prop_int,/clocks/clk_ipo,clock-frequency) config NUM_IRQS default 110 +endif + +if SOC_MAX32655_RV32 + +config SYS_CLOCK_HW_CYCLES_PER_SEC + default $(dt_node_int_prop_int,/clocks/clk_iso,clock-frequency) + +config NUM_IRQS + default 64 + +config ISR_STACK_SIZE + default 1024 + +config IDLE_STACK_SIZE + default 512 + +config ZTEST_STACK_SIZE + default 1024 + depends on ZTEST + +config TEST_EXTRA_STACK_SIZE + default 512 + +endif + endif # SOC_MAX32655 diff --git a/soc/adi/max32/Kconfig.defconfig.max32680 b/soc/adi/max32/Kconfig.defconfig.max32680 index 41e0674313de8..4a996967c8f4a 100644 --- a/soc/adi/max32/Kconfig.defconfig.max32680 +++ b/soc/adi/max32/Kconfig.defconfig.max32680 @@ -9,6 +9,7 @@ config SYS_CLOCK_HW_CYCLES_PER_SEC default $(dt_node_int_prop_int,/clocks/clk_ipo,clock-frequency) config NUM_IRQS - default 104 + default 104 if SOC_MAX32680_M4 + default 60 if SOC_MAX32680_RV32 endif # SOC_MAX32680 diff --git a/soc/adi/max32/Kconfig.defconfig.max32690 b/soc/adi/max32/Kconfig.defconfig.max32690 index a82759aff09f0..6df12827c07ef 100644 --- a/soc/adi/max32/Kconfig.defconfig.max32690 +++ b/soc/adi/max32/Kconfig.defconfig.max32690 @@ -5,10 +5,25 @@ if SOC_MAX32690 +if SOC_MAX32690_M4 + config SYS_CLOCK_HW_CYCLES_PER_SEC default $(dt_node_int_prop_int,/clocks/clk_ipo,clock-frequency) config NUM_IRQS default 112 +endif + +if SOC_MAX32690_RV32 + +config SYS_CLOCK_HW_CYCLES_PER_SEC + default $(dt_node_int_prop_int,/clocks/clk_iso,clock-frequency) + +config NUM_IRQS + default 64 + +endif + + endif # SOC_MAX32690 diff --git a/soc/adi/max32/Kconfig.defconfig.max78000 b/soc/adi/max32/Kconfig.defconfig.max78000 index 8643911a766e1..1a0e71cbda16b 100644 --- a/soc/adi/max32/Kconfig.defconfig.max78000 +++ b/soc/adi/max32/Kconfig.defconfig.max78000 @@ -5,10 +5,25 @@ if SOC_MAX78000 +if SOC_MAX78000_M4 + config SYS_CLOCK_HW_CYCLES_PER_SEC default $(dt_node_int_prop_int,/clocks/clk_ipo,clock-frequency) config NUM_IRQS default 119 +endif # SOC_MAX78000_M4 + +if SOC_MAX78000_RV32 + +config SYS_CLOCK_HW_CYCLES_PER_SEC + default $(dt_node_int_prop_int,/clocks/clk_iso,clock-frequency) + +config NUM_IRQS + default 60 + +endif # SOC_MAX78000_RV32 + + endif # SOC_MAX78000 diff --git a/soc/adi/max32/Kconfig.defconfig.max78002 b/soc/adi/max32/Kconfig.defconfig.max78002 index 307a757088804..78166666fcb71 100644 --- a/soc/adi/max32/Kconfig.defconfig.max78002 +++ b/soc/adi/max32/Kconfig.defconfig.max78002 @@ -5,10 +5,25 @@ if SOC_MAX78002 +if SOC_MAX78002_M4 + config SYS_CLOCK_HW_CYCLES_PER_SEC default $(dt_node_int_prop_int,/clocks/clk_ipo,clock-frequency) config NUM_IRQS default 105 +endif # SOC_MAX78002_M4 + +if SOC_MAX78002_RV32 + +config SYS_CLOCK_HW_CYCLES_PER_SEC + default $(dt_node_int_prop_int,/clocks/clk_iso,clock-frequency) + +config NUM_IRQS + default 60 + +endif # SOC_MAX78002_RV32 + + endif # SOC_MAX78002 diff --git a/soc/adi/max32/Kconfig.soc b/soc/adi/max32/Kconfig.soc index e4b2347ca0218..462d702f683ed 100644 --- a/soc/adi/max32/Kconfig.soc +++ b/soc/adi/max32/Kconfig.soc @@ -14,6 +14,10 @@ config SOC_FAMILY_MAX32_M4 bool select SOC_FAMILY_MAX32 +config SOC_FAMILY_MAX32_RV32 + bool + select SOC_FAMILY_MAX32 + config SOC_FAMILY default "max32" if SOC_FAMILY_MAX32 @@ -29,6 +33,11 @@ config SOC_MAX32655_M4 select SOC_MAX32655 select SOC_FAMILY_MAX32_M4 +config SOC_MAX32655_RV32 + bool + select SOC_MAX32655 + select SOC_FAMILY_MAX32_RV32 + config SOC_MAX32657 bool select SOC_FAMILY_MAX32_M33 @@ -69,6 +78,11 @@ config SOC_MAX32680_M4 select SOC_MAX32680 select SOC_FAMILY_MAX32_M4 +config SOC_MAX32680_RV32 + bool + select SOC_MAX32680 + select SOC_FAMILY_MAX32_RV32 + config SOC_MAX32690 bool @@ -77,6 +91,11 @@ config SOC_MAX32690_M4 select SOC_MAX32690 select SOC_FAMILY_MAX32_M4 +config SOC_MAX32690_RV32 + bool + select SOC_MAX32690 + select SOC_FAMILY_MAX32_RV32 + config SOC_MAX78000 bool @@ -85,6 +104,11 @@ config SOC_MAX78000_M4 select SOC_MAX78000 select SOC_FAMILY_MAX32_M4 +config SOC_MAX78000_RV32 + bool + select SOC_MAX78000 + select SOC_FAMILY_MAX32_RV32 + config SOC_MAX78002 bool @@ -93,6 +117,11 @@ config SOC_MAX78002_M4 select SOC_MAX78002 select SOC_FAMILY_MAX32_M4 +config SOC_MAX78002_RV32 + bool + select SOC_MAX78002 + select SOC_FAMILY_MAX32_RV32 + config SOC default "max32650" if SOC_MAX32650 default "max32655" if SOC_MAX32655 diff --git a/soc/adi/max32/soc.c b/soc/adi/max32/soc.c index 3b737b36b79b4..63d1c51b38c6a 100644 --- a/soc/adi/max32/soc.c +++ b/soc/adi/max32/soc.c @@ -10,6 +10,7 @@ */ #include +#include #include #include #include @@ -37,6 +38,29 @@ bool z_arm_on_enter_cpu_idle(void) } #endif +#define RV32_CPU DT_NODELABEL(cpu1) +#define DO_RV32_DEBUG_PINCTRL (DT_PINCTRL_HAS_NAME(RV32_CPU, default)) + +#if CONFIG_MAX32_SECONDARY_RV32 && DO_RV32_DEBUG_PINCTRL + +PINCTRL_DT_DEFINE(RV32_CPU); + +static const struct pinctrl_dev_config *rv32_pcfg = PINCTRL_DT_DEV_CONFIG_GET(RV32_CPU); + +#endif + +#if defined(CONFIG_MAX32_SECONDARY_RV32) && defined(CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY) && \ + (CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY > 0) + +static ALWAYS_INLINE void soc_max32_rv32_delay(int n) +{ + while (n--) { + __asm__ volatile("nop"); + } +} + +#endif + /** * @brief Perform basic hardware initialization at boot. * @@ -58,7 +82,18 @@ void soc_early_init_hook(void) #endif /* defined(MAX32_STANDBY_DELAY) && (MAX32_STANDBY_DELAY > 0) */ #ifdef CONFIG_MAX32_SECONDARY_RV32 - MXC_FCR->urvbootaddr = CONFIG_MAX32_SECONDARY_RV32_BOOT_ADDRESS; + +#if DO_RV32_DEBUG_PINCTRL + pinctrl_apply_state(rv32_pcfg, PINCTRL_STATE_DEFAULT); +#endif + +#if defined(CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY) && \ + (CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY > 0) + soc_max32_rv32_delay(CONFIG_MAX32_SECONDARY_RV32_STARTUP_DELAY); +#endif + + MXC_FCR->urvbootaddr = + CONFIG_MAX32_SECONDARY_RV32_BOOT_ADDRESS + CONFIG_MAX32_SECONDARY_RV32_BOOT_OFFSET; MXC_SYS_ClockEnable(MXC_SYS_PERIPH_CLOCK_CPU1); MXC_GCR->rst1 |= MXC_F_GCR_RST1_CPU1; #endif /* CONFIG_MAX32_SECONDARY_RV32 */ diff --git a/soc/adi/max32/soc.h b/soc/adi/max32/soc.h index fd785920a4a0b..6f837fc862233 100644 --- a/soc/adi/max32/soc.h +++ b/soc/adi/max32/soc.h @@ -14,4 +14,18 @@ #include +#if defined(CONFIG_SOC_FAMILY_MAX32_RV32) + +/** + * The RV32 core does not support the FENCE instruction, so redefine these intrinsics. + */ + +#undef __sync_synchronize +#define __sync_synchronize() {} + +#undef __atomic_thread_fence +#define __atomic_thread_fence(_arg) {} + +#endif + #endif /* _MAX32_SOC_H_ */ diff --git a/soc/adi/max32/soc.yml b/soc/adi/max32/soc.yml index 1a4b7c2568d38..5d058ad4d1687 100644 --- a/soc/adi/max32/soc.yml +++ b/soc/adi/max32/soc.yml @@ -8,6 +8,7 @@ family: - name: max32655 cpuclusters: - name: m4 + - name: rv32 - name: max32657 - name: max32660 - name: max32662 @@ -20,12 +21,16 @@ family: - name: max32680 cpuclusters: - name: m4 + - name: rv32 - name: max32690 cpuclusters: - name: m4 + - name: rv32 - name: max78000 cpuclusters: - name: m4 + - name: rv32 - name: max78002 cpuclusters: - name: m4 + - name: rv32 diff --git a/soc/adi/max32/soc_context.h b/soc/adi/max32/soc_context.h new file mode 100644 index 0000000000000..bf70effc9a761 --- /dev/null +++ b/soc/adi/max32/soc_context.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2018 Foundries.io Ltd + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/* + * Extra definitions required for CONFIG_RISCV_SOC_CONTEXT_SAVE. + */ + +#ifndef SOC_ADI_MAX32_RV32_SOC_CONTEXT_H_ +#define SOC_ADI_MAX32_RV32_SOC_CONTEXT_H_ + +#ifdef CONFIG_SOC_FAMILY_MAX32_RV32 + +/* Extra state for RI5CY hardware loop registers. */ +#define SOC_ESF_MEMBERS \ + uint32_t lpstart0; \ + uint32_t lpend0; \ + uint32_t lpcount0; \ + uint32_t lpstart1; \ + uint32_t lpend1; \ + uint32_t lpcount1 + +/* Initial saved state. */ +#define SOC_ESF_INIT 0, 0, 0, 0, 0, 0 + +#endif /* CONFIG_SOC_FAMILY_MAX32_RV32 */ + +#endif /* SOC_ADI_MAX32_RV32_SOC_CONTEXT_H_ */ diff --git a/soc/adi/max32/soc_irq_rv32.S b/soc/adi/max32/soc_irq_rv32.S new file mode 100644 index 0000000000000..01ab04496141c --- /dev/null +++ b/soc/adi/max32/soc_irq_rv32.S @@ -0,0 +1,78 @@ +/* + * Copyright (c) 2018 Foundries.io Ltd + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include +#include +#include +#include + +#include + +/* Exports */ +GTEXT(__soc_handle_irq) +#ifdef CONFIG_RISCV_SOC_CONTEXT_SAVE +GTEXT(__soc_save_context) +GTEXT(__soc_restore_context) +#endif + +/* + * SOC-specific function to handle pending IRQ number generating the interrupt. + * Exception number is returned via register a0. + */ +SECTION_FUNC(exception.other, __soc_handle_irq) + addi sp, sp, -4 + sw ra, 0x00(sp) + la t1, max32_rv32_intc_get_next_source + jalr ra, t1, 0 + lw ra, 0x00(sp) + addi sp, sp, 4 + ret + +#ifdef CONFIG_RISCV_SOC_CONTEXT_SAVE +/* + * The RI5CY core has ISA extensions for faster loop performance + * that use extra registers. + * + * If the toolchain generates instructions that use them, they must be saved + * prior to handling an interrupt/exception. This case is handled using + * Zephyr's generic RISC-V mechanism for soc-specific context. + * + * For details, see the Kconfig help for CONFIG_RISCV_SOC_CONTEXT_SAVE. + */ +SECTION_FUNC(exception.other, __soc_save_context) + csrr t0, RI5CY_LPSTART0 + csrr t1, RI5CY_LPEND0 + csrr t2, RI5CY_LPCOUNT0 + sw t0, __soc_esf_t_lpstart0_OFFSET(a0) + sw t1, __soc_esf_t_lpend0_OFFSET(a0) + sw t2, __soc_esf_t_lpcount0_OFFSET(a0) + csrr t0, RI5CY_LPSTART1 + csrr t1, RI5CY_LPEND1 + csrr t2, RI5CY_LPCOUNT1 + sw t0, __soc_esf_t_lpstart1_OFFSET(a0) + sw t1, __soc_esf_t_lpend1_OFFSET(a0) + sw t2, __soc_esf_t_lpcount1_OFFSET(a0) + + ret + +SECTION_FUNC(exception.other, __soc_restore_context) + lw t0, __soc_esf_t_lpstart0_OFFSET(a0) + lw t1, __soc_esf_t_lpend0_OFFSET(a0) + lw t2, __soc_esf_t_lpcount0_OFFSET(a0) + csrw RI5CY_LPSTART0, t0 + csrw RI5CY_LPEND0, t1 + csrw RI5CY_LPCOUNT0, t2 + lw t0, __soc_esf_t_lpstart1_OFFSET(a0) + lw t1, __soc_esf_t_lpend1_OFFSET(a0) + lw t2, __soc_esf_t_lpcount1_OFFSET(a0) + csrw RI5CY_LPSTART1, t0 + csrw RI5CY_LPEND1, t1 + csrw RI5CY_LPCOUNT1, t2 + + ret +#endif /* CONFIG_RISCV_SOC_CONTEXT_SAVE */ diff --git a/soc/adi/max32/soc_offsets.h b/soc/adi/max32/soc_offsets.h new file mode 100644 index 0000000000000..8466a3b66ad54 --- /dev/null +++ b/soc/adi/max32/soc_offsets.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2018 Foundries.io Ltd + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/* + * Extra definitions required for CONFIG_RISCV_SOC_OFFSETS. + */ + +#ifndef SOC_ADI_MAX32_RV32_SOC_OFFSETS_H_ +#define SOC_ADI_MAX32_RV32_SOC_OFFSETS_H_ + +#ifdef CONFIG_SOC_FAMILY_MAX32_RV32 +/* + * Ensure offset macros are available in . + * + * Also create a macro which contains the value of &EVENT0->INTPTPENDCLEAR, + * for use in assembly. + */ +#define GEN_SOC_OFFSET_SYMS() \ + GEN_OFFSET_SYM(soc_esf_t, lpstart0); \ + GEN_OFFSET_SYM(soc_esf_t, lpend0); \ + GEN_OFFSET_SYM(soc_esf_t, lpcount0); \ + GEN_OFFSET_SYM(soc_esf_t, lpstart1); \ + GEN_OFFSET_SYM(soc_esf_t, lpend1); \ + GEN_OFFSET_SYM(soc_esf_t, lpcount1); + +#endif /* CONFIG_SOC_FAMILY_MAX32_RV32 */ + +#endif /* SOC_ADI_MAX32_RV32_SOC_OFFSETS_H_ */ diff --git a/soc/adi/max32/soc_ri5cy.h b/soc/adi/max32/soc_ri5cy.h new file mode 100644 index 0000000000000..934206a5a1f79 --- /dev/null +++ b/soc/adi/max32/soc_ri5cy.h @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2018 Foundries.io Ltd + * Copyright (c) 2025 Analog Devices, Inc + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#ifndef SOC_ADI_MAX32_RV32_SOC_RI5CY_H_ +#define SOC_ADI_MAX32_RV32_SOC_RI5CY_H_ + +/* Control and Status Registers (CSRs) available for RI5CY. */ +#define RI5CY_USTATUS 0x000 +#define RI5CY_UTVEC 0x005 +#define RI5CY_UHARTID 0x014 +#define RI5CY_UEPC 0x041 +#define RI5CY_UCAUSE 0x042 +#define RI5CY_MSTATUS 0x300 +#define RI5CY_MTVEC 0x305 +#define RI5CY_MEPC 0x341 +#define RI5CY_MCAUSE 0x342 +#define RI5CY_PCCR0 0x780 +#define RI5CY_PCCR1 0x781 +#define RI5CY_PCCR2 0x782 +#define RI5CY_PCCR3 0x783 +#define RI5CY_PCCR4 0x784 +#define RI5CY_PCCR5 0x785 +#define RI5CY_PCCR6 0x786 +#define RI5CY_PCCR7 0x787 +#define RI5CY_PCCR8 0x788 +#define RI5CY_PCCR9 0x789 +#define RI5CY_PCCR10 0x78A +#define RI5CY_PCCR11 0x78B +#define RI5CY_PCER 0x7A0 +#define RI5CY_PCMR 0x7A1 +#define RI5CY_LPSTART0 0x7B0 +#define RI5CY_LPEND0 0x7B1 +#define RI5CY_LPCOUNT0 0x7B2 +#define RI5CY_LPSTART1 0x7B4 +#define RI5CY_LPEND1 0x7B5 +#define RI5CY_LPCOUNT1 0x7B6 +#define RI5CY_PRIVLV 0xC10 +#define RI5CY_MHARTID 0xF14 + +#endif /* SOC_ADI_MAX32_RV32_SOC_RI5CY_H_ */ diff --git a/soc/adi/max32/vector_rv32.S b/soc/adi/max32/vector_rv32.S new file mode 100644 index 0000000000000..d6150c86b206c --- /dev/null +++ b/soc/adi/max32/vector_rv32.S @@ -0,0 +1,98 @@ +/* + * Copyright (c) 2017 Jean-Paul Etienne + * Contributors: 2018 Antmicro + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include +#include + +/* exports */ +GTEXT(__start) +GTEXT(__ivt) +GTEXT(__rv32_isr_wrapper) + +/* imports */ +GTEXT(__initialize) +#if defined(CONFIG_GEN_SW_ISR_TABLE) +GTEXT(_isr_wrapper) +#endif + +SECTION_FUNC(vectors, __ivt) + .option push + .option norvc + j __start + j _isr_wrapper + j _isr_wrapper + j _isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + j __rv32_isr_wrapper + +SECTION_FUNC(vectors, __rv32_isr_wrapper) + addi sp, sp, -8 + sw t0, 0x00(sp) + sw t1, 0x04(sp) + csrr t0, mcause + /* Synthesize interrupt cause by setting 31st bit */ + li t1, 1 << RISCV_MCAUSE_IRQ_POS + or t0, t0, t1 + csrw mcause, t0 + lw t0, 0x00(sp) + lw t1, 0x04(sp) + addi sp, sp, 8 + j _isr_wrapper + +SECTION_FUNC(vectors, __start) +#if defined(CONFIG_RISCV_GP) + /* Initialize global pointer */ + .option push + .option norelax + la gp, __global_pointer$ + .option pop +#endif + + .option norvc; + +#if defined(CONFIG_SOC_RESET_HOOK) + call soc_reset_hook +#endif + + la t0, __ivt /* Load address of interrupt vector table */ + addi t0, t0, 0x01 /* Enable vectored mode by setting LSB */ + csrw mtvec, t0 + + /* Enable IRQs */ + csrwi mstatus, 8 + + /* Jump to __reset */ + tail __reset diff --git a/tests/arch/common/gen_isr_table/testcase.yaml b/tests/arch/common/gen_isr_table/testcase.yaml index 8648e1fa2e1c6..11f037f510725 100644 --- a/tests/arch/common/gen_isr_table/testcase.yaml +++ b/tests/arch/common/gen_isr_table/testcase.yaml @@ -62,6 +62,7 @@ tests: - CONFIG_ISR_TABLES_LOCAL_DECLARATION=y arch.interrupt.gen_isr_table_local.riscv: arch_allow: riscv + filter: CONFIG_ISR_TABLES_LOCAL_DECLARATION_SUPPORTED extra_configs: - CONFIG_ISR_TABLES_LOCAL_DECLARATION=y diff --git a/tests/arch/common/interrupt/testcase.yaml b/tests/arch/common/interrupt/testcase.yaml index 2e7fcfc247ea7..35da1435d8a46 100644 --- a/tests/arch/common/interrupt/testcase.yaml +++ b/tests/arch/common/interrupt/testcase.yaml @@ -39,6 +39,9 @@ tests: # On it8xxx2_evb, current trigger_irq implementation of RISC-V architecture # does not trigger interrupts - it8xxx2_evb + - max32655evkit/max32655/rv32 + - max32690evkit/max32690/rv32 + - max78002evkit/max78002/rv32 arch_exclude: # test needs 2 working interrupt lines - xtensa @@ -52,7 +55,11 @@ tests: filter: not CONFIG_TRUSTED_EXECUTION_NONSECURE arch.shared_interrupt.lto: &shared-interrupt-lto # excluded because of failures during test_prevent_interruption - platform_exclude: qemu_cortex_m0 + platform_exclude: + - qemu_cortex_m0 + - max32655evkit/max32655/rv32 + - max32690evkit/max32690/rv32 + - max78002evkit/max78002/rv32 arch_exclude: # test needs 2 working interrupt lines - xtensa diff --git a/tests/drivers/flash/common/boards/max32690_flash1_storage_partition.overlay b/tests/drivers/flash/common/boards/max32690_flash1_storage_partition.overlay index c11613caf9262..d87e86305848b 100644 --- a/tests/drivers/flash/common/boards/max32690_flash1_storage_partition.overlay +++ b/tests/drivers/flash/common/boards/max32690_flash1_storage_partition.overlay @@ -11,6 +11,8 @@ }; }; +/delete-node/ &storage_partition; + &flash1 { status = "okay"; diff --git a/tests/drivers/flash/common/boards/max32690evkit_max32690_m4.overlay b/tests/drivers/flash/common/boards/max32690evkit_max32690_m4.overlay deleted file mode 100644 index dee6fb376908d..0000000000000 --- a/tests/drivers/flash/common/boards/max32690evkit_max32690_m4.overlay +++ /dev/null @@ -1,23 +0,0 @@ -/* - * Copyright (c) 2024 Analog Devices, Inc. - * - * SPDX-License-Identifier: Apache-2.0 - */ - -&flash0 { - partitions { - compatible = "fixed-partitions"; - #address-cells = <1>; - #size-cells = <1>; - - code_partition: partition@0 { - reg = <0x0 DT_SIZE_M(2)>; - read-only; - }; - - storage_partition: partition@200000 { - label = "storage"; - reg = <0x200000 DT_SIZE_M(1)>; - }; - }; -}; diff --git a/tests/drivers/flash/common/boards/max32690evkit_max32690_rv32.overlay b/tests/drivers/flash/common/boards/max32690evkit_max32690_rv32.overlay new file mode 100644 index 0000000000000..4f323e4ec4bf7 --- /dev/null +++ b/tests/drivers/flash/common/boards/max32690evkit_max32690_rv32.overlay @@ -0,0 +1,8 @@ +/* + * Copyright (c) 2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/delete-node/ &storage_partition; +storage_partition: &rv32_storage_partition {}; diff --git a/tests/drivers/flash/common/boards/max78002evkit_max78002_m4.overlay b/tests/drivers/flash/common/boards/max78002evkit_max78002_m4.overlay index 08546f0fbcc0e..12a67c50d2fa5 100644 --- a/tests/drivers/flash/common/boards/max78002evkit_max78002_m4.overlay +++ b/tests/drivers/flash/common/boards/max78002evkit_max78002_m4.overlay @@ -4,20 +4,4 @@ * SPDX-License-Identifier: Apache-2.0 */ -&flash0 { - partitions { - compatible = "fixed-partitions"; - #address-cells = <1>; - #size-cells = <1>; - - code_partition: partition@0 { - reg = <0x0 DT_SIZE_M(2)>; - read-only; - }; - - storage_partition: partition@200000 { - label = "storage"; - reg = <0x200000 DT_SIZE_K(512)>; - }; - }; -}; +storage_partition: &m4_storage_partition {}; diff --git a/tests/drivers/flash/common/testcase.yaml b/tests/drivers/flash/common/testcase.yaml index 3025a3d7f213e..652b1cbfaebd6 100644 --- a/tests/drivers/flash/common/testcase.yaml +++ b/tests/drivers/flash/common/testcase.yaml @@ -22,12 +22,10 @@ tests: - apard32690/max32690/m4 drivers.flash.common.max32_flash1: platform_allow: - - apard32690/max32690/m4 - max32690evkit/max32690/m4 extra_args: - DTC_OVERLAY_FILE=boards/max32690_flash1_storage_partition.overlay integration_platforms: - - apard32690/max32690/m4 - max32690evkit/max32690/m4 drivers.flash.common.nrf_qspi_nor.size_in_bytes: platform_allow: nrf52840dk/nrf52840 diff --git a/tests/drivers/gpio/gpio_basic_api/boards/max32655evkit_max32655_rv32.overlay b/tests/drivers/gpio/gpio_basic_api/boards/max32655evkit_max32655_rv32.overlay new file mode 100644 index 0000000000000..aef5fe92da573 --- /dev/null +++ b/tests/drivers/gpio/gpio_basic_api/boards/max32655evkit_max32655_rv32.overlay @@ -0,0 +1,13 @@ +/* + * Copyright (c) 2023-2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/ { + resources { + compatible = "test-gpio-basic-api"; + out-gpios = <&gpio2 0 0>; + in-gpios = <&gpio2 1 0>; + }; +}; diff --git a/tests/drivers/gpio/gpio_basic_api/boards/max78002evkit_max78002_rv32.overlay b/tests/drivers/gpio/gpio_basic_api/boards/max78002evkit_max78002_rv32.overlay new file mode 100644 index 0000000000000..79684b32850b4 --- /dev/null +++ b/tests/drivers/gpio/gpio_basic_api/boards/max78002evkit_max78002_rv32.overlay @@ -0,0 +1,13 @@ +/* + * Copyright (c) 2024 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/ { + resources { + compatible = "test-gpio-basic-api"; + out-gpios = <&gpio0 8 0>; + in-gpios = <&gpio0 9 0>; + }; +}; diff --git a/tests/drivers/watchdog/wdt_basic_api/boards/max32_wdt.overlay b/tests/drivers/watchdog/wdt_basic_api/boards/max32_wdt.overlay new file mode 100644 index 0000000000000..75c94ef84ca63 --- /dev/null +++ b/tests/drivers/watchdog/wdt_basic_api/boards/max32_wdt.overlay @@ -0,0 +1,11 @@ +/* + * Copyright (c) 2025 Analog Devices, Inc. + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/ { + chosen { + zephyr,sram = &sram3; + }; +}; diff --git a/tests/drivers/watchdog/wdt_basic_api/testcase.yaml b/tests/drivers/watchdog/wdt_basic_api/testcase.yaml index 84d4ab51b9496..df31bf4f8672e 100644 --- a/tests/drivers/watchdog/wdt_basic_api/testcase.yaml +++ b/tests/drivers/watchdog/wdt_basic_api/testcase.yaml @@ -11,7 +11,7 @@ tests: or dt_compat_enabled("st,stm32-window-watchdog") or dt_compat_enabled("st,stm32-watchdog") or CONFIG_SOC_FAMILY_LPC or CONFIG_SOC_SERIES_IMXRT6XX or CONFIG_SOC_SERIES_IMXRT5XX or - CONFIG_SOC_FAMILY_GD_GD32 or SOC_SERIES_GD32VF103) + CONFIG_SOC_FAMILY_GD_GD32 or SOC_SERIES_GD32VF103 or CONFIG_SOC_MAX32655) platform_exclude: - mec15xxevb_assy6853 - s32z2xxdc2/s32z270/rtu0 @@ -155,3 +155,9 @@ tests: platform_allow: - frdm_mcxw71 - frdm_mcxw72/mcxw727c/cpu0 + drivers.watchdog.max32: + filter: dt_compat_enabled("adi,max32-watchdog") + extra_args: DTC_OVERLAY_FILE="boards/max32_wdt.overlay" + platform_allow: + - max32655evkit/max32655/m4 + - max32655fthr/max32655/m4 diff --git a/tests/kernel/fatal/exception/src/main.c b/tests/kernel/fatal/exception/src/main.c index 730a82f21033c..1afc79dea09bd 100644 --- a/tests/kernel/fatal/exception/src/main.c +++ b/tests/kernel/fatal/exception/src/main.c @@ -112,15 +112,21 @@ void entry_cpu_exception_extend(void *p1, void *p2, void *p3) __asm__ volatile ("udf #0"); #elif defined(CONFIG_RX) __asm__ volatile ("brk"); +#elif defined(CONFIG_SOC_FAMILY_MAX32_RV32) + /* The MAX32 RV32 core does not trap on writes to + * non-existent CSRs, so use a different illegal instruction + * for this test. + */ + __asm__ volatile (".word 0"); #elif defined(CONFIG_RISCV) /* In riscv architecture, use an undefined * instruction to trigger illegal instruction on RISCV. */ __asm__ volatile ("unimp"); +#elif defined(CONFIG_ARC) /* In arc architecture, SWI instruction is used * to trigger soft interrupt. */ -#elif defined(CONFIG_ARC) __asm__ volatile ("swi"); #else /* used to create a divide by zero error on X86 and MIPS */ diff --git a/tests/subsys/debug/coredump/src/main.c b/tests/subsys/debug/coredump/src/main.c index 4903261bc862a..330fdf4418439 100644 --- a/tests/subsys/debug/coredump/src/main.c +++ b/tests/subsys/debug/coredump/src/main.c @@ -43,11 +43,12 @@ __no_optimization void func_3(uint32_t *addr) defined(CONFIG_BOARD_RISCV32_VIRTUAL) || \ defined(CONFIG_SOC_FAMILY_INTEL_ISH) || \ defined(CONFIG_SOC_FAMILY_INTEL_ADSP) || \ + defined(CONFIG_SOC_FAMILY_MAX32_RV32) || \ defined(CONFIG_SOC_FAMILY_OPENHWGROUP_CVA6) /* clang-format on */ ARG_UNUSED(addr); /* Call k_panic() directly so Renode doesn't pause execution. - * Needed on ADSP as well, since null pointer derefence doesn't + * Needed on ADSP/RV32 as well, since null pointer derefence doesn't * fault as the lowest memory region is writable. SOF uses k_panic * a lot, so it's good to check that it causes a coredump. */ diff --git a/tests/subsys/secure_storage/psa/its/testcase.yaml b/tests/subsys/secure_storage/psa/its/testcase.yaml index 75950a798143a..00a9acb2fd5e4 100644 --- a/tests/subsys/secure_storage/psa/its/testcase.yaml +++ b/tests/subsys/secure_storage/psa/its/testcase.yaml @@ -4,6 +4,7 @@ common: - nrf54l15dk/nrf54l15/cpuapp platform_exclude: - qemu_cortex_m0 # settings subsystem initialization fails + - max78002evkit/max78002/rv32 # Erase of flash nukes the ARM core host app timeout: 600 tags: - psa.secure_storage diff --git a/west.yml b/west.yml index a5154435a3cdf..ca804b984cc70 100644 --- a/west.yml +++ b/west.yml @@ -144,7 +144,7 @@ manifest: groups: - fs - name: hal_adi - revision: eeb155f7382343438114605963ae64436cc53434 + revision: f3216a28d70499975238c19189ed07c689f0cf24 path: modules/hal/adi groups: - hal