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

将编辑框缓冲区转为以%结尾的字符串数组时触发访问违例

问题排查:C语言字符串分割时的访问违例错误

问题场景

需要将编辑框文本转换为一组以%结尾的字符串,实现代码及运行错误如下:

原实现代码

void Converter(HWND hwnd)
{
    int Length = GetWindowTextLength(hEdit) + 1;
    LPSTR data = (LPSTR)malloc(Length);
    char set[500][11];

    GetWindowTextA(hEdit, data, Length);

    int x = 0, y = 0;
    char record[10];
    
    for (int i = 0; i < Length, x<500; i++)
    {
        if(data[i]!= '\0' )
            {
            record[y] = data[i];
            y++;
            }
        else if(data[i] == '%')
        {
            strcpy(set[x], record);
            x++;
            y = 0;
        }
    }
    free(data);
}

运行错误信息

在myproject.exe中的0x00007FF684C91F9B位置触发异常:0xC0000005: 在位置0x000000CBFC8D5DAF读取时发生访问违例。


问题原因

  • 数组越界无限制:record是长度为10的数组,循环中未限制y的最大值,当连续读取超过9个字符时,会写入record的越界位置,破坏栈内存引发错误。
  • 循环条件逻辑错误:for循环用逗号表达式i < Length, x<500,实际仅判断x<500,忽略i < Length,导致i超出data长度后访问非法内存。
  • 判断顺序颠倒:先判断data[i] != '\0',再判断data[i] == '%',但%不属于'\0',导致处理分隔符的分支永远无法触发,record持续写入直到越界。
  • 字符串无终止符:strcpy要求源字符串以'\0'结尾,但record未手动添加终止符,strcpy会读取内存中随机位置的'\0',引发非法访问。

解决办法

修正后的代码如下:

void Converter(HWND hwnd)
{
    int Length = GetWindowTextLength(hEdit) + 1;
    LPSTR data = (LPSTR)malloc(Length);
    if (data == NULL) { // 新增内存分配失败判断
        return;
    }
    char set[500][11]; // 每个元素预留1位存终止符

    GetWindowTextA(hEdit, data, Length);

    int x = 0, y = 0;
    char record[11]; // 扩容为11位,预留终止符位置
    
    // 修正循环条件,同时限制i和x的范围
    for (int i = 0; i < Length && x < 500; i++)
    {
        if (data[i] == '%') { // 优先判断分隔符
            if (y > 0) { // 避免空字符串存入
                record[y] = '\0'; // 手动添加字符串终止符
                strcpy(set[x], record);
                x++;
                y = 0;
            }
        } else if (data[i] != '\0' && y < 10) { // 限制y的最大值,防止越界
            record[y] = data[i];
            y++;
        }
    }
    free(data);
}

关键修正点

  1. 扩容record为11位,同时限制y < 10,避免数组越界。
  2. 调换判断顺序,先处理%分隔符,再处理普通字符。
  3. 用&&替代逗号表达式,同时限制i和x的范围,避免访问非法内存。
  4. 复制前给record添加'\0'终止符,保证strcpy操作安全。
  5. 新增内存分配失败的判断,避免空指针操作。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.09 18:10:48