module ti.sysbios.family.arm.a8.Mmu

Memory Management Unit Manager

This module allows the ARM processor to map a virtual address to a different physical address and enable/disable the MMU. It does this through a translation table in memory. The translation table is 16KB and manages only the first level descriptor table. Each entry in the table defines the properties of memory areas of size 1MB. These properties include memory access permissions, cacheability, bufferability, and domain access. [ more ... ]
C synopsis target-domain sourced in ti/sysbios/family/arm/a8/Mmu.xdc
#include <ti/sysbios/family/arm/a8/Mmu.h>
Functions
Void 
Void 
UInt32 
Ptr 
Void 
Bool 
Void 
Void 
Void 
Functions common to all target modules
Typedefs
typedef enum
typedef struct
Constants
extern const Assert_Id 
extern const Assert_Id 
extern const Bool 
 
DETAILS
This module allows the ARM processor to map a virtual address to a different physical address and enable/disable the MMU. It does this through a translation table in memory. The translation table is 16KB and manages only the first level descriptor table. Each entry in the table defines the properties of memory areas of size 1MB. These properties include memory access permissions, cacheability, bufferability, and domain access.
By default, the MMU translation table is initialized with cache-enabled entries for every memory segment defined in the platform. Cache-disabled entries are also added for the peripheral addresses used by SYS/BIOS (i.e. Timers, Interrupt controller).
The translation table is placed in an output section called "ti.sysbios.family.arm.a8.mmuTableSection". This section is placed into the platform's default dataMemory and in order to minimize object file size, specified to not be initialized via the "NOLOAD" type on GNU compilers and "NOINIT" on TI compilers.
This module does not manage the second level descriptor tables. A 'SECTION' mapped access requires only a first level fetch. In this case, there is no need for a second level descriptor table. A 'PAGE_TABLE' mapped access requires a second level descriptor table which can be supplied by the user.
The following is an example of how to place the MMU table and how to enable L1 data + L2 caching for the address range 0x80000000-0x90000000 in the *.cfg file:
    // For Cortex-A8
    var Cache = xdc.useModule('ti.sysbios.family.arm.a8.Cache');
    // For Cortex-A9
    var Cache = xdc.useModule('ti.sysbios.family.arm.a9.Cache');

    var Mmu = xdc.useModule('ti.sysbios.family.arm.a8.Mmu');

    // Enable the cache
    Cache.enableCache = true;

    // Enable the MMU (Required for L1/L2 data caching)
    Mmu.enableMMU = true;

    // descriptor attribute structure for marking the memory region
    // as normal cacheable memory (write-back and write-allocate)
    var attrs = {
        type: Mmu.FirstLevelDesc_SECTION,  // SECTION descriptor
        tex: 0x1,
        bufferable: true,                  // bufferable
        cacheable: true,                   // cacheable
    };

    // Set the descriptor for each entry in the address range
    for (var i=0x80000000; i < 0x90000000; i = i + 0x00100000) {
        // Each 'SECTION' descriptor entry spans a 1MB address range
        Mmu.setFirstLevelDescMeta(i, i, attrs);
    }

    var memmap = Program.cpu.memoryMap;
    var DDR = null;

    // Find DDR in memory map
    for (var i=0; i < memmap.length; i++) {
        if (memmap[i].name == "DDR") {
            DDR = memmap[i];
        }
    }

    // Place the MMU table in the DDR memory segment if it exists
    if (DDR != null) {
        var sectionName = "ti.sysbios.family.arm.a8.mmuTableSection";
        Program.sectMap[sectionName] = new Program.SectionSpec();
        Program.sectMap[sectionName].type = "NOLOAD"; // NOINIT for TI Tools
        Program.sectMap[sectionName].loadSegment = "DDR";
    }
    else {
        print("No DDR memory segment was found");
    }

The following example demonstrates how to add a peripheral's address to the MMU table so that it can be accessed by code at runtime:
    // For Cortex-A8
    var Cache = xdc.useModule('ti.sysbios.family.arm.a8.Cache');
    // For Cortex-A9
    var Cache = xdc.useModule('ti.sysbios.family.arm.a9.Cache');

    var Mmu = xdc.useModule('ti.sysbios.family.arm.a8.Mmu');

    // Enable the cache
    Cache.enableCache = true;

    // Enable the MMU (Required for L1/L2 data caching)
    Mmu.enableMMU = true;

    // Force peripheral section to be NON cacheable strongly-ordered memory
    var peripheralAttrs = {
        type : Mmu.FirstLevelDesc_SECTION, // SECTION descriptor
        tex: 0,
        bufferable : false,                // bufferable
        cacheable  : false,                // cacheable
        shareable  : false,                // shareable
        noexecute  : true,                 // not executable
    };

    // Define the base address of the 1 Meg page
    // the peripheral resides in.
    var peripheralBaseAddr = 0xa0400000;

    // Configure the corresponding MMU page descriptor accordingly
    Mmu.setFirstLevelDescMeta(peripheralBaseAddr,
                              peripheralBaseAddr,
                              peripheralAttrs);
