Subversion Repositories HelenOS-doc

Compare Revisions

Ignore whitespace Rev 83 → Rev 84

/design/trunk/src/ch_memory_management.xml
534,7 → 534,7
 
<para>The remote TLB invalidation is called TLB shootdown. HelenOS uses
a simplified variant of the algorithm described in <xref
linkend="Black89" />. </para>
linkend="Black89" />.</para>
 
<para>TLB shootdown is performed in three phases.</para>
 
572,85 → 572,71
operation.</para>
</formalpara>
</section>
</section>
 
<section>
<title>Address spaces</title>
<section>
<title>Address spaces</title>
 
<section>
<indexterm>
<primary>address space</primary>
<para>last bits about address spaces</para>
 
<secondary>- area</secondary>
</indexterm>
<section>
<indexterm>
<primary>address space</primary>
 
<title>Address space areas</title>
<secondary>- ASID</secondary>
</indexterm>
 
<para>Each address space consists of mutually disjunctive continuous
address space areas. Address space area is precisely defined by its
base address and the number of frames/pages is contains.</para>
<title>Address Space ID (ASID)</title>
 
<para>Address space area , that define behaviour and permissions on
the particular area. <itemizedlist>
<listitem><emphasis>AS_AREA_READ</emphasis> flag indicates reading
permission.</listitem>
<para>Modern processor architectures optimize TLB utilization by
associating TLB entries with address spaces through assigning
identification numbers to them. In HelenOS, the term ASID, originally
taken from the mips32 terminology, is used to refer to the address space
identification number. The advantage of having ASIDs is that TLB does
not have to be invalidated on thread context switch as long as ASIDs are
unique. Unfotunatelly, architectures supported by HelenOS use all
different widths of ASID numbers<footnote>
<para>amd64 and ia32 don't use similar abstraction at all, mips32
has 8-bit ASIDs and ia64 can have ASIDs between 18 to 24 bits
wide.</para>
</footnote> out of which none is sufficient. The amd64 and ia32
architectures cannot make use of ASIDs as their TLB doesn't recognize
such an abstraction. Other architectures have support for ASIDs, but for
instance ppc32 doesn't make use of them in the current version of
HelenOS. The rest of the architectures does use ASIDs. However, even on
the ia64 architecture, the minimal supported width of ASID<footnote>
<para>RID in ia64 terminology.</para>
</footnote> is insufficient to provide a unique integer identifier to
all address spaces that might hypothetically coexist in the running
system. The situation on mips32 is even worse: the architecture has only
256 unique identifiers.</para>
 
<listitem><emphasis>AS_AREA_WRITE</emphasis> flag indicates
writing permission.</listitem>
<indexterm>
<primary>address space</primary>
 
<listitem><emphasis>AS_AREA_EXEC</emphasis> flag indicates code
execution permission. Some architectures do not support execution
persmission restriction. In this case this flag has no
effect.</listitem>
<secondary>- ASID stealing</secondary>
</indexterm>
 
<listitem><emphasis>AS_AREA_DEVICE</emphasis> marks area as mapped
to the device memory.</listitem>
</itemizedlist></para>
 
<para>Kernel provides possibility tasks create/expand/shrink/share its
address space via the set of syscalls.</para>
</section>
 
<section>
<indexterm>
<primary>address space</primary>
 
<secondary>- ASID</secondary>
</indexterm>
 
<title>Address Space ID (ASID)</title>
 
<para>Every task in the operating system has it's own view of the
virtual memory. When performing context switch between different
tasks, the kernel must switch the address space mapping as well. As
modern processors perform very aggressive caching of virtual mappings,
flushing the complete TLB on every context switch would be very
inefficient. To avoid such performance penalty, some architectures
introduce an address space identifier, which allows storing several
different mappings inside TLB.</para>
 
<para>HelenOS kernel can take advantage of this hardware support by
having an ASID abstraction. I.e. on ia64 kernel ASID is derived from
RID (region identifier) and on the mips32 kernel ASID is actually the
hardware identifier. As expected, this ASID information record is the
part of <emphasis>as_t</emphasis> structure.</para>
 
<para>Due to the hardware limitations, hardware ASID has limited
length from 8 bits on ia64 to 24 bits on mips32, which makes it
impossible to use it as unique address space identifier for all tasks
running in the system. In such situations special ASID stealing
algoritm is used, which takes ASID from inactive task and assigns it
to the active task.</para>
 
<indexterm>
<primary>address space</primary>
 
<secondary>- ASID stealing</secondary>
</indexterm>
 
<para>
<classname>ASID stealing algoritm here.</classname>
</para>
</section>
<para>To mitigate the shortage of ASIDs, HelenOS uses the following
strategy. When the system initializes, a FIFO queue<footnote>
<para>Note that architecture-specific measures are taken to avoid
too large FIFO queue. For instance, seven consecutive ia64 RIDs are
grouped to form one HelenOS ASID.</para>
</footnote> is created and filled with all available ASIDs. Moreover,
every address space remembers the number of processors on which it is
active. Address spaces that have a valid ASID and that are not active on
any processor are appended to the list of inactive address spaces with
valid ASID. When an address space needs to be assigned a valid ASID, it
first checks the FIFO queue. If it contains at least one ASID, the ASID
is allocated. If the queue is empty, an ASID is simply stolen from the
first address space in the list. In that case, the address space that
loses the ASID in favor of another address space, is removed from the
list. After the new ASID is purged from all TLBs, it can be used by the
address space. Note that this approach works due to the fact that the
number of ASIDs is greater than the maximal number of processors
supported by HelenOS and that there can be only one active address space
per processor. In other words, when the FIFO queue is empty, there must
be address spaces that are not active on any processor.</para>
</section>
</section>
</chapter>