Udostępnij przez


Różne kontrole

Opcja Różne kontrole w weryfikatorze sterowników monitoruje sterownik pod kątem typowych błędów, które powodują awarię sterownika lub systemu, takich jak zwalnianie pamięci, która nadal zawiera aktywne obiekty jądra.

W szczególności opcja Różne kontrole wyszukuje następujące nieprawidłowe zachowanie sterownika:

  • Aktywne elementy robocze w zwolnionej pamięci. Sterownik wywołuje funkcję ExFreePool , aby zwolnić blok puli zawierający elementy robocze, które zostały w kolejce przy użyciu elementu IoQueueWorkItem.

  • Zasoby aktywne w zwolnionej pamięci. Sterownik wywołuje funkcję ExFreePool, aby zwolnić blok puli zawierający aktywne struktury ERESOURCE. Sterownik powinien wywołać polecenie ExDeleteResource , aby usunąć obiekty ERESOURCE przed wywołaniem funkcji ExFreePool.

  • Aktywne listy odnośników w zwolnionej pamięci. Sterownik wywołuje funkcję ExFreePool w celu zwolnienia bloku puli, który nadal zawiera aktywne listy lookaside, takie jak NPAGED_LOOKASIDE_LIST lub PAGED_LOOKASIDE_LIST. Sterownik powinien wywołać metodę ExDeleteNPagedLookasideList lub ExDeletePagedLookasideList , aby usunąć listy lookaside przed wywołaniem funkcji ExFreePool.

  • Instrumentacja zarządzania Windows (WMI) i śledzenie zdarzeń w przypadku problemów z rejestracją systemu Windows (ETW). Takie problemy wykryte przez weryfikatora sterowników obejmują:

    • Sterownik, który próbuje się wyładować bez wyrejestrowania wywołania zwrotnego WMI.

    • Sterownik, który próbuje usunąć obiekt urządzenia, który nie został wyrejestrowany z WMI.

    • Sterownik, który próbuje rozładować bez wyrejestrowania dostawców trybu jądra ETW.

    • Sterownik, który próbuje wyrejestrować dostawcę, który jest już wyrejestrowany.

  • Błędy obsługi jądra. (Windows Vista i nowsze wersje) Włączenie opcji Różne kontrole umożliwi również śledzenie uchwytów dla procesu systemowego, aby ułatwić badanie przecieków uchwytów jądra i Błąd kontrolny 0x93: INVALID_KERNEL_HANDLE. Po włączeniu śledzenia uchwytów, jądro będzie zbierać ślady stosu dla najnowszych operacji otwierania i zamykania uchwytów. Ślady stosu można wyświetlić w debuggerze jądra przy użyciu rozszerzenia debuggera !htrace. Aby uzyskać więcej informacji na temat programu !htrace, zobacz dokumentację Narzędzia debugowania dla systemu Windows.

  • Obsługa trybu użytkownika z dostępem w trybie jądra Począwszy od systemu Windows 7, po wybraniu opcji Różne kontrole, weryfikator sterownika sprawdza również wywołania ObReferenceObjectByHandle. Nie można przekazać dojścia trybu użytkownika do trybu jądra. Jeśli taka operacja wystąpi, weryfikator sterowników wystawia błąd krytyczny 0xC4, z wartością parametru 1 równą 0xF6.

  • Tryb użytkownika: oczekiwanie na obiekty synchronizacji alokowane na stosie jądra

    Począwszy od systemu Windows 7, Weryfikator sterowników może wykrywać dodatkowe sposoby niepoprawnego używania mechanizmów synchronizacji wielowątkowych zapewnianych przez system operacyjny.

    Przydzielanie obiektów synchronizacji, takich jak struktury KEVENT, jako zmienne lokalne na stosie jądra jest powszechną praktyką. Gdy proces jest załadowany do pamięci, stosy jądra jego wątków nigdy nie są przycinane z zestawu roboczego ani stronicowane na dysk. Przydzielanie obiektów synchronizacji w takiej niewymienialnej pamięci jest poprawne.

    Jednak gdy sterowniki wywołają interfejsy API, takie jak KeWaitForSingleObject lub KeWaitForMultipleObjects , będą czekać na obiekt przydzielony na stosie, muszą określić wartość KernelMode dla parametru WaitMode interfejsu API. Gdy wszystkie wątki procesu oczekują w trybie UserMode, proces ten kwalifikuje się do przeniesienia na dysk. W związku z tym, jeśli sterownik określił UserMode jako wartość parametru WaitMode, system operacyjny może zamienić bieżący proces na inny tak długo, jak każdy wątek w tym samym procesie czeka w trybie UserMode. Przełączanie całego procesu na dysk obejmuje wytronicowanie stosów jądra. Oczekiwanie na obiekt synchronizacji, który został zamieniony przez system operacyjny, jest niepoprawne. W pewnym momencie wątek musi pojawić się i zasygnalizować obiekt synchronizacji. Sygnalizowanie obiektu synchronizacji obejmuje jądro systemu Windows manipulowanie obiektem przy IRQL równym DISPATCH_LEVEL lub wyższym. Dotknięcie stronicowanej lub zamienionej pamięci na DISPATCH_LEVEL lub powyżej powoduje awarię systemu.

    Począwszy od systemu Windows 7, po wybraniu opcji Różne testy, weryfikator sterowników sprawdza, czy obiekty synchronizacji, z których zweryfikowany sterownik korzysta do oczekiwania w trybie użytkownika, nie są przydzielane na stosie jądra bieżącego wątku. Gdy weryfikator sterownika wykryje takie nieprawidłowe oczekiwanie, wystawia sprawdzenie błędu 0xC4: DRIVER_VERIFIER_DETECTED_VIOLATION z wartością parametru 1 równą 0x123.

  • Nieprawidłowe odwołania do uchwytów jądra

    Każdy proces systemu Windows ma tabelę obsługi. Tabelę uchwytów można wyświetlić jako tablicę wpisów uchwytów. Każda prawidłowa wartość uchwytu odwołuje się do prawidłowego wpisu w tej tablicy.

    Uchwyt jądra jako uchwyt, który jest prawidłowy dla tabeli uchwytów procesu systemowego. Uchwyt użytkownika jest uchwytem, który jest ważny dla dowolnego procesu z wyjątkiem procesu systemowego.

    W systemie Windows 7 weryfikator sterowników wykrywa próby odwołania do wartości obsługi jądra, które są niepoprawne. Te wady sterowników są zgłaszane jako Bug Check 0x93: INVALID_KERNEL_HANDLE, jeśli opcja Różnorodne sprawdzenia sterownika jest włączona. Zazwyczaj tego rodzaju nieprawidłowe odwołanie do uchwytu oznacza, że sterownik już zamknął ten uchwyt, ale dalej próbuje z niego korzystać. Tego typu wada może spowodować nieprzewidywalne problemy dla systemu, ponieważ wartość uchwytu, do którego się odwołuje, mogła zostać już użyta przez inny niepowiązany sterownik.

    Jeśli sterownik jądra niedawno zamknął dojście jądra, a następnie odwołuje się do zamkniętego dojścia, Driver Verifier wymusza sprawdzenie usterek zgodnie z wcześniejszym opisem. W tym przypadku dane wyjściowe rozszerzenia debugera !htrace udostępniają ślad stosu dla ścieżki kodu, która zamknęła ten uchwyt. Użyj adresu procesu systemowego jako parametru !htrace. Aby znaleźć adres procesu systemowego, użyj polecenia !process 4 0 .

    Począwszy od systemu Windows 7, Verifier sterowników dodaje sprawdzanie dla funkcji ObReferenceObjectByHandle. Obecnie nie można przekazać dojścia do obszaru użytkownika z dostępem JądraMode. Jeśli taka kombinacja zostanie wykryta, weryfikator sterowników zgłasza błąd z kontrolnym kodem 0xC4: DRIVER_VERIFIER_DETECTED_VIOLATION, z wartością parametru 1 wynoszącą 0xF6.

