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

Вниз

Использование хука из сервиса   Найти похожие ветки 

 
Неопытный   (2004-01-19 04:46) [0]

При написаниии сервиса столкнулся с проблемой. Необходимо поставить хук типа WH_SHELL (что впрочем не важно). Функция, которая устанавливает хук возвращает true. Но хук не работает.

В DLL использую PostThreadMessage для отправки сообщений сервису.
У меня складывается впечатление, что процедура обработки хука не доходит до конца, хотя там и стоит только PostThreadMessage. Пытался перед ней ставить запись в файл какой-нибудь информации (например того-же дескриптора процесса). Но файл даже не создается, а если и создается, то пустой и его нельзя удалить, потому что он используется. То есть получается, что процедура обработки прерывается еще до закрытия файла. Это может происходить только при запуске сервиса, когда хук ставится и сразу же ловит запуск сервиса, который его и поставил (не пойму, почему). После этого похоже хук падает вообще.

Возможно в этой теме в конце как раз такой случай
http://delphimaster.net/view/4-1069096480/

Могу привести исходные тексты, если нужно.


 
VMcL ©   (2004-01-19 06:53) [1]

В FAQ смотрел? Там пример есть.


 
Sting   (2004-01-19 07:41) [2]

Смотрел. Там есть пример на перехват клавиш. Он у меня прекрасно работает, но не в сервисе. А насчет сервисов я там ничего не видел.


 
BiN ©   (2004-01-19 10:06) [3]

скорее всего не установлено взаимодейсвтие с рабочим столом, а точнее с пользовательской средой


 
Sting   (2004-01-19 12:21) [4]

Все это установлено. Interactive = true.


 
Sting   (2004-01-19 12:57) [5]

А ведь причина действительно кроется в использовании CreateFileMapping. Только что попробовал убрал ее и нужную переменную записал в реестр, все заработало. Конечно хотелось бы обойтись без дополнительных средств, типа реестра, но видимо тут поделать ничего нельзя.


 
Digitman ©   (2004-01-19 13:00) [6]


> Sting


проблема - в SecurityAttributes при открытии MMF .. необходимо настроить SE должным образом


 
Digitman ©   (2004-01-19 13:24) [7]

можно и без выкрутасов с SE обойтись

достаточно просто попытаться сначала выполнить OpenFileMapping(только чтение)

если MMF-объект не существует еще, то это первый экз-р хук-DLL и следует тут же выполнить CreateFileMapping(запись и чтение)


 
Sting   (2004-01-19 13:58) [8]

То есть поставить такой код:
if OpenFileMapping(только чтение)=0 then CreateFileMapping(запись и чтение) ?


 
Digitman ©   (2004-01-19 14:01) [9]

да

и, соответственно, последующий вызов MapViewOfFile() должен быть выполнен с теми же правами, что и предыдущий CreateFileMapping или OpenFileMapping, завершившийся успешно


 
Sting   (2004-01-19 14:51) [10]

Вот наваял код:

MapHandle1:=OpenFileMapping(FILE_MAP_READ, false, GlobMapID1);
if MapHandle1 = 0 then
       begin
         MapHandle1:=CreateFileMapping(INVALID_HANDLE_VALUE, nil, PAGE_READWRITE, 0, SizeOf(TShareInf), GlobMapID1);
         ShareInfo:=MapViewOfFile(MapHandle1, FILE_MAP_ALL_ACCESS, 0, 0, SizeOf(TShareInf));
       end else
         ShareInfo:=MapViewOfFile(MapHandle1, FILE_MAP_READ, 0, 0, SizeOf(TShareInf));

После первого вызова OpenFileMapping возвращает не ноль. Почему? Может я что-то с параметрами напутал.


 
SuperDee   (2004-01-19 15:06) [11]

Ты лол


 
Digitman ©   (2004-01-19 15:47) [12]

ладно, не мучайся

поступи проще - используй мьютекс


function OpenGlobalData: Boolean;
begin
 InitializeSecurityDescriptor(@SecAttr, SECURITY_DESCRIPTOR_REVISION);
 WM_ETKAHOOK:= RegisterWindowMessage(HookMonMsg);
 hMutex := OpenMutex(SYNCHRONIZE, False, MutexName);
 if hMutex = 0 then
   IsFirstInstance := True;
 try
   if IsFirstInstance then
     begin
       hMutex := CreateMutex(@SecAttr, False, MutexName);
       Win32Check(hMutex <> 0);
     end;
   try
     if IsFirstInstance then
       begin
         hMMF:= CreateFileMapping(INVALID_HANDLE_VALUE, @SecAttr, PAGE_READWRITE, 0, SizeOf(GlobalHookData^), MMFName);
         Win32Check(hMMF <> 0);
         try
           GlobalHookData:= MapViewOfFile(hMMF, FILE_MAP_ALL_ACCESS, 0, 0, SizeOf(GlobalHookData^));
           Win32Check(Assigned(GlobalHookData));
           with GlobalHookData^ do
             begin
               hCallWndProc := 0;
               hCallWndProcRet := 0;
               hMonitor := 0;
             end;
         except
           CloseHandle(hMMF);
           hMMF := 0;
           raise;
         end;
       end
     else
       begin
         WaitForSingleObject(hMutex, INFINITE);
         ReleaseMutex(hMutex);
         hMMF:= OpenFileMapping(FILE_MAP_READ, False, MMFName);
         Win32Check(hMMF <> 0);
         try
           GlobalHookData:= MapViewOfFile(hMMF, FILE_MAP_READ, 0, 0, SizeOf(GlobalHookData^));
           Win32Check(Assigned(GlobalHookData));
         except
           CloseHandle(hMMF);
           hMMF := 0;
           raise;
         end;
       end;
   except
     CloseHandle(hMutex);
     hMutex := 0;
     raise;
   end;
   Result := True;
 except
   Result := False;
 end;
