windows - AppVerifier rapporterer 'Ugyldigt håndtag - kode c0000008', når du lukker gyldigt håndtag

Indlæg af Hanne Mølgaard Plasc

Problem



Jeg har et simpelt testprogram, der undlader med undtagelse, når det kører under AppVerifier. Programmet duplicerer STD\_INPUT\_HANDLE og forsøger derefter at lukke det ved hjælp af CloseHandle(). Programmet virker fint uden AppVerifier tilbage TRUE for CloseHandle. Men hvis det kører under AppVerifier med Lock, Heaps og Handles, er det muligt at kaste en undtagelse. Detaljerne er nedenfor. Kan nogen kommentere, hvorfor det sker? Er det en AppVerifier fejl?


*/

// stdintst.cpp : Defines the entry point for the console application.
//


//
// This code fails if run under AppVerifier x64 4.0.0665
// Test is compiled under VS 2005
//


#include "stdafx.h"


#include <windows.h>
#include <stdio.h>
static int duplicate(HANDLE h)
{
HANDLE ph = GetCurrentProcess();
HANDLE tmph = INVALID\_HANDLE\_VALUE;


if (!DuplicateHandle(GetCurrentProcess(), h, GetCurrentProcess(), &tmph, 0, TRUE, DUPLICATE\_SAME\_ACCESS))
return 0;
else {
DWORD dw = CloseHandle(tmph);             // fails here with exception if run under AppVerifier
printf ("CloseHandle \%d \%x
", dw, GetLastError());
}


return 1;
}




int wmain(int argc, \_TCHAR* argv[])
{


HANDLE h = INVALID\_HANDLE\_VALUE;
h = GetStdHandle(STD\_INPUT\_HANDLE);
if (h == INVALID\_HANDLE\_VALUE)
exit(-1);


printf("STD\_INPUT\_HANDLE: \%d
", duplicate(h));


h = GetStdHandle(STD\_OUTPUT\_HANDLE);
if (h == INVALID\_HANDLE\_VALUE)
exit(-1);


printf("STD\_INPUT\_HANDLE: \%d
", duplicate(h));


h = GetStdHandle(STD\_ERROR\_HANDLE);
if (h == INVALID\_HANDLE\_VALUE)
exit(-1);


printf("STD\_INPUT\_HANDLE: \%d
", duplicate(h));


return 0;
}
Windbg:
\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_


// before CloseHandle()


0018fe2c dw = 0xcccccccc
0018fe54 h = 0x00000003
0018fe44 ph = 0xffffffff
0018fe38 tmph = 0x0000000f
0:000:x86> p  // CloseHandle()
(870.1644): Invalid handle - code c0000008 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
ntdll!KiRaiseUserExceptionDispatcher+0x3a:
00000000`77b012f7 8b8424c0000000  mov     eax,dword ptr [rsp+0C0h] ss:00000000`0008e2e0=c0000008
0:000> !analyze -v
ERROR: FindPlugIns 8007007b
*******************************************************************************
*                                                                             *
*                        Exception Analysis                                   *
*                                                                             *
*******************************************************************************


APPLICATION\_VERIFIER\_HANDLES\_INVALID\_HANDLE (300)
Invalid handle exception for current stack trace.
This stop is generated if the function on the top of the stack passed an
invalid handle to system routines. Usually a simple kb command will reveal
what is the value of the handle passed (must be one of the parameters -
usually the first one). If the value is null then this is clearly wrong.
If the value looks ok you need to use !htrace debugger extension to get a
history of operations pertaining to this handle value. In most cases it
must be that the handle value is used after being closed. 
Arguments:
Arg1: ffffffffc0000008, Exception code. 
Arg2: 0000000000000000, Exception record. Use .exr to display it. 
Arg3: 0000000000000000, Context record. Use .cxr to display it. 
Arg4: 0000000000000000, Not used. 


FAULTING\_IP: 
ntdll!KiRaiseUserExceptionDispatcher+3a
00000000`77b012f7 8b8424c0000000  mov     eax,dword ptr [rsp+0C0h]


EXCEPTION\_RECORD:  ffffffffffffffff -- (.exr 0xffffffffffffffff)
ExceptionAddress: 0000000077b012f7 (ntdll!KiRaiseUserExceptionDispatcher+0x000000000000003a)
   ExceptionCode: c0000008 (Invalid handle)
  ExceptionFlags: 00000000
NumberParameters: 0
Thread tried to close a handle that was invalid or illegal to close


FAULTING\_THREAD:  0000000000001644


DEFAULT\_BUCKET\_ID:  STATUS\_INVALID\_HANDLE


PROCESS\_NAME:  stdintst.exe


BAD\_HANDLE: 000000000000000e (!htrace 000000000000000e)


ERROR\_CODE: (NTSTATUS) 0xc0000008 - An invalid HANDLE was specified.


EXCEPTION\_CODE: (NTSTATUS) 0xc0000008 - An invalid HANDLE was specified.


MOD\_LIST: <ANALYSIS/>


NTGLOBALFLAG:  2000100


APPLICATION\_VERIFIER\_FLAGS:  80040007


PRIMARY\_PROBLEM\_CLASS:  STATUS\_INVALID\_HANDLE


BUGCHECK\_STR:  APPLICATION\_FAULT\_STATUS\_INVALID\_HANDLE


LAST\_CONTROL\_TRANSFER:  from 00000000001e2386 to 0000000077b012f7


STACK\_TEXT:  
00000000`0008e220 00000000`001e2386 : 00000000`0000000e 00000000`7efdb000 00000000`0008e318 00000000`0008e320 : ntdll!KiRaiseUserExceptionDispatcher+0x3a
00000000`0008e2f0 00000000`7531f2cd : 00000000`0018fd20 00000000`0018fd2c 00000000`7efdb000 00000000`0008fd20 : verifier!AVrfpNtClose+0xbe
00000000`0008e320 00000000`7531cf87 : 00000000`00000000 00000000`0018fc08 00000000`7efdb000 00000000`7efdd000 : wow64!whNtClose+0x11
00000000`0008e350 00000000`75262776 : 00000000`77ca01b4 00000000`75310023 00000000`00000246 00000000`0018fff0 : wow64!Wow64SystemServiceEx+0xd7
00000000`0008ec10 00000000`7531d07e : 00000000`0008fd20 00000000`75261920 00000000`00000000 00000000`0008ed40 : wow64cpu!TurboDispatchJumpAddressEnd+0x2d
00000000`0008ecd0 00000000`7531c549 : 00000000`00000000 00000000`00000000 00000000`75314ac8 00000000`7ffe0030 : wow64!RunCpuSimulation+0xa
00000000`0008ed20 00000000`77af4956 : 00000000`01d32f00 00000000`00000000 00000000`77be2670 00000000`77bb5978 : wow64!Wow64LdrpInitialize+0x429
00000000`0008f270 00000000`77af1a17 : 00000000`00000000 00000000`77af4061 00000000`0008f820 00000000`00000000 : ntdll!LdrpInitializeProcess+0x17e4
00000000`0008f760 00000000`77adc32e : 00000000`0008f820 00000000`00000000 00000000`7efdf000 00000000`00000000 : ntdll! ?? ::FNODOBFM::`string'+0x29220
00000000`0008f7d0 00000000`00000000 : 00000000`00000000 00000000`00000000 00000000`00000000 00000000`00000000 : ntdll!LdrInitializeThunk+0xe




FOLLOWUP\_IP: 
wow64!whNtClose+11
00000000`7531f2cd 90              nop


SYMBOL\_STACK\_INDEX:  2


SYMBOL\_NAME:  wow64!whNtClose+11


FOLLOWUP\_NAME:  MachineOwner


MODULE\_NAME: wow64


IMAGE\_NAME:  wow64.dll


DEBUG\_FLR\_IMAGE\_TIMESTAMP:  4e212272


STACK\_COMMAND:  ~0s ; kb


FAILURE\_BUCKET\_ID:  STATUS\_INVALID\_HANDLE\_c0000008\_wow64.dll!whNtClose


BUCKET\_ID:  X64\_APPLICATION\_FAULT\_STATUS\_INVALID\_HANDLE\_wow64!whNtClose+11


Followup: MachineOwner
---------


0:000> !htrace 000000000000000e
--------------------------------------
Handle = 0x000000000000000e - *** BAD REFERENCE ***
Thread ID = 0x0000000000001644, Process ID = 0x0000000000000870


0x0000000077b0140a: ntdll!NtClose+0x000000000000000a
0x00000000001e2386: verifier!AVrfpNtClose+0x00000000000000be
0x000000007531f2cd: wow64!whNtClose+0x0000000000000011
0x000000007531cf87: wow64!Wow64SystemServiceEx+0x00000000000000d7
0x0000000075262776: wow64cpu!TurboDispatchJumpAddressEnd+0x000000000000002d
0x000000007531d07e: wow64!RunCpuSimulation+0x000000000000000a
0x000000007531c549: wow64!Wow64LdrpInitialize+0x0000000000000429
0x0000000077af4956: ntdll!LdrpInitializeProcess+0x00000000000017e4
0x0000000077af1a17: ntdll! ?? ::FNODOBFM::`string'+0x0000000000029220
0x0000000077adc32e: ntdll!LdrInitializeThunk+0x000000000000000e
0x0000000077caf9d2: ntdll32!NtClose+0x0000000000000012
0x000000006f2f2f52: vfbasics!AVrfpNtClose+0x0000000000000030
0x00000000770ab9f2: KERNELBASE!CloseHandle+0x000000000000002d
0x000000006f2f3e86: vfbasics!AVrfpCloseHandle+0x0000000000000074
0x000000000041157a: stdintst!duplicate+0x000000000000008a


--------------------------------------
Parsed 0x3A stack traces.
Dumped 0x1 stack traces.








Output Without Appverifier:
-------------------------------


CloseHandle 1 0
STD\_INPUT\_HANDLE: 1
CloseHandle 1 0
STD\_INPUT\_HANDLE: 1
CloseHandle 1 0
STD\_INPUT\_HANDLE: 1

Bedste reference