记录一下自己的心得,毕竟是2009年的最后一天了。
在这个特殊的一天里,我竟然修一个BUG修了一天。。。杯具啊
BUG属于内存被非法改写的类型,最后我利用逐步添加代码模块逐步排除的方法找出了罪魁祸首。嘿嘿
大概那段代码如下:
{ //unicode转ascii
UINT32 Len_str = 0;
UINT32 Len_str_bk = 0;
UINT32 Length = 0;
UINT32 pos = 0;
U16 *pText = (U16 *)EsrResult.pItemText;
Len_str = iToystrlen((U16 *)EsrResult.pItemText);
Len_str = Len_str<<1; //2倍
Len_str_bk = Len_str;
memset(&Esr_pTextAscii_Buffer[0], 0, sizeof(Esr_pTextAscii_Buffer));
while(Len_str != 0)
{
Length = __uni2ascii(*pText++, &Esr_pTextAscii_Buffer[pos]);
pos += Length;
Len_str -= Length;
}
Esr_pTextAscii_Buffer[Len_str_bk] = '/0';
ASSERT(pos == Len_str_bk);
}
代码思路解释一下:
从识别引擎返回的结果EsrResult.pItemText是unicode-16的,我现在需要把它转化为ascii字符之后输出到TXT文件中,
我事先定义了一个内存Esr_pTextAscii_Buffer[100]来存放转换过后的ascii字符(这个空间是够大的)。
问题出来了,请注意红色部分,仔细一琢磨,这是有风险的。判断条件为 Len_str != 0,再看后面的Len_str -= Length.这里就是出问题的地方
正常情况下,Len_str -= Length 减到最后应该正好等于0,但是在某种情况下,可能Len_str = 1, 而Length = 2, 得到的结果为 -1,而
Len_str是 unsigned int 型的,所以它的值编成了最大的 0xFFFFFFFF,这就正好导致循环条件不会被中止,一直循环下去,而在循环体里
正好又是对某段特定的内存读写操作,可想而知,肯定产生了对其他位置内存上数据的改写,而改写的如果正好是重要数据的话,系统崩溃。
好了,如果解决了,初步想到的是,判断条件改成 while( Len_str != 0 && Len_str < Len_str_bk)