Skip to content

ARC MMU features ASID and SASID

Vineet Gupta edited this page Oct 17, 2019 · 7 revisions

This page gives a quick summary of the Address Space Identifier and Shared Address Space Identifier features of the ARC MMU.

1. Address Space Identifier: ASID

ARC MMU TLB entries are "tagged" with a unique ASID per task allowing entries with same virtual address (vaddr) to co-exist without need to flush the TLB on every OS context switch. OS manages ASID and assigns each task with a unique value.

MMU PID register contains the "current" ASID which is used by MMU to restrict its search through the TLB at the time of a vaddr lookup.

The TLB entries with Global bit set ignore the ASID and are always considered for match during a lookup (based on vaddr of course)

2. Shared Address Space Identifier: SASID

SASID is orthogonal and effectively opposite to ASID. It is a unique optimization feature of ARC MMU which allows for sharing and reusing of TLB entries between tasks. In a nutshell, ASID allows segregation of TLB entries per task (even for same vaddr) while SASID allows aggregation of TLB entries between tasks.

It is useful for a high level OS (not an RTOS) which supports features such as mmap, Shared libraries and Dynamic loading of libraries [Note 1]

The issue it addresses is as follows: When a shared library is loaded and mapped by multiple tasks, the underlying code and rodata pages are by definition shared and only 1 copy exists in physical memory (and possibly cache). However at the MMU TLB level, the same library page requires distinct translation entries per task, due to ASID, even if mapping virtual address is same.

Consider a libc code page containing codr for malloc (assume it fits in 1 MMU page and that this page is mapped at same vaddr in each task). Every task that maps libc and calls malloc will incur a TLB Miss for that page, leading to a unique entry in MMU, with same vaddr (and paddr since only 1 physical page exists) but distinct ASID. SASID alleviates this extra TLB Miss / capacity overhead by decoupling the regular TLB entries from ones which can be shared.

In terms of programming model:

  • SASID mechanism in only enabled on PID.S being set.
  • Shared TLB entries have TLB.S bit set and `TLB.ASID`` actually contains SASID value (e.g. 0 for libc, 1 for libm, 2 for libpthead, 3 for libssp)
  • MMU SASID1:SASID0 contain a bitmap, allowing up to 64 libraries to be shared, each bit representing pow2 of library SASID value (e.g. 0x1 for libc, 0x8 for libssp etc) thus represent the task shared library "subscriptions" e.g. if task maps only libc and libpthread SASID0 is 0x5, SASID1 is 0

The requirement from OS is that libraries need to be mapped at exactly same virtual address across tasks.

Support for SASID feature was added in 2.6.35 ARC Linux kernel (out of tree) but the changes never made it to upstream kernel. It also required pairing changes in uClibc dynamic loader

The 2.6.35 kernel implementation can be found at: https://git.kernel.org/pub/scm/linux/kernel/git/vgupta/arc.git/log/?h=arc-history-pre-upstream&ofs=400

3. MMU lookup showing ASID, SASID usage

The image below shows the high level MMU lookup flow: MMU lookup

Note 1: Not to be confused with ARC MMUv5 dyanmic loading feature which allows overlay like functionality.

Clone this wiki locally