当前位置: 华文问答 > 数码

有没有什么有趣的软件BUG是因为硬件升级产生的?

2022-05-16数码

这是一个隐藏很深的bug因电脑升级而暴露出来的例子。

Protel99se是2000年前后推出的电子设计软件,包含画原理图、画PCB、CAM、电路仿真等功能。它用法简明,能满足大多数情况下PCB设计的需求,而且在低性能电脑上也能流畅运行。至今仍有大量老一辈工程师在使用,因此PCB工厂也必须兼容这种陈旧的文件格式。

protel99se启动画面

2008年左右大家渐渐开始发现,在保存工程时,有时会弹出这样的错误框

报错弹框

熟悉C语言的你肯定知道,这是printf这类函数的格式化字符串参数写错了。但搞电子设计的前辈工程师们并不懂得这么深入。

终于有一天,一位EE与IT双修的年轻大佬用OllyDbg探查,揭开了谜底。

原来,软件中有这样一个函数,每次调用生成一个随机文件名,用于临时文件。核心逻辑写成伪代码是这样的

def get_random_file_name (): 随机数 = GetTickCount () #1 文件名 = ' %s \ %s%x .tmp' % ( ** , ** , 随机数 ) while True : if 文件名不存在 : break 随机数 = GetTickCount () 文件名 = ' %s \s %x %.tmp' % ( ** , ** , 随机数 ) #2 return 文件名

如果硬盘很快,迅速保存好了前一个文件,就会导致下次调用的间隔太短,1处会返回同一个值,于是执行到2处。而2处的格式字符串写错了。所以,高性能电脑就会触发这个bug。

字符串位于文字池里,是明文存储的,所以只要搜索这串文字并改正就好了,可以直接给exe文件打补丁。这位大佬同时发布了这个二进制补丁。

参考资料

[原创]关于出现 Protel 99 SE 'Format '%x' invalid or incompatible with argument' 的分析

针对评论区补充一下。

伪代码只是展示程序逻辑,我用python当皮套只因它精练。

据大佬分析,源程序是delphi写的,并不是C艹。上述伪代码展现的业务逻辑是先用ida插件从汇编反推C再简化而来的,万恶之源的delphi源码是怎么写的已经不得而知了。