i.MX 8M EVK:如何计算1ms定时器的频率值



我想实现一个简单的"GPT";每1ms产生一次中断的计时器。然而,我每3毫秒就会收到一次中断(而不是所需的1毫秒(。

我的错误在哪里?我应该设置什么值才能获得1ms计时器?

以下是我对GPT计时器的计算:

计时器值的解释:

我们采用PLL1 DIV2 400MHz作为源时钟我们将根除数定义为4=>400MHz/4=100MHz

100MHz=每10ns增加一次我们希望每1ms 生成一个中断

因此,我们有:Output_compare_value=延迟时间x GPT_frequency

输出比较值=1 x 10^-3 x(1/(10 x 10^-9((=100000

这是我的代码(我在每次中断时更改GPIO的状态,以检查示波器上计时器的操作(:

/*
* Copyright (c) 2016, Freescale Semiconductor, Inc.
* Copyright 2016-2017 NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
*/
#include "fsl_debug_console.h"
#include "pin_mux.h"
#include "clock_config.h"
#include "board.h"
#include "fsl_gpt.h"
#include "fsl_gpio.h"
#include "fsl_common.h"
/*******************************************************************************
* Definitions
******************************************************************************/
#define GPT_IRQ_ID  GPT1_IRQn
#define EXAMPLE_GPT GPT1
//#define EXAMPLE_GPT_CLK_FREQ                                                                
//    (CLOCK_GetPllFreq(kCLOCK_SystemPll1Ctrl) / (CLOCK_GetRootPreDivider(kCLOCK_RootGpt1)) / 
//     (CLOCK_GetRootPostDivider(kCLOCK_RootGpt1)) / 2) /* SYSTEM PLL1 DIV2 */
#define EXAMPLE_GPT_CLK_FREQ    100000
#define EXAMPLE_GPT_IRQHandler GPT1_IRQHandler
#define EXAMPLE_LED_GPIO     GPIO3
#define EXAMPLE_LED_GPIO_PIN 23U
/*******************************************************************************
* Prototypes
******************************************************************************/
/*******************************************************************************
* Variables
******************************************************************************/
volatile bool gptIsrFlag = false;
/* The PIN status */
volatile bool g_pinSet = false;
/*******************************************************************************
* Code
******************************************************************************/
void EXAMPLE_GPT_IRQHandler(void)
{
/* Clear interrupt flag.*/
GPT_ClearStatusFlags(EXAMPLE_GPT, kGPT_OutputCompare1Flag);
gptIsrFlag = true;
/* Add for ARM errata 838869, affects Cortex-M4, Cortex-M4F, Cortex-M7, Cortex-M7F Store immediate overlapping
exception return operation might vector to incorrect interrupt */
#if defined __CORTEX_M && (__CORTEX_M == 4U || __CORTEX_M == 7U)
__DSB();
#endif
}
/*!
* @brief Main function
*/
int main(void)
{
uint32_t gptFreq;
gpt_config_t gptConfig;
/* Define the init structure for the output LED pin*/
gpio_pin_config_t led_config = {kGPIO_DigitalOutput, 0, kGPIO_NoIntmode};
/* Board pin, clock, debug console init */
/* Board specific RDC settings */
BOARD_RdcInit();
BOARD_InitBootPins();
BOARD_BootClockRUN();
BOARD_InitDebugConsole();
BOARD_InitMemory();
CLOCK_SetRootMux(kCLOCK_RootGpt1, kCLOCK_GptRootmuxSysPll1Div2); /* Set GPT1 source to SYSTEM PLL1 DIV2 400MHZ */
CLOCK_SetRootDivider(kCLOCK_RootGpt1, 1U, 4U);                   /* Set root clock to 400MHZ / 4 = 100MHZ */
GPT_GetDefaultConfig(&gptConfig);
/* Initialize GPT module */
GPT_Init(EXAMPLE_GPT, &gptConfig);
/* Divide GPT clock source frequency by 3 inside GPT module */
GPT_SetClockDivider(EXAMPLE_GPT, 1);
/* Get GPT clock frequency */
gptFreq = EXAMPLE_GPT_CLK_FREQ;
/* GPT frequency is divided by 3 inside module */
gptFreq /= 1;
/* Set both GPT modules to 1 second duration */
GPT_SetOutputCompareValue(EXAMPLE_GPT, kGPT_OutputCompare_Channel1, gptFreq);
/* Enable GPT Output Compare1 interrupt */
GPT_EnableInterrupts(EXAMPLE_GPT, kGPT_OutputCompare1InterruptEnable);
/* Enable at the Interrupt */
EnableIRQ(GPT_IRQ_ID);
PRINTF("rnPress any key to start the example");
GETCHAR();
/* Init output LED GPIO. */
GPIO_PinInit(EXAMPLE_LED_GPIO, EXAMPLE_LED_GPIO_PIN, &led_config);
/* Start Timer */
PRINTF("rnStarting GPT timer ...");
GPT_StartTimer(EXAMPLE_GPT);
while (true)
{
/* Check whether occur interupt and toggle LED */
if (true == gptIsrFlag)
{
PRINTF("rn GPT interrupt is occurred !");
gptIsrFlag = false;
if (g_pinSet)
{
GPIO_PinWrite(EXAMPLE_LED_GPIO, EXAMPLE_LED_GPIO_PIN, 0U);
g_pinSet = false;
}
else
{
GPIO_PinWrite(EXAMPLE_LED_GPIO, EXAMPLE_LED_GPIO_PIN, 1U);
g_pinSet = true;
}
}
else
{
__WFI();
}
}
}

我发现了计时器的问题所在。事实上,我的所有值都很好,但日志记录的执行需要时间(第PRINTF("GPT interrupt is occurred !");行(。所以我本可以进一步降低重载值,但我仍然需要时间来运行日志记录。

最新更新