MEMORY REGION ATTRIBUTES
Memory regions can be configured as different memory types by setting the bufferable, cacheable and tex (type extension) fields of the FirstLevelDescAttrs structure which is passed as an argument to setFirstLevelDesc. The three memory types supported by the hardware are "Normal" (cacheable), "Device" and "Strongly-ordered" memory. "Device" and "Strongly-ordered" memory types are recommended for mapping peripheral address space like memory-mapped registers. These two types ensure that the memory accesses to the peripheral memory are not performed speculatively, are not repeated and are performed in order. The "Normal" memory type is recommended for mapping memory regions storing application code and data.
Here are some common settings for the bufferable, cacheable and tex fields to define different memory region types:
  ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  + Memory Type                             | bufferable | cacheable | tex +
  ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  + Shareable Strongly-ordered memory       |    false   |   false   |  0  +
  +-----------------------------------------+------------+-----------+-----+
  + Shareable Device memory                 |    true    |   false   |  0  +
  +-----------------------------------------+------------+-----------+-----+
  + Outer & Inner Non-cacheable             |    false   |   false   |  1  +
  +-----------------------------------------+------------+-----------+-----+
  + Outer & Inner Write-back Write-allocate |    true    |   true    |  1  +
  + cacheable                               |            |           |     +
  ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
For an exhaustive list of all different memory type settings and a detailed explanation of the memory region attributes, please read the 'Short-descriptor translation table format' section of the ARM v7-AR Architecture Reference Manual issue C.
Notes:
  • The 'Supersection' table descriptor is NOT supported.
  • The 'not global' page descriptor setting is NOT supported.
  • The 'non-secure' page descriptor setting is NOT supported.
  • There are size and alignment requirements on the second level descriptor tables depending on the page size.
  • See the ARM Architecture Reference Manual for more info.
 
enum Mmu_FirstLevelDesc

First Level descriptors

C synopsis target-domain
typedef enum Mmu_FirstLevelDesc {
    Mmu_FirstLevelDesc_FAULT,
    // Virtual address is unmapped
    Mmu_FirstLevelDesc_PAGE_TABLE,
    // Page table addr descriptor
    Mmu_FirstLevelDesc_SECTION,
    // Section descriptor
    Mmu_FirstLevelDesc_RESERVED
    // Reserved
} Mmu_FirstLevelDesc;
 
DETAILS
Different descriptor type encodings: 0b00 -> Invalid or Fault entry 0b01 -> Page table entry 0b10 -> Section descriptor 0b11 -> Reserved
 
struct Mmu_FirstLevelDescAttrs

Structure for setting first level descriptor entries

C synopsis target-domain
typedef struct Mmu_FirstLevelDescAttrs {
    Mmu_FirstLevelDesc type;
    // first level descriptor type
    Bool bufferable;
    // is memory section bufferable
    Bool cacheable;
    // is memory section cacheable
    Bool shareable;
    // is memory section shareable
    Bool noexecute;
    // is memory section not executable
    UInt8 imp;
    // implementation defined
    UInt8 domain;
    // domain access control value 0-15
    UInt8 accPerm;
    // access permission bits value 0-7
    UInt8 tex;
    // memory region attr type extension field
    Bool notGlobal;
    // not global bit
} Mmu_FirstLevelDescAttrs;
 
DETAILS
The B (Bufferable), C (Cacheable), and TEX (Type extension) bits in the translation table descriptor define the memory region attributes.
See the 'Short-descriptor translation table format' section of the ARM v7-AR Architecture Reference Manual issue C for more details.
 
config Mmu_A_nullPointer  // module-wide

Assert raised when a pointer is null

C synopsis target-domain
extern const Assert_Id Mmu_A_nullPointer;
 
 
config Mmu_A_unknownDescType  // module-wide

Assert raised when the descriptor type is not recognized

C synopsis target-domain
extern const Assert_Id Mmu_A_unknownDescType;
 
 
config Mmu_defaultAttrs  // module-wide

default descriptor attributes structure

C synopsis target-domain
extern const Mmu_FirstLevelDescAttrs Mmu_defaultAttrs;
 
 
config Mmu_enableMMU  // module-wide

Configuration parameter to enable MMU

C synopsis target-domain
extern const Bool Mmu_enableMMU;
 
 
Mmu_disable()  // module-wide

Disables the MMU

C synopsis target-domain
Void Mmu_disable();
 
