-
Notifications
You must be signed in to change notification settings - Fork 98
libutils: Add support for stm32mp2 SoC family #205
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
bruelc
wants to merge
1
commit into
seL4:master
Choose a base branch
from
bruelc:master-stm32mp2
base: master
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Some comments aren't visible on the classic Files Changed page.
There are no files selected for viewing
16 changes: 16 additions & 0 deletions
16
libplatsupport/plat_include/stm32mp2/platsupport/plat/clock.h
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,16 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
|
|
||
| #pragma oncew | ||
|
|
||
| enum clk_id { | ||
| CLK_MASTER, | ||
| NCLOCKS, | ||
| }; | ||
|
|
||
| enum clock_gate { | ||
| NCLKGATES | ||
| }; |
13 changes: 13 additions & 0 deletions
13
libplatsupport/plat_include/stm32mp2/platsupport/plat/i2c.h
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,13 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <platsupport/io.h> | ||
|
|
||
| enum i2c_id { | ||
| NI2C | ||
| }; |
32 changes: 32 additions & 0 deletions
32
libplatsupport/plat_include/stm32mp2/platsupport/plat/serial.h
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,32 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
|
|
||
| #pragma once | ||
|
|
||
| #define USART1_PADDR 0x40330000 | ||
| #define USART2_PADDR 0x400e0000 | ||
| #define USART3_PADDR 0x400f0000 | ||
| #define USART6_PADDR 0x40220000 | ||
| #define UART4_PADDR 0x40100000 | ||
| #define UART5_PADDR 0x40110000 | ||
| #define UART7_PADDR 0x40370000 | ||
| #define UART8_PADDR 0x40380000 | ||
| #define UART9_PADDR 0x402c0000 | ||
|
|
||
| /* official device names */ | ||
| enum chardev_id { | ||
| USART1, | ||
| USART2, | ||
| USART3, | ||
| USART6, | ||
| UART4, | ||
| UART5, | ||
| UART7, | ||
| UART8, | ||
| UART9, | ||
| /* defaults */ | ||
| PS_SERIAL_DEFAULT = USART2 | ||
| }; |
70 changes: 70 additions & 0 deletions
70
libplatsupport/plat_include/stm32mp2/platsupport/plat/timer.h
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,70 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
| #pragma once | ||
|
|
||
| #include <platsupport/ltimer.h> | ||
| #include <platsupport/timer.h> | ||
|
|
||
| /* Input clock */ | ||
| #define TIM2_HZ 200000000UL | ||
| #define TICK_NS 5000UL | ||
|
|
||
| /* RCC TIM2 basic timer */ | ||
| #define RCC_PADDR 0x44200000 | ||
| #define RCC_TIM2_OFF 0x704 | ||
| #define RCC_TIM2_PADDR (RCC_PADDR + RCC_TIM2_OFF) | ||
| #define RCC_TIM2_SIZE 4 | ||
| #define TIM2_IRQ 137 | ||
| #define TIM2_MAP 0x40000000 | ||
|
|
||
| typedef struct stm32_regs { | ||
| uint32_t cr1; | ||
| uint32_t cr2; | ||
| uint32_t smcr; | ||
| uint32_t dier; | ||
| uint32_t sr; | ||
| uint32_t egr; | ||
| uint32_t ccmr1; | ||
| uint32_t ccmr2; | ||
| uint32_t ccer; | ||
| uint32_t cnt; | ||
| uint32_t psc; | ||
| uint32_t arr; | ||
| uint32_t rcr; /* n/a for TIM2 */ | ||
| uint32_t ccr1; | ||
| uint32_t ccr2; | ||
| uint32_t ccr3; | ||
| uint32_t ccr4; | ||
| } stm32_regs_t; | ||
|
Indanz marked this conversation as resolved.
|
||
|
|
||
| #define STM32_TIM_CCER_CC1E BIT(0) | ||
|
|
||
| #define STM32_TIM_CR1_CEN BIT(0) | ||
| #define STM32_TIM_CR1_UDIS BIT(1) | ||
| #define STM32_TIM_CR1_URS BIT(1) | ||
| #define STM32_TIM_CR1_OPM BIT(6) | ||
| #define STM32_TIM_CR1_ARPE BIT(7) | ||
|
|
||
| #define STM32_TIM_EGR_UG BIT(0) | ||
|
|
||
| #define STM32_TIM_DIER_UIE BIT(0) | ||
| #define STM32_TIM_DIER_CC1IE BIT(1) | ||
|
|
||
| #define STM32_TIM_SR_UIF BIT(0) | ||
| #define STM32_TIM_SR_CC1IF BIT(1) | ||
|
|
||
| typedef struct { | ||
| volatile stm32_regs_t *hw; | ||
| uint32_t periodic_t; | ||
| uint32_t cnt_h; /* keep overflow for get_time */ | ||
| } stm32_t; | ||
|
|
||
| int stm32mp2_timer_init(stm32_t *stm32, ps_io_ops_t ops); | ||
| void stm32_timer_reset(stm32_t *stm32); | ||
| uint64_t stm32_get_time(stm32_t *stm32); | ||
| int stm32_set_timeout(stm32_t *dmt, uint64_t ns, bool periodic); | ||
| int stm32_start_timer(stm32_t *stm32); | ||
| int stm32_stop_timer(stm32_t *stm32); | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,47 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
|
|
||
| #include "../../chardev.h" | ||
| #include "../../common.h" | ||
| #include <utils/util.h> | ||
|
|
||
| #define UART_DEFN(devid) { \ | ||
| .id = UART##devid, \ | ||
| .paddr = UART##devid##_PADDR, \ | ||
| .size = BIT(12), \ | ||
| .init_fn = &uart_init \ | ||
| } | ||
|
|
||
| #define USART_DEFN(devid) { \ | ||
| .id = USART##devid, \ | ||
| .paddr = USART##devid##_PADDR, \ | ||
| .size = BIT(12), \ | ||
| .init_fn = &uart_init \ | ||
| } | ||
|
|
||
| static const struct dev_defn dev_defn[] = { | ||
| USART_DEFN(1), | ||
| USART_DEFN(2), | ||
| USART_DEFN(3), | ||
| USART_DEFN(6), | ||
| UART_DEFN(4), | ||
| UART_DEFN(5), | ||
| UART_DEFN(7), | ||
| UART_DEFN(8), | ||
| UART_DEFN(9), | ||
| }; | ||
|
|
||
| struct ps_chardevice * | ||
| ps_cdev_init(enum chardev_id id, const ps_io_ops_t *o, struct ps_chardevice *d) | ||
| { | ||
| unsigned int i; | ||
| for (i = 0; i < ARRAY_SIZE(dev_defn); i++) { | ||
| if (dev_defn[i].id == id) { | ||
| return (dev_defn[i].init_fn(dev_defn + i, o, d)) ? NULL : d; | ||
| } | ||
| } | ||
| return NULL; | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,186 @@ | ||
| /* | ||
| * Copyright 2026, STMicroelectronics | ||
| * | ||
| * SPDX-License-Identifier: BSD-2-Clause | ||
| */ | ||
| #include <stdio.h> | ||
|
|
||
| #include <utils/util.h> | ||
| #include <utils/time.h> | ||
|
|
||
| #include <platsupport/plat/timer.h> | ||
| #include <platsupport/io.h> | ||
|
|
||
| #include "../../ltimer.h" | ||
|
|
||
| typedef struct { | ||
| stm32_t stm32_timer; | ||
| irq_id_t irq_id; | ||
| timer_callback_data_t callback_data; | ||
| ltimer_callback_fn_t user_cb_fn; | ||
| void *user_cb_token; | ||
| ps_io_ops_t ops; | ||
| } stm32_ltimer_t; | ||
|
|
||
| static pmem_region_t pmems = { | ||
| .type = PMEM_TYPE_DEVICE, | ||
| .base_addr = TIM2_MAP, | ||
| .length = PAGE_SIZE_4K | ||
| }; | ||
|
|
||
| static ps_irq_t irqs = { | ||
| .type = PS_INTERRUPT, | ||
| .irq.number = TIM2_IRQ, | ||
| }; | ||
|
|
||
| static int get_time(void *data, uint64_t *time) | ||
| { | ||
| stm32_ltimer_t *stm32_ltimer = data; | ||
|
|
||
| *time = stm32_get_time(&stm32_ltimer->stm32_timer); | ||
|
|
||
| return 0; | ||
| } | ||
|
|
||
| static int set_timeout(void *data, uint64_t ns, timeout_type_t type) | ||
| { | ||
| uint64_t timeout; | ||
| stm32_ltimer_t *stm32_ltimer = data; | ||
| uint64_t time = stm32_get_time(&stm32_ltimer->stm32_timer); | ||
|
|
||
| switch (type) { | ||
| case TIMEOUT_ABSOLUTE: | ||
| if ((ns - time) / TICK_NS > UINT32_MAX) { | ||
| ZF_LOGE("Timeout too far in the future"); | ||
| return ETIME; | ||
| } | ||
| timeout = ns; | ||
| break; | ||
|
bruelc marked this conversation as resolved.
|
||
| case TIMEOUT_RELATIVE: | ||
| case TIMEOUT_PERIODIC: | ||
| if (ns / TICK_NS > UINT32_MAX) { | ||
| ZF_LOGE("Timeout too far in the future"); | ||
| return ETIME; | ||
| } | ||
| timeout = ns + time; | ||
| break; | ||
|
bruelc marked this conversation as resolved.
|
||
| } | ||
|
|
||
| return stm32_set_timeout(&stm32_ltimer->stm32_timer, timeout, type == TIMEOUT_PERIODIC); | ||
| } | ||
|
|
||
| static int reset(void *data) | ||
| { | ||
| stm32_ltimer_t *stm32_ltimer = data; | ||
|
|
||
| stm32_stop_timer(&stm32_ltimer->stm32_timer); | ||
| stm32_start_timer(&stm32_ltimer->stm32_timer); | ||
|
|
||
| return 0; | ||
| } | ||
|
|
||
| static void destroy(void *data) | ||
| { | ||
| stm32_ltimer_t *stm32_ltimer = data; | ||
|
|
||
| stm32_stop_timer(&stm32_ltimer->stm32_timer); | ||
|
|
||
| if (stm32_ltimer->stm32_timer.hw) { | ||
| ps_pmem_unmap(&stm32_ltimer->ops, pmems, (void *) stm32_ltimer->stm32_timer.hw); | ||
| } | ||
|
|
||
| if (stm32_ltimer->irq_id != PS_INVALID_IRQ_ID) { | ||
| int error = ps_irq_unregister(&stm32_ltimer->ops.irq_ops, stm32_ltimer->irq_id); | ||
| ZF_LOGF_IF(error, "Failed to unregister IRQ"); | ||
| } | ||
|
|
||
| ps_free(&stm32_ltimer->ops.malloc_ops, sizeof(stm32_ltimer_t), stm32_ltimer); | ||
| } | ||
|
|
||
| static int handle_irq(void *data, ps_irq_t *irq) | ||
| { | ||
| stm32_ltimer_t *stm32_ltimer = data; | ||
|
|
||
| long irq_number = irq->irq.number; | ||
| stm32_t *stm32 = &stm32_ltimer->stm32_timer; | ||
| volatile stm32_regs_t *stm32_regs = stm32->hw; | ||
| uint32_t sr; | ||
|
|
||
| assert(irq_number == irqs.irq.number); | ||
|
|
||
| sr = stm32_regs->sr; | ||
|
|
||
| if (sr & STM32_TIM_SR_UIF) { | ||
| stm32->cnt_h++; | ||
| sr &= ~STM32_TIM_SR_UIF; | ||
|
|
||
| if (stm32_ltimer->user_cb_fn) { | ||
| stm32_ltimer->user_cb_fn(stm32_ltimer->user_cb_token, LTIMER_OVERFLOW_EVENT); | ||
| } | ||
| } | ||
|
|
||
| if (sr & STM32_TIM_SR_CC1IF) { | ||
| if (stm32->periodic_t) { | ||
| stm32->hw->ccr1 += stm32->periodic_t; | ||
| } else { | ||
| stm32_regs->dier &= ~STM32_TIM_DIER_CC1IE; | ||
| } | ||
| sr &= ~STM32_TIM_SR_CC1IF; | ||
|
|
||
| if (stm32_ltimer->user_cb_fn) { | ||
| stm32_ltimer->user_cb_fn(stm32_ltimer->user_cb_token, LTIMER_TIMEOUT_EVENT); | ||
| } | ||
| } | ||
|
|
||
| stm32_regs->sr = sr; | ||
|
|
||
| return 0; | ||
| } | ||
|
|
||
| int ltimer_default_init(ltimer_t *ltimer, ps_io_ops_t ops, ltimer_callback_fn_t callback, void *callback_token) | ||
| { | ||
| int rc; | ||
| void *stm32_map_base; | ||
|
|
||
| rc = create_ltimer_simple(ltimer, ops, sizeof(stm32_ltimer_t), get_time, | ||
| set_timeout, reset, destroy); | ||
| if (rc) { | ||
| ZF_LOGE("ltimer creation failed"); | ||
| return rc; | ||
| } | ||
|
|
||
| stm32_ltimer_t *stm32_ltimer = ltimer->data; | ||
| stm32_ltimer->ops = ops; | ||
|
|
||
| stm32_t *stm32 = &stm32_ltimer->stm32_timer; | ||
|
|
||
| stm32_ltimer->user_cb_fn = callback; | ||
| stm32_ltimer->user_cb_token = callback_token; | ||
|
|
||
| stm32_map_base = ps_pmem_map(&ops, pmems, false, PS_MEM_NORMAL); | ||
| if (stm32_map_base == NULL) { | ||
| destroy(ltimer->data); | ||
| return EINVAL; | ||
| } | ||
| stm32_ltimer->stm32_timer.hw = stm32_map_base; | ||
|
|
||
| stm32_ltimer->callback_data.ltimer = ltimer; | ||
| stm32_ltimer->callback_data.irq_handler = handle_irq; | ||
| stm32_ltimer->callback_data.irq = &irqs; | ||
|
|
||
| stm32_ltimer->irq_id = ps_irq_register(&ops.irq_ops, irqs, handle_irq_wrapper, | ||
| &stm32_ltimer->callback_data); | ||
| if (stm32_ltimer->irq_id < 0) { | ||
| destroy(ltimer->data); | ||
| return EIO; | ||
| } | ||
|
|
||
| rc = stm32mp2_timer_init(&stm32_ltimer->stm32_timer, ops); | ||
| if (rc) { | ||
| ZF_LOGE("Failed to init stm32 timeout timer"); | ||
| destroy(&stm32_ltimer); | ||
| return rc; | ||
| } | ||
|
|
||
| return 0; | ||
| } | ||
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.