본문 바로가기
VisualStudio.C++.C#/코딩팁,함수활용,단편

Event Object, CreateEvent.WaitForSingleObject

by i.got.it 2020. 4. 20.

개요

 

Windows에서 Event Object 는 스레드나 프로세스가 ‘신호(signaled)’ / ‘비신호(nonsignaled)’ 상태를 기다리고 제어할 수 있는 커널 동기화 객체 

 

 

CreateEvent 는 이벤트개체를 생성하는 함수이며, 이벤트 개체가 생성되면 함수 SetEvent, ResetEvent 로 이벤트 상태를 제어할 수 있다.

 

이벤트 상태를 점검하기 위하여 함수 WaitForSingleObject 이용가능하다.  이벤트 개체는 1개의 프로세스 내부뿐만 아니라, 다른 프로세스에서도 공유가능하다.

 

HANDLE hEvent_WaitQRead_LOBDelta = NULL;

//2번인자 : TRUE. signal 이후 non-signal로 하려면 ResetEvent 해줘야 함., FALSE : signal 이후 자동으로 non-signal로 됨.  3번인자 true : 초기 signaled 상태.
hEvent_WaitQRead = CreateEvent(NULL, TRUE, TRUE, _T("WaitQRead"));

SetEvent(hEvent_WaitQRead); //hEvent_WaitQRead 를 signal 상태로 함.
ResetEvent(hEvent_WaitQRead); // hEvent_WaitQRead 를 non-signal 상태로 함.

// 2번인자 . 대기 타임아웃 밀리초 단위. INFINITE 는 타임아웃비적용.
WaitForSingleObject(hEvent_WaitQRead, INFINITE); // hEvent_WaitQRead non-signal 이면 여기서 대기. signal이면 대기탈출하고 이후 코드 실행.


 

 

 

 

프로세스간 이벤트 공유 

Windows 내부에서 Event Object 는 커널 오브젝트로 생성되어 커널(운영체제)이 관리하는 시스템 자원.

핸들 자체는 프로세스마다 별도이지만, 같은 커널 오브젝트를 가리키는 핸들을 여러 프로세스가 가질 수 있는 구조. 
이것 때문에 다른 프로세스에서도 이벤트 공유 가능 

 

 

공유 방법 1. 이름기반 

이름으로 “같은 커널 오브젝트”를 참조해서 공유하는 방식.

HANDLE h = CreateEvent(NULL, TRUE, FALSE, _T("MySharedEvent"));

 

 

  • 이벤트에 "MySharedEvent" 같은 이름을 지정하면 같은 이름을 가진 이벤트는 시스템 전체에서 하나만 존재.
  • 다른 프로세스에서도 아래처럼 이름으로 열어 같은 객체를 사용할 수 있다.
HANDLE hOther = OpenEvent(EVENT_ALL_ACCESS, FALSE, _T("MySharedEvent"));

 

 

또는 같은 이름으로 CreateEvent를 다시 호출해도 이미 존재하는 객체를 열어준다. 이때 GetLastError()는 ERROR_ALREADY_EXISTS 를 반환. 

 

 

무결성 공유 이벤트 생성 방법 

2개 프로세스에서 모두 CreateEvent 호출하며 2개 프로세스 실행순서 무관하게 항상 공유 이벤트 활용 가능하다. 

 

CreateEvent + OpenEvent 방식보다 좋은 이유

방식 설명
A: CreateEvent / B: OpenEvent B가 먼저 실행되면 실패
둘 다 CreateEvent ✔ 실행 순서 무관
DuplicateHandle ✔ 하지만 연결 복잡
InheritHandle 부모-자식 한정

 

 

 

공유방법2. 핸들 상속. 

  • 부모 프로세스가 CreateProcess()로 자식 프로세스를 만들 때,
  • SECURITY_ATTRIBUTES 구조체에서 bInheritHandle = TRUE 로 설정하면
    이벤트 핸들을 자식에게 바로 넘겨줄 수 있다.  Microsoft Learn

이 방식은 같은 객체를 공유하지만 이름이 필요 없는 경우에 유용.

 

 

공유방법3. 핸들 복제 

한 프로세스에서 다른 프로세스의 핸들로 핸들 복제(Duplicate) 하여
서로 같은 이벤트 객체를 가리키게 한다.

 

DuplicateHandle(hSrcProc, hEvent, hTargetProc, &hNewHandle, …);

 

 

다른 것과 비교 


방식  레이턴시
Event (커널) 매우 빠름
Mutex 느림 (ownership 처리)
Critical Section 가장 빠름 (단, 동일 프로세스 한정)
PostMessage 느림 (메시지 큐)
Socket / Pipe 훨씬 느림

프로세스 간 동기화 중에서는 Event가 최상급

 

 

 

CreateEvent 이름 지정시 Global / Local 

Windows OS에서 CreateEvent 함수를 사용하여 이벤트 객체를 생성할 때, 이름 앞에 접두사(Prefix)를 붙여 이름 공간(Namespace)을 지정할 수 있다. 이는  프로세스 간 동기화 시 객체의 접근 범위를 결정하기 위해 사용.

1. Global 이름 공간 (Global\)
  • 설명: 모든 세션( 로그인 사용자 Session)에서 접근 가능한 전역 이름 공간에 객체를 생성.
  • 용도: 서로 다른 세션에서 실행 중인 프로세스 간에 이벤트를 공유할 때 사용. (예: 서비스 프로세스와 일반 사용자 응용 프로그램 간의 통신)
  • 특징:
    • 이름 형식: Global\EventName
    • 객체를 생성하려면 SeCreateGlobalPrivilege 권한이 필요할 수 있으며, 일반적으로 관리자 권한이 요구.
    • 클라이언트/서버 구조의 애플리케이션에서 서버가 서비스를 통해 실행될 때 주로 사용.
2. Local 이름 공간 (Local\)
  • 설명: 객체를 생성한 프로세스가 속한 특정 세션 내에서만 유효한 이름 공간.
  • 용도: 동일한 세션(동일한 사용자 로그인 세션) 내에서 실행되는 프로세스들끼리 이벤트를 공유할 때 사용.
  • 특징:
    • 이름 형식: Local\EventName
    • 접두사를 생략할 경우 기본값(Default)으로 Local\이 적용.
    • 각 세션마다 독립된 이름 공간을 가지므로, 서로 다른 세션에서 동일한 이름의 Local\ 이벤트를 생성해도 서로 간섭하지 않는다.
3. 주요 차이점 요약
 
접두사 Global\ Local\ (또는 생략)
접근 범위 시스템 전체 (모든 세션) 현재 사용자 세션 내
권한 관리자 권한 필요 (생성 시) 일반 사용자 권한으로 가능
주요 사례 서비스 ↔ 사용자 앱 통신 동일 사용자의 앱 간 통신

주의 사항: 터미널 서비스나 원격 데스크톱 환경에서는 세션이 분리되므로, 여러 사용자가 접속한 환경에서 프로세스 간 동기화가 필요하다면 Global\ 사용 .

 

 

 


첫 등록 : 2016.02.19

최종 수정 : 2026.01.08

단축 주소 : https://igotit.tistory.com/670


 

 

 

댓글



비트코인




            암호화폐/외환/나스닥/골드          
       
현물 |선물 인버스 |선물 USDT , bybit MT5               프랍 트레이딩. MT4,MT5