CIS Inc. Ltd.

Sign by Dealighted - Coupons & Discount Shopping

Домашняя Обратная связь Поиск

Ловушка
Вверх

 

[В стадии разработки]

Домашняя
Секреты
Ловушка
Перехват CD
Формы
Нонсенс
Hide
Alias

 

 
www.yandex.ru

Не жадничай!
ЯндексЯндекс. ДеньгиХочу такую же кнопку

Праздники славян

бесплатная музыка mp3

Яндекс цитирования

 


Components and tools for developers

PoleSoft Technologies Group

DIGITLAND.RU Портал программирования, цифровых технологий и электроники

Шрифт

Locations of visitors to this page

free counters

 

Создание ловушек

Создание ловушки клавиатуры в Borland C++ Builder 6

5 августа 2004  

    Создадим программу, которая будет отслеживать нажатие клавиш ALT+F12 и делать видимой главную форму. При создании этого проекта вы научитесь создавать и обрабатывать сообщения с помощью карты сообщений (таблицы отображения сообщений), делать невидимой главную форму приложения и собственно создавать и устанавливать ловушки.
    При создании ловушек (Hook’s) помните два основных правила:

  1. Процедура заглушки должна располагаться в DLL;

  2. Процедура заглушки должна заканчиваться вызовом функции CallNextHookEx().

    Создайте новую группу приложений (ProjectGroup) и добавьте в нее библиотеку DLL. Для этого воспользуйтесь мастером создания DLL. В мастере создания DLL оставьте все настройки по умолчанию (C++, Use VCL, Multi Threaded). Добавьте новое приложение. Перейдите в проект DLL и добавьте новый текстовый файл, который сохраните под именем Unit1.h. Сохраните группу. Теперь перейдем непосредственно к созданию кода.
Перейдите в окно редактора кода Unit1.h и введите следующий код:
#ifndef Unit1H
#define Unit1H

#ifdef __DLL__
#define DLL_EXP __declspec(dllexport)
#else
#define DLL_EXP __declspec(dllimport)
#endif
#define MYMESSAGE WM_USER + 100

HOOKPROC lpfn;
HHOOK hhk;
HWND hWnd;
extern "C" LRESULT CALLBACK DLL_EXP KeyboardHook(int nCode, WPARAM wParam,
LPARAM lParam);

#endif
заголовочный файл для нашей DLL готов. Группа директив препроцессора работает следующим образом: если определено имя __DLL__, то DLL_EXP раскрывается в __declspec(dllexport). Если имя __DLL__ не определено, DLL_EXP раскрывается в __declspec(dllimport). Имя __DLL__ автоматически определяется в Borland C++ Builder при создании проекта DLL, и не определяется при создании проекта приложения. Этот заголовок можно использовать как для DLL, так и для приложений. При построении DLL все классы и функции, объявленные с DLL_EXP, будут экспортированы, а при построении вызывающего приложения, все функции и классы, объявленные с DLL_EXP, будут импортированны.
    Перейдите в редактор кода файла Unit1.cpp. Можете удалить закомментированные строки, которые предупреждают о необходимости добавления библиотеки MEMMGR.LIB и использовании BORLNDMM.DLL в случае работы со статической RTL. В нашем проекте мы не используем статическую RTL. Добавьте строчку с подключением заголовочного файла Unit1.h, пропустите функцию DllEntryPoint() и добавьте следующий код:
LRESULT CALLBACK DLL_EXP KeyboardHook(int nCode,WPARAM wParam,LPARAM lParam)
{
    if(nCode < 0 || nCode != HC_ACTION)
        return CallNextHookEx(hhk, nCode, wParam, lParam);
    if(wParam == (VK_F12))
    {
        if(lParam & 0x80000000 || lParam & 0x40000000)
            return CallNextHookEx(hhk, nCode, wParam, lParam);
        if((lParam >> 29) & 1)
        {
            hWnd = FindWindow("TForm2", NULL);
            SendMessage(hWnd, MYMESSAGE, 0, 0);
        }
    }
    return CallNextHookEx(hhk, nCode, wParam, lParam);
}.

В функцию ловушки передаются следующие параметры:
nCode – определяет порядок обработки сообщения;
wParam – код виртуальной клавиши;
lParam – дополнительная информация: счетчик нажатий, скэн-код и др. (рисунок 1).


 

 

 

 

Рисунок 1

    Нас интересуют параметры wParam и lParam. Если wParam содержит VK_F12, то есть нажата клавиша F12, идет проверка на удержание клавиш. Последний оператор if проверяет нажатие клавиши ALT. В операторном блоке этого if ищется наша главная форма и ей посылается сообщение. Так как наша функция является функцией обратного вызова она возвращает управление в следующую ловушку, то есть как было сказано выше, вызывает функцию CallNextHookEx(). Ловушка готова. Далее переходим к написанию кода главного приложения.
