![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Динамический импорт функции из DLL [D7]
Igit © (2005-06-23 11:43:00)Здравтсвйте мастера! Есть у меня одлин модуль, в нем описываются функции вызываемые из NTDLL.DLL... они видны в таблице импорта... и из-за них под вин9x программа не запускается вовсе... (у меня в программе идет проверка какая винда и в зависимости от этого исп. тот или иной метод). Так вот, как можно переписать например вот это
Function DbgUiConnectToDbg(): NTStatus;stdcall;external 'ntdll.dll';
на такое чтоб не жестко привязывалось к ntdll а динамически?
GrayFace (2005-06-28 21:00:00) [1]-=XP=- © (27.06.05 11:17) [30]
Единственное, чем интересен - не требует borlandmm.dll в комплекте с программой поставлять.
Неужто, обычный требует?
GrayFace (2005-06-28 20:59:00) [2]evvcom © (27.06.05 11:31) [31]
У меня не класс, а маленькая функция для динамической загрузки. (См. [29])
evvcom (2005-06-27 11:31:00) [3]
> Это требует определенных усилий - сохранять, какие библиотеки
> загружены, какие - нет. А если проверять GetModuleHandle,
> то ее могут выгрузить.
А ты возьми себе за правило, что если ты в классе вызвал LoadLibrary, то в нем же вызываешь и FreeLibrary, когда более она не нужна. И так в каждом классе. И никаких глобальных счетчиков и проч. Этот счетчик уже есть в системе и работает он лучше, чем напишешь ты.
-=XP=- (2005-06-27 11:17:00) [4]достаточно один раз вызвать LoadLibrary
Мне тут "под руку" попался какой-то китайский менеджер памяти (вместо ShareMem) - называется, кажется, ShareMemRep.pas (но это к слову). Единственное, чем интересен - не требует borlandmm.dll в комплекте с программой поставлять.
Так вот, этот менеджер, при завершении приложения, проверяет динамически загруженные библиотеки, и очень настойчиво ругается (возможна утечка памяти, говорит), если хоть одна библиотека осталась в памяти. Приходится четко отслеживать процесс выгрузки.
GrayFace (2005-06-27 10:49:00) [5]Digitman © (24.06.05 8:20) [28]
достаточно один раз вызвать LoadLibrary
Это требует определенных усилий - сохранять, какие библиотеки загружены, какие - нет. А если проверять GetModuleHandle, то ее могут выгрузить. Просто маленькая функция для динамической загрузки - часть моего пакета.
Digitman (2005-06-24 08:20:00) [6]
> нормально ли вызывать много раз LoadLibrary, не вызывая
> Free?
достаточно один раз вызвать LoadLibrary
GrayFace (2005-06-23 20:16:00) [7]А если надо, чтобы библиотека загружалась динамически, но навсегда, нормально ли вызывать много раз LoadLibrary, не вызывая Free?
Игорь Шевченко (2005-06-23 19:13:00) [8]http://www.schevchenko.net.ru/SRC/Common_60.zip
Там пример (ntdll.pas) который меня ни разу не подводил. Изучай.
Igit (2005-06-23 16:44:00) [9]Спасибо большое всем вам за помощь! У меня все получилось... зделал для себя вывод: забыл я все, нужно прочитать про синтаксис паскаля, и организацию модулей.
-=XP=- (2005-06-23 16:34:00) [10]Все зделал как положено, но
А это кому написано было:
type
TZwCreateThread = function(ThreadHandle: pdword;
DesiredAccess: ACCESS_MASK;
ObjectAttributes: pointer;
ProcessHandle: THandle;
ClientId: PClientID;
ThreadContext: pointer;
UserStack: pointer;
CreateSuspended: boolean):NTStatus;
stdcall;
Digitman (2005-06-23 16:21:00) [11]
> Что я не так сделал?
ты нарушил языковые соглашения Паскаля, который ожидает в дан.случае следующее :
type
TZwCreateThread = Function(<параметры>):NTStatus;stdcall;
где TZwCreateThread - это тот самый cимвольный идентификатор типа, который expected, но вместо которого компилятор встретил зарезервированное ключ.слово function
строки в секции type должны соответствовать правилу
Символьный_Идентификатор_Типа = Выражение_описывающее_тип;
Igit (2005-06-23 16:11:00) [12]Все зделал как положено, но
type
Function TZwCreateThread(<параметры>):NTStatus;stdcall;
выдает ошибку "Identifier expected but FUNCTION found"
Что я не так сделал?
-=XP=- (2005-06-23 14:45:00) [13]
<...>
implementation
<...>
var
Lib: THandle;
<...>
initialization
if (<Под NT>) then
begin
Lib := LoadLibrary(<...>);
ZwCreateThread := GetProcAddress(Lib, <...>);
<...>
end
else
<...>
finalization
if (Lib <> 0) then FreeLibrary(Lib);
end.
Igit (2005-06-23 14:28:00) [14]Нет, неправильно выразился, в этом модуле
unit SuUnit;
interface
uses
Windows;
type
TZwCreateThread = function(ThreadHandle: pdword;
DesiredAccess: ACCESS_MASK;
ObjectAttributes: pointer;
ProcessHandle: THandle;
ClientId: PClientID;
ThreadContext: pointer;
UserStack: pointer;
CreateSuspended: boolean):NTStatus;
stdcall;
var
ZwCreateThread: TZwCreateThread;
implementation
end.
Куда нужно всавить GetModuleHandle и GetProcAddress чтобы в других модулях использующих эту функцию не нужно было ничего изменять?
-=XP=- (2005-06-23 14:20:00) [15]Так, проверить решил..
О как! Век живи - век учись! :о)
куда передавать хэнд загруженной dll
В GetProcAddress(<Handle>, '<ProcName>');
Igit (2005-06-23 13:58:00) [16]Так, проверить решил..
Заморозил выполнение на CloseFile(f); и посмотрел в LordPE. Вместе сней загружены такие dll
rptc4.dll
advapi32.dll
gdi32.dll
user32.dll
kernel32.dll
ntdll.dll
И еще вопрос, я не понял, в коде
-=XP=- © (23.06.05 12:34) [7] куда передавать хэнд загруженной dll?
-=XP=- (2005-06-23 13:26:00) [17]речь, очевидно, шла о ntdll.dll
Если так - то да, в приложениях Delphi (с использованием VCL), работающих под NT, эта библиотека загружена всегда. Хотя, это поведение, насколько мне известно - не документированно Microsoft?
-=XP=- (2005-06-23 13:21:00) [18]NativeAPI в NT берутся из ntdll... все АПИ используют NativeAPI, значит в NT она по идее загружена всегда.
program Test;
var
f: TextFile;
begin
AssignFile(f, 'c:\test.txt');
Rewrite(f);
Writeln(f, 'Я подозреваю, что в адресное пространство этого "приложения" не загружено ни одной библиотеки');
CloseFile(f);
end.
Но это так, к примеру.
Еще раз: если в приложении есть статическая линковка какой-то библиотеки, то эта библиотека будет загружена в АП. Если статической линковки нет - библиотека загружена не будет. Исключение - когда одна библиотека линкует другую библиотеку. Но опираться на этот факт не стоит, ибо это недокументированное поведение.
Хотите в приложении знать, загружена ли библиотека, или нет - используйте как приведено в [10], но, все же, проверяйте Handle на валидность.
Digitman (2005-06-23 13:14:00) [19]
> -=XP=- © (23.06.05 12:56) [12]
> Почему?
речь, очевидно, шла о ntdll.dll
импорт ее - статический
гоняй туда-сюда ее счетчик - выгрузить штатными ср-вами тебе ее не удастся
потому и сабж
-=XP=- (2005-06-23 13:08:00) [20]Так ntdd или ntdll? :)
Я описал ситуацию в общем, применительно к любой библиотеке.
Что делать в конкретном случае - Ваше дело. ;)