16 位 .com 可执行文件可以调用 win32 API 吗?
有没有 16 位 .com 在 Windows 上使用 Win32 API 显示窗口 GUI 的最小示例?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
有没有 16 位 .com 在 Windows 上使用 Win32 API 显示窗口 GUI 的最小示例?
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
接受
或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
发布评论
评论(3)
Win16-> Win32
这可以通过使用
CallProc32W
LoadLibraryEx32W()
来加载Win32 DLL来完成。GetProcAddress32W()
来获取DLL例程的地址。CallProc32W()
或CallProcEx32W
调用 DLL 例程。代码示例
概念
Dos -> Win32
http://www.ragestorm.net/tutorial?id=27
Win16 -> Win32
This can be done using
CallProc32W
LoadLibraryEx32W()
to load the Win32 DLL.GetProcAddress32W()
to get the address of the DLL routine.CallProc32W()
orCallProcEx32W
.Code Example
Concept
Dos -> Win32
http://www.ragestorm.net/tutorial?id=27
多路复用中断(中断 0x2f)可用于从 Windows 内的 DOS 会话访问各种 Windows 功能,但它只能访问选定数量的功能;据我所知,无法通过它使用任意 API 调用。
The Multiplex Interrupt (interrupt 0x2f) can be used to access various Windows functionalities from a DOS session within Windows, but it only gives access to a select number of capabilities; there's no way to use an arbitrary API call via it as far as I know.
那是行不通的。假设您的目标是制作一个可以在普通 DOS 或 Windows 中运行的程序,您有几个选择:
最简单的选择是使用 DOS 扩展器 HX,它允许您在 DOS 下使用 Win32 API 的大部分子集运行应用程序。基本上,您只需像往常一样创建一个 win32 应用程序,然后在可执行文件上运行
PEstub
工具以允许其在 DOS 下运行。PEstub
的工作原理是将 DOS 存根替换为调用 HX 来加载和运行 win32 程序的存根。这种方法有两个缺点:您必须分发几个附加文件;至少:
DPMILD32.EXE
- PE 二进制加载程序(由 EXE 上的 DOS 存根自动调用)DKRNL32.DLL
- 模拟 KERNEL32.DLLDUSER32.DLL
- 模拟 USER32.DLL如果您不能指望 DPMI 服务器已处于活动状态(或者不知道这意味着什么),您最好还包括:
HDPMI.EXE
- DPMI 服务器(如果尚未加载服务器,则由 DPMILD32 自动加载)win32 可执行文件中的 DOS 存根是通常会打印出一条消息,类似于“哈哈,笨蛋,你不能在你那小小的 DOS 中运行这个程序!试试 Windows 95!”当你在 DOS 中运行 Windows 程序时。但它不必这样做;它可以是您喜欢的任何 MZ 格式的 MS-DOS 可执行文件:我见过自解压 zip 存档,它们使用它来允许在 DOS 上解压,但在 win32 系统上呈现 GUI。
这给我们带来了另一种选择:您可以自己编写 win32 应用程序及其 DOS 存根,并指示链接器使用您的存根而不是默认的存根。例如,如果您使用 MSVC 构建 win32 应用程序,则可以使用 link.exe 的 /STUB 选项。我假设您可以自行弄清楚如何生成 MS-DOS .exe 并传递给链接器。这种方法也有两个很大的缺点:
您本质上必须编写两个不同的程序,尽管小心它们可以共享源文件。
您需要生成一个 MS-DOS 可执行文件,这意味着您需要使用可以创建它们的工具,或者至少在汇编代码中添加一些混乱的样板文件。
That won't work. Assuming your goal is to make a program that can run either in plain DOS or in Windows, you have a couple of options:
The easiest option would be to use the DOS extender HX, which allows you to run applications using a large subset of the Win32 API under DOS. Basically, you would just create a win32 app as usual, then run the
PEstub
tool on the executable to allow it to run under DOS.PEstub
works by replacing the DOS stub with one that invokes HX to load and run your win32 program. There are two drawbacks to this approach:It only works with a 386 or higher CPU, since you can't exactly run a win32 program without one.
You would have to distribute several additional files; at bare minimum:
DPMILD32.EXE
- PE binary Loader (automatically invoked by the DOS stub on your EXE)DKRNL32.DLL
- emulates KERNEL32.DLLDUSER32.DLL
- emulates USER32.DLLIf you can't count on a DPMI server being active already (or don't know what that means), you'd better also include:
HDPMI.EXE
- DPMI Server (automatically loaded by DPMILD32 if no server was loaded yet)The DOS stub in a win32 executable is the part that typically prints out a message along the lines of "Haha, sucker, you can't run this program in your puny DOS! Try Windows 95 instead!" when your run a windows program in DOS. It doesn't have to do that, though; it could be any MZ-format MS-DOS executable you like: I've seen self-extracting zip archives that used this to allow extraction on DOS, but present a GUI on win32 systems.
This leads us to the other option: you could write both the win32 application and its DOS stub yourself, and instruct the linker to use your stub instead of the default one. For example, if you use MSVC to build your win32 app, you would use link.exe's /STUB option. I'll assume you can figure out how to produce the MS-DOS .exe to pass to the linker on your own. This approach also has two big disadvantages:
You essentially have to write two different programs, though with care they could share source files.
You need to produce an MS-DOS executable, which means that you either need to use a tool that can create them, or at least add some messy boilerplate to your assembler code.