RISC-V Sv39 Boot Mappings: Distinguish a Bad Virtual Address from a Misaligned Superpage

An RV64 supervisor faults immediately after enabling translation. The page-table root is aligned, the leaf has its valid bit set, and adding more translation fences changes nothing. The mapping can still be structurally invalid: Sv39 constrains both the shape of the virtual address and the physical alignment of a large-page leaf.

This walkthrough uses the Supervisor-Level ISA version 1.13, Sv39 and Virtual Address Translation Process, pinned at commit ff6bb3c. It concerns ordinary nonvirtualized Sv39 mappings with no special page-table extensions assumed. The hexadecimal examples are derived worksheets, not a booted page table or a hardware fault capture.

Check the address before walking the table

Sv39 uses a 39-bit virtual address space within 64-bit effective addresses. Bits 63 through 39 must all equal bit 38. Violating that requirement causes a page fault; a valid PTE elsewhere cannot repair the malformed address presented to translation.

For example, 0x0000004000000000 has bit 38 set but its upper bits clear. It is not a valid Sv39 virtual-address representation. The sign-extended form of that low 39-bit pattern is 0xffffffc000000000, which meets the address-shape requirement.

That second address is only structurally admissible. It still needs a valid mapping and appropriate permissions. Do not report “canonical” as synonymous with “mapped,” and do not automatically sign-extend arbitrary corrupted pointers in a fault handler. Correct the component that constructed the intended virtual address.

Record the actual effective address, access type and active translation mode. An address accepted under another mode or used as a physical address during early boot does not automatically satisfy Sv39’s virtual-address rule.

Identify whether each entry points down or maps memory

An Sv39 page table contains 512 entries of eight bytes and occupies one naturally aligned 4 KiB page. Its three levels use nine virtual-page-number bits each. The root’s physical page number comes from satp.PPN; it is not a virtual pointer to the root’s C object.

After rejecting invalid and reserved encodings, the translation algorithm treats an entry with R=1 or X=1 as a leaf. Otherwise it follows that entry to the next level. A copied permission flag can therefore change the interpretation of a physical page number from “next table” to “mapped data.”

In the ordinary encoding considered here, V=0 is invalid, and R=0,W=1 is reserved rather than a write-only mapping. For non-leaf entries, the specification reserves U, A and D and requires software to clear them until a standard extension defines otherwise. Build table-pointer and leaf entries through distinct helpers rather than reusing one unrestricted flag combination.

Sv39 diagnostic worksheet separates virtual-address sign extension, level-1 leaf alignment, and the resulting two-megabyte offset calculation.

Original Sv39 mapping worksheet. These are conditional translation calculations, not observed device results.

A level-1 leaf maps two MiB, not one arbitrary page

With level zero as the bottom level, a leaf at level one represents a 2 MiB mapping. The physical base must be aligned to 2 MiB, so its low nine physical-page-number bits, PPN[0], must be zero. A root-level leaf represents 1 GiB and has a correspondingly wider low-PPN zero requirement.

Consider mapping virtual base 0x40000000 to physical base 0x80200000 through a level-1 leaf. Both bases are aligned to 2 MiB. If all other validity, permission and access checks pass, virtual address 0x40001234 translates to physical address 0x80201234.

The offset is supplied by the lower virtual-page-number bits and the unchanged 12-bit page offset. The leaf’s low PPN bits are not another place to encode that offset. Setting the physical base to 0x80201000 leaves the address 4 KiB-aligned but violates the larger leaf’s alignment requirement. Translation must fault rather than quietly round the base down.

A table generator can verify the intended relationship without touching the target:

level-1 leaf size:      0x200000
candidate base:        0x80201000
base modulo leaf size: 0x001000
result:                reject as a 2 MiB leaf base

Choosing a bottom-level 4 KiB mapping may represent the intended address, but that changes the table structure and coverage. It is not equivalent to deleting the low physical bits and unintentionally mapping a different region.

Keep entry-format failures separate from access permissions

Sv39 reserves upper PTE bits unless their defined extensions apply. In particular, bit 63 belongs to Svnapot and bits 62 through 61 to Svpbmt; without those extensions they must be zero. Bits 60 through 54 also cannot serve as arbitrary application flags under the ordinary format.

Preserve the complete eight-byte PTE when collecting evidence. A dump that displays only the low flags can hide the reserved upper bit that invalidates an otherwise plausible entry. Conversely, a valid address and aligned leaf can still fail the intended load, store or instruction fetch because its permissions or access/dirty-bit handling do not allow that operation.

The translation algorithm also distinguishes an access fault while reading page-table memory under physical protection checks from a page fault caused by an invalid translation entry. Capture the actual exception classification rather than labelling every early boot trap a missing mapping.

Make the boot review deterministic

For each critical boot access, retain the effective address, translation mode, root physical address, indices, full entries, leaf level, intended physical base and access type. Check canonical address shape, entry interpretation and leaf-size alignment before investigating dynamic translation-cache invalidation.

A fence cannot make an intrinsically malformed PTE valid. After correcting a table, however, the platform still needs its supported publication and translation-invalidation sequence; a static worksheet does not replace those synchronization obligations.

Proposed negative fixtures include one noncanonical virtual address, a level-1 leaf with nonzero PPN[0], a table-pointer entry accidentally marked executable and a reserved upper PTE bit. Test them first in an approved model or isolated bring-up environment with a recoverable trap path. No such fixtures were executed here. The deliverable is a mapping-specific explanation of where translation fails, not a claim that one page-table pattern boots every RISC-V board.

Similar Posts