엑셀 & VBA/엑셀 VBA 코딩패턴

Logging 패턴: OutputDebugString, DebugView 활용

ProDA 2022. 2. 19.

이 글은 새로운 블로그로 옮겼습니다. 5초후 자동으로 이동합니다.

▶ 새로운 블로그 주소: https://prodskill.com/

▶ 새로운 글 주소: https://prodskill.com/excel-vba-coding-pattern-logging-outputdebugstring-debugview/

이 글에서는 엑셀 VBA에서 Windows API OutputDebugString과 DebugView 유틸리티를 활용한 효과적인 Logging 방법을 살펴본다.

 

목차


     

    1. 기본적인 Logging 패턴

    엑셀 VBA 강좌(9): 엑셀 VBA How-To

     

    엑셀 VBA 강좌(9): 엑셀 VBA How-To

    이번 글은 엑셀 VBA 코딩시 알아두면 좋은 How-To에 대해 살펴본다. 이전 글에서 이어지는 내용이다. 엑셀 VBA 강좌(8): 엑셀 VBA 언어 기본-자료형(Data type), 자료구조(Data structure) 엑셀 VBA 강좌(8): 엑셀

    prodtool.tistory.com

    위 글의 4.3. 직접 실행 창 도구 활용 방법 목차 에서 "3. 출력 메시지 확인"에 대한 내용을 다루었다.

    직접 실행 창 도구 활용 방법
    직접 실행 창 도구 활용 방법

     

    Debug.Print 로 출력되는 내용을 직접 실행창에서 확인할 수 있는 방법이다. 이 방법은 매우 간편하다는 장점이 있는 반면에, 다음과 같은 단점이 있다.

     

    • VBE(Visual Basic Editor)는 엑셀 프로세스가 멈춤상태에 있는 경우 출력되는 log 내용을 확인할 수 없다.
    • 위 활용 방법 중 "2. 실행시 변수값 확인"과 혼용할 경우 log와 변수값이 중간중간 섞여서 log 확인에 방해가 될 수 있다.
    • 200 line이 넘는 메시지는 지워진다. 즉, 마지막 200 line만 유지된다.

     

    Debug.Print 를 대체하면서 더 좋은 방법으로 Windows API인 OutputDebugString과 유틸리티인 DebugView를 사용하는 방법이 있다.

     

    2. OutputDebugString 사용 패턴

    2.1. VBA 코드

    아래 글에서 Windows API인 OutputDebugString을 사용하는 방법에 대해 소개했었다.

    1차원 Bin Packing 알고리즘을 활용한 작업 배분 최적화_4.별첨

     

    1차원 Bin Packing 알고리즘을 활용한 작업 배분 최적화_4.별첨

    이 글의 소스코드는 Bin Packing 도구의 처음 버전 기준으로 작성되어 있다. 기능이 개선된 최신버전이 있으므로 함께 참조하기 바란다. 2021.06.12 - [엑셀&VBA/Tools] - 1차원 Bin Packing 도구 최근 변경 사

    prodtool.tistory.com

     

    5.1.4. modUtil 모듈 소스 코드 에서 소개한 코드를 약간 변형하여 필요한 내용 전체를 다음과 같이 작성하였다.

    Option Explicit
    Public Const LOG_PREFIX As String = "[VBA] " 'DebugView에서 로그 메시지를 필터링하기 위한 Prefix 지정
    
    Private Declare PtrSafe Sub OutputDebugString Lib "kernel32" Alias "OutputDebugStringA" (ByVal lpOutputString As String)
    
    'OutputDebugString API를 이용한 Debug Message 출력
    'DebugView등을 이용하여 메시지 View 가능함
    Public Sub DoLog(aMsg As String)
        OutputDebugString LOG_PREFIX + aMsg
    End Sub
    
    'Log 예시 프로시져
    Public Sub TestLog()
        Dim lIdx As Long
        For lIdx = 1 To 1000
            DoLog "Log[" + CStr(lIdx) + "]"
        Next
    End Sub

     

    • 2행: DebugView에서 로그 메시지를 필터링하기 위한 Prefix를 지정한다. 필터링 방법은 아래에서 설명한다.
    • 4행: Windows API인 OutputDebugString을 import하여 함수로 선언한다.
    • 9행: LOG_PREFIX 와 로그 메시지를 합쳐서 4행에서 import한 함수에 parameter로 전달하여 실행한다. 이 과정을 DoLog 함수로 만든다.
    • 16행: 로그 메시지 출력이 필요한 곳에 DoLog 함수를 호출한다.

     

    여기까지 하면 VBA 코드에서 필요한 작업은 모두 끝났다. 다음으로 DebugView 유틸리티를 살펴보자.

     

    2.2. DebugView 유틸리티 소개와 활용

    2.2.1. DebugView 유틸리티 소개

    DebugView는 Sysinternals suite에 포함되어 있는 유틸리티 도구이다.

    DebugView - Windows Sysinternals | Microsoft Docs

     

    DebugView - Windows Sysinternals

    이 프로그램은 장치 드라이버 및 Win32 프로그램에서 만든 OutputDebugString에 의해 DbgPrint에 대 한 호출을 차단 합니다.

    docs.microsoft.com

     

    DebugView v4.90 소개
    DebugView v4.90 소개

     

    DebugView v 4.90

    Mark Russinovich
    게시일: 4 월 23 일, 2019
    DebugView(1.3 MB) 다운로드

    소개
    Debugview 는 로컬 시스템 또는 tcp/ip를 통해 연결할 수 있는 네트워크 상의 모든 컴퓨터에서 디버그 출력을 모니터링할 수 있는 응용 프로그램입니다. 커널 모드와 Win32 디버그 출력을 모두 표시할 수 있으므로 응용 프로그램 또는 장치 드라이버가 생성 하는 디버그 출력을 catch 하는 디버거가 필요 하지 않으며 비표준 디버그 출력 Api를 사용 하도록 응용 프로그램 또는 드라이버를 수정 하지 않아도 됩니다.

    DebugView 캡처
    Windows 2000에서 XP, Server 2003 및 Vista debugview 는 다음을 캡처합니다.
      - Win32 OutputDebugString
      - 커널 모드 DbgPrint
      - Windows XP 및 Server 2003에 구현 된 DbgPrint 의 모든 커널 모드 변형

     

    간단하게 요약하면 "DebugView는 Windows API인 OutputDebugString 호출시 전달되는 문자열을 캡처하여 화면에 보여주는 유틸리티 도구"이다.

     

    DebugView 예시 화면은 다음과 같다.

    DebugView 예시 화면
    DebugView 예시 화면

    * 출처: https://docs.microsoft.com/ko-kr/sysinternals/downloads/debugview#installation-and-use

     

    2.2.2. DebugView 유틸리티 활용

    DebugView를 다운로드하고 실행한 다음 Filter/Highlight 메뉴를 실행한다.

    DebugView Filter/Highlight 메뉴
    DebugView Filter/Highlight 메뉴

     

    위 메뉴를 실행하면 다음과 같은 화면이 표시된다.

    DebugView Filter/Highlight 화면
    DebugView Filter/Highlight 화면

     

    • Include: 출력할 메시지에 포함된 문자열 입력. wildcard 문자로 * 사용 (예: [VBA]*) 비어 있으면 모든 메시지 출력. 여러 문자열을 입력할 경우 semicolon(;)로 구분.
    • Exclude: 출력하지 않을 메시지에 포함된 문자열 입력. 여러 문자열을 입력할 경우 semicolon(;)로 구분.
    • Highlight: Filter 1 ~ 20을 선택하고 강조할 문자열과 색상 선택. 색상은 전경색, 배경색 지정 가능

     

    한 가지 주의할 것은, Include에 필터링할 문자열을 입력하지 않는 경우 여러 다른 프로세스에서 출력하는 메시지가 캡쳐되어 마구 섞이게 된다. 필터링할 문자열은 필수로 지정하는 것이 좋다.

     

    "2.1. VBA 코드" 목차에서 작성한 예시 VBA코드의 결과를 캡쳐하기 위하여, Include에 "[VBA]*"를 입력하고 OK 버튼을 누른다.

    VBA 코드를 실행하면 다음과 같이 DebugView에 캡처된 메시지를 확인할 수 있다.

    DebugView에 캡처된 메시지 예시
    DebugView에 캡처된 메시지 예시

     

    참고로, Highlight 기능을 이용하면 다음과 같이 출력할 수 있다.

    DebugView의 Highlight 기능 예시
    DebugView의 Highlight 기능 예시

    특정 문자열이 포함되어 있을 때 배경색, 전경색을 달리하면 로그의 현재 진행상태를 확인하기에 시각적으로 매우 좋다.


    여기까지 엑셀 VBA에서 Windows API OutputDebugString과 DebugView 유틸리티를 활용한 효과적인 Logging 방법을 살펴보았다.

    DebugView는 Highlight 기능, Remote Logging 기능 등 매력적인 기능들이 많이 있다. 이 기능들은 나중에 별도의 글로 다루겠다.

     


    DA# Macro 기능 시연 영상(YouTube) 포스팅에서 DebugView 유틸리티에서 메시지가 캡처되는 상황을 함께 녹화해 두었다.

    아래 영상에서 우측 상단이 DebugView 이다. 기능이 동작하는 과정의 로그를 기록하고 나중에 다시 살펴볼 수 있다.

    참고로, DA# Macro(1): DA#, DA# API, DA# Macro(매크로) 개요 에서 소개한 DA# Macro는 LOG_PREFIX를 "[DA#] "으로 사용하고 있다.

     

    댓글

    💲 추천 글