[FdF] MiniLibX about hooking

bolee·2022년 7월 3일
0

42seoul

목록 보기
15/27

hooking?

소프트 웨어 공학 용어로, 운영 체제나 응용 소프트웨어 등의 각종 컴퓨터 프로그램에서 소프트웨어 구성 요소간에 발생하는 함수 호출, 메세지, 이벤트 등을 중간에서 바꾸거나 가로채는 명령, 방법, 기술이나 행위를 말한다.

MiniLibx hooking

MiniLibX(이하 mlx)는 Input device(마우스, 키보드)의 입력을 감지하고 가져와 hooking하는 함수들이다.

mlx는 키보드, 마우스에 특화된 hooking 함수와 범용적인 hooking 함수, 그리고 루프에 연결된 hooking 함수 총 4가지 함수들을 가지고 있다.

mlx_mouse_hook()

int	mlx_mouse_hook(void *win_ptr, int (*f)(), void *param);

마우스 이벤트를 hooking하는 함수이다.
지정된 화면의 아무 곳이나 클릭할 때마다 트리거가 발동된다.

  • win_ptr: window instance pointer
  • (*f)()
    • 핸들러(handler) 함수를 가리키는 함수 포인터
    • 핸들러 함수는 다음과 같은 프로토타입을 가진다.
      • int (f)(int button, int x, int y, void param);
  • param: 각 이벤트에 제공할 parameter

return_value:

  • 없음 (리턴 안함)

mlx_key_hook()

int	mlx_key_hook(void *win_ptr, int (*f)(), void *param);

키보드 이벤트를 hooking하는 함수이다.
포커스된 창(focused window)에서 키를 누를 때마다 트리거가 발동된다.
포커스가 되지 않은 창(unfocused window)에서는 트리거가 발동되지 않는다.

  • win_ptr: window instance pointer
  • (*f)()
    • 핸들러(handler) 함수를 가리키는 함수 포인터
    • 핸들러 함수는 다음과 같은 프로토타입을 가진다.
      • int (f)(int keycode, void param);
  • param: 각 이벤트에 제공할 parameter

return_value:

  • 없음 (리턴 안함)

mlx_hook()

void	mlx_hook(mlx_win_list_t *win_ptr, int x_event, int x_mask, int (*f)(), void *param)

보다 범용적으로 사용할 수 있는 이벤트 hooking 함수이다.

  • win_ptr: window instance pointer
  • x_envet: mlx 에 등록된 X11 events 즉, 이벤트 번호이며 해당 번호에 해당하는 이벤트를 hooking 한다. 아래는 X11 events 예이다.
    • 02: KeyPress
    • 03: KeyRelease
    • 04: ButtonPress
    • 05: ButtonRelease
  • x_mask: 각 X11 events에는 해당하는 mask도 존재한다. 이를 통해 트리거가 발동할 때 하나의 키에만 등록하거나 모든 키에 등록하는 등 여러가지 방법으로 이벤트를 관리할 수 있다.
  • (*f)()
    • 핸들러(handler) 함수를 가리키는 함수 포인터
    • 핸들러 함수는 다음과 같은 프로토타입을 가진다.
      • int (f)(int button, int x, int y, void param);
  • param: 각 이벤트에 제공할 parameter

return_value:

  • 없음 (리턴 안함)

X11 Events

KeyEventKeyEventKeyEvent
02KeyPress14NoExpose26CirculateNotify
03KeyRelease15VisibilityNotify27CirculateRequest
04ButtonPress16CreateNotify28PropertyNotify
05ButtonRelease17DestroyNotify29SelectionClear
06MotionNotify18UnmapNotify30SelectionRequest
07EnterNotify19MapNotify31SelectionNotify
08LeaveNotify20MapRequest32ColormapNotify
09FocusIn21ReparentNotify33ClientMessage
10FocusOut22ConfigureNotify34MappingNotify
11KeymapNotify23ConfigureRequest35GenericEvent
12Expose24GravityNotify36LASTEvent
13GraphicsExpose25ResizeRequest

