- 打卡等级:偶尔看看I
- 打卡总天数:14
- 最近打卡:2025-12-16 13:03:08
已绑定手机
注册会员
- 积分
- 67
|
发表于 2025-11-17 13:06:04
|
显示全部楼层
麻烦帮我看下代码
/**
***********************************************************
* @brief 文件烧录
* @param
* @return
* @note 命令格式:FT+WR+FILE=<"文件名称">,<文件大小>,<数据包大小>,<"数据请求命令">,<\r\n><crc>
* 示例: FT+WR+FILE="0:pictrue.bmp",5054,133,"FT_REQ",\r\ncrc
***********************************************************
*/
void Fatfs_FileBurnTask(void)
{
static UartWriteFatfsState state = FAT_WAIT_CMD;
static uint8_t reqCnt = 0; // 数据请求次数
static bool reqFlag = true; // true-立即请求,false-每隔N秒请求
uint16_t crc_code = 0;
switch(state)
{
case FAT_WAIT_CMD:
g_pktRcvdLen = UartRecvData_Get(g_recvBuf);
if(g_pktRcvdLen == 0)
{
return; // 未接收到命令
}
if(g_pktRcvdLen < DATA_PACK_LEN_MIN)
{
ClearRecvBuf();
return; // 数据包长度不足
}
if(strstr((const char*)g_recvBuf,"FT+WR+FILE") != NULL)
{
fileInfo.crc = g_recvBuf[g_pktRcvdLen-CRC_INDEX_OFFSET + 1] << 8 | g_recvBuf[g_pktRcvdLen-CRC_INDEX_OFFSET];
crc_code = usMBCRC16(g_recvBuf, g_pktRcvdLen - 2);
if(crc_code != fileInfo.crc)
{
ClearRecvBuf();
printf("FT_CRC_ERROR\r\n");
return; // crc校验错误
}
// 获取文件信息
memset(fileInfo.fileName, 0, FILE_NAME_MAX);
memset(fileInfo.dataReqCmd, 0, DATA_REQ_MAX);
int ret = sscanf((char*)g_recvBuf, "FT+WR+FILE=\"%[^\"]\",%u,%u,\"%[^\"]\"",
fileInfo.fileName, &fileInfo.fileSize, &fileInfo.packLen, fileInfo.dataReqCmd);
if(ret != 4)
{
ClearRecvBuf();
printf("FT_CMD_ERROR\r\n");
return; // 指令错误
}
ClearRecvBuf();
// 打印参数信息
printf("fileName : %s\r\n",fileInfo.fileName);
printf("fileSize : %u\r\n", fileInfo.fileSize);
printf("packLen : %u\r\n", fileInfo.packLen);
printf("dataReqCmd : %s\r\n", fileInfo.dataReqCmd);
printf("crc : 0x%X\r\n", fileInfo.crc);
if(Fatfs_InitState_Get() == false)
{
state = FAT_WAIT_CMD;
printf("fatfs init fail\r\n");
return; // 文件系统参数失败
}
if(f_open(&file, (const char*)fileInfo.fileName, FA_CREATE_ALWAYS | FA_WRITE) != FR_OK) // 创建一个文件,如果文件存在就覆盖掉,允许写操作
{
printf("file open fail\r\n");
return; // 打开文件失败
}
fileInfo.writeLen = 0; // 计数清零
sysTime = GetSysRunTime(); // 保存系统运行时间
state = FAT_RECV_DATA;
}
break;
case FAT_RECV_DATA:
g_pktRcvdLen = UartRecvData_Get(g_recvBuf);
if(g_pktRcvdLen == 0)
{
//没有接收到数据,每隔5秒发送一次输请求指令
if((GetSysRunTime() - sysTime > 5000U) || (reqFlag == true))
{
reqFlag = false;
UartSendData(fileInfo.dataReqCmd); // 发送数据请求
sysTime = GetSysRunTime(); // 保存系统运行时间
reqCnt++;
if(reqCnt == 12)
{
reqCnt = 0;
f_close(&file); // 关闭文件
f_unlink((const char*)fileInfo.fileName); // 删除文件
state = FAT_WAIT_CMD;
printf("recv timeout\r\n"); // 接收超时
}
}
}
else
{
reqCnt = 0; // 请求计数清零
if(g_pktRcvdLen < DATA_PACK_LEN_MIN)
{
return; // 数据包长度不符,继续等待。
}
fileInfo.crc = g_recvBuf[g_pktRcvdLen-CRC_INDEX_OFFSET + 1] << 8 | g_recvBuf[g_pktRcvdLen-CRC_INDEX_OFFSET];
crc_code = usMBCRC16(g_recvBuf, g_pktRcvdLen - 2);
if(crc_code != fileInfo.crc)
{
ClearRecvBuf();
f_close(&file); // 关闭文件
f_unlink((const char*)fileInfo.fileName); // 删除文件
state = FAT_WAIT_CMD;
printf("FT_DATA_CRC_ERROR\r\n");
return; // 数据crc校验错误
}
// 到这里已经接到到一帧正确的数据
uint32_t writeNum = 0;
if (f_write(&file, g_recvBuf, g_pktRcvdLen - 2, &writeNum) != FR_OK)
{
ClearRecvBuf();
f_close(&file); // 关闭文件
f_unlink((const char*)fileInfo.fileName); // 删除文件
state = FAT_WAIT_CMD;
printf("FT_DATA_WRITE_FAIL\r\n");
return; // 数据写入失败
}
if(writeNum != g_pktRcvdLen - 2)
{
printf("write error\r\n");
}
reqFlag = true;
printf("writeLen = %u\r\n", fileInfo.writeLen);
ClearRecvBuf(); // 数据存储区清零
fileInfo.writeLen += writeNum; // 成功写入的数据计数
if(fileInfo.writeLen == fileInfo.fileSize)
{
uint32_t fileSize = f_size(&file);
printf("fileSize = %u\r\n", fileSize);
f_close(&file); // 关闭文件
state = FAT_WRITE_END;
}
}
break;
case FAT_WRITE_END:
printf("file write end\r\n");
printf("data = %u\r\n", fileInfo.writeLen);
state = FAT_WAIT_CMD;
break;
default:
state = FAT_WAIT_CMD;
break;
}
}
|
|