From 6d8b4d9e536e408d205b30eb990e73fb964ca222 Mon Sep 17 00:00:00 2001 From: bkleiner Date: Sat, 20 Apr 2024 00:26:09 +0200 Subject: [PATCH] make firmware compile for stm32g4 --- boards/STM32F405RG.json | 2 +- boards/STM32F411RE.json | 2 +- boards/STM32F722RE.json | 2 +- boards/STM32F745XG.json | 2 +- boards/STM32F765VI.json | 2 +- boards/STM32G473CE.json | 37 ++ boards/STM32H743VI.json | 2 +- platformio.ini | 20 +- script/device_gen.py | 3 +- src/core/target.h | 2 + src/driver/adc.h | 6 +- src/driver/at32/adc.c | 8 +- src/driver/fmc.h | 5 +- src/driver/stm32/adc.c | 41 +- src/driver/stm32/dma.c | 41 +- src/driver/stm32/dma.h | 17 + src/driver/stm32/exti.c | 2 +- src/driver/stm32/fmc.c | 14 +- src/driver/stm32/gpio.c | 8 +- src/driver/stm32/motor_dshot.c | 14 +- src/driver/stm32/motor_pwm.c | 2 +- src/driver/stm32/rcc.c | 2 +- src/driver/stm32/rcc.h | 2 +- src/driver/stm32/reset.c | 11 + src/driver/stm32/serial.c | 8 +- src/driver/stm32/spi.c | 23 +- src/driver/stm32/system.h | 33 +- src/driver/stm32/time.c | 3 + src/driver/stm32/timer.c | 202 +++------- src/driver/stm32/usb.c | 24 +- src/driver/timer.h | 22 +- src/system/stm32f405/flash_layout.ld | 11 - src/system/stm32g473/flash_layout.ld | 163 ++++++++ src/system/stm32g473/gpio_pins.in | 170 ++++++++ src/system/stm32g473/gpio_pins.yaml | 566 +++++++++++++++++++++++++++ src/system/stm32g473/interrupts.c | 108 +++++ src/system/stm32g473/startup.S | 239 +++++++++++ src/system/stm32g473/system.c | 141 +++++++ 38 files changed, 1742 insertions(+), 218 deletions(-) create mode 100644 boards/STM32G473CE.json create mode 100644 src/system/stm32g473/flash_layout.ld create mode 100644 src/system/stm32g473/gpio_pins.in create mode 100644 src/system/stm32g473/gpio_pins.yaml create mode 100644 src/system/stm32g473/interrupts.c create mode 100644 src/system/stm32g473/startup.S create mode 100644 src/system/stm32g473/system.c diff --git a/boards/STM32F405RG.json b/boards/STM32F405RG.json index 5221432e7..b2216fca1 100644 --- a/boards/STM32F405RG.json +++ b/boards/STM32F405RG.json @@ -34,5 +34,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32f405rg.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/boards/STM32F411RE.json b/boards/STM32F411RE.json index 8e267e78a..bedfb9369 100644 --- a/boards/STM32F411RE.json +++ b/boards/STM32F411RE.json @@ -34,5 +34,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32f411re.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/boards/STM32F722RE.json b/boards/STM32F722RE.json index b0d402e61..9c65c1a94 100644 --- a/boards/STM32F722RE.json +++ b/boards/STM32F722RE.json @@ -30,5 +30,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32f722re.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/boards/STM32F745XG.json b/boards/STM32F745XG.json index c00d1276b..269a2eeec 100644 --- a/boards/STM32F745XG.json +++ b/boards/STM32F745XG.json @@ -30,5 +30,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32f745xg.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/boards/STM32F765VI.json b/boards/STM32F765VI.json index cba9f322f..cbcbe5eb7 100644 --- a/boards/STM32F765VI.json +++ b/boards/STM32F765VI.json @@ -30,5 +30,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32f765vi.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/boards/STM32G473CE.json b/boards/STM32G473CE.json new file mode 100644 index 000000000..241193f45 --- /dev/null +++ b/boards/STM32G473CE.json @@ -0,0 +1,37 @@ +{ + "build": { + "core": "stm32", + "cpu": "cortex-m4", + "extra_flags": "-DSTM32G473xx -DSTM32G473 -DSTM32G4xx -DSTM32G4 -DSTM32 -DMCU_NAME=stm32g473 -DHSE_VALUE=8000000U -DUSE_FAST_RAM -DUSB_PMASIZE=0x400", + "f_cpu": "170000000L", + "mcu": "stm32g473", + "product_line": "STM32G473xx", + "variant": "Generic_G473" + }, + "debug": { + "jlink_device": "STM32G473CB", + "openocd_target": "stm32g4x", + "svd_path": "STM32G473xx.svd" + }, + "frameworks": [ + "arduino", + "cmsis", + "libopencm3", + "stm32cube" + ], + "name": "STM32G473CE (128k RAM. 512k Flash)", + "upload": { + "maximum_ram_size": 131072, + "maximum_size": 524288, + "protocol": "stlink", + "protocols": [ + "stlink", + "jlink", + "cmsis-dap", + "blackmagic", + "mbed" + ] + }, + "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32g473ce.html", + "vendor": "ST" +} \ No newline at end of file diff --git a/boards/STM32H743VI.json b/boards/STM32H743VI.json index acc67884c..8375da1f4 100644 --- a/boards/STM32H743VI.json +++ b/boards/STM32H743VI.json @@ -30,5 +30,5 @@ ] }, "url": "https://www.st.com/en/microcontrollers-microprocessors/stm32h743vi.html", - "vendor": "Generic" + "vendor": "ST" } \ No newline at end of file diff --git a/platformio.ini b/platformio.ini index 8b8e9f2c7..8348bed7b 100644 --- a/platformio.ini +++ b/platformio.ini @@ -35,7 +35,7 @@ build_flags = [stm32] extends = common -platform = ststm32@~17.0.0 +platform = ststm32@~17.3.0 build_src_filter = ${common.build_src_filter} + framework = stm32cube board_build.stm32cube.custom_system_setup = yes @@ -133,6 +133,24 @@ build_flags = [env:stm32h743] extends = stm32h743 +[stm32g4] +extends = stm32 +system_flags = + -mfloat-abi=hard + -mfpu=fpv4-sp-d16 + +[stm32g473] +extends = stm32g4 +board = STM32G473CE +build_src_filter = ${stm32.build_src_filter} + +board_build.ldscript = $PROJECT_DIR/src/system/stm32g473/flash_layout.ld +build_flags = + ${stm32g4.build_flags} + -Isrc/system/stm32g473 + +[env:stm32g473] +extends = stm32g473 + [at32] extends = common platform = https://github.com/ArteryTek/platform-arterytekat32.git#5729d36 diff --git a/script/device_gen.py b/script/device_gen.py index 01261eaa2..28d9de8ad 100644 --- a/script/device_gen.py +++ b/script/device_gen.py @@ -33,7 +33,7 @@ def parse_all(self): ) # roughly filter to supported devices - supported = ["stm32f4", "stm32f7", "stm32h7"] + supported = ["stm32f4", "stm32g4", "stm32f7", "stm32h7"] device_file_names = [ dfn for dfn in device_file_names if any(s in dfn for s in supported) ] @@ -109,6 +109,7 @@ def __getitem__(self, item) -> modm_devices.device.Device: devices = [ "stm32f405rg", "stm32f411re", + "stm32g473ce", "stm32f722re", "stm32f745vg", "stm32f765vi", diff --git a/src/core/target.h b/src/core/target.h index 8aacbf9dd..a191d3c26 100644 --- a/src/core/target.h +++ b/src/core/target.h @@ -45,7 +45,9 @@ typedef enum { SERIAL_PORT4, SERIAL_PORT5, #endif +#ifndef STM32G4 SERIAL_PORT6, +#endif #if defined(STM32F7) || defined(STM32H7) || defined(AT32F4) SERIAL_PORT7, SERIAL_PORT8, diff --git a/src/driver/adc.h b/src/driver/adc.h index f56b2a5ef..ace908273 100644 --- a/src/driver/adc.h +++ b/src/driver/adc.h @@ -10,7 +10,11 @@ typedef enum { ADC_DEVICE2, ADC_DEVICE3, #endif - ADC_DEVICEMAX, +#ifdef STM32G473 + ADC_DEVICE4, + ADC_DEVICE5, +#endif + ADC_DEVICE_MAX, } adc_devices_t; typedef enum { diff --git a/src/driver/at32/adc.c b/src/driver/at32/adc.c index 8be05fd2f..689af521b 100644 --- a/src/driver/at32/adc.c +++ b/src/driver/at32/adc.c @@ -14,7 +14,7 @@ extern uint16_t adc_array[ADC_CHAN_MAX]; extern adc_channel_t adc_pins[ADC_CHAN_MAX]; -static adc_type *adc_devs[ADC_DEVICEMAX] = { +static adc_type *adc_devs[ADC_DEVICE_MAX] = { ADC1, ADC2, ADC3, @@ -23,7 +23,7 @@ static adc_type *adc_devs[ADC_DEVICEMAX] = { static void adc_init_pin(adc_chan_t chan, gpio_pins_t pin) { adc_array[chan] = 1; adc_pins[chan].pin = PIN_NONE; - adc_pins[chan].dev = ADC_DEVICEMAX; + adc_pins[chan].dev = ADC_DEVICE_MAX; switch (chan) { case ADC_CHAN_VREF: @@ -70,7 +70,7 @@ static void adc_init_dev() { common_init.vbat_state = FALSE; adc_common_config(&common_init); - for (uint32_t i = 0; i < ADC_DEVICEMAX; i++) { + for (uint32_t i = 0; i < ADC_DEVICE_MAX; i++) { adc_base_config_type base_init; base_init.sequence_mode = FALSE; base_init.repeat_mode = FALSE; @@ -141,7 +141,7 @@ uint16_t adc_read_raw(adc_chan_t index) { do { last_adc_chan = (last_adc_chan + 1) % ADC_CHAN_MAX; // skip through all channels without a dev - } while (adc_pins[last_adc_chan].dev == ADC_DEVICEMAX); + } while (adc_pins[last_adc_chan].dev == ADC_DEVICE_MAX); adc_start_conversion(last_adc_chan); } diff --git a/src/driver/fmc.h b/src/driver/fmc.h index aac0ec6ab..943e68b46 100644 --- a/src/driver/fmc.h +++ b/src/driver/fmc.h @@ -4,7 +4,10 @@ #include "util/util.h" -#if defined(STM32H7) +#if defined(STM32G4) +#define FLASH_WORD_SIZE 8 +typedef uint64_t flash_word_t; +#elif defined(STM32H7) #define FLASH_WORD_SIZE 32 typedef uint64_t flash_word_t; #else diff --git a/src/driver/stm32/adc.c b/src/driver/stm32/adc.c index 6220ab227..5235e3848 100644 --- a/src/driver/stm32/adc.c +++ b/src/driver/stm32/adc.c @@ -5,12 +5,25 @@ typedef struct { ADC_Common_TypeDef *common; } adc_dev_t; -#ifdef STM32H7 +#if defined(STM32G4) +#define ADC_INTERNAL_CHANNEL ADC_DEVICE1 +#define LL_ADC_CHANNEL_TEMPSENSOR LL_ADC_CHANNEL_TEMPSENSOR_ADC1 +#define ADC_SAMPLINGTIME LL_ADC_SAMPLINGTIME_247CYCLES_5 +#define READY_TO_CONVERT(dev) LL_ADC_IsActiveFlag_EOC(dev) + +static const adc_dev_t adc_dev[ADC_DEVICE_MAX] = { + {.adc = ADC1, .common = ADC12_COMMON}, + {.adc = ADC2, .common = ADC12_COMMON}, + {.adc = ADC3, .common = ADC345_COMMON}, + {.adc = ADC4, .common = ADC345_COMMON}, + {.adc = ADC5, .common = ADC345_COMMON}, +}; +#elif defined(STM32H7) #define ADC_INTERNAL_CHANNEL ADC_DEVICE3 #define ADC_SAMPLINGTIME LL_ADC_SAMPLINGTIME_387CYCLES_5 #define READY_TO_CONVERT(dev) LL_ADC_IsActiveFlag_EOC(dev) -static const adc_dev_t adc_dev[ADC_DEVICEMAX] = { +static const adc_dev_t adc_dev[ADC_DEVICE_MAX] = { {.adc = ADC1, .common = ADC12_COMMON}, {.adc = ADC2, .common = ADC12_COMMON}, {.adc = ADC3, .common = ADC3_COMMON}, @@ -20,7 +33,7 @@ static const adc_dev_t adc_dev[ADC_DEVICEMAX] = { #define ADC_SAMPLINGTIME LL_ADC_SAMPLINGTIME_480CYCLES #define READY_TO_CONVERT(dev) LL_ADC_IsActiveFlag_EOCS(dev) -static const adc_dev_t adc_dev[ADC_DEVICEMAX] = { +static const adc_dev_t adc_dev[ADC_DEVICE_MAX] = { {.adc = ADC1, .common = ADC}, }; #endif @@ -56,7 +69,7 @@ static const uint32_t channel_map[] = { static void adc_init_pin(adc_chan_t chan, gpio_pins_t pin) { adc_array[chan] = 1; adc_pins[chan].pin = PIN_NONE; - adc_pins[chan].dev = ADC_DEVICEMAX; + adc_pins[chan].dev = ADC_DEVICE_MAX; switch (chan) { case ADC_CHAN_VREF: @@ -117,7 +130,10 @@ static void adc_init_dev(adc_devices_t index) { LL_ADC_InitTypeDef adc_init; adc_init.Resolution = LL_ADC_RESOLUTION_12B; -#ifdef STM32H7 +#if defined(STM32G4) + adc_init.DataAlignment = LL_ADC_DATA_ALIGN_RIGHT; + adc_init.LowPowerMode = LL_ADC_LP_MODE_NONE; +#elif defined(STM32H7) adc_init.LeftBitShift = LL_ADC_LEFT_BIT_SHIFT_NONE; adc_init.LowPowerMode = LL_ADC_LP_MODE_NONE; #else @@ -134,7 +150,7 @@ static void adc_init_dev(adc_devices_t index) { LL_ADC_SetCommonPathInternalCh(dev->common, LL_ADC_PATH_INTERNAL_TEMPSENSOR); } -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) LL_ADC_DisableDeepPowerDown(dev->adc); LL_ADC_EnableInternalRegulator(dev->adc); time_delay_us(LL_ADC_DELAY_INTERNAL_REGUL_STAB_US); @@ -148,7 +164,7 @@ static void adc_init_dev(adc_devices_t index) { LL_ADC_Enable(dev->adc); -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) while (LL_ADC_IsActiveFlag_ADRDY(dev->adc) == 0) ; #endif @@ -165,7 +181,7 @@ static void adc_start_conversion(adc_chan_t index) { LL_ADC_SetChannelSamplingTime(dev->adc, chan->channel, ADC_SAMPLINGTIME); LL_ADC_REG_SetSequencerRanks(dev->adc, LL_ADC_REG_RANK_1, chan->channel); -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) LL_ADC_REG_StartConversion(dev->adc); #else LL_ADC_REG_StartConversionSWStart(dev->adc); @@ -173,7 +189,10 @@ static void adc_start_conversion(adc_chan_t index) { } void adc_init() { -#ifdef STM32H7 +#if defined(STM32G4) + rcc_enable(RCC_AHB2_GRP1(ADC12)); + rcc_enable(RCC_AHB2_GRP1(ADC345)); +#elif defined(STM32H7) rcc_enable(RCC_AHB1_GRP1(ADC12)); rcc_enable(RCC_AHB4_GRP1(ADC3)); #else @@ -192,7 +211,7 @@ void adc_init() { adc_init_pin(ADC_CHAN_IBAT, target.ibat); } - for (uint32_t i = 0; i < ADC_DEVICEMAX; i++) { + for (uint32_t i = 0; i < ADC_DEVICE_MAX; i++) { adc_init_dev(i); } @@ -211,7 +230,7 @@ uint16_t adc_read_raw(adc_chan_t index) { do { last_adc_chan = (last_adc_chan + 1) % ADC_CHAN_MAX; // skip through all channels without a dev - } while (adc_pins[last_adc_chan].dev == ADC_DEVICEMAX); + } while (adc_pins[last_adc_chan].dev == ADC_DEVICE_MAX); adc_start_conversion(last_adc_chan); } diff --git a/src/driver/stm32/dma.c b/src/driver/stm32/dma.c index 2797a6198..13e7af8fe 100644 --- a/src/driver/stm32/dma.c +++ b/src/driver/stm32/dma.c @@ -2,6 +2,7 @@ #include "driver/rcc.h" +#if !defined(STM32G4) // DMA1 Stream0 SPI3_RX // DMA1 Stream1 // DMA1 Stream2 @@ -32,8 +33,35 @@ DMA_STREAM(2, 6, 3, TIM1_CH1) \ DMA_STREAM(2, 6, 6, TIM1_CH3) \ DMA_STREAM(2, 6, 4, TIM1_CH4) +#else +#define DMA_STREAMS \ + DMA_STREAM(1, 0, 1, SPI1_RX) \ + DMA_STREAM(1, 0, 2, SPI1_TX) \ + DMA_STREAM(1, 0, 3, SPI2_RX) \ + DMA_STREAM(1, 0, 4, SPI2_TX) \ + DMA_STREAM(1, 0, 5, SPI3_RX) \ + DMA_STREAM(1, 0, 6, SPI3_TX) \ + DMA_STREAM(1, 0, 7, SPI4_RX) \ + DMA_STREAM(1, 0, 8, SPI4_TX) \ + DMA_STREAM(2, 0, 1, TIM1_CH1) \ + DMA_STREAM(2, 0, 2, TIM1_CH3) \ + DMA_STREAM(2, 0, 3, TIM1_CH4) +#endif -#ifdef STM32H7 +#if defined(STM32G4) +#define DMA_STREAM(_port, _chan, _stream, _dev) \ + [DMA_DEVICE_##_dev] = { \ + .device = DMA_DEVICE_##_dev, \ + .port = DMA##_port, \ + .port_index = _port, \ + .channel = 0, \ + .channel_index = 0, \ + .request = LL_DMAMUX_REQ_##_dev, \ + .stream = DMA##_port##_Channel##_stream, \ + .stream_index = LL_DMA_CHANNEL_##_stream, \ + .irq = DMA##_port##_Channel##_stream##_IRQn, \ + }, +#elif defined(STM32H7) #define DMA_STREAM(_port, _chan, _stream, _dev) \ [DMA_DEVICE_##_dev] = { \ .device = DMA_DEVICE_##_dev, \ @@ -87,6 +115,10 @@ void dma_prepare_rx_memory(void *addr, uint32_t size) { } void dma_enable_rcc(dma_device_t dev) { +#ifdef STM32G4 + rcc_enable(RCC_AHB1_GRP1(DMAMUX1)); +#endif + const dma_stream_def_t *dma = &dma_stream_defs[dev]; switch (dma->port_index) { case 1: @@ -125,10 +157,9 @@ static void handle_dma_stream_isr(dma_device_t dev) { } } -#define DMA_STREAM(_port, _chan, _stream, _dev) \ - void DMA##_port##_Stream##_stream##_IRQHandler() { \ - handle_dma_stream_isr(DMA_DEVICE_##_dev); \ - } +#define DMA_STREAM(_port, _chan, _stream, _dev) \ + void DMA##_port##_Stream##_stream##_IRQHandler() { handle_dma_stream_isr(DMA_DEVICE_##_dev); } \ + void DMA##_port##_Channel##_stream##_IRQHandler() { handle_dma_stream_isr(DMA_DEVICE_##_dev); } DMA_STREAMS diff --git a/src/driver/stm32/dma.h b/src/driver/stm32/dma.h index b47d6011c..4f6269627 100644 --- a/src/driver/stm32/dma.h +++ b/src/driver/stm32/dma.h @@ -1,5 +1,20 @@ #pragma once +#ifdef STM32G4 +#define DMA_FLAG_TE (0x1 << 3) +#define DMA_FLAG_HT (0x1 << 2) +#define DMA_FLAG_TC (0x1 << 1) +#define DMA_FLAG_GI (0x1 << 0) + +#define dma_flag_for_channel(dev, flags) ((flags) << (dev->stream_index * 4)) +#define dma_is_flag_active_tc(dev) READ_BIT(dev->port->ISR, dma_flag_for_channel(dev, DMA_FLAG_TC)) +#define dma_clear_flag_tc(dev) WRITE_REG(dev->port->IFCR, dma_flag_for_channel(dev, DMA_FLAG_TC | DMA_FLAG_TE | DMA_FLAG_HT | DMA_FLAG_GI)); + +#define LL_DMA_EnableStream LL_DMA_EnableChannel +#define LL_DMA_DisableStream LL_DMA_DisableChannel +#define LL_DMA_IsEnabledStream LL_DMA_IsEnabledChannel + +#else #define DMA_FLAG_TC (0x1 << 5) #define DMA_FLAG_HT (0x1 << 4) #define DMA_FLAG_TE (0x1 << 3) @@ -19,3 +34,5 @@ static const uint32_t _dma_flag_shift[] = {0, 6, 16, 22, 0, 6, 16, 22}; else \ WRITE_REG(dev->port->HIFCR, dma_flag_for_channel(dev, DMA_FLAG_TC | DMA_FLAG_TE | DMA_FLAG_HT | DMA_FLAG_FE)); \ } + +#endif \ No newline at end of file diff --git a/src/driver/stm32/exti.c b/src/driver/stm32/exti.c index 6beb94945..e0f2e84cf 100644 --- a/src/driver/stm32/exti.c +++ b/src/driver/stm32/exti.c @@ -172,7 +172,7 @@ void EXTI15_10_IRQHandler() { handle_exit_isr(); } -#if defined(STM32F4) || defined(STM32F7) || defined(STM32H7) +#if defined(STM32F4) || defined(STM32F7) || defined(STM32H7) || defined(STM32G4) #define EXTI5_IRQn EXTI9_5_IRQn #define EXTI6_IRQn EXTI9_5_IRQn diff --git a/src/driver/stm32/fmc.c b/src/driver/stm32/fmc.c index 0c65b4fd7..2be8c385d 100644 --- a/src/driver/stm32/fmc.c +++ b/src/driver/stm32/fmc.c @@ -13,7 +13,9 @@ #define FLASH_FLAG_ALL_ERRORS (FLASH_FLAG_EOP | FLASH_FLAG_OPERR | FLASH_FLAG_WRPERR | FLASH_FLAG_PGSERR) #endif -#ifdef STM32H7 +#if defined(STM32G4) +#define PROGRAM_TYPE FLASH_TYPEPROGRAM_DOUBLEWORD +#elif defined(STM32H7) #define PROGRAM_TYPE FLASH_TYPEPROGRAM_FLASHWORD #else #define PROGRAM_TYPE FLASH_TYPEPROGRAM_WORD @@ -34,7 +36,15 @@ void fmc_unlock() { void fmc_erase() { // clear error status __HAL_FLASH_CLEAR_FLAG(FLASH_FLAG_ALL_ERRORS); -#ifdef STM32H7 +#if defined(STM32G4) + uint32_t page_error; + FLASH_EraseInitTypeDef erase_init; + erase_init.TypeErase = FLASH_TYPEERASE_PAGES; + erase_init.Banks = FLASH_BANK_1; + erase_init.Page = 24; + erase_init.NbPages = 8; + HAL_FLASHEx_Erase(&erase_init, &page_error); +#elif defined(STM32H7) FLASH_Erase_Sector(FLASH_SECTOR_1, FLASH_BANK_BOTH, FLASH_VOLTAGE_RANGE_3); #else FLASH_Erase_Sector(FLASH_SECTOR_3, FLASH_VOLTAGE_RANGE_3); diff --git a/src/driver/stm32/gpio.c b/src/driver/stm32/gpio.c index 3ac97d389..1c35a77b4 100644 --- a/src/driver/stm32/gpio.c +++ b/src/driver/stm32/gpio.c @@ -35,9 +35,13 @@ void gpio_ports_init() { RCC->AHB1ENR, RCC_AHB1ENR_GPIOAEN | RCC_AHB1ENR_GPIOBEN | RCC_AHB1ENR_GPIOCEN | RCC_AHB1ENR_GPIODEN | RCC_AHB1ENR_GPIOEEN | RCC_AHB1ENR_GPIOHEN); +#endif - // for exit - rcc_enable(RCC_APB2_GRP1(SYSCFG)); +#ifdef STM32G4 + SET_BIT( + RCC->AHB2ENR, + RCC_AHB2ENR_GPIOAEN | RCC_AHB2ENR_GPIOBEN | RCC_AHB2ENR_GPIOCEN | + RCC_AHB2ENR_GPIODEN | RCC_AHB2ENR_GPIOEEN | RCC_AHB2ENR_GPIOFEN); #endif #ifdef STM32F7 diff --git a/src/driver/stm32/motor_dshot.c b/src/driver/stm32/motor_dshot.c index e3fb601b7..953494c48 100644 --- a/src/driver/stm32/motor_dshot.c +++ b/src/driver/stm32/motor_dshot.c @@ -108,11 +108,12 @@ static void dshot_init_gpio_port(dshot_gpio_port_t *port) { const dma_stream_def_t *dma = &dma_stream_defs[port->dma_device]; + dma_enable_rcc(port->dma_device); LL_DMA_DeInit(dma->port, dma->stream_index); LL_DMA_InitTypeDef DMA_InitStructure; LL_DMA_StructInit(&DMA_InitStructure); -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) DMA_InitStructure.PeriphRequest = dma->request; #else DMA_InitStructure.Channel = dma->channel; @@ -127,9 +128,11 @@ static void dshot_init_gpio_port(dshot_gpio_port_t *port) { DMA_InitStructure.MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_WORD; DMA_InitStructure.Mode = LL_DMA_MODE_NORMAL; DMA_InitStructure.Priority = LL_DMA_PRIORITY_VERYHIGH; +#ifndef STM32G4 DMA_InitStructure.FIFOMode = LL_DMA_FIFOMODE_DISABLE; DMA_InitStructure.MemBurst = LL_DMA_MBURST_SINGLE; DMA_InitStructure.PeriphBurst = LL_DMA_PBURST_SINGLE; +#endif LL_DMA_Init(dma->port, dma->stream_index, &DMA_InitStructure); interrupt_enable(dma->irq, DMA_PRIORITY); @@ -173,10 +176,8 @@ void motor_dshot_init() { gpio_port_count = 0; rcc_enable(RCC_APB2_GRP1(TIM1)); - rcc_enable(RCC_AHB1_GRP1(DMA2)); // setup timer to 1/3 of the full bit time - LL_TIM_InitTypeDef tim_init; LL_TIM_StructInit(&tim_init); tim_init.Autoreload = DSHOT_SYMBOL_TIME; @@ -185,6 +186,7 @@ void motor_dshot_init() { tim_init.CounterMode = LL_TIM_COUNTERMODE_UP; LL_TIM_Init(TIM1, &tim_init); LL_TIM_EnableARRPreload(TIM1); + LL_TIM_DisableMasterSlaveMode(TIM1); for (uint32_t i = 0; i < MOTOR_PIN_MAX; i++) { dshot_init_motor_pin(i); @@ -210,9 +212,9 @@ static void dshot_dma_setup_port(uint32_t index) { dma_clear_flag_tc(dma); - dma->stream->PAR = (uint32_t)&port->gpio->BSRR; - dma->stream->M0AR = (uint32_t)&port_dma_buffer[index][0]; - dma->stream->NDTR = DSHOT_DMA_BUFFER_SIZE; + LL_DMA_SetPeriphAddress(dma->port, dma->stream_index, (uint32_t)&port->gpio->BSRR); + LL_DMA_SetMemoryAddress(dma->port, dma->stream_index, (uint32_t)&port_dma_buffer[index][0]); + LL_DMA_SetDataLength(dma->port, dma->stream_index, DSHOT_DMA_BUFFER_SIZE); LL_DMA_EnableStream(dma->port, dma->stream_index); dshot_enable_dma_request(port->timer_channel); diff --git a/src/driver/stm32/motor_pwm.c b/src/driver/stm32/motor_pwm.c index 28a50956e..1b26ea667 100644 --- a/src/driver/stm32/motor_pwm.c +++ b/src/driver/stm32/motor_pwm.c @@ -48,7 +48,7 @@ void motor_pwm_init() { timer_up_init(tim, PWM_DIVIDER, PWM_TOP); LL_TIM_OC_Init(timer_defs[tim].instance, timer_channel_val(ch), &tim_oc_init); LL_TIM_EnableCounter(timer_defs[tim].instance); -#ifndef STM32F411 +#if defined(TIMER14) if (tim != TIMER14) { LL_TIM_EnableAllOutputs(timer_defs[tim].instance); } diff --git a/src/driver/stm32/rcc.c b/src/driver/stm32/rcc.c index 9ce53079e..9dd04373d 100644 --- a/src/driver/stm32/rcc.c +++ b/src/driver/stm32/rcc.c @@ -24,7 +24,7 @@ void rcc_enable(rcc_reg_t reg) { case RCC_APB1_GRP1: LL_APB1_GRP1_EnableClock(periph); break; -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) case RCC_APB1_GRP2: LL_APB1_GRP2_EnableClock(periph); break; diff --git a/src/driver/stm32/rcc.h b/src/driver/stm32/rcc.h index bbe62c015..42a95ee0d 100644 --- a/src/driver/stm32/rcc.h +++ b/src/driver/stm32/rcc.h @@ -13,7 +13,7 @@ typedef enum { RCC_AHB4_GRP1, #endif RCC_APB1_GRP1, -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) RCC_APB1_GRP2, #endif RCC_APB2_GRP1, diff --git a/src/driver/stm32/reset.c b/src/driver/stm32/reset.c index 827ac0ae2..b71bbe371 100644 --- a/src/driver/stm32/reset.c +++ b/src/driver/stm32/reset.c @@ -8,6 +8,12 @@ #define BOOTLOADER_OFFSET 0x1FFF0000 #endif +#ifdef STM32G4 +#define BOOTLOADER_OFFSET 0x1FFF0000 +#define LL_RTC_BAK_SetRegister LL_RTC_BKP_SetRegister +#define LL_RTC_BAK_GetRegister LL_RTC_BKP_GetRegister +#endif + #ifdef STM32F7 #define BOOTLOADER_OFFSET 0x1FF00000 #endif @@ -40,6 +46,11 @@ __attribute__((__used__)) void system_check_for_bootloader() { case RESET_BOOTLOADER_MAGIC: { backup_register_write(0); + HAL_RCC_DeInit(); +#ifdef __HAL_SYSCFG_REMAPMEMORY_SYSTEMFLASH + __HAL_SYSCFG_REMAPMEMORY_SYSTEMFLASH(); +#endif + void (*DfuBootJump)(void) = (void (*)(void))(*((uint32_t *)(BOOTLOADER_OFFSET + 4))); __set_MSP(*((uint32_t *)BOOTLOADER_OFFSET)); DfuBootJump(); diff --git a/src/driver/stm32/serial.c b/src/driver/stm32/serial.c index 50905c22b..5fd285898 100644 --- a/src/driver/stm32/serial.c +++ b/src/driver/stm32/serial.c @@ -36,12 +36,14 @@ const usart_port_def_t usart_port_defs[SERIAL_PORT_MAX] = { .rcc = RCC_APB1_GRP1(UART5), }, #endif +#ifndef STM32G4 { .channel_index = 6, .channel = USART6, .irq = USART6_IRQn, .rcc = RCC_APB2_GRP1(USART6), }, +#endif #if defined(STM32F7) || defined(STM32H7) { .channel_index = 7, @@ -98,7 +100,7 @@ void handle_usart_invert(serial_ports_t port, bool invert) { gpio_pin_reset(dev->inverter); } #endif -#if defined(STM32F7) || defined(STM32H7) +#if defined(STM32F7) || defined(STM32H7) || defined(STM32G4) if (invert) { LL_USART_SetRXPinLevel(USART.channel, LL_USART_RXPIN_LEVEL_INVERTED); LL_USART_SetTXPinLevel(USART.channel, LL_USART_TXPIN_LEVEL_INVERTED); @@ -137,7 +139,7 @@ void serial_hard_init(serial_port_t *serial, serial_port_config_t config, bool s } #endif -#if !defined(STM32F7) && !defined(STM32H7) +#if !defined(STM32F7) && !defined(STM32H7) && !defined(STM32G4) LL_USART_ClearFlag_RXNE(USART.channel); #endif LL_USART_ClearFlag_TC(USART.channel); @@ -268,7 +270,9 @@ USART_IRQ_HANDLER(3) USART_IRQ_HANDLER(4) USART_IRQ_HANDLER(5) #endif +#ifndef STM32G4 USART_IRQ_HANDLER(6) +#endif #if defined(STM32F7) || defined(STM32H7) USART_IRQ_HANDLER(7) USART_IRQ_HANDLER(8) diff --git a/src/driver/stm32/spi.c b/src/driver/stm32/spi.c index defc716f8..2cf2184e0 100644 --- a/src/driver/stm32/spi.c +++ b/src/driver/stm32/spi.c @@ -110,11 +110,14 @@ static void spi_dma_init_rx(spi_ports_t port) { LL_DMA_DeInit(dma->port, dma->stream_index); LL_DMA_InitTypeDef DMA_InitStructure; -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) DMA_InitStructure.PeriphRequest = dma->request; - DMA_InitStructure.PeriphOrM2MSrcAddress = (uint32_t)&PORT.channel->RXDR; #else DMA_InitStructure.Channel = dma->channel; +#endif +#if defined(STM32H7) + DMA_InitStructure.PeriphOrM2MSrcAddress = (uint32_t)&PORT.channel->RXDR; +#else DMA_InitStructure.PeriphOrM2MSrcAddress = LL_SPI_DMA_GetRegAddr(PORT.channel); #endif DMA_InitStructure.MemoryOrM2MDstAddress = 0; @@ -126,9 +129,11 @@ static void spi_dma_init_rx(spi_ports_t port) { DMA_InitStructure.MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_BYTE; DMA_InitStructure.Mode = LL_DMA_MODE_NORMAL; DMA_InitStructure.Priority = LL_DMA_PRIORITY_HIGH; +#ifndef STM32G4 DMA_InitStructure.FIFOMode = LL_DMA_FIFOMODE_DISABLE; DMA_InitStructure.MemBurst = LL_DMA_MBURST_SINGLE; DMA_InitStructure.PeriphBurst = LL_DMA_PBURST_SINGLE; +#endif LL_DMA_Init(dma->port, dma->stream_index, &DMA_InitStructure); } @@ -138,11 +143,14 @@ static void spi_dma_init_tx(spi_ports_t port) { LL_DMA_DeInit(dma->port, dma->stream_index); LL_DMA_InitTypeDef DMA_InitStructure; -#ifdef STM32H7 +#if defined(STM32H7) || defined(STM32G4) DMA_InitStructure.PeriphRequest = dma->request; - DMA_InitStructure.PeriphOrM2MSrcAddress = (uint32_t)&PORT.channel->TXDR; #else DMA_InitStructure.Channel = dma->channel; +#endif +#if defined(STM32H7) + DMA_InitStructure.PeriphOrM2MSrcAddress = (uint32_t)&PORT.channel->TXDR; +#else DMA_InitStructure.PeriphOrM2MSrcAddress = LL_SPI_DMA_GetRegAddr(PORT.channel); #endif DMA_InitStructure.MemoryOrM2MDstAddress = 0; @@ -154,9 +162,11 @@ static void spi_dma_init_tx(spi_ports_t port) { DMA_InitStructure.MemoryOrM2MDstDataSize = LL_DMA_MDATAALIGN_BYTE; DMA_InitStructure.Mode = LL_DMA_MODE_NORMAL; DMA_InitStructure.Priority = LL_DMA_PRIORITY_VERYHIGH; +#ifndef STM32G4 DMA_InitStructure.FIFOMode = LL_DMA_FIFOMODE_DISABLE; DMA_InitStructure.MemBurst = LL_DMA_MBURST_SINGLE; DMA_InitStructure.PeriphBurst = LL_DMA_PBURST_SINGLE; +#endif LL_DMA_Init(dma->port, dma->stream_index, &DMA_InitStructure); } @@ -267,6 +277,11 @@ static void spi_device_init(spi_ports_t port) { LL_SPI_SetFIFOThreshold(def->channel, LL_SPI_FIFO_TH_01DATA); #endif LL_SPI_Init(def->channel, &default_init); +#if defined(STM32G4) + LL_SPI_SetRxFIFOThreshold(def->channel, LL_SPI_RX_FIFO_TH_QUARTER); + LL_SPI_SetStandard(def->channel, LL_SPI_PROTOCOL_MOTOROLA); + LL_SPI_DisableNSSPulseMgt(def->channel); +#endif spi_dev[port].is_init = true; spi_dev[port].dma_done = true; diff --git a/src/driver/stm32/system.h b/src/driver/stm32/system.h index d15d1cabe..7aa7da0d7 100644 --- a/src/driver/stm32/system.h +++ b/src/driver/stm32/system.h @@ -16,6 +16,23 @@ #include #endif +#ifdef STM32G4 +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#endif + #ifdef STM32F7 #include #include @@ -50,12 +67,20 @@ #ifdef STM32F411 #define SYS_CLOCK_FREQ_HZ 108000000 -#define PWM_CLOCK_FREQ_HZ 108000000 +#define PWM_CLOCK_FREQ_HZ SYS_CLOCK_FREQ_HZ #define SPI_CLOCK_FREQ_HZ (SYS_CLOCK_FREQ_HZ / 2) #define LOOPTIME_MAX 250 #endif +#ifdef STM32G473 +#define SYS_CLOCK_FREQ_HZ 168000000 +#define PWM_CLOCK_FREQ_HZ SYS_CLOCK_FREQ_HZ +#define SPI_CLOCK_FREQ_HZ SYS_CLOCK_FREQ_HZ + +#define LOOPTIME_MAX 125 +#endif + #ifdef STM32F405 #define SYS_CLOCK_FREQ_HZ 168000000 #define PWM_CLOCK_FREQ_HZ 84000000 @@ -66,7 +91,7 @@ #ifdef STM32F7 #define SYS_CLOCK_FREQ_HZ 216000000 -#define PWM_CLOCK_FREQ_HZ 216000000 +#define PWM_CLOCK_FREQ_HZ SYS_CLOCK_FREQ_HZ #define SPI_CLOCK_FREQ_HZ (SYS_CLOCK_FREQ_HZ / 4) #define LOOPTIME_MAX 125 @@ -102,7 +127,11 @@ typedef struct { uint32_t request; +#ifdef STM32G4 + DMA_Channel_TypeDef *stream; +#else DMA_Stream_TypeDef *stream; +#endif uint8_t stream_index; IRQn_Type irq; diff --git a/src/driver/stm32/time.c b/src/driver/stm32/time.c index 588df6d1d..69a025112 100644 --- a/src/driver/stm32/time.c +++ b/src/driver/stm32/time.c @@ -33,6 +33,9 @@ void time_init() { #endif __HAL_RCC_SYSCFG_CLK_ENABLE(); +#ifdef STM32G4 + LL_PWR_DisableUCPDDeadBattery(); +#endif // interrupt only every 1ms SysTick_Config(SYS_CLOCK_FREQ_HZ / 1000); diff --git a/src/driver/stm32/timer.c b/src/driver/stm32/timer.c index db8984347..5827fde3e 100644 --- a/src/driver/stm32/timer.c +++ b/src/driver/stm32/timer.c @@ -6,98 +6,45 @@ const timer_def_t timer_defs[TIMER_MAX] = { [TIMER_INVALID] = {}, - [TIMER1] = { - .rcc = RCC_APB2_GRP1(TIM1), - .irq = TIM1_UP_TIM10_IRQn, - .instance = TIM1, - }, - [TIMER2] = { - .rcc = RCC_APB1_GRP1(TIM2), - .irq = TIM2_IRQn, - .instance = TIM2, - }, - [TIMER3] = { - .rcc = RCC_APB1_GRP1(TIM3), - .irq = TIM3_IRQn, - .instance = TIM3, - }, - [TIMER4] = { - .rcc = RCC_APB1_GRP1(TIM4), - .irq = TIM4_IRQn, - .instance = TIM4, - }, - [TIMER5] = { - .rcc = RCC_APB1_GRP1(TIM5), - .irq = TIM5_IRQn, - .instance = TIM5, - }, +#if defined(STM32G4) + [TIMER1] = {.rcc = RCC_APB2_GRP1(TIM1), .irq = TIM1_UP_TIM16_IRQn, .instance = TIM1}, + [TIMER2] = {.rcc = RCC_APB1_GRP1(TIM2), .irq = TIM2_IRQn, .instance = TIM2}, + [TIMER3] = {.rcc = RCC_APB1_GRP1(TIM3), .irq = TIM3_IRQn, .instance = TIM3}, + [TIMER4] = {.rcc = RCC_APB1_GRP1(TIM4), .irq = TIM4_IRQn, .instance = TIM4}, + [TIMER5] = {.rcc = RCC_APB1_GRP1(TIM5), .irq = TIM5_IRQn, .instance = TIM5}, + [TIMER6] = {.rcc = RCC_APB1_GRP1(TIM6), .irq = TIM6_DAC_IRQn, .instance = TIM6}, + [TIMER7] = {.rcc = RCC_APB1_GRP1(TIM7), .irq = TIM7_DAC_IRQn, .instance = TIM7}, + [TIMER8] = {.rcc = RCC_APB2_GRP1(TIM8), .irq = TIM8_UP_IRQn, .instance = TIM8}, + [TIMER15] = {.rcc = RCC_APB2_GRP1(TIM15), .irq = TIM1_BRK_TIM15_IRQn, .instance = TIM15}, + [TIMER16] = {.rcc = RCC_APB2_GRP1(TIM16), .irq = TIM1_UP_TIM16_IRQn, .instance = TIM16}, + [TIMER17] = {.rcc = RCC_APB2_GRP1(TIM17), .irq = TIM1_TRG_COM_TIM17_IRQn, .instance = TIM17}, + [TIMER20] = {.rcc = RCC_APB2_GRP1(TIM20), .irq = TIM20_UP_IRQn, .instance = TIM20}, +#else + [TIMER1] = {.rcc = RCC_APB2_GRP1(TIM1), .irq = TIM1_UP_TIM10_IRQn, .instance = TIM1}, + [TIMER2] = {.rcc = RCC_APB1_GRP1(TIM2), .irq = TIM2_IRQn, .instance = TIM2}, + [TIMER3] = {.rcc = RCC_APB1_GRP1(TIM3), .irq = TIM3_IRQn, .instance = TIM3}, + [TIMER4] = {.rcc = RCC_APB1_GRP1(TIM4), .irq = TIM4_IRQn, .instance = TIM4}, + [TIMER5] = {.rcc = RCC_APB1_GRP1(TIM5), .irq = TIM5_IRQn, .instance = TIM5}, #ifndef STM32F411 - [TIMER6] = { - .rcc = RCC_APB1_GRP1(TIM6), - .irq = TIM6_DAC_IRQn, - .instance = TIM6, - }, - [TIMER7] = { - .rcc = RCC_APB1_GRP1(TIM7), - .irq = TIM7_IRQn, - .instance = TIM7, - }, - [TIMER8] = { - .rcc = RCC_APB2_GRP1(TIM8), - .irq = TIM8_UP_TIM13_IRQn, - .instance = TIM8, - }, + [TIMER6] = {.rcc = RCC_APB1_GRP1(TIM6), .irq = TIM6_DAC_IRQn, .instance = TIM6}, + [TIMER7] = {.rcc = RCC_APB1_GRP1(TIM7), .irq = TIM7_IRQn, .instance = TIM7}, + [TIMER8] = {.rcc = RCC_APB2_GRP1(TIM8), .irq = TIM8_UP_TIM13_IRQn, .instance = TIM8}, #endif #ifndef STM32H7 - [TIMER9] = { - .rcc = RCC_APB2_GRP1(TIM9), - .irq = TIM1_BRK_TIM9_IRQn, - .instance = TIM9, - }, - [TIMER10] = { - .rcc = RCC_APB2_GRP1(TIM10), - .irq = TIM1_UP_TIM10_IRQn, - .instance = TIM10, - }, - [TIMER11] = { - .rcc = RCC_APB2_GRP1(TIM11), - .irq = TIM1_TRG_COM_TIM11_IRQn, - .instance = TIM11, - }, + [TIMER9] = {.rcc = RCC_APB2_GRP1(TIM9), .irq = TIM1_BRK_TIM9_IRQn, .instance = TIM9}, + [TIMER10] = {.rcc = RCC_APB2_GRP1(TIM10), .irq = TIM1_UP_TIM10_IRQn, .instance = TIM10}, + [TIMER11] = {.rcc = RCC_APB2_GRP1(TIM11), .irq = TIM1_TRG_COM_TIM11_IRQn, .instance = TIM11}, #endif #ifndef STM32F411 - [TIMER12] = { - .rcc = RCC_APB1_GRP1(TIM12), - .irq = TIM8_BRK_TIM12_IRQn, - .instance = TIM12, - }, - [TIMER13] = { - .rcc = RCC_APB1_GRP1(TIM13), - .irq = TIM8_UP_TIM13_IRQn, - .instance = TIM13, - }, - [TIMER14] = { - .rcc = RCC_APB1_GRP1(TIM14), - .irq = TIM8_TRG_COM_TIM14_IRQn, - .instance = TIM14, - }, + [TIMER12] = {.rcc = RCC_APB1_GRP1(TIM12), .irq = TIM8_BRK_TIM12_IRQn, .instance = TIM12}, + [TIMER13] = {.rcc = RCC_APB1_GRP1(TIM13), .irq = TIM8_UP_TIM13_IRQn, .instance = TIM13}, + [TIMER14] = {.rcc = RCC_APB1_GRP1(TIM14), .irq = TIM8_TRG_COM_TIM14_IRQn, .instance = TIM14}, #endif #ifdef STM32H743 - [TIMER15] = { - .rcc = RCC_APB2_GRP1(TIM15), - .irq = TIM15_IRQn, - .instance = TIM15, - }, - [TIMER16] = { - .rcc = RCC_APB2_GRP1(TIM16), - .irq = TIM16_IRQn, - .instance = TIM16, - }, - [TIMER17] = { - .rcc = RCC_APB2_GRP1(TIM17), - .irq = TIM17_IRQn, - .instance = TIM17, - }, + [TIMER15] = {.rcc = RCC_APB2_GRP1(TIM15), .irq = TIM15_IRQn, .instance = TIM15}, + [TIMER16] = {.rcc = RCC_APB2_GRP1(TIM16), .irq = TIM16_IRQn, .instance = TIM16}, + [TIMER17] = {.rcc = RCC_APB2_GRP1(TIM17), .irq = TIM17_IRQn, .instance = TIM17}, +#endif #endif }; @@ -149,63 +96,28 @@ static void timer_irq_handler() { #undef TIM1_TRG_COM_TIM11_IRQHandler #endif -void TIM15_IRQHandler() { - timer_irq_handler(); -} -void TIM16_IRQHandler() { - timer_irq_handler(); -} -void TIM17_IRQHandler() { - timer_irq_handler(); -} -void TIM1_BRK_IRQHandler() { - timer_irq_handler(); -} -void TIM1_BRK_TIM9_IRQHandler() { - timer_irq_handler(); -} -void TIM1_CC_IRQHandler() { - timer_irq_handler(); -} -void TIM1_TRG_COM_IRQHandler() { - timer_irq_handler(); -} -void TIM1_TRG_COM_TIM11_IRQHandler() { - timer_irq_handler(); -} -void TIM1_UP_IRQHandler() { - timer_irq_handler(); -} -void TIM1_UP_TIM10_IRQHandler() { - timer_irq_handler(); -} -void TIM2_IRQHandler() { - timer_irq_handler(); -} -void TIM3_IRQHandler() { - timer_irq_handler(); -} -void TIM4_IRQHandler() { - timer_irq_handler(); -} -void TIM5_IRQHandler() { - timer_irq_handler(); -} -void TIM6_DAC_IRQHandler() { - timer_irq_handler(); -} -void TIM7_IRQHandler() { - timer_irq_handler(); -} -void TIM8_BRK_TIM12_IRQHandler() { - timer_irq_handler(); -} -void TIM8_CC_IRQHandler() { - timer_irq_handler(); -} -void TIM8_TRG_COM_TIM14_IRQHandler() { - timer_irq_handler(); -} -void TIM8_UP_TIM13_IRQHandler() { - timer_irq_handler(); -} +void TIM1_BRK_IRQHandler() { timer_irq_handler(); } +void TIM1_BRK_TIM15_IRQHandler() { timer_irq_handler(); } +void TIM1_BRK_TIM9_IRQHandler() { timer_irq_handler(); } +void TIM1_CC_IRQHandler() { timer_irq_handler(); } +void TIM1_TRG_COM_IRQHandler() { timer_irq_handler(); } +void TIM1_TRG_COM_TIM11_IRQHandler() { timer_irq_handler(); } +void TIM1_TRG_COM_TIM17_IRQHandler() { timer_irq_handler(); } +void TIM1_UP_IRQHandler() { timer_irq_handler(); } +void TIM1_UP_TIM10_IRQHandler() { timer_irq_handler(); } +void TIM1_UP_TIM16_IRQHandler() { timer_irq_handler(); } +void TIM15_IRQHandler() { timer_irq_handler(); } +void TIM16_IRQHandler() { timer_irq_handler(); } +void TIM17_IRQHandler() { timer_irq_handler(); } +void TIM2_IRQHandler() { timer_irq_handler(); } +void TIM20_UP_IRQHandler() { timer_irq_handler(); } +void TIM3_IRQHandler() { timer_irq_handler(); } +void TIM4_IRQHandler() { timer_irq_handler(); } +void TIM5_IRQHandler() { timer_irq_handler(); } +void TIM6_DAC_IRQHandler() { timer_irq_handler(); } +void TIM7_DAC_IRQHandler() { timer_irq_handler(); } +void TIM7_IRQHandler() { timer_irq_handler(); } +void TIM8_BRK_TIM12_IRQHandler() { timer_irq_handler(); } +void TIM8_TRG_COM_TIM14_IRQHandler() { timer_irq_handler(); } +void TIM8_UP_IRQHandler() { timer_irq_handler(); } +void TIM8_UP_TIM13_IRQHandler() { timer_irq_handler(); } \ No newline at end of file diff --git a/src/driver/stm32/usb.c b/src/driver/stm32/usb.c index 0d16df287..e9da6de2f 100644 --- a/src/driver/stm32/usb.c +++ b/src/driver/stm32/usb.c @@ -19,6 +19,14 @@ #define CDC_PROTOCOL USB_PROTO_NONE +#ifdef STM32G4 +#define USB_IRQ USB_LP_IRQn +#define USB_IRQ_HANDLER USB_LP_IRQHandler +#else +#define USB_IRQ OTG_FS_IRQn +#define USB_IRQ_HANDLER OTG_FS_IRQHandler +#endif + struct cdc_config { struct usb_config_descriptor config; struct usb_iad_descriptor comm_iad; @@ -222,7 +230,7 @@ static usbd_respond cdc_control(usbd_device *dev, usbd_ctlreq *req, usbd_rqc_cal static void cdc_rxonly(usbd_device *dev, uint8_t event, uint8_t ep) { if (ring_buffer_free(&usb_rx_buffer) <= CDC_DATA_SZ) { - interrupt_disable(OTG_FS_IRQn); + interrupt_disable(USB_IRQ); rx_stalled = true; return; } @@ -241,9 +249,9 @@ static void cdc_kickoff_rx() { return; } - interrupt_disable(OTG_FS_IRQn); + interrupt_disable(USB_IRQ); cdc_rxonly(&udev, 0, CDC_RXD_EP); - interrupt_enable(OTG_FS_IRQn, USB_PRIORITY); + interrupt_enable(USB_IRQ, USB_PRIORITY); } static void cdc_txonly(usbd_device *dev, uint8_t event, uint8_t ep) { @@ -278,9 +286,9 @@ static void cdc_kickoff_tx() { return; } - interrupt_disable(OTG_FS_IRQn); + interrupt_disable(USB_IRQ); cdc_txonly(&udev, 0, CDC_TXD_EP); - interrupt_enable(OTG_FS_IRQn, USB_PRIORITY); + interrupt_enable(USB_IRQ, USB_PRIORITY); } static usbd_respond cdc_setconf(usbd_device *dev, uint8_t cfg) { @@ -311,11 +319,12 @@ static usbd_respond cdc_setconf(usbd_device *dev, uint8_t cfg) { } } -void OTG_FS_IRQHandler() { +void USB_IRQ_HANDLER() { usbd_poll(&udev); } void usb_drv_init() { +#ifndef STM32G4 gpio_config_t gpio_init; gpio_init.mode = GPIO_ALTERNATE; gpio_init.output = GPIO_PUSHPULL; @@ -328,9 +337,10 @@ void usb_drv_init() { #else gpio_pin_init_af(PIN_A11, gpio_init, GPIO_AF10_OTG_FS); gpio_pin_init_af(PIN_A12, gpio_init, GPIO_AF10_OTG_FS); +#endif #endif - interrupt_enable(OTG_FS_IRQn, USB_PRIORITY); + interrupt_enable(USB_IRQ, USB_PRIORITY); usbd_init(&udev, &usbd_hw, CDC_EP0_SIZE, ubuf, sizeof(ubuf)); usbd_reg_config(&udev, cdc_setconf); diff --git a/src/driver/timer.h b/src/driver/timer.h index 9a704c8ef..843ba6d55 100644 --- a/src/driver/timer.h +++ b/src/driver/timer.h @@ -6,6 +6,20 @@ typedef enum { TIMER_INVALID, +#if defined(STM32G4) + TIMER1, + TIMER2, + TIMER3, + TIMER4, + TIMER5, + TIMER6, + TIMER7, + TIMER8, + TIMER15, + TIMER16, + TIMER17, + TIMER20, +#else TIMER1, TIMER2, TIMER3, @@ -19,18 +33,19 @@ typedef enum { TIMER9, TIMER10, TIMER11, -#ifndef STM32F411 +#if !defined(STM32F411) && !defined(STM32G473) TIMER12, TIMER13, TIMER14, #endif -#ifdef STM32H743 +#if defined(STM32H743) || defined(STM32G473) TIMER15, TIMER16, TIMER17, #endif -#ifdef AT32F4 +#if defined(AT32F4) || defined(STM32G473) TIMER20, +#endif #endif TIMER_MAX, } timer_index_t; @@ -44,6 +59,7 @@ typedef enum { TIMER_CH3 = (0x1 << 4), TIMER_CH3N = (0x1 << 5), TIMER_CH4 = (0x1 << 6), + TIMER_CH4N = (0x1 << 7), TIMER_CH_ALL = 0xff, } timer_channel_t; diff --git a/src/system/stm32f405/flash_layout.ld b/src/system/stm32f405/flash_layout.ld index ef3b63885..6a0969494 100644 --- a/src/system/stm32f405/flash_layout.ld +++ b/src/system/stm32f405/flash_layout.ld @@ -54,7 +54,6 @@ MEMORY FLASH_CONFIG (r) : ORIGIN = 0x0800C000, LENGTH = 16K FLASH_CODE (rx) : ORIGIN = 0x08010000, LENGTH = 960K RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 128K - MEMORY_B1 (rx) : ORIGIN = 0x60000000, LENGTH = 0K FAST_RAM (rw) : ORIGIN = 0x10000000, LENGTH = 64K } @@ -185,16 +184,6 @@ SECTIONS . = ALIGN(4); } >FAST_RAM - /* MEMORY_bank1 section, code must be located here explicitly */ - /* Example: extern int foo() __attribute__ ((section (".mb1text"))); */ - .memory_b1_text : - { - *(.mb1text) /* .mb1text sections (code) */ - *(.mb1text*) /* .mb1text* sections (code) */ - *(.mb1rodata) /* read-only data (constants) */ - *(.mb1rodata*) - } >MEMORY_B1 - /* Remove information from the standard libraries */ /DISCARD/ : { diff --git a/src/system/stm32g473/flash_layout.ld b/src/system/stm32g473/flash_layout.ld new file mode 100644 index 000000000..8f9b97a7c --- /dev/null +++ b/src/system/stm32g473/flash_layout.ld @@ -0,0 +1,163 @@ +/* Entry Point */ +ENTRY(Reset_Handler) + +/* Highest address of the user mode stack */ +_estack = ORIGIN(FAST_RAM) + LENGTH(FAST_RAM); /* end of 128K RAM */ + +/* Generate a link error if heap and stack don't fit into RAM */ +_Min_Heap_Size = 0; /* required amount of heap */ +_Min_Stack_Size = 0x4000; /* required amount of stack */ + +/* Specify the memory areas */ +/* +Flash Layout: +0x08000000 - 0x0800C000: isr, rodata, data (Section 0 - Section 2) +0x0800C000 - 0x08010000: configuration, profile (Section 3) +0x08010000 - 0x080FFFFF: code (Section 4 - Section 11) +*/ +MEMORY +{ + FLASH (rx) : ORIGIN = 0x08000000, LENGTH = 48K + FLASH_CONFIG (r) : ORIGIN = 0x0800C000, LENGTH = 16K + FLASH_CODE (rx) : ORIGIN = 0x08010000, LENGTH = 448K + FAST_RAM (rw) : ORIGIN = 0x10000000, LENGTH = 32K + RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 96K +} + +/* Define output sections */ +SECTIONS +{ + .config_flash : + { + _config_flash_start = .; + KEEP(*(.config_flash)) + _config_flash_end = .; + } >FLASH_CONFIG + + /* The startup code goes first into FLASH */ + .isr_vector : + { + . = ALIGN(4); + KEEP(*(.isr_vector)) /* Startup code */ + . = ALIGN(4); + } >FLASH + + /* The program code and other data goes into FLASH */ + .text : + { + . = ALIGN(4); + *(.text) /* .text sections (code) */ + *(.text*) /* .text* sections (code) */ + *(.glue_7) /* glue arm to thumb code */ + *(.glue_7t) /* glue thumb to arm code */ + *(.eh_frame) + + KEEP (*(.init)) + KEEP (*(.fini)) + + . = ALIGN(4); + _etext = .; /* define a global symbols at end of code */ + } >FLASH_CODE + + /* Constant data goes into FLASH */ + .rodata : + { + . = ALIGN(4); + *(.rodata) /* .rodata sections (constants, strings, etc.) */ + *(.rodata*) /* .rodata* sections (constants, strings, etc.) */ + . = ALIGN(4); + } >FLASH + + .ARM.extab : { *(.ARM.extab* .gnu.linkonce.armextab.*) } >FLASH + .ARM : { + __exidx_start = .; + *(.ARM.exidx*) + __exidx_end = .; + } >FLASH + + .preinit_array : + { + PROVIDE_HIDDEN (__preinit_array_start = .); + KEEP (*(.preinit_array*)) + PROVIDE_HIDDEN (__preinit_array_end = .); + } >FLASH + .init_array : + { + PROVIDE_HIDDEN (__init_array_start = .); + KEEP (*(SORT(.init_array.*))) + KEEP (*(.init_array*)) + PROVIDE_HIDDEN (__init_array_end = .); + } >FLASH + .fini_array : + { + PROVIDE_HIDDEN (__fini_array_start = .); + KEEP (*(SORT(.fini_array.*))) + KEEP (*(.fini_array*)) + PROVIDE_HIDDEN (__fini_array_end = .); + } >FLASH + + /* used by the startup to initialize data */ + _sidata = LOADADDR(.data); + + /* Initialized data sections goes into RAM, load LMA copy after code */ + .data : + { + . = ALIGN(4); + _sdata = .; /* create a global symbol at data start */ + *(.data) /* .data sections */ + *(.data*) /* .data* sections */ + + . = ALIGN(4); + _edata = .; /* define a global symbol at data end */ + } >RAM AT> FLASH + + _fast_ram_data = LOADADDR(.fast_ram); + + .fast_ram : + { + . = ALIGN(4); + _fast_ram_start = .; /* create a global symbol at fast_ram start */ + *(.fast_ram) + *(.fast_ram*) + + . = ALIGN(4); + _fast_ram_end = .; /* create a global symbol at fast_ram end */ + } >FAST_RAM AT> FLASH + + /* Uninitialized data section */ + . = ALIGN(4); + .bss : + { + /* This is used by the startup in order to initialize the .bss secion */ + _sbss = .; /* define a global symbol at bss start */ + __bss_start__ = _sbss; + *(.bss) + *(.bss*) + *(COMMON) + + . = ALIGN(4); + _ebss = .; /* define a global symbol at bss end */ + __bss_end__ = _ebss; + } >RAM + + /* User_heap_stack section, used to check that there is enough RAM left */ + ._user_heap_stack : + { + . = ALIGN(4); + PROVIDE ( end = . ); + PROVIDE ( _end = . ); + . = . + _Min_Heap_Size; + . = . + _Min_Stack_Size; + . = ALIGN(4); + } >FAST_RAM + + /* Remove information from the standard libraries */ + /DISCARD/ : + { + libc.a ( * ) + libm.a ( * ) + libgcc.a ( * ) + } + + .ARM.attributes 0 : { *(.ARM.attributes) } +} diff --git a/src/system/stm32g473/gpio_pins.in b/src/system/stm32g473/gpio_pins.in new file mode 100644 index 000000000..c2abe55f1 --- /dev/null +++ b/src/system/stm32g473/gpio_pins.in @@ -0,0 +1,170 @@ +GPIO_PIN(A, 0) +GPIO_AF(PIN_A0, -1, ADC_TAG(ADC_DEVICE1, 1)) +GPIO_AF(PIN_A0, -1, ADC_TAG(ADC_DEVICE2, 1)) +GPIO_AF(PIN_A0, 1, TIMER_TAG(TIMER2, TIMER_CH1)) +GPIO_AF(PIN_A0, 2, TIMER_TAG(TIMER5, TIMER_CH1)) +GPIO_PIN(A, 1) +GPIO_AF(PIN_A1, -1, ADC_TAG(ADC_DEVICE1, 2)) +GPIO_AF(PIN_A1, -1, ADC_TAG(ADC_DEVICE2, 2)) +GPIO_AF(PIN_A1, 1, TIMER_TAG(TIMER2, TIMER_CH2)) +GPIO_AF(PIN_A1, 2, TIMER_TAG(TIMER5, TIMER_CH2)) +GPIO_AF(PIN_A1, 9, TIMER_TAG(TIMER15, TIMER_CH1N)) +GPIO_PIN(A, 2) +GPIO_AF(PIN_A2, -1, ADC_TAG(ADC_DEVICE1, 3)) +GPIO_AF(PIN_A2, 1, TIMER_TAG(TIMER2, TIMER_CH3)) +GPIO_AF(PIN_A2, 2, TIMER_TAG(TIMER5, TIMER_CH3)) +GPIO_AF(PIN_A2, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_TX)) +GPIO_AF(PIN_A2, 9, TIMER_TAG(TIMER15, TIMER_CH1)) +GPIO_PIN(A, 3) +GPIO_AF(PIN_A3, -1, ADC_TAG(ADC_DEVICE1, 4)) +GPIO_AF(PIN_A3, 1, TIMER_TAG(TIMER2, TIMER_CH4)) +GPIO_AF(PIN_A3, 2, TIMER_TAG(TIMER5, TIMER_CH4)) +GPIO_AF(PIN_A3, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_RX)) +GPIO_AF(PIN_A3, 9, TIMER_TAG(TIMER15, TIMER_CH2)) +GPIO_PIN(A, 4) +GPIO_AF(PIN_A4, -1, ADC_TAG(ADC_DEVICE2, 17)) +GPIO_AF(PIN_A4, 2, TIMER_TAG(TIMER3, TIMER_CH2)) +GPIO_PIN(A, 5) +GPIO_AF(PIN_A5, -1, ADC_TAG(ADC_DEVICE2, 13)) +GPIO_AF(PIN_A5, 1, TIMER_TAG(TIMER2, TIMER_CH1)) +GPIO_AF(PIN_A5, 5, SPI_TAG(SPI_PORT1, RES_SPI_SCK)) +GPIO_PIN(A, 6) +GPIO_AF(PIN_A6, -1, ADC_TAG(ADC_DEVICE2, 3)) +GPIO_AF(PIN_A6, 1, TIMER_TAG(TIMER16, TIMER_CH1)) +GPIO_AF(PIN_A6, 2, TIMER_TAG(TIMER3, TIMER_CH1)) +GPIO_AF(PIN_A6, 5, SPI_TAG(SPI_PORT1, RES_SPI_MISO)) +GPIO_PIN(A, 7) +GPIO_AF(PIN_A7, -1, ADC_TAG(ADC_DEVICE2, 4)) +GPIO_AF(PIN_A7, 1, TIMER_TAG(TIMER17, TIMER_CH1)) +GPIO_AF(PIN_A7, 2, TIMER_TAG(TIMER3, TIMER_CH2)) +GPIO_AF(PIN_A7, 4, TIMER_TAG(TIMER8, TIMER_CH1N)) +GPIO_AF(PIN_A7, 5, SPI_TAG(SPI_PORT1, RES_SPI_MOSI)) +GPIO_AF(PIN_A7, 6, TIMER_TAG(TIMER1, TIMER_CH1N)) +GPIO_PIN(A, 8) +GPIO_AF(PIN_A8, -1, ADC_TAG(ADC_DEVICE5, 1)) +GPIO_AF(PIN_A8, 6, TIMER_TAG(TIMER1, TIMER_CH1)) +GPIO_PIN(A, 9) +GPIO_AF(PIN_A9, -1, ADC_TAG(ADC_DEVICE5, 2)) +GPIO_AF(PIN_A9, 6, TIMER_TAG(TIMER1, TIMER_CH2)) +GPIO_AF(PIN_A9, 7, SERIAL_TAG(SERIAL_PORT1, RES_SERIAL_TX)) +GPIO_AF(PIN_A9, 10, TIMER_TAG(TIMER2, TIMER_CH3)) +GPIO_PIN(A, 10) +GPIO_AF(PIN_A10, 5, SPI_TAG(SPI_PORT2, RES_SPI_MISO)) +GPIO_AF(PIN_A10, 6, TIMER_TAG(TIMER1, TIMER_CH3)) +GPIO_AF(PIN_A10, 7, SERIAL_TAG(SERIAL_PORT1, RES_SERIAL_RX)) +GPIO_AF(PIN_A10, 10, TIMER_TAG(TIMER2, TIMER_CH4)) +GPIO_PIN(A, 11) +GPIO_AF(PIN_A11, 5, SPI_TAG(SPI_PORT2, RES_SPI_MOSI)) +GPIO_AF(PIN_A11, 6, TIMER_TAG(TIMER1, TIMER_CH1N)) +GPIO_AF(PIN_A11, 10, TIMER_TAG(TIMER4, TIMER_CH1)) +GPIO_AF(PIN_A11, 11, TIMER_TAG(TIMER1, TIMER_CH4)) +GPIO_PIN(A, 12) +GPIO_AF(PIN_A12, 1, TIMER_TAG(TIMER16, TIMER_CH1)) +GPIO_AF(PIN_A12, 6, TIMER_TAG(TIMER1, TIMER_CH2N)) +GPIO_AF(PIN_A12, 10, TIMER_TAG(TIMER4, TIMER_CH2)) +GPIO_PIN(A, 13) +GPIO_AF(PIN_A13, 1, TIMER_TAG(TIMER16, TIMER_CH1N)) +GPIO_AF(PIN_A13, 10, TIMER_TAG(TIMER4, TIMER_CH3)) +GPIO_PIN(A, 14) +GPIO_AF(PIN_A14, 5, TIMER_TAG(TIMER8, TIMER_CH2)) +GPIO_AF(PIN_A14, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_TX)) +GPIO_PIN(A, 15) +GPIO_AF(PIN_A15, 1, TIMER_TAG(TIMER2, TIMER_CH1)) +GPIO_AF(PIN_A15, 2, TIMER_TAG(TIMER8, TIMER_CH1)) +GPIO_AF(PIN_A15, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_RX)) +GPIO_PIN(B, 0) +GPIO_AF(PIN_B0, -1, ADC_TAG(ADC_DEVICE1, 15)) +GPIO_AF(PIN_B0, -1, ADC_TAG(ADC_DEVICE3, 12)) +GPIO_AF(PIN_B0, 2, TIMER_TAG(TIMER3, TIMER_CH3)) +GPIO_AF(PIN_B0, 4, TIMER_TAG(TIMER8, TIMER_CH2N)) +GPIO_AF(PIN_B0, 6, TIMER_TAG(TIMER1, TIMER_CH2N)) +GPIO_PIN(B, 1) +GPIO_AF(PIN_B1, -1, ADC_TAG(ADC_DEVICE1, 12)) +GPIO_AF(PIN_B1, -1, ADC_TAG(ADC_DEVICE3, 1)) +GPIO_AF(PIN_B1, 2, TIMER_TAG(TIMER3, TIMER_CH4)) +GPIO_AF(PIN_B1, 4, TIMER_TAG(TIMER8, TIMER_CH3N)) +GPIO_AF(PIN_B1, 6, TIMER_TAG(TIMER1, TIMER_CH3N)) +GPIO_PIN(B, 2) +GPIO_AF(PIN_B2, -1, ADC_TAG(ADC_DEVICE2, 12)) +GPIO_AF(PIN_B2, 2, TIMER_TAG(TIMER5, TIMER_CH1)) +GPIO_AF(PIN_B2, 3, TIMER_TAG(TIMER20, TIMER_CH1)) +GPIO_PIN(B, 3) +GPIO_AF(PIN_B3, 1, TIMER_TAG(TIMER2, TIMER_CH2)) +GPIO_AF(PIN_B3, 4, TIMER_TAG(TIMER8, TIMER_CH1N)) +GPIO_AF(PIN_B3, 5, SPI_TAG(SPI_PORT1, RES_SPI_SCK)) +GPIO_AF(PIN_B3, 6, SPI_TAG(SPI_PORT3, RES_SPI_SCK)) +GPIO_AF(PIN_B3, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_TX)) +GPIO_PIN(B, 4) +GPIO_AF(PIN_B4, 1, TIMER_TAG(TIMER16, TIMER_CH1)) +GPIO_AF(PIN_B4, 2, TIMER_TAG(TIMER3, TIMER_CH1)) +GPIO_AF(PIN_B4, 4, TIMER_TAG(TIMER8, TIMER_CH2N)) +GPIO_AF(PIN_B4, 5, SPI_TAG(SPI_PORT1, RES_SPI_MISO)) +GPIO_AF(PIN_B4, 6, SPI_TAG(SPI_PORT3, RES_SPI_MISO)) +GPIO_AF(PIN_B4, 7, SERIAL_TAG(SERIAL_PORT2, RES_SERIAL_RX)) +GPIO_PIN(B, 5) +GPIO_AF(PIN_B5, 2, TIMER_TAG(TIMER3, TIMER_CH2)) +GPIO_AF(PIN_B5, 3, TIMER_TAG(TIMER8, TIMER_CH3N)) +GPIO_AF(PIN_B5, 5, SPI_TAG(SPI_PORT1, RES_SPI_MOSI)) +GPIO_AF(PIN_B5, 6, SPI_TAG(SPI_PORT3, RES_SPI_MOSI)) +GPIO_AF(PIN_B5, 10, TIMER_TAG(TIMER17, TIMER_CH1)) +GPIO_PIN(B, 6) +GPIO_AF(PIN_B6, 1, TIMER_TAG(TIMER16, TIMER_CH1N)) +GPIO_AF(PIN_B6, 2, TIMER_TAG(TIMER4, TIMER_CH1)) +GPIO_AF(PIN_B6, 5, TIMER_TAG(TIMER8, TIMER_CH1)) +GPIO_AF(PIN_B6, 7, SERIAL_TAG(SERIAL_PORT1, RES_SERIAL_TX)) +GPIO_PIN(B, 7) +GPIO_AF(PIN_B7, 1, TIMER_TAG(TIMER17, TIMER_CH1N)) +GPIO_AF(PIN_B7, 2, TIMER_TAG(TIMER4, TIMER_CH2)) +GPIO_AF(PIN_B7, 7, SERIAL_TAG(SERIAL_PORT1, RES_SERIAL_RX)) +GPIO_AF(PIN_B7, 10, TIMER_TAG(TIMER3, TIMER_CH4)) +GPIO_PIN(B, 8) +GPIO_AF(PIN_B8, 1, TIMER_TAG(TIMER16, TIMER_CH1)) +GPIO_AF(PIN_B8, 2, TIMER_TAG(TIMER4, TIMER_CH3)) +GPIO_AF(PIN_B8, 7, SERIAL_TAG(SERIAL_PORT3, RES_SERIAL_RX)) +GPIO_AF(PIN_B8, 10, TIMER_TAG(TIMER8, TIMER_CH2)) +GPIO_PIN(B, 9) +GPIO_AF(PIN_B9, 1, TIMER_TAG(TIMER17, TIMER_CH1)) +GPIO_AF(PIN_B9, 2, TIMER_TAG(TIMER4, TIMER_CH4)) +GPIO_AF(PIN_B9, 7, SERIAL_TAG(SERIAL_PORT3, RES_SERIAL_TX)) +GPIO_AF(PIN_B9, 10, TIMER_TAG(TIMER8, TIMER_CH3)) +GPIO_AF(PIN_B9, 12, TIMER_TAG(TIMER1, TIMER_CH3N)) +GPIO_PIN(B, 10) +GPIO_AF(PIN_B10, 1, TIMER_TAG(TIMER2, TIMER_CH3)) +GPIO_AF(PIN_B10, 7, SERIAL_TAG(SERIAL_PORT3, RES_SERIAL_TX)) +GPIO_PIN(B, 11) +GPIO_AF(PIN_B11, -1, ADC_TAG(ADC_DEVICE1, 14)) +GPIO_AF(PIN_B11, -1, ADC_TAG(ADC_DEVICE2, 14)) +GPIO_AF(PIN_B11, 1, TIMER_TAG(TIMER2, TIMER_CH4)) +GPIO_AF(PIN_B11, 7, SERIAL_TAG(SERIAL_PORT3, RES_SERIAL_RX)) +GPIO_PIN(B, 12) +GPIO_AF(PIN_B12, -1, ADC_TAG(ADC_DEVICE1, 11)) +GPIO_AF(PIN_B12, -1, ADC_TAG(ADC_DEVICE4, 3)) +GPIO_PIN(B, 13) +GPIO_AF(PIN_B13, -1, ADC_TAG(ADC_DEVICE3, 5)) +GPIO_AF(PIN_B13, 5, SPI_TAG(SPI_PORT2, RES_SPI_SCK)) +GPIO_AF(PIN_B13, 6, TIMER_TAG(TIMER1, TIMER_CH1N)) +GPIO_PIN(B, 14) +GPIO_AF(PIN_B14, -1, ADC_TAG(ADC_DEVICE1, 5)) +GPIO_AF(PIN_B14, -1, ADC_TAG(ADC_DEVICE4, 4)) +GPIO_AF(PIN_B14, 1, TIMER_TAG(TIMER15, TIMER_CH1)) +GPIO_AF(PIN_B14, 5, SPI_TAG(SPI_PORT2, RES_SPI_MISO)) +GPIO_AF(PIN_B14, 6, TIMER_TAG(TIMER1, TIMER_CH2N)) +GPIO_PIN(B, 15) +GPIO_AF(PIN_B15, -1, ADC_TAG(ADC_DEVICE2, 15)) +GPIO_AF(PIN_B15, -1, ADC_TAG(ADC_DEVICE4, 5)) +GPIO_AF(PIN_B15, 1, TIMER_TAG(TIMER15, TIMER_CH2)) +GPIO_AF(PIN_B15, 2, TIMER_TAG(TIMER15, TIMER_CH1N)) +GPIO_AF(PIN_B15, 4, TIMER_TAG(TIMER1, TIMER_CH3N)) +GPIO_AF(PIN_B15, 5, SPI_TAG(SPI_PORT2, RES_SPI_MOSI)) +GPIO_PIN(C, 13) +GPIO_AF(PIN_C13, 4, TIMER_TAG(TIMER1, TIMER_CH1N)) +GPIO_AF(PIN_C13, 6, TIMER_TAG(TIMER8, TIMER_CH4N)) +GPIO_PIN(C, 14) +GPIO_PIN(C, 15) +GPIO_PIN(F, 0) +GPIO_AF(PIN_F0, -1, ADC_TAG(ADC_DEVICE1, 10)) +GPIO_AF(PIN_F0, 6, TIMER_TAG(TIMER1, TIMER_CH3N)) +GPIO_PIN(F, 1) +GPIO_AF(PIN_F1, -1, ADC_TAG(ADC_DEVICE2, 10)) +GPIO_AF(PIN_F1, 5, SPI_TAG(SPI_PORT2, RES_SPI_SCK)) +GPIO_PIN(G, 10) diff --git a/src/system/stm32g473/gpio_pins.yaml b/src/system/stm32g473/gpio_pins.yaml new file mode 100644 index 000000000..d0f272a90 --- /dev/null +++ b/src/system/stm32g473/gpio_pins.yaml @@ -0,0 +1,566 @@ +PA0: +- func: adc + af: -1 + instance: 1 + name: '1' +- func: adc + af: -1 + instance: 2 + name: '1' +- func: timer + af: 1 + instance: 2 + name: ch1 +- func: timer + af: 2 + instance: 5 + name: ch1 +PA1: +- func: adc + af: -1 + instance: 1 + name: '2' +- func: adc + af: -1 + instance: 2 + name: '2' +- func: timer + af: 1 + instance: 2 + name: ch2 +- func: timer + af: 2 + instance: 5 + name: ch2 +- func: timer + af: 9 + instance: 15 + name: ch1n +PA2: +- func: adc + af: -1 + instance: 1 + name: '3' +- func: timer + af: 1 + instance: 2 + name: ch3 +- func: timer + af: 2 + instance: 5 + name: ch3 +- func: serial + af: 7 + instance: 2 + name: tx +- func: timer + af: 9 + instance: 15 + name: ch1 +PA3: +- func: adc + af: -1 + instance: 1 + name: '4' +- func: timer + af: 1 + instance: 2 + name: ch4 +- func: timer + af: 2 + instance: 5 + name: ch4 +- func: serial + af: 7 + instance: 2 + name: rx +- func: timer + af: 9 + instance: 15 + name: ch2 +PA4: +- func: adc + af: -1 + instance: 2 + name: '17' +- func: timer + af: 2 + instance: 3 + name: ch2 +PA5: +- func: adc + af: -1 + instance: 2 + name: '13' +- func: timer + af: 1 + instance: 2 + name: ch1 +- func: spi + af: 5 + instance: 1 + name: sck +PA6: +- func: adc + af: -1 + instance: 2 + name: '3' +- func: timer + af: 1 + instance: 16 + name: ch1 +- func: timer + af: 2 + instance: 3 + name: ch1 +- func: spi + af: 5 + instance: 1 + name: miso +PA7: +- func: adc + af: -1 + instance: 2 + name: '4' +- func: timer + af: 1 + instance: 17 + name: ch1 +- func: timer + af: 2 + instance: 3 + name: ch2 +- func: timer + af: 4 + instance: 8 + name: ch1n +- func: spi + af: 5 + instance: 1 + name: mosi +- func: timer + af: 6 + instance: 1 + name: ch1n +PA8: +- func: adc + af: -1 + instance: 5 + name: '1' +- func: timer + af: 6 + instance: 1 + name: ch1 +PA9: +- func: adc + af: -1 + instance: 5 + name: '2' +- func: timer + af: 6 + instance: 1 + name: ch2 +- func: serial + af: 7 + instance: 1 + name: tx +- func: timer + af: 10 + instance: 2 + name: ch3 +PA10: +- func: spi + af: 5 + instance: 2 + name: miso +- func: timer + af: 6 + instance: 1 + name: ch3 +- func: serial + af: 7 + instance: 1 + name: rx +- func: timer + af: 10 + instance: 2 + name: ch4 +PA11: +- func: spi + af: 5 + instance: 2 + name: mosi +- func: timer + af: 6 + instance: 1 + name: ch1n +- func: timer + af: 10 + instance: 4 + name: ch1 +- func: timer + af: 11 + instance: 1 + name: ch4 +PA12: +- func: timer + af: 1 + instance: 16 + name: ch1 +- func: timer + af: 6 + instance: 1 + name: ch2n +- func: timer + af: 10 + instance: 4 + name: ch2 +PA13: +- func: timer + af: 1 + instance: 16 + name: ch1n +- func: timer + af: 10 + instance: 4 + name: ch3 +PA14: +- func: timer + af: 5 + instance: 8 + name: ch2 +- func: serial + af: 7 + instance: 2 + name: tx +PA15: +- func: timer + af: 1 + instance: 2 + name: ch1 +- func: timer + af: 2 + instance: 8 + name: ch1 +- func: serial + af: 7 + instance: 2 + name: rx +PB0: +- func: adc + af: -1 + instance: 1 + name: '15' +- func: adc + af: -1 + instance: 3 + name: '12' +- func: timer + af: 2 + instance: 3 + name: ch3 +- func: timer + af: 4 + instance: 8 + name: ch2n +- func: timer + af: 6 + instance: 1 + name: ch2n +PB1: +- func: adc + af: -1 + instance: 1 + name: '12' +- func: adc + af: -1 + instance: 3 + name: '1' +- func: timer + af: 2 + instance: 3 + name: ch4 +- func: timer + af: 4 + instance: 8 + name: ch3n +- func: timer + af: 6 + instance: 1 + name: ch3n +PB2: +- func: adc + af: -1 + instance: 2 + name: '12' +- func: timer + af: 2 + instance: 5 + name: ch1 +- func: timer + af: 3 + instance: 20 + name: ch1 +PB3: +- func: timer + af: 1 + instance: 2 + name: ch2 +- func: timer + af: 4 + instance: 8 + name: ch1n +- func: spi + af: 5 + instance: 1 + name: sck +- func: spi + af: 6 + instance: 3 + name: sck +- func: serial + af: 7 + instance: 2 + name: tx +PB4: +- func: timer + af: 1 + instance: 16 + name: ch1 +- func: timer + af: 2 + instance: 3 + name: ch1 +- func: timer + af: 4 + instance: 8 + name: ch2n +- func: spi + af: 5 + instance: 1 + name: miso +- func: spi + af: 6 + instance: 3 + name: miso +- func: serial + af: 7 + instance: 2 + name: rx +PB5: +- func: timer + af: 2 + instance: 3 + name: ch2 +- func: timer + af: 3 + instance: 8 + name: ch3n +- func: spi + af: 5 + instance: 1 + name: mosi +- func: spi + af: 6 + instance: 3 + name: mosi +- func: timer + af: 10 + instance: 17 + name: ch1 +PB6: +- func: timer + af: 1 + instance: 16 + name: ch1n +- func: timer + af: 2 + instance: 4 + name: ch1 +- func: timer + af: 5 + instance: 8 + name: ch1 +- func: serial + af: 7 + instance: 1 + name: tx +PB7: +- func: timer + af: 1 + instance: 17 + name: ch1n +- func: timer + af: 2 + instance: 4 + name: ch2 +- func: serial + af: 7 + instance: 1 + name: rx +- func: timer + af: 10 + instance: 3 + name: ch4 +PB8: +- func: timer + af: 1 + instance: 16 + name: ch1 +- func: timer + af: 2 + instance: 4 + name: ch3 +- func: serial + af: 7 + instance: 3 + name: rx +- func: timer + af: 10 + instance: 8 + name: ch2 +PB9: +- func: timer + af: 1 + instance: 17 + name: ch1 +- func: timer + af: 2 + instance: 4 + name: ch4 +- func: serial + af: 7 + instance: 3 + name: tx +- func: timer + af: 10 + instance: 8 + name: ch3 +- func: timer + af: 12 + instance: 1 + name: ch3n +PB10: +- func: timer + af: 1 + instance: 2 + name: ch3 +- func: serial + af: 7 + instance: 3 + name: tx +PB11: +- func: adc + af: -1 + instance: 1 + name: '14' +- func: adc + af: -1 + instance: 2 + name: '14' +- func: timer + af: 1 + instance: 2 + name: ch4 +- func: serial + af: 7 + instance: 3 + name: rx +PB12: +- func: adc + af: -1 + instance: 1 + name: '11' +- func: adc + af: -1 + instance: 4 + name: '3' +PB13: +- func: adc + af: -1 + instance: 3 + name: '5' +- func: spi + af: 5 + instance: 2 + name: sck +- func: timer + af: 6 + instance: 1 + name: ch1n +PB14: +- func: adc + af: -1 + instance: 1 + name: '5' +- func: adc + af: -1 + instance: 4 + name: '4' +- func: timer + af: 1 + instance: 15 + name: ch1 +- func: spi + af: 5 + instance: 2 + name: miso +- func: timer + af: 6 + instance: 1 + name: ch2n +PB15: +- func: adc + af: -1 + instance: 2 + name: '15' +- func: adc + af: -1 + instance: 4 + name: '5' +- func: timer + af: 1 + instance: 15 + name: ch2 +- func: timer + af: 2 + instance: 15 + name: ch1n +- func: timer + af: 4 + instance: 1 + name: ch3n +- func: spi + af: 5 + instance: 2 + name: mosi +PC13: +- func: timer + af: 4 + instance: 1 + name: ch1n +- func: timer + af: 6 + instance: 8 + name: ch4n +PC14: [] +PC15: [] +PF0: +- func: adc + af: -1 + instance: 1 + name: '10' +- func: timer + af: 6 + instance: 1 + name: ch3n +PF1: +- func: adc + af: -1 + instance: 2 + name: '10' +- func: spi + af: 5 + instance: 2 + name: sck +PG10: [] diff --git a/src/system/stm32g473/interrupts.c b/src/system/stm32g473/interrupts.c new file mode 100644 index 000000000..ad6023284 --- /dev/null +++ b/src/system/stm32g473/interrupts.c @@ -0,0 +1,108 @@ +__attribute__((weak)) void Default_Handler(); + +__attribute__((used)) void Default_Handler_Proxy() { + Default_Handler(); +} + +__attribute__((weak, alias("Default_Handler_Proxy"))) void NMI_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void HardFault_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void MemManage_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void BusFault_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void UsageFault_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SVC_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DebugMon_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void PendSV_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SysTick_Handler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void WWDG_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void PVD_PVM_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void RTC_TAMP_LSECSS_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void RTC_WKUP_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FLASH_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void RCC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI0_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel6_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel7_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void ADC1_2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USB_HP_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USB_LP_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN1_IT0_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN1_IT1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI9_5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM1_BRK_TIM15_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM1_UP_TIM16_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM1_TRG_COM_TIM17_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM1_CC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C1_EV_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C1_ER_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C2_EV_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C2_ER_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SPI1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SPI2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USART1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USART2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USART3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void EXTI15_10_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void RTC_Alarm_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void USBWakeUp_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM8_BRK_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM8_UP_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM8_TRG_COM_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM8_CC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void ADC3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FMC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void LPTIM1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SPI3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void UART4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void UART5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM6_DAC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM7_DAC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel2_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void ADC4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void ADC5_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void UCPD1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void COMP1_2_3_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void COMP4_5_6_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void COMP7_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void CRS_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SAI1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM20_BRK_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM20_UP_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM20_TRG_COM_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void TIM20_CC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FPU_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C4_EV_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C4_ER_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void SPI4_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN2_IT0_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN2_IT1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN3_IT0_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FDCAN3_IT1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void RNG_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void LPUART1_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C3_EV_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void I2C3_ER_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMAMUX_OVR_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void QUADSPI_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA1_Channel8_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel6_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel7_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void DMA2_Channel8_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void CORDIC_IRQHandler(); +__attribute__((weak, alias("Default_Handler_Proxy"))) void FMAC_IRQHandler(); \ No newline at end of file diff --git a/src/system/stm32g473/startup.S b/src/system/stm32g473/startup.S new file mode 100644 index 000000000..268825b10 --- /dev/null +++ b/src/system/stm32g473/startup.S @@ -0,0 +1,239 @@ +/** + ****************************************************************************** + * @file startup_stm32g473xx.s + * @author MCD Application Team + * @brief STM32G473xx devices vector table GCC toolchain. + * This module performs: + * - Set the initial SP + * - Set the initial PC == Reset_Handler, + * - Set the vector table entries with the exceptions ISR address, + * - Configure the clock system + * - Branches to main in the C library (which eventually + * calls main()). + * After Reset the Cortex-M4 processor is in Thread mode, + * priority is Privileged, and the Stack is set to Main. + ****************************************************************************** + * @attention + * + * Copyright (c) 2019 STMicroelectronics. + * All rights reserved. + * + * This software is licensed under terms that can be found in the LICENSE file + * in the root directory of this software component. + * If no LICENSE file comes with this software, it is provided AS-IS. + * + ****************************************************************************** + */ + + .syntax unified + .cpu cortex-m4 + .fpu softvfp + .thumb + +.global g_pfnVectors +.global Default_Handler + +/* start address for the initialization values of the .data section. +defined in linker script */ +.word _sidata +/* start address for the .data section. defined in linker script */ +.word _sdata +/* end address for the .data section. defined in linker script */ +.word _edata +/* start address for the .bss section. defined in linker script */ +.word _sbss +/* end address for the .bss section. defined in linker script */ +.word _ebss + +.equ BootRAM, 0xF1E0F85F +/** + * @brief This is the code that gets called when the processor first + * starts execution following a reset event. Only the absolutely + * necessary set is performed, after which the application + * supplied main() routine is called. + * @param None + * @retval : None +*/ + + .section .text.Reset_Handler + .weak Reset_Handler + .type Reset_Handler, %function +Reset_Handler: + ldr r0, =_estack + mov sp, r0 /* set stack pointer */ + +/* Copy the data segment initializers from flash to SRAM */ + ldr r0, =_sdata + ldr r1, =_edata + ldr r2, =_sidata + movs r3, #0 + b LoopCopyDataInit + +CopyDataInit: + ldr r4, [r2, r3] + str r4, [r0, r3] + adds r3, r3, #4 + +LoopCopyDataInit: + adds r4, r0, r3 + cmp r4, r1 + bcc CopyDataInit + +/* Zero fill the bss segment. */ + ldr r2, =_sbss + ldr r4, =_ebss + movs r3, #0 + b LoopFillZerobss + +FillZerobss: + str r3, [r2] + adds r2, r2, #4 + +LoopFillZerobss: + cmp r2, r4 + bcc FillZerobss + + bl system_check_for_bootloader + bl SystemInit + bl __libc_init_array + bl memory_section_init + bl main + +LoopForever: + b LoopForever + +.size Reset_Handler, .-Reset_Handler + +/****************************************************************************** +* +* The minimal vector table for a Cortex-M4. Note that the proper constructs +* must be placed on this to ensure that it ends up at physical address +* 0x0000.0000. +* +******************************************************************************/ + .section .isr_vector,"a",%progbits + .type g_pfnVectors, %object + + +g_pfnVectors: + .word _estack + .word Reset_Handler + .word NMI_Handler + .word HardFault_Handler + .word MemManage_Handler + .word BusFault_Handler + .word UsageFault_Handler + .word 0 + .word 0 + .word 0 + .word 0 + .word SVC_Handler + .word DebugMon_Handler + .word 0 + .word PendSV_Handler + .word SysTick_Handler + .word WWDG_IRQHandler + .word PVD_PVM_IRQHandler + .word RTC_TAMP_LSECSS_IRQHandler + .word RTC_WKUP_IRQHandler + .word FLASH_IRQHandler + .word RCC_IRQHandler + .word EXTI0_IRQHandler + .word EXTI1_IRQHandler + .word EXTI2_IRQHandler + .word EXTI3_IRQHandler + .word EXTI4_IRQHandler + .word DMA1_Channel1_IRQHandler + .word DMA1_Channel2_IRQHandler + .word DMA1_Channel3_IRQHandler + .word DMA1_Channel4_IRQHandler + .word DMA1_Channel5_IRQHandler + .word DMA1_Channel6_IRQHandler + .word DMA1_Channel7_IRQHandler + .word ADC1_2_IRQHandler + .word USB_HP_IRQHandler + .word USB_LP_IRQHandler + .word FDCAN1_IT0_IRQHandler + .word FDCAN1_IT1_IRQHandler + .word EXTI9_5_IRQHandler + .word TIM1_BRK_TIM15_IRQHandler + .word TIM1_UP_TIM16_IRQHandler + .word TIM1_TRG_COM_TIM17_IRQHandler + .word TIM1_CC_IRQHandler + .word TIM2_IRQHandler + .word TIM3_IRQHandler + .word TIM4_IRQHandler + .word I2C1_EV_IRQHandler + .word I2C1_ER_IRQHandler + .word I2C2_EV_IRQHandler + .word I2C2_ER_IRQHandler + .word SPI1_IRQHandler + .word SPI2_IRQHandler + .word USART1_IRQHandler + .word USART2_IRQHandler + .word USART3_IRQHandler + .word EXTI15_10_IRQHandler + .word RTC_Alarm_IRQHandler + .word USBWakeUp_IRQHandler + .word TIM8_BRK_IRQHandler + .word TIM8_UP_IRQHandler + .word TIM8_TRG_COM_IRQHandler + .word TIM8_CC_IRQHandler + .word ADC3_IRQHandler + .word FMC_IRQHandler + .word LPTIM1_IRQHandler + .word TIM5_IRQHandler + .word SPI3_IRQHandler + .word UART4_IRQHandler + .word UART5_IRQHandler + .word TIM6_DAC_IRQHandler + .word TIM7_DAC_IRQHandler + .word DMA2_Channel1_IRQHandler + .word DMA2_Channel2_IRQHandler + .word DMA2_Channel3_IRQHandler + .word DMA2_Channel4_IRQHandler + .word DMA2_Channel5_IRQHandler + .word ADC4_IRQHandler + .word ADC5_IRQHandler + .word UCPD1_IRQHandler + .word COMP1_2_3_IRQHandler + .word COMP4_5_6_IRQHandler + .word COMP7_IRQHandler + .word 0 + .word 0 + .word 0 + .word 0 + .word 0 + .word 0 + .word 0 + .word 0 + .word CRS_IRQHandler + .word SAI1_IRQHandler + .word TIM20_BRK_IRQHandler + .word TIM20_UP_IRQHandler + .word TIM20_TRG_COM_IRQHandler + .word TIM20_CC_IRQHandler + .word FPU_IRQHandler + .word I2C4_EV_IRQHandler + .word I2C4_ER_IRQHandler + .word SPI4_IRQHandler + .word 0 + .word FDCAN2_IT0_IRQHandler + .word FDCAN2_IT1_IRQHandler + .word FDCAN3_IT0_IRQHandler + .word FDCAN3_IT1_IRQHandler + .word RNG_IRQHandler + .word LPUART1_IRQHandler + .word I2C3_EV_IRQHandler + .word I2C3_ER_IRQHandler + .word DMAMUX_OVR_IRQHandler + .word QUADSPI_IRQHandler + .word DMA1_Channel8_IRQHandler + .word DMA2_Channel6_IRQHandler + .word DMA2_Channel7_IRQHandler + .word DMA2_Channel8_IRQHandler + .word CORDIC_IRQHandler + .word FMAC_IRQHandler + + .size g_pfnVectors, .-g_pfnVectors + diff --git a/src/system/stm32g473/system.c b/src/system/stm32g473/system.c new file mode 100644 index 000000000..4b40b36d4 --- /dev/null +++ b/src/system/stm32g473/system.c @@ -0,0 +1,141 @@ +/** + * This file configures the system clock as follows: + *============================================================================= + *----------------------------------------------------------------------------- + * System Clock source | HSI + *----------------------------------------------------------------------------- + * SYSCLK(Hz) | 168000000 + *----------------------------------------------------------------------------- + * HCLK(Hz) | 168000000 + *----------------------------------------------------------------------------- + * AHB Prescaler | 1 + *----------------------------------------------------------------------------- + * APB1 Prescaler | 1 + *----------------------------------------------------------------------------- + * APB2 Prescaler | 1 + *----------------------------------------------------------------------------- + * PLL_M | 1 + *----------------------------------------------------------------------------- + * PLL_N | 21 + *----------------------------------------------------------------------------- + * PLL_P | 2 + *----------------------------------------------------------------------------- + * PLL_Q | 2 + *----------------------------------------------------------------------------- + * PLL_R | 2 + *----------------------------------------------------------------------------- + * Require 48MHz for RNG | Disabled + *----------------------------------------------------------------------------- + *============================================================================= + */ + +#include "stm32g4xx.h" + +#if !defined(HSE_VALUE) +#define HSE_VALUE 8000000U +#endif + +#if !defined(HSI_VALUE) +#define HSI_VALUE 16000000U +#endif + +/************************* Miscellaneous Configuration ************************/ +#define VECT_TAB_OFFSET 0x00UL +/******************************************************************************/ + +uint32_t SystemCoreClock = 168000000; +const uint8_t AHBPrescTable[16] = {0U, 0U, 0U, 0U, 0U, 0U, 0U, 0U, 1U, 2U, 3U, 4U, 6U, 7U, 8U, 9U}; +const uint8_t APBPrescTable[8] = {0U, 0U, 0U, 0U, 1U, 2U, 3U, 4U}; + +static void ErrorHandler(void) { + while (1) + ; +} + +static void SystemClock_Config(void) { + HAL_InitTick(TICK_INT_PRIORITY); + + // Configure the main internal regulator output voltage + HAL_PWREx_ControlVoltageScaling(PWR_REGULATOR_VOLTAGE_SCALE1_BOOST); + + // Initializes the CPU, AHB and APB busses clocks + RCC_OscInitTypeDef RCC_OscInitStruct = {0}; + RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI | RCC_OSCILLATORTYPE_HSI48 | RCC_OSCILLATORTYPE_LSI | RCC_OSCILLATORTYPE_HSE; + RCC_OscInitStruct.HSEState = RCC_HSE_ON; + RCC_OscInitStruct.HSIState = RCC_HSI_ON; + RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT; + RCC_OscInitStruct.LSIState = RCC_LSI_ON; + RCC_OscInitStruct.HSI48State = RCC_HSI48_ON; + RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON; + RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI; + RCC_OscInitStruct.PLL.PLLM = RCC_PLLM_DIV1; + RCC_OscInitStruct.PLL.PLLN = 21; + RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2; + RCC_OscInitStruct.PLL.PLLQ = RCC_PLLQ_DIV2; + RCC_OscInitStruct.PLL.PLLR = RCC_PLLR_DIV2; + if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK) { + ErrorHandler(); + } + + // Initializes the CPU, AHB and APB busses clocks + RCC_ClkInitTypeDef RCC_ClkInitStruct = {0}; + RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK | RCC_CLOCKTYPE_SYSCLK | RCC_CLOCKTYPE_PCLK1 | RCC_CLOCKTYPE_PCLK2; + RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK; + RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1; + RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1; + RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1; + if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_8) != HAL_OK) { + ErrorHandler(); + } + + // Initializes the peripherals clocks + RCC_PeriphCLKInitTypeDef PeriphClkInit = {0}; + PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_USART1 | RCC_PERIPHCLK_USART2 | RCC_PERIPHCLK_USART3 | RCC_PERIPHCLK_UART4 | RCC_PERIPHCLK_UART5 | RCC_PERIPHCLK_I2C1 | RCC_PERIPHCLK_I2C2 | RCC_PERIPHCLK_I2C3 | RCC_PERIPHCLK_I2C4 | RCC_PERIPHCLK_USB | RCC_PERIPHCLK_ADC12 | RCC_PERIPHCLK_ADC345 | RCC_PERIPHCLK_FDCAN | RCC_PERIPHCLK_LPUART1; + PeriphClkInit.Usart1ClockSelection = RCC_USART1CLKSOURCE_PCLK2; + PeriphClkInit.Usart2ClockSelection = RCC_USART2CLKSOURCE_PCLK1; + PeriphClkInit.Usart3ClockSelection = RCC_USART3CLKSOURCE_PCLK1; + PeriphClkInit.Uart4ClockSelection = RCC_UART4CLKSOURCE_PCLK1; + PeriphClkInit.Uart5ClockSelection = RCC_UART5CLKSOURCE_PCLK1; + PeriphClkInit.Lpuart1ClockSelection = RCC_LPUART1CLKSOURCE_PCLK1; + PeriphClkInit.I2c1ClockSelection = RCC_I2C1CLKSOURCE_PCLK1; + PeriphClkInit.I2c2ClockSelection = RCC_I2C2CLKSOURCE_PCLK1; + PeriphClkInit.I2c3ClockSelection = RCC_I2C3CLKSOURCE_PCLK1; + PeriphClkInit.I2c4ClockSelection = RCC_I2C4CLKSOURCE_PCLK1; + PeriphClkInit.Adc12ClockSelection = RCC_ADC12CLKSOURCE_SYSCLK; + PeriphClkInit.Adc345ClockSelection = RCC_ADC345CLKSOURCE_SYSCLK; + PeriphClkInit.FdcanClockSelection = RCC_FDCANCLKSOURCE_PCLK1; + PeriphClkInit.UsbClockSelection = RCC_USBCLKSOURCE_HSI48; + PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI; + if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK) { + ErrorHandler(); + } + + // Configures CRS + RCC_CRSInitTypeDef CRSInit = {0}; + CRSInit.Prescaler = RCC_CRS_SYNC_DIV1; + CRSInit.Source = RCC_CRS_SYNC_SOURCE_USB; + CRSInit.Polarity = RCC_CRS_SYNC_POLARITY_RISING; + CRSInit.ReloadValue = __HAL_RCC_CRS_RELOADVALUE_CALCULATE(48000000, 1000); + CRSInit.ErrorLimitValue = 34; + CRSInit.HSI48CalibrationValue = 32; + HAL_RCCEx_CRSConfig(&CRSInit); + + /* Configure Flash prefetch, Instruction cache, Data cache and wait state */ + FLASH->ACR = FLASH_ACR_DBG_SWEN | FLASH_ACR_PRFTEN | FLASH_ACR_ICEN | FLASH_ACR_DCEN | FLASH_ACR_LATENCY_4WS; +} + +__attribute__((__used__)) void SystemInit(void) { +/* FPU settings ------------------------------------------------------------*/ +#if (__FPU_PRESENT == 1) && (__FPU_USED == 1) + SCB->CPACR |= ((3UL << (10 * 2)) | (3UL << (11 * 2))); /* set CP10 and CP11 Full Access */ +#endif + + /* Configure the Vector Table location add offset address ------------------*/ +#ifdef VECT_TAB_SRAM + SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM */ +#else + SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */ +#endif + + SystemClock_Config(); +}