背景
游戏遇到一个crash问题,希望我能帮忙看看。
分析过程
本身游戏是接入了我之前提供的crash lib 所以一旦异常立刻会保存dump并记录异常上下文。拿到dump,加载pdb文件,通过1
2
3
4
5
6
7
8
9!analyze -v
FAILURE_BUCKET_ID: STACK_BUFFER_OVERRUN_STACK_BUFFER_OVERRUN_MISSING_GSFRAME_c0000409_roomsvrzgxr.exe!CRoomData::SendRandomPlaying
并通过 .ecxr 找到异常触发函数
roomsvrzgxr!CRoomData::SendRandomPlaying+0x129 [d:\roomsvrzgxr\roomdata.cpp@[281]
roomsvrzgxr!CRoomData::LaunchGame+0x9b [d:\roomsvrzgxr\roomdata.cpp @ [439]
roomsvrzgxr!CRoomData::LaunchGame+0x2f [d:\roomsvrzgxr\roomdata.cpp @ 452]
可以确定原因是由于 栈溢出导致的。 因为程序默认开始了/GS (Buffer Security Check)功能,所以在检测到栈溢出时会直接抛出异常,这个异常的捕获需要特殊处理才能捕获,可以参考我之前的文章。
以我的经验这类问题一般都是字符串格式化参数错误导致,所以搜索了下代码没有相关性。
或者是局部变量内存复制越界,所以看了下指定函数代码
1 | WAIT_TIME_FOR_ARRANGE_TABLE stuCostTimeOfArrangingTable; |
其中1
2
3
4
5
6
7
8
9
10typedef struct _tagWaitTimeForArrangeTable
{
int nGameID;
int nRoomType;
struct {
int nUserID;
//int nLTScore;
int nWaitTime;
} stuItem[TOTAL_CHAIRS];//TOTAL_CHAIRS=2
}WAIT_TIME_FOR_ARRANGE_TABLE, *LPWAIT_TIME_FOR_ARRANGE_TABLE;
stuCostTimeOfArrangingTable.stuItem[] 的最大索引是2. 那么是否可能存在pNewTable->th.nPlayerCount过大而导致溢出呢?
带着这个疑问去查找pNewTable的内容,nPlayerCount=3 ,那么刚好存在越界的可能。