Project History/원격 제어 프로그램 만들기

[C# 원격 제어 프로그램 만들기 #03] Win API (user32.dll)을 이용한 윈도우 이벤트 구현 (DllImport / Win32 API / keybd_event 등)

JeongKyun 2022. 1. 9.
반응형

서론

이번 글에서는 Win32 api인 user32.dll을 이용하여 키보드, 마우스 이벤트를 전송할 때 사용하는 방법을 알아보겠다. 방법은 간단하다. 

 


 

Win API ? (Win32 API)

Win API의 명칭부터 정리하면 과거에는 Win32 API라는 이름으로 불렸지만 현재는 64비트의 시대이기때문에 통합해서 Windows API라고 부른다고 한다. 해당 API는 Windows 운영 체제에 대한 인터페이스를 말하며, OS와의 모든 상호 작용 (창 만들기, 파일 열기, 네트워크 액세스 등)은 제공된 함수 호출을 거쳐서 진행되는 API이다. 이것을 다시 쉽게 정리하면 MS에서 어플리케이션 개발자들에게 쉽게 가져다 쓰라고 제공해준 API라고 보면된다.

 

- MSDN indows API 사이트

https://docs.microsoft.com/en-us/windows/win32/apiindex/windows-api-list

 

Windows API index - Win32 apps

A list of the reference content for the Windows API.

docs.microsoft.com

 


그렇다면 C#에서 해당 Win API(User32.dll)를 어떻게 참조할까?

(구현 소스)

   [Flags]
    public enum KeyFlag
    {
        KE_DOWN = 0, KE__EXTENDEDKEY = 1, KE_UP = 2
    }

    [Flags]
    public enum MouseFlag
    {
        ME_MOVE = 1, ME_LEFTDOWN = 2, ME_LEFTUP = 4, ME_RIGHTDOWN = 8,
        ME_RIGHTUP = 0x10, ME_MIDDLEDOWN = 0x20, ME_MIDDLEUP = 0x40, ME_WHEEL = 0x800,
        ME_ABSOULUTE = 8000
    }

    public static class WrapNative
    {
        [DllImport("user32.dll")]
        static extern void keybd_event(byte vk, byte scan, int flags, int extra);

        [DllImport("user32.dll")]
        static extern void mouse_event(byte vk, int dx, int dy, int buttons, int extra);

        [DllImport("user32.dll")]
        static extern bool GetCursorPos(ref Point point);

        [DllImport("user32.dll")]
        static extern int SetCursorPos(int x, int y);

 

위 소스를 보면 DllImport("user32.dll")이 바로 이 Win api를 선언하는 방법이다. 여기서 사용된 DllImport는 상단에 using System.Runtime.InteropServices; 을 선언하면 사용할 수 있고 이 녀석의 역할은 다른 언어에서 사용되는 것들을 C#언어에서 사용할 수 있게해주는 속성을 가진 선언형 함수이다. 

 

위의 소스처럼 [DllImport("user32.dll")] 이렇게 선언을 해주면 MS에서 제공된 API 문서를 참고하여 사용할 이벤트들을 정의하여 사용할 수 있게된다.

 

나는 Key와 Mouse를 enum 형식으로 변수마다 Win api에서 지정된 10진수와 16진수로 이뤄진 값을 넣어놓고 사용을 했다. 

 


 

키보드 이벤트인 keybd_event를 알아보자

 

내가 사용한 이벤트 함수 중 keybd_event를 아래 소스로 한번 알아보자.

/*
msdn에서 제공한 keybd_event 설명
*/
void keybd_event(
  [in] BYTE      bVk, // 1~254사이의 값인 가상 키 코드 
  [in] BYTE      bScan, // 키에 대한 하드웨어 스캔 코드
  [in] DWORD     dwFlags, // 기능 작동을 제어하는 코드
  [in] ULONG_PTR dwExtraInfo // 키 입력과 관련된 추가 값
);


/*
구현한 원격 프로그램에서 해당 키보드 이벤트를 호출 하는 소스.

bvk : keycode는 시프트 연산을 통해 구한 비트
bScan : 사용 안하여 0 고정
dwFlags : Keyup or KeyDown 값(1 or 2) 전달
dwExtraInfo : 사용 안하여 0 고정

*/
keybd_event((byte)keycode, 0, (int)KeyFlag.KE_DOWN, 0);

위의 keybd_event에 선언되어있는 구조는 c++로 이루어진 형태이며, Win API는 C++로 이루어져있고 상황에 맞춰 C#에서 파라미터 값을 적절하게 사용하여 호출하면 된다.

 

다른 함수들의 파라미터 내용과 쓰임은 MSDN에서 제공해주고 있게 아래의 링크에서 찾아보면 좋을 것 같다.

https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-keybd_event

 

keybd_event function (winuser.h) - Win32 apps

Synthesizes a keystroke.

docs.microsoft.com

 

윈도우 후킹 알아보기 (바로가기)

윈도우 후킹이란?

댓글

💲 많이 본 글