C++Builder Programming Forum
C++Builder  |  Delphi  |  FireMonkey  |  C/C++  |  Free Pascal  |  Firebird
볼랜드포럼 BorlandForum
 경고! 게시물 작성자의 사전 허락없는 메일주소 추출행위 절대 금지
C++빌더 포럼
Q & A
FAQ
팁&트릭
강좌/문서
자료실
컴포넌트/라이브러리
메신저 프로젝트
볼랜드포럼 홈
헤드라인 뉴스
IT 뉴스
공지사항
자유게시판
해피 브레이크
공동 프로젝트
구인/구직
회원 장터
건의사항
운영진 게시판
회원 메뉴
북마크
볼랜드포럼 광고 모집

C++빌더 Q&A
C++Builder Programming Q&A
[37185] Re:Re:메시지훅인데여 왜 처음엔 되는되 나중에는 안될까여???
하느리 [handebug] 1066 읽음    2004-09-09 18:24
MMF에 대한 설명이 부족한 것 같아 좀 더 첨부합니다.
아래는 사용 예입니다.
아래의 각각의 파일을 만드시고, 각 파일을 dll과 application에 첨부하시고 해당 함수를 사용하시면 됩니다.
여기서 Create_MMF_KBDLock ()함수는 dll과 application이 구동되는 시작점에서 호출하시고,
MMF영역에 자료를 써야할 경우에는, HookKBDLock 자료구조를 가지는 변수를 생성하시고, 원하는 값을 입력한 다음, Write_MMF_KBDLock ()함수를 호출하시면 되고, 역으로 읽고자 할 경우에는 HookKBDLock 자료구조를 가지는 변수를 생성하시고, Read_MMF_KBDLock ()함수를 호출하시면 해당 변수에 MMF메모리영역 내에 값이 생성된 변수에 복사되어 옵니다.

앞에서 설명하였던 부분중, 훅함수의 핸들을 h_lock_KBD 변수에 기록하여 dll과 application에서 서로 공유하면 됩니다.


『참조』읽고쓰고 하는 함수의 내부를 보시면 아시겠지만, MapViewOfFile () 함수에 의해 MMF로 지정된 해당 메모리를 access합니다.




// MMF.h 헤더파일 내에 선언된 struct 구조
typedef struct
{ // keyboard lock용 hook data type
    HHOOK           h_lock_KBD;
    int             nCode;
    int             wParam;
    int             lParam;

} HookKBDLock;

// MMF.cpp 에 정의된 함수
static  HANDLE          gMMF_KBDLock_File = NULL;
//---------------------------------------------------------------------------
// MMF 영역 생성
bool Create_MMF_KBDLock (void)
{
    gMMF_KBDLock_File = CreateFileMapping ((HANDLE) 0xFFFFFFFF, NULL, PAGE_READWRITE, 0,
                                           sizeof (HookKBDLock), "MMF_HOOK_KBDLock");
    if ( ! gMMF_KBDLock_File )
    {
        gMMF_KBDLock_File = CreateFileMapping ((HANDLE) 0xFFFFFFFF, NULL, PAGE_READWRITE, 0,
                                               sizeof (HookKBDLock), "MMF_HOOK_KBDLock");
    }
    return (bool) (gMMF_KBDLock_File);
}
//---------------------------------------------------
// MMF에 의해 공유되는 메모리 영역 읽기
bool Read_MMF_KBDLock (HookKBDLock *mmf_data)
{
    bool    r = false;
    LPVOID  p_data = NULL;
    if ( ! gMMF_KBDLock_File )  return false;
    try
    {
        p_data = MapViewOfFile (gMMF_KBDLock_File, FILE_MAP_WRITE, 0, 0, 0);
        if ( p_data )
        {
            memcpy (mmf_data, p_data, sizeof (HookKBDLock));
            r = true;
        }
    }
    __finally
    { UnmapViewOfFile (p_data); }

    return r;
}
//---------------------------------------------------
// MMF에 의해 공유되는 메모리 영역에 쓰기
bool Write_MMF_KBDLock (HookKBDLock *mmf_data)
{
    bool    r = false;
    LPVOID  p_data;

    if ( ! gMMF_KBDLock_File )  return false;
    try
    {
        p_data = MapViewOfFile (gMMF_KBDLock_File, FILE_MAP_WRITE, 0, 0, 0);
        if ( p_data )
        {
            memcpy (p_data, mmf_data, sizeof (HookKBDLock));
            r = true;
        }
    }
    __finally
    { UnmapViewOfFile (p_data); }

    return r;
}
//---------------------------------------------------
// MMF영역 닫기
void Close_MMF_KBDLock (void)
{
    CloseHandle (gMMF_KBDLock_File);
}


