我们已经添加了所有需要的文件,但现在程序还是不能正常运行,因为默认生成的main.c文件已经被从项目中删除了,我们需要在Core_portme.c中添加初始化的代码,并根据不同的计时方法修改 Core_portme.c 中计时相关函数和代码
Core_portme.c中的portable_init函数在Core_main.c的main函数中首先被调用,平台的初始化的函数(时钟,GPIO,串口,缓存)可以放在这里,所以我们将 CubeMX 生成的 Main 函数中的初始化代码拷贝到 portable_init 函数中
修改前为
- void portable_init(core_portable *p, int *argc, char *argv[])
- {
- if (sizeof(ee_ptr_int) != sizeof(ee_u8 *)) {
- ee_printf("ERROR! Please define ee_ptr_int to a type that holds a
- pointer!n");
- }
- if (sizeof(ee_u32) != 4) {
- ee_printf("ERROR! Please define ee_u32 to a 32b unsigned type!n");
- }
- p->portable_id=1;
- }
复制代码
修改后为
- void portable_init(core_portable *p, int *argc, char *argv[])
- {
- /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
- HAL_Init();
- /* Configure the system clock */
- SystemClock_Config();
- /* Initialize all configured peripherals */
- MX_GPIO_Init();
- MX_USART1_UART_Init();
- /* Enable I-Cache */
- SCB_EnableICache();
- /* Enable D-Cache */
- SCB_EnableDCache();
- if (sizeof(ee_ptr_int) != sizeof(ee_u8 *)) {
- ee_printf("ERROR! Please define ee_ptr_int to a type that holds a
- pointer!n");
- }
- if (sizeof(ee_u32) != 4) {
- ee_printf("ERROR! Please define ee_u32 to a 32b unsigned type!n");
- }
- p->portable_id=1;
- }
复制代码
将main.c中的SystemClock_Config,MX_USART1_UART_Init 和 MX_GPIO_Init函数拷贝过来,并添将加printf重定向代码
- /** System Clock Configuration
- */
- void SystemClock_Config(void)
- {
- RCC_OscInitTypeDef RCC_OscInitStruct;
- RCC_ClkInitTypeDef RCC_ClkInitStruct;
- RCC_PeriphCLKInitTypeDef PeriphClkInitStruct;
- __HAL_RCC_PWR_CLK_ENABLE();
- __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);
- RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
- RCC_OscInitStruct.HSEState = RCC_HSE_ON;
- RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
- RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
- RCC_OscInitStruct.PLL.PLLM = 25;
- RCC_OscInitStruct.PLL.PLLN = 432;
- RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2;
- RCC_OscInitStruct.PLL.PLLQ = 2;
- HAL_RCC_OscConfig(&RCC_OscInitStruct);
- HAL_PWREx_EnableOverDrive();
- RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
- |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
- RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
- RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
- RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV4;
- RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV2;
- HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_7);
- PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_USART1;
- PeriphClkInitStruct.Usart1ClockSelection = RCC_USART1CLKSOURCE_PCLK2;
- HAL_RCCEx_PeriphCLKConfig(&PeriphClkInitStruct);
- HAL_SYSTICK_Config(HAL_RCC_GetHCLKFreq()/1000);
- HAL_SYSTICK_CLKSourceConfig(SYSTICK_CLKSOURCE_HCLK);
- /* SysTick_IRQn interrupt configuration */
- HAL_NVIC_SetPriority(SysTick_IRQn, 0, 0);
- }
- /* USART1 init function */
- void MX_USART1_UART_Init(void)
- {
- huart1.Instance = USART1;
- huart1.Init.BaudRate = 9600;
- huart1.Init.WordLength = UART_WORDLENGTH_8B;
- huart1.Init.StopBits = UART_STOPBITS_1;
- huart1.Init.Parity = UART_PARITY_ODD;
- huart1.Init.Mode = UART_MODE_TX_RX;
- huart1.Init.HwFlowCtl = UART_HWCONTROL_NONE;
- huart1.Init.OverSampling = UART_OVERSAMPLING_16;
- huart1.Init.OneBitSampling = UART_ONE_BIT_SAMPLE_DISABLE;
- huart1.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_NO_INIT;
- HAL_UART_Init(&huart1);
- }
- /** Configure pins as
- * Analog
- * Input
- * Output
- * EVENT_OUT
- * EXTI
- */
- void MX_GPIO_Init(void)
- {
- /* GPIO Ports Clock Enable */
- __HAL_RCC_GPIOA_CLK_ENABLE();
- __HAL_RCC_GPIOH_CLK_ENABLE();
- }
- #ifdef __GNUC__
- /* With GCC/RAISONANCE, small printf (option LD Linker->Libraries->Small printf
- set to 'Yes') calls __io_putchar() */
- #define PUTCHAR_PROTOTYPE int __io_putchar(int ch)
- #else
- #define PUTCHAR_PROTOTYPE int fputc(int ch, FILE *f)
- #endif /* __GNUC__ */
- /**
- * @brief Retargets the C library printf function to the USART.
- * @param None
- * @retval None
- */
- PUTCHAR_PROTOTYPE
- {
- /* Place your implementation of fputc here */
- /* e.g. write a character to the EVAL_COM1 and Loop until the end of transmission */
- HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xFFFF);
- ret
复制代码
在文件开头添加函数声明和变量定义
- UART_HandleTypeDef huart1;
- void SystemClock_Config(void);
- static void MX_GPIO_Init(void);
- static void MX_USART1_UART_Init(void);
复制代码
添加新的include文件
- #include
- #include "system_stm32f4xx.h"
- #include "stm32f4xx_hal.h"
复制代码
start_time/ stop_time/ get_time 这几个函数是coremark程序运行时计算程序运行时间所用,这里使用system tick进行计时,system tick配置为1ms的中断间隔,system tick 中断函数中更新Tick的值,每进一次中断加 1,所以还需要修改system tick的中断处理函数
在Core_portme.c中按下表找到需要修改的地方,并按下面的内容进行修改:
修改前
- void start_time(void) {
- GETMYTIME(&start_time_val );
- }
复制代码
修改后
- void start_time(void) {
- Tick = 0;
- SysTick_Config(SystemCoreClock/1000);
- }
复制代码
修改前
- void stop_time(void) {
- GETMYTIME(&stop_time_val );
- }
复制代码
修改后
- void stop_time(void) {
- /* Stop the Timer and get the encoding
- time */
- SysTick->CTRL &=
- SysTick_Counter_Disable;
- /* Clear the SysTick Counter */
- SysTick->VAL = SysTick_Counter_Clear;
- }
复制代码
修改前
- CORE_TICKS get_time(void) {
- CORE_TICKS
- elapsed=(CORE_TICKS)(MYTIMEDIFF(stop_time_val,
- start_time_val));
- return elapsed;
- }
复制代码
修改后
- CORE_TICKS get_time(void) {
- CORE_TICKS elapsed =
- (CORE_TICKS)Tick;
- return elapsed;
- }
复制代码
修改前
- #define NSECS_PER_SEC CLOCKS_PER_SEC
- #define CORETIMETYPE clock_t
- #define GETMYTIME(_t) (*_t=clock())
- #define MYTIMEDIFF(fin,ini) ((fin)-(ini))
- #define TIMER_RES_DIVIDER 1
- #define SAMPLE_TIME_IMPLEMENTATION 1
- ……
- static CORETIMETYPE start_time_val,
- stop_time_val;
复制代码
修改后
- //#define NSECS_PER_SEC CLOCKS_PER_SEC
- //#define CORETIMETYPE clock_t
- //#define GETMYTIME(_t) (*_t=clock())
- //#define MYTIMEDIFF(fin,ini) ((fin)-
- (ini))
- //#define TIMER_RES_DIVIDER 1
- //#define SAMPLE_TIME_IMPLEMENTATION 1
- ……
- //static CORETIMETYPE start_time_val,
- stop_time_val;
复制代码
修改前
- #define EE_TICKS_PER_SEC (NSECS_PER_SEC /
- TIMER_RES_DIVIDER)
复制代码
修改后
- #define EE_TICKS_PER_SEC 1000
复制代码
在 Core_portme.c 文件中添加新定义的变量和函数
- #define SysTick_Counter_Disable ((uint32_t)0xFFFFFFFE)
- #define SysTick_Counter_Enable ((uint32_t)0x00000001)
- #define SysTick_Counter_Clear ((uint32_t)0x00000000)
- __IO uint32_t Tick;
复制代码
修改SysTick_Handler函数,修改前
- void SysTick_Handler(void)
- {
- /* USER CODE BEGIN SysTick_IRQn 0 */
- /* USER CODE END SysTick_IRQn 0 */
- HAL_IncTick();
- HAL_SYSTICK_IRQHandler();
- /* USER CODE BEGIN SysTick_IRQn 1 */
- /* USER CODE END SysTick_IRQn 1 */
- }
复制代码
修改后
- void SysTick_Handler(void)
- {
- /* USER CODE BEGIN SysTick_IRQn 0 */
- extern __IO uint32_t Tick;
- Tick++;
- /* USER CODE END SysTick_IRQn 0 */
- /* USER CODE BEGIN SysTick_IRQn 1 */
- /* USER CODE END SysTick_IRQn 1 */
- }
复制代码
CoreMark 要求程序运行的最短时间至少是 10s, 根据使用的系统时钟等情况,可以在Core_portme.h中修改迭代次数
设置打印信息,修改前
- #ifndef COMPILER_FLAGS
- #define COMPILER_FLAGS FLAGS_STR /*
- "Please put compiler flags here (e.g. -o3)"
- */
- #endif
复制代码
修改后
- #ifndef COMPILER_FLAGS
- #define COMPILER_FLAGS "-Ohs -
- no_size_constraints"
- #endif
复制代码
完成后进入Options->C/C++ Compiler->Optimizations, 选择 High for speed和No size constraints以达到最优的运行速度
最后连接NUCLEO-F412ZG到电脑并用Putty等串口软件查看跑分情况