Pointers
An array of VMKRHY structures are embedded in VMKRH at krh_akrhy.
An array of VMKRHS structures are embedded in VMKRH at krh_akrhs.
ksh_hdrEntry in VMKSH points to the first chained VMKSHD.
kshd_pbNext in VMKSHD points to subsequent VMKSHD structures. VMKRHF structures from the dummy VMKRHF embedded in VMKRK at krh_krhfDummy
VMKSHD structure are allocated from the Kernel Resident Heap.
VMKSH prefixes a swappable heap.
Allocated blocks (VMKSHB) are sparsely allocated from the heap.
VMKSHB prefixes the data portion of an allocated block.
VMKSH and VMKSHB:
vmkshrw (0xffef).
VMKSH Kernel Swappable Heap Header (RETAIL kernel)
┌────────────────┬──────┬──────┬────┬────────────────────────────────────────┐│Field Name │Offset│Length│Type│Description │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_hdrEntry │+0 │12 │S │Dummy head descriptor of free chain │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ │+0 │4 │D │ │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ │+4 │4 │D │pointer to next descriptor │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ │+8 │4 │D │ │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pHint │+c │4 │D │Descriptor pointer to last block touched│ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pHPrev │+10 │4 │D │Descriptor pointer to PrevBlk of last │ │ │ │ │ │touched │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_HintSize │+14 │4 │D │Size of last block touched │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbEndRes │+18 │4 │D │Upper bound of reserved virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbEndCom │+1c │4 │D │Upper bound of committed virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_fl │+20 │4 │D │Swappable heap allocation flags │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_hob │+24 │2 │W │Heap object handle │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbStart │+26 │4 │D │Lower bound of reserved virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_ksem │+2a │C │S │KSEM for swappable heap │ └────────────────┴──────┴──────┴────┴────────────────────────────────────────┘
VMKSH Kernel Swappable Heap Header (ALLSTRICT kernel)
┌────────────────┬──────┬──────┬────┬────────────────────────────────────────┐ │Field Name │Offset│Length│Type│Description │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_hdrEntry │+0 │4 │D │Head of descriptor chain │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pHint │+4 │4 │D │Descriptor pointer to last block touched│ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pHPrev │+8 │4 │D │Descriptor pointer to PrevBlk of last │ │ │ │ │ │touched │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_HintSize │+C │4 │D │Size of last block touched │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbEndRes │+10 │4 │D │Upper bound of reserved virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbEndCom │+14 │4 │D │Upper bound of committed virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_fl │+18 │4 │D │Swappable heap allocation flags │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_hob │+1C │2 │W │Heap object handle │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_pbStart │+1E │4 │D │Lower bound of reserved virt mem │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_ksem │+22 │10 │S │KSEM for swappable heap │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_ckshds │+32 │4 │D │Count of heap modifications │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_cFrees │+36 │4 │D │Count of heap modifications │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ksh_cAllocs │+3a │4 │D │Count of heap modifications │ └────────────────┴──────┴──────┴────┴────────────────────────────────────────┘
VMKSHD Kernel Swappable Heap Descriptor Record for Free Blocks.
┌────────────────┬──────┬──────┬────┬────────────────────────────────────────┐ │Field Name │Offset│Length│Type│Description │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshb_size │+0 │4 │D │Size of block in dwords │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshd_pNext │+4 │4 │D │Next free block │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshd_pb │+8 │4 │D │Address of block header │ └────────────────┴──────┴──────┴────┴────────────────────────────────────────┘
VMKSHB Kernel Swappable Heap Block Header for Allocated blocks.
┌────────────────┬──────┬──────┬────┬────────────────────────────────────────┐ │Field Name │Offset│Length│Type│Description │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │ │+0 │1 │D │Signature 0x52 │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshb_size │ │3 │ │size of block │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshb_hobowner │+4 │2 │W │Owner │ ├────────────────┼──────┼──────┼────┼────────────────────────────────────────┤ │kshb_sel │+6 │2 │W │Selector │ └────────────────┴──────┴──────┴────┴────────────────────────────────────────┘
ksh_fl flag definitions.
┌──────────────┬──────────┬─────────────────────────────────┐ │Name │Bit Mask │Description │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_CONTIG │0x00000001│contiguous physical memory │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_NOINCR │0x00000001│don't increment physical addrs │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_W │0x00000002│Writable - value from pte │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_U │0x00000004│user mode accessible - from pte │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_X │0x00000008│eXecutable │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_R │0x00000010│Readable │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_1M │0x00000020│must reside below 1 meg physical │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_GUARD │0x00000040│guard page - from pte │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_16M │0x00000040│must reside below 16 meg physical│ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_ZEROFILL │0x00000080│zero initialize pages │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_SWAPONWRITE│0x00000100│value from vp │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_UVIRT │0x00000200│value from pte │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_RESIDENT │0x00000400│value from pte │ ├──────────────┼──────────┼─────────────────────────────────┤ │PG_DISCARDABLE│0x00000800│value from vp │ └──────────────┴──────────┴─────────────────────────────────┘