Hi,
I am currently testing the USART on my STM32F103C8 Blue Pill, which I should be able to send text to and it will echo back anything typed and respond to various commands.
I'm finding something a little odd, though. It prints the start up messages fine and goes into the main loop to wait for characters from the USART, which it echoes back to the terminal. The problem is it ignores the first 10 chars every time it restarts. Every time.
Here's the basic code:
/* Initialize all configured peripherals */ MX_GPIO_Init(); MX_TIM2_Init(CLKSPD); MX_TIM3_Init(); MX_USART2_UART_Init(); // Clear the terminal window HAL_UART_Transmit(&huart2, (uint8_t *)12, 1, HAL_MAX_DELAY); // Start progress logging HAL_UART_Transmit(&huart2, (uint8_t *)"GPIO, Timers and UART set up.\r\n", 32, HAL_MAX_DELAY); /* USER CODE BEGIN 2 */ HAL_TIM_Base_Start(&htim2); HAL_TIM_PWM_Start(&htim2,TIM_CHANNEL_1); HAL_TIM_Base_Start(&htim3); HAL_TIM_PWM_Start(&htim3,TIM_CHANNEL_1); HAL_UART_Transmit(&huart2, (uint8_t *)"Clock outputs enabled.\r\n", 26, HAL_MAX_DELAY); //__HAL_UART_ENABLE_IT(&huart1,UART_IT_RXNE); HAL_UART_Receive_IT(&huart2, (uint8_t *)aRxBuffer, RXBUFFERSIZE); HAL_UART_Transmit(&huart2, (uint8_t *)"aRxBuffer set up.\r\n", 21, HAL_MAX_DELAY); // USART INTERRUPTS NVIC_SetPriority(USART2_IRQn, 0); NVIC_EnableIRQ(USART2_IRQn); /* USER CODE END 2 */ HAL_UART_Transmit(&huart2, (uint8_t *)"USART Interrupts enabled.\r\n", 28, HAL_MAX_DELAY); /* Infinite loop */ /* USER CODE BEGIN WHILE */ uint8_t buffer[40] = ""; int bufferRxPtr = 0; uint8_t CR[4] = "\r\n"; HAL_UART_Transmit(&huart2, (uint8_t *)"Entering main loop...\r\n", 24, HAL_MAX_DELAY); while (1) { HAL_UART_Receive(&huart2, &buffer[bufferRxPtr], 1, HAL_MAX_DELAY); if (buffer[bufferRxPtr] == 13) { // CR & LF HAL_UART_Transmit(&huart2, CR, sizeof(CR), HAL_MAX_DELAY); bufferRxPtr = 0; } else if (buffer[bufferRxPtr] == 35) { // End of Line char '#' detected - interpret command buffer[bufferRxPtr] = '\0'; bufferRxPtr = 0; HAL_UART_Transmit(&huart2, CR, sizeof(CR), HAL_MAX_DELAY); // Check for command char at the start of the buffer if (buffer[0] == 37) { // Now get the command switch (buffer[1]) { case 67: // Uppercase C case 99: // Lowercase c ToggleClkSpeed(true, buffer[2]); break; case 82: // Uppercase R case 114: // Lowercase r HAL_UART_Transmit(&huart2, (uint8_t *)"Resetting...\r\n", 14, HAL_MAX_DELAY); SystemReset(); break; case 83: // Uppercase S case 115: // Lowercase s HAL_UART_Transmit(&huart2, (uint8_t *)"%S", 2, HAL_MAX_DELAY); HAL_UART_Transmit(&huart2, &CLKSPD, 1, HAL_MAX_DELAY); HAL_UART_Transmit(&huart2, (uint8_t *)"#", 1, HAL_MAX_DELAY); break; case 88: // Uppercase X case 120: // Lowercase x ToggleClkSpeed(false, buffer[2]); break; default: HAL_UART_Transmit(&huart2, (uint8_t *)"Unrecognised command: ", 22, HAL_MAX_DELAY); HAL_UART_Transmit(&huart2, buffer, strlen((char*)buffer), HAL_MAX_DELAY); HAL_UART_Transmit(&huart2, CR, sizeof(CR), HAL_MAX_DELAY); break; } } } else { HAL_UART_Transmit(&huart2, &buffer[bufferRxPtr], 1, HAL_MAX_DELAY); // Check for potential buffer overflow if (bufferRxPtr > sizeof(buffer) - 2) { bufferRxPtr = 0; } else { bufferRxPtr += 1; } }
Now, I know it's not interrupt driven, I'm just trying to get the basics working first. In the terminal window, on reset, I'm seeing everything up to "Entering main loop..." - I then have to tap a key 11 times - on the 11th time, I see the char echoed back in the terminal window.
Any ideas why it's ignoring me for 10 chars?
That really is a basic skill that you need to learn right from the beginning!
Yes, I know. I was hoping that the STM32 would be as easy to set up as the Arduino Nano, so I dived straight into the code not expecting to need to use a debugger. Best laid plans, and all that...
Don't bother with the simulator - just use the debugger.
Righto. So there's some extra connections I need to make between the ST-Link and the Blue Pill, I gather. Will get on that ASAP.
Why not start with a Nucleo board, which has the ST-Link built in - probably cheaper than the cost of a separate board + even an eBay ST-Link rip-off.
(a real ST-Link is only ~£20)
Because I'm a hobbyist rather than a professional and I'm just trying to evaluate the STM32F103 as a possible replacement for the ATmega328 I've got doing the job currently. I need more IO pins than the '328 offers as I'd like the micro-controller to have full access to the address and data bus of the SBC it supervises for DMA.
If it's Arduino you want, see:
community.st.com/.../stm32-cores-enabled-in-arduino-ide
(although the site is broken at the moment)
I don't see why being a hobbyist prevents you using a Nucleo board?
eg, uk.farnell.com/.../2394226
under a tenner with an ST-Link built in!
>>Righto. So there's some extra connections I need to make between the ST-Link and the Blue Pill, I gather. Will get on that ASAP.
SWDIO, SWCLK, NRST, GND - Same pins to program as debug. Basic requirements of a SWD attached debug pod.
For a real external ST-LINK the VTarget voltage will also need connecting to power the buffers.
* I don't see why being a hobbyist prevents you using a Nucleo board? *
No reason other than I'm trying to minimise cost on something I may not actually end up using.
* eg, uk.farnell.com/.../2394226 under a tenner with an ST-Link built in! *
I obviously misread your post - under a tenner isn't bad at all!