Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2006.10.15;
Скачать: CL | DM;

Вниз

DLLCHILD...   Найти похожие ветки 

 
memo   (2006-09-28 11:28) [0]

Здравствуйте!
У меня такой вопрос (Даже скорей проблема):
"Я создал внутри DLL, форму , пример процедур видно ниже. Cама DLL компилируется отлично... Не каких проблем...-->


procedure InitPlugin(App, Scr: integer); StdCall;
begin
 DLLScr:= Screen;
 Screen:= TScreen(Scr);
 DLLApp:= Application;
 Application:= TApplication(App);
end;

procedure DonePlugin; StdCall;
begin
 Screen:= DLLScr;
 Application:= DLLApp;
end;

function CreateCardMDI: integer; StdCall;
begin
 Result:= integer(TCardForm.Create(Application))
end;

exports
 InitPlugin,
 DonePlugin,
 CreateCardMDI;


--> ...А вот с вызовом этой формы из DLL, у меня возникли проблемы..."
А в частности меня интересует динамическая загрузка...

Ниже код вызова формы из DLL (Не получается.... :o( ):


procedure TMainForm.Buttom1Click(Sender: TObject);
var
 CardHandle: THandle;
begin
 CardHandle:= LoadLibrary("dll\Card\dCardMDI.dll");
 GetProcAddress(CardHandle,"InitPlugin");
  InitPlugin(integer(Application), integer(Screen));
 GetProcAddress(CardHandle,"CreateCardMDI");
  CreateCardMDI;
 GetProcAddress(CardHandle,"DonePlugin");
  DonePlugin;
 FreeLibrary(CardHandle);
end;


ВОПРОС:
"Что я делаю не так..???"
И если можно, то конкретно подчеркнуть мои ошибки...
Заранее благодарен! Memo.


 
alles ©   (2006-09-28 11:40) [1]

procedure TMainForm.Buttom1Click(Sender: TObject);
var
CardHandle: THandle;
begin
CardHandle:= LoadLibrary("dll\Card\dCardMDI.dll");
if CardHandle=0 then exit;
GetProcAddress(CardHandle,"InitPlugin");
InitPlugin(integer(Application), integer(Screen));
GetProcAddress(CardHandle,"CreateCardMDI");
 CreateCardMDI; как обьявил эту проц.?
GetProcAddress(CardHandle,"DonePlugin");
 DonePlugin; как обьявил эту проц.?
FreeLibrary(CardHandle);
end;


 
clickmaker ©   (2006-09-28 11:42) [2]


> Ниже код вызова формы из DLL (Не получается.... :o( ):

что именно не получается?

PS. Преобразования к integer - лишние. Там и так 4-байтовые указатели


 
memo   (2006-09-28 11:51) [3]

Хорошо, вот к примеру...


type
  TDllfunc = function: TDllobjectClass;
   stdcall;

Функцию объявил....


......
@fDllfunc := GetProcAddress(fHandle, "Dllfunc");
......

Получил указатель.... Далее по коду вызвал...


if Assigned(@fDllfunc) then....


А вот как объявить процедуры...?
Скока вариантов и примеров не пробовал, не получается...

Ктобы мог расписать правельно код, в моём случае...???


 
alles ©   (2006-09-28 11:53) [4]

взято и Кулибы

Я сделал так - выбираю все DLL из каталога с программой, загружаю каждую и пытаюсь найти в ней функцию (через API GetProcAddress) с заранее определенным жестко именем (например что нибудь типа IsPluginForMyStuff). Если нашлась - DLL считается моим плагином, если нет - выгрузить и забыть.

А набор вызываемых функций по идее одинаков у всех плагинов, и программа (основная) в курсе какие именно функции она ищет в DLL. Если даже и не так, то ничего не мешает тебе определить в плагине функцию наподобие GetFeatures, возвращающую список строк-названий поддержанных плагином процедур.

Вот часть моего кода по работе с плагинами...

--------------------------------------------------------------------------------
   ...
type

// Процедурные типы для хранения ссылок на функции плагинов
TGetNProc=function:shortstring;
TGetSProc=function:integer;
TProcessProc=procedure(config:pointer; request:PRequest; var reply:PReply);
TConfigProc=procedure(defcfg:PSysConfig; var config:pointer);
TSaveLoadProc=procedure(inifile:pointer; var config:pointer);

// Информация об отдельном плагине
TPlugin=record
Name:shortstring;                   // Полное название
Filename:shortstring;               // Имя файла
Handle:integer;                     // Хэндл загруженной DLL
CFGSize:integer;                    // Размер конфигурации в RAM
ProcessProc: TProcessProc;      // Адрес процедуры обработки
ConfigProc: TConfigProc;       // Адрес процедуры настройки
LoadCFG,SaveCFG:TSaveLoadProc;      // Адреса процедур чтения/записи cfg
end;
PPlugin=^TPlugin;

// Список загруженных плагинов
TPlugins=class(TList);

...

var

Plugins:TPlugins;  sr:TSearchRec;  lib:integer;
pgetn:TGetNProc;  pgets: TGetSProc;  plugin:PPlugin;

...

// Читаем плагины и создаем их список.
Plugins:=TPlugins.Create;
if FindFirst("*.dll",faAnyFile,sr)<>0 then begin

ShowMessage("Hе найдено подключаемых модулей.");
Close;
end;
repeat

lib:=LoadLibrary(PChar(sr.Name));
if lib<>0 then begin
@pgetn:=GetProcAddress(lib, "GetPluginName");
if @pgetn=nil then FreeLibrary(lib)    // Hе плагин
else begin
New(plugin);
@pgets:=GetProcAddress(lib, "GetCFGSize");
plugin.Name:=pgetn;
plugin.Filename:=sr.Name;
plugin.CFGSize:=pgets;
plugin.Handle:=lib;
plugin.ConfigProc:=GetProcAddress(lib, "Configure");
plugin.ProcessProc:=GetProcAddress(lib, "Process");
plugin.SaveCFG:=GetProcAddress(lib, "SaveCFG");
plugin.LoadCFG:=GetProcAddress(lib, "LoadCFG");
Plugins.Add(plugin);
end;
end;
until FindNext(sr)<>0;
FindClose(sr);


 
clickmaker ©   (2006-09-28 11:53) [5]

type
 TInitPlugin = procedure(App, Scr: integer); StdCall;

var
 p: TInitPlugin;

 @p = GetProcAddress;
 p(Application, Screen);


 
memo   (2006-09-28 11:56) [6]


> clickmaker ©   (28.09.06 11:42) [2]

Ругается... Типа:
"Не хочу компилировать! У вас необявлена процедура   InitPlugin(integer(Application), integer(Screen));"

А я вот голову ломаю на... хренна ее объевлять, если я получаю на нее укозатель и вызываю вообще из ДЛЛ... :o(

Не пойму структуры вызова и обработки DLL-ных... процедур и функций...
:o/


 
memo   (2006-09-28 12:04) [7]

Да еще вопрос...
Могу ли я на "Форму DLL", поместить ADOConntction1 , таблиц , квериков...
и тем самым вызывать форму из длл , как какогота к примеру клиента MSSQL?
В обще магу ли я имея форму в ДЛЛ, работать с БД???


 
clickmaker ©   (2006-09-28 12:08) [8]


> [6] memo   (28.09.06 11:56)

я ж написал, как ее надо вызывать...


 
Amoeba ©   (2006-09-28 13:19) [9]


> memo   (28.09.06 12:04) [7]
> Да еще вопрос...
> Могу ли я на "Форму DLL", поместить ADOConntction1 , таблиц
> , квериков...
> и тем самым вызывать форму из длл , как какогота к примеру
> клиента MSSQL?
> В обще магу ли я имея форму в ДЛЛ, работать с БД???

Можешь. Только вот передавать в DLL объекты из основной программы или использовать в основной программе объекты создаваемые в DLL нельзя, т.к. если даже как бы и будет работать, но но все равно возникнут неразрешимые проблемы.


 
Ketmar ©   (2006-09-28 13:22) [10]

>[9] Amoeba(c) 28-Sep-2006, 13:19
>Только вот передавать в DLL объекты из
>основной программы или использовать в основной
>программе объекты создаваемые в DLL нельзя
???


 
clickmaker ©   (2006-09-28 13:33) [11]


> [9] Amoeba ©   (28.09.06 13:19)

давно уже такая технология отлажена и работает. С одним но. И экзе и dll должны быть собраны с одними run-time vcl пакетами


 
Ketmar ©   (2006-09-28 13:38) [12]

>[11] clickmaker(c) 28-Sep-2006, 13:33
>одним но. И экзе и dll должны быть собраны с
>одними run-time vcl пакетами
или с ShareMem. или с его аналогами. %-)



Страницы: 1 вся ветка

Текущий архив: 2006.10.15;
Скачать: CL | DM;

Наверх




Память: 0.5 MB
Время: 0.045 c
1-1157331654
dwar
2006-09-04 05:00
2006.10.15
Алгоритм парсинга XML


4-1149099745
Корешь
2006-05-31 22:22
2006.10.15
EnumPorts странно работает


3-1155506976
Hell's Angel
2006-08-14 02:09
2006.10.15
Заполнение БД(FireBird 1.5)


15-1158853641
hamster
2006-09-21 19:47
2006.10.15
Где винт???


15-1158552431
КаПиБаРа
2006-09-18 08:07
2006.10.15
Уровень жизни