end;

procedure CloseGlobalData;
begin
 if Assigned(GlobalHookData) then
   UnmapViewOfFile(GlobalHookData);
 if hMMF <> 0 then
   CloseHandle(hMMF);
 if hMutex <> 0 then
   CloseHandle(hMutex);
end;



 
Sting   (2004-01-19 15:50) [13]

Ладно. Попробую разобраться.
В любом случае спасибо большое.
Если что, уж тогда через реестр сделаю, хотя при этом DLL получается большая. Еще раз спасибо.


 
Sting   (2004-01-19 19:06) [14]

Вот я тут попробовал приведенный код. И все же не пойму. В первый раз он у меня сработал. А потом опять первый вызов функции OpenMutex выдвал не ноль. После перезагрузки компьютера опять все заработало. После рестарта службы история повторяется. Ведь даже в хэлпе написано, что после того как последний процесс, используюший мьютекс закрывается, то и мьютекс уничтожается. Почему этого не происходит у меня. Дллка выдь из памяти выгружается. И службы тоже нет.


 
NiaSoft   (2004-01-19 23:06) [15]

Я тут попробовал следующую штуку, и как ни странно с первого раза заработало (такое случается достаточно редко :) )


   SetSecurityInfo(hFileMappingObject, SE_KERNEL_OBJECT,
     DACL_SECURITY_INFORMATION,
     Nil, Nil, Nil, Nil);


данный код вызывыется после создания мап-файла, и дает всем полные права на доступ к объекту.
ЗЫ: Конечно не так хорошо с по отношению к безопастности как хотелось бы, но работает :).


 
NiaSoft   (2004-01-19 23:10) [16]

А выше приведенные методы несколько не подойдут, если из из хуков нужно будет писать в расшаренную область памяти, ведь доступ только на чтение.


 
Digitman ©   (2004-01-20 08:18) [17]


> Sting   (19.01.04 19:06) [14]


сразу после выполнения UnhookWindowsHookEx() (т.е. снятия глоб.хука в ходе завершения или остановки сервиса) выполни

SendMessage(HWND_BROADCAST, WM_NULL, 0, 0);

дело в том, что в трее у тебя наверняка висят разного рода Винампы и иже с ними ... вот в их адресном пр-ве уже после снятия хука и продолжают еще "висеть" экз-ры хук-библ-ки, в контексте которых объеуты глоб.доступа/синхронизации, как ты понимаешь, на этот момент еще не закрыты (оттого и <> 0)

выполнив бродкаст любого dummy-сообщения, ты "подстегнешь" эти оставшиеся процессы, и система выгрузит твою хук-библ-ку и из их АП ... разумеется, сервис должен иметь опцию взаимодействия с дисктопом


 
Digitman ©   (2004-01-20 08:24) [18]

кстати, упомянутый бродкаст следует выполнить и сразу после SetWindowsHookEx(), иначе хук не будет сразу же внедрен в некоторые "висящие в трее" процессы а-ля Винамп... можешь убедиться в этом сам, выводя по таймеру список процессов, в которые был внедрен хук сразу после его установки ... как только мышка "поелозит" в зоне иконок трея (читай - система пошлет при этом Винампу соотв.оконное сообщение), ты сразу увидишь появление в списке процессов со внедренным хук-модулем процесс того же Винампа


 
Sting   (2004-01-20 11:50) [19]

> NiaSoft
Нет писать никуда ничего не надо.
Доступ на чтение подойдет.

> Digitman
Спасибо. Попробую.


 
NiaSoft   (2004-01-20 20:49) [20]

А у меня надо писать :)



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

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

Наверх




Память: 0.52 MB
Время: 0.084 c
1-1079355085
Cosinus
2004-03-15 15:51
2004.04.04
Сохранение всех документов, отправленных на принтер


3-1078470164
bushmen
2004-03-05 10:02
2004.04.04
ADOStoredProc


14-1078976465
Думкин
2004-03-11 06:41
2004.04.04
С днем рождения! 11 марта


6-1074962960
kor@l
2004-01-24 19:49
2004.04.04
Browser


7-1073284686
Den_lam
2004-01-05 09:38
2004.04.04
LPT