DETAILS
If the MMU is already disabled, then simply return. Otherwise this function does the following: If the L1 data cache is enabled, write back invalidate all of L1 data cache. If the L1 program cache is enabled, invalidate all of L1 program cache. This function does not change the cache L1 data/program settings.
 
Mmu_enable()  // module-wide

Enables the MMU

C synopsis target-domain
Void Mmu_enable();
 
DETAILS
If the MMU is already enabled, then simply return. Otherwise this function does the following: If the L1 program cache is enabled, invalidate all of L1 program cache. This function does not change the L1 data/program cache settings.
 
Mmu_getDomainAccessCtrlReg()  // module-wide

Returns the domain access control register value (DACR)

C synopsis target-domain
UInt32 Mmu_getDomainAccessCtrlReg();
 
RETURNS
Domain Access Ctrl Register value
 
Mmu_getPhysicalAddr()  // module-wide

Returns the translated physical address for the given virtual address. If the virtual address cannot be translated i.e. the virtual address would generate a fault if translated, ~(0) is returned

C synopsis target-domain
Ptr Mmu_getPhysicalAddr(Ptr virtualAddr);
 
ARGUMENTS
virtualAddr — virtual address
RETURNS
translated physical address
 
Mmu_initDescAttrs()  // module-wide

Initializes the first level descriptor attribute structure

C synopsis target-domain
Void Mmu_initDescAttrs(Mmu_FirstLevelDescAttrs *attrs);
 
ARGUMENTS
attrs — Pointer to first level descriptor attribute struct
 
Mmu_isEnabled()  // module-wide

Determines if the MMU is enabled

C synopsis target-domain
Bool Mmu_isEnabled();
 
 
Mmu_setDomainAccessCtrlReg()  // module-wide

Write the passed argument to domain access control register (DACR)

C synopsis target-domain
Void Mmu_setDomainAccessCtrlReg(UInt32 regVal);
 
ARGUMENTS
regVal — Contents to be written to DACR register
DETAILS
The domain access control register has 16 2-bit fields to control the access permissions of each domain.
         |31 30|29 28|27 26|25 24|23 22| ... |7   6|5   4|3   2|1   0|
          -----------------------------------------------------------
  Domain | D15 | D14 | D13 | D12 | D11 | ... | D3  | D2  | D1  |  D0 |
          -----------------------------------------------------------

  Possible domain access permission value for each field:
  0b00   No access. Any domain access will generate a fault.
  0b01   Accesses are checked against translation table permission bits.
  0b11   No access permission checking is performed for this domain.
 
Mmu_setFirstLevelDesc()  // module-wide

Sets the descriptor for the virtual address

C synopsis target-domain
Void Mmu_setFirstLevelDesc(Ptr virtualAddr, Ptr phyAddr, Mmu_FirstLevelDescAttrs *attrs);
 
ARGUMENTS
virtualAddr — The modified virtual address
phyAddr — The physical address
attrs — Pointer to first level descriptor attribute struct
DETAILS
The first level table entry for the virtual address is mapped to the physical address with the attributes specified. The descriptor table is effective when the MMU is enabled.
 
Mmu_tlbInvAll()  // module-wide

Invalidate entire TLB (both data and instruction)

C synopsis target-domain
Void Mmu_tlbInvAll();
 
Module-Wide Built-Ins

C synopsis target-domain
Types_ModuleId Mmu_Module_id();
// Get this module's unique id
 
Bool Mmu_Module_startupDone();
// Test if this module has completed startup
 
IHeap_Handle Mmu_Module_heap();
// The heap from which this module allocates memory
 
Bool Mmu_Module_hasMask();
// Test whether this module has a diagnostics mask
 
Bits16 Mmu_Module_getMask();
// Returns the diagnostics mask for this module
 
Void Mmu_Module_setMask(Bits16 mask);
// Set the diagnostics mask for this module
 
Configuration settings sourced in ti/sysbios/family/arm/a8/Mmu.xdc
var Mmu = xdc.useModule('ti.sysbios.family.arm.a8.Mmu');
module-wide constants & types
 
        obj.bufferable// is memory section bufferable = Bool  ...
        obj.cacheable// is memory section cacheable = Bool  ...
        obj.shareable// is memory section shareable = Bool  ...
        obj.noexecute// is memory section not executable = Bool  ...
        obj.imp// implementation defined = UInt8  ...
        obj.domain// domain access control value 0-15 = UInt8  ...
        obj.accPerm// access permission bits value 0-7 = UInt8  ...
        obj.tex// memory region attr type extension field = UInt8  ...
        obj.notGlobal// not global bit = Bool  ...
