DLL动态调用后的完全释放(大家严重关注一下)(100分)

  • 主题发起人 主题发起人 mentoro
  • 开始时间 开始时间
M

mentoro

Unregistered / Unconfirmed
GUEST, unregistred user!
我上网查了好多资料,结果没有找到答案的,我的问题如下:

我的主程序调用一个DLL(简称第一个DLL),这个第一个DLL中静态调用了其他的DLL(简称第二个DLL),在关闭第一个DLL时无法完全释放,从内存中可以看到还有残余的东东,代码如下,请教大家帮我。

第一个DLL(下含一个FORM,该FORM中调用了第二个DLL)
library P_wqfx;



uses
ShareMem,
ActiveX,
SysUtils,
Classes,
Forms,
windows,
RemoteUdpConnection,
RemoteStoredProc,
remoteudpdataset,
U_WQSZ in 'U_WQSZ.pas' {F_TZWQ};

{$R *.res}

PROCEDURE WQ_FX(H: THandle; app: TForm; AConn: TRemoteUdpConnection; lpid, yhjs: STRING); Stdcall;
VAR
frm: TF_TZWQ;
ptr: PLongInt;
i: integer;
BEGIN
Application.Handle := h;
ptr := @(application.MainForm);
ptr^ := longint(app);
frm := TF_TZWQ.Create(app);
FOR i := 0 TO frm.ComponentCount - 1 DO
BEGIN
IF frm.Components IS tremoteudpdataset THEN
(frm.Components AS tremoteudpdataset).remoteudpconnection := AConn;
END;
///////初始化窗体
frm.lpids := lpid;
frm.YHJS := yhjs;
frm.ShowModal;
FreeAndNil(frm);
END;

EXPORTS
WQ_FX;

VAR
DLLApp: TApplication;
DLLScreen: TScreen;


PROCEDURE DLLUnloadProc(Reason: Integer);
BEGIN
if Reason = DLL_PROCESS_DETACH then
begin
Application := DLLApp; //恢复
Screen := DLLScreen;
end;
END;

BEGIN
DLLApp := Application; //保存 DLL 中初始的 Application 对象
DLLProc := @DLLUnloadProc; //保证 DLL 卸载时恢复原来的 Application

DLLApp := Application; //保存 DLL 中初始的 Application 对象
DLLScreen := Screen;
DLLProc := @DLLUnloadProc; //保证 DLL 卸载时恢复原来的 Application
DLLUnloadProc(DLL_PROCESS_DETACH);

END.

主程序如下:
procedure Tfrm_hoho.Button32Click(Sender: TObject);
TYPE TWQ_FX= PROCEDURE(H: THandle; app: TForm; AConn: TRemoteUdpConnection; lpid, yhjs: STRING); Stdcall;
VAR
DLLHandle: THandle; //使用DLL句柄
FPointer: pointer; //定义函数入口指针
WQ_FX: TWQ_FX; //定义函数类型变量
BEGIN
DLLHandle := LoadLibrary('P_wqfx.dll'); //DLL文件的绝对路径
IF DLLHandle = 0 THEN //判断句柄是否有值
BEGIN
Application.MessageBox('加载错误:P_wqfx.dll', '提示', MB_OK +
MB_ICONSTOP);
Exit;
END;
IF DLLHandle > 0 THEN
TRY
FPointer := GetProcAddress(DLLHandle, 'WQ_FX'); //根据函数名称获得函数指针
IF FPointer <> NIL THEN //判断FPointer是否为空,不为空则得到函数地址
BEGIN
WQ_FX := TWQ_FX(FPointer); //指针强制转化为函数指针
WQ_FX(frm_hoho.Handle, frm_hoho, RemoteUdpConnection1, '8','1'); //调用导出的函数
END
ELSE
application.MessageBox(' WQ_FX调用出错', '错误', MB_OK + MB_IconError);
FINALLY
FreeLibrary(DLLHandle);
END;

end;


第一个DLL中采用的是静态调用DLL
//权限控制
PROCEDURE SORH(TF: tform; rds_temp, RDS_TEMP1: tremoteudpdataset; yhjsid: string); Stdcall;External 'P_procedure.dll';
//装载数据指令过程
PROCEDURE a_loaddata(remotedataset1, rds_temp: tremoteudpdataset; remoteupdatesql1: tremoteupdatesql; s_data, s_where: STRING); Stdcall;External 'P_procedure.dll';
 
第一个带form的dll在form realease前释放他调用的dll就不会有问题了
 
你DLL里调用另一个DLL建议还是用动态调用的好吧

试下我这个改版的Loadrary函数库看看

http://u.skygz.com/mypane.aspx?down=ok&filepath=skygz%2f%b2%fa%c6%b7%2f%c4%da%b4%e6%d7%b0%d4%d8DLL%b2%a2%b5%f7%d3%c3_%ba%af%ca%fd%bf%e2_FOR_Delphi_v1_0_0_1.rar
 
有没有其他方式,现在还是解决不了

风铃夜思雨
你的我看了,但是不了解使用方法,有没有介绍说明文字
 

Similar threads

I
回复
0
查看
842
import
I
D
回复
0
查看
1K
DelphiTeacher的专栏
D
I
回复
0
查看
661
import
I
I
回复
0
查看
903
import
I
后退
顶部