概述
一、同步通信
通信双方时钟一致。
typedef struct {
uint16_t USART_Clock; // 时钟使能控制
uint16_t USART_CPOL; // 时钟极性
uint16_t USART_CPHA; // 时钟相位
uint16_t USART_LastBit; // 最尾位时钟脉冲
} USART_ClockInitTypeDef;
二、异步通信
需要约定通信双方的的通信波特率。
void UART1Config( uint32_t bound)
{
USART_InitTypeDef USART_InitStructure;
//波特率设置
USART_InitStructure.USART_BaudRate = bound;
//字长为8位数据格式
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
//一个停止位
USART_InitStructure.USART_StopBits = USART_StopBits_1;
//无奇偶校验位
USART_InitStructure.USART_Parity = USART_Parity_No;
//无硬件数据流控制
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
//收发模式
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
//初始化串口1
USART_Init(DEGUG_USARTX, &USART_InitStructure);
}
三、初始化串口
void UART1Init(void)
{
// 使能串口时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);
// 中断服务分组
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);
// 中断嵌套
NVICInit(USART1_IRQn,0,0);
// PA9 USART1_TX
GPIOInit(USART1_TX_PORT,USART1_TX_PIN,GPIO_Mode_AF_PP);
// PA10 USART1_RX
GPIOInit(USART1_RX_PORT,USART1_RX_PIN,GPIO_Mode_IN_FLOATING);
// 波特率设置
UART1Config(115200);
USART_Cmd(USART1,ENABLE);
// 接收中断
USART_ITConfig(DEGUG_USARTX,USART_IT_RXNE,ENABLE);
// 发送中断
USART_ITConfig(DEGUG_USARTX,USART_IT_TXE,ENABLE);
}
四、中断配置
void NVICInit(uint8_t IRQChannel,uint8_t IRQC_PTP,uint8_t IRQC_SP)
{
//NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
NVIC_InitTypeDef NVIC_InitStructure;
// 中断通道
NVIC_InitStructure.NVIC_IRQChannel = IRQChannel;
// 抢占式优先级
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = IRQC_PTP;
// 响应式优先级/副优先级
NVIC_InitStructure.NVIC_IRQChannelSubPriority = IRQC_SP;
// 使能
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
/*
外部中断
EXTI 的每根输入线都可单独进行配置,以选择类型(中 断或事件)和相应的触发事件(上升沿触发、下降沿触发或边沿触发)
EXTI线路 说明
EXTI线0~15 对应外部IO口的输入中断
EXTI线 16 连接到PVD输出
EXTI线17 连接到RTC闹钟事件
EXTI线18 连接到USB OTG FS唤醒事件
EXTI线19 连接到以太网唤醒事件
每个 GPIO 端口均有 16 个管脚,每个 端口的 16 个 IO 对应那 16 根中断线 EXTI0-EXTI15。
*/
/*
Function:外部中断
*/
void EXTIInit(uint8_t GPIO_PORT, uint8_t GPIO_Pin,uint32_t EXTILine,EXTIMode_TypeDef Mode, EXTITrigger_TypeDef EXTI_Trigger)
{
EXTI_InitTypeDef EXTI_InitStructure;
// 时钟
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);
// 外部中断的端口 与引脚
GPIO_EXTILineConfig(GPIO_PORT, GPIO_Pin);
EXTI_InitStructure.EXTI_Line =EXTILine; // 中断/事件线
EXTI_InitStructure.EXTI_Mode = Mode; // EXTI 模式
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger; // EXTI 触发方式
EXTI_InitStructure.EXTI_LineCmd =ENABLE; // 中断线使能或失能
EXTI_Init(&EXTI_InitStructure);
}
五、GPIO配置
void GPIOInit(uint32_t RCC_APB2Periph,GPIO_TypeDef* GPIOx,uint16_t GPIOPin,uint16_t GPIOMode)
{
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph,ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIOPin;
GPIO_InitStructure.GPIO_Mode = (GPIOMode_TypeDef)GPIOMode;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOx,&GPIO_InitStructure);
}
APB2上的时钟可选:
RCC_APB2Periph_AFIO, RCC_APB2Periph_GPIOA, RCC_APB2Periph_GPIOB,
RCC_APB2Periph_GPIOC, RCC_APB2Periph_GPIOD, RCC_APB2Periph_GPIOE,
RCC_APB2Periph_GPIOF, RCC_APB2Periph_GPIOG, RCC_APB2Periph_ADC1,
RCC_APB2Periph_ADC2, RCC_APB2Periph_TIM1, RCC_APB2Periph_SPI1,
RCC_APB2Periph_TIM8, RCC_APB2Periph_USART1, RCC_APB2Periph_ADC3,
RCC_APB2Periph_TIM15, RCC_APB2Periph_TIM16, RCC_APB2Periph_TIM17,
RCC_APB2Periph_TIM9, RCC_APB2Periph_TIM10, RCC_APB2Periph_TIM11
六、中断服务函数
6.1、方式一
void DEBUG_USART_IRQHandler(void)
{
uint8_t ucTemp;
if (USART_GetITStatus(USART1,USART_IT_RXNE)!=RESET) {
ucTemp = USART_ReceiveData( USART1);
USART_SendData(USART1,ucTemp);
}
}
/***************** 发送一个字符 **********************/
void Usart_SendByte( USART_TypeDef * pUSARTx, uint8_t ch)
{
/* 发送一个字节数据到 USART */
USART_SendData(USART1,ch);
/* 等待发送数据寄存器为空 */
while (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET);
}
/***************** 发送字符串 **********************/
void Usart_SendString( USART_TypeDef * pUSARTx, char *str)
{
unsigned int k=0;
do {
Usart_SendByte( USART1, *(str + k) );
k++;
} while (*(str + k)!='