Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > C/C++ программирование > Общие вопросы C/C++
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 11.05.2010, 19:31   #1
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
Вопрос (C++) Работа с Win API, ХУКАМИ.

У меня есть два проекта, один Dll библиотека, второй исполняемый файл

Примерная схема библиотеки:
Код:
//------------------------------------------
#pragma data_seg(".hdata") // секция в памяти общая для всех процессов
HINSTANCE hi=NULL;
#pragma data_seg() // конец секции
#pragma comment(linker, "/section:.hdata,rws")

HHOOK hKeyHook=NULL;
HHOOK hCBTHook=NULL;

LRESULT CALLBACK KeyboardProc(int nCode,WPARAM wParam,LPARAM lParam)
{
    if (nCode) return CallNextHookEx(hKeyHook,nCode,wParam,lParam);
    if(lParam>=0) DoNextAction(lParam);
   return CallNextHookEx(hKeyHook,nCode,wParam,lParam);
}

LRESULT WINAPI CBTProc(int nCode, WPARAM wParam, LPARAM lParam)
{
   if(nCode==HCBT_ACTIVATE) // вызывается перед тем как система собирается активировать
                                          //какоето окно или открыть новое
           DoNextAction2((HWND)wParam);
   return CallNextHookEx(hCBTHook, nCode, wParam, lParam);
}

extern "C" __declspec (dllexport) BOOL SetKeyboardHook(void)
{
   hCBTHook=SetWindowsHookEx(WH_CBT ,CBTProc, hi, 0);
   hKeyHook=SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, hi, 0);
   return hKeyHook;
}

//------------------------------
Содержание исполняемого файла:
Код:
//------------------------------
extern "C" __declspec (dllimport) BOOL SetKeyboardHook(void);     // функция импортируемая из DLL

//----- функция вызова
   if(!SetKeyboardHook()) // устанавливаем хуки
       return 1; // не получилось закрываемся
//--------
Дак вот, почему не удается установить хук??

И если у меня нету в исполняемом файле нет главного окна, то будет ли WH_KEYBOARD обрабатывать нажатия клавиатуры? Может нужно использовать WH_KEYBOARD_LL ?

WH_CBT Вообще не происходит....Почему?

Возможно WH_CBT и WH_KEYBOARD должны быть описаны в исполняемом файле?? (я о функция соотвецтвующих хукам)

У меня KeyboardProc CBTProc описаны в самой библиотеке, это правильно?

Если я хочу перехватывать допустим все события клавиатуры, будет ли мне их выдавать WH_KEYBOARD ?? или необходимо использовать WH_KEYBOARD_LL ??

Последний раз редактировалось stribogaaa; 11.05.2010 в 20:20.
stribogaaa вне форума Ответить с цитированием
Старый 11.05.2010, 20:07   #2
counter
Участник клуба
 
Регистрация: 18.10.2008
Сообщений: 1,409
По умолчанию

а как библиотека подключается к исполняемому файлу?
counter вне форума Ответить с цитированием
Старый 11.05.2010, 20:12   #3
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
Сообщение

Цитата:
Сообщение от counter Посмотреть сообщение
а как библиотека подключается к исполняемому файлу?
Код:
#pragma comment (lib, "hook.lib")
С подключением вроде все в поряде, даже функцию вызывает, если верить VS.

Тут проблема с хуками... либо я не те использую.. либо что то другое...

Последний раз редактировалось stribogaaa; 11.05.2010 в 20:14.
stribogaaa вне форума Ответить с цитированием
Старый 11.05.2010, 20:46   #4
counter
Участник клуба
 
Регистрация: 18.10.2008
Сообщений: 1,409
По умолчанию

в SetWindowsHookEx должен передаваться HINSTANCE модуля, в котором находится фильтр-процедура, а у вас hi=0
counter вне форума Ответить с цитированием
Старый 11.05.2010, 21:37   #5
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
Сообщение

Цитата:
Сообщение от counter Посмотреть сообщение
в SetWindowsHookEx должен передаваться HINSTANCE модуля, в котором находится фильтр-процедура, а у вас hi=0
Я инициализирую hi при регистрации длл.
Код:
BOOL APIENTRY DllMain(HINSTANCE hModule,DWORD ul_reason_for_call,LPVOID lpReserved)
{
    switch(ul_reason_for_call)
     {
        case DLL_PROCESS_ATTACH: 
        {
            if(!hi) // запоминаем запустивший хэндл
                hi=hModule; // дескриптор модуля DLL

.................
        }
     }
}
PS те фильтр-процедура находится в самом Длл.
(забыл сразу включить в вопрос эту часть кода)
stribogaaa вне форума Ответить с цитированием
Старый 11.05.2010, 21:41   #6
BOBAH13
Android Developer
Старожил Подтвердите свой е-майл
 
Аватар для BOBAH13
 
Регистрация: 19.02.2007
Сообщений: 3,708
По умолчанию

Так к слову, идеальный и самый верный метод создания хуков:
1. Загрузка динамическая - LoadLibrary вашей .dll
2. .dll экспортирует функции обработчики хуков
3. Исполняемый файл вызывает SetWindowHookEx + HINSTANCE вашего загруженного .dll

Правильный подход, сразу убирает возможные грабли
BOBAH13 вне форума Ответить с цитированием
Старый 12.05.2010, 10:24   #7
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
По умолчанию

BOBAH13, вы считаете проблема в загрузке библиотеки?

Может это поможет разобраться, при вызове функции
Код:
extern "C" __declspec (dllexport) BOOL SetKeyboardHook(void)
{
   hCBTHook=SetWindowsHookEx(WH_CBT ,CBTProc, hi, 0);
   hKeyHook=SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, hi, 0);
   return hKeyHook;
}
hCBTHook и hKeyHook не определяются...