module-wide config parameters
        msg: "A_nullPointer: Pointer is null"
    };
        msg: "A_unknownDescType: Descriptor type is not recognized"
    };
        type: Mmu.FirstLevelDesc_SECTION,
        bufferable: false,
        cacheable: false,
        shareable: false,
        noexecute: false,
        imp: 1,
        domain: 0,
        accPerm: 3,
        tex: 1,
        notGlobal: false
    };
 
module-wide functions
 
 
enum Mmu.FirstLevelDesc

First Level descriptors

Configuration settings
values of type Mmu.FirstLevelDesc
    const Mmu.FirstLevelDesc_FAULT;
    // Virtual address is unmapped
    const Mmu.FirstLevelDesc_PAGE_TABLE;
    // Page table addr descriptor
    const Mmu.FirstLevelDesc_SECTION;
    // Section descriptor
    const Mmu.FirstLevelDesc_RESERVED;
    // Reserved
 
DETAILS
Different descriptor type encodings: 0b00 -> Invalid or Fault entry 0b01 -> Page table entry 0b10 -> Section descriptor 0b11 -> Reserved
C SYNOPSIS
 
struct Mmu.FirstLevelDescAttrs

Structure for setting first level descriptor entries

Configuration settings
var obj = new Mmu.FirstLevelDescAttrs;
 
    obj.type = Mmu.FirstLevelDesc  ...
    // first level descriptor type
    obj.bufferable = Bool  ...
    // is memory section bufferable
    obj.cacheable = Bool  ...
    // is memory section cacheable
    obj.shareable = Bool  ...
    // is memory section shareable
    obj.noexecute = Bool  ...
    // is memory section not executable
    obj.imp = UInt8  ...
    // implementation defined
    obj.domain = UInt8  ...
    // domain access control value 0-15
    obj.accPerm = UInt8  ...
    // access permission bits value 0-7
    obj.tex = UInt8  ...
    // memory region attr type extension field
    obj.notGlobal = Bool  ...
    // not global bit
 
DETAILS
The B (Bufferable), C (Cacheable), and TEX (Type extension) bits in the translation table descriptor define the memory region attributes.
See the 'Short-descriptor translation table format' section of the ARM v7-AR Architecture Reference Manual issue C for more details.
C SYNOPSIS
 
config Mmu.A_nullPointer  // module-wide

Assert raised when a pointer is null

Configuration settings
Mmu.A_nullPointer = Assert.Desc {
    msg: "A_nullPointer: Pointer is null"
};
 
C SYNOPSIS
 
config Mmu.A_unknownDescType  // module-wide

Assert raised when the descriptor type is not recognized

Configuration settings
Mmu.A_unknownDescType = Assert.Desc {
    msg: "A_unknownDescType: Descriptor type is not recognized"
};
 
C SYNOPSIS
 
config Mmu.defaultAttrs  // module-wide

default descriptor attributes structure

Configuration settings
Mmu.defaultAttrs = Mmu.FirstLevelDescAttrs {
    bufferable: false,
    cacheable: false,
    shareable: false,
    noexecute: false,
    imp: 1,
    domain: 0,
    accPerm: 3,
    tex: 1,
    notGlobal: false
};
 
C SYNOPSIS
 
config Mmu.enableMMU  // module-wide

Configuration parameter to enable MMU

Configuration settings
Mmu.enableMMU = Bool true;
 
C SYNOPSIS
 
metaonly config Mmu.cachePlatformMemory  // module-wide

Flag to automatically mark platform's code/data/stack memory as cacheable in MMU descriptor table

Configuration settings
Mmu.cachePlatformMemory = Bool true;
 
DETAILS
By default, all memory regions defined in the platform an application is built with are marked as cacheable.
If manual configuration of memory regions is required, set this config parameter to 'false'.
SEE
 
metaonly config Mmu.common$  // module-wide

Common module configuration parameters

Configuration settings
Mmu.common$ = Types.Common$ undefined;
 
DETAILS
All modules have this configuration parameter. Its name contains the '$' character to ensure it does not conflict with configuration parameters declared by the module. This allows new configuration parameters to be added in the future without any chance of breaking existing modules.
 
metaonly config Mmu.rovViewInfo  // module-wide
Configuration settings
Mmu.rovViewInfo = ViewInfo.Instance ViewInfo.create;
 
 
metaonly Mmu.setFirstLevelDescMeta()  // module-wide

Statically sets the descriptor for the virtual address

Configuration settings
Mmu.setFirstLevelDescMeta(Ptr virtualAddr, Ptr phyAddr, Mmu.FirstLevelDescAttrs attrs) returns Void
 
ARGUMENTS
virtualAddr — The modified virtual address
phyAddr — The physical address
attrs — Pointer to first level descriptor attribute struct
DETAILS
The first level table entry for the virtual address is mapped to the physical address with the attributes specified. The descriptor table is effective when the MMU is enabled.
generated on Thu, 23 May 2019 00:22:45 GMT