I am having a problem building code for the “genericSTM32F103RB” board, in particular, referencing the serial ports. There is an inconsistency between the bluepill board, which uses a very similar uC.
Both of these parts are classified as medium-density in the datasheet (stm32f103c8.pdf), and therefore, I would expect them to have the same peripherals defined.
However, while both boards have Serial defined, BluePill has Serial1 defined, while the generic does not, and generic has Serial2 defined, while bluepill does not.
Is this purely based on which pins are physically available on the PCB? Or is there something else underlying this? And if so, where can I find where this is defined?
Every variant has a different set of serials activated. The documentation tells you how to active the other non-activated ones. Use this info together with build_flags.
Thank you for responding!
Can you possibly point me to how I enable the alternate function? I.e. so I can use USART3 on pins PC_11 (rx) and PC_10(tx)?
I did try to simply create the HardwareSerial port on those pins, and that did not work.
I have been trawling through the source, but so far have been unable to figure it out.
I have found the pin_function() function, but cannot figure out the argument it needs. And there are very few hits on the internet of any relevance.
Unfortunately, I was an idiot. A typo in the src led to the wrong serial port being used. The following works perfectly to enable the third serial port on the alternate pins:
Defining your own Serial3 object will conflict for those specific board variants which have their Serial object set to be Serial3 (aka UART3 is the standard one). I do not know whether any of the board variants in the STM32Duino core actually have their standard serial on UART3. The way I would have done it is to follow the documentation and use the ENABLE_HWSERIALx with PIN_SERIALn_RX and PIN_SERIALn_TX macros as build flags, so e.g.
This is a very low-level function. If you want to change the pins during run-time, you should call the
functions on your serial object (which are instances of the HardwareSerial class).
So if you e.g. have a Serial3 object (because you’ve previously enabled it or created it yourself), then you you can use
Serial3.setRx(PC11);
Serial3.setTx(PC10);
in the code.
The arguments are either the pin numbers (uint32_t) or a value from the PinNameenum. The pun numbers are the PXY macros (e.g. PC3) where as the enum is the e.g. PC_3 value.
Thanks for looking into this in such detail. I guess you are correct, in terms of predefining the UART in the build flags, rather than in code. My rationale is that I am porting ESPHome, code designed on run on the ESP8266 and ESP32, the latter of which is almost entirely flexible in terms of pin allocations to peripherals.
Of course, since ESPHome constructs the platformio.ini file as well, adding the UART pin assignments in the build file is also an option.
Unfortunately, adding the STM32 into a mix of “only ESP8266 and ESP32” adds an exponential amount of complexity to the project.