首页 新闻 会员 周边

stm32不进入蓝牙串口接收中断函数

0
悬赏园豆:50 [待解决问题]

主函数文件:

include "stm32f10x.h" // Device header

include "Delay.h"

include "OLED_2.h"

include "Serial.h"

include "LED.h"

include "Servo.h"

include "PWM.h"

include "string.h"

include "sys.h"

extern uint16_t Distance,Size;
extern uint16_t x_pos,y_pos;
u8 str_buff15[64];
u8 str_buff16[64];

int main(void)
{
OLED_Init();
LED_Init();
Serial_Init();
Servo_Init();
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); //中断优先级分组 分2组
int i,j;

while (1)
{

GPIO_ResetBits(GPIOA,GPIO_Pin_8);
for(i=0;i<1000;i++)
for(j=0;j<1000;j++);
GPIO_SetBits(GPIOA,GPIO_Pin_8);
for(i=0;i<1000;i++)
for(j=0;j<1000;j++);

		OLED_Clear();
		sprintf((char *)str_buff15,"MAIN:%d",i);
		OLED_ShowString(16,16,str_buff15,16,1);

		sprintf((char *)str_buff16,"flash:%d",flash);
		OLED_ShowString(16,32,str_buff16,16,1);

		OLED_Refresh();

}
}

串口文件:

include "stm32f10x.h" // Device header

include <stdio.h>

include <stdarg.h>

include "LED.h"

include "OLED_2.h"

include "Servo.h"

include <stdlib.h>

include <string.h>

char Serial_RxPacket1[10]; //"@msg\r\n" pitch_str
char Serial_RxPacket2[10]; //roll_str
uint8_t flash ;
u8 str_buff1[64];
u8 str_buff2[64];
//u8 str_buff3[64];
//u8 str_buff4[64];

uint8_t X1, X2, X3, X4, X5, X6, X7, X8, Y1, Y2, Y3, Y4, Y5, Y6, Y7, Y8, Y, X;
uint16_t x_pos,y_pos;
float erro1=0 , erro2=0 , Angle1=0 , Angle2=0;
float OUT_Angle1=0 , OUT_Angle2=0;
//uint8_t Serial_RxFlag;

void Serial_Init(void)
{
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);

GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;//tx
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;//rx
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);

USART_InitTypeDef USART_InitStructure;
USART_InitStructure.USART_BaudRate =9600;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_Init(USART1, &USART_InitStructure);

USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);

NVIC_InitTypeDef NVIC_InitStructure;
NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_Init(&NVIC_InitStructure);

USART_Cmd(USART1, ENABLE);
USART_ClearFlag(USART1, USART_FLAG_TC);
}

void Serial_SendByte(uint8_t Byte)//////////发送一个字节
{
USART_SendData(USART1, Byte);
while (USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET);
}

void Serial_SendArray(uint8_t *Array, uint16_t Length)//////////发送一个数组
{
uint16_t i;
for (i = 0; i < Length; i ++)
{
Serial_SendByte(Array[i]);
}
}

void Serial_SendString(char *String)//////////发送一个字符串(字符串用双引号括起来)\r\n 可以换行
{
uint8_t i;
for (i = 0; String[i] != '\0'; i ++)
{
Serial_SendByte(String[i]);
}
}

uint32_t Serial_Pow(uint32_t X, uint32_t Y)//////////次方函数,返回值=X的Y次方
{
uint32_t Result = 1;
while (Y --)
{
Result *= X;
}
return Result;
}

void Serial_SendNumber(uint32_t Number, uint8_t Length)
{
uint8_t i;
for (i = 0; i < Length; i ++)
{
Serial_SendByte(Number / Serial_Pow(10, Length - i - 1) % 10 + '0');
}
}

int fputc(int ch, FILE *f)
{
Serial_SendByte(ch);
return ch;
}

void Serial_Printf(char *format, ...)
{
char String[100];
va_list arg;
va_start(arg, format);
vsprintf(String, format, arg);
va_end(arg);
Serial_SendString(String);
}