Aktywowanie tej opcji

Możesz aktywować opcję Różne kontrole dla co najmniej jednego sterownika przy użyciu Menedżera weryfikatora sterowników lub wiersza polecenia Verifier.exe. Aby uzyskać szczegółowe informacje, zobacz Wybieranie opcji weryfikatora sterowników.

  • W wierszu polecenia

    Na wierszu polecenia opcja Różne kontrole jest reprezentowana przez bit 11 (0x800). Aby aktywować różne kontrole, użyj wartości flagi 0x800 lub dodaj 0x800 do wartości flagi. Przykład:

    verifier /flags 0x800 /driver MyDriver.sys
    

    Opcja będzie aktywna po następnym rozruchu.

    W systemie Windows Vista i nowszych wersjach systemu Windows można również aktywować i dezaktywować różne kontrole bez ponownego uruchamiania komputera, dodając /volatile parametr do polecenia . Przykład:

    verifier /volatile /flags 0x800 /adddriver MyDriver.sys
    

    To ustawienie jest skuteczne natychmiast, ale zostanie utracone po zamknięciu lub ponownym uruchomieniu komputera. Aby uzyskać szczegółowe informacje, zobacz Używanie zmiennych ustawień.

    Opcja Różne kontrole jest również uwzględniona w ustawieniach standardowych. Przykład:

    verifier  /standard /driver MyDriver.sys
    
  • Korzystanie z Menedżera weryfikatora sterowników

    1. Uruchom Menedżera weryfikatora sterowników. Wpisz Weryfikator w oknie wiersza polecenia.

    2. Wybierz pozycję Utwórz ustawienia niestandardowe (dla deweloperów kodu), a następnie kliknij przycisk Dalej.

    3. Wybierz poszczególne ustawienia z pełnej listy.

    4. Wybierz pozycję Różne kontrole.

    Funkcja Różne kontrole jest również uwzględniona w ustawieniach standardowych. Aby użyć tej funkcji, w Menedżerze weryfikatora sterowników kliknij pozycję Utwórz ustawienia standardowe.

Wyświetlanie wyników

