/* ---------------------------------------------------------------------------- * ATMEL Microcontroller Software Support * ---------------------------------------------------------------------------- * Copyright (c) 2008, Atmel Corporation * * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * - Redistributions of source code must retain the above copyright notice, * this list of conditions and the disclaimer below. * * Atmel's name may not be used to endorse or promote products derived from * this software without specific prior written permission. * * DISCLAIMER: THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE * DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * ---------------------------------------------------------------------------- */ //----------------------------------------------------------------------------- // Headers //----------------------------------------------------------------------------- #include #ifdef CP15_PRESENT #include #include "cp15.h" #if defined(__ICCARM__) #include #endif //----------------------------------------------------------------------------- // Macros //----------------------------------------------------------------------------- //----------------------------------------------------------------------------- // Defines //----------------------------------------------------------------------------- /* #define CP15_RR_BIT 14 // RR bit Replacement strategy for ICache and DCache: // 0 = Random replacement // 1 = Round-robin replacement. #define CP15_V_BIT 13 // V bit Location of exception vectors: // 0 = Normal exception vectors selected address range = 0x0000 0000 to 0x0000 001C // 1 = High exception vect selected, address range = 0xFFFF 0000 to 0xFFFF 001C */ #define CP15_I_BIT 12 // I bit ICache enable/disable: // 0 = ICache disabled // 1 = ICache enabled /* #define CP15_R_BIT 9 // R bit ROM protection #define CP15_S_BIT 8 // S bit System protection #define CP15_B_BIT 7 // B bit Endianness: // 0 = Little-endian operation // 1 = Big-endian operation. */ #define CP15_C_BIT 2 // C bit DCache enable/disable: // 0 = Cache disabled // 1 = Cache enabled /* #define CP15_A_BIT 1 // A bit Alignment fault enable/disable: // 0 = Data address alignment fault checking disabled // 1 = Data address alignment fault checking enabled */ #define CP15_M_BIT 0 // M bit MMU enable/disable: 0 = disabled 1 = enabled. // 0 = disabled // 1 = enabled //----------------------------------------------------------------------------- // Global functions //----------------------------------------------------------------------------- //------------------------------------------------------------------------------ /// Check Instruction Cache /// \return 0 if I_Cache disable, 1 if I_Cache enable //------------------------------------------------------------------------------ unsigned int CP15_Is_I_CacheEnabled(void) { unsigned int control; control = _readControlRegister(); return ((control & (1 << CP15_I_BIT)) != 0); } //------------------------------------------------------------------------------ /// Enable Instruction Cache //------------------------------------------------------------------------------ void CP15_Enable_I_Cache(void) { unsigned int control; control = _readControlRegister(); // Check if cache is disabled if ((control & (1 << CP15_I_BIT)) == 0) { control |= (1 << CP15_I_BIT); _writeControlRegister(control); TRACE_INFO("I cache enabled.\n\r"); } #if !defined(OP_BOOTSTRAP_on) else { TRACE_INFO("I cache is already enabled.\n\r"); } #endif } //------------------------------------------------------------------------------ /// Disable Instruction Cache //------------------------------------------------------------------------------ void CP15_Disable_I_Cache(void) { unsigned int control; control = _readControlRegister(); // Check if cache is enabled if ((control & (1 << CP15_I_BIT)) != 0) { control &= ~(1 << CP15_I_BIT); _writeControlRegister(control); TRACE_INFO("I cache disabled.\n\r"); } else { TRACE_INFO("I cache is already disabled.\n\r"); } } //------------------------------------------------------------------------------ /// Check MMU /// \return 0 if MMU disable, 1 if MMU enable //------------------------------------------------------------------------------ unsigned int CP15_Is_MMUEnabled(void) { unsigned int control; control = _readControlRegister(); return ((control & (1 << CP15_M_BIT)) != 0); } //------------------------------------------------------------------------------ /// Enable MMU //------------------------------------------------------------------------------ void CP15_EnableMMU(void) { unsigned int control; control = _readControlRegister(); // Check if MMU is disabled if ((control & (1 << CP15_M_BIT)) == 0) { control |= (1 << CP15_M_BIT); _writeControlRegister(control); TRACE_INFO("MMU enabled.\n\r"); } else { TRACE_INFO("MMU is already enabled.\n\r"); } } //------------------------------------------------------------------------------ /// Disable MMU //------------------------------------------------------------------------------ void CP15_DisableMMU(void) { unsigned int control; control = _readControlRegister(); // Check if MMU is enabled if ((control & (1 << CP15_M_BIT)) != 0) { control &= ~(1 << CP15_M_BIT); control &= ~(1 << CP15_C_BIT); _writeControlRegister(control); TRACE_INFO("MMU disabled.\n\r"); } else { TRACE_INFO("MMU is already disabled.\n\r"); } } //------------------------------------------------------------------------------ /// Check D_Cache /// \return 0 if D_Cache disable, 1 if D_Cache enable (with MMU of course) //------------------------------------------------------------------------------ unsigned int CP15_Is_DCacheEnabled(void) { unsigned int control; control = _readControlRegister(); return ((control & ((1 << CP15_C_BIT)||(1 << CP15_M_BIT))) != 0); } //------------------------------------------------------------------------------ /// Enable Data Cache //------------------------------------------------------------------------------ void CP15_Enable_D_Cache(void) { unsigned int control; control = _readControlRegister(); if( !CP15_Is_MMUEnabled() ) { TRACE_ERROR("Do nothing: MMU not enabled\n\r"); } else { // Check if cache is disabled if ((control & (1 << CP15_C_BIT)) == 0) { control |= (1 << CP15_C_BIT); _writeControlRegister(control); TRACE_INFO("D cache enabled.\n\r"); } else { TRACE_INFO("D cache is already enabled.\n\r"); } } } //------------------------------------------------------------------------------ /// Disable Data Cache //------------------------------------------------------------------------------ void CP15_Disable_D_Cache(void) { unsigned int control; control = _readControlRegister(); // Check if cache is enabled if ((control & (1 << CP15_C_BIT)) != 0) { control &= ~(1 << CP15_C_BIT); _writeControlRegister(control); TRACE_INFO("D cache disabled.\n\r"); } else { TRACE_INFO("D cache is already disabled.\n\r"); } } #endif // CP15_PRESENT