MSP430G2231中uint16_t转十六进制字符串异常求助
问题排查与解决方案
核心问题分析
缓冲区溢出
你定义的char status[4]空间不足:uint16_t类型数据转十六进制需要4个ASCII字符,加上字符串终止符'\0',总共需要5字节的存储空间。缓冲区过小会导致终止符写入数组外的内存区域,破坏其他数据,直接引发乱码。缺少前导零填充
原递归itohexa函数仅转换有效数字位,不会自动补前导零。例如0x0B4C会被转换为"b4c"而非预期的"0b4c",输出长度不一致会导致后续打印逻辑混乱。
修复方案
1. 修正缓冲区大小
将status的定义修改为:
char status[5]; // 4个十六进制字符 + 1个终止符,刚好满足需求
2. 替换为固定长度的十六进制转换函数
递归实现不仅在MSP430这类小内存MCU上存在栈消耗风险,还无法保证固定长度输出。改用非递归的固定4位转换函数,强制填充前导零:
char *itohexa(char *dest, uint16_t x) { const char hex_chars[] = "0123456789ABCDEF"; // 若需要小写则用"0123456789abcdef" // 从高位到低位依次提取4位十六进制数 dest[0] = hex_chars[(x >> 12) & 0x0F]; dest[1] = hex_chars[(x >> 8) & 0x0F]; dest[2] = hex_chars[(x >> 4) & 0x0F]; dest[3] = hex_chars[x & 0x0F]; dest[4] = '\0'; // 添加字符串终止符 return dest; }
3. 验证UART打印函数
确保TimerA_UART_print函数是通过检测'\0'来终止打印,而非固定长度读取,避免截断或读取多余内存数据。
测试验证
修改后,当输入0x0B4C时,转换结果为"0B4C",配合足够的缓冲区,UART将输出符合预期的ASCII十六进制字符串,不会再出现乱码问题。
内容的提问来源于stack exchange,提问作者Boyfinn
相关产品推荐
相关产品推荐

