本帖最后由 zchong 于 2016-2-29 09:13 编辑
设计意图:由systick定时器产生每秒25600个中断,然后定时器中断中每256次通过软件中断产生一个中断,每5120次产生另外一个中断;
测试结果:
1、IAR,JLINK仿真状态下,5120点的那个软件中断产生的次数明显不对,256点的是正常的;
2、脱离仿真器,直接运行,结果是正确的;
搞不清状况了,大伙可以测试一下,代码如下:
static void systick_init(void)
{
RCC_ClocksTypeDef rcc_clocks;
uint32_t cnts;
SysTick_CLKSourceConfig(SysTick_CLKSource_HCLK);
RCC_GetClocksFreq(&rcc_clocks);
cnts = (uint32_t)rcc_clocks.HCLK_Frequency / 25600;
if ((cnts - 1UL) > SysTick_LOAD_RELOAD_Msk) { while(1); } /* Reload value impossible */
SysTick->LOAD = (uint32_t)(cnts - 1UL); /* set reload register */
NVIC_SetPriority (SysTick_IRQn, 0); /* set Priority highest */
SysTick->VAL = 0; /* Load the SysTick Counter Value */
SysTick->CTRL = SysTick_CTRL_CLKSOURCE_Msk |
SysTick_CTRL_TICKINT_Msk |
SysTick_CTRL_ENABLE_Msk; /* Enable SysTick IRQ and SysTick Timer */
}
static void EXTILine0_Config(void)
{
EXTI_InitTypeDef EXTI_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
/* Enable SYSCFG clock */
RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);
/* Configure EXTI Line0 */
EXTI_InitStructure.EXTI_Line = EXTI_Line0;
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;
EXTI_Init(&EXTI_InitStructure);
/* Enable and set EXTI Line0 Interrupt to the lowest priority */
NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] Configures EXTI Line15 (connected to PG15 pin) in interrupt mode
* @param None
* @retval None
*/
static void EXTILine13_15_Config(void)
{
EXTI_InitTypeDef EXTI_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
/* Enable SYSCFG clock */
RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);
/* Configure EXTI Line13 */
EXTI_InitStructure.EXTI_Line = EXTI_Line13;
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;
EXTI_Init(&EXTI_InitStructure);
/* Enable and set EXTI15_10 Interrupt to the lowest priority */
NVIC_InitStructure.NVIC_IRQChannel = EXTI15_10_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
static void exti_init(void)
{
EXTILine0_Config();
EXTILine13_15_Config();
}
void period_init(void)
{
/* Configures the priority grouping: pre-emption priority and subpriority */
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
/* Sample periodic interrupt config */
systick_init();
/* Externel interrupt init */
exti_init();
}
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] Main program
* @param None
* @retval None
*/
int main(void)
{
/* Timer, cycle sampling init */
period_init();
/* Infinite loop */
while (1)
{
}
}
int32_t short_interrupt_trig_cnt = 0;
int32_t short_interrupt_cnt= 0;
int32_t long_interrupt_trig_cnt = 0;
int32_t long_interrupt_cnt= 0;
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] Period sampling handler,512 pionts every cycle.
* @param None
* @retval None
*/
void SysTick_Handler(void)
{
static uint16_t counter = 0;
counter++;
/* 256 points,half cycle */
if ((counter&0x00FF) == 0x00FF)
{
/* Generate software interrupt */
EXTI_GenerateSWInterrupt(EXTI_Line0);
short_interrupt_trig_cnt++;
}
/* 5120 points,ten cycles */
if (counter >= 5119)
{
counter = 0;
/* Generate software interrupt */
EXTI_GenerateSWInterrupt(EXTI_Line13);
long_interrupt_trig_cnt++;
}
}
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] This function handles External line 0 interrupt request.
* @param None
* @retval None
*/
void EXTI0_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_Line0) != RESET)
{
/* Clear the EXTI line 0 pending bit */
EXTI_ClearITPendingBit(EXTI_Line0);
short_interrupt_cnt++;
}
}
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] This function handles External lines 15 to 10 interrupt request.
* @param None
* @retval None
*/
void EXTI15_10_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_Line13) != RESET)
{
/* Clear the EXTI line 13 pending bit */
EXTI_ClearITPendingBit(EXTI_Line13);
//delay(0x1);
long_interrupt_cnt++;
}
}
附上IAR工程,很方便移植到其它的STM32处理器上,感兴趣的可以测试一下!! |