DragonFlyBSD Kernel Audit
DF-0821 / panic.txt
← back to finding ↓ download raw
=== DF-0821 panic signature (default GENERIC, INVARIANTS ON) ===
Guest: DragonFly 6.5-DEVELOPMENT #0 (X86_64_GENERIC)
Trigger: mount crafted hammer2 image with poisoned freemap bmap->linear = 0x80001000,
         then write a file (inode create) -> freemap allocation -> hammer2_bmap_alloc.

panic: assertion "bmap->linear >= 0 && bmap->linear + size <= HAMMER2_SEGSIZE && (bmap->linear & (HAMMER2_ALLOC_MIN - 1)) == 0" failed in hammer2_bmap_alloc at /usr/src/sys/vfs/hammer2/hammer2_freemap.c:633
cpuid = 3
Trace beginning at frame 0xfffff80118fc3550
hammer2_bmap_alloc.constprop.2() at hammer2_bmap_alloc.constprop.2+0x3a5 0xffffffff809825b5 
hammer2_bmap_alloc.constprop.2() at hammer2_bmap_alloc.constprop.2+0x3a5 0xffffffff809825b5 
hammer2_freemap_alloc() at hammer2_freemap_alloc+0x45c 0xffffffff80982a3c 
hammer2_chain_modify() at hammer2_chain_modify+0x60c 0xffffffff809702ec 
hammer2_chain_create() at hammer2_chain_create+0xe24 0xffffffff80973a14 
hammer2_xop_inode_create_det() at hammer2_xop_inode_create_det+0x125 0xffffffff8097fe95 
Debugger("panic")

CPU3 stopping CPUs: 0x00000037
 stopped
Stopped at      Debugger+0x7c:  movb    $0,0xbdaf09(%rip)
db> 

=== Analysis ===
The KKASSERT at hammer2_freemap.c:631-633 fires because the poisoned bmap->linear
(0x80001000 = int32 -2147479552) is negative, failing the first sub-condition
(bmap->linear >= 0).  On GENERIC (INVARIANTS ON) this is the panic point — the OOB
array access at :727/:749/:785/:803 is never reached.  On an INVARIANTS-OFF kernel
the KKASSERT is compiled out and the negative linear drives:
  offset = bmap->linear           = -2147479552
  i = offset / (SEGSIZE / 8)      = -4095
  bmap->bitmapq[i]                = bmap->bitmapq[-4095]  (32760 bytes BEFORE bitmapq[0])
which is an OOB heap read (test at :727/:749/:785) and OOB heap write (set at :803).