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

C语言循环内调用strcat导致循环变量r异常、循环次数错乱问题

问题原因

该异常由栈缓冲区溢出导致:strcat函数执行时的越界写入操作,直接篡改了栈空间上存储的循环变量r,最终造成循环逻辑失控。

问题复现逻辑

  • 函数内定义的temp数组仅分配了15字节空间,初始化后仅预留14字节可用于存储字符串内容,剩余1字节必须存放字符串结束符\0。
  • strcat本身不做任何边界检查,会把源字符串从起始位置到\0的全部内容,直接追加到目标字符串末尾:
    • 第一次循环(r=0,i=0):追加abcdef及结束符,temp共占用7字节,未越界
    • 第二次循环(r=1,i=1):追加bcdef及结束符,temp共占用12字节,未越界
    • 第三次循环(r=2,i=2):追加cdef及结束符,temp共需要16字节存储空间,已经超出15字节的数组边界。多写入的内容会直接覆盖栈上temp相邻位置的内存,而局部变量r恰好分配在这片相邻栈空间上,值首先被结束符\0改写为0
    • 后续循环的越界写入会持续覆盖r的存储空间,最终把r改成无意义的垃圾值(即输出中看到的1717920769),循环判断条件r < 11完全失效。
  • 注释掉strcat调用后不存在越界写入操作,栈上的r不会被篡改,因此循环可以正常执行。

修复方法

  • 为temp数组分配足够容纳所有拼接内容的存储空间,必须预留1字节存放字符串结束符\0
  • 调用strcat前增加长度校验,避免写入内容超出数组边界

参考修复代码:

#include <stdio.h>
#include <string.h> 
void scan_eqn (char *eqn)
{
    // 扩大数组容量,预留足够拼接空间
    char temp[128] = "";
    int i, r;
    for (i = 0, r = 0; r < 11; r++, i++)
    {
        // 拼接前做长度校验,从根源避免溢出
        if (strlen(temp) + strlen(eqn + i) + 1 > sizeof(temp)) {
            break;
        }
        strcat (temp, eqn + i); 
        printf("r: %d ", r);
    }
    printf("\n\n\n");
} 

int main()
{
    char eq[50];
    printf("Enter the sentence: ");
    scanf("%[^\n]s", eq);
    scan_eqn(eq);
    return 0;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.27 14:51:21