请教大佬Ai8G1K08的51技术问题
您好大佬,我的两个单片机都是Ai8G1K08的51单片机,我想要实现的功能是:单片机1号先接收电脑通过串口给的8字节数据,然后对这8字节数据进行差分曼彻斯特编码,将编码后的数据通过单片机1号的P1.1传输给单片机2号,然后单片机2号通过P1.0接收到数据后将数据进行差分曼彻斯特解码,单片机2号再将解码后的数据通过串口发送出来。
目前的问题是:
单片机1号发送的编码数据是正常的,单片机2号也可以解码正确并发送,但是单片机2号在解码后只能将解码后的数据发送出来一遍,不知道为什么会卡住,请求大佬帮忙看看,结尾附上了我写的代码。
上图为电脑通过串口给单片机1号发送了三次55 AA 00 00 00 00 00 00八个字节的数据。
上图为单片机2号解码后,将解码后的数据通过串口发送出去,发送出去的内容是正确的,但只发送了一次八字节数据,按道理是三次。
我希望实现的是电脑给单片机1号发送一次八字节数据,单片机2号就解码一次并发送出来。
非常迫切的等待大佬的回复,非常感谢!!
您好,感谢您的提问。您提到的STC8G1K08是一款基于51内核的增强型单片机,具备较高的性价比和灵活性,适用于多种嵌入式应用。针对您描述的问题——“单片机2号在解码后只能将解码后的数据发送出来一遍”,我们从代码逻辑、串口通信机制以及差分曼彻斯特编码/解码流程三个方面进行分析。
首先,您描述的系统结构如下:
单片机1号:接收电脑通过串口发送的8字节数据 → 差分曼彻斯特编码 → 通过P1.1发送;
单片机2号:通过P1.0接收数据 → 差分曼彻斯特解码 → 通过串口发送解码后的数据。
问题集中在:单片机2号只发送一次数据,而应发送三次(对应三次输入)。
一、可能的原因分析
1. 串口发送函数未被重复调用
在您的代码中,如果串口发送函数仅在某个条件判断下执行一次,那么即使有新的数据到来,也不会再次触发发送。建议检查串口发送函数是否被正确地调用多次。
2. 数据接收逻辑未被重新触发
如果单片机2号在接收到一次数据后没有重新进入接收状态,可能导致后续数据无法被处理。请检查接收缓冲区或标志位是否被正确重置。
3. 差分曼彻斯特解码逻辑存在阻塞或等待
如果解码过程中使用了延时或等待语句,可能会导致程序卡住,从而无法处理后续数据。请检查解码函数是否有长时间等待或阻塞操作。
4. 串口接收中断未被正确配置或响应
如果使用的是串口接收中断方式,请确认中断服务程序是否正确处理了每次接收,并且在处理完一次数据后能够重新进入接收状态。
5. 数据帧识别逻辑不完善
如果您使用的是固定长度数据帧(如8字节),请确保在接收完成后能够正确识别并处理该帧,同时准备好接收下一帧。
二、建议优化方向
1. 确保串口发送函数可重复调用
请确认串口发送函数(如 UARTSendByte 或 UARTSendString)是否为独立函数,而不是被封装在某个条件判断中。例如:
c
void SendData(u8 data, u8 len) {
for (u8 i = 0; i < len; i++) {
UARTSendByte(data);
}
}
若该函数被调用一次后不再被重复调用,则会导致只发送一次数据。
2. 接收数据后重置接收标志位
在接收完成一个数据包后,应将接收标志位清零,以便接收下一个数据包。例如:
c
if (rxflag == 1) {
// 处理接收数据
rxflag = 0;
}
3. 避免在解码过程中使用阻塞式延时
差分曼彻斯特解码通常需要精确的时序控制,但不应使用 delayms() 这类阻塞式延时函数。建议使用定时器或状态机实现时序控制。
4. 检查串口接收中断配置
若您使用的是串口接收中断,请确保中断服务函数中对数据进行了正确处理,并在处理完成后重新使能中断。
5. 数据帧识别逻辑优化
建议在接收数据前设置起始标志,接收完成后设置结束标志,避免误判或遗漏数据。
三、示例代码片段(简化版)
以下为简化版的数据接收与发送流程,供参考:
c
// 定义接收缓冲区
u8 rxbuffer;
u8 rxindex = 0;
bit rxflag = 0;
// 串口接收中断服务函数
void UARTISR(void) interrupt 4 {
if (RI) {
RI = 0;
rxbuffer = SBUF;
if (rxindex >= 8) {
rxflag = 1;
rxindex = 0;
}
}
}
// 主循环
void main() {
UARTInit();
while (1) {
if (rxflag) {
// 差分曼彻斯特解码
u8 decodeddata;
DecodeManchester(rxbuffer, decodeddata);
// 发送解码后数据
SendData(decodeddata, 8);
rxflag = 0; // 重置接收标志
}
}
}
四、总结
您目前遇到的问题可能是由于串口发送函数未被重复调用、接收标志位未被重置、或者解码过程中存在阻塞操作所导致。建议从上述几个方面入手排查,并确保每个环节都能正确响应多次数据传输。
如需进一步协助,欢迎提供完整的代码片段,我们将为您进行更详细的分析。
祝您项目顺利!
[本文内容由国芯人工智能辅助生成,仅供参考]
请教大佬STC8G1K08的51技术问题
您好大佬,我的两个单片机都是STC8G1K08的51单片机,我想要实现的功能是:单片机1号先接收电脑通过串口给的8字节数据,然后对这8字节数据进行差分曼彻斯特编码,将编码后的数据通过单片机1号的P1.1传输给单片机2号,然后单片机2号通过P1.0接收到数据后将数据进行差分曼彻斯特解码,单片机2号再将解码后的数据通过串口发送出来。
目前的问题是:
单片机1号发送的编码数据是正常的,单片机2号也可以解码正确并发送,但是单片机2号在解码后只能将解码后的数据发送出来一遍,不知道为什么会卡住,请求大佬帮忙看看,结尾附上了我写的代码。
https://www.stcaimcu.com/data/attachment/forum/202507/30/171531hj0xh6jyw99e9mly.jpg
上图为电脑通过串口给单片机1号发送了三次55 AA 00 00 00 00 00 00八个字节的数据。
https://www.stcaimcu.com/data/attachment/forum/202507/30/171930t36ck0ydcywv4jjl.jpg
上图为单片机2号解码后,将解码后的数据通过串口发送出去,发送出去的内容是正确的,但只发送了一次八字节数据,按道理是三次。
我希望实现的是电脑给单片机1号发送一次八字节数据,单片机2号就解码一次并发送出来。
非常迫切的等待大佬的回复,非常感谢!!
您好,感谢您的提问。针对您描述的STC8G1K08单片机系统中出现的“单片机2号仅发送一次数据”的问题,以下是对该问题的分析与建议。
首先,从您的描述来看,系统结构为:电脑→单片机1(STC8G1K08)→单片机2(STC8G1K08)→串口输出。其中,单片机1负责接收电脑发送的8字节数据,并对其进行差分曼彻斯特编码后通过P1.1发送;单片机2接收编码数据并解码后,通过串口发送解码后的数据。
根据您提供的图片及代码附件内容,可以初步判断问题可能出现在以下几个方面:
一、数据传输逻辑未实现循环或重复机制
您提到“电脑给单片机1号发送一次八字节数据,单片机2号就解码一次并发送出来”,但实际运行中却只发送了一次。这表明在单片机1和单片机2之间可能存在数据触发机制不完善的问题。
可能原因:
单片机1在接收到一次数据后,未重新等待下一次数据输入。
单片机2在接收到一次编码数据后,未能正确进入下一个接收循环。
建议:
在单片机1中,应设计一个主循环,持续监听串口输入,每次接收到8字节数据后进行编码,并发送至单片机2。
在单片机2中,应设计一个接收状态机,确保每次接收到完整编码数据后,立即进行解码并发送。
二、单片机2的串口发送逻辑未实现多次发送
您提到“单片机2号解码后只能将解码后的数据发送出来一遍”,说明串口发送逻辑可能只执行一次,而未在每次接收到新数据时重复执行。
可能原因:
发送函数被设计为一次性调用,没有嵌入到循环或状态控制中。
编码数据的接收未触发发送操作。
建议:
将串口发送函数封装为独立函数,并在接收到解码数据后调用该函数。
确保每次接收到完整的解码数据后,触发一次串口发送。
三、编码/解码过程存在同步或时序问题
差分曼彻斯特编码是一种对时序要求较高的编码方式,若单片机1和单片机2之间的时钟同步不一致,可能导致解码失败或部分数据丢失。
可能原因:
单片机1的编码速率与单片机2的解码速率不匹配。
单片机2的解码逻辑未正确处理编码数据的起始与结束标志。
建议:
确保编码和解码过程中的时序一致,可采用定时器控制发送/接收频率。
在解码过程中加入起始位检测和数据长度判断,避免误判或漏读。
四、代码结构问题
您提供的代码可能缺乏模块化设计,导致逻辑混乱或功能重复执行。
可能原因:
主函数中未使用状态机或事件驱动机制。
数据接收与发送逻辑混杂,难以调试。
建议:
将编码、解码、发送等功能模块化,提高代码可读性与维护性。
使用全局变量或标志位来标记当前状态,如“数据已接收”、“数据已解码”等。
五、硬件连接问题
虽然您未提及硬件连接情况,但仍需确认以下几点:
单片机1的P1.1与单片机2的P1.0是否正确连接。
单片机2的串口引脚是否正确配置并连接至电脑。
六、测试与调试建议
1. 使用示波器观察信号:检查单片机1发送的编码信号是否正常,是否存在抖动或失真。
2. 添加调试信息输出:在关键节点(如数据接收完成、解码完成、发送完成)添加LED指示或串口打印,帮助定位问题。
3. 逐步调试:将代码拆分为多个小模块,逐一验证其功能是否正常。
综上所述,您的问题主要集中在数据传输逻辑、串口发送机制以及编码解码同步等方面。建议从以上几个方面入手,逐步排查并优化代码结构与逻辑流程。
如果您愿意提供具体的代码片段,我可以进一步帮您分析并提出修改建议。希望以上内容对您有所帮助,祝您项目顺利!
[本文内容由国芯人工智能辅助生成,仅供参考] 全局变量不能在初始化时赋值,赋值要移到函数内
新手必读:
https://www.stcaimcu.com/thread-16535-1-1.html
temp_byte[(sc-1)/16]|= (0x80>>( (sc/2)%8 ));
有越界风险,比如消息回传时定时器还在运作。
使用另外一个串口或者当前串口定时回传关键变量,增加调试信息。
定时器中断里不要自己开自己,交给main处理。
ercircle 发表于 2025-7-30 21:30
temp_byte[(sc-1)/16]|= (0x80>>( (sc/2)%8 ));
有越界风险,比如消息回传时定时器还在运作。
您好大佬,前一阵您提供的方案非常有效,现在单片机2号的串口能将数据传输出去了。
还想再问您一个新的问题,就是现在想实现一个新的功能,在接收到8个字节数据后,单片机2号进入掉电模式,在接收到INT2的中断后唤醒单片机2号的掉电模式,唤醒后将解码后的8字节数据通过串口1传输出去。
现在唤醒后的串口不停的一直传输0,按道理说是应该传输解码后的8个字节数据,问题如下图所示:
下面附上了我的单片机2号的代码,算法方面是没错的,能够解码正确,其余的不知道是哪里写错了,您能帮忙看看是哪里出现问题了嘛?
如果您能帮助真的万分感谢!!!
DebugLab 发表于 2025-7-30 20:35
全局变量不能在初始化时赋值,赋值要移到函数内
您好大佬,前一阵您提供的方案非常有效,现在单片机2号的串口能将数据传输出去了。
还想再问您一个新的问题,就是现在想实现一个新的功能,在接收到8个字节数据后,单片机2号进入掉电模式,在接收到INT2的中断后唤醒单片机2号的掉电模式,唤醒后将解码后的8字节数据通过串口1传输出去。
现在单片机2号唤醒后的串口不停的一直传输0,按道理说是应该传输解码后的8个字节数据,问题如下图所示:
下面附上了我的单片机2号的代码,算法方面是没错的,能够解码正确,其余的不知道是哪里写错了,您能帮忙看看是哪里出现问题了嘛?
如果您能帮助真的万分感谢!!!
平一帆 发表于 2025-8-20 21:53
您好大佬,前一阵您提供的方案非常有效,现在单片机2号的串口能将数据传输出去了。
还想再问您一个新的问 ...
猜测是哪里读取后清理了,可以给不同的清零位置赋值改为0123456,再看打出来是几。
或者为这一条业务线单独分配buffer,发送后清零,反正才八个字节。
工程不完整缺失文件,注意代码文件关联了相对路径不是当前工程下文件:
页:
[1]