stm32: use stm32-rs SVDs which are of much higher quality

This commit changes the number of wait states for the stm32f103 chip to
2 instead of 4. This gets it back in line with the datasheet, but it
also has the side effect of breaking I2C. Therefore, another (seemingly
unrelated) change is needed: the i2cTimeout constant must be increased
to a higher value to adjust to the lower flash wait states - presumably
because the lower number of wait states allows the chip to run code
faster.
This commit is contained in:
Ayke van Laethem
2020-12-29 13:14:00 +01:00
committed by Ron Evans
parent 65caf777dd
commit 154c7c691b
24 changed files with 259 additions and 333 deletions
+9 -9
View File
@@ -122,17 +122,17 @@ var (
UART1 = UART{
Buffer: NewRingBuffer(),
Bus: stm32.USART3,
AltFuncSelector: stm32.AF7_USART1_2_3,
AltFuncSelector: AF7_USART1_2_3,
}
UART2 = UART{
Buffer: NewRingBuffer(),
Bus: stm32.USART6,
AltFuncSelector: stm32.AF8_USART4_5_6,
AltFuncSelector: AF8_USART4_5_6,
}
UART3 = UART{
Buffer: NewRingBuffer(),
Bus: stm32.USART1,
AltFuncSelector: stm32.AF7_USART1_2_3,
AltFuncSelector: AF7_USART1_2_3,
}
UART0 = UART1
)
@@ -181,15 +181,15 @@ const (
var (
SPI1 = SPI{
Bus: stm32.SPI2,
AltFuncSelector: stm32.AF5_SPI1_SPI2,
AltFuncSelector: AF5_SPI1_SPI2,
}
SPI2 = SPI{
Bus: stm32.SPI3,
AltFuncSelector: stm32.AF6_SPI3,
AltFuncSelector: AF6_SPI3,
}
SPI3 = SPI{
Bus: stm32.SPI1,
AltFuncSelector: stm32.AF5_SPI1_SPI2,
AltFuncSelector: AF5_SPI1_SPI2,
}
SPI0 = SPI1
)
@@ -229,15 +229,15 @@ const (
var (
I2C1 = I2C{
Bus: stm32.I2C1,
AltFuncSelector: stm32.AF4_I2C1_2_3,
AltFuncSelector: AF4_I2C1_2_3,
}
I2C2 = I2C{
Bus: stm32.I2C2,
AltFuncSelector: stm32.AF4_I2C1_2_3,
AltFuncSelector: AF4_I2C1_2_3,
}
I2C3 = I2C{
Bus: stm32.I2C1,
AltFuncSelector: stm32.AF4_I2C1_2_3,
AltFuncSelector: AF4_I2C1_2_3,
}
I2C0 = I2C1
)
+1 -1
View File
@@ -55,7 +55,7 @@ var (
// Console UART (LPUSART1)
UART0 = UART{
Buffer: NewRingBuffer(),
Bus: stm32.LPUSART1,
Bus: stm32.LPUART1,
AltFuncSelector: 6,
}
+2 -2
View File
@@ -30,7 +30,7 @@ var (
UART0 = UART{
Buffer: NewRingBuffer(),
Bus: stm32.USART2,
AltFuncSelector: stm32.AF7_USART1_2_3,
AltFuncSelector: AF7_USART1_2_3,
}
UART1 = &UART0
)
@@ -62,7 +62,7 @@ const (
var (
SPI0 = SPI{
Bus: stm32.SPI1,
AltFuncSelector: stm32.AF5_SPI1_SPI2,
AltFuncSelector: AF5_SPI1_SPI2,
}
SPI1 = &SPI0
)
+3 -3
View File
@@ -1,4 +1,4 @@
// +build stm32,!stm32f103xx,!stm32f407,!stm32f7x2,!stm32l0
// +build stm32,!stm32f103,!stm32f407,!stm32f7x2,!stm32l0
package machine
@@ -110,10 +110,10 @@ type (
)
func (sa address7Bit) toRead() uint32 {
return uint32(((uint8(sa) << 1) | uint8(stm32.I2C_OAR1_ADD0)) & 0xFF)
return uint32(((uint8(sa) << 1) | 1) & 0xFF)
}
func (sa address7Bit) toWrite() uint32 {
return uint32(((uint8(sa) << 1) & ^(uint8(stm32.I2C_OAR1_ADD0))) & 0xFF)
return uint32((uint8(sa) << 1) & 0xFF)
}
func (sa address7Bit) bitSize() uint8 { return 7 } // 7-bit addresses
+57 -36
View File
@@ -1,4 +1,4 @@
// +build stm32,!stm32f103xx
// +build stm32,!stm32f103
package machine
@@ -38,85 +38,106 @@ const (
// TBD
)
// Define several bitfields that have different names across chip families but
// essentially have the same meaning.
const (
// MODER bitfields.
gpioModeInput = 0
gpioModeOutput = 1
gpioModeAlternate = 2
gpioModeAnalog = 3
gpioModeMask = 0x3
// PUPDR bitfields.
gpioPullFloating = 0
gpioPullUp = 1
gpioPullDown = 2
gpioPullMask = 0x3
// OSPEED bitfields.
gpioOutputSpeedHigh = 2
gpioOutputSpeedLow = 0
gpioOutputSpeedMask = 0x3
)
// Configure this pin with the given configuration
func (p Pin) Configure(config PinConfig) {
// Use the default system alternate function; this
// will only be used if you try to call this with
// one of the peripheral modes instead of vanilla GPIO.
p.ConfigureAltFunc(config, stm32.AF0_SYSTEM)
p.ConfigureAltFunc(config, 0)
}
// Configure this pin with the given configuration including alternate
// function mapping if necessary.
func (p Pin) ConfigureAltFunc(config PinConfig, altFunc stm32.AltFunc) {
func (p Pin) ConfigureAltFunc(config PinConfig, altFunc uint8) {
// Configure the GPIO pin.
p.enableClock()
port := p.getPort()
pin := uint8(p) % 16
pos := pin * 2
pos := (uint8(p) % 16) * 2 // assume each field is two bits in size (with mask 0x3)
switch config.Mode {
// GPIO
case PinInputFloating:
port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeInput, gpioModeMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
case PinInputPulldown:
port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullDown, 0x3, pos)
port.MODER.ReplaceBits(gpioModeInput, gpioModeMask, pos)
port.PUPDR.ReplaceBits(gpioPullDown, gpioPullMask, pos)
case PinInputPullup:
port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullUp, 0x3, pos)
port.MODER.ReplaceBits(gpioModeInput, gpioModeMask, pos)
port.PUPDR.ReplaceBits(gpioPullUp, gpioPullMask, pos)
case PinOutput:
port.MODER.ReplaceBits(stm32.GPIOModeOutputGeneral, 0x3, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedHigh, 0x3, pos)
port.MODER.ReplaceBits(gpioModeOutput, gpioModeMask, pos)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedHigh, gpioOutputSpeedMask, pos)
// UART
case PinModeUARTTX:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedHigh, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullUp, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedHigh, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullUp, gpioPullMask, pos)
p.SetAltFunc(altFunc)
case PinModeUARTRX:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
// I2C
case PinModeI2CSCL:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OTYPER.ReplaceBits(stm32.GPIOOutputTypeOpenDrain, 0x1, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OTYPER.ReplaceBits(stm32.GPIO_OTYPER_OT0_OpenDrain, stm32.GPIO_OTYPER_OT0_Msk, pos/2)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedLow, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
case PinModeI2CSDA:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OTYPER.ReplaceBits(stm32.GPIOOutputTypeOpenDrain, 0x1, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OTYPER.ReplaceBits(stm32.GPIO_OTYPER_OT0_OpenDrain, stm32.GPIO_OTYPER_OT0_Msk, pos/2)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedLow, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
// SPI
case PinModeSPICLK:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedLow, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
case PinModeSPISDO:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedLow, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
case PinModeSPISDI:
port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos)
port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos)
port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos)
port.MODER.ReplaceBits(gpioModeAlternate, gpioModeMask, pos)
port.OSPEEDR.ReplaceBits(gpioOutputSpeedLow, gpioOutputSpeedMask, pos)
port.PUPDR.ReplaceBits(gpioPullFloating, gpioPullMask, pos)
p.SetAltFunc(altFunc)
}
}
// SetAltFunc maps the given alternative function to the I/O pin
func (p Pin) SetAltFunc(af stm32.AltFunc) {
func (p Pin) SetAltFunc(af uint8) {
port := p.getPort()
pin := uint8(p) % 16
pos := (pin % 8) * 4
@@ -1,4 +1,4 @@
// +build stm32,stm32f103xx
// +build stm32,stm32f103
package machine
@@ -169,21 +169,21 @@ func (spi SPI) getBaudRate(config SPIConfig) uint32 {
switch config.Frequency {
case 125000:
// Note: impossible to achieve lower frequency with current PCLK2!
conf |= stm32.SPI_BaudRatePrescaler_256
conf |= stm32.SPI_CR1_BR_Div256
case 250000:
conf |= stm32.SPI_BaudRatePrescaler_256
conf |= stm32.SPI_CR1_BR_Div256
case 500000:
conf |= stm32.SPI_BaudRatePrescaler_128
conf |= stm32.SPI_CR1_BR_Div128
case 1000000:
conf |= stm32.SPI_BaudRatePrescaler_64
conf |= stm32.SPI_CR1_BR_Div64
case 2000000:
conf |= stm32.SPI_BaudRatePrescaler_32
conf |= stm32.SPI_CR1_BR_Div32
case 4000000:
conf |= stm32.SPI_BaudRatePrescaler_16
conf |= stm32.SPI_CR1_BR_Div16
case 8000000:
conf |= stm32.SPI_BaudRatePrescaler_8
conf |= stm32.SPI_CR1_BR_Div8
default:
conf |= stm32.SPI_BaudRatePrescaler_256
conf |= stm32.SPI_CR1_BR_Div256
}
return conf
}
@@ -542,7 +542,7 @@ func (i2c I2C) Tx(addr uint16, w, r []byte) error {
return nil
}
const i2cTimeout = 500
const i2cTimeout = 1000
// signalStart sends a start signal.
func (i2c I2C) signalStart() error {
+23 -3
View File
@@ -14,13 +14,33 @@ func CPUFrequency() uint32 {
return 168000000
}
// Alternative peripheral pin functions
const (
AF0_SYSTEM = 0
AF1_TIM1_2 = 1
AF2_TIM3_4_5 = 2
AF3_TIM8_9_10_11 = 3
AF4_I2C1_2_3 = 4
AF5_SPI1_SPI2 = 5
AF6_SPI3 = 6
AF7_USART1_2_3 = 7
AF8_USART4_5_6 = 8
AF9_CAN1_CAN2_TIM12_13_14 = 9
AF10_OTG_FS_OTG_HS = 10
AF11_ETH = 11
AF12_FSMC_SDIO_OTG_HS_1 = 12
AF13_DCMI = 13
AF14 = 14
AF15_EVENTOUT = 15
)
// -- UART ---------------------------------------------------------------------
type UART struct {
Buffer *RingBuffer
Bus *stm32.USART_Type
Interrupt interrupt.Interrupt
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
func (uart UART) configurePins(config UARTConfig) {
@@ -44,7 +64,7 @@ func (uart UART) getBaudRateDivisor(baudRate uint32) uint32 {
type SPI struct {
Bus *stm32.SPI_Type
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
func (spi SPI) configurePins(config SPIConfig) {
@@ -93,7 +113,7 @@ func (spi SPI) getBaudRate(config SPIConfig) uint32 {
type I2C struct {
Bus *stm32.I2C_Type
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
func (i2c I2C) configurePins(config I2CConfig) {
+31 -11
View File
@@ -13,6 +13,26 @@ func CPUFrequency() uint32 {
return 168000000
}
// Alternative peripheral pin functions
const (
AF0_SYSTEM = 0
AF1_TIM1_2 = 1
AF2_TIM3_4_5 = 2
AF3_TIM8_9_10_11 = 3
AF4_I2C1_2_3 = 4
AF5_SPI1_SPI2 = 5
AF6_SPI3 = 6
AF7_USART1_2_3 = 7
AF8_USART4_5_6 = 8
AF9_CAN1_CAN2_TIM12_13_14 = 9
AF10_OTG_FS_OTG_HS = 10
AF11_ETH = 11
AF12_FSMC_SDIO_OTG_HS_1 = 12
AF13_DCMI = 13
AF14 = 14
AF15_EVENTOUT = 15
)
//---------- UART related types and code
// UART representation
@@ -20,7 +40,7 @@ type UART struct {
Buffer *RingBuffer
Bus *stm32.USART_Type
Interrupt interrupt.Interrupt
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
// Configure the UART.
@@ -48,7 +68,7 @@ func (uart UART) getBaudRateDivisor(baudRate uint32) uint32 {
// SPI on the STM32Fxxx using MODER / alternate function pins
type SPI struct {
Bus *stm32.SPI_Type
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
// Set baud rate for SPI
@@ -70,26 +90,26 @@ func (spi SPI) getBaudRate(config SPIConfig) uint32 {
// TODO: also include the MCU/APB clock setting in the equation
switch true {
case localFrequency < 328125:
conf = stm32.SPI_PCLK_256
conf = stm32.SPI_CR1_BR_Div256
case localFrequency < 656250:
conf = stm32.SPI_PCLK_128
conf = stm32.SPI_CR1_BR_Div128
case localFrequency < 1312500:
conf = stm32.SPI_PCLK_64
conf = stm32.SPI_CR1_BR_Div64
case localFrequency < 2625000:
conf = stm32.SPI_PCLK_32
conf = stm32.SPI_CR1_BR_Div32
case localFrequency < 5250000:
conf = stm32.SPI_PCLK_16
conf = stm32.SPI_CR1_BR_Div16
case localFrequency < 10500000:
conf = stm32.SPI_PCLK_8
conf = stm32.SPI_CR1_BR_Div8
// NOTE: many SPI components won't operate reliably (or at all) above 10MHz
// Check the datasheet of the part
case localFrequency < 21000000:
conf = stm32.SPI_PCLK_4
conf = stm32.SPI_CR1_BR_Div4
case localFrequency < 42000000:
conf = stm32.SPI_PCLK_2
conf = stm32.SPI_CR1_BR_Div2
default:
// None of the specific baudrates were selected; choose the lowest speed
conf = stm32.SPI_PCLK_256
conf = stm32.SPI_CR1_BR_Div256
}
return conf << stm32.SPI_CR1_BR_Pos
+1 -1
View File
@@ -20,7 +20,7 @@ type UART struct {
Buffer *RingBuffer
Bus *stm32.USART_Type
Interrupt interrupt.Interrupt
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
// Configure the UART.
+14 -14
View File
@@ -164,7 +164,7 @@ func enableAltFuncClock(bus unsafe.Pointer) {
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_USART2EN)
case unsafe.Pointer(stm32.SPI2): // SPI2 clock enable
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_SPI2EN)
case unsafe.Pointer(stm32.LPUSART1): // LPUSART1 clock enable
case unsafe.Pointer(stm32.LPUART1): // LPUART1 clock enable
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_LPUART1EN)
case unsafe.Pointer(stm32.WWDG): // Window watchdog clock enable
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_WWDGEN)
@@ -176,7 +176,7 @@ func enableAltFuncClock(bus unsafe.Pointer) {
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_TIM3EN)
case unsafe.Pointer(stm32.TIM2): // TIM2 clock enable
stm32.RCC.APB1ENR.SetBits(stm32.RCC_APB1ENR_TIM2EN)
case unsafe.Pointer(stm32.SYSCFG_COMP): // System configuration controller clock enable
case unsafe.Pointer(stm32.SYSCFG): // System configuration controller clock enable
stm32.RCC.APB2ENR.SetBits(stm32.RCC_APB2ENR_SYSCFGEN)
case unsafe.Pointer(stm32.SPI1): // SPI1 clock enable
stm32.RCC.APB2ENR.SetBits(stm32.RCC_APB2ENR_SPI1EN)
@@ -194,7 +194,7 @@ type UART struct {
Buffer *RingBuffer
Bus *stm32.USART_Type
Interrupt interrupt.Interrupt
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
// Configure the UART.
@@ -208,7 +208,7 @@ func (uart UART) configurePins(config UARTConfig) {
func (uart UART) getBaudRateDivisor(baudRate uint32) uint32 {
var clock, rate uint32
switch uart.Bus {
case stm32.LPUSART1:
case stm32.LPUART1:
clock = CPUFrequency() / 2 // APB1 Frequency
rate = uint32((256 * clock) / baudRate)
case stm32.USART1:
@@ -227,7 +227,7 @@ func (uart UART) getBaudRateDivisor(baudRate uint32) uint32 {
// SPI on the STM32Fxxx using MODER / alternate function pins
type SPI struct {
Bus *stm32.SPI_Type
AltFuncSelector stm32.AltFunc
AltFuncSelector uint8
}
// Set baud rate for SPI
@@ -255,26 +255,26 @@ func (spi SPI) getBaudRate(config SPIConfig) uint32 {
// TODO: also include the MCU/APB clock setting in the equation
switch {
case localFrequency < 328125:
conf = stm32.SPI_PCLK_256
conf = stm32.SPI_CR1_BR_Div256
case localFrequency < 656250:
conf = stm32.SPI_PCLK_128
conf = stm32.SPI_CR1_BR_Div128
case localFrequency < 1312500:
conf = stm32.SPI_PCLK_64
conf = stm32.SPI_CR1_BR_Div64
case localFrequency < 2625000:
conf = stm32.SPI_PCLK_32
conf = stm32.SPI_CR1_BR_Div32
case localFrequency < 5250000:
conf = stm32.SPI_PCLK_16
conf = stm32.SPI_CR1_BR_Div16
case localFrequency < 10500000:
conf = stm32.SPI_PCLK_8
conf = stm32.SPI_CR1_BR_Div8
// NOTE: many SPI components won't operate reliably (or at all) above 10MHz
// Check the datasheet of the part
case localFrequency < 21000000:
conf = stm32.SPI_PCLK_4
conf = stm32.SPI_CR1_BR_Div4
case localFrequency < 42000000:
conf = stm32.SPI_PCLK_2
conf = stm32.SPI_CR1_BR_Div2
default:
// None of the specific baudrates were selected; choose the lowest speed
conf = stm32.SPI_PCLK_256
conf = stm32.SPI_CR1_BR_Div256
}
return conf << stm32.SPI_CR1_BR_Pos