c语言串口驱动中断的机制,STM32F103 实例应用(8)——串口中断接收不定长字符串...

/**===========================================================================

@file board_timer.c

@brief 本文件是基本定时器TIM6的驱动

@author 青梅煮久

@version r0.1

@date 2021/01/15

----------------------------------------------------------------------------

Remark: (备注描述)

给串口2的接收提供定时,再一次中断内(1ms)接收数据的长度不变则认为接收

完成。

----------------------------------------------------------------------------

History

----------------------------------------------------------------------------

| | |

-------------|-----------|----------------|---------------------------------

2021/01/15 | r0.1 | 青梅煮久 | 创建

-------------|-----------|----------------|---------------------------------

| | |

-------------|-----------|----------------|---------------------------------

| | |

-------------|-----------|----------------|---------------------------------

| | |

============================================================================*/

/*********************************************************************

* INCLUDES

*/

#include "main.h"

#include "board_timer.h"

#include "board_uart.h"

#define BASIC_TIM_IRQHandler TIM6_IRQHandler

/*********************************************************************

* PUBLIC FUNCTIONS

*/

/**

@brief NVIC初始化(使用TIM6基本定时器)

@param 无

@return 无

*/

void BASIC_TIM_NVIC_Config(void)

{

NVIC_InitTypeDef NVIC_InitStructure;

// 设置中断组为 2

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);

NVIC_InitStructure.NVIC_IRQChannel = TIM6_IRQn;

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;

NVIC_Init(&NVIC_InitStructure);

}

/**

@brief 定时器中断配置(使用TIM6基本定时器)

@param 无

@return 无

*/

void BASIC_TIM_Config(void)

{

TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;

/*

可以从上图看出基本定时器和通用定时器使用APB1总线,

高级定时器使用APB2总线。

*/

// 开启定时器时钟,即内部时钟 CK_INT=72M

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6, ENABLE);

/*

预分频将输入时钟频率按1~65536之间的值任意分频,分频值决定了计数频率。

计数值为计数的个数,当计数寄存器的值达到计数值时,产生溢出,发生中断。

如系统时钟为72MHz,预分频 TIM_Prescaler = 71,

计数值 TIM_Period = 1000,

则 TIM_Period * (TIM_Prescaler + 1) / 72000000 = 0.001,

即每1ms产生一次中断。

*/

// 自动重装载寄存器周的值(计数值)

TIM_TimeBaseStructure.TIM_Period = 1000;

// 累计 TIM_Period 个频率后产生一个更新或者中断

// 时钟预分频数为 71,

// 则驱动计数器的时钟 CK_CNT = CK_INT / (71+1)=1M

TIM_TimeBaseStructure.TIM_Prescaler = 71;

// 时钟分频因子 ,基本定时器没有,不用管

//TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;

// 计数器计数模式,基本定时器只能向上计数,没有计数模式的设置

//TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up;

// 重复计数器的值,基本定时器没有,不用管

//TIM_TimeBaseStructure.TIM_RepetitionCounter=0;

/*

完成时基设置

*/

// 初始化定时器

TIM_TimeBaseInit(TIM6, &TIM_TimeBaseStructure);

/*

为了避免在设置时进入中断,这里需要清除中断标志位。

如果是向上计数模式(基本定时器采用向上计数),

则采用函数 TIM_ClearFlag(TIM6, TIM_FLAG_Update),

清除向上溢出中断标志。

*/

// 清除计数器中断标志位

TIM_ClearFlag(TIM6, TIM_FLAG_Update);

// 使能计数器

TIM_ITConfig(TIM6,TIM_IT_Update,ENABLE);

// 开启计数器

TIM_Cmd(TIM6, ENABLE);

// 暂时关闭定时器的时钟,等待使用

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6, DISABLE);

}

/**

@brief 定时器中断(使用TIM6基本定时器)

@param 无

@return 无

*/

void BASIC_TIM_IRQHandler(void)

{

if(TIM_GetITStatus(TIM6, TIM_IT_Update) != RESET)

{

TIM_ClearITPendingBit(TIM6, TIM_FLAG_Update);

if(g_currentLength == g_receiveLength)

{

// 接收完成

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6, DISABLE);

printf("接收完成\n");

memcpy(g_manageBuffer, g_receiveBuffer, g_receiveLength);

g_rxFlag = 0;

g_receiveLength = 0;

memset(g_receiveBuffer, 0, sizeof(g_receiveBuffer));

g_rxFinish = 1;

}

else

{

g_currentLength = g_receiveLength;

}

}

}

//使用微库(平台式keil-MDK),点击“魔术棒” Target标签下有个Use MicroLIB—勾选

//重定向c库函数printf到USART2

/**

@brief 重定向c库函数printf到USART2

@param 无

@return 无

*/

int fputc(int ch, FILE *f)

{

USART_SendData(USART2,(u8)ch);

while(USART_GetFlagStatus(USART2,USART_FLAG_TXE)==RESET);

return (ch);

}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值