Aby wyświetlić wyniki opcji Różne kontrole, użyj rozszerzenia !weryfikatora w debugerze jądra. (Aby uzyskać informacje o !weryfikatorze, zobacz dokumentację narzędzia debugowania dla systemu Windows ).

W poniższym przykładzie opcja Miscellaneous Checks wykryła aktywną strukturę ERESOURCE w pamięci, którą sterownik próbował zwolnić, co spowodowało sprawdzenie błędu 0xC4: DRIVER_VERIFIER_DETECTED_VIOLATION. Kod błędu 0xC4 zawiera adres ERESOURCE i dotyczy zaatakowanej pamięci.

1: kd> !verifier 1

Verify Level 800 ... enabled options are:
 Miscellaneous checks enabled

Summary of All Verifier Statistics

RaiseIrqls                             0x0
AcquireSpinLocks                       0x0
Synch Executions                       0x0
Trims                                  0x0

Pool Allocations Attempted             0x1
Pool Allocations Succeeded             0x1
Pool Allocations Succeeded SpecialPool 0x0
Pool Allocations With NO TAG           0x0
Pool Allocations Failed                0x0
Resource Allocations Failed Deliberately   0x0

Current paged pool allocations         0x0 for 00000000 bytes
Peak paged pool allocations            0x0 for 00000000 bytes
Current nonpaged pool allocations      0x0 for 00000000 bytes
Peak nonpaged pool allocations         0x0 for 00000000 bytes

Driver Verification List

Entry     State           NonPagedPool   PagedPool   Module

8459ca50 Loaded           00000000       00000000    buggy.sys



*** Fatal System Error: 0x000000c4
 (0x000000D2,0x9655D4A8,0x9655D468,0x000000B0)


        0xD2 : Freeing pool allocation that contains active ERESOURCE.
               2 -  ERESOURCE address.
               3 -  Pool allocation start address.
               4 -  Pool allocation size.

Aby zbadać alokację puli, użyj rozszerzenia debuggera !pool z adresem początkowym alokacji puli, 9655D468. (Flaga 2 wyświetla tylko informacje nagłówka dla puli zawierającej określony adres. Informacje nagłówkowe dla innych pul są pomijane).

1: kd> !pool 9655d468  2
Pool page 9655d468 region is Paged pool
*9655d468 size:   b0 previous size:    8  (Allocated) *Bug_

Aby znaleźć informacje o ERESOURCE, użyj rozszerzenia debugera !locks (!kdext*.locks) z adresem struktury.

1: kd> !locks 0x9655D4A8     <<<<<- ERESOURCE @0x9655D4A8 lives inside the pool block being freed

Resource @ 0x9655d4a8    Available
1 total locks

Możesz również użyć polecenia debugera kb , aby wyświetlić ślad stosu wywołań, które doprowadziły do błędu. W poniższym przykładzie pokazano stos, w tym wywołanie funkcji ExFreePoolWithTag przechwycone przez Driver Verifier (weryfikator sterowników).

1: kd> kb
ChildEBP RetAddr  Args to Child
92f6374c 82c2c95a 00000003 92f68cdc 00000000 nt!RtlpBreakWithStatusInstruction
92f6379c 82c2d345 00000003 9655d468 000000c4 nt!KiBugCheckDebugBreak+0x1c
92f63b48 82c2c804 000000c4 000000d2 9655d4a8 nt!KeBugCheck2+0x5a9
92f63b6c 82e73bae 000000c4 000000d2 9655d4a8 nt!KeBugCheckEx+0x1e
92f63b88 82e78c32 9655d4a8 9655d468 000000b0 nt!VerifierBugCheckIfAppropriate+0x3c
92f63ba4 82ca7dcb 9655d468 000000b0 00000000 nt!VfCheckForResource+0x52
92f63bc8 82e7fb2d 000000b0 00000190 9655d470 nt!ExpCheckForResource+0x21
92f63be4 82e6dc6c 9655d470 92f63c18 89b6c58c nt!ExFreePoolSanityChecks+0x1fb
92f63bf0 89b6c58c 9655d470 00000000 89b74194 nt!VerifierExFreePoolWithTag+0x28
92f63c00 89b6c0f6 846550c8 846550c8 846e2200 buggy!MmTestProbeLockForEverStress+0x2e
92f63c18 82e6c5f1 846e2200 846550c8 85362e30 buggy!TdDeviceControl+0xc4
92f63c38 82c1fd81 82d4d148 846550c8 846e2200 nt!IovCallDriver+0x251
92f63c4c 82d4d148 85362e30 846550c8 84655138 nt!IofCallDriver+0x1b
92f63c6c 82d4df9e 846e2200 85362e30 00000000 nt!IopSynchronousServiceTail+0x1e6
92f63d00 82d527be 00000001 846550c8 00000000 nt!IopXxxControlFile+0x684
92f63d34 82cb9efc 0000004c 00000000 00000000 nt!NtDeviceIoControlFile+0x2a
92f63d34 6a22b204 0000004c 00000000 00000000 nt!KiFastCallEntry+0x12c