Heap Verifier Stops
Attempt To Destroy Process Heap
It is incorrect to try to destroy the default process heap (the one returned by GetProcessHeap() interface).
Corrupted End Stamp of Block Header
This stop occurs when the end stamp of the header of the block is corrupted. This happens during buffer underruns. 可以参考一下下面的The Structure of a Page Heap Block.
Corrupted Infix Pattern For Freed Block
Freed blocks are sometimes marked non-accessible and a program touching them will generate an access violation. In other cases (light page heap), the block is marked with a magic pattern and will be kept for a while. Eventually the blocks get freed in a First In First out (FIFO) fashion. At this moment, the infix pattern is checked and if it has been modified you will get this stop. This error is hit when there is a corrupted infix pattern for freed block. 参考下面的The Structure of a Page Heap Block,如果该page被分配了,并且用户没有要求清零,它的值是E0;如果这个page是free的则值为F0
Corrupted Prefix Pattern
This error occurs when the prefix pattern is corrupted. This happens during buffer underruns.
Corrupted Start Stamp Of Block Header
This error is hit when the start stamp of the header of the block is corrupted. This occurs during buffer underruns.
Corrupted Suffix pattern
This happens when Application Verifier places non-accessible pages at the end of the allocation and a buffer overrun causes an access violation. The heap block that the buffer overruns into has a special pattern associated to it, if this pattern is changed when the block gets freed you will get this stop.
Exception Raised While Verifying Block Header
This situation happens if a type of corruption for the block cannot be determined. For instance, you will get this error if during a heap free operation you pass an address that points to a non-accessible memory area. This also happens while validating the light pageheap block header.
Excessive Size For The Current Operation
This stop will be generated if in a HeapAlloc() or HeapReAlloc() operation the size of the block is above any reasonable value. Typically this value is 0x80000000 on 32-bit platforms and a larger value on 64-bit platforms. This stop also occurs when the allocation size is computed incorrectly, resulting in a negative number.
Heap Handle With Incorrect Signature
The heap structures are tagged with a magic value. If the heap handle used in the call to a heap interface does not have this pattern, then this stop will be generated. This stop can occur if the internal heap structure got corrupted due to a random corruption or when an incorrect value is used as a heap handle.
Heap Operation Performed On An Invalid Heap Handle
The heap structures are tagged with a specific value. If the heap handle used in the call to a heap interface does not have this specific value, then this stop will be generated. This bug can happen if the internal heap structure got corrupted or an invalid heap handle was used.
Memory Access Operation in the context of a freed block: reuse-after-delete or double-delete
This is an error found in the heap blocks when they are freed several times. This is detected when the second free of the block does not have the proper prefix header and cannot be found among the allocated blocks. This stop can be a variant of the reallocation problem because when the application frees what it thinks is the address of the block, that block was already freed as part of the reallocation.
Memory Access Operation In The Context Of An Allocated Block: Heap Overrun or Heap Underrun
This error occurs if there is a buffer overrun or underrun in an allocated heap block. There are two causes for this error:
-
If you have set the Overrun Protection setting to overrun, this break is due to a buffer overrun.
-
If you have set the Overrun Protection setting to underrun, this break is due to a buffer underrun.
This exception occurs when the heap verifier places a non-accessible page at the end or beginning of a heap allocation and a buffer overrun or underrun touches the page.
Multithreaded Access In A HEAP_NO_SERIALIZE Heap
A heap created with HEAP_NO_SERIALIZE flag is not supposed to be accessed simultaneously from two threads. The typical way this situation happens in a program is by linking with a single-threaded version of the C runtime. For instance, Visual C++ can link statically to such a library when proper flags are used.
Process Heap List Count Is Wrong
This stop can happen if while calling the GetProcessHeaps() interface the page heap manager detects some internal inconsistencies. This can be caused by some random corruption in the process address space.
The Heap Block Object Of The Current Operation Is Corrupted
This stop occurs when one or more validations of the header for a light page heap block fails. It's also a fallback case when other stops are continued.
Unexpected Exception Raised In Heap Code Path
This stop is generated if while executing the heap manager code an access violation. The exception record information can be used to find the exact context of the exception. This stop can also happen if there is a random corruption in the internal heap structures or in double free situations, if the block among full page heap cannot be found and it’s probed as a light page heap block.
======The Structure of a Page Heap Block=======
When full page heap is enabled, guard pages are used and buffer overrun/underrun are caught instantly as the program will access violate at the point of overrun/underrun. These failures are easy to debug because the current stack trace points directly to the broken code. If normal page heap is used or the corruption happens in the small fill pattern at end of buffer for alignment reasons the corruption will be detected only when the block is freed. In these cases more involved detective techniques are required. To make life easier in such cases the page heap manager places a header before all allocations (full and normal). This header contains a few valuable bits of information (owning heap, user requested size and stack trace for the allocation in some cases). The structure of the full and normal page heap blocks is described below.
Normal page heap block structure
Full page heap block structure
The information block has the following structure:
DPH_BLOCK_INFORMATION
ULONG StartStamp;
PVOID Heap;
SIZE_T RequestedSize;
SIZE_T ActualSize;
LIST_ENTRY FreeQueue;
PVOID StackTrace;
ULONG EndStamp;
The Heap field stores the owning heap. The user requested size for the block is in RequestedSize. The stack trace address is stored in the stack trace field.
The StackTrace field will not always contain a non-null value for various reasons. First of all stack trace detection is supported only on x86 platforms and second, even on x86 machines the stack trace detection algorithms are not completely reliable. If the block is an allocated block the stack trace is for the allocation moment. If the block was freed, the stack trace is for the free moment.