From 3639963a9783dc3f06804bd7dff9283010edb372 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Tue, 16 Nov 2021 18:32:11 +0800 Subject: 添加TMS320C6678处理器,keystone架构底层代码 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-c6678/.ccsproject | 12 + bsp/ti-c6678/.cproject | 160 + bsp/ti-c6678/.project | 154 + .../.settings/org.eclipse.cdt.codan.core.prefs | 3 + .../.settings/org.eclipse.cdt.debug.core.prefs | 2 + .../.settings/org.eclipse.core.resources.prefs | 10 + bsp/ti-c6678/KeyStone.cmd | 47 + bsp/ti-c6678/applications/board.c | 60 + bsp/ti-c6678/applications/board.h | 20 + bsp/ti-c6678/applications/main.c | 99 + bsp/ti-c6678/driver/KeyStone_common.c | 4355 ++++++++++++++++++++ bsp/ti-c6678/driver/KeyStone_common.h | 1090 +++++ bsp/ti-c6678/driver/drv_timer.c | 55 + bsp/ti-c6678/driver/drv_timer.h | 19 + bsp/ti-c6678/rtconfig.h | 122 + bsp/ti-c6678/rtconfig_project.h | 23 + libcpu/ti-dsp/c6x/SConscript | 14 + libcpu/ti-dsp/c6x/c66xx.h | 106 + libcpu/ti-dsp/c6x/context.asm | 312 ++ libcpu/ti-dsp/c6x/cpuport.c | 225 + libcpu/ti-dsp/c6x/inct.asm | 374 ++ libcpu/ti-dsp/c6x/interrupt.c | 90 + libcpu/ti-dsp/c6x/interrupt.h | 24 + libcpu/ti-dsp/c6x/stack.asm | 103 + libcpu/ti-dsp/c6x/trap.c | 352 ++ libcpu/ti-dsp/c6x/trap.h | 76 + libcpu/ti-dsp/c6x/vector.asm | 95 + 27 files changed, 8002 insertions(+) create mode 100644 bsp/ti-c6678/.ccsproject create mode 100644 bsp/ti-c6678/.cproject create mode 100644 bsp/ti-c6678/.project create mode 100644 bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs create mode 100644 bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs create mode 100644 bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs create mode 100644 bsp/ti-c6678/KeyStone.cmd create mode 100644 bsp/ti-c6678/applications/board.c create mode 100644 bsp/ti-c6678/applications/board.h create mode 100644 bsp/ti-c6678/applications/main.c create mode 100644 bsp/ti-c6678/driver/KeyStone_common.c create mode 100644 bsp/ti-c6678/driver/KeyStone_common.h create mode 100644 bsp/ti-c6678/driver/drv_timer.c create mode 100644 bsp/ti-c6678/driver/drv_timer.h create mode 100644 bsp/ti-c6678/rtconfig.h create mode 100644 bsp/ti-c6678/rtconfig_project.h create mode 100644 libcpu/ti-dsp/c6x/SConscript create mode 100644 libcpu/ti-dsp/c6x/c66xx.h create mode 100644 libcpu/ti-dsp/c6x/context.asm create mode 100644 libcpu/ti-dsp/c6x/cpuport.c create mode 100644 libcpu/ti-dsp/c6x/inct.asm create mode 100644 libcpu/ti-dsp/c6x/interrupt.c create mode 100644 libcpu/ti-dsp/c6x/interrupt.h create mode 100644 libcpu/ti-dsp/c6x/stack.asm create mode 100644 libcpu/ti-dsp/c6x/trap.c create mode 100644 libcpu/ti-dsp/c6x/trap.h create mode 100644 libcpu/ti-dsp/c6x/vector.asm diff --git a/bsp/ti-c6678/.ccsproject b/bsp/ti-c6678/.ccsproject new file mode 100644 index 0000000000..82f98bbb00 --- /dev/null +++ b/bsp/ti-c6678/.ccsproject @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/bsp/ti-c6678/.cproject b/bsp/ti-c6678/.cproject new file mode 100644 index 0000000000..aef3a8c240 --- /dev/null +++ b/bsp/ti-c6678/.cproject @@ -0,0 +1,160 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/bsp/ti-c6678/.project b/bsp/ti-c6678/.project new file mode 100644 index 0000000000..d1c8afd3a3 --- /dev/null +++ b/bsp/ti-c6678/.project @@ -0,0 +1,154 @@ + + + ti-c6678 + + + + + + org.eclipse.cdt.managedbuilder.core.genmakebuilder + + + + + org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder + full,incremental, + + + + + + com.ti.ccstudio.core.ccsNature + org.eclipse.cdt.core.cnature + org.eclipse.cdt.managedbuilder.core.managedBuildNature + org.eclipse.cdt.core.ccnature + org.eclipse.cdt.managedbuilder.core.ScannerConfigNature + + + + SConscript + 1 + PARENT-2-PROJECT_LOC/src/SConscript + + + clock.c + 1 + PARENT-2-PROJECT_LOC/src/clock.c + + + components.c + 1 + PARENT-2-PROJECT_LOC/src/components.c + + + context.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/context.asm + + + cpu.c + 1 + PARENT-2-PROJECT_LOC/src/cpu.c + + + cpuport.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/cpuport.c + + + device.c + 1 + PARENT-2-PROJECT_LOC/src/device.c + + + idle.c + 1 + PARENT-2-PROJECT_LOC/src/idle.c + + + inct.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/inct.asm + + + interrupt.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/interrupt.c + + + ipc.c + 1 + PARENT-2-PROJECT_LOC/src/ipc.c + + + irq.c + 1 + PARENT-2-PROJECT_LOC/src/irq.c + + + kservice.c + 1 + PARENT-2-PROJECT_LOC/src/kservice.c + + + mem.c + 1 + PARENT-2-PROJECT_LOC/src/mem.c + + + memheap.c + 1 + PARENT-2-PROJECT_LOC/src/memheap.c + + + mempool.c + 1 + PARENT-2-PROJECT_LOC/src/mempool.c + + + object.c + 1 + PARENT-2-PROJECT_LOC/src/object.c + + + scheduler.c + 1 + PARENT-2-PROJECT_LOC/src/scheduler.c + + + signal.c + 1 + PARENT-2-PROJECT_LOC/src/signal.c + + + slab.c + 1 + PARENT-2-PROJECT_LOC/src/slab.c + + + stack.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/stack.asm + + + thread.c + 1 + PARENT-2-PROJECT_LOC/src/thread.c + + + timer.c + 1 + PARENT-2-PROJECT_LOC/src/timer.c + + + trap.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/trap.c + + + vector.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/vector.asm + + + diff --git a/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs b/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs new file mode 100644 index 0000000000..f653028c53 --- /dev/null +++ b/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs @@ -0,0 +1,3 @@ +eclipse.preferences.version=1 +inEditor=false +onBuild=false diff --git a/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs b/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs new file mode 100644 index 0000000000..2adc7b1dde --- /dev/null +++ b/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs @@ -0,0 +1,2 @@ +eclipse.preferences.version=1 +org.eclipse.cdt.debug.core.toggleBreakpointModel=com.ti.ccstudio.debug.CCSBreakpointMarker diff --git a/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs b/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs new file mode 100644 index 0000000000..83b10321a8 --- /dev/null +++ b/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs @@ -0,0 +1,10 @@ +eclipse.preferences.version=1 +encoding//Debug/applications/subdir_rules.mk=UTF-8 +encoding//Debug/applications/subdir_vars.mk=UTF-8 +encoding//Debug/driver/subdir_rules.mk=UTF-8 +encoding//Debug/driver/subdir_vars.mk=UTF-8 +encoding//Debug/makefile=UTF-8 +encoding//Debug/objects.mk=UTF-8 +encoding//Debug/sources.mk=UTF-8 +encoding//Debug/subdir_rules.mk=UTF-8 +encoding//Debug/subdir_vars.mk=UTF-8 diff --git a/bsp/ti-c6678/KeyStone.cmd b/bsp/ti-c6678/KeyStone.cmd new file mode 100644 index 0000000000..0f30bc506e --- /dev/null +++ b/bsp/ti-c6678/KeyStone.cmd @@ -0,0 +1,47 @@ +/****************************************************************************/ +/* */ +/* M6678.cmd */ +/* Copyright (c): NUDT */ +/* */ +/* */ +/* Description: This file is a sample linker command file that can be */ +/* used for linking programs built with the C compiler and */ +/* running the resulting .out file on an M6678 */ +/* device. Use it as a guideline. You will want to */ +/* change the memory layout to match your specific C6xxx */ +/* target system. You may want to change the allocation */ +/* scheme according to the size of your program. */ +/* */ +/* */ +/****************************************************************************/ + +-heap 0x800 +-stack 0x1000 + +MEMORY +{ + VECTORS: o = 0x00800000 l = 0x00000200 + LL2_CODE: o = 0x00800200 l = 0x0001FE00 + LL2_RW_DATA: o = 0x00820000 l = 0x00020000 /*set memory protection attribitue as read/write*/ +} + +SECTIONS +{ + .vecs > VECTORS + + .text > LL2_CODE + .cinit > LL2_CODE + .const > LL2_CODE + .switch > LL2_CODE + .stack > LL2_RW_DATA + GROUP + { + .neardata + .rodata + .bss + } > LL2_RW_DATA + .far > LL2_RW_DATA + .fardata > LL2_RW_DATA + .cio > LL2_RW_DATA + .sysmem > LL2_RW_DATA +} diff --git a/bsp/ti-c6678/applications/board.c b/bsp/ti-c6678/applications/board.c new file mode 100644 index 0000000000..140871fd75 --- /dev/null +++ b/bsp/ti-c6678/applications/board.c @@ -0,0 +1,60 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "board.h" +#include "trap.h" +#include "interrupt.h" +#include "drv_timer.h" +#include "KeyStone_common.h" + +#include + +/** + * This is the timer interrupt service routine. + * + */ +void rt_hw_systick_isr(void) +{ + /* enter interrupt */ + rt_interrupt_enter(); + + rt_tick_increase(); + + /* leave interrupt */ + rt_interrupt_leave(); +} + +/** + * This function will initial board. + */ +void rt_hw_board_init(void) +{ + // initial CPU core + KeyStone_common_CPU_init(); + + // initial interrupt controller + rt_hw_interrupt_init(); + + // initial system trap + rt_trap_init(); + + // initial system timer + hw_system_timer_init(); + +#ifdef RT_USING_HEAP + /* initialize memory system */ + rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); + rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); +#endif + // ...... + + hw_system_timer_start(); +} + diff --git a/bsp/ti-c6678/applications/board.h b/bsp/ti-c6678/applications/board.h new file mode 100644 index 0000000000..88e6e94e6e --- /dev/null +++ b/bsp/ti-c6678/applications/board.h @@ -0,0 +1,20 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#ifndef __BOARD_H__ +#define __BOARD_H__ + +#define RT_HW_HEAP_BEGIN (void*)0x0C000000 +#define RT_HW_HEAP_END (void*)0x0C100000 + +void rt_hw_board_init(void); + +#endif /* __BOARD_H__ */ + diff --git a/bsp/ti-c6678/applications/main.c b/bsp/ti-c6678/applications/main.c new file mode 100644 index 0000000000..fd418f09f4 --- /dev/null +++ b/bsp/ti-c6678/applications/main.c @@ -0,0 +1,99 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include +#include + +#include "board.h" + +void rt_init_thread_entry(void *parameter) +{ + + while(1) + { + rt_thread_sleep(10); + } +} + +void rt_my_thread_entry(void *parameter) +{ + while(1) + { + rt_thread_sleep(20); + } +} + +int rt_application_init(void) +{ + rt_thread_t tid; + + tid = rt_thread_create("init", rt_init_thread_entry, RT_NULL, 4096, 3, 200); + if (tid != RT_NULL) + { + rt_thread_startup(tid); + } else { + return -1; + } + /******************************************************************/ + tid = rt_thread_create("mythread", rt_my_thread_entry, RT_NULL, 4096, 3, 200); + if (tid != RT_NULL) + { + rt_thread_startup(tid); + } else { + return -1; + } + + return 0; +} + +/** + * This function will startup RT-Thread RTOS. + */ +void rtthread_startup(void) +{ + /* disable interrupt first */ + rt_hw_interrupt_disable(); + + /* init board */ + rt_hw_board_init(); + + /* show version */ + rt_show_version(); + + /* init timer system */ + rt_system_timer_init(); + + /* init scheduler system */ + rt_system_scheduler_init(); + + /* init application */ + rt_application_init(); + + /* init timer thread */ + rt_system_timer_thread_init(); + + /* init idle thread */ + rt_thread_idle_init(); + + /* start scheduler */ + rt_system_scheduler_start(); + + /* never reach here */ + return ; +} + +void main(void) +{ + /* startup RT-Thread RTOS */ + rtthread_startup(); + + for ( ; ; ); +} + diff --git a/bsp/ti-c6678/driver/KeyStone_common.c b/bsp/ti-c6678/driver/KeyStone_common.c new file mode 100644 index 0000000000..5807ed7aff --- /dev/null +++ b/bsp/ti-c6678/driver/KeyStone_common.c @@ -0,0 +1,4355 @@ +/****************************************************************************** + + Copyright (C), 2001-2012, Texas Instrument. + + ****************************************************************************** + File Name : KeyStone_common.c + Version : Initial Draft + Author : Brighton Feng + Created : 2010-12-12 + Last Modified : + Description : KeyStone common miscellaneous functions and definitions + History : + 1.Date : 2010-12-12 + Author : Brighton Feng + Modification: Created file + + 2.Date : 2012-10-6 + Author : Brighton Feng + Modification : Add memory protection and EDC configuration + + 3.Date : 2014-12-8 + Author : Brighton Feng + Modification : Add common device, CPU, interrupt initialization functions. + Print device information including device type, speed grade, + boot mode, required voltage, ID�� + Add EDMA enable/disable functions. + To support square wave generation by timer. +******************************************************************************/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include "CSL_msmc.h" +#include "CSL_msmcAux.h" +#include "KeyStone_common.h" + +/*----------------------------------------------* + * external variables * + *----------------------------------------------*/ + +/*----------------------------------------------* + * external routine prototypes * + *----------------------------------------------*/ + +/*----------------------------------------------* + * internal routine prototypes * + *----------------------------------------------*/ + +/*----------------------------------------------* + * project-wide global variables * + *----------------------------------------------*/ +CSL_XmcRegs * gpXMC_regs = (CSL_XmcRegs *) CSL_XMC_CONFIG_REGS; +CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; +CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; +CSL_PllcRegs * gpPLLC_regs = (CSL_PllcRegs * )CSL_PLL_CONTROLLER_REGS; +CSL_PscRegs * gpPSC_regs = (CSL_PscRegs *)CSL_PSC_REGS; +CSL_MsmcRegs * gpMSMC_regs = (CSL_MsmcRegs *)CSL_MSMC_CONFIG_REGS; +CSL_GpioRegs * gpGPIO_regs= (CSL_GpioRegs * )CSL_GPIO_REGS; + +CSL_CPINTCRegs* gpCIC0_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; +CSL_CPINTCRegs* gpCIC1_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_1_REGS; +/*The register pointer for the CIC routing events DSP core. +By default, it is CIC0; but for core 4~7 of C6678, it is CIC1*/ +CSL_CPINTCRegs* gpCIC_regs= (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; + +CSL_TpccRegs* gpEDMA_CC0_regs = (CSL_TpccRegs*)CSL_EDMA0CC_REGS; +CSL_TpccRegs* gpEDMA_CC1_regs = (CSL_TpccRegs*)CSL_EDMA1CC_REGS; +CSL_TpccRegs* gpEDMA_CC2_regs = (CSL_TpccRegs*)CSL_EDMA2CC_REGS; +CSL_TpccRegs* gpEDMA_CC_regs[3] = { + (CSL_TpccRegs*)CSL_EDMA0CC_REGS, + (CSL_TpccRegs*)CSL_EDMA1CC_REGS, + (CSL_TpccRegs*)CSL_EDMA2CC_REGS +}; + +CSL_TptcRegs * gpEDMA_TC_0_0_regs=(CSL_TptcRegs *) CSL_EDMA0TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_0_1_regs=(CSL_TptcRegs *) CSL_EDMA0TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_1_0_regs=(CSL_TptcRegs *) CSL_EDMA1TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_1_1_regs=(CSL_TptcRegs *) CSL_EDMA1TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_1_2_regs=(CSL_TptcRegs *) CSL_EDMA1TC2_REGS; +CSL_TptcRegs * gpEDMA_TC_1_3_regs=(CSL_TptcRegs *) CSL_EDMA1TC3_REGS; +CSL_TptcRegs * gpEDMA_TC_2_0_regs=(CSL_TptcRegs *) CSL_EDMA2TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_2_1_regs=(CSL_TptcRegs *) CSL_EDMA2TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_2_2_regs=(CSL_TptcRegs *) CSL_EDMA2TC2_REGS; +CSL_TptcRegs * gpEDMA_TC_2_3_regs=(CSL_TptcRegs *) CSL_EDMA2TC3_REGS; + +CSL_TptcRegs * gpEDMA_TC_regs[10]= { + (CSL_TptcRegs *) CSL_EDMA0TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA0TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC2_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC3_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC2_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC3_REGS +}; + +CSL_TmrPlusRegs * gpTimer0Regs = (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS; +CSL_TmrPlusRegs * gpTimer1Regs = (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS; +CSL_TmrPlusRegs * gpTimer2Regs = (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS; +CSL_TmrPlusRegs * gpTimer3Regs = (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS; +CSL_TmrPlusRegs * gpTimer4Regs = (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS; +CSL_TmrPlusRegs * gpTimer5Regs = (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS; +CSL_TmrPlusRegs * gpTimer6Regs = (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS; +CSL_TmrPlusRegs * gpTimer7Regs = (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS; +CSL_TmrPlusRegs * gpTimer8Regs = (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)); +CSL_TmrPlusRegs * gpTimerRegs[9] = { + (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS, + (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)) +}; + +/*MPU for peripherals registers and data space*/ +CSL_MpuRegs * gpMPU0_regs= (CSL_MpuRegs *)CSL_MPU_0_REGS; +CSL_MpuRegs * gpMPU1_regs= (CSL_MpuRegs *)CSL_MPU_1_REGS; +CSL_MpuRegs * gpMPU2_regs= (CSL_MpuRegs *)CSL_MPU_2_REGS; +CSL_MpuRegs * gpMPU3_regs= (CSL_MpuRegs *)CSL_MPU_3_REGS; + +CSL_Emif4fRegs * gpDDR_regs= (CSL_Emif4fRegs *)CSL_DDR3_EMIF_CONFIG_REGS; +unsigned int gDSP_Core_Speed_Hz= 1000000000; //DSP core clock speed in Hz +TDSP_Board_Type gDSP_board_type= UNKNOWN; + +/*----------------------------------------------* + * module-wide global variables * + *----------------------------------------------*/ + +/*----------------------------------------------* + * constants * + *----------------------------------------------*/ + +/*----------------------------------------------* + * macros * + *----------------------------------------------*/ + +/*----------------------------------------------* + * routines' implementations * + *----------------------------------------------*/ + +/***************************************************************************** + Prototype : KeyStone_main_PLL_init + Description : DSP core PLL configuration + DSP core will be configured to run at ref_clock_MHz*multiplier/divisor + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : + Return Value : + + History : + 1.Date : 2010-12-12 + Author : Brighton Feng + Modification : Created function + 2.Date : May 19, 2013 + Author : Brighton Feng + Modification : update parameter check; replace constant with macro + +*****************************************************************************/ +void KeyStone_main_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + unsigned int i; + + if(0==divisor) + { + puts("Error: PLL input divider = 0"); + return; + } + + if(64SECCTL & PLLCTL_BYPASS_MASK) + { + /*a. In MAINPLLCTL1, write ENSAT = 1 (for optimal PLL operation) */ + gpBootCfgRegs->CORE_PLL_CTL1 |= PLLCTL1_ENSAT_MASK; /*Set ENSAT bit = 1*/ + + /*b. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLEN_MASK; + + /*c. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLENSRC_MASK; + + /*d. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ + /*mux switches properly to the bypass) */ + for(i=0; i< 4; i++) + asm(" nop 5"); + + /*e. In SECCTL, write BYPASS = 1 (bypass enabled in PLL mux) */ + gpPLLC_regs->SECCTL |= PLLCTL_BYPASS_MASK; + + /*f. In PLLCTL, write PLLPWRDN = 1 (power down the PLL) */ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLPWRDN_MASK; //Power down the PLL + + /*g. Wait for at least 5 ��s based on the reference clock CLKIN (PLL power down */ + /*toggling time) */ + for(i=0; i< 1000; i++) + asm(" nop 5"); + + /*h. In PLLCTL, write PLLPWRDN = 0 (power up the PLL) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLPWRDN_MASK; // Power up PLL + } + else + { + /*a. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ + gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLEN_MASK); + + /*b. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ + gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLENSRC_MASK); + + /*c. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ + /*mux switches properly to the bypass) */ + for(i=0; i< 4*multiplier/divisor; i++) + asm(" nop 5"); + } + + /*4. PLLM is split in two different registers. Program PLLM[5:0] in PLL multiplier */ + /*control register (PLLM) and PLLM[12:6] in MAINPLLCTL0 register */ + /*5. BWADJ is split in two different registers. Program BWADJ[7:0] in */ + /*MAINPLLCTL0 and BWADJ[11:8] in MAINPLLCTL1 register. BWADJ value */ + /*must be set to ((PLLM + 1) >> 1) - 1) */ + /*6. Program PLLD in MAINPLLCTL0 register */ + gpBootCfgRegs->CORE_PLL_CTL0 = ((multiplier-1)<PLLM= (multiplier*2-1)&0x3F; + gpBootCfgRegs->CORE_PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; + gpBootCfgRegs->CORE_PLL_CTL1 |= (multiplier-1)>>8; /*BWADJ[11:8]*/ + + /*7. In SECCTL, write OD (Output Divide) = 1 (that is divide-by-2) */ + gpPLLC_regs->SECCTL &= ~PLLCTL_OD_MASK; + gpPLLC_regs->SECCTL |= 1<PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); + + /* Step 8b: Program the RATIO field in PLLDIVn to the desired new divide-down rate. + If RATIO field is changed, the PLL controller will flag the change in the + corresponding bit of DCHANGE*/ + gpPLLC_regs->PLLDIV1_3[3-1] = (3-1) | CSL_PLLC_PLLDIV1_3_DNEN_MASK; //Set PLLDIV3 + gpPLLC_regs->PLLDIV4_16[4-4] = (5-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV4 + gpPLLC_regs->PLLDIV4_16[7-4] = (6-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV7 + + /* Step 8c: Set GOSET bit in PLLCMD to initiate the GO operation to change the divide + values and align the SYSCLKs as programmed */ + gpPLLC_regs->PLLCMD |= CSL_PLLC_PLLCMD_GOSET_MASK; + + /*Step 8d/e: Read the GOSTAT bit in PLLSTAT to make sure the bit returns to 0 to + indicate that the GO operation has completed */ + while((gpPLLC_regs->PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); +#endif + + /*9. In PLLCTL , write PLLRST = 1 (PLL reset is asserted)*/ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLRST_MASK; + + /*10. Wait for at least 7 ��s based on the reference clock CLKIN (PLL reset time) */ + for(i=0; i< 2000; i++) + asm(" nop 5"); + + /*11. In PLLCTL, write PLLRST = 0 (PLL reset is released) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLRST_MASK; + + /*12. Wait for at least 2000 �� CLKIN cycles �� (PLLD + 1) (PLL lock time) */ + for(i=0; i< 400*multiplier; i++) + asm(" nop 5"); + + /*13. In SECCTL, write BYPASS = 0 (enable PLL mux to switch to PLL mode) */ + gpPLLC_regs->SECCTL &= ~PLLCTL_BYPASS_MASK; + + /*14. Set the PLLEN bit in PLLCTL to 1 to enable PLL mode*/ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLEN_MASK; + +} +/***************************************************************************** + Prototype : KeyStone_PLL_init + Description : Config the PLL of PA and DDR + target clock speed will be ref_clock_MHz/inputDivisor*multiplier/outputDivisor + Input : unsigned int inputDivisor + unsigned int multiplier + unsigned int outputDivisor + Output : None + Return Value : 0 for success, other value for error + + History : + 1.Date : May 18, 2013 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +int KeyStone_PLL_init (PLL_ControlRegs * PLL_Regs, unsigned int inputDivisor, + unsigned int multiplier, unsigned int outputDivisor) +{ + if(0==inputDivisor) + { + puts("Error: PLL input divider = 0"); + return 1; + } + + if(64PLL_CTL1 = PLLCTL1_ENSAT_MASK; + + /*2. In PLLCTL0, write BYPASS = 1 (set the PLL in Bypass)*/ + PLL_Regs->PLL_CTL0 |= PLLCTL_BYPASS_MASK; + + /*3. Program PLLM and PLLD in PLLCTL0 register*/ + /*4. Program BWADJ[7:0] in PLLCTL0 and BWADJ[11:8] in PLLCTL1 register. + BWADJ value must be set to ((PLLM + 1) >> 1) �C 1)*/ + PLL_Regs->PLL_CTL0 = ((multiplier/2-1)<PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; + PLL_Regs->PLL_CTL1 |= (multiplier/2-1)>>8; /*BWADJ[11:8]*/ + + /*5. In PLLCTL1, write PLLRST = 1 (PLL is reset)*/ + PLL_Regs->PLL_CTL1 |= PLLCTL1_PLLRESET_MASK; //Set RESET bit = 1 + + /*6. Wait for at least 7 us based on the reference clock (PLL reset time)*/ + TSC_delay_us(7); + + /*For PASS, In PASSPLLCTL1, write PLLSELECT = 1 + (for selecting the output of PA PLL as the input to PASS)*/ + if(PLL_Regs==(PLL_ControlRegs *)gpBootCfgRegs->PA_PLL_CTL0) + PLL_Regs->PLL_CTL1 |= PLLCTL1_PAPLL_MASK; + + /*7. In PLLCTL1, write PLLRST = 0 (PLL reset is released)*/ + PLL_Regs->PLL_CTL1 &= ~PLLCTL1_PLLRESET_MASK; //Clear RESET bit + + /*8. Wait for at least 500 * REFCLK cycles * (PLLD + 1) (PLL lock time)*/ + TSC_delay_us(500); + + /*9. In PLLCTL0, write BYPASS = 0 (switch to PLL mode)*/ + PLL_Regs->PLL_CTL0 &= ~PLLCTL_BYPASS_MASK ; + + return 0; +} +/***************************************************************************** + Prototype : KeyStone_PASS_PLL_init + Description : Config the PASS PLL + target clock speed will be ref_clock_MHz/divisor*multiplier + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : None + Return Value : + + History : + 1.Date : 2013-2-14 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_PASS_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + //output divisor for PASS PLL should be 2 + if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->PA_PLL_CTL0, + divisor, multiplier*2, 2)) + { + printf("Initialize PASS PLL clock = %.2fMHz/%dx%d = %.3fMHz\n", + ref_clock_MHz, divisor, multiplier, + ref_clock_MHz*multiplier/divisor); + } +} + +/***************************************************************************** + Prototype : KeyStone_DDR_PLL_init + Description : Config the DDR PLL + target clock speed will be ref_clock_MHz/divisor*multiplier + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : None + Return Value : + + History : + 1.Date : 2013-8-18 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_DDR_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + //output divisor for DDR PLL should be 2 + if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->DDR3_PLL_CTL0, + divisor, multiplier, 2)) + { + printf("Initialize DDR speed = %.2fMHzx/%dx%d = %.3fMTS\n", + ref_clock_MHz, divisor, multiplier, + ref_clock_MHz*multiplier/divisor); + } +} + +/*===============================TSC===================================*/ +unsigned int cycle_measure_overhead=50; +/***************************************************************************** + Prototype : calc_cycle_measure_overhead + Description : calclucate the cycles measurement overhead + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void calc_cycle_measure_overhead() +{ + unsigned int cycle_cold, cycle_warm; + cycle_cold= TSCL; + cycle_cold = TSC_getDelay(cycle_cold); + cycle_warm= TSCL; + cycle_warm = TSC_getDelay(cycle_warm); + cycle_measure_overhead = (cycle_cold + cycle_warm)/2; +} + +/***************************************************************************** + Prototype : TSC_init + Description : Initialize Time stamp counter to measure cycles + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void TSC_init() +{ + TSCL = 0; /* Enable the TSC */ + calc_cycle_measure_overhead(); +} + +/***************************************************************************** + Prototype : TSC_delay_ms + Description : Implement the delay function in millisecond + Input : Uint32 ms + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void TSC_delay_ms(Uint32 ms) +{ + volatile unsigned long long startTSC, currentTSC; + unsigned long long delay_cycles; + Uint32 tscl, tsch; + + tscl= TSCL; + tsch= TSCH; + startTSC= _itoll(tsch,tscl); + + delay_cycles= ((unsigned long long)ms*gDSP_Core_Speed_Hz/1000); + + do + { + tscl= TSCL; + tsch= TSCH; + currentTSC= _itoll(tsch,tscl); + } + while((currentTSC-startTSC)TGCR) + { + gpTimerRegs[timer_num]->TGCR= 0; + gpTimerRegs[timer_num]->TCR= 0; + } +} + + /***************************************************************************** + Prototype : Timer64_Init + Description : Initialize a 64-bit timer + Input : Timer64_Config * tmrCfg + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void Timer64_Init(Timer64_Config * tmrCfg) +{ + Reset_Timer(tmrCfg->timer_num); + + gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; + gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; + + /*please note, in clock mode, two timer periods generate a clock, + one timer period output high voltage level, the other timer period + output low voltage level, so, the timer period should be half to the + desired output clock period*/ + if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) + tmrCfg->period= tmrCfg->period/2; + + /*the value written into period register is the expected value minus one*/ + gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); + gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); + if(tmrCfg->reload_period>1) + { + gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); + gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); + } + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select watch-dog mode*/ + (CSL_TMR_TIMMODE_WDT<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK + /*for plus featuers, dual 32-bit unchained timer mode should be used*/ + |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; + } + else + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select 64-bit general timer mode*/ + (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& + ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + /*enable watchdog timer*/ + gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<WDTCR = + (CSL_TMR_WDTCR_WDKEY_CMD1<WDTCR = + (CSL_TMR_WDTCR_WDKEY_CMD2<0x3FFFFFFF) + { + printf("Enable power domain %d timeout!\n", pwrDmnNum); + return -2; + } + } + } + + /* Enable the clocks too*/ + CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_ENABLE); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Enable clock domain %d timeout!\n", moduleNum); + return -2; + } + } + + /* Return PSC status */ + if ((CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_ON) && + (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_ENABLE)) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } +} +/***************************************************************************** + Prototype : KeyStone_disable_PSC_module + Description : Disable the PSC module in KeyStone device + Input : Uint32 pwrDmnNum + Uint32 moduleNum + Output : None + Return Value : + + History : + 1.Date : 2010/2/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +Int32 KeyStone_disable_PSC_module (Uint32 pwrDmnNum, Uint32 moduleNum) +{ + Uint32 uiStartTSC= TSCL; + + /* disable the clocks*/ + CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_SWRSTDISABLE); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Disable clock domain %d timeout!\n", moduleNum); + return -2; + } + } + + /* Return PSC status */ + if (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_SWRSTDISABLE) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } + +} +/***************************************************************************** + Prototype : KeyStone_disable_PSC_Power_Domain + Description : Disable the PSC power domain + Input : Uint32 pwrDmnNum + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +Int32 KeyStone_disable_PSC_Power_Domain (Uint32 pwrDmnNum) +{ + Uint32 uiStartTSC= TSCL; + + /* Set Power domain to OFF */ + CSL_PSC_disablePowerDomain (pwrDmnNum); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Disable power domain %d timeout!\n", pwrDmnNum); + return -2; + } + } + + /* Return PSC status */ + if (CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_OFF) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } + +} + +/*============================EDMA=====================================*/ + /***************************************************************************** + Prototype : EDMA_channel_TC_cfg + Description : Setup uiChannel of an EDMA to use uiTC + Input : Uint32 uiCC + Uint32 uiChannel + Uint32 uiTC + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_channel_TC_cfg (Uint32 uiCC, + Uint32 uiChannel, Uint32 uiTC) +{ + gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8] = + (gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8]&(~(0xF<<((uiChannel&7)*4)))) + |(uiTC<<((uiChannel&7)*4)); +} +/***************************************************************************** + Prototype : EDMA_TC_priority_cfg + Description : Setup uiChannel of an EDMA TC priority + Input : Uint32 uiCC + Uint32 uiPri + Uint32 uiTC + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_TC_priority_cfg(Uint32 uiCC, + Uint32 uiPri, Uint32 uiTC) +{ + gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI= + (gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI&(~(0xF<<((uiTC&3)*4)))) + |(uiPri<<((uiTC&3)*4)); +} +/***************************************************************************** + Prototype : EDMA_init + Description : Initialize all EDMA registers and clear the event + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_init () +{ + int i; + unsigned int * uipPaRAM; + + /*clear PaRAM*/ + uipPaRAM= (unsigned int *)&(gpEDMA_CC0_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC0_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + uipPaRAM= (unsigned int *)&(gpEDMA_CC1_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC1_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + uipPaRAM= (unsigned int *)&(gpEDMA_CC2_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC2_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + /*Assign PaRAM for different channels*/ + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + /*Assign TC/Queue for different channels*/ + gpEDMA_CC0_regs->TPCC_DMAQNUM[0]= 0x10101010; + gpEDMA_CC0_regs->TPCC_DMAQNUM[1]= 0x10101010; + + gpEDMA_CC1_regs->TPCC_DMAQNUM[0]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[1]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[2]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[3]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[4]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[5]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[6]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[7]= 0x32103210; + + gpEDMA_CC2_regs->TPCC_DMAQNUM[0]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[1]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[2]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[3]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[4]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[5]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[6]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[7]= 0x32103210; + + /*clear any events and status*/ + gpEDMA_CC0_regs->TPCC_ECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_EECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_ICR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_IECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_EMCR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_QEMCR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_SECR= 0xFFFF; + + gpEDMA_CC1_regs->TPCC_ECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ICR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ICRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_IECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_IECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EMCR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EMCRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_QEMCR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC1_regs->TPCC_SECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_SECRH= 0xFFFFFFFF; + + gpEDMA_CC2_regs->TPCC_ECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ICR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ICRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_IECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_IECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EMCR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EMCRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_QEMCR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC2_regs->TPCC_SECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_SECRH= 0xFFFFFFFF; + + for(i=0; iTPTC_ERRCLR= 0xF; + + //enable error interrupt + gpEDMA_TC_regs[i]->TPTC_ERREN= + (1<TPCC_EESR= 1<<(uiChannel); + } + else + { + //enable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EESRH= 1<<(uiChannel-32); + } +} + +void EDMA_event_disable(Uint32 uiCC, Uint32 uiChannel) +{ + if(uiChannel<32) + { + //disable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EECR= 1<<(uiChannel); + } + else + { + //disable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EECRH= 1<<(uiChannel-32); + } +} + +void EDMA_interrupt_enable(Uint32 uiCC, Uint32 uiIntNum) +{ + if(uiIntNum<32) + { + //enable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IESR= 1<<(uiIntNum); + } + else + { + //enable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IESRH= 1<<(uiIntNum-32); + } +} + +void EDMA_interrupt_disable(Uint32 uiCC, Uint32 uiIntNum) +{ + if(uiIntNum<32) + { + //disable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IECR= 1<<(uiIntNum); + } + else + { + //disable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IECRH= 1<<(uiIntNum-32); + } +} + +/***************************************************************************** + Prototype : EDMA_wait + Description : wait the pending EDMA complete + Input : EDMA_CC_Channel_Num CC_channel + Output : None + Return Value : + + History : + 1.Date : 2012/10/30 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_wait(EDMA_CC_Channel_Num CC_channel) +{ + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + + if(uiChannel<32) + { + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + } + else + { + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannel -= 32; + } + + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannel)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannel); +} + +/***************************************************************************** + Prototype : EDMA_Copy + Description : EDMA copy function with manual trigger + Input : unsigned int srcAddr + unsigned int dstAddr + unsigned int byteCount, <64KB + EDMA_CC_Channel_Num CC_channel + DMA_Wait wait + Output : None + Return Value : + + History : + 1.Date : 2012/10/30 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_copy(unsigned int srcAddr, unsigned int dstAddr, + unsigned int byteCount, EDMA_CC_Channel_Num CC_channel, DMA_Wait wait) +{ + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel; + volatile Uint32 * TPCC_ESR; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + + EDMACCRegs->PARAMSET[uiChannel].OPT= + CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, + CSL_EDMA3_TCCH_DIS, + CSL_EDMA3_ITCINT_DIS, + CSL_EDMA3_TCINT_EN, + uiChannel, + CSL_EDMA3_TCC_NORMAL, + CSL_EDMA3_FIFOWIDTH_NONE, + CSL_EDMA3_STATIC_DIS, + CSL_EDMA3_SYNC_A, + CSL_EDMA3_ADDRMODE_INCR, + CSL_EDMA3_ADDRMODE_INCR); + EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(srcAddr); + EDMACCRegs->PARAMSET[uiChannel].A_B_CNT=CSL_EDMA3_CNT_MAKE(byteCount&0xFFFF, 1); + EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(dstAddr); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 1); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; + + if(uiChannel<32) + { + TPCC_ESR= &EDMACCRegs->TPCC_ESR; + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + } + else + { + TPCC_ESR= &EDMACCRegs->TPCC_ESRH; + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannel -= 32; + } + + /*Manually trigger the EDMA*/ + (*TPCC_ESR)= 1<<(uiChannel); + + if(wait) + { + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannel)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannel); + } +} + +/***************************************************************************** + Prototype : EDMA_fill + Description : EDMA fill function with manual trigger + Input : unsigned int address, must align to 8 bytes boundary + unsigned long long data + unsigned int byteCount, must be multiple of 8 + EDMA_CC_Channel_Num CC_channel + Output : None + Return Value : + + History : + 1.Date : 2013/8/11 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_fill(unsigned int address, unsigned long long data, + unsigned int byteCount, EDMA_CC_Channel_Num CC_channel) +{ + int i; + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel, uiChannelShift, uiBCNT; + volatile Uint32 * TPCC_ESR; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + unsigned long long tempBuf[128/8]; + Uint32 tempBufSize=128, headerSize, tailSize; + + if(tempBufSize>byteCount) + tempBufSize=byteCount; + + for(i=0; i< tempBufSize/8; i++) + tempBuf[i]= data; + + /*split the transfer into 3 sections at 128 byte boundary*/ + if(address&127) //header address not start on 128 byte boundary + { + headerSize= 128- (address&127); + if(headerSize>byteCount) + headerSize=byteCount; + EDMA_copy((Uint32)tempBuf, address, headerSize, CC_channel, DMA_WAIT); + address+= headerSize; + byteCount-= headerSize; + } + + if(byteCount&&((address+byteCount)&127))//tail address not start on 128 byte boundary + { + tailSize= (address+byteCount)&127; + EDMA_copy((Uint32)tempBuf, address+byteCount-tailSize, tailSize, CC_channel, DMA_WAIT); + byteCount-= tailSize; + } + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + if(uiChannel<32) + { + TPCC_ESR= &EDMACCRegs->TPCC_ESR; + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + uiChannelShift= uiChannel; + } + else + { + TPCC_ESR= &EDMACCRegs->TPCC_ESRH; + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannelShift= uiChannel - 32; + } + + EDMACCRegs->PARAMSET[uiChannel].OPT= + CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, + CSL_EDMA3_TCCH_DIS, + CSL_EDMA3_ITCINT_DIS, + CSL_EDMA3_TCINT_EN, + uiChannel, + CSL_EDMA3_TCC_NORMAL, + CSL_EDMA3_FIFOWIDTH_NONE, + CSL_EDMA3_STATIC_EN, //keep PARAM unchanged + CSL_EDMA3_SYNC_AB, + CSL_EDMA3_ADDRMODE_INCR, + CSL_EDMA3_ADDRMODE_INCR); + EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(tempBuf); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= CSL_EDMA3_BIDX_MAKE(0, 128); + EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 0); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; + + while(byteCount) //the reminding must be multiple of 128 bytes + { + uiBCNT= byteCount/128; + if(uiBCNT>65535) + uiBCNT= 65535; + + EDMACCRegs->PARAMSET[uiChannel].A_B_CNT= CSL_EDMA3_CNT_MAKE(128, uiBCNT); + EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(address); + + /*Manually trigger the EDMA*/ + (*TPCC_ESR)= 1<<(uiChannelShift); + + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannelShift)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannelShift); + + byteCount -= uiBCNT*128; + address += uiBCNT*128; + } +} + +/***************************************************************************** + Prototype : IDMA_wait + Description : wait the pending IDMA complete + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void IDMA_wait() +{ + /* Wait until copying is completed */ + while (gpCGEM_regs->IDMA1_STAT); +} +/***************************************************************************** + Prototype : IDMA_copy + Description : implement the data copy via IDMA + Input : unsigned int srcAddr + unsigned int dstAddr + unsigned int byteCount, <64KB + IDMA_Wait wait + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brigthon + Modification : Created function + +*****************************************************************************/ +void IDMA_copy(unsigned int srcAddr, unsigned int dstAddr, + unsigned int byteCount, DMA_Wait wait) +{ + gpCGEM_regs->IDMA1_SOURCE= srcAddr; + gpCGEM_regs->IDMA1_DEST= dstAddr; + gpCGEM_regs->IDMA1_COUNT= byteCount&0xFFFC; + + if(wait) + { + /* Wait until copying is completed */ + while (gpCGEM_regs->IDMA1_STAT); + } +} +/***************************************************************************** + Prototype : EDMA_CC_error_handler + Description : Edma channel controller error processing + Input : Uint32 edmaNum, EDMA module number (0~2) + Output : None + Return Value : + + History : + 1.Date : 2012/11/7 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_CC_error_handler(Uint32 edmaNum) +{ + int i; + CSL_TpccRegs* EDMACCRegs= gpEDMA_CC_regs[edmaNum]; + Uint32 EMR, EMRH= 0, QEMR, CCERR; + + //read error status + EMR= EDMACCRegs->TPCC_EMR; + QEMR= EDMACCRegs->TPCC_QEMR; + CCERR= EDMACCRegs->TPCC_CCERR; + exception_record.status.ext_sts.info.edma.CC_info.EMR= EMR; + exception_record.status.ext_sts.info.edma.CC_info.QEMR= QEMR; + exception_record.status.ext_sts.info.edma.CC_info.CCERR= CCERR; + + //clear error status + EDMACCRegs->TPCC_EMCR= EMR; + EDMACCRegs->TPCC_QEMCR= QEMR; + EDMACCRegs->TPCC_CCERRCLR= CCERR; + + //channel 32~63 for EDMA CC1 and CC2 + if(0TPCC_EMRH; + exception_record.status.ext_sts.info.edma.CC_info.EMRH= EMRH; + + //clear error status + EDMACCRegs->TPCC_EMCRH= EMRH; + } + + for(i=0; i<32; i++) + { + if((EMR>>i)&1) + printf(" EDMA Channel %d event missed.\n", i); + if((EMRH>>i)&1) + printf(" EDMA Channel %d event missed.\n", i+32); + } + + for(i=0; i<8; i++) + { + if((QEMR>>i)&1) + printf(" QDMA Channel %d event missed.\n", i); + } + + for(i=0; i<4; i++) + { + if((CCERR>>i)&1) + printf(" Queue %d Watermark/threshold has been exceeded.\n", i); + } + + if(CCERR&CSL_TPCC_TPCC_CCERR_TCCERR_MASK) + puts(" Total number of allowed TCCs has been reached."); + +} +/***************************************************************************** + Prototype : EDMA_TC_error_handler + Description : Edma transfer controller error processing + Input : CSL_TptcRegs * edmaTCRegs + Output : None + Return Value : + + History : + 1.Date : 2012/11/7 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_TC_error_handler(CSL_TptcRegs * edmaTCRegs) +{ + Uint32 ERRSTAT, ERRDET, STAT; + + //read error status + ERRSTAT= edmaTCRegs->TPTC_ERRSTAT; + ERRDET= edmaTCRegs->TPTC_ERRDET; + exception_record.status.ext_sts.info.edma.TC_info.ERRSTAT=ERRSTAT ; + exception_record.status.ext_sts.info.edma.TC_info.ERRDET= ERRDET; + + //clear error + edmaTCRegs->TPTC_ERRCLR= ERRSTAT; + + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_MMRAERR_MASK) + puts(" User attempted to read or write to an invalid address in configuration memory map."); + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_TRERR_MASK) + puts(" TR detected that violates constant addressing mode transfer (SAM or DAM is set) alignment rules or has ACNT or BCNT== 0."); + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_BUSERR_MASK) + { + puts(" EDMA3TC has detected an error at source or destination address."); + + STAT= ERRDET&CSL_TPTC_TPTC_ERRDET_STAT_MASK; + + if(STAT>=8) + printf(" write error (%d). ",STAT); + else if(STAT>=1) + printf(" read error (%d). ",STAT); + else + printf(" no error!?"); + + printf("TCC= %d. TCINTEN= %d. TCCHEN= %d\n", + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCC_MASK)>>CSL_TPTC_TPTC_ERRDET_TCC_SHIFT, + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCINTEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCINTEN_SHIFT, + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCCHEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCCHEN_SHIFT); + } + +} +/***************************************************************************** + Prototype : EDMA_error_handler + Description : EDMA error processing function + Input : Uint32 edmaNum + Uint32 errorFlag + error flag bit fields are defined as below + (follow the sequence in CIC) + 0 EDMACC_ERRINT EDMA3CC error interrupt + 2 EDMATC_ERRINT0 EDMA3TC0 error interrupt + 3 EDMATC_ERRINT1 EDMA3TC1 error interrupt + 4 EDMATC_ERRINT2 EDMA3TC2 error interrupt + 5 EDMATC_ERRINT3 EDMA3TC3 error interrupt + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_error_handler(Uint32 edmaNum, Uint32 errorFlag) +{ + int i; + + printf(" EDMA module %d error\n", edmaNum); + if(errorFlag&1) + EDMA_CC_error_handler(edmaNum); + + errorFlag >>= 2; + + for(i=0; i<4; i++) + { + if(errorFlag&(1<MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; + } + + /*3. Write a 1 to the LOCK field of the MPLKCMD register. This engages the lock.*/ + gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); +} + +/***************************************************************************** + Prototype : unlock_mem_prot_regs + Description : unlock memory protection registers + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma CODE_SECTION (unlock_mem_prot_regs, ".text:Core_MPAX") +void unlock_mem_prot_regs() +{ + int i; + + /*1. Write a 1 to the KEYR field in the MPLKCMD register. This resets some internal + status for the MPLK0 through the MPLK3 registers.*/ + gpCGEM_regs->MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; + } + + /*3. Write a 1 to the UNLOCK field in the MPLKCMD register. If the key written in + step 2 matches the stored key, the hardware disengages the lock. If the key written + in step 2 does not match, the hardware signals an exception. The hardware + reports the fault address as the address of the MPLKCMD register.*/ + gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); +} + +/***************************************************************************** + Prototype : L1_MPPA_setup + Description : setup the memory protection for local L1 memory + Input : volatile Uint32 MPPA_regs[], Uint32 MPPA[] + Output : None + Return Value : + +usage example: + Uint32 MPPA[16]= + { + MP_LOCAL|MP_SR|MP_UR, //page 0 for read only + MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for read/write + ...... + } + ...... + L1_MPPA_setup(gpCGEM_regs->L1PMPPA, MPPA); + + History : + 1.Date : 2012/12/6 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1_MPPA_setup(volatile Uint32 MPPA_regs[], Uint32 MPPA[]) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1PMPFCR = 1; + gpCGEM_regs->L1DMPFCR = 1; + + /*setup the memory protection attributes for 32 pages*/ + for(i=0; i<16; i++) + { + MPPA_regs[i] = MPPA[i]; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1P_memory_protection_cfg + Description : config "AccessPermisionMask" for L1P + Input : Uint32 AccessPermisionMask + Output : None + Return Value : +*****************************************************************************/ +void L1P_memory_protection_cfg(Uint32 AccessPermisionMask) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1PMPFCR = 1; + + /*set L1P only for cacheable local execution, disable all external access*/ + for(i=0; i<16; i++) + { + gpCGEM_regs->L1PMPPA[i] = AccessPermisionMask; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1D_memory_protection_cfg + Description : config "AccessPermisionMask" for L1P + Input : Uint32 AccessPermisionMask + Output : None + Return Value : +*****************************************************************************/ +void L1D_memory_protection_cfg(Uint32 AccessPermisionMask) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1DMPFCR = 1; + + /*set L1P only for cacheable local execution, disable all external access*/ + for(i=0; i<16; i++) + { + gpCGEM_regs->L1DMPPA[i] = AccessPermisionMask; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1_cache_protection + Description : protect L1 as cache + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1_cache_protection() +{ + /*set L1P only for cacheable local execution, disable all external access*/ + L1P_memory_protection_cfg(0); + + /*set L1D only for cacheable local read/write, disable all external access*/ + L1D_memory_protection_cfg(0); +} + + +/***************************************************************************** + Prototype : LL2_MPPA_setup + Description : setup the memory protection for local L2 memory + Input : Uint32 MPPA[] + Output : None + Return Value : +usage example: + Uint32 MPPA[32]= + { + MP_LOCAL|MP_SX|MP_UX, //page 0 for local code only + MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for local data only + ...... + } + ...... + LL2_MPPA_setup(MPPA); + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_MPPA_setup(Uint32 MPPA[]) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L2MPFCR = 1; + + /*setup the memory protection attributes for 32 pages*/ + for(i=0; i<32; i++) + { + gpCGEM_regs->L2MPPA[i] = MPPA[i]; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : LL2_Memory_Protection_cfg + Description : config "AccessPermisionMask" for local L2 memory section from + "startAddress" with "byteCount" size + Input : Uint32 startAddress + Uint32 byteCount + Uint32 AccessPermisionMask + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_Memory_Protection_cfg(Uint32 startAddress, + Uint32 byteCount, Uint32 AccessPermisionMask) +{ + int i; + Uint32 uiEndAddress; + Uint32 uiPageIndex, uiNumPages, uiPageSize, uiPageAddressMask, uiPageShift; + TDSP_Board_Type DSP_Board_Type; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + DSP_Board_Type = KeyStone_Get_dsp_board_type(); + + /*L2 memory protection size is 32KB for TCI6614, C6670, + it is 16KB for C6678*/ + uiPageSize= 32*1024; + uiPageAddressMask= 32*1024-1; + uiPageShift= 15; + if(C6678_EVM == DSP_Board_Type) + { + uiPageSize= 16*1024; + uiPageAddressMask= 16*1024-1; + uiPageShift= 14; + } + + if(startAddress>=0x10800000) + { + printf("LL2 memory protection start Address 0x%x is not a local address\n", + startAddress); + startAddress &= 0xFFFFFF; /*convert to local address*/ + } + uiEndAddress= startAddress+ byteCount; + + if(startAddress&uiPageAddressMask) + { + printf("LL2 memory protection start Address 0x%x does not align to page boundary\n", + startAddress); + startAddress &= (~uiPageAddressMask); + } + uiPageIndex= (startAddress-0x800000)>>uiPageShift; + + byteCount= uiEndAddress- startAddress; + if(byteCount&uiPageAddressMask) + { + printf("LL2 memory protection section size 0x%x is not multiple of page size\n", + byteCount); + byteCount = (byteCount+uiPageSize)&(~uiPageAddressMask); + } + uiNumPages= byteCount>>uiPageShift; + + for(i= 0; iL2MPPA[uiPageIndex+i] = AccessPermisionMask; + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : KeyStone_CorePac_AID_map + Description : map CorePac AID to PrivID: + map_table[0] assign the PrivID for AID0, + map_table[1] assign the PrivID for AID1 + ...... + map_table[5] assign the PrivID for AID5 + Input : Uint8 map_table[] + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_CorePac_AID_map(Uint8 map_table[]) +{ + int i; + Uint32 *PAMAP= (Uint32 *)&(gpCGEM_regs->PAMAP0); + + /*map all PrivID to AIDx by default*/ + for(i=0; i<16; i++) + PAMAP[i]= CSL_CGEM_PAMAP0_AID_MASK; + + /*map AID0~AID5*/ + for(i=0; i<6; i++) + { + if(map_table[i]<16) /*PrivID must be less than 16*/ + PAMAP[map_table[i]]= i; + } +} + +/***************************************************************************** + Prototype : KeyStone_PrivID_Remap + Description : privilege ID remap to AID + Input : int privID + int AID + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_PrivID_Remap(int privID, int AID) +{ + volatile unsigned int * pamapReg = NULL; + unsigned int val = 0; + + pamapReg = (volatile unsigned int *)(&gpCGEM_regs->PAMAP0 + privID); + + if(AID >= MAX_AID_NUM) + AID = 0; + val = *pamapReg; + + val &= (~CSL_CGEM_PAMAP0_AID_MASK); + + val |= ((AID<>4)) + { + printf("Segment replacement address 0x%x does not start from power-of-2 boundary corresponds to segment size 0x%x.\n", + RADDR, SegementSize); + RADDR &= (~(SegSizeMask>>4)); + printf("Extended replacement address to 0x%x.\n", RADDR); + } + + MPAX_regs->MPAXH= BADDR|(SegSizeBits-1); + MPAX_regs->MPAXL= RADDR|AccessPermisionMask; + +} + +/***************************************************************************** + Prototype : KeyStone_XMC_MPAX_setup + Description : configure multiple MPAX segments in XMC with a configuration + table. + Please note, the code of this function or the data used by this function + (stack, parameters...) can not be put in the segment that will be modified + by this function. Normally, to put this function and its related data in + LL2 is a good idea. + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma CODE_SECTION (KeyStone_XMC_MPAX_setup, ".text:Core_MPAX") +void KeyStone_XMC_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs) +{ + int i; + + if(firstSeg >= 16) + { + printf("The XMC MPAX segment number %d >= 16, not supported.\n ", firstSeg); + return; + } + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*CAUTION: + A MPAX segment can only be modified when there is no access to the space + of this segment. Any data in cache or prefetch buffer from the space of this + segment must be writeback and invalidated before the segment modification. + It is recommended to configure the MPAX at the very beginning of application + software before any shared memory is used. Code and data for CorePac MPAX + configuration should be allocated in LL2. + If a MPAX segment must be modified on-the-fly, the safer way is, to write + the new configuration to a unused higher segment, and then clear the old + segment. This is based on the fact that higher numbered segments take + precedence over lower numbered segments. */ + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + _mfence(); + _mfence(); //ensure all writeback invalidate have completed. + + for(i=numSegs-1; i>=0 ; i--) + { + KeyStone_MPAX_seg_setup((MPAX_Regs *)&gpXMC_regs->XMPAX[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : KeyStone_SMS_MPAX_setup + Description : configure multiple MPAX segments in SMS of MSMC with a conf- + iguration table + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Uint32 PrivID + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SMS_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) +{ + int i; + + if( gpMSMC_regs->SMS_MPAX_LCKSTAT&(1<=0 ; i--) + KeyStone_MPAX_seg_setup( + (MPAX_Regs *)&gpMSMC_regs->SMS_MPAX_PER_PRIVID[PrivID].SMS[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + + CSL_MSMC_lockSMS(PrivID); +} + +/***************************************************************************** + Prototype : KeyStone_SES_MPAX_setup + Description : configure multiple MPAX segments in SES of MSMC with a conf- + iguration table + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Uint32 PrivID + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SES_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) +{ + int i; + + if( gpMSMC_regs->SES_MPAX_LCKSTAT&(1<=0 ; i--) + KeyStone_MPAX_seg_setup( + (MPAX_Regs *)&gpMSMC_regs->SES_MPAX_PER_PRIVID[PrivID].SES[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + + CSL_MSMC_lockSES(PrivID); +} + +/***************************************************************************** + Prototype : KeyStone_MSMC_MP_interrupt_en + Description : Enable MSMC Memory protection error interrupt for PrivIDs + indicated by "PRIVID_MASK" + Input : Uint32 PRIVID_MASK + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_MSMC_MP_interrupt_en(Uint32 PRIVID_MASK) +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /*clear MP fault record*/ + gpMSMC_regs->SMPFCR = 1; + + /*clear interrupt error status flag*/ + gpMSMC_regs->SMIRC = (PRIVID_MASK)<SMIESTAT |= (PRIVID_MASK<> + CSL_CGEM_L2MPFSR_FID_SHIFT; + + printf(" memory protection exception caused by master with ID %d at 0x%x\n", + master_id, MPFAR); + } + + if (MPFSR & CSL_CGEM_L2MPFSR_UX_MASK) { + puts(" User Execute violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_UW_MASK) { + puts(" User Write violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_UR_MASK) { + puts(" User Read violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SX_MASK) { + puts(" Supervisor Execute violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SW_MASK) { + puts(" Supervisor Write violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SR_MASK) { + puts(" Supervisor Read violation"); + } + +} + +/***************************************************************************** + Prototype : KeyStone_MSMC_protection_exception_handler + Description : MSMC memory protection processing + Input : None + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_MSMC_protection_exception_handler() +{ + unsigned int master_id; + unsigned int priv_id; + unsigned int address; + unsigned int NM; + + address = gpMSMC_regs->SMPFAR; + + master_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FMSTID_MASK)>> + CSL_MSMC_SMPFR_FMSTID_SHIFT; + priv_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FPID_MASK)>> + CSL_MSMC_SMPFR_FPID_SHIFT; + + exception_record.status.ext_sts.info.memory.fault_address= address; + exception_record.status.ext_sts.info.memory.fault_status.SMPFR= gpMSMC_regs->SMPFR; + + NM = (gpMSMC_regs->SMPFXR & CSL_MSMC_SMPFXR_NM_MASK) >> CSL_MSMC_SMPFXR_NM_SHIFT; + + printf(" memory protection exception caused by master %d (PrivID= %d) at address 0x%x\n", + master_id, priv_id, address); + + if(1 == NM) + { + printf(" Fault is caused by the address not matching any of the segment BADDR\n"); + } + + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + /*clear fault record*/ + gpMSMC_regs->SMPFCR = 1; + /*clear interrupt error status flag*/ + gpMSMC_regs->SMIRC = (1<PROG_START_ADDRESS = uiStartAddress; + MPPA_regs->PROG_END_ADDRESS = uiEndAddress; + MPPA_regs->PROG_MPPA = AccessPermisionMask; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_setup + Description : peripherals MPU ranges configuration + Input : Uint32 uiMPU_num: number of the MPU to be setup + MPU_Range_Config MPU_cfg[]: MPU ranges configuration table + Uint32 numRangeCfg: number of ranges to be configured + Output : None + Return Value : + + History : + 1.Date : 2012/12/15 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_MPU_setup(Uint32 uiMPU_num, + MPU_Range_Config MPU_cfg[], Uint32 numRangeCfg) +{ + int i; + unsigned int mpuNumProgmableRange; + CSL_MpuRegs * mpuRegs; + + /*For Turbo Nyquist, add following code to modify initial value, + Or user can modify the initail values directly*/ + if(5==uiMPU_num) + TN_MPU5_constant(); + + mpuRegs= gpMPU_regs[uiMPU_num]; + + mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; + if(mpuNumProgmableRange == 0) + { + mpuNumProgmableRange = 16; + } + + if(numRangeCfg>mpuNumProgmableRange) + { + printf("MPU %d programmable ranges %d < %d.\n", + uiMPU_num, mpuNumProgmableRange, numRangeCfg); + numRangeCfg=mpuNumProgmableRange; + } + else if(numRangeCfg gstruMpuAddrRange[uiMPU_num].EndAddr) ) + { + printf("The configuration address is out of MPU %d protection range\n", + uiMPU_num); + continue; + } + + KeyStone_MPU_range_setup(&mpuRegs->PROG_REGION[i], + MPU_cfg[i].StartAddr, MPU_cfg[i].EndAddr, + MPU_cfg[i].AccessPermisionMask); + + } + + //clear unused ranges + for( ;iPROG_REGION[i].PROG_MPPA = 0; + } + + //clear status + mpuRegs->FAULT_CLEAR = 1; + mpuRegs->INT_ENABLED_STATUS_CLEAR = + CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK + |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; + + /* enable the interrupt */ + mpuRegs->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK + | CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; + + return; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_MPPA_modify + Description : search the range which match a address and then modify + the access permission of that range. + Input : Uint32 uiMPU_num: number of the MPU to be modifed + Uint32 uiAddress: address which need modify permision + Uint32 AccessPermisionMask: permission mask for that range + Output : None + Return Value : + + History : + 1.Date : 2012/12/13 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_MPU_MPPA_modify(Uint32 uiMPU_num, + Uint32 uiAddress, Uint32 AccessPermisionMask) +{ + int i; + unsigned int mpuNumProgmableRange; + CSL_MpuRegs * mpuRegs; + + /*For Turbo Nyquist, add following code to modify initial value, + Or user can modify the initail values directly*/ + if(5==uiMPU_num) + TN_MPU5_constant(); + + mpuRegs= gpMPU_regs[uiMPU_num]; + + mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; + if(mpuNumProgmableRange == 0) + { + mpuNumProgmableRange = 16; + } + + /*search through all ranges*/ + for(i=0; i< mpuNumProgmableRange; i++) + { + /*match with one range*/ + if((uiAddress >= mpuRegs->PROG_REGION[i].PROG_START_ADDRESS) + &&(uiAddress <= mpuRegs->PROG_REGION[i].PROG_END_ADDRESS)) + { + mpuRegs->PROG_REGION[i].PROG_MPPA = AccessPermisionMask; + return; + } + } + + printf("address 0x%08x does not match any range in MPU %d\n", + uiAddress, uiMPU_num); + + return; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_interrupts_enable + Description : enable the all MPU interrupts + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_MPU_interrupt_enable(Uint32 uiMPU_num) +{ + if((gpMPU_regs[uiMPU_num]->REVISION&0xFFFF0000)!= + (CSL_MPU_REVISION_RESETVAL&0xFFFF0000)) + { + printf("Can't read MPU%d ID register, make sure corresponding power domain is enabled.", uiMPU_num); + return; + } + + gpMPU_regs[uiMPU_num]->FAULT_CLEAR = 1; + gpMPU_regs[uiMPU_num]->INT_ENABLED_STATUS_CLEAR = + CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK + |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; + gpMPU_regs[uiMPU_num]->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK + |CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; + +} +void KeyStone_MPU_interrupts_enable() +{ + int i; + TDSP_Board_Type DSP_Board_Type = KeyStone_Get_dsp_board_type(); + + TN_MPU5_constant(); + + for(i=0; i<4; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + + if((C6670_EVM== DSP_Board_Type) + ||(TCI6614_EVM== DSP_Board_Type)) + { + for(i=4; i<6; i++) + { + /*MPU5 (for BCP) of TCI6614 is only accessible + when BCP is enabled through PSC*/ + if((5==i)&&(TCI6614_EVM== DSP_Board_Type)&& + ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || + (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) + { + puts("Enable power domain for MPU5 before configure it."); + continue; + } + + KeyStone_MPU_interrupt_enable(i); + } + } + + if(TCI6614_EVM== DSP_Board_Type) + { + for(i=6; i<8; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + } + + return; +} + +char * Peri_MPU_err_type_str[]= +{ + "User execution fault!", + "User write fault!", + "User read fault!", + "Supervisor execution fault!", + "Supervisor write fault!", + "Supervisor read fault!" +}; + +char * Ns_str[]= +{ + "secure", + "non-secure" +}; +/***************************************************************************** + Prototype : KeyStone_peripherals_MPU_fault_status + Description : Print the MPU error information + Input : unsigned int uwFltStatus + unsigned int uwFltAddr + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_peripherals_MPU_fault_status(unsigned int uwFltStatus, + unsigned int uwFltAddr) +{ + unsigned int MSTID; + unsigned int PRIVID; + unsigned int NS; + unsigned int FaultType; + unsigned int BitsCnt; + + MSTID = (uwFltStatus & CSL_MPU_FAULT_STATUS_MSTID_MASK)>>CSL_MPU_FAULT_STATUS_MSTID_SHIFT; + PRIVID = (uwFltStatus & CSL_MPU_FAULT_STATUS_PRIVID_MASK)>>CSL_MPU_FAULT_STATUS_PRIVID_SHIFT; + NS = (uwFltStatus & CSL_MPU_FAULT_STATUS_NS_MASK)>>CSL_MPU_FAULT_STATUS_NS_SHIFT; + printf(" The MSTID %d (PRIVID %d) triggered MPU error at 0x%x with %s access\n", + MSTID, PRIVID, uwFltAddr, Ns_str[NS]); + + FaultType = (uwFltStatus & CSL_MPU_FAULT_STATUS_FAULT_TYPE_MASK) >> CSL_MPU_FAULT_STATUS_FAULT_TYPE_SHIFT; + if(1==(_dotpu4(_bitc4(FaultType), 0x01010101))) + { + BitsCnt= 31 - _lmbd(1, FaultType); + printf(" %s\n",Peri_MPU_err_type_str[BitsCnt]); + } + else if(0x3F == FaultType) + { + puts(" Relaxed cache line fill fault!"); + } + else if(0x12 == FaultType) + { + puts(" Relaxed cache write back fault!"); + } +} +/***************************************************************************** + Prototype : KeyStone_peripherals_MPU_excepiton_handler + Description : peripheral MPU processing + Input : Uint32 uwMpuNum + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_peripherals_MPU_excepiton_handler(Uint32 uwMpuNum) +{ + Uint32 uwStatus; + Uint32 uwFltAddr; + Uint32 uwFltStatus; + CSL_MpuRegs *pstruMpuRegs= gpMPU_regs[uwMpuNum]; + + uwStatus = pstruMpuRegs->INT_ENABLED_STATUS_CLEAR; + if(uwStatus & 0x2) + { + printf(" MPU %d address violation error\n", uwMpuNum); + pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 2; + } + + if(uwStatus & 0x1) + { + printf(" MPU %d protection violation error\n", uwMpuNum); + pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 1; + } + + uwFltAddr = pstruMpuRegs->FAULT_ADDRESS; + uwFltStatus = pstruMpuRegs->FAULT_STATUS; + exception_record.status.ext_sts.info.memory.fault_address= uwFltAddr; + exception_record.status.ext_sts.info.memory.fault_status.MPU_FAULT_STATUS= uwFltStatus; + + KeyStone_peripherals_MPU_fault_status(uwFltStatus,uwFltAddr); + pstruMpuRegs->FAULT_CLEAR = 1; + + pstruMpuRegs->EOI = 0; +} + + +/*======================memory EDC=====================================*/ +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_enable + Description : Enable MSMC EDC + Input : scrubCnt, number of MSMC clock cycles between scrubbing + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_enable(Uint32 scrubCnt) +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /*Software must wait for the PRR (Parity RAM Ready) bit before making + the first read access to MSMC RAM after reset.*/ + while(0==(gpMSMC_regs->SMEDCC&CSL_MSMC_SMEDCC_PRR_MASK)); + + /* set scrubbing period value */ + if(scrubCnt>255) + scrubCnt= 255; + CSL_MSMC_setCounterBankRefreshRead(scrubCnt); //the scrubbing engine works every scrubCnt*1024 cycle*/ + + /* clear EDC errors and enable EDC event*/ + gpMSMC_regs->SMIRC = 0xf; + gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK + | CSL_MSMC_SMIESTAT_CSIE_MASK + | CSL_MSMC_SMIESTAT_NCEIE_MASK + | CSL_MSMC_SMIESTAT_CEIE_MASK); + + //enable SL2 EDC + CSL_MSMC_setECM(1); + + CSL_MSMC_lockNonMPAX(); +} + +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_interrupt_en + Description : Enable MSMC EDC error interrupt + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_interrupt_en() +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /* clear EDC errors*/ + gpMSMC_regs->SMIRC = 0xf; + + /* Enable EDC error interrupt */ + gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK + | CSL_MSMC_SMIESTAT_CSIE_MASK + | CSL_MSMC_SMIESTAT_NCEIE_MASK + | CSL_MSMC_SMIESTAT_CEIE_MASK); + + CSL_MSMC_lockNonMPAX(); +} + +/***************************************************************************** + Prototype : LL2_EDC_setup + Description : Eenable LL2 EDC and scrub whole LL2 + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/10 + Author : Jane + Modification : Created function + + 2.Date : 2012/10/20 + Author : Brighton Feng + +*****************************************************************************/ +void LL2_EDC_setup() +{ + int i; + unsigned int uiByteCnt= 512*1024; + TDSP_Board_Type DSP_Board_Type; + + /* 1. Disable the EDC */ + CSL_CGEM_disableL2EDC(); + + /* 2. Clear any EDC errors */ + CSL_CGEM_clearL2EDCErrorStatus(1, 1, 1, 1); + + /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ + DSP_Board_Type = KeyStone_Get_dsp_board_type(); + if((DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(C6670_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + uiByteCnt= 1024*1024; + } + + /*Each IDMA can transfer up to 65532 bytes, + here we transfer 32KB each time*/ + for(i=0; i< (uiByteCnt>>15); i++) + { + IDMA_copy((0x00800000 + i*(1<<15)), (0x00800000 + i*(1<<15)), + (1<<15), DMA_WAIT); + } + + /* 4. Enable the EDC*/ + CSL_CGEM_enableL2EDC(); + gpCGEM_regs->L2EDCEN= (1<= uiLL2EndAddress) + uiLL2_scrub_addr=0x800000; + +} + +/***************************************************************************** + Prototype : L1P_EDC_setup + Description : enable L1P ED and scrub whole L1P + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/10 + Author : Jane + Modification : Created function + + 2.Date : 2012/10/30 + Author : Brighton Feng +*****************************************************************************/ +void L1P_EDC_setup() +{ + Uint32 preL1PMPPA[16]; + + /* 1. Disable the EDC */ + CSL_CGEM_disablePMCErrorDetection(); + + /* 2. Clear any EDC errors */ + CSL_CGEM_clearPMCErrorDetectionStatus(1, 1); + + /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ + memcpy(preL1PMPPA, (void *)gpCGEM_regs->L1PMPPA, 64);//save protection attributes + L1P_memory_protection_cfg(0xFFFF); //enable IDMA access to L1P + IDMA_copy(0x00E00000, 0x00E00000, 32*1024, DMA_WAIT); + L1_MPPA_setup(gpCGEM_regs->L1PMPPA, preL1PMPPA);//restore protection for L1 + + /* 4. Enable the EDC*/ + CSL_CGEM_enablePMCErrorDetection(); +} + +char * LL2_EDC_victim_err_str="LL2 victims"; +char * LL2_EDC_DMA_err_str= "DMA access"; +char * LL2_EDC_L1D_err_str= "L1D access"; +char * LL2_EDC_L1P_err_str= "L1P access"; + +/***************************************************************************** + Prototype : LL2_EDC_handler + Description : LL2 EDC exception/interrupt handler + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_EDC_handler(Bool bCorrected) +{ + /* EDC error during the L1D access */ + Uint8 derr; + /* EDC error during the L1P access */ + Uint8 perr; + /* EDC error during the DMA access*/ + Uint8 dmaerr; + /* EDC error during the L2 victim occurred */ + Uint8 verr; + /* single bit or dual bit EDC error */ + Uint8 nerr; + + char *errStr; + Uint32 errAddr; + + /* Get the all LL2 error status */ + CSL_CGEM_getL2EDCErrorStatus(&derr, &perr, &dmaerr, &verr, &nerr); + + if(derr|perr|dmaerr|verr) + { + errAddr= gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_ADDR_MASK; + + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + exception_record.status.ext_sts.info.memory.fault_status.L2EDSTAT= + gpCGEM_regs->L2EDSTAT; + + if(bCorrected) + { + printf(" LL2 EDC (correctable) at bit %d of ",(gpCGEM_regs->L2EDSTAT& + CSL_CGEM_L2EDSTAT_BITPOS_MASK)>>CSL_CGEM_L2EDSTAT_BITPOS_SHIFT); + + //scrub 64 bytes including the error address to correct the error + if(perr) //by L1P access + IDMA_copy(errAddr&0xFFFFFFC0, errAddr&0xFFFFFFC0, 64, DMA_WAIT); + else + { + volatile Uint32 * uipAddress= (volatile Uint32 *)(errAddr&0xFFFFFFC0); + /*read one word into a cache line, and write to make it dirty, + which will be automatically written back sooner or later*/ + *uipAddress= *uipAddress; + } + } + else + { + printf(" LL2 EDC error (non-correctable) at "); + } + errStr = (char *)(perr * (Uint32)LL2_EDC_L1P_err_str + + derr * (Uint32)LL2_EDC_L1D_err_str + + verr * (Uint32)LL2_EDC_victim_err_str + + dmaerr * (Uint32)LL2_EDC_DMA_err_str); + + printf("address 0x%x caused by %s.\n", + errAddr, + errStr); + + if(0==(gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_RAM_MASK)) + { + printf(" Error detected in Way %d of L2 cache\n", + (gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_WAY_MASK)>>CSL_CGEM_L2EDADDR_WAY_SHIFT); + } + + printf(" total non-correctable error number= %d, total correctable error number= %d.\n", + gpCGEM_regs->L2EDCNEC, gpCGEM_regs->L2EDCPEC); + + CSL_CGEM_clearL2EDCErrorStatus(derr, perr, dmaerr, verr); + } + else + { + puts(" Enter LL2 EDC handler, but no error flag is set!"); + } +} +/***************************************************************************** + Prototype : L1P_ED_handler + Description : L1P EDC processing + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1P_ED_handler() +{ + Uint32 errAddr; + Uint8 errRAM; + + /* EDC error during DMA access */ + Uint8 dmaerr; + /* EDC error during program fetch access */ + Uint8 perr; + + /* Read PMC EDC status*/ + CSL_CGEM_getPMCErrorDetectionStatus(&dmaerr, &perr); + + if(perr|dmaerr) + { + CSL_CGEM_getPMCErrorInfo(&errAddr, &errRAM); + + exception_record.status.ext_sts.info.memory.fault_address= errAddr*32; + exception_record.status.ext_sts.info.memory.fault_status.L1PEDSTAT= + gpCGEM_regs->L1PEDSTAT; + + if(errRAM) + printf(" L1P RAM "); + else + printf(" L1P Cache "); + + printf("parity check error caused by "); + + if(perr == 1) + { + printf("program fetch "); + + /*flush wrong code in L1P. Code will be refetched from L2*/ + CACHE_invL1p((void *)NRP, 64, CACHE_WAIT); + } + else if(dmaerr == 1) + { + printf("DMA "); + } + printf("at address 0x%x\n", errAddr*32); + + CSL_CGEM_clearPMCErrorDetectionStatus(dmaerr,perr); + } +} + + +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_handler + Description : SL2 EDC Processing + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_handler() +{ + /* EDC correctable error during scrubbing cycle */ + Uint8 cses; + /* EDC non-correctable error during scrubbing cycle */ + Uint8 ncses; + /* EDC correctable error during SRAM access*/ + Uint8 cees; + /* EDC non-correctable error during SRAM access*/ + Uint8 ncees; + /* protection fault status*/ + Uint16 pfeStat; + + /* error address */ + Uint32 errAddr, bitPos, PrivID; + + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + CSL_MSMC_getPendingInterrupts(&pfeStat, &cees, &ncees, &cses, &ncses); + + exception_record.status.ext_sts.info.memory.fault_status.SMESTAT= + gpMSMC_regs->SMESTAT; + + if((cses == 1)||(ncses == 1)) + { + if(cses == 1) + { + /*scrubbing engine report address offset from 0*/ + errAddr = (gpMSMC_regs->SMCEA&0xFFFFFF)+0xc000000; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + bitPos = (gpMSMC_regs->SMCEA&CSL_MSMC_SMCEA_ESYN_MASK) + >>CSL_MSMC_SMCEA_ESYN_SHIFT; + printf("SL2 Correctable error occurred at bit %d of address 0x%x by scrubbing\n", + bitPos, errAddr); + } + if(ncses == 1) + { + /*scrubbing engine report address offset from 0*/ + errAddr = gpMSMC_regs->SMNCEA+0xc000000; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + printf("SL2 Non-correctable error occurred at address 0x%x by scrubbing\n", errAddr); + } + printf("%d correctable errors, %d non-correctable errors occurred during scrubbing.\n", + (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SCEC_MASK) + >>CSL_MSMC_SMSECC_SCEC_SHIFT, + (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SNCEC_MASK) + >>CSL_MSMC_SMSECC_SNCEC_SHIFT); + } + if(cees == 1) + { + volatile Uint32 scrubValue; + + errAddr = gpMSMC_regs->SMCERRAR; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + //scrub the address to correct the error + scrubValue= *(volatile Uint32 *)errAddr; //touch to cach + *(volatile Uint32 *)errAddr= scrubValue; //make cache dirty + CACHE_wbInvL2((void *)errAddr, 32, CACHE_WAIT); + + bitPos = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_ESYN_MASK) + >>CSL_MSMC_SMCERRXR_ESYN_SHIFT; + PrivID = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SEPID_MASK) + >>CSL_MSMC_SMCERRXR_SEPID_SHIFT; + printf("SL2 Correctable error occurred at bit %d of address 0x%x by PrivID %d ", + bitPos, errAddr, PrivID); + if(gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SER_MASK) + printf("(not from C66x CorePacs)\n"); + else + printf("(from C66x CorePacs)\n"); + } + if(ncees ==1) + { + errAddr = gpMSMC_regs->SMNCERRAR; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + PrivID = (gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SEPID_MASK) + >>CSL_MSMC_SMNCERRXR_SEPID_SHIFT; + printf("SL2 Non-correctable error occurred at address 0x%x by PrivID %d ", + errAddr, PrivID); + if(gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SER_MASK) + printf("(not from C66x CorePacs)\n"); + else + printf("(from C66x CorePacs)\n"); + } + + /* clear EDC error status */ + CSL_MSMC_clearRawInterruptStatus(0, cees,ncees, cses, ncses); + + CSL_MSMC_lockNonMPAX(); +} + +/*===============================Exception=============================*/ +//data structure to save exception info +Exception_Record exception_record; + +/*some exception events routed from CIC to INTC and then to exception moduel, +all these events are routed to one input of INTC*/ +Uint32 guwIntcCICExcEvtIdx= 95; /*INTC event number mapping to CIC exception events*/ +Uint32 gCIC_EXC_out_num = 15; //CIC output event number +Uint32 gCIC_EXC_EN_MASK[8]= {0,0,0,0,0,0,0,0}; +/***************************************************************************** + Prototype : KeyStone_CIC_exception_events_mapping + Description : CIC exception event mapping to the NMI external exception + Input : void + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + + 2.Date : 2012/10/20 + Author : Zhan + Modification : Add event for TCI6614 + + 3.Date : 2012/10/28 + Author : Brighton Feng +*****************************************************************************/ +void KeyStone_CIC_exception_events_mapping(void) +{ + TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); + +#if 1 + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||TCI6614_EVM==DSP_Board_Type) + { + gCIC_EXC_out_num= 15+16*DNUM; + } + else if(C6678_EVM==DSP_Board_Type) + { + if(DNUM<4) + gCIC_EXC_out_num= 7+8*DNUM; + else + { + gCIC_EXC_out_num= 7+8*(DNUM-4); + gpCIC_regs= gpCIC1_regs; + } + } + else + { + puts("Unknown DSP board type!"); + return; + } +#endif + + /*-----------------------CP_INTC configuration---------------------*/ + /* Disable Global host interrupts. */ + gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 0; + + /* route following system events to CIC out (event 22 of INTC), and then to exception + TCI6614, C6670, C6678: + CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt + CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt + CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt + CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt + CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt + CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt + CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt + CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt + CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt + CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt + CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt + CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt + CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt + CIC: 99 MSMC_dedc_nc_error Non-correctable soft error detected on SRAM read + CIC: 100 MSMC_scrub_nc_error Non-correctable soft error detected during scrub cycle + CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID + CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID + CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID + CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID + CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID + CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID + CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID + CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID + CIC: 110 DDR3_ERR DDR3 ECC Error Interrupt + TCI6614, C6670: + CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID + CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID + CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID + CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID + */ + KeyStone_CIC_event_map(gpCIC_regs, 0 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 2 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 3 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 4 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 5 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 16, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 18, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 19, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 20, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 21, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[0] |= + (1<<0 ) + |(1<<2 ) + |(1<<3 ) + |(1<<4 ) + |(1<<5 ) + |(1<<16) + |(1<<18) + |(1<<19) + |(1<<20) + |(1<<21); + + KeyStone_CIC_event_map(gpCIC_regs, 32, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 34, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 35, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[1] |= + (1<<(32-32)) + |(1<<(34-32)) + |(1<<(35-32)); + + KeyStone_CIC_event_map(gpCIC_regs, 99, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 100, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 102, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 103, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 104, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 105, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 106, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 107, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 108, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 109, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 110, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[3] |= + (1<<(99 -32*3)) + |(1<<(100-32*3)) + |(1<<(102-32*3)) + |(1<<(103-32*3)) + |(1<<(104-32*3)) + |(1<<(105-32*3)) + |(1<<(106-32*3)) + |(1<<(107-32*3)) + |(1<<(108-32*3)) + |(1<<(109-32*3)) + |(1<<(110-32*3)); + + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||TCI6614_EVM==DSP_Board_Type) + { + KeyStone_CIC_event_map(gpCIC_regs, 170, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 171, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 172, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 173, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[5] |= + (1<<(170-32*5)) + |(1<<(171-32*5)) + |(1<<(172-32*5)) + |(1<<(173-32*5)); + } + + /* ----------- Mapping MPU interrupt for different chips start -----------------------*/ + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||C6678_EVM==DSP_Board_Type) + { + /* route the following system events to CIC out + CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt + CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt + CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt + CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt + */ + KeyStone_CIC_event_map(gpCIC_regs, 90, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 92, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 94, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 96, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[2] |= + (1<<(90 -32*2)) + |(1<<(92 -32*2)) + |(1<<(94 -32*2)); + gCIC_EXC_EN_MASK[3] |= + (1<<(96 -32*3)); + + /* 6618_6670 only */ + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type) + { + /* + CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt + CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt + */ + KeyStone_CIC_event_map(gpCIC_regs, 174, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 180, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[5] |= + (1<<(174-32*5)) + |(1<<(180-32*5)); + } + } + + if(TCI6614_EVM==DSP_Board_Type) + { + /* route the following system events to CIC out + CIC: 23 MPU0~7 addressing violation interrupt combine output + CIC: 37 MPU0~7 protection violation interrupt combine output + */ + KeyStone_CIC_event_map(gpCIC_regs, 23, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 37, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[0] |= + (1<<23); + gCIC_EXC_EN_MASK[1] |= + (1<<(37 -32)); + + } + /* ----------- Mapping MPU interrupt for different chips end -----------------------*/ + + /* Enable Global host interrupts. */ + gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 1; + +} +/***************************************************************************** + Prototype : KeyStone_Exception_cfg + Description : Config the system err and external exception to generate the NMI. + Call this function as last step after all + configuration/initialization complete + Input : Bool bGlobalExceptionMaster. If TRUE, the global exception events + from CIC will be routed to exception model of this CPU core. + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_Exception_cfg(Bool bGlobalExceptionMaster) +{ + + puts("Enable Exception handling..."); + + TSCL = 0; /* Enable the TSC */ + + memset(&exception_record, 0, sizeof(exception_record)); +#if 0 + /*Clear all CPU events*/ + gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; +#endif + /*clear memory fault*/ + gpCGEM_regs->L1PMPFCR = 1; + gpCGEM_regs->L1DMPFCR = 1; + gpCGEM_regs->L2MPFCR = 1; + gpXMC_regs->XMPFCR = 1; + + /*clear configuration bus error*/ + gpCGEM_regs->ICFGMPFCR= 1; + gpCGEM_regs->ECFGERRCLR= 1; + + /* clear the MDMAERR */ + gpCGEM_regs->MDMAERRCLR = 1; + + /*clear interrupt drop staus*/ + gpCGEM_regs->INTXCLR = 1; + + gpCGEM_regs->INTDMASK= ~IER; /*only monitor drop of enabled interrupts*/ + + /*enable events: + 10 MSMC_mpf_error_n MSMC Memory protection fault caused by local CorePac + 96 INTERR Dropped CPU interrupt event + 97 EMC_IDMAERR Invalid IDMA parameters + 110 MDMAERREVT XMC VBUSM error event + 113 PMC_ED Single bit error detected during DMA accesses L1P + 117 UMC_ED2 Uncorrected bit error detected LL2 + 119 SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control + 120 PMC_CMPA CPU memory protection fault for L1P + 121 PMC_DMPA DMA memory protection fault for L1P + 122 DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller) + 123 DMC_DMPA DMA memory protection fault for L1D + 124 UMC_CMPA CPU memory protection fault for LL2 + 125 UMC_DMPA DMA memory protection fault for LL2 + 126 EMC_CMPA CPU memory protection fault for other local configuration space between 0x01000000 - 0x01BFFFFF + 127 EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF + */ + gpCGEM_regs->EXPMASK[0]= ~(1<EXPMASK[1]= 0xFFFFFFFF; + gpCGEM_regs->EXPMASK[2]= 0xFFFFFFFF; + gpCGEM_regs->EXPMASK[3]= ~((1<<(CSL_GEM_INTERR - 96))| + (1<<(CSL_GEM_EMC_IDMAERR-96))| + (1<<(CSL_GEM_MDMAERREVT-96))| + (1<<(CSL_GEM_PMC_ED-96))| + (1<<(CSL_GEM_UMC_ED2-96))| + (1<<(CSL_GEM_SYS_CMPA-96))| + (1<<(CSL_GEM_PMC_CMPA-96))| + (1<<(CSL_GEM_PMC_DMPA-96))| + (1<<(CSL_GEM_DMC_CMPA-96))| + (1<<(CSL_GEM_DMC_DMPA-96))| + (1<<(CSL_GEM_UMC_CMPA-96))| + (1<<(CSL_GEM_UMC_DMPA-96))| + (1<<(CSL_GEM_EMC_CMPA-96))| + (1<<(CSL_GEM_EMC_BUSERR-96))); + + + if(bGlobalExceptionMaster) + { + /*enable exception events routed from CIC, + please note, this should be only configured for one CPU*/ + KeyStone_CIC_exception_events_mapping(); + gpCGEM_regs->EXPMASK[guwIntcCICExcEvtIdx>>5] &= (~(1<<(guwIntcCICExcEvtIdx&0x1F))); + } + + /*clear exception flag*/ + ECR = EFR; + IERR = 0; + + /*Eanble external exception, global exception enable*/ + TSR = TSR| + (1<>CSL_CGEM_MDMAERR_ERR_SHIFT; + if (1==err) { + puts(" MDMA read status error detected"); + } + else if (2==err) { + puts(" MDMA write status error detected"); + } + else if (3==err) { + puts(" CFG read status error detected"); + } + else if (4==err) { + puts(" CFG write status error detected"); + } + + printf(" XID (Transaction ID)= %d\n", + (ERR_REG & CSL_CGEM_MDMAERR_XID_MASK)>>CSL_CGEM_MDMAERR_XID_SHIFT); + + stat= (ERR_REG & CSL_CGEM_MDMAERR_STAT_MASK)>>CSL_CGEM_MDMAERR_STAT_SHIFT; + printf(" %s\n", bus_err_stat_str[stat]); +} + +/***************************************************************************** + Prototype : KeyStone_CIC_EXC_handler + Description : This function handle the exception events from CIC + Input : void + Output : None + Return Value : void + + History : + 1.Date : 2012/10/18 + Author : Zhan + Modification : Created function + + 2.Date : 2012/10/28 + Author : Brighton Feng + Modification : Add EDMA error processing + +*****************************************************************************/ +void KeyStone_CIC_EXC_handler() +{ + int i; + Uint32 status[4], status5 = 0; + + TDSP_Board_Type DSP_Board_Type; + + DSP_Board_Type= KeyStone_Get_dsp_board_type(); + + /*Step1: Disable CIC host interrupt*/ + KeyStone_CIC_disable_host_int(gpCIC_regs, gCIC_EXC_out_num); + + status[0]= gpCIC_regs->ENA_STATUS_REG[0]&gCIC_EXC_EN_MASK[0]; + status[1]= gpCIC_regs->ENA_STATUS_REG[1]&gCIC_EXC_EN_MASK[1]; + status[2]= gpCIC_regs->ENA_STATUS_REG[2]&gCIC_EXC_EN_MASK[2]; + status[3]= gpCIC_regs->ENA_STATUS_REG[3]&gCIC_EXC_EN_MASK[3]; + exception_record.status.ext_sts.CIC_STATUS[0]= status[0]; + exception_record.status.ext_sts.CIC_STATUS[1]= status[1]; + exception_record.status.ext_sts.CIC_STATUS[2]= status[2]; + exception_record.status.ext_sts.CIC_STATUS[3]= status[3]; + + /*Step2: clear system events*/ + gpCIC_regs->ENA_STATUS_REG[0]= status[0]; + gpCIC_regs->ENA_STATUS_REG[1]= status[1]; + gpCIC_regs->ENA_STATUS_REG[2]= status[2]; + gpCIC_regs->ENA_STATUS_REG[3]= status[3]; + + /* The different device INTC number is different, if read the non-exist space will + trigger the L1D memory protection error. + */ + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + status5 = gpCIC_regs->ENA_STATUS_REG[5]&gCIC_EXC_EN_MASK[5]; + exception_record.status.ext_sts.CIC_STATUS[5]= status5; + + /*Step2: clear system events*/ + gpCIC_regs->ENA_STATUS_REG[5]= status5 ; + } + + /*----------------------------EDMA error-----------------------------*/ + /* + CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt + CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt + CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt + CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt + CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt*/ + if(status[0]&0x3D) + EDMA_error_handler(1, status[0]&0x3D); + + /* + CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt + CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt + CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt + CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt + CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt*/ + if((status[0]>>16)&0x3D) + EDMA_error_handler(2, (status[0]>>16)&0x3D); + + /* + CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt + CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt + CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt*/ + if(status[1]&0xD) + EDMA_error_handler(0, status[1]&0xD); + + /*----------------------------MPU error-----------------------------*/ + if(TCI6614_EVM == DSP_Board_Type) + { + //CIC: 23 MPU0~7 addressing violation interrupt combine output + //CIC: 37 MPU0~7 protection violation interrupt combine output + if((status[0]&(1<<23))||(status[1]&(1<<(37-32)))) + { + for(i=0; i<8; i++) + { + /*MPU5 (for BCP) of TCI6614 is only accessible + when BCP is enabled through PSC*/ + if((5==i)&& + ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || + (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) + continue; + + if(gpMPU_regs[i]->INT_RAW_STATUS_SET & 0x3) + { + KeyStone_peripherals_MPU_excepiton_handler(i); + } + } + + /*The MPU events in TCI6614 are different from other KeyStone + devices. All the MPU0~7 events are combined into single event + and connected to the CIC0 as one system event. + We have to clear the MPU event flag at the source level first + and then are able to clear the CIC flags because the INTD for the + MPU events is for the combination purpose but do not convert + the level interrupt to pulse.*/ + /*clear system events*/ + gpCIC_regs->ENA_STATUS_REG[0]= status[0]; + gpCIC_regs->ENA_STATUS_REG[1]= status[1]; + } + } + else + { + //CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(90-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(0); + } + //CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(92-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(1); + } + //CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(94-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(2); + } + //CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt + if(status[3]&(1<<(96-96))) + { + KeyStone_peripherals_MPU_excepiton_handler(3); + } + + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type)) + { + //CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt + //CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt + if(status5&(1<<(174-160))) + { + KeyStone_peripherals_MPU_excepiton_handler(4); + } + if(status5&(1<<(180-160))) + { + KeyStone_peripherals_MPU_excepiton_handler(5); + } + } + } + + /*----------------------------MSMC error-----------------------------*/ + //CIC: 99 MSMC_dedc_nc_error Non-correctable (2-bit) soft error detected on SRAM read + if(status[3]&(1<<(99-96))) + { + KeyStone_SL2_EDC_handler(); + } + //CIC: 100 MSMC_scrub_nc_error Non-correctable (2-bit) soft error detected during scrub cycle + if(status[3]&(1<<(100-96))) + { + KeyStone_SL2_EDC_handler(); + } + + /* + CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID + CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID + CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID + CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID + CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID + CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID + CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID + CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID*/ + if((status[3]>>(102-96))&0xFF) + KeyStone_MSMC_protection_exception_handler(); + + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + /* + CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID + CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID + CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID + CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID*/ + if((status5>>(170-160))&0xF) + KeyStone_MSMC_protection_exception_handler(); + + } + + /*----------------------------DDR ECC error-------------------------*/ + //CIC: 110 DDR3_ERR DDR3_EMIF Error Interrupt + if(status[3]&(1<<(110-96))) + { + printf(" DDR ECC error happened during "); + + exception_record.status.ext_sts.info.memory.fault_status.DDR_IRQSTATUS_SYS= + gpDDR_regs->IRQSTATUS_SYS; + + if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK) + printf("read "); + if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK) + printf("write "); + printf(".\n"); + + //clear the status + gpDDR_regs->IRQSTATUS_SYS= CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK + |CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK; + } + + /*Step3: Enable the CIC host interrupt */ + KeyStone_CIC_enable_host_int(gpCIC_regs, gCIC_EXC_out_num); + +} + +/***************************************************************************** + Prototype : KeyStone_EXC_external + Description : external exception processing + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_EXC_external(void) +{ + int i; + unsigned int INTXSTAT, flag[4]; + + for(i= 0; i<4; i++) + { + flag[i] = gpCGEM_regs->MEXPFLAG[i]; + if(flag[i]) + { + exception_record.status.ext_sts.MEXPFLAG[i]= flag[i]; + printf("External exception happened. MEXPFLAG[%d]=0x%x.\n", + i, flag[i]); + gpCGEM_regs->EVTCLR[i] = flag[i]; + } + } + + if(0 == (flag[0]|flag[1]|flag[2]|flag[3])) + { + puts("Enter external Exception service routine, but external excpetion flage is 0!"); + return; + } + + /*Exception events routed from CIC*/ + if(flag[guwIntcCICExcEvtIdx>>5] & (1<<(guwIntcCICExcEvtIdx&0x1F))) + { + KeyStone_CIC_EXC_handler(); + } + + /*MSMC memory protection exception*/ + if(flag[0]&(1<INTXSTAT; + exception_record.status.ext_sts.info.INTXSTAT= INTXSTAT; + + if(INTXSTAT&CSL_CGEM_INTXSTAT_DROP_MASK) + printf(" Event 96: DSP Interrupt %d (INTC input Event %d) dropped\n", + (INTXSTAT&CSL_CGEM_INTXSTAT_CPUINT_MASK)>>CSL_CGEM_INTXSTAT_CPUINT_SHIFT, + (INTXSTAT&CSL_CGEM_INTXSTAT_SYSINT_MASK)>>CSL_CGEM_INTXSTAT_SYSINT_SHIFT); + } + + if(flag[3]&(1<<(CSL_GEM_EMC_IDMAERR-96))) + puts(" Event 97: EMC_IDMAERR Invalid IDMA parameters"); + + /*MDMA XMC VBUSM error*/ + if(flag[3]&(1<<(CSL_GEM_MDMAERREVT-96))) + { + puts(" Event 110: MDMAERREVT XMC VBUSM error event"); + if(gpXMC_regs->XMPFSR) + { + /*XMC protection error*/ + memory_protection_exception_handler(gpXMC_regs->XMPFAR, gpXMC_regs->XMPFSR); + gpXMC_regs->XMPFCR = 1; + } + else + { + /*other VBUSM error*/ + Bus_error_handler(gpCGEM_regs->MDMAERR); + } + /* clear the MDMAERR */ + gpCGEM_regs->MDMAERRCLR = 1; + } + + /*L1P Single bit error detected during DMA read*/ + if(flag[3]&(1<<(CSL_GEM_PMC_ED-96))) + { + puts(" Event 113: PMC_ED Single bit error detected during DMA read"); + L1P_ED_handler(); + } + + /*LL2 Uncorrected bit error detected*/ + if(flag[3]&(1<<(CSL_GEM_UMC_ED2-96))) + { + puts(" Event 117: UMC_ED2 Uncorrected bit error detected"); + LL2_EDC_handler(FALSE); + } + + /*local register memory protection exception*/ + if(flag[3]&(1<<(CSL_GEM_SYS_CMPA-96))) + { + puts(" Event 119: SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control"); + } + + /*L1P memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_PMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_PMC_CMPA-96))) + puts(" Event 120: PMC_CMPA CPU memory protection fault for L1P"); + if(flag[3]&(1<<(CSL_GEM_PMC_DMPA-96))) + puts(" Event 121: PMC_DMPA DMA memory protection fault for L1P"); + memory_protection_exception_handler(gpCGEM_regs->L1PMPFAR, gpCGEM_regs->L1PMPFSR); + gpCGEM_regs->L1PMPFCR = 1; + } + + /*L1D memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_DMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_DMC_CMPA-96))) + puts(" Event 122: DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller)"); + if(flag[3]&(1<<(CSL_GEM_DMC_DMPA-96))) + puts(" Event 123: DMC_DMPA DMA memory protection fault for L1D"); + memory_protection_exception_handler(gpCGEM_regs->L1DMPFAR, gpCGEM_regs->L1DMPFSR); + gpCGEM_regs->L1DMPFCR = 1; + } + + /*LL2 memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_UMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_UMC_CMPA-96))) + puts(" Event 124: UMC_CMPA CPU memory protection fault for L2 "); + if(flag[3]&(1<<(CSL_GEM_UMC_DMPA-96))) + puts(" Event 125: UMC_DMPA DMA memory protection fault for L2 "); + memory_protection_exception_handler(gpCGEM_regs->L2MPFAR, gpCGEM_regs->L2MPFSR); + gpCGEM_regs->L2MPFCR = 1; + } + + /*local registers protection exception*/ + if(flag[3]&(1<<(CSL_GEM_EMC_CMPA-96))) + { + puts(" Event 126: EMC_CMPA CPU memory protection fault for local configuration space between 0x01000000-0x01BFFFFF"); + memory_protection_exception_handler(gpCGEM_regs->ICFGMPFAR, gpCGEM_regs->ICFGMPFSR); + gpCGEM_regs->ICFGMPFCR= 1; + } + + /*external configuration bus error*/ + if(flag[3]&(Uint32)(1<<(CSL_GEM_EMC_BUSERR-96))) + { + puts(" Event 127: EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF"); + Bus_error_handler(gpCGEM_regs->ECFGERR); + gpCGEM_regs->ECFGERRCLR= 1; + } +} + +char * internal_exception_str[]= +{ + "Instruction fetch exception", + "Fetch packet exception", + "Execute packet exception", + "Opcode exception", + "Resource conflict exception", + "Resource access exception", + "Privilege exception", + "SPLOOP buffer exception", + "Missed stall exception" +}; + +/***************************************************************************** + Prototype : EXC_internal + Description : internal exception handler + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +/*internal exception handler*/ +void EXC_internal(void) +{ + int i; + unsigned int ierr; + + /*record IERR */ + ierr = IERR; + exception_record.status.IERR= ierr; + + if(ierr) + { + /*Clear internal excpeiton flag*/ + IERR= 0; + + printf("internal excpetion happened. IERR=0x%x.\n", ierr); + for(i=0; i<9; i++) + { + if((ierr>>i)&1) + printf(" %s\n", internal_exception_str[i]); + } + if (ierr & CSL_CHIP_IERR_IFX_MASK) { + /* L1P EDC Processing*/ + L1P_ED_handler(); + } + } + else + puts("Enter Internal Exception service routine, but internal excpetion flage is 0!"); + +} +/***************************************************************************** + Prototype : EXC_nmi + Description : NMI processing + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EXC_NMI(void) +{ + puts("NMI exception happened, normally you should reset the DSP to recover from the problem!"); +} + +/***************************************************************************** + Prototype : EXC_swgen + Description : software generated exception handler + Input : void + Output : None + Return Value : +*****************************************************************************/ +void EXC_swgen(void) +{ + puts("Software generated exception happened."); +} + +/***************************************************************************** + Prototype : Exception_service_routine + Description : Exception service routine + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma NMI_INTERRUPT( Exception_service_routine ); +void Exception_service_routine(void) +{ + unsigned int efr, nrp, ntsr, tscl, tsch, irp, itsr; + + /*record timestamp*/ + tscl = TSCL; + exception_record.TSCL= tscl; + tsch = TSCH; + exception_record.TSCH= tsch; + + nrp = NRP; /*record NRP */ + exception_record.NRP= nrp; + ntsr = NTSR; /*record NTSR */ + exception_record.NTSR= ntsr; + efr = EFR; /*record EFR */ + exception_record.EFR= efr; + + irp = IRP; /*record IRP */ + itsr = ITSR; /*record ITSR */ + exception_record.IRP= irp; + exception_record.ITSR= itsr; + + if(efr) + { + /*Clear excpeiton flag*/ + ECR = efr; + + /*check all possible exceptions*/ + if (efr & CSL_CHIP_EFR_OXF_MASK) { + /* S/W generated exception */ + EXC_swgen(); + } + if (efr & CSL_CHIP_EFR_IXF_MASK) { + /* internal exception */ + EXC_internal(); + } + if (efr & CSL_CHIP_EFR_EXF_MASK) { + /* external exception */ + KeyStone_EXC_external(); + } + if (efr & CSL_CHIP_EFR_NXF_MASK) { + /* legacy NMI exception */ + EXC_NMI(); + } + } + else + puts("Enter Exception service routine, but excpetion flage is 0!"); + + printf("NRP=0x%x, NTSR=0x%x, IRP=0x%x, ITSR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", + nrp, ntsr, irp, itsr, tsch, tscl); + + printf(" B3=0x%x, A4=0x%x, B4= 0x%x, B14= 0x%x, B15= 0x%x\n", + exception_record.B3, exception_record.A4, + exception_record.B4, exception_record.B14, + exception_record.B15); + + /* + It is not always possible to safely exit the exception handling routine. Conditions that + can prevent a safe return from exceptions include: + 1. SPLOOPs that are terminated by an exception cannot be resumed correctly. The + SPLX bit in NTSR should be verified to be 0 before returning. + 2. Exceptions that occur when interrupts are blocked cannot be resumed correctly. + The IB bit in NTSR should be verified to be 0 before returning. + 3. Exceptions that occur at any point in the code that cannot be interrupted safely + (for example, a tight loop containing multiple assignments) cannot be safely + returned to. The compiler will normally disable interrupts at these points in the + program; check the GIE bit in NTSR to be 1 to verify that this condition is met. + 4. NRP is not in valid address space*/ + if((ntsr&CSL_CHIP_TSR_SPLX_MASK) + ||(ntsr&CSL_CHIP_TSR_IB_MASK) + ||(0==(ntsr&CSL_CHIP_TSR_GIE_MASK)) + ||(0x800000>NRP)) + { + puts("Exception happened at a place can not safely return!"); + //while(1); //trap + exit(0); + } + +} + +/***************************************************************************** + Prototype : Nested_Exception_service_routine + Description : Nested Exception service routine + When a non-maskable exception happens in the first exception service routine, + then the reset vector is used when redirecting program execution to service the second + exception. In this case, NTSR and NRP are left unchanged. TSR is copied to ITSR and + the current PC is copied to IRP. TSR is set to the default exception processing value and + the NMIE bit in IER is cleared in this case preventing any further external exceptions. + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/29 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +interrupt void Nested_Exception_service_routine(void) +{ + unsigned int tscl, tsch; + + /*record timestamp*/ + tscl = TSCL; + tsch = TSCH; + + if(0==exception_record.TSCL) + exception_record.TSCL= tscl; + if(0==exception_record.TSCH) + exception_record.TSCH= tsch; + if(0==exception_record.NRP) + exception_record.NRP= NRP; + if(0==exception_record.NTSR) + exception_record.NTSR= NTSR; + if(0==exception_record.EFR) + exception_record.EFR= EFR; + if(0==exception_record.status.IERR) + exception_record.status.IERR= IERR; + + exception_record.IRP= IRP; + exception_record.ITSR= ITSR; + + printf("Nested exception happened! IRP=0x%x, ITSR=0x%x\n", + IRP, ITSR); + + printf("NRP=0x%x, NTSR=0x%x, EFR=0x%x, IERR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", + NRP, NTSR, EFR, IERR, tsch, tscl); + + while(1); //trap +// exit(0); +} + +/*=========================other utility functions==========================*/ +/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ +void CPU_interrupt_init() +{ + //clear interrupt and excpetion events + ICR = IFR; + ECR = EFR; + IER= 3; //disable all interrupts + + /* disable event combine */ + gpCGEM_regs->EVTMASK[0] = 0xffffffff; + gpCGEM_regs->EVTMASK[1] = 0xffffffff; + gpCGEM_regs->EVTMASK[2] = 0xffffffff; + gpCGEM_regs->EVTMASK[3] = 0xffffffff; + + /*Clear all CPU events*/ + gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; + + /*Interrupt Service Table Pointer to begining of LL2 memory*/ + ISTP= 0x800000; +} + +/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ +void CPU_interrupt_enable(Uint32 uiIER_en_mask) +{ + ICR= uiIER_en_mask; + IER |= uiIER_en_mask; + + //enable GIE + //TSR = TSR|1; +} + +/***************************************************************************** + Prototype : KeyStone_get_device_info + Description : Get device information + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + 2.Date : 2014/12/2 + Author : Brighton Feng + Modification : Update to parser device type, boot mode, endian information, + speed grade, required CVDD + +*****************************************************************************/ +//get device speed grade from the EFUSE register +void KeyStone_get_device_speed_grade() +{ + Uint32 uiDevSpeed, uiSpeedCode; + + uiSpeedCode= (DEVSPEED&DEVSPEED_DSP_SPEED_MASK)>>DEVSPEED_DSP_SPEED_SHIFT; + + if(uiSpeedCode&DEVSPEED_800_MHZ_MASK_H) uiDevSpeed= 800; + else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_H) uiDevSpeed= 1000; + else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_H) uiDevSpeed= 1200; + else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_H) uiDevSpeed= 1250; + else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_H) uiDevSpeed= 1400; + else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_L) uiDevSpeed= 1400; + else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_L) uiDevSpeed= 1250; + else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_L) uiDevSpeed= 1200; + else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_L) uiDevSpeed= 1000; + else uiDevSpeed= 800; + + printf("Device speed grade = %dMHz.\n", uiDevSpeed); +} + +char * device_type_str[]= +{ + "TCI6616", + "C6670/TCI6618", + "C6678/TCI6608", + "TCI6614", + "unknown" +}; +char * endian_str[]= +{ + "big", + "little" +}; +char * boot_mode_str[]= +{ + "No boot or EMIF16(NOR FLASH) or UART", + "Serial Rapid I/O", + "Ethernet (SGMII)", + "Ethernet (SGMII) or NAND FLASH", + "PCIE", + "I2C", + "SPI", + "HyperLink" + }; +char * input_clk_str[]= +{ + "50MHz", + "66.67MHz", + "80MHz", + "100MHz", + "156.25MHz", + "250MHz", + "312.5MHz", + "122.88MHz", + "bypassed" +}; +void KeyStone_get_device_info() +{ + char * boot_mode; + Uint8 ucBootMode, ucBootMaster; + Uint32 uiVID; + Uint8 ucPLL_cfg= 8; //8 means bypassed + Uint32 * DieID= (Uint32 *)&gpBootCfgRegs->DIE_ID_REG0; + Uint32 uiJTAG_ID = gpBootCfgRegs->DEVICE_ID_REG0; + Uint32 uiDevStat = gpBootCfgRegs->BOOT_REG0; + + gDSP_board_type=KeyStone_Get_dsp_board_type(); + + ucBootMode= (uiDevStat&DEVSTAT_BOOTMODE_MASK)>>DEVSTAT_BOOTMODE_SHIFT; + ucBootMaster= (uiDevStat&DEVSTAT_BOOTMASTER_MASK)>>DEVSTAT_BOOTMASTER_SHIFT; + + if((TCI6614_EVM==gDSP_board_type)&&(1==ucBootMaster)) + { + boot_mode= "ARM"; //ARM boot + } + else + boot_mode= boot_mode_str[ucBootMode]; + + //PLL is not configured with SPI and I2C master boot mode + if((5!=ucBootMode)&&(6!=ucBootMode)) + ucPLL_cfg= (uiDevStat&DEVSTAT_SYSPLL_MASK)>>DEVSTAT_SYSPLL_SHIFT; + + printf("JTAG ID= 0x%08x. This is %s device, version variant = %d.\n", uiJTAG_ID, + device_type_str[gDSP_board_type], uiJTAG_ID>>28); + + printf("DEVSTAT= 0x%08x. %s endian, %s boot, PLL configuration implies the input clock for core is %s.\n", + uiDevStat, endian_str[uiDevStat&DEVSTAT_LENDIAN_MASK], boot_mode, + input_clk_str[ucPLL_cfg]); + + uiVID= (gpPSC_regs->VCNTLID&CSL_PSC_VCNTLID_VCNTL_MASK)>>CSL_PSC_VCNTLID_VCNTL_SHIFT; + printf("SmartReflex VID= %d, required core voltage= %.3fV.\n", uiVID, 0.7+(float)uiVID*0.41/64.f); + + printf("Die ID= 0x%08x, 0x%08x, 0x%08x, 0x%08x\n", DieID[0], DieID[1], DieID[2], DieID[3]); + + KeyStone_get_device_speed_grade(); +} +/***************************************************************************** + Prototype : KeyStone_common_device_init + Description : common initialization for internal modules in K2 device + enable memory protection interrupts, EDC for MSMC RAM + History : + 1.Date : July 11, 2014 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_common_device_init() +{ + int i; + KeyStone_get_device_info(); + + /* enable common MPU interrupts */ + for(i=0; i<4; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + + /*Enable MSMC EDC and setup scrubbing cycle counter= 255*1024*/ + KeyStone_SL2_EDC_enable(255); +} + +/***************************************************************************** + Prototype : KeyStone_common_CPU_init + Description : common initialization for internal modules in K2 device + enable TSC, EDC for local RAM; clear cache; protect L1 as cache + History : + 1.Date : September 1, 2014 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_common_CPU_init() +{ + TSC_init(); //initialize TSC to measure cycle + + /*clear all interrupt flag/status, setup ISTP to begining of LL2*/ + CPU_interrupt_init(); + + /*clean cache from previous run, not required from power on or cold reset*/ + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + _mfence(); + _mfence(); + + /* protect L1 as cache */ + L1_cache_protection(); + + //Enable MSMC Memory protection error interrupt for local core, refer to MSMC user guide section3.8 + // KeyStone_MSMC_MP_interrupt_en(1< +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*----------------------PLL registers definition----------------*/ +#define PLLCTL0_PLLD_SHIFT (0) +#define PLLCTL0_PLLD_MASK (0x3F<>4) | 0x80000000) + +/*max number in two numbers*/ +#define MAX(a, b) (a>b?a:b) +/*min number in two numbers*/ +#define MIN(a, b) (a0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline void WritebackCache(void * blockPtr, Uint32 byteCnt) +{ + if(byteCnt>0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbL2((void *)blockPtr, byteCnt, CACHE_WAIT); + } + _mfence(); + _mfence(); +} + +static inline void WritebackAllCache(void * blockPtr) +{ + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbAllL1d(CACHE_WAIT);; + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbAllL2(CACHE_WAIT); + } + _mfence(); + _mfence(); +} + +static inline void WritebackInvalidCache(void * blockPtr, Uint32 byteCnt) +{ +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + Uint32 uiOldGIE= _disable_interrupts(); +#endif + + if(byteCnt>0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbInvL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbInvL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline void WritebackInvalidAllCache(void * blockPtr) +{ +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + Uint32 uiOldGIE= _disable_interrupts(); +#endif + + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbInvAllL1d(CACHE_WAIT);//CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + //CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline unsigned int SWAP_ENDIAN(unsigned int byte_index) +{ +#ifdef _BIG_ENDIAN + return ((byte_index&0xFFFFFFFC)+(3-byte_index&3)); +#else + return byte_index; +#endif +} + +static inline void KeyStone_CIC_clear_system_event(CSL_CPINTCRegs* cpIntcRegs, + int input_event_num) +{ + volatile Uint32 dummy_value; + + /*clear input interrupts events*/ + cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->STATUS_CLR_INDEX_REG; +} + +static inline void KeyStone_CIC_disable_host_int(CSL_CPINTCRegs* cpIntcRegs, + int host_int_num) +{ + volatile Uint32 dummy_value; + + /* Disable the host interrupt */ + cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG = host_int_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG; +} + +static inline void KeyStone_CIC_enable_host_int(CSL_CPINTCRegs* cpIntcRegs, + int host_int_num) +{ + volatile Uint32 dummy_value; + + /* Enable the host interrupt */ + cpIntcRegs->HINT_ENABLE_SET_INDEX_REG = host_int_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->HINT_ENABLE_SET_INDEX_REG; +} + +static inline void KeyStone_CIC_event_map(CSL_CPINTCRegs* cpIntcRegs, + int input_event_num, int out_num) +{ + /*Map input event to output*/ + cpIntcRegs->CH_MAP[SWAP_ENDIAN(input_event_num)]= out_num; + + /*clear input interrupts events*/ + cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; + + /*enable input interrupts events*/ + cpIntcRegs->ENABLE_SET_INDEX_REG= input_event_num; + + /*enable output*/ + cpIntcRegs->HINT_ENABLE_SET_INDEX_REG= out_num; +} + + +typedef enum +{ + DUAL_NYQUIST_EVM = 0, + C6670_EVM, + C6678_EVM, + TCI6614_EVM, + C6657_EVM, + UNKNOWN +}TDSP_Board_Type; + +extern TDSP_Board_Type gDSP_board_type; + +static inline TDSP_Board_Type KeyStone_Get_dsp_board_type() +{ + Uint32 deviceID= gpBootCfgRegs->DEVICE_ID_REG0&0x0FFFFFFF; + + gDSP_board_type= UNKNOWN; + if(0x0009D02F == deviceID) + gDSP_board_type= DUAL_NYQUIST_EVM; + if(0x0B94102F == deviceID) + { + gDSP_board_type= C6670_EVM; + //DSP_Board_Type= DUAL_NYQUIST_EVM; + } + if(0x0009E02F == deviceID) + gDSP_board_type= C6678_EVM; + if(0x0B96202F == deviceID) + gDSP_board_type= TCI6614_EVM; + if(0x0B97A02F == deviceID) + gDSP_board_type= C6657_EVM; + + return gDSP_board_type; +} + +static inline Uint32 KeyStone_Get_DSP_Number() +{ + TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); + + if(DUAL_NYQUIST_EVM==DSP_Board_Type) + { + /*Nyquist EVM use boot configure pin 4 and 5 to identify DSPs*/ + return (( gpBootCfgRegs->BOOT_REG0 >> (3+1) ) & 0x03); + } + + /*if use DNUM to differentiate DSPs for two DSPs test, + the program must be run on core 0 of DSP 0 and core 1 of DSP1*/ + return DNUM; +} + +/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ +extern void CPU_interrupt_init(); +/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ +extern void CPU_interrupt_enable(Uint32 uiIER_en_mask); + +//get device speed grade from the EFUSE register +extern void KeyStone_get_device_speed_grade(); + +/*Get device information including device type, boot mode, endian information, +speed grade, required voltage...*/ +extern void KeyStone_get_device_info(); + +/*common initialization for internal modules in K2 device. +enable memory protection interrupts, EDC for MSMC RAM*/ +extern void KeyStone_common_device_init(); + +/* enable TSC, EDC for local RAM; clear cache; protect L1 as cache */ +extern void KeyStone_common_CPU_init(); + + +#endif diff --git a/bsp/ti-c6678/driver/drv_timer.c b/bsp/ti-c6678/driver/drv_timer.c new file mode 100644 index 0000000000..4cda450e49 --- /dev/null +++ b/bsp/ti-c6678/driver/drv_timer.c @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "drv_timer.h" +#include "KeyStone_common.h" + +#include +#include + +/** + * @b Description + * @n + * The function initial system timer. + * Use local timer (==DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well + * + * @param[] + * + * @retval + * NULL + */ +void hw_system_timer_init(void) +{ + // initial system timer interrupt + // map local timer interrupt to INT14 + gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)< + +#ifdef _BIG_ENDIAN +#define REG_PAIR(odd, even) unsigned long odd; unsigned long even +#else +#define REG_PAIR(odd, even) unsigned long even; unsigned long odd +#endif + +/* + * this struct defines the way the registers are stored on the + * stack during a system call. fields defined with REG_PAIR + * are saved and restored using double-word memory operations + * which means the word ordering of the pair depends on endianess. + */ + +struct rt_hw_register +{ + REG_PAIR(b17, b16); + REG_PAIR(b19, b18); + REG_PAIR(b21, b20); + REG_PAIR(b23, b22); + REG_PAIR(b25, b24); + REG_PAIR(b27, b26); + REG_PAIR(b29, b28); + REG_PAIR(b31, b30); + + REG_PAIR(b1, b0); + REG_PAIR(b3, b2); + REG_PAIR(b5, b4); + REG_PAIR(b7, b6); + REG_PAIR(b9, b8); + REG_PAIR(b11, b10); + REG_PAIR(b13, b12); + + REG_PAIR(a17, a16); + REG_PAIR(a19, a18); + REG_PAIR(a21, a20); + REG_PAIR(a23, a22); + REG_PAIR(a25, a24); + REG_PAIR(a27, a26); + REG_PAIR(a29, a28); + REG_PAIR(a31, a30); + + REG_PAIR(a1, a0); + REG_PAIR(a3, a2); + REG_PAIR(a5, a4); + REG_PAIR(a7, a6); + REG_PAIR(a9, a8); + REG_PAIR(a11, a10); + REG_PAIR(a13, a12); + + REG_PAIR(a15, a14); + REG_PAIR(sp, dp); +}; + +struct rt_hw_exp_stack_register +{ + REG_PAIR(tsr, orig_a4); + REG_PAIR(rilc, ilc); + REG_PAIR(pc, csr); + struct rt_hw_register hw_register; +}; + +extern cregister volatile unsigned int IERR; /* Internal Exception Report Register */ +extern cregister volatile unsigned int ECR; /* Exception Clear Register */ +extern cregister volatile unsigned int EFR; /* Exception Flag Register */ +extern cregister volatile unsigned int TSR; /* Task State Register */ +extern cregister volatile unsigned int ITSR; /* Interrupt Task State Register */ +extern cregister volatile unsigned int NTSR; /* NMI/exception Task State Register */ +extern cregister volatile unsigned int TSCL; /* Time Stamp Counter Register - Low Half */ +extern cregister volatile unsigned int TSCH; /* Time Stamp Counter Register - High Half */ +extern cregister volatile unsigned int DNUM; /* Core number */ + +#define get_creg(reg) reg +#define set_creg(reg, v) reg = (v) +#define or_creg(reg, n) reg |= (n) +#define and_creg(reg, n) reg &= (n) + +#define __dint() asm(" DINT") +#define __rint() asm(" RINT") + +#define __system_call() asm(" SWE") +#define __enter_idle() asm(" IDLE") +#define __nop() asm(" NOP") +#define __mfence() asm(" MFENCE") + +#define __SYSREG(ADDR, TYPE) (*(volatile TYPE*)(ADDR)) +#define __SYSREGA(ADDR, TYPE) ((volatile TYPE*)(ADDR)) + +extern void rt_hw_enable_exception(void); + +#endif /* __C66XX_H__ */ + diff --git a/libcpu/ti-dsp/c6x/context.asm b/libcpu/ti-dsp/c6x/context.asm new file mode 100644 index 0000000000..07affb6a1a --- /dev/null +++ b/libcpu/ti-dsp/c6x/context.asm @@ -0,0 +1,312 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; context switch for C6678 DSP +;----------------------------------------------------------- + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +DP .set B14 +SP .set B15 + +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; global variable +;----------------------------------------------------------- + .global rt_interrupt_from_thread + .global rt_interrupt_to_thread + .global rt_thread_switch_interrupt_flag + +; +;----------------------------------------------------------- +; + .sect ".text" +;----------------------------------------------------------- +; void rt_hw_enable_exception(void) +;----------------------------------------------------------- + .global rt_hw_enable_exception +rt_hw_enable_exception: + DINT + MVC .S2 TSR,B0 + MVC .S2 B3,NRP + MVK .L2 0xc,B1 + OR .D2 B0,B1,B0 + MVC .S2 B0,TSR ; Set GEE and XEN in TSR + B .S2 NRP + NOP 5 + +;----------------------------------------------------------- +; rt_base_t rt_hw_interrupt_enable(void) +;----------------------------------------------------------- + .global rt_hw_interrupt_disable +rt_hw_interrupt_disable: +;{ + MVC CSR,B4 + MV B4,A4 + AND 1,B4,B0 + [!B0] CLR B4,1,1,B4 + [B0] SET B4,1,1,B4 + CLR B4,0,0,B4 + MVC B4,CSR + B B3 + NOP 5 +;} + +;----------------------------------------------------------- +; void rt_hw_interrupt_enable(rt_base_t scr) +;----------------------------------------------------------- + .global rt_hw_interrupt_enable +rt_hw_interrupt_enable: +;{ + MVC A4,CSR + B B3 + NOP 5 +;} + +; +;----------------------------------------------------------- +; + +; +; void rt_hw_context_switch(rt_uint32 from, rt_uint32 to); +; A4 --> from +; B4 --> to +; + .global rt_hw_context_switch +rt_hw_context_switch: +; { + SUBAW .D2 SP,2,SP + ADD .D1X SP,-8,A15 + || STDW .D2T1 A15:A14,*SP--[3] ; Store A15:A14 + + STDW .D2T2 B13:B12,*SP--[1] ; Store B13:B12 + || STDW .D1T1 A13:A12,*A15--[1] ; Store A13:A12 + || MV B3,B13 + STDW .D2T2 B11:B10,*SP--[1] ; Store B11:B10 + || STDW .D1T1 A11:A10,*A15--[1] ; Store A11:A10 + || MVC .S2 CSR,B12 + STDW .D2T2 B13:B12,*SP--[1] ; Store PC:CSR + || MVC .S2 TSR,B5 + + MVC ILC,B11 ; + MVC RILC,B10 ; + STDW .D2T2 B11:B10,*SP--[1] ; Store RILC:ILC + || MV .S1X B5,A3 + + ZERO A2 ; + STDW .D2T1 A3:A2,*SP--[1] ; Store TSR:stack type + STW SP,*A4 ; Save thread's stack pointer + + MV B4,A4 ; + B rt_hw_context_switch_to + NOP 5 +;} + +; +; void rt_hw_context_switch_to(rt_uint32 to); +; A4 --> to +; + .global rt_hw_context_switch_to +rt_hw_context_switch_to: +;{ + LDW *A4,SP + NOP 4 + LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) and stack frame type (B8) + LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) + LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) + NOP 2 + MV B8,B0 + [B0] B _rt_thread_interrupt_stack ; + NOP 5 +; +; this maybe do better +; + MVC .S2 B11,RILC ; Restore RILC + MVC .S2 B10,ILC ; Restore ILC + MV B13,B3 ; Restore PC + MVC .S2 B12,CSR ; Restore CSR + + LDDW *++SP[1],B11:B10 + LDDW *++SP[1],B13:B12 + LDDW *++SP[1],A11:A10 + LDDW *++SP[1],A13:A12 + LDDW *++SP[1],A15:A14 + B B3 ; Return to caller + ADDAW SP,2,SP + NOP 4 ; Delay slots +_rt_thread_interrupt_stack: + ADDAW .D1X SP,30,A15 + LDDW .D1T1 *++A15[1],A17:A16 + || LDDW .D2T2 *++SP[1],B17:B16 + LDDW .D1T1 *++A15[1],A19:A18 + || LDDW .D2T2 *++SP[1],B19:B18 + LDDW .D1T1 *++A15[1],A21:A20 + || LDDW .D2T2 *++SP[1],B21:B20 + LDDW .D1T1 *++A15[1],A23:A22 + || LDDW .D2T2 *++SP[1],B23:B22 + LDDW .D1T1 *++A15[1],A25:A24 + || LDDW .D2T2 *++SP[1],B25:B24 + LDDW .D1T1 *++A15[1],A27:A26 + || LDDW .D2T2 *++SP[1],B27:B26 + LDDW .D1T1 *++A15[1],A29:A28 + || LDDW .D2T2 *++SP[1],B29:B28 + LDDW .D1T1 *++A15[1],A31:A30 + || LDDW .D2T2 *++SP[1],B31:B30 + + LDDW .D1T1 *++A15[1],A1:A0 + || LDDW .D2T2 *++SP[1],B1:B0 + + LDDW .D1T1 *++A15[1],A3:A2 + || LDDW .D2T2 *++SP[1],B3:B2 + || MVC .S2 B9,ITSR ; Restore ITSR + LDDW .D1T1 *++A15[1],A5:A4 + || LDDW .D2T2 *++SP[1],B5:B4 + || MVC .S2 B11,RILC ; Restore RILC + LDDW .D1T1 *++A15[1],A7:A6 + || LDDW .D2T2 *++SP[1],B7:B6 + || MVC .S2 B10,ILC ; Restore ILC + + LDDW .D1T1 *++A15[1],A9:A8 + || LDDW .D2T2 *++SP[1],B9:B8 + || MVC .S2 B13,IRP ; Restore IPR + + LDDW .D1T1 *++A15[1],A11:A10 + || LDDW .D2T2 *++SP[1],B11:B10 + || MVC .S2 B12,CSR ; Restore CSR + + LDDW .D1T1 *++A15[1],A13:A12 + || LDDW .D2T2 *++SP[1],B13:B12 + + MV .D2X A15,SP + LDDW .D2T1 *++SP[1],A15:A14 + B IRP ; Return to point of interrupt + LDDW .D2T2 *+SP[1],SP:DP + NOP 4 ; Delay slots +;} + +; +;----------------------------------------------------------- +; + +; +; void rt_hw_context_switch_interrupt(rt_uint32_t from, rt_uint32_t to) +; A4 --> from +; B4 --> to + .global rt_hw_context_switch_interrupt +rt_hw_context_switch_interrupt: + SUB B15,0x8,B15 + STW B4,*B15[2] + STW A4,*B15[1] + LDW *+B14(rt_thread_switch_interrupt_flag),B4 + NOP 4 + CMPEQ 1,B4,B0 + [ B0] BNOP _reswitch,5 + MVK 1,B4 + STW B4,*+B14(rt_thread_switch_interrupt_flag) + MV A4,B4 + STW B4,*+B14(rt_interrupt_from_thread) +_reswitch: + LDW *B15[2],B4 + NOP 4 + STW B4,*+B14(rt_interrupt_to_thread) + ADD 8,B15,B15 + BNOP B3,5 +;} + +;----------------------------------------------------------- +; +;void rt_interrupt_context_restore(void) +; + .global rt_interrupt_context_restore +rt_interrupt_context_restore: +;{ +; if rt_switch_interrupt_flag set, jump to rt_hw_context_switch_interrupt and don't return + MVKL rt_thread_switch_interrupt_flag,A3 + MVKH rt_thread_switch_interrupt_flag,A3 + LDW *A3,A1 + NOP 4 + CMPEQ 1,A1,A2 + [A2] BNOP rt_preempt_context_restore,5 + NOP 5 + LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) + LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) + LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) + + ADDAW .D1X SP,30,A15 + + LDDW .D1T1 *++A15[1],A17:A16 + || LDDW .D2T2 *++SP[1],B17:B16 + LDDW .D1T1 *++A15[1],A19:A18 + || LDDW .D2T2 *++SP[1],B19:B18 + LDDW .D1T1 *++A15[1],A21:A20 + || LDDW .D2T2 *++SP[1],B21:B20 + LDDW .D1T1 *++A15[1],A23:A22 + || LDDW .D2T2 *++SP[1],B23:B22 + LDDW .D1T1 *++A15[1],A25:A24 + || LDDW .D2T2 *++SP[1],B25:B24 + LDDW .D1T1 *++A15[1],A27:A26 + || LDDW .D2T2 *++SP[1],B27:B26 + LDDW .D1T1 *++A15[1],A29:A28 + || LDDW .D2T2 *++SP[1],B29:B28 + LDDW .D1T1 *++A15[1],A31:A30 + || LDDW .D2T2 *++SP[1],B31:B30 + + LDDW .D1T1 *++A15[1],A1:A0 + || LDDW .D2T2 *++SP[1],B1:B0 + LDDW .D1T1 *++A15[1],A3:A2 + || LDDW .D2T2 *++SP[1],B3:B2 + || MVC .S2 B9,ITSR + LDDW .D1T1 *++A15[1],A5:A4 + || LDDW .D2T2 *++SP[1],B5:B4 + || MVC .S2 B11,RILC + LDDW .D1T1 *++A15[1],A7:A6 + || LDDW .D2T2 *++SP[1],B7:B6 + || MVC .S2 B10,ILC + LDDW .D1T1 *++A15[1],A9:A8 + || LDDW .D2T2 *++SP[1],B9:B8 + || MVC .S2 B13,IRP + + LDDW .D1T1 *++A15[1],A11:A10 + || LDDW .D2T2 *++SP[1],B11:B10 + || MVC .S2 B12,CSR + LDDW .D1T1 *++A15[1],A13:A12 + || LDDW .D2T2 *++SP[1],B13:B12 + + MV .D2X A15,SP + LDDW .D2T1 *++SP[1],A15:A14 + B .S2 IRP ; return from interruption + LDDW .D2T2 *+SP[1],SP:DP + NOP 4 + +rt_preempt_context_restore: + ZERO A12 + STW A12,*A3 ; clear rt_thread_switch_interrupt_flag + + MVKL rt_interrupt_from_thread,A11 + MVKH rt_interrupt_from_thread,A11 + LDW *A11,A10 + NOP + MVKL rt_interrupt_to_thread,B10 + MVKH rt_interrupt_to_thread,B10 + LDW *B10,B11 + NOP 3 + STW SP,*A10 ; store sp in preempted tasks's TCB + MV B11,A4 ; + B rt_hw_context_switch_to + NOP 5 +;} + + .end + diff --git a/libcpu/ti-dsp/c6x/cpuport.c b/libcpu/ti-dsp/c6x/cpuport.c new file mode 100644 index 0000000000..a00a2e9046 --- /dev/null +++ b/libcpu/ti-dsp/c6x/cpuport.c @@ -0,0 +1,225 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include +#include + +#include "trap.h" + +/*------------ rt_hw_cpu_shutdown() function ---------------------------------- + * DESCRIPTION: Shutdown CPU + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +RT_WEAK void rt_hw_cpu_shutdown(void) +{ + rt_kprintf("shutdown...\n"); + + rt_hw_interrupt_disable(); + + RT_ASSERT(0); +} +//----------------------------------------------------------------------------- + +/*------------ nested_exception_handler() function --------------------------- + * DESCRIPTION: Function handles Nested Exception + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ + +void nested_exception_handler(void) +{ + for ( ; ; ); +} +//----------------------------------------------------------------------------- + + +/*------------ hw_nmi_handler() function -------------------------------------- + * DESCRIPTION: Function handles NMI interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_nmi_handler(struct rt_hw_exp_stack_register *regs) +{ + for ( ; ; ); +} +//----------------------------------------------------------------------------- + + +/*------------ hw_bad_handler() function -------------------------------------- + * DESCRIPTION: Function handles Bad interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_bad_handler(void) +{ + for ( ; ; ); +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int4_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT4 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int4_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int5_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT5 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int5_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int6_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT6 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int6_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int7_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT7 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int7_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int8_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT8 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int8_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int9_handler() function ------------------------------------- + * DESCRIPTION: Function handles INT9 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int9_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int10_handler() function ------------------------------------ + * DESCRIPTION: Function handles INT10 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int10_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int11_handler() function ------------------------------------ + * DESCRIPTION: Function handles INT11 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int11_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int12_handler() function ------------------------------------ + * DESCRIPTION: Function handles INT12 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int12_handler(void) +{ +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int13_handler() function ------------------------------------ + * DESCRIPTION: Function handles INT13 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int13_handler(void) +{ + +} +//----------------------------------------------------------------------------- + + +/*------------------ hw_int14_handler() function ------------------------------ + * DESCRIPTION: Function handles INT14 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: +-----------------------------------------------------------------------------*/ +void hw_int14_handler(void) +{ +extern void rt_hw_systick_isr(); + rt_hw_systick_isr(); +} +//----------------------------------------------------------------------------- + + +/*------------ hw_int15_handler() function ------------------------------------ + * DESCRIPTION: Function handles INT15 interrupt + * ARGUMENTS: + * None + * RETURNED VALUE: None +-----------------------------------------------------------------------------*/ +void hw_int15_handler(void) +{ + +} + diff --git a/libcpu/ti-dsp/c6x/inct.asm b/libcpu/ti-dsp/c6x/inct.asm new file mode 100644 index 0000000000..4f866e4800 --- /dev/null +++ b/libcpu/ti-dsp/c6x/inct.asm @@ -0,0 +1,374 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; interrupt handler for C6678 DSP +;----------------------------------------------------------- + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +DP .set B14 +SP .set B15 +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; global function +;----------------------------------------------------------- + .global _nmi_handler + .global _bad_handler + .global _int4_handler + .global _int5_handler + .global _int6_handler + .global _int7_handler + .global _int8_handler + .global _int9_handler + .global _int10_handler + .global _int11_handler + .global _int12_handler + .global _int13_handler + .global _int14_handler + .global _int15_handler +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; extern function +;----------------------------------------------------------- + .ref hw_nmi_handler + .ref hw_bad_handler + .ref hw_int4_handler + .ref hw_int5_handler + .ref hw_int6_handler + .ref hw_int7_handler + .ref hw_int8_handler + .ref hw_int9_handler + .ref hw_int10_handler + .ref hw_int11_handler + .ref hw_int12_handler + .ref hw_int13_handler + .ref hw_int14_handler + .ref hw_int15_handler + .ref rt_hw_process_exception + .ref rt_interrupt_context_restore +; +;----------------------------------------------------------- +; + +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +SAVE_ALL .macro __rp, __tsr + STDW .D2T2 SP:DP,*--SP[1] + SUBAW .D2 SP,2,SP + ADD .D1X SP,-8,A15 + || STDW .D2T1 A15:A14,*SP--[16] ; save A15:A14 + + STDW .D2T2 B13:B12,*SP--[1] + || STDW .D1T1 A13:A12,*A15--[1] + || MVC .S2 __rp,B13 + + STDW .D2T2 B11:B10,*SP--[1] + || STDW .D1T1 A11:A10,*A15--[1] + || MVC .S2 CSR,B12 + + STDW .D2T2 B9:B8,*SP--[1] + || STDW .D1T1 A9:A8,*A15--[1] + || MVC .S2 RILC,B11 + STDW .D2T2 B7:B6,*SP--[1] + || STDW .D1T1 A7:A6,*A15--[1] + || MVC .S2 ILC,B10 + + STDW .D2T2 B5:B4,*SP--[1] + || STDW .D1T1 A5:A4,*A15--[1] + + STDW .D2T2 B3:B2,*SP--[1] + || STDW .D1T1 A3:A2,*A15--[1] + || MVC .S2 __tsr,B5 + + STDW .D2T2 B1:B0,*SP--[1] + || STDW .D1T1 A1:A0,*A15--[1] + || MV .S1X B5,A5 + + STDW .D2T2 B31:B30,*SP--[1] + || STDW .D1T1 A31:A30,*A15--[1] + || MVKL 1,A4 + + STDW .D2T2 B29:B28,*SP--[1] + || STDW .D1T1 A29:A28,*A15--[1] + STDW .D2T2 B27:B26,*SP--[1] + || STDW .D1T1 A27:A26,*A15--[1] + STDW .D2T2 B25:B24,*SP--[1] + || STDW .D1T1 A25:A24,*A15--[1] + STDW .D2T2 B23:B22,*SP--[1] + || STDW .D1T1 A23:A22,*A15--[1] + STDW .D2T2 B21:B20,*SP--[1] + || STDW .D1T1 A21:A20,*A15--[1] + STDW .D2T2 B19:B18,*SP--[1] + || STDW .D1T1 A19:A18,*A15--[1] + STDW .D2T2 B17:B16,*SP--[1] + || STDW .D1T1 A17:A16,*A15--[1] + + STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR + + STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC + STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 + .endm + +RESTORE_ALL .macro __rp, __tsr + LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) + LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) + LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) + + ADDAW .D1X SP,30,A15 + + LDDW .D1T1 *++A15[1],A17:A16 + || LDDW .D2T2 *++SP[1],B17:B16 + LDDW .D1T1 *++A15[1],A19:A18 + || LDDW .D2T2 *++SP[1],B19:B18 + LDDW .D1T1 *++A15[1],A21:A20 + || LDDW .D2T2 *++SP[1],B21:B20 + LDDW .D1T1 *++A15[1],A23:A22 + || LDDW .D2T2 *++SP[1],B23:B22 + LDDW .D1T1 *++A15[1],A25:A24 + || LDDW .D2T2 *++SP[1],B25:B24 + LDDW .D1T1 *++A15[1],A27:A26 + || LDDW .D2T2 *++SP[1],B27:B26 + LDDW .D1T1 *++A15[1],A29:A28 + || LDDW .D2T2 *++SP[1],B29:B28 + LDDW .D1T1 *++A15[1],A31:A30 + || LDDW .D2T2 *++SP[1],B31:B30 + + LDDW .D1T1 *++A15[1],A1:A0 + || LDDW .D2T2 *++SP[1],B1:B0 + LDDW .D1T1 *++A15[1],A3:A2 + || LDDW .D2T2 *++SP[1],B3:B2 + || MVC .S2 B9,__tsr + LDDW .D1T1 *++A15[1],A5:A4 + || LDDW .D2T2 *++SP[1],B5:B4 + || MVC .S2 B11,RILC + LDDW .D1T1 *++A15[1],A7:A6 + || LDDW .D2T2 *++SP[1],B7:B6 + || MVC .S2 B10,ILC + LDDW .D1T1 *++A15[1],A9:A8 + || LDDW .D2T2 *++SP[1],B9:B8 + || MVC .S2 B13,__rp + + LDDW .D1T1 *++A15[1],A11:A10 + || LDDW .D2T2 *++SP[1],B11:B10 + || MVC .S2 B12,CSR + LDDW .D1T1 *++A15[1],A13:A12 + || LDDW .D2T2 *++SP[1],B13:B12 + + MV .D2X A15,SP + LDDW .D2T1 *++SP[1],A15:A14 + B .S2 __rp ; return from interruption + LDDW .D2T2 *+SP[1],SP:DP + NOP 4 + .endm +;----------------------------------------------------------- +; interrupt macro definition +;----------------------------------------------------------- +RT_INTERRUPT_ENTRY .macro + SAVE_ALL IRP,ITSR + .endm + +RT_CALL_INT .macro __isr + CALLP __isr,B3 + B .S1 rt_interrupt_context_restore + NOP 5 + .endm +;----------------------------------------------------------- +; execption macro definition +;----------------------------------------------------------- +RT_EXECPTION_ENTRY .macro + SAVE_ALL NRP,NTSR + .endm + +RT_EXECPTION_EXIT .macro + RESTORE_ALL NRP,NTSR + .endm + +; +;----------------------------------------------------------- +; + + .sect ".text" +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; handler NMI interrupt +;----------------------------------------------------------- +_nmi_handler: +;{ + RT_EXECPTION_ENTRY + MVC .S2 EFR,B2 + CMPEQ .L2 1,B2,B2 + || MVC .S2 TSR,B1 + MV .D1X B2,A2 + || CLR .S2 B1,10,10,B1 + MVC .S2 B1,TSR + [!A2] MVKL .S1 rt_hw_process_exception,A0 + ||[B2] MVKL .S2 rt_hw_software_exception,B1 + [!A2] MVKH .S1 rt_hw_process_exception,A0 + ||[B2] MVKH .S2 rt_hw_software_exception,B1 + [!B2] B .S2X A0 + [B2] B .S2 B1 + [!B2] ADDAW .D2 SP,2,B1 + [!B2] MV .D1X B1,A4 + ADDKPC .S2 ret_from_trap,B3,2 +; +; return from trap +; +ret_from_trap: + MV .D2X A4,B0 + [!B0] MVKL .S2 ret_from_exception,B3 + [!B0] MVKH .S2 ret_from_exception,B3 + [!B0] BNOP .S2 B3,5 +; +; return from trap£¬restore exception context +; +ret_from_exception: + RT_EXECPTION_EXIT +; +rt_hw_software_exception: + MVKL .S1 rt_hw_process_exception,A0 + MVKH .S1 rt_hw_process_exception,A0 + B .S2X A0 + ADDAW .D2 SP,2,B1 + MV .D1X B1,A4 + ADDKPC .S2 ret_from_trap,B3,2 + NOP 2 +;} + +;----------------------------------------------------------- +; handler bad interrupt +;----------------------------------------------------------- +_bad_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_bad_handler +;} + +;----------------------------------------------------------- +; handler INT4 interrupt +;----------------------------------------------------------- +_int4_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int4_handler +;} + +;----------------------------------------------------------- +; handler INT5 interrupt +;----------------------------------------------------------- +_int5_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int5_handler +;} + +;----------------------------------------------------------- +; handler INT6 interrupt +;----------------------------------------------------------- +_int6_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int6_handler +;} + +;----------------------------------------------------------- +; handler INT7 interrupt +;----------------------------------------------------------- +_int7_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int7_handler +;} +;----------------------------------------------------------- +; handler INT8 interrupt +;----------------------------------------------------------- +_int8_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int8_handler +;} + +;----------------------------------------------------------- +; handler INT9 interrupt +;----------------------------------------------------------- +_int9_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int9_handler +;} + +;----------------------------------------------------------- +; handler INT10 interrupt +;----------------------------------------------------------- +_int10_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int10_handler +;} + +;----------------------------------------------------------- +; handler INT11 interrupt +;----------------------------------------------------------- +_int11_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int11_handler +;} + +;----------------------------------------------------------- +; handler INT12 interrupt +;----------------------------------------------------------- +_int12_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int12_handler +;} + +;----------------------------------------------------------- +; handler INT13 interrupt +;----------------------------------------------------------- +_int13_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int13_handler +;} + +;----------------------------------------------------------- +; handler INT14 interrupt +;----------------------------------------------------------- +_int14_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int14_handler +;} +;----------------------------------------------------------- +; handler INT15 interrupt +;----------------------------------------------------------- +_int15_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int15_handler +;} + .end diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c new file mode 100644 index 0000000000..69205e0d38 --- /dev/null +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + + +#include "c66xx.h" +#include "interrupt.h" + +#define MAX_HANDLERS 128 + +extern volatile rt_uint8_t rt_interrupt_nest; +struct rt_irq_desc isr_table[MAX_HANDLERS]; +rt_uint32_t rt_interrupt_from_thread; +rt_uint32_t rt_interrupt_to_thread; +rt_uint32_t rt_thread_switch_interrupt_flag; + +/** + * This function will initialize hardware interrupt + */ +void rt_hw_interrupt_init(void) +{ + /* init exceptions table */ + rt_memset(isr_table, 0x00, sizeof(isr_table)); + + /* init interrupt nest, and context in thread sp */ + rt_interrupt_nest = 0; + rt_interrupt_from_thread = 0; + rt_interrupt_to_thread = 0; + rt_thread_switch_interrupt_flag = 0; +} + +/** + * This function will mask a interrupt. + * @param vector the interrupt number + */ +void rt_hw_interrupt_mask(int vector) +{ + if (vector < 0 || vector >= MAX_HANDLERS) + return; +} + +/** + * This function will un-mask a interrupt. + * @param vector the interrupt number + */ +void rt_hw_interrupt_umask(int vector) +{ + if (vector < 0 || vector >= MAX_HANDLERS) + return; +} + +/** + * This function will install a interrupt service routine to a interrupt. + * @param vector the interrupt number + * @param new_handler the interrupt service routine to be installed + * @param old_handler the old interrupt service routine + */ +rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, + void *param, const char *name) +{ + rt_isr_handler_t old_handler = RT_NULL; + + if (vector < MAX_HANDLERS || vector >= 0) + { + old_handler = isr_table[vector].handler; + + if (handler != RT_NULL) + { +#ifdef RT_USING_INTERRUPT_INFO + rt_strncpy(isr_table[vector].name, name, RT_NAME_MAX); +#endif /* RT_USING_INTERRUPT_INFO */ + isr_table[vector].handler = handler; + isr_table[vector].param = param; + } + } + + return old_handler; +} + +void rt_hw_interrupt_clear(int vector) +{ + if (vector < 0 || vector >= MAX_HANDLERS) + return; +} diff --git a/libcpu/ti-dsp/c6x/interrupt.h b/libcpu/ti-dsp/c6x/interrupt.h new file mode 100644 index 0000000000..de7935b38a --- /dev/null +++ b/libcpu/ti-dsp/c6x/interrupt.h @@ -0,0 +1,24 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#ifndef __INTERRUPT_H__ +#define __INTERRUPT_H__ + +#include +#include + +void rt_hw_interrupt_init(void); +void rt_hw_interrupt_mask(int vector); +void rt_hw_interrupt_umask(int vector); +void rt_hw_interrupt_clear(int vector); +rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, + void *param, const char *name); + +#endif /* __INTERRUPT_H__ */ diff --git a/libcpu/ti-dsp/c6x/stack.asm b/libcpu/ti-dsp/c6x/stack.asm new file mode 100644 index 0000000000..4415a9767c --- /dev/null +++ b/libcpu/ti-dsp/c6x/stack.asm @@ -0,0 +1,103 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; build system stack for C6678 DSP +;----------------------------------------------------------- + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +ADDRESS_MSK .set 0xFFFFFFF0 + +; +;----------------------------------------------------------- +; + + .sect ".text" +; +; rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, rt_uint8_t *stack_addr, void *texit) +; tentry --> A4 +; parameter --> B4 +; stack_addr --> A6 +; texit --> B6 +;{ + .global rt_hw_stack_init +rt_hw_stack_init: + SUB A6,1,B1 ; + MVKL ADDRESS_MSK,A1 ; + MVKH ADDRESS_MSK,A1 ; Build address mask + MVC CSR,B0 ; + AND -2,B0,B0 ; Clear GIE bit + OR 2,B0,B0 ; Set PGIE bit for interrupt return + AND A1,B1,B1 ; Ensure alignment +; +; Actually build the stack frame. +; + MV B1,A3 + MV B14,A2 + STDW A3:A2,*--B1[1] ; Initial B15:B14 + SUBAW .D2 B1,2,B1 + ZERO A2 + ZERO A3 ; Clear value + STDW A3:A2,*B1--[1] ; Initial A15:A14 + STDW A3:A2,*B1--[1] ; Initial A13:A12 + STDW A3:A2,*B1--[1] ; Initial A11:A10 + STDW A3:A2,*B1--[1] ; Initial A9:A8 + STDW A3:A2,*B1--[1] ; Initial A7:A6 + MV B4,A2 + STDW A3:A2,*B1--[1] ; Initial A5:A4 + ZERO A2 + STDW A3:A2,*B1--[1] ; Initial A3:A2 + STDW A3:A2,*B1--[1] ; Initial A1:A0 + + STDW A3:A2,*B1--[1] ; Initial A31:A30 + STDW A3:A2,*B1--[1] ; Initial A29:A28 + STDW A3:A2,*B1--[1] ; Initial A27:A26 + STDW A3:A2,*B1--[1] ; Initial A25:A24 + STDW A3:A2,*B1--[1] ; Initial A23:A22 + STDW A3:A2,*B1--[1] ; Initial A21:A20 + STDW A3:A2,*B1--[1] ; Initial A19:A18 + STDW A3:A2,*B1--[1] ; Initial A17:A16 + + STDW A3:A2,*B1--[1] ; Initial B13:B12 + STDW A3:A2,*B1--[1] ; Initial B11:B10 + STDW A3:A2,*B1--[1] ; Initial B9:B8 + STDW A3:A2,*B1--[1] ; Initial B7:B6 + STDW A3:A2,*B1--[1] ; Initial B5:B4 + MV B6,A3 + STDW A3:A2,*B1--[1] ; Initial B3:B2 + ZERO A3 + STDW A3:A2,*B1--[1] ; Initial B1:B0 + + STDW A3:A2,*B1--[1] ; Initial B31:B30 + STDW A3:A2,*B1--[1] ; Initial B29:B28 + STDW A3:A2,*B1--[1] ; Initial B27:B26 + STDW A3:A2,*B1--[1] ; Initial B25:B24 + STDW A3:A2,*B1--[1] ; Initial B23:B22 + STDW A3:A2,*B1--[1] ; Initial B21:B20 + STDW A3:A2,*B1--[1] ; Initial B19:B18 + STDW A3:A2,*B1--[1] ; Initial B17:B16 + + MV A4,A3 + MV B0,A2 + STDW A3:A2,*B1--[1] ; Initial PC:CSR + + ZERO A2 + ZERO A3 + STDW A3:A2,*B1--[1] ; Initial ILC:RILC + B B3 + MVKL 0x3,B0 + MV B0,A3 + MVKL 1,A2 + STDW A3:A2,*B1--[1] ; Initial TSR:stack type + MV B1,A4 ; Save to TCB +;} + .end diff --git a/libcpu/ti-dsp/c6x/trap.c b/libcpu/ti-dsp/c6x/trap.c new file mode 100644 index 0000000000..eb1863fa9c --- /dev/null +++ b/libcpu/ti-dsp/c6x/trap.c @@ -0,0 +1,352 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "trap.h" +#include "c66xx.h" + +#include +#include + +void rt_trap_init(void) +{ + ack_exception(EXCEPT_TYPE_NXF); + ack_exception(EXCEPT_TYPE_EXC); + ack_exception(EXCEPT_TYPE_IXF); + ack_exception(EXCEPT_TYPE_SXF); + rt_hw_enable_exception(); +} + +void show_regs(struct rt_hw_exp_stack_register *regs) +{ + rt_kprintf("\n"); + rt_kprintf("PC: %08lx SP: %08lx\n", + regs->pc, regs->hw_register.sp); + rt_kprintf("Status: %08lx ORIG_A4: %08lx\n", + regs->csr, regs->orig_a4); + rt_kprintf("A0: %08lx B0: %08lx\n", + regs->hw_register.a0, regs->hw_register.b0); + rt_kprintf("A1: %08lx B1: %08lx\n", + regs->hw_register.a1, regs->hw_register.b1); + rt_kprintf("A2: %08lx B2: %08lx\n", + regs->hw_register.a2, regs->hw_register.b2); + rt_kprintf("A3: %08lx B3: %08lx\n", + regs->hw_register.a3, regs->hw_register.b3); + rt_kprintf("A4: %08lx B4: %08lx\n", + regs->hw_register.a4, regs->hw_register.b4); + rt_kprintf("A5: %08lx B5: %08lx\n", + regs->hw_register.a5, regs->hw_register.b5); + rt_kprintf("A6: %08lx B6: %08lx\n", + regs->hw_register.a6, regs->hw_register.b6); + rt_kprintf("A7: %08lx B7: %08lx\n", + regs->hw_register.a7, regs->hw_register.b7); + rt_kprintf("A8: %08lx B8: %08lx\n", + regs->hw_register.a8, regs->hw_register.b8); + rt_kprintf("A9: %08lx B9: %08lx\n", + regs->hw_register.a9, regs->hw_register.b9); + rt_kprintf("A10: %08lx B10: %08lx\n", + regs->hw_register.a10, regs->hw_register.b10); + rt_kprintf("A11: %08lx B11: %08lx\n", + regs->hw_register.a11, regs->hw_register.b11); + rt_kprintf("A12: %08lx B12: %08lx\n", + regs->hw_register.a12, regs->hw_register.b12); + rt_kprintf("A13: %08lx B13: %08lx\n", + regs->hw_register.a13, regs->hw_register.b13); + rt_kprintf("A14: %08lx B14: %08lx\n", + regs->hw_register.a14, regs->hw_register.dp); + rt_kprintf("A15: %08lx B15: %08lx\n", + regs->hw_register.a15, regs->hw_register.sp); + rt_kprintf("A16: %08lx B16: %08lx\n", + regs->hw_register.a16, regs->hw_register.b16); + rt_kprintf("A17: %08lx B17: %08lx\n", + regs->hw_register.a17, regs->hw_register.b17); + rt_kprintf("A18: %08lx B18: %08lx\n", + regs->hw_register.a18, regs->hw_register.b18); + rt_kprintf("A19: %08lx B19: %08lx\n", + regs->hw_register.a19, regs->hw_register.b19); + rt_kprintf("A20: %08lx B20: %08lx\n", + regs->hw_register.a20, regs->hw_register.b20); + rt_kprintf("A21: %08lx B21: %08lx\n", + regs->hw_register.a21, regs->hw_register.b21); + rt_kprintf("A22: %08lx B22: %08lx\n", + regs->hw_register.a22, regs->hw_register.b22); + rt_kprintf("A23: %08lx B23: %08lx\n", + regs->hw_register.a23, regs->hw_register.b23); + rt_kprintf("A24: %08lx B24: %08lx\n", + regs->hw_register.a24, regs->hw_register.b24); + rt_kprintf("A25: %08lx B25: %08lx\n", + regs->hw_register.a25, regs->hw_register.b25); + rt_kprintf("A26: %08lx B26: %08lx\n", + regs->hw_register.a26, regs->hw_register.b26); + rt_kprintf("A27: %08lx B27: %08lx\n", + regs->hw_register.a27, regs->hw_register.b27); + rt_kprintf("A28: %08lx B28: %08lx\n", + regs->hw_register.a28, regs->hw_register.b28); + rt_kprintf("A29: %08lx B29: %08lx\n", + regs->hw_register.a29, regs->hw_register.b29); + rt_kprintf("A30: %08lx B30: %08lx\n", + regs->hw_register.a30, regs->hw_register.b30); + rt_kprintf("A31: %08lx B31: %08lx\n", + regs->hw_register.a31, regs->hw_register.b31); +} + + +void do_trap(struct rt_exception_info *except_info, struct rt_hw_exp_stack_register *regs) +{ + rt_kprintf("Enter exception: %s\n", except_info->kernel_str); + + show_regs(regs); + + for( ; ; ); +} + + +static struct rt_exception_info iexcept_table[10] = { + { " - instruction fetch", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - fetch packet", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - execute packet", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - resource conflict", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - resource access", ABORT_TYPE_UNDDEF, ABORT_PRVREG_ILL }, + { " - privilege", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, + { " - loops buffer", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, + { " - software exception", ABORT_TYPE_UNDDEF, ABORT_ILLTRP_ILL }, + { " - unknown exception", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL } +}; + +/* + * Process an internal exception (non maskable) + */ +static int process_iexcept(struct rt_hw_exp_stack_register *regs) +{ + unsigned int iexcept_report = get_iexcept(); + unsigned int iexcept_num; + + ack_exception(EXCEPT_TYPE_IXF); + + while(iexcept_report) { + iexcept_num = __ffs(iexcept_report); + iexcept_report &= ~(1 << iexcept_num); + set_iexcept(iexcept_report); + + if (*(unsigned int *)regs->pc == BKPT_OPCODE) { + /* This is a breakpoint */ + struct rt_exception_info bkpt_exception = { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; + do_trap(&bkpt_exception, regs); + iexcept_report &= ~(0xFF); + set_iexcept(iexcept_report); + continue; + } + + do_trap(&iexcept_table[iexcept_num], regs); + } + return 0; +} + +static struct rt_exception_info except_table[128] = { + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - EMC CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - EMC bus error", ABORT_TYPE_MAP, ABORT_BUS_ADDRERR } +}; + +/* + * Process an external exception (maskable) + */ +static void process_except(struct rt_hw_exp_stack_register *regs) +{ + int except_num; + int bank = 0; + int i; + + for (i = 0; i <= 3; i++) { + while (INTC_MEXPMASK[i]) { + __dint(); + except_num = __ffs(INTC_MEXPMASK[i]); + INTC_MEXPMASK[i] &= ~(1 << except_num); /* ack the external exception */ + __rint(); + do_trap(&except_table[except_num + (bank << 5)], regs); + } + bank++; + } + + ack_exception(EXCEPT_TYPE_EXC); +} + +extern void hw_nmi_handler(struct rt_hw_exp_stack_register *regs); + +/* + * Main exception processing + */ +int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) +{ + int type; + int type_num; + int ie_num = 9; /* default is unknown exception */ + + while ((type = get_except_type()) != 0) { + type_num = fls(type) - 1; + + switch(type_num) { + case EXCEPT_TYPE_NXF: /* NMI exception */ + ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ + if (hw_nmi_handler != RT_NULL) + hw_nmi_handler(regs); + break; + + case EXCEPT_TYPE_IXF: /* internal exception */ + if (process_iexcept(regs)) + return 1; + break; + + case EXCEPT_TYPE_EXC: /* external exception */ + process_except(regs); + break; + + case EXCEPT_TYPE_SXF: /* software exception */ + ie_num = 8; + ack_exception(type_num); + break; + default: /* clear exception */ + ack_exception(type_num); + do_trap(&iexcept_table[ie_num], regs); + break; + } + } + return 0; +} + diff --git a/libcpu/ti-dsp/c6x/trap.h b/libcpu/ti-dsp/c6x/trap.h new file mode 100644 index 0000000000..5494fa900b --- /dev/null +++ b/libcpu/ti-dsp/c6x/trap.h @@ -0,0 +1,76 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#ifndef __TRAP_H__ +#define __TRAP_H__ + +#include "c66xx.h" + +/* + * exception operation macro + */ +#define disable_exception() +#define get_except_type() EFR +#define ack_exception(type) ECR = 1ul << (type) +#define get_iexcept() IERR +#define set_iexcept(mask) IERR = (mask) + +/* + * exception types + */ +#define EXCEPT_TYPE_NXF 31 /* NMI */ +#define EXCEPT_TYPE_EXC 30 /* external exception */ +#define EXCEPT_TYPE_IXF 1 /* internal exception */ +#define EXCEPT_TYPE_SXF 0 /* software exception */ + +#define EXCEPT_CAUSE_LBX (1 << 7) /* loop buffer exception */ +#define EXCEPT_CAUSE_PRX (1 << 6) /* privilege exception */ +#define EXCEPT_CAUSE_RAX (1 << 5) /* resource access exception */ +#define EXCEPT_CAUSE_RCX (1 << 4) /* resource conflict exception */ +#define EXCEPT_CAUSE_OPX (1 << 3) /* opcode exception */ +#define EXCEPT_CAUSE_EPX (1 << 2) /* execute packet exception */ +#define EXCEPT_CAUSE_FPX (1 << 1) /* fetch packet exception */ +#define EXCEPT_CAUSE_IFX (1 << 0) /* instruction fetch exception */ + +enum SYSTEM_TRAP_CODE +{ + ABORT_BUS_ADDRERR = 0, // bus address error + ABORT_BUS_ACCERR, // bus access permission error + ABORT_OPCODE_ILL, // illegal opcode + ABORT_PRVREG_ILL, // privilege register + ABORT_PRVOPC_ILL, // privileged opcode + ABORT_ILLTRP_ILL, // illegal trap + ABORT_BRKPT_ILL, // handling breakpoints +}; + +/* + * abort types + */ +#define ABORT_TYPE_BUS 0 // bus access abnormal +#define ABORT_TYPE_MAP 1 // page table mapping error +#define ABORT_TYPE_UNDDEF 0xff // undefined exception +#define ABORT_TYPE_FATAL 0xffffffff // fatal error + +struct rt_exception_info { + char *kernel_str; + int type; + int code; +}; + +#define BKPT_OPCODE 0x56454314 /* illegal opcode */ +#define INTC_MEXPMASK __SYSREGA(0x018000e0, unsigned int) + +#define __ffs(a) (_lmbd(1, _bitr(a))) +#define fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) + +void rt_trap_init(void); + +#endif /* __TRAP_H__ */ + diff --git a/libcpu/ti-dsp/c6x/vector.asm b/libcpu/ti-dsp/c6x/vector.asm new file mode 100644 index 0000000000..47eb8781f5 --- /dev/null +++ b/libcpu/ti-dsp/c6x/vector.asm @@ -0,0 +1,95 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; interrupt vector table for C6678 DSP +;----------------------------------------------------------- + +;----------------------------------------------------------- +; extern function +;----------------------------------------------------------- + .ref _c_int00 ; entry point + .ref _nmi_handler + .ref _bad_handler + .ref _int4_handler + .ref _int5_handler + .ref _int6_handler + .ref _int7_handler + .ref _int8_handler + .ref _int9_handler + .ref _int10_handler + .ref _int11_handler + .ref _int12_handler + .ref _int13_handler + .ref _int14_handler + .ref _int15_handler + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- + +; +; create interrupt vector for reset (interrupt 0) +; +VEC_RESET .macro addr + MVKL addr,B0 + MVKH addr,B0 + B B0 + MVC PCE1,B0 + NOP 4 + .align 32 + .endm + +; +; create interrupt vector for other used interrupts +; +IRQVEC .macro __name, __isr + .align 32 + .hidden __name + .global __name +__name: + B .S2 __isr + NOP + NOP + NOP + NOP + NOP + NOP + NOP + .endm +; +;----------------------------------------------------------- +; + +; +; vector table +; + .sect ".vecs" + .align 32 + .global vector +vector: + VEC_RESET _c_int00 + IRQVEC NMI, _nmi_handler + IRQVEC AINT, _bad_handler + IRQVEC MSGINT,_bad_handler + IRQVEC INT4, _int4_handler + IRQVEC INT5, _int5_handler + IRQVEC INT6, _int6_handler + IRQVEC INT7, _int7_handler + IRQVEC INT8, _int8_handler + IRQVEC INT9, _int9_handler + IRQVEC INT10, _int10_handler + IRQVEC INT11, _int11_handler + IRQVEC INT12, _int12_handler + IRQVEC INT13, _int13_handler + IRQVEC INT14, _int14_handler + IRQVEC INT15, _int15_handler + + .end -- cgit v1.3.1 From 456492e7eab69c7e9bb3feb2129dc5a905491efc Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 17 Nov 2021 17:43:42 +0800 Subject: 添加支持中断栈部分代码,修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-c6678/.ccsproject | 12 - bsp/ti-c6678/.cproject | 160 - bsp/ti-c6678/.project | 154 - .../.settings/org.eclipse.cdt.codan.core.prefs | 3 - .../.settings/org.eclipse.cdt.debug.core.prefs | 2 - .../.settings/org.eclipse.core.resources.prefs | 10 - bsp/ti-c6678/KeyStone.cmd | 47 - bsp/ti-c6678/applications/board.c | 60 - bsp/ti-c6678/applications/board.h | 20 - bsp/ti-c6678/applications/main.c | 99 - bsp/ti-c6678/driver/KeyStone_common.c | 4355 -------------------- bsp/ti-c6678/driver/KeyStone_common.h | 1090 ----- bsp/ti-c6678/driver/drv_timer.c | 55 - bsp/ti-c6678/driver/drv_timer.h | 19 - bsp/ti-c6678/rtconfig.h | 122 - bsp/ti-c6678/rtconfig_project.h | 23 - bsp/ti-tms320c6678/.ccsproject | 12 + bsp/ti-tms320c6678/.cproject | 160 + bsp/ti-tms320c6678/.project | 154 + .../.settings/org.eclipse.cdt.codan.core.prefs | 3 + .../.settings/org.eclipse.cdt.debug.core.prefs | 2 + .../.settings/org.eclipse.core.resources.prefs | 10 + bsp/ti-tms320c6678/KeyStone.cmd | 47 + bsp/ti-tms320c6678/applications/board.c | 57 + bsp/ti-tms320c6678/applications/board.h | 20 + bsp/ti-tms320c6678/applications/main.c | 80 + bsp/ti-tms320c6678/driver/drv_timer.c | 55 + bsp/ti-tms320c6678/driver/drv_timer.h | 19 + bsp/ti-tms320c6678/readme.txt | 3 + bsp/ti-tms320c6678/rtconfig.h | 122 + bsp/ti-tms320c6678/rtconfig_project.h | 23 + libcpu/ti-dsp/c6x/c66xx.h | 5 +- libcpu/ti-dsp/c6x/context.asm | 52 +- libcpu/ti-dsp/c6x/contextinc.asm | 187 + libcpu/ti-dsp/c6x/cpuport.c | 30 +- libcpu/ti-dsp/c6x/inct.asm | 374 -- libcpu/ti-dsp/c6x/interrupt.c | 1 - libcpu/ti-dsp/c6x/intexc.asm | 269 ++ libcpu/ti-dsp/c6x/stack.asm | 6 +- libcpu/ti-dsp/c6x/trap.c | 12 +- libcpu/ti-dsp/c6x/trap.h | 4 +- libcpu/ti-dsp/c6x/vector.asm | 32 +- 42 files changed, 1294 insertions(+), 6676 deletions(-) delete mode 100644 bsp/ti-c6678/.ccsproject delete mode 100644 bsp/ti-c6678/.cproject delete mode 100644 bsp/ti-c6678/.project delete mode 100644 bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs delete mode 100644 bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs delete mode 100644 bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs delete mode 100644 bsp/ti-c6678/KeyStone.cmd delete mode 100644 bsp/ti-c6678/applications/board.c delete mode 100644 bsp/ti-c6678/applications/board.h delete mode 100644 bsp/ti-c6678/applications/main.c delete mode 100644 bsp/ti-c6678/driver/KeyStone_common.c delete mode 100644 bsp/ti-c6678/driver/KeyStone_common.h delete mode 100644 bsp/ti-c6678/driver/drv_timer.c delete mode 100644 bsp/ti-c6678/driver/drv_timer.h delete mode 100644 bsp/ti-c6678/rtconfig.h delete mode 100644 bsp/ti-c6678/rtconfig_project.h create mode 100644 bsp/ti-tms320c6678/.ccsproject create mode 100644 bsp/ti-tms320c6678/.cproject create mode 100644 bsp/ti-tms320c6678/.project create mode 100644 bsp/ti-tms320c6678/.settings/org.eclipse.cdt.codan.core.prefs create mode 100644 bsp/ti-tms320c6678/.settings/org.eclipse.cdt.debug.core.prefs create mode 100644 bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs create mode 100644 bsp/ti-tms320c6678/KeyStone.cmd create mode 100644 bsp/ti-tms320c6678/applications/board.c create mode 100644 bsp/ti-tms320c6678/applications/board.h create mode 100644 bsp/ti-tms320c6678/applications/main.c create mode 100644 bsp/ti-tms320c6678/driver/drv_timer.c create mode 100644 bsp/ti-tms320c6678/driver/drv_timer.h create mode 100644 bsp/ti-tms320c6678/readme.txt create mode 100644 bsp/ti-tms320c6678/rtconfig.h create mode 100644 bsp/ti-tms320c6678/rtconfig_project.h create mode 100644 libcpu/ti-dsp/c6x/contextinc.asm delete mode 100644 libcpu/ti-dsp/c6x/inct.asm create mode 100644 libcpu/ti-dsp/c6x/intexc.asm diff --git a/bsp/ti-c6678/.ccsproject b/bsp/ti-c6678/.ccsproject deleted file mode 100644 index 82f98bbb00..0000000000 --- a/bsp/ti-c6678/.ccsproject +++ /dev/null @@ -1,12 +0,0 @@ - - - - - - - - - - - - diff --git a/bsp/ti-c6678/.cproject b/bsp/ti-c6678/.cproject deleted file mode 100644 index aef3a8c240..0000000000 --- a/bsp/ti-c6678/.cproject +++ /dev/null @@ -1,160 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/bsp/ti-c6678/.project b/bsp/ti-c6678/.project deleted file mode 100644 index d1c8afd3a3..0000000000 --- a/bsp/ti-c6678/.project +++ /dev/null @@ -1,154 +0,0 @@ - - - ti-c6678 - - - - - - org.eclipse.cdt.managedbuilder.core.genmakebuilder - - - - - org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder - full,incremental, - - - - - - com.ti.ccstudio.core.ccsNature - org.eclipse.cdt.core.cnature - org.eclipse.cdt.managedbuilder.core.managedBuildNature - org.eclipse.cdt.core.ccnature - org.eclipse.cdt.managedbuilder.core.ScannerConfigNature - - - - SConscript - 1 - PARENT-2-PROJECT_LOC/src/SConscript - - - clock.c - 1 - PARENT-2-PROJECT_LOC/src/clock.c - - - components.c - 1 - PARENT-2-PROJECT_LOC/src/components.c - - - context.asm - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/context.asm - - - cpu.c - 1 - PARENT-2-PROJECT_LOC/src/cpu.c - - - cpuport.c - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/cpuport.c - - - device.c - 1 - PARENT-2-PROJECT_LOC/src/device.c - - - idle.c - 1 - PARENT-2-PROJECT_LOC/src/idle.c - - - inct.asm - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/inct.asm - - - interrupt.c - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/interrupt.c - - - ipc.c - 1 - PARENT-2-PROJECT_LOC/src/ipc.c - - - irq.c - 1 - PARENT-2-PROJECT_LOC/src/irq.c - - - kservice.c - 1 - PARENT-2-PROJECT_LOC/src/kservice.c - - - mem.c - 1 - PARENT-2-PROJECT_LOC/src/mem.c - - - memheap.c - 1 - PARENT-2-PROJECT_LOC/src/memheap.c - - - mempool.c - 1 - PARENT-2-PROJECT_LOC/src/mempool.c - - - object.c - 1 - PARENT-2-PROJECT_LOC/src/object.c - - - scheduler.c - 1 - PARENT-2-PROJECT_LOC/src/scheduler.c - - - signal.c - 1 - PARENT-2-PROJECT_LOC/src/signal.c - - - slab.c - 1 - PARENT-2-PROJECT_LOC/src/slab.c - - - stack.asm - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/stack.asm - - - thread.c - 1 - PARENT-2-PROJECT_LOC/src/thread.c - - - timer.c - 1 - PARENT-2-PROJECT_LOC/src/timer.c - - - trap.c - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/trap.c - - - vector.asm - 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/vector.asm - - - diff --git a/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs b/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs deleted file mode 100644 index f653028c53..0000000000 --- a/bsp/ti-c6678/.settings/org.eclipse.cdt.codan.core.prefs +++ /dev/null @@ -1,3 +0,0 @@ -eclipse.preferences.version=1 -inEditor=false -onBuild=false diff --git a/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs b/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs deleted file mode 100644 index 2adc7b1dde..0000000000 --- a/bsp/ti-c6678/.settings/org.eclipse.cdt.debug.core.prefs +++ /dev/null @@ -1,2 +0,0 @@ -eclipse.preferences.version=1 -org.eclipse.cdt.debug.core.toggleBreakpointModel=com.ti.ccstudio.debug.CCSBreakpointMarker diff --git a/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs b/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs deleted file mode 100644 index 83b10321a8..0000000000 --- a/bsp/ti-c6678/.settings/org.eclipse.core.resources.prefs +++ /dev/null @@ -1,10 +0,0 @@ -eclipse.preferences.version=1 -encoding//Debug/applications/subdir_rules.mk=UTF-8 -encoding//Debug/applications/subdir_vars.mk=UTF-8 -encoding//Debug/driver/subdir_rules.mk=UTF-8 -encoding//Debug/driver/subdir_vars.mk=UTF-8 -encoding//Debug/makefile=UTF-8 -encoding//Debug/objects.mk=UTF-8 -encoding//Debug/sources.mk=UTF-8 -encoding//Debug/subdir_rules.mk=UTF-8 -encoding//Debug/subdir_vars.mk=UTF-8 diff --git a/bsp/ti-c6678/KeyStone.cmd b/bsp/ti-c6678/KeyStone.cmd deleted file mode 100644 index 0f30bc506e..0000000000 --- a/bsp/ti-c6678/KeyStone.cmd +++ /dev/null @@ -1,47 +0,0 @@ -/****************************************************************************/ -/* */ -/* M6678.cmd */ -/* Copyright (c): NUDT */ -/* */ -/* */ -/* Description: This file is a sample linker command file that can be */ -/* used for linking programs built with the C compiler and */ -/* running the resulting .out file on an M6678 */ -/* device. Use it as a guideline. You will want to */ -/* change the memory layout to match your specific C6xxx */ -/* target system. You may want to change the allocation */ -/* scheme according to the size of your program. */ -/* */ -/* */ -/****************************************************************************/ - --heap 0x800 --stack 0x1000 - -MEMORY -{ - VECTORS: o = 0x00800000 l = 0x00000200 - LL2_CODE: o = 0x00800200 l = 0x0001FE00 - LL2_RW_DATA: o = 0x00820000 l = 0x00020000 /*set memory protection attribitue as read/write*/ -} - -SECTIONS -{ - .vecs > VECTORS - - .text > LL2_CODE - .cinit > LL2_CODE - .const > LL2_CODE - .switch > LL2_CODE - .stack > LL2_RW_DATA - GROUP - { - .neardata - .rodata - .bss - } > LL2_RW_DATA - .far > LL2_RW_DATA - .fardata > LL2_RW_DATA - .cio > LL2_RW_DATA - .sysmem > LL2_RW_DATA -} diff --git a/bsp/ti-c6678/applications/board.c b/bsp/ti-c6678/applications/board.c deleted file mode 100644 index 140871fd75..0000000000 --- a/bsp/ti-c6678/applications/board.c +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology - * - * SPDX-License-Identifier: Apache-2.0 - * - * Change Logs: - * Date Author Notes - * 2021-11-16 Dystopia the first version - */ - -#include "board.h" -#include "trap.h" -#include "interrupt.h" -#include "drv_timer.h" -#include "KeyStone_common.h" - -#include - -/** - * This is the timer interrupt service routine. - * - */ -void rt_hw_systick_isr(void) -{ - /* enter interrupt */ - rt_interrupt_enter(); - - rt_tick_increase(); - - /* leave interrupt */ - rt_interrupt_leave(); -} - -/** - * This function will initial board. - */ -void rt_hw_board_init(void) -{ - // initial CPU core - KeyStone_common_CPU_init(); - - // initial interrupt controller - rt_hw_interrupt_init(); - - // initial system trap - rt_trap_init(); - - // initial system timer - hw_system_timer_init(); - -#ifdef RT_USING_HEAP - /* initialize memory system */ - rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); - rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); -#endif - // ...... - - hw_system_timer_start(); -} - diff --git a/bsp/ti-c6678/applications/board.h b/bsp/ti-c6678/applications/board.h deleted file mode 100644 index 88e6e94e6e..0000000000 --- a/bsp/ti-c6678/applications/board.h +++ /dev/null @@ -1,20 +0,0 @@ -/* - * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology - * - * SPDX-License-Identifier: Apache-2.0 - * - * Change Logs: - * Date Author Notes - * 2021-11-16 Dystopia the first version - */ - -#ifndef __BOARD_H__ -#define __BOARD_H__ - -#define RT_HW_HEAP_BEGIN (void*)0x0C000000 -#define RT_HW_HEAP_END (void*)0x0C100000 - -void rt_hw_board_init(void); - -#endif /* __BOARD_H__ */ - diff --git a/bsp/ti-c6678/applications/main.c b/bsp/ti-c6678/applications/main.c deleted file mode 100644 index fd418f09f4..0000000000 --- a/bsp/ti-c6678/applications/main.c +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology - * - * SPDX-License-Identifier: Apache-2.0 - * - * Change Logs: - * Date Author Notes - * 2021-11-16 Dystopia the first version - */ - -#include -#include - -#include "board.h" - -void rt_init_thread_entry(void *parameter) -{ - - while(1) - { - rt_thread_sleep(10); - } -} - -void rt_my_thread_entry(void *parameter) -{ - while(1) - { - rt_thread_sleep(20); - } -} - -int rt_application_init(void) -{ - rt_thread_t tid; - - tid = rt_thread_create("init", rt_init_thread_entry, RT_NULL, 4096, 3, 200); - if (tid != RT_NULL) - { - rt_thread_startup(tid); - } else { - return -1; - } - /******************************************************************/ - tid = rt_thread_create("mythread", rt_my_thread_entry, RT_NULL, 4096, 3, 200); - if (tid != RT_NULL) - { - rt_thread_startup(tid); - } else { - return -1; - } - - return 0; -} - -/** - * This function will startup RT-Thread RTOS. - */ -void rtthread_startup(void) -{ - /* disable interrupt first */ - rt_hw_interrupt_disable(); - - /* init board */ - rt_hw_board_init(); - - /* show version */ - rt_show_version(); - - /* init timer system */ - rt_system_timer_init(); - - /* init scheduler system */ - rt_system_scheduler_init(); - - /* init application */ - rt_application_init(); - - /* init timer thread */ - rt_system_timer_thread_init(); - - /* init idle thread */ - rt_thread_idle_init(); - - /* start scheduler */ - rt_system_scheduler_start(); - - /* never reach here */ - return ; -} - -void main(void) -{ - /* startup RT-Thread RTOS */ - rtthread_startup(); - - for ( ; ; ); -} - diff --git a/bsp/ti-c6678/driver/KeyStone_common.c b/bsp/ti-c6678/driver/KeyStone_common.c deleted file mode 100644 index 5807ed7aff..0000000000 --- a/bsp/ti-c6678/driver/KeyStone_common.c +++ /dev/null @@ -1,4355 +0,0 @@ -/****************************************************************************** - - Copyright (C), 2001-2012, Texas Instrument. - - ****************************************************************************** - File Name : KeyStone_common.c - Version : Initial Draft - Author : Brighton Feng - Created : 2010-12-12 - Last Modified : - Description : KeyStone common miscellaneous functions and definitions - History : - 1.Date : 2010-12-12 - Author : Brighton Feng - Modification: Created file - - 2.Date : 2012-10-6 - Author : Brighton Feng - Modification : Add memory protection and EDC configuration - - 3.Date : 2014-12-8 - Author : Brighton Feng - Modification : Add common device, CPU, interrupt initialization functions. - Print device information including device type, speed grade, - boot mode, required voltage, ID�� - Add EDMA enable/disable functions. - To support square wave generation by timer. -******************************************************************************/ - -#include -#include -#include -#include -#include -#include -#include -#include -#include "CSL_msmc.h" -#include "CSL_msmcAux.h" -#include "KeyStone_common.h" - -/*----------------------------------------------* - * external variables * - *----------------------------------------------*/ - -/*----------------------------------------------* - * external routine prototypes * - *----------------------------------------------*/ - -/*----------------------------------------------* - * internal routine prototypes * - *----------------------------------------------*/ - -/*----------------------------------------------* - * project-wide global variables * - *----------------------------------------------*/ -CSL_XmcRegs * gpXMC_regs = (CSL_XmcRegs *) CSL_XMC_CONFIG_REGS; -CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; -CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; -CSL_PllcRegs * gpPLLC_regs = (CSL_PllcRegs * )CSL_PLL_CONTROLLER_REGS; -CSL_PscRegs * gpPSC_regs = (CSL_PscRegs *)CSL_PSC_REGS; -CSL_MsmcRegs * gpMSMC_regs = (CSL_MsmcRegs *)CSL_MSMC_CONFIG_REGS; -CSL_GpioRegs * gpGPIO_regs= (CSL_GpioRegs * )CSL_GPIO_REGS; - -CSL_CPINTCRegs* gpCIC0_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; -CSL_CPINTCRegs* gpCIC1_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_1_REGS; -/*The register pointer for the CIC routing events DSP core. -By default, it is CIC0; but for core 4~7 of C6678, it is CIC1*/ -CSL_CPINTCRegs* gpCIC_regs= (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; - -CSL_TpccRegs* gpEDMA_CC0_regs = (CSL_TpccRegs*)CSL_EDMA0CC_REGS; -CSL_TpccRegs* gpEDMA_CC1_regs = (CSL_TpccRegs*)CSL_EDMA1CC_REGS; -CSL_TpccRegs* gpEDMA_CC2_regs = (CSL_TpccRegs*)CSL_EDMA2CC_REGS; -CSL_TpccRegs* gpEDMA_CC_regs[3] = { - (CSL_TpccRegs*)CSL_EDMA0CC_REGS, - (CSL_TpccRegs*)CSL_EDMA1CC_REGS, - (CSL_TpccRegs*)CSL_EDMA2CC_REGS -}; - -CSL_TptcRegs * gpEDMA_TC_0_0_regs=(CSL_TptcRegs *) CSL_EDMA0TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_0_1_regs=(CSL_TptcRegs *) CSL_EDMA0TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_1_0_regs=(CSL_TptcRegs *) CSL_EDMA1TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_1_1_regs=(CSL_TptcRegs *) CSL_EDMA1TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_1_2_regs=(CSL_TptcRegs *) CSL_EDMA1TC2_REGS; -CSL_TptcRegs * gpEDMA_TC_1_3_regs=(CSL_TptcRegs *) CSL_EDMA1TC3_REGS; -CSL_TptcRegs * gpEDMA_TC_2_0_regs=(CSL_TptcRegs *) CSL_EDMA2TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_2_1_regs=(CSL_TptcRegs *) CSL_EDMA2TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_2_2_regs=(CSL_TptcRegs *) CSL_EDMA2TC2_REGS; -CSL_TptcRegs * gpEDMA_TC_2_3_regs=(CSL_TptcRegs *) CSL_EDMA2TC3_REGS; - -CSL_TptcRegs * gpEDMA_TC_regs[10]= { - (CSL_TptcRegs *) CSL_EDMA0TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA0TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC2_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC3_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC2_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC3_REGS -}; - -CSL_TmrPlusRegs * gpTimer0Regs = (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS; -CSL_TmrPlusRegs * gpTimer1Regs = (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS; -CSL_TmrPlusRegs * gpTimer2Regs = (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS; -CSL_TmrPlusRegs * gpTimer3Regs = (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS; -CSL_TmrPlusRegs * gpTimer4Regs = (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS; -CSL_TmrPlusRegs * gpTimer5Regs = (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS; -CSL_TmrPlusRegs * gpTimer6Regs = (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS; -CSL_TmrPlusRegs * gpTimer7Regs = (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS; -CSL_TmrPlusRegs * gpTimer8Regs = (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)); -CSL_TmrPlusRegs * gpTimerRegs[9] = { - (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS, - (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)) -}; - -/*MPU for peripherals registers and data space*/ -CSL_MpuRegs * gpMPU0_regs= (CSL_MpuRegs *)CSL_MPU_0_REGS; -CSL_MpuRegs * gpMPU1_regs= (CSL_MpuRegs *)CSL_MPU_1_REGS; -CSL_MpuRegs * gpMPU2_regs= (CSL_MpuRegs *)CSL_MPU_2_REGS; -CSL_MpuRegs * gpMPU3_regs= (CSL_MpuRegs *)CSL_MPU_3_REGS; - -CSL_Emif4fRegs * gpDDR_regs= (CSL_Emif4fRegs *)CSL_DDR3_EMIF_CONFIG_REGS; -unsigned int gDSP_Core_Speed_Hz= 1000000000; //DSP core clock speed in Hz -TDSP_Board_Type gDSP_board_type= UNKNOWN; - -/*----------------------------------------------* - * module-wide global variables * - *----------------------------------------------*/ - -/*----------------------------------------------* - * constants * - *----------------------------------------------*/ - -/*----------------------------------------------* - * macros * - *----------------------------------------------*/ - -/*----------------------------------------------* - * routines' implementations * - *----------------------------------------------*/ - -/***************************************************************************** - Prototype : KeyStone_main_PLL_init - Description : DSP core PLL configuration - DSP core will be configured to run at ref_clock_MHz*multiplier/divisor - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : - Return Value : - - History : - 1.Date : 2010-12-12 - Author : Brighton Feng - Modification : Created function - 2.Date : May 19, 2013 - Author : Brighton Feng - Modification : update parameter check; replace constant with macro - -*****************************************************************************/ -void KeyStone_main_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - unsigned int i; - - if(0==divisor) - { - puts("Error: PLL input divider = 0"); - return; - } - - if(64SECCTL & PLLCTL_BYPASS_MASK) - { - /*a. In MAINPLLCTL1, write ENSAT = 1 (for optimal PLL operation) */ - gpBootCfgRegs->CORE_PLL_CTL1 |= PLLCTL1_ENSAT_MASK; /*Set ENSAT bit = 1*/ - - /*b. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLEN_MASK; - - /*c. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLENSRC_MASK; - - /*d. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ - /*mux switches properly to the bypass) */ - for(i=0; i< 4; i++) - asm(" nop 5"); - - /*e. In SECCTL, write BYPASS = 1 (bypass enabled in PLL mux) */ - gpPLLC_regs->SECCTL |= PLLCTL_BYPASS_MASK; - - /*f. In PLLCTL, write PLLPWRDN = 1 (power down the PLL) */ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLPWRDN_MASK; //Power down the PLL - - /*g. Wait for at least 5 ��s based on the reference clock CLKIN (PLL power down */ - /*toggling time) */ - for(i=0; i< 1000; i++) - asm(" nop 5"); - - /*h. In PLLCTL, write PLLPWRDN = 0 (power up the PLL) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLPWRDN_MASK; // Power up PLL - } - else - { - /*a. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ - gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLEN_MASK); - - /*b. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ - gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLENSRC_MASK); - - /*c. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ - /*mux switches properly to the bypass) */ - for(i=0; i< 4*multiplier/divisor; i++) - asm(" nop 5"); - } - - /*4. PLLM is split in two different registers. Program PLLM[5:0] in PLL multiplier */ - /*control register (PLLM) and PLLM[12:6] in MAINPLLCTL0 register */ - /*5. BWADJ is split in two different registers. Program BWADJ[7:0] in */ - /*MAINPLLCTL0 and BWADJ[11:8] in MAINPLLCTL1 register. BWADJ value */ - /*must be set to ((PLLM + 1) >> 1) - 1) */ - /*6. Program PLLD in MAINPLLCTL0 register */ - gpBootCfgRegs->CORE_PLL_CTL0 = ((multiplier-1)<PLLM= (multiplier*2-1)&0x3F; - gpBootCfgRegs->CORE_PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; - gpBootCfgRegs->CORE_PLL_CTL1 |= (multiplier-1)>>8; /*BWADJ[11:8]*/ - - /*7. In SECCTL, write OD (Output Divide) = 1 (that is divide-by-2) */ - gpPLLC_regs->SECCTL &= ~PLLCTL_OD_MASK; - gpPLLC_regs->SECCTL |= 1<PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); - - /* Step 8b: Program the RATIO field in PLLDIVn to the desired new divide-down rate. - If RATIO field is changed, the PLL controller will flag the change in the - corresponding bit of DCHANGE*/ - gpPLLC_regs->PLLDIV1_3[3-1] = (3-1) | CSL_PLLC_PLLDIV1_3_DNEN_MASK; //Set PLLDIV3 - gpPLLC_regs->PLLDIV4_16[4-4] = (5-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV4 - gpPLLC_regs->PLLDIV4_16[7-4] = (6-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV7 - - /* Step 8c: Set GOSET bit in PLLCMD to initiate the GO operation to change the divide - values and align the SYSCLKs as programmed */ - gpPLLC_regs->PLLCMD |= CSL_PLLC_PLLCMD_GOSET_MASK; - - /*Step 8d/e: Read the GOSTAT bit in PLLSTAT to make sure the bit returns to 0 to - indicate that the GO operation has completed */ - while((gpPLLC_regs->PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); -#endif - - /*9. In PLLCTL , write PLLRST = 1 (PLL reset is asserted)*/ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLRST_MASK; - - /*10. Wait for at least 7 ��s based on the reference clock CLKIN (PLL reset time) */ - for(i=0; i< 2000; i++) - asm(" nop 5"); - - /*11. In PLLCTL, write PLLRST = 0 (PLL reset is released) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLRST_MASK; - - /*12. Wait for at least 2000 �� CLKIN cycles �� (PLLD + 1) (PLL lock time) */ - for(i=0; i< 400*multiplier; i++) - asm(" nop 5"); - - /*13. In SECCTL, write BYPASS = 0 (enable PLL mux to switch to PLL mode) */ - gpPLLC_regs->SECCTL &= ~PLLCTL_BYPASS_MASK; - - /*14. Set the PLLEN bit in PLLCTL to 1 to enable PLL mode*/ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLEN_MASK; - -} -/***************************************************************************** - Prototype : KeyStone_PLL_init - Description : Config the PLL of PA and DDR - target clock speed will be ref_clock_MHz/inputDivisor*multiplier/outputDivisor - Input : unsigned int inputDivisor - unsigned int multiplier - unsigned int outputDivisor - Output : None - Return Value : 0 for success, other value for error - - History : - 1.Date : May 18, 2013 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -int KeyStone_PLL_init (PLL_ControlRegs * PLL_Regs, unsigned int inputDivisor, - unsigned int multiplier, unsigned int outputDivisor) -{ - if(0==inputDivisor) - { - puts("Error: PLL input divider = 0"); - return 1; - } - - if(64PLL_CTL1 = PLLCTL1_ENSAT_MASK; - - /*2. In PLLCTL0, write BYPASS = 1 (set the PLL in Bypass)*/ - PLL_Regs->PLL_CTL0 |= PLLCTL_BYPASS_MASK; - - /*3. Program PLLM and PLLD in PLLCTL0 register*/ - /*4. Program BWADJ[7:0] in PLLCTL0 and BWADJ[11:8] in PLLCTL1 register. - BWADJ value must be set to ((PLLM + 1) >> 1) �C 1)*/ - PLL_Regs->PLL_CTL0 = ((multiplier/2-1)<PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; - PLL_Regs->PLL_CTL1 |= (multiplier/2-1)>>8; /*BWADJ[11:8]*/ - - /*5. In PLLCTL1, write PLLRST = 1 (PLL is reset)*/ - PLL_Regs->PLL_CTL1 |= PLLCTL1_PLLRESET_MASK; //Set RESET bit = 1 - - /*6. Wait for at least 7 us based on the reference clock (PLL reset time)*/ - TSC_delay_us(7); - - /*For PASS, In PASSPLLCTL1, write PLLSELECT = 1 - (for selecting the output of PA PLL as the input to PASS)*/ - if(PLL_Regs==(PLL_ControlRegs *)gpBootCfgRegs->PA_PLL_CTL0) - PLL_Regs->PLL_CTL1 |= PLLCTL1_PAPLL_MASK; - - /*7. In PLLCTL1, write PLLRST = 0 (PLL reset is released)*/ - PLL_Regs->PLL_CTL1 &= ~PLLCTL1_PLLRESET_MASK; //Clear RESET bit - - /*8. Wait for at least 500 * REFCLK cycles * (PLLD + 1) (PLL lock time)*/ - TSC_delay_us(500); - - /*9. In PLLCTL0, write BYPASS = 0 (switch to PLL mode)*/ - PLL_Regs->PLL_CTL0 &= ~PLLCTL_BYPASS_MASK ; - - return 0; -} -/***************************************************************************** - Prototype : KeyStone_PASS_PLL_init - Description : Config the PASS PLL - target clock speed will be ref_clock_MHz/divisor*multiplier - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : None - Return Value : - - History : - 1.Date : 2013-2-14 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_PASS_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - //output divisor for PASS PLL should be 2 - if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->PA_PLL_CTL0, - divisor, multiplier*2, 2)) - { - printf("Initialize PASS PLL clock = %.2fMHz/%dx%d = %.3fMHz\n", - ref_clock_MHz, divisor, multiplier, - ref_clock_MHz*multiplier/divisor); - } -} - -/***************************************************************************** - Prototype : KeyStone_DDR_PLL_init - Description : Config the DDR PLL - target clock speed will be ref_clock_MHz/divisor*multiplier - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : None - Return Value : - - History : - 1.Date : 2013-8-18 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_DDR_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - //output divisor for DDR PLL should be 2 - if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->DDR3_PLL_CTL0, - divisor, multiplier, 2)) - { - printf("Initialize DDR speed = %.2fMHzx/%dx%d = %.3fMTS\n", - ref_clock_MHz, divisor, multiplier, - ref_clock_MHz*multiplier/divisor); - } -} - -/*===============================TSC===================================*/ -unsigned int cycle_measure_overhead=50; -/***************************************************************************** - Prototype : calc_cycle_measure_overhead - Description : calclucate the cycles measurement overhead - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void calc_cycle_measure_overhead() -{ - unsigned int cycle_cold, cycle_warm; - cycle_cold= TSCL; - cycle_cold = TSC_getDelay(cycle_cold); - cycle_warm= TSCL; - cycle_warm = TSC_getDelay(cycle_warm); - cycle_measure_overhead = (cycle_cold + cycle_warm)/2; -} - -/***************************************************************************** - Prototype : TSC_init - Description : Initialize Time stamp counter to measure cycles - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void TSC_init() -{ - TSCL = 0; /* Enable the TSC */ - calc_cycle_measure_overhead(); -} - -/***************************************************************************** - Prototype : TSC_delay_ms - Description : Implement the delay function in millisecond - Input : Uint32 ms - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void TSC_delay_ms(Uint32 ms) -{ - volatile unsigned long long startTSC, currentTSC; - unsigned long long delay_cycles; - Uint32 tscl, tsch; - - tscl= TSCL; - tsch= TSCH; - startTSC= _itoll(tsch,tscl); - - delay_cycles= ((unsigned long long)ms*gDSP_Core_Speed_Hz/1000); - - do - { - tscl= TSCL; - tsch= TSCH; - currentTSC= _itoll(tsch,tscl); - } - while((currentTSC-startTSC)TGCR) - { - gpTimerRegs[timer_num]->TGCR= 0; - gpTimerRegs[timer_num]->TCR= 0; - } -} - - /***************************************************************************** - Prototype : Timer64_Init - Description : Initialize a 64-bit timer - Input : Timer64_Config * tmrCfg - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void Timer64_Init(Timer64_Config * tmrCfg) -{ - Reset_Timer(tmrCfg->timer_num); - - gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; - gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; - - /*please note, in clock mode, two timer periods generate a clock, - one timer period output high voltage level, the other timer period - output low voltage level, so, the timer period should be half to the - desired output clock period*/ - if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) - tmrCfg->period= tmrCfg->period/2; - - /*the value written into period register is the expected value minus one*/ - gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); - gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); - if(tmrCfg->reload_period>1) - { - gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); - gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); - } - - if(TIMER_WATCH_DOG==tmrCfg->timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= - /*Select watch-dog mode*/ - (CSL_TMR_TIMMODE_WDT<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK - /*for plus featuers, dual 32-bit unchained timer mode should be used*/ - |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; - } - else - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= - /*Select 64-bit general timer mode*/ - (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& - ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); - - if(TIMER_WATCH_DOG==tmrCfg->timerMode) - { - /*enable watchdog timer*/ - gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<WDTCR = - (CSL_TMR_WDTCR_WDKEY_CMD1<WDTCR = - (CSL_TMR_WDTCR_WDKEY_CMD2<0x3FFFFFFF) - { - printf("Enable power domain %d timeout!\n", pwrDmnNum); - return -2; - } - } - } - - /* Enable the clocks too*/ - CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_ENABLE); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Enable clock domain %d timeout!\n", moduleNum); - return -2; - } - } - - /* Return PSC status */ - if ((CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_ON) && - (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_ENABLE)) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } -} -/***************************************************************************** - Prototype : KeyStone_disable_PSC_module - Description : Disable the PSC module in KeyStone device - Input : Uint32 pwrDmnNum - Uint32 moduleNum - Output : None - Return Value : - - History : - 1.Date : 2010/2/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -Int32 KeyStone_disable_PSC_module (Uint32 pwrDmnNum, Uint32 moduleNum) -{ - Uint32 uiStartTSC= TSCL; - - /* disable the clocks*/ - CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_SWRSTDISABLE); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Disable clock domain %d timeout!\n", moduleNum); - return -2; - } - } - - /* Return PSC status */ - if (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_SWRSTDISABLE) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } - -} -/***************************************************************************** - Prototype : KeyStone_disable_PSC_Power_Domain - Description : Disable the PSC power domain - Input : Uint32 pwrDmnNum - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -Int32 KeyStone_disable_PSC_Power_Domain (Uint32 pwrDmnNum) -{ - Uint32 uiStartTSC= TSCL; - - /* Set Power domain to OFF */ - CSL_PSC_disablePowerDomain (pwrDmnNum); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Disable power domain %d timeout!\n", pwrDmnNum); - return -2; - } - } - - /* Return PSC status */ - if (CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_OFF) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } - -} - -/*============================EDMA=====================================*/ - /***************************************************************************** - Prototype : EDMA_channel_TC_cfg - Description : Setup uiChannel of an EDMA to use uiTC - Input : Uint32 uiCC - Uint32 uiChannel - Uint32 uiTC - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_channel_TC_cfg (Uint32 uiCC, - Uint32 uiChannel, Uint32 uiTC) -{ - gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8] = - (gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8]&(~(0xF<<((uiChannel&7)*4)))) - |(uiTC<<((uiChannel&7)*4)); -} -/***************************************************************************** - Prototype : EDMA_TC_priority_cfg - Description : Setup uiChannel of an EDMA TC priority - Input : Uint32 uiCC - Uint32 uiPri - Uint32 uiTC - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_TC_priority_cfg(Uint32 uiCC, - Uint32 uiPri, Uint32 uiTC) -{ - gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI= - (gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI&(~(0xF<<((uiTC&3)*4)))) - |(uiPri<<((uiTC&3)*4)); -} -/***************************************************************************** - Prototype : EDMA_init - Description : Initialize all EDMA registers and clear the event - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_init () -{ - int i; - unsigned int * uipPaRAM; - - /*clear PaRAM*/ - uipPaRAM= (unsigned int *)&(gpEDMA_CC0_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC0_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - uipPaRAM= (unsigned int *)&(gpEDMA_CC1_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC1_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - uipPaRAM= (unsigned int *)&(gpEDMA_CC2_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC2_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - /*Assign PaRAM for different channels*/ - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - /*Assign TC/Queue for different channels*/ - gpEDMA_CC0_regs->TPCC_DMAQNUM[0]= 0x10101010; - gpEDMA_CC0_regs->TPCC_DMAQNUM[1]= 0x10101010; - - gpEDMA_CC1_regs->TPCC_DMAQNUM[0]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[1]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[2]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[3]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[4]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[5]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[6]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[7]= 0x32103210; - - gpEDMA_CC2_regs->TPCC_DMAQNUM[0]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[1]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[2]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[3]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[4]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[5]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[6]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[7]= 0x32103210; - - /*clear any events and status*/ - gpEDMA_CC0_regs->TPCC_ECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_EECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_ICR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_IECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_EMCR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_QEMCR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_SECR= 0xFFFF; - - gpEDMA_CC1_regs->TPCC_ECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ICR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ICRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_IECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_IECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EMCR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EMCRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_QEMCR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC1_regs->TPCC_SECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_SECRH= 0xFFFFFFFF; - - gpEDMA_CC2_regs->TPCC_ECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ICR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ICRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_IECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_IECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EMCR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EMCRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_QEMCR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC2_regs->TPCC_SECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_SECRH= 0xFFFFFFFF; - - for(i=0; iTPTC_ERRCLR= 0xF; - - //enable error interrupt - gpEDMA_TC_regs[i]->TPTC_ERREN= - (1<TPCC_EESR= 1<<(uiChannel); - } - else - { - //enable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EESRH= 1<<(uiChannel-32); - } -} - -void EDMA_event_disable(Uint32 uiCC, Uint32 uiChannel) -{ - if(uiChannel<32) - { - //disable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EECR= 1<<(uiChannel); - } - else - { - //disable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EECRH= 1<<(uiChannel-32); - } -} - -void EDMA_interrupt_enable(Uint32 uiCC, Uint32 uiIntNum) -{ - if(uiIntNum<32) - { - //enable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IESR= 1<<(uiIntNum); - } - else - { - //enable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IESRH= 1<<(uiIntNum-32); - } -} - -void EDMA_interrupt_disable(Uint32 uiCC, Uint32 uiIntNum) -{ - if(uiIntNum<32) - { - //disable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IECR= 1<<(uiIntNum); - } - else - { - //disable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IECRH= 1<<(uiIntNum-32); - } -} - -/***************************************************************************** - Prototype : EDMA_wait - Description : wait the pending EDMA complete - Input : EDMA_CC_Channel_Num CC_channel - Output : None - Return Value : - - History : - 1.Date : 2012/10/30 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_wait(EDMA_CC_Channel_Num CC_channel) -{ - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - - if(uiChannel<32) - { - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - } - else - { - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannel -= 32; - } - - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannel)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannel); -} - -/***************************************************************************** - Prototype : EDMA_Copy - Description : EDMA copy function with manual trigger - Input : unsigned int srcAddr - unsigned int dstAddr - unsigned int byteCount, <64KB - EDMA_CC_Channel_Num CC_channel - DMA_Wait wait - Output : None - Return Value : - - History : - 1.Date : 2012/10/30 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_copy(unsigned int srcAddr, unsigned int dstAddr, - unsigned int byteCount, EDMA_CC_Channel_Num CC_channel, DMA_Wait wait) -{ - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel; - volatile Uint32 * TPCC_ESR; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - - EDMACCRegs->PARAMSET[uiChannel].OPT= - CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, - CSL_EDMA3_TCCH_DIS, - CSL_EDMA3_ITCINT_DIS, - CSL_EDMA3_TCINT_EN, - uiChannel, - CSL_EDMA3_TCC_NORMAL, - CSL_EDMA3_FIFOWIDTH_NONE, - CSL_EDMA3_STATIC_DIS, - CSL_EDMA3_SYNC_A, - CSL_EDMA3_ADDRMODE_INCR, - CSL_EDMA3_ADDRMODE_INCR); - EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(srcAddr); - EDMACCRegs->PARAMSET[uiChannel].A_B_CNT=CSL_EDMA3_CNT_MAKE(byteCount&0xFFFF, 1); - EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(dstAddr); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 1); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; - - if(uiChannel<32) - { - TPCC_ESR= &EDMACCRegs->TPCC_ESR; - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - } - else - { - TPCC_ESR= &EDMACCRegs->TPCC_ESRH; - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannel -= 32; - } - - /*Manually trigger the EDMA*/ - (*TPCC_ESR)= 1<<(uiChannel); - - if(wait) - { - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannel)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannel); - } -} - -/***************************************************************************** - Prototype : EDMA_fill - Description : EDMA fill function with manual trigger - Input : unsigned int address, must align to 8 bytes boundary - unsigned long long data - unsigned int byteCount, must be multiple of 8 - EDMA_CC_Channel_Num CC_channel - Output : None - Return Value : - - History : - 1.Date : 2013/8/11 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_fill(unsigned int address, unsigned long long data, - unsigned int byteCount, EDMA_CC_Channel_Num CC_channel) -{ - int i; - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel, uiChannelShift, uiBCNT; - volatile Uint32 * TPCC_ESR; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - unsigned long long tempBuf[128/8]; - Uint32 tempBufSize=128, headerSize, tailSize; - - if(tempBufSize>byteCount) - tempBufSize=byteCount; - - for(i=0; i< tempBufSize/8; i++) - tempBuf[i]= data; - - /*split the transfer into 3 sections at 128 byte boundary*/ - if(address&127) //header address not start on 128 byte boundary - { - headerSize= 128- (address&127); - if(headerSize>byteCount) - headerSize=byteCount; - EDMA_copy((Uint32)tempBuf, address, headerSize, CC_channel, DMA_WAIT); - address+= headerSize; - byteCount-= headerSize; - } - - if(byteCount&&((address+byteCount)&127))//tail address not start on 128 byte boundary - { - tailSize= (address+byteCount)&127; - EDMA_copy((Uint32)tempBuf, address+byteCount-tailSize, tailSize, CC_channel, DMA_WAIT); - byteCount-= tailSize; - } - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - if(uiChannel<32) - { - TPCC_ESR= &EDMACCRegs->TPCC_ESR; - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - uiChannelShift= uiChannel; - } - else - { - TPCC_ESR= &EDMACCRegs->TPCC_ESRH; - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannelShift= uiChannel - 32; - } - - EDMACCRegs->PARAMSET[uiChannel].OPT= - CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, - CSL_EDMA3_TCCH_DIS, - CSL_EDMA3_ITCINT_DIS, - CSL_EDMA3_TCINT_EN, - uiChannel, - CSL_EDMA3_TCC_NORMAL, - CSL_EDMA3_FIFOWIDTH_NONE, - CSL_EDMA3_STATIC_EN, //keep PARAM unchanged - CSL_EDMA3_SYNC_AB, - CSL_EDMA3_ADDRMODE_INCR, - CSL_EDMA3_ADDRMODE_INCR); - EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(tempBuf); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= CSL_EDMA3_BIDX_MAKE(0, 128); - EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 0); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; - - while(byteCount) //the reminding must be multiple of 128 bytes - { - uiBCNT= byteCount/128; - if(uiBCNT>65535) - uiBCNT= 65535; - - EDMACCRegs->PARAMSET[uiChannel].A_B_CNT= CSL_EDMA3_CNT_MAKE(128, uiBCNT); - EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(address); - - /*Manually trigger the EDMA*/ - (*TPCC_ESR)= 1<<(uiChannelShift); - - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannelShift)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannelShift); - - byteCount -= uiBCNT*128; - address += uiBCNT*128; - } -} - -/***************************************************************************** - Prototype : IDMA_wait - Description : wait the pending IDMA complete - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void IDMA_wait() -{ - /* Wait until copying is completed */ - while (gpCGEM_regs->IDMA1_STAT); -} -/***************************************************************************** - Prototype : IDMA_copy - Description : implement the data copy via IDMA - Input : unsigned int srcAddr - unsigned int dstAddr - unsigned int byteCount, <64KB - IDMA_Wait wait - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brigthon - Modification : Created function - -*****************************************************************************/ -void IDMA_copy(unsigned int srcAddr, unsigned int dstAddr, - unsigned int byteCount, DMA_Wait wait) -{ - gpCGEM_regs->IDMA1_SOURCE= srcAddr; - gpCGEM_regs->IDMA1_DEST= dstAddr; - gpCGEM_regs->IDMA1_COUNT= byteCount&0xFFFC; - - if(wait) - { - /* Wait until copying is completed */ - while (gpCGEM_regs->IDMA1_STAT); - } -} -/***************************************************************************** - Prototype : EDMA_CC_error_handler - Description : Edma channel controller error processing - Input : Uint32 edmaNum, EDMA module number (0~2) - Output : None - Return Value : - - History : - 1.Date : 2012/11/7 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_CC_error_handler(Uint32 edmaNum) -{ - int i; - CSL_TpccRegs* EDMACCRegs= gpEDMA_CC_regs[edmaNum]; - Uint32 EMR, EMRH= 0, QEMR, CCERR; - - //read error status - EMR= EDMACCRegs->TPCC_EMR; - QEMR= EDMACCRegs->TPCC_QEMR; - CCERR= EDMACCRegs->TPCC_CCERR; - exception_record.status.ext_sts.info.edma.CC_info.EMR= EMR; - exception_record.status.ext_sts.info.edma.CC_info.QEMR= QEMR; - exception_record.status.ext_sts.info.edma.CC_info.CCERR= CCERR; - - //clear error status - EDMACCRegs->TPCC_EMCR= EMR; - EDMACCRegs->TPCC_QEMCR= QEMR; - EDMACCRegs->TPCC_CCERRCLR= CCERR; - - //channel 32~63 for EDMA CC1 and CC2 - if(0TPCC_EMRH; - exception_record.status.ext_sts.info.edma.CC_info.EMRH= EMRH; - - //clear error status - EDMACCRegs->TPCC_EMCRH= EMRH; - } - - for(i=0; i<32; i++) - { - if((EMR>>i)&1) - printf(" EDMA Channel %d event missed.\n", i); - if((EMRH>>i)&1) - printf(" EDMA Channel %d event missed.\n", i+32); - } - - for(i=0; i<8; i++) - { - if((QEMR>>i)&1) - printf(" QDMA Channel %d event missed.\n", i); - } - - for(i=0; i<4; i++) - { - if((CCERR>>i)&1) - printf(" Queue %d Watermark/threshold has been exceeded.\n", i); - } - - if(CCERR&CSL_TPCC_TPCC_CCERR_TCCERR_MASK) - puts(" Total number of allowed TCCs has been reached."); - -} -/***************************************************************************** - Prototype : EDMA_TC_error_handler - Description : Edma transfer controller error processing - Input : CSL_TptcRegs * edmaTCRegs - Output : None - Return Value : - - History : - 1.Date : 2012/11/7 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_TC_error_handler(CSL_TptcRegs * edmaTCRegs) -{ - Uint32 ERRSTAT, ERRDET, STAT; - - //read error status - ERRSTAT= edmaTCRegs->TPTC_ERRSTAT; - ERRDET= edmaTCRegs->TPTC_ERRDET; - exception_record.status.ext_sts.info.edma.TC_info.ERRSTAT=ERRSTAT ; - exception_record.status.ext_sts.info.edma.TC_info.ERRDET= ERRDET; - - //clear error - edmaTCRegs->TPTC_ERRCLR= ERRSTAT; - - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_MMRAERR_MASK) - puts(" User attempted to read or write to an invalid address in configuration memory map."); - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_TRERR_MASK) - puts(" TR detected that violates constant addressing mode transfer (SAM or DAM is set) alignment rules or has ACNT or BCNT== 0."); - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_BUSERR_MASK) - { - puts(" EDMA3TC has detected an error at source or destination address."); - - STAT= ERRDET&CSL_TPTC_TPTC_ERRDET_STAT_MASK; - - if(STAT>=8) - printf(" write error (%d). ",STAT); - else if(STAT>=1) - printf(" read error (%d). ",STAT); - else - printf(" no error!?"); - - printf("TCC= %d. TCINTEN= %d. TCCHEN= %d\n", - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCC_MASK)>>CSL_TPTC_TPTC_ERRDET_TCC_SHIFT, - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCINTEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCINTEN_SHIFT, - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCCHEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCCHEN_SHIFT); - } - -} -/***************************************************************************** - Prototype : EDMA_error_handler - Description : EDMA error processing function - Input : Uint32 edmaNum - Uint32 errorFlag - error flag bit fields are defined as below - (follow the sequence in CIC) - 0 EDMACC_ERRINT EDMA3CC error interrupt - 2 EDMATC_ERRINT0 EDMA3TC0 error interrupt - 3 EDMATC_ERRINT1 EDMA3TC1 error interrupt - 4 EDMATC_ERRINT2 EDMA3TC2 error interrupt - 5 EDMATC_ERRINT3 EDMA3TC3 error interrupt - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_error_handler(Uint32 edmaNum, Uint32 errorFlag) -{ - int i; - - printf(" EDMA module %d error\n", edmaNum); - if(errorFlag&1) - EDMA_CC_error_handler(edmaNum); - - errorFlag >>= 2; - - for(i=0; i<4; i++) - { - if(errorFlag&(1<MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; - } - - /*3. Write a 1 to the LOCK field of the MPLKCMD register. This engages the lock.*/ - gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); -} - -/***************************************************************************** - Prototype : unlock_mem_prot_regs - Description : unlock memory protection registers - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma CODE_SECTION (unlock_mem_prot_regs, ".text:Core_MPAX") -void unlock_mem_prot_regs() -{ - int i; - - /*1. Write a 1 to the KEYR field in the MPLKCMD register. This resets some internal - status for the MPLK0 through the MPLK3 registers.*/ - gpCGEM_regs->MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; - } - - /*3. Write a 1 to the UNLOCK field in the MPLKCMD register. If the key written in - step 2 matches the stored key, the hardware disengages the lock. If the key written - in step 2 does not match, the hardware signals an exception. The hardware - reports the fault address as the address of the MPLKCMD register.*/ - gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); -} - -/***************************************************************************** - Prototype : L1_MPPA_setup - Description : setup the memory protection for local L1 memory - Input : volatile Uint32 MPPA_regs[], Uint32 MPPA[] - Output : None - Return Value : - -usage example: - Uint32 MPPA[16]= - { - MP_LOCAL|MP_SR|MP_UR, //page 0 for read only - MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for read/write - ...... - } - ...... - L1_MPPA_setup(gpCGEM_regs->L1PMPPA, MPPA); - - History : - 1.Date : 2012/12/6 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1_MPPA_setup(volatile Uint32 MPPA_regs[], Uint32 MPPA[]) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1PMPFCR = 1; - gpCGEM_regs->L1DMPFCR = 1; - - /*setup the memory protection attributes for 32 pages*/ - for(i=0; i<16; i++) - { - MPPA_regs[i] = MPPA[i]; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1P_memory_protection_cfg - Description : config "AccessPermisionMask" for L1P - Input : Uint32 AccessPermisionMask - Output : None - Return Value : -*****************************************************************************/ -void L1P_memory_protection_cfg(Uint32 AccessPermisionMask) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1PMPFCR = 1; - - /*set L1P only for cacheable local execution, disable all external access*/ - for(i=0; i<16; i++) - { - gpCGEM_regs->L1PMPPA[i] = AccessPermisionMask; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1D_memory_protection_cfg - Description : config "AccessPermisionMask" for L1P - Input : Uint32 AccessPermisionMask - Output : None - Return Value : -*****************************************************************************/ -void L1D_memory_protection_cfg(Uint32 AccessPermisionMask) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1DMPFCR = 1; - - /*set L1P only for cacheable local execution, disable all external access*/ - for(i=0; i<16; i++) - { - gpCGEM_regs->L1DMPPA[i] = AccessPermisionMask; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1_cache_protection - Description : protect L1 as cache - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1_cache_protection() -{ - /*set L1P only for cacheable local execution, disable all external access*/ - L1P_memory_protection_cfg(0); - - /*set L1D only for cacheable local read/write, disable all external access*/ - L1D_memory_protection_cfg(0); -} - - -/***************************************************************************** - Prototype : LL2_MPPA_setup - Description : setup the memory protection for local L2 memory - Input : Uint32 MPPA[] - Output : None - Return Value : -usage example: - Uint32 MPPA[32]= - { - MP_LOCAL|MP_SX|MP_UX, //page 0 for local code only - MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for local data only - ...... - } - ...... - LL2_MPPA_setup(MPPA); - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_MPPA_setup(Uint32 MPPA[]) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L2MPFCR = 1; - - /*setup the memory protection attributes for 32 pages*/ - for(i=0; i<32; i++) - { - gpCGEM_regs->L2MPPA[i] = MPPA[i]; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : LL2_Memory_Protection_cfg - Description : config "AccessPermisionMask" for local L2 memory section from - "startAddress" with "byteCount" size - Input : Uint32 startAddress - Uint32 byteCount - Uint32 AccessPermisionMask - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_Memory_Protection_cfg(Uint32 startAddress, - Uint32 byteCount, Uint32 AccessPermisionMask) -{ - int i; - Uint32 uiEndAddress; - Uint32 uiPageIndex, uiNumPages, uiPageSize, uiPageAddressMask, uiPageShift; - TDSP_Board_Type DSP_Board_Type; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - DSP_Board_Type = KeyStone_Get_dsp_board_type(); - - /*L2 memory protection size is 32KB for TCI6614, C6670, - it is 16KB for C6678*/ - uiPageSize= 32*1024; - uiPageAddressMask= 32*1024-1; - uiPageShift= 15; - if(C6678_EVM == DSP_Board_Type) - { - uiPageSize= 16*1024; - uiPageAddressMask= 16*1024-1; - uiPageShift= 14; - } - - if(startAddress>=0x10800000) - { - printf("LL2 memory protection start Address 0x%x is not a local address\n", - startAddress); - startAddress &= 0xFFFFFF; /*convert to local address*/ - } - uiEndAddress= startAddress+ byteCount; - - if(startAddress&uiPageAddressMask) - { - printf("LL2 memory protection start Address 0x%x does not align to page boundary\n", - startAddress); - startAddress &= (~uiPageAddressMask); - } - uiPageIndex= (startAddress-0x800000)>>uiPageShift; - - byteCount= uiEndAddress- startAddress; - if(byteCount&uiPageAddressMask) - { - printf("LL2 memory protection section size 0x%x is not multiple of page size\n", - byteCount); - byteCount = (byteCount+uiPageSize)&(~uiPageAddressMask); - } - uiNumPages= byteCount>>uiPageShift; - - for(i= 0; iL2MPPA[uiPageIndex+i] = AccessPermisionMask; - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : KeyStone_CorePac_AID_map - Description : map CorePac AID to PrivID: - map_table[0] assign the PrivID for AID0, - map_table[1] assign the PrivID for AID1 - ...... - map_table[5] assign the PrivID for AID5 - Input : Uint8 map_table[] - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_CorePac_AID_map(Uint8 map_table[]) -{ - int i; - Uint32 *PAMAP= (Uint32 *)&(gpCGEM_regs->PAMAP0); - - /*map all PrivID to AIDx by default*/ - for(i=0; i<16; i++) - PAMAP[i]= CSL_CGEM_PAMAP0_AID_MASK; - - /*map AID0~AID5*/ - for(i=0; i<6; i++) - { - if(map_table[i]<16) /*PrivID must be less than 16*/ - PAMAP[map_table[i]]= i; - } -} - -/***************************************************************************** - Prototype : KeyStone_PrivID_Remap - Description : privilege ID remap to AID - Input : int privID - int AID - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_PrivID_Remap(int privID, int AID) -{ - volatile unsigned int * pamapReg = NULL; - unsigned int val = 0; - - pamapReg = (volatile unsigned int *)(&gpCGEM_regs->PAMAP0 + privID); - - if(AID >= MAX_AID_NUM) - AID = 0; - val = *pamapReg; - - val &= (~CSL_CGEM_PAMAP0_AID_MASK); - - val |= ((AID<>4)) - { - printf("Segment replacement address 0x%x does not start from power-of-2 boundary corresponds to segment size 0x%x.\n", - RADDR, SegementSize); - RADDR &= (~(SegSizeMask>>4)); - printf("Extended replacement address to 0x%x.\n", RADDR); - } - - MPAX_regs->MPAXH= BADDR|(SegSizeBits-1); - MPAX_regs->MPAXL= RADDR|AccessPermisionMask; - -} - -/***************************************************************************** - Prototype : KeyStone_XMC_MPAX_setup - Description : configure multiple MPAX segments in XMC with a configuration - table. - Please note, the code of this function or the data used by this function - (stack, parameters...) can not be put in the segment that will be modified - by this function. Normally, to put this function and its related data in - LL2 is a good idea. - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma CODE_SECTION (KeyStone_XMC_MPAX_setup, ".text:Core_MPAX") -void KeyStone_XMC_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs) -{ - int i; - - if(firstSeg >= 16) - { - printf("The XMC MPAX segment number %d >= 16, not supported.\n ", firstSeg); - return; - } - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*CAUTION: - A MPAX segment can only be modified when there is no access to the space - of this segment. Any data in cache or prefetch buffer from the space of this - segment must be writeback and invalidated before the segment modification. - It is recommended to configure the MPAX at the very beginning of application - software before any shared memory is used. Code and data for CorePac MPAX - configuration should be allocated in LL2. - If a MPAX segment must be modified on-the-fly, the safer way is, to write - the new configuration to a unused higher segment, and then clear the old - segment. This is based on the fact that higher numbered segments take - precedence over lower numbered segments. */ - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - _mfence(); - _mfence(); //ensure all writeback invalidate have completed. - - for(i=numSegs-1; i>=0 ; i--) - { - KeyStone_MPAX_seg_setup((MPAX_Regs *)&gpXMC_regs->XMPAX[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : KeyStone_SMS_MPAX_setup - Description : configure multiple MPAX segments in SMS of MSMC with a conf- - iguration table - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Uint32 PrivID - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SMS_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) -{ - int i; - - if( gpMSMC_regs->SMS_MPAX_LCKSTAT&(1<=0 ; i--) - KeyStone_MPAX_seg_setup( - (MPAX_Regs *)&gpMSMC_regs->SMS_MPAX_PER_PRIVID[PrivID].SMS[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - - CSL_MSMC_lockSMS(PrivID); -} - -/***************************************************************************** - Prototype : KeyStone_SES_MPAX_setup - Description : configure multiple MPAX segments in SES of MSMC with a conf- - iguration table - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Uint32 PrivID - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SES_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) -{ - int i; - - if( gpMSMC_regs->SES_MPAX_LCKSTAT&(1<=0 ; i--) - KeyStone_MPAX_seg_setup( - (MPAX_Regs *)&gpMSMC_regs->SES_MPAX_PER_PRIVID[PrivID].SES[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - - CSL_MSMC_lockSES(PrivID); -} - -/***************************************************************************** - Prototype : KeyStone_MSMC_MP_interrupt_en - Description : Enable MSMC Memory protection error interrupt for PrivIDs - indicated by "PRIVID_MASK" - Input : Uint32 PRIVID_MASK - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_MSMC_MP_interrupt_en(Uint32 PRIVID_MASK) -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /*clear MP fault record*/ - gpMSMC_regs->SMPFCR = 1; - - /*clear interrupt error status flag*/ - gpMSMC_regs->SMIRC = (PRIVID_MASK)<SMIESTAT |= (PRIVID_MASK<> - CSL_CGEM_L2MPFSR_FID_SHIFT; - - printf(" memory protection exception caused by master with ID %d at 0x%x\n", - master_id, MPFAR); - } - - if (MPFSR & CSL_CGEM_L2MPFSR_UX_MASK) { - puts(" User Execute violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_UW_MASK) { - puts(" User Write violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_UR_MASK) { - puts(" User Read violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SX_MASK) { - puts(" Supervisor Execute violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SW_MASK) { - puts(" Supervisor Write violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SR_MASK) { - puts(" Supervisor Read violation"); - } - -} - -/***************************************************************************** - Prototype : KeyStone_MSMC_protection_exception_handler - Description : MSMC memory protection processing - Input : None - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_MSMC_protection_exception_handler() -{ - unsigned int master_id; - unsigned int priv_id; - unsigned int address; - unsigned int NM; - - address = gpMSMC_regs->SMPFAR; - - master_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FMSTID_MASK)>> - CSL_MSMC_SMPFR_FMSTID_SHIFT; - priv_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FPID_MASK)>> - CSL_MSMC_SMPFR_FPID_SHIFT; - - exception_record.status.ext_sts.info.memory.fault_address= address; - exception_record.status.ext_sts.info.memory.fault_status.SMPFR= gpMSMC_regs->SMPFR; - - NM = (gpMSMC_regs->SMPFXR & CSL_MSMC_SMPFXR_NM_MASK) >> CSL_MSMC_SMPFXR_NM_SHIFT; - - printf(" memory protection exception caused by master %d (PrivID= %d) at address 0x%x\n", - master_id, priv_id, address); - - if(1 == NM) - { - printf(" Fault is caused by the address not matching any of the segment BADDR\n"); - } - - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - /*clear fault record*/ - gpMSMC_regs->SMPFCR = 1; - /*clear interrupt error status flag*/ - gpMSMC_regs->SMIRC = (1<PROG_START_ADDRESS = uiStartAddress; - MPPA_regs->PROG_END_ADDRESS = uiEndAddress; - MPPA_regs->PROG_MPPA = AccessPermisionMask; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_setup - Description : peripherals MPU ranges configuration - Input : Uint32 uiMPU_num: number of the MPU to be setup - MPU_Range_Config MPU_cfg[]: MPU ranges configuration table - Uint32 numRangeCfg: number of ranges to be configured - Output : None - Return Value : - - History : - 1.Date : 2012/12/15 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_MPU_setup(Uint32 uiMPU_num, - MPU_Range_Config MPU_cfg[], Uint32 numRangeCfg) -{ - int i; - unsigned int mpuNumProgmableRange; - CSL_MpuRegs * mpuRegs; - - /*For Turbo Nyquist, add following code to modify initial value, - Or user can modify the initail values directly*/ - if(5==uiMPU_num) - TN_MPU5_constant(); - - mpuRegs= gpMPU_regs[uiMPU_num]; - - mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; - if(mpuNumProgmableRange == 0) - { - mpuNumProgmableRange = 16; - } - - if(numRangeCfg>mpuNumProgmableRange) - { - printf("MPU %d programmable ranges %d < %d.\n", - uiMPU_num, mpuNumProgmableRange, numRangeCfg); - numRangeCfg=mpuNumProgmableRange; - } - else if(numRangeCfg gstruMpuAddrRange[uiMPU_num].EndAddr) ) - { - printf("The configuration address is out of MPU %d protection range\n", - uiMPU_num); - continue; - } - - KeyStone_MPU_range_setup(&mpuRegs->PROG_REGION[i], - MPU_cfg[i].StartAddr, MPU_cfg[i].EndAddr, - MPU_cfg[i].AccessPermisionMask); - - } - - //clear unused ranges - for( ;iPROG_REGION[i].PROG_MPPA = 0; - } - - //clear status - mpuRegs->FAULT_CLEAR = 1; - mpuRegs->INT_ENABLED_STATUS_CLEAR = - CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK - |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; - - /* enable the interrupt */ - mpuRegs->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK - | CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; - - return; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_MPPA_modify - Description : search the range which match a address and then modify - the access permission of that range. - Input : Uint32 uiMPU_num: number of the MPU to be modifed - Uint32 uiAddress: address which need modify permision - Uint32 AccessPermisionMask: permission mask for that range - Output : None - Return Value : - - History : - 1.Date : 2012/12/13 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_MPU_MPPA_modify(Uint32 uiMPU_num, - Uint32 uiAddress, Uint32 AccessPermisionMask) -{ - int i; - unsigned int mpuNumProgmableRange; - CSL_MpuRegs * mpuRegs; - - /*For Turbo Nyquist, add following code to modify initial value, - Or user can modify the initail values directly*/ - if(5==uiMPU_num) - TN_MPU5_constant(); - - mpuRegs= gpMPU_regs[uiMPU_num]; - - mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; - if(mpuNumProgmableRange == 0) - { - mpuNumProgmableRange = 16; - } - - /*search through all ranges*/ - for(i=0; i< mpuNumProgmableRange; i++) - { - /*match with one range*/ - if((uiAddress >= mpuRegs->PROG_REGION[i].PROG_START_ADDRESS) - &&(uiAddress <= mpuRegs->PROG_REGION[i].PROG_END_ADDRESS)) - { - mpuRegs->PROG_REGION[i].PROG_MPPA = AccessPermisionMask; - return; - } - } - - printf("address 0x%08x does not match any range in MPU %d\n", - uiAddress, uiMPU_num); - - return; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_interrupts_enable - Description : enable the all MPU interrupts - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_MPU_interrupt_enable(Uint32 uiMPU_num) -{ - if((gpMPU_regs[uiMPU_num]->REVISION&0xFFFF0000)!= - (CSL_MPU_REVISION_RESETVAL&0xFFFF0000)) - { - printf("Can't read MPU%d ID register, make sure corresponding power domain is enabled.", uiMPU_num); - return; - } - - gpMPU_regs[uiMPU_num]->FAULT_CLEAR = 1; - gpMPU_regs[uiMPU_num]->INT_ENABLED_STATUS_CLEAR = - CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK - |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; - gpMPU_regs[uiMPU_num]->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK - |CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; - -} -void KeyStone_MPU_interrupts_enable() -{ - int i; - TDSP_Board_Type DSP_Board_Type = KeyStone_Get_dsp_board_type(); - - TN_MPU5_constant(); - - for(i=0; i<4; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - - if((C6670_EVM== DSP_Board_Type) - ||(TCI6614_EVM== DSP_Board_Type)) - { - for(i=4; i<6; i++) - { - /*MPU5 (for BCP) of TCI6614 is only accessible - when BCP is enabled through PSC*/ - if((5==i)&&(TCI6614_EVM== DSP_Board_Type)&& - ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || - (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) - { - puts("Enable power domain for MPU5 before configure it."); - continue; - } - - KeyStone_MPU_interrupt_enable(i); - } - } - - if(TCI6614_EVM== DSP_Board_Type) - { - for(i=6; i<8; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - } - - return; -} - -char * Peri_MPU_err_type_str[]= -{ - "User execution fault!", - "User write fault!", - "User read fault!", - "Supervisor execution fault!", - "Supervisor write fault!", - "Supervisor read fault!" -}; - -char * Ns_str[]= -{ - "secure", - "non-secure" -}; -/***************************************************************************** - Prototype : KeyStone_peripherals_MPU_fault_status - Description : Print the MPU error information - Input : unsigned int uwFltStatus - unsigned int uwFltAddr - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_peripherals_MPU_fault_status(unsigned int uwFltStatus, - unsigned int uwFltAddr) -{ - unsigned int MSTID; - unsigned int PRIVID; - unsigned int NS; - unsigned int FaultType; - unsigned int BitsCnt; - - MSTID = (uwFltStatus & CSL_MPU_FAULT_STATUS_MSTID_MASK)>>CSL_MPU_FAULT_STATUS_MSTID_SHIFT; - PRIVID = (uwFltStatus & CSL_MPU_FAULT_STATUS_PRIVID_MASK)>>CSL_MPU_FAULT_STATUS_PRIVID_SHIFT; - NS = (uwFltStatus & CSL_MPU_FAULT_STATUS_NS_MASK)>>CSL_MPU_FAULT_STATUS_NS_SHIFT; - printf(" The MSTID %d (PRIVID %d) triggered MPU error at 0x%x with %s access\n", - MSTID, PRIVID, uwFltAddr, Ns_str[NS]); - - FaultType = (uwFltStatus & CSL_MPU_FAULT_STATUS_FAULT_TYPE_MASK) >> CSL_MPU_FAULT_STATUS_FAULT_TYPE_SHIFT; - if(1==(_dotpu4(_bitc4(FaultType), 0x01010101))) - { - BitsCnt= 31 - _lmbd(1, FaultType); - printf(" %s\n",Peri_MPU_err_type_str[BitsCnt]); - } - else if(0x3F == FaultType) - { - puts(" Relaxed cache line fill fault!"); - } - else if(0x12 == FaultType) - { - puts(" Relaxed cache write back fault!"); - } -} -/***************************************************************************** - Prototype : KeyStone_peripherals_MPU_excepiton_handler - Description : peripheral MPU processing - Input : Uint32 uwMpuNum - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_peripherals_MPU_excepiton_handler(Uint32 uwMpuNum) -{ - Uint32 uwStatus; - Uint32 uwFltAddr; - Uint32 uwFltStatus; - CSL_MpuRegs *pstruMpuRegs= gpMPU_regs[uwMpuNum]; - - uwStatus = pstruMpuRegs->INT_ENABLED_STATUS_CLEAR; - if(uwStatus & 0x2) - { - printf(" MPU %d address violation error\n", uwMpuNum); - pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 2; - } - - if(uwStatus & 0x1) - { - printf(" MPU %d protection violation error\n", uwMpuNum); - pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 1; - } - - uwFltAddr = pstruMpuRegs->FAULT_ADDRESS; - uwFltStatus = pstruMpuRegs->FAULT_STATUS; - exception_record.status.ext_sts.info.memory.fault_address= uwFltAddr; - exception_record.status.ext_sts.info.memory.fault_status.MPU_FAULT_STATUS= uwFltStatus; - - KeyStone_peripherals_MPU_fault_status(uwFltStatus,uwFltAddr); - pstruMpuRegs->FAULT_CLEAR = 1; - - pstruMpuRegs->EOI = 0; -} - - -/*======================memory EDC=====================================*/ -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_enable - Description : Enable MSMC EDC - Input : scrubCnt, number of MSMC clock cycles between scrubbing - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_enable(Uint32 scrubCnt) -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /*Software must wait for the PRR (Parity RAM Ready) bit before making - the first read access to MSMC RAM after reset.*/ - while(0==(gpMSMC_regs->SMEDCC&CSL_MSMC_SMEDCC_PRR_MASK)); - - /* set scrubbing period value */ - if(scrubCnt>255) - scrubCnt= 255; - CSL_MSMC_setCounterBankRefreshRead(scrubCnt); //the scrubbing engine works every scrubCnt*1024 cycle*/ - - /* clear EDC errors and enable EDC event*/ - gpMSMC_regs->SMIRC = 0xf; - gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK - | CSL_MSMC_SMIESTAT_CSIE_MASK - | CSL_MSMC_SMIESTAT_NCEIE_MASK - | CSL_MSMC_SMIESTAT_CEIE_MASK); - - //enable SL2 EDC - CSL_MSMC_setECM(1); - - CSL_MSMC_lockNonMPAX(); -} - -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_interrupt_en - Description : Enable MSMC EDC error interrupt - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_interrupt_en() -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /* clear EDC errors*/ - gpMSMC_regs->SMIRC = 0xf; - - /* Enable EDC error interrupt */ - gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK - | CSL_MSMC_SMIESTAT_CSIE_MASK - | CSL_MSMC_SMIESTAT_NCEIE_MASK - | CSL_MSMC_SMIESTAT_CEIE_MASK); - - CSL_MSMC_lockNonMPAX(); -} - -/***************************************************************************** - Prototype : LL2_EDC_setup - Description : Eenable LL2 EDC and scrub whole LL2 - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/10 - Author : Jane - Modification : Created function - - 2.Date : 2012/10/20 - Author : Brighton Feng - -*****************************************************************************/ -void LL2_EDC_setup() -{ - int i; - unsigned int uiByteCnt= 512*1024; - TDSP_Board_Type DSP_Board_Type; - - /* 1. Disable the EDC */ - CSL_CGEM_disableL2EDC(); - - /* 2. Clear any EDC errors */ - CSL_CGEM_clearL2EDCErrorStatus(1, 1, 1, 1); - - /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ - DSP_Board_Type = KeyStone_Get_dsp_board_type(); - if((DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(C6670_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - uiByteCnt= 1024*1024; - } - - /*Each IDMA can transfer up to 65532 bytes, - here we transfer 32KB each time*/ - for(i=0; i< (uiByteCnt>>15); i++) - { - IDMA_copy((0x00800000 + i*(1<<15)), (0x00800000 + i*(1<<15)), - (1<<15), DMA_WAIT); - } - - /* 4. Enable the EDC*/ - CSL_CGEM_enableL2EDC(); - gpCGEM_regs->L2EDCEN= (1<= uiLL2EndAddress) - uiLL2_scrub_addr=0x800000; - -} - -/***************************************************************************** - Prototype : L1P_EDC_setup - Description : enable L1P ED and scrub whole L1P - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/10 - Author : Jane - Modification : Created function - - 2.Date : 2012/10/30 - Author : Brighton Feng -*****************************************************************************/ -void L1P_EDC_setup() -{ - Uint32 preL1PMPPA[16]; - - /* 1. Disable the EDC */ - CSL_CGEM_disablePMCErrorDetection(); - - /* 2. Clear any EDC errors */ - CSL_CGEM_clearPMCErrorDetectionStatus(1, 1); - - /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ - memcpy(preL1PMPPA, (void *)gpCGEM_regs->L1PMPPA, 64);//save protection attributes - L1P_memory_protection_cfg(0xFFFF); //enable IDMA access to L1P - IDMA_copy(0x00E00000, 0x00E00000, 32*1024, DMA_WAIT); - L1_MPPA_setup(gpCGEM_regs->L1PMPPA, preL1PMPPA);//restore protection for L1 - - /* 4. Enable the EDC*/ - CSL_CGEM_enablePMCErrorDetection(); -} - -char * LL2_EDC_victim_err_str="LL2 victims"; -char * LL2_EDC_DMA_err_str= "DMA access"; -char * LL2_EDC_L1D_err_str= "L1D access"; -char * LL2_EDC_L1P_err_str= "L1P access"; - -/***************************************************************************** - Prototype : LL2_EDC_handler - Description : LL2 EDC exception/interrupt handler - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_EDC_handler(Bool bCorrected) -{ - /* EDC error during the L1D access */ - Uint8 derr; - /* EDC error during the L1P access */ - Uint8 perr; - /* EDC error during the DMA access*/ - Uint8 dmaerr; - /* EDC error during the L2 victim occurred */ - Uint8 verr; - /* single bit or dual bit EDC error */ - Uint8 nerr; - - char *errStr; - Uint32 errAddr; - - /* Get the all LL2 error status */ - CSL_CGEM_getL2EDCErrorStatus(&derr, &perr, &dmaerr, &verr, &nerr); - - if(derr|perr|dmaerr|verr) - { - errAddr= gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_ADDR_MASK; - - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - exception_record.status.ext_sts.info.memory.fault_status.L2EDSTAT= - gpCGEM_regs->L2EDSTAT; - - if(bCorrected) - { - printf(" LL2 EDC (correctable) at bit %d of ",(gpCGEM_regs->L2EDSTAT& - CSL_CGEM_L2EDSTAT_BITPOS_MASK)>>CSL_CGEM_L2EDSTAT_BITPOS_SHIFT); - - //scrub 64 bytes including the error address to correct the error - if(perr) //by L1P access - IDMA_copy(errAddr&0xFFFFFFC0, errAddr&0xFFFFFFC0, 64, DMA_WAIT); - else - { - volatile Uint32 * uipAddress= (volatile Uint32 *)(errAddr&0xFFFFFFC0); - /*read one word into a cache line, and write to make it dirty, - which will be automatically written back sooner or later*/ - *uipAddress= *uipAddress; - } - } - else - { - printf(" LL2 EDC error (non-correctable) at "); - } - errStr = (char *)(perr * (Uint32)LL2_EDC_L1P_err_str - + derr * (Uint32)LL2_EDC_L1D_err_str - + verr * (Uint32)LL2_EDC_victim_err_str - + dmaerr * (Uint32)LL2_EDC_DMA_err_str); - - printf("address 0x%x caused by %s.\n", - errAddr, - errStr); - - if(0==(gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_RAM_MASK)) - { - printf(" Error detected in Way %d of L2 cache\n", - (gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_WAY_MASK)>>CSL_CGEM_L2EDADDR_WAY_SHIFT); - } - - printf(" total non-correctable error number= %d, total correctable error number= %d.\n", - gpCGEM_regs->L2EDCNEC, gpCGEM_regs->L2EDCPEC); - - CSL_CGEM_clearL2EDCErrorStatus(derr, perr, dmaerr, verr); - } - else - { - puts(" Enter LL2 EDC handler, but no error flag is set!"); - } -} -/***************************************************************************** - Prototype : L1P_ED_handler - Description : L1P EDC processing - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1P_ED_handler() -{ - Uint32 errAddr; - Uint8 errRAM; - - /* EDC error during DMA access */ - Uint8 dmaerr; - /* EDC error during program fetch access */ - Uint8 perr; - - /* Read PMC EDC status*/ - CSL_CGEM_getPMCErrorDetectionStatus(&dmaerr, &perr); - - if(perr|dmaerr) - { - CSL_CGEM_getPMCErrorInfo(&errAddr, &errRAM); - - exception_record.status.ext_sts.info.memory.fault_address= errAddr*32; - exception_record.status.ext_sts.info.memory.fault_status.L1PEDSTAT= - gpCGEM_regs->L1PEDSTAT; - - if(errRAM) - printf(" L1P RAM "); - else - printf(" L1P Cache "); - - printf("parity check error caused by "); - - if(perr == 1) - { - printf("program fetch "); - - /*flush wrong code in L1P. Code will be refetched from L2*/ - CACHE_invL1p((void *)NRP, 64, CACHE_WAIT); - } - else if(dmaerr == 1) - { - printf("DMA "); - } - printf("at address 0x%x\n", errAddr*32); - - CSL_CGEM_clearPMCErrorDetectionStatus(dmaerr,perr); - } -} - - -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_handler - Description : SL2 EDC Processing - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_handler() -{ - /* EDC correctable error during scrubbing cycle */ - Uint8 cses; - /* EDC non-correctable error during scrubbing cycle */ - Uint8 ncses; - /* EDC correctable error during SRAM access*/ - Uint8 cees; - /* EDC non-correctable error during SRAM access*/ - Uint8 ncees; - /* protection fault status*/ - Uint16 pfeStat; - - /* error address */ - Uint32 errAddr, bitPos, PrivID; - - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - CSL_MSMC_getPendingInterrupts(&pfeStat, &cees, &ncees, &cses, &ncses); - - exception_record.status.ext_sts.info.memory.fault_status.SMESTAT= - gpMSMC_regs->SMESTAT; - - if((cses == 1)||(ncses == 1)) - { - if(cses == 1) - { - /*scrubbing engine report address offset from 0*/ - errAddr = (gpMSMC_regs->SMCEA&0xFFFFFF)+0xc000000; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - bitPos = (gpMSMC_regs->SMCEA&CSL_MSMC_SMCEA_ESYN_MASK) - >>CSL_MSMC_SMCEA_ESYN_SHIFT; - printf("SL2 Correctable error occurred at bit %d of address 0x%x by scrubbing\n", - bitPos, errAddr); - } - if(ncses == 1) - { - /*scrubbing engine report address offset from 0*/ - errAddr = gpMSMC_regs->SMNCEA+0xc000000; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - printf("SL2 Non-correctable error occurred at address 0x%x by scrubbing\n", errAddr); - } - printf("%d correctable errors, %d non-correctable errors occurred during scrubbing.\n", - (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SCEC_MASK) - >>CSL_MSMC_SMSECC_SCEC_SHIFT, - (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SNCEC_MASK) - >>CSL_MSMC_SMSECC_SNCEC_SHIFT); - } - if(cees == 1) - { - volatile Uint32 scrubValue; - - errAddr = gpMSMC_regs->SMCERRAR; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - //scrub the address to correct the error - scrubValue= *(volatile Uint32 *)errAddr; //touch to cach - *(volatile Uint32 *)errAddr= scrubValue; //make cache dirty - CACHE_wbInvL2((void *)errAddr, 32, CACHE_WAIT); - - bitPos = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_ESYN_MASK) - >>CSL_MSMC_SMCERRXR_ESYN_SHIFT; - PrivID = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SEPID_MASK) - >>CSL_MSMC_SMCERRXR_SEPID_SHIFT; - printf("SL2 Correctable error occurred at bit %d of address 0x%x by PrivID %d ", - bitPos, errAddr, PrivID); - if(gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SER_MASK) - printf("(not from C66x CorePacs)\n"); - else - printf("(from C66x CorePacs)\n"); - } - if(ncees ==1) - { - errAddr = gpMSMC_regs->SMNCERRAR; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - PrivID = (gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SEPID_MASK) - >>CSL_MSMC_SMNCERRXR_SEPID_SHIFT; - printf("SL2 Non-correctable error occurred at address 0x%x by PrivID %d ", - errAddr, PrivID); - if(gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SER_MASK) - printf("(not from C66x CorePacs)\n"); - else - printf("(from C66x CorePacs)\n"); - } - - /* clear EDC error status */ - CSL_MSMC_clearRawInterruptStatus(0, cees,ncees, cses, ncses); - - CSL_MSMC_lockNonMPAX(); -} - -/*===============================Exception=============================*/ -//data structure to save exception info -Exception_Record exception_record; - -/*some exception events routed from CIC to INTC and then to exception moduel, -all these events are routed to one input of INTC*/ -Uint32 guwIntcCICExcEvtIdx= 95; /*INTC event number mapping to CIC exception events*/ -Uint32 gCIC_EXC_out_num = 15; //CIC output event number -Uint32 gCIC_EXC_EN_MASK[8]= {0,0,0,0,0,0,0,0}; -/***************************************************************************** - Prototype : KeyStone_CIC_exception_events_mapping - Description : CIC exception event mapping to the NMI external exception - Input : void - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - - 2.Date : 2012/10/20 - Author : Zhan - Modification : Add event for TCI6614 - - 3.Date : 2012/10/28 - Author : Brighton Feng -*****************************************************************************/ -void KeyStone_CIC_exception_events_mapping(void) -{ - TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); - -#if 1 - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||TCI6614_EVM==DSP_Board_Type) - { - gCIC_EXC_out_num= 15+16*DNUM; - } - else if(C6678_EVM==DSP_Board_Type) - { - if(DNUM<4) - gCIC_EXC_out_num= 7+8*DNUM; - else - { - gCIC_EXC_out_num= 7+8*(DNUM-4); - gpCIC_regs= gpCIC1_regs; - } - } - else - { - puts("Unknown DSP board type!"); - return; - } -#endif - - /*-----------------------CP_INTC configuration---------------------*/ - /* Disable Global host interrupts. */ - gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 0; - - /* route following system events to CIC out (event 22 of INTC), and then to exception - TCI6614, C6670, C6678: - CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt - CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt - CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt - CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt - CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt - CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt - CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt - CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt - CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt - CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt - CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt - CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt - CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt - CIC: 99 MSMC_dedc_nc_error Non-correctable soft error detected on SRAM read - CIC: 100 MSMC_scrub_nc_error Non-correctable soft error detected during scrub cycle - CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID - CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID - CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID - CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID - CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID - CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID - CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID - CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID - CIC: 110 DDR3_ERR DDR3 ECC Error Interrupt - TCI6614, C6670: - CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID - CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID - CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID - CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID - */ - KeyStone_CIC_event_map(gpCIC_regs, 0 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 2 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 3 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 4 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 5 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 16, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 18, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 19, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 20, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 21, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[0] |= - (1<<0 ) - |(1<<2 ) - |(1<<3 ) - |(1<<4 ) - |(1<<5 ) - |(1<<16) - |(1<<18) - |(1<<19) - |(1<<20) - |(1<<21); - - KeyStone_CIC_event_map(gpCIC_regs, 32, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 34, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 35, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[1] |= - (1<<(32-32)) - |(1<<(34-32)) - |(1<<(35-32)); - - KeyStone_CIC_event_map(gpCIC_regs, 99, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 100, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 102, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 103, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 104, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 105, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 106, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 107, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 108, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 109, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 110, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[3] |= - (1<<(99 -32*3)) - |(1<<(100-32*3)) - |(1<<(102-32*3)) - |(1<<(103-32*3)) - |(1<<(104-32*3)) - |(1<<(105-32*3)) - |(1<<(106-32*3)) - |(1<<(107-32*3)) - |(1<<(108-32*3)) - |(1<<(109-32*3)) - |(1<<(110-32*3)); - - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||TCI6614_EVM==DSP_Board_Type) - { - KeyStone_CIC_event_map(gpCIC_regs, 170, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 171, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 172, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 173, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[5] |= - (1<<(170-32*5)) - |(1<<(171-32*5)) - |(1<<(172-32*5)) - |(1<<(173-32*5)); - } - - /* ----------- Mapping MPU interrupt for different chips start -----------------------*/ - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||C6678_EVM==DSP_Board_Type) - { - /* route the following system events to CIC out - CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt - CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt - CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt - CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt - */ - KeyStone_CIC_event_map(gpCIC_regs, 90, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 92, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 94, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 96, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[2] |= - (1<<(90 -32*2)) - |(1<<(92 -32*2)) - |(1<<(94 -32*2)); - gCIC_EXC_EN_MASK[3] |= - (1<<(96 -32*3)); - - /* 6618_6670 only */ - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type) - { - /* - CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt - CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt - */ - KeyStone_CIC_event_map(gpCIC_regs, 174, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 180, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[5] |= - (1<<(174-32*5)) - |(1<<(180-32*5)); - } - } - - if(TCI6614_EVM==DSP_Board_Type) - { - /* route the following system events to CIC out - CIC: 23 MPU0~7 addressing violation interrupt combine output - CIC: 37 MPU0~7 protection violation interrupt combine output - */ - KeyStone_CIC_event_map(gpCIC_regs, 23, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 37, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[0] |= - (1<<23); - gCIC_EXC_EN_MASK[1] |= - (1<<(37 -32)); - - } - /* ----------- Mapping MPU interrupt for different chips end -----------------------*/ - - /* Enable Global host interrupts. */ - gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 1; - -} -/***************************************************************************** - Prototype : KeyStone_Exception_cfg - Description : Config the system err and external exception to generate the NMI. - Call this function as last step after all - configuration/initialization complete - Input : Bool bGlobalExceptionMaster. If TRUE, the global exception events - from CIC will be routed to exception model of this CPU core. - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_Exception_cfg(Bool bGlobalExceptionMaster) -{ - - puts("Enable Exception handling..."); - - TSCL = 0; /* Enable the TSC */ - - memset(&exception_record, 0, sizeof(exception_record)); -#if 0 - /*Clear all CPU events*/ - gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; -#endif - /*clear memory fault*/ - gpCGEM_regs->L1PMPFCR = 1; - gpCGEM_regs->L1DMPFCR = 1; - gpCGEM_regs->L2MPFCR = 1; - gpXMC_regs->XMPFCR = 1; - - /*clear configuration bus error*/ - gpCGEM_regs->ICFGMPFCR= 1; - gpCGEM_regs->ECFGERRCLR= 1; - - /* clear the MDMAERR */ - gpCGEM_regs->MDMAERRCLR = 1; - - /*clear interrupt drop staus*/ - gpCGEM_regs->INTXCLR = 1; - - gpCGEM_regs->INTDMASK= ~IER; /*only monitor drop of enabled interrupts*/ - - /*enable events: - 10 MSMC_mpf_error_n MSMC Memory protection fault caused by local CorePac - 96 INTERR Dropped CPU interrupt event - 97 EMC_IDMAERR Invalid IDMA parameters - 110 MDMAERREVT XMC VBUSM error event - 113 PMC_ED Single bit error detected during DMA accesses L1P - 117 UMC_ED2 Uncorrected bit error detected LL2 - 119 SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control - 120 PMC_CMPA CPU memory protection fault for L1P - 121 PMC_DMPA DMA memory protection fault for L1P - 122 DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller) - 123 DMC_DMPA DMA memory protection fault for L1D - 124 UMC_CMPA CPU memory protection fault for LL2 - 125 UMC_DMPA DMA memory protection fault for LL2 - 126 EMC_CMPA CPU memory protection fault for other local configuration space between 0x01000000 - 0x01BFFFFF - 127 EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF - */ - gpCGEM_regs->EXPMASK[0]= ~(1<EXPMASK[1]= 0xFFFFFFFF; - gpCGEM_regs->EXPMASK[2]= 0xFFFFFFFF; - gpCGEM_regs->EXPMASK[3]= ~((1<<(CSL_GEM_INTERR - 96))| - (1<<(CSL_GEM_EMC_IDMAERR-96))| - (1<<(CSL_GEM_MDMAERREVT-96))| - (1<<(CSL_GEM_PMC_ED-96))| - (1<<(CSL_GEM_UMC_ED2-96))| - (1<<(CSL_GEM_SYS_CMPA-96))| - (1<<(CSL_GEM_PMC_CMPA-96))| - (1<<(CSL_GEM_PMC_DMPA-96))| - (1<<(CSL_GEM_DMC_CMPA-96))| - (1<<(CSL_GEM_DMC_DMPA-96))| - (1<<(CSL_GEM_UMC_CMPA-96))| - (1<<(CSL_GEM_UMC_DMPA-96))| - (1<<(CSL_GEM_EMC_CMPA-96))| - (1<<(CSL_GEM_EMC_BUSERR-96))); - - - if(bGlobalExceptionMaster) - { - /*enable exception events routed from CIC, - please note, this should be only configured for one CPU*/ - KeyStone_CIC_exception_events_mapping(); - gpCGEM_regs->EXPMASK[guwIntcCICExcEvtIdx>>5] &= (~(1<<(guwIntcCICExcEvtIdx&0x1F))); - } - - /*clear exception flag*/ - ECR = EFR; - IERR = 0; - - /*Eanble external exception, global exception enable*/ - TSR = TSR| - (1<>CSL_CGEM_MDMAERR_ERR_SHIFT; - if (1==err) { - puts(" MDMA read status error detected"); - } - else if (2==err) { - puts(" MDMA write status error detected"); - } - else if (3==err) { - puts(" CFG read status error detected"); - } - else if (4==err) { - puts(" CFG write status error detected"); - } - - printf(" XID (Transaction ID)= %d\n", - (ERR_REG & CSL_CGEM_MDMAERR_XID_MASK)>>CSL_CGEM_MDMAERR_XID_SHIFT); - - stat= (ERR_REG & CSL_CGEM_MDMAERR_STAT_MASK)>>CSL_CGEM_MDMAERR_STAT_SHIFT; - printf(" %s\n", bus_err_stat_str[stat]); -} - -/***************************************************************************** - Prototype : KeyStone_CIC_EXC_handler - Description : This function handle the exception events from CIC - Input : void - Output : None - Return Value : void - - History : - 1.Date : 2012/10/18 - Author : Zhan - Modification : Created function - - 2.Date : 2012/10/28 - Author : Brighton Feng - Modification : Add EDMA error processing - -*****************************************************************************/ -void KeyStone_CIC_EXC_handler() -{ - int i; - Uint32 status[4], status5 = 0; - - TDSP_Board_Type DSP_Board_Type; - - DSP_Board_Type= KeyStone_Get_dsp_board_type(); - - /*Step1: Disable CIC host interrupt*/ - KeyStone_CIC_disable_host_int(gpCIC_regs, gCIC_EXC_out_num); - - status[0]= gpCIC_regs->ENA_STATUS_REG[0]&gCIC_EXC_EN_MASK[0]; - status[1]= gpCIC_regs->ENA_STATUS_REG[1]&gCIC_EXC_EN_MASK[1]; - status[2]= gpCIC_regs->ENA_STATUS_REG[2]&gCIC_EXC_EN_MASK[2]; - status[3]= gpCIC_regs->ENA_STATUS_REG[3]&gCIC_EXC_EN_MASK[3]; - exception_record.status.ext_sts.CIC_STATUS[0]= status[0]; - exception_record.status.ext_sts.CIC_STATUS[1]= status[1]; - exception_record.status.ext_sts.CIC_STATUS[2]= status[2]; - exception_record.status.ext_sts.CIC_STATUS[3]= status[3]; - - /*Step2: clear system events*/ - gpCIC_regs->ENA_STATUS_REG[0]= status[0]; - gpCIC_regs->ENA_STATUS_REG[1]= status[1]; - gpCIC_regs->ENA_STATUS_REG[2]= status[2]; - gpCIC_regs->ENA_STATUS_REG[3]= status[3]; - - /* The different device INTC number is different, if read the non-exist space will - trigger the L1D memory protection error. - */ - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - status5 = gpCIC_regs->ENA_STATUS_REG[5]&gCIC_EXC_EN_MASK[5]; - exception_record.status.ext_sts.CIC_STATUS[5]= status5; - - /*Step2: clear system events*/ - gpCIC_regs->ENA_STATUS_REG[5]= status5 ; - } - - /*----------------------------EDMA error-----------------------------*/ - /* - CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt - CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt - CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt - CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt - CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt*/ - if(status[0]&0x3D) - EDMA_error_handler(1, status[0]&0x3D); - - /* - CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt - CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt - CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt - CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt - CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt*/ - if((status[0]>>16)&0x3D) - EDMA_error_handler(2, (status[0]>>16)&0x3D); - - /* - CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt - CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt - CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt*/ - if(status[1]&0xD) - EDMA_error_handler(0, status[1]&0xD); - - /*----------------------------MPU error-----------------------------*/ - if(TCI6614_EVM == DSP_Board_Type) - { - //CIC: 23 MPU0~7 addressing violation interrupt combine output - //CIC: 37 MPU0~7 protection violation interrupt combine output - if((status[0]&(1<<23))||(status[1]&(1<<(37-32)))) - { - for(i=0; i<8; i++) - { - /*MPU5 (for BCP) of TCI6614 is only accessible - when BCP is enabled through PSC*/ - if((5==i)&& - ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || - (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) - continue; - - if(gpMPU_regs[i]->INT_RAW_STATUS_SET & 0x3) - { - KeyStone_peripherals_MPU_excepiton_handler(i); - } - } - - /*The MPU events in TCI6614 are different from other KeyStone - devices. All the MPU0~7 events are combined into single event - and connected to the CIC0 as one system event. - We have to clear the MPU event flag at the source level first - and then are able to clear the CIC flags because the INTD for the - MPU events is for the combination purpose but do not convert - the level interrupt to pulse.*/ - /*clear system events*/ - gpCIC_regs->ENA_STATUS_REG[0]= status[0]; - gpCIC_regs->ENA_STATUS_REG[1]= status[1]; - } - } - else - { - //CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(90-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(0); - } - //CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(92-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(1); - } - //CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(94-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(2); - } - //CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt - if(status[3]&(1<<(96-96))) - { - KeyStone_peripherals_MPU_excepiton_handler(3); - } - - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type)) - { - //CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt - //CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt - if(status5&(1<<(174-160))) - { - KeyStone_peripherals_MPU_excepiton_handler(4); - } - if(status5&(1<<(180-160))) - { - KeyStone_peripherals_MPU_excepiton_handler(5); - } - } - } - - /*----------------------------MSMC error-----------------------------*/ - //CIC: 99 MSMC_dedc_nc_error Non-correctable (2-bit) soft error detected on SRAM read - if(status[3]&(1<<(99-96))) - { - KeyStone_SL2_EDC_handler(); - } - //CIC: 100 MSMC_scrub_nc_error Non-correctable (2-bit) soft error detected during scrub cycle - if(status[3]&(1<<(100-96))) - { - KeyStone_SL2_EDC_handler(); - } - - /* - CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID - CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID - CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID - CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID - CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID - CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID - CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID - CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID*/ - if((status[3]>>(102-96))&0xFF) - KeyStone_MSMC_protection_exception_handler(); - - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - /* - CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID - CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID - CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID - CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID*/ - if((status5>>(170-160))&0xF) - KeyStone_MSMC_protection_exception_handler(); - - } - - /*----------------------------DDR ECC error-------------------------*/ - //CIC: 110 DDR3_ERR DDR3_EMIF Error Interrupt - if(status[3]&(1<<(110-96))) - { - printf(" DDR ECC error happened during "); - - exception_record.status.ext_sts.info.memory.fault_status.DDR_IRQSTATUS_SYS= - gpDDR_regs->IRQSTATUS_SYS; - - if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK) - printf("read "); - if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK) - printf("write "); - printf(".\n"); - - //clear the status - gpDDR_regs->IRQSTATUS_SYS= CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK - |CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK; - } - - /*Step3: Enable the CIC host interrupt */ - KeyStone_CIC_enable_host_int(gpCIC_regs, gCIC_EXC_out_num); - -} - -/***************************************************************************** - Prototype : KeyStone_EXC_external - Description : external exception processing - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_EXC_external(void) -{ - int i; - unsigned int INTXSTAT, flag[4]; - - for(i= 0; i<4; i++) - { - flag[i] = gpCGEM_regs->MEXPFLAG[i]; - if(flag[i]) - { - exception_record.status.ext_sts.MEXPFLAG[i]= flag[i]; - printf("External exception happened. MEXPFLAG[%d]=0x%x.\n", - i, flag[i]); - gpCGEM_regs->EVTCLR[i] = flag[i]; - } - } - - if(0 == (flag[0]|flag[1]|flag[2]|flag[3])) - { - puts("Enter external Exception service routine, but external excpetion flage is 0!"); - return; - } - - /*Exception events routed from CIC*/ - if(flag[guwIntcCICExcEvtIdx>>5] & (1<<(guwIntcCICExcEvtIdx&0x1F))) - { - KeyStone_CIC_EXC_handler(); - } - - /*MSMC memory protection exception*/ - if(flag[0]&(1<INTXSTAT; - exception_record.status.ext_sts.info.INTXSTAT= INTXSTAT; - - if(INTXSTAT&CSL_CGEM_INTXSTAT_DROP_MASK) - printf(" Event 96: DSP Interrupt %d (INTC input Event %d) dropped\n", - (INTXSTAT&CSL_CGEM_INTXSTAT_CPUINT_MASK)>>CSL_CGEM_INTXSTAT_CPUINT_SHIFT, - (INTXSTAT&CSL_CGEM_INTXSTAT_SYSINT_MASK)>>CSL_CGEM_INTXSTAT_SYSINT_SHIFT); - } - - if(flag[3]&(1<<(CSL_GEM_EMC_IDMAERR-96))) - puts(" Event 97: EMC_IDMAERR Invalid IDMA parameters"); - - /*MDMA XMC VBUSM error*/ - if(flag[3]&(1<<(CSL_GEM_MDMAERREVT-96))) - { - puts(" Event 110: MDMAERREVT XMC VBUSM error event"); - if(gpXMC_regs->XMPFSR) - { - /*XMC protection error*/ - memory_protection_exception_handler(gpXMC_regs->XMPFAR, gpXMC_regs->XMPFSR); - gpXMC_regs->XMPFCR = 1; - } - else - { - /*other VBUSM error*/ - Bus_error_handler(gpCGEM_regs->MDMAERR); - } - /* clear the MDMAERR */ - gpCGEM_regs->MDMAERRCLR = 1; - } - - /*L1P Single bit error detected during DMA read*/ - if(flag[3]&(1<<(CSL_GEM_PMC_ED-96))) - { - puts(" Event 113: PMC_ED Single bit error detected during DMA read"); - L1P_ED_handler(); - } - - /*LL2 Uncorrected bit error detected*/ - if(flag[3]&(1<<(CSL_GEM_UMC_ED2-96))) - { - puts(" Event 117: UMC_ED2 Uncorrected bit error detected"); - LL2_EDC_handler(FALSE); - } - - /*local register memory protection exception*/ - if(flag[3]&(1<<(CSL_GEM_SYS_CMPA-96))) - { - puts(" Event 119: SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control"); - } - - /*L1P memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_PMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_PMC_CMPA-96))) - puts(" Event 120: PMC_CMPA CPU memory protection fault for L1P"); - if(flag[3]&(1<<(CSL_GEM_PMC_DMPA-96))) - puts(" Event 121: PMC_DMPA DMA memory protection fault for L1P"); - memory_protection_exception_handler(gpCGEM_regs->L1PMPFAR, gpCGEM_regs->L1PMPFSR); - gpCGEM_regs->L1PMPFCR = 1; - } - - /*L1D memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_DMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_DMC_CMPA-96))) - puts(" Event 122: DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller)"); - if(flag[3]&(1<<(CSL_GEM_DMC_DMPA-96))) - puts(" Event 123: DMC_DMPA DMA memory protection fault for L1D"); - memory_protection_exception_handler(gpCGEM_regs->L1DMPFAR, gpCGEM_regs->L1DMPFSR); - gpCGEM_regs->L1DMPFCR = 1; - } - - /*LL2 memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_UMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_UMC_CMPA-96))) - puts(" Event 124: UMC_CMPA CPU memory protection fault for L2 "); - if(flag[3]&(1<<(CSL_GEM_UMC_DMPA-96))) - puts(" Event 125: UMC_DMPA DMA memory protection fault for L2 "); - memory_protection_exception_handler(gpCGEM_regs->L2MPFAR, gpCGEM_regs->L2MPFSR); - gpCGEM_regs->L2MPFCR = 1; - } - - /*local registers protection exception*/ - if(flag[3]&(1<<(CSL_GEM_EMC_CMPA-96))) - { - puts(" Event 126: EMC_CMPA CPU memory protection fault for local configuration space between 0x01000000-0x01BFFFFF"); - memory_protection_exception_handler(gpCGEM_regs->ICFGMPFAR, gpCGEM_regs->ICFGMPFSR); - gpCGEM_regs->ICFGMPFCR= 1; - } - - /*external configuration bus error*/ - if(flag[3]&(Uint32)(1<<(CSL_GEM_EMC_BUSERR-96))) - { - puts(" Event 127: EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF"); - Bus_error_handler(gpCGEM_regs->ECFGERR); - gpCGEM_regs->ECFGERRCLR= 1; - } -} - -char * internal_exception_str[]= -{ - "Instruction fetch exception", - "Fetch packet exception", - "Execute packet exception", - "Opcode exception", - "Resource conflict exception", - "Resource access exception", - "Privilege exception", - "SPLOOP buffer exception", - "Missed stall exception" -}; - -/***************************************************************************** - Prototype : EXC_internal - Description : internal exception handler - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -/*internal exception handler*/ -void EXC_internal(void) -{ - int i; - unsigned int ierr; - - /*record IERR */ - ierr = IERR; - exception_record.status.IERR= ierr; - - if(ierr) - { - /*Clear internal excpeiton flag*/ - IERR= 0; - - printf("internal excpetion happened. IERR=0x%x.\n", ierr); - for(i=0; i<9; i++) - { - if((ierr>>i)&1) - printf(" %s\n", internal_exception_str[i]); - } - if (ierr & CSL_CHIP_IERR_IFX_MASK) { - /* L1P EDC Processing*/ - L1P_ED_handler(); - } - } - else - puts("Enter Internal Exception service routine, but internal excpetion flage is 0!"); - -} -/***************************************************************************** - Prototype : EXC_nmi - Description : NMI processing - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EXC_NMI(void) -{ - puts("NMI exception happened, normally you should reset the DSP to recover from the problem!"); -} - -/***************************************************************************** - Prototype : EXC_swgen - Description : software generated exception handler - Input : void - Output : None - Return Value : -*****************************************************************************/ -void EXC_swgen(void) -{ - puts("Software generated exception happened."); -} - -/***************************************************************************** - Prototype : Exception_service_routine - Description : Exception service routine - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma NMI_INTERRUPT( Exception_service_routine ); -void Exception_service_routine(void) -{ - unsigned int efr, nrp, ntsr, tscl, tsch, irp, itsr; - - /*record timestamp*/ - tscl = TSCL; - exception_record.TSCL= tscl; - tsch = TSCH; - exception_record.TSCH= tsch; - - nrp = NRP; /*record NRP */ - exception_record.NRP= nrp; - ntsr = NTSR; /*record NTSR */ - exception_record.NTSR= ntsr; - efr = EFR; /*record EFR */ - exception_record.EFR= efr; - - irp = IRP; /*record IRP */ - itsr = ITSR; /*record ITSR */ - exception_record.IRP= irp; - exception_record.ITSR= itsr; - - if(efr) - { - /*Clear excpeiton flag*/ - ECR = efr; - - /*check all possible exceptions*/ - if (efr & CSL_CHIP_EFR_OXF_MASK) { - /* S/W generated exception */ - EXC_swgen(); - } - if (efr & CSL_CHIP_EFR_IXF_MASK) { - /* internal exception */ - EXC_internal(); - } - if (efr & CSL_CHIP_EFR_EXF_MASK) { - /* external exception */ - KeyStone_EXC_external(); - } - if (efr & CSL_CHIP_EFR_NXF_MASK) { - /* legacy NMI exception */ - EXC_NMI(); - } - } - else - puts("Enter Exception service routine, but excpetion flage is 0!"); - - printf("NRP=0x%x, NTSR=0x%x, IRP=0x%x, ITSR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", - nrp, ntsr, irp, itsr, tsch, tscl); - - printf(" B3=0x%x, A4=0x%x, B4= 0x%x, B14= 0x%x, B15= 0x%x\n", - exception_record.B3, exception_record.A4, - exception_record.B4, exception_record.B14, - exception_record.B15); - - /* - It is not always possible to safely exit the exception handling routine. Conditions that - can prevent a safe return from exceptions include: - 1. SPLOOPs that are terminated by an exception cannot be resumed correctly. The - SPLX bit in NTSR should be verified to be 0 before returning. - 2. Exceptions that occur when interrupts are blocked cannot be resumed correctly. - The IB bit in NTSR should be verified to be 0 before returning. - 3. Exceptions that occur at any point in the code that cannot be interrupted safely - (for example, a tight loop containing multiple assignments) cannot be safely - returned to. The compiler will normally disable interrupts at these points in the - program; check the GIE bit in NTSR to be 1 to verify that this condition is met. - 4. NRP is not in valid address space*/ - if((ntsr&CSL_CHIP_TSR_SPLX_MASK) - ||(ntsr&CSL_CHIP_TSR_IB_MASK) - ||(0==(ntsr&CSL_CHIP_TSR_GIE_MASK)) - ||(0x800000>NRP)) - { - puts("Exception happened at a place can not safely return!"); - //while(1); //trap - exit(0); - } - -} - -/***************************************************************************** - Prototype : Nested_Exception_service_routine - Description : Nested Exception service routine - When a non-maskable exception happens in the first exception service routine, - then the reset vector is used when redirecting program execution to service the second - exception. In this case, NTSR and NRP are left unchanged. TSR is copied to ITSR and - the current PC is copied to IRP. TSR is set to the default exception processing value and - the NMIE bit in IER is cleared in this case preventing any further external exceptions. - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/29 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -interrupt void Nested_Exception_service_routine(void) -{ - unsigned int tscl, tsch; - - /*record timestamp*/ - tscl = TSCL; - tsch = TSCH; - - if(0==exception_record.TSCL) - exception_record.TSCL= tscl; - if(0==exception_record.TSCH) - exception_record.TSCH= tsch; - if(0==exception_record.NRP) - exception_record.NRP= NRP; - if(0==exception_record.NTSR) - exception_record.NTSR= NTSR; - if(0==exception_record.EFR) - exception_record.EFR= EFR; - if(0==exception_record.status.IERR) - exception_record.status.IERR= IERR; - - exception_record.IRP= IRP; - exception_record.ITSR= ITSR; - - printf("Nested exception happened! IRP=0x%x, ITSR=0x%x\n", - IRP, ITSR); - - printf("NRP=0x%x, NTSR=0x%x, EFR=0x%x, IERR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", - NRP, NTSR, EFR, IERR, tsch, tscl); - - while(1); //trap -// exit(0); -} - -/*=========================other utility functions==========================*/ -/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ -void CPU_interrupt_init() -{ - //clear interrupt and excpetion events - ICR = IFR; - ECR = EFR; - IER= 3; //disable all interrupts - - /* disable event combine */ - gpCGEM_regs->EVTMASK[0] = 0xffffffff; - gpCGEM_regs->EVTMASK[1] = 0xffffffff; - gpCGEM_regs->EVTMASK[2] = 0xffffffff; - gpCGEM_regs->EVTMASK[3] = 0xffffffff; - - /*Clear all CPU events*/ - gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; - - /*Interrupt Service Table Pointer to begining of LL2 memory*/ - ISTP= 0x800000; -} - -/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ -void CPU_interrupt_enable(Uint32 uiIER_en_mask) -{ - ICR= uiIER_en_mask; - IER |= uiIER_en_mask; - - //enable GIE - //TSR = TSR|1; -} - -/***************************************************************************** - Prototype : KeyStone_get_device_info - Description : Get device information - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - 2.Date : 2014/12/2 - Author : Brighton Feng - Modification : Update to parser device type, boot mode, endian information, - speed grade, required CVDD - -*****************************************************************************/ -//get device speed grade from the EFUSE register -void KeyStone_get_device_speed_grade() -{ - Uint32 uiDevSpeed, uiSpeedCode; - - uiSpeedCode= (DEVSPEED&DEVSPEED_DSP_SPEED_MASK)>>DEVSPEED_DSP_SPEED_SHIFT; - - if(uiSpeedCode&DEVSPEED_800_MHZ_MASK_H) uiDevSpeed= 800; - else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_H) uiDevSpeed= 1000; - else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_H) uiDevSpeed= 1200; - else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_H) uiDevSpeed= 1250; - else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_H) uiDevSpeed= 1400; - else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_L) uiDevSpeed= 1400; - else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_L) uiDevSpeed= 1250; - else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_L) uiDevSpeed= 1200; - else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_L) uiDevSpeed= 1000; - else uiDevSpeed= 800; - - printf("Device speed grade = %dMHz.\n", uiDevSpeed); -} - -char * device_type_str[]= -{ - "TCI6616", - "C6670/TCI6618", - "C6678/TCI6608", - "TCI6614", - "unknown" -}; -char * endian_str[]= -{ - "big", - "little" -}; -char * boot_mode_str[]= -{ - "No boot or EMIF16(NOR FLASH) or UART", - "Serial Rapid I/O", - "Ethernet (SGMII)", - "Ethernet (SGMII) or NAND FLASH", - "PCIE", - "I2C", - "SPI", - "HyperLink" - }; -char * input_clk_str[]= -{ - "50MHz", - "66.67MHz", - "80MHz", - "100MHz", - "156.25MHz", - "250MHz", - "312.5MHz", - "122.88MHz", - "bypassed" -}; -void KeyStone_get_device_info() -{ - char * boot_mode; - Uint8 ucBootMode, ucBootMaster; - Uint32 uiVID; - Uint8 ucPLL_cfg= 8; //8 means bypassed - Uint32 * DieID= (Uint32 *)&gpBootCfgRegs->DIE_ID_REG0; - Uint32 uiJTAG_ID = gpBootCfgRegs->DEVICE_ID_REG0; - Uint32 uiDevStat = gpBootCfgRegs->BOOT_REG0; - - gDSP_board_type=KeyStone_Get_dsp_board_type(); - - ucBootMode= (uiDevStat&DEVSTAT_BOOTMODE_MASK)>>DEVSTAT_BOOTMODE_SHIFT; - ucBootMaster= (uiDevStat&DEVSTAT_BOOTMASTER_MASK)>>DEVSTAT_BOOTMASTER_SHIFT; - - if((TCI6614_EVM==gDSP_board_type)&&(1==ucBootMaster)) - { - boot_mode= "ARM"; //ARM boot - } - else - boot_mode= boot_mode_str[ucBootMode]; - - //PLL is not configured with SPI and I2C master boot mode - if((5!=ucBootMode)&&(6!=ucBootMode)) - ucPLL_cfg= (uiDevStat&DEVSTAT_SYSPLL_MASK)>>DEVSTAT_SYSPLL_SHIFT; - - printf("JTAG ID= 0x%08x. This is %s device, version variant = %d.\n", uiJTAG_ID, - device_type_str[gDSP_board_type], uiJTAG_ID>>28); - - printf("DEVSTAT= 0x%08x. %s endian, %s boot, PLL configuration implies the input clock for core is %s.\n", - uiDevStat, endian_str[uiDevStat&DEVSTAT_LENDIAN_MASK], boot_mode, - input_clk_str[ucPLL_cfg]); - - uiVID= (gpPSC_regs->VCNTLID&CSL_PSC_VCNTLID_VCNTL_MASK)>>CSL_PSC_VCNTLID_VCNTL_SHIFT; - printf("SmartReflex VID= %d, required core voltage= %.3fV.\n", uiVID, 0.7+(float)uiVID*0.41/64.f); - - printf("Die ID= 0x%08x, 0x%08x, 0x%08x, 0x%08x\n", DieID[0], DieID[1], DieID[2], DieID[3]); - - KeyStone_get_device_speed_grade(); -} -/***************************************************************************** - Prototype : KeyStone_common_device_init - Description : common initialization for internal modules in K2 device - enable memory protection interrupts, EDC for MSMC RAM - History : - 1.Date : July 11, 2014 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_common_device_init() -{ - int i; - KeyStone_get_device_info(); - - /* enable common MPU interrupts */ - for(i=0; i<4; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - - /*Enable MSMC EDC and setup scrubbing cycle counter= 255*1024*/ - KeyStone_SL2_EDC_enable(255); -} - -/***************************************************************************** - Prototype : KeyStone_common_CPU_init - Description : common initialization for internal modules in K2 device - enable TSC, EDC for local RAM; clear cache; protect L1 as cache - History : - 1.Date : September 1, 2014 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_common_CPU_init() -{ - TSC_init(); //initialize TSC to measure cycle - - /*clear all interrupt flag/status, setup ISTP to begining of LL2*/ - CPU_interrupt_init(); - - /*clean cache from previous run, not required from power on or cold reset*/ - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - _mfence(); - _mfence(); - - /* protect L1 as cache */ - L1_cache_protection(); - - //Enable MSMC Memory protection error interrupt for local core, refer to MSMC user guide section3.8 - // KeyStone_MSMC_MP_interrupt_en(1< -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/*----------------------PLL registers definition----------------*/ -#define PLLCTL0_PLLD_SHIFT (0) -#define PLLCTL0_PLLD_MASK (0x3F<>4) | 0x80000000) - -/*max number in two numbers*/ -#define MAX(a, b) (a>b?a:b) -/*min number in two numbers*/ -#define MIN(a, b) (a0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline void WritebackCache(void * blockPtr, Uint32 byteCnt) -{ - if(byteCnt>0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbL2((void *)blockPtr, byteCnt, CACHE_WAIT); - } - _mfence(); - _mfence(); -} - -static inline void WritebackAllCache(void * blockPtr) -{ - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbAllL1d(CACHE_WAIT);; - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbAllL2(CACHE_WAIT); - } - _mfence(); - _mfence(); -} - -static inline void WritebackInvalidCache(void * blockPtr, Uint32 byteCnt) -{ -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - Uint32 uiOldGIE= _disable_interrupts(); -#endif - - if(byteCnt>0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbInvL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbInvL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline void WritebackInvalidAllCache(void * blockPtr) -{ -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - Uint32 uiOldGIE= _disable_interrupts(); -#endif - - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbInvAllL1d(CACHE_WAIT);//CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - //CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline unsigned int SWAP_ENDIAN(unsigned int byte_index) -{ -#ifdef _BIG_ENDIAN - return ((byte_index&0xFFFFFFFC)+(3-byte_index&3)); -#else - return byte_index; -#endif -} - -static inline void KeyStone_CIC_clear_system_event(CSL_CPINTCRegs* cpIntcRegs, - int input_event_num) -{ - volatile Uint32 dummy_value; - - /*clear input interrupts events*/ - cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->STATUS_CLR_INDEX_REG; -} - -static inline void KeyStone_CIC_disable_host_int(CSL_CPINTCRegs* cpIntcRegs, - int host_int_num) -{ - volatile Uint32 dummy_value; - - /* Disable the host interrupt */ - cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG = host_int_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG; -} - -static inline void KeyStone_CIC_enable_host_int(CSL_CPINTCRegs* cpIntcRegs, - int host_int_num) -{ - volatile Uint32 dummy_value; - - /* Enable the host interrupt */ - cpIntcRegs->HINT_ENABLE_SET_INDEX_REG = host_int_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->HINT_ENABLE_SET_INDEX_REG; -} - -static inline void KeyStone_CIC_event_map(CSL_CPINTCRegs* cpIntcRegs, - int input_event_num, int out_num) -{ - /*Map input event to output*/ - cpIntcRegs->CH_MAP[SWAP_ENDIAN(input_event_num)]= out_num; - - /*clear input interrupts events*/ - cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; - - /*enable input interrupts events*/ - cpIntcRegs->ENABLE_SET_INDEX_REG= input_event_num; - - /*enable output*/ - cpIntcRegs->HINT_ENABLE_SET_INDEX_REG= out_num; -} - - -typedef enum -{ - DUAL_NYQUIST_EVM = 0, - C6670_EVM, - C6678_EVM, - TCI6614_EVM, - C6657_EVM, - UNKNOWN -}TDSP_Board_Type; - -extern TDSP_Board_Type gDSP_board_type; - -static inline TDSP_Board_Type KeyStone_Get_dsp_board_type() -{ - Uint32 deviceID= gpBootCfgRegs->DEVICE_ID_REG0&0x0FFFFFFF; - - gDSP_board_type= UNKNOWN; - if(0x0009D02F == deviceID) - gDSP_board_type= DUAL_NYQUIST_EVM; - if(0x0B94102F == deviceID) - { - gDSP_board_type= C6670_EVM; - //DSP_Board_Type= DUAL_NYQUIST_EVM; - } - if(0x0009E02F == deviceID) - gDSP_board_type= C6678_EVM; - if(0x0B96202F == deviceID) - gDSP_board_type= TCI6614_EVM; - if(0x0B97A02F == deviceID) - gDSP_board_type= C6657_EVM; - - return gDSP_board_type; -} - -static inline Uint32 KeyStone_Get_DSP_Number() -{ - TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); - - if(DUAL_NYQUIST_EVM==DSP_Board_Type) - { - /*Nyquist EVM use boot configure pin 4 and 5 to identify DSPs*/ - return (( gpBootCfgRegs->BOOT_REG0 >> (3+1) ) & 0x03); - } - - /*if use DNUM to differentiate DSPs for two DSPs test, - the program must be run on core 0 of DSP 0 and core 1 of DSP1*/ - return DNUM; -} - -/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ -extern void CPU_interrupt_init(); -/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ -extern void CPU_interrupt_enable(Uint32 uiIER_en_mask); - -//get device speed grade from the EFUSE register -extern void KeyStone_get_device_speed_grade(); - -/*Get device information including device type, boot mode, endian information, -speed grade, required voltage...*/ -extern void KeyStone_get_device_info(); - -/*common initialization for internal modules in K2 device. -enable memory protection interrupts, EDC for MSMC RAM*/ -extern void KeyStone_common_device_init(); - -/* enable TSC, EDC for local RAM; clear cache; protect L1 as cache */ -extern void KeyStone_common_CPU_init(); - - -#endif diff --git a/bsp/ti-c6678/driver/drv_timer.c b/bsp/ti-c6678/driver/drv_timer.c deleted file mode 100644 index 4cda450e49..0000000000 --- a/bsp/ti-c6678/driver/drv_timer.c +++ /dev/null @@ -1,55 +0,0 @@ -/* - * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology - * - * SPDX-License-Identifier: Apache-2.0 - * - * Change Logs: - * Date Author Notes - * 2021-11-16 Dystopia the first version - */ - -#include "drv_timer.h" -#include "KeyStone_common.h" - -#include -#include - -/** - * @b Description - * @n - * The function initial system timer. - * Use local timer (==DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well - * - * @param[] - * - * @retval - * NULL - */ -void hw_system_timer_init(void) -{ - // initial system timer interrupt - // map local timer interrupt to INT14 - gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)< + + + + + + + + + + + diff --git a/bsp/ti-tms320c6678/.cproject b/bsp/ti-tms320c6678/.cproject new file mode 100644 index 0000000000..aef3a8c240 --- /dev/null +++ b/bsp/ti-tms320c6678/.cproject @@ -0,0 +1,160 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/bsp/ti-tms320c6678/.project b/bsp/ti-tms320c6678/.project new file mode 100644 index 0000000000..d1c8afd3a3 --- /dev/null +++ b/bsp/ti-tms320c6678/.project @@ -0,0 +1,154 @@ + + + ti-c6678 + + + + + + org.eclipse.cdt.managedbuilder.core.genmakebuilder + + + + + org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder + full,incremental, + + + + + + com.ti.ccstudio.core.ccsNature + org.eclipse.cdt.core.cnature + org.eclipse.cdt.managedbuilder.core.managedBuildNature + org.eclipse.cdt.core.ccnature + org.eclipse.cdt.managedbuilder.core.ScannerConfigNature + + + + SConscript + 1 + PARENT-2-PROJECT_LOC/src/SConscript + + + clock.c + 1 + PARENT-2-PROJECT_LOC/src/clock.c + + + components.c + 1 + PARENT-2-PROJECT_LOC/src/components.c + + + context.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/context.asm + + + cpu.c + 1 + PARENT-2-PROJECT_LOC/src/cpu.c + + + cpuport.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/cpuport.c + + + device.c + 1 + PARENT-2-PROJECT_LOC/src/device.c + + + idle.c + 1 + PARENT-2-PROJECT_LOC/src/idle.c + + + inct.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/inct.asm + + + interrupt.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/interrupt.c + + + ipc.c + 1 + PARENT-2-PROJECT_LOC/src/ipc.c + + + irq.c + 1 + PARENT-2-PROJECT_LOC/src/irq.c + + + kservice.c + 1 + PARENT-2-PROJECT_LOC/src/kservice.c + + + mem.c + 1 + PARENT-2-PROJECT_LOC/src/mem.c + + + memheap.c + 1 + PARENT-2-PROJECT_LOC/src/memheap.c + + + mempool.c + 1 + PARENT-2-PROJECT_LOC/src/mempool.c + + + object.c + 1 + PARENT-2-PROJECT_LOC/src/object.c + + + scheduler.c + 1 + PARENT-2-PROJECT_LOC/src/scheduler.c + + + signal.c + 1 + PARENT-2-PROJECT_LOC/src/signal.c + + + slab.c + 1 + PARENT-2-PROJECT_LOC/src/slab.c + + + stack.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/stack.asm + + + thread.c + 1 + PARENT-2-PROJECT_LOC/src/thread.c + + + timer.c + 1 + PARENT-2-PROJECT_LOC/src/timer.c + + + trap.c + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/trap.c + + + vector.asm + 1 + PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/vector.asm + + + diff --git a/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.codan.core.prefs b/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.codan.core.prefs new file mode 100644 index 0000000000..f653028c53 --- /dev/null +++ b/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.codan.core.prefs @@ -0,0 +1,3 @@ +eclipse.preferences.version=1 +inEditor=false +onBuild=false diff --git a/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.debug.core.prefs b/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.debug.core.prefs new file mode 100644 index 0000000000..2adc7b1dde --- /dev/null +++ b/bsp/ti-tms320c6678/.settings/org.eclipse.cdt.debug.core.prefs @@ -0,0 +1,2 @@ +eclipse.preferences.version=1 +org.eclipse.cdt.debug.core.toggleBreakpointModel=com.ti.ccstudio.debug.CCSBreakpointMarker diff --git a/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs b/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs new file mode 100644 index 0000000000..83b10321a8 --- /dev/null +++ b/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs @@ -0,0 +1,10 @@ +eclipse.preferences.version=1 +encoding//Debug/applications/subdir_rules.mk=UTF-8 +encoding//Debug/applications/subdir_vars.mk=UTF-8 +encoding//Debug/driver/subdir_rules.mk=UTF-8 +encoding//Debug/driver/subdir_vars.mk=UTF-8 +encoding//Debug/makefile=UTF-8 +encoding//Debug/objects.mk=UTF-8 +encoding//Debug/sources.mk=UTF-8 +encoding//Debug/subdir_rules.mk=UTF-8 +encoding//Debug/subdir_vars.mk=UTF-8 diff --git a/bsp/ti-tms320c6678/KeyStone.cmd b/bsp/ti-tms320c6678/KeyStone.cmd new file mode 100644 index 0000000000..0f30bc506e --- /dev/null +++ b/bsp/ti-tms320c6678/KeyStone.cmd @@ -0,0 +1,47 @@ +/****************************************************************************/ +/* */ +/* M6678.cmd */ +/* Copyright (c): NUDT */ +/* */ +/* */ +/* Description: This file is a sample linker command file that can be */ +/* used for linking programs built with the C compiler and */ +/* running the resulting .out file on an M6678 */ +/* device. Use it as a guideline. You will want to */ +/* change the memory layout to match your specific C6xxx */ +/* target system. You may want to change the allocation */ +/* scheme according to the size of your program. */ +/* */ +/* */ +/****************************************************************************/ + +-heap 0x800 +-stack 0x1000 + +MEMORY +{ + VECTORS: o = 0x00800000 l = 0x00000200 + LL2_CODE: o = 0x00800200 l = 0x0001FE00 + LL2_RW_DATA: o = 0x00820000 l = 0x00020000 /*set memory protection attribitue as read/write*/ +} + +SECTIONS +{ + .vecs > VECTORS + + .text > LL2_CODE + .cinit > LL2_CODE + .const > LL2_CODE + .switch > LL2_CODE + .stack > LL2_RW_DATA + GROUP + { + .neardata + .rodata + .bss + } > LL2_RW_DATA + .far > LL2_RW_DATA + .fardata > LL2_RW_DATA + .cio > LL2_RW_DATA + .sysmem > LL2_RW_DATA +} diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c new file mode 100644 index 0000000000..a0f951d31e --- /dev/null +++ b/bsp/ti-tms320c6678/applications/board.c @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "board.h" +#include "trap.h" +#include "interrupt.h" +#include "drv_timer.h" +#include "KeyStone_common.h" + +#include + +/** + * This is the timer interrupt service routine. + * + */ +void rt_hw_systick_isr(void) +{ + /* enter interrupt */ + rt_interrupt_enter(); + + rt_tick_increase(); + + /* leave interrupt */ + rt_interrupt_leave(); +} + +/** + * This function will initial board. + */ +void rt_hw_board_init(void) +{ + // initial CPU core + KeyStone_common_CPU_init(); + + // initial interrupt controller + rt_hw_interrupt_init(); + + // initial system trap + rt_trap_init(); + + // initial system timer + hw_system_timer_init(); + + /* initialize memory system */ + rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); + rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); + + hw_system_timer_start(); +} + diff --git a/bsp/ti-tms320c6678/applications/board.h b/bsp/ti-tms320c6678/applications/board.h new file mode 100644 index 0000000000..88e6e94e6e --- /dev/null +++ b/bsp/ti-tms320c6678/applications/board.h @@ -0,0 +1,20 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#ifndef __BOARD_H__ +#define __BOARD_H__ + +#define RT_HW_HEAP_BEGIN (void*)0x0C000000 +#define RT_HW_HEAP_END (void*)0x0C100000 + +void rt_hw_board_init(void); + +#endif /* __BOARD_H__ */ + diff --git a/bsp/ti-tms320c6678/applications/main.c b/bsp/ti-tms320c6678/applications/main.c new file mode 100644 index 0000000000..a8b9e17efc --- /dev/null +++ b/bsp/ti-tms320c6678/applications/main.c @@ -0,0 +1,80 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include +#include + +#include "board.h" + +void rt_init_thread_entry(void *parameter) +{ + rt_kprintf("hello rt-thread\n"); + return 0; +} + +int rt_application_init(void) +{ + rt_thread_t tid; + + tid = rt_thread_create("init", rt_init_thread_entry, RT_NULL, 4096, 3, 200); + if (tid != RT_NULL) + { + rt_thread_startup(tid); + } else { + return -1; + } + + return 0; +} + +/** + * This function will startup RT-Thread RTOS. + */ +void rtthread_startup(void) +{ + /* disable interrupt first */ + rt_hw_interrupt_disable(); + + /* init board */ + rt_hw_board_init(); + + /* show version */ + rt_show_version(); + + /* init timer system */ + rt_system_timer_init(); + + /* init scheduler system */ + rt_system_scheduler_init(); + + /* init application */ + rt_application_init(); + + /* init timer thread */ + rt_system_timer_thread_init(); + + /* init idle thread */ + rt_thread_idle_init(); + + /* start scheduler */ + rt_system_scheduler_start(); + + /* never reach here */ + return ; +} + +void main(void) +{ + /* startup RT-Thread RTOS */ + rtthread_startup(); + + for ( ; ; ); +} + diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c new file mode 100644 index 0000000000..4cda450e49 --- /dev/null +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "drv_timer.h" +#include "KeyStone_common.h" + +#include +#include + +/** + * @b Description + * @n + * The function initial system timer. + * Use local timer (==DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well + * + * @param[] + * + * @retval + * NULL + */ +void hw_system_timer_init(void) +{ + // initial system timer interrupt + // map local timer interrupt to INT14 + gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)< from ; B4 --> to +;{ .global rt_hw_context_switch_interrupt rt_hw_context_switch_interrupt: SUB B15,0x8,B15 @@ -285,14 +289,26 @@ rt_interrupt_context_restore: || LDDW .D2T2 *++SP[1],B13:B12 MV .D2X A15,SP + || MVKL .S1 rt_system_stack_top,A15 + MVKH .S1 rt_system_stack_top,A15 + || ADDAW .D1X SP,6,A14 + STW .D1T1 A14,*A15 ; save system stack pointer + LDDW .D2T1 *++SP[1],A15:A14 B .S2 IRP ; return from interruption LDDW .D2T2 *+SP[1],SP:DP NOP 4 - rt_preempt_context_restore: ZERO A12 - STW A12,*A3 ; clear rt_thread_switch_interrupt_flag + STW A12,*A3 ; clear rt_thread_switch_interrupt_flag +; +; restore saved registers by system stack +; + RESTORE_ALL IRP,ITSR +; +; store registers to thread stack +; + THREAD_SAVE_ALL IRP,ITSR MVKL rt_interrupt_from_thread,A11 MVKH rt_interrupt_from_thread,A11 @@ -302,10 +318,10 @@ rt_preempt_context_restore: MVKH rt_interrupt_to_thread,B10 LDW *B10,B11 NOP 3 - STW SP,*A10 ; store sp in preempted tasks's TCB - MV B11,A4 ; - B rt_hw_context_switch_to - NOP 5 + STW SP,*A10 ; store sp in preempted tasks's TCB + B rt_hw_context_switch_to + MV B11,A4 ; + NOP 4 ;} .end diff --git a/libcpu/ti-dsp/c6x/contextinc.asm b/libcpu/ti-dsp/c6x/contextinc.asm new file mode 100644 index 0000000000..18926aa088 --- /dev/null +++ b/libcpu/ti-dsp/c6x/contextinc.asm @@ -0,0 +1,187 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +SAVE_ALL .macro __rp, __tsr + STW .D2T2 B0,*SP--[2] ; save original B0 + MVKL .S2 rt_system_stack_top,B0 + MVKH .S2 rt_system_stack_top,B0 + LDW .D2T2 *B0,B1 ; system stack + + NOP 3 + STW .D2T2 B1,*+SP[1] ; save original B1 + XOR .D2 SP,B1,B0 ; (SP ^ KSP, check current stack types) + LDW .D2T2 *+SP[1],B1 ; restore B0/B1 + LDW .D2T2 *++SP[2],B0 + SHR .S2 B0,12,B0 ; 0 if already using system stack + [B0] STDW .D2T2 SP:DP,*--B1[1] ; thread: save thread sp/dp system stack + [B0] MV .S2 B1,SP ; and switch to system stack +||[!B0] STDW .D2T2 SP:DP,*--SP[1] ; kernel: nest interrupt save(not support) + + SUBAW .D2 SP,2,SP + + ADD .D1X SP,-8,A15 + || STDW .D2T1 A15:A14,*SP--[16] ; save A15:A14 + + STDW .D2T2 B13:B12,*SP--[1] + || STDW .D1T1 A13:A12,*A15--[1] + || MVC .S2 __rp,B13 + STDW .D2T2 B11:B10,*SP--[1] + || STDW .D1T1 A11:A10,*A15--[1] + || MVC .S2 CSR,B12 + + STDW .D2T2 B9:B8,*SP--[1] + || STDW .D1T1 A9:A8,*A15--[1] + || MVC .S2 RILC,B11 + STDW .D2T2 B7:B6,*SP--[1] + || STDW .D1T1 A7:A6,*A15--[1] + || MVC .S2 ILC,B10 + STDW .D2T2 B5:B4,*SP--[1] + || STDW .D1T1 A5:A4,*A15--[1] + STDW .D2T2 B3:B2,*SP--[1] + || STDW .D1T1 A3:A2,*A15--[1] + || MVC .S2 __tsr,B5 + STDW .D2T2 B1:B0,*SP--[1] + || STDW .D1T1 A1:A0,*A15--[1] + || MV .S1X B5,A5 + + STDW .D2T2 B31:B30,*SP--[1] + || STDW .D1T1 A31:A30,*A15--[1] + || MVKL 1,A4 + + STDW .D2T2 B29:B28,*SP--[1] + || STDW .D1T1 A29:A28,*A15--[1] + STDW .D2T2 B27:B26,*SP--[1] + || STDW .D1T1 A27:A26,*A15--[1] + STDW .D2T2 B25:B24,*SP--[1] + || STDW .D1T1 A25:A24,*A15--[1] + STDW .D2T2 B23:B22,*SP--[1] + || STDW .D1T1 A23:A22,*A15--[1] + STDW .D2T2 B21:B20,*SP--[1] + || STDW .D1T1 A21:A20,*A15--[1] + STDW .D2T2 B19:B18,*SP--[1] + || STDW .D1T1 A19:A18,*A15--[1] + STDW .D2T2 B17:B16,*SP--[1] + || STDW .D1T1 A17:A16,*A15--[1] + + STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR + STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC + STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 + .endm + +RESTORE_ALL .macro __rp, __tsr + LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) + LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) + LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) + + ADDAW .D1X SP,30,A15 + + LDDW .D1T1 *++A15[1],A17:A16 + || LDDW .D2T2 *++SP[1],B17:B16 + LDDW .D1T1 *++A15[1],A19:A18 + || LDDW .D2T2 *++SP[1],B19:B18 + LDDW .D1T1 *++A15[1],A21:A20 + || LDDW .D2T2 *++SP[1],B21:B20 + LDDW .D1T1 *++A15[1],A23:A22 + || LDDW .D2T2 *++SP[1],B23:B22 + LDDW .D1T1 *++A15[1],A25:A24 + || LDDW .D2T2 *++SP[1],B25:B24 + LDDW .D1T1 *++A15[1],A27:A26 + || LDDW .D2T2 *++SP[1],B27:B26 + LDDW .D1T1 *++A15[1],A29:A28 + || LDDW .D2T2 *++SP[1],B29:B28 + LDDW .D1T1 *++A15[1],A31:A30 + || LDDW .D2T2 *++SP[1],B31:B30 + + LDDW .D1T1 *++A15[1],A1:A0 + || LDDW .D2T2 *++SP[1],B1:B0 + LDDW .D1T1 *++A15[1],A3:A2 + || LDDW .D2T2 *++SP[1],B3:B2 + || MVC .S2 B9,__tsr + LDDW .D1T1 *++A15[1],A5:A4 + || LDDW .D2T2 *++SP[1],B5:B4 + || MVC .S2 B11,RILC + LDDW .D1T1 *++A15[1],A7:A6 + || LDDW .D2T2 *++SP[1],B7:B6 + || MVC .S2 B10,ILC + LDDW .D1T1 *++A15[1],A9:A8 + || LDDW .D2T2 *++SP[1],B9:B8 + || MVC .S2 B13,__rp + + LDDW .D1T1 *++A15[1],A11:A10 + || LDDW .D2T2 *++SP[1],B11:B10 + || MVC .S2 B12,CSR + LDDW .D1T1 *++A15[1],A13:A12 + || LDDW .D2T2 *++SP[1],B13:B12 + + MV .D2X A15,SP + || MVKL .S1 rt_system_stack_top,A15 + MVKH .S1 rt_system_stack_top,A15 + || ADDAW .D1X SP,6,A14 + STW .D1T1 A14,*A15 ; save system stack pointer + + LDDW .D2T1 *++SP[1],A15:A14 + LDDW .D2T2 *+SP[1],SP:DP + NOP 4 + .endm + +THREAD_SAVE_ALL .macro __rp, __tsr + STDW .D2T2 SP:DP,*--SP[1] + SUBAW .D2 SP,2,SP + + ADD .D1X SP,-8,A15 + || STDW .D2T1 A15:A14,*SP--[16] ; save A15:A14 + + STDW .D2T2 B13:B12,*SP--[1] + || STDW .D1T1 A13:A12,*A15--[1] + || MVC .S2 __rp,B13 + STDW .D2T2 B11:B10,*SP--[1] + || STDW .D1T1 A11:A10,*A15--[1] + || MVC .S2 CSR,B12 + + STDW .D2T2 B9:B8,*SP--[1] + || STDW .D1T1 A9:A8,*A15--[1] + || MVC .S2 RILC,B11 + STDW .D2T2 B7:B6,*SP--[1] + || STDW .D1T1 A7:A6,*A15--[1] + || MVC .S2 ILC,B10 + STDW .D2T2 B5:B4,*SP--[1] + || STDW .D1T1 A5:A4,*A15--[1] + STDW .D2T2 B3:B2,*SP--[1] + || STDW .D1T1 A3:A2,*A15--[1] + || MVC .S2 __tsr,B5 + STDW .D2T2 B1:B0,*SP--[1] + || STDW .D1T1 A1:A0,*A15--[1] + || MV .S1X B5,A5 + + STDW .D2T2 B31:B30,*SP--[1] + || STDW .D1T1 A31:A30,*A15--[1] + || MVKL 1,A4 + STDW .D2T2 B29:B28,*SP--[1] + || STDW .D1T1 A29:A28,*A15--[1] + STDW .D2T2 B27:B26,*SP--[1] + || STDW .D1T1 A27:A26,*A15--[1] + STDW .D2T2 B25:B24,*SP--[1] + || STDW .D1T1 A25:A24,*A15--[1] + STDW .D2T2 B23:B22,*SP--[1] + || STDW .D1T1 A23:A22,*A15--[1] + STDW .D2T2 B21:B20,*SP--[1] + || STDW .D1T1 A21:A20,*A15--[1] + STDW .D2T2 B19:B18,*SP--[1] + || STDW .D1T1 A19:A18,*A15--[1] + STDW .D2T2 B17:B16,*SP--[1] + || STDW .D1T1 A17:A16,*A15--[1] + + STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR + STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC + STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 + .endm diff --git a/libcpu/ti-dsp/c6x/cpuport.c b/libcpu/ti-dsp/c6x/cpuport.c index a00a2e9046..716e8a16fa 100644 --- a/libcpu/ti-dsp/c6x/cpuport.c +++ b/libcpu/ti-dsp/c6x/cpuport.c @@ -27,7 +27,6 @@ RT_WEAK void rt_hw_cpu_shutdown(void) RT_ASSERT(0); } -//----------------------------------------------------------------------------- /*------------ nested_exception_handler() function --------------------------- * DESCRIPTION: Function handles Nested Exception @@ -40,8 +39,6 @@ void nested_exception_handler(void) { for ( ; ; ); } -//----------------------------------------------------------------------------- - /*------------ hw_nmi_handler() function -------------------------------------- * DESCRIPTION: Function handles NMI interrupt @@ -53,8 +50,6 @@ void hw_nmi_handler(struct rt_hw_exp_stack_register *regs) { for ( ; ; ); } -//----------------------------------------------------------------------------- - /*------------ hw_bad_handler() function -------------------------------------- * DESCRIPTION: Function handles Bad interrupt @@ -66,8 +61,6 @@ void hw_bad_handler(void) { for ( ; ; ); } -//----------------------------------------------------------------------------- - /*------------ hw_int4_handler() function ------------------------------------- * DESCRIPTION: Function handles INT4 interrupt @@ -79,8 +72,6 @@ void hw_int4_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int5_handler() function ------------------------------------- * DESCRIPTION: Function handles INT5 interrupt @@ -92,8 +83,6 @@ void hw_int5_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int6_handler() function ------------------------------------- * DESCRIPTION: Function handles INT6 interrupt @@ -105,8 +94,6 @@ void hw_int6_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int7_handler() function ------------------------------------- * DESCRIPTION: Function handles INT7 interrupt @@ -118,8 +105,6 @@ void hw_int7_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int8_handler() function ------------------------------------- * DESCRIPTION: Function handles INT8 interrupt @@ -131,8 +116,6 @@ void hw_int8_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int9_handler() function ------------------------------------- * DESCRIPTION: Function handles INT9 interrupt @@ -144,8 +127,6 @@ void hw_int9_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int10_handler() function ------------------------------------ * DESCRIPTION: Function handles INT10 interrupt @@ -157,8 +138,6 @@ void hw_int10_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int11_handler() function ------------------------------------ * DESCRIPTION: Function handles INT11 interrupt @@ -170,8 +149,6 @@ void hw_int11_handler(void) { } -//----------------------------------------------------------------------------- - /*------------ hw_int12_handler() function ------------------------------------ * DESCRIPTION: Function handles INT12 interrupt @@ -181,9 +158,8 @@ void hw_int11_handler(void) -----------------------------------------------------------------------------*/ void hw_int12_handler(void) { + } -//----------------------------------------------------------------------------- - /*------------ hw_int13_handler() function ------------------------------------ * DESCRIPTION: Function handles INT13 interrupt @@ -195,8 +171,6 @@ void hw_int13_handler(void) { } -//----------------------------------------------------------------------------- - /*------------------ hw_int14_handler() function ------------------------------ * DESCRIPTION: Function handles INT14 interrupt @@ -209,8 +183,6 @@ void hw_int14_handler(void) extern void rt_hw_systick_isr(); rt_hw_systick_isr(); } -//----------------------------------------------------------------------------- - /*------------ hw_int15_handler() function ------------------------------------ * DESCRIPTION: Function handles INT15 interrupt diff --git a/libcpu/ti-dsp/c6x/inct.asm b/libcpu/ti-dsp/c6x/inct.asm deleted file mode 100644 index 4f866e4800..0000000000 --- a/libcpu/ti-dsp/c6x/inct.asm +++ /dev/null @@ -1,374 +0,0 @@ -; -; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology -; -; SPDX-License-Identifier: Apache-2.0 -; -; Change Logs: -; Date Author Notes -; 2021-11-16 Dystopia the first version -; - -;----------------------------------------------------------- -; interrupt handler for C6678 DSP -;----------------------------------------------------------- - -;----------------------------------------------------------- -; macro definition -;----------------------------------------------------------- -DP .set B14 -SP .set B15 -; -;----------------------------------------------------------- -; - -;----------------------------------------------------------- -; global function -;----------------------------------------------------------- - .global _nmi_handler - .global _bad_handler - .global _int4_handler - .global _int5_handler - .global _int6_handler - .global _int7_handler - .global _int8_handler - .global _int9_handler - .global _int10_handler - .global _int11_handler - .global _int12_handler - .global _int13_handler - .global _int14_handler - .global _int15_handler -; -;----------------------------------------------------------- -; - -;----------------------------------------------------------- -; extern function -;----------------------------------------------------------- - .ref hw_nmi_handler - .ref hw_bad_handler - .ref hw_int4_handler - .ref hw_int5_handler - .ref hw_int6_handler - .ref hw_int7_handler - .ref hw_int8_handler - .ref hw_int9_handler - .ref hw_int10_handler - .ref hw_int11_handler - .ref hw_int12_handler - .ref hw_int13_handler - .ref hw_int14_handler - .ref hw_int15_handler - .ref rt_hw_process_exception - .ref rt_interrupt_context_restore -; -;----------------------------------------------------------- -; - -; -;----------------------------------------------------------- -; - -;----------------------------------------------------------- -; macro definition -;----------------------------------------------------------- -SAVE_ALL .macro __rp, __tsr - STDW .D2T2 SP:DP,*--SP[1] - SUBAW .D2 SP,2,SP - ADD .D1X SP,-8,A15 - || STDW .D2T1 A15:A14,*SP--[16] ; save A15:A14 - - STDW .D2T2 B13:B12,*SP--[1] - || STDW .D1T1 A13:A12,*A15--[1] - || MVC .S2 __rp,B13 - - STDW .D2T2 B11:B10,*SP--[1] - || STDW .D1T1 A11:A10,*A15--[1] - || MVC .S2 CSR,B12 - - STDW .D2T2 B9:B8,*SP--[1] - || STDW .D1T1 A9:A8,*A15--[1] - || MVC .S2 RILC,B11 - STDW .D2T2 B7:B6,*SP--[1] - || STDW .D1T1 A7:A6,*A15--[1] - || MVC .S2 ILC,B10 - - STDW .D2T2 B5:B4,*SP--[1] - || STDW .D1T1 A5:A4,*A15--[1] - - STDW .D2T2 B3:B2,*SP--[1] - || STDW .D1T1 A3:A2,*A15--[1] - || MVC .S2 __tsr,B5 - - STDW .D2T2 B1:B0,*SP--[1] - || STDW .D1T1 A1:A0,*A15--[1] - || MV .S1X B5,A5 - - STDW .D2T2 B31:B30,*SP--[1] - || STDW .D1T1 A31:A30,*A15--[1] - || MVKL 1,A4 - - STDW .D2T2 B29:B28,*SP--[1] - || STDW .D1T1 A29:A28,*A15--[1] - STDW .D2T2 B27:B26,*SP--[1] - || STDW .D1T1 A27:A26,*A15--[1] - STDW .D2T2 B25:B24,*SP--[1] - || STDW .D1T1 A25:A24,*A15--[1] - STDW .D2T2 B23:B22,*SP--[1] - || STDW .D1T1 A23:A22,*A15--[1] - STDW .D2T2 B21:B20,*SP--[1] - || STDW .D1T1 A21:A20,*A15--[1] - STDW .D2T2 B19:B18,*SP--[1] - || STDW .D1T1 A19:A18,*A15--[1] - STDW .D2T2 B17:B16,*SP--[1] - || STDW .D1T1 A17:A16,*A15--[1] - - STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR - - STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC - STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 - .endm - -RESTORE_ALL .macro __rp, __tsr - LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) - LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) - LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) - - ADDAW .D1X SP,30,A15 - - LDDW .D1T1 *++A15[1],A17:A16 - || LDDW .D2T2 *++SP[1],B17:B16 - LDDW .D1T1 *++A15[1],A19:A18 - || LDDW .D2T2 *++SP[1],B19:B18 - LDDW .D1T1 *++A15[1],A21:A20 - || LDDW .D2T2 *++SP[1],B21:B20 - LDDW .D1T1 *++A15[1],A23:A22 - || LDDW .D2T2 *++SP[1],B23:B22 - LDDW .D1T1 *++A15[1],A25:A24 - || LDDW .D2T2 *++SP[1],B25:B24 - LDDW .D1T1 *++A15[1],A27:A26 - || LDDW .D2T2 *++SP[1],B27:B26 - LDDW .D1T1 *++A15[1],A29:A28 - || LDDW .D2T2 *++SP[1],B29:B28 - LDDW .D1T1 *++A15[1],A31:A30 - || LDDW .D2T2 *++SP[1],B31:B30 - - LDDW .D1T1 *++A15[1],A1:A0 - || LDDW .D2T2 *++SP[1],B1:B0 - LDDW .D1T1 *++A15[1],A3:A2 - || LDDW .D2T2 *++SP[1],B3:B2 - || MVC .S2 B9,__tsr - LDDW .D1T1 *++A15[1],A5:A4 - || LDDW .D2T2 *++SP[1],B5:B4 - || MVC .S2 B11,RILC - LDDW .D1T1 *++A15[1],A7:A6 - || LDDW .D2T2 *++SP[1],B7:B6 - || MVC .S2 B10,ILC - LDDW .D1T1 *++A15[1],A9:A8 - || LDDW .D2T2 *++SP[1],B9:B8 - || MVC .S2 B13,__rp - - LDDW .D1T1 *++A15[1],A11:A10 - || LDDW .D2T2 *++SP[1],B11:B10 - || MVC .S2 B12,CSR - LDDW .D1T1 *++A15[1],A13:A12 - || LDDW .D2T2 *++SP[1],B13:B12 - - MV .D2X A15,SP - LDDW .D2T1 *++SP[1],A15:A14 - B .S2 __rp ; return from interruption - LDDW .D2T2 *+SP[1],SP:DP - NOP 4 - .endm -;----------------------------------------------------------- -; interrupt macro definition -;----------------------------------------------------------- -RT_INTERRUPT_ENTRY .macro - SAVE_ALL IRP,ITSR - .endm - -RT_CALL_INT .macro __isr - CALLP __isr,B3 - B .S1 rt_interrupt_context_restore - NOP 5 - .endm -;----------------------------------------------------------- -; execption macro definition -;----------------------------------------------------------- -RT_EXECPTION_ENTRY .macro - SAVE_ALL NRP,NTSR - .endm - -RT_EXECPTION_EXIT .macro - RESTORE_ALL NRP,NTSR - .endm - -; -;----------------------------------------------------------- -; - - .sect ".text" -; -;----------------------------------------------------------- -; - -;----------------------------------------------------------- -; handler NMI interrupt -;----------------------------------------------------------- -_nmi_handler: -;{ - RT_EXECPTION_ENTRY - MVC .S2 EFR,B2 - CMPEQ .L2 1,B2,B2 - || MVC .S2 TSR,B1 - MV .D1X B2,A2 - || CLR .S2 B1,10,10,B1 - MVC .S2 B1,TSR - [!A2] MVKL .S1 rt_hw_process_exception,A0 - ||[B2] MVKL .S2 rt_hw_software_exception,B1 - [!A2] MVKH .S1 rt_hw_process_exception,A0 - ||[B2] MVKH .S2 rt_hw_software_exception,B1 - [!B2] B .S2X A0 - [B2] B .S2 B1 - [!B2] ADDAW .D2 SP,2,B1 - [!B2] MV .D1X B1,A4 - ADDKPC .S2 ret_from_trap,B3,2 -; -; return from trap -; -ret_from_trap: - MV .D2X A4,B0 - [!B0] MVKL .S2 ret_from_exception,B3 - [!B0] MVKH .S2 ret_from_exception,B3 - [!B0] BNOP .S2 B3,5 -; -; return from trap£¬restore exception context -; -ret_from_exception: - RT_EXECPTION_EXIT -; -rt_hw_software_exception: - MVKL .S1 rt_hw_process_exception,A0 - MVKH .S1 rt_hw_process_exception,A0 - B .S2X A0 - ADDAW .D2 SP,2,B1 - MV .D1X B1,A4 - ADDKPC .S2 ret_from_trap,B3,2 - NOP 2 -;} - -;----------------------------------------------------------- -; handler bad interrupt -;----------------------------------------------------------- -_bad_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_bad_handler -;} - -;----------------------------------------------------------- -; handler INT4 interrupt -;----------------------------------------------------------- -_int4_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int4_handler -;} - -;----------------------------------------------------------- -; handler INT5 interrupt -;----------------------------------------------------------- -_int5_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int5_handler -;} - -;----------------------------------------------------------- -; handler INT6 interrupt -;----------------------------------------------------------- -_int6_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int6_handler -;} - -;----------------------------------------------------------- -; handler INT7 interrupt -;----------------------------------------------------------- -_int7_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int7_handler -;} -;----------------------------------------------------------- -; handler INT8 interrupt -;----------------------------------------------------------- -_int8_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int8_handler -;} - -;----------------------------------------------------------- -; handler INT9 interrupt -;----------------------------------------------------------- -_int9_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int9_handler -;} - -;----------------------------------------------------------- -; handler INT10 interrupt -;----------------------------------------------------------- -_int10_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int10_handler -;} - -;----------------------------------------------------------- -; handler INT11 interrupt -;----------------------------------------------------------- -_int11_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int11_handler -;} - -;----------------------------------------------------------- -; handler INT12 interrupt -;----------------------------------------------------------- -_int12_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int12_handler -;} - -;----------------------------------------------------------- -; handler INT13 interrupt -;----------------------------------------------------------- -_int13_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int13_handler -;} - -;----------------------------------------------------------- -; handler INT14 interrupt -;----------------------------------------------------------- -_int14_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int14_handler -;} -;----------------------------------------------------------- -; handler INT15 interrupt -;----------------------------------------------------------- -_int15_handler: -;{ - RT_INTERRUPT_ENTRY - RT_CALL_INT hw_int15_handler -;} - .end diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c index 69205e0d38..d78de95abb 100644 --- a/libcpu/ti-dsp/c6x/interrupt.c +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -8,7 +8,6 @@ * 2021-11-16 Dystopia the first version */ - #include "c66xx.h" #include "interrupt.h" diff --git a/libcpu/ti-dsp/c6x/intexc.asm b/libcpu/ti-dsp/c6x/intexc.asm new file mode 100644 index 0000000000..d3ed54dc3b --- /dev/null +++ b/libcpu/ti-dsp/c6x/intexc.asm @@ -0,0 +1,269 @@ +; +; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology +; +; SPDX-License-Identifier: Apache-2.0 +; +; Change Logs: +; Date Author Notes +; 2021-11-16 Dystopia the first version +; + +;----------------------------------------------------------- +; interrupt and execption handler for C6678 DSP +;----------------------------------------------------------- + +;----------------------------------------------------------- +; macro definition +;----------------------------------------------------------- +DP .set B14 +SP .set B15 +; +;----------------------------------------------------------- +; + .include "contextinc.asm" +;----------------------------------------------------------- +; global function +;----------------------------------------------------------- + .global _nmi_handler + .global _bad_handler + .global _int4_handler + .global _int5_handler + .global _int6_handler + .global _int7_handler + .global _int8_handler + .global _int9_handler + .global _int10_handler + .global _int11_handler + .global _int12_handler + .global _int13_handler + .global _int14_handler + .global _int15_handler +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; extern function +;----------------------------------------------------------- + .ref hw_nmi_handler + .ref hw_bad_handler + .ref hw_int4_handler + .ref hw_int5_handler + .ref hw_int6_handler + .ref hw_int7_handler + .ref hw_int8_handler + .ref hw_int9_handler + .ref hw_int10_handler + .ref hw_int11_handler + .ref hw_int12_handler + .ref hw_int13_handler + .ref hw_int14_handler + .ref hw_int15_handler + .ref rt_hw_process_exception + .ref rt_interrupt_context_restore +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; extern variable +;----------------------------------------------------------- + .ref rt_system_stack_top +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; interrupt macro definition +;----------------------------------------------------------- +RT_INTERRUPT_ENTRY .macro + SAVE_ALL IRP,ITSR + .endm + +RT_CALL_INT .macro __isr + CALLP __isr,B3 + B .S1 rt_interrupt_context_restore + NOP 5 + .endm +;----------------------------------------------------------- +; execption macro definition +;----------------------------------------------------------- +RT_EXECPTION_ENTRY .macro + SAVE_ALL NRP,NTSR + .endm + +RT_EXECPTION_EXIT .macro + RESTORE_ALL NRP,NTSR + B .S2 NRP ; return from interruption + NOP 5 + .endm + +; +;----------------------------------------------------------- +; + + .sect ".text" +; +;----------------------------------------------------------- +; + +;----------------------------------------------------------- +; handler NMI interrupt +;----------------------------------------------------------- +_nmi_handler: +;{ + RT_EXECPTION_ENTRY + MVC .S2 EFR,B2 + CMPEQ .L2 1,B2,B2 + || MVC .S2 TSR,B1 + MV .D1X B2,A2 + || CLR .S2 B1,10,10,B1 + MVC .S2 B1,TSR + [!A2] MVKL .S1 rt_hw_process_exception,A0 + ||[B2] MVKL .S2 rt_hw_software_exception,B1 + [!A2] MVKH .S1 rt_hw_process_exception,A0 + ||[B2] MVKH .S2 rt_hw_software_exception,B1 + [!B2] B .S2X A0 + [B2] B .S2 B1 + [!B2] ADDAW .D2 SP,2,B1 + [!B2] MV .D1X B1,A4 + ADDKPC .S2 ret_from_trap,B3,2 +; +; return from trap +; +ret_from_trap: + MV .D2X A4,B0 + [!B0] MVKL .S2 ret_from_exception,B3 + [!B0] MVKH .S2 ret_from_exception,B3 + [!B0] BNOP .S2 B3,5 +; +; return from trap£¬restore exception context +; +ret_from_exception: + RT_EXECPTION_EXIT +; +rt_hw_software_exception: + MVKL .S1 rt_hw_process_exception,A0 + MVKH .S1 rt_hw_process_exception,A0 + B .S2X A0 + ADDAW .D2 SP,2,B1 + MV .D1X B1,A4 + ADDKPC .S2 ret_from_trap,B3,2 + NOP 2 +;} + +;----------------------------------------------------------- +; handler bad interrupt +;----------------------------------------------------------- +_bad_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_bad_handler +;} + +;----------------------------------------------------------- +; handler INT4 interrupt +;----------------------------------------------------------- +_int4_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int4_handler +;} + +;----------------------------------------------------------- +; handler INT5 interrupt +;----------------------------------------------------------- +_int5_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int5_handler +;} + +;----------------------------------------------------------- +; handler INT6 interrupt +;----------------------------------------------------------- +_int6_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int6_handler +;} + +;----------------------------------------------------------- +; handler INT7 interrupt +;----------------------------------------------------------- +_int7_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int7_handler +;} +;----------------------------------------------------------- +; handler INT8 interrupt +;----------------------------------------------------------- +_int8_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int8_handler +;} + +;----------------------------------------------------------- +; handler INT9 interrupt +;----------------------------------------------------------- +_int9_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int9_handler +;} + +;----------------------------------------------------------- +; handler INT10 interrupt +;----------------------------------------------------------- +_int10_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int10_handler +;} + +;----------------------------------------------------------- +; handler INT11 interrupt +;----------------------------------------------------------- +_int11_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int11_handler +;} + +;----------------------------------------------------------- +; handler INT12 interrupt +;----------------------------------------------------------- +_int12_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int12_handler +;} + +;----------------------------------------------------------- +; handler INT13 interrupt +;----------------------------------------------------------- +_int13_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int13_handler +;} + +;----------------------------------------------------------- +; handler INT14 interrupt +;----------------------------------------------------------- +_int14_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int14_handler +;} +;----------------------------------------------------------- +; handler INT15 interrupt +;----------------------------------------------------------- +_int15_handler: +;{ + RT_INTERRUPT_ENTRY + RT_CALL_INT hw_int15_handler +;} + .end diff --git a/libcpu/ti-dsp/c6x/stack.asm b/libcpu/ti-dsp/c6x/stack.asm index 4415a9767c..6a523a1c95 100644 --- a/libcpu/ti-dsp/c6x/stack.asm +++ b/libcpu/ti-dsp/c6x/stack.asm @@ -13,7 +13,7 @@ ;----------------------------------------------------------- ;----------------------------------------------------------- -; macro definition +; macro definition ;----------------------------------------------------------- ADDRESS_MSK .set 0xFFFFFFF0 @@ -22,6 +22,10 @@ ADDRESS_MSK .set 0xFFFFFFF0 ; .sect ".text" +; +;----------------------------------------------------------- +; + ; ; rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, rt_uint8_t *stack_addr, void *texit) ; tentry --> A4 diff --git a/libcpu/ti-dsp/c6x/trap.c b/libcpu/ti-dsp/c6x/trap.c index eb1863fa9c..f919467f2b 100644 --- a/libcpu/ti-dsp/c6x/trap.c +++ b/libcpu/ti-dsp/c6x/trap.c @@ -14,8 +14,18 @@ #include #include +#include + +#define RT_SYS_STACK_SIZE 4096 + +rt_uint8_t rt_system_stack[RT_SYS_STACK_SIZE]; +rt_uint8_t *rt_system_stack_top; + void rt_trap_init(void) { + rt_system_stack_top = &rt_system_stack[RT_SYS_STACK_SIZE-1]; + rt_system_stack_top = (rt_uint8_t *)RT_ALIGN_DOWN((rt_uint32_t)rt_system_stack_top, 8); + ack_exception(EXCEPT_TYPE_NXF); ack_exception(EXCEPT_TYPE_EXC); ack_exception(EXCEPT_TYPE_IXF); @@ -319,7 +329,7 @@ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) int ie_num = 9; /* default is unknown exception */ while ((type = get_except_type()) != 0) { - type_num = fls(type) - 1; + type_num = __fls(type) - 1; switch(type_num) { case EXCEPT_TYPE_NXF: /* NMI exception */ diff --git a/libcpu/ti-dsp/c6x/trap.h b/libcpu/ti-dsp/c6x/trap.h index 5494fa900b..6d4312e243 100644 --- a/libcpu/ti-dsp/c6x/trap.h +++ b/libcpu/ti-dsp/c6x/trap.h @@ -67,8 +67,8 @@ struct rt_exception_info { #define BKPT_OPCODE 0x56454314 /* illegal opcode */ #define INTC_MEXPMASK __SYSREGA(0x018000e0, unsigned int) -#define __ffs(a) (_lmbd(1, _bitr(a))) -#define fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) +#define __ffs(a) (_lmbd(1, _bitr(a))) +#define __fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) void rt_trap_init(void); diff --git a/libcpu/ti-dsp/c6x/vector.asm b/libcpu/ti-dsp/c6x/vector.asm index 47eb8781f5..c942029d86 100644 --- a/libcpu/ti-dsp/c6x/vector.asm +++ b/libcpu/ti-dsp/c6x/vector.asm @@ -75,21 +75,21 @@ __name: .align 32 .global vector vector: - VEC_RESET _c_int00 - IRQVEC NMI, _nmi_handler - IRQVEC AINT, _bad_handler - IRQVEC MSGINT,_bad_handler - IRQVEC INT4, _int4_handler - IRQVEC INT5, _int5_handler - IRQVEC INT6, _int6_handler - IRQVEC INT7, _int7_handler - IRQVEC INT8, _int8_handler - IRQVEC INT9, _int9_handler - IRQVEC INT10, _int10_handler - IRQVEC INT11, _int11_handler - IRQVEC INT12, _int12_handler - IRQVEC INT13, _int13_handler - IRQVEC INT14, _int14_handler - IRQVEC INT15, _int15_handler + VEC_RESET _c_int00 + IRQVEC NMI, _nmi_handler + IRQVEC AINT, _bad_handler + IRQVEC MSGINT, _bad_handler + IRQVEC INT4, _int4_handler + IRQVEC INT5, _int5_handler + IRQVEC INT6, _int6_handler + IRQVEC INT7, _int7_handler + IRQVEC INT8, _int8_handler + IRQVEC INT9, _int9_handler + IRQVEC INT10, _int10_handler + IRQVEC INT11, _int11_handler + IRQVEC INT12, _int12_handler + IRQVEC INT13, _int13_handler + IRQVEC INT14, _int14_handler + IRQVEC INT15, _int15_handler .end -- cgit v1.3.1 From cbc0e1ffcf4ad79d08ab199e2529941fa8c510d1 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 17 Nov 2021 18:31:58 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/board.c | 30 ++------ bsp/ti-tms320c6678/driver/drv_timer.c | 40 +++++++---- libcpu/ti-dsp/c6x/c66xx.h | 18 ----- libcpu/ti-dsp/c6x/context.asm | 2 +- libcpu/ti-dsp/c6x/interrupt.c | 7 +- libcpu/ti-dsp/c6x/intexc.asm | 2 +- libcpu/ti-dsp/c6x/stack.asm | 122 ++++++++++++++++---------------- libcpu/ti-dsp/c6x/trap.c | 1 + libcpu/ti-dsp/c6x/trap.h | 2 +- libcpu/ti-dsp/c6x/vector.asm | 2 +- 10 files changed, 102 insertions(+), 124 deletions(-) diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c index a0f951d31e..0a96a82ff8 100644 --- a/bsp/ti-tms320c6678/applications/board.c +++ b/bsp/ti-tms320c6678/applications/board.c @@ -9,28 +9,12 @@ */ #include "board.h" -#include "trap.h" #include "interrupt.h" #include "drv_timer.h" #include "KeyStone_common.h" #include -/** - * This is the timer interrupt service routine. - * - */ -void rt_hw_systick_isr(void) -{ - /* enter interrupt */ - rt_interrupt_enter(); - - rt_tick_increase(); - - /* leave interrupt */ - rt_interrupt_leave(); -} - /** * This function will initial board. */ @@ -42,16 +26,12 @@ void rt_hw_board_init(void) // initial interrupt controller rt_hw_interrupt_init(); - // initial system trap - rt_trap_init(); - // initial system timer - hw_system_timer_init(); + hw_system_timer_init(); - /* initialize memory system */ - rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); - rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); + /* initialize memory system */ + rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); + rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); - hw_system_timer_start(); + hw_system_timer_start(); } - diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 4cda450e49..163d802aca 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -15,41 +15,51 @@ #include /** - * @b Description - * @n - * The function initial system timer. - * Use local timer (==DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well + * This is the timer interrupt service routine. * - * @param[] - * - * @retval - * NULL + */ +void rt_hw_systick_isr(void) +{ + /* enter interrupt */ + rt_interrupt_enter(); + + rt_tick_increase(); + + /* leave interrupt */ + rt_interrupt_leave(); +} + +/** + * The function initial system timer interrupt. */ void hw_system_timer_init(void) { - // initial system timer interrupt - // map local timer interrupt to INT14 + // initial system timer interrupt, map local timer interrupt to INT14 gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)< Date: Wed, 17 Nov 2021 18:44:00 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/board.c | 4 ++-- bsp/ti-tms320c6678/driver/drv_timer.c | 4 ++-- bsp/ti-tms320c6678/driver/drv_timer.h | 4 ++-- libcpu/ti-dsp/c6x/c66xx.h | 7 ------- libcpu/ti-dsp/c6x/context.asm | 2 +- 5 files changed, 7 insertions(+), 14 deletions(-) diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c index 0a96a82ff8..b6a4105599 100644 --- a/bsp/ti-tms320c6678/applications/board.c +++ b/bsp/ti-tms320c6678/applications/board.c @@ -27,11 +27,11 @@ void rt_hw_board_init(void) rt_hw_interrupt_init(); // initial system timer - hw_system_timer_init(); + rt_hw_system_timer_init(); /* initialize memory system */ rt_kprintf("heap: 0x%08x - 0x%08x\n", RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); rt_system_heap_init(RT_HW_HEAP_BEGIN, RT_HW_HEAP_END); - hw_system_timer_start(); + rt_hw_system_timer_start(); } diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 163d802aca..330e04dcde 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -32,7 +32,7 @@ void rt_hw_systick_isr(void) /** * The function initial system timer interrupt. */ -void hw_system_timer_init(void) +void rt_hw_system_timer_init(void) { // initial system timer interrupt, map local timer interrupt to INT14 gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN< Date: Wed, 17 Nov 2021 18:48:54 +0800 Subject: 修改格式, MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libcpu/ti-dsp/c6x/c66xx.h | 74 +++++++++++++++++++++++------------------------ 1 file changed, 37 insertions(+), 37 deletions(-) diff --git a/libcpu/ti-dsp/c6x/c66xx.h b/libcpu/ti-dsp/c6x/c66xx.h index a8b08438ee..cb106f2f6a 100644 --- a/libcpu/ti-dsp/c6x/c66xx.h +++ b/libcpu/ti-dsp/c6x/c66xx.h @@ -14,56 +14,56 @@ #include #ifdef _BIG_ENDIAN -#define REG_PAIR(odd, even) unsigned long odd; unsigned long even +#define RT_REG_PAIR(odd, even) unsigned long odd; unsigned long even #else -#define REG_PAIR(odd, even) unsigned long even; unsigned long odd +#define RT_REG_PAIR(odd, even) unsigned long even; unsigned long odd #endif struct rt_hw_register { - REG_PAIR(b17, b16); - REG_PAIR(b19, b18); - REG_PAIR(b21, b20); - REG_PAIR(b23, b22); - REG_PAIR(b25, b24); - REG_PAIR(b27, b26); - REG_PAIR(b29, b28); - REG_PAIR(b31, b30); + RT_REG_PAIR(b17, b16); + RT_REG_PAIR(b19, b18); + RT_REG_PAIR(b21, b20); + RT_REG_PAIR(b23, b22); + RT_REG_PAIR(b25, b24); + RT_REG_PAIR(b27, b26); + RT_REG_PAIR(b29, b28); + RT_REG_PAIR(b31, b30); - REG_PAIR(b1, b0); - REG_PAIR(b3, b2); - REG_PAIR(b5, b4); - REG_PAIR(b7, b6); - REG_PAIR(b9, b8); - REG_PAIR(b11, b10); - REG_PAIR(b13, b12); + RT_REG_PAIR(b1, b0); + RT_REG_PAIR(b3, b2); + RT_REG_PAIR(b5, b4); + RT_REG_PAIR(b7, b6); + RT_REG_PAIR(b9, b8); + RT_REG_PAIR(b11, b10); + RT_REG_PAIR(b13, b12); - REG_PAIR(a17, a16); - REG_PAIR(a19, a18); - REG_PAIR(a21, a20); - REG_PAIR(a23, a22); - REG_PAIR(a25, a24); - REG_PAIR(a27, a26); - REG_PAIR(a29, a28); - REG_PAIR(a31, a30); + RT_REG_PAIR(a17, a16); + RT_REG_PAIR(a19, a18); + RT_REG_PAIR(a21, a20); + RT_REG_PAIR(a23, a22); + RT_REG_PAIR(a25, a24); + RT_REG_PAIR(a27, a26); + RT_REG_PAIR(a29, a28); + RT_REG_PAIR(a31, a30); - REG_PAIR(a1, a0); - REG_PAIR(a3, a2); - REG_PAIR(a5, a4); - REG_PAIR(a7, a6); - REG_PAIR(a9, a8); - REG_PAIR(a11, a10); - REG_PAIR(a13, a12); + RT_REG_PAIR(a1, a0); + RT_REG_PAIR(a3, a2); + RT_REG_PAIR(a5, a4); + RT_REG_PAIR(a7, a6); + RT_REG_PAIR(a9, a8); + RT_REG_PAIR(a11, a10); + RT_REG_PAIR(a13, a12); - REG_PAIR(a15, a14); - REG_PAIR(sp, dp); + RT_REG_PAIR(a15, a14); + RT_REG_PAIR(sp, dp); }; struct rt_hw_exp_stack_register { - REG_PAIR(tsr, orig_a4); - REG_PAIR(rilc, ilc); - REG_PAIR(pc, csr); + RT_REG_PAIR(tsr, orig_a4); + RT_REG_PAIR(rilc, ilc); + RT_REG_PAIR(pc, csr); struct rt_hw_register hw_register; }; -- cgit v1.3.1 From 8ab19db7fa1aa1bd1d9a5c3724b4de6a04012f41 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Thu, 18 Nov 2021 08:53:30 +0800 Subject: 修改汇编rt_hw_context_switch_to处关于时间槽的使用;修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libcpu/ti-dsp/c6x/context.asm | 10 ++-- libcpu/ti-dsp/c6x/contextinc.asm | 6 +-- libcpu/ti-dsp/c6x/intexc.asm | 6 +-- libcpu/ti-dsp/c6x/stack.asm | 106 +++++++++++++++++++-------------------- 4 files changed, 63 insertions(+), 65 deletions(-) diff --git a/libcpu/ti-dsp/c6x/context.asm b/libcpu/ti-dsp/c6x/context.asm index 2bbe0477f5..a66caf2736 100644 --- a/libcpu/ti-dsp/c6x/context.asm +++ b/libcpu/ti-dsp/c6x/context.asm @@ -136,15 +136,14 @@ rt_hw_context_switch_to: ; ; this maybe do better ; - MVC .S2 B11,RILC ; Restore RILC - MVC .S2 B10,ILC ; Restore ILC - MV B13,B3 ; Restore PC - MVC .S2 B12,CSR ; Restore CSR - LDDW .D2T2 *++SP[1],B11:B10 + || MVC .S2 B11,RILC ; Restore RILC LDDW .D2T2 *++SP[1],B13:B12 + || MVC .S2 B10,ILC ; Restore ILC LDDW .D2T1 *++SP[1],A11:A10 + || MV B13,B3 ; Restore PC LDDW .D2T1 *++SP[1],A13:A12 + || MVC .S2 B12,CSR ; Restore CSR LDDW .D2T1 *++SP[1],A15:A14 B B3 ; Return to caller ADDAW .D2 SP,2,SP @@ -236,7 +235,6 @@ _reswitch: .global rt_interrupt_context_restore rt_interrupt_context_restore: ;{ -; if rt_switch_interrupt_flag set, jump to rt_hw_context_switch_interrupt and don't return MVKL rt_thread_switch_interrupt_flag,A3 MVKH rt_thread_switch_interrupt_flag,A3 LDW *A3,A1 diff --git a/libcpu/ti-dsp/c6x/contextinc.asm b/libcpu/ti-dsp/c6x/contextinc.asm index 18926aa088..d89e66fd4d 100644 --- a/libcpu/ti-dsp/c6x/contextinc.asm +++ b/libcpu/ti-dsp/c6x/contextinc.asm @@ -19,7 +19,7 @@ SAVE_ALL .macro __rp, __tsr NOP 3 STW .D2T2 B1,*+SP[1] ; save original B1 - XOR .D2 SP,B1,B0 ; (SP ^ KSP, check current stack types) + XOR .D2 SP,B1,B0 ; check current stack types LDW .D2T2 *+SP[1],B1 ; restore B0/B1 LDW .D2T2 *++SP[2],B0 SHR .S2 B0,12,B0 ; 0 if already using system stack @@ -75,7 +75,7 @@ SAVE_ALL .macro __rp, __tsr STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC - STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 + STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4(stack type) .endm RESTORE_ALL .macro __rp, __tsr @@ -183,5 +183,5 @@ THREAD_SAVE_ALL .macro __rp, __tsr STDW .D2T2 B13:B12,*SP--[1] ; save PC and CSR STDW .D2T2 B11:B10,*SP--[1] ; save RILC and ILC - STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4 + STDW .D2T1 A5:A4,*SP--[1] ; save TSR and orig A4(stack type) .endm diff --git a/libcpu/ti-dsp/c6x/intexc.asm b/libcpu/ti-dsp/c6x/intexc.asm index 709a9c4232..e5bfef4a2a 100644 --- a/libcpu/ti-dsp/c6x/intexc.asm +++ b/libcpu/ti-dsp/c6x/intexc.asm @@ -9,7 +9,7 @@ ; ;----------------------------------------------------------- -; interrupt and execption handler for C000 DSP +; interrupt and execption handler for C6000 DSP ;----------------------------------------------------------- ;----------------------------------------------------------- @@ -94,7 +94,7 @@ RT_EXECPTION_ENTRY .macro RT_EXECPTION_EXIT .macro RESTORE_ALL NRP,NTSR - B .S2 NRP ; return from interruption + B .S2 NRP ; return from execption NOP 5 .endm @@ -137,7 +137,7 @@ ret_from_trap: [!B0] MVKH .S2 ret_from_exception,B3 [!B0] BNOP .S2 B3,5 ; -; return from trap£¬restore exception context +; return from trap restore exception context ; ret_from_exception: RT_EXECPTION_EXIT diff --git a/libcpu/ti-dsp/c6x/stack.asm b/libcpu/ti-dsp/c6x/stack.asm index 6823ef7a66..610f4f8f80 100644 --- a/libcpu/ti-dsp/c6x/stack.asm +++ b/libcpu/ti-dsp/c6x/stack.asm @@ -35,73 +35,73 @@ ADDRESS_MSK .set 0xFFFFFFF0 ;{ .global rt_hw_stack_init rt_hw_stack_init: - SUB A6,1,B1 ; - MVKL ADDRESS_MSK,A1 ; - MVKH ADDRESS_MSK,A1 ; Build address mask - MVC CSR,B0 ; - AND -2,B0,B0 ; Clear GIE bit - OR 2,B0,B0 ; Set PGIE bit for interrupt return - AND A1,B1,B1 ; Ensure alignment + SUB A6,1,B1 ; + MVKL .S1 ADDRESS_MSK,A1 ; + MVKH .S1 ADDRESS_MSK,A1 ; Build address mask + MVC .S2 CSR,B0 ; + AND -2,B0,B0 ; Clear GIE bit + OR 2,B0,B0 ; Set PGIE bit for interrupt return + AND A1,B1,B1 ; Ensure alignment ; ; Actually build the stack frame. ; - MV B1,A3 - MV B14,A2 - STDW A3:A2,*--B1[1] ; Initial B15:B14 + MV .S1 B1,A3 + MV .S1 B14,A2 + STDW .D2T1 A3:A2,*--B1[1] ; Initial B15:B14 SUBAW .D2 B1,2,B1 ZERO A2 - ZERO A3 ; Clear value - STDW A3:A2,*B1--[1] ; Initial A15:A14 - STDW A3:A2,*B1--[1] ; Initial A13:A12 - STDW A3:A2,*B1--[1] ; Initial A11:A10 - STDW A3:A2,*B1--[1] ; Initial A9:A8 - STDW A3:A2,*B1--[1] ; Initial A7:A6 - MV B4,A2 - STDW A3:A2,*B1--[1] ; Initial A5:A4 + ZERO A3 ; Clear value + STDW .D2T1 A3:A2,*B1--[1] ; Initial A15:A14 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A13:A12 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A11:A10 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A9:A8 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A7:A6 + MV .S1 B4,A2 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A5:A4 ZERO A2 - STDW A3:A2,*B1--[1] ; Initial A3:A2 - STDW A3:A2,*B1--[1] ; Initial A1:A0 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A3:A2 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A1:A0 - STDW A3:A2,*B1--[1] ; Initial A31:A30 - STDW A3:A2,*B1--[1] ; Initial A29:A28 - STDW A3:A2,*B1--[1] ; Initial A27:A26 - STDW A3:A2,*B1--[1] ; Initial A25:A24 - STDW A3:A2,*B1--[1] ; Initial A23:A22 - STDW A3:A2,*B1--[1] ; Initial A21:A20 - STDW A3:A2,*B1--[1] ; Initial A19:A18 - STDW A3:A2,*B1--[1] ; Initial A17:A16 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A31:A30 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A29:A28 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A27:A26 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A25:A24 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A23:A22 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A21:A20 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A19:A18 + STDW .D2T1 A3:A2,*B1--[1] ; Initial A17:A16 - STDW A3:A2,*B1--[1] ; Initial B13:B12 - STDW A3:A2,*B1--[1] ; Initial B11:B10 - STDW A3:A2,*B1--[1] ; Initial B9:B8 - STDW A3:A2,*B1--[1] ; Initial B7:B6 - STDW A3:A2,*B1--[1] ; Initial B5:B4 - MV B6,A3 - STDW A3:A2,*B1--[1] ; Initial B3:B2 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B13:B12 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B11:B10 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B9:B8 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B7:B6 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B5:B4 + MV .S1 B6,A3 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B3:B2 ZERO A3 - STDW A3:A2,*B1--[1] ; Initial B1:B0 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B1:B0 - STDW A3:A2,*B1--[1] ; Initial B31:B30 - STDW A3:A2,*B1--[1] ; Initial B29:B28 - STDW A3:A2,*B1--[1] ; Initial B27:B26 - STDW A3:A2,*B1--[1] ; Initial B25:B24 - STDW A3:A2,*B1--[1] ; Initial B23:B22 - STDW A3:A2,*B1--[1] ; Initial B21:B20 - STDW A3:A2,*B1--[1] ; Initial B19:B18 - STDW A3:A2,*B1--[1] ; Initial B17:B16 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B31:B30 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B29:B28 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B27:B26 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B25:B24 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B23:B22 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B21:B20 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B19:B18 + STDW .D2T1 A3:A2,*B1--[1] ; Initial B17:B16 - MV A4,A3 - MV B0,A2 - STDW A3:A2,*B1--[1] ; Initial PC:CSR + MV .S1 A4,A3 + MV .S1 B0,A2 + STDW .D2T1 A3:A2,*B1--[1] ; Initial PC:CSR ZERO A2 ZERO A3 - STDW A3:A2,*B1--[1] ; Initial ILC:RILC + STDW .D2T1 A3:A2,*B1--[1] ; Initial ILC:RILC B B3 - MVKL 0x3,B0 - MV B0,A3 - MVKL 1,A2 - STDW A3:A2,*B1--[1] ; Initial TSR:stack type - MV B1,A4 ; Save to TCB + MVKL .S2 0x3,B0 + MV .S1 B0,A3 + MVKL .S1 1,A2 + STDW .D2T1 A3:A2,*B1--[1] ; Initial TSR:stack type + MV .S1 B1,A4 ; Save to TCB ;} .end -- cgit v1.3.1 From 2b13e2fa57a8cc2f536b8279eb0c952c6e3b49d7 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Thu, 18 Nov 2021 09:23:29 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/board.c | 10 ++-- bsp/ti-tms320c6678/applications/main.c | 52 +++++++++---------- bsp/ti-tms320c6678/driver/drv_timer.c | 12 ++--- libcpu/ti-dsp/c6x/c66xx.h | 88 ++++++++++++++++----------------- libcpu/ti-dsp/c6x/context.asm | 80 +++++++++++++++--------------- libcpu/ti-dsp/c6x/contextinc.asm | 44 ++++++++--------- libcpu/ti-dsp/c6x/cpuport.c | 1 - libcpu/ti-dsp/c6x/interrupt.c | 4 +- libcpu/ti-dsp/c6x/intexc.asm | 16 +++--- libcpu/ti-dsp/c6x/stack.asm | 88 ++++++++++++++++----------------- libcpu/ti-dsp/c6x/trap.c | 12 ++--- libcpu/ti-dsp/c6x/trap.h | 28 +++++------ 12 files changed, 216 insertions(+), 219 deletions(-) diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c index b6a4105599..51a21f6cd8 100644 --- a/bsp/ti-tms320c6678/applications/board.c +++ b/bsp/ti-tms320c6678/applications/board.c @@ -20,13 +20,13 @@ */ void rt_hw_board_init(void) { - // initial CPU core - KeyStone_common_CPU_init(); + // initial CPU core + KeyStone_common_CPU_init(); - // initial interrupt controller - rt_hw_interrupt_init(); + // initial interrupt controller + rt_hw_interrupt_init(); - // initial system timer + // initial system timer rt_hw_system_timer_init(); /* initialize memory system */ diff --git a/bsp/ti-tms320c6678/applications/main.c b/bsp/ti-tms320c6678/applications/main.c index a8b9e17efc..f72b93b9dc 100644 --- a/bsp/ti-tms320c6678/applications/main.c +++ b/bsp/ti-tms320c6678/applications/main.c @@ -15,8 +15,8 @@ void rt_init_thread_entry(void *parameter) { - rt_kprintf("hello rt-thread\n"); - return 0; + rt_kprintf("hello rt-thread\n"); + return 0; } int rt_application_init(void) @@ -39,42 +39,42 @@ int rt_application_init(void) */ void rtthread_startup(void) { - /* disable interrupt first */ - rt_hw_interrupt_disable(); - - /* init board */ - rt_hw_board_init(); + /* disable interrupt first */ + rt_hw_interrupt_disable(); + + /* init board */ + rt_hw_board_init(); - /* show version */ - rt_show_version(); + /* show version */ + rt_show_version(); - /* init timer system */ - rt_system_timer_init(); + /* init timer system */ + rt_system_timer_init(); - /* init scheduler system */ - rt_system_scheduler_init(); + /* init scheduler system */ + rt_system_scheduler_init(); - /* init application */ - rt_application_init(); + /* init application */ + rt_application_init(); - /* init timer thread */ - rt_system_timer_thread_init(); + /* init timer thread */ + rt_system_timer_thread_init(); - /* init idle thread */ - rt_thread_idle_init(); + /* init idle thread */ + rt_thread_idle_init(); - /* start scheduler */ - rt_system_scheduler_start(); + /* start scheduler */ + rt_system_scheduler_start(); - /* never reach here */ - return ; + /* never reach here */ + return ; } void main(void) { - /* startup RT-Thread RTOS */ - rtthread_startup(); + /* startup RT-Thread RTOS */ + rtthread_startup(); - for ( ; ; ); + for ( ; ; ); } diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 330e04dcde..b2a9319875 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -20,13 +20,13 @@ */ void rt_hw_systick_isr(void) { - /* enter interrupt */ - rt_interrupt_enter(); + /* enter interrupt */ + rt_interrupt_enter(); - rt_tick_increase(); + rt_tick_increase(); - /* leave interrupt */ - rt_interrupt_leave(); + /* leave interrupt */ + rt_interrupt_leave(); } /** @@ -34,7 +34,7 @@ void rt_hw_systick_isr(void) */ void rt_hw_system_timer_init(void) { - // initial system timer interrupt, map local timer interrupt to INT14 + // initial system timer interrupt, map local timer interrupt to INT14 gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN< Date: Thu, 18 Nov 2021 09:37:05 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/main.c | 2 +- bsp/ti-tms320c6678/driver/drv_timer.c | 10 +- libcpu/ti-dsp/c6x/cpuport.c | 8 +- libcpu/ti-dsp/c6x/trap.c | 590 ++++++++++++++++----------------- 4 files changed, 304 insertions(+), 306 deletions(-) diff --git a/bsp/ti-tms320c6678/applications/main.c b/bsp/ti-tms320c6678/applications/main.c index f72b93b9dc..d29fd00a4f 100644 --- a/bsp/ti-tms320c6678/applications/main.c +++ b/bsp/ti-tms320c6678/applications/main.c @@ -75,6 +75,6 @@ void main(void) /* startup RT-Thread RTOS */ rtthread_startup(); - for ( ; ; ); + for(;;){} } diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index b2a9319875..a755689df4 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -35,7 +35,7 @@ void rt_hw_systick_isr(void) void rt_hw_system_timer_init(void) { // initial system timer interrupt, map local timer interrupt to INT14 - gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<INTMUX3=(CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)< -#define RT_SYS_STACK_SIZE 4096 +#define RT_SYS_STACK_SIZE 4096 extern void rt_hw_enable_exception(void); rt_uint8_t rt_system_stack[RT_SYS_STACK_SIZE]; @@ -24,111 +24,110 @@ rt_uint8_t *rt_system_stack_top; void rt_trap_init(void) { - rt_system_stack_top = &rt_system_stack[RT_SYS_STACK_SIZE-1]; - rt_system_stack_top = (rt_uint8_t *)RT_ALIGN_DOWN((rt_uint32_t)rt_system_stack_top, 8); - - ack_exception(EXCEPT_TYPE_NXF); - ack_exception(EXCEPT_TYPE_EXC); - ack_exception(EXCEPT_TYPE_IXF); - ack_exception(EXCEPT_TYPE_SXF); - rt_hw_enable_exception(); + rt_system_stack_top = &rt_system_stack[RT_SYS_STACK_SIZE-1]; + rt_system_stack_top = (rt_uint8_t *)RT_ALIGN_DOWN((rt_uint32_t)rt_system_stack_top, 8); + + ack_exception(EXCEPT_TYPE_NXF); + ack_exception(EXCEPT_TYPE_EXC); + ack_exception(EXCEPT_TYPE_IXF); + ack_exception(EXCEPT_TYPE_SXF); + rt_hw_enable_exception(); } void show_regs(struct rt_hw_exp_stack_register *regs) { - rt_kprintf("\n"); - rt_kprintf("PC: %08lx SP: %08lx\n", - regs->pc, regs->hw_register.sp); - rt_kprintf("Status: %08lx ORIG_A4: %08lx\n", - regs->csr, regs->orig_a4); - rt_kprintf("A0: %08lx B0: %08lx\n", - regs->hw_register.a0, regs->hw_register.b0); - rt_kprintf("A1: %08lx B1: %08lx\n", - regs->hw_register.a1, regs->hw_register.b1); - rt_kprintf("A2: %08lx B2: %08lx\n", - regs->hw_register.a2, regs->hw_register.b2); - rt_kprintf("A3: %08lx B3: %08lx\n", - regs->hw_register.a3, regs->hw_register.b3); - rt_kprintf("A4: %08lx B4: %08lx\n", - regs->hw_register.a4, regs->hw_register.b4); - rt_kprintf("A5: %08lx B5: %08lx\n", - regs->hw_register.a5, regs->hw_register.b5); - rt_kprintf("A6: %08lx B6: %08lx\n", - regs->hw_register.a6, regs->hw_register.b6); - rt_kprintf("A7: %08lx B7: %08lx\n", - regs->hw_register.a7, regs->hw_register.b7); - rt_kprintf("A8: %08lx B8: %08lx\n", - regs->hw_register.a8, regs->hw_register.b8); - rt_kprintf("A9: %08lx B9: %08lx\n", - regs->hw_register.a9, regs->hw_register.b9); - rt_kprintf("A10: %08lx B10: %08lx\n", - regs->hw_register.a10, regs->hw_register.b10); - rt_kprintf("A11: %08lx B11: %08lx\n", - regs->hw_register.a11, regs->hw_register.b11); - rt_kprintf("A12: %08lx B12: %08lx\n", - regs->hw_register.a12, regs->hw_register.b12); - rt_kprintf("A13: %08lx B13: %08lx\n", - regs->hw_register.a13, regs->hw_register.b13); - rt_kprintf("A14: %08lx B14: %08lx\n", - regs->hw_register.a14, regs->hw_register.dp); - rt_kprintf("A15: %08lx B15: %08lx\n", - regs->hw_register.a15, regs->hw_register.sp); - rt_kprintf("A16: %08lx B16: %08lx\n", - regs->hw_register.a16, regs->hw_register.b16); - rt_kprintf("A17: %08lx B17: %08lx\n", - regs->hw_register.a17, regs->hw_register.b17); - rt_kprintf("A18: %08lx B18: %08lx\n", - regs->hw_register.a18, regs->hw_register.b18); - rt_kprintf("A19: %08lx B19: %08lx\n", - regs->hw_register.a19, regs->hw_register.b19); - rt_kprintf("A20: %08lx B20: %08lx\n", - regs->hw_register.a20, regs->hw_register.b20); - rt_kprintf("A21: %08lx B21: %08lx\n", - regs->hw_register.a21, regs->hw_register.b21); - rt_kprintf("A22: %08lx B22: %08lx\n", - regs->hw_register.a22, regs->hw_register.b22); - rt_kprintf("A23: %08lx B23: %08lx\n", - regs->hw_register.a23, regs->hw_register.b23); - rt_kprintf("A24: %08lx B24: %08lx\n", - regs->hw_register.a24, regs->hw_register.b24); - rt_kprintf("A25: %08lx B25: %08lx\n", - regs->hw_register.a25, regs->hw_register.b25); - rt_kprintf("A26: %08lx B26: %08lx\n", - regs->hw_register.a26, regs->hw_register.b26); - rt_kprintf("A27: %08lx B27: %08lx\n", - regs->hw_register.a27, regs->hw_register.b27); - rt_kprintf("A28: %08lx B28: %08lx\n", - regs->hw_register.a28, regs->hw_register.b28); - rt_kprintf("A29: %08lx B29: %08lx\n", - regs->hw_register.a29, regs->hw_register.b29); - rt_kprintf("A30: %08lx B30: %08lx\n", - regs->hw_register.a30, regs->hw_register.b30); - rt_kprintf("A31: %08lx B31: %08lx\n", - regs->hw_register.a31, regs->hw_register.b31); + rt_kprintf("\n"); + rt_kprintf("PC: %08lx SP: %08lx\n", + regs->pc, regs->hw_register.sp); + rt_kprintf("Status: %08lx ORIG_A4: %08lx\n", + regs->csr, regs->orig_a4); + rt_kprintf("A0: %08lx B0: %08lx\n", + regs->hw_register.a0, regs->hw_register.b0); + rt_kprintf("A1: %08lx B1: %08lx\n", + regs->hw_register.a1, regs->hw_register.b1); + rt_kprintf("A2: %08lx B2: %08lx\n", + regs->hw_register.a2, regs->hw_register.b2); + rt_kprintf("A3: %08lx B3: %08lx\n", + regs->hw_register.a3, regs->hw_register.b3); + rt_kprintf("A4: %08lx B4: %08lx\n", + regs->hw_register.a4, regs->hw_register.b4); + rt_kprintf("A5: %08lx B5: %08lx\n", + regs->hw_register.a5, regs->hw_register.b5); + rt_kprintf("A6: %08lx B6: %08lx\n", + regs->hw_register.a6, regs->hw_register.b6); + rt_kprintf("A7: %08lx B7: %08lx\n", + regs->hw_register.a7, regs->hw_register.b7); + rt_kprintf("A8: %08lx B8: %08lx\n", + regs->hw_register.a8, regs->hw_register.b8); + rt_kprintf("A9: %08lx B9: %08lx\n", + regs->hw_register.a9, regs->hw_register.b9); + rt_kprintf("A10: %08lx B10: %08lx\n", + regs->hw_register.a10, regs->hw_register.b10); + rt_kprintf("A11: %08lx B11: %08lx\n", + regs->hw_register.a11, regs->hw_register.b11); + rt_kprintf("A12: %08lx B12: %08lx\n", + regs->hw_register.a12, regs->hw_register.b12); + rt_kprintf("A13: %08lx B13: %08lx\n", + regs->hw_register.a13, regs->hw_register.b13); + rt_kprintf("A14: %08lx B14: %08lx\n", + regs->hw_register.a14, regs->hw_register.dp); + rt_kprintf("A15: %08lx B15: %08lx\n", + regs->hw_register.a15, regs->hw_register.sp); + rt_kprintf("A16: %08lx B16: %08lx\n", + regs->hw_register.a16, regs->hw_register.b16); + rt_kprintf("A17: %08lx B17: %08lx\n", + regs->hw_register.a17, regs->hw_register.b17); + rt_kprintf("A18: %08lx B18: %08lx\n", + regs->hw_register.a18, regs->hw_register.b18); + rt_kprintf("A19: %08lx B19: %08lx\n", + regs->hw_register.a19, regs->hw_register.b19); + rt_kprintf("A20: %08lx B20: %08lx\n", + regs->hw_register.a20, regs->hw_register.b20); + rt_kprintf("A21: %08lx B21: %08lx\n", + regs->hw_register.a21, regs->hw_register.b21); + rt_kprintf("A22: %08lx B22: %08lx\n", + regs->hw_register.a22, regs->hw_register.b22); + rt_kprintf("A23: %08lx B23: %08lx\n", + regs->hw_register.a23, regs->hw_register.b23); + rt_kprintf("A24: %08lx B24: %08lx\n", + regs->hw_register.a24, regs->hw_register.b24); + rt_kprintf("A25: %08lx B25: %08lx\n", + regs->hw_register.a25, regs->hw_register.b25); + rt_kprintf("A26: %08lx B26: %08lx\n", + regs->hw_register.a26, regs->hw_register.b26); + rt_kprintf("A27: %08lx B27: %08lx\n", + regs->hw_register.a27, regs->hw_register.b27); + rt_kprintf("A28: %08lx B28: %08lx\n", + regs->hw_register.a28, regs->hw_register.b28); + rt_kprintf("A29: %08lx B29: %08lx\n", + regs->hw_register.a29, regs->hw_register.b29); + rt_kprintf("A30: %08lx B30: %08lx\n", + regs->hw_register.a30, regs->hw_register.b30); + rt_kprintf("A31: %08lx B31: %08lx\n", + regs->hw_register.a31, regs->hw_register.b31); } void do_trap(struct rt_exception_info *except_info, struct rt_hw_exp_stack_register *regs) { - rt_kprintf("Enter exception: %s\n", except_info->kernel_str); + rt_kprintf("Enter exception: %s\n", except_info->kernel_str); - show_regs(regs); + show_regs(regs); - for( ; ; ); + for(;;){} } - static struct rt_exception_info iexcept_table[10] = { - { " - instruction fetch", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - fetch packet", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - execute packet", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, - { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, - { " - resource conflict", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, - { " - resource access", ABORT_TYPE_UNDDEF, ABORT_PRVREG_ILL }, - { " - privilege", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, - { " - loops buffer", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, - { " - software exception", ABORT_TYPE_UNDDEF, ABORT_ILLTRP_ILL }, - { " - unknown exception", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL } + { " - instruction fetch", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - fetch packet", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - execute packet", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - resource conflict", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - resource access", ABORT_TYPE_UNDDEF, ABORT_PRVREG_ILL }, + { " - privilege", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, + { " - loops buffer", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, + { " - software exception", ABORT_TYPE_UNDDEF, ABORT_ILLTRP_ILL }, + { " - unknown exception", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL } }; /* @@ -136,163 +135,162 @@ static struct rt_exception_info iexcept_table[10] = { */ static int process_iexcept(struct rt_hw_exp_stack_register *regs) { - unsigned int iexcept_report = get_iexcept(); - unsigned int iexcept_num; - - ack_exception(EXCEPT_TYPE_IXF); - - while(iexcept_report) { - iexcept_num = __ffs(iexcept_report); - iexcept_report &= ~(1 << iexcept_num); - set_iexcept(iexcept_report); - - if (*(unsigned int *)regs->pc == BKPT_OPCODE) { - /* This is a breakpoint */ - struct rt_exception_info bkpt_exception = { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; - do_trap(&bkpt_exception, regs); - iexcept_report &= ~(0xFF); - set_iexcept(iexcept_report); - continue; - } - - do_trap(&iexcept_table[iexcept_num], regs); - } - return 0; + unsigned int iexcept_report = get_iexcept(); + unsigned int iexcept_num; + + ack_exception(EXCEPT_TYPE_IXF); + + while(iexcept_report) { + iexcept_num = __ffs(iexcept_report); + iexcept_report &= ~(1 << iexcept_num); + set_iexcept(iexcept_report); + + if (*(unsigned int *)regs->pc == BKPT_OPCODE) { + /* This is a breakpoint */ + struct rt_exception_info bkpt_exception = { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; + do_trap(&bkpt_exception, regs); + iexcept_report &= ~(0xFF); + set_iexcept(iexcept_report); + continue; + } + do_trap(&iexcept_table[iexcept_num], regs); + } + return 0; } static struct rt_exception_info except_table[128] = { - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - - { " - CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - CPU memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - DMA memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - CPU memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - DMA memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - CPU memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - DMA memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - EMC CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, - { " - EMC bus error", ABORT_TYPE_MAP, ABORT_BUS_ADDRERR } + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + + { " - CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L1P", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L1D", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - CPU memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - DMA memory protection fault in L2", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - EMC CPU memory protection fault", ABORT_TYPE_MAP, ABORT_BUS_ACCERR }, + { " - EMC bus error", ABORT_TYPE_MAP, ABORT_BUS_ADDRERR } }; /* @@ -300,22 +298,22 @@ static struct rt_exception_info except_table[128] = { */ static void process_except(struct rt_hw_exp_stack_register *regs) { - int except_num; - int bank = 0; - int i; - - for (i = 0; i <= 3; i++) { - while (INTC_MEXPMASK[i]) { - __dint(); - except_num = __ffs(INTC_MEXPMASK[i]); - INTC_MEXPMASK[i] &= ~(1 << except_num); /* ack the external exception */ - __rint(); - do_trap(&except_table[except_num + (bank << 5)], regs); - } - bank++; - } - - ack_exception(EXCEPT_TYPE_EXC); + int except_num; + int bank = 0; + int i; + + for (i = 0; i <= 3; i++) { + while (INTC_MEXPMASK[i]) { + __dint(); + except_num = __ffs(INTC_MEXPMASK[i]); + INTC_MEXPMASK[i] &= ~(1 << except_num); /* ack the external exception */ + __rint(); + do_trap(&except_table[except_num + (bank << 5)], regs); + } + bank++; + } + + ack_exception(EXCEPT_TYPE_EXC); } extern void hw_nmi_handler(struct rt_hw_exp_stack_register *regs); @@ -325,39 +323,39 @@ extern void hw_nmi_handler(struct rt_hw_exp_stack_register *regs); */ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) { - int type; - int type_num; - int ie_num = 9; /* default is unknown exception */ - - while ((type = get_except_type()) != 0) { - type_num = __fls(type) - 1; - - switch(type_num) { - case EXCEPT_TYPE_NXF: /* NMI exception */ - ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ - if (hw_nmi_handler != RT_NULL) - hw_nmi_handler(regs); - break; - - case EXCEPT_TYPE_IXF: /* internal exception */ - if (process_iexcept(regs)) - return 1; - break; - - case EXCEPT_TYPE_EXC: /* external exception */ - process_except(regs); - break; - - case EXCEPT_TYPE_SXF: /* software exception */ - ie_num = 8; - ack_exception(type_num); - break; - default: /* clear exception */ - ack_exception(type_num); - do_trap(&iexcept_table[ie_num], regs); - break; - } - } - return 0; + int type; + int type_num; + int ie_num = 9; /* default is unknown exception */ + + while ((type = get_except_type()) != 0) { + type_num = __fls(type) - 1; + + switch(type_num) { + case EXCEPT_TYPE_NXF: /* NMI exception */ + ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ + if (hw_nmi_handler != RT_NULL) + hw_nmi_handler(regs); + break; + + case EXCEPT_TYPE_IXF: /* internal exception */ + if (process_iexcept(regs)) + return 1; + break; + + case EXCEPT_TYPE_EXC: /* external exception */ + process_except(regs); + break; + + case EXCEPT_TYPE_SXF: /* software exception */ + ie_num = 8; + ack_exception(type_num); + break; + default: /* clear exception */ + ack_exception(type_num); + do_trap(&iexcept_table[ie_num], regs); + break; + } + } + return 0; } -- cgit v1.3.1 From 4a2ce8bca5b3682a514de8b1a0499624ad6da1fc Mon Sep 17 00:00:00 2001 From: Huang bo Date: Thu, 18 Nov 2021 09:48:06 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/driver/drv_timer.c | 8 ++++---- libcpu/ti-dsp/c6x/interrupt.c | 7 ++++++- libcpu/ti-dsp/c6x/trap.c | 28 ++++++++++++++++----------- libcpu/ti-dsp/c6x/trap.h | 36 +++++++++++++++++------------------ 4 files changed, 45 insertions(+), 34 deletions(-) diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index a755689df4..30b2770f24 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -35,7 +35,7 @@ void rt_hw_systick_isr(void) void rt_hw_system_timer_init(void) { // initial system timer interrupt, map local timer interrupt to INT14 - gpCGEM_regs->INTMUX3=(CSL_GEM_TINTLN<INTMUX3 = (CSL_GEM_TINTLN<TOUTSEL = (DNUM*2)<= MAX_HANDLERS) + { return; + } } /** @@ -56,7 +57,9 @@ void rt_hw_interrupt_mask(int vector) void rt_hw_interrupt_umask(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) + { return; + } } /** @@ -90,5 +93,7 @@ rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, void rt_hw_interrupt_clear(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) + { return; + } } diff --git a/libcpu/ti-dsp/c6x/trap.c b/libcpu/ti-dsp/c6x/trap.c index 7d4c063798..c7030c9bec 100644 --- a/libcpu/ti-dsp/c6x/trap.c +++ b/libcpu/ti-dsp/c6x/trap.c @@ -12,9 +12,8 @@ #include "c66xx.h" #include -#include - #include +#include #define RT_SYS_STACK_SIZE 4096 @@ -136,16 +135,18 @@ static struct rt_exception_info iexcept_table[10] = { static int process_iexcept(struct rt_hw_exp_stack_register *regs) { unsigned int iexcept_report = get_iexcept(); - unsigned int iexcept_num; + unsigned int iexcept_num = 0; ack_exception(EXCEPT_TYPE_IXF); - while(iexcept_report) { + while(iexcept_report) + { iexcept_num = __ffs(iexcept_report); iexcept_report &= ~(1 << iexcept_num); set_iexcept(iexcept_report); - if (*(unsigned int *)regs->pc == BKPT_OPCODE) { + if (*(unsigned int *)regs->pc == BKPT_OPCODE) + { /* This is a breakpoint */ struct rt_exception_info bkpt_exception = { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; do_trap(&bkpt_exception, regs); @@ -300,10 +301,12 @@ static void process_except(struct rt_hw_exp_stack_register *regs) { int except_num; int bank = 0; - int i; + int i = 0; - for (i = 0; i <= 3; i++) { - while (INTC_MEXPMASK[i]) { + for (i = 0; i <= 3; i++) + { + while (INTC_MEXPMASK[i]) + { __dint(); except_num = __ffs(INTC_MEXPMASK[i]); INTC_MEXPMASK[i] &= ~(1 << except_num); /* ack the external exception */ @@ -317,14 +320,13 @@ static void process_except(struct rt_hw_exp_stack_register *regs) } extern void hw_nmi_handler(struct rt_hw_exp_stack_register *regs); - /* * Main exception processing */ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) { - int type; - int type_num; + int type = 0; + int type_num = 0; int ie_num = 9; /* default is unknown exception */ while ((type = get_except_type()) != 0) { @@ -334,12 +336,16 @@ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) case EXCEPT_TYPE_NXF: /* NMI exception */ ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ if (hw_nmi_handler != RT_NULL) + { hw_nmi_handler(regs); + } break; case EXCEPT_TYPE_IXF: /* internal exception */ if (process_iexcept(regs)) + { return 1; + } break; case EXCEPT_TYPE_EXC: /* external exception */ diff --git a/libcpu/ti-dsp/c6x/trap.h b/libcpu/ti-dsp/c6x/trap.h index 062acee768..9c8f52dd14 100644 --- a/libcpu/ti-dsp/c6x/trap.h +++ b/libcpu/ti-dsp/c6x/trap.h @@ -41,34 +41,34 @@ enum SYSTEM_TRAP_CODE { - ABORT_BUS_ADDRERR = 0, // bus address error - ABORT_BUS_ACCERR, // bus access permission error - ABORT_OPCODE_ILL, // illegal opcode - ABORT_PRVREG_ILL, // privilege register - ABORT_PRVOPC_ILL, // privileged opcode - ABORT_ILLTRP_ILL, // illegal trap - ABORT_BRKPT_ILL, // handling breakpoints + ABORT_BUS_ADDRERR = 0, // bus address error + ABORT_BUS_ACCERR, // bus access permission error + ABORT_OPCODE_ILL, // illegal opcode + ABORT_PRVREG_ILL, // privilege register + ABORT_PRVOPC_ILL, // privileged opcode + ABORT_ILLTRP_ILL, // illegal trap + ABORT_BRKPT_ILL, // handling breakpoints }; /* * abort types */ -#define ABORT_TYPE_BUS 0 // bus access abnormal -#define ABORT_TYPE_MAP 1 // page table mapping error -#define ABORT_TYPE_UNDDEF 0xff // undefined exception -#define ABORT_TYPE_FATAL 0xffffffff // fatal error +#define ABORT_TYPE_BUS 0 // bus access abnormal +#define ABORT_TYPE_MAP 1 // page table mapping error +#define ABORT_TYPE_UNDDEF 0xff // undefined exception +#define ABORT_TYPE_FATAL 0xffffffff // fatal error struct rt_exception_info { - char *kernel_str; - int type; - int code; + char *kernel_str; + int type; + int code; }; -#define BKPT_OPCODE 0x56454314 /* illegal opcode */ -#define INTC_MEXPMASK __SYSREGA(0x018000e0, unsigned int) +#define BKPT_OPCODE 0x56454314 /* illegal opcode */ +#define INTC_MEXPMASK __SYSREGA(0x018000e0, unsigned int) -#define __ffs(a) (_lmbd(1, _bitr(a))) -#define __fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) +#define __ffs(a) (_lmbd(1, _bitr(a))) +#define __fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) extern void rt_trap_init(void); -- cgit v1.3.1 From 17246ed77bad3e00941555e225dd35a754ba143c Mon Sep 17 00:00:00 2001 From: Huang bo Date: Thu, 18 Nov 2021 09:56:45 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/driver/drv_timer.c | 8 ++++---- libcpu/ti-dsp/c6x/trap.c | 7 ++++--- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 30b2770f24..9fe4e05fed 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -35,9 +35,9 @@ void rt_hw_systick_isr(void) void rt_hw_system_timer_init(void) { // initial system timer interrupt, map local timer interrupt to INT14 - gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN<INTMUX3 = (CSL_GEM_TINTLN << CSL_CGEM_INTMUX3_INTSEL14_SHIFT); // enable CPU INT14 - CPU_interrupt_enable(1<<14); + CPU_interrupt_enable(1 << 14); return ; } @@ -52,12 +52,12 @@ void rt_hw_system_timer_start(void) Timer64_Config tmrCfg; // select output on TIMO0 from local timer. - gpBootCfgRegs->TOUTSEL = (DNUM*2)<TOUTSEL = (DNUM*2) << CSL_BOOTCFG_TOUTSEL_TOUTSEL0_SHIFT; // configure the timer to generate clocks and interrupts tmrCfg.timer_num = DNUM; tmrCfg.timerMode = TIMER_PERIODIC_CLOCK; - tmrCfg.period = (unsigned long long) RT_TICK_PER_SECOND*gDSP_Core_Speed_Hz/6000; + tmrCfg.period = (unsigned long long) RT_TICK_PER_SECOND * gDSP_Core_Speed_Hz / 6000; tmrCfg.reload_period = 0; // initial timer diff --git a/libcpu/ti-dsp/c6x/trap.c b/libcpu/ti-dsp/c6x/trap.c index c7030c9bec..634e486396 100644 --- a/libcpu/ti-dsp/c6x/trap.c +++ b/libcpu/ti-dsp/c6x/trap.c @@ -106,7 +106,6 @@ void show_regs(struct rt_hw_exp_stack_register *regs) regs->hw_register.a31, regs->hw_register.b31); } - void do_trap(struct rt_exception_info *except_info, struct rt_hw_exp_stack_register *regs) { rt_kprintf("Enter exception: %s\n", except_info->kernel_str); @@ -148,7 +147,9 @@ static int process_iexcept(struct rt_hw_exp_stack_register *regs) if (*(unsigned int *)regs->pc == BKPT_OPCODE) { /* This is a breakpoint */ - struct rt_exception_info bkpt_exception = { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; + struct rt_exception_info bkpt_exception = \ + { " - undefined instruction",\ + ABORT_TYPE_UNDDEF, ABORT_BRKPT_ILL }; do_trap(&bkpt_exception, regs); iexcept_report &= ~(0xFF); set_iexcept(iexcept_report); @@ -299,7 +300,7 @@ static struct rt_exception_info except_table[128] = { */ static void process_except(struct rt_hw_exp_stack_register *regs) { - int except_num; + int except_num = 0; int bank = 0; int i = 0; -- cgit v1.3.1 From c69cdadd69bdc2733b2774997c62006eaad4cce6 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Thu, 18 Nov 2021 10:08:01 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libcpu/ti-dsp/c6x/interrupt.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c index 6479da02f2..1bfc19cbdd 100644 --- a/libcpu/ti-dsp/c6x/interrupt.c +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -45,9 +45,9 @@ void rt_hw_interrupt_init(void) void rt_hw_interrupt_mask(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) - { + { return; - } + } } /** @@ -57,9 +57,9 @@ void rt_hw_interrupt_mask(int vector) void rt_hw_interrupt_umask(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) - { + { return; - } + } } /** @@ -93,7 +93,7 @@ rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, void rt_hw_interrupt_clear(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) - { - return; - } + { + return; + } } -- cgit v1.3.1 From 4a779f5131dea2ebcf95cc275df3ab23850ac6c0 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Tue, 23 Nov 2021 16:28:44 +0800 Subject: 修改使用C语言构建任务栈帧,清除fls和ffs对文件的依赖 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libcpu/ti-dsp/c6x/c66xx.h | 18 +++++-- libcpu/ti-dsp/c6x/context.asm | 34 ++++++++++++ libcpu/ti-dsp/c6x/cpuport.c | 2 +- libcpu/ti-dsp/c6x/interrupt.c | 2 +- libcpu/ti-dsp/c6x/intexc.asm | 4 +- libcpu/ti-dsp/c6x/stack.asm | 107 ------------------------------------- libcpu/ti-dsp/c6x/stack.c | 120 ++++++++++++++++++++++++++++++++++++++++++ libcpu/ti-dsp/c6x/trap.c | 27 +++++----- libcpu/ti-dsp/c6x/trap.h | 47 +++++++++++++++-- 9 files changed, 228 insertions(+), 133 deletions(-) delete mode 100644 libcpu/ti-dsp/c6x/stack.asm create mode 100644 libcpu/ti-dsp/c6x/stack.c diff --git a/libcpu/ti-dsp/c6x/c66xx.h b/libcpu/ti-dsp/c6x/c66xx.h index ea204907d8..903edbfaf1 100644 --- a/libcpu/ti-dsp/c6x/c66xx.h +++ b/libcpu/ti-dsp/c6x/c66xx.h @@ -11,7 +11,15 @@ #ifndef __C66XX_H__ #define __C66XX_H__ -#include +extern cregister volatile unsigned int IERR; /* Internal Exception Report Register */ +extern cregister volatile unsigned int ECR; /* Exception Clear Register */ +extern cregister volatile unsigned int EFR; /* Exception Flag Register */ +extern cregister volatile unsigned int TSR; /* Task State Register */ +extern cregister volatile unsigned int ITSR; /* Interrupt Task State Register */ +extern cregister volatile unsigned int NTSR; /* NMI/exception Task State Register */ +extern cregister volatile unsigned int TSCL; /* Time Stamp Counter Register - Low Half */ +extern cregister volatile unsigned int TSCH; /* Time Stamp Counter Register - High Half */ +extern cregister volatile unsigned int DNUM; /* Core number */ #ifdef _BIG_ENDIAN #define RT_REG_PAIR(odd, even) unsigned long odd; unsigned long even @@ -37,7 +45,7 @@ struct rt_hw_register RT_REG_PAIR(b9, b8); RT_REG_PAIR(b11, b10); RT_REG_PAIR(b13, b12); - + RT_REG_PAIR(a17, a16); RT_REG_PAIR(a19, a18); RT_REG_PAIR(a21, a20); @@ -58,14 +66,14 @@ struct rt_hw_register RT_REG_PAIR(a15, a14); RT_REG_PAIR(sp, dp); }; - -struct rt_hw_exp_stack_register + +typedef struct rt_hw_exp_stack_register { RT_REG_PAIR(tsr, orig_a4); RT_REG_PAIR(rilc, ilc); RT_REG_PAIR(pc, csr); struct rt_hw_register hw_register; -}; +} rt_hw_thread_stack_register; #define __dint() asm(" DINT") #define __rint() asm(" RINT") diff --git a/libcpu/ti-dsp/c6x/context.asm b/libcpu/ti-dsp/c6x/context.asm index b3146d1eb3..2a57e9414d 100644 --- a/libcpu/ti-dsp/c6x/context.asm +++ b/libcpu/ti-dsp/c6x/context.asm @@ -79,6 +79,40 @@ rt_hw_interrupt_enable: NOP 5 ;} +;----------------------------------------------------------- +; rt_uint32_t rt_hw_get_current_dp(void) +;----------------------------------------------------------- + .global rt_hw_get_current_dp +rt_hw_get_current_dp: +;{ + B B3 + MV B14, A4 + NOP 4 +;} + +;----------------------------------------------------------- +; rt_int32_t __fls(rt_int32_t val) +;----------------------------------------------------------- + .global __fls +__fls: +;{ + B B3 + LMBD .L1 1,A4,A4 + NOP 4 +;} + +;----------------------------------------------------------- +; rt_int32_t __ffs(rt_int32_t val) +;----------------------------------------------------------- + .global __ffs +__ffs: +;{ + BITR .M1 A4,A4 + B B3 + LMBD .L1 1,A4,A4 + NOP 4 +;} + ; ;----------------------------------------------------------- ; diff --git a/libcpu/ti-dsp/c6x/cpuport.c b/libcpu/ti-dsp/c6x/cpuport.c index 367b884a60..3f755a5c7c 100644 --- a/libcpu/ti-dsp/c6x/cpuport.c +++ b/libcpu/ti-dsp/c6x/cpuport.c @@ -158,7 +158,7 @@ void hw_int11_handler(void) -----------------------------------------------------------------------------*/ void hw_int12_handler(void) { - + } /*------------ hw_int13_handler() function ------------------------------------ diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c index 1bfc19cbdd..2be2f88313 100644 --- a/libcpu/ti-dsp/c6x/interrupt.c +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -94,6 +94,6 @@ void rt_hw_interrupt_clear(int vector) { if (vector < 0 || vector >= MAX_HANDLERS) { - return; + return; } } diff --git a/libcpu/ti-dsp/c6x/intexc.asm b/libcpu/ti-dsp/c6x/intexc.asm index 4485c6579c..2490977331 100644 --- a/libcpu/ti-dsp/c6x/intexc.asm +++ b/libcpu/ti-dsp/c6x/intexc.asm @@ -81,7 +81,9 @@ RT_INTERRUPT_ENTRY .macro .endm RT_CALL_INT .macro __isr - CALLP __isr,B3 + B __isr + ADDKPC $1 ,B3,4 +$1: B .S1 rt_interrupt_context_restore NOP 5 .endm diff --git a/libcpu/ti-dsp/c6x/stack.asm b/libcpu/ti-dsp/c6x/stack.asm deleted file mode 100644 index f9b31dec93..0000000000 --- a/libcpu/ti-dsp/c6x/stack.asm +++ /dev/null @@ -1,107 +0,0 @@ -; -; Copyright (c) 2021, Shenzhen Academy of Aerospace Technology -; -; SPDX-License-Identifier: Apache-2.0 -; -; Change Logs: -; Date Author Notes -; 2021-11-16 Dystopia the first version -; - -;----------------------------------------------------------- -; build thread stack for C6000 DSP -;----------------------------------------------------------- - -;----------------------------------------------------------- -; macro definition -;----------------------------------------------------------- -ADDRESS_MSK .set 0xFFFFFFF0 - -; -;----------------------------------------------------------- -; - - .sect ".text" -; -;----------------------------------------------------------- -; - -; -; rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, rt_uint8_t *stack_addr, void *texit) -; tentry --> A4 -; parameter --> B4 -; stack_addr --> A6 -; texit --> B6 -;{ - .global rt_hw_stack_init -rt_hw_stack_init: - SUB A6,1,B1 ; - MVKL .S1 ADDRESS_MSK,A1 ; - MVKH .S1 ADDRESS_MSK,A1 ; Build address mask - MVC .S2 CSR,B0 ; - AND -2,B0,B0 ; Clear GIE bit - OR 2,B0,B0 ; Set PGIE bit for interrupt return - AND A1,B1,B1 ; Ensure alignment -; -; Actually build the stack frame. -; - MV .S1 B1,A3 - MV .S1 B14,A2 - STDW .D2T1 A3:A2,*--B1[1] ; Initial B15:B14 - SUBAW .D2 B1,2,B1 - ZERO A2 - ZERO A3 ; Clear value - STDW .D2T1 A3:A2,*B1--[1] ; Initial A15:A14 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A13:A12 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A11:A10 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A9:A8 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A7:A6 - MV .S1 B4,A2 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A5:A4 - ZERO A2 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A3:A2 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A1:A0 - - STDW .D2T1 A3:A2,*B1--[1] ; Initial A31:A30 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A29:A28 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A27:A26 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A25:A24 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A23:A22 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A21:A20 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A19:A18 - STDW .D2T1 A3:A2,*B1--[1] ; Initial A17:A16 - - STDW .D2T1 A3:A2,*B1--[1] ; Initial B13:B12 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B11:B10 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B9:B8 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B7:B6 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B5:B4 - MV .S1 B6,A3 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B3:B2 - ZERO A3 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B1:B0 - - STDW .D2T1 A3:A2,*B1--[1] ; Initial B31:B30 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B29:B28 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B27:B26 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B25:B24 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B23:B22 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B21:B20 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B19:B18 - STDW .D2T1 A3:A2,*B1--[1] ; Initial B17:B16 - - MV .S1 A4,A3 - MV .S1 B0,A2 - STDW .D2T1 A3:A2,*B1--[1] ; Initial PC:CSR - - ZERO A2 - ZERO A3 - STDW .D2T1 A3:A2,*B1--[1] ; Initial ILC:RILC - B B3 - MVKL .S2 0x3,B0 - MV .S1 B0,A3 - MVKL .S1 1,A2 - STDW .D2T1 A3:A2,*B1--[1] ; Initial TSR:stack type - MV .S1 B1,A4 ; Save to TCB -;} - .end diff --git a/libcpu/ti-dsp/c6x/stack.c b/libcpu/ti-dsp/c6x/stack.c new file mode 100644 index 0000000000..3fe3377a1c --- /dev/null +++ b/libcpu/ti-dsp/c6x/stack.c @@ -0,0 +1,120 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include +#include + +extern rt_uint32_t rt_hw_get_current_dp(void); + +/** + * @addtogroup C66xx + */ +/*@{*/ + +/** + * This function will initialize thread stack + * + * @param tentry the entry of thread + * @param parameter the parameter of entry + * @param stack_addr the beginning stack address + * @param texit the function will be called when thread exit + * + * @return stack address + */ +rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, + rt_uint8_t *stack_addr, void *texit) +{ + rt_hw_thread_stack_register *thread_context; + rt_uint32_t stk; + + stack_addr += sizeof(rt_uint32_t); + stack_addr = (rt_uint8_t *)RT_ALIGN_DOWN((rt_uint32_t)stack_addr, 8); + stk = (rt_uint32_t)stack_addr; + thread_context = (rt_hw_thread_stack_register *)(stk - sizeof(rt_hw_thread_stack_register)); + + thread_context->pc = (rt_uint32_t)tentry; + thread_context->csr = 0x0103; + thread_context->tsr = 0x3; + thread_context->orig_a4 = 1; + thread_context->ilc = 0; + thread_context->rilc = 0; + + thread_context->hw_register.b17 = 0xB17; + thread_context->hw_register.b16 = 0xB16; + thread_context->hw_register.b19 = 0xB19; + thread_context->hw_register.b18 = 0xB18; + thread_context->hw_register.b21 = 0xB21; + thread_context->hw_register.b20 = 0xB20; + thread_context->hw_register.b23 = 0xB23; + thread_context->hw_register.b22 = 0xB22; + thread_context->hw_register.b25 = 0xB25; + thread_context->hw_register.b24 = 0xB24; + thread_context->hw_register.b27 = 0xB27; + thread_context->hw_register.b26 = 0xB26; + thread_context->hw_register.b29 = 0xB29; + thread_context->hw_register.b28 = 0xB28; + thread_context->hw_register.b31 = 0xB31; + thread_context->hw_register.b30 = 0xB30; + + thread_context->hw_register.b1 = 0xB01; + thread_context->hw_register.b0 = 0xB00; + thread_context->hw_register.b3 = (rt_uint32_t)texit; + thread_context->hw_register.b2 = 0xB02; + thread_context->hw_register.b5 = 0xB05; + thread_context->hw_register.b4 = 0xB04; + thread_context->hw_register.b7 = 0xB07; + thread_context->hw_register.b6 = 0xB06; + thread_context->hw_register.b9 = 0xB09; + thread_context->hw_register.b8 = 0xB08; + thread_context->hw_register.b11 = 0xB11; + thread_context->hw_register.b10 = 0xB10; + thread_context->hw_register.b13 = 0xB13; + thread_context->hw_register.b12 = 0xB12; + + thread_context->hw_register.a17 = 0xA17; + thread_context->hw_register.a16 = 0xA16; + thread_context->hw_register.a19 = 0xA19; + thread_context->hw_register.a18 = 0xA18; + thread_context->hw_register.a21 = 0xA21; + thread_context->hw_register.a20 = 0xA20; + thread_context->hw_register.a23 = 0xA23; + thread_context->hw_register.a22 = 0xA22; + thread_context->hw_register.a25 = 0xA25; + thread_context->hw_register.a24 = 0xA24; + thread_context->hw_register.a27 = 0xA27; + thread_context->hw_register.a26 = 0xA26; + thread_context->hw_register.a29 = 0xA29; + thread_context->hw_register.a28 = 0xA28; + thread_context->hw_register.a31 = 0xA31; + thread_context->hw_register.a30 = 0xA30; + + thread_context->hw_register.a1 = 0xA01; + thread_context->hw_register.a0 = 0xA00; + thread_context->hw_register.a3 = 0xA03; + thread_context->hw_register.a2 = 0xA02; + thread_context->hw_register.a5 = 0xA05; + thread_context->hw_register.a4 = (rt_uint32_t)parameter; + thread_context->hw_register.a7 = 0xA07; + thread_context->hw_register.a6 = 0xA06; + thread_context->hw_register.a9 = 0xA09; + thread_context->hw_register.a8 = 0xA08; + thread_context->hw_register.a11 = 0xA11; + thread_context->hw_register.a10 = 0xA10; + thread_context->hw_register.a13 = 0xA13; + thread_context->hw_register.a12 = 0xA12; + + thread_context->hw_register.a15 = 0xA15; + thread_context->hw_register.a14 = 0xA14; + thread_context->hw_register.dp = rt_hw_get_current_dp(); + thread_context->hw_register.sp = (rt_uint32_t)stk; + + /* return task's current stack address */ + return (rt_uint8_t *)thread_context - 8; +} diff --git a/libcpu/ti-dsp/c6x/trap.c b/libcpu/ti-dsp/c6x/trap.c index 634e486396..9f8f80d5ed 100644 --- a/libcpu/ti-dsp/c6x/trap.c +++ b/libcpu/ti-dsp/c6x/trap.c @@ -17,7 +17,6 @@ #define RT_SYS_STACK_SIZE 4096 -extern void rt_hw_enable_exception(void); rt_uint8_t rt_system_stack[RT_SYS_STACK_SIZE]; rt_uint8_t *rt_system_stack_top; @@ -117,14 +116,14 @@ void do_trap(struct rt_exception_info *except_info, struct rt_hw_exp_stack_regis static struct rt_exception_info iexcept_table[10] = { { " - instruction fetch", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - fetch packet", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, - { " - execute packet", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, + { " - fetch packet", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, + { " - execute packet", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, { " - undefined instruction", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, { " - resource conflict", ABORT_TYPE_UNDDEF, ABORT_OPCODE_ILL }, - { " - resource access", ABORT_TYPE_UNDDEF, ABORT_PRVREG_ILL }, + { " - resource access", ABORT_TYPE_UNDDEF, ABORT_PRVREG_ILL }, { " - privilege", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, - { " - loops buffer", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, - { " - software exception", ABORT_TYPE_UNDDEF, ABORT_ILLTRP_ILL }, + { " - loops buffer", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL }, + { " - software exception", ABORT_TYPE_UNDDEF, ABORT_ILLTRP_ILL }, { " - unknown exception", ABORT_TYPE_UNDDEF, ABORT_PRVOPC_ILL } }; @@ -140,7 +139,7 @@ static int process_iexcept(struct rt_hw_exp_stack_register *regs) while(iexcept_report) { - iexcept_num = __ffs(iexcept_report); + iexcept_num = ffs(iexcept_report); iexcept_report &= ~(1 << iexcept_num); set_iexcept(iexcept_report); @@ -160,7 +159,7 @@ static int process_iexcept(struct rt_hw_exp_stack_register *regs) return 0; } -static struct rt_exception_info except_table[128] = { +static struct rt_exception_info eexcept_table[128] = { { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, { " - external exception", ABORT_TYPE_BUS, ABORT_BUS_ADDRERR }, @@ -298,7 +297,7 @@ static struct rt_exception_info except_table[128] = { /* * Process an external exception (maskable) */ -static void process_except(struct rt_hw_exp_stack_register *regs) +static void process_eexcept(struct rt_hw_exp_stack_register *regs) { int except_num = 0; int bank = 0; @@ -309,10 +308,10 @@ static void process_except(struct rt_hw_exp_stack_register *regs) while (INTC_MEXPMASK[i]) { __dint(); - except_num = __ffs(INTC_MEXPMASK[i]); + except_num = ffs(INTC_MEXPMASK[i]); INTC_MEXPMASK[i] &= ~(1 << except_num); /* ack the external exception */ __rint(); - do_trap(&except_table[except_num + (bank << 5)], regs); + do_trap(&eexcept_table[except_num + (bank << 5)], regs); } bank++; } @@ -331,11 +330,11 @@ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) int ie_num = 9; /* default is unknown exception */ while ((type = get_except_type()) != 0) { - type_num = __fls(type) - 1; + type_num = fls(type) - 1; switch(type_num) { case EXCEPT_TYPE_NXF: /* NMI exception */ - ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ + ack_exception(EXCEPT_TYPE_NXF); /* clear exception */ if (hw_nmi_handler != RT_NULL) { hw_nmi_handler(regs); @@ -350,7 +349,7 @@ int rt_hw_process_exception(struct rt_hw_exp_stack_register *regs) break; case EXCEPT_TYPE_EXC: /* external exception */ - process_except(regs); + process_eexcept(regs); break; case EXCEPT_TYPE_SXF: /* software exception */ diff --git a/libcpu/ti-dsp/c6x/trap.h b/libcpu/ti-dsp/c6x/trap.h index 9c8f52dd14..12734df4a7 100644 --- a/libcpu/ti-dsp/c6x/trap.h +++ b/libcpu/ti-dsp/c6x/trap.h @@ -67,10 +67,49 @@ struct rt_exception_info { #define BKPT_OPCODE 0x56454314 /* illegal opcode */ #define INTC_MEXPMASK __SYSREGA(0x018000e0, unsigned int) -#define __ffs(a) (_lmbd(1, _bitr(a))) -#define __fls(a) (!(a) ? 0 : (32 - _lmbd(1, (a)))) - extern void rt_trap_init(void); +extern void rt_hw_enable_exception(void); +extern int __fls(int val); +extern int __ffs(int val); -#endif /* __TRAP_H__ */ +/* + * ffz - find first zero in word. + * @word: The word to search + * + * Undefined if no zero exists, so code should check against ~0UL first. + */ +#define ffz(x) __ffs(~(x)) + +/** + * fls - find last (most-significant) bit set + * @x: the word to search + * + * This is defined the same way as ffs. + * Note fls(0) = 0, fls(1) = 1, fls(0x80000000) = 32. + */ +static inline int fls(int x) +{ + if (!x) + return 0; + + return 32 - __fls(x); +} + +/** + * ffs - find first bit set + * @x: the word to search + * + * This is defined the same way as + * the libc and compiler builtin ffs routines, therefore + * differs in spirit from the above ffz (man ffs). + * Note ffs(0) = 0, ffs(1) = 1, ffs(0x80000000) = 32. + */ +static inline int ffs(int x) +{ + if (!x) + return 0; + return __ffs(x) + 1; +} + +#endif /* __TRAP_H__ */ -- cgit v1.3.1 From c37fcb6049de1ba0c39265a261cc07fad78e6cf6 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 15 Dec 2021 09:17:25 +0800 Subject: 修改bsp tms320c6678工程,并测试 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/.cproject | 142 +- bsp/ti-tms320c6678/.project | 66 +- .../.settings/org.eclipse.core.resources.prefs | 10 - bsp/ti-tms320c6678/applications/main.c | 1 - bsp/ti-tms320c6678/common/KeyStone_common.c | 4355 ++++++++++++++++++++ bsp/ti-tms320c6678/common/KeyStone_common.h | 1090 +++++ bsp/ti-tms320c6678/readme.txt | 7 +- libcpu/ti-dsp/c6x/context.asm | 9 +- libcpu/ti-dsp/c6x/contextinc.asm | 5 + libcpu/ti-dsp/c6x/interrupt.c | 2 +- libcpu/ti-dsp/c6x/intexc.asm | 8 - libcpu/ti-dsp/c6x/stack.c | 4 +- libcpu/ti-dsp/c6x/trap.h | 6 +- 13 files changed, 5565 insertions(+), 140 deletions(-) delete mode 100644 bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs create mode 100644 bsp/ti-tms320c6678/common/KeyStone_common.c create mode 100644 bsp/ti-tms320c6678/common/KeyStone_common.h diff --git a/bsp/ti-tms320c6678/.cproject b/bsp/ti-tms320c6678/.cproject index aef3a8c240..0c4124a28d 100644 --- a/bsp/ti-tms320c6678/.cproject +++ b/bsp/ti-tms320c6678/.cproject @@ -3,8 +3,8 @@ - - + + @@ -14,10 +14,10 @@ - - - - - - + + @@ -89,10 +87,10 @@ - - - - - + diff --git a/bsp/ti-tms320c6678/.project b/bsp/ti-tms320c6678/.project index d1c8afd3a3..a0c5dddf40 100644 --- a/bsp/ti-tms320c6678/.project +++ b/bsp/ti-tms320c6678/.project @@ -1,6 +1,6 @@ - ti-c6678 + ti-tms320c6678 @@ -25,130 +25,130 @@ org.eclipse.cdt.managedbuilder.core.ScannerConfigNature - - SConscript - 1 - PARENT-2-PROJECT_LOC/src/SConscript - clock.c 1 - PARENT-2-PROJECT_LOC/src/clock.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/clock.c components.c 1 - PARENT-2-PROJECT_LOC/src/components.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/components.c context.asm 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/context.asm + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/context.asm + + + contextinc.asm + 1 + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/contextinc.asm cpu.c 1 - PARENT-2-PROJECT_LOC/src/cpu.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/cpu.c cpuport.c 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/cpuport.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/cpuport.c device.c 1 - PARENT-2-PROJECT_LOC/src/device.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/device.c idle.c 1 - PARENT-2-PROJECT_LOC/src/idle.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/idle.c - inct.asm + interrupt.c 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/inct.asm + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/interrupt.c - interrupt.c + intexc.asm 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/interrupt.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/intexc.asm ipc.c 1 - PARENT-2-PROJECT_LOC/src/ipc.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/ipc.c irq.c 1 - PARENT-2-PROJECT_LOC/src/irq.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/irq.c kservice.c 1 - PARENT-2-PROJECT_LOC/src/kservice.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/kservice.c mem.c 1 - PARENT-2-PROJECT_LOC/src/mem.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/mem.c memheap.c 1 - PARENT-2-PROJECT_LOC/src/memheap.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/memheap.c mempool.c 1 - PARENT-2-PROJECT_LOC/src/mempool.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/mempool.c object.c 1 - PARENT-2-PROJECT_LOC/src/object.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/object.c scheduler.c 1 - PARENT-2-PROJECT_LOC/src/scheduler.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/scheduler.c signal.c 1 - PARENT-2-PROJECT_LOC/src/signal.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/signal.c slab.c 1 - PARENT-2-PROJECT_LOC/src/slab.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/slab.c - stack.asm + stack.c 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/stack.asm + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/stack.c thread.c 1 - PARENT-2-PROJECT_LOC/src/thread.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/thread.c timer.c 1 - PARENT-2-PROJECT_LOC/src/timer.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/src/timer.c trap.c 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/trap.c + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/trap.c vector.asm 1 - PARENT-2-PROJECT_LOC/libcpu/ti-dsp/c6x/vector.asm + PARENT-2-PROJECT_LOC/git-source/rt-thread/libcpu/ti-dsp/c6x/vector.asm diff --git a/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs b/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs deleted file mode 100644 index 83b10321a8..0000000000 --- a/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs +++ /dev/null @@ -1,10 +0,0 @@ -eclipse.preferences.version=1 -encoding//Debug/applications/subdir_rules.mk=UTF-8 -encoding//Debug/applications/subdir_vars.mk=UTF-8 -encoding//Debug/driver/subdir_rules.mk=UTF-8 -encoding//Debug/driver/subdir_vars.mk=UTF-8 -encoding//Debug/makefile=UTF-8 -encoding//Debug/objects.mk=UTF-8 -encoding//Debug/sources.mk=UTF-8 -encoding//Debug/subdir_rules.mk=UTF-8 -encoding//Debug/subdir_vars.mk=UTF-8 diff --git a/bsp/ti-tms320c6678/applications/main.c b/bsp/ti-tms320c6678/applications/main.c index d29fd00a4f..aab374fa63 100644 --- a/bsp/ti-tms320c6678/applications/main.c +++ b/bsp/ti-tms320c6678/applications/main.c @@ -16,7 +16,6 @@ void rt_init_thread_entry(void *parameter) { rt_kprintf("hello rt-thread\n"); - return 0; } int rt_application_init(void) diff --git a/bsp/ti-tms320c6678/common/KeyStone_common.c b/bsp/ti-tms320c6678/common/KeyStone_common.c new file mode 100644 index 0000000000..bfa6fbac3c --- /dev/null +++ b/bsp/ti-tms320c6678/common/KeyStone_common.c @@ -0,0 +1,4355 @@ +/****************************************************************************** + + Copyright (C), 2001-2012, Texas Instrument. + + ****************************************************************************** + File Name : KeyStone_common.c + Version : Initial Draft + Author : Brighton Feng + Created : 2010-12-12 + Last Modified : + Description : KeyStone common miscellaneous functions and definitions + History : + 1.Date : 2010-12-12 + Author : Brighton Feng + Modification: Created file + + 2.Date : 2012-10-6 + Author : Brighton Feng + Modification : Add memory protection and EDC configuration + + 3.Date : 2014-12-8 + Author : Brighton Feng + Modification : Add common device, CPU, interrupt initialization functions. + Print device information including device type, speed grade, + boot mode, required voltage, ID�� + Add EDMA enable/disable functions. + To support square wave generation by timer. +******************************************************************************/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include "CSL_msmc.h" +#include "CSL_msmcAux.h" +#include "KeyStone_common.h" + +/*----------------------------------------------* + * external variables * + *----------------------------------------------*/ + +/*----------------------------------------------* + * external routine prototypes * + *----------------------------------------------*/ + +/*----------------------------------------------* + * internal routine prototypes * + *----------------------------------------------*/ + +/*----------------------------------------------* + * project-wide global variables * + *----------------------------------------------*/ +CSL_XmcRegs * gpXMC_regs = (CSL_XmcRegs *) CSL_XMC_CONFIG_REGS; +CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; +CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; +CSL_PllcRegs * gpPLLC_regs = (CSL_PllcRegs * )CSL_PLL_CONTROLLER_REGS; +CSL_PscRegs * gpPSC_regs = (CSL_PscRegs *)CSL_PSC_REGS; +CSL_MsmcRegs * gpMSMC_regs = (CSL_MsmcRegs *)CSL_MSMC_CONFIG_REGS; +CSL_GpioRegs * gpGPIO_regs= (CSL_GpioRegs * )CSL_GPIO_REGS; + +CSL_CPINTCRegs* gpCIC0_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; +CSL_CPINTCRegs* gpCIC1_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_1_REGS; +/*The register pointer for the CIC routing events DSP core. +By default, it is CIC0; but for core 4~7 of C6678, it is CIC1*/ +CSL_CPINTCRegs* gpCIC_regs= (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; + +CSL_TpccRegs* gpEDMA_CC0_regs = (CSL_TpccRegs*)CSL_EDMA0CC_REGS; +CSL_TpccRegs* gpEDMA_CC1_regs = (CSL_TpccRegs*)CSL_EDMA1CC_REGS; +CSL_TpccRegs* gpEDMA_CC2_regs = (CSL_TpccRegs*)CSL_EDMA2CC_REGS; +CSL_TpccRegs* gpEDMA_CC_regs[3] = { + (CSL_TpccRegs*)CSL_EDMA0CC_REGS, + (CSL_TpccRegs*)CSL_EDMA1CC_REGS, + (CSL_TpccRegs*)CSL_EDMA2CC_REGS +}; + +CSL_TptcRegs * gpEDMA_TC_0_0_regs=(CSL_TptcRegs *) CSL_EDMA0TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_0_1_regs=(CSL_TptcRegs *) CSL_EDMA0TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_1_0_regs=(CSL_TptcRegs *) CSL_EDMA1TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_1_1_regs=(CSL_TptcRegs *) CSL_EDMA1TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_1_2_regs=(CSL_TptcRegs *) CSL_EDMA1TC2_REGS; +CSL_TptcRegs * gpEDMA_TC_1_3_regs=(CSL_TptcRegs *) CSL_EDMA1TC3_REGS; +CSL_TptcRegs * gpEDMA_TC_2_0_regs=(CSL_TptcRegs *) CSL_EDMA2TC0_REGS; +CSL_TptcRegs * gpEDMA_TC_2_1_regs=(CSL_TptcRegs *) CSL_EDMA2TC1_REGS; +CSL_TptcRegs * gpEDMA_TC_2_2_regs=(CSL_TptcRegs *) CSL_EDMA2TC2_REGS; +CSL_TptcRegs * gpEDMA_TC_2_3_regs=(CSL_TptcRegs *) CSL_EDMA2TC3_REGS; + +CSL_TptcRegs * gpEDMA_TC_regs[10]= { + (CSL_TptcRegs *) CSL_EDMA0TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA0TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC2_REGS, + (CSL_TptcRegs *) CSL_EDMA1TC3_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC0_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC1_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC2_REGS, + (CSL_TptcRegs *) CSL_EDMA2TC3_REGS +}; + +CSL_TmrPlusRegs * gpTimer0Regs = (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS; +CSL_TmrPlusRegs * gpTimer1Regs = (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS; +CSL_TmrPlusRegs * gpTimer2Regs = (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS; +CSL_TmrPlusRegs * gpTimer3Regs = (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS; +CSL_TmrPlusRegs * gpTimer4Regs = (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS; +CSL_TmrPlusRegs * gpTimer5Regs = (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS; +CSL_TmrPlusRegs * gpTimer6Regs = (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS; +CSL_TmrPlusRegs * gpTimer7Regs = (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS; +CSL_TmrPlusRegs * gpTimer8Regs = (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)); +CSL_TmrPlusRegs * gpTimerRegs[9] = { + (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS, + (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)) +}; + +/*MPU for peripherals registers and data space*/ +CSL_MpuRegs * gpMPU0_regs= (CSL_MpuRegs *)CSL_MPU_0_REGS; +CSL_MpuRegs * gpMPU1_regs= (CSL_MpuRegs *)CSL_MPU_1_REGS; +CSL_MpuRegs * gpMPU2_regs= (CSL_MpuRegs *)CSL_MPU_2_REGS; +CSL_MpuRegs * gpMPU3_regs= (CSL_MpuRegs *)CSL_MPU_3_REGS; + +CSL_Emif4fRegs * gpDDR_regs= (CSL_Emif4fRegs *)CSL_DDR3_EMIF_CONFIG_REGS; +unsigned int gDSP_Core_Speed_Hz= 1000000000; //DSP core clock speed in Hz +TDSP_Board_Type gDSP_board_type= UNKNOWN; + +/*----------------------------------------------* + * module-wide global variables * + *----------------------------------------------*/ + +/*----------------------------------------------* + * constants * + *----------------------------------------------*/ + +/*----------------------------------------------* + * macros * + *----------------------------------------------*/ + +/*----------------------------------------------* + * routines' implementations * + *----------------------------------------------*/ + +/***************************************************************************** + Prototype : KeyStone_main_PLL_init + Description : DSP core PLL configuration + DSP core will be configured to run at ref_clock_MHz*multiplier/divisor + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : + Return Value : + + History : + 1.Date : 2010-12-12 + Author : Brighton Feng + Modification : Created function + 2.Date : May 19, 2013 + Author : Brighton Feng + Modification : update parameter check; replace constant with macro + +*****************************************************************************/ +void KeyStone_main_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + unsigned int i; + + if(0==divisor) + { + puts("Error: PLL input divider = 0"); + return; + } + + if(64SECCTL & PLLCTL_BYPASS_MASK) + { + /*a. In MAINPLLCTL1, write ENSAT = 1 (for optimal PLL operation) */ + gpBootCfgRegs->CORE_PLL_CTL1 |= PLLCTL1_ENSAT_MASK; /*Set ENSAT bit = 1*/ + + /*b. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLEN_MASK; + + /*c. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLENSRC_MASK; + + /*d. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ + /*mux switches properly to the bypass) */ + for(i=0; i< 4; i++) + asm(" nop 5"); + + /*e. In SECCTL, write BYPASS = 1 (bypass enabled in PLL mux) */ + gpPLLC_regs->SECCTL |= PLLCTL_BYPASS_MASK; + + /*f. In PLLCTL, write PLLPWRDN = 1 (power down the PLL) */ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLPWRDN_MASK; //Power down the PLL + + /*g. Wait for at least 5 ��s based on the reference clock CLKIN (PLL power down */ + /*toggling time) */ + for(i=0; i< 1000; i++) + asm(" nop 5"); + + /*h. In PLLCTL, write PLLPWRDN = 0 (power up the PLL) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLPWRDN_MASK; // Power up PLL + } + else + { + /*a. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ + gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLEN_MASK); + + /*b. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ + gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLENSRC_MASK); + + /*c. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ + /*mux switches properly to the bypass) */ + for(i=0; i< 4*multiplier/divisor; i++) + asm(" nop 5"); + } + + /*4. PLLM is split in two different registers. Program PLLM[5:0] in PLL multiplier */ + /*control register (PLLM) and PLLM[12:6] in MAINPLLCTL0 register */ + /*5. BWADJ is split in two different registers. Program BWADJ[7:0] in */ + /*MAINPLLCTL0 and BWADJ[11:8] in MAINPLLCTL1 register. BWADJ value */ + /*must be set to ((PLLM + 1) >> 1) - 1) */ + /*6. Program PLLD in MAINPLLCTL0 register */ + gpBootCfgRegs->CORE_PLL_CTL0 = ((multiplier-1)<PLLM= (multiplier*2-1)&0x3F; + gpBootCfgRegs->CORE_PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; + gpBootCfgRegs->CORE_PLL_CTL1 |= (multiplier-1)>>8; /*BWADJ[11:8]*/ + + /*7. In SECCTL, write OD (Output Divide) = 1 (that is divide-by-2) */ + gpPLLC_regs->SECCTL &= ~PLLCTL_OD_MASK; + gpPLLC_regs->SECCTL |= 1<PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); + + /* Step 8b: Program the RATIO field in PLLDIVn to the desired new divide-down rate. + If RATIO field is changed, the PLL controller will flag the change in the + corresponding bit of DCHANGE*/ + gpPLLC_regs->PLLDIV1_3[3-1] = (3-1) | CSL_PLLC_PLLDIV1_3_DNEN_MASK; //Set PLLDIV3 + gpPLLC_regs->PLLDIV4_16[4-4] = (5-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV4 + gpPLLC_regs->PLLDIV4_16[7-4] = (6-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV7 + + /* Step 8c: Set GOSET bit in PLLCMD to initiate the GO operation to change the divide + values and align the SYSCLKs as programmed */ + gpPLLC_regs->PLLCMD |= CSL_PLLC_PLLCMD_GOSET_MASK; + + /*Step 8d/e: Read the GOSTAT bit in PLLSTAT to make sure the bit returns to 0 to + indicate that the GO operation has completed */ + while((gpPLLC_regs->PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); +#endif + + /*9. In PLLCTL , write PLLRST = 1 (PLL reset is asserted)*/ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLRST_MASK; + + /*10. Wait for at least 7 ��s based on the reference clock CLKIN (PLL reset time) */ + for(i=0; i< 2000; i++) + asm(" nop 5"); + + /*11. In PLLCTL, write PLLRST = 0 (PLL reset is released) */ + gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLRST_MASK; + + /*12. Wait for at least 2000 �� CLKIN cycles �� (PLLD + 1) (PLL lock time) */ + for(i=0; i< 400*multiplier; i++) + asm(" nop 5"); + + /*13. In SECCTL, write BYPASS = 0 (enable PLL mux to switch to PLL mode) */ + gpPLLC_regs->SECCTL &= ~PLLCTL_BYPASS_MASK; + + /*14. Set the PLLEN bit in PLLCTL to 1 to enable PLL mode*/ + gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLEN_MASK; + +} +/***************************************************************************** + Prototype : KeyStone_PLL_init + Description : Config the PLL of PA and DDR + target clock speed will be ref_clock_MHz/inputDivisor*multiplier/outputDivisor + Input : unsigned int inputDivisor + unsigned int multiplier + unsigned int outputDivisor + Output : None + Return Value : 0 for success, other value for error + + History : + 1.Date : May 18, 2013 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +int KeyStone_PLL_init (PLL_ControlRegs * PLL_Regs, unsigned int inputDivisor, + unsigned int multiplier, unsigned int outputDivisor) +{ + if(0==inputDivisor) + { + puts("Error: PLL input divider = 0"); + return 1; + } + + if(64PLL_CTL1 = PLLCTL1_ENSAT_MASK; + + /*2. In PLLCTL0, write BYPASS = 1 (set the PLL in Bypass)*/ + PLL_Regs->PLL_CTL0 |= PLLCTL_BYPASS_MASK; + + /*3. Program PLLM and PLLD in PLLCTL0 register*/ + /*4. Program BWADJ[7:0] in PLLCTL0 and BWADJ[11:8] in PLLCTL1 register. + BWADJ value must be set to ((PLLM + 1) >> 1) �C 1)*/ + PLL_Regs->PLL_CTL0 = ((multiplier/2-1)<PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; + PLL_Regs->PLL_CTL1 |= (multiplier/2-1)>>8; /*BWADJ[11:8]*/ + + /*5. In PLLCTL1, write PLLRST = 1 (PLL is reset)*/ + PLL_Regs->PLL_CTL1 |= PLLCTL1_PLLRESET_MASK; //Set RESET bit = 1 + + /*6. Wait for at least 7 us based on the reference clock (PLL reset time)*/ + TSC_delay_us(7); + + /*For PASS, In PASSPLLCTL1, write PLLSELECT = 1 + (for selecting the output of PA PLL as the input to PASS)*/ + if(PLL_Regs==(PLL_ControlRegs *)gpBootCfgRegs->PA_PLL_CTL0) + PLL_Regs->PLL_CTL1 |= PLLCTL1_PAPLL_MASK; + + /*7. In PLLCTL1, write PLLRST = 0 (PLL reset is released)*/ + PLL_Regs->PLL_CTL1 &= ~PLLCTL1_PLLRESET_MASK; //Clear RESET bit + + /*8. Wait for at least 500 * REFCLK cycles * (PLLD + 1) (PLL lock time)*/ + TSC_delay_us(500); + + /*9. In PLLCTL0, write BYPASS = 0 (switch to PLL mode)*/ + PLL_Regs->PLL_CTL0 &= ~PLLCTL_BYPASS_MASK ; + + return 0; +} +/***************************************************************************** + Prototype : KeyStone_PASS_PLL_init + Description : Config the PASS PLL + target clock speed will be ref_clock_MHz/divisor*multiplier + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : None + Return Value : + + History : + 1.Date : 2013-2-14 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_PASS_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + //output divisor for PASS PLL should be 2 + if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->PA_PLL_CTL0, + divisor, multiplier*2, 2)) + { + printf("Initialize PASS PLL clock = %.2fMHz/%dx%d = %.3fMHz\n", + ref_clock_MHz, divisor, multiplier, + ref_clock_MHz*multiplier/divisor); + } +} + +/***************************************************************************** + Prototype : KeyStone_DDR_PLL_init + Description : Config the DDR PLL + target clock speed will be ref_clock_MHz/divisor*multiplier + Input : float ref_clock_MHz + unsigned int multiplier: 1~4096 + unsigned int divisor: 1~64 + Output : None + Return Value : + + History : + 1.Date : 2013-8-18 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_DDR_PLL_init (float ref_clock_MHz, + unsigned int multiplier, unsigned int divisor) +{ + //output divisor for DDR PLL should be 2 + if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->DDR3_PLL_CTL0, + divisor, multiplier, 2)) + { + printf("Initialize DDR speed = %.2fMHzx/%dx%d = %.3fMTS\n", + ref_clock_MHz, divisor, multiplier, + ref_clock_MHz*multiplier/divisor); + } +} + +/*===============================TSC===================================*/ +unsigned int cycle_measure_overhead=50; +/***************************************************************************** + Prototype : calc_cycle_measure_overhead + Description : calclucate the cycles measurement overhead + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void calc_cycle_measure_overhead() +{ + unsigned int cycle_cold, cycle_warm; + cycle_cold= TSCL; + cycle_cold = TSC_getDelay(cycle_cold); + cycle_warm= TSCL; + cycle_warm = TSC_getDelay(cycle_warm); + cycle_measure_overhead = (cycle_cold + cycle_warm)/2; +} + +/***************************************************************************** + Prototype : TSC_init + Description : Initialize Time stamp counter to measure cycles + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void TSC_init() +{ + TSCL = 0; /* Enable the TSC */ + calc_cycle_measure_overhead(); +} + +/***************************************************************************** + Prototype : TSC_delay_ms + Description : Implement the delay function in millisecond + Input : Uint32 ms + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void TSC_delay_ms(Uint32 ms) +{ + volatile unsigned long long startTSC, currentTSC; + unsigned long long delay_cycles; + Uint32 tscl, tsch; + + tscl= TSCL; + tsch= TSCH; + startTSC= _itoll(tsch,tscl); + + delay_cycles= ((unsigned long long)ms*gDSP_Core_Speed_Hz/1000); + + do + { + tscl= TSCL; + tsch= TSCH; + currentTSC= _itoll(tsch,tscl); + } + while((currentTSC-startTSC)TGCR) + { + gpTimerRegs[timer_num]->TGCR= 0; + gpTimerRegs[timer_num]->TCR= 0; + } +} + + /***************************************************************************** + Prototype : Timer64_Init + Description : Initialize a 64-bit timer + Input : Timer64_Config * tmrCfg + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void Timer64_Init(Timer64_Config * tmrCfg) +{ + Reset_Timer(tmrCfg->timer_num); + + gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; + gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; + + /*please note, in clock mode, two timer periods generate a clock, + one timer period output high voltage level, the other timer period + output low voltage level, so, the timer period should be half to the + desired output clock period*/ + if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) + tmrCfg->period= tmrCfg->period/2; + + /*the value written into period register is the expected value minus one*/ + gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); + gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); + if(tmrCfg->reload_period>1) + { + gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); + gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); + } + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select watch-dog mode*/ + (CSL_TMR_TIMMODE_WDT<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK + /*for plus featuers, dual 32-bit unchained timer mode should be used*/ + |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; + } + else + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select 64-bit general timer mode*/ + (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& + ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + /*enable watchdog timer*/ + gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<WDTCR = + (CSL_TMR_WDTCR_WDKEY_CMD1<WDTCR = + (CSL_TMR_WDTCR_WDKEY_CMD2<0x3FFFFFFF) + { + printf("Enable power domain %d timeout!\n", pwrDmnNum); + return -2; + } + } + } + + /* Enable the clocks too*/ + CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_ENABLE); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Enable clock domain %d timeout!\n", moduleNum); + return -2; + } + } + + /* Return PSC status */ + if ((CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_ON) && + (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_ENABLE)) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } +} +/***************************************************************************** + Prototype : KeyStone_disable_PSC_module + Description : Disable the PSC module in KeyStone device + Input : Uint32 pwrDmnNum + Uint32 moduleNum + Output : None + Return Value : + + History : + 1.Date : 2010/2/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +Int32 KeyStone_disable_PSC_module (Uint32 pwrDmnNum, Uint32 moduleNum) +{ + Uint32 uiStartTSC= TSCL; + + /* disable the clocks*/ + CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_SWRSTDISABLE); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Disable clock domain %d timeout!\n", moduleNum); + return -2; + } + } + + /* Return PSC status */ + if (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_SWRSTDISABLE) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } + +} +/***************************************************************************** + Prototype : KeyStone_disable_PSC_Power_Domain + Description : Disable the PSC power domain + Input : Uint32 pwrDmnNum + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +Int32 KeyStone_disable_PSC_Power_Domain (Uint32 pwrDmnNum) +{ + Uint32 uiStartTSC= TSCL; + + /* Set Power domain to OFF */ + CSL_PSC_disablePowerDomain (pwrDmnNum); + + /* Start the state transition */ + CSL_PSC_startStateTransition (pwrDmnNum); + + /* Wait until the state transition process is completed. */ + while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) + { + if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) + { + printf("Disable power domain %d timeout!\n", pwrDmnNum); + return -2; + } + } + + /* Return PSC status */ + if (CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_OFF) + { + /*Ready for use */ + return 0; + } + else + { + /*Return error */ + return -1; + } + +} + +/*============================EDMA=====================================*/ + /***************************************************************************** + Prototype : EDMA_channel_TC_cfg + Description : Setup uiChannel of an EDMA to use uiTC + Input : Uint32 uiCC + Uint32 uiChannel + Uint32 uiTC + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_channel_TC_cfg (Uint32 uiCC, + Uint32 uiChannel, Uint32 uiTC) +{ + gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8] = + (gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8]&(~(0xF<<((uiChannel&7)*4)))) + |(uiTC<<((uiChannel&7)*4)); +} +/***************************************************************************** + Prototype : EDMA_TC_priority_cfg + Description : Setup uiChannel of an EDMA TC priority + Input : Uint32 uiCC + Uint32 uiPri + Uint32 uiTC + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_TC_priority_cfg(Uint32 uiCC, + Uint32 uiPri, Uint32 uiTC) +{ + gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI= + (gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI&(~(0xF<<((uiTC&3)*4)))) + |(uiPri<<((uiTC&3)*4)); +} +/***************************************************************************** + Prototype : EDMA_init + Description : Initialize all EDMA registers and clear the event + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_init () +{ + int i; + unsigned int * uipPaRAM; + + /*clear PaRAM*/ + uipPaRAM= (unsigned int *)&(gpEDMA_CC0_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC0_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + uipPaRAM= (unsigned int *)&(gpEDMA_CC1_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC1_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + uipPaRAM= (unsigned int *)&(gpEDMA_CC2_regs->PARAMSET[0]); + for(i=0; i<8*CSL_EDMA3_TPCC2_NUM_PARAMSETS; i++) + *uipPaRAM++=0; + + /*Assign PaRAM for different channels*/ + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; + + /*Assign TC/Queue for different channels*/ + gpEDMA_CC0_regs->TPCC_DMAQNUM[0]= 0x10101010; + gpEDMA_CC0_regs->TPCC_DMAQNUM[1]= 0x10101010; + + gpEDMA_CC1_regs->TPCC_DMAQNUM[0]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[1]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[2]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[3]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[4]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[5]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[6]= 0x32103210; + gpEDMA_CC1_regs->TPCC_DMAQNUM[7]= 0x32103210; + + gpEDMA_CC2_regs->TPCC_DMAQNUM[0]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[1]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[2]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[3]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[4]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[5]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[6]= 0x32103210; + gpEDMA_CC2_regs->TPCC_DMAQNUM[7]= 0x32103210; + + /*clear any events and status*/ + gpEDMA_CC0_regs->TPCC_ECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_EECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_ICR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_IECR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_EMCR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_QEMCR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC0_regs->TPCC_SECR= 0xFFFF; + + gpEDMA_CC1_regs->TPCC_ECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ICR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_ICRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_IECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_IECRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EMCR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_EMCRH= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_QEMCR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC1_regs->TPCC_SECR= 0xFFFFFFFF; + gpEDMA_CC1_regs->TPCC_SECRH= 0xFFFFFFFF; + + gpEDMA_CC2_regs->TPCC_ECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ICR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_ICRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_IECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_IECRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EMCR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_EMCRH= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_QEMCR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_CCERRCLR= 0xFFFF; + gpEDMA_CC2_regs->TPCC_SECR= 0xFFFFFFFF; + gpEDMA_CC2_regs->TPCC_SECRH= 0xFFFFFFFF; + + for(i=0; iTPTC_ERRCLR= 0xF; + + //enable error interrupt + gpEDMA_TC_regs[i]->TPTC_ERREN= + (1<TPCC_EESR= 1<<(uiChannel); + } + else + { + //enable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EESRH= 1<<(uiChannel-32); + } +} + +void EDMA_event_disable(Uint32 uiCC, Uint32 uiChannel) +{ + if(uiChannel<32) + { + //disable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EECR= 1<<(uiChannel); + } + else + { + //disable the EDMA channel + gpEDMA_CC_regs[uiCC]->TPCC_EECRH= 1<<(uiChannel-32); + } +} + +void EDMA_interrupt_enable(Uint32 uiCC, Uint32 uiIntNum) +{ + if(uiIntNum<32) + { + //enable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IESR= 1<<(uiIntNum); + } + else + { + //enable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IESRH= 1<<(uiIntNum-32); + } +} + +void EDMA_interrupt_disable(Uint32 uiCC, Uint32 uiIntNum) +{ + if(uiIntNum<32) + { + //disable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IECR= 1<<(uiIntNum); + } + else + { + //disable the EDMA channel interrupt + gpEDMA_CC_regs[uiCC]->TPCC_IECRH= 1<<(uiIntNum-32); + } +} + +/***************************************************************************** + Prototype : EDMA_wait + Description : wait the pending EDMA complete + Input : EDMA_CC_Channel_Num CC_channel + Output : None + Return Value : + + History : + 1.Date : 2012/10/30 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_wait(EDMA_CC_Channel_Num CC_channel) +{ + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + + if(uiChannel<32) + { + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + } + else + { + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannel -= 32; + } + + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannel)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannel); +} + +/***************************************************************************** + Prototype : EDMA_Copy + Description : EDMA copy function with manual trigger + Input : unsigned int srcAddr + unsigned int dstAddr + unsigned int byteCount, <64KB + EDMA_CC_Channel_Num CC_channel + DMA_Wait wait + Output : None + Return Value : + + History : + 1.Date : 2012/10/30 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_copy(unsigned int srcAddr, unsigned int dstAddr, + unsigned int byteCount, EDMA_CC_Channel_Num CC_channel, DMA_Wait wait) +{ + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel; + volatile Uint32 * TPCC_ESR; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + + EDMACCRegs->PARAMSET[uiChannel].OPT= + CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, + CSL_EDMA3_TCCH_DIS, + CSL_EDMA3_ITCINT_DIS, + CSL_EDMA3_TCINT_EN, + uiChannel, + CSL_EDMA3_TCC_NORMAL, + CSL_EDMA3_FIFOWIDTH_NONE, + CSL_EDMA3_STATIC_DIS, + CSL_EDMA3_SYNC_A, + CSL_EDMA3_ADDRMODE_INCR, + CSL_EDMA3_ADDRMODE_INCR); + EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(srcAddr); + EDMACCRegs->PARAMSET[uiChannel].A_B_CNT=CSL_EDMA3_CNT_MAKE(byteCount&0xFFFF, 1); + EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(dstAddr); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 1); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; + + if(uiChannel<32) + { + TPCC_ESR= &EDMACCRegs->TPCC_ESR; + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + } + else + { + TPCC_ESR= &EDMACCRegs->TPCC_ESRH; + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannel -= 32; + } + + /*Manually trigger the EDMA*/ + (*TPCC_ESR)= 1<<(uiChannel); + + if(wait) + { + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannel)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannel); + } +} + +/***************************************************************************** + Prototype : EDMA_fill + Description : EDMA fill function with manual trigger + Input : unsigned int address, must align to 8 bytes boundary + unsigned long long data + unsigned int byteCount, must be multiple of 8 + EDMA_CC_Channel_Num CC_channel + Output : None + Return Value : + + History : + 1.Date : 2013/8/11 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_fill(unsigned int address, unsigned long long data, + unsigned int byteCount, EDMA_CC_Channel_Num CC_channel) +{ + int i; + CSL_TpccRegs* EDMACCRegs; + unsigned int uiChannel, uiChannelShift, uiBCNT; + volatile Uint32 * TPCC_ESR; + volatile Uint32 * TPCC_IPR; + volatile Uint32 * TPCC_ICR; + unsigned long long tempBuf[128/8]; + Uint32 tempBufSize=128, headerSize, tailSize; + + if(tempBufSize>byteCount) + tempBufSize=byteCount; + + for(i=0; i< tempBufSize/8; i++) + tempBuf[i]= data; + + /*split the transfer into 3 sections at 128 byte boundary*/ + if(address&127) //header address not start on 128 byte boundary + { + headerSize= 128- (address&127); + if(headerSize>byteCount) + headerSize=byteCount; + EDMA_copy((Uint32)tempBuf, address, headerSize, CC_channel, DMA_WAIT); + address+= headerSize; + byteCount-= headerSize; + } + + if(byteCount&&((address+byteCount)&127))//tail address not start on 128 byte boundary + { + tailSize= (address+byteCount)&127; + EDMA_copy((Uint32)tempBuf, address+byteCount-tailSize, tailSize, CC_channel, DMA_WAIT); + byteCount-= tailSize; + } + + EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; + uiChannel = CC_channel&0xFF; + if(uiChannel<32) + { + TPCC_ESR= &EDMACCRegs->TPCC_ESR; + TPCC_IPR= &EDMACCRegs->TPCC_IPR; + TPCC_ICR= &EDMACCRegs->TPCC_ICR; + uiChannelShift= uiChannel; + } + else + { + TPCC_ESR= &EDMACCRegs->TPCC_ESRH; + TPCC_IPR= &EDMACCRegs->TPCC_IPRH; + TPCC_ICR= &EDMACCRegs->TPCC_ICRH; + uiChannelShift= uiChannel - 32; + } + + EDMACCRegs->PARAMSET[uiChannel].OPT= + CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, + CSL_EDMA3_TCCH_DIS, + CSL_EDMA3_ITCINT_DIS, + CSL_EDMA3_TCINT_EN, + uiChannel, + CSL_EDMA3_TCC_NORMAL, + CSL_EDMA3_FIFOWIDTH_NONE, + CSL_EDMA3_STATIC_EN, //keep PARAM unchanged + CSL_EDMA3_SYNC_AB, + CSL_EDMA3_ADDRMODE_INCR, + CSL_EDMA3_ADDRMODE_INCR); + EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(tempBuf); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= CSL_EDMA3_BIDX_MAKE(0, 128); + EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 0); + EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; + EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; + + while(byteCount) //the reminding must be multiple of 128 bytes + { + uiBCNT= byteCount/128; + if(uiBCNT>65535) + uiBCNT= 65535; + + EDMACCRegs->PARAMSET[uiChannel].A_B_CNT= CSL_EDMA3_CNT_MAKE(128, uiBCNT); + EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(address); + + /*Manually trigger the EDMA*/ + (*TPCC_ESR)= 1<<(uiChannelShift); + + /*wait for completion*/ + while(0==((*TPCC_IPR)&(1<<(uiChannelShift)))); + + /*clear completion flag*/ + (*TPCC_ICR)= 1<<(uiChannelShift); + + byteCount -= uiBCNT*128; + address += uiBCNT*128; + } +} + +/***************************************************************************** + Prototype : IDMA_wait + Description : wait the pending IDMA complete + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void IDMA_wait() +{ + /* Wait until copying is completed */ + while (gpCGEM_regs->IDMA1_STAT); +} +/***************************************************************************** + Prototype : IDMA_copy + Description : implement the data copy via IDMA + Input : unsigned int srcAddr + unsigned int dstAddr + unsigned int byteCount, <64KB + IDMA_Wait wait + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brigthon + Modification : Created function + +*****************************************************************************/ +void IDMA_copy(unsigned int srcAddr, unsigned int dstAddr, + unsigned int byteCount, DMA_Wait wait) +{ + gpCGEM_regs->IDMA1_SOURCE= srcAddr; + gpCGEM_regs->IDMA1_DEST= dstAddr; + gpCGEM_regs->IDMA1_COUNT= byteCount&0xFFFC; + + if(wait) + { + /* Wait until copying is completed */ + while (gpCGEM_regs->IDMA1_STAT); + } +} +/***************************************************************************** + Prototype : EDMA_CC_error_handler + Description : Edma channel controller error processing + Input : Uint32 edmaNum, EDMA module number (0~2) + Output : None + Return Value : + + History : + 1.Date : 2012/11/7 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_CC_error_handler(Uint32 edmaNum) +{ + int i; + CSL_TpccRegs* EDMACCRegs= gpEDMA_CC_regs[edmaNum]; + Uint32 EMR, EMRH= 0, QEMR, CCERR; + + //read error status + EMR= EDMACCRegs->TPCC_EMR; + QEMR= EDMACCRegs->TPCC_QEMR; + CCERR= EDMACCRegs->TPCC_CCERR; + exception_record.status.ext_sts.info.edma.CC_info.EMR= EMR; + exception_record.status.ext_sts.info.edma.CC_info.QEMR= QEMR; + exception_record.status.ext_sts.info.edma.CC_info.CCERR= CCERR; + + //clear error status + EDMACCRegs->TPCC_EMCR= EMR; + EDMACCRegs->TPCC_QEMCR= QEMR; + EDMACCRegs->TPCC_CCERRCLR= CCERR; + + //channel 32~63 for EDMA CC1 and CC2 + if(0TPCC_EMRH; + exception_record.status.ext_sts.info.edma.CC_info.EMRH= EMRH; + + //clear error status + EDMACCRegs->TPCC_EMCRH= EMRH; + } + + for(i=0; i<32; i++) + { + if((EMR>>i)&1) + printf(" EDMA Channel %d event missed.\n", i); + if((EMRH>>i)&1) + printf(" EDMA Channel %d event missed.\n", i+32); + } + + for(i=0; i<8; i++) + { + if((QEMR>>i)&1) + printf(" QDMA Channel %d event missed.\n", i); + } + + for(i=0; i<4; i++) + { + if((CCERR>>i)&1) + printf(" Queue %d Watermark/threshold has been exceeded.\n", i); + } + + if(CCERR&CSL_TPCC_TPCC_CCERR_TCCERR_MASK) + puts(" Total number of allowed TCCs has been reached."); + +} +/***************************************************************************** + Prototype : EDMA_TC_error_handler + Description : Edma transfer controller error processing + Input : CSL_TptcRegs * edmaTCRegs + Output : None + Return Value : + + History : + 1.Date : 2012/11/7 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_TC_error_handler(CSL_TptcRegs * edmaTCRegs) +{ + Uint32 ERRSTAT, ERRDET, STAT; + + //read error status + ERRSTAT= edmaTCRegs->TPTC_ERRSTAT; + ERRDET= edmaTCRegs->TPTC_ERRDET; + exception_record.status.ext_sts.info.edma.TC_info.ERRSTAT=ERRSTAT ; + exception_record.status.ext_sts.info.edma.TC_info.ERRDET= ERRDET; + + //clear error + edmaTCRegs->TPTC_ERRCLR= ERRSTAT; + + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_MMRAERR_MASK) + puts(" User attempted to read or write to an invalid address in configuration memory map."); + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_TRERR_MASK) + puts(" TR detected that violates constant addressing mode transfer (SAM or DAM is set) alignment rules or has ACNT or BCNT== 0."); + if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_BUSERR_MASK) + { + puts(" EDMA3TC has detected an error at source or destination address."); + + STAT= ERRDET&CSL_TPTC_TPTC_ERRDET_STAT_MASK; + + if(STAT>=8) + printf(" write error (%d). ",STAT); + else if(STAT>=1) + printf(" read error (%d). ",STAT); + else + printf(" no error!?"); + + printf("TCC= %d. TCINTEN= %d. TCCHEN= %d\n", + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCC_MASK)>>CSL_TPTC_TPTC_ERRDET_TCC_SHIFT, + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCINTEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCINTEN_SHIFT, + (ERRDET&CSL_TPTC_TPTC_ERRDET_TCCHEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCCHEN_SHIFT); + } + +} +/***************************************************************************** + Prototype : EDMA_error_handler + Description : EDMA error processing function + Input : Uint32 edmaNum + Uint32 errorFlag + error flag bit fields are defined as below + (follow the sequence in CIC) + 0 EDMACC_ERRINT EDMA3CC error interrupt + 2 EDMATC_ERRINT0 EDMA3TC0 error interrupt + 3 EDMATC_ERRINT1 EDMA3TC1 error interrupt + 4 EDMATC_ERRINT2 EDMA3TC2 error interrupt + 5 EDMATC_ERRINT3 EDMA3TC3 error interrupt + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EDMA_error_handler(Uint32 edmaNum, Uint32 errorFlag) +{ + int i; + + printf(" EDMA module %d error\n", edmaNum); + if(errorFlag&1) + EDMA_CC_error_handler(edmaNum); + + errorFlag >>= 2; + + for(i=0; i<4; i++) + { + if(errorFlag&(1<MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; + } + + /*3. Write a 1 to the LOCK field of the MPLKCMD register. This engages the lock.*/ + gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); +} + +/***************************************************************************** + Prototype : unlock_mem_prot_regs + Description : unlock memory protection registers + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma CODE_SECTION (unlock_mem_prot_regs, ".text:Core_MPAX") +void unlock_mem_prot_regs() +{ + int i; + + /*1. Write a 1 to the KEYR field in the MPLKCMD register. This resets some internal + status for the MPLK0 through the MPLK3 registers.*/ + gpCGEM_regs->MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; + } + + /*3. Write a 1 to the UNLOCK field in the MPLKCMD register. If the key written in + step 2 matches the stored key, the hardware disengages the lock. If the key written + in step 2 does not match, the hardware signals an exception. The hardware + reports the fault address as the address of the MPLKCMD register.*/ + gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); +} + +/***************************************************************************** + Prototype : L1_MPPA_setup + Description : setup the memory protection for local L1 memory + Input : volatile Uint32 MPPA_regs[], Uint32 MPPA[] + Output : None + Return Value : + +usage example: + Uint32 MPPA[16]= + { + MP_LOCAL|MP_SR|MP_UR, //page 0 for read only + MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for read/write + ...... + } + ...... + L1_MPPA_setup(gpCGEM_regs->L1PMPPA, MPPA); + + History : + 1.Date : 2012/12/6 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1_MPPA_setup(volatile Uint32 MPPA_regs[], Uint32 MPPA[]) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1PMPFCR = 1; + gpCGEM_regs->L1DMPFCR = 1; + + /*setup the memory protection attributes for 32 pages*/ + for(i=0; i<16; i++) + { + MPPA_regs[i] = MPPA[i]; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1P_memory_protection_cfg + Description : config "AccessPermisionMask" for L1P + Input : Uint32 AccessPermisionMask + Output : None + Return Value : +*****************************************************************************/ +void L1P_memory_protection_cfg(Uint32 AccessPermisionMask) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1PMPFCR = 1; + + /*set L1P only for cacheable local execution, disable all external access*/ + for(i=0; i<16; i++) + { + gpCGEM_regs->L1PMPPA[i] = AccessPermisionMask; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1D_memory_protection_cfg + Description : config "AccessPermisionMask" for L1P + Input : Uint32 AccessPermisionMask + Output : None + Return Value : +*****************************************************************************/ +void L1D_memory_protection_cfg(Uint32 AccessPermisionMask) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L1DMPFCR = 1; + + /*set L1P only for cacheable local execution, disable all external access*/ + for(i=0; i<16; i++) + { + gpCGEM_regs->L1DMPPA[i] = AccessPermisionMask; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : L1_cache_protection + Description : protect L1 as cache + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1_cache_protection() +{ + /*set L1P only for cacheable local execution, disable all external access*/ + L1P_memory_protection_cfg(0); + + /*set L1D only for cacheable local read/write, disable all external access*/ + L1D_memory_protection_cfg(0); +} + + +/***************************************************************************** + Prototype : LL2_MPPA_setup + Description : setup the memory protection for local L2 memory + Input : Uint32 MPPA[] + Output : None + Return Value : +usage example: + Uint32 MPPA[32]= + { + MP_LOCAL|MP_SX|MP_UX, //page 0 for local code only + MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for local data only + ...... + } + ...... + LL2_MPPA_setup(MPPA); + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_MPPA_setup(Uint32 MPPA[]) +{ + int i; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*clear any memory protection fault*/ + gpCGEM_regs->L2MPFCR = 1; + + /*setup the memory protection attributes for 32 pages*/ + for(i=0; i<32; i++) + { + gpCGEM_regs->L2MPPA[i] = MPPA[i]; + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : LL2_Memory_Protection_cfg + Description : config "AccessPermisionMask" for local L2 memory section from + "startAddress" with "byteCount" size + Input : Uint32 startAddress + Uint32 byteCount + Uint32 AccessPermisionMask + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_Memory_Protection_cfg(Uint32 startAddress, + Uint32 byteCount, Uint32 AccessPermisionMask) +{ + int i; + Uint32 uiEndAddress; + Uint32 uiPageIndex, uiNumPages, uiPageSize, uiPageAddressMask, uiPageShift; + TDSP_Board_Type DSP_Board_Type; + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + DSP_Board_Type = KeyStone_Get_dsp_board_type(); + + /*L2 memory protection size is 32KB for TCI6614, C6670, + it is 16KB for C6678*/ + uiPageSize= 32*1024; + uiPageAddressMask= 32*1024-1; + uiPageShift= 15; + if(C6678_EVM == DSP_Board_Type) + { + uiPageSize= 16*1024; + uiPageAddressMask= 16*1024-1; + uiPageShift= 14; + } + + if(startAddress>=0x10800000) + { + printf("LL2 memory protection start Address 0x%x is not a local address\n", + startAddress); + startAddress &= 0xFFFFFF; /*convert to local address*/ + } + uiEndAddress= startAddress+ byteCount; + + if(startAddress&uiPageAddressMask) + { + printf("LL2 memory protection start Address 0x%x does not align to page boundary\n", + startAddress); + startAddress &= (~uiPageAddressMask); + } + uiPageIndex= (startAddress-0x800000)>>uiPageShift; + + byteCount= uiEndAddress- startAddress; + if(byteCount&uiPageAddressMask) + { + printf("LL2 memory protection section size 0x%x is not multiple of page size\n", + byteCount); + byteCount = (byteCount+uiPageSize)&(~uiPageAddressMask); + } + uiNumPages= byteCount>>uiPageShift; + + for(i= 0; iL2MPPA[uiPageIndex+i] = AccessPermisionMask; + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : KeyStone_CorePac_AID_map + Description : map CorePac AID to PrivID: + map_table[0] assign the PrivID for AID0, + map_table[1] assign the PrivID for AID1 + ...... + map_table[5] assign the PrivID for AID5 + Input : Uint8 map_table[] + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_CorePac_AID_map(Uint8 map_table[]) +{ + int i; + Uint32 *PAMAP= (Uint32 *)&(gpCGEM_regs->PAMAP0); + + /*map all PrivID to AIDx by default*/ + for(i=0; i<16; i++) + PAMAP[i]= CSL_CGEM_PAMAP0_AID_MASK; + + /*map AID0~AID5*/ + for(i=0; i<6; i++) + { + if(map_table[i]<16) /*PrivID must be less than 16*/ + PAMAP[map_table[i]]= i; + } +} + +/***************************************************************************** + Prototype : KeyStone_PrivID_Remap + Description : privilege ID remap to AID + Input : int privID + int AID + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_PrivID_Remap(int privID, int AID) +{ + volatile unsigned int * pamapReg = NULL; + unsigned int val = 0; + + pamapReg = (volatile unsigned int *)(&gpCGEM_regs->PAMAP0 + privID); + + if(AID >= MAX_AID_NUM) + AID = 0; + val = *pamapReg; + + val &= (~CSL_CGEM_PAMAP0_AID_MASK); + + val |= ((AID<>4)) + { + printf("Segment replacement address 0x%x does not start from power-of-2 boundary corresponds to segment size 0x%x.\n", + RADDR, SegementSize); + RADDR &= (~(SegSizeMask>>4)); + printf("Extended replacement address to 0x%x.\n", RADDR); + } + + MPAX_regs->MPAXH= BADDR|(SegSizeBits-1); + MPAX_regs->MPAXL= RADDR|AccessPermisionMask; + +} + +/***************************************************************************** + Prototype : KeyStone_XMC_MPAX_setup + Description : configure multiple MPAX segments in XMC with a configuration + table. + Please note, the code of this function or the data used by this function + (stack, parameters...) can not be put in the segment that will be modified + by this function. Normally, to put this function and its related data in + LL2 is a good idea. + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma CODE_SECTION (KeyStone_XMC_MPAX_setup, ".text:Core_MPAX") +void KeyStone_XMC_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs) +{ + int i; + + if(firstSeg >= 16) + { + printf("The XMC MPAX segment number %d >= 16, not supported.\n ", firstSeg); + return; + } + + if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) + unlock_mem_prot_regs(); + + /*CAUTION: + A MPAX segment can only be modified when there is no access to the space + of this segment. Any data in cache or prefetch buffer from the space of this + segment must be writeback and invalidated before the segment modification. + It is recommended to configure the MPAX at the very beginning of application + software before any shared memory is used. Code and data for CorePac MPAX + configuration should be allocated in LL2. + If a MPAX segment must be modified on-the-fly, the safer way is, to write + the new configuration to a unused higher segment, and then clear the old + segment. This is based on the fact that higher numbered segments take + precedence over lower numbered segments. */ + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + _mfence(); + _mfence(); //ensure all writeback invalidate have completed. + + for(i=numSegs-1; i>=0 ; i--) + { + KeyStone_MPAX_seg_setup((MPAX_Regs *)&gpXMC_regs->XMPAX[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + } + + lock_mem_prot_regs(); +} + +/***************************************************************************** + Prototype : KeyStone_SMS_MPAX_setup + Description : configure multiple MPAX segments in SMS of MSMC with a conf- + iguration table + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Uint32 PrivID + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SMS_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) +{ + int i; + + if( gpMSMC_regs->SMS_MPAX_LCKSTAT&(1<=0 ; i--) + KeyStone_MPAX_seg_setup( + (MPAX_Regs *)&gpMSMC_regs->SMS_MPAX_PER_PRIVID[PrivID].SMS[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + + CSL_MSMC_lockSMS(PrivID); +} + +/***************************************************************************** + Prototype : KeyStone_SES_MPAX_setup + Description : configure multiple MPAX segments in SES of MSMC with a conf- + iguration table + Input : MPAX_Config MPAX_cfg[] + Uint32 firstSeg + Uint32 numSegs + Uint32 PrivID + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SES_MPAX_setup(MPAX_Config MPAX_cfg[], + Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) +{ + int i; + + if( gpMSMC_regs->SES_MPAX_LCKSTAT&(1<=0 ; i--) + KeyStone_MPAX_seg_setup( + (MPAX_Regs *)&gpMSMC_regs->SES_MPAX_PER_PRIVID[PrivID].SES[firstSeg+i], + MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, + MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); + + CSL_MSMC_lockSES(PrivID); +} + +/***************************************************************************** + Prototype : KeyStone_MSMC_MP_interrupt_en + Description : Enable MSMC Memory protection error interrupt for PrivIDs + indicated by "PRIVID_MASK" + Input : Uint32 PRIVID_MASK + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Zhan + Modification : Created function + +*****************************************************************************/ +void KeyStone_MSMC_MP_interrupt_en(Uint32 PRIVID_MASK) +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /*clear MP fault record*/ + gpMSMC_regs->SMPFCR = 1; + + /*clear interrupt error status flag*/ + gpMSMC_regs->SMIRC = (PRIVID_MASK)<SMIESTAT |= (PRIVID_MASK<> + CSL_CGEM_L2MPFSR_FID_SHIFT; + + printf(" memory protection exception caused by master with ID %d at 0x%x\n", + master_id, MPFAR); + } + + if (MPFSR & CSL_CGEM_L2MPFSR_UX_MASK) { + puts(" User Execute violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_UW_MASK) { + puts(" User Write violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_UR_MASK) { + puts(" User Read violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SX_MASK) { + puts(" Supervisor Execute violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SW_MASK) { + puts(" Supervisor Write violation"); + } + if (MPFSR & CSL_CGEM_L2MPFSR_SR_MASK) { + puts(" Supervisor Read violation"); + } + +} + +/***************************************************************************** + Prototype : KeyStone_MSMC_protection_exception_handler + Description : MSMC memory protection processing + Input : None + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_MSMC_protection_exception_handler() +{ + unsigned int master_id; + unsigned int priv_id; + unsigned int address; + unsigned int NM; + + address = gpMSMC_regs->SMPFAR; + + master_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FMSTID_MASK)>> + CSL_MSMC_SMPFR_FMSTID_SHIFT; + priv_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FPID_MASK)>> + CSL_MSMC_SMPFR_FPID_SHIFT; + + exception_record.status.ext_sts.info.memory.fault_address= address; + exception_record.status.ext_sts.info.memory.fault_status.SMPFR= gpMSMC_regs->SMPFR; + + NM = (gpMSMC_regs->SMPFXR & CSL_MSMC_SMPFXR_NM_MASK) >> CSL_MSMC_SMPFXR_NM_SHIFT; + + printf(" memory protection exception caused by master %d (PrivID= %d) at address 0x%x\n", + master_id, priv_id, address); + + if(1 == NM) + { + printf(" Fault is caused by the address not matching any of the segment BADDR\n"); + } + + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + /*clear fault record*/ + gpMSMC_regs->SMPFCR = 1; + /*clear interrupt error status flag*/ + gpMSMC_regs->SMIRC = (1<PROG_START_ADDRESS = uiStartAddress; + MPPA_regs->PROG_END_ADDRESS = uiEndAddress; + MPPA_regs->PROG_MPPA = AccessPermisionMask; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_setup + Description : peripherals MPU ranges configuration + Input : Uint32 uiMPU_num: number of the MPU to be setup + MPU_Range_Config MPU_cfg[]: MPU ranges configuration table + Uint32 numRangeCfg: number of ranges to be configured + Output : None + Return Value : + + History : + 1.Date : 2012/12/15 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_MPU_setup(Uint32 uiMPU_num, + MPU_Range_Config MPU_cfg[], Uint32 numRangeCfg) +{ + int i; + unsigned int mpuNumProgmableRange; + CSL_MpuRegs * mpuRegs; + + /*For Turbo Nyquist, add following code to modify initial value, + Or user can modify the initail values directly*/ + if(5==uiMPU_num) + TN_MPU5_constant(); + + mpuRegs= gpMPU_regs[uiMPU_num]; + + mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; + if(mpuNumProgmableRange == 0) + { + mpuNumProgmableRange = 16; + } + + if(numRangeCfg>mpuNumProgmableRange) + { + printf("MPU %d programmable ranges %d < %d.\n", + uiMPU_num, mpuNumProgmableRange, numRangeCfg); + numRangeCfg=mpuNumProgmableRange; + } + else if(numRangeCfg gstruMpuAddrRange[uiMPU_num].EndAddr) ) + { + printf("The configuration address is out of MPU %d protection range\n", + uiMPU_num); + continue; + } + + KeyStone_MPU_range_setup(&mpuRegs->PROG_REGION[i], + MPU_cfg[i].StartAddr, MPU_cfg[i].EndAddr, + MPU_cfg[i].AccessPermisionMask); + + } + + //clear unused ranges + for( ;iPROG_REGION[i].PROG_MPPA = 0; + } + + //clear status + mpuRegs->FAULT_CLEAR = 1; + mpuRegs->INT_ENABLED_STATUS_CLEAR = + CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK + |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; + + /* enable the interrupt */ + mpuRegs->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK + | CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; + + return; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_MPPA_modify + Description : search the range which match a address and then modify + the access permission of that range. + Input : Uint32 uiMPU_num: number of the MPU to be modifed + Uint32 uiAddress: address which need modify permision + Uint32 AccessPermisionMask: permission mask for that range + Output : None + Return Value : + + History : + 1.Date : 2012/12/13 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_MPU_MPPA_modify(Uint32 uiMPU_num, + Uint32 uiAddress, Uint32 AccessPermisionMask) +{ + int i; + unsigned int mpuNumProgmableRange; + CSL_MpuRegs * mpuRegs; + + /*For Turbo Nyquist, add following code to modify initial value, + Or user can modify the initail values directly*/ + if(5==uiMPU_num) + TN_MPU5_constant(); + + mpuRegs= gpMPU_regs[uiMPU_num]; + + mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; + if(mpuNumProgmableRange == 0) + { + mpuNumProgmableRange = 16; + } + + /*search through all ranges*/ + for(i=0; i< mpuNumProgmableRange; i++) + { + /*match with one range*/ + if((uiAddress >= mpuRegs->PROG_REGION[i].PROG_START_ADDRESS) + &&(uiAddress <= mpuRegs->PROG_REGION[i].PROG_END_ADDRESS)) + { + mpuRegs->PROG_REGION[i].PROG_MPPA = AccessPermisionMask; + return; + } + } + + printf("address 0x%08x does not match any range in MPU %d\n", + uiAddress, uiMPU_num); + + return; +} + +/***************************************************************************** + Prototype : KeyStone_MPU_interrupts_enable + Description : enable the all MPU interrupts + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_MPU_interrupt_enable(Uint32 uiMPU_num) +{ + if((gpMPU_regs[uiMPU_num]->REVISION&0xFFFF0000)!= + (CSL_MPU_REVISION_RESETVAL&0xFFFF0000)) + { + printf("Can't read MPU%d ID register, make sure corresponding power domain is enabled.", uiMPU_num); + return; + } + + gpMPU_regs[uiMPU_num]->FAULT_CLEAR = 1; + gpMPU_regs[uiMPU_num]->INT_ENABLED_STATUS_CLEAR = + CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK + |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; + gpMPU_regs[uiMPU_num]->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK + |CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; + +} +void KeyStone_MPU_interrupts_enable() +{ + int i; + TDSP_Board_Type DSP_Board_Type = KeyStone_Get_dsp_board_type(); + + TN_MPU5_constant(); + + for(i=0; i<4; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + + if((C6670_EVM== DSP_Board_Type) + ||(TCI6614_EVM== DSP_Board_Type)) + { + for(i=4; i<6; i++) + { + /*MPU5 (for BCP) of TCI6614 is only accessible + when BCP is enabled through PSC*/ + if((5==i)&&(TCI6614_EVM== DSP_Board_Type)&& + ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || + (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) + { + puts("Enable power domain for MPU5 before configure it."); + continue; + } + + KeyStone_MPU_interrupt_enable(i); + } + } + + if(TCI6614_EVM== DSP_Board_Type) + { + for(i=6; i<8; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + } + + return; +} + +char * Peri_MPU_err_type_str[]= +{ + "User execution fault!", + "User write fault!", + "User read fault!", + "Supervisor execution fault!", + "Supervisor write fault!", + "Supervisor read fault!" +}; + +char * Ns_str[]= +{ + "secure", + "non-secure" +}; +/***************************************************************************** + Prototype : KeyStone_peripherals_MPU_fault_status + Description : Print the MPU error information + Input : unsigned int uwFltStatus + unsigned int uwFltAddr + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_peripherals_MPU_fault_status(unsigned int uwFltStatus, + unsigned int uwFltAddr) +{ + unsigned int MSTID; + unsigned int PRIVID; + unsigned int NS; + unsigned int FaultType; + unsigned int BitsCnt; + + MSTID = (uwFltStatus & CSL_MPU_FAULT_STATUS_MSTID_MASK)>>CSL_MPU_FAULT_STATUS_MSTID_SHIFT; + PRIVID = (uwFltStatus & CSL_MPU_FAULT_STATUS_PRIVID_MASK)>>CSL_MPU_FAULT_STATUS_PRIVID_SHIFT; + NS = (uwFltStatus & CSL_MPU_FAULT_STATUS_NS_MASK)>>CSL_MPU_FAULT_STATUS_NS_SHIFT; + printf(" The MSTID %d (PRIVID %d) triggered MPU error at 0x%x with %s access\n", + MSTID, PRIVID, uwFltAddr, Ns_str[NS]); + + FaultType = (uwFltStatus & CSL_MPU_FAULT_STATUS_FAULT_TYPE_MASK) >> CSL_MPU_FAULT_STATUS_FAULT_TYPE_SHIFT; + if(1==(_dotpu4(_bitc4(FaultType), 0x01010101))) + { + BitsCnt= 31 - _lmbd(1, FaultType); + printf(" %s\n",Peri_MPU_err_type_str[BitsCnt]); + } + else if(0x3F == FaultType) + { + puts(" Relaxed cache line fill fault!"); + } + else if(0x12 == FaultType) + { + puts(" Relaxed cache write back fault!"); + } +} +/***************************************************************************** + Prototype : KeyStone_peripherals_MPU_excepiton_handler + Description : peripheral MPU processing + Input : Uint32 uwMpuNum + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_peripherals_MPU_excepiton_handler(Uint32 uwMpuNum) +{ + Uint32 uwStatus; + Uint32 uwFltAddr; + Uint32 uwFltStatus; + CSL_MpuRegs *pstruMpuRegs= gpMPU_regs[uwMpuNum]; + + uwStatus = pstruMpuRegs->INT_ENABLED_STATUS_CLEAR; + if(uwStatus & 0x2) + { + printf(" MPU %d address violation error\n", uwMpuNum); + pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 2; + } + + if(uwStatus & 0x1) + { + printf(" MPU %d protection violation error\n", uwMpuNum); + pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 1; + } + + uwFltAddr = pstruMpuRegs->FAULT_ADDRESS; + uwFltStatus = pstruMpuRegs->FAULT_STATUS; + exception_record.status.ext_sts.info.memory.fault_address= uwFltAddr; + exception_record.status.ext_sts.info.memory.fault_status.MPU_FAULT_STATUS= uwFltStatus; + + KeyStone_peripherals_MPU_fault_status(uwFltStatus,uwFltAddr); + pstruMpuRegs->FAULT_CLEAR = 1; + + pstruMpuRegs->EOI = 0; +} + + +/*======================memory EDC=====================================*/ +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_enable + Description : Enable MSMC EDC + Input : scrubCnt, number of MSMC clock cycles between scrubbing + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_enable(Uint32 scrubCnt) +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /*Software must wait for the PRR (Parity RAM Ready) bit before making + the first read access to MSMC RAM after reset.*/ + while(0==(gpMSMC_regs->SMEDCC&CSL_MSMC_SMEDCC_PRR_MASK)); + + /* set scrubbing period value */ + if(scrubCnt>255) + scrubCnt= 255; + CSL_MSMC_setCounterBankRefreshRead(scrubCnt); //the scrubbing engine works every scrubCnt*1024 cycle*/ + + /* clear EDC errors and enable EDC event*/ + gpMSMC_regs->SMIRC = 0xf; + gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK + | CSL_MSMC_SMIESTAT_CSIE_MASK + | CSL_MSMC_SMIESTAT_NCEIE_MASK + | CSL_MSMC_SMIESTAT_CEIE_MASK); + + //enable SL2 EDC + CSL_MSMC_setECM(1); + + CSL_MSMC_lockNonMPAX(); +} + +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_interrupt_en + Description : Enable MSMC EDC error interrupt + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/15 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_interrupt_en() +{ + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + /* clear EDC errors*/ + gpMSMC_regs->SMIRC = 0xf; + + /* Enable EDC error interrupt */ + gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK + | CSL_MSMC_SMIESTAT_CSIE_MASK + | CSL_MSMC_SMIESTAT_NCEIE_MASK + | CSL_MSMC_SMIESTAT_CEIE_MASK); + + CSL_MSMC_lockNonMPAX(); +} + +/***************************************************************************** + Prototype : LL2_EDC_setup + Description : Eenable LL2 EDC and scrub whole LL2 + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/10 + Author : Jane + Modification : Created function + + 2.Date : 2012/10/20 + Author : Brighton Feng + +*****************************************************************************/ +void LL2_EDC_setup() +{ + int i; + unsigned int uiByteCnt= 512*1024; + TDSP_Board_Type DSP_Board_Type; + + /* 1. Disable the EDC */ + CSL_CGEM_disableL2EDC(); + + /* 2. Clear any EDC errors */ + CSL_CGEM_clearL2EDCErrorStatus(1, 1, 1, 1); + + /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ + DSP_Board_Type = KeyStone_Get_dsp_board_type(); + if((DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(C6670_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + uiByteCnt= 1024*1024; + } + + /*Each IDMA can transfer up to 65532 bytes, + here we transfer 32KB each time*/ + for(i=0; i< (uiByteCnt>>15); i++) + { + IDMA_copy((0x00800000 + i*(1<<15)), (0x00800000 + i*(1<<15)), + (1<<15), DMA_WAIT); + } + + /* 4. Enable the EDC*/ + CSL_CGEM_enableL2EDC(); + gpCGEM_regs->L2EDCEN= (1<= uiLL2EndAddress) + uiLL2_scrub_addr=0x800000; + +} + +/***************************************************************************** + Prototype : L1P_EDC_setup + Description : enable L1P ED and scrub whole L1P + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/10 + Author : Jane + Modification : Created function + + 2.Date : 2012/10/30 + Author : Brighton Feng +*****************************************************************************/ +void L1P_EDC_setup() +{ + Uint32 preL1PMPPA[16]; + + /* 1. Disable the EDC */ + CSL_CGEM_disablePMCErrorDetection(); + + /* 2. Clear any EDC errors */ + CSL_CGEM_clearPMCErrorDetectionStatus(1, 1); + + /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ + memcpy(preL1PMPPA, (void *)gpCGEM_regs->L1PMPPA, 64);//save protection attributes + L1P_memory_protection_cfg(0xFFFF); //enable IDMA access to L1P + IDMA_copy(0x00E00000, 0x00E00000, 32*1024, DMA_WAIT); + L1_MPPA_setup(gpCGEM_regs->L1PMPPA, preL1PMPPA);//restore protection for L1 + + /* 4. Enable the EDC*/ + CSL_CGEM_enablePMCErrorDetection(); +} + +char * LL2_EDC_victim_err_str="LL2 victims"; +char * LL2_EDC_DMA_err_str= "DMA access"; +char * LL2_EDC_L1D_err_str= "L1D access"; +char * LL2_EDC_L1P_err_str= "L1P access"; + +/***************************************************************************** + Prototype : LL2_EDC_handler + Description : LL2 EDC exception/interrupt handler + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void LL2_EDC_handler(Bool bCorrected) +{ + /* EDC error during the L1D access */ + Uint8 derr; + /* EDC error during the L1P access */ + Uint8 perr; + /* EDC error during the DMA access*/ + Uint8 dmaerr; + /* EDC error during the L2 victim occurred */ + Uint8 verr; + /* single bit or dual bit EDC error */ + Uint8 nerr; + + char *errStr; + Uint32 errAddr; + + /* Get the all LL2 error status */ + CSL_CGEM_getL2EDCErrorStatus(&derr, &perr, &dmaerr, &verr, &nerr); + + if(derr|perr|dmaerr|verr) + { + errAddr= gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_ADDR_MASK; + + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + exception_record.status.ext_sts.info.memory.fault_status.L2EDSTAT= + gpCGEM_regs->L2EDSTAT; + + if(bCorrected) + { + printf(" LL2 EDC (correctable) at bit %d of ",(gpCGEM_regs->L2EDSTAT& + CSL_CGEM_L2EDSTAT_BITPOS_MASK)>>CSL_CGEM_L2EDSTAT_BITPOS_SHIFT); + + //scrub 64 bytes including the error address to correct the error + if(perr) //by L1P access + IDMA_copy(errAddr&0xFFFFFFC0, errAddr&0xFFFFFFC0, 64, DMA_WAIT); + else + { + volatile Uint32 * uipAddress= (volatile Uint32 *)(errAddr&0xFFFFFFC0); + /*read one word into a cache line, and write to make it dirty, + which will be automatically written back sooner or later*/ + *uipAddress= *uipAddress; + } + } + else + { + printf(" LL2 EDC error (non-correctable) at "); + } + errStr = (char *)(perr * (Uint32)LL2_EDC_L1P_err_str + + derr * (Uint32)LL2_EDC_L1D_err_str + + verr * (Uint32)LL2_EDC_victim_err_str + + dmaerr * (Uint32)LL2_EDC_DMA_err_str); + + printf("address 0x%x caused by %s.\n", + errAddr, + errStr); + + if(0==(gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_RAM_MASK)) + { + printf(" Error detected in Way %d of L2 cache\n", + (gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_WAY_MASK)>>CSL_CGEM_L2EDADDR_WAY_SHIFT); + } + + printf(" total non-correctable error number= %d, total correctable error number= %d.\n", + gpCGEM_regs->L2EDCNEC, gpCGEM_regs->L2EDCPEC); + + CSL_CGEM_clearL2EDCErrorStatus(derr, perr, dmaerr, verr); + } + else + { + puts(" Enter LL2 EDC handler, but no error flag is set!"); + } +} +/***************************************************************************** + Prototype : L1P_ED_handler + Description : L1P EDC processing + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void L1P_ED_handler() +{ + Uint32 errAddr; + Uint8 errRAM; + + /* EDC error during DMA access */ + Uint8 dmaerr; + /* EDC error during program fetch access */ + Uint8 perr; + + /* Read PMC EDC status*/ + CSL_CGEM_getPMCErrorDetectionStatus(&dmaerr, &perr); + + if(perr|dmaerr) + { + CSL_CGEM_getPMCErrorInfo(&errAddr, &errRAM); + + exception_record.status.ext_sts.info.memory.fault_address= errAddr*32; + exception_record.status.ext_sts.info.memory.fault_status.L1PEDSTAT= + gpCGEM_regs->L1PEDSTAT; + + if(errRAM) + printf(" L1P RAM "); + else + printf(" L1P Cache "); + + printf("parity check error caused by "); + + if(perr == 1) + { + printf("program fetch "); + + /*flush wrong code in L1P. Code will be refetched from L2*/ + CACHE_invL1p((void *)NRP, 64, CACHE_WAIT); + } + else if(dmaerr == 1) + { + printf("DMA "); + } + printf("at address 0x%x\n", errAddr*32); + + CSL_CGEM_clearPMCErrorDetectionStatus(dmaerr,perr); + } +} + + +/***************************************************************************** + Prototype : KeyStone_SL2_EDC_handler + Description : SL2 EDC Processing + Input : None + Output : None + Return Value : + + History : + 1.Date : 2012/10/28 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void KeyStone_SL2_EDC_handler() +{ + /* EDC correctable error during scrubbing cycle */ + Uint8 cses; + /* EDC non-correctable error during scrubbing cycle */ + Uint8 ncses; + /* EDC correctable error during SRAM access*/ + Uint8 cees; + /* EDC non-correctable error during SRAM access*/ + Uint8 ncees; + /* protection fault status*/ + Uint16 pfeStat; + + /* error address */ + Uint32 errAddr, bitPos, PrivID; + + if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) + CSL_MSMC_unlockNonMPAX(); + + CSL_MSMC_getPendingInterrupts(&pfeStat, &cees, &ncees, &cses, &ncses); + + exception_record.status.ext_sts.info.memory.fault_status.SMESTAT= + gpMSMC_regs->SMESTAT; + + if((cses == 1)||(ncses == 1)) + { + if(cses == 1) + { + /*scrubbing engine report address offset from 0*/ + errAddr = (gpMSMC_regs->SMCEA&0xFFFFFF)+0xc000000; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + bitPos = (gpMSMC_regs->SMCEA&CSL_MSMC_SMCEA_ESYN_MASK) + >>CSL_MSMC_SMCEA_ESYN_SHIFT; + printf("SL2 Correctable error occurred at bit %d of address 0x%x by scrubbing\n", + bitPos, errAddr); + } + if(ncses == 1) + { + /*scrubbing engine report address offset from 0*/ + errAddr = gpMSMC_regs->SMNCEA+0xc000000; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + printf("SL2 Non-correctable error occurred at address 0x%x by scrubbing\n", errAddr); + } + printf("%d correctable errors, %d non-correctable errors occurred during scrubbing.\n", + (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SCEC_MASK) + >>CSL_MSMC_SMSECC_SCEC_SHIFT, + (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SNCEC_MASK) + >>CSL_MSMC_SMSECC_SNCEC_SHIFT); + } + if(cees == 1) + { + volatile Uint32 scrubValue; + + errAddr = gpMSMC_regs->SMCERRAR; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + //scrub the address to correct the error + scrubValue= *(volatile Uint32 *)errAddr; //touch to cach + *(volatile Uint32 *)errAddr= scrubValue; //make cache dirty + CACHE_wbInvL2((void *)errAddr, 32, CACHE_WAIT); + + bitPos = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_ESYN_MASK) + >>CSL_MSMC_SMCERRXR_ESYN_SHIFT; + PrivID = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SEPID_MASK) + >>CSL_MSMC_SMCERRXR_SEPID_SHIFT; + printf("SL2 Correctable error occurred at bit %d of address 0x%x by PrivID %d ", + bitPos, errAddr, PrivID); + if(gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SER_MASK) + printf("(not from C66x CorePacs)\n"); + else + printf("(from C66x CorePacs)\n"); + } + if(ncees ==1) + { + errAddr = gpMSMC_regs->SMNCERRAR; + exception_record.status.ext_sts.info.memory.fault_address= errAddr; + + PrivID = (gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SEPID_MASK) + >>CSL_MSMC_SMNCERRXR_SEPID_SHIFT; + printf("SL2 Non-correctable error occurred at address 0x%x by PrivID %d ", + errAddr, PrivID); + if(gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SER_MASK) + printf("(not from C66x CorePacs)\n"); + else + printf("(from C66x CorePacs)\n"); + } + + /* clear EDC error status */ + CSL_MSMC_clearRawInterruptStatus(0, cees,ncees, cses, ncses); + + CSL_MSMC_lockNonMPAX(); +} + +/*===============================Exception=============================*/ +//data structure to save exception info +Exception_Record exception_record; + +/*some exception events routed from CIC to INTC and then to exception moduel, +all these events are routed to one input of INTC*/ +Uint32 guwIntcCICExcEvtIdx= 95; /*INTC event number mapping to CIC exception events*/ +Uint32 gCIC_EXC_out_num = 15; //CIC output event number +Uint32 gCIC_EXC_EN_MASK[8]= {0,0,0,0,0,0,0,0}; +/***************************************************************************** + Prototype : KeyStone_CIC_exception_events_mapping + Description : CIC exception event mapping to the NMI external exception + Input : void + Output : None + Return Value : + + History : + 1.Date : 2012/10/5 + Author : Brighton Feng + Modification : Created function + + 2.Date : 2012/10/20 + Author : Zhan + Modification : Add event for TCI6614 + + 3.Date : 2012/10/28 + Author : Brighton Feng +*****************************************************************************/ +void KeyStone_CIC_exception_events_mapping(void) +{ + TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); + +#if 1 + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||TCI6614_EVM==DSP_Board_Type) + { + gCIC_EXC_out_num= 15+16*DNUM; + } + else if(C6678_EVM==DSP_Board_Type) + { + if(DNUM<4) + gCIC_EXC_out_num= 7+8*DNUM; + else + { + gCIC_EXC_out_num= 7+8*(DNUM-4); + gpCIC_regs= gpCIC1_regs; + } + } + else + { + puts("Unknown DSP board type!"); + return; + } +#endif + + /*-----------------------CP_INTC configuration---------------------*/ + /* Disable Global host interrupts. */ + gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 0; + + /* route following system events to CIC out (event 22 of INTC), and then to exception + TCI6614, C6670, C6678: + CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt + CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt + CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt + CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt + CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt + CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt + CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt + CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt + CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt + CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt + CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt + CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt + CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt + CIC: 99 MSMC_dedc_nc_error Non-correctable soft error detected on SRAM read + CIC: 100 MSMC_scrub_nc_error Non-correctable soft error detected during scrub cycle + CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID + CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID + CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID + CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID + CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID + CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID + CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID + CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID + CIC: 110 DDR3_ERR DDR3 ECC Error Interrupt + TCI6614, C6670: + CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID + CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID + CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID + CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID + */ + KeyStone_CIC_event_map(gpCIC_regs, 0 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 2 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 3 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 4 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 5 , gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 16, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 18, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 19, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 20, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 21, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[0] |= + (1<<0 ) + |(1<<2 ) + |(1<<3 ) + |(1<<4 ) + |(1<<5 ) + |(1<<16) + |(1<<18) + |(1<<19) + |(1<<20) + |(1<<21); + + KeyStone_CIC_event_map(gpCIC_regs, 32, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 34, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 35, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[1] |= + (1<<(32-32)) + |(1<<(34-32)) + |(1<<(35-32)); + + KeyStone_CIC_event_map(gpCIC_regs, 99, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 100, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 102, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 103, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 104, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 105, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 106, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 107, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 108, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 109, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 110, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[3] |= + (1<<(99 -32*3)) + |(1<<(100-32*3)) + |(1<<(102-32*3)) + |(1<<(103-32*3)) + |(1<<(104-32*3)) + |(1<<(105-32*3)) + |(1<<(106-32*3)) + |(1<<(107-32*3)) + |(1<<(108-32*3)) + |(1<<(109-32*3)) + |(1<<(110-32*3)); + + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||TCI6614_EVM==DSP_Board_Type) + { + KeyStone_CIC_event_map(gpCIC_regs, 170, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 171, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 172, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 173, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[5] |= + (1<<(170-32*5)) + |(1<<(171-32*5)) + |(1<<(172-32*5)) + |(1<<(173-32*5)); + } + + /* ----------- Mapping MPU interrupt for different chips start -----------------------*/ + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type + ||C6678_EVM==DSP_Board_Type) + { + /* route the following system events to CIC out + CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt + CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt + CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt + CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt + */ + KeyStone_CIC_event_map(gpCIC_regs, 90, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 92, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 94, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 96, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[2] |= + (1<<(90 -32*2)) + |(1<<(92 -32*2)) + |(1<<(94 -32*2)); + gCIC_EXC_EN_MASK[3] |= + (1<<(96 -32*3)); + + /* 6618_6670 only */ + if(C6670_EVM==DSP_Board_Type + ||DUAL_NYQUIST_EVM==DSP_Board_Type) + { + /* + CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt + CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt + */ + KeyStone_CIC_event_map(gpCIC_regs, 174, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 180, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[5] |= + (1<<(174-32*5)) + |(1<<(180-32*5)); + } + } + + if(TCI6614_EVM==DSP_Board_Type) + { + /* route the following system events to CIC out + CIC: 23 MPU0~7 addressing violation interrupt combine output + CIC: 37 MPU0~7 protection violation interrupt combine output + */ + KeyStone_CIC_event_map(gpCIC_regs, 23, gCIC_EXC_out_num); + KeyStone_CIC_event_map(gpCIC_regs, 37, gCIC_EXC_out_num); + gCIC_EXC_EN_MASK[0] |= + (1<<23); + gCIC_EXC_EN_MASK[1] |= + (1<<(37 -32)); + + } + /* ----------- Mapping MPU interrupt for different chips end -----------------------*/ + + /* Enable Global host interrupts. */ + gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 1; + +} +/***************************************************************************** + Prototype : KeyStone_Exception_cfg + Description : Config the system err and external exception to generate the NMI. + Call this function as last step after all + configuration/initialization complete + Input : Bool bGlobalExceptionMaster. If TRUE, the global exception events + from CIC will be routed to exception model of this CPU core. + Output : None + Return Value : +*****************************************************************************/ +void KeyStone_Exception_cfg(Bool bGlobalExceptionMaster) +{ + + puts("Enable Exception handling..."); + + TSCL = 0; /* Enable the TSC */ + + memset(&exception_record, 0, sizeof(exception_record)); +#if 0 + /*Clear all CPU events*/ + gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; +#endif + /*clear memory fault*/ + gpCGEM_regs->L1PMPFCR = 1; + gpCGEM_regs->L1DMPFCR = 1; + gpCGEM_regs->L2MPFCR = 1; + gpXMC_regs->XMPFCR = 1; + + /*clear configuration bus error*/ + gpCGEM_regs->ICFGMPFCR= 1; + gpCGEM_regs->ECFGERRCLR= 1; + + /* clear the MDMAERR */ + gpCGEM_regs->MDMAERRCLR = 1; + + /*clear interrupt drop staus*/ + gpCGEM_regs->INTXCLR = 1; + + gpCGEM_regs->INTDMASK= ~IER; /*only monitor drop of enabled interrupts*/ + + /*enable events: + 10 MSMC_mpf_error_n MSMC Memory protection fault caused by local CorePac + 96 INTERR Dropped CPU interrupt event + 97 EMC_IDMAERR Invalid IDMA parameters + 110 MDMAERREVT XMC VBUSM error event + 113 PMC_ED Single bit error detected during DMA accesses L1P + 117 UMC_ED2 Uncorrected bit error detected LL2 + 119 SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control + 120 PMC_CMPA CPU memory protection fault for L1P + 121 PMC_DMPA DMA memory protection fault for L1P + 122 DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller) + 123 DMC_DMPA DMA memory protection fault for L1D + 124 UMC_CMPA CPU memory protection fault for LL2 + 125 UMC_DMPA DMA memory protection fault for LL2 + 126 EMC_CMPA CPU memory protection fault for other local configuration space between 0x01000000 - 0x01BFFFFF + 127 EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF + */ + gpCGEM_regs->EXPMASK[0]= ~(1<EXPMASK[1]= 0xFFFFFFFF; + gpCGEM_regs->EXPMASK[2]= 0xFFFFFFFF; + gpCGEM_regs->EXPMASK[3]= ~((1<<(CSL_GEM_INTERR - 96))| + (1<<(CSL_GEM_EMC_IDMAERR-96))| + (1<<(CSL_GEM_MDMAERREVT-96))| + (1<<(CSL_GEM_PMC_ED-96))| + (1<<(CSL_GEM_UMC_ED2-96))| + (1<<(CSL_GEM_SYS_CMPA-96))| + (1<<(CSL_GEM_PMC_CMPA-96))| + (1<<(CSL_GEM_PMC_DMPA-96))| + (1<<(CSL_GEM_DMC_CMPA-96))| + (1<<(CSL_GEM_DMC_DMPA-96))| + (1<<(CSL_GEM_UMC_CMPA-96))| + (1<<(CSL_GEM_UMC_DMPA-96))| + (1<<(CSL_GEM_EMC_CMPA-96))| + (1<<(CSL_GEM_EMC_BUSERR-96))); + + + if(bGlobalExceptionMaster) + { + /*enable exception events routed from CIC, + please note, this should be only configured for one CPU*/ + KeyStone_CIC_exception_events_mapping(); + gpCGEM_regs->EXPMASK[guwIntcCICExcEvtIdx>>5] &= (~(1<<(guwIntcCICExcEvtIdx&0x1F))); + } + + /*clear exception flag*/ + ECR = EFR; + IERR = 0; + + /*Eanble external exception, global exception enable*/ + TSR = TSR| + (1<>CSL_CGEM_MDMAERR_ERR_SHIFT; + if (1==err) { + puts(" MDMA read status error detected"); + } + else if (2==err) { + puts(" MDMA write status error detected"); + } + else if (3==err) { + puts(" CFG read status error detected"); + } + else if (4==err) { + puts(" CFG write status error detected"); + } + + printf(" XID (Transaction ID)= %d\n", + (ERR_REG & CSL_CGEM_MDMAERR_XID_MASK)>>CSL_CGEM_MDMAERR_XID_SHIFT); + + stat= (ERR_REG & CSL_CGEM_MDMAERR_STAT_MASK)>>CSL_CGEM_MDMAERR_STAT_SHIFT; + printf(" %s\n", bus_err_stat_str[stat]); +} + +/***************************************************************************** + Prototype : KeyStone_CIC_EXC_handler + Description : This function handle the exception events from CIC + Input : void + Output : None + Return Value : void + + History : + 1.Date : 2012/10/18 + Author : Zhan + Modification : Created function + + 2.Date : 2012/10/28 + Author : Brighton Feng + Modification : Add EDMA error processing + +*****************************************************************************/ +void KeyStone_CIC_EXC_handler() +{ + int i; + Uint32 status[4], status5 = 0; + + TDSP_Board_Type DSP_Board_Type; + + DSP_Board_Type= KeyStone_Get_dsp_board_type(); + + /*Step1: Disable CIC host interrupt*/ + KeyStone_CIC_disable_host_int(gpCIC_regs, gCIC_EXC_out_num); + + status[0]= gpCIC_regs->ENA_STATUS_REG[0]&gCIC_EXC_EN_MASK[0]; + status[1]= gpCIC_regs->ENA_STATUS_REG[1]&gCIC_EXC_EN_MASK[1]; + status[2]= gpCIC_regs->ENA_STATUS_REG[2]&gCIC_EXC_EN_MASK[2]; + status[3]= gpCIC_regs->ENA_STATUS_REG[3]&gCIC_EXC_EN_MASK[3]; + exception_record.status.ext_sts.CIC_STATUS[0]= status[0]; + exception_record.status.ext_sts.CIC_STATUS[1]= status[1]; + exception_record.status.ext_sts.CIC_STATUS[2]= status[2]; + exception_record.status.ext_sts.CIC_STATUS[3]= status[3]; + + /*Step2: clear system events*/ + gpCIC_regs->ENA_STATUS_REG[0]= status[0]; + gpCIC_regs->ENA_STATUS_REG[1]= status[1]; + gpCIC_regs->ENA_STATUS_REG[2]= status[2]; + gpCIC_regs->ENA_STATUS_REG[3]= status[3]; + + /* The different device INTC number is different, if read the non-exist space will + trigger the L1D memory protection error. + */ + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + status5 = gpCIC_regs->ENA_STATUS_REG[5]&gCIC_EXC_EN_MASK[5]; + exception_record.status.ext_sts.CIC_STATUS[5]= status5; + + /*Step2: clear system events*/ + gpCIC_regs->ENA_STATUS_REG[5]= status5 ; + } + + /*----------------------------EDMA error-----------------------------*/ + /* + CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt + CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt + CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt + CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt + CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt*/ + if(status[0]&0x3D) + EDMA_error_handler(1, status[0]&0x3D); + + /* + CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt + CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt + CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt + CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt + CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt*/ + if((status[0]>>16)&0x3D) + EDMA_error_handler(2, (status[0]>>16)&0x3D); + + /* + CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt + CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt + CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt*/ + if(status[1]&0xD) + EDMA_error_handler(0, status[1]&0xD); + + /*----------------------------MPU error-----------------------------*/ + if(TCI6614_EVM == DSP_Board_Type) + { + //CIC: 23 MPU0~7 addressing violation interrupt combine output + //CIC: 37 MPU0~7 protection violation interrupt combine output + if((status[0]&(1<<23))||(status[1]&(1<<(37-32)))) + { + for(i=0; i<8; i++) + { + /*MPU5 (for BCP) of TCI6614 is only accessible + when BCP is enabled through PSC*/ + if((5==i)&& + ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || + (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) + continue; + + if(gpMPU_regs[i]->INT_RAW_STATUS_SET & 0x3) + { + KeyStone_peripherals_MPU_excepiton_handler(i); + } + } + + /*The MPU events in TCI6614 are different from other KeyStone + devices. All the MPU0~7 events are combined into single event + and connected to the CIC0 as one system event. + We have to clear the MPU event flag at the source level first + and then are able to clear the CIC flags because the INTD for the + MPU events is for the combination purpose but do not convert + the level interrupt to pulse.*/ + /*clear system events*/ + gpCIC_regs->ENA_STATUS_REG[0]= status[0]; + gpCIC_regs->ENA_STATUS_REG[1]= status[1]; + } + } + else + { + //CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(90-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(0); + } + //CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(92-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(1); + } + //CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt + if(status[2]&(1<<(94-64))) + { + KeyStone_peripherals_MPU_excepiton_handler(2); + } + //CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt + if(status[3]&(1<<(96-96))) + { + KeyStone_peripherals_MPU_excepiton_handler(3); + } + + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type)) + { + //CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt + //CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt + if(status5&(1<<(174-160))) + { + KeyStone_peripherals_MPU_excepiton_handler(4); + } + if(status5&(1<<(180-160))) + { + KeyStone_peripherals_MPU_excepiton_handler(5); + } + } + } + + /*----------------------------MSMC error-----------------------------*/ + //CIC: 99 MSMC_dedc_nc_error Non-correctable (2-bit) soft error detected on SRAM read + if(status[3]&(1<<(99-96))) + { + KeyStone_SL2_EDC_handler(); + } + //CIC: 100 MSMC_scrub_nc_error Non-correctable (2-bit) soft error detected during scrub cycle + if(status[3]&(1<<(100-96))) + { + KeyStone_SL2_EDC_handler(); + } + + /* + CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID + CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID + CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID + CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID + CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID + CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID + CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID + CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID*/ + if((status[3]>>(102-96))&0xFF) + KeyStone_MSMC_protection_exception_handler(); + + if((C6670_EVM == DSP_Board_Type) + ||(DUAL_NYQUIST_EVM == DSP_Board_Type) + ||(TCI6614_EVM == DSP_Board_Type)) + { + /* + CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID + CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID + CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID + CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID*/ + if((status5>>(170-160))&0xF) + KeyStone_MSMC_protection_exception_handler(); + + } + + /*----------------------------DDR ECC error-------------------------*/ + //CIC: 110 DDR3_ERR DDR3_EMIF Error Interrupt + if(status[3]&(1<<(110-96))) + { + printf(" DDR ECC error happened during "); + + exception_record.status.ext_sts.info.memory.fault_status.DDR_IRQSTATUS_SYS= + gpDDR_regs->IRQSTATUS_SYS; + + if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK) + printf("read "); + if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK) + printf("write "); + printf(".\n"); + + //clear the status + gpDDR_regs->IRQSTATUS_SYS= CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK + |CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK; + } + + /*Step3: Enable the CIC host interrupt */ + KeyStone_CIC_enable_host_int(gpCIC_regs, gCIC_EXC_out_num); + +} + +/***************************************************************************** + Prototype : KeyStone_EXC_external + Description : external exception processing + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_EXC_external(void) +{ + int i; + unsigned int INTXSTAT, flag[4]; + + for(i= 0; i<4; i++) + { + flag[i] = gpCGEM_regs->MEXPFLAG[i]; + if(flag[i]) + { + exception_record.status.ext_sts.MEXPFLAG[i]= flag[i]; + printf("External exception happened. MEXPFLAG[%d]=0x%x.\n", + i, flag[i]); + gpCGEM_regs->EVTCLR[i] = flag[i]; + } + } + + if(0 == (flag[0]|flag[1]|flag[2]|flag[3])) + { + puts("Enter external Exception service routine, but external excpetion flage is 0!"); + return; + } + + /*Exception events routed from CIC*/ + if(flag[guwIntcCICExcEvtIdx>>5] & (1<<(guwIntcCICExcEvtIdx&0x1F))) + { + KeyStone_CIC_EXC_handler(); + } + + /*MSMC memory protection exception*/ + if(flag[0]&(1<INTXSTAT; + exception_record.status.ext_sts.info.INTXSTAT= INTXSTAT; + + if(INTXSTAT&CSL_CGEM_INTXSTAT_DROP_MASK) + printf(" Event 96: DSP Interrupt %d (INTC input Event %d) dropped\n", + (INTXSTAT&CSL_CGEM_INTXSTAT_CPUINT_MASK)>>CSL_CGEM_INTXSTAT_CPUINT_SHIFT, + (INTXSTAT&CSL_CGEM_INTXSTAT_SYSINT_MASK)>>CSL_CGEM_INTXSTAT_SYSINT_SHIFT); + } + + if(flag[3]&(1<<(CSL_GEM_EMC_IDMAERR-96))) + puts(" Event 97: EMC_IDMAERR Invalid IDMA parameters"); + + /*MDMA XMC VBUSM error*/ + if(flag[3]&(1<<(CSL_GEM_MDMAERREVT-96))) + { + puts(" Event 110: MDMAERREVT XMC VBUSM error event"); + if(gpXMC_regs->XMPFSR) + { + /*XMC protection error*/ + memory_protection_exception_handler(gpXMC_regs->XMPFAR, gpXMC_regs->XMPFSR); + gpXMC_regs->XMPFCR = 1; + } + else + { + /*other VBUSM error*/ + Bus_error_handler(gpCGEM_regs->MDMAERR); + } + /* clear the MDMAERR */ + gpCGEM_regs->MDMAERRCLR = 1; + } + + /*L1P Single bit error detected during DMA read*/ + if(flag[3]&(1<<(CSL_GEM_PMC_ED-96))) + { + puts(" Event 113: PMC_ED Single bit error detected during DMA read"); + L1P_ED_handler(); + } + + /*LL2 Uncorrected bit error detected*/ + if(flag[3]&(1<<(CSL_GEM_UMC_ED2-96))) + { + puts(" Event 117: UMC_ED2 Uncorrected bit error detected"); + LL2_EDC_handler(FALSE); + } + + /*local register memory protection exception*/ + if(flag[3]&(1<<(CSL_GEM_SYS_CMPA-96))) + { + puts(" Event 119: SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control"); + } + + /*L1P memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_PMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_PMC_CMPA-96))) + puts(" Event 120: PMC_CMPA CPU memory protection fault for L1P"); + if(flag[3]&(1<<(CSL_GEM_PMC_DMPA-96))) + puts(" Event 121: PMC_DMPA DMA memory protection fault for L1P"); + memory_protection_exception_handler(gpCGEM_regs->L1PMPFAR, gpCGEM_regs->L1PMPFSR); + gpCGEM_regs->L1PMPFCR = 1; + } + + /*L1D memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_DMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_DMC_CMPA-96))) + puts(" Event 122: DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller)"); + if(flag[3]&(1<<(CSL_GEM_DMC_DMPA-96))) + puts(" Event 123: DMC_DMPA DMA memory protection fault for L1D"); + memory_protection_exception_handler(gpCGEM_regs->L1DMPFAR, gpCGEM_regs->L1DMPFSR); + gpCGEM_regs->L1DMPFCR = 1; + } + + /*LL2 memory protection exception*/ + if(flag[3]&(3<<(CSL_GEM_UMC_CMPA-96))) + { + if(flag[3]&(1<<(CSL_GEM_UMC_CMPA-96))) + puts(" Event 124: UMC_CMPA CPU memory protection fault for L2 "); + if(flag[3]&(1<<(CSL_GEM_UMC_DMPA-96))) + puts(" Event 125: UMC_DMPA DMA memory protection fault for L2 "); + memory_protection_exception_handler(gpCGEM_regs->L2MPFAR, gpCGEM_regs->L2MPFSR); + gpCGEM_regs->L2MPFCR = 1; + } + + /*local registers protection exception*/ + if(flag[3]&(1<<(CSL_GEM_EMC_CMPA-96))) + { + puts(" Event 126: EMC_CMPA CPU memory protection fault for local configuration space between 0x01000000-0x01BFFFFF"); + memory_protection_exception_handler(gpCGEM_regs->ICFGMPFAR, gpCGEM_regs->ICFGMPFSR); + gpCGEM_regs->ICFGMPFCR= 1; + } + + /*external configuration bus error*/ + if(flag[3]&(Uint32)(1<<(CSL_GEM_EMC_BUSERR-96))) + { + puts(" Event 127: EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF"); + Bus_error_handler(gpCGEM_regs->ECFGERR); + gpCGEM_regs->ECFGERRCLR= 1; + } +} + +char * internal_exception_str[]= +{ + "Instruction fetch exception", + "Fetch packet exception", + "Execute packet exception", + "Opcode exception", + "Resource conflict exception", + "Resource access exception", + "Privilege exception", + "SPLOOP buffer exception", + "Missed stall exception" +}; + +/***************************************************************************** + Prototype : EXC_internal + Description : internal exception handler + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +/*internal exception handler*/ +void EXC_internal(void) +{ + int i; + unsigned int ierr; + + /*record IERR */ + ierr = IERR; + exception_record.status.IERR= ierr; + + if(ierr) + { + /*Clear internal excpeiton flag*/ + IERR= 0; + + printf("internal excpetion happened. IERR=0x%x.\n", ierr); + for(i=0; i<9; i++) + { + if((ierr>>i)&1) + printf(" %s\n", internal_exception_str[i]); + } + if (ierr & CSL_CHIP_IERR_IFX_MASK) { + /* L1P EDC Processing*/ + L1P_ED_handler(); + } + } + else + puts("Enter Internal Exception service routine, but internal excpetion flage is 0!"); + +} +/***************************************************************************** + Prototype : EXC_nmi + Description : NMI processing + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +void EXC_NMI(void) +{ + puts("NMI exception happened, normally you should reset the DSP to recover from the problem!"); +} + +/***************************************************************************** + Prototype : EXC_swgen + Description : software generated exception handler + Input : void + Output : None + Return Value : +*****************************************************************************/ +void EXC_swgen(void) +{ + puts("Software generated exception happened."); +} + +/***************************************************************************** + Prototype : Exception_service_routine + Description : Exception service routine + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +#pragma NMI_INTERRUPT( Exception_service_routine ); +void Exception_service_routine(void) +{ + unsigned int efr, nrp, ntsr, tscl, tsch, irp, itsr; + + /*record timestamp*/ + tscl = TSCL; + exception_record.TSCL= tscl; + tsch = TSCH; + exception_record.TSCH= tsch; + + nrp = NRP; /*record NRP */ + exception_record.NRP= nrp; + ntsr = NTSR; /*record NTSR */ + exception_record.NTSR= ntsr; + efr = EFR; /*record EFR */ + exception_record.EFR= efr; + + irp = IRP; /*record IRP */ + itsr = ITSR; /*record ITSR */ + exception_record.IRP= irp; + exception_record.ITSR= itsr; + + if(efr) + { + /*Clear excpeiton flag*/ + ECR = efr; + + /*check all possible exceptions*/ + if (efr & CSL_CHIP_EFR_OXF_MASK) { + /* S/W generated exception */ + EXC_swgen(); + } + if (efr & CSL_CHIP_EFR_IXF_MASK) { + /* internal exception */ + EXC_internal(); + } + if (efr & CSL_CHIP_EFR_EXF_MASK) { + /* external exception */ + KeyStone_EXC_external(); + } + if (efr & CSL_CHIP_EFR_NXF_MASK) { + /* legacy NMI exception */ + EXC_NMI(); + } + } + else + puts("Enter Exception service routine, but excpetion flage is 0!"); + + printf("NRP=0x%x, NTSR=0x%x, IRP=0x%x, ITSR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", + nrp, ntsr, irp, itsr, tsch, tscl); + + printf(" B3=0x%x, A4=0x%x, B4= 0x%x, B14= 0x%x, B15= 0x%x\n", + exception_record.B3, exception_record.A4, + exception_record.B4, exception_record.B14, + exception_record.B15); + + /* + It is not always possible to safely exit the exception handling routine. Conditions that + can prevent a safe return from exceptions include: + 1. SPLOOPs that are terminated by an exception cannot be resumed correctly. The + SPLX bit in NTSR should be verified to be 0 before returning. + 2. Exceptions that occur when interrupts are blocked cannot be resumed correctly. + The IB bit in NTSR should be verified to be 0 before returning. + 3. Exceptions that occur at any point in the code that cannot be interrupted safely + (for example, a tight loop containing multiple assignments) cannot be safely + returned to. The compiler will normally disable interrupts at these points in the + program; check the GIE bit in NTSR to be 1 to verify that this condition is met. + 4. NRP is not in valid address space*/ + if((ntsr&CSL_CHIP_TSR_SPLX_MASK) + ||(ntsr&CSL_CHIP_TSR_IB_MASK) + ||(0==(ntsr&CSL_CHIP_TSR_GIE_MASK)) + ||(0x800000>NRP)) + { + puts("Exception happened at a place can not safely return!"); + //while(1); //trap + exit(0); + } + +} + +/***************************************************************************** + Prototype : Nested_Exception_service_routine + Description : Nested Exception service routine + When a non-maskable exception happens in the first exception service routine, + then the reset vector is used when redirecting program execution to service the second + exception. In this case, NTSR and NRP are left unchanged. TSR is copied to ITSR and + the current PC is copied to IRP. TSR is set to the default exception processing value and + the NMIE bit in IER is cleared in this case preventing any further external exceptions. + Input : void + Output : None + Return Value : + + History : + 1.Date : 2010/12/29 + Author : Brighton Feng + Modification : Created function + +*****************************************************************************/ +interrupt void Nested_Exception_service_routine(void) +{ + unsigned int tscl, tsch; + + /*record timestamp*/ + tscl = TSCL; + tsch = TSCH; + + if(0==exception_record.TSCL) + exception_record.TSCL= tscl; + if(0==exception_record.TSCH) + exception_record.TSCH= tsch; + if(0==exception_record.NRP) + exception_record.NRP= NRP; + if(0==exception_record.NTSR) + exception_record.NTSR= NTSR; + if(0==exception_record.EFR) + exception_record.EFR= EFR; + if(0==exception_record.status.IERR) + exception_record.status.IERR= IERR; + + exception_record.IRP= IRP; + exception_record.ITSR= ITSR; + + printf("Nested exception happened! IRP=0x%x, ITSR=0x%x\n", + IRP, ITSR); + + printf("NRP=0x%x, NTSR=0x%x, EFR=0x%x, IERR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", + NRP, NTSR, EFR, IERR, tsch, tscl); + + while(1); //trap +// exit(0); +} + +/*=========================other utility functions==========================*/ +/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ +void CPU_interrupt_init() +{ + //clear interrupt and excpetion events + ICR = IFR; + ECR = EFR; + IER= 3; //disable all interrupts + + /* disable event combine */ + gpCGEM_regs->EVTMASK[0] = 0xffffffff; + gpCGEM_regs->EVTMASK[1] = 0xffffffff; + gpCGEM_regs->EVTMASK[2] = 0xffffffff; + gpCGEM_regs->EVTMASK[3] = 0xffffffff; + + /*Clear all CPU events*/ + gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; + + /*Interrupt Service Table Pointer to begining of LL2 memory*/ + ISTP= 0x800000; +} + +/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ +void CPU_interrupt_enable(Uint32 uiIER_en_mask) +{ + ICR= uiIER_en_mask; + IER |= uiIER_en_mask; + + //enable GIE + TSR = TSR|1; +} + +/***************************************************************************** + Prototype : KeyStone_get_device_info + Description : Get device information + Input : None + Output : None + Return Value : + + History : + 1.Date : 2010/12/12 + Author : Brighton Feng + Modification : Created function + 2.Date : 2014/12/2 + Author : Brighton Feng + Modification : Update to parser device type, boot mode, endian information, + speed grade, required CVDD + +*****************************************************************************/ +//get device speed grade from the EFUSE register +void KeyStone_get_device_speed_grade() +{ + Uint32 uiDevSpeed, uiSpeedCode; + + uiSpeedCode= (DEVSPEED&DEVSPEED_DSP_SPEED_MASK)>>DEVSPEED_DSP_SPEED_SHIFT; + + if(uiSpeedCode&DEVSPEED_800_MHZ_MASK_H) uiDevSpeed= 800; + else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_H) uiDevSpeed= 1000; + else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_H) uiDevSpeed= 1200; + else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_H) uiDevSpeed= 1250; + else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_H) uiDevSpeed= 1400; + else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_L) uiDevSpeed= 1400; + else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_L) uiDevSpeed= 1250; + else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_L) uiDevSpeed= 1200; + else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_L) uiDevSpeed= 1000; + else uiDevSpeed= 800; + + printf("Device speed grade = %dMHz.\n", uiDevSpeed); +} + +char * device_type_str[]= +{ + "TCI6616", + "C6670/TCI6618", + "C6678/TCI6608", + "TCI6614", + "unknown" +}; +char * endian_str[]= +{ + "big", + "little" +}; +char * boot_mode_str[]= +{ + "No boot or EMIF16(NOR FLASH) or UART", + "Serial Rapid I/O", + "Ethernet (SGMII)", + "Ethernet (SGMII) or NAND FLASH", + "PCIE", + "I2C", + "SPI", + "HyperLink" + }; +char * input_clk_str[]= +{ + "50MHz", + "66.67MHz", + "80MHz", + "100MHz", + "156.25MHz", + "250MHz", + "312.5MHz", + "122.88MHz", + "bypassed" +}; +void KeyStone_get_device_info() +{ + char * boot_mode; + Uint8 ucBootMode, ucBootMaster; + Uint32 uiVID; + Uint8 ucPLL_cfg= 8; //8 means bypassed + Uint32 * DieID= (Uint32 *)&gpBootCfgRegs->DIE_ID_REG0; + Uint32 uiJTAG_ID = gpBootCfgRegs->DEVICE_ID_REG0; + Uint32 uiDevStat = gpBootCfgRegs->BOOT_REG0; + + gDSP_board_type=KeyStone_Get_dsp_board_type(); + + ucBootMode= (uiDevStat&DEVSTAT_BOOTMODE_MASK)>>DEVSTAT_BOOTMODE_SHIFT; + ucBootMaster= (uiDevStat&DEVSTAT_BOOTMASTER_MASK)>>DEVSTAT_BOOTMASTER_SHIFT; + + if((TCI6614_EVM==gDSP_board_type)&&(1==ucBootMaster)) + { + boot_mode= "ARM"; //ARM boot + } + else + boot_mode= boot_mode_str[ucBootMode]; + + //PLL is not configured with SPI and I2C master boot mode + if((5!=ucBootMode)&&(6!=ucBootMode)) + ucPLL_cfg= (uiDevStat&DEVSTAT_SYSPLL_MASK)>>DEVSTAT_SYSPLL_SHIFT; + + printf("JTAG ID= 0x%08x. This is %s device, version variant = %d.\n", uiJTAG_ID, + device_type_str[gDSP_board_type], uiJTAG_ID>>28); + + printf("DEVSTAT= 0x%08x. %s endian, %s boot, PLL configuration implies the input clock for core is %s.\n", + uiDevStat, endian_str[uiDevStat&DEVSTAT_LENDIAN_MASK], boot_mode, + input_clk_str[ucPLL_cfg]); + + uiVID= (gpPSC_regs->VCNTLID&CSL_PSC_VCNTLID_VCNTL_MASK)>>CSL_PSC_VCNTLID_VCNTL_SHIFT; + printf("SmartReflex VID= %d, required core voltage= %.3fV.\n", uiVID, 0.7+(float)uiVID*0.41/64.f); + + printf("Die ID= 0x%08x, 0x%08x, 0x%08x, 0x%08x\n", DieID[0], DieID[1], DieID[2], DieID[3]); + + KeyStone_get_device_speed_grade(); +} +/***************************************************************************** + Prototype : KeyStone_common_device_init + Description : common initialization for internal modules in K2 device + enable memory protection interrupts, EDC for MSMC RAM + History : + 1.Date : July 11, 2014 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_common_device_init() +{ + int i; + KeyStone_get_device_info(); + + /* enable common MPU interrupts */ + for(i=0; i<4; i++) + { + KeyStone_MPU_interrupt_enable(i); + } + + /*Enable MSMC EDC and setup scrubbing cycle counter= 255*1024*/ + KeyStone_SL2_EDC_enable(255); +} + +/***************************************************************************** + Prototype : KeyStone_common_CPU_init + Description : common initialization for internal modules in K2 device + enable TSC, EDC for local RAM; clear cache; protect L1 as cache + History : + 1.Date : September 1, 2014 + Author : Brighton Feng + Modification : Created function +*****************************************************************************/ +void KeyStone_common_CPU_init() +{ + TSC_init(); //initialize TSC to measure cycle + + /*clear all interrupt flag/status, setup ISTP to begining of LL2*/ + CPU_interrupt_init(); + + /*clean cache from previous run, not required from power on or cold reset*/ + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + _mfence(); + _mfence(); + + /* protect L1 as cache */ + L1_cache_protection(); + + //Enable MSMC Memory protection error interrupt for local core, refer to MSMC user guide section3.8 + KeyStone_MSMC_MP_interrupt_en(1< +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/*----------------------PLL registers definition----------------*/ +#define PLLCTL0_PLLD_SHIFT (0) +#define PLLCTL0_PLLD_MASK (0x3F<>4) | 0x80000000) + +/*max number in two numbers*/ +#define MAX(a, b) (a>b?a:b) +/*min number in two numbers*/ +#define MIN(a, b) (a0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline void WritebackCache(void * blockPtr, Uint32 byteCnt) +{ + if(byteCnt>0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbL2((void *)blockPtr, byteCnt, CACHE_WAIT); + } + _mfence(); + _mfence(); +} + +static inline void WritebackAllCache(void * blockPtr) +{ + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbAllL1d(CACHE_WAIT);; + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbAllL2(CACHE_WAIT); + } + _mfence(); + _mfence(); +} + +static inline void WritebackInvalidCache(void * blockPtr, Uint32 byteCnt) +{ +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + Uint32 uiOldGIE= _disable_interrupts(); +#endif + + if(byteCnt>0xFFFF*4) + byteCnt= 0xFFFF*4; + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbInvL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + CACHE_wbInvL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline void WritebackInvalidAllCache(void * blockPtr) +{ +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + Uint32 uiOldGIE= _disable_interrupts(); +#endif + + if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 + { + CACHE_wbInvAllL1d(CACHE_WAIT);//CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + else if((Uint32)blockPtr>=0x10000000) //DDR or other cores + { + //CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); + CACHE_wbInvAllL2(CACHE_WAIT); + CSL_XMC_invalidatePrefetchBuffer(); + } + _mfence(); + _mfence(); + +#if CACHE_DISABLE_INT +/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations +Issue" described in errata of some devices*/ + asm(" nop 8"); + asm(" nop 8"); + _restore_interrupts(uiOldGIE); //restore interrupt +#endif +} + +static inline unsigned int SWAP_ENDIAN(unsigned int byte_index) +{ +#ifdef _BIG_ENDIAN + return ((byte_index&0xFFFFFFFC)+(3-byte_index&3)); +#else + return byte_index; +#endif +} + +static inline void KeyStone_CIC_clear_system_event(CSL_CPINTCRegs* cpIntcRegs, + int input_event_num) +{ + volatile Uint32 dummy_value; + + /*clear input interrupts events*/ + cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->STATUS_CLR_INDEX_REG; +} + +static inline void KeyStone_CIC_disable_host_int(CSL_CPINTCRegs* cpIntcRegs, + int host_int_num) +{ + volatile Uint32 dummy_value; + + /* Disable the host interrupt */ + cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG = host_int_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG; +} + +static inline void KeyStone_CIC_enable_host_int(CSL_CPINTCRegs* cpIntcRegs, + int host_int_num) +{ + volatile Uint32 dummy_value; + + /* Enable the host interrupt */ + cpIntcRegs->HINT_ENABLE_SET_INDEX_REG = host_int_num; + + /*dummy read to make sure the previous write data land into the register*/ + dummy_value= cpIntcRegs->HINT_ENABLE_SET_INDEX_REG; +} + +static inline void KeyStone_CIC_event_map(CSL_CPINTCRegs* cpIntcRegs, + int input_event_num, int out_num) +{ + /*Map input event to output*/ + cpIntcRegs->CH_MAP[SWAP_ENDIAN(input_event_num)]= out_num; + + /*clear input interrupts events*/ + cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; + + /*enable input interrupts events*/ + cpIntcRegs->ENABLE_SET_INDEX_REG= input_event_num; + + /*enable output*/ + cpIntcRegs->HINT_ENABLE_SET_INDEX_REG= out_num; +} + + +typedef enum +{ + DUAL_NYQUIST_EVM = 0, + C6670_EVM, + C6678_EVM, + TCI6614_EVM, + C6657_EVM, + UNKNOWN +}TDSP_Board_Type; + +extern TDSP_Board_Type gDSP_board_type; + +static inline TDSP_Board_Type KeyStone_Get_dsp_board_type() +{ + Uint32 deviceID= gpBootCfgRegs->DEVICE_ID_REG0&0x0FFFFFFF; + + gDSP_board_type= UNKNOWN; + if(0x0009D02F == deviceID) + gDSP_board_type= DUAL_NYQUIST_EVM; + if(0x0B94102F == deviceID) + { + gDSP_board_type= C6670_EVM; + //DSP_Board_Type= DUAL_NYQUIST_EVM; + } + if(0x0009E02F == deviceID) + gDSP_board_type= C6678_EVM; + if(0x0B96202F == deviceID) + gDSP_board_type= TCI6614_EVM; + if(0x0B97A02F == deviceID) + gDSP_board_type= C6657_EVM; + + return gDSP_board_type; +} + +static inline Uint32 KeyStone_Get_DSP_Number() +{ + TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); + + if(DUAL_NYQUIST_EVM==DSP_Board_Type) + { + /*Nyquist EVM use boot configure pin 4 and 5 to identify DSPs*/ + return (( gpBootCfgRegs->BOOT_REG0 >> (3+1) ) & 0x03); + } + + /*if use DNUM to differentiate DSPs for two DSPs test, + the program must be run on core 0 of DSP 0 and core 1 of DSP1*/ + return DNUM; +} + +/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ +extern void CPU_interrupt_init(); +/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ +extern void CPU_interrupt_enable(Uint32 uiIER_en_mask); + +//get device speed grade from the EFUSE register +extern void KeyStone_get_device_speed_grade(); + +/*Get device information including device type, boot mode, endian information, +speed grade, required voltage...*/ +extern void KeyStone_get_device_info(); + +/*common initialization for internal modules in K2 device. +enable memory protection interrupts, EDC for MSMC RAM*/ +extern void KeyStone_common_device_init(); + +/* enable TSC, EDC for local RAM; clear cache; protect L1 as cache */ +extern void KeyStone_common_CPU_init(); + + +#endif diff --git a/bsp/ti-tms320c6678/readme.txt b/bsp/ti-tms320c6678/readme.txt index 3309207357..84f608122c 100644 --- a/bsp/ti-tms320c6678/readme.txt +++ b/bsp/ti-tms320c6678/readme.txt @@ -1,3 +1,4 @@ - 本工程使用TI公司编译器CCS5.5进行编译,工程中使用到了TI官方提供的K1_STK_v1.1, -如有需要的请到TI官方论坛自行下载,并将K1_STK_v1.1中的KeyStone_common.c和KeyStone_common.h文件 -放置到本工程的driver目录下。 \ No newline at end of file + 本工程使用TI公司编译器CCS5.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6, +我的安装路径为C盘。 +"C:\ti\pdk_C6678_1_1_2_6\packages" +"C:\ti\pdk_C6678_1_1_2_6\packages\ti\csl" \ No newline at end of file diff --git a/libcpu/ti-dsp/c6x/context.asm b/libcpu/ti-dsp/c6x/context.asm index 2a57e9414d..aa7a138887 100644 --- a/libcpu/ti-dsp/c6x/context.asm +++ b/libcpu/ti-dsp/c6x/context.asm @@ -18,11 +18,6 @@ ;----------------------------------------------------------- DP .set B14 SP .set B15 - -;----------------------------------------------------------- -; extern variable -;----------------------------------------------------------- - .ref rt_system_stack_top ; ;----------------------------------------------------------- ; @@ -165,8 +160,7 @@ rt_hw_context_switch_to: LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) NOP 2 MV B8,B0 - [B0] B _rt_thread_interrupt_stack - NOP 5 + [B0] BNOP _rt_thread_interrupt_stack, 5 ; ; this maybe do better ; @@ -275,7 +269,6 @@ rt_interrupt_context_restore: NOP 4 CMPEQ 1,A1,A2 [A2] BNOP rt_preempt_context_restore,5 - NOP 5 LDDW .D2T2 *++SP[1],B9:B8 ; get TSR (B9) LDDW .D2T2 *++SP[1],B11:B10 ; get RILC (B11) and ILC (B10) LDDW .D2T2 *++SP[1],B13:B12 ; get PC (B13) and CSR (B12) diff --git a/libcpu/ti-dsp/c6x/contextinc.asm b/libcpu/ti-dsp/c6x/contextinc.asm index d51211ae9e..3bc6afafc6 100644 --- a/libcpu/ti-dsp/c6x/contextinc.asm +++ b/libcpu/ti-dsp/c6x/contextinc.asm @@ -8,6 +8,11 @@ ; 2021-11-16 Dystopia the first version ; +;----------------------------------------------------------- +; extern variable +;----------------------------------------------------------- + .ref rt_system_stack_top + ;----------------------------------------------------------- ; macro definition ;----------------------------------------------------------- diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c index 2be2f88313..1f532f6c32 100644 --- a/libcpu/ti-dsp/c6x/interrupt.c +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -26,7 +26,7 @@ rt_uint32_t rt_thread_switch_interrupt_flag; void rt_hw_interrupt_init(void) { // initial system trap - rt_trap_init(); + //rt_trap_init(); /* init exceptions table */ rt_memset(isr_table, 0x00, sizeof(isr_table)); diff --git a/libcpu/ti-dsp/c6x/intexc.asm b/libcpu/ti-dsp/c6x/intexc.asm index 2490977331..81a77426ec 100644 --- a/libcpu/ti-dsp/c6x/intexc.asm +++ b/libcpu/ti-dsp/c6x/intexc.asm @@ -65,14 +65,6 @@ SP .set B15 ;----------------------------------------------------------- ; -;----------------------------------------------------------- -; extern variable -;----------------------------------------------------------- - .ref rt_system_stack_top -; -;----------------------------------------------------------- -; - ;----------------------------------------------------------- ; interrupt macro definition ;----------------------------------------------------------- diff --git a/libcpu/ti-dsp/c6x/stack.c b/libcpu/ti-dsp/c6x/stack.c index 3fe3377a1c..05e9534538 100644 --- a/libcpu/ti-dsp/c6x/stack.c +++ b/libcpu/ti-dsp/c6x/stack.c @@ -31,8 +31,8 @@ extern rt_uint32_t rt_hw_get_current_dp(void); rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, rt_uint8_t *stack_addr, void *texit) { - rt_hw_thread_stack_register *thread_context; - rt_uint32_t stk; + rt_hw_thread_stack_register *thread_context = RT_NULL; + rt_uint32_t stk = 0; stack_addr += sizeof(rt_uint32_t); stack_addr = (rt_uint8_t *)RT_ALIGN_DOWN((rt_uint32_t)stack_addr, 8); diff --git a/libcpu/ti-dsp/c6x/trap.h b/libcpu/ti-dsp/c6x/trap.h index 12734df4a7..d895344728 100644 --- a/libcpu/ti-dsp/c6x/trap.h +++ b/libcpu/ti-dsp/c6x/trap.h @@ -90,8 +90,9 @@ extern int __ffs(int val); static inline int fls(int x) { if (!x) + { return 0; - + } return 32 - __fls(x); } @@ -107,8 +108,9 @@ static inline int fls(int x) static inline int ffs(int x) { if (!x) + { return 0; - + } return __ffs(x) + 1; } -- cgit v1.3.1 From 466f9ad4e32873008eb6bbd97b4d2ac65e87c7ee Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 15 Dec 2021 10:43:06 +0800 Subject: 删除依赖TI的KeyStone_common.c文件 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/board.c | 4 +- bsp/ti-tms320c6678/common/KeyStone_common.c | 4355 --------------------------- bsp/ti-tms320c6678/common/KeyStone_common.h | 1090 ------- bsp/ti-tms320c6678/common/common.c | 201 ++ bsp/ti-tms320c6678/common/common.h | 110 + bsp/ti-tms320c6678/driver/drv_timer.c | 9 +- bsp/ti-tms320c6678/driver/drv_timer.h | 3 + libcpu/ti-dsp/c6x/c66xx.h | 28 +- libcpu/ti-dsp/c6x/interrupt.c | 5 + 9 files changed, 345 insertions(+), 5460 deletions(-) delete mode 100644 bsp/ti-tms320c6678/common/KeyStone_common.c delete mode 100644 bsp/ti-tms320c6678/common/KeyStone_common.h create mode 100644 bsp/ti-tms320c6678/common/common.c create mode 100644 bsp/ti-tms320c6678/common/common.h diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c index 51a21f6cd8..0e622765da 100644 --- a/bsp/ti-tms320c6678/applications/board.c +++ b/bsp/ti-tms320c6678/applications/board.c @@ -11,7 +11,7 @@ #include "board.h" #include "interrupt.h" #include "drv_timer.h" -#include "KeyStone_common.h" +#include "common.h" #include @@ -21,7 +21,7 @@ void rt_hw_board_init(void) { // initial CPU core - KeyStone_common_CPU_init(); + keystone_cpu_init(); // initial interrupt controller rt_hw_interrupt_init(); diff --git a/bsp/ti-tms320c6678/common/KeyStone_common.c b/bsp/ti-tms320c6678/common/KeyStone_common.c deleted file mode 100644 index bfa6fbac3c..0000000000 --- a/bsp/ti-tms320c6678/common/KeyStone_common.c +++ /dev/null @@ -1,4355 +0,0 @@ -/****************************************************************************** - - Copyright (C), 2001-2012, Texas Instrument. - - ****************************************************************************** - File Name : KeyStone_common.c - Version : Initial Draft - Author : Brighton Feng - Created : 2010-12-12 - Last Modified : - Description : KeyStone common miscellaneous functions and definitions - History : - 1.Date : 2010-12-12 - Author : Brighton Feng - Modification: Created file - - 2.Date : 2012-10-6 - Author : Brighton Feng - Modification : Add memory protection and EDC configuration - - 3.Date : 2014-12-8 - Author : Brighton Feng - Modification : Add common device, CPU, interrupt initialization functions. - Print device information including device type, speed grade, - boot mode, required voltage, ID�� - Add EDMA enable/disable functions. - To support square wave generation by timer. -******************************************************************************/ - -#include -#include -#include -#include -#include -#include -#include -#include -#include "CSL_msmc.h" -#include "CSL_msmcAux.h" -#include "KeyStone_common.h" - -/*----------------------------------------------* - * external variables * - *----------------------------------------------*/ - -/*----------------------------------------------* - * external routine prototypes * - *----------------------------------------------*/ - -/*----------------------------------------------* - * internal routine prototypes * - *----------------------------------------------*/ - -/*----------------------------------------------* - * project-wide global variables * - *----------------------------------------------*/ -CSL_XmcRegs * gpXMC_regs = (CSL_XmcRegs *) CSL_XMC_CONFIG_REGS; -CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; -CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; -CSL_PllcRegs * gpPLLC_regs = (CSL_PllcRegs * )CSL_PLL_CONTROLLER_REGS; -CSL_PscRegs * gpPSC_regs = (CSL_PscRegs *)CSL_PSC_REGS; -CSL_MsmcRegs * gpMSMC_regs = (CSL_MsmcRegs *)CSL_MSMC_CONFIG_REGS; -CSL_GpioRegs * gpGPIO_regs= (CSL_GpioRegs * )CSL_GPIO_REGS; - -CSL_CPINTCRegs* gpCIC0_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; -CSL_CPINTCRegs* gpCIC1_regs = (CSL_CPINTCRegs*)CSL_CP_INTC_1_REGS; -/*The register pointer for the CIC routing events DSP core. -By default, it is CIC0; but for core 4~7 of C6678, it is CIC1*/ -CSL_CPINTCRegs* gpCIC_regs= (CSL_CPINTCRegs*)CSL_CP_INTC_0_REGS; - -CSL_TpccRegs* gpEDMA_CC0_regs = (CSL_TpccRegs*)CSL_EDMA0CC_REGS; -CSL_TpccRegs* gpEDMA_CC1_regs = (CSL_TpccRegs*)CSL_EDMA1CC_REGS; -CSL_TpccRegs* gpEDMA_CC2_regs = (CSL_TpccRegs*)CSL_EDMA2CC_REGS; -CSL_TpccRegs* gpEDMA_CC_regs[3] = { - (CSL_TpccRegs*)CSL_EDMA0CC_REGS, - (CSL_TpccRegs*)CSL_EDMA1CC_REGS, - (CSL_TpccRegs*)CSL_EDMA2CC_REGS -}; - -CSL_TptcRegs * gpEDMA_TC_0_0_regs=(CSL_TptcRegs *) CSL_EDMA0TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_0_1_regs=(CSL_TptcRegs *) CSL_EDMA0TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_1_0_regs=(CSL_TptcRegs *) CSL_EDMA1TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_1_1_regs=(CSL_TptcRegs *) CSL_EDMA1TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_1_2_regs=(CSL_TptcRegs *) CSL_EDMA1TC2_REGS; -CSL_TptcRegs * gpEDMA_TC_1_3_regs=(CSL_TptcRegs *) CSL_EDMA1TC3_REGS; -CSL_TptcRegs * gpEDMA_TC_2_0_regs=(CSL_TptcRegs *) CSL_EDMA2TC0_REGS; -CSL_TptcRegs * gpEDMA_TC_2_1_regs=(CSL_TptcRegs *) CSL_EDMA2TC1_REGS; -CSL_TptcRegs * gpEDMA_TC_2_2_regs=(CSL_TptcRegs *) CSL_EDMA2TC2_REGS; -CSL_TptcRegs * gpEDMA_TC_2_3_regs=(CSL_TptcRegs *) CSL_EDMA2TC3_REGS; - -CSL_TptcRegs * gpEDMA_TC_regs[10]= { - (CSL_TptcRegs *) CSL_EDMA0TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA0TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC2_REGS, - (CSL_TptcRegs *) CSL_EDMA1TC3_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC0_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC1_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC2_REGS, - (CSL_TptcRegs *) CSL_EDMA2TC3_REGS -}; - -CSL_TmrPlusRegs * gpTimer0Regs = (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS; -CSL_TmrPlusRegs * gpTimer1Regs = (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS; -CSL_TmrPlusRegs * gpTimer2Regs = (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS; -CSL_TmrPlusRegs * gpTimer3Regs = (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS; -CSL_TmrPlusRegs * gpTimer4Regs = (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS; -CSL_TmrPlusRegs * gpTimer5Regs = (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS; -CSL_TmrPlusRegs * gpTimer6Regs = (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS; -CSL_TmrPlusRegs * gpTimer7Regs = (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS; -CSL_TmrPlusRegs * gpTimer8Regs = (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)); -CSL_TmrPlusRegs * gpTimerRegs[9] = { - (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS, - (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS, - (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)) -}; - -/*MPU for peripherals registers and data space*/ -CSL_MpuRegs * gpMPU0_regs= (CSL_MpuRegs *)CSL_MPU_0_REGS; -CSL_MpuRegs * gpMPU1_regs= (CSL_MpuRegs *)CSL_MPU_1_REGS; -CSL_MpuRegs * gpMPU2_regs= (CSL_MpuRegs *)CSL_MPU_2_REGS; -CSL_MpuRegs * gpMPU3_regs= (CSL_MpuRegs *)CSL_MPU_3_REGS; - -CSL_Emif4fRegs * gpDDR_regs= (CSL_Emif4fRegs *)CSL_DDR3_EMIF_CONFIG_REGS; -unsigned int gDSP_Core_Speed_Hz= 1000000000; //DSP core clock speed in Hz -TDSP_Board_Type gDSP_board_type= UNKNOWN; - -/*----------------------------------------------* - * module-wide global variables * - *----------------------------------------------*/ - -/*----------------------------------------------* - * constants * - *----------------------------------------------*/ - -/*----------------------------------------------* - * macros * - *----------------------------------------------*/ - -/*----------------------------------------------* - * routines' implementations * - *----------------------------------------------*/ - -/***************************************************************************** - Prototype : KeyStone_main_PLL_init - Description : DSP core PLL configuration - DSP core will be configured to run at ref_clock_MHz*multiplier/divisor - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : - Return Value : - - History : - 1.Date : 2010-12-12 - Author : Brighton Feng - Modification : Created function - 2.Date : May 19, 2013 - Author : Brighton Feng - Modification : update parameter check; replace constant with macro - -*****************************************************************************/ -void KeyStone_main_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - unsigned int i; - - if(0==divisor) - { - puts("Error: PLL input divider = 0"); - return; - } - - if(64SECCTL & PLLCTL_BYPASS_MASK) - { - /*a. In MAINPLLCTL1, write ENSAT = 1 (for optimal PLL operation) */ - gpBootCfgRegs->CORE_PLL_CTL1 |= PLLCTL1_ENSAT_MASK; /*Set ENSAT bit = 1*/ - - /*b. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLEN_MASK; - - /*c. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLENSRC_MASK; - - /*d. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ - /*mux switches properly to the bypass) */ - for(i=0; i< 4; i++) - asm(" nop 5"); - - /*e. In SECCTL, write BYPASS = 1 (bypass enabled in PLL mux) */ - gpPLLC_regs->SECCTL |= PLLCTL_BYPASS_MASK; - - /*f. In PLLCTL, write PLLPWRDN = 1 (power down the PLL) */ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLPWRDN_MASK; //Power down the PLL - - /*g. Wait for at least 5 ��s based on the reference clock CLKIN (PLL power down */ - /*toggling time) */ - for(i=0; i< 1000; i++) - asm(" nop 5"); - - /*h. In PLLCTL, write PLLPWRDN = 0 (power up the PLL) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLPWRDN_MASK; // Power up PLL - } - else - { - /*a. In PLLCTL, write PLLEN = 0 (bypass enabled in PLL controller mux) */ - gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLEN_MASK); - - /*b. In PLLCTL, write PLLENSRC = 0 (enable PLLEN to control PLL controller mux */ - gpPLLC_regs->PLLCTL &= (~CSL_PLLC_PLLCTL_PLLENSRC_MASK); - - /*c. Wait 4 cycles of the reference clock CLKIN (to make sure the PLL controller */ - /*mux switches properly to the bypass) */ - for(i=0; i< 4*multiplier/divisor; i++) - asm(" nop 5"); - } - - /*4. PLLM is split in two different registers. Program PLLM[5:0] in PLL multiplier */ - /*control register (PLLM) and PLLM[12:6] in MAINPLLCTL0 register */ - /*5. BWADJ is split in two different registers. Program BWADJ[7:0] in */ - /*MAINPLLCTL0 and BWADJ[11:8] in MAINPLLCTL1 register. BWADJ value */ - /*must be set to ((PLLM + 1) >> 1) - 1) */ - /*6. Program PLLD in MAINPLLCTL0 register */ - gpBootCfgRegs->CORE_PLL_CTL0 = ((multiplier-1)<PLLM= (multiplier*2-1)&0x3F; - gpBootCfgRegs->CORE_PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; - gpBootCfgRegs->CORE_PLL_CTL1 |= (multiplier-1)>>8; /*BWADJ[11:8]*/ - - /*7. In SECCTL, write OD (Output Divide) = 1 (that is divide-by-2) */ - gpPLLC_regs->SECCTL &= ~PLLCTL_OD_MASK; - gpPLLC_regs->SECCTL |= 1<PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); - - /* Step 8b: Program the RATIO field in PLLDIVn to the desired new divide-down rate. - If RATIO field is changed, the PLL controller will flag the change in the - corresponding bit of DCHANGE*/ - gpPLLC_regs->PLLDIV1_3[3-1] = (3-1) | CSL_PLLC_PLLDIV1_3_DNEN_MASK; //Set PLLDIV3 - gpPLLC_regs->PLLDIV4_16[4-4] = (5-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV4 - gpPLLC_regs->PLLDIV4_16[7-4] = (6-1) | CSL_PLLC_PLLDIV4_16_DNEN_MASK; //Set PLLDIV7 - - /* Step 8c: Set GOSET bit in PLLCMD to initiate the GO operation to change the divide - values and align the SYSCLKs as programmed */ - gpPLLC_regs->PLLCMD |= CSL_PLLC_PLLCMD_GOSET_MASK; - - /*Step 8d/e: Read the GOSTAT bit in PLLSTAT to make sure the bit returns to 0 to - indicate that the GO operation has completed */ - while((gpPLLC_regs->PLLSTAT) & CSL_PLLC_PLLSTAT_GOSTAT_MASK); -#endif - - /*9. In PLLCTL , write PLLRST = 1 (PLL reset is asserted)*/ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLRST_MASK; - - /*10. Wait for at least 7 ��s based on the reference clock CLKIN (PLL reset time) */ - for(i=0; i< 2000; i++) - asm(" nop 5"); - - /*11. In PLLCTL, write PLLRST = 0 (PLL reset is released) */ - gpPLLC_regs->PLLCTL &= ~CSL_PLLC_PLLCTL_PLLRST_MASK; - - /*12. Wait for at least 2000 �� CLKIN cycles �� (PLLD + 1) (PLL lock time) */ - for(i=0; i< 400*multiplier; i++) - asm(" nop 5"); - - /*13. In SECCTL, write BYPASS = 0 (enable PLL mux to switch to PLL mode) */ - gpPLLC_regs->SECCTL &= ~PLLCTL_BYPASS_MASK; - - /*14. Set the PLLEN bit in PLLCTL to 1 to enable PLL mode*/ - gpPLLC_regs->PLLCTL |= CSL_PLLC_PLLCTL_PLLEN_MASK; - -} -/***************************************************************************** - Prototype : KeyStone_PLL_init - Description : Config the PLL of PA and DDR - target clock speed will be ref_clock_MHz/inputDivisor*multiplier/outputDivisor - Input : unsigned int inputDivisor - unsigned int multiplier - unsigned int outputDivisor - Output : None - Return Value : 0 for success, other value for error - - History : - 1.Date : May 18, 2013 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -int KeyStone_PLL_init (PLL_ControlRegs * PLL_Regs, unsigned int inputDivisor, - unsigned int multiplier, unsigned int outputDivisor) -{ - if(0==inputDivisor) - { - puts("Error: PLL input divider = 0"); - return 1; - } - - if(64PLL_CTL1 = PLLCTL1_ENSAT_MASK; - - /*2. In PLLCTL0, write BYPASS = 1 (set the PLL in Bypass)*/ - PLL_Regs->PLL_CTL0 |= PLLCTL_BYPASS_MASK; - - /*3. Program PLLM and PLLD in PLLCTL0 register*/ - /*4. Program BWADJ[7:0] in PLLCTL0 and BWADJ[11:8] in PLLCTL1 register. - BWADJ value must be set to ((PLLM + 1) >> 1) �C 1)*/ - PLL_Regs->PLL_CTL0 = ((multiplier/2-1)<PLL_CTL1 &= ~PLLCTL1_BWADJ_MASK; - PLL_Regs->PLL_CTL1 |= (multiplier/2-1)>>8; /*BWADJ[11:8]*/ - - /*5. In PLLCTL1, write PLLRST = 1 (PLL is reset)*/ - PLL_Regs->PLL_CTL1 |= PLLCTL1_PLLRESET_MASK; //Set RESET bit = 1 - - /*6. Wait for at least 7 us based on the reference clock (PLL reset time)*/ - TSC_delay_us(7); - - /*For PASS, In PASSPLLCTL1, write PLLSELECT = 1 - (for selecting the output of PA PLL as the input to PASS)*/ - if(PLL_Regs==(PLL_ControlRegs *)gpBootCfgRegs->PA_PLL_CTL0) - PLL_Regs->PLL_CTL1 |= PLLCTL1_PAPLL_MASK; - - /*7. In PLLCTL1, write PLLRST = 0 (PLL reset is released)*/ - PLL_Regs->PLL_CTL1 &= ~PLLCTL1_PLLRESET_MASK; //Clear RESET bit - - /*8. Wait for at least 500 * REFCLK cycles * (PLLD + 1) (PLL lock time)*/ - TSC_delay_us(500); - - /*9. In PLLCTL0, write BYPASS = 0 (switch to PLL mode)*/ - PLL_Regs->PLL_CTL0 &= ~PLLCTL_BYPASS_MASK ; - - return 0; -} -/***************************************************************************** - Prototype : KeyStone_PASS_PLL_init - Description : Config the PASS PLL - target clock speed will be ref_clock_MHz/divisor*multiplier - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : None - Return Value : - - History : - 1.Date : 2013-2-14 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_PASS_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - //output divisor for PASS PLL should be 2 - if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->PA_PLL_CTL0, - divisor, multiplier*2, 2)) - { - printf("Initialize PASS PLL clock = %.2fMHz/%dx%d = %.3fMHz\n", - ref_clock_MHz, divisor, multiplier, - ref_clock_MHz*multiplier/divisor); - } -} - -/***************************************************************************** - Prototype : KeyStone_DDR_PLL_init - Description : Config the DDR PLL - target clock speed will be ref_clock_MHz/divisor*multiplier - Input : float ref_clock_MHz - unsigned int multiplier: 1~4096 - unsigned int divisor: 1~64 - Output : None - Return Value : - - History : - 1.Date : 2013-8-18 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_DDR_PLL_init (float ref_clock_MHz, - unsigned int multiplier, unsigned int divisor) -{ - //output divisor for DDR PLL should be 2 - if(0==KeyStone_PLL_init((PLL_ControlRegs *)&gpBootCfgRegs->DDR3_PLL_CTL0, - divisor, multiplier, 2)) - { - printf("Initialize DDR speed = %.2fMHzx/%dx%d = %.3fMTS\n", - ref_clock_MHz, divisor, multiplier, - ref_clock_MHz*multiplier/divisor); - } -} - -/*===============================TSC===================================*/ -unsigned int cycle_measure_overhead=50; -/***************************************************************************** - Prototype : calc_cycle_measure_overhead - Description : calclucate the cycles measurement overhead - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void calc_cycle_measure_overhead() -{ - unsigned int cycle_cold, cycle_warm; - cycle_cold= TSCL; - cycle_cold = TSC_getDelay(cycle_cold); - cycle_warm= TSCL; - cycle_warm = TSC_getDelay(cycle_warm); - cycle_measure_overhead = (cycle_cold + cycle_warm)/2; -} - -/***************************************************************************** - Prototype : TSC_init - Description : Initialize Time stamp counter to measure cycles - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void TSC_init() -{ - TSCL = 0; /* Enable the TSC */ - calc_cycle_measure_overhead(); -} - -/***************************************************************************** - Prototype : TSC_delay_ms - Description : Implement the delay function in millisecond - Input : Uint32 ms - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void TSC_delay_ms(Uint32 ms) -{ - volatile unsigned long long startTSC, currentTSC; - unsigned long long delay_cycles; - Uint32 tscl, tsch; - - tscl= TSCL; - tsch= TSCH; - startTSC= _itoll(tsch,tscl); - - delay_cycles= ((unsigned long long)ms*gDSP_Core_Speed_Hz/1000); - - do - { - tscl= TSCL; - tsch= TSCH; - currentTSC= _itoll(tsch,tscl); - } - while((currentTSC-startTSC)TGCR) - { - gpTimerRegs[timer_num]->TGCR= 0; - gpTimerRegs[timer_num]->TCR= 0; - } -} - - /***************************************************************************** - Prototype : Timer64_Init - Description : Initialize a 64-bit timer - Input : Timer64_Config * tmrCfg - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void Timer64_Init(Timer64_Config * tmrCfg) -{ - Reset_Timer(tmrCfg->timer_num); - - gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; - gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; - - /*please note, in clock mode, two timer periods generate a clock, - one timer period output high voltage level, the other timer period - output low voltage level, so, the timer period should be half to the - desired output clock period*/ - if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) - tmrCfg->period= tmrCfg->period/2; - - /*the value written into period register is the expected value minus one*/ - gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); - gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); - if(tmrCfg->reload_period>1) - { - gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); - gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); - } - - if(TIMER_WATCH_DOG==tmrCfg->timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= - /*Select watch-dog mode*/ - (CSL_TMR_TIMMODE_WDT<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK - /*for plus featuers, dual 32-bit unchained timer mode should be used*/ - |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; - } - else - { - gpTimerRegs[tmrCfg->timer_num]->TGCR= - /*Select 64-bit general timer mode*/ - (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& - ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); - - if(TIMER_WATCH_DOG==tmrCfg->timerMode) - { - /*enable watchdog timer*/ - gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) - { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<WDTCR = - (CSL_TMR_WDTCR_WDKEY_CMD1<WDTCR = - (CSL_TMR_WDTCR_WDKEY_CMD2<0x3FFFFFFF) - { - printf("Enable power domain %d timeout!\n", pwrDmnNum); - return -2; - } - } - } - - /* Enable the clocks too*/ - CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_ENABLE); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Enable clock domain %d timeout!\n", moduleNum); - return -2; - } - } - - /* Return PSC status */ - if ((CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_ON) && - (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_ENABLE)) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } -} -/***************************************************************************** - Prototype : KeyStone_disable_PSC_module - Description : Disable the PSC module in KeyStone device - Input : Uint32 pwrDmnNum - Uint32 moduleNum - Output : None - Return Value : - - History : - 1.Date : 2010/2/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -Int32 KeyStone_disable_PSC_module (Uint32 pwrDmnNum, Uint32 moduleNum) -{ - Uint32 uiStartTSC= TSCL; - - /* disable the clocks*/ - CSL_PSC_setModuleNextState (moduleNum, PSC_MODSTATE_SWRSTDISABLE); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Disable clock domain %d timeout!\n", moduleNum); - return -2; - } - } - - /* Return PSC status */ - if (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_SWRSTDISABLE) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } - -} -/***************************************************************************** - Prototype : KeyStone_disable_PSC_Power_Domain - Description : Disable the PSC power domain - Input : Uint32 pwrDmnNum - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -Int32 KeyStone_disable_PSC_Power_Domain (Uint32 pwrDmnNum) -{ - Uint32 uiStartTSC= TSCL; - - /* Set Power domain to OFF */ - CSL_PSC_disablePowerDomain (pwrDmnNum); - - /* Start the state transition */ - CSL_PSC_startStateTransition (pwrDmnNum); - - /* Wait until the state transition process is completed. */ - while (!CSL_PSC_isStateTransitionDone (pwrDmnNum)) - { - if(TSC_count_cycle_from(uiStartTSC)>0x3FFFFFFF) - { - printf("Disable power domain %d timeout!\n", pwrDmnNum); - return -2; - } - } - - /* Return PSC status */ - if (CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_OFF) - { - /*Ready for use */ - return 0; - } - else - { - /*Return error */ - return -1; - } - -} - -/*============================EDMA=====================================*/ - /***************************************************************************** - Prototype : EDMA_channel_TC_cfg - Description : Setup uiChannel of an EDMA to use uiTC - Input : Uint32 uiCC - Uint32 uiChannel - Uint32 uiTC - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_channel_TC_cfg (Uint32 uiCC, - Uint32 uiChannel, Uint32 uiTC) -{ - gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8] = - (gpEDMA_CC_regs[uiCC]->TPCC_DMAQNUM[uiChannel/8]&(~(0xF<<((uiChannel&7)*4)))) - |(uiTC<<((uiChannel&7)*4)); -} -/***************************************************************************** - Prototype : EDMA_TC_priority_cfg - Description : Setup uiChannel of an EDMA TC priority - Input : Uint32 uiCC - Uint32 uiPri - Uint32 uiTC - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_TC_priority_cfg(Uint32 uiCC, - Uint32 uiPri, Uint32 uiTC) -{ - gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI= - (gpEDMA_CC_regs[uiCC]->TPCC_QUEPRI&(~(0xF<<((uiTC&3)*4)))) - |(uiPri<<((uiTC&3)*4)); -} -/***************************************************************************** - Prototype : EDMA_init - Description : Initialize all EDMA registers and clear the event - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_init () -{ - int i; - unsigned int * uipPaRAM; - - /*clear PaRAM*/ - uipPaRAM= (unsigned int *)&(gpEDMA_CC0_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC0_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - uipPaRAM= (unsigned int *)&(gpEDMA_CC1_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC1_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - uipPaRAM= (unsigned int *)&(gpEDMA_CC2_regs->PARAMSET[0]); - for(i=0; i<8*CSL_EDMA3_TPCC2_NUM_PARAMSETS; i++) - *uipPaRAM++=0; - - /*Assign PaRAM for different channels*/ - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - for(i=0; iTPCC_DCHMAP[i] = i<< CSL_TPCC_TPCC_DCHMAP0_PAENTRY_SHIFT; - - /*Assign TC/Queue for different channels*/ - gpEDMA_CC0_regs->TPCC_DMAQNUM[0]= 0x10101010; - gpEDMA_CC0_regs->TPCC_DMAQNUM[1]= 0x10101010; - - gpEDMA_CC1_regs->TPCC_DMAQNUM[0]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[1]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[2]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[3]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[4]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[5]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[6]= 0x32103210; - gpEDMA_CC1_regs->TPCC_DMAQNUM[7]= 0x32103210; - - gpEDMA_CC2_regs->TPCC_DMAQNUM[0]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[1]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[2]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[3]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[4]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[5]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[6]= 0x32103210; - gpEDMA_CC2_regs->TPCC_DMAQNUM[7]= 0x32103210; - - /*clear any events and status*/ - gpEDMA_CC0_regs->TPCC_ECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_EECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_ICR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_IECR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_EMCR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_QEMCR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC0_regs->TPCC_SECR= 0xFFFF; - - gpEDMA_CC1_regs->TPCC_ECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ICR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_ICRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_IECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_IECRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EMCR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_EMCRH= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_QEMCR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC1_regs->TPCC_SECR= 0xFFFFFFFF; - gpEDMA_CC1_regs->TPCC_SECRH= 0xFFFFFFFF; - - gpEDMA_CC2_regs->TPCC_ECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ICR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_ICRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_IECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_IECRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EMCR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_EMCRH= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_QEMCR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_CCERRCLR= 0xFFFF; - gpEDMA_CC2_regs->TPCC_SECR= 0xFFFFFFFF; - gpEDMA_CC2_regs->TPCC_SECRH= 0xFFFFFFFF; - - for(i=0; iTPTC_ERRCLR= 0xF; - - //enable error interrupt - gpEDMA_TC_regs[i]->TPTC_ERREN= - (1<TPCC_EESR= 1<<(uiChannel); - } - else - { - //enable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EESRH= 1<<(uiChannel-32); - } -} - -void EDMA_event_disable(Uint32 uiCC, Uint32 uiChannel) -{ - if(uiChannel<32) - { - //disable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EECR= 1<<(uiChannel); - } - else - { - //disable the EDMA channel - gpEDMA_CC_regs[uiCC]->TPCC_EECRH= 1<<(uiChannel-32); - } -} - -void EDMA_interrupt_enable(Uint32 uiCC, Uint32 uiIntNum) -{ - if(uiIntNum<32) - { - //enable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IESR= 1<<(uiIntNum); - } - else - { - //enable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IESRH= 1<<(uiIntNum-32); - } -} - -void EDMA_interrupt_disable(Uint32 uiCC, Uint32 uiIntNum) -{ - if(uiIntNum<32) - { - //disable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IECR= 1<<(uiIntNum); - } - else - { - //disable the EDMA channel interrupt - gpEDMA_CC_regs[uiCC]->TPCC_IECRH= 1<<(uiIntNum-32); - } -} - -/***************************************************************************** - Prototype : EDMA_wait - Description : wait the pending EDMA complete - Input : EDMA_CC_Channel_Num CC_channel - Output : None - Return Value : - - History : - 1.Date : 2012/10/30 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_wait(EDMA_CC_Channel_Num CC_channel) -{ - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - - if(uiChannel<32) - { - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - } - else - { - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannel -= 32; - } - - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannel)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannel); -} - -/***************************************************************************** - Prototype : EDMA_Copy - Description : EDMA copy function with manual trigger - Input : unsigned int srcAddr - unsigned int dstAddr - unsigned int byteCount, <64KB - EDMA_CC_Channel_Num CC_channel - DMA_Wait wait - Output : None - Return Value : - - History : - 1.Date : 2012/10/30 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_copy(unsigned int srcAddr, unsigned int dstAddr, - unsigned int byteCount, EDMA_CC_Channel_Num CC_channel, DMA_Wait wait) -{ - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel; - volatile Uint32 * TPCC_ESR; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - - EDMACCRegs->PARAMSET[uiChannel].OPT= - CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, - CSL_EDMA3_TCCH_DIS, - CSL_EDMA3_ITCINT_DIS, - CSL_EDMA3_TCINT_EN, - uiChannel, - CSL_EDMA3_TCC_NORMAL, - CSL_EDMA3_FIFOWIDTH_NONE, - CSL_EDMA3_STATIC_DIS, - CSL_EDMA3_SYNC_A, - CSL_EDMA3_ADDRMODE_INCR, - CSL_EDMA3_ADDRMODE_INCR); - EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(srcAddr); - EDMACCRegs->PARAMSET[uiChannel].A_B_CNT=CSL_EDMA3_CNT_MAKE(byteCount&0xFFFF, 1); - EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(dstAddr); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 1); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; - - if(uiChannel<32) - { - TPCC_ESR= &EDMACCRegs->TPCC_ESR; - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - } - else - { - TPCC_ESR= &EDMACCRegs->TPCC_ESRH; - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannel -= 32; - } - - /*Manually trigger the EDMA*/ - (*TPCC_ESR)= 1<<(uiChannel); - - if(wait) - { - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannel)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannel); - } -} - -/***************************************************************************** - Prototype : EDMA_fill - Description : EDMA fill function with manual trigger - Input : unsigned int address, must align to 8 bytes boundary - unsigned long long data - unsigned int byteCount, must be multiple of 8 - EDMA_CC_Channel_Num CC_channel - Output : None - Return Value : - - History : - 1.Date : 2013/8/11 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_fill(unsigned int address, unsigned long long data, - unsigned int byteCount, EDMA_CC_Channel_Num CC_channel) -{ - int i; - CSL_TpccRegs* EDMACCRegs; - unsigned int uiChannel, uiChannelShift, uiBCNT; - volatile Uint32 * TPCC_ESR; - volatile Uint32 * TPCC_IPR; - volatile Uint32 * TPCC_ICR; - unsigned long long tempBuf[128/8]; - Uint32 tempBufSize=128, headerSize, tailSize; - - if(tempBufSize>byteCount) - tempBufSize=byteCount; - - for(i=0; i< tempBufSize/8; i++) - tempBuf[i]= data; - - /*split the transfer into 3 sections at 128 byte boundary*/ - if(address&127) //header address not start on 128 byte boundary - { - headerSize= 128- (address&127); - if(headerSize>byteCount) - headerSize=byteCount; - EDMA_copy((Uint32)tempBuf, address, headerSize, CC_channel, DMA_WAIT); - address+= headerSize; - byteCount-= headerSize; - } - - if(byteCount&&((address+byteCount)&127))//tail address not start on 128 byte boundary - { - tailSize= (address+byteCount)&127; - EDMA_copy((Uint32)tempBuf, address+byteCount-tailSize, tailSize, CC_channel, DMA_WAIT); - byteCount-= tailSize; - } - - EDMACCRegs= gpEDMA_CC_regs[CC_channel>>16]; - uiChannel = CC_channel&0xFF; - if(uiChannel<32) - { - TPCC_ESR= &EDMACCRegs->TPCC_ESR; - TPCC_IPR= &EDMACCRegs->TPCC_IPR; - TPCC_ICR= &EDMACCRegs->TPCC_ICR; - uiChannelShift= uiChannel; - } - else - { - TPCC_ESR= &EDMACCRegs->TPCC_ESRH; - TPCC_IPR= &EDMACCRegs->TPCC_IPRH; - TPCC_ICR= &EDMACCRegs->TPCC_ICRH; - uiChannelShift= uiChannel - 32; - } - - EDMACCRegs->PARAMSET[uiChannel].OPT= - CSL_EDMA3_OPT_MAKE(CSL_EDMA3_ITCCH_DIS, - CSL_EDMA3_TCCH_DIS, - CSL_EDMA3_ITCINT_DIS, - CSL_EDMA3_TCINT_EN, - uiChannel, - CSL_EDMA3_TCC_NORMAL, - CSL_EDMA3_FIFOWIDTH_NONE, - CSL_EDMA3_STATIC_EN, //keep PARAM unchanged - CSL_EDMA3_SYNC_AB, - CSL_EDMA3_ADDRMODE_INCR, - CSL_EDMA3_ADDRMODE_INCR); - EDMACCRegs->PARAMSET[uiChannel].SRC= GLOBAL_ADDR(tempBuf); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_BIDX= CSL_EDMA3_BIDX_MAKE(0, 128); - EDMACCRegs->PARAMSET[uiChannel].LINK_BCNTRLD= CSL_EDMA3_LINKBCNTRLD_MAKE(0xFFFF, 0); - EDMACCRegs->PARAMSET[uiChannel].SRC_DST_CIDX= 0; - EDMACCRegs->PARAMSET[uiChannel].CCNT= 1; - - while(byteCount) //the reminding must be multiple of 128 bytes - { - uiBCNT= byteCount/128; - if(uiBCNT>65535) - uiBCNT= 65535; - - EDMACCRegs->PARAMSET[uiChannel].A_B_CNT= CSL_EDMA3_CNT_MAKE(128, uiBCNT); - EDMACCRegs->PARAMSET[uiChannel].DST= GLOBAL_ADDR(address); - - /*Manually trigger the EDMA*/ - (*TPCC_ESR)= 1<<(uiChannelShift); - - /*wait for completion*/ - while(0==((*TPCC_IPR)&(1<<(uiChannelShift)))); - - /*clear completion flag*/ - (*TPCC_ICR)= 1<<(uiChannelShift); - - byteCount -= uiBCNT*128; - address += uiBCNT*128; - } -} - -/***************************************************************************** - Prototype : IDMA_wait - Description : wait the pending IDMA complete - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void IDMA_wait() -{ - /* Wait until copying is completed */ - while (gpCGEM_regs->IDMA1_STAT); -} -/***************************************************************************** - Prototype : IDMA_copy - Description : implement the data copy via IDMA - Input : unsigned int srcAddr - unsigned int dstAddr - unsigned int byteCount, <64KB - IDMA_Wait wait - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brigthon - Modification : Created function - -*****************************************************************************/ -void IDMA_copy(unsigned int srcAddr, unsigned int dstAddr, - unsigned int byteCount, DMA_Wait wait) -{ - gpCGEM_regs->IDMA1_SOURCE= srcAddr; - gpCGEM_regs->IDMA1_DEST= dstAddr; - gpCGEM_regs->IDMA1_COUNT= byteCount&0xFFFC; - - if(wait) - { - /* Wait until copying is completed */ - while (gpCGEM_regs->IDMA1_STAT); - } -} -/***************************************************************************** - Prototype : EDMA_CC_error_handler - Description : Edma channel controller error processing - Input : Uint32 edmaNum, EDMA module number (0~2) - Output : None - Return Value : - - History : - 1.Date : 2012/11/7 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_CC_error_handler(Uint32 edmaNum) -{ - int i; - CSL_TpccRegs* EDMACCRegs= gpEDMA_CC_regs[edmaNum]; - Uint32 EMR, EMRH= 0, QEMR, CCERR; - - //read error status - EMR= EDMACCRegs->TPCC_EMR; - QEMR= EDMACCRegs->TPCC_QEMR; - CCERR= EDMACCRegs->TPCC_CCERR; - exception_record.status.ext_sts.info.edma.CC_info.EMR= EMR; - exception_record.status.ext_sts.info.edma.CC_info.QEMR= QEMR; - exception_record.status.ext_sts.info.edma.CC_info.CCERR= CCERR; - - //clear error status - EDMACCRegs->TPCC_EMCR= EMR; - EDMACCRegs->TPCC_QEMCR= QEMR; - EDMACCRegs->TPCC_CCERRCLR= CCERR; - - //channel 32~63 for EDMA CC1 and CC2 - if(0TPCC_EMRH; - exception_record.status.ext_sts.info.edma.CC_info.EMRH= EMRH; - - //clear error status - EDMACCRegs->TPCC_EMCRH= EMRH; - } - - for(i=0; i<32; i++) - { - if((EMR>>i)&1) - printf(" EDMA Channel %d event missed.\n", i); - if((EMRH>>i)&1) - printf(" EDMA Channel %d event missed.\n", i+32); - } - - for(i=0; i<8; i++) - { - if((QEMR>>i)&1) - printf(" QDMA Channel %d event missed.\n", i); - } - - for(i=0; i<4; i++) - { - if((CCERR>>i)&1) - printf(" Queue %d Watermark/threshold has been exceeded.\n", i); - } - - if(CCERR&CSL_TPCC_TPCC_CCERR_TCCERR_MASK) - puts(" Total number of allowed TCCs has been reached."); - -} -/***************************************************************************** - Prototype : EDMA_TC_error_handler - Description : Edma transfer controller error processing - Input : CSL_TptcRegs * edmaTCRegs - Output : None - Return Value : - - History : - 1.Date : 2012/11/7 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_TC_error_handler(CSL_TptcRegs * edmaTCRegs) -{ - Uint32 ERRSTAT, ERRDET, STAT; - - //read error status - ERRSTAT= edmaTCRegs->TPTC_ERRSTAT; - ERRDET= edmaTCRegs->TPTC_ERRDET; - exception_record.status.ext_sts.info.edma.TC_info.ERRSTAT=ERRSTAT ; - exception_record.status.ext_sts.info.edma.TC_info.ERRDET= ERRDET; - - //clear error - edmaTCRegs->TPTC_ERRCLR= ERRSTAT; - - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_MMRAERR_MASK) - puts(" User attempted to read or write to an invalid address in configuration memory map."); - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_TRERR_MASK) - puts(" TR detected that violates constant addressing mode transfer (SAM or DAM is set) alignment rules or has ACNT or BCNT== 0."); - if(ERRSTAT&CSL_TPTC_TPTC_ERRSTAT_BUSERR_MASK) - { - puts(" EDMA3TC has detected an error at source or destination address."); - - STAT= ERRDET&CSL_TPTC_TPTC_ERRDET_STAT_MASK; - - if(STAT>=8) - printf(" write error (%d). ",STAT); - else if(STAT>=1) - printf(" read error (%d). ",STAT); - else - printf(" no error!?"); - - printf("TCC= %d. TCINTEN= %d. TCCHEN= %d\n", - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCC_MASK)>>CSL_TPTC_TPTC_ERRDET_TCC_SHIFT, - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCINTEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCINTEN_SHIFT, - (ERRDET&CSL_TPTC_TPTC_ERRDET_TCCHEN_MASK)>>CSL_TPTC_TPTC_ERRDET_TCCHEN_SHIFT); - } - -} -/***************************************************************************** - Prototype : EDMA_error_handler - Description : EDMA error processing function - Input : Uint32 edmaNum - Uint32 errorFlag - error flag bit fields are defined as below - (follow the sequence in CIC) - 0 EDMACC_ERRINT EDMA3CC error interrupt - 2 EDMATC_ERRINT0 EDMA3TC0 error interrupt - 3 EDMATC_ERRINT1 EDMA3TC1 error interrupt - 4 EDMATC_ERRINT2 EDMA3TC2 error interrupt - 5 EDMATC_ERRINT3 EDMA3TC3 error interrupt - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EDMA_error_handler(Uint32 edmaNum, Uint32 errorFlag) -{ - int i; - - printf(" EDMA module %d error\n", edmaNum); - if(errorFlag&1) - EDMA_CC_error_handler(edmaNum); - - errorFlag >>= 2; - - for(i=0; i<4; i++) - { - if(errorFlag&(1<MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; - } - - /*3. Write a 1 to the LOCK field of the MPLKCMD register. This engages the lock.*/ - gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); -} - -/***************************************************************************** - Prototype : unlock_mem_prot_regs - Description : unlock memory protection registers - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma CODE_SECTION (unlock_mem_prot_regs, ".text:Core_MPAX") -void unlock_mem_prot_regs() -{ - int i; - - /*1. Write a 1 to the KEYR field in the MPLKCMD register. This resets some internal - status for the MPLK0 through the MPLK3 registers.*/ - gpCGEM_regs->MPLKCMD = (1<MPLK[i] = mem_prot_key[i]; - } - - /*3. Write a 1 to the UNLOCK field in the MPLKCMD register. If the key written in - step 2 matches the stored key, the hardware disengages the lock. If the key written - in step 2 does not match, the hardware signals an exception. The hardware - reports the fault address as the address of the MPLKCMD register.*/ - gpCGEM_regs->MPLKCMD = (1<MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK)); -} - -/***************************************************************************** - Prototype : L1_MPPA_setup - Description : setup the memory protection for local L1 memory - Input : volatile Uint32 MPPA_regs[], Uint32 MPPA[] - Output : None - Return Value : - -usage example: - Uint32 MPPA[16]= - { - MP_LOCAL|MP_SR|MP_UR, //page 0 for read only - MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for read/write - ...... - } - ...... - L1_MPPA_setup(gpCGEM_regs->L1PMPPA, MPPA); - - History : - 1.Date : 2012/12/6 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1_MPPA_setup(volatile Uint32 MPPA_regs[], Uint32 MPPA[]) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1PMPFCR = 1; - gpCGEM_regs->L1DMPFCR = 1; - - /*setup the memory protection attributes for 32 pages*/ - for(i=0; i<16; i++) - { - MPPA_regs[i] = MPPA[i]; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1P_memory_protection_cfg - Description : config "AccessPermisionMask" for L1P - Input : Uint32 AccessPermisionMask - Output : None - Return Value : -*****************************************************************************/ -void L1P_memory_protection_cfg(Uint32 AccessPermisionMask) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1PMPFCR = 1; - - /*set L1P only for cacheable local execution, disable all external access*/ - for(i=0; i<16; i++) - { - gpCGEM_regs->L1PMPPA[i] = AccessPermisionMask; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1D_memory_protection_cfg - Description : config "AccessPermisionMask" for L1P - Input : Uint32 AccessPermisionMask - Output : None - Return Value : -*****************************************************************************/ -void L1D_memory_protection_cfg(Uint32 AccessPermisionMask) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L1DMPFCR = 1; - - /*set L1P only for cacheable local execution, disable all external access*/ - for(i=0; i<16; i++) - { - gpCGEM_regs->L1DMPPA[i] = AccessPermisionMask; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : L1_cache_protection - Description : protect L1 as cache - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1_cache_protection() -{ - /*set L1P only for cacheable local execution, disable all external access*/ - L1P_memory_protection_cfg(0); - - /*set L1D only for cacheable local read/write, disable all external access*/ - L1D_memory_protection_cfg(0); -} - - -/***************************************************************************** - Prototype : LL2_MPPA_setup - Description : setup the memory protection for local L2 memory - Input : Uint32 MPPA[] - Output : None - Return Value : -usage example: - Uint32 MPPA[32]= - { - MP_LOCAL|MP_SX|MP_UX, //page 0 for local code only - MP_LOCAL|MP_SR|MP_SW|MP_UR|MP_UW, //page 1 for local data only - ...... - } - ...... - LL2_MPPA_setup(MPPA); - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_MPPA_setup(Uint32 MPPA[]) -{ - int i; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*clear any memory protection fault*/ - gpCGEM_regs->L2MPFCR = 1; - - /*setup the memory protection attributes for 32 pages*/ - for(i=0; i<32; i++) - { - gpCGEM_regs->L2MPPA[i] = MPPA[i]; - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : LL2_Memory_Protection_cfg - Description : config "AccessPermisionMask" for local L2 memory section from - "startAddress" with "byteCount" size - Input : Uint32 startAddress - Uint32 byteCount - Uint32 AccessPermisionMask - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_Memory_Protection_cfg(Uint32 startAddress, - Uint32 byteCount, Uint32 AccessPermisionMask) -{ - int i; - Uint32 uiEndAddress; - Uint32 uiPageIndex, uiNumPages, uiPageSize, uiPageAddressMask, uiPageShift; - TDSP_Board_Type DSP_Board_Type; - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - DSP_Board_Type = KeyStone_Get_dsp_board_type(); - - /*L2 memory protection size is 32KB for TCI6614, C6670, - it is 16KB for C6678*/ - uiPageSize= 32*1024; - uiPageAddressMask= 32*1024-1; - uiPageShift= 15; - if(C6678_EVM == DSP_Board_Type) - { - uiPageSize= 16*1024; - uiPageAddressMask= 16*1024-1; - uiPageShift= 14; - } - - if(startAddress>=0x10800000) - { - printf("LL2 memory protection start Address 0x%x is not a local address\n", - startAddress); - startAddress &= 0xFFFFFF; /*convert to local address*/ - } - uiEndAddress= startAddress+ byteCount; - - if(startAddress&uiPageAddressMask) - { - printf("LL2 memory protection start Address 0x%x does not align to page boundary\n", - startAddress); - startAddress &= (~uiPageAddressMask); - } - uiPageIndex= (startAddress-0x800000)>>uiPageShift; - - byteCount= uiEndAddress- startAddress; - if(byteCount&uiPageAddressMask) - { - printf("LL2 memory protection section size 0x%x is not multiple of page size\n", - byteCount); - byteCount = (byteCount+uiPageSize)&(~uiPageAddressMask); - } - uiNumPages= byteCount>>uiPageShift; - - for(i= 0; iL2MPPA[uiPageIndex+i] = AccessPermisionMask; - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : KeyStone_CorePac_AID_map - Description : map CorePac AID to PrivID: - map_table[0] assign the PrivID for AID0, - map_table[1] assign the PrivID for AID1 - ...... - map_table[5] assign the PrivID for AID5 - Input : Uint8 map_table[] - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_CorePac_AID_map(Uint8 map_table[]) -{ - int i; - Uint32 *PAMAP= (Uint32 *)&(gpCGEM_regs->PAMAP0); - - /*map all PrivID to AIDx by default*/ - for(i=0; i<16; i++) - PAMAP[i]= CSL_CGEM_PAMAP0_AID_MASK; - - /*map AID0~AID5*/ - for(i=0; i<6; i++) - { - if(map_table[i]<16) /*PrivID must be less than 16*/ - PAMAP[map_table[i]]= i; - } -} - -/***************************************************************************** - Prototype : KeyStone_PrivID_Remap - Description : privilege ID remap to AID - Input : int privID - int AID - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_PrivID_Remap(int privID, int AID) -{ - volatile unsigned int * pamapReg = NULL; - unsigned int val = 0; - - pamapReg = (volatile unsigned int *)(&gpCGEM_regs->PAMAP0 + privID); - - if(AID >= MAX_AID_NUM) - AID = 0; - val = *pamapReg; - - val &= (~CSL_CGEM_PAMAP0_AID_MASK); - - val |= ((AID<>4)) - { - printf("Segment replacement address 0x%x does not start from power-of-2 boundary corresponds to segment size 0x%x.\n", - RADDR, SegementSize); - RADDR &= (~(SegSizeMask>>4)); - printf("Extended replacement address to 0x%x.\n", RADDR); - } - - MPAX_regs->MPAXH= BADDR|(SegSizeBits-1); - MPAX_regs->MPAXL= RADDR|AccessPermisionMask; - -} - -/***************************************************************************** - Prototype : KeyStone_XMC_MPAX_setup - Description : configure multiple MPAX segments in XMC with a configuration - table. - Please note, the code of this function or the data used by this function - (stack, parameters...) can not be put in the segment that will be modified - by this function. Normally, to put this function and its related data in - LL2 is a good idea. - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma CODE_SECTION (KeyStone_XMC_MPAX_setup, ".text:Core_MPAX") -void KeyStone_XMC_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs) -{ - int i; - - if(firstSeg >= 16) - { - printf("The XMC MPAX segment number %d >= 16, not supported.\n ", firstSeg); - return; - } - - if(gpCGEM_regs->MPLKSTAT&CSL_CGEM_MPLKSTAT_LK_MASK) - unlock_mem_prot_regs(); - - /*CAUTION: - A MPAX segment can only be modified when there is no access to the space - of this segment. Any data in cache or prefetch buffer from the space of this - segment must be writeback and invalidated before the segment modification. - It is recommended to configure the MPAX at the very beginning of application - software before any shared memory is used. Code and data for CorePac MPAX - configuration should be allocated in LL2. - If a MPAX segment must be modified on-the-fly, the safer way is, to write - the new configuration to a unused higher segment, and then clear the old - segment. This is based on the fact that higher numbered segments take - precedence over lower numbered segments. */ - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - _mfence(); - _mfence(); //ensure all writeback invalidate have completed. - - for(i=numSegs-1; i>=0 ; i--) - { - KeyStone_MPAX_seg_setup((MPAX_Regs *)&gpXMC_regs->XMPAX[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - } - - lock_mem_prot_regs(); -} - -/***************************************************************************** - Prototype : KeyStone_SMS_MPAX_setup - Description : configure multiple MPAX segments in SMS of MSMC with a conf- - iguration table - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Uint32 PrivID - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SMS_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) -{ - int i; - - if( gpMSMC_regs->SMS_MPAX_LCKSTAT&(1<=0 ; i--) - KeyStone_MPAX_seg_setup( - (MPAX_Regs *)&gpMSMC_regs->SMS_MPAX_PER_PRIVID[PrivID].SMS[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - - CSL_MSMC_lockSMS(PrivID); -} - -/***************************************************************************** - Prototype : KeyStone_SES_MPAX_setup - Description : configure multiple MPAX segments in SES of MSMC with a conf- - iguration table - Input : MPAX_Config MPAX_cfg[] - Uint32 firstSeg - Uint32 numSegs - Uint32 PrivID - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SES_MPAX_setup(MPAX_Config MPAX_cfg[], - Uint32 firstSeg, Uint32 numSegs, Uint32 PrivID) -{ - int i; - - if( gpMSMC_regs->SES_MPAX_LCKSTAT&(1<=0 ; i--) - KeyStone_MPAX_seg_setup( - (MPAX_Regs *)&gpMSMC_regs->SES_MPAX_PER_PRIVID[PrivID].SES[firstSeg+i], - MPAX_cfg[i].BADDR, MPAX_cfg[i].RADDR, - MPAX_cfg[i].SegementSize, MPAX_cfg[i].AccessPermisionMask); - - CSL_MSMC_lockSES(PrivID); -} - -/***************************************************************************** - Prototype : KeyStone_MSMC_MP_interrupt_en - Description : Enable MSMC Memory protection error interrupt for PrivIDs - indicated by "PRIVID_MASK" - Input : Uint32 PRIVID_MASK - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Zhan - Modification : Created function - -*****************************************************************************/ -void KeyStone_MSMC_MP_interrupt_en(Uint32 PRIVID_MASK) -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /*clear MP fault record*/ - gpMSMC_regs->SMPFCR = 1; - - /*clear interrupt error status flag*/ - gpMSMC_regs->SMIRC = (PRIVID_MASK)<SMIESTAT |= (PRIVID_MASK<> - CSL_CGEM_L2MPFSR_FID_SHIFT; - - printf(" memory protection exception caused by master with ID %d at 0x%x\n", - master_id, MPFAR); - } - - if (MPFSR & CSL_CGEM_L2MPFSR_UX_MASK) { - puts(" User Execute violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_UW_MASK) { - puts(" User Write violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_UR_MASK) { - puts(" User Read violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SX_MASK) { - puts(" Supervisor Execute violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SW_MASK) { - puts(" Supervisor Write violation"); - } - if (MPFSR & CSL_CGEM_L2MPFSR_SR_MASK) { - puts(" Supervisor Read violation"); - } - -} - -/***************************************************************************** - Prototype : KeyStone_MSMC_protection_exception_handler - Description : MSMC memory protection processing - Input : None - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_MSMC_protection_exception_handler() -{ - unsigned int master_id; - unsigned int priv_id; - unsigned int address; - unsigned int NM; - - address = gpMSMC_regs->SMPFAR; - - master_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FMSTID_MASK)>> - CSL_MSMC_SMPFR_FMSTID_SHIFT; - priv_id = (gpMSMC_regs->SMPFR&CSL_MSMC_SMPFR_FPID_MASK)>> - CSL_MSMC_SMPFR_FPID_SHIFT; - - exception_record.status.ext_sts.info.memory.fault_address= address; - exception_record.status.ext_sts.info.memory.fault_status.SMPFR= gpMSMC_regs->SMPFR; - - NM = (gpMSMC_regs->SMPFXR & CSL_MSMC_SMPFXR_NM_MASK) >> CSL_MSMC_SMPFXR_NM_SHIFT; - - printf(" memory protection exception caused by master %d (PrivID= %d) at address 0x%x\n", - master_id, priv_id, address); - - if(1 == NM) - { - printf(" Fault is caused by the address not matching any of the segment BADDR\n"); - } - - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - /*clear fault record*/ - gpMSMC_regs->SMPFCR = 1; - /*clear interrupt error status flag*/ - gpMSMC_regs->SMIRC = (1<PROG_START_ADDRESS = uiStartAddress; - MPPA_regs->PROG_END_ADDRESS = uiEndAddress; - MPPA_regs->PROG_MPPA = AccessPermisionMask; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_setup - Description : peripherals MPU ranges configuration - Input : Uint32 uiMPU_num: number of the MPU to be setup - MPU_Range_Config MPU_cfg[]: MPU ranges configuration table - Uint32 numRangeCfg: number of ranges to be configured - Output : None - Return Value : - - History : - 1.Date : 2012/12/15 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_MPU_setup(Uint32 uiMPU_num, - MPU_Range_Config MPU_cfg[], Uint32 numRangeCfg) -{ - int i; - unsigned int mpuNumProgmableRange; - CSL_MpuRegs * mpuRegs; - - /*For Turbo Nyquist, add following code to modify initial value, - Or user can modify the initail values directly*/ - if(5==uiMPU_num) - TN_MPU5_constant(); - - mpuRegs= gpMPU_regs[uiMPU_num]; - - mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; - if(mpuNumProgmableRange == 0) - { - mpuNumProgmableRange = 16; - } - - if(numRangeCfg>mpuNumProgmableRange) - { - printf("MPU %d programmable ranges %d < %d.\n", - uiMPU_num, mpuNumProgmableRange, numRangeCfg); - numRangeCfg=mpuNumProgmableRange; - } - else if(numRangeCfg gstruMpuAddrRange[uiMPU_num].EndAddr) ) - { - printf("The configuration address is out of MPU %d protection range\n", - uiMPU_num); - continue; - } - - KeyStone_MPU_range_setup(&mpuRegs->PROG_REGION[i], - MPU_cfg[i].StartAddr, MPU_cfg[i].EndAddr, - MPU_cfg[i].AccessPermisionMask); - - } - - //clear unused ranges - for( ;iPROG_REGION[i].PROG_MPPA = 0; - } - - //clear status - mpuRegs->FAULT_CLEAR = 1; - mpuRegs->INT_ENABLED_STATUS_CLEAR = - CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK - |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; - - /* enable the interrupt */ - mpuRegs->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK - | CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; - - return; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_MPPA_modify - Description : search the range which match a address and then modify - the access permission of that range. - Input : Uint32 uiMPU_num: number of the MPU to be modifed - Uint32 uiAddress: address which need modify permision - Uint32 AccessPermisionMask: permission mask for that range - Output : None - Return Value : - - History : - 1.Date : 2012/12/13 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_MPU_MPPA_modify(Uint32 uiMPU_num, - Uint32 uiAddress, Uint32 AccessPermisionMask) -{ - int i; - unsigned int mpuNumProgmableRange; - CSL_MpuRegs * mpuRegs; - - /*For Turbo Nyquist, add following code to modify initial value, - Or user can modify the initail values directly*/ - if(5==uiMPU_num) - TN_MPU5_constant(); - - mpuRegs= gpMPU_regs[uiMPU_num]; - - mpuNumProgmableRange = (mpuRegs->CONFIG & CSL_MPU_CONFIG_NUM_PROG_MASK)>>CSL_MPU_CONFIG_NUM_PROG_SHIFT; - if(mpuNumProgmableRange == 0) - { - mpuNumProgmableRange = 16; - } - - /*search through all ranges*/ - for(i=0; i< mpuNumProgmableRange; i++) - { - /*match with one range*/ - if((uiAddress >= mpuRegs->PROG_REGION[i].PROG_START_ADDRESS) - &&(uiAddress <= mpuRegs->PROG_REGION[i].PROG_END_ADDRESS)) - { - mpuRegs->PROG_REGION[i].PROG_MPPA = AccessPermisionMask; - return; - } - } - - printf("address 0x%08x does not match any range in MPU %d\n", - uiAddress, uiMPU_num); - - return; -} - -/***************************************************************************** - Prototype : KeyStone_MPU_interrupts_enable - Description : enable the all MPU interrupts - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_MPU_interrupt_enable(Uint32 uiMPU_num) -{ - if((gpMPU_regs[uiMPU_num]->REVISION&0xFFFF0000)!= - (CSL_MPU_REVISION_RESETVAL&0xFFFF0000)) - { - printf("Can't read MPU%d ID register, make sure corresponding power domain is enabled.", uiMPU_num); - return; - } - - gpMPU_regs[uiMPU_num]->FAULT_CLEAR = 1; - gpMPU_regs[uiMPU_num]->INT_ENABLED_STATUS_CLEAR = - CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_ADDR_ERR_MASK - |CSL_MPU_INT_ENABLED_STATUS_CLEAR_ENABLED_PROT_ERR_MASK; - gpMPU_regs[uiMPU_num]->INT_ENABLE = CSL_MPU_INT_ENABLE_ADDR_ERR_EN_MASK - |CSL_MPU_INT_ENABLE_PROT_ERR_EN_MASK; - -} -void KeyStone_MPU_interrupts_enable() -{ - int i; - TDSP_Board_Type DSP_Board_Type = KeyStone_Get_dsp_board_type(); - - TN_MPU5_constant(); - - for(i=0; i<4; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - - if((C6670_EVM== DSP_Board_Type) - ||(TCI6614_EVM== DSP_Board_Type)) - { - for(i=4; i<6; i++) - { - /*MPU5 (for BCP) of TCI6614 is only accessible - when BCP is enabled through PSC*/ - if((5==i)&&(TCI6614_EVM== DSP_Board_Type)&& - ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || - (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) - { - puts("Enable power domain for MPU5 before configure it."); - continue; - } - - KeyStone_MPU_interrupt_enable(i); - } - } - - if(TCI6614_EVM== DSP_Board_Type) - { - for(i=6; i<8; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - } - - return; -} - -char * Peri_MPU_err_type_str[]= -{ - "User execution fault!", - "User write fault!", - "User read fault!", - "Supervisor execution fault!", - "Supervisor write fault!", - "Supervisor read fault!" -}; - -char * Ns_str[]= -{ - "secure", - "non-secure" -}; -/***************************************************************************** - Prototype : KeyStone_peripherals_MPU_fault_status - Description : Print the MPU error information - Input : unsigned int uwFltStatus - unsigned int uwFltAddr - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_peripherals_MPU_fault_status(unsigned int uwFltStatus, - unsigned int uwFltAddr) -{ - unsigned int MSTID; - unsigned int PRIVID; - unsigned int NS; - unsigned int FaultType; - unsigned int BitsCnt; - - MSTID = (uwFltStatus & CSL_MPU_FAULT_STATUS_MSTID_MASK)>>CSL_MPU_FAULT_STATUS_MSTID_SHIFT; - PRIVID = (uwFltStatus & CSL_MPU_FAULT_STATUS_PRIVID_MASK)>>CSL_MPU_FAULT_STATUS_PRIVID_SHIFT; - NS = (uwFltStatus & CSL_MPU_FAULT_STATUS_NS_MASK)>>CSL_MPU_FAULT_STATUS_NS_SHIFT; - printf(" The MSTID %d (PRIVID %d) triggered MPU error at 0x%x with %s access\n", - MSTID, PRIVID, uwFltAddr, Ns_str[NS]); - - FaultType = (uwFltStatus & CSL_MPU_FAULT_STATUS_FAULT_TYPE_MASK) >> CSL_MPU_FAULT_STATUS_FAULT_TYPE_SHIFT; - if(1==(_dotpu4(_bitc4(FaultType), 0x01010101))) - { - BitsCnt= 31 - _lmbd(1, FaultType); - printf(" %s\n",Peri_MPU_err_type_str[BitsCnt]); - } - else if(0x3F == FaultType) - { - puts(" Relaxed cache line fill fault!"); - } - else if(0x12 == FaultType) - { - puts(" Relaxed cache write back fault!"); - } -} -/***************************************************************************** - Prototype : KeyStone_peripherals_MPU_excepiton_handler - Description : peripheral MPU processing - Input : Uint32 uwMpuNum - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_peripherals_MPU_excepiton_handler(Uint32 uwMpuNum) -{ - Uint32 uwStatus; - Uint32 uwFltAddr; - Uint32 uwFltStatus; - CSL_MpuRegs *pstruMpuRegs= gpMPU_regs[uwMpuNum]; - - uwStatus = pstruMpuRegs->INT_ENABLED_STATUS_CLEAR; - if(uwStatus & 0x2) - { - printf(" MPU %d address violation error\n", uwMpuNum); - pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 2; - } - - if(uwStatus & 0x1) - { - printf(" MPU %d protection violation error\n", uwMpuNum); - pstruMpuRegs->INT_ENABLED_STATUS_CLEAR = 1; - } - - uwFltAddr = pstruMpuRegs->FAULT_ADDRESS; - uwFltStatus = pstruMpuRegs->FAULT_STATUS; - exception_record.status.ext_sts.info.memory.fault_address= uwFltAddr; - exception_record.status.ext_sts.info.memory.fault_status.MPU_FAULT_STATUS= uwFltStatus; - - KeyStone_peripherals_MPU_fault_status(uwFltStatus,uwFltAddr); - pstruMpuRegs->FAULT_CLEAR = 1; - - pstruMpuRegs->EOI = 0; -} - - -/*======================memory EDC=====================================*/ -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_enable - Description : Enable MSMC EDC - Input : scrubCnt, number of MSMC clock cycles between scrubbing - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_enable(Uint32 scrubCnt) -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /*Software must wait for the PRR (Parity RAM Ready) bit before making - the first read access to MSMC RAM after reset.*/ - while(0==(gpMSMC_regs->SMEDCC&CSL_MSMC_SMEDCC_PRR_MASK)); - - /* set scrubbing period value */ - if(scrubCnt>255) - scrubCnt= 255; - CSL_MSMC_setCounterBankRefreshRead(scrubCnt); //the scrubbing engine works every scrubCnt*1024 cycle*/ - - /* clear EDC errors and enable EDC event*/ - gpMSMC_regs->SMIRC = 0xf; - gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK - | CSL_MSMC_SMIESTAT_CSIE_MASK - | CSL_MSMC_SMIESTAT_NCEIE_MASK - | CSL_MSMC_SMIESTAT_CEIE_MASK); - - //enable SL2 EDC - CSL_MSMC_setECM(1); - - CSL_MSMC_lockNonMPAX(); -} - -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_interrupt_en - Description : Enable MSMC EDC error interrupt - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/15 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_interrupt_en() -{ - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - /* clear EDC errors*/ - gpMSMC_regs->SMIRC = 0xf; - - /* Enable EDC error interrupt */ - gpMSMC_regs->SMIESTAT |= (CSL_MSMC_SMIESTAT_NCSIE_MASK - | CSL_MSMC_SMIESTAT_CSIE_MASK - | CSL_MSMC_SMIESTAT_NCEIE_MASK - | CSL_MSMC_SMIESTAT_CEIE_MASK); - - CSL_MSMC_lockNonMPAX(); -} - -/***************************************************************************** - Prototype : LL2_EDC_setup - Description : Eenable LL2 EDC and scrub whole LL2 - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/10 - Author : Jane - Modification : Created function - - 2.Date : 2012/10/20 - Author : Brighton Feng - -*****************************************************************************/ -void LL2_EDC_setup() -{ - int i; - unsigned int uiByteCnt= 512*1024; - TDSP_Board_Type DSP_Board_Type; - - /* 1. Disable the EDC */ - CSL_CGEM_disableL2EDC(); - - /* 2. Clear any EDC errors */ - CSL_CGEM_clearL2EDCErrorStatus(1, 1, 1, 1); - - /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ - DSP_Board_Type = KeyStone_Get_dsp_board_type(); - if((DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(C6670_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - uiByteCnt= 1024*1024; - } - - /*Each IDMA can transfer up to 65532 bytes, - here we transfer 32KB each time*/ - for(i=0; i< (uiByteCnt>>15); i++) - { - IDMA_copy((0x00800000 + i*(1<<15)), (0x00800000 + i*(1<<15)), - (1<<15), DMA_WAIT); - } - - /* 4. Enable the EDC*/ - CSL_CGEM_enableL2EDC(); - gpCGEM_regs->L2EDCEN= (1<= uiLL2EndAddress) - uiLL2_scrub_addr=0x800000; - -} - -/***************************************************************************** - Prototype : L1P_EDC_setup - Description : enable L1P ED and scrub whole L1P - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/10 - Author : Jane - Modification : Created function - - 2.Date : 2012/10/30 - Author : Brighton Feng -*****************************************************************************/ -void L1P_EDC_setup() -{ - Uint32 preL1PMPPA[16]; - - /* 1. Disable the EDC */ - CSL_CGEM_disablePMCErrorDetection(); - - /* 2. Clear any EDC errors */ - CSL_CGEM_clearPMCErrorDetectionStatus(1, 1); - - /* 3. Memory Scrubbing with IDMA, generate the parity bits*/ - memcpy(preL1PMPPA, (void *)gpCGEM_regs->L1PMPPA, 64);//save protection attributes - L1P_memory_protection_cfg(0xFFFF); //enable IDMA access to L1P - IDMA_copy(0x00E00000, 0x00E00000, 32*1024, DMA_WAIT); - L1_MPPA_setup(gpCGEM_regs->L1PMPPA, preL1PMPPA);//restore protection for L1 - - /* 4. Enable the EDC*/ - CSL_CGEM_enablePMCErrorDetection(); -} - -char * LL2_EDC_victim_err_str="LL2 victims"; -char * LL2_EDC_DMA_err_str= "DMA access"; -char * LL2_EDC_L1D_err_str= "L1D access"; -char * LL2_EDC_L1P_err_str= "L1P access"; - -/***************************************************************************** - Prototype : LL2_EDC_handler - Description : LL2 EDC exception/interrupt handler - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void LL2_EDC_handler(Bool bCorrected) -{ - /* EDC error during the L1D access */ - Uint8 derr; - /* EDC error during the L1P access */ - Uint8 perr; - /* EDC error during the DMA access*/ - Uint8 dmaerr; - /* EDC error during the L2 victim occurred */ - Uint8 verr; - /* single bit or dual bit EDC error */ - Uint8 nerr; - - char *errStr; - Uint32 errAddr; - - /* Get the all LL2 error status */ - CSL_CGEM_getL2EDCErrorStatus(&derr, &perr, &dmaerr, &verr, &nerr); - - if(derr|perr|dmaerr|verr) - { - errAddr= gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_ADDR_MASK; - - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - exception_record.status.ext_sts.info.memory.fault_status.L2EDSTAT= - gpCGEM_regs->L2EDSTAT; - - if(bCorrected) - { - printf(" LL2 EDC (correctable) at bit %d of ",(gpCGEM_regs->L2EDSTAT& - CSL_CGEM_L2EDSTAT_BITPOS_MASK)>>CSL_CGEM_L2EDSTAT_BITPOS_SHIFT); - - //scrub 64 bytes including the error address to correct the error - if(perr) //by L1P access - IDMA_copy(errAddr&0xFFFFFFC0, errAddr&0xFFFFFFC0, 64, DMA_WAIT); - else - { - volatile Uint32 * uipAddress= (volatile Uint32 *)(errAddr&0xFFFFFFC0); - /*read one word into a cache line, and write to make it dirty, - which will be automatically written back sooner or later*/ - *uipAddress= *uipAddress; - } - } - else - { - printf(" LL2 EDC error (non-correctable) at "); - } - errStr = (char *)(perr * (Uint32)LL2_EDC_L1P_err_str - + derr * (Uint32)LL2_EDC_L1D_err_str - + verr * (Uint32)LL2_EDC_victim_err_str - + dmaerr * (Uint32)LL2_EDC_DMA_err_str); - - printf("address 0x%x caused by %s.\n", - errAddr, - errStr); - - if(0==(gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_RAM_MASK)) - { - printf(" Error detected in Way %d of L2 cache\n", - (gpCGEM_regs->L2EDADDR&CSL_CGEM_L2EDADDR_WAY_MASK)>>CSL_CGEM_L2EDADDR_WAY_SHIFT); - } - - printf(" total non-correctable error number= %d, total correctable error number= %d.\n", - gpCGEM_regs->L2EDCNEC, gpCGEM_regs->L2EDCPEC); - - CSL_CGEM_clearL2EDCErrorStatus(derr, perr, dmaerr, verr); - } - else - { - puts(" Enter LL2 EDC handler, but no error flag is set!"); - } -} -/***************************************************************************** - Prototype : L1P_ED_handler - Description : L1P EDC processing - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void L1P_ED_handler() -{ - Uint32 errAddr; - Uint8 errRAM; - - /* EDC error during DMA access */ - Uint8 dmaerr; - /* EDC error during program fetch access */ - Uint8 perr; - - /* Read PMC EDC status*/ - CSL_CGEM_getPMCErrorDetectionStatus(&dmaerr, &perr); - - if(perr|dmaerr) - { - CSL_CGEM_getPMCErrorInfo(&errAddr, &errRAM); - - exception_record.status.ext_sts.info.memory.fault_address= errAddr*32; - exception_record.status.ext_sts.info.memory.fault_status.L1PEDSTAT= - gpCGEM_regs->L1PEDSTAT; - - if(errRAM) - printf(" L1P RAM "); - else - printf(" L1P Cache "); - - printf("parity check error caused by "); - - if(perr == 1) - { - printf("program fetch "); - - /*flush wrong code in L1P. Code will be refetched from L2*/ - CACHE_invL1p((void *)NRP, 64, CACHE_WAIT); - } - else if(dmaerr == 1) - { - printf("DMA "); - } - printf("at address 0x%x\n", errAddr*32); - - CSL_CGEM_clearPMCErrorDetectionStatus(dmaerr,perr); - } -} - - -/***************************************************************************** - Prototype : KeyStone_SL2_EDC_handler - Description : SL2 EDC Processing - Input : None - Output : None - Return Value : - - History : - 1.Date : 2012/10/28 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void KeyStone_SL2_EDC_handler() -{ - /* EDC correctable error during scrubbing cycle */ - Uint8 cses; - /* EDC non-correctable error during scrubbing cycle */ - Uint8 ncses; - /* EDC correctable error during SRAM access*/ - Uint8 cees; - /* EDC non-correctable error during SRAM access*/ - Uint8 ncees; - /* protection fault status*/ - Uint16 pfeStat; - - /* error address */ - Uint32 errAddr, bitPos, PrivID; - - if(gpMSMC_regs->CFGLCKSTAT&CSL_MSMC_CFGLCKSTAT_WSTAT_MASK) - CSL_MSMC_unlockNonMPAX(); - - CSL_MSMC_getPendingInterrupts(&pfeStat, &cees, &ncees, &cses, &ncses); - - exception_record.status.ext_sts.info.memory.fault_status.SMESTAT= - gpMSMC_regs->SMESTAT; - - if((cses == 1)||(ncses == 1)) - { - if(cses == 1) - { - /*scrubbing engine report address offset from 0*/ - errAddr = (gpMSMC_regs->SMCEA&0xFFFFFF)+0xc000000; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - bitPos = (gpMSMC_regs->SMCEA&CSL_MSMC_SMCEA_ESYN_MASK) - >>CSL_MSMC_SMCEA_ESYN_SHIFT; - printf("SL2 Correctable error occurred at bit %d of address 0x%x by scrubbing\n", - bitPos, errAddr); - } - if(ncses == 1) - { - /*scrubbing engine report address offset from 0*/ - errAddr = gpMSMC_regs->SMNCEA+0xc000000; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - printf("SL2 Non-correctable error occurred at address 0x%x by scrubbing\n", errAddr); - } - printf("%d correctable errors, %d non-correctable errors occurred during scrubbing.\n", - (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SCEC_MASK) - >>CSL_MSMC_SMSECC_SCEC_SHIFT, - (gpMSMC_regs->SMSECC&CSL_MSMC_SMSECC_SNCEC_MASK) - >>CSL_MSMC_SMSECC_SNCEC_SHIFT); - } - if(cees == 1) - { - volatile Uint32 scrubValue; - - errAddr = gpMSMC_regs->SMCERRAR; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - //scrub the address to correct the error - scrubValue= *(volatile Uint32 *)errAddr; //touch to cach - *(volatile Uint32 *)errAddr= scrubValue; //make cache dirty - CACHE_wbInvL2((void *)errAddr, 32, CACHE_WAIT); - - bitPos = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_ESYN_MASK) - >>CSL_MSMC_SMCERRXR_ESYN_SHIFT; - PrivID = (gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SEPID_MASK) - >>CSL_MSMC_SMCERRXR_SEPID_SHIFT; - printf("SL2 Correctable error occurred at bit %d of address 0x%x by PrivID %d ", - bitPos, errAddr, PrivID); - if(gpMSMC_regs->SMCERRXR&CSL_MSMC_SMCERRXR_SER_MASK) - printf("(not from C66x CorePacs)\n"); - else - printf("(from C66x CorePacs)\n"); - } - if(ncees ==1) - { - errAddr = gpMSMC_regs->SMNCERRAR; - exception_record.status.ext_sts.info.memory.fault_address= errAddr; - - PrivID = (gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SEPID_MASK) - >>CSL_MSMC_SMNCERRXR_SEPID_SHIFT; - printf("SL2 Non-correctable error occurred at address 0x%x by PrivID %d ", - errAddr, PrivID); - if(gpMSMC_regs->SMNCERRXR&CSL_MSMC_SMNCERRXR_SER_MASK) - printf("(not from C66x CorePacs)\n"); - else - printf("(from C66x CorePacs)\n"); - } - - /* clear EDC error status */ - CSL_MSMC_clearRawInterruptStatus(0, cees,ncees, cses, ncses); - - CSL_MSMC_lockNonMPAX(); -} - -/*===============================Exception=============================*/ -//data structure to save exception info -Exception_Record exception_record; - -/*some exception events routed from CIC to INTC and then to exception moduel, -all these events are routed to one input of INTC*/ -Uint32 guwIntcCICExcEvtIdx= 95; /*INTC event number mapping to CIC exception events*/ -Uint32 gCIC_EXC_out_num = 15; //CIC output event number -Uint32 gCIC_EXC_EN_MASK[8]= {0,0,0,0,0,0,0,0}; -/***************************************************************************** - Prototype : KeyStone_CIC_exception_events_mapping - Description : CIC exception event mapping to the NMI external exception - Input : void - Output : None - Return Value : - - History : - 1.Date : 2012/10/5 - Author : Brighton Feng - Modification : Created function - - 2.Date : 2012/10/20 - Author : Zhan - Modification : Add event for TCI6614 - - 3.Date : 2012/10/28 - Author : Brighton Feng -*****************************************************************************/ -void KeyStone_CIC_exception_events_mapping(void) -{ - TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); - -#if 1 - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||TCI6614_EVM==DSP_Board_Type) - { - gCIC_EXC_out_num= 15+16*DNUM; - } - else if(C6678_EVM==DSP_Board_Type) - { - if(DNUM<4) - gCIC_EXC_out_num= 7+8*DNUM; - else - { - gCIC_EXC_out_num= 7+8*(DNUM-4); - gpCIC_regs= gpCIC1_regs; - } - } - else - { - puts("Unknown DSP board type!"); - return; - } -#endif - - /*-----------------------CP_INTC configuration---------------------*/ - /* Disable Global host interrupts. */ - gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 0; - - /* route following system events to CIC out (event 22 of INTC), and then to exception - TCI6614, C6670, C6678: - CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt - CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt - CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt - CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt - CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt - CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt - CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt - CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt - CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt - CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt - CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt - CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt - CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt - CIC: 99 MSMC_dedc_nc_error Non-correctable soft error detected on SRAM read - CIC: 100 MSMC_scrub_nc_error Non-correctable soft error detected during scrub cycle - CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID - CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID - CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID - CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID - CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID - CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID - CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID - CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID - CIC: 110 DDR3_ERR DDR3 ECC Error Interrupt - TCI6614, C6670: - CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID - CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID - CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID - CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID - */ - KeyStone_CIC_event_map(gpCIC_regs, 0 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 2 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 3 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 4 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 5 , gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 16, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 18, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 19, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 20, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 21, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[0] |= - (1<<0 ) - |(1<<2 ) - |(1<<3 ) - |(1<<4 ) - |(1<<5 ) - |(1<<16) - |(1<<18) - |(1<<19) - |(1<<20) - |(1<<21); - - KeyStone_CIC_event_map(gpCIC_regs, 32, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 34, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 35, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[1] |= - (1<<(32-32)) - |(1<<(34-32)) - |(1<<(35-32)); - - KeyStone_CIC_event_map(gpCIC_regs, 99, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 100, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 102, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 103, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 104, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 105, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 106, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 107, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 108, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 109, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 110, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[3] |= - (1<<(99 -32*3)) - |(1<<(100-32*3)) - |(1<<(102-32*3)) - |(1<<(103-32*3)) - |(1<<(104-32*3)) - |(1<<(105-32*3)) - |(1<<(106-32*3)) - |(1<<(107-32*3)) - |(1<<(108-32*3)) - |(1<<(109-32*3)) - |(1<<(110-32*3)); - - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||TCI6614_EVM==DSP_Board_Type) - { - KeyStone_CIC_event_map(gpCIC_regs, 170, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 171, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 172, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 173, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[5] |= - (1<<(170-32*5)) - |(1<<(171-32*5)) - |(1<<(172-32*5)) - |(1<<(173-32*5)); - } - - /* ----------- Mapping MPU interrupt for different chips start -----------------------*/ - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type - ||C6678_EVM==DSP_Board_Type) - { - /* route the following system events to CIC out - CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt - CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt - CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt - CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt - */ - KeyStone_CIC_event_map(gpCIC_regs, 90, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 92, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 94, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 96, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[2] |= - (1<<(90 -32*2)) - |(1<<(92 -32*2)) - |(1<<(94 -32*2)); - gCIC_EXC_EN_MASK[3] |= - (1<<(96 -32*3)); - - /* 6618_6670 only */ - if(C6670_EVM==DSP_Board_Type - ||DUAL_NYQUIST_EVM==DSP_Board_Type) - { - /* - CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt - CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt - */ - KeyStone_CIC_event_map(gpCIC_regs, 174, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 180, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[5] |= - (1<<(174-32*5)) - |(1<<(180-32*5)); - } - } - - if(TCI6614_EVM==DSP_Board_Type) - { - /* route the following system events to CIC out - CIC: 23 MPU0~7 addressing violation interrupt combine output - CIC: 37 MPU0~7 protection violation interrupt combine output - */ - KeyStone_CIC_event_map(gpCIC_regs, 23, gCIC_EXC_out_num); - KeyStone_CIC_event_map(gpCIC_regs, 37, gCIC_EXC_out_num); - gCIC_EXC_EN_MASK[0] |= - (1<<23); - gCIC_EXC_EN_MASK[1] |= - (1<<(37 -32)); - - } - /* ----------- Mapping MPU interrupt for different chips end -----------------------*/ - - /* Enable Global host interrupts. */ - gpCIC_regs->GLOBAL_ENABLE_HINT_REG= 1; - -} -/***************************************************************************** - Prototype : KeyStone_Exception_cfg - Description : Config the system err and external exception to generate the NMI. - Call this function as last step after all - configuration/initialization complete - Input : Bool bGlobalExceptionMaster. If TRUE, the global exception events - from CIC will be routed to exception model of this CPU core. - Output : None - Return Value : -*****************************************************************************/ -void KeyStone_Exception_cfg(Bool bGlobalExceptionMaster) -{ - - puts("Enable Exception handling..."); - - TSCL = 0; /* Enable the TSC */ - - memset(&exception_record, 0, sizeof(exception_record)); -#if 0 - /*Clear all CPU events*/ - gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; -#endif - /*clear memory fault*/ - gpCGEM_regs->L1PMPFCR = 1; - gpCGEM_regs->L1DMPFCR = 1; - gpCGEM_regs->L2MPFCR = 1; - gpXMC_regs->XMPFCR = 1; - - /*clear configuration bus error*/ - gpCGEM_regs->ICFGMPFCR= 1; - gpCGEM_regs->ECFGERRCLR= 1; - - /* clear the MDMAERR */ - gpCGEM_regs->MDMAERRCLR = 1; - - /*clear interrupt drop staus*/ - gpCGEM_regs->INTXCLR = 1; - - gpCGEM_regs->INTDMASK= ~IER; /*only monitor drop of enabled interrupts*/ - - /*enable events: - 10 MSMC_mpf_error_n MSMC Memory protection fault caused by local CorePac - 96 INTERR Dropped CPU interrupt event - 97 EMC_IDMAERR Invalid IDMA parameters - 110 MDMAERREVT XMC VBUSM error event - 113 PMC_ED Single bit error detected during DMA accesses L1P - 117 UMC_ED2 Uncorrected bit error detected LL2 - 119 SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control - 120 PMC_CMPA CPU memory protection fault for L1P - 121 PMC_DMPA DMA memory protection fault for L1P - 122 DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller) - 123 DMC_DMPA DMA memory protection fault for L1D - 124 UMC_CMPA CPU memory protection fault for LL2 - 125 UMC_DMPA DMA memory protection fault for LL2 - 126 EMC_CMPA CPU memory protection fault for other local configuration space between 0x01000000 - 0x01BFFFFF - 127 EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF - */ - gpCGEM_regs->EXPMASK[0]= ~(1<EXPMASK[1]= 0xFFFFFFFF; - gpCGEM_regs->EXPMASK[2]= 0xFFFFFFFF; - gpCGEM_regs->EXPMASK[3]= ~((1<<(CSL_GEM_INTERR - 96))| - (1<<(CSL_GEM_EMC_IDMAERR-96))| - (1<<(CSL_GEM_MDMAERREVT-96))| - (1<<(CSL_GEM_PMC_ED-96))| - (1<<(CSL_GEM_UMC_ED2-96))| - (1<<(CSL_GEM_SYS_CMPA-96))| - (1<<(CSL_GEM_PMC_CMPA-96))| - (1<<(CSL_GEM_PMC_DMPA-96))| - (1<<(CSL_GEM_DMC_CMPA-96))| - (1<<(CSL_GEM_DMC_DMPA-96))| - (1<<(CSL_GEM_UMC_CMPA-96))| - (1<<(CSL_GEM_UMC_DMPA-96))| - (1<<(CSL_GEM_EMC_CMPA-96))| - (1<<(CSL_GEM_EMC_BUSERR-96))); - - - if(bGlobalExceptionMaster) - { - /*enable exception events routed from CIC, - please note, this should be only configured for one CPU*/ - KeyStone_CIC_exception_events_mapping(); - gpCGEM_regs->EXPMASK[guwIntcCICExcEvtIdx>>5] &= (~(1<<(guwIntcCICExcEvtIdx&0x1F))); - } - - /*clear exception flag*/ - ECR = EFR; - IERR = 0; - - /*Eanble external exception, global exception enable*/ - TSR = TSR| - (1<>CSL_CGEM_MDMAERR_ERR_SHIFT; - if (1==err) { - puts(" MDMA read status error detected"); - } - else if (2==err) { - puts(" MDMA write status error detected"); - } - else if (3==err) { - puts(" CFG read status error detected"); - } - else if (4==err) { - puts(" CFG write status error detected"); - } - - printf(" XID (Transaction ID)= %d\n", - (ERR_REG & CSL_CGEM_MDMAERR_XID_MASK)>>CSL_CGEM_MDMAERR_XID_SHIFT); - - stat= (ERR_REG & CSL_CGEM_MDMAERR_STAT_MASK)>>CSL_CGEM_MDMAERR_STAT_SHIFT; - printf(" %s\n", bus_err_stat_str[stat]); -} - -/***************************************************************************** - Prototype : KeyStone_CIC_EXC_handler - Description : This function handle the exception events from CIC - Input : void - Output : None - Return Value : void - - History : - 1.Date : 2012/10/18 - Author : Zhan - Modification : Created function - - 2.Date : 2012/10/28 - Author : Brighton Feng - Modification : Add EDMA error processing - -*****************************************************************************/ -void KeyStone_CIC_EXC_handler() -{ - int i; - Uint32 status[4], status5 = 0; - - TDSP_Board_Type DSP_Board_Type; - - DSP_Board_Type= KeyStone_Get_dsp_board_type(); - - /*Step1: Disable CIC host interrupt*/ - KeyStone_CIC_disable_host_int(gpCIC_regs, gCIC_EXC_out_num); - - status[0]= gpCIC_regs->ENA_STATUS_REG[0]&gCIC_EXC_EN_MASK[0]; - status[1]= gpCIC_regs->ENA_STATUS_REG[1]&gCIC_EXC_EN_MASK[1]; - status[2]= gpCIC_regs->ENA_STATUS_REG[2]&gCIC_EXC_EN_MASK[2]; - status[3]= gpCIC_regs->ENA_STATUS_REG[3]&gCIC_EXC_EN_MASK[3]; - exception_record.status.ext_sts.CIC_STATUS[0]= status[0]; - exception_record.status.ext_sts.CIC_STATUS[1]= status[1]; - exception_record.status.ext_sts.CIC_STATUS[2]= status[2]; - exception_record.status.ext_sts.CIC_STATUS[3]= status[3]; - - /*Step2: clear system events*/ - gpCIC_regs->ENA_STATUS_REG[0]= status[0]; - gpCIC_regs->ENA_STATUS_REG[1]= status[1]; - gpCIC_regs->ENA_STATUS_REG[2]= status[2]; - gpCIC_regs->ENA_STATUS_REG[3]= status[3]; - - /* The different device INTC number is different, if read the non-exist space will - trigger the L1D memory protection error. - */ - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - status5 = gpCIC_regs->ENA_STATUS_REG[5]&gCIC_EXC_EN_MASK[5]; - exception_record.status.ext_sts.CIC_STATUS[5]= status5; - - /*Step2: clear system events*/ - gpCIC_regs->ENA_STATUS_REG[5]= status5 ; - } - - /*----------------------------EDMA error-----------------------------*/ - /* - CIC: 0 EDMA3CC1 EDMACC_ERRINT EDMA3CC1 error interrupt - CIC: 2 EDMA3CC1 EDMATC_ERRINT0 EDMA3CC1 EDMA3TC0 error interrupt - CIC: 3 EDMA3CC1 EDMATC_ERRINT1 EDMA3CC1 EDMA3TC1 error interrupt - CIC: 4 EDMA3CC1 EDMATC_ERRINT2 EDMA3CC1 EDMA3TC2 error interrupt - CIC: 5 EDMA3CC1 EDMATC_ERRINT3 EDMA3CC1 EDMA3TC3 error interrupt*/ - if(status[0]&0x3D) - EDMA_error_handler(1, status[0]&0x3D); - - /* - CIC: 16 EDMA3CC2 EDMACC_ERRINT EDMA3CC2 error interrupt - CIC: 18 EDMA3CC2 EDMATC_ERRINT0 EDMA3CC2 EDMA3TC0 error interrupt - CIC: 19 EDMA3CC2 EDMATC_ERRINT1 EDMA3CC2 EDMA3TC1 error interrupt - CIC: 20 EDMA3CC2 EDMATC_ERRINT2 EDMA3CC2 EDMA3TC2 error interrupt - CIC: 21 EDMA3CC2 EDMATC_ERRINT3 EDMA3CC2 EDMA3TC3 error interrupt*/ - if((status[0]>>16)&0x3D) - EDMA_error_handler(2, (status[0]>>16)&0x3D); - - /* - CIC: 32 EDMA3CC0 EDMACC_ERRINT EDMA3CC0 error interrupt - CIC: 34 EDMA3CC0 EDMATC_ERRINT0 EDMA3CC0 EDMA3TC0 error interrupt - CIC: 35 EDMA3CC0 EDMATC_ERRINT1 EDMA3CC0 EDMA3TC1 error interrupt*/ - if(status[1]&0xD) - EDMA_error_handler(0, status[1]&0xD); - - /*----------------------------MPU error-----------------------------*/ - if(TCI6614_EVM == DSP_Board_Type) - { - //CIC: 23 MPU0~7 addressing violation interrupt combine output - //CIC: 37 MPU0~7 protection violation interrupt combine output - if((status[0]&(1<<23))||(status[1]&(1<<(37-32)))) - { - for(i=0; i<8; i++) - { - /*MPU5 (for BCP) of TCI6614 is only accessible - when BCP is enabled through PSC*/ - if((5==i)&& - ((CSL_PSC_getPowerDomainState(5) != PSC_PDSTATE_ON) || - (CSL_PSC_getModuleState (12) != PSC_MODSTATE_ENABLE))) - continue; - - if(gpMPU_regs[i]->INT_RAW_STATUS_SET & 0x3) - { - KeyStone_peripherals_MPU_excepiton_handler(i); - } - } - - /*The MPU events in TCI6614 are different from other KeyStone - devices. All the MPU0~7 events are combined into single event - and connected to the CIC0 as one system event. - We have to clear the MPU event flag at the source level first - and then are able to clear the CIC flags because the INTD for the - MPU events is for the combination purpose but do not convert - the level interrupt to pulse.*/ - /*clear system events*/ - gpCIC_regs->ENA_STATUS_REG[0]= status[0]; - gpCIC_regs->ENA_STATUS_REG[1]= status[1]; - } - } - else - { - //CIC: 90 MPU0 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(90-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(0); - } - //CIC: 92 MPU1 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(92-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(1); - } - //CIC: 94 MPU2 addressing violation interrupt and protection violation interrupt - if(status[2]&(1<<(94-64))) - { - KeyStone_peripherals_MPU_excepiton_handler(2); - } - //CIC: 96 MPU3 addressing violation interrupt and protection violation interrupt - if(status[3]&(1<<(96-96))) - { - KeyStone_peripherals_MPU_excepiton_handler(3); - } - - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type)) - { - //CIC: 174 MPU4 addressing violation interrupt and protection violation interrupt - //CIC: 180 MPU5 addressing violation interrupt and protection violation interrupt - if(status5&(1<<(174-160))) - { - KeyStone_peripherals_MPU_excepiton_handler(4); - } - if(status5&(1<<(180-160))) - { - KeyStone_peripherals_MPU_excepiton_handler(5); - } - } - } - - /*----------------------------MSMC error-----------------------------*/ - //CIC: 99 MSMC_dedc_nc_error Non-correctable (2-bit) soft error detected on SRAM read - if(status[3]&(1<<(99-96))) - { - KeyStone_SL2_EDC_handler(); - } - //CIC: 100 MSMC_scrub_nc_error Non-correctable (2-bit) soft error detected during scrub cycle - if(status[3]&(1<<(100-96))) - { - KeyStone_SL2_EDC_handler(); - } - - /* - CIC: 102 MSMC_mpf_error8 Memory protection fault indicators for each system master PrivID - CIC: 103 MSMC_mpf_error9 Memory protection fault indicators for each system master PrivID - CIC: 104 MSMC_mpf_error10 Memory protection fault indicators for each system master PrivID - CIC: 105 MSMC_mpf_error11 Memory protection fault indicators for each system master PrivID - CIC: 106 MSMC_mpf_error12 Memory protection fault indicators for each system master PrivID - CIC: 107 MSMC_mpf_error13 Memory protection fault indicators for each system master PrivID - CIC: 108 MSMC_mpf_error14 Memory protection fault indicators for each system master PrivID - CIC: 109 MSMC_mpf_error15 Memory protection fault indicators for each system master PrivID*/ - if((status[3]>>(102-96))&0xFF) - KeyStone_MSMC_protection_exception_handler(); - - if((C6670_EVM == DSP_Board_Type) - ||(DUAL_NYQUIST_EVM == DSP_Board_Type) - ||(TCI6614_EVM == DSP_Board_Type)) - { - /* - CIC: 170 MSMC_mpf_error4 Memory protection fault indicators for each system master PrivID - CIC: 171 MSMC_mpf_error5 Memory protection fault indicators for each system master PrivID - CIC: 172 MSMC_mpf_error6 Memory protection fault indicators for each system master PrivID - CIC: 173 MSMC_mpf_error7 Memory protection fault indicators for each system master PrivID*/ - if((status5>>(170-160))&0xF) - KeyStone_MSMC_protection_exception_handler(); - - } - - /*----------------------------DDR ECC error-------------------------*/ - //CIC: 110 DDR3_ERR DDR3_EMIF Error Interrupt - if(status[3]&(1<<(110-96))) - { - printf(" DDR ECC error happened during "); - - exception_record.status.ext_sts.info.memory.fault_status.DDR_IRQSTATUS_SYS= - gpDDR_regs->IRQSTATUS_SYS; - - if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK) - printf("read "); - if(gpDDR_regs->IRQSTATUS_SYS&CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK) - printf("write "); - printf(".\n"); - - //clear the status - gpDDR_regs->IRQSTATUS_SYS= CSL_EMIF4F_IRQSTATUS_SYS_REG_RD_ECC_ERR_SYS_MASK - |CSL_EMIF4F_IRQSTATUS_SYS_REG_WR_ECC_ERR_SYS_MASK; - } - - /*Step3: Enable the CIC host interrupt */ - KeyStone_CIC_enable_host_int(gpCIC_regs, gCIC_EXC_out_num); - -} - -/***************************************************************************** - Prototype : KeyStone_EXC_external - Description : external exception processing - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_EXC_external(void) -{ - int i; - unsigned int INTXSTAT, flag[4]; - - for(i= 0; i<4; i++) - { - flag[i] = gpCGEM_regs->MEXPFLAG[i]; - if(flag[i]) - { - exception_record.status.ext_sts.MEXPFLAG[i]= flag[i]; - printf("External exception happened. MEXPFLAG[%d]=0x%x.\n", - i, flag[i]); - gpCGEM_regs->EVTCLR[i] = flag[i]; - } - } - - if(0 == (flag[0]|flag[1]|flag[2]|flag[3])) - { - puts("Enter external Exception service routine, but external excpetion flage is 0!"); - return; - } - - /*Exception events routed from CIC*/ - if(flag[guwIntcCICExcEvtIdx>>5] & (1<<(guwIntcCICExcEvtIdx&0x1F))) - { - KeyStone_CIC_EXC_handler(); - } - - /*MSMC memory protection exception*/ - if(flag[0]&(1<INTXSTAT; - exception_record.status.ext_sts.info.INTXSTAT= INTXSTAT; - - if(INTXSTAT&CSL_CGEM_INTXSTAT_DROP_MASK) - printf(" Event 96: DSP Interrupt %d (INTC input Event %d) dropped\n", - (INTXSTAT&CSL_CGEM_INTXSTAT_CPUINT_MASK)>>CSL_CGEM_INTXSTAT_CPUINT_SHIFT, - (INTXSTAT&CSL_CGEM_INTXSTAT_SYSINT_MASK)>>CSL_CGEM_INTXSTAT_SYSINT_SHIFT); - } - - if(flag[3]&(1<<(CSL_GEM_EMC_IDMAERR-96))) - puts(" Event 97: EMC_IDMAERR Invalid IDMA parameters"); - - /*MDMA XMC VBUSM error*/ - if(flag[3]&(1<<(CSL_GEM_MDMAERREVT-96))) - { - puts(" Event 110: MDMAERREVT XMC VBUSM error event"); - if(gpXMC_regs->XMPFSR) - { - /*XMC protection error*/ - memory_protection_exception_handler(gpXMC_regs->XMPFAR, gpXMC_regs->XMPFSR); - gpXMC_regs->XMPFCR = 1; - } - else - { - /*other VBUSM error*/ - Bus_error_handler(gpCGEM_regs->MDMAERR); - } - /* clear the MDMAERR */ - gpCGEM_regs->MDMAERRCLR = 1; - } - - /*L1P Single bit error detected during DMA read*/ - if(flag[3]&(1<<(CSL_GEM_PMC_ED-96))) - { - puts(" Event 113: PMC_ED Single bit error detected during DMA read"); - L1P_ED_handler(); - } - - /*LL2 Uncorrected bit error detected*/ - if(flag[3]&(1<<(CSL_GEM_UMC_ED2-96))) - { - puts(" Event 117: UMC_ED2 Uncorrected bit error detected"); - LL2_EDC_handler(FALSE); - } - - /*local register memory protection exception*/ - if(flag[3]&(1<<(CSL_GEM_SYS_CMPA-96))) - { - puts(" Event 119: SYS_CMPA CPU Memory Protection Fault for local configuration of INTC and power control"); - } - - /*L1P memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_PMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_PMC_CMPA-96))) - puts(" Event 120: PMC_CMPA CPU memory protection fault for L1P"); - if(flag[3]&(1<<(CSL_GEM_PMC_DMPA-96))) - puts(" Event 121: PMC_DMPA DMA memory protection fault for L1P"); - memory_protection_exception_handler(gpCGEM_regs->L1PMPFAR, gpCGEM_regs->L1PMPFSR); - gpCGEM_regs->L1PMPFCR = 1; - } - - /*L1D memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_DMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_DMC_CMPA-96))) - puts(" Event 122: DMC_CMPA CPU memory protection fault for L1D (and other memory read finally goes through the L1D controller)"); - if(flag[3]&(1<<(CSL_GEM_DMC_DMPA-96))) - puts(" Event 123: DMC_DMPA DMA memory protection fault for L1D"); - memory_protection_exception_handler(gpCGEM_regs->L1DMPFAR, gpCGEM_regs->L1DMPFSR); - gpCGEM_regs->L1DMPFCR = 1; - } - - /*LL2 memory protection exception*/ - if(flag[3]&(3<<(CSL_GEM_UMC_CMPA-96))) - { - if(flag[3]&(1<<(CSL_GEM_UMC_CMPA-96))) - puts(" Event 124: UMC_CMPA CPU memory protection fault for L2 "); - if(flag[3]&(1<<(CSL_GEM_UMC_DMPA-96))) - puts(" Event 125: UMC_DMPA DMA memory protection fault for L2 "); - memory_protection_exception_handler(gpCGEM_regs->L2MPFAR, gpCGEM_regs->L2MPFSR); - gpCGEM_regs->L2MPFCR = 1; - } - - /*local registers protection exception*/ - if(flag[3]&(1<<(CSL_GEM_EMC_CMPA-96))) - { - puts(" Event 126: EMC_CMPA CPU memory protection fault for local configuration space between 0x01000000-0x01BFFFFF"); - memory_protection_exception_handler(gpCGEM_regs->ICFGMPFAR, gpCGEM_regs->ICFGMPFSR); - gpCGEM_regs->ICFGMPFCR= 1; - } - - /*external configuration bus error*/ - if(flag[3]&(Uint32)(1<<(CSL_GEM_EMC_BUSERR-96))) - { - puts(" Event 127: EMC_BUSERR Bus Error Interrupt for global configuration space between 0x01C00000 - 0x07FFFFFF"); - Bus_error_handler(gpCGEM_regs->ECFGERR); - gpCGEM_regs->ECFGERRCLR= 1; - } -} - -char * internal_exception_str[]= -{ - "Instruction fetch exception", - "Fetch packet exception", - "Execute packet exception", - "Opcode exception", - "Resource conflict exception", - "Resource access exception", - "Privilege exception", - "SPLOOP buffer exception", - "Missed stall exception" -}; - -/***************************************************************************** - Prototype : EXC_internal - Description : internal exception handler - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -/*internal exception handler*/ -void EXC_internal(void) -{ - int i; - unsigned int ierr; - - /*record IERR */ - ierr = IERR; - exception_record.status.IERR= ierr; - - if(ierr) - { - /*Clear internal excpeiton flag*/ - IERR= 0; - - printf("internal excpetion happened. IERR=0x%x.\n", ierr); - for(i=0; i<9; i++) - { - if((ierr>>i)&1) - printf(" %s\n", internal_exception_str[i]); - } - if (ierr & CSL_CHIP_IERR_IFX_MASK) { - /* L1P EDC Processing*/ - L1P_ED_handler(); - } - } - else - puts("Enter Internal Exception service routine, but internal excpetion flage is 0!"); - -} -/***************************************************************************** - Prototype : EXC_nmi - Description : NMI processing - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -void EXC_NMI(void) -{ - puts("NMI exception happened, normally you should reset the DSP to recover from the problem!"); -} - -/***************************************************************************** - Prototype : EXC_swgen - Description : software generated exception handler - Input : void - Output : None - Return Value : -*****************************************************************************/ -void EXC_swgen(void) -{ - puts("Software generated exception happened."); -} - -/***************************************************************************** - Prototype : Exception_service_routine - Description : Exception service routine - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -#pragma NMI_INTERRUPT( Exception_service_routine ); -void Exception_service_routine(void) -{ - unsigned int efr, nrp, ntsr, tscl, tsch, irp, itsr; - - /*record timestamp*/ - tscl = TSCL; - exception_record.TSCL= tscl; - tsch = TSCH; - exception_record.TSCH= tsch; - - nrp = NRP; /*record NRP */ - exception_record.NRP= nrp; - ntsr = NTSR; /*record NTSR */ - exception_record.NTSR= ntsr; - efr = EFR; /*record EFR */ - exception_record.EFR= efr; - - irp = IRP; /*record IRP */ - itsr = ITSR; /*record ITSR */ - exception_record.IRP= irp; - exception_record.ITSR= itsr; - - if(efr) - { - /*Clear excpeiton flag*/ - ECR = efr; - - /*check all possible exceptions*/ - if (efr & CSL_CHIP_EFR_OXF_MASK) { - /* S/W generated exception */ - EXC_swgen(); - } - if (efr & CSL_CHIP_EFR_IXF_MASK) { - /* internal exception */ - EXC_internal(); - } - if (efr & CSL_CHIP_EFR_EXF_MASK) { - /* external exception */ - KeyStone_EXC_external(); - } - if (efr & CSL_CHIP_EFR_NXF_MASK) { - /* legacy NMI exception */ - EXC_NMI(); - } - } - else - puts("Enter Exception service routine, but excpetion flage is 0!"); - - printf("NRP=0x%x, NTSR=0x%x, IRP=0x%x, ITSR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", - nrp, ntsr, irp, itsr, tsch, tscl); - - printf(" B3=0x%x, A4=0x%x, B4= 0x%x, B14= 0x%x, B15= 0x%x\n", - exception_record.B3, exception_record.A4, - exception_record.B4, exception_record.B14, - exception_record.B15); - - /* - It is not always possible to safely exit the exception handling routine. Conditions that - can prevent a safe return from exceptions include: - 1. SPLOOPs that are terminated by an exception cannot be resumed correctly. The - SPLX bit in NTSR should be verified to be 0 before returning. - 2. Exceptions that occur when interrupts are blocked cannot be resumed correctly. - The IB bit in NTSR should be verified to be 0 before returning. - 3. Exceptions that occur at any point in the code that cannot be interrupted safely - (for example, a tight loop containing multiple assignments) cannot be safely - returned to. The compiler will normally disable interrupts at these points in the - program; check the GIE bit in NTSR to be 1 to verify that this condition is met. - 4. NRP is not in valid address space*/ - if((ntsr&CSL_CHIP_TSR_SPLX_MASK) - ||(ntsr&CSL_CHIP_TSR_IB_MASK) - ||(0==(ntsr&CSL_CHIP_TSR_GIE_MASK)) - ||(0x800000>NRP)) - { - puts("Exception happened at a place can not safely return!"); - //while(1); //trap - exit(0); - } - -} - -/***************************************************************************** - Prototype : Nested_Exception_service_routine - Description : Nested Exception service routine - When a non-maskable exception happens in the first exception service routine, - then the reset vector is used when redirecting program execution to service the second - exception. In this case, NTSR and NRP are left unchanged. TSR is copied to ITSR and - the current PC is copied to IRP. TSR is set to the default exception processing value and - the NMIE bit in IER is cleared in this case preventing any further external exceptions. - Input : void - Output : None - Return Value : - - History : - 1.Date : 2010/12/29 - Author : Brighton Feng - Modification : Created function - -*****************************************************************************/ -interrupt void Nested_Exception_service_routine(void) -{ - unsigned int tscl, tsch; - - /*record timestamp*/ - tscl = TSCL; - tsch = TSCH; - - if(0==exception_record.TSCL) - exception_record.TSCL= tscl; - if(0==exception_record.TSCH) - exception_record.TSCH= tsch; - if(0==exception_record.NRP) - exception_record.NRP= NRP; - if(0==exception_record.NTSR) - exception_record.NTSR= NTSR; - if(0==exception_record.EFR) - exception_record.EFR= EFR; - if(0==exception_record.status.IERR) - exception_record.status.IERR= IERR; - - exception_record.IRP= IRP; - exception_record.ITSR= ITSR; - - printf("Nested exception happened! IRP=0x%x, ITSR=0x%x\n", - IRP, ITSR); - - printf("NRP=0x%x, NTSR=0x%x, EFR=0x%x, IERR=0x%x, TSCH= 0x%x, TSCL= 0x%x\n", - NRP, NTSR, EFR, IERR, tsch, tscl); - - while(1); //trap -// exit(0); -} - -/*=========================other utility functions==========================*/ -/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ -void CPU_interrupt_init() -{ - //clear interrupt and excpetion events - ICR = IFR; - ECR = EFR; - IER= 3; //disable all interrupts - - /* disable event combine */ - gpCGEM_regs->EVTMASK[0] = 0xffffffff; - gpCGEM_regs->EVTMASK[1] = 0xffffffff; - gpCGEM_regs->EVTMASK[2] = 0xffffffff; - gpCGEM_regs->EVTMASK[3] = 0xffffffff; - - /*Clear all CPU events*/ - gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; - - /*Interrupt Service Table Pointer to begining of LL2 memory*/ - ISTP= 0x800000; -} - -/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ -void CPU_interrupt_enable(Uint32 uiIER_en_mask) -{ - ICR= uiIER_en_mask; - IER |= uiIER_en_mask; - - //enable GIE - TSR = TSR|1; -} - -/***************************************************************************** - Prototype : KeyStone_get_device_info - Description : Get device information - Input : None - Output : None - Return Value : - - History : - 1.Date : 2010/12/12 - Author : Brighton Feng - Modification : Created function - 2.Date : 2014/12/2 - Author : Brighton Feng - Modification : Update to parser device type, boot mode, endian information, - speed grade, required CVDD - -*****************************************************************************/ -//get device speed grade from the EFUSE register -void KeyStone_get_device_speed_grade() -{ - Uint32 uiDevSpeed, uiSpeedCode; - - uiSpeedCode= (DEVSPEED&DEVSPEED_DSP_SPEED_MASK)>>DEVSPEED_DSP_SPEED_SHIFT; - - if(uiSpeedCode&DEVSPEED_800_MHZ_MASK_H) uiDevSpeed= 800; - else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_H) uiDevSpeed= 1000; - else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_H) uiDevSpeed= 1200; - else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_H) uiDevSpeed= 1250; - else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_H) uiDevSpeed= 1400; - else if(uiSpeedCode&DEVSPEED_1400_MHZ_MASK_L) uiDevSpeed= 1400; - else if(uiSpeedCode&DEVSPEED_1250_MHZ_MASK_L) uiDevSpeed= 1250; - else if(uiSpeedCode&DEVSPEED_1200_MHZ_MASK_L) uiDevSpeed= 1200; - else if(uiSpeedCode&DEVSPEED_1000_MHZ_MASK_L) uiDevSpeed= 1000; - else uiDevSpeed= 800; - - printf("Device speed grade = %dMHz.\n", uiDevSpeed); -} - -char * device_type_str[]= -{ - "TCI6616", - "C6670/TCI6618", - "C6678/TCI6608", - "TCI6614", - "unknown" -}; -char * endian_str[]= -{ - "big", - "little" -}; -char * boot_mode_str[]= -{ - "No boot or EMIF16(NOR FLASH) or UART", - "Serial Rapid I/O", - "Ethernet (SGMII)", - "Ethernet (SGMII) or NAND FLASH", - "PCIE", - "I2C", - "SPI", - "HyperLink" - }; -char * input_clk_str[]= -{ - "50MHz", - "66.67MHz", - "80MHz", - "100MHz", - "156.25MHz", - "250MHz", - "312.5MHz", - "122.88MHz", - "bypassed" -}; -void KeyStone_get_device_info() -{ - char * boot_mode; - Uint8 ucBootMode, ucBootMaster; - Uint32 uiVID; - Uint8 ucPLL_cfg= 8; //8 means bypassed - Uint32 * DieID= (Uint32 *)&gpBootCfgRegs->DIE_ID_REG0; - Uint32 uiJTAG_ID = gpBootCfgRegs->DEVICE_ID_REG0; - Uint32 uiDevStat = gpBootCfgRegs->BOOT_REG0; - - gDSP_board_type=KeyStone_Get_dsp_board_type(); - - ucBootMode= (uiDevStat&DEVSTAT_BOOTMODE_MASK)>>DEVSTAT_BOOTMODE_SHIFT; - ucBootMaster= (uiDevStat&DEVSTAT_BOOTMASTER_MASK)>>DEVSTAT_BOOTMASTER_SHIFT; - - if((TCI6614_EVM==gDSP_board_type)&&(1==ucBootMaster)) - { - boot_mode= "ARM"; //ARM boot - } - else - boot_mode= boot_mode_str[ucBootMode]; - - //PLL is not configured with SPI and I2C master boot mode - if((5!=ucBootMode)&&(6!=ucBootMode)) - ucPLL_cfg= (uiDevStat&DEVSTAT_SYSPLL_MASK)>>DEVSTAT_SYSPLL_SHIFT; - - printf("JTAG ID= 0x%08x. This is %s device, version variant = %d.\n", uiJTAG_ID, - device_type_str[gDSP_board_type], uiJTAG_ID>>28); - - printf("DEVSTAT= 0x%08x. %s endian, %s boot, PLL configuration implies the input clock for core is %s.\n", - uiDevStat, endian_str[uiDevStat&DEVSTAT_LENDIAN_MASK], boot_mode, - input_clk_str[ucPLL_cfg]); - - uiVID= (gpPSC_regs->VCNTLID&CSL_PSC_VCNTLID_VCNTL_MASK)>>CSL_PSC_VCNTLID_VCNTL_SHIFT; - printf("SmartReflex VID= %d, required core voltage= %.3fV.\n", uiVID, 0.7+(float)uiVID*0.41/64.f); - - printf("Die ID= 0x%08x, 0x%08x, 0x%08x, 0x%08x\n", DieID[0], DieID[1], DieID[2], DieID[3]); - - KeyStone_get_device_speed_grade(); -} -/***************************************************************************** - Prototype : KeyStone_common_device_init - Description : common initialization for internal modules in K2 device - enable memory protection interrupts, EDC for MSMC RAM - History : - 1.Date : July 11, 2014 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_common_device_init() -{ - int i; - KeyStone_get_device_info(); - - /* enable common MPU interrupts */ - for(i=0; i<4; i++) - { - KeyStone_MPU_interrupt_enable(i); - } - - /*Enable MSMC EDC and setup scrubbing cycle counter= 255*1024*/ - KeyStone_SL2_EDC_enable(255); -} - -/***************************************************************************** - Prototype : KeyStone_common_CPU_init - Description : common initialization for internal modules in K2 device - enable TSC, EDC for local RAM; clear cache; protect L1 as cache - History : - 1.Date : September 1, 2014 - Author : Brighton Feng - Modification : Created function -*****************************************************************************/ -void KeyStone_common_CPU_init() -{ - TSC_init(); //initialize TSC to measure cycle - - /*clear all interrupt flag/status, setup ISTP to begining of LL2*/ - CPU_interrupt_init(); - - /*clean cache from previous run, not required from power on or cold reset*/ - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - _mfence(); - _mfence(); - - /* protect L1 as cache */ - L1_cache_protection(); - - //Enable MSMC Memory protection error interrupt for local core, refer to MSMC user guide section3.8 - KeyStone_MSMC_MP_interrupt_en(1< -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/*----------------------PLL registers definition----------------*/ -#define PLLCTL0_PLLD_SHIFT (0) -#define PLLCTL0_PLLD_MASK (0x3F<>4) | 0x80000000) - -/*max number in two numbers*/ -#define MAX(a, b) (a>b?a:b) -/*min number in two numbers*/ -#define MIN(a, b) (a0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline void WritebackCache(void * blockPtr, Uint32 byteCnt) -{ - if(byteCnt>0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbL2((void *)blockPtr, byteCnt, CACHE_WAIT); - } - _mfence(); - _mfence(); -} - -static inline void WritebackAllCache(void * blockPtr) -{ - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbAllL1d(CACHE_WAIT);; - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbAllL2(CACHE_WAIT); - } - _mfence(); - _mfence(); -} - -static inline void WritebackInvalidCache(void * blockPtr, Uint32 byteCnt) -{ -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - Uint32 uiOldGIE= _disable_interrupts(); -#endif - - if(byteCnt>0xFFFF*4) - byteCnt= 0xFFFF*4; - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbInvL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - CACHE_wbInvL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline void WritebackInvalidAllCache(void * blockPtr) -{ -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - Uint32 uiOldGIE= _disable_interrupts(); -#endif - - if((Uint32)blockPtr>=0x0C000000&&(Uint32)blockPtr<0x0D000000) //SL2 - { - CACHE_wbInvAllL1d(CACHE_WAIT);//CACHE_invL1d((void *)blockPtr, byteCnt, CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - else if((Uint32)blockPtr>=0x10000000) //DDR or other cores - { - //CACHE_invL2((void *)blockPtr, byteCnt, CACHE_WAIT); - CACHE_wbInvAllL2(CACHE_WAIT); - CSL_XMC_invalidatePrefetchBuffer(); - } - _mfence(); - _mfence(); - -#if CACHE_DISABLE_INT -/*workaround for the "L2 Cache Corruption During Block and Global Coherence Operations -Issue" described in errata of some devices*/ - asm(" nop 8"); - asm(" nop 8"); - _restore_interrupts(uiOldGIE); //restore interrupt -#endif -} - -static inline unsigned int SWAP_ENDIAN(unsigned int byte_index) -{ -#ifdef _BIG_ENDIAN - return ((byte_index&0xFFFFFFFC)+(3-byte_index&3)); -#else - return byte_index; -#endif -} - -static inline void KeyStone_CIC_clear_system_event(CSL_CPINTCRegs* cpIntcRegs, - int input_event_num) -{ - volatile Uint32 dummy_value; - - /*clear input interrupts events*/ - cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->STATUS_CLR_INDEX_REG; -} - -static inline void KeyStone_CIC_disable_host_int(CSL_CPINTCRegs* cpIntcRegs, - int host_int_num) -{ - volatile Uint32 dummy_value; - - /* Disable the host interrupt */ - cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG = host_int_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->HINT_ENABLE_CLR_INDEX_REG; -} - -static inline void KeyStone_CIC_enable_host_int(CSL_CPINTCRegs* cpIntcRegs, - int host_int_num) -{ - volatile Uint32 dummy_value; - - /* Enable the host interrupt */ - cpIntcRegs->HINT_ENABLE_SET_INDEX_REG = host_int_num; - - /*dummy read to make sure the previous write data land into the register*/ - dummy_value= cpIntcRegs->HINT_ENABLE_SET_INDEX_REG; -} - -static inline void KeyStone_CIC_event_map(CSL_CPINTCRegs* cpIntcRegs, - int input_event_num, int out_num) -{ - /*Map input event to output*/ - cpIntcRegs->CH_MAP[SWAP_ENDIAN(input_event_num)]= out_num; - - /*clear input interrupts events*/ - cpIntcRegs->STATUS_CLR_INDEX_REG= input_event_num; - - /*enable input interrupts events*/ - cpIntcRegs->ENABLE_SET_INDEX_REG= input_event_num; - - /*enable output*/ - cpIntcRegs->HINT_ENABLE_SET_INDEX_REG= out_num; -} - - -typedef enum -{ - DUAL_NYQUIST_EVM = 0, - C6670_EVM, - C6678_EVM, - TCI6614_EVM, - C6657_EVM, - UNKNOWN -}TDSP_Board_Type; - -extern TDSP_Board_Type gDSP_board_type; - -static inline TDSP_Board_Type KeyStone_Get_dsp_board_type() -{ - Uint32 deviceID= gpBootCfgRegs->DEVICE_ID_REG0&0x0FFFFFFF; - - gDSP_board_type= UNKNOWN; - if(0x0009D02F == deviceID) - gDSP_board_type= DUAL_NYQUIST_EVM; - if(0x0B94102F == deviceID) - { - gDSP_board_type= C6670_EVM; - //DSP_Board_Type= DUAL_NYQUIST_EVM; - } - if(0x0009E02F == deviceID) - gDSP_board_type= C6678_EVM; - if(0x0B96202F == deviceID) - gDSP_board_type= TCI6614_EVM; - if(0x0B97A02F == deviceID) - gDSP_board_type= C6657_EVM; - - return gDSP_board_type; -} - -static inline Uint32 KeyStone_Get_DSP_Number() -{ - TDSP_Board_Type DSP_Board_Type= KeyStone_Get_dsp_board_type(); - - if(DUAL_NYQUIST_EVM==DSP_Board_Type) - { - /*Nyquist EVM use boot configure pin 4 and 5 to identify DSPs*/ - return (( gpBootCfgRegs->BOOT_REG0 >> (3+1) ) & 0x03); - } - - /*if use DNUM to differentiate DSPs for two DSPs test, - the program must be run on core 0 of DSP 0 and core 1 of DSP1*/ - return DNUM; -} - -/*clear all interrupt flag/status, setup ISTP to begining of LL2*/ -extern void CPU_interrupt_init(); -/*enable interrupt to CPU: IER |= uiIER_en_mask; GIE=1*/ -extern void CPU_interrupt_enable(Uint32 uiIER_en_mask); - -//get device speed grade from the EFUSE register -extern void KeyStone_get_device_speed_grade(); - -/*Get device information including device type, boot mode, endian information, -speed grade, required voltage...*/ -extern void KeyStone_get_device_info(); - -/*common initialization for internal modules in K2 device. -enable memory protection interrupts, EDC for MSMC RAM*/ -extern void KeyStone_common_device_init(); - -/* enable TSC, EDC for local RAM; clear cache; protect L1 as cache */ -extern void KeyStone_common_CPU_init(); - - -#endif diff --git a/bsp/ti-tms320c6678/common/common.c b/bsp/ti-tms320c6678/common/common.c new file mode 100644 index 0000000000..0e026659ed --- /dev/null +++ b/bsp/ti-tms320c6678/common/common.c @@ -0,0 +1,201 @@ +/* + * Copyright (c) 2021, Shenzhen Academy of Aerospace Technology + * + * SPDX-License-Identifier: Apache-2.0 + * + * Change Logs: + * Date Author Notes + * 2021-11-16 Dystopia the first version + */ + +#include "common.h" + +CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; +CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; +CSL_TmrPlusRegs * gpTimerRegs[9] = { + (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_3_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_4_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_5_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_6_REGS, + (CSL_TmrPlusRegs *)CSL_TIMER_7_REGS, + (CSL_TmrPlusRegs *)(CSL_TIMER_7_REGS+(CSL_TIMER_7_REGS-CSL_TIMER_6_REGS)) +}; + +void cpu_interrupt_init(void) +{ + //clear interrupt and excpetion events + ICR = IFR; + ECR = EFR; + IER= 3; //disable all interrupts + + /* disable event combine */ + gpCGEM_regs->EVTMASK[0] = 0xffffffff; + gpCGEM_regs->EVTMASK[1] = 0xffffffff; + gpCGEM_regs->EVTMASK[2] = 0xffffffff; + gpCGEM_regs->EVTMASK[3] = 0xffffffff; + + /*Clear all CPU events*/ + gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; + gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; + + /*Interrupt Service Table Pointer to begining of LL2 memory*/ + ISTP= 0x800000; +} + +void keystone_cpu_init(void) +{ + /* clear all interrupt flag/status, setup ISTP to begining of LL2 */ + cpu_interrupt_init(); +} + +/*===============================Timer=================================*/ +void reset_timer(int timer_num) +{ + if(gpTimerRegs[timer_num]->TGCR) + { + gpTimerRegs[timer_num]->TGCR= 0; + gpTimerRegs[timer_num]->TCR= 0; + } +} + +void timer64_init(Timer64_Config * tmrCfg) +{ + reset_timer(tmrCfg->timer_num); + + gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; + gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; + + /*please note, in clock mode, two timer periods generate a clock, + one timer period output high voltage level, the other timer period + output low voltage level, so, the timer period should be half to the + desired output clock period*/ + if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) + tmrCfg->period= tmrCfg->period/2; + + /*the value written into period register is the expected value minus one*/ + gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); + gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); + if(tmrCfg->reload_period>1) + { + gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); + gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); + } + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select watch-dog mode*/ + (CSL_TMR_TIMMODE_WDT<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK + /*for plus featuers, dual 32-bit unchained timer mode should be used*/ + |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; + } + else + { + gpTimerRegs[tmrCfg->timer_num]->TGCR= + /*Select 64-bit general timer mode*/ + (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& + ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); + + if(TIMER_WATCH_DOG==tmrCfg->timerMode) + { + /*enable watchdog timer*/ + gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timerMode) + { + gpTimerRegs[tmrCfg->timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<timer_num]->TCR= + (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth< +#include +#include +#include +#include +#include + +/* DSP core clock speed in Hz */ +#define DSP_CORE_SPEED_HZ 1000000000 + +extern CSL_CgemRegs * gpCGEM_regs; +extern CSL_BootcfgRegs * gpBootCfgRegs; + +/*----------------------Timer plus registers definition----------------*/ +typedef struct { + volatile unsigned int PID12; + volatile unsigned int EMUMGT_CLKSPD; + volatile unsigned int GPINT_EN; + volatile unsigned int GPDIR_DAT; + volatile unsigned int CNTLO; + volatile unsigned int CNTHI; + volatile unsigned int PRDLO; + volatile unsigned int PRDHI; + volatile unsigned int TCR; + volatile unsigned int TGCR; + volatile unsigned int WDTCR; + volatile unsigned int TLGC; + volatile unsigned int TLMR; + volatile unsigned int RELLO; + volatile unsigned int RELHI; + volatile unsigned int CAPLO; + volatile unsigned int CAPHI; + volatile unsigned int INTCTL_STAT; + volatile unsigned char RSVD0[24]; + volatile unsigned int TIMERLO_COMPARE_REG[8]; + volatile unsigned char RSVD1[32]; +} CSL_TmrPlusRegs; + +#define TMR_TCR_READRSTMODE_HI_SHIFT (26) +#define TMR_TCR_CAPEVTMODE_LO_SHIFT (12) +#define TMR_TCR_CAPMODE_LO_SHIFT (11) +#define TMR_TCR_READRSTMODE_LO_SHIFT (10) + +#define TMR_TCR_READRSTMODE_HI_MASK (1<<26) +#define TMR_TCR_CAPEVTMODE_LO_MASK (3<<12) +#define TMR_TCR_CAPMODE_LO_MASK (1<<11) +#define TMR_TCR_READRSTMODE_LO_MASK (1<<10) + +#define TMR_TGCR_PLUSEN_SHIFT 4 +#define TMR_TGCR_PLUSEN_MASK (1<<4) + +#define TMR_INTCTLSTAT_EN_ALL_CLR_ALL 0x000F000F + +#define CSL_TMR_WDTCR_WDKEY_CMD1 (0x0000A5C6u) +#define CSL_TMR_WDTCR_WDKEY_CMD2 (0x0000DA7Eu) + +#define CSL_TMR_ENAMODE_CONT_RELOAD 3 + +extern CSL_TmrPlusRegs * gpTimer0Regs; +extern CSL_TmrPlusRegs * gpTimer1Regs; +extern CSL_TmrPlusRegs * gpTimer2Regs; +extern CSL_TmrPlusRegs * gpTimer3Regs; +extern CSL_TmrPlusRegs * gpTimer4Regs; +extern CSL_TmrPlusRegs * gpTimer5Regs; +extern CSL_TmrPlusRegs * gpTimer6Regs; +extern CSL_TmrPlusRegs * gpTimer7Regs; +extern CSL_TmrPlusRegs * gpTimer8Regs; +extern CSL_TmrPlusRegs * gpTimerRegs[]; + +typedef enum +{ + TIMER_ONE_SHOT_PULSE = 0, /*generate one shot pulse with timer*/ + TIMER_PERIODIC_PULSE, /*generate periodic pulse with timer*/ + TIMER_PERIODIC_CLOCK, /*generate periodic clock with timer*/ + /*generate periodic square wave with period reload feature, the difference + between wave and clock is the duty cycle of clock is always 50%*/ + TIMER_PERIODIC_WAVE, + TIMER_WATCH_DOG /*configure timer as watch dog*/ +}TTimerMode; + +typedef struct { + int timer_num; /*select one timer*/ + TTimerMode timerMode; /*select function of the timer*/ + unsigned long long period; /*in the unit of DSP core clock/6*/ + unsigned long long reload_period; /*the reload value of period*/ + int pulseWidth; /*pulse width between 0~3*/ +}Timer64_Config; + +/* Reset a 64-bit timer */ +extern void reset_timer(int timer_num); + +/* Initailize a 64-bit timer */ +extern void timer64_init(Timer64_Config * tmrCfg); + +extern void keystone_cpu_init(void); + +#endif /* __COMMON_H__ */ diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 9fe4e05fed..08915ef966 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -9,7 +9,8 @@ */ #include "drv_timer.h" -#include "KeyStone_common.h" +#include "interrupt.h" +#include "common.h" #include #include @@ -37,7 +38,7 @@ void rt_hw_system_timer_init(void) // initial system timer interrupt, map local timer interrupt to INT14 gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN << CSL_CGEM_INTMUX3_INTSEL14_SHIFT); // enable CPU INT14 - CPU_interrupt_enable(1 << 14); + rt_hw_interrupt_umask(1 << 14); return ; } @@ -57,9 +58,9 @@ void rt_hw_system_timer_start(void) // configure the timer to generate clocks and interrupts tmrCfg.timer_num = DNUM; tmrCfg.timerMode = TIMER_PERIODIC_CLOCK; - tmrCfg.period = (unsigned long long) RT_TICK_PER_SECOND * gDSP_Core_Speed_Hz / 6000; + tmrCfg.period = (unsigned long long) RT_TICK_PER_SECOND * DSP_CORE_SPEED_HZ / 6000; tmrCfg.reload_period = 0; // initial timer - Timer64_Init(&tmrCfg); + timer64_init(&tmrCfg); } diff --git a/bsp/ti-tms320c6678/driver/drv_timer.h b/bsp/ti-tms320c6678/driver/drv_timer.h index f30dd940da..d663a5bb67 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.h +++ b/bsp/ti-tms320c6678/driver/drv_timer.h @@ -11,6 +11,9 @@ #ifndef __SYS_TIMER_H__ #define __SYS_TIMER_H__ +#include +#include + void rt_hw_system_timer_init(void); void rt_hw_system_timer_start(void); diff --git a/libcpu/ti-dsp/c6x/c66xx.h b/libcpu/ti-dsp/c6x/c66xx.h index 903edbfaf1..b69561c163 100644 --- a/libcpu/ti-dsp/c6x/c66xx.h +++ b/libcpu/ti-dsp/c6x/c66xx.h @@ -11,15 +11,25 @@ #ifndef __C66XX_H__ #define __C66XX_H__ -extern cregister volatile unsigned int IERR; /* Internal Exception Report Register */ -extern cregister volatile unsigned int ECR; /* Exception Clear Register */ -extern cregister volatile unsigned int EFR; /* Exception Flag Register */ -extern cregister volatile unsigned int TSR; /* Task State Register */ -extern cregister volatile unsigned int ITSR; /* Interrupt Task State Register */ -extern cregister volatile unsigned int NTSR; /* NMI/exception Task State Register */ -extern cregister volatile unsigned int TSCL; /* Time Stamp Counter Register - Low Half */ -extern cregister volatile unsigned int TSCH; /* Time Stamp Counter Register - High Half */ -extern cregister volatile unsigned int DNUM; /* Core number */ +extern __cregister volatile unsigned int IERR; /* Internal Exception Report Register */ +extern __cregister volatile unsigned int ECR; /* Exception Clear Register */ +extern __cregister volatile unsigned int EFR; /* Exception Flag Register */ +extern __cregister volatile unsigned int TSR; /* Task State Register */ +extern __cregister volatile unsigned int ITSR; /* Interrupt Task State Register */ +extern __cregister volatile unsigned int NTSR; /* NMI/exception Task State Register */ +extern __cregister volatile unsigned int TSCL; /* Time Stamp Counter Register - Low Half */ +extern __cregister volatile unsigned int TSCH; /* Time Stamp Counter Register - High Half */ +extern __cregister volatile unsigned int DNUM; /* Core number */ + +extern __cregister volatile unsigned int AMR; +extern __cregister volatile unsigned int CSR; +extern __cregister volatile unsigned int IFR; +extern __cregister volatile unsigned int ISR; +extern __cregister volatile unsigned int ICR; +extern __cregister volatile unsigned int IER; +extern __cregister volatile unsigned int ISTP; +extern __cregister volatile unsigned int IRP; +extern __cregister volatile unsigned int NRP; #ifdef _BIG_ENDIAN #define RT_REG_PAIR(odd, even) unsigned long odd; unsigned long even diff --git a/libcpu/ti-dsp/c6x/interrupt.c b/libcpu/ti-dsp/c6x/interrupt.c index 1f532f6c32..6e48cb8efa 100644 --- a/libcpu/ti-dsp/c6x/interrupt.c +++ b/libcpu/ti-dsp/c6x/interrupt.c @@ -60,6 +60,11 @@ void rt_hw_interrupt_umask(int vector) { return; } + ICR = vector; + IER |= vector; + + //enable GIE + TSR = TSR | 1; } /** -- cgit v1.3.1 From b8db37f53f3546594fe151894024ae15fbcb7904 Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 15 Dec 2021 10:55:24 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/applications/board.c | 2 +- bsp/ti-tms320c6678/common/common.c | 146 ++++++++++++++++---------------- 2 files changed, 75 insertions(+), 73 deletions(-) diff --git a/bsp/ti-tms320c6678/applications/board.c b/bsp/ti-tms320c6678/applications/board.c index 0e622765da..bfa4057c1f 100644 --- a/bsp/ti-tms320c6678/applications/board.c +++ b/bsp/ti-tms320c6678/applications/board.c @@ -21,7 +21,7 @@ void rt_hw_board_init(void) { // initial CPU core - keystone_cpu_init(); + keystone_cpu_init(); // initial interrupt controller rt_hw_interrupt_init(); diff --git a/bsp/ti-tms320c6678/common/common.c b/bsp/ti-tms320c6678/common/common.c index 0e026659ed..66826e2183 100644 --- a/bsp/ti-tms320c6678/common/common.c +++ b/bsp/ti-tms320c6678/common/common.c @@ -58,7 +58,7 @@ void reset_timer(int timer_num) { if(gpTimerRegs[timer_num]->TGCR) { - gpTimerRegs[timer_num]->TGCR= 0; + gpTimerRegs[timer_num]->TGCR = 0; gpTimerRegs[timer_num]->TCR= 0; } } @@ -67,135 +67,137 @@ void timer64_init(Timer64_Config * tmrCfg) { reset_timer(tmrCfg->timer_num); - gpTimerRegs[tmrCfg->timer_num]->CNTLO= 0; - gpTimerRegs[tmrCfg->timer_num]->CNTHI= 0; + gpTimerRegs[tmrCfg->timer_num]->CNTLO = 0; + gpTimerRegs[tmrCfg->timer_num]->CNTHI = 0; /*please note, in clock mode, two timer periods generate a clock, one timer period output high voltage level, the other timer period output low voltage level, so, the timer period should be half to the desired output clock period*/ - if(TIMER_PERIODIC_CLOCK==tmrCfg->timerMode) - tmrCfg->period= tmrCfg->period/2; + if(TIMER_PERIODIC_CLOCK == tmrCfg->timerMode) + { + tmrCfg->period = tmrCfg->period/2; + } /*the value written into period register is the expected value minus one*/ - gpTimerRegs[tmrCfg->timer_num]->PRDLO= _loll(tmrCfg->period-1); - gpTimerRegs[tmrCfg->timer_num]->PRDHI= _hill(tmrCfg->period-1); + gpTimerRegs[tmrCfg->timer_num]->PRDLO = _loll(tmrCfg->period-1); + gpTimerRegs[tmrCfg->timer_num]->PRDHI = _hill(tmrCfg->period-1); if(tmrCfg->reload_period>1) { - gpTimerRegs[tmrCfg->timer_num]->RELLO= _loll(tmrCfg->reload_period-1); - gpTimerRegs[tmrCfg->timer_num]->RELHI= _hill(tmrCfg->reload_period-1); + gpTimerRegs[tmrCfg->timer_num]->RELLO = _loll(tmrCfg->reload_period-1); + gpTimerRegs[tmrCfg->timer_num]->RELHI = _hill(tmrCfg->reload_period-1); } - if(TIMER_WATCH_DOG==tmrCfg->timerMode) + if(TIMER_WATCH_DOG == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TGCR= + gpTimerRegs[tmrCfg->timer_num]->TGCR = /*Select watch-dog mode*/ - (CSL_TMR_TIMMODE_WDT<timerMode) + else if(TIMER_PERIODIC_WAVE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TGCR= TMR_TGCR_PLUSEN_MASK + gpTimerRegs[tmrCfg->timer_num]->TGCR = TMR_TGCR_PLUSEN_MASK /*for plus featuers, dual 32-bit unchained timer mode should be used*/ - |(CSL_TMR_TIMMODE_DUAL_UNCHAINED<timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; } else { - gpTimerRegs[tmrCfg->timer_num]->TGCR= + gpTimerRegs[tmrCfg->timer_num]->TGCR = /*Select 64-bit general timer mode*/ - (CSL_TMR_TIMMODE_GPT<timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); - if(TIMER_WATCH_DOG==tmrCfg->timerMode) + if(TIMER_WATCH_DOG == tmrCfg->timerMode) { /*enable watchdog timer*/ gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD1<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<pulseWidth<pulseWidth << CSL_TMR_TCR_PWID_LO_SHIFT)&CSL_TMR_TCR_PWID_LO_MASK) /*select pulse mode*/ - |(CSL_TMR_CP_PULSE<timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK - |(CSL_TMR_WDTCR_WDKEY_CMD2<timerMode) + else if(TIMER_ONE_SHOT_PULSE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<timer_num]->TCR = + (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) + | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled one-shot*/ - |(CSL_TMR_ENAMODE_ENABLE<pulseWidth<pulseWidth << CSL_TMR_TCR_PWID_LO_SHIFT)&CSL_TMR_TCR_PWID_LO_MASK) /*select pulse mode*/ - |(CSL_TMR_CP_PULSE<timerMode) + else if(TIMER_PERIODIC_CLOCK == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<timer_num]->TCR = + (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) + | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously*/ - |(CSL_TMR_ENAMODE_CONT<pulseWidth<pulseWidth << CSL_TMR_TCR_PWID_LO_SHIFT)&CSL_TMR_TCR_PWID_LO_MASK) /*select clock mode*/ - |(CSL_TMR_CP_CLOCK<timerMode) + else if(TIMER_PERIODIC_WAVE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<timer_num]->TCR = + (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) + | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously with period reload*/ - |(CSL_TMR_ENAMODE_CONT_RELOAD<pulseWidth<pulseWidth << CSL_TMR_TCR_PWID_LO_SHIFT)&CSL_TMR_TCR_PWID_LO_MASK) /*select clock mode*/ - |(CSL_TMR_CP_CLOCK<timer_num]->TCR= - (CSL_TMR_CLOCK_INP_NOGATE<timer_num]->TCR = + (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) + | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously*/ - |(CSL_TMR_ENAMODE_CONT<pulseWidth<pulseWidth << CSL_TMR_TCR_PWID_LO_SHIFT)&CSL_TMR_TCR_PWID_LO_MASK) /*select clock mode*/ - |(CSL_TMR_CP_PULSE< Date: Wed, 15 Dec 2021 11:10:13 +0800 Subject: 修改格式 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/common/common.c | 68 +++++++++++++++++------------------ bsp/ti-tms320c6678/common/common.h | 24 ++++++------- bsp/ti-tms320c6678/driver/drv_timer.c | 6 ++-- 3 files changed, 49 insertions(+), 49 deletions(-) diff --git a/bsp/ti-tms320c6678/common/common.c b/bsp/ti-tms320c6678/common/common.c index 66826e2183..1c362d76f8 100644 --- a/bsp/ti-tms320c6678/common/common.c +++ b/bsp/ti-tms320c6678/common/common.c @@ -10,9 +10,9 @@ #include "common.h" -CSL_BootcfgRegs * gpBootCfgRegs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; -CSL_CgemRegs * gpCGEM_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; -CSL_TmrPlusRegs * gpTimerRegs[9] = { +CSL_BootcfgRegs * gp_bootcfg_regs = (CSL_BootcfgRegs *)CSL_BOOT_CFG_REGS; +CSL_CgemRegs * gp_cgem_regs = (CSL_CgemRegs *)CSL_CGEM0_5_REG_BASE_ADDRESS_REGS; +CSL_TmrPlusRegs * gp_timer_regs[9] = { (CSL_TmrPlusRegs *)CSL_TIMER_0_REGS, (CSL_TmrPlusRegs *)CSL_TIMER_1_REGS, (CSL_TmrPlusRegs *)CSL_TIMER_2_REGS, @@ -29,22 +29,22 @@ void cpu_interrupt_init(void) //clear interrupt and excpetion events ICR = IFR; ECR = EFR; - IER= 3; //disable all interrupts + IER = 3; //disable all interrupts /* disable event combine */ - gpCGEM_regs->EVTMASK[0] = 0xffffffff; - gpCGEM_regs->EVTMASK[1] = 0xffffffff; - gpCGEM_regs->EVTMASK[2] = 0xffffffff; - gpCGEM_regs->EVTMASK[3] = 0xffffffff; + gp_cgem_regs->EVTMASK[0] = 0xffffffff; + gp_cgem_regs->EVTMASK[1] = 0xffffffff; + gp_cgem_regs->EVTMASK[2] = 0xffffffff; + gp_cgem_regs->EVTMASK[3] = 0xffffffff; /*Clear all CPU events*/ - gpCGEM_regs->EVTCLR[0]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[1]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[2]= 0xFFFFFFFF; - gpCGEM_regs->EVTCLR[3]= 0xFFFFFFFF; + gp_cgem_regs->EVTCLR[0] = 0xFFFFFFFF; + gp_cgem_regs->EVTCLR[1] = 0xFFFFFFFF; + gp_cgem_regs->EVTCLR[2] = 0xFFFFFFFF; + gp_cgem_regs->EVTCLR[3] = 0xFFFFFFFF; /*Interrupt Service Table Pointer to begining of LL2 memory*/ - ISTP= 0x800000; + ISTP = 0x800000; } void keystone_cpu_init(void) @@ -56,10 +56,10 @@ void keystone_cpu_init(void) /*===============================Timer=================================*/ void reset_timer(int timer_num) { - if(gpTimerRegs[timer_num]->TGCR) + if(gp_timer_regs[timer_num]->TGCR) { - gpTimerRegs[timer_num]->TGCR = 0; - gpTimerRegs[timer_num]->TCR= 0; + gp_timer_regs[timer_num]->TGCR = 0; + gp_timer_regs[timer_num]->TCR= 0; } } @@ -67,8 +67,8 @@ void timer64_init(Timer64_Config * tmrCfg) { reset_timer(tmrCfg->timer_num); - gpTimerRegs[tmrCfg->timer_num]->CNTLO = 0; - gpTimerRegs[tmrCfg->timer_num]->CNTHI = 0; + gp_timer_regs[tmrCfg->timer_num]->CNTLO = 0; + gp_timer_regs[tmrCfg->timer_num]->CNTHI = 0; /*please note, in clock mode, two timer periods generate a clock, one timer period output high voltage level, the other timer period @@ -80,17 +80,17 @@ void timer64_init(Timer64_Config * tmrCfg) } /*the value written into period register is the expected value minus one*/ - gpTimerRegs[tmrCfg->timer_num]->PRDLO = _loll(tmrCfg->period-1); - gpTimerRegs[tmrCfg->timer_num]->PRDHI = _hill(tmrCfg->period-1); + gp_timer_regs[tmrCfg->timer_num]->PRDLO = _loll(tmrCfg->period-1); + gp_timer_regs[tmrCfg->timer_num]->PRDHI = _hill(tmrCfg->period-1); if(tmrCfg->reload_period>1) { - gpTimerRegs[tmrCfg->timer_num]->RELLO = _loll(tmrCfg->reload_period-1); - gpTimerRegs[tmrCfg->timer_num]->RELHI = _hill(tmrCfg->reload_period-1); + gp_timer_regs[tmrCfg->timer_num]->RELLO = _loll(tmrCfg->reload_period-1); + gp_timer_regs[tmrCfg->timer_num]->RELHI = _hill(tmrCfg->reload_period-1); } if(TIMER_WATCH_DOG == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TGCR = + gp_timer_regs[tmrCfg->timer_num]->TGCR = /*Select watch-dog mode*/ (CSL_TMR_TIMMODE_WDT << CSL_TMR_TGCR_TIMMODE_SHIFT) /*Remove the timer from reset*/ @@ -99,18 +99,18 @@ void timer64_init(Timer64_Config * tmrCfg) } else if(TIMER_PERIODIC_WAVE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TGCR = TMR_TGCR_PLUSEN_MASK + gp_timer_regs[tmrCfg->timer_num]->TGCR = TMR_TGCR_PLUSEN_MASK /*for plus featuers, dual 32-bit unchained timer mode should be used*/ | (CSL_TMR_TIMMODE_DUAL_UNCHAINED << CSL_TMR_TGCR_TIMMODE_SHIFT) /*Remove the timer from reset*/ | (CSL_TMR_TGCR_TIMLORS_MASK); //in plus mode, interrupt/event must be enabled manually - gpTimerRegs[tmrCfg->timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; + gp_timer_regs[tmrCfg->timer_num]->INTCTL_STAT= TMR_INTCTLSTAT_EN_ALL_CLR_ALL; } else { - gpTimerRegs[tmrCfg->timer_num]->TGCR = + gp_timer_regs[tmrCfg->timer_num]->TGCR = /*Select 64-bit general timer mode*/ (CSL_TMR_TIMMODE_GPT << CSL_TMR_TGCR_TIMMODE_SHIFT) /*Remove the timer from reset*/ @@ -119,16 +119,16 @@ void timer64_init(Timer64_Config * tmrCfg) } /*make timer stop with emulation*/ - gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD = (gpTimerRegs[tmrCfg->timer_num]->EMUMGT_CLKSPD& + gp_timer_regs[tmrCfg->timer_num]->EMUMGT_CLKSPD = (gp_timer_regs[tmrCfg->timer_num]->EMUMGT_CLKSPD& ~(CSL_TMR_EMUMGT_CLKSPD_FREE_MASK|CSL_TMR_EMUMGT_CLKSPD_SOFT_MASK)); if(TIMER_WATCH_DOG == tmrCfg->timerMode) { /*enable watchdog timer*/ - gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + gp_timer_regs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK | (CSL_TMR_WDTCR_WDKEY_CMD1 << CSL_TMR_WDTCR_WDKEY_SHIFT); - gpTimerRegs[tmrCfg->timer_num]->TCR= + gp_timer_regs[tmrCfg->timer_num]->TCR = (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously*/ @@ -141,12 +141,12 @@ void timer64_init(Timer64_Config * tmrCfg) | (0 << CSL_TMR_TCR_TSTAT_LO_SHIFT); /*active watchdog timer*/ - gpTimerRegs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK + gp_timer_regs[tmrCfg->timer_num]->WDTCR = CSL_TMR_WDTCR_WDEN_MASK | (CSL_TMR_WDTCR_WDKEY_CMD2 << CSL_TMR_WDTCR_WDKEY_SHIFT); } else if(TIMER_ONE_SHOT_PULSE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR = + gp_timer_regs[tmrCfg->timer_num]->TCR = (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled one-shot*/ @@ -160,7 +160,7 @@ void timer64_init(Timer64_Config * tmrCfg) } else if(TIMER_PERIODIC_CLOCK == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR = + gp_timer_regs[tmrCfg->timer_num]->TCR = (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously*/ @@ -174,7 +174,7 @@ void timer64_init(Timer64_Config * tmrCfg) } else if(TIMER_PERIODIC_WAVE == tmrCfg->timerMode) { - gpTimerRegs[tmrCfg->timer_num]->TCR = + gp_timer_regs[tmrCfg->timer_num]->TCR = (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously with period reload*/ @@ -188,7 +188,7 @@ void timer64_init(Timer64_Config * tmrCfg) } else /*TIMER_PERIODIC_PULSE*/ { - gpTimerRegs[tmrCfg->timer_num]->TCR = + gp_timer_regs[tmrCfg->timer_num]->TCR = (CSL_TMR_CLOCK_INP_NOGATE << CSL_TMR_TCR_TIEN_LO_SHIFT) | (CSL_TMR_CLKSRC_INTERNAL << CSL_TMR_TCR_CLKSRC_LO_SHIFT) /*The timer is enabled continuously*/ diff --git a/bsp/ti-tms320c6678/common/common.h b/bsp/ti-tms320c6678/common/common.h index d75063903d..61da9ca25a 100644 --- a/bsp/ti-tms320c6678/common/common.h +++ b/bsp/ti-tms320c6678/common/common.h @@ -21,8 +21,8 @@ /* DSP core clock speed in Hz */ #define DSP_CORE_SPEED_HZ 1000000000 -extern CSL_CgemRegs * gpCGEM_regs; -extern CSL_BootcfgRegs * gpBootCfgRegs; +extern CSL_CgemRegs * gp_cgem_regs; +extern CSL_BootcfgRegs * gp_bootcfg_regs; /*----------------------Timer plus registers definition----------------*/ typedef struct { @@ -69,16 +69,16 @@ typedef struct { #define CSL_TMR_ENAMODE_CONT_RELOAD 3 -extern CSL_TmrPlusRegs * gpTimer0Regs; -extern CSL_TmrPlusRegs * gpTimer1Regs; -extern CSL_TmrPlusRegs * gpTimer2Regs; -extern CSL_TmrPlusRegs * gpTimer3Regs; -extern CSL_TmrPlusRegs * gpTimer4Regs; -extern CSL_TmrPlusRegs * gpTimer5Regs; -extern CSL_TmrPlusRegs * gpTimer6Regs; -extern CSL_TmrPlusRegs * gpTimer7Regs; -extern CSL_TmrPlusRegs * gpTimer8Regs; -extern CSL_TmrPlusRegs * gpTimerRegs[]; +extern CSL_TmrPlusRegs * gp_timer0_regs; +extern CSL_TmrPlusRegs * gp_timer1_regs; +extern CSL_TmrPlusRegs * gp_timer2_regs; +extern CSL_TmrPlusRegs * gp_timer3_regs; +extern CSL_TmrPlusRegs * gp_timer4_regs; +extern CSL_TmrPlusRegs * gp_timer5_regs; +extern CSL_TmrPlusRegs * gp_timer6_regs; +extern CSL_TmrPlusRegs * gp_timer7_regs; +extern CSL_TmrPlusRegs * gp_timer8_regs; +extern CSL_TmrPlusRegs * gp_timer_regs[]; typedef enum { diff --git a/bsp/ti-tms320c6678/driver/drv_timer.c b/bsp/ti-tms320c6678/driver/drv_timer.c index 08915ef966..fe8aca1273 100644 --- a/bsp/ti-tms320c6678/driver/drv_timer.c +++ b/bsp/ti-tms320c6678/driver/drv_timer.c @@ -36,7 +36,7 @@ void rt_hw_systick_isr(void) void rt_hw_system_timer_init(void) { // initial system timer interrupt, map local timer interrupt to INT14 - gpCGEM_regs->INTMUX3 = (CSL_GEM_TINTLN << CSL_CGEM_INTMUX3_INTSEL14_SHIFT); + gp_cgem_regs->INTMUX3 = (CSL_GEM_TINTLN << CSL_CGEM_INTMUX3_INTSEL14_SHIFT); // enable CPU INT14 rt_hw_interrupt_umask(1 << 14); @@ -45,7 +45,7 @@ void rt_hw_system_timer_init(void) /** * The function initial system timer. - * Use local timer (==DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well + * Use local timer (== DNUM of a core) to generate a clock on TIMO0,interrupts are generated as well * */ void rt_hw_system_timer_start(void) @@ -53,7 +53,7 @@ void rt_hw_system_timer_start(void) Timer64_Config tmrCfg; // select output on TIMO0 from local timer. - gpBootCfgRegs->TOUTSEL = (DNUM*2) << CSL_BOOTCFG_TOUTSEL_TOUTSEL0_SHIFT; + gp_bootcfg_regs->TOUTSEL = (DNUM*2) << CSL_BOOTCFG_TOUTSEL_TOUTSEL0_SHIFT; // configure the timer to generate clocks and interrupts tmrCfg.timer_num = DNUM; -- cgit v1.3.1 From 457fcecda9fba7b862214ef58bf8837636757bbc Mon Sep 17 00:00:00 2001 From: Huang bo Date: Wed, 29 Dec 2021 09:23:17 +0800 Subject: 添加编译说明 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/.cproject | 94 +++++++++++---------- .../.settings/org.eclipse.core.resources.prefs | 12 +++ bsp/ti-tms320c6678/figures/debug(1).png | Bin 0 -> 25508 bytes bsp/ti-tms320c6678/figures/debug(2).png | Bin 0 -> 56653 bytes bsp/ti-tms320c6678/figures/filepath.png | Bin 0 -> 12891 bytes bsp/ti-tms320c6678/figures/general.jpg | Bin 0 -> 21087 bytes bsp/ti-tms320c6678/figures/import(1).png | Bin 0 -> 37130 bytes bsp/ti-tms320c6678/figures/import(2).png | Bin 0 -> 25813 bytes bsp/ti-tms320c6678/figures/load.png | Bin 0 -> 61832 bytes bsp/ti-tms320c6678/readme.txt | 2 +- 10 files changed, 62 insertions(+), 46 deletions(-) create mode 100644 bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs create mode 100644 bsp/ti-tms320c6678/figures/debug(1).png create mode 100644 bsp/ti-tms320c6678/figures/debug(2).png create mode 100644 bsp/ti-tms320c6678/figures/filepath.png create mode 100644 bsp/ti-tms320c6678/figures/general.jpg create mode 100644 bsp/ti-tms320c6678/figures/import(1).png create mode 100644 bsp/ti-tms320c6678/figures/import(2).png create mode 100644 bsp/ti-tms320c6678/figures/load.png diff --git a/bsp/ti-tms320c6678/.cproject b/bsp/ti-tms320c6678/.cproject index 0c4124a28d..a906191430 100644 --- a/bsp/ti-tms320c6678/.cproject +++ b/bsp/ti-tms320c6678/.cproject @@ -16,27 +16,24 @@ - - @@ -98,36 +99,36 @@ - diff --git a/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs b/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs new file mode 100644 index 0000000000..243442d787 --- /dev/null +++ b/bsp/ti-tms320c6678/.settings/org.eclipse.core.resources.prefs @@ -0,0 +1,12 @@ +eclipse.preferences.version=1 +encoding//Debug/applications/subdir_rules.mk=UTF-8 +encoding//Debug/applications/subdir_vars.mk=UTF-8 +encoding//Debug/common/subdir_rules.mk=UTF-8 +encoding//Debug/common/subdir_vars.mk=UTF-8 +encoding//Debug/driver/subdir_rules.mk=UTF-8 +encoding//Debug/driver/subdir_vars.mk=UTF-8 +encoding//Debug/makefile=UTF-8 +encoding//Debug/objects.mk=UTF-8 +encoding//Debug/sources.mk=UTF-8 +encoding//Debug/subdir_rules.mk=UTF-8 +encoding//Debug/subdir_vars.mk=UTF-8 diff --git a/bsp/ti-tms320c6678/figures/debug(1).png b/bsp/ti-tms320c6678/figures/debug(1).png new file mode 100644 index 0000000000..00f7616b49 Binary files /dev/null and b/bsp/ti-tms320c6678/figures/debug(1).png differ diff --git a/bsp/ti-tms320c6678/figures/debug(2).png b/bsp/ti-tms320c6678/figures/debug(2).png new file mode 100644 index 0000000000..35d6f4e85f Binary files /dev/null and b/bsp/ti-tms320c6678/figures/debug(2).png differ diff --git a/bsp/ti-tms320c6678/figures/filepath.png b/bsp/ti-tms320c6678/figures/filepath.png new file mode 100644 index 0000000000..71a11da2fd Binary files /dev/null and b/bsp/ti-tms320c6678/figures/filepath.png differ diff --git a/bsp/ti-tms320c6678/figures/general.jpg b/bsp/ti-tms320c6678/figures/general.jpg new file mode 100644 index 0000000000..52b8ca9ffd Binary files /dev/null and b/bsp/ti-tms320c6678/figures/general.jpg differ diff --git a/bsp/ti-tms320c6678/figures/import(1).png b/bsp/ti-tms320c6678/figures/import(1).png new file mode 100644 index 0000000000..9bc4eac5d2 Binary files /dev/null and b/bsp/ti-tms320c6678/figures/import(1).png differ diff --git a/bsp/ti-tms320c6678/figures/import(2).png b/bsp/ti-tms320c6678/figures/import(2).png new file mode 100644 index 0000000000..d9d29af981 Binary files /dev/null and b/bsp/ti-tms320c6678/figures/import(2).png differ diff --git a/bsp/ti-tms320c6678/figures/load.png b/bsp/ti-tms320c6678/figures/load.png new file mode 100644 index 0000000000..99d3b5f51c Binary files /dev/null and b/bsp/ti-tms320c6678/figures/load.png differ diff --git a/bsp/ti-tms320c6678/readme.txt b/bsp/ti-tms320c6678/readme.txt index 84f608122c..aa677425d5 100644 --- a/bsp/ti-tms320c6678/readme.txt +++ b/bsp/ti-tms320c6678/readme.txt @@ -1,4 +1,4 @@ - 本工程使用TI公司编译器CCS5.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6, + 本工程使用TI公司编译器CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6, 我的安装路径为C盘。 "C:\ti\pdk_C6678_1_1_2_6\packages" "C:\ti\pdk_C6678_1_1_2_6\packages\ti\csl" \ No newline at end of file -- cgit v1.3.1 From 72083e39866ecbc208931bf330cf3d9b06cfe245 Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 13:57:07 +0000 Subject: rename bsp/ti-tms320c6678/readme.txt to bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 13 +++++++++++++ bsp/ti-tms320c6678/readme.txt | 4 ---- 2 files changed, 13 insertions(+), 4 deletions(-) create mode 100644 bsp/ti-tms320c6678/README.md delete mode 100644 bsp/ti-tms320c6678/readme.txt diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md new file mode 100644 index 0000000000..ca8195b661 --- /dev/null +++ b/bsp/ti-tms320c6678/README.md @@ -0,0 +1,13 @@ + +# 1.简介 + TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。 +该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 + +## 2.编译说明 + TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试, +CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 + +pdk_C6678_1_1_2_6安装路径为: +"C:\ti\pdk_C6678_1_1_2_6\packages" +"C:\ti\pdk_C6678_1_1_2_6\packages\ti\csl" + diff --git a/bsp/ti-tms320c6678/readme.txt b/bsp/ti-tms320c6678/readme.txt deleted file mode 100644 index aa677425d5..0000000000 --- a/bsp/ti-tms320c6678/readme.txt +++ /dev/null @@ -1,4 +0,0 @@ - 本工程使用TI公司编译器CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6, -我的安装路径为C盘。 -"C:\ti\pdk_C6678_1_1_2_6\packages" -"C:\ti\pdk_C6678_1_1_2_6\packages\ti\csl" \ No newline at end of file -- cgit v1.3.1 From 36471da716f85abe65c0415dce11c81730d64eff Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:29:36 +0000 Subject: update bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 29 ++++++++++++++++++++++++----- 1 file changed, 24 insertions(+), 5 deletions(-) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index ca8195b661..bdaae84265 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -1,13 +1,32 @@ -# 1.简介 +# 1. 简介 TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。 该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 -## 2.编译说明 +## 2. 编译说明 TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试, CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 -pdk_C6678_1_1_2_6安装路径为: -"C:\ti\pdk_C6678_1_1_2_6\packages" -"C:\ti\pdk_C6678_1_1_2_6\packages\ti\csl" +## 2.1 导入工程 + 首先打开 Code Composer Studio,点击 Project -> Import CCS Projects... +![输入图片说明](figures/import(1).png) + 在打开的对话框中,点击 Select search -> directory 右边的 Browse... 选择 TMS320C6678 BSP 所在文件夹,如图所示。选择完成后点击 Finish 完成导入。 +![输入图片说明](figures/import(2).png) +## 2.2 检查工程路径和编译器 + 检查工程路径是否正确,是否成功安装pdk_C6678_1_1_2_6,本工程安装路径为C盘。 +![输入图片说明](figures/filepath.png) + 检查编译器版本,本工程使用的是TIv8.3.5 +![输入图片说明](figures/general.jpg) + +## 3 编译工程 + 导入工程后,选中导入的 ti-tms320c6678 工程,右键点击,在弹出的菜单中选择 Build Project 即可开始编译。 + +## 4 加载和调试 + 编译完成后,可以开始加载和调试。将板子和 XDS560 仿真器连接,仿真器可以将编译生成的可执行文件加载到L2或MSMC执行。 + 如下图ti-tms320c6678.out是编译之后生成的可执行文件。 +![输入图片说明](figures/debug(1).png) + 本工程目前只支持单核运行,按如下图加载可执行文件。 +![输入图片说明](figures/load.png) + 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 +![输入图片说明](figures/debug(2).png) \ No newline at end of file -- cgit v1.3.1 From 9fb11fd815379ed782273c06628f0f1ae648ece2 Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:30:44 +0000 Subject: update bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index bdaae84265..ba9d16ecc5 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -8,25 +8,33 @@ CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 ## 2.1 导入工程 + 首先打开 Code Composer Studio,点击 Project -> Import CCS Projects... ![输入图片说明](figures/import(1).png) + 在打开的对话框中,点击 Select search -> directory 右边的 Browse... 选择 TMS320C6678 BSP 所在文件夹,如图所示。选择完成后点击 Finish 完成导入。 ![输入图片说明](figures/import(2).png) ## 2.2 检查工程路径和编译器 + 检查工程路径是否正确,是否成功安装pdk_C6678_1_1_2_6,本工程安装路径为C盘。 ![输入图片说明](figures/filepath.png) + 检查编译器版本,本工程使用的是TIv8.3.5 ![输入图片说明](figures/general.jpg) ## 3 编译工程 + 导入工程后,选中导入的 ti-tms320c6678 工程,右键点击,在弹出的菜单中选择 Build Project 即可开始编译。 ## 4 加载和调试 + 编译完成后,可以开始加载和调试。将板子和 XDS560 仿真器连接,仿真器可以将编译生成的可执行文件加载到L2或MSMC执行。 如下图ti-tms320c6678.out是编译之后生成的可执行文件。 ![输入图片说明](figures/debug(1).png) + 本工程目前只支持单核运行,按如下图加载可执行文件。 ![输入图片说明](figures/load.png) + 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 ![输入图片说明](figures/debug(2).png) \ No newline at end of file -- cgit v1.3.1 From 0ea04eb84215497f741dd42b50f05db0c2bb12e1 Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:33:48 +0000 Subject: update bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index ba9d16ecc5..fb88f82626 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -1,11 +1,8 @@ - # 1. 简介 - TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。 -该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 + TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 ## 2. 编译说明 - TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试, -CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 + TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试,CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 ## 2.1 导入工程 @@ -37,4 +34,6 @@ CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_ ![输入图片说明](figures/load.png) 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 -![输入图片说明](figures/debug(2).png) \ No newline at end of file +![输入图片说明](figures/debug(2).png) + + 到此,可以开启tms320c6678 + rt-thread的愉快旅程了。 \ No newline at end of file -- cgit v1.3.1 From 5c8b4908e78dac292cf37e0d9e68391ad4e08a9f Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:38:46 +0000 Subject: update bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 40 ++++++++++++++++++++++------------------ 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index fb88f82626..4ab913062b 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -1,39 +1,43 @@ -# 1. 简介 - TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 +### 1. 简介 -## 2. 编译说明 - TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试,CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 +TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 -## 2.1 导入工程 +### 2. 编译说明 - 首先打开 Code Composer Studio,点击 Project -> Import CCS Projects... +TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Composer Studio。在本工程使用的是 CCS5.5 版本编译调试,CCS5.5 Compiler version:TIv8.3.5进行编译,需要安装TI提供的CSL库pdk_C6678_1_1_2_6。 + +### 2.1 导入工程 + +首先打开 Code Composer Studio,点击 Project -> Import CCS Projects... ![输入图片说明](figures/import(1).png) - 在打开的对话框中,点击 Select search -> directory 右边的 Browse... 选择 TMS320C6678 BSP 所在文件夹,如图所示。选择完成后点击 Finish 完成导入。 +在打开的对话框中,点击 Select search -> directory 右边的 Browse... 选择 TMS320C6678 BSP 所在文件夹,如图所示。选择完成后点击 Finish 完成导入。 ![输入图片说明](figures/import(2).png) -## 2.2 检查工程路径和编译器 +### 2.2 检查工程路径和编译器 - 检查工程路径是否正确,是否成功安装pdk_C6678_1_1_2_6,本工程安装路径为C盘。 +- 检查工程路径是否正确,是否成功安装pdk_C6678_1_1_2_6,本工程安装路径为C盘。 ![输入图片说明](figures/filepath.png) - 检查编译器版本,本工程使用的是TIv8.3.5 +- 检查编译器版本,本工程使用的是TIv8.3.5 + ![输入图片说明](figures/general.jpg) -## 3 编译工程 +### 3. 编译工程 + +导入工程后,选中导入的 ti-tms320c6678 工程,右键点击,在弹出的菜单中选择 Build Project 即可开始编译。 - 导入工程后,选中导入的 ti-tms320c6678 工程,右键点击,在弹出的菜单中选择 Build Project 即可开始编译。 +### 4. 加载和调试 -## 4 加载和调试 +编译完成后,可以开始加载和调试。将板子和 XDS560 仿真器连接,仿真器可以将编译生成的可执行文件加载到L2或MSMC执行。 - 编译完成后,可以开始加载和调试。将板子和 XDS560 仿真器连接,仿真器可以将编译生成的可执行文件加载到L2或MSMC执行。 - 如下图ti-tms320c6678.out是编译之后生成的可执行文件。 +- 如下图ti-tms320c6678.out是编译之后生成的可执行文件。 ![输入图片说明](figures/debug(1).png) - 本工程目前只支持单核运行,按如下图加载可执行文件。 +- 本工程目前只支持单核运行,按如下图加载可执行文件。 ![输入图片说明](figures/load.png) - 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 +- 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 ![输入图片说明](figures/debug(2).png) - 到此,可以开启tms320c6678 + rt-thread的愉快旅程了。 \ No newline at end of file + 到此,可以开启tms320c6678 + rt-thread的愉快旅程了 :smile: 。 \ No newline at end of file -- cgit v1.3.1 From 0d4e3a4b16d84a6e41ecb2eb2b4e32319c92d3be Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:42:08 +0000 Subject: update bsp/ti-tms320c6678/README.md. 添加READM.md说明文档 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- bsp/ti-tms320c6678/README.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index 4ab913062b..7c6ffdf9e0 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -9,14 +9,17 @@ TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Comp ### 2.1 导入工程 首先打开 Code Composer Studio,点击 Project -> Import CCS Projects... + ![输入图片说明](figures/import(1).png) 在打开的对话框中,点击 Select search -> directory 右边的 Browse... 选择 TMS320C6678 BSP 所在文件夹,如图所示。选择完成后点击 Finish 完成导入。 + ![输入图片说明](figures/import(2).png) ### 2.2 检查工程路径和编译器 - 检查工程路径是否正确,是否成功安装pdk_C6678_1_1_2_6,本工程安装路径为C盘。 + ![输入图片说明](figures/filepath.png) - 检查编译器版本,本工程使用的是TIv8.3.5 @@ -32,12 +35,15 @@ TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Comp 编译完成后,可以开始加载和调试。将板子和 XDS560 仿真器连接,仿真器可以将编译生成的可执行文件加载到L2或MSMC执行。 - 如下图ti-tms320c6678.out是编译之后生成的可执行文件。 + ![输入图片说明](figures/debug(1).png) - 本工程目前只支持单核运行,按如下图加载可执行文件。 + ![输入图片说明](figures/load.png) - 加载可执行文件完成后,CCS将进入调试模式,可以选择继续运行、单步调试、复位等操作。 + ![输入图片说明](figures/debug(2).png) 到此,可以开启tms320c6678 + rt-thread的愉快旅程了 :smile: 。 \ No newline at end of file -- cgit v1.3.1 From c5ab5250bc7b0b57afa4bfd98aad818dd1889e66 Mon Sep 17 00:00:00 2001 From: hdwei <1147479335@qq.com> Date: Thu, 27 Jan 2022 14:43:52 +0000 Subject: update bsp/ti-tms320c6678/README.md. --- bsp/ti-tms320c6678/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/bsp/ti-tms320c6678/README.md b/bsp/ti-tms320c6678/README.md index 7c6ffdf9e0..f78f4850bc 100644 --- a/bsp/ti-tms320c6678/README.md +++ b/bsp/ti-tms320c6678/README.md @@ -1,6 +1,6 @@ ### 1. 简介 -TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1至1.25 GHz到10 GHz的运行。该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 +TMS320C6678是TI基于KeyStone的多核固定浮点数字信号处理器,DSP集成C66x CorePac,每个核心在1GHz至1.25 GHz的运行。该设备支持高性能的信号处理应用,如任务关键,医疗成像,测试和自动化。 ### 2. 编译说明 @@ -46,4 +46,4 @@ TMS320C6678 工程的编译和下载要使用的是 TI 官方提供的 Code Comp ![输入图片说明](figures/debug(2).png) - 到此,可以开启tms320c6678 + rt-thread的愉快旅程了 :smile: 。 \ No newline at end of file +到此,可以开启tms320c6678 + rt-thread的愉快旅程了 :smile: 。 \ No newline at end of file -- cgit v1.3.1