AVR单片机USART无法发送字符数组问题求助
嘿,我来帮你排查这个USART字符串发送的问题!既然单个字符发送正常,说明USART的基础配置和硬件连接大概率是没问题的,问题很可能出在你的send_string函数实现或者调用方式上。我给你梳理几个关键排查点和解决方案:
1. 检查send_string函数的实现逻辑
你只给出了函数声明,没有具体实现代码——这往往是问题核心。单个字符发送需要等待发送缓冲区为空(UDRE标志位),发送字符串时也必须为每个字符做同样的等待,否则会因为缓冲区未就绪导致字符丢失。
推荐你用这个可靠的实现,直接复用已经验证过的USART_Transmit函数:
void send_string(const char *str, uint8_t len) { // 循环发送每个字符 for (uint8_t i = 0; i < len; i++) { USART_Transmit(str[i]); // 调用单个字符发送函数,自动处理等待逻辑 } }
如果你的USART_Transmit实现本身是正确的(比如包含了while (!(UCSRA & (1 << UDRE)));等待步骤),这个字符串发送函数就能正常工作。
2. 确认你是否正确调用了send_string
从你给出的main函数代码来看,只调用了USART_Transmit('O');,但没有看到调用send_string(txt, 5);的语句。别忘了在main里添加这一行,才能触发字符串发送:
int main(void) { USART_Init(207); adc_init(); const char txt[5]="hello"; PORTB =0b1010000; USART_Transmit('O'); // 单个字符正常 send_string(txt, 5); // 新增这行调用字符串发送 // ... 其他代码 }
3. 注意字符串的长度与结束符问题
你定义的const char txt[5]="hello";刚好容纳"hello"的5个字符,但没有预留字符串结束符'\0'的位置。如果后续你想改成按结束符自动判断的发送函数(不需要传长度),建议这样定义数组:
const char txt[]="hello"; // 自动分配6个字节,包含末尾的'\0'
对应的字符串发送函数可以改成:
void send_string(const char *str) { // 循环直到遇到结束符 while (*str != '\0') { USART_Transmit(*str++); } }
调用时直接写send_string(txt);即可,更灵活。
4. 额外检查:USART配置的一致性
虽然单个字符发送正常,但还是要确认USART_Init里的配置是否匹配你的需求:比如数据位是8位(AVR默认可能是8位,但如果改成7位,发送某些字符会出错)、波特率计算是否正确(你用的207对应16MHz时钟下9600波特率,是对的)。
按照上面的步骤排查,应该就能解决字符串发送不完整的问题了!
内容的提问来源于stack exchange,提问作者user3978484

