如何由32位应用程序调用16位DLL

rose 2000-01-03 02:33:00
我遇到的问题是修改一个 VC1.5编写的应用程序,但其中部分代码只有DLL,没有原代码,目前难以找到VC1.5,而VC6似乎只支持32位编程,请诸位高手指点迷津。
...全文
253 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
cottle 2000-01-06
  • 打赏
  • 举报
回复
有两种方法可以。

1 如果你的16位DLL中的引出函数只有简单类型的参数,可以使用一种未公开的方法调用它。在kernel32中有四个未公开的函数可以用于调用16位DLL。它们是
HANDLE LoadLibrary16(LPSTR LibraryName); // kernel32 index 35;
void FreeLibrary16(HANDLE HInstance); // kernel32 index 36;
void(*()) GetProcAddress16(HANDLE Hinstance,LPSTR ProcName);
// kernel32 index 37;
QT_Thunk; //kernel32 name 'QT_Thunk';
后面附有一段DELPHI代码是用这个方法调用16位DLL的。
关于这一方法的详细讨论或参考WIN95系统编程奥秘一书。

2 如果你需要向16位DLL传递指针、浮点数等复杂类型参数,你只有按微软推荐的方法分别写一个32位和16位DLL,由你的16位DLL调用你原来的16位DLL,你的程序调用32位DLL,由新写的32位DLL和16位DLL交互完成相应的类型转换及其它工作。为帮助你写这两个DLL,微软在WIN95SDK中提供了一个THUNK编译器用于生成这两个DLL的部分代码。详细的资料可以在MSDN上找到。
在MSDN上以"THUNK"为关键搜索有更多这方面的资料。
////////////////// Samples Code ////////////////////
unit thunk;

interface

function GetThunkSum(num1 , num2: WORD): WORD;

implementation

uses SysUtils, Windows;

{ Undocumented Kernel32 calls. }
function LoadLibrary16(LibraryName: PChar): THandle; stdcall; external kernel32 index 35;
procedure FreeLibrary16(HInstance: THandle); stdcall; external kernel32 index 36;
function GetProcAddress16(Hinstance: THandle; ProcName: PChar): Pointer; stdcall; external kernel32 index 37;
procedure QT_Thunk; cdecl; external kernel32 name 'QT_Thunk';

{ Use global variables, so QT_Thunk does not trash them. }
var
hInst16: THandle; {the handle to keep the library in}
pFunc: Pointer; {pointer to the function}

{ QT_Thunk needs a stack frame. }
{$StackFrames On}

function GetThunkSum(num1, num2: WORD): WORD;
var
ThunkTrash: array[0..$20] of Word;
begin
{ Prevent the optimizer from getting rid of ThunkTrash. }
ThunkTrash[0] := hInst16;

hInst16 := LoadLibrary16('DLL16.DLL');
if hInst16 < 32 then
raise Exception.Create('Cannot load DLL16.DLL');
{ Get the function pointer for the 16-bit function in USER.EXE. }
pFunc := GetProcAddress16(hInst16, 'GetSum');
if pFunc = nil then
raise Exception.Create('Can not get address of GetPassword');

asm
push num1 { push argument 1 }
push num2 { push argument 2 }
mov edx, pFunc { load 16-bit procedure pointer }
call QT_Thunk { call thunk }
mov Result, ax { save the result }
end;
FreeLibrary16(hInst16); {Free the library}
end;

end.

tide 2000-01-03
  • 打赏
  • 举报
回复
所谓的thunk(形实转换)也就实在16位dll和32位dll间做一个缓冲。懂得这点可能对你看 thunk95这篇资料有帮助。
tide 2000-01-03
  • 打赏
  • 举报
回复
<<win95系统编程奥秘>>中有这方面的论述。
zdg 2000-01-03
  • 打赏
  • 举报
回复
就在这个网站的Delphi开发文档就有相应的资料, 连接是:
http://www.midatech.com/csdn/Delphi/Document/thunk95.htm
祝你好运......

16,467

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