又一种内存越界的情况, 野指针导致sprintf函数内存越界

  最近做一个C++服务端程序,在使用多线程时,程序有时候会崩溃,从VC的错题提示看是内存访问错误导致程序崩溃,单步执行跟踪也无法定位错误所在。

  根据个人的经验分析,这种错误是内存越界导致其他对象或者堆(heap)被破坏而引起非法内存访问,结果出现不可debug跟踪的程序崩溃。

  这个问题困扰了我几周,我分析程序代码,搜索所有strcpy,memcpy,memset等内存操作相关的函数,确认所有使用这些函数的地方都没有内存越界的问题
  我又分析程序中一些字符数组char[]变量,发现也不存在数组空间不够大的问题。非常头疼,找不出原因,又替换了程序中一个觉得可疑的模块,问题还是存在。

  今天又再继续观察程序运行打印的LOG,发现似乎每次崩溃的时候,好像都是在处理某个客户端请求时发生。
  于是就单步debug该处理过程,这一次果然发现问题了,
  原来该处理过程有用到sprintf函数来把客户端上传的参数组合成一个sql语句,
  因为没有检测参数的合法性,导致参数非法的时候,可能造成内存越界的情况,
  但是不是每次内存越界的结果都会有一样的现象。

下面使用代码来说明这个问题。

int functiontest(char *pszParam, int nLen, int nID)
{
char szSQL[500];
sprintf(szSQL,
" Select * from tabble1 " 
" where cond1 = %s and id = %d ",
pszParam,    //当pszParam为未初始化的野指针,可能导致内存越界
nID
);
//以下代码省略
//......
}

没错,就是上述使用sprintf()函数时产生了内存越界的错误,但是该函数本身的执行并不一定马上报错或者引起程序崩溃,
因为pszParam为野指针, strlen(pszParam)则是未确定的长度,
所以在有些情况下,strlen(pszParam)的长度可能远大于szSQL数组的大小512,sprintf()就会有内存越界的操作,
结果就会导致未定义的异常,我的程序里就导致了后续其他函数内存访问错误,直接程序崩溃。

其实在该函数中我忽略了nLen参数的意义,该参数是指pszParam的长度,
但是nLen == 0 的情况我确没有判断并加以处理,所以导致内存越界程序崩溃。

你可能感兴趣的:(又一种内存越界的情况, 野指针导致sprintf函数内存越界)