1// +build stm32,!stm32f103xx 2 3package machine 4 5import ( 6 "device/stm32" 7) 8 9// GPIO for the stm32 families except the stm32f1xx which uses a simpler but 10// less flexible mechanism. Extend the +build directive above to exclude other 11// models in the stm32f1xx series as necessary 12 13const ( 14 // Mode Flag 15 PinOutput PinMode = 0 16 PinInput PinMode = PinInputFloating 17 PinInputFloating PinMode = 1 18 PinInputPulldown PinMode = 2 19 PinInputPullup PinMode = 3 20 21 // for UART 22 PinModeUARTTX PinMode = 4 23 PinModeUARTRX PinMode = 5 24 25 // for I2C 26 PinModeI2CSCL PinMode = 6 27 PinModeI2CSDA PinMode = 7 28 29 // for SPI 30 PinModeSPICLK PinMode = 8 31 PinModeSPISDO PinMode = 9 32 PinModeSPISDI PinMode = 10 33 34 // for analog/ADC 35 PinInputAnalog PinMode = 11 36 37 // for PWM 38 // TBD 39) 40 41// Configure this pin with the given configuration 42func (p Pin) Configure(config PinConfig) { 43 // Use the default system alternate function; this 44 // will only be used if you try to call this with 45 // one of the peripheral modes instead of vanilla GPIO. 46 p.ConfigureAltFunc(config, stm32.AF0_SYSTEM) 47} 48 49// Configure this pin with the given configuration including alternate 50// function mapping if necessary. 51func (p Pin) ConfigureAltFunc(config PinConfig, altFunc stm32.AltFunc) { 52 // Configure the GPIO pin. 53 p.enableClock() 54 port := p.getPort() 55 pin := uint8(p) % 16 56 pos := pin * 2 57 58 switch config.Mode { 59 60 // GPIO 61 case PinInputFloating: 62 port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos) 63 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 64 case PinInputPulldown: 65 port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos) 66 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullDown, 0x3, pos) 67 case PinInputPullup: 68 port.MODER.ReplaceBits(stm32.GPIOModeInput, 0x3, pos) 69 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullUp, 0x3, pos) 70 case PinOutput: 71 port.MODER.ReplaceBits(stm32.GPIOModeOutputGeneral, 0x3, pos) 72 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedHigh, 0x3, pos) 73 74 // UART 75 case PinModeUARTTX: 76 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 77 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedHigh, 0x3, pos) 78 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRPullUp, 0x3, pos) 79 p.SetAltFunc(altFunc) 80 case PinModeUARTRX: 81 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 82 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 83 p.SetAltFunc(altFunc) 84 85 // I2C 86 case PinModeI2CSCL: 87 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 88 port.OTYPER.ReplaceBits(stm32.GPIOOutputTypeOpenDrain, 0x1, pos) 89 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos) 90 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 91 p.SetAltFunc(altFunc) 92 case PinModeI2CSDA: 93 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 94 port.OTYPER.ReplaceBits(stm32.GPIOOutputTypeOpenDrain, 0x1, pos) 95 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos) 96 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 97 p.SetAltFunc(altFunc) 98 99 // SPI 100 case PinModeSPICLK: 101 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 102 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos) 103 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 104 p.SetAltFunc(altFunc) 105 case PinModeSPISDO: 106 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 107 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos) 108 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 109 p.SetAltFunc(altFunc) 110 case PinModeSPISDI: 111 port.MODER.ReplaceBits(stm32.GPIOModeOutputAltFunc, 0x3, pos) 112 port.OSPEEDR.ReplaceBits(stm32.GPIOSpeedLow, 0x3, pos) 113 port.PUPDR.ReplaceBits(stm32.GPIOPUPDRFloating, 0x3, pos) 114 p.SetAltFunc(altFunc) 115 } 116} 117 118// SetAltFunc maps the given alternative function to the I/O pin 119func (p Pin) SetAltFunc(af stm32.AltFunc) { 120 port := p.getPort() 121 pin := uint8(p) % 16 122 pos := (pin % 8) * 4 123 if pin < 8 { 124 port.AFRL.ReplaceBits(uint32(af), 0xf, pos) 125 } else { 126 port.AFRH.ReplaceBits(uint32(af), 0xf, pos) 127 } 128} 129