将Win16 C代码转换为Win32
时间:2020-03-06 14:51:30 来源:igfitidea点击:
通常,将16位Windows程序转换为Win32需要做什么?我敢肯定我不是唯一继承代码库的人,并被震惊地发现潜伏在角落的16位代码。
有问题的代码是C。
解决方案
原始的win32 sdk有一个工具可以扫描源代码并标记需要更改的行,但是我不记得该工具的名称。
过去不得不这样做时,我使用了蛮力技术,即:
1更新makefile文件或者构建环境以使用32位编译器和链接器。 (可选)只需在IDE中创建一个新项目(我使用Visual Studio),然后手动添加文件。
2楼
3个修复错误
4重复2&3,直到完成
该过程的痛苦取决于我们要迁移的应用程序。我在一小时内转换了10,000个行程序,而在不到一周的时间内转换了75,000个行程序。我还放弃了一些小实用程序,并且从头开始重写了(大部分)。
我同意艾伦的观点,反复试验可能是最好的方法。
这里有一些很好的技巧。
同意编译器可能会捕获大多数错误。另外,如果使用的是" near"和" far"指针,则可以删除这些名称-指针只是Win32中的指针。
除了正确构建环境之外,我们还需要解决以下一些具体问题:
- 包含int的结构将需要从16位变短或者变宽到32位。如果更改结构的大小并将其加载/保存到磁盘,则需要写入数据文件升级代码。
- 每个窗口的数据通常使用GWL_USERDATA与窗口句柄一起存储。如果将某些数据扩展到32位,则偏移量将更改。
- POINT&SIZE结构在Win32中为64位。在Win16中,它们是32位,可以作为DWORD返回(调用方会将返回值分成两个16位值)。这在Win32中不再起作用(即Win32不会返回64位结果),并且功能已更改为接受用于存储返回值的指针。我们将需要编辑所有这些。诸如GetTextExtent之类的API会受到此影响。同样的问题也适用于某些Windows消息。
- 在Win32中不鼓励使用INI文件来支持注册表。尽管INI文件功能仍然起作用,但我们在使用Vista问题时需要格外小心。 16位程序通常将其INI文件存储在Windows系统目录中。
这只是我记得的几个问题。自从我进行任何Win32移植以来已有十多年了。一旦进入它,它就会很快。每个代码库在移植时都会有自己的"感觉",这是我们会习惯的。我们甚至可能会在此过程中发现一些错误。
- wParam和lParam的含义在许多地方已经改变。我强烈建议我们保持偏执,并尽可能多地转换以使用消息破解程序。它们将使我们免于头痛。如果我只能给我们一个建议,便是这样。
- 只要我们使用的是消息破解程序,请同时启用
STRICT
。它可以使用int
捕获Win16代码库,而应该使用HWND
,HANDLE
或者其他东西。转换这些将大大有助于此列表中的#9. - hPrevInstance是没有用的。确保未使用它。
- 确保我们使用的是Unicode友好的调用。这并不意味着我们需要将所有内容都转换为TCHAR,而是意味着我们最好将其OpenFile,_lopen和_lcreat替换为CreateFile,以示明显的名字。
- " LibMain"现在是" DllMain",并且整个库格式和导出约定都不同
- Win16没有VMM。应将GlobalGlobaloc,LocalAlloc,GlobalFree和LocalFree替换为更现代的等效项。完成后,清理对" LocalLock"," LocalUnlock"和朋友的调用;他们现在没用了。并不是我可以想象应用程序会这样做,但是请确保我们在那儿时不依赖于
WM_COMPACTING
。 - Win16也没有内存保护。确保我们没有使用
SendMessage
或者PostMessage
将指针发送到进程外窗口。我们需要切换到更现代的IPC机制,例如管道或者内存映射文件。 - Win16还缺少抢先式多任务处理。如果我们想从另一个窗口快速获得答案,那么调用
SendMessage
并等待消息被处理是非常酷的。现在这可能是个坏主意。考虑一下" PostMessage"是否不是更好的选择。 - 指针和整数大小会发生变化。记住要仔细检查正在读取或者向磁盘写入数据的任何地方,尤其是它们是Win16结构时。我们需要手动重做它们以处理较短的值。同样,解决此问题的最痛苦的方法是在可能的情况下使用消息破解程序。否则,我们将需要手动查找并将int转换为DWORD,并在适用的情况下依此类推。
- 最后,当我们发现明显的问题时,请考虑启用64位编译检查。从16位转换为32位所面临的许多问题与从32位转换为64位相同,并且Visual C ++实际上实际上已经很聪明了。我们不仅会遇到一些挥之不去的问题;我们也将为最终的Win64迁移做好准备。
编辑:正如@ChrisN所指出的那样,仍然可以使用将Win16应用程序移植到Win32的官方指南,并且两者都充实并补充了我的观点。
在MSDN上将16位代码移植到32位Windows上有明确的指南。