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

利用数组越界访问调用结构体中win函数指针的可行性咨询

数组越界漏洞利用:能否通过越界访问调用win函数?

问题背景

手头有一个存在漏洞的C文件,需要分析其利用方式。发现漏洞出在结构体访问环节,相关代码如下:

#define BOARD_SIZE 10

typedef int (*turn_function_t)(struct board *);
typedef void (*win_function_t)(struct board *);

struct board {
    uint8_t f1[BOARD_SIZE][BOARD_SIZE];
    uint8_t f2[BOARD_SIZE][BOARD_SIZE];
    win_function_t win;
    turn_function_t turn;
    int avail;
};

int do_shot(struct board *board, int strength, int x, int y) {
    if(!(x >= 0 && x <= BOARD_SIZE && y >= 0 && y <= BOARD_SIZE)) {
        return SHOT_ERR_EINVAL;
    }

    /* If there was already a sunken ship, return error */
    if(board->f1[x][y] && !board->f2[x][y])
        return SHOT_ERR_SUNKEN;

    /* Now perform shot */
    if(!board->f2[x][y])
        return SHOT_WATER;

    board->f2[x][y] -= strength;

    if(!board->f2[x][y])
        return SHOT_SUNKEN;
    return SHOT_HIT;
}

漏洞点在于do_shot函数对数组f2的索引检查错误:允许输入0到10(包含)的x、y值,但f2是[10][10]的数组,合法索引仅为0-9,这意味着x=10或y=10时会触发越界访问。而win函数指针恰好存储在f2数组的内存后方,想知道能否利用这个越界访问调用win函数(参数无关)。


分析与结论

无法直接通过do_shot的越界访问调用win函数,因为do_shot本身没有任何调用函数指针的逻辑。但可以利用这个越界写漏洞修改win函数指针的内容,待程序后续在正常业务流程中调用win时,触发执行目标代码(包括原win函数或自定义恶意逻辑)。具体利用步骤如下:

  1. 确定内存偏移与对齐
    f1和f2各占10*10=100字节,总大小为200字节。需注意编译器的内存对齐规则:部分编译器会在f2数组与win指针之间添加填充字节,以满足函数指针的对齐要求(32位系统通常4字节对齐,64位为8字节)。
    可通过offsetof(struct board, win)宏计算win指针相对于结构体起始地址的偏移量,再减去f2的偏移量(100字节),得到f2数组到win指针的字节偏移。例如:

    • 若无填充,偏移量为100字节,对应x=10,y从0开始即可访问win指针的各个字节;
    • 若存在4字节填充,需x=10,y从4开始才能定位到win指针。
  2. 逐字节修改win函数指针
    由于board->f2[x][y] -= strength是单字节写入操作,可通过多次调用do_shot,每次修改win指针的一个字节:

    • 针对32位系统,调用4次do_shot,分别修改win指针的4个字节,将其指向目标函数地址;
    • 针对64位系统,需调用8次完成完整地址覆盖。
  3. 触发win函数调用
    等待程序进入调用win指针的正常流程(例如游戏胜利后的回调逻辑),此时程序会执行我们修改后的指针指向的代码,从而达成调用目标函数的目的。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 16:50:42