Здравствуйте, DDS, Вы писали:
DDS>Подскажите в чем беда, пытаюсб из библиотеки вызвать экспортную функцию подключенного приложения (естесственно тоже моего). Пишу так:
DDS>В DLL: DDS>
DDS>...
DDS>function GetFromAPP(p:pchar):pchar; stdcall; export;
DDS>begin
DDS> ShowMessage('cool!');
DDS>end;
DDS>exports
DDS> GetFromAPP index 1 name 'GetFromAPP';
DDS>end.
DDS>
DDS>Дак вот все время один SHIT)) Не находит он функцию. HWND правильный, в проге этот код располагаю в тексте проекта, но и в тексте модуля формы (че как раз HWND) тоже пробовал. Не помогает. Подскажите...
Традиционно хэндл приложения (hInstance) получается через GetModuleHandle(nil); эта функция возвращает хэндл работающего кода, т.е. для dll это будет хэндл длл, для программы — хэндл программы. Кроме того, переменная hInstance — ссылающаяся на собственный хэндл кода afaik инициализируется RTL при старте.
Не совсем понял задачу — надо из длл вызвать какое приложение? которое dll загрузило? в этом случае удобнее предусмотреть функцию в DLL которая будет хранить (опять-же, в длл) указатель на объект/интерфейс/функцию основной программы. Т.е. схема примерно такая:
1. грузим длл
2. вызываем функцию длл передавая ей как параметр адрес функции/объекта/интерфейса программы
3. из длл по полученному указателю вызываются функции программы.
Такая схема удобна тем что нет необходимости динамически определять адреса функций в длл, достаточно определить интерфейс (в широком смысле слова) и передать один указатель.
Если надо вызывать функцию третьей программы, ее предварительно надо подгрузить.
Подскажите в чем беда, пытаюсб из библиотеки вызвать экспортную функцию подключенного приложения (естесственно тоже моего). Пишу так:
В DLL:
...
var
fD: function:pchar; stdcall;
begin
fD:=GetProcAddress( GetWindowWord(hwn,GWW_HINSTANCE) ,'GetFromAPP');
if @fD<>nil then fD else ShowMessage('shit!');
end;
...
В проге так:
...
function GetFromAPP(p:pchar):pchar; stdcall; export;
begin
ShowMessage('cool!');
end;
exports
GetFromAPP index 1 name 'GetFromAPP';
end.
Дак вот все время один SHIT)) Не находит он функцию. HWND правильный, в проге этот код располагаю в тексте проекта, но и в тексте модуля формы (че как раз HWND) тоже пробовал. Не помогает. Подскажите...
Здравствуйте, DDS, Вы писали:
DDS>Подскажите в чем беда, пытаюсб из библиотеки вызвать экспортную функцию подключенного приложения (естесственно тоже моего). Пишу так:
DDS>В DLL: DDS>
И у меня сробатывало, поскольку Load<чегото там чтобы получить Handle приложения>('имя_приложения.exe'); возвращал 0, и это не потому что он не срабатывал
Re: Экспортные функции у приложения
От:
Аноним
Дата:
08.08.07 06:56
Оценка:
Насколько я помню в Дельфи нельзя делать экспорт функций из EXE.
Там релокация работает неверно.
Здравствуйте, Аноним, Вы писали:
А>Насколько я помню в Дельфи нельзя делать экспорт функций из EXE. А>Там релокация работает неверно.
Ага, как же... Работает нормально. Вот примерный код. Могут быть синтаксические ошибки, но смысл, надеюсь, будет понятен.
//------------------------
// главный EXE
//-----------------------type
THelloProc=procedure; stdcall;
// эту процедуру будем вызывать из библиотекиprocedure Hello; stdcall;
begin
ShowMessage('Hello!');
end;
// это для теста вызова функции приложения из ДЛЛprocedure TestHello;
var FHandle:THandle;
P:THelloProc;
begin
FHandle:=LoadLibrary('TestHelloLib');
if FHandle<>0 then
begin
@P:=GetProcAddress(FHandle,'Test');
if @P<>nil then P;
FreeLibrary(FHandle);
end;
end;
// собственно тестprocedure TForm1.OnButtonClick(Sender:TObject);
begin
TestHello;
end;
exports
Hello;
end.
//--------------------
// модуль интерфейса приложение <-> библиотека
//--------------------unit MainExeExports;
interface
procedure Hello; stdcall;
implementation
procedure Hello; external'MyMainExe.exe' name 'Hello';
end;
//--------------------
// библиотека
//--------------------library TestHelloLib;
Uses MainExeExports;
procedure Test; stdcall;
begin
Hello;
end;
exports
Test;
end.
Здравствуйте, Leonidze, Вы писали:
L>Традиционно хэндл приложения (hInstance) получается через GetModuleHandle(nil); эта функция возвращает хэндл работающего кода, т.е. для dll это будет хэндл длл, для программы — хэндл программы. Кроме того, переменная hInstance — ссылающаяся на собственный хэндл кода afaik инициализируется RTL при старте.
L>Не совсем понял задачу — надо из длл вызвать какое приложение? которое dll загрузило? в этом случае удобнее предусмотреть функцию в DLL которая будет хранить (опять-же, в длл) указатель на объект/интерфейс/функцию основной программы. Т.е. схема примерно такая: L>1. грузим длл L>2. вызываем функцию длл передавая ей как параметр адрес функции/объекта/интерфейса программы L>3. из длл по полученному указателю вызываются функции программы. L>Такая схема удобна тем что нет необходимости динамически определять адреса функций в длл, достаточно определить интерфейс (в широком смысле слова) и передать один указатель.
Последний способ не плох, но придется либо хранить глобальный "адрес функции/объекта/интерфейса программы" или таскать его при каждом вызове в контексте...
А вот GetModuleHandle(nil); в DLL как раз возвращает хендл EXE вроди