void USART1_IRQHandler(void)
{
static uint8_t RxState = 0;//定义一个静态变量RxState并初始化为0,用于跟踪接收状态。
static uint8_t pRxPacket_pitch_str = 0; //跟踪接收包的位置。
static uint8_t pRxPacket_roll_str = 0;
flash = RxState;
if (USART_GetITStatus(USART1, USART_IT_RXNE) == SET)
{
uint8_t RxData = USART_ReceiveData(USART1); //从USART1接收寄存器中读取数据,并将其存储在变量RxData中。
// USART_ClearITPendingBit(USART1, USART_IT_RXNE);//清除USART1的接收缓冲区非空中断标志位。

if (RxState == 0)
{
		flash = RxState;

	if (RxData == '@')//检查接收到的数据是否为字符"@"。
	{					
		RxState = 1;
		pRxPacket_pitch_str = 0;
		pRxPacket_roll_str = 0;
		
	}
}
else if (RxState == 1)//接收pitch_str 
{
		flash = RxState;

	if (RxData == 109)   //m
	{
		RxState = 2;
	}
	else 
	{
		Serial_RxPacket1[pRxPacket_pitch_str] = RxData;
		pRxPacket_pitch_str ++;
	}
}
else if (RxState == 2)//接收roll_str
{
		flash = RxState;

	if (RxData == 65) //A
	{
		RxState = 3;
	}
	else 
	{
		Serial_RxPacket2[pRxPacket_roll_str] = RxData;
		pRxPacket_roll_str ++;
	}
}
else if (RxState == 3)   //接收完成
{			
		flash= RxState;

	if (RxData == 70)//F
	{
		Y1=Serial_RxPacket1[0];//0
		Y2=Serial_RxPacket1[1];//X
		Y3=Serial_RxPacket1[2];

		
		
		X1=Serial_RxPacket2[0];
		X2=Serial_RxPacket2[1];
		X3=Serial_RxPacket2[2];


		
		x_pos=(X1-48)*100+(X2-48)*10+(X3-48);
	//	printf("%d\r\n",Serial_RxPacket2[0]);
	//	printf("%d\r\n",Serial_RxPacket2[1]);
	//	printf("%d\r\n",Serial_RxPacket2[2]);
		y_pos=(Y1-48)*100+(Y2-48)*10+(Y3-48);
		
		OLED_Clear();
		sprintf((char *)str_buff1,"x_pos:%d",x_pos);//0300
		OLED_ShowString(16,16,str_buff1,16,1);
		sprintf((char *)str_buff2,"y_pos :%d",y_pos);//0300
		OLED_ShowString(16,32,str_buff2,16,1);

		OLED_Refresh();
		
		RxState = 4;
	}
}
else if (RxState == 4)
{
		flash = RxState;


		USART_ITConfig(USART1,USART_IT_RXNE,DISABLE);//关闭DTSABLE中断

// printf("%d\r\n",Serial_RxPacket[0]);
// printf("%d\r\n",Serial_RxPacket[1]);
printf("%d\r\n",x_pos);
printf("%d\r\n",y_pos);
//erro1 =160-x_pos ;
//erro2 = y_pos-120 ;
erro1 =160-110 ;
erro2 = 163-120 ;
Angle1 = S1_PID(erro1);
Angle2 = S2_PID(erro2);
OUT_Angle1=PWM1_Limt(Angle1);
OUT_Angle2=PWM2_Limt(Angle2);
Servo_SetAngle(OUT_Angle1,OUT_Angle2);

	  RxState=0;
		pRxPacket_pitch_str = 0;
		pRxPacket_roll_str = 0;
		USART_ITConfig(USART1,USART_IT_RXNE,ENABLE);									
}	
USART_ClearITPendingBit(USART1, USART_IT_RXNE);

}
}

PWM文件:

include "stm32f10x.h" // Device header

void PWM_Init(void)
{
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);

GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_0;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);

TIM_InternalClockConfig(TIM2);

TIM_TimeBaseInitTypeDef TIM_TimerBaseInitStructure;
TIM_TimerBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimerBaseInitStructure.TIM_CounterMode = TIM_CKD_DIV1;
TIM_TimerBaseInitStructure.TIM_Period = 57600 - 1;//ARR
TIM_TimerBaseInitStructure.TIM_Prescaler = 25 - 1;//PSC
TIM_TimerBaseInitStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM2, &TIM_TimerBaseInitStructure);

TIM_OCInitTypeDef TIM_OCInitStructure;
TIM_OCStructInit(&TIM_OCInitStructure);
TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High;
TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM_OCInitStructure.TIM_Pulse = 0;//CCR
TIM_OC1Init(TIM2, &TIM_OCInitStructure);
TIM_OC2Init(TIM2, &TIM_OCInitStructure);

TIM_Cmd(TIM2, ENABLE);
}

void PWM_SetCompare1( int Compare)
{
TIM_SetCompare1(TIM2, Compare);
}
void PWM_SetCompare2( int Compare)
{
TIM_SetCompare2(TIM2, Compare);
}

云台:

include "stm32f10x.h" // Device header

include "PWM.h"

include "string.h"

include <stdio.h>

include <stdarg.h>

float P1=0 , I1=0 , D1=0 ,
P2=0 , I2=0 , D2=0 ;
float now_error = 0 , last_error = 0 , now_error_LeiJi = 0 ,
last_last_error = 0 , Out_posPID = 0 , OUT_PWM1 = 0 , OUT_PWM2 = 0;
float servo1_duty , servo2_duty;