Активизируйте Project2 и на форме разместите 3 компонента Button и компонент Label. Задайте свойство Caption у Button1 “Set Hook’s”, у Button2 “Unhook’s”, у Button3 “Hide” и удалите у Label1. Установите свойство Enabled в false у Button2 и Button3. В обработчик OnClick компонента Button1 добавьте следующий код:
hMod = LoadLibrary("Project1.dll");
lpfn = (HOOKPROC)GetProcAddress(hMod, "KeyboardHook");
hhk = SetWindowsHookEx(WH_KEYBOARD, lpfn, hMod, 0);
if(hhk == NULL)
{
    FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
                    FORMAT_MESSAGE_FROM_SYSTEM,
       NULL, GetLastError(), MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
                    (LPTSTR) &lpMsgBuf, 0, NULL);
    MessageBox(NULL, (LPTSTR)lpMsgBuf, "Не могу установить ловушку клавиатуры",
                    MB_OK | MB_ICONERROR);
    LocalFree(lpMsgBuf);
}
else
{
    Button1->Enabled = false;
    Button2->Enabled = true;
    Button3->Enabled = true;
    Label1->Caption = "Ловушка установлена.\nИспользуйте ALT+F12";
}.
    Первая строка кода загружает в память нашу DLL с функцией ловушки. Вторая получает адрес функции ловушки. Третья строка устанавливает нашу ловушку. Если ловушка не установлена выводиться сообщение об ошибке.
    В обработчик OnClick компонента Button2 добавьте код:
if(UnhookWindowsHookEx(hhk))
{
    Button1->Enabled = true;
    Button2->Enabled = false;
    Button3->Enabled = false;
    Label1->Caption = "Ловушка выгружена.";
}
FreeLibrary(hMod);
который удаляет нашу заглушку из цепочки заглушек операционной системы и выгружает нашу DLL из памяти.
    Теперь осталось написать код для скрытия нашего приложения. В обработчик OnClick компонента Button3 добавьте строку кода: Form2->Hide(), в событие OnHide формы добавьте код:
        ShowWindow(Application->Handle, SW_HIDE);
        Application->MainForm->Visible = false;,
а в событие OnShow добавьте код:
        ShowWindow(Application->Handle, SW_SHOW);
        Application->MainForm->Visible = true;.
    Наше приложение почти готово, осталось написать код для обработки сообщения MYMESSAGE, которое было определено в заголовочном файле DLL. Для обработки нашего сообщения необходимо создать карту сообщений. Перейдите в редактор кода заголовочного файла формы. Добавьте код для подключения заголовочного файла DLL – #include "Unit1.h". В общий раздел класса формы добавьте следующий код:
HINSTANCE hMod;
LPVOID lpMsgBuf;
void __fastcall OnMyMessage(TMessage& Msg);
BEGIN_MESSAGE_MAP
    MESSAGE_HANDLER(MYMESSAGE, TMessage, OnMyMessage)
END_MESSAGE_MAP(TForm).
    Первая строка кода объявляет переменную для хранения хэндла библиотеки DLL, вторая переменную для хранения сообщения об ошибке, третья строка объявляет функцию, которая будет обрабатывать наше сообщение (обработчик сообщения). Далее следует карта сообщений (таблица отображения сообщений), которая связывает некоторое сообщение Windows (в нашем случае MYMESSAGE) с определенной функцией в нашем коде (OnMyMessage). Карта сообщений всегда располагается в конце определения класса. Она начинается с BEGIN_MESSAGE_MAP и заканчивается END_MESSAGE_MAP. В END_MESSAGE_MAP передается единственный параметр, имя базового класса. Между этими элементами располагается одно или несколько объявлений MESSAGE_HANDLER (обработчиков). Для компонентов VCL используется VCL_ MESSAGE_HANDLER. Вы наверно догадались, что это макроопределения. Компилятор раскрывает макросы таблицы сообщений в функцию Dispatch(). В общем случае эта функция выглядит следующим образом:
vitrual void __fastcall Dispatch(void *Message)
{
    switch((Pmessage)Message)->Msg)
    {
        case UserMsg1 : HandlerMsg1((StructMsg1&) *Message);
            break;
        case UserMsg2 : HandlerMsg2((StructMsg2&) *Message);
            break;
       
        default: Name_of_Base_Class::Dispatch(Message);
        break;
    }
}
    Рассмотрим более подробно параметры макроса MESSAGE_HANDLER, который имеет следующий синтаксис:
    MESSAGE_HANDLER(<UserMsg>, <StructMsg>, <HandlerMsg>).
    UserMsg – сообщение Windows или определенное вами, которое вы хотите обработать в нашем случае сообщение MYMESSAGE, определенное в Unit1.h).
    StructMsg – имя структуры, которая будет содержать параметры сообщения после его раскрытия VCL. Эта структура передается обработчику сообщения.
    HandlerMsg – фактическое имя функции, которая обрабатывает сообщение.
Функция обработки сообщения (обработчик сообщения) – это функция, которая будет вызываться каждый раз, когда ваше приложение получает обрабатываемое сообщение. Эта функция имеет один параметр – структуру, раскрывающую обрабатываемое сообщение. Для нашего примера функция обработки сообщения выглядит следующим образом:
void __fastcall TForm2::OnMyMessage(TMessage& Msg)
{
    Form2->Show();
}.
    Добавьте ее в Unit2.cpp. Выполните команду “Build All Projects”, закройте Borland C++ Builder и запустите Project2.exe на выполнение.
 

Скачать

MD5    CB286EE627D31183F0F70ADC18F297C4

 

 

 

This site is a member of WebRing.
To browse visit Here.

 

Отправить сообщение для: Web-мастера с вопросами и замечаниями об этом веб-узле.
© 2010 Serg Kappa CIS Inc. Ltd. ©1990 - 2010
Дата изменения: 21.10.2010

Одноклассники.ru - Поиск одноклассников, однокурсников, бывших выпускников и старых друзей

 

Сайт управляется системой uCoz