In the previous STM32 Nucleo-64 tutorial, I showed how to simulate the nucleo board in Proteus electronics and microcontroller simulation software.In that guide, I also gave the download link for downloading the STM32 Nucleo-64 simulation model. This download link is also provided at the end of this guide. In that guide, I used the default ARM compiler set in Proteus which is gcc for ARM compiler. Here an alternative method to write code is to use STM32Cube IDE which also uses gcc but is user friendly in that using STM32Cube one can see the pins of the microcontroller which is STM32F401RE what they are doing and how they are configured along with other microcontroller setting such as the clock for the system and ports. Using the STEM32cube IDE has another advantage which is the there is HAL functions which are similar to Arduino functions.
Here we will blink a LED connected to the PA9 pin which is shown below on the STM32 Nucleo-64 board.
The circuit diagram of LED connection to the STM32 Nucleo-64 board on this PA9 pin is shown below.
Now I will explain how to write and generate hex code in order to use with the STM32 Nucleo-64 LED blink circuit in Proteus.In brief, open STM32Cube IDE, search and select the STM32 Nucleo-64 board with STM32F401RE part. Configure the port pin PA9 for output and other default pin state configuration, set the IDE to output hex code. Write the code for toggling the pin PA9 with some delay in the main.c. Build the project and generate the code. In the project debug folder, find the .hex file and upload to the STM32 Nucleo-64 board in proteus and run the simulation. The LED should be blinking. This is illustrated in the following video.
The main.c code is below.
#include "main.h"
void SystemClock_Config(void);
static void MX_GPIO_Init(void);
static void MX_USART2_UART_Init(void);
int main(void)
{
HAL_Init();
SystemClock_Config();
MX_GPIO_Init();
MX_USART2_UART_Init();
while (1)
{
HAL_GPIO_TogglePin (GPIOA, GPIO_PIN_9);
HAL_Delay (200); /* Insert delay 200 ms */
}
}
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
__HAL_RCC_PWR_CLK_ENABLE();
__HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE2);
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_NONE;
if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
{
Error_Handler();
}
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
|RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_HSI;
RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;
RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;
if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_0) != HAL_OK)
{
Error_Handler();
}
}
static void MX_USART2_UART_Init(void)
{
huart2.Instance = USART2;
huart2.Init.BaudRate = 115200;
huart2.Init.WordLength = UART_WORDLENGTH_8B;
huart2.Init.StopBits = UART_STOPBITS_1;
huart2.Init.Parity = UART_PARITY_NONE;
huart2.Init.Mode = UART_MODE_TX_RX;
huart2.Init.HwFlowCtl = UART_HWCONTROL_NONE;
huart2.Init.OverSampling = UART_OVERSAMPLING_16;
if (HAL_UART_Init(&huart2) != HAL_OK)
{
Error_Handler();
}
}
static void MX_GPIO_Init(void)
{
GPIO_InitTypeDef GPIO_InitStruct = {0};
__HAL_RCC_GPIOC_CLK_ENABLE();
__HAL_RCC_GPIOH_CLK_ENABLE();
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_GPIOB_CLK_ENABLE();
HAL_GPIO_WritePin(GPIOA, LD2_Pin|LED_Pin, GPIO_PIN_RESET);
GPIO_InitStruct.Pin = B1_Pin;
GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
GPIO_InitStruct.Pull = GPIO_NOPULL;
HAL_GPIO_Init(B1_GPIO_Port, &GPIO_InitStruct);
GPIO_InitStruct.Pin = LD2_Pin|LED_Pin;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
}
void Error_Handler(void)
{
__disable_irq();
while (1)
{
}
}
#ifdef USE_FULL_ASSERT
void assert_failed(uint8_t *file, uint32_t line)
{
}
#endif
The main function that toggles the PA9 pin is the following:
HAL_GPIO_TogglePin (GPIOA, GPIO_PIN_9);
To download the STM32 Nucleo-64 simulation model for proteus simulation you can download for free from the link below.