From b7a21bf6a086748b4907c0577eaa114445995783 Mon Sep 17 00:00:00 2001 From: Keith Packard Date: Tue, 11 Sep 2018 00:07:38 -0700 Subject: altos/stm32f4: Start adding support for STM32F413 Enough to get clocks lit up at least. Signed-off-by: Keith Packard --- src/stm32f4/ao_interrupt.c | 239 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 239 insertions(+) create mode 100644 src/stm32f4/ao_interrupt.c (limited to 'src/stm32f4/ao_interrupt.c') diff --git a/src/stm32f4/ao_interrupt.c b/src/stm32f4/ao_interrupt.c new file mode 100644 index 00000000..a00df54b --- /dev/null +++ b/src/stm32f4/ao_interrupt.c @@ -0,0 +1,239 @@ +/* + * Copyright © 2018 Keith Packard + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#include +#include "stm32f4.h" +#include +#include + +extern void main(void); +extern char __stack__; +extern char __text_start__, __text_end__; +extern char _start__, _end__; +extern char __bss_start__, __bss_end__; + +/* Interrupt functions */ + +void stm_halt_isr(void) +{ + ao_panic(AO_PANIC_CRASH); +} + +void stm_ignore_isr(void) +{ +} + +const void *stm_interrupt_vector[]; + +void start(void) +{ +#ifdef AO_BOOT_CHAIN + if (ao_boot_check_chain()) { +#ifdef AO_BOOT_PIN + ao_boot_check_pin(); +#endif + } +#endif + /* Enable FPU */ + stm_scb.cpacr |= ((STM_SCB_CPACR_FULL << STM_SCB_CPACR_FP0) | + (STM_SCB_CPACR_FULL << STM_SCB_CPACR_FP1)); + ao_arch_nop(); + /* Set interrupt vector table offset */ + stm_scb.vtor = (uint32_t) &stm_interrupt_vector; + memcpy(&_start__, &__text_end__, &_end__ - &_start__); + memset(&__bss_start__, '\0', &__bss_end__ - &__bss_start__); + main(); +} + +#define STRINGIFY(x) #x + +#define isr(name) \ + void __attribute__ ((weak)) stm_ ## name ## _isr(void); \ + _Pragma(STRINGIFY(weak stm_ ## name ## _isr = stm_ignore_isr)) + +#define isr_halt(name) \ + void __attribute__ ((weak)) stm_ ## name ## _isr(void); \ + _Pragma(STRINGIFY(weak stm_ ## name ## _isr = stm_halt_isr)) + +isr(nmi) +isr_halt(hardfault) +isr_halt(memmanage) +isr_halt(busfault) +isr_halt(usagefault) +isr(svc) +isr(debugmon) +isr(pendsv) +isr(systick) +isr(wwdg) +isr(pvd) +isr(tamper_stamp) +isr(rtc_wkup) +isr(flash) +isr(rcc) +isr(exti0) +isr(exti1) +isr(exti2) +isr(exti3) +isr(exti4) +isr(dma1_stream0) +isr(dma1_stream1) +isr(dma1_stream2) +isr(dma1_stream3) +isr(dma1_stream4) +isr(dma1_stream5) +isr(dma1_stream6) +isr(adc) +isr(can1_tx) +isr(can1_rx0) +isr(can1_rx1) +isr(can1_sce) +isr(exti9_5) +isr(tim1_brk_tim9) +isr(tim1_up_tim10) +isr(tim_trg_com_tim11) +isr(tim1_cc) +isr(tim2) +isr(tim3) +isr(tim4) +isr(i2c1_evt) +isr(i2c1_err) +isr(i2c2_evt) +isr(i2c2_err) +isr(spi1) +isr(spi2) +isr(usart1) +isr(usart2) +isr(usart3) +isr(exti5_10) +isr(rtc_alarm) +isr(otg_fs_wkup) +isr(tim8_brk_tim12) +isr(tim8_up_tim13) +isr(tim8_trg_com_tim14) +isr(tim8_cc) +isr(dma1_stream7) +isr(fsmc) +isr(sdio) +isr(tim5) +isr(spi3) +isr(uart4) +isr(uart5) +isr(tim6_glb_it) +isr(tim7) +isr(dma2_stream0) +isr(dma2_stream1) +isr(dma2_stream2) +isr(dma2_stream3) +isr(dma2_stream4) +isr(dfsdm1_flt0) +isr(dfsdm1_flt1) +isr(can2_tx) +isr(can2_rx0) +isr(can2_rx1) +isr(can2_sce) +isr(otg_fs) +isr(dma2_stream5) +isr(dma2_stream6) +isr(dma2_stream7) +isr(usart6) +isr(i2c3_ev) +isr(i2c3_er) +isr(can3_tx) +isr(can3_rx0) +isr(can3_rx1) +isr(can3_sce) +isr(crypto) +isr(rng) +isr(fpu) +isr(uart7) +isr(uart8) +isr(spi4) +isr(spi5) +isr(sai1) +isr(uart9) +isr(uart10) +isr(quad_spi) +isr(i2cfmp1_ev) +isr(i2cfmp1_er) +isr(exti23) +isr(dfsdm2_flt0) +isr(dfsdm2_flt1) +isr(dfsdm2_flt2) +isr(dfsdm2_flt3) + +#define i(addr,name) [(addr)/4] = stm_ ## name ## _isr + +__attribute__ ((section(".interrupt"))) +const void *stm_interrupt_vector[] = { + [0] = &__stack__, + [1] = start, + i(0x08, nmi), + i(0x0c, hardfault), + i(0x10, memmanage), + i(0x14, busfault), + i(0x18, usagefault), + i(0x2c, svc), + i(0x30, debugmon), + i(0x38, pendsv), + i(0x3c, systick), + i(0x40, wwdg), + i(0x44, pvd), + i(0x48, tamper_stamp), + i(0x4c, rtc_wkup), + i(0x50, flash), + i(0x54, rcc), + i(0x58, exti0), + i(0x5c, exti1), + i(0x60, exti2), + i(0x64, exti3), + i(0x68, exti4), + i(0x6c, dma1_stream0), + i(0x70, dma1_stream1), + i(0x74, dma1_stream2), + i(0x78, dma1_stream3), + i(0x7c, dma1_stream4), + i(0x80, dma1_stream5), + i(0x84, dma1_stream6), + i(0x88, adc), + i(0x8c, can1_tx), + i(0x90, can1_rx0), + i(0x94, can1_rx1), + i(0x98, can1_sce), + i(0x9c, exti9_5), + i(0xa0, tim1_brk_tim9), + i(0xa4, tim1_up_tim10), + i(0xa8, tim_trg_com_tim11), + i(0xac, tim1_cc), + i(0xb0, tim2), + i(0xb4, tim3), + i(0xb8, tim4), + i(0xbc, i2c1_evt), + i(0xc0, i2c1_err), + i(0xc4, i2c2_evt), + i(0xc8, i2c2_err), + i(0xcc, spi1), + i(0xd0, spi2), + i(0xd4, usart1), + i(0xd8, usart2), + i(0xdc, usart3), + i(0xe0, exti5_10), + i(0xe4, rtc_alarm), + i(0xe8, otg_fs_wkup), + i(0xec, tim8_brk_tim12), + i(0xf0, tim8_up_tim13), +}; -- cgit v1.2.3 From 0b5ac831d2e63a091833c702b07b0331fba32e72 Mon Sep 17 00:00:00 2001 From: Keith Packard Date: Tue, 11 Sep 2018 18:49:22 -0700 Subject: altos/stm32f4: Add usart driver for usart6 This is what the disco board hooks up. Signed-off-by: Keith Packard --- src/stm32f4/ao_arch.h | 28 ++++ src/stm32f4/ao_arch_funcs.h | 6 + src/stm32f4/ao_interrupt.c | 5 +- src/stm32f4/ao_usart_stm32f4.c | 350 +++++++++++++++++++++++++++++++++++++++++ src/stm32f4/registers.ld | 20 +++ src/stm32f4/stm32f4.h | 317 ++++++++++++++++++++++++++++++++++++- 6 files changed, 723 insertions(+), 3 deletions(-) create mode 100644 src/stm32f4/ao_usart_stm32f4.c (limited to 'src/stm32f4/ao_interrupt.c') diff --git a/src/stm32f4/ao_arch.h b/src/stm32f4/ao_arch.h index d4c78f60..083a4e5b 100644 --- a/src/stm32f4/ao_arch.h +++ b/src/stm32f4/ao_arch.h @@ -100,4 +100,32 @@ #define AO_SYSTICK (AO_HCLK) #define AO_PANIC_DELAY_SCALE (AO_SYSCLK / 12000000) +/* The stm32f413 implements only 4 bits of the priority fields? */ + +#if AO_NONMASK_INTERRUPT +#define AO_STM_NVIC_NONMASK_PRIORITY 0x00 + +/* Set the basepri register to this value to mask all + * non-maskable priorities + */ +#define AO_STM_NVIC_BASEPRI_MASK 0x10 +#endif + +#define AO_STM_NVIC_HIGH_PRIORITY 0x40 +#define AO_STM_NVIC_MED_PRIORITY 0x80 +#define AO_STM_NVIC_LOW_PRIORITY 0xC0 +#define AO_STM_NVIC_CLOCK_PRIORITY 0xf0 + +#define AO_GPIO_MODE_PULL_NONE 0 +#define AO_GPIO_MODE_PULL_UP 4 +#define AO_GPIO_MODE_PULL_DOWN 8 + +/* usart stuff */ + +#define AO_SERIAL_SPEED_4800 4800 +#define AO_SERIAL_SPEED_9600 9600 +#define AO_SERIAL_SPEED_19200 19200 +#define AO_SERIAL_SPEED_57600 57600 +#define AO_SERIAL_SPEED_115200 115200 + #endif /* _AO_ARCH_H_ */ diff --git a/src/stm32f4/ao_arch_funcs.h b/src/stm32f4/ao_arch_funcs.h index 8c0da03b..b1ffb5b6 100644 --- a/src/stm32f4/ao_arch_funcs.h +++ b/src/stm32f4/ao_arch_funcs.h @@ -331,4 +331,10 @@ static inline void ao_disable_port(struct stm_gpio *port) ao_gpio_set_mode(port, bit, mode); \ } while (0) +/* usart */ + +void +ao_usart_init(void); + + #endif /* _AO_ARCH_FUNCS_H_ */ diff --git a/src/stm32f4/ao_interrupt.c b/src/stm32f4/ao_interrupt.c index a00df54b..f1cb8eee 100644 --- a/src/stm32f4/ao_interrupt.c +++ b/src/stm32f4/ao_interrupt.c @@ -119,7 +119,7 @@ isr(spi2) isr(usart1) isr(usart2) isr(usart3) -isr(exti5_10) +isr(exti15_10) isr(rtc_alarm) isr(otg_fs_wkup) isr(tim8_brk_tim12) @@ -231,9 +231,10 @@ const void *stm_interrupt_vector[] = { i(0xd4, usart1), i(0xd8, usart2), i(0xdc, usart3), - i(0xe0, exti5_10), + i(0xe0, exti15_10), i(0xe4, rtc_alarm), i(0xe8, otg_fs_wkup), i(0xec, tim8_brk_tim12), i(0xf0, tim8_up_tim13), + i(0x15c, usart6), }; diff --git a/src/stm32f4/ao_usart_stm32f4.c b/src/stm32f4/ao_usart_stm32f4.c new file mode 100644 index 00000000..28331b1e --- /dev/null +++ b/src/stm32f4/ao_usart_stm32f4.c @@ -0,0 +1,350 @@ +/* + * Copyright © 2018 Keith Packard + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#include +#include + +/* ao_serial_stm.c */ +struct ao_stm_usart { + struct ao_fifo rx_fifo; + struct ao_fifo tx_fifo; + struct stm_usart *reg; + uint32_t clk; + uint8_t tx_running; + uint8_t draining; +#if HAS_SERIAL_SW_FLOW + /* RTS - 0 if we have FIFO space, 1 if not + * CTS - 0 if we can send, 0 if not + */ + struct stm_gpio *gpio_rts; + struct stm_gpio *gpio_cts; + uint8_t pin_rts; + uint8_t pin_cts; + uint8_t rts; +#endif +}; + +static int +_ao_usart_tx_start(struct ao_stm_usart *usart) +{ + if (!ao_fifo_empty(usart->tx_fifo)) { +#if HAS_SERIAL_SW_FLOW + if (usart->gpio_cts && ao_gpio_get(usart->gpio_cts, usart->pin_cts) == 1) { + ao_exti_enable(usart->gpio_cts, usart->pin_cts); + return 0; + } +#endif + if (usart->reg->sr & (1 << STM_USART_SR_TXE)) + { + usart->tx_running = 1; + usart->reg->cr1 |= (1 << STM_USART_CR1_TXEIE) | (1 << STM_USART_CR1_TCIE); + ao_fifo_remove(usart->tx_fifo, usart->reg->dr); + ao_wakeup(&usart->tx_fifo); + return 1; + } + } + return 0; +} + +#if HAS_SERIAL_SW_FLOW +static void +_ao_usart_cts(struct ao_stm_usart *usart) +{ + if (_ao_usart_tx_start(usart)) + ao_exti_disable(usart->gpio_cts, usart->pin_cts); +} +#endif + +static void +_ao_usart_rx(struct ao_stm_usart *usart, int is_stdin) +{ + if (usart->reg->sr & (1 << STM_USART_SR_RXNE)) { + if (!ao_fifo_full(usart->rx_fifo)) { + ao_fifo_insert(usart->rx_fifo, usart->reg->dr); + ao_wakeup(&usart->rx_fifo); + if (is_stdin) + ao_wakeup(&ao_stdin_ready); +#if HAS_SERIAL_SW_FLOW + /* If the fifo is nearly full, turn off RTS and wait + * for it to drain a bunch + */ + if (usart->gpio_rts && ao_fifo_mostly(usart->rx_fifo)) { + ao_gpio_set(usart->gpio_rts, usart->pin_rts, 1); + usart->rts = 0; + } +#endif + } else { + usart->reg->cr1 &= ~(1 << STM_USART_CR1_RXNEIE); + } + } +} + +static void +ao_usart_isr(struct ao_stm_usart *usart, int is_stdin) +{ + _ao_usart_rx(usart, is_stdin); + + if (!_ao_usart_tx_start(usart)) + usart->reg->cr1 &= ~(1<< STM_USART_CR1_TXEIE); + + if (usart->reg->sr & (1 << STM_USART_SR_TC)) { + usart->tx_running = 0; + usart->reg->cr1 &= ~(1 << STM_USART_CR1_TCIE); + if (usart->draining) { + usart->draining = 0; + ao_wakeup(&usart->tx_fifo); + } + } +} + +static int +_ao_usart_pollchar(struct ao_stm_usart *usart) +{ + int c; + + if (ao_fifo_empty(usart->rx_fifo)) + c = AO_READ_AGAIN; + else { + uint8_t u; + ao_fifo_remove(usart->rx_fifo,u); + if ((usart->reg->cr1 & (1 << STM_USART_CR1_RXNEIE)) == 0) { + if (ao_fifo_barely(usart->rx_fifo)) + usart->reg->cr1 |= (1 << STM_USART_CR1_RXNEIE); + } +#if HAS_SERIAL_SW_FLOW + /* If we've cleared RTS, check if there's space now and turn it back on */ + if (usart->gpio_rts && usart->rts == 0 && ao_fifo_barely(usart->rx_fifo)) { + ao_gpio_set(usart->gpio_rts, usart->pin_rts, 0); + usart->rts = 1; + } +#endif + c = u; + } + return c; +} + +static char +ao_usart_getchar(struct ao_stm_usart *usart) +{ + int c; + ao_arch_block_interrupts(); + while ((c = _ao_usart_pollchar(usart)) == AO_READ_AGAIN) + ao_sleep(&usart->rx_fifo); + ao_arch_release_interrupts(); + return (char) c; +} + +static inline uint8_t +_ao_usart_sleep_for(struct ao_stm_usart *usart, uint16_t timeout) +{ + return ao_sleep_for(&usart->rx_fifo, timeout); +} + +static void +ao_usart_putchar(struct ao_stm_usart *usart, char c) +{ + ao_arch_block_interrupts(); + while (ao_fifo_full(usart->tx_fifo)) + ao_sleep(&usart->tx_fifo); + ao_fifo_insert(usart->tx_fifo, c); + _ao_usart_tx_start(usart); + ao_arch_release_interrupts(); +} + +static void +ao_usart_drain(struct ao_stm_usart *usart) +{ + ao_arch_block_interrupts(); + while (!ao_fifo_empty(usart->tx_fifo) || usart->tx_running) { + usart->draining = 1; + ao_sleep(&usart->tx_fifo); + } + ao_arch_release_interrupts(); +} + +static void +ao_usart_set_speed(struct ao_stm_usart *usart, uint32_t speed) +{ + if (speed > 115200) + return; + usart->reg->brr = usart->clk / speed; +} + +static void +_ao_usart_init(struct ao_stm_usart *usart, int hw_flow) +{ + usart->reg->cr1 = ((0 << STM_USART_CR1_OVER8) | + (1 << STM_USART_CR1_UE) | + (0 << STM_USART_CR1_M) | + (0 << STM_USART_CR1_WAKE) | + (0 << STM_USART_CR1_PCE) | + (0 << STM_USART_CR1_PS) | + (0 << STM_USART_CR1_PEIE) | + (0 << STM_USART_CR1_TXEIE) | + (0 << STM_USART_CR1_TCIE) | + (1 << STM_USART_CR1_RXNEIE) | + (0 << STM_USART_CR1_IDLEIE) | + (1 << STM_USART_CR1_TE) | + (1 << STM_USART_CR1_RE) | + (0 << STM_USART_CR1_RWU) | + (0 << STM_USART_CR1_SBK)); + + usart->reg->cr2 = ((0 << STM_USART_CR2_LINEN) | + (STM_USART_CR2_STOP_1 << STM_USART_CR2_STOP) | + (0 << STM_USART_CR2_CLKEN) | + (0 << STM_USART_CR2_CPOL) | + (0 << STM_USART_CR2_CPHA) | + (0 << STM_USART_CR2_LBCL) | + (0 << STM_USART_CR2_LBDIE) | + (0 << STM_USART_CR2_LBDL) | + (0 << STM_USART_CR2_ADD)); + + usart->reg->cr3 = ((0 << STM_USART_CR3_ONEBIT) | + (0 << STM_USART_CR3_CTSIE) | + (0 << STM_USART_CR3_CTSE) | + (0 << STM_USART_CR3_RTSE) | + (0 << STM_USART_CR3_DMAT) | + (0 << STM_USART_CR3_DMAR) | + (0 << STM_USART_CR3_SCEN) | + (0 << STM_USART_CR3_NACK) | + (0 << STM_USART_CR3_HDSEL) | + (0 << STM_USART_CR3_IRLP) | + (0 << STM_USART_CR3_IREN) | + (0 << STM_USART_CR3_EIE)); + + if (hw_flow) + usart->reg->cr3 |= ((1 << STM_USART_CR3_CTSE) | + (1 << STM_USART_CR3_RTSE)); + + /* Pick a 9600 baud rate */ + ao_usart_set_speed(usart, 9600); +} + +#if HAS_SERIAL_HW_FLOW +static void +ao_usart_set_flow(struct ao_stm_usart *usart) +{ +} +#endif + +#if HAS_SERIAL_6 + +struct ao_stm_usart ao_stm_usart6; + +void stm_usart6_isr(void) { ao_usart_isr(&ao_stm_usart6, USE_SERIAL_6_STDIN); } + +char +ao_serial6_getchar(void) +{ + return ao_usart_getchar(&ao_stm_usart6); +} + +void +ao_serial6_putchar(char c) +{ + ao_usart_putchar(&ao_stm_usart6, c); +} + +int +_ao_serial6_pollchar(void) +{ + return _ao_usart_pollchar(&ao_stm_usart6); +} + +uint8_t +_ao_serial6_sleep_for(uint16_t timeout) +{ + return _ao_usart_sleep_for(&ao_stm_usart6, timeout); +} + +void +ao_serial6_set_speed(uint32_t speed) +{ + ao_usart_drain(&ao_stm_usart6); + ao_usart_set_speed(&ao_stm_usart6, speed); +} + +void +ao_serial6_drain(void) +{ + ao_usart_drain(&ao_stm_usart6); +} +#endif /* HAS_SERIAL_6 */ + +#if HAS_SERIAL_SW_FLOW +static void +ao_serial_set_sw_rts_cts(struct ao_stm_usart *usart, + void (*isr)(void), + struct stm_gpio *port_rts, + int pin_rts, + struct stm_gpio *port_cts, + int pin_cts) +{ + /* Pull RTS low to note that there's space in the FIFO */ + ao_enable_output(port_rts, pin_rts, 0); + usart->gpio_rts = port_rts; + usart->pin_rts = pin_rts; + usart->rts = 1; + + ao_exti_setup(port_cts, pin_cts, AO_EXTI_MODE_FALLING|AO_EXTI_PRIORITY_MED, isr); + usart->gpio_cts = port_cts; + usart->pin_cts = pin_cts; +} +#endif + +void +ao_usart_init(void) +{ +#if HAS_SERIAL_6 + stm_rcc.apb2enr |= (1 << STM_RCC_APB2ENR_USART6EN); + + ao_stm_usart6.reg = &stm_usart6; + ao_stm_usart6.clk = AO_P2CLK; + + ao_enable_port(SERIAL_6_RX_PORT); + ao_enable_port(SERIAL_6_TX_PORT); + + stm_afr_set(SERIAL_6_RX_PORT, SERIAL_6_RX_PIN, STM_AFR_AF8); + stm_afr_set(SERIAL_6_TX_PORT, SERIAL_6_TX_PIN, STM_AFR_AF8); + + stm_nvic_set_enable(STM_ISR_USART6_POS); + stm_nvic_set_priority(STM_ISR_USART6_POS, AO_STM_NVIC_MED_PRIORITY); + + _ao_usart_init(&ao_stm_usart6, USE_SERIAL_6_FLOW && !USE_SERIAL_6_SW_FLOW); + +# if USE_SERIAL_6_FLOW +# if USE_SERIAL_6_SW_FLOW + ao_serial_set_sw_rts_cts(&ao_stm_usart6, + ao_serial6_cts, + SERIAL_6_PORT_RTS, + SERIAL_6_PIN_RTS, + SERIAL_6_PORT_CTS, + SERIAL_6_PIN_CTS); +# else + stm_afr_set(SERIAL_6_PORT_RTS, SERIAL_6_PIN_RTS, STM_AFR_AF8); + stm_afr_set(SERIAL_6_PORT_CTS, SERIAL_6_PIN_CTS, STM_AFR_AF8); +# endif +#endif + +#if USE_SERIAL_6_STDIN && !DELAY_SERIAL_6_STDIN + ao_add_stdio(_ao_serial6_pollchar, + ao_serial6_putchar, + NULL); +#endif +#endif +} diff --git a/src/stm32f4/registers.ld b/src/stm32f4/registers.ld index b36b2098..20ffa0a0 100644 --- a/src/stm32f4/registers.ld +++ b/src/stm32f4/registers.ld @@ -19,6 +19,26 @@ stm_dac1 = 0x40007400; stm_uart7 = 0x40007800; stm_uart8 = 0x40007c00; +stm_tim1 = 0x40010000; +stm_tim8 = 0x40010400; +stm_usart1 = 0x40011000; +stm_usart6 = 0x40011400; +stm_uart9 = 0x40011800; +stm_uart10 = 0x40011c00; +stm_adc = 0x40012000; +stm_sdio = 0x40012c00; +stm_spi1 = 0x40013000; +stm_spi4 = 0x40013400; +stm_syscfg = 0x40013800; +stm_exti = 0x40013c00; +stm_tim9 = 0x40014000; +stm_tim10 = 0x40014400; +stm_tim11 = 0x40014800; +stm_spi5 = 0x40015000; +stm_sai1 = 0x40015800; +stm_dfsdm1 = 0x40016000; +stm_dfsdm2 = 0x40016400; + stm_gpioa = 0x40020000; stm_gpiob = 0x40020400; stm_gpioc = 0x40020800; diff --git a/src/stm32f4/stm32f4.h b/src/stm32f4/stm32f4.h index 3429e458..715a2c92 100644 --- a/src/stm32f4/stm32f4.h +++ b/src/stm32f4/stm32f4.h @@ -223,6 +223,26 @@ extern struct stm_rcc stm_rcc; #define STM_RCC_APB1ENR_TIM3EN 1 #define STM_RCC_APB1ENR_TIM2EN 0 +#define STM_RCC_APB2ENR_DFSDM2EN 25 +#define STM_RCC_APB2ENR_DFSDM1EN 24 +#define STM_RCC_APB2ENR_SAI1EN 22 +#define STM_RCC_APB2ENR_SPI5EN 20 +#define STM_RCC_APB2ENR_TIM11EN 18 +#define STM_RCC_APB2ENR_TIM10EN 17 +#define STM_RCC_APB2ENR_TIM9EN 16 +#define STM_RCC_APB2ENR_EXITEN 15 +#define STM_RCC_APB2ENR_SYSCFGEN 14 +#define STM_RCC_APB2ENR_SPI4EN 13 +#define STM_RCC_APB2ENR_SPI1EN 12 +#define STM_RCC_APB2ENR_SDIOEN 11 +#define STM_RCC_APB2ENR_ADC1EN 8 +#define STM_RCC_APB2ENR_UART10EN 7 +#define STM_RCC_APB2ENR_UART9EN 5 +#define STM_RCC_APB2ENR_USART6EN 5 +#define STM_RCC_APB2ENR_USART1EN 4 +#define STM_RCC_APB2ENR_TIM8EN 1 +#define STM_RCC_APB2ENR_TIM1EN 0 + #define STM_RCC_CSR_RMVF 24 struct stm_ictr { @@ -283,7 +303,7 @@ static inline int stm_nvic_enabled(int irq) { return IRQ_BOOL(stm_nvic.iser[IRQ_REG(irq)], irq); } - + static inline void stm_nvic_set_pending(int irq) { stm_nvic.ispr[IRQ_REG(irq)] = IRQ_MASK(irq); @@ -324,6 +344,152 @@ stm_nvic_get_priority(int irq) { return (stm_nvic.ipr[IRQ_PRIO_REG(irq)] >> IRQ_PRIO_BIT(irq)) & IRQ_PRIO_MASK(0); } +#define isr(name) void stm_ ## name ## _isr(void) + +isr(nmi); +isr(hardfault); +isr(memmanage); +isr(busfault); +isr(usagefault); +isr(svc); +isr(debugmon); +isr(pendsv); +isr(systick); +isr(wwdg); +isr(pvd); +isr(tamper_stamp); +isr(rtc_wkup); +isr(flash); +isr(rcc); +isr(exti0); +isr(exti1); +isr(exti2); +isr(exti3); +isr(exti4); +isr(dma1_stream0); +isr(dma1_stream1); +isr(dma1_stream2); +isr(dma1_stream3); +isr(dma1_stream4); +isr(dma1_stream5); +isr(dma1_stream6); +isr(adc); +isr(can1_tx); +isr(can1_rx0); +isr(can1_rx1); +isr(can1_sce); +isr(exti9_5); +isr(tim1_brk_tim9); +isr(tim1_up_tim10); +isr(tim_trg_com_tim11); +isr(tim1_cc); +isr(tim2); +isr(tim3); +isr(tim4); +isr(i2c1_evt); +isr(i2c1_err); +isr(i2c2_evt); +isr(i2c2_err); +isr(spi1); +isr(spi2); +isr(usart1); +isr(usart2); +isr(usart3); +isr(exti15_10); +isr(rtc_alarm); +isr(otg_fs_wkup); +isr(tim8_brk_tim12); +isr(tim8_up_tim13); +isr(tim8_trg_com_tim14); +isr(tim8_cc); +isr(dma1_stream7); +isr(fsmc); +isr(sdio); +isr(tim5); +isr(spi3); +isr(uart4); +isr(uart5); +isr(tim6_glb_it); +isr(tim7); +isr(dma2_stream0); +isr(dma2_stream1); +isr(dma2_stream2); +isr(dma2_stream3); +isr(dma2_stream4); +isr(dfsdm1_flt0); +isr(dfsdm1_flt1); +isr(can2_tx); +isr(can2_rx0); +isr(can2_rx1); +isr(can2_sce); +isr(otg_fs); +isr(dma2_stream5); +isr(dma2_stream6); +isr(dma2_stream7); +isr(usart6); +isr(i2c3_ev); +isr(i2c3_er); +isr(can3_tx); +isr(can3_rx0); +isr(can3_rx1); +isr(can3_sce); +isr(crypto); +isr(rng); +isr(fpu); +isr(uart7); +isr(uart8); +isr(spi4); +isr(spi5); +isr(sai1); +isr(uart9); +isr(uart10); +isr(quad_spi); +isr(i2cfmp1_ev); +isr(i2cfmp1_er); +isr(exti23); +isr(dfsdm2_flt0); +isr(dfsdm2_flt1); +isr(dfsdm2_flt2); +isr(dfsdm2_flt3); + +#undef isr + +#define STM_ISR_WWDG_POS 0 +#define STM_ISR_PVD_POS 1 +#define STM_ISR_TAMPER_STAMP_POS 2 +#define STM_ISR_RTC_WKUP_POS 3 +#define STM_ISR_FLASH_POS 4 +#define STM_ISR_RCC_POS 5 +#define STM_ISR_EXTI0_POS 6 +#define STM_ISR_EXTI1_POS 7 +#define STM_ISR_EXTI2_POS 8 +#define STM_ISR_EXTI3_POS 9 +#define STM_ISR_EXTI4_POS 10 +#define STM_ISR_DMA1_STREAM0_POS 11 +#define STM_ISR_DMA1_STREAM1_POS 12 +#define STM_ISR_DMA1_STREAM2_POS 13 +#define STM_ISR_DMA1_STREAM3_POS 14 +#define STM_ISR_DMA1_STREAM4_POS 15 +#define STM_ISR_DMA1_STREAM5_POS 16 +#define STM_ISR_DMA1_STREAM6_POS 17 +#define STM_ISR_ADC_POS 18 +#define STM_ISR_CAN1_TX_POS 19 +#define STM_ISR_CAN1_RX0_POS 20 +#define STM_ISR_CAN1_RX1_POS 21 +#define STM_ISR_CAN1_SCE_POS 22 +#define STM_ISR_EXTI9_5_POS 23 +#define STM_ISR_USART1_POS 37 +#define STM_ISR_USART2_POS 38 +#define STM_ISR_USART3_POS 39 +#define STM_ISR_UART4_POS 52 +#define STM_ISR_UART5_POS 53 +#define STM_ISR_USART6_POS 71 +#define STM_ISR_UART7_POS 82 +#define STM_ISR_UART9_POS 88 +#define STM_ISR_UART10_POS 89 + +#define STM_ISR_EXTI15_10_POS 40 + struct stm_flash { vuint32_t acr; vuint32_t keyr; @@ -595,6 +761,13 @@ extern struct stm_scb stm_scb; #define STM_SCB_CPACR_FP0 STM_SCB_CPACR_CP(10) #define STM_SCB_CPACR_FP1 STM_SCB_CPACR_CP(11) +#define STM_SCB_AIRCR_VECTKEY 16 +#define STM_SCB_AIRCR_VECTKEY_KEY 0x05fa +#define STM_SCB_AIRCR_PRIGROUP 8 +#define STM_SCB_AIRCR_SYSRESETREQ 2 +#define STM_SCB_AIRCR_VECTCLRACTIVE 1 +#define STM_SCB_AIRCR_VECTRESET 0 + /* The SYSTICK starts at 0xe000e010 */ struct stm_systick { @@ -615,6 +788,148 @@ extern struct stm_systick stm_systick; #define STM_SYSTICK_CSR_CLKSOURCE_AHB 1 #define STM_SYSTICK_CSR_COUNTFLAG 16 +#define STM_SYSCFG_EXTICR_PA 0 +#define STM_SYSCFG_EXTICR_PB 1 +#define STM_SYSCFG_EXTICR_PC 2 +#define STM_SYSCFG_EXTICR_PD 3 +#define STM_SYSCFG_EXTICR_PE 4 +#define STM_SYSCFG_EXTICR_PF 5 +#define STM_SYSCFG_EXTICR_PG 6 +#define STM_SYSCFG_EXTICR_PH 7 + +struct stm_syscfg { + vuint32_t memrmp; + vuint32_t pmc; + vuint32_t exticr[4]; +}; + +extern struct stm_syscfg stm_syscfg; + +#define stm_syscfg (*((struct stm_syscfg *) 0x40013800)) + +#define STM_SYSCFG_MEMRMP_MEM_MODE 0 +#define STM_SYSCFG_MEMRMP_MEM_MODE_MAIN_FLASH 0 +#define STM_SYSCFG_MEMRMP_MEM_MODE_SYSTEM_FLASH 1 +#define STM_SYSCFG_MEMRMP_MEM_MODE_SRAM 3 +#define STM_SYSCFG_MEMRMP_MEM_MODE_MASK 3 + +#define STM_SYSCFG_PMC_ADC1DC2 0 + +static inline void +stm_exticr_set(struct stm_gpio *gpio, int pin) { + uint8_t reg = pin >> 2; + uint8_t shift = (pin & 3) << 2; + uint8_t val = 0; + + /* Enable SYSCFG */ + stm_rcc.apb2enr |= (1 << STM_RCC_APB2ENR_SYSCFGEN); + + if (gpio == &stm_gpioa) + val = STM_SYSCFG_EXTICR_PA; + else if (gpio == &stm_gpiob) + val = STM_SYSCFG_EXTICR_PB; + else if (gpio == &stm_gpioc) + val = STM_SYSCFG_EXTICR_PC; + else if (gpio == &stm_gpiod) + val = STM_SYSCFG_EXTICR_PD; + else if (gpio == &stm_gpioe) + val = STM_SYSCFG_EXTICR_PE; + else if (gpio == &stm_gpiof) + val = STM_SYSCFG_EXTICR_PF; + else if (gpio == &stm_gpiog) + val = STM_SYSCFG_EXTICR_PG; + else if (gpio == &stm_gpioh) + val = STM_SYSCFG_EXTICR_PH; + + stm_syscfg.exticr[reg] = (stm_syscfg.exticr[reg] & ~(0xf << shift)) | val << shift; +} + +struct stm_exti { + vuint32_t imr; + vuint32_t emr; + vuint32_t rtsr; + vuint32_t ftsr; + + vuint32_t swier; + vuint32_t pr; +}; + +extern struct stm_exti stm_exti; + +#define stm_exti (*((struct stm_exti *) 0x40013c00)) + +struct stm_usart { + vuint32_t sr; /* status register */ + vuint32_t dr; /* data register */ + vuint32_t brr; /* baud rate register */ + vuint32_t cr1; /* control register 1 */ + + vuint32_t cr2; /* control register 2 */ + vuint32_t cr3; /* control register 3 */ + vuint32_t gtpr; /* guard time and prescaler */ +}; + +extern struct stm_usart stm_usart6; + +#define stm_usart6 (*((struct stm_usart *) 0x40011400)) + +#define STM_USART_SR_CTS (9) /* CTS flag */ +#define STM_USART_SR_LBD (8) /* LIN break detection flag */ +#define STM_USART_SR_TXE (7) /* Transmit data register empty */ +#define STM_USART_SR_TC (6) /* Transmission complete */ +#define STM_USART_SR_RXNE (5) /* Read data register not empty */ +#define STM_USART_SR_IDLE (4) /* IDLE line detected */ +#define STM_USART_SR_ORE (3) /* Overrun error */ +#define STM_USART_SR_NF (2) /* Noise detected flag */ +#define STM_USART_SR_FE (1) /* Framing error */ +#define STM_USART_SR_PE (0) /* Parity error */ + +#define STM_USART_CR1_OVER8 (15) /* Oversampling mode */ +#define STM_USART_CR1_UE (13) /* USART enable */ +#define STM_USART_CR1_M (12) /* Word length */ +#define STM_USART_CR1_WAKE (11) /* Wakeup method */ +#define STM_USART_CR1_PCE (10) /* Parity control enable */ +#define STM_USART_CR1_PS (9) /* Parity selection */ +#define STM_USART_CR1_PEIE (8) /* PE interrupt enable */ +#define STM_USART_CR1_TXEIE (7) /* TXE interrupt enable */ +#define STM_USART_CR1_TCIE (6) /* Transmission complete interrupt enable */ +#define STM_USART_CR1_RXNEIE (5) /* RXNE interrupt enable */ +#define STM_USART_CR1_IDLEIE (4) /* IDLE interrupt enable */ +#define STM_USART_CR1_TE (3) /* Transmitter enable */ +#define STM_USART_CR1_RE (2) /* Receiver enable */ +#define STM_USART_CR1_RWU (1) /* Receiver wakeup */ +#define STM_USART_CR1_SBK (0) /* Send break */ + +#define STM_USART_CR2_LINEN (14) /* LIN mode enable */ +#define STM_USART_CR2_STOP (12) /* STOP bits */ +#define STM_USART_CR2_STOP_MASK 3 +#define STM_USART_CR2_STOP_1 0 +#define STM_USART_CR2_STOP_0_5 1 +#define STM_USART_CR2_STOP_2 2 +#define STM_USART_CR2_STOP_1_5 3 + +#define STM_USART_CR2_CLKEN (11) /* Clock enable */ +#define STM_USART_CR2_CPOL (10) /* Clock polarity */ +#define STM_USART_CR2_CPHA (9) /* Clock phase */ +#define STM_USART_CR2_LBCL (8) /* Last bit clock pulse */ +#define STM_USART_CR2_LBDIE (6) /* LIN break detection interrupt enable */ +#define STM_USART_CR2_LBDL (5) /* lin break detection length */ +#define STM_USART_CR2_ADD (0) +#define STM_USART_CR2_ADD_MASK 0xf + +#define STM_USART_CR3_ONEBIT (11) /* One sample bit method enable */ +#define STM_USART_CR3_CTSIE (10) /* CTS interrupt enable */ +#define STM_USART_CR3_CTSE (9) /* CTS enable */ +#define STM_USART_CR3_RTSE (8) /* RTS enable */ +#define STM_USART_CR3_DMAT (7) /* DMA enable transmitter */ +#define STM_USART_CR3_DMAR (6) /* DMA enable receiver */ +#define STM_USART_CR3_SCEN (5) /* Smartcard mode enable */ +#define STM_USART_CR3_NACK (4) /* Smartcard NACK enable */ +#define STM_USART_CR3_HDSEL (3) /* Half-duplex selection */ +#define STM_USART_CR3_IRLP (2) /* IrDA low-power */ +#define STM_USART_CR3_IREN (1) /* IrDA mode enable */ +#define STM_USART_CR3_EIE (0) /* Error interrupt enable */ + /* Errata 2.1.5 Delay after an RCC peripheral clock enabling -- cgit v1.2.3 From 015d3055a52532070e96469907683c3aa3eda44e Mon Sep 17 00:00:00 2001 From: Keith Packard Date: Tue, 2 Oct 2018 12:44:58 -0700 Subject: altos/stm32f4: Add more stm32f413 definitions and support code Signed-off-by: Keith Packard --- src/stm32f4/ao_arch.h | 6 +- src/stm32f4/ao_interrupt.c | 50 +++++ src/stm32f4/ao_timer.c | 14 +- src/stm32f4/registers.ld | 8 + src/stm32f4/stm32f4.h | 509 +++++++++++++++++++++++++++++++++++++++++++++ 5 files changed, 580 insertions(+), 7 deletions(-) (limited to 'src/stm32f4/ao_interrupt.c') diff --git a/src/stm32f4/ao_arch.h b/src/stm32f4/ao_arch.h index 4e9bdeb6..73dc3e93 100644 --- a/src/stm32f4/ao_arch.h +++ b/src/stm32f4/ao_arch.h @@ -19,7 +19,11 @@ #include #ifndef AO_STACK_SIZE -#define AO_STACK_SIZE 1024 +#define AO_STACK_SIZE 2048 +#endif + +#ifndef HAS_TASK_QUEUE +#define HAS_TASK_QUEUE 1 #endif #define AO_STACK_ALIGNMENT __attribute__ ((aligned(8))) diff --git a/src/stm32f4/ao_interrupt.c b/src/stm32f4/ao_interrupt.c index f1cb8eee..24f56abc 100644 --- a/src/stm32f4/ao_interrupt.c +++ b/src/stm32f4/ao_interrupt.c @@ -236,5 +236,55 @@ const void *stm_interrupt_vector[] = { i(0xe8, otg_fs_wkup), i(0xec, tim8_brk_tim12), i(0xf0, tim8_up_tim13), + i(0xf4, tim8_trg_com_tim14), + i(0xf8, tim8_cc), + i(0xfc, dma1_stream7), + i(0x100, fsmc), + i(0x104, sdio), + i(0x108, tim5), + i(0x10c, spi3), + i(0x110, uart4), + i(0x114, uart5), + i(0x118,tim6_glb_it), + i(0x11c, tim7), + i(0x120, dma2_stream0), + i(0x124, dma2_stream1), + i(0x128, dma2_stream2), + i(0x12c, dma2_stream3), + i(0x130, dma2_stream4), + i(0x134, dfsdm1_flt0), + i(0x138, dfsdm1_flt1), + i(0x13c, can2_tx), + i(0x140, can2_rx0), + i(0x144, can2_rx1), + i(0x148, can2_sce), + i(0x14c, otg_fs), + i(0x150, dma2_stream5), + i(0x154, dma2_stream6), + i(0x158, dma2_stream7), i(0x15c, usart6), + i(0x160, i2c3_ev), + i(0x164, i2c3_er), + i(0x168, can3_tx), + i(0x16c, can3_rx0), + i(0x170, can3_rx1), + i(0x174, can3_sce), + i(0x17c, crypto), + i(0x180, rng), + i(0x184, fpu), + i(0x188, uart7), + i(0x18c, uart8), + i(0x190, spi4), + i(0x194, spi5), + i(0x19c, sai1), + i(0x1a0, uart9), + i(0x1a4, uart10), + i(0x1b0, quad_spi), + i(0x1bc, i2cfmp1_ev), + i(0x1c0, i2cfmp1_er), + i(0x1c4, exti23), + i(0x1c8, dfsdm2_flt0), + i(0x1cc, dfsdm2_flt1), + i(0x1d0, dfsdm2_flt2), + i(0x1d4, dfsdm2_flt3), }; diff --git a/src/stm32f4/ao_timer.c b/src/stm32f4/ao_timer.c index e378ed07..d6ef9bc3 100644 --- a/src/stm32f4/ao_timer.c +++ b/src/stm32f4/ao_timer.c @@ -181,6 +181,14 @@ ao_clock_init(void) cfgr |= (AO_RCC_CFGR_PPRE2_DIV << STM_RCC_CFGR_PPRE2); stm_rcc.cfgr = cfgr; + /* Clock configuration register DCKCFGR2; mostly make sure USB + * gets clocked from PLL_Q + */ + stm_rcc.dckcfgr2 = ((STM_RCC_DCKCFGR2_LPTIMER1SEL_APB << STM_RCC_DCKCFGR2_LPTIMER1SEL) | + (STM_RCC_DCKCFGR2_SDIOSEL_CK_48MHZ << STM_RCC_DCKCFGR2_SDIOSEL) | + (STM_RCC_DCKCFGR2_CK48MSEL_PLL_Q << STM_RCC_DCKCFGR2_CK48MSEL) | + (STM_RCC_DCKCFGR2_I2CFMP1SEL_APB << STM_RCC_DCKCFGR2_I2CFMP1SEL)); + /* Disable the PLL */ stm_rcc.cr &= ~(1 << STM_RCC_CR_PLLON); while (stm_rcc.cr & (1 << STM_RCC_CR_PLLRDY)) @@ -196,7 +204,6 @@ ao_clock_init(void) pllcfgr |= (AO_PLL_M << STM_RCC_PLLCFGR_PLLM); pllcfgr |= (AO_PLL1_N << STM_RCC_PLLCFGR_PLLN); -#if AO_PLL1_P #if AO_PLL1_P == 2 #define AO_RCC_PLLCFGR_PLLP STM_RCC_PLLCFGR_PLLP_DIV_2 #endif @@ -210,13 +217,8 @@ ao_clock_init(void) #define AO_RCC_PLLCFGR_PLLP STM_RCC_PLLCFGR_PLLP_DIV_8 #endif pllcfgr |= (AO_RCC_PLLCFGR_PLLP << STM_RCC_PLLCFGR_PLLP); -#endif -#if AO_PLL1_Q pllcfgr |= (AO_PLL1_Q << STM_RCC_PLLCFGR_PLLQ); -#endif -#if AO_PLL1_R pllcfgr |= (AO_PLL1_R << STM_RCC_PLLCFGR_PLLR); -#endif /* PLL source */ pllcfgr &= ~(1 << STM_RCC_PLLCFGR_PLLSRC); #if AO_HSI diff --git a/src/stm32f4/registers.ld b/src/stm32f4/registers.ld index 20ffa0a0..bc924106 100644 --- a/src/stm32f4/registers.ld +++ b/src/stm32f4/registers.ld @@ -1,3 +1,4 @@ + stm_tim2 = 0x40000000; stm_tim3 = 0x40000400; stm_tim4 = 0x40000800; @@ -39,6 +40,8 @@ stm_sai1 = 0x40015800; stm_dfsdm1 = 0x40016000; stm_dfsdm2 = 0x40016400; +/* AHB1 */ + stm_gpioa = 0x40020000; stm_gpiob = 0x40020400; stm_gpioc = 0x40020800; @@ -54,6 +57,11 @@ stm_flash = 0x40023c00; stm_dma1 = 0x40026000; stm_dma2 = 0x40026400; +/* AHB2 */ + +stm_usb = 0x50000000; +stm_rng = 0x50060800; + stm_systick = 0xe000e010; stm_ictr = 0xe000e004; diff --git a/src/stm32f4/stm32f4.h b/src/stm32f4/stm32f4.h index 715a2c92..dcdce667 100644 --- a/src/stm32f4/stm32f4.h +++ b/src/stm32f4/stm32f4.h @@ -193,6 +193,10 @@ extern struct stm_rcc stm_rcc; #define STM_RCC_AHB1ENR_IOPGEN 6 #define STM_RCC_AHB1ENR_IOPHEN 7 +#define STM_RCC_AHB2ENR_OTGFSEN 7 +#define STM_RCC_AHB2ENR_RNGEN 6 +#define STM_RCC_AHB2ENR_CRYPEN 4 + #define STM_RCC_APB1ENR_UART8EN 31 #define STM_RCC_APB1ENR_UART7EN 30 #define STM_RCC_APB1ENR_DACEN 29 @@ -245,6 +249,34 @@ extern struct stm_rcc stm_rcc; #define STM_RCC_CSR_RMVF 24 +#define STM_RCC_DCKCFGR_CKDFSDMSEL 31 +#define STM_RCC_DCKCFGR_I2S2SRC 27 +#define STM_RCC_DCKCFGR_I2S1SRC 25 +#define STM_RCC_DCKCFGR_TIMPRE 24 +#define STM_RCC_DCKCFGR_SAII1BSRC 22 +#define STM_RCC_DCKCFGR_SAII1ASRC 20 +#define STM_RCC_DCKCFGR_CKDFSDM1ASEL 15 +#define STM_RCC_DCKCFGR_CKDFSDM2ASEL 14 +#define STM_RCC_DCKCFGR_PLLDIVR 8 +#define STM_RCC_DCKCFGR_PLLI2SDIVR 0 + +#define STM_RCC_DCKCFGR2_LPTIMER1SEL 30 +#define STM_RCC_DCKCFGR2_LPTIMER1SEL_APB 0 +#define STM_RCC_DCKCFGR2_LPTIMER1SEL_HSI 1 +#define STM_RCC_DCKCFGR2_LPTIMER1SEL_LSI 2 +#define STM_RCC_DCKCFGR2_LPTIMER1SEL_LSE 3 +#define STM_RCC_DCKCFGR2_SDIOSEL 28 +#define STM_RCC_DCKCFGR2_SDIOSEL_CK_48MHZ 0 +#define STM_RCC_DCKCFGR2_SDIOSEL_SYSTEM_CLOCK 1 +#define STM_RCC_DCKCFGR2_CK48MSEL 27 +#define STM_RCC_DCKCFGR2_CK48MSEL_PLL_Q 1 +#define STM_RCC_DCKCFGR2_CK48MSEL_PLLI2S_Q 1 +#define STM_RCC_DCKCFGR2_I2CFMP1SEL 22 +#define STM_RCC_DCKCFGR2_I2CFMP1SEL_APB 0 +#define STM_RCC_DCKCFGR2_I2CFMP1SEL_SYSTEM_CLOCK 1 +#define STM_RCC_DCKCFGR2_I2CFMP1SEL_HSI 2 +#define STM_RCC_DCKCFGR2_I2CFMP1SEL_APB_ALSO 3 + struct stm_ictr { vuint32_t ictr; }; @@ -478,11 +510,53 @@ isr(dfsdm2_flt3); #define STM_ISR_CAN1_RX1_POS 21 #define STM_ISR_CAN1_SCE_POS 22 #define STM_ISR_EXTI9_5_POS 23 +#define STM_ISR_TIM1_BRK_TIM9_POS 24 +#define STM_ISR_TIM1_UP_TIM10_POS 25 +#define STM_ISR_TIM_TRG_COM_TIM11_POS 26 +#define STM_ISR_TIM1_CC_POS 27 +#define STM_ISR_TIM2_POS 28 +#define STM_ISR_TIM3_POS 29 +#define STM_ISR_TIM4_POS 30 +#define STM_ISR_I2C1_EVT_POS 31 +#define STM_ISR_I2C1_ERR_POS 32 +#define STM_ISR_I2C2_EVT_POS 33 +#define STM_ISR_I2C2_ERR_POS 34 +#define STM_ISR_SPI1_POS 35 +#define STM_ISR_SPI2_POS 36 #define STM_ISR_USART1_POS 37 #define STM_ISR_USART2_POS 38 #define STM_ISR_USART3_POS 39 +#define STM_ISR_EXTI15_10_POS 40 +#define STM_ISR_EXTI17_RTC_ALARM_POS 41 +#define STM_ISR_EXTI18_OTG_FS_WKUP_POS 42 +#define STM_ISR_TIM2_BRK_TIM12_POS 43 +#define STM_ISR_TIM8_UP_TIM13_POS 44 +#define STM_ISR_TIM8_TRG_COM_TIM14_POS 45 +#define STM_ISR_TIM8_CC_POS 46 +#define STM_ISR_DMA1_STREAM7_POS 47 +#define STM_ISR_FSMC_POS 48 +#define STM_ISR_SDIO_POS 49 +#define STM_ISR_TIM5_POS 50 +#define STM_ISR_SPI3_POS 41 #define STM_ISR_UART4_POS 52 #define STM_ISR_UART5_POS 53 +#define STM_ISR_TIM6_GLB_IT_DAC1_DAC2_POS 54 +#define STM_ISR_TIM7_POS 55 +#define STM_ISR_DMA2_STREAM0_POS 56 +#define STM_ISR_DMA2_STREAM1_POS 57 +#define STM_ISR_DMA2_STREAM2_POS 58 +#define STM_ISR_DMA2_STREAM3_POS 59 +#define STM_ISR_DMA2_STREAM4_POS 60 +#define STM_ISR_DFSDM1_FLT0_POS 61 +#define STM_ISR_DFSDM1_FLT1_POS 62 +#define STM_ISR_CAN2_TX_POS 63 +#define STM_ISR_CAN2_RX0_POS 64 +#define STM_ISR_CAN2_RX1_POS 65 +#define STM_ISR_CAN2_SCE_POS 66 +#define STM_ISR_OTG_FS_POS 67 +#define STM_ISR_DMA2_STREAM5_POS 68 +#define STM_ISR_DMA2_STREAM6_POS 69 +#define STM_ISR_DMA2_STREAM7_POS 70 #define STM_ISR_USART6_POS 71 #define STM_ISR_UART7_POS 82 #define STM_ISR_UART9_POS 88 @@ -930,6 +1004,441 @@ extern struct stm_usart stm_usart6; #define STM_USART_CR3_IREN (1) /* IrDA mode enable */ #define STM_USART_CR3_EIE (0) /* Error interrupt enable */ +/* USB */ +struct stm_usb { + vuint32_t gotgctl; + vuint32_t gotgint; + vuint32_t gahbcfg; + vuint32_t gusbcfg; + + vuint32_t grstctl; + vuint32_t gintsts; + vuint32_t gintmsk; + vuint32_t grxstsr; + + vuint32_t grxstsp; + vuint32_t grxfsiz; + vuint32_t dieptxf0; + vuint32_t hnptxsts; + + vuint32_t pad_30; + vuint32_t pad_34; + vuint32_t gccfg; + vuint32_t cid; + + vuint32_t pad_40; + vuint32_t pad_44; + vuint32_t pad_48; + vuint32_t ghwcfg3; /* not in docs? */ + + vuint32_t pad_50; + vuint32_t glpmcfg; + vuint32_t pad_58; + vuint32_t gdfifocfg; /* not in docs? */ + + uint8_t pad_60[0x100 - 0x60]; + + vuint32_t hptxfsiz; /* 0x100 */ + vuint32_t dieptxf[0xf]; /* 0x104 5 in docs? */ + + uint8_t pad_140[0x400 - 0x140]; + + vuint32_t hcfg; + vuint32_t hfir; + vuint32_t hfnum; + vuint32_t pad_40c; + + vuint32_t hptxsts; + vuint32_t haint; + vuint32_t haintmsk; + vuint32_t pad_41c; + + uint8_t pad_420[0x440-0x420]; + + vuint32_t hprt; + + uint8_t pad_444[0x500 - 0x444]; + + vuint32_t hcchar0; + vuint32_t pad_504; + vuint32_t hcint0; + vuint32_t hcintmsk0; + + vuint32_t hctsiz0; + vuint32_t pad_514; + vuint32_t pad_518; + vuint32_t pad_51c; + + struct { + vuint32_t hcchar; + vuint32_t pad_4; + vuint32_t hcint; + vuint32_t hcintmsk; + + vuint32_t hctsiz; + vuint32_t pad_14; + vuint32_t pad_18; + vuint32_t pad_1c; + } h[11]; + + uint8_t pad_680[0x800 - 0x680]; + + vuint32_t dcfg; + vuint32_t dctl; + vuint32_t dsts; + vuint32_t pad_80c; + + vuint32_t diepmsk; + vuint32_t doepmsk; + vuint32_t daint; + vuint32_t daintmsk; + + vuint32_t pad_820; + vuint32_t pad_824; + vuint32_t dvbusdis; + vuint32_t dvbuspulse; + + vuint32_t pad_830; + vuint32_t diepempmsk; + + uint8_t pad_838[0x900 - 0x838]; + + struct { + vuint32_t diepctl; + vuint32_t pad_04; + vuint32_t diepint; + vuint32_t pad_0c; + + vuint32_t dieptsiz; + vuint32_t pad_14; + vuint32_t dtxfsts; + vuint32_t pad_1c; + } diep[6]; + + uint8_t pad_9c0[0xb00 - 0x9c0]; + + struct { + vuint32_t doepctl; + vuint32_t pad_04; + vuint32_t doepint; + vuint32_t pad_0c; + + vuint32_t doeptsiz; + vuint32_t pad_14; + vuint32_t pad_18; + vuint32_t pad_1c; + } doep[6]; + + uint8_t pad_bc0[0xe00 - 0xbc0]; + + vuint32_t pcgcctl; + + uint8_t pad_e04[0x1000 - 0xe04]; + + struct { + vuint32_t fifo; + uint8_t pad_004[0x1000 - 0x004]; + } dfifo[6]; +}; + +extern struct stm_usb stm_usb; + +#define stm_usb (*((struct stm_usb *) 0x50000000)) + +#define STM_USB_GOTGCTL_CURMOD 21 +#define STM_USB_GOTGCTL_OTGVER 20 +#define STM_USB_GOTGCTL_BSVLD 19 +#define STM_USB_GOTGCTL_ASVLD 18 +#define STM_USB_GOTGCTL_DBCT 17 +#define STM_USB_GOTGCTL_CIDSTS 16 +#define STM_USB_GOTGCTL_EHEN 12 +#define STM_USB_GOTGCTL_DHNPEN 11 +#define STM_USB_GOTGCTL_HSHNPEN 10 +#define STM_USB_GOTGCTL_HNPRQ 9 +#define STM_USB_GOTGCTL_HNGSCS 8 +#define STM_USB_GOTGCTL_BVALOVAL 7 +#define STM_USB_GOTGCTL_BVALOEN 6 +#define STM_USB_GOTGCTL_AVALOVAL 5 +#define STM_USB_GOTGCTL_AVALOEN 4 +#define STM_USB_GOTGCTL_VBVALOVAL 3 +#define STM_USB_GOTGCTL_VBVALOEN 2 +#define STM_USB_GOTGCTL_SRQ 1 +#define STM_USB_GOTGCTL_SRQSCS 0 + +#define STM_USB_GOTGINT_IDCHNG 20 +#define STM_USB_GOTGINT_DBCDNE 19 +#define STM_USB_GOTGINT_ADTOCHG 18 +#define STM_USB_GOTGINT_HNGDET 17 +#define STM_USB_GOTGINT_HNSSCHG 9 +#define STM_USB_GOTGINT_SRSSCHG 8 +#define STM_USB_GOTGINT_SEDET 2 + +#define STM_USB_GAHBCFG_PTXFELVL 8 +#define STM_USB_GAHBCFG_TXFELVL 7 +#define STM_USB_GAHBCFG_GINTMSK 0 + +#define STM_USB_GUSBCFG_FDMOD 30 +#define STM_USB_GUSBCFG_FHMOD 29 +#define STM_USB_GUSBCFG_TRDT 10 +#define STM_USB_GUSBCFG_TRDT_MASK 0xf +#define STM_USB_GUSBCFG_HNPCAP 9 +#define STM_USB_GUSBCFG_SRPCAP 8 +#define STM_USB_GUSBCFG_PHYSEL 6 +#define STM_USB_GUSBCFG_TOCAL 0 +#define STM_USB_GUSBCFG_TOCAL_MASK 0x7 + +#define STM_USB_GRSTCTL_AHBIDL 31 +#define STM_USB_GRSTCTL_TXFNUM 6 +#define STM_USB_GRSTCTL_TXFNUM_ALL 0x10 +#define STM_USB_GRSTCTL_TXFNUM_MASK 0x1f +#define STM_USB_GRSTCTL_TXFFLSH 5 +#define STM_USB_GRSTCTL_RXFFLSH 4 +#define STM_USB_GRSTCTL_FCRST 2 +#define STM_USB_GRSTCTL_PSRST 1 +#define STM_USB_GRSTCTL_CSRST 0 + +#define STM_USB_GINTSTS_WKUPINT 31 +#define STM_USB_GINTSTS_SRQINT 30 +#define STM_USB_GINTSTS_DISCINT 29 +#define STM_USB_GINTSTS_CIDSCHG 28 +#define STM_USB_GINTSTS_LPMINT 27 +#define STM_USB_GINTSTS_PTXFE 26 +#define STM_USB_GINTSTS_HCINT 25 +#define STM_USB_GINTSTS_HPRTINT 24 +#define STM_USB_GINTSTS_RSTDET 23 +#define STM_USB_GINTSTS_IPXFER 21 +#define STM_USB_GINTSTS_IISOIXFR 20 +#define STM_USB_GINTSTS_OEPINT 19 +#define STM_USB_GINTSTS_IEPINT 18 +#define STM_USB_GINTSTS_EOPF 15 +#define STM_USB_GINTSTS_ISOODRP 14 +#define STM_USB_GINTSTS_ENUMDNE 13 +#define STM_USB_GINTSTS_USBRST 12 +#define STM_USB_GINTSTS_USBSUSP 11 +#define STM_USB_GINTSTS_ESUSP 10 +#define STM_USB_GINTSTS_GONAKEFF 7 +#define STM_USB_GINTSTS_GINAKEFF 6 +#define STM_USB_GINTSTS_NPTXFE 5 +#define STM_USB_GINTSTS_RXFLVL 4 +#define STM_USB_GINTSTS_SOF 3 +#define STM_USB_GINTSTS_OTGINT 2 +#define STM_USB_GINTSTS_MMIS 1 +#define STM_USB_GINTSTS_CMOD 0 + +#define STM_USB_GINTMSK_WUIM 31 +#define STM_USB_GINTMSK_SRQIM 30 +#define STM_USB_GINTMSK_DISCINT 29 +#define STM_USB_GINTMSK_CIDSCHGM 28 +#define STM_USB_GINTMSK_LPMINTM 27 +#define STM_USB_GINTMSK_PTXFEM 26 +#define STM_USB_GINTMSK_HCIM 25 +#define STM_USB_GINTMSK_PRTIM 24 +#define STM_USB_GINTMSK_RSTDETM 23 +#define STM_USB_GINTMSK_IPXFERM 21 /* host mode */ +#define STM_USB_GINTMSK_IISOOXFRM 21 /* device mode */ +#define STM_USB_GINTMSK_IISOIXFRM 20 +#define STM_USB_GINTMSK_OEPINT 19 +#define STM_USB_GINTMSK_IEPINT 18 +#define STM_USB_GINTMSK_EOPFM 15 +#define STM_USB_GINTMSK_ISOODRPM 14 +#define STM_USB_GINTMSK_ENUMDNEM 13 +#define STM_USB_GINTMSK_USBRST 12 +#define STM_USB_GINTMSK_USBSUSPM 11 +#define STM_USB_GINTMSK_ESUSPM 10 +#define STM_USB_GINTMSK_GONAKEFFM 7 +#define STM_USB_GINTMSK_GINAKEFFM 6 +#define STM_USB_GINTMSK_NPTXFEM 5 +#define STM_USB_GINTMSK_RXFLVLM 4 +#define STM_USB_GINTMSK_SOFM 3 +#define STM_USB_GINTMSK_OTGINT 2 +#define STM_USB_GINTMSK_MMISM 1 + +#define STM_USB_GRXSTSP_STSPHST 27 +#define STM_USB_GRXSTSP_FRMNUM 21 +#define STM_USB_GRXSTSP_FRMNUM_MASK 0xf +#define STM_USB_GRXSTSP_PKTSTS 17 +#define STM_USB_GRXSTSP_PKTSTS_NAK 1 +#define STM_USB_GRXSTSP_PKTSTS_OUT_DATA 2 +#define STM_USB_GRXSTSP_PKTSTS_OUT_COMPLETE 3 +#define STM_USB_GRXSTSP_PKTSTS_SETUP_COMPLETE 4 +#define STM_USB_GRXSTSP_PKTSTS_SETUP_DATA 5 +#define STM_USB_GRXSTSP_PKTSTS_MASK 0xf +#define STM_USB_GRXSTSP_DPID 15 +#define STM_USB_GRXSTSP_DPID_MASK 3 +#define STM_USB_GRXSTSP_BCNT 4 +#define STM_USB_GRXSTSP_BCNT 4 +#define STM_USB_GRXSTSP_BCNT_MASK 0x3ff +#define STM_USB_GRXSTSP_EPNUM 0 +#define STM_USB_GRXSTSP_EPNUM_MASK 0xf + +#define STM_USB_GRXFSIZ_RXFD 0 +#define STM_USB_GRXFSIZ_RXFD_MASK 0xffff + +#define STM_USB_GCCFG_VBDEN 21 +#define STM_USB_GCCFG_SDEN 20 +#define STM_USB_GCCFG_PDEN 19 +#define STM_USB_GCCFG_DCDEN 18 +#define STM_USB_GCCFG_BCDEN 17 +#define STM_USB_GCCFG_PWRDWN 16 +#define STM_USB_GCCFG_PS2DET 3 +#define STM_USB_GCCFG_SDET 2 +#define STM_USB_GCCFG_PDET 1 +#define STM_USB_GCCFG_DCDET 0 + +#define STM_USB_DIEPTXF0_TX0FD 16 +#define STM_USB_DIEPTXF0_TX0FSA 0 + +#define STM_USB_DCFG_ERRATIM 15 +#define STM_USB_DCFG_PFIVL 11 +#define STM_USB_DCFG_PFIVL_80 0 +#define STM_USB_DCFG_PFIVL_85 1 +#define STM_USB_DCFG_PFIVL_90 2 +#define STM_USB_DCFG_PFIVL_95 3 +#define STM_USB_DCFG_PFIVL_MASK 3 +#define STM_USB_DCFG_DAD 4 +#define STM_USB_DCFG_DAD_MASK 0x7f +#define STM_USB_DCFG_NZLSOHSK 2 +#define STM_USB_DCFG_DSPD 0 +#define STM_USB_DCFG_DSPD_FULL_SPEED 3 +#define STM_USB_DCFG_DSPD_MASK 3 +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ +#define STM_USB_DCFG_ + +#define STM_USB_DCTL_DSBESLRJCT 18 +#define STM_USB_DCTL_POPRGDNE 11 +#define STM_USB_DCTL_CGONAK 10 +#define STM_USB_DCTL_SGONAK 9 +#define STM_USB_DCTL_CGINAK 8 +#define STM_USB_DCTL_SGINAK 7 +#define STM_USB_DCTL_TCTL 4 +#define STM_USB_DCTL_GONSTS 3 +#define STM_USB_DCTL_GINSTS 2 +#define STM_USB_DCTL_SDIS 1 +#define STM_USB_DCTL_RWUSIG 0 + +#define STM_USB_DSTS_DEVLNSTS 22 +#define STM_USB_DSTS_DEVLNSTS_MASK 0x3 +#define STM_USB_DSTS_FNSOF 8 +#define STM_USB_DSTS_FNSOF_MASK 0x3fff +#define STM_USB_DSTS_EERR 3 +#define STM_USB_DSTS_ENUMSPD 1 +#define STM_USB_DSTS_ENUMSPD_MASK 3 +#define STM_USB_DSTS_SUSPSTS 0 + +#define STM_USB_DIEPMSK_NAKM 13 +#define STM_USB_DIEPMSK_TXFURM 8 +#define STM_USB_DIEPMSK_INEPNEM 6 +#define STM_USB_DIEPMSK_INEPNMM 5 +#define STM_USB_DIEPMSK_ITTXFEMSK 4 +#define STM_USB_DIEPMSK_TOM 3 +#define STM_USB_DIEPMSK_EPDM 1 +#define STM_USB_DIEPMSK_XFRCM 0 + +#define STM_USB_DOEPMSK_NYETMSK 14 +#define STM_USB_DOEPMSK_NAKMSK 13 +#define STM_USB_DOEPMSK_BERRM 12 +#define STM_USB_DOEPMSK_OUTPKTERRM 8 +#define STM_USB_DOEPMSK_STSPHSRXM 5 +#define STM_USB_DOEPMSK_OTEPDM 4 +#define STM_USB_DOEPMSK_STUPM 3 +#define STM_USB_DOEPMSK_EPDM 1 +#define STM_USB_DOEPMSK_XFRCM 0 + +#define STM_USB_DAINT_OEPINT 16 +#define STM_USB_DAINT_OEPINT_MASK 0xffff +#define STM_USB_DAINT_IEPINT 16 +#define STM_USB_DAINT_IEPINT_MASK 0xffff + +#define STM_USB_DAINTMSK_OEPM 16 +#define STM_USB_DAINTMSK_OEPM_MASK 0xffff +#define STM_USB_DAINTMSK_IEPM 0 +#define STM_USB_DAINTMSK_IEPM_MASK 0xffff + +#define STM_USB_DIEPCTL_EPENA 31 +#define STM_USB_DIEPCTL_EPDIS 30 +#define STM_USB_DIEPCTL_SNAK 27 +#define STM_USB_DIEPCTL_CNAK 26 +#define STM_USB_DIEPCTL_TXFNUM 22 +#define STM_USB_DIEPCTL_TXFNUM_MASK 0xf +#define STM_USB_DIEPCTL_STALL 21 +#define STM_USB_DIEPCTL_EPTYP 18 +#define STM_USB_DIEPCTL_EPTYP_CONTROL 0 +#define STM_USB_DIEPCTL_EPTYP_ISOCHRONOUS 1 +#define STM_USB_DIEPCTL_EPTYP_BULK 2 +#define STM_USB_DIEPCTL_EPTYP_INTERRUPT 3 +#define STM_USB_DIEPCTL_EPTYP_MASK 3 +#define STM_USB_DIEPCTL_NAKSTS 17 +#define STM_USB_DIEPCTL_EONUM 16 +#define STM_USB_DIEPCTL_USBAEP 15 +#define STM_USB_DIEPCTL_MPSIZ 0 +#define STM_USB_DIEPCTL_MPSIZ0_64 0 +#define STM_USB_DIEPCTL_MPSIZ0_32 1 +#define STM_USB_DIEPCTL_MPSIZ0_16 2 +#define STM_USB_DIEPCTL_MPSIZ0_8 3 +#define STM_USB_DIEPCTL_MPSIZ0_MASK 3 +#define STM_USB_DIEPCTL_MPSIZ_MASK 0x7f + +#define STM_USB_DIEPINT_NAK 13 +#define STM_USB_DIEPINT_PKTDRPSTS 11 +#define STM_USB_DIEPINT_TXFIFOUDRN 8 +#define STM_USB_DIEPINT_TXFE 7 +#define STM_USB_DIEPINT_INEPNE 6 +#define STM_USB_DIEPINT_INEPNM 5 +#define STM_USB_DIEPINT_ITTXFE 4 +#define STM_USB_DIEPINT_TOC 3 +#define STM_USB_DIEPINT_EPDISD 1 +#define STM_USB_DIEPINT_XFRC 0 + +#define STM_USB_DIEPTSIZ_MCNT 29 +#define STM_USB_DIEPTSIZ_MCNT_MASK 3 +#define STM_USB_DIEPTSIZ_PKTCNT 19 +#define STM_USB_DIEPTSIZ_PKTCNT0_MASK 3 +#define STM_USB_DIEPTSIZ_PKTCNT_MASK 0x3ff +#define STM_USB_DIEPTSIZ_XFRSIZ 0 +#define STM_USB_DIEPTSIZ_XFRSIZ0_MASK 0x7f +#define STM_USB_DIEPTSIZ_XFRSIZ_MASK 0x7ffff + +#define STM_USB_DOEPCTL_EPENA 31 +#define STM_USB_DOEPCTL_EPDIS 30 +#define STM_USB_DOEPCTL_SNAK 27 +#define STM_USB_DOEPCTL_CNAK 26 +#define STM_USB_DOEPCTL_STALL 21 +#define STM_USB_DOEPCTL_SNPM 20 +#define STM_USB_DOEPCTL_EPTYP 18 +#define STM_USB_DOEPCTL_EPTYP_CONTROL 0 +#define STM_USB_DOEPCTL_EPTYP_ISOCHRONOUS 1 +#define STM_USB_DOEPCTL_EPTYP_BULK 2 +#define STM_USB_DOEPCTL_EPTYP_INTERRUPT 3 +#define STM_USB_DOEPCTL_EPTYP_MASK 3 +#define STM_USB_DOEPCTL_NAKSTS 17 +#define STM_USB_DOEPCTL_USBAEP 15 +#define STM_USB_DOEPCTL_MPSIZ 0 +#define STM_USB_DOEPCTL_MPSIZ0_64 0 +#define STM_USB_DOEPCTL_MPSIZ0_32 1 +#define STM_USB_DOEPCTL_MPSIZ0_16 2 +#define STM_USB_DOEPCTL_MPSIZ0_8 3 +#define STM_USB_DOEPCTL_MPSIZ0_MASK 3 + +#define STM_USB_DOEPINT_NAK 13 +#define STM_USB_DOEPINT_BERR 12 +#define STM_USB_DOEPINT_OUTPKTERR 8 +#define STM_USB_DOEPINT_STSPHSRX 5 +#define STM_USB_DOEPINT_OTEPDIS 4 +#define STM_USB_DOEPINT_STUP 3 +#define STM_USB_DOEPINT_EPDISD 1 +#define STM_USB_DOEPINT_XFRC 0 + +#define STM_USB_DOEPTSIZ_STUPCNT 29 +#define STM_USB_DOEPTSIZ_STUPCNT_MASK 3 +#define STM_USB_DOEPTSIZ_PKTCNT 19 +#define STM_USB_DOEPTSIZ_XFRSIZ 0 +#define STM_USB_DOEPTSIZ_XFRSIZ_MASK 0x7f + /* Errata 2.1.5 Delay after an RCC peripheral clock enabling -- cgit v1.2.3