调试实战 | 代码丢了?用搜索找出真相

缘起

前几天,修复 bug 后,本地测试通过,提交代码到 tfs,关闭 bug。但是客户拿到程序后,效果依然不对。来来回回检查了好几遍,逻辑是正确的,本地验证通过了,代码也确实上传到 tfs 了,但是程序到客户手里,效果确实不对。如果是你,该如何调(shuai)查(guo)呢?

说明:本文只是分享一种排查问题的思路。

背景介绍

用一句话描述遇到的问题就是:在修改 bug 时,加了一句关键的 result.push_back(L"地下室外墙"),但是客户那里却没有看到新加的字符串。

排查思路

在我看来,这个问题有两种可能:

  1. 客户拿到的程序并没有包含最新的修复。
  2. 修复的逻辑有问题,只不过在本机测试的时候没有暴露出来。

因为整个修复逻辑很简单,不太可能出错,难不成还真有可能是第一种情况?该如何排查呢?

代码里的字符串一定会以某种格式保存在最终生成的程序文件里。如果客户拿到的程序里没有这个字符串,说明客户拿到的程序并没有包含最新的修复。

该怎么搜?

因为关键代码在 dll 文件中,不能直接使用 windbg 打开。否则就可以直接在 windbg 中使用 s -u 0x0 L?0xffffffffffffffff "地下室外墙" 搜索。没关系,还有十六进制编辑神器—— Hex Editor Neo。按 ctrl + f 调出搜索框,选择 UNICODE String 并输入要搜索的内容, 即可搜索。

search-unicode-string

说明:

  1. 上图之所以能搜到,是因为我新建了一个测试程序,里面包含了相关的字符串。在客户机器上有问题的 dll 中并没有搜索到的。
  2. Hex Editor Neo 非常好用,但不是免费软件(有免费版本)。欢迎推荐更好用的十六进制编辑工具。

More

因为我知道要搜索的字符串是 UNICODE 编码的,所以可以按 UNICODE String 进行搜索。如果在不知道编码的情况下该怎么搜索呢?

可以产生一个既包含目标字符串又包含标记字符串的测试字符串,通过搜索标记字符串来找到目标字符串在程序中的字节码。可以编写如下测试代码:

1
2
3
4
5
int _tmain(int argc, _TCHAR* argv[])
{
std::cout << L"test地下室外墙test1test2test3!" << std::endl;
return 0;
}

在生成的程序中,分别尝试以各种编码类型搜索关键字 test1test2test3 ,这样就可以找到目标字符串在最终程序中的字节码了。

search-specific-string

有了这个字节码,就可以大概猜出来是什么编码了,或者既然已经拿到对应的字节码,可以直接根据字节码搜索。

总结

善用搜索工具,也许会有意想不到的效果。

BianChengNan wechat
扫描左侧二维码关注公众号,扫描右侧二维码加我个人微信:)
0%