class ArchVmAspaceInterface

Defined at line 47 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

per arch base class api to encapsulate the mmu routines on an aspace

Beyond construction/destruction lifetimes users of this object must ensure that none of the

main methods are called before calling Init or after calling Destroy. Doing so is allowed to

cause a panic.

Aside from Init and Destroy, the main methods are all thread-safe.

Public Methods

void ArchVmAspaceInterface ()

Defined at line 49 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

zx_status_t Init ()

The Init* methods are used to initialize the ArchVmAspace. The method that should be used

is dependent on the type of address space being created.

`Init`: This is used to create a regular address space with no special features. In

architectures that do not support unified address spaces, it is also used to create

shared and restricted address spaces. However, when unified address spaces are

supported, the shared and restricted address spaces should be created with `InitShared`

and `InitRestricted`.

`InitShared`: This is used to create a shared address space, whose contents can be

accessed from multiple unified address spaces. These address spaces have a statically

initialized top level page.

`InitRestricted`: This is used to create a restricted address space, whose contents can be

accessed from a single unified address space.

`InitUnified`: This is used to create a unified address space. This type of address space

owns no mappings of its own; rather, it is composed of a shared address space and a

restricted address space. As a result, it expects `InitShared` to have been called

on the shared address space, and expects `InitRestricted` to have been called on the

restricted address space.

zx_status_t InitShared ()
zx_status_t InitRestricted ()
zx_status_t InitUnified (ArchVmAspaceInterface & shared, ArchVmAspaceInterface & restricted)
void DisableUpdates ()

This method puts the instance into read-only mode and asserts that it contains no mappings.

Note, this method may be a no-op on some architectures. See https://fxbug.dev/42159319.

It is an error to call this method on an instance that contains mappings. Once called,

subsequent operations that modify the page table will trigger a panic.

The purpose of this method is to help enforce lifecycle and state transitions of VmAspace and

ArchVmAspaceInterface.

zx_status_t Destroy ()

Destroy expects the aspace to be fully unmapped, as any mapped regions indicate incomplete

cleanup at the higher layers. Note that this does not apply to unified aspaces, which may

still contain some mappings when Destroy() is called.

It is safe to call Destroy even if Init, InitShared, InitRestricted, or InitUnified failed.

Once destroy has been called it is a user error to call any of the other methods on the aspace,

unless specifically stated otherwise, and doing so may cause a panic.

zx_status_t MapContiguous (vaddr_t vaddr, paddr_t paddr, size_t count, uint mmu_flags)

main methods

Map a physically contiguous region into the virtual address space. This is allowed to use any

page size the architecture allows given the from the input parameters.

zx_status_t Map (vaddr_t vaddr, paddr_t * phys, size_t count, uint mmu_flags, ExistingEntryAction existing_action)
zx_status_t Unmap (vaddr_t vaddr, size_t count, ArchUnmapOptions enlarge)
bool UnmapOnlyEnlargeOnOom ()

Returns whether or not an unmap might need to enlarge an operation for reasons other than being

out of memory. If this returns true, then unmapping a partial large page will fail always

require an enlarged operation.

zx_status_t Protect (vaddr_t vaddr, size_t count, uint mmu_flags, ArchUnmapOptions enlarge)

Change the page protections on the given virtual address range

May return ZX_ERR_NO_MEMORY if the operation requires splitting

a large page and the next level page table allocation fails. In

this case, mappings in the input range may be a mix of the old and

new flags.

ArchUnmapOptions controls whether the a larger range than requested is permitted to experience

a temporary permissions change. A temporary change may be required if a break-before-make style

unmap -> remap of the large page is required.

zx_status_t Query (vaddr_t vaddr, paddr_t * paddr, uint * mmu_flags)
vaddr_t PickSpot (vaddr_t base, vaddr_t end, vaddr_t align, size_t size, uint mmu_flags)
zx_status_t HarvestAccessed (vaddr_t vaddr, size_t count, NonTerminalAction non_terminal_action, TerminalAction terminal_action)

Walks the given range of pages and for any pages that are mapped and have their access bit set

* Tells the page queues it has been accessed via PageQueues::MarkAccessed

* Potentially removes the accessed flag.

* Potentially frees unaccessed page tables.

zx_status_t MarkAccessed (vaddr_t vaddr, size_t count)

Marks any pages in the given virtual address range as being accessed.

bool AccessedSinceLastCheck (bool clear)

Returns whether or not this aspace might have additional accessed information since the last

time this method was called with clear=true. If this returns |false| then, modulo races,

HarvestAccessed is defined to not find any set bits and not call PageQueues::MarkAccessed.

This is intended for use by the harvester to avoid scanning for any accessed or dirty bits if

the aspace has not been accessed at all.

Note that restricted and shared ArchVmAspace's will report that they have been accessed if an

associated unified ArchVmAspace has been accessed. However, the reverse is not true; the

unified ArchVmAspace will not return true if the associated shared/restricted aspaces have been

accessed.

The |clear| flag controls whether the aspace having been accessed should be cleared or not. Not

clearing makes this function const and not modify any state.

paddr_t arch_table_phys ()

Physical address of the backing data structure used for translation.

This should be treated as an opaque value outside of

architecture-specific components.

void ~ArchVmAspaceInterface ()

Defined at line 50 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

Enumerations

enum ExistingEntryAction
Name Value
Skip 0
Error 1
Upgrade 2

Map the given array of pages into the virtual address space starting at

|vaddr|, in the order they appear in |phys|.

If any address in the range [vaddr, vaddr + count * kPageSize) is already

mapped when this is called, |existing_action| controls the behavior used:

- |Skip| - Skip updating any existing mappings.

- |Error| - Existing mappings result in a ZX_ERR_ALREADY_EXISTS error.

- |Upgrade| - Upgrade any existing mappings, meaning a read-only mapping

can be converted to read-write, or the mapping can have its

paddr changed.

On error none of the provided pages will be mapped. In the case of |Upgrade| the state of any

previous mappings is undefined, and could either still be present or be unmapped.

Defined at line 121 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

enum ArchUnmapOptions
Name Value
None 0
Enlarge (1u << 0)
Harvest (1u << 1)

Options for unmapping the given virtual address range.

ArchUnmapOptions::Enlarge controls whether the unmap region can be extended to be larger, or if

only the exact region may be unmapped. The unmap region might be extended, even if only

temporarily, if large pages need to be split.

ArchUnmapOptions::Harvest requests that the accessed bit be harvested, and the page queues

updated.

Defined at line 136 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

enum NonTerminalAction
Name Value
FreeUnaccessed 0
Retain 1

For HarvestAccessed Terminal and non-terminal get processed based on the following two

controls.

Defined at line 168 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h

enum TerminalAction
Name Value
UpdateAgeAndHarvest 0
UpdateAge 1

Defined at line 175 of file ../../zircon/kernel/vm/include/vm/arch_vm_aspace.h