![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Ошибка выгрузки DLL [D6, Win2k]
Dynamit © (2002-09-16 14:45:00)Уважаемые мастера, у меня странный трабл! Собственно сабж.
Делаю простейшие вещи с DLL. Все получается, но при выгрузке происходит ошибка обращения к памяти (т.е. обьект воздействия не существует!?!).
Если есть какие мысли - подскажите сирому, не пожалейте времени ;(
Исходник вот:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, ExtCtrls, StdCtrls;
type
TLoadJorn = Function (AHandle, FHandle: THandle):Longint; StdCall;
TUnLoadJorn = Procedure (ARef: LongInt); StdCall;
EDLLLoadError=class(Exception);
TForm1 = class(TForm)
Button1: TButton;
Button2: TButton;
Panel1: TPanel;
procedure Button1Click(Sender: TObject);
procedure Button2Click(Sender: TObject);
private
{ Private declarations }
LibHandle: THandle;
CurHndl: LongInt;
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure TForm1.Button1Click(Sender: TObject);
Var
LoadJorn: TLoadJorn;
begin
LibHandle:=LoadLibrary("JornDLL.Dll");
If LibHandle=0 Then
Raise EDLLLoadError.Create("Не могу загрузить DLL");
@LoadJorn:=GetProcAddress(LibHandle,"LoadJorn");
If Not (@LoadJorn=nil) Then
CurHndl:=LoadJorn(Handle, Panel1.Handle);
end;
procedure TForm1.Button2Click(Sender: TObject);
Var
UnLoadJorn: TUnLoadJorn;
begin
If LibHandle<>0 Then
Begin
@UnloadJorn:=GetProcAddress(LibHandle,"UnLoadJorn");
If Not (@UnloadJorn=nil) Then
Begin
UnloadJorn(CurHndl);
End;
If Not FreeLibrary(LibHandle)Then
Begin
ShowMessage("Error "+IntToStr(GetLastError));
End;
End;
end;
end.
REA (2002-09-18 10:39:00) [1]Да у меня все отлично работает и так и так. С ShareMem конечно есть нюансы, зато можно классы передавать, хотя может это и кривой подход, зато быстрее делать. А какой прямой подход в Delphi - интерфейсы передавать?
Dynamit (2002-09-18 09:42:00) [2]Да инет у меня до 17.00 - работа такая!
А вот вам новая фишка - прога не глючит с любой другой DLL!
УРААА!!!
Убрал ShareMem - все заработало (лишний раз мне доказательство того, что не надо полностью доверять умным книжкам и советам help-ов)!
Если у вас есть еще какие пожелания или советы - пишите, буду рад почитать.
Всем огромное спасибо - не дали помереть глупому ослику ;)
AlexT1000 (2002-09-17 18:08:00) [3]прально товарисчь говорит.
sharemem - убрать.
где там автор темы?
че молчит?
Ketmar (2002-09-17 17:31:00) [4]ShareMem нужно, если вы выполняете GetMem в главной программе и FreeMem в DLL-ках. (или наоборот %-). также нужно если вы передаете в/из DLL AnsiStrings. если такового не происходит - можно смело чистить uses от лишнего модуля. %-)
Satanas Nobiscum! 17-Sep-XXXVII A.S.
Andre V. (2002-09-17 17:02:00) [5]ShareMem как речут мудрые люди позволяет использовать динамические массивы.
Только должен признаться без ??? у меня работает лучше
AlexT1000 (2002-09-17 16:34:00) [6]у ЁЁЁЁЁЁЁЁЁЁЁЁ!
так типа за совпадением типов следить надо . это штука такая.
а sharemem тебе точно нужен? а если убать то чо?
так вроде все правильно.
и еще мож просто перегрузиться ,а не дельфи переставлять.
ну не мож такого быть.
Dynamit (2002-09-17 16:28:00) [7]
> AlexT1000
"Наличие символа (@) перед переменной процедурного типа данных не позволяет компилятору выдать ошибку несовпадения типов."- цитата из очень умной книжки.
Dynamit (2002-09-17 16:23:00) [8]Я даже в одну процедуру запихал загрузку и выгрузку!
Нет, наверно глюк не в исходниках (как не люблю я ругать среду разработки, но в данном случае придется).
> Ketmar
Может мне Делфю переставить ???
AlexT1000 (2002-09-17 16:18:00) [9]
@LoadJorn:=GetProcAddress(LibHandle,"LoadJorn");
нафига здесь @?!
оно тут не нужно!
LoadJorn:=GetProcAddress(LibHandle,"LoadJorn");
во как!
REA (2002-09-17 16:04:00) [10]В таком проекте их и не должно быть, а вот если несколько thread запустить или MDIChild окон из DLL навешать в MDIParent приложения, тогда мелочи и всплывут, хотя и они побеждаются.
Ketmar (2002-09-17 15:46:00) [11]будете смеяться, но как я не игрался, ни одной ошибки у меня не выскочило. по-всякому развлекался - ну нету ошибок, и все тут. к чему бы это?
Satanas Nobiscum! 17-Sep-XXXVII A.S.
REA (2002-09-17 15:31:00) [12]Ketmar
Лучше бы умные Delphi научились объединять RTTI DLL и приложения, а то в форму приложения даже Control не вставить, который в DLL создан.
Dynamit (2002-09-17 15:07:00) [13]Нет, глюки в чем-то другом, так как я не собираюсь компоновать каждую DLL-ку выжимкой VCL, да и само приложение построено "с пакетами", а в дистрибутиве навалены BPL.
Может есть еще идеи?
Ketmar (2002-09-17 14:06:00) [14]>Только я еще RTL packages включаю - без них вместе с Sharemem глючит.
и будет. потому что при построении "с пакетами" умные дельфи создают ОДИН экземпляр Application, а "без пакетов" глупые дельфи радостно плодят по экземпляру на каждую DLL, где есть "uses Forms". видимо, от этой путаницы у вас и глюки.
Satanas Nobiscum! 17-Sep-XXXVII A.S.
Dynamit (2002-09-17 13:55:00) [15]Попробовал восстановление Handle - не помогло :(
Насчет ShowMessage - без него тоже глючит!
Во глюк-то! Без LoadJorn и UnLoadJorn - все равно глючит, а ведь всего навсего загрузка-выгрузка DLL!!!!
Я ж прям с учебника списывал :)
?????
REA (2002-09-17 12:36:00) [16]У меня такое работает с переопределением Handle без восстановления. Только я еще RTL packages включаю - без них вместе с Sharemem глючит.
Andre V. (2002-09-17 12:24:00) [17]А тебя переопределение указателя на приложение не смущает.
Оно же потом не восстанавливается...
А использует программа его достаточно широко.
Ученик (2002-09-17 12:18:00) [18]>Dynamit (17.09.02 10:26)
Если не вызывать LoadJorn, ошибка есть ?
REA (2002-09-17 12:04:00) [19]ShareMem в основном проекте точно первым юнитом идет? Вроде ничего криминального нет тут. На всякий случай убери ShowMessage и используй OutputDebugString и проверь что в проекте тоже StdCall объявлено.
Dynamit (2002-09-17 10:26:00) [20]Вот блин!!
Упростил DLL донельзя - и все равно тотже глюк!!!!!
Все волосы на голове выдрал :(
Может кто глянет, а?
Исходник DLL:
library JornDLL;
uses
ShareMem,
SysUtils,
Classes,
Dialogs,
Forms;
{$R *.res}
Function LoadJorn(AHandle, FHandle: THandle):Longint; StdCall;
begin
Application.Handle:=AHandle;
ShowMessage("Start");
Result:=0;
End;
Procedure UnLoadJorn(ARef: LongInt); StdCall;
begin
ShowMessage("Stop");
End;
Exports
LoadJorn,
UnLoadJorn;
begin
end.