X11 masks

MaskDescriptionMaskDescription
0LNoEventMask(1L<<12)Button5MotionMask
(1L<<0)KeyPressMask(1L<<13)ButtonMotionMask
(1L<<1)KeyReleaseMask(1L<<14)KeymapStateMask
(1L<<2)ButtonPressMask(1L<<15)ExposureMask
(1L<<3)ButtonReleaseMask(1L<<16)VisibilityChangeMask
(1L<<4)EnterWindowMask(1L<<17)StructureNotifyMask
(1L<<5)LeaveWindowMask(1L<<18)ResizeRedirectMask
(1L<<6)PointerMotionMask(1L<<19)SubstructureNotifyMask
(1L<<7)PointerMotionHintMask(1L<<20)SubstructureRedirectMask
(1L<<8)Button1MotionMask(1L<<21)FocusChangeMask
(1L<<9)Button2MotionMask(1L<<22)PropertyChangeMask
(1L<<10)Button3MotionMask(1L<<23)ColormapChangeMask
(1L<<11)Button4MotionMask(1L<<24)OwnerGrabButtonMask

mlx_loop_hook()

int		mlx_loop_hook(void *mlx_ptr, int (*f)(), void *param);

루프(loop)에 연결된 이벤트 hooking 함수이다.

  • win_ptr: window instance pointer
  • (*f)()
    • 핸들러(handler) 함수를 가리키는 함수 포인터
    • 핸들러 함수는 다음과 같은 프로토타입을 가진다.
      • int (f)(void param);
  • param: 각 이벤트에 제공할 parameter

return_value:

  • 없음 (리턴 안함)

사용 예

key event hooking with mlx_key_hook()

아래 예는 아무 키나 입력하면 생성된 창이 닫히는 예제이다.

#include <mlx.h>

typedef struct s_var
{
	void	*mlx;
    void	*win;
}	t_vars;

// 이벤트 발생 시 call 될 함수
int close(int keycode, t_vars *vars)
{
	mlx_destroy_window(vars->mlx, vars->win);	// 창 닫기
    return 0;
}

int main()
{
	t_vars vars;
    
    vars.mlx = mlx_init();
    vars.win = mlx_new_window(vars.mlx, 1920, 1080, "Hello world!");
    mlx_key_hook(vars.win, close, &vars);	// 생성된 창에서 key 입력 이벤트 발생 시 close 함수를 실행
    mlx_loop(vars.mlx);
}

mouse event hooking with mlx_hook()

mlx_hook() 함수를 사용해 마우스 클릭 이벤트를 hooking해 마우스를 클릭하면 생성된 창이 닫히는 예제이다.

mlx_hook()을 사용하면 hooking하고 싶어하는 이벤트를 보다 자세하게 명시할 수 있다.

#include <mlx.h>

typedef struct s_vars
{
	void	*mlx;
    void	*win;
} t_vars;

int close(int keycode, t_vars *vars)
{
	mlx_destroy_window(vars->mlx, vars->win);	// 창 닫기
    return 0;
}

int main()
{
	t_vars var;
    
    vars.mlx. = mlx_init();
    vars.win = mlx_new_window(vars.mlx, 1920, 1080, "Hello world!");
    mlx_hook(vars.win, 4, 1L<<0, close, &vars); // 생성된 창에서 마우스 클릭 이벤트 발생 시 close 함수를 실행
    mlx_loop(vars.mlx);
}

참고자료
https://ko.wikipedia.org/wiki/%ED%9B%84%ED%82%B9
https://harm-smits.github.io/42docs/libs/minilibx/events.html
https://harm-smits.github.io/42docs/libs/minilibx/hooks.html
https://harm-smits.github.io/42docs/libs/minilibx/prototypes.html
https://velog.io/@sayi/42cursursmlx-%ED%8A%9C%ED%86%A0%EB%A6%AC%EC%96%BC-%EC%9E%85%EB%A0%A5-%EC%9D%B4%EB%B2%A4%ED%8A%B8-hooking

0개의 댓글