void Servo_Init(void)
{
PWM_Init();
}

void Servo_SetAngle(float Angle1,float Angle2)
{
// Angle1=Angle12;
// Angle2=Angle22;
PWM_SetCompare1(2.88(Angle1 / 180 * 2000) + 1440);//500
PWM_SetCompare2(2.88
(Angle2 / 180 * 2000) + 1440);//500
servo1_duty = ((Angle1+90)/18010+2.5);
servo2_duty = ((Angle2+90)/18010+2.5);
// printf("%.3f\r\n",servo1_duty);
// printf("%.3f\r\n",servo2_duty);
}

float S1_PID(float erro)
{
static float S1_PD_Kp = 0.55506 ,
S1_PD_Ki = 0.000038 ,
S1_PD_Kd = 0.22096 ;
now_error = erro ; //误差
now_error_LeiJi = now_error + now_error_LeiJi;//累计误差_求和

P1 = S1_PD_Kp * now_error;
I1 = S1_PD_Ki * now_error_LeiJi;
D1 = S1_PD_Kd * (now_error - last_error);
last_error = now_error;
Out_posPID = P1 + I1 + D1;
OUT_PWM1 = Out_posPID; //输出
OUT_PWM1 = OUT_PWM1 ;
return OUT_PWM1 ;
}

float S2_PID(float erro)
{
static float S2_PD_Kp = 0.73900 ,
S2_PD_Ki = 0.00009 ,
S2_PD_Kd = 0.16880 ;
now_error = erro ; //误差
now_error_LeiJi = now_error + now_error_LeiJi;//累计误差_求和

P2 = S2_PD_Kp * now_error;
I2 = S2_PD_Ki * now_error_LeiJi;
D2 = S2_PD_Kd * ( now_error - last_error);
Out_posPID = P2 + I2 + D2;
last_error = now_error;
OUT_PWM2 = Out_posPID;
OUT_PWM2 = OUT_PWM2 ;
return OUT_PWM2 ;
}

float PWM1_Limt(float Angle)
{
if (Angle > 90)
Angle = 90;
else if (Angle < -90)
Angle = -90;
Angle=Angle+90;
return Angle;
}

float PWM2_Limt(float Angle)
{
if (Angle > 90)
Angle = 90;
else if (Angle < -90)
Angle = -90;
Angle=Angle+90;
return Angle;
}

打不死的猕猴桃的主页 打不死的猕猴桃 | 初学一级 | 园豆:152
提问于:2023-12-29 08:24
< >
分享
所有回答(1)
0

STM32不进入蓝牙串口接收中断函数可能是由于多种原因导致的。以下是一些可能的原因和相应的解决方法:

  1. 中断未被使能:
    确保你已经使能了串口接收中断。在STM32的HAL库中,这通常通过调用HAL_UART_Receive_IT()函数完成。
  2. 中断优先级问题:
    检查中断优先级是否正确设置。确保中断优先级没有被其他中断或任务占用。
  3. 中断向量表:
    确保中断向量表设置正确。如果你的项目中使用了其他中断或与STM32相关的软件包(例如CMSIS、RTOS等),它们可能会影响中断向量表。
  4. 配置问题:
    检查相关的寄存器配置是否正确。例如,检查USARTx->CR1和USARTx->CR2寄存器的配置,确保它们是正确的。
  5. 外部干扰或硬件问题:
    如果你的硬件有外部干扰或存在硬件问题,这可能会导致中断不工作。尝试在不同的硬件上测试你的代码,或使用示波器检查相关的信号。
  6. 软件问题:
    确保你的代码没有错误,例如未初始化的变量、数组越界等。使用编译器提供的调试工具检查这些可能的错误。
  7. 上下文问题:
    确保在其他上下文中(例如在其他任务或中断中)没有其他代码修改了与串口接收相关的寄存器或内存。
  8. 其他库或中间件的影响:
    如果你使用了其他库或中间件,确保它们不会干扰串口接收中断的处理。
  9. 固件版本:
    确保你使用的STM32 HAL库和微控制器固件版本是最新的,或者至少是已知稳定的版本。
  10. 查看文档和论坛:
    查阅STM32的官方文档和相关社区论坛,看是否有其他开发者遇到并解决了类似的问题。
    如果你尝试了上述方法仍然无法解决问题,建议提供更详细的背景信息(例如你的代码、使用的STM32型号、库版本等),以便获得更具体的帮助。
    --
    WPS AI 回复
快乐的凡人721 | 园豆:3922 (老鸟四级) | 2023-12-29 09:09

我只使用了一个串口中断优先级还需要小心设置吗

支持(0) 反对(0) 打不死的猕猴桃 | 园豆:152 (初学一级) | 2023-12-29 09:11
清除回答草稿
   您需要登录以后才能回答,未注册用户请先注册