하느리 님이 쓰신 글 :
: 코드 내용으로 보아 시스템 전역에 훅을 걸고자 하는 것 같네요.
: 이런 경우, 생각하셔야 할 것이 dll과 이를 호출하는 application 간의 관계인데요.
: 우선 dll은 자신의 application만이 사용을 하는 것이 아니고, 훅을 걸므로 해서 현재 실행된
: 다른 application에서도 이 dll을 호출하여 사용하게 된다는 것입니다. 그러므로 해서 시스템 전역에
: 자신이 원하는 기능을 수행시킬 수 있게 되는 것이죠.
: 그렇다면, 정상적으로 처리하는 방법이 어떻게 되느냐 하면,
:
: 우선, SetWindowsHookEx () 이 함수는 키보드를 락하는 기능을 제어할 application에서 호출할 것이므로
: dll 내에 두지 말고 해당 application 내에서 사용하도록 하시고요.
: dll 내에는 KeyHookProc () 함수만 두시고 export를 시키십시오.
: 이렇게 할 경우,
: CallNextHookEx (hKeyHook, nCode,wParam,lParam);
: 에서 반드시 hKeyHook(훅함수의 핸들)이 application에서 훅을 설정할 때의 핸들과 동일한 핸들이어야 합니다.
: 그래서, dll과 application 간의 메모리 공유가 필요하게 됩니다.
: 이때 흔히 사용되는 방법이 Memory Mapped File I/O라는 방식이 있습니다.
: MMF (Memory Mapped File I/O)의 경우는,
: gMMF_KBDLock_File = CreateFileMapping ((HANDLE) 0xFFFFFFFF, NULL, PAGE_READWRITE, 0, sizeof (HookKBDLock), "MMF_HOOK_KBDLock");
: 와 같이 CreateFileMapping ()이라는 함수에 의해서 구현됩니다.
:
: 완전한 소스를 올려드리는 것보다 설명을 드리는 것이 나을 것 같아 설명만 하였습니다.
:
:
:
: 금영이 님이 쓰신 글 :
: : 메시지 훅을 이용하여 키보드키값을 버리는 예제를 만들어 봤습니다.
: : 메인에서 버튼을 누르면 키 입력값을 전부 버려 키가 않먹히게 했구여
: : 다시 버튼을 누르면 키값이 입력되게 했습니다.
: : 그런데 처음에는 되는데 해제를 하고 다시 잠그려 하면 되질 않네여
: : 왜그럴까여???? ㅠㅠ
: : 아무리봐두 모르겠습니다.
: : 조언좀 부탁드립니다.
: : 혹시 훅 해제할때 시간이 좀 걸리나여???
: : 제가 훅 해제하구 바루 또 훅 설정해서 그런것 같기도한데...
: :
: : main함수에서는여
: : 잠금버튼클릭시 InstallHook();
: : 풀기버튼클릭시UninstallHook();
: : 이렇게 했구여
: :
: : 헤더파일에는
: : extern "C" __declspec(dllimport) void InstallHook(HWND hWnd);
: : extern "C" __declspec(dllimport) void UninstallHook();
: :
: : dll파일에는
: : #include <windows.h>
: :
: : #pragma data_seg(".kbdata")
: : HINSTANCE hModule = NULL;
: : HHOOK hKeyHook = NULL;
: : #pragma data_seg()
: : #pragma comment (linker, "/SECTION:.kbdata,RWS")
: :
: : LRESULT CALLBACK KeyHookProc(int nCode, WPARAM wParam, LPARAM lParam)
: : {
: :     if (nCode >= 0)
: :     {
: :         return true;
: :     }
: :     return CallNextHookEx(hKeyHook, nCode,wParam,lParam);
: : }
: :
: : extern "C" __declspec(dllexport) void InstallHook()
: : {
: :     hKeyHook = SetWindowsHookEx(WH_KEYBOARD, KeyHookProc, hModule, NULL);
: : }
: :
: : extern "C" __declspec(dllexport) void UninstallHook()
: : {
: :     UnhookWindowsHookEx(hKeyHook);
: : }
: :
: : BOOL WINAPI DllEntryPoint(HINSTANCE hInst, DWORD fdwReason, LPVOID lpRes)// DllMain(HINSTANCE hInst, DWORD fdwReason, LPVOID lpRes)
: : {
: :     switch (fdwReason)
: :     {
: :     case DLL_PROCESS_ATTACH:
: :         hModule=hInst;
: :         break;
: :     case DLL_PROCESS_DETACH:
: :         break;
: :     }
: :     return TRUE;
: : }
: : 이런식으로 했습니다. 고수님들 도와주세여 ㅠㅠ

+ -

관련 글 리스트
37156 메시지훅인데여 왜 처음엔 되는되 나중에는 안될까여??? 금영이 950 2004/09/07
37183     Re:메시지훅인데여 왜 처음엔 되는되 나중에는 안될까여??? 하느리 999 2004/09/09
37185         Re:Re:메시지훅인데여 왜 처음엔 되는되 나중에는 안될까여??? 하느리 1066 2004/09/09
Google
Copyright © 1999-2015, borlandforum.com. All right reserved.