- hCBTHook 0x007e08cb {unused=??? } HHOOK__ *
unused CXX0030: ошибка: невозможно вычислить выражение
- hKeyHook 0x00650911 {unused=0 } HHOOK__ *
unused 0 int
- hi 0x10000000 {unused=9460301 } HINSTANCE__ *
unused 9460301 int

Может кто-то по поводу этой ошибки выскажет предположения??

И еще WH_KEYBOARD_LL немного меняет ситуацию... но обработка hCBTHook так и не происходит?? истина, возможно, кроется в этом...

Последний раз редактировалось stribogaaa; 12.05.2010 в 10:26.
stribogaaa вне форума Ответить с цитированием
Старый 12.05.2010, 16:23   #8
JeyKip
Форумчанин
 
Регистрация: 18.09.2009
Сообщений: 133
По умолчанию

Истина на виду...
1)функция установки хука возвращает
Код:
return hKeyHook;
ХУК КЛАВИАТУРЫ...WH_CBT ИГНОРИРУЕТСЯ...
БЛИН, И КАК ЖЕ МОЖЕТ БЫТЬ ФУНКЦИЯ УСТАНОВКИ ХУКА БУЛЕВСКОЙ, И ПРИ ЭТОМ ВОЗВРАЩАТЬ ДЕСКРИПТОР ХУКА!!!???
2)
Код:
#pragma data_seg(".hdata") // секция в памяти общая для всех процессов
HINSTANCE hi=NULL;
HHOOK hHook=NULL;//хук должен быть глобальным, объявленный в этой секции, чтобы DLL могла его внедрить в любой чужой процесс
#pragma data_seg() // конец секции
#pragma comment(linker, "/section:.hdata,rws")
3)Процедуры обработки хука удобнее держать в DLL, не объявляя их экспортируемыми...(LRESULT CALLBACK имя процедуры)...ниже привожу код экспортируемой функции, которая устанавливает хук, в зависимости от условия:
3.1) в заголовочном файле DLL:
Код:
#define HOOK __declspec(dllexport)
#include <windows.h>
extern "C"
{
	HOOK int SetKeyHook(int);//в качестве параметра из главной программы передается номер хука 
	HOOK int DelKeyHook();
}
3.2) Установка хука:
Код:
HOOK int SetKeyHook(int hook)
{

	if (hook==WH_KEYBOARD)
		hHook = SetWindowsHookEx (WH_KEYBOARD,KeyboardProc,hInst,NULL);
	else if (hook==WH_CBT)
		hHook = SetWindowsHookEx (WH_CBT,CBTProc,hInst,NULL);
	else if (hook==WH_MOUSE)
		hHook = SetWindowsHookEx (WH_MOUSE,MouseProc,hInst,NULL);
	return 0;
}
3.3)Удаление хука:
Код:
HOOK int DelKeyHook ()
{
	UnhookWindowsHookEx(hHook);
	hHook=NULL;
	return 0;
}
4) В тексте вызывающей программы (в зависимости от меню или кнопок управления, которые отвечают за установку какого-либо хука) при вызове SetKeyHook(int) передаете номер хука, который нужен...

О том, как загрузить функцию из DLL писалось выше...УДАЧИ!!!

Последний раз редактировалось JeyKip; 12.05.2010 в 16:33.
JeyKip вне форума Ответить с цитированием
Старый 12.05.2010, 16:52   #9
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
Плохо

JeyKip,ты бы дочитал вопрос до конца!!!

Цитата:
Сообщение от JeyKip Посмотреть сообщение
БЛИН, И КАК ЖЕ МОЖЕТ БЫТЬ ФУНКЦИЯ УСТАНОВКИ ХУКА БУЛЕВСКОЙ, И ПРИ ЭТОМ ВОЗВРАЩАТЬ ДЕСКРИПТОР ХУКА!!!???
Возвращение дескриптора хука и не планировалось, функция должна только возвращать установлен хук или нет... что она и возвращает!!!
Предполагалось возвращение
Код:
return hKeyHook && hCBTHook;
Цитата:
Сообщение от JeyKip Посмотреть сообщение
HHOOK hHook=NULL;//хук должен быть глобальным, объявленный в этой секции, чтобы DLL могла его внедрить в любой чужой процесс
это не решило проблемы!!

Цитата:
Сообщение от JeyKip Посмотреть сообщение
Процедуры обработки хука удобнее держать в DLL, не объявляя их экспортируемыми...
Они итак в Dll

Цитата:
Сообщение от JeyKip Посмотреть сообщение
Истина на виду...
Если бы она была бы на виду, ЭТОТ ТОПИК НЕ ВИСЕЛ БЫ ТУТ УЖЕ 2 ДНЯ !!!
stribogaaa вне форума Ответить с цитированием
Старый 12.05.2010, 16:57   #10
stribogaaa
 
Регистрация: 11.05.2010
Сообщений: 6
По умолчанию

Цитата:
Сообщение от JeyKip Посмотреть сообщение
4) В тексте вызывающей программы (в зависимости от меню или кнопок управления, которые отвечают за установку какого-либо хука) при вызове SetKeyHook(int) передаете номер хука, который нужен...
Мне кажется это понятно даже "ТУБУРЕТКЕ", в итоге от своего поста никакого толку...!!!
stribogaaa вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Win API ( CИ) ПроГрам Помощь студентам 0 29.04.2010 21:43
Win Api alexov Общие вопросы C/C++ 4 29.01.2009 13:33
Win API aleks_n Общие вопросы Delphi 0 15.09.2008 11:07
Win Api, работа с мышью Petrr Win Api 2 26.04.2008 19:58