You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为什么使用sscanf会修改原始char数组的内容?

异常原因分析

该问题的核心是栈缓冲区溢出触发的C语言未定义行为,具体原因如下:

  • C标准库的sscanf函数使用%s格式符读取字符串时,不会校验目标缓冲区的容量,会持续读取到空白字符(空格、换行、制表符等)为止,且会自动在读取的内容末尾追加字符串结束符\0。如果读取的内容总长度超过目标缓冲区的大小,就会发生越界写入,直接覆盖栈上相邻的其他内存空间。
  • 你的代码中,sscanf读取的第四段子串为newlinetest,共11个字符,加上自动追加的\0总长度为12字节,但你定义的parm4缓冲区长度只有10,不足以容纳读取的内容,发生越界写入。
  • 栈上的局部变量是按编译器分配的顺序连续存储的,初始代码中s数组正好处于parm4溢出写入的内存区域,parm4越界写入的内容将s数组的第二个字节覆盖为\0,因此打印s时只会输出第一个字符t。
  • 当你将parm1的长度调整为90后,栈上局部变量的内存布局发生变化,parm4溢出写入的内容不再覆盖s数组的有效区域,因此s的输出看起来恢复正常,但这只是随机的巧合,缓冲区溢出的本质问题并没有解决,仍然属于未定义行为,随时可能出现程序崩溃、输出异常等问题。
修复建议
  • 使用带长度限制的格式符控制读取长度:在%s中加入最大读取字符数,需要预留1字节给结束符\0,例如parm4长度为10,格式符应写为%9s,完整的sscanf写法为sscanf(s, "%9s %3s %255s %9s", parm1, parm2, parm3, parm4);
  • 优先使用带显式长度参数的输入函数,避免无限制读取导致的溢出问题。

内容的提问来源于stack exchange,提问作者squinky

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.03 00:57:02