사용자 모드 모니터
사용자 모드 모니터를 사용하면 테스트 실패를 조사하거나 기존 테스트에서 더 나은 확인을 사용하도록 설정하기 위해 테스트가 '테스트 중인 프로세스'의 실행에 대한 더 많은 컨텍스트를 얻을 수 있습니다. 현재 사용자 모드 모니터 구현은 후속 릴리스에서 더 많은 사용자 지정 및 구성을 제공하는 기본 구현을 제공합니다.
소개
UMM(사용자 모드 모니터)은 하위 수준 Windows API를 사용하여 지정된 프로세스에서 발생하는 모든 '디버거' 이벤트(스레드 시작 및 중지, 모듈 로드, 크래시 및 처리된 예외)에 대한 알림을 받습니다. 디버거 이벤트를 수신하면 UMM 코드는 주석 로깅, 오류 로깅(테스트 실패를 위해) 또는 테스트 중인 프로세스의 미니덤프를 수행하는 등의 여러 작업 중 하나를 수행할 수 있습니다.
사용자 모드 모니터 사용
지정된 테스트 사례에 UMM을 사용하도록 설정하려면 다음 두 가지 구성을 제공해야 합니다.
- 테스트는 'ProcessUnderTest' 메타데이터 값으로 표시되어야 합니다. 이렇게 하면 UMM에서 테스트 중인 프로세스를 식별할 수 있습니다.
- Te.exe 명령줄에는 UMM 기능을 켜려면 '/userModeMonitor'가 포함되어야 합니다.
UMM 코드를 사용할 때 다음 사항을 고려해야 합니다.
- 테스트 중인 프로세스라는 이름의 인스턴스가 여러 대 있는 경우 먼저 검색된 instance 사용됩니다.
- 테스트 자동화를 실행하는 사용자는 테스트 중인 프로세스에서 디버거 이벤트를 받을 수 있는 충분한 권한이 있어야 합니다.
- UMM 코드는 모든 설치 픽스처가 실행된 후 테스트 중인 프로세스에 '연결'하고 정리 픽스처가 실행되기 전에 '분리'됩니다. 이렇게 하면 테스트의 설치 픽스처가 테스트 중인 프로세스를 시작하고 테스트를 준비하는 데 필요한 초기화를 수행할 수 있습니다.
지원되는 사용자 모드 모니터 '작업'
사용자 모드 모니터에는 모니터링되는 프로세스에서 지정된 디버거 이벤트가 발생할 때 수행할 수 있는 '작업' 집합이 있습니다. 현재 구현에서 지정된 이벤트는 기본 작업만 호출합니다. 현재 구성 지원이 없습니다.
작업 | Description |
---|---|
LogComment | 이벤트의 컨텍스트 정보를 사용하여 로그에 주석을 추가합니다. |
LogError | 현재 테스트에 실패하는 로그에 오류를 기록합니다. |
미니 덤프 | 미니덤프를 작성하고 로그에 저장합니다. |
무시 | 아무 작업도 하지 않습니다. |
지원되는 사용자 모드 모니터 '이벤트'
사용자 모드 모니터는 위에 나열된 '작업' 중 하나를 적용할 수 있는 '이벤트'를 표시합니다. 다음 표에서는 이벤트가 수신될 때 수행되는 기본 작업과 함께 보고된 이벤트의 현재 목록을 보여 줍니다.
이벤트 | 기본 작업(두 번째 확률 기본 작업) |
---|---|
스레드 만들기 | 무시 |
스레드 종료 | 무시 |
프로세스 만들기 | 무시 |
종료 프로세스 | LogError |
모듈 로드 | LogComment |
모듈 언로드 | 무시 |
시스템 오류 | 무시 |
초기 중단점 | LogError |
초기 모듈 로드 | 무시 |
디버기 출력 | LogComment |
액세스 위반 | LogError(LogError) |
어설션 실패 | LogError(LogError) |
애플리케이션 중단 | LogError(LogError) |
중단 명령 예외 | LogError |
중단 명령 예외 계속 | 무시 |
C++ EH 예외 | LogError(LogError) |
CLR 예외 | LogError(LogError) |
CLR 알림 예외 | LogError(무시) |
Control-LogError 예외 | LogError |
Control-LogError 예외 계속 | 무시 |
Control-C 예외 | LogError |
Control-C 예외 계속 | 무시 |
데이터가 잘못 정렬됨 | LogError(LogError) |
디버거 명령 예외 | 무시 |
보호 페이지 위반 | LogError(LogError) |
잘못된 명령 | LogError(LogError) |
페이지 내 I/O 오류 | LogError(LogError) |
정수 0으로 나누기 | LogError(LogError) |
정수 오버플로 | LogError(LogError) |
잘못된 핸들 | LogError |
잘못된 핸들 계속 | LogError |
잘못된 잠금 시퀀스 | LogError(LogError) |
잘못된 시스템 호출 | LogError(LogError) |
포트 연결이 끊김 | LogError(LogError) |
서비스 중단 | LogError(LogError) |
단일 단계 예외 | LogError |
단일 단계 예외 계속 | 무시 |
스택 버퍼 오버플로 | LogError(LogError) |
Stack Overflow | LogError(LogError) |
검증 도구 중지 | LogError(LogError) |
Visual C++ 예외 | 무시(무시) |
절전 모드 해제 디버거 | LogError(LogError) |
WOW64 중단점 | LogError(무시) |
WOW64 단일 단계 예외 | LogError(무시) |
기타 예외 | LogError(LogError) |
예제
UMM 기능의 사용을 설명하기 위해 'MSPaint'를 자동화하는 테스트의 (약간 모순된) 예제를 살펴보겠습니다.
namespace UserModeMonitorExample
{
using System;
using System.Diagnostics;
using System.Threading;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using WEX.Logging.Interop;
using WEX.TestExecution;
[TestClass]
public class BasicExample
{
[TestInitialize]
public void TestInitialize()
{
Process[] runningPaintInstances = Process.GetProcessesByName("mspaint.exe");
Verify.IsTrue(runningPaintInstances.Length == 0, "There are no running instances of mspaint.exe");
this.mspaintUnderTest = Process.Start("mspaint.exe");
}
[TestCleanup]
public void TestCleanup()
{
// Close the 'mspaint under test' - if it's already gone, this will throw, but that's no big deal.
this.mspaintUnderTest.CloseMainWindow();
}
[TestMethod]
[TestProperty("ProcessUnderTest", "mspaint.exe")]
[TestProperty("Description", "Shows how a test can be failed if the UI is closed from underneath the test.")]
public void SimpleInteraction()
{
Log.Comment("If the 'user mode monitor' is enabled and mspaint.exe is closed,");
Log.Comment("then this test will be failed.");
Log.Comment("Sleeping for 5 seconds");
Thread.Sleep(TimeSpan.FromSeconds(5));
}
private Process mspaintUnderTest;
}
}
다음은 테스트 구조에 대한 빠른 분석입니다.
- 'SimpleInteraction' 테스트는 UI 기반 애플리케이션과 상호 작용하는 테스트를 나타냅니다. 이 경우 "MSPaint.exe"입니다. 이 테스트가 "mspaint.exe" 프로세스를 테스트하고 있음을 호출하기 위해 "ProcessUnderTest" 메타데이터가 적용되었습니다.
- 테스트에는 실행 중인 기존 인스턴스가 없는지 확인하고 테스트할 단일 instance 시작하는 설정 픽스처가 있습니다.
- 테스트에는 설치 설비에서 시작된 instance 닫는 정리 설비도 있습니다.
'테스트'는 매우 간단합니다. 가능한 결과를 살펴보겠습니다.
- 테스트는 문제 없이 실행됩니다. 이것은 가능한 최상의 결과입니다.
- UMM을 사용하지 않으면 사용자가 실행 중에 MSPaint instance 닫습니다. 이 경우 테스트는 통과하지만 'InvalidOperationException'으로 정리가 실패합니다.
- UMM을 사용하도록 설정하면 사용자가 실행 중에 MSPaint instance 닫습니다. 이 경우 UMM 코드는 프로세스가 닫혀 테스트에 실패했음을 보여 주는 오류를 기록합니다. 대/소문자(2)와 같이 정리가 실패합니다.
UMM을 사용하도록 설정하면 잘못된 동작이 즉시 보고되고 테스트 결과에 직접 영향을 줍니다. 오류가 가능한 한 빨리 보고되고 테스트 실패를 디버깅하거나 이해하는 데 도움이 되는 추가 컨텍스트가 제공되므로 이는 훨씬 더 나은 테스트 패턴입니다.