想使用STM32F1结合RFID对电机进行操控,具体功能是RFID不断寻卡,寻到卡后电机输入脉冲停止,过几秒后电机继续运行。
使用Delay函数对脉冲频率进行控制,电机所需要的脉冲频率在微秒级别。
我一开始在while(1)循环中同时驱动电机和RFID读写,但是发现由于电机脉冲频率过高,RFID的读写又需要一定时间,导致实际脉冲输出频率误差较大。
while (1)
{
HAL_GPIO_WritePin(Motor_Pulse_GPIO_Port, Motor_Pulse_Pin, GPIO_PIN_SET);
Delay_us(1000);
HAL_GPIO_WritePin(Motor_Pulse_GPIO_Port, Motor_Pulse_Pin, GPIO_PIN_RESET);
Delay_us(1000);
if(!readCard(readUid,NULL)){
printf("卡号:%x-%x-%x-%x\n",readUid[0],readUid[1],readUid[2],readUid[3]);
if(!strncmp((char *)readUid,(char *)UID,4)){
//比对卡号正确要做什么
printf("卡号正确\r\n");
HAL_GPIO_WritePin(Motor_Pulse_GPIO_Port, Motor_Pulse_Pin, GPIO_PIN_RESET);
HAL_Delay(3000);
}
else{
//比对卡号错误要做什么
printf("卡号错误\r\n");
}
}
}
个人认为,电机和RFID的读取都是需要不断循环的事件,但是前者对于时间精确度要求高,所以两者不能放在同一个循环内,想到用中断函数,但是RFID的不断读取又感觉不能使用中断函数完成,刚入门,求指导~
你的想法很正确,确实应该将电机和RFID读写分别处理,避免因为一个事件的阻塞影响到另一个事件的执行。使用中断函数是一个好的选择,但是你提到的问题也是存在的,由于RFID需要不断地寻卡和读写,无法保证在固定的时间间隔内触发中断。
因此,我建议你可以将读取RFID的部分放在独立的线程当中,并设置适当的时间间隔。在主线程中,则可以控制电机运行并进行脉冲输出。具体来说,你可以采用操作系统提供的多线程机制,通过创建一个新的线程来处理RFID读写的任务。下面是一个示例代码:
void RFID_Thread(void const *argument){
uint8_t readUid[5];
while(1){
if(!readCard(readUid,NULL)){
printf("卡号:%x-%x-%x-%x\n",readUid[0],readUid[1],readUid[2],readUid[3]);
if(!strncmp((char *)readUid,(char *)UID,4)){
//比对卡号正确要做什么
printf("卡号正确\r\n");
}
else{
//比对卡号错误要做什么
printf("卡号错误\r\n");
}
}
osDelay(100); // 设置读卡间隔为100毫秒
}
}
int main(void)
{
// 硬件初始化代码
// 创建RFID读写线程
osThreadDef(RFID_Thread, RFID_Thread, osPriorityNormal, 0, 128);
osThreadCreate(osThread(RFID_Thread), NULL);
while(1){
HAL_GPIO_WritePin(Motor_Pulse_GPIO_Port, Motor_Pulse_Pin, GPIO_PIN_SET);
Delay_us(1000);
HAL_GPIO_WritePin(Motor_Pulse_GPIO_Port, Motor_Pulse_Pin, GPIO_PIN_RESET);
Delay_us(1000);
}
}
在主线程中,你可以通过不断地输出脉冲来控制电机运行。在RFID读写线程中,则可以定时读取RFID卡,并进行处理。由于线程的优先级和调度机制,两个线程是可以实现并行执行的,不会相互阻塞。值得注意的是,在多线程环境下需要考虑资源的共享和同步,避免出现数据竞争等问题。