update to current PPC exception and memory map structure

This commit is contained in:
Thomas Doerfler
2008-09-03 15:40:46 +00:00
parent 6f776e7118
commit d8b2e89c8d
15 changed files with 1290 additions and 1589 deletions

View File

@@ -1,3 +1,28 @@
2008-09-03 Sebastian Huber <sebastian.huber@embedded-brains.de>
* irq/irq.h, irq/irq_asm.h, irq/irq_init.c, vectors/vectors.S,
vectors/vectors.h, vectors/vectors_init.c: Removed files.
* include/irq-config.h, include/irq.h, include/mscan-base.h,
mscan/mscan-base.c, startup/linkcmds.base: New files.
* mscan/mscan.c, mscan/mscan_int.h: Moved general MSCAN functions into
separate header and source files (include/mscan-base.h and
mscan/mscan-base.c). Formatted code.
* bestcomm/bestcomm_glue.c, bestcomm/load_task.c, clock/clock.c,
console/console.c, i2c/mpc5200mbus.c, ide/idecfg.c, ide/pcmcia_ide.c,
include/bsp.h, irq/irq.c, network_5200/network.c,
slicetimer/slicetimer.c, start/start.S, startup/bspclean.c,
startup/bspstart.c, startup/cpuinit.c: Converted to use shared
exception and interrupt code.
* startup/linkcmds, startup/linkcmds.brs5l, startup/linkcmds.icecube,
startup/linkcmds.pm520: Changed to include new file
startup/linkcmds.base. Supports small data area now.
* configure.ac, Makefile.am, bsp_specs, preinstall.am: Update.
2008-08-25 Sebastian Huber <sebastian.huber@embedded-brains.de>
* startup/cpuinit.h: Uses now powerpc-utility.h. Changed invalid usage

View File

@@ -7,10 +7,12 @@ ACLOCAL_AMFLAGS = -I ../../../../aclocal
include $(top_srcdir)/../../../../automake/compile.am
include $(top_srcdir)/../../bsp.am
libcpudir = ../../../libcpu/@RTEMS_CPU@
dist_project_lib_DATA = bsp_specs
include_HEADERS = include/bsp.h include/i2cdrv.h include/u-boot.h \
include/i2c.h include/mpc5200.h
include/i2c.h
include_HEADERS += include/tm27.h
nodist_include_HEADERS = include/bspopts.h
@@ -34,10 +36,11 @@ rtems_crti.$(OBJEXT): ../../powerpc/shared/start/rtems_crti.S
$(CPPASCOMPILE) -o $@ -c $<
project_lib_DATA += rtems_crti.$(OBJEXT)
dist_project_lib_DATA += startup/linkcmds
dist_project_lib_DATA += startup/linkcmds.brs5l
dist_project_lib_DATA += startup/linkcmds.icecube
dist_project_lib_DATA += startup/linkcmds.pm520
dist_project_lib_DATA += startup/linkcmds \
startup/linkcmds.base \
startup/linkcmds.brs5l \
startup/linkcmds.icecube \
startup/linkcmds.pm520
noinst_PROGRAMS += bestcomm.rel
bestcomm_rel_SOURCES = bestcomm/include/ppctypes.h \
@@ -65,10 +68,25 @@ console_SOURCES = console/console.c
i2c_SOURCES = i2c/i2c.c i2c/i2cdrv.c i2c/mpc5200mbus.c i2c/mpc5200mbus.h
ide_SOURCES = ide/idecfg.c ide/pcmcia_ide.c ide/pcmcia_ide.h
include_bsp_HEADERS = irq/irq.h include/i2cdrv.h include/mpc5200.h \
include/i2c.h include/u-boot.h
irq_SOURCES = irq/irq.c irq/irq_init.c irq/irq.h irq/irq_asm.S
mscan_SOURCES = mscan/mscan.c mscan/mscan.h mscan/mscan_int.h
include_bsp_HEADERS = $(libcpudir)/new-exceptions/bspsupport/vectors.h \
$(libcpudir)/new-exceptions/bspsupport/ppc_exc_bspsupp.h \
../../shared/include/irq-generic.h \
include/irq-config.h \
include/irq.h \
include/i2cdrv.h \
include/i2c.h \
include/mpc5200.h \
include/mscan-base.h \
include/u-boot.h \
mscan/mscan.h
irq_SOURCES = include/irq.h \
include/irq-config.h \
irq/irq.c \
../../shared/src/irq-generic.c \
../../shared/src/irq-legacy.c
mscan_SOURCES = mscan/mscan.c mscan/mscan-base.c mscan/mscan.h mscan/mscan_int.h
include_bsp_HEADERS += nvram/nvram.h
nvram_SOURCES = nvram/nvram.c nvram/nvram.h nvram/m93cxx.h
@@ -79,16 +97,19 @@ slicetimer_SOURCES = slicetimer/slicetimer.c slicetimer/slicetimer.h
tod_SOURCES = tod/todcfg.c tod/pcf8563.c tod/pcf8563.h \
../../shared/tod.c
include_bsp_HEADERS += vectors/vectors.h
startup_SOURCES = startup/bspclean.c ../../shared/bsplibc.c \
../../shared/bsppost.c startup/bspstart.c ../../shared/bootcard.c \
../../shared/sbrk.c ../shared/uboot_dump_bdinfo.c \
../../shared/gnatinstallhandler.c startup/cpuinit.c \
../shared/showbats.c startup/uboot_support.c ../shared/uboot_getenv.c
vectors_SOURCES = vectors/vectors_init.c vectors/vectors.h \
vectors/vectors.S
startup_SOURCES = ../../shared/bootcard.c \
../../shared/bsplibc.c \
../../shared/bsppost.c \
../../shared/bsppretaskinghook.c \
../../shared/gnatinstallhandler.c \
../../shared/sbrk.c \
../shared/showbats.c \
../shared/uboot_dump_bdinfo.c \
../shared/uboot_getenv.c \
startup/bspclean.c \
startup/bspstart.c \
startup/cpuinit.c \
startup/uboot_support.c
if HAS_NETWORKING
network_CPPFLAGS = -D__INSIDE_RTEMS_BSD_TCPIP_STACK__
@@ -102,18 +123,17 @@ endif
noinst_LIBRARIES = libbsp.a
libbsp_a_SOURCES = $(clock_SOURCES) $(console_SOURCES) $(i2c_SOURCES) \
$(ide_SOURCES) $(irq_SOURCES) $(mscan_SOURCES) $(nvram_SOURCES) \
$(slicetimer_SOURCES) $(tod_SOURCES) $(startup_SOURCES) \
$(vectors_SOURCES)
$(slicetimer_SOURCES) $(tod_SOURCES) $(startup_SOURCES)
libbsp_a_LIBADD = \
bestcomm.rel \
../../../libcpu/@RTEMS_CPU@/shared/cpuIdent.rel \
../../../libcpu/@RTEMS_CPU@/shared/cache.rel \
../../../libcpu/@RTEMS_CPU@/shared/stack.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/rtems-cpu.rel \
../../../libcpu/@RTEMS_CPU@/mpc6xx/mmu.rel \
../../../libcpu/@RTEMS_CPU@/mpc6xx/timer.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/raw_exception.rel
libbsp_a_LIBADD = $(libcpudir)/shared/cpuIdent.rel \
$(libcpudir)/shared/cache.rel \
$(libcpudir)/shared/stack.rel \
$(libcpudir)/@exceptions@/rtems-cpu.rel \
$(libcpudir)/@exceptions@/raw_exception.rel \
$(libcpudir)/@exceptions@/exc_bspsupport.rel \
$(libcpudir)/mpc6xx/mmu.rel \
$(libcpudir)/mpc6xx/timer.rel \
bestcomm.rel
if HAS_NETWORKING
libbsp_a_LIBADD += network.rel

View File

@@ -11,4 +11,4 @@
%{!qrtems: %(old_endfile)} %{qrtems: ecrtn.o%s}
*link:
%{!qrtems: %(old_link)} %{qrtems: -dc -dp -u __vectors -N -u start -e start}
%{!qrtems: %(old_link)} %{qrtems: -dc -dp -N -u start -e start}

View File

@@ -39,6 +39,8 @@ AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
# Explicitly list all Makefiles here
AC_CONFIG_FILES([Makefile])
RTEMS_BSP_BOOTCARD_HANDLES_RAM_ALLOCATION
RTEMS_PPC_EXCEPTIONS
AC_OUTPUT

View File

@@ -0,0 +1,44 @@
/**
* @file
*
* @ingroup bsp_interrupt
*
* @brief BSP interrupt support configuration.
*/
/*
* Copyright (c) 2008
* Embedded Brains GmbH
* Obere Lagerstr. 30
* D-82178 Puchheim
* Germany
* rtems@embedded-brains.de
*
* The license and distribution terms for this file may be found in the file
* LICENSE in this distribution or at http://www.rtems.com/license/LICENSE.
*/
#ifndef LIBBSP_POWERPC_GEN5200_IRQ_CONFIG_H
#define LIBBSP_POWERPC_GEN5200_IRQ_CONFIG_H
#include <bsp/irq.h>
/**
* @addtogroup bsp_interrupt
*
* @{
*/
/**
* @brief Minimum vector number.
*/
#define BSP_INTERRUPT_VECTOR_MIN BSP_LOWEST_OFFSET
/**
* @brief Maximum vector number.
*/
#define BSP_INTERRUPT_VECTOR_MAX BSP_MAX_OFFSET
/** @} */
#endif /* LIBBSP_POWERPC_GEN5200_IRQ_CONFIG_H */

View File

@@ -84,8 +84,8 @@
/* */
/***********************************************************************/
#ifndef LIBBSP_POWERPC_MPC5200_IRQ_IRQ_H
#define LIBBSP_POWERPC_MPC5200_IRQ_IRQ_H
#ifndef LIBBSP_POWERPC_GEN5200_IRQ_H
#define LIBBSP_POWERPC_GEN5200_IRQ_H
#define CHK_CE_SHADOW(_pmce) ((_pmce) & 0x00000001)
#define CHK_CSE_STICKY(_pmce) (((_pmce) >> 10) & 0x00000001)
@@ -141,9 +141,9 @@
#ifndef ASM
/*
extern volatile unsigned int ppc_cached_irq_mask;
*/
#include <rtems.h>
#include <rtems/irq.h>
#include <rtems/irq-extension.h>
/*
* index table for the module specific handlers, a few entries are only placeholders
@@ -204,187 +204,8 @@ typedef enum {
} rtems_irq_symbolic_name;
#define BSP_CRIT_IRQ_PRIO_LEVELS 4
/*#define BSP_PERIODIC_TIMER BSP_DECREMENTER*/
#define BSP_PERIODIC_TIMER BSP_SIU_IRQ_TMR6
/*#define CPM_INTERRUPT*/
/*
* Type definition for RTEMS managed interrupts
*/
typedef unsigned char rtems_irq_prio;
struct __rtems_irq_connect_data__; /* forward declaratiuon */
typedef unsigned int rtems_irq_number;
typedef void *rtems_irq_hdl_param;
typedef void (*rtems_irq_hdl)(rtems_irq_hdl_param);
typedef void (*rtems_irq_enable)(const struct __rtems_irq_connect_data__*);
typedef void (*rtems_irq_disable)(const struct __rtems_irq_connect_data__*);
typedef int (*rtems_irq_is_enabled)(const struct __rtems_irq_connect_data__*);
typedef struct __rtems_irq_connect_data__ {
/*
* IRQ line
*/
rtems_irq_number name;
/*
* handler. See comment on handler properties below in function prototype.
*/
rtems_irq_hdl hdl;
/*
* Handler handle to store private data
*/
rtems_irq_hdl_param handle;
/*
* function for enabling interrupts at device level (ONLY!).
* The BSP code will automatically enable it at i8259s level.
* RATIONALE : anyway such code has to exist in current driver code.
* It is usually called immediately AFTER connecting the interrupt handler.
* RTEMS may well need such a function when restoring normal interrupt
* processing after a debug session.
*
*/
rtems_irq_enable on;
/*
* function for disabling interrupts at device level (ONLY!).
* The code will disable it at i8259s level. RATIONALE : anyway
* such code has to exist for clean shutdown. It is usually called
* BEFORE disconnecting the interrupt. RTEMS may well need such
* a function when disabling normal interrupt processing for
* a debug session. May well be a NOP function.
*/
rtems_irq_disable off;
/*
* function enabling to know what interrupt may currently occur
* if someone manipulates the i8259s interrupt mask without care...
*/
rtems_irq_is_enabled isOn;
#ifdef BSP_SHARED_HANDLER_SUPPORT
/*
* Set to -1 for vectors forced to have only 1 handler
*/
void *next_handler;
#endif
} rtems_irq_connect_data;
typedef struct {
/*
* size of all the table fields (*Tbl) described below.
*/
unsigned int irqNb;
/*
* Default handler used when disconnecting interrupts.
*/
rtems_irq_connect_data defaultEntry;
/*
* Table containing initials/current value.
*/
rtems_irq_connect_data* irqHdlTbl;
/*
* actual value of BSP_PER_IRQ_LOWEST_OFFSET...
*/
rtems_irq_symbolic_name irqBase;
/*
* software priorities associated with interrupts.
* if irqPrio [i] > intrPrio [j] it means that
* interrupt handler hdl connected for interrupt name i
* will not be interrupted by the handler connected for interrupt j
* The interrupt source will be physically masked at i8259 level.
*/
rtems_irq_prio* irqPrioTbl;
} rtems_irq_global_settings;
/*-------------------------------------------------------------------------+
| Function Prototypes.
+--------------------------------------------------------------------------*/
/*
* ------------------------ PPC CPM Mngt Routines -------
*/
/*
* function to disable a particular irq. After calling
* this function, even if the device asserts the interrupt line it will
* not be propagated further to the processor
*/
int BSP_irq_disable_at_siu(const rtems_irq_symbolic_name irqLine);
/*
* function to enable a particular irq. After calling
* this function, if the device asserts the interrupt line it will
* be propagated further to the processor
*/
int BSP_irq_enable_at_siu(const rtems_irq_symbolic_name irqLine);
/*
* function to acknowledge a particular irq. After calling
* this function, if a device asserts an enabled interrupt line it will
* be propagated further to the processor. Mainly useful for people
* writing raw handlers as this is automagically done for rtems managed
* handlers.
*/
int BSP_irq_ack_at_siu(const rtems_irq_symbolic_name irqLine);
/*
* function to check ifl d a particular irq is enabled. After calling
*/
int BSP_irq_enabled_at_siu(const rtems_irq_symbolic_name irqLine);
/*
* ------------------------ RTEMS Single Irq Handler Mngt Routines ----------------
*/
/*
* function to connect a particular irq handler. This hanlder will NOT be called
* directly as the result of the corresponding interrupt. Instead, a RTEMS
* irq prologue will be called that will :
*
* 1) save the C scratch registers,
* 2) switch to a interrupt stack if the interrupt is not nested,
* 4) modify them to disable the current interrupt at SIU level (and may
* be others depending on software priorities)
* 5) aknowledge the SIU',
* 6) demask the processor,
* 7) call the application handler
*
* As a result the hdl function provided
*
* a) can perfectly be written is C,
* b) may also well directly call the part of the RTEMS API that can be used
* from interrupt level,
* c) It only responsible for handling the jobs that need to be done at
* the device level including (aknowledging/re-enabling the interrupt at device,
* level, getting the data,...)
*
* When returning from the function, the following will be performed by
* the RTEMS irq epilogue :
*
* 1) masks the interrupts again,
* 2) restore the original SIU interrupt masks
* 3) switch back on the orinal stack if needed,
* 4) perform rescheduling when necessary,
* 5) restore the C scratch registers...
* 6) restore initial execution flow
*
*/
int BSP_install_rtems_irq_handler(const rtems_irq_connect_data*);
/*
* function to get the current RTEMS irq handler for ptr->name. It enables to
* define hanlder chain...
*/
int BSP_get_current_rtems_irq_handler(rtems_irq_connect_data* ptr);
/*
* function to get disconnect the RTEMS irq handler for ptr->name.
* This function checks that the value given is the current one for safety reason.
* The user can use the previous function to get it.
*/
int BSP_remove_rtems_irq_handler(const rtems_irq_connect_data*);
void BSP_rtems_irq_mng_init(unsigned cpuId);
int BSP_rtems_irq_mngt_set(rtems_irq_global_settings* config);
#endif
#endif
#endif /* LIBBSP_POWERPC_GEN5200_IRQ_H */

View File

@@ -0,0 +1,266 @@
/**
* @file
*
* @ingroup m
*
* @brief MSCAN register definitions and support functions.
*/
/*
* Copyright (c) 2008
* Embedded Brains GmbH
* Obere Lagerstr. 30
* D-82178 Puchheim
* Germany
* rtems@embedded-brains.de
*
* The license and distribution terms for this file may be found in the file
* LICENSE in this distribution or at http://www.rtems.com/license/LICENSE.
*/
#ifndef LIBBSP_MSCAN_BASE_H
#define LIBBSP_MSCAN_BASE_H
#include <stdbool.h>
#include <bsp/mpc5200.h>
/**
* @defgroup m MSCAN
*
* @{
*/
#define MSCAN_BIT_RATE_DEFAULT 100000
#define MSCAN_FILTER_NUMBER_MIN 0
#define MSCAN_FILTER_NUMBER_2 2
#define MSCAN_FILTER_NUMBER_4 4
#define MSCAN_FILTER_NUMBER_MAX 8
#define MSCAN_FILTER_ID_DEFAULT 0U
#define MSCAN_FILTER_MASK_DEFAULT 0xffffffffU
#define MSCAN_TRANSMIT_BUFFER_NUMBER 3
/**
* @name MSCAN Control Register 0 (CANCTL0)
*
* @{
*/
#define CTL0_RXFRM (1 << 7)
#define CTL0_RXACT (1 << 6)
#define CTL0_CSWAI (1 << 5)
#define CTL0_SYNCH (1 << 4)
#define CTL0_TIME (1 << 3)
#define CTL0_WUPE (1 << 2)
#define CTL0_SLPRQ (1 << 1)
#define CTL0_INITRQ (1 << 0)
/** @} */
/**
* @name MSCAN Control Register 1 (CANCTL1)
*
* @{
*/
#define CTL1_CANE (1 << 7)
#define CTL1_CLKSRC (1 << 6)
#define CTL1_LOOPB (1 << 5)
#define CTL1_LISTEN (1 << 4)
#define CTL1_WUPM (1 << 2)
#define CTL1_SLPAK (1 << 1)
#define CTL1_INITAK (1 << 0)
/** @} */
/**
* @name MSCAN Bus Timing Register 0 (CANBTR0)
*
* @{
*/
#define BTR0_SJW(btr0) ((btr0) << 6)
#define BTR0_BRP(btr0) ((btr0) << 0)
/** @} */
/**
* @name MSCAN Bus Timing Register 1 (CANBTR1)
*
* @{
*/
#define BTR1_SAMP (1 << 7)
#define BTR1_TSEG2(btr1) ((btr1) << 4)
#define BTR1_TSEG1(btr1) ((btr1) << 0)
/** @} */
/**
* @name MSCAN Receiver Flag Register (CANRFLG)
*
* @{
*/
#define RFLG_WUPIF (1 << 7)
#define RFLG_CSCIF (1 << 6)
#define RFLG_RSTAT_MASK (3 << 4)
#define RFLG_RSTAT_OK (0 << 4)
#define RFLG_RSTAT_WRN (1 << 4)
#define RFLG_RSTAT_ERR (2 << 4)
#define RFLG_RSTAT_OFF (3 << 4)
#define RFLG_TSTAT_MASK (3 << 2)
#define RFLG_TSTAT_OK (0 << 2)
#define RFLG_TSTAT_WRN (1 << 2)
#define RFLG_TSTAT_ERR (2 << 2)
#define RFLG_TSTAT_OFF (3 << 2)
#define RFLG_OVRIF (1 << 1)
#define RFLG_RXF (1 << 0)
#define RFLG_GET_RX_STATE(rflg) (((rflg) >> 4) & 0x03)
#define RFLG_GET_TX_STATE(rflg) (((rflg) >> 2) & 0x03)
/** @} */
/**
* @name MSCAN Receiver Interrupt Enable Register (CANRIER)
*
* @{
*/
#define RIER_WUPIE (1 << 7)
#define RIER_CSCIE (1 << 6)
#define RIER_RSTAT(rier) ((rier) << 4)
#define RIER_TSTAT(rier) ((rier) << 2)
#define RIER_OVRIE (1 << 1)
#define RIER_RXFIE (1 << 0)
/** @} */
/**
* @name MSCAN Transmitter Flag Register (CANTFLG)
*
* @{
*/
#define TFLG_TXE2 (1 << 2)
#define TFLG_TXE1 (1 << 1)
#define TFLG_TXE0 (1 << 0)
/** @} */
/**
* @name MSCAN Transmitter Interrupt Enable Register (CANTIER)
*
* @{
*/
#define TIER_TXEI2 (1 << 2)
#define TIER_TXEI1 (1 << 1)
#define TIER_TXEI0 (1 << 0)
/** @} */
/**
* @name MSCAN Transmitter Message Abort Request (CANTARQ)
*
* @{
*/
#define TARQ_ABTRQ2 (1 << 2)
#define TARQ_ABTRQ1 (1 << 1)
#define TARQ_ABTRQ0 (1 << 0)
/** @} */
/**
* @name MSCAN Transmitter Message Abort Acknoledge (CANTAAK)
*
* @{
*/
#define TAAK_ABTRQ2 (1 << 2)
#define TAAK_ABTRQ1 (1 << 1)
#define TAAK_ABTRQ0 (1 << 0)
/** @} */
/**
* @name MSCAN Transmit Buffer Selection (CANBSEL)
*
* @{
*/
#define BSEL_TX2 (1 << 2)
#define BSEL_TX1 (1 << 1)
#define BSEL_TX0 (1 << 0)
/** @} */
/**
* @name MSCAN ID Acceptance Control Register (CANIDAC)
*
* @{
*/
#define IDAC_IDAM1 (1 << 5)
#define IDAC_IDAM0 (1 << 4)
#define IDAC_IDAM (IDAC_IDAM1 | IDAC_IDAM0)
#define IDAC_IDHIT( idac) ((idac) & 0x7)
/** @} */
/**
* @brief MSCAN registers.
*/
typedef struct mpc5200_mscan mscan;
/**
* @brief MSCAN context that has to be saved throughout the initialization
* mode.
*/
typedef struct {
uint8_t ctl0;
uint8_t rier;
uint8_t tier;
} mscan_context;
void mscan_enable( mscan *m, unsigned bit_rate);
void mscan_disable( mscan *m);
void mscan_interrupts_disable( mscan *m);
void mscan_set_bit_rate( mscan *m, unsigned bit_rate);
void mscan_initialization_mode_enter( mscan *m, mscan_context *context);
void mscan_initialization_mode_leave( mscan *m, const mscan_context *context);
void mscan_sleep_mode_enter( mscan *m);
void mscan_sleep_mode_leave( mscan *m);
uint8_t *mscan_id_acceptance_register( mscan *m, unsigned i);
uint8_t *mscan_id_mask_register( mscan *m, unsigned i);
unsigned mscan_filter_number( mscan *m);
bool mscan_set_filter_number( mscan *m, unsigned number);
bool mscan_filter_operation( mscan *m, bool set, unsigned index, uint32_t *id, uint32_t *mask);
void mscan_filter_clear( mscan *m);
void mscan_get_error_counters( mscan *m, unsigned *rec, unsigned *tec);
/** @} */
#endif /* LIBBSP_MSCAN_BASE_H */

View File

@@ -1,428 +0,0 @@
/*===============================================================*\
| Project: RTEMS generic MPC5200 BSP |
+-----------------------------------------------------------------+
| File: irq_asm.S
+-----------------------------------------------------------------+
| Partially based on the code references which are named below. |
| Adaptions, modifications, enhancements and any recent parts of |
| the code are: |
| Copyright (c) 2005 |
| Embedded Brains GmbH |
| Obere Lagerstr. 30 |
| D-82178 Puchheim |
| Germany |
| rtems@embedded-brains.de |
+-----------------------------------------------------------------+
| The license and distribution terms for this file may be |
| found in the file LICENSE in this distribution or at |
| |
| http://www.rtems.com/license/LICENSE. |
| |
+-----------------------------------------------------------------+
| this file contains the assembler portion of the irq handling |
+-----------------------------------------------------------------+
\*===============================================================*/
/***********************************************************************/
/* */
/* Module: irq_asm.S */
/* Date: 07/17/2003 */
/* Purpose: RTEMS assembly code for PowerPC IRQ veneers */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Description: This file contains the assembly code for the */
/* PowerPC IRQ veneers for RTEMS. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Code */
/* References: RTEMS assembly code for PowerPC IRQ veneers */
/* Module: irq_asm.S */
/* Project: RTEMS 4.6.0pre1 / MCF8260ads BSP */
/* Version 1.2 */
/* Date: 04/18/2002 */
/* */
/* Author(s) / Copyright(s): */
/* */
/* The license and distribution terms for this file may be */
/* found in found in the file LICENSE in this distribution or at */
/* http://www.rtems.com/license/LICENSE. */
/* */
/* Modified to support the MCP750. */
/* Modifications Copyright (C) 1999 Eric Valette.valette@crf.canon.fr*/
/* */
/*---------------------------------------------------------------------*/
/* */
/* Partially based on the code references which are named above. */
/* Adaptions, modifications, enhancements and any recent parts of */
/* the code are under the right of */
/* */
/* IPR Engineering, Dachauer Straße 38, D-80335 München */
/* Copyright(C) 2003 */
/* */
/*---------------------------------------------------------------------*/
/* */
/* IPR Engineering makes no representation or warranties with */
/* respect to the performance of this computer program, and */
/* specifically disclaims any responsibility for any damages, */
/* special or consequential, connected with the use of this program. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Version history: 1.0 */
/* */
/***********************************************************************/
/*#include <bsp/vectors.h>*/
#include "../vectors/vectors.h"
#include <rtems/score/cpuopts.h> /* for PPC_HAS_FPU */
#include <rtems/score/cpu.h>
#include <rtems/asm.h>
#include <libcpu/raw_exception.h>
#define SYNC \
sync; \
isync
.text
.p2align 5
PUBLIC_VAR(decrementer_exception_vector_prolog_code)
SYM (decrementer_exception_vector_prolog_code):
/*
* let room for exception frame
*/
stwu r1, - (EXCEPTION_FRAME_END)(r1)
stw r4, GPR4_OFFSET(r1)
li r4, ASM_DEC_VECTOR
ba shared_raw_irq_code_entry
PUBLIC_VAR (decrementer_exception_vector_prolog_code_size)
decrementer_exception_vector_prolog_code_size = . - decrementer_exception_vector_prolog_code
PUBLIC_VAR(external_exception_vector_prolog_code)
SYM (external_exception_vector_prolog_code):
/*
* let room for exception frame
*/
stwu r1, - (EXCEPTION_FRAME_END)(r1)
stw r4, GPR4_OFFSET(r1)
li r4, ASM_EXT_VECTOR
ba shared_raw_irq_code_entry
PUBLIC_VAR (external_exception_vector_prolog_code_size)
external_exception_vector_prolog_code_size = . - external_exception_vector_prolog_code
PUBLIC_VAR(system_management_exception_vector_prolog_code)
SYM (system_management_exception_vector_prolog_code):
/*
* let room for exception frame
*/
stwu r1, - (EXCEPTION_FRAME_END)(r1)
stw r4, GPR4_OFFSET(r1)
li r4, ASM_60X_SYSMGMT_VECTOR
ba shared_raw_irq_code_entry
PUBLIC_VAR (system_management_exception_vector_prolog_code_size)
system_management_exception_vector_prolog_code_size = . - system_management_exception_vector_prolog_code
PUBLIC_VAR(shared_raw_irq_code_entry)
PUBLIC_VAR(C_dispatch_irq_handler)
.p2align 5
SYM (shared_raw_irq_code_entry):
/*
* Entry conditions :
* Registers already saved : R1, R4
* R1 : points to a location with enough room for the
* interrupt frame
* R4 : vector number
*/
/*
* Save SRR0/SRR1 As soon As possible as it is the minimal needed
* to reenable exception processing
*/
stw r0, GPR0_OFFSET(r1)
stw r2, GPR2_OFFSET(r1)
stw r3, GPR3_OFFSET(r1)
mfsrr0 r0
mfsrr1 r2
mfmsr r3
stw r0, SRR0_FRAME_OFFSET(r1)
stw r2, SRR1_FRAME_OFFSET(r1)
/*
* Enable data and instruction address translation, exception recovery
*
* also, on CPUs with FP, enable FP so that FP context can be
* saved and restored (using FP instructions)
*/
#if (PPC_HAS_FPU == 0)
ori r3, r3, MSR_RI | MSR_DR/*| MSR_IR*/
#else
ori r3, r3, MSR_RI | MSR_DR | /*MSR_IR |*/ MSR_FP
#endif
mtmsr r3
SYNC
/*
* Push C scratch registers on the current stack. It may
* actually be the thread stack or the interrupt stack.
* Anyway we have to make it in order to be able to call C/C++
* functions. Depending on the nesting interrupt level, we will
* switch to the right stack later.
*/
stw r5, GPR5_OFFSET(r1)
stw r6, GPR6_OFFSET(r1)
stw r7, GPR7_OFFSET(r1)
stw r8, GPR8_OFFSET(r1)
stw r9, GPR9_OFFSET(r1)
stw r10, GPR10_OFFSET(r1)
stw r11, GPR11_OFFSET(r1)
stw r12, GPR12_OFFSET(r1)
stw r13, GPR13_OFFSET(r1)
mfcr r5
mfctr r6
mfxer r7
mflr r8
stw r5, EXC_CR_OFFSET(r1)
stw r6, EXC_CTR_OFFSET(r1)
stw r7, EXC_XER_OFFSET(r1)
stw r8, EXC_LR_OFFSET(r1)
/*
* Add some non volatile registers to store information
* that will be used when returning from C handler
*/
stw r14, GPR14_OFFSET(r1)
stw r15, GPR15_OFFSET(r1)
/*
* save current stack pointer location in R14
*/
addi r14, r1, 0
/*
* store part of _Thread_Dispatch_disable_level address in R15
*/
addis r15,0, _Thread_Dispatch_disable_level@ha
/*
* Get current nesting level in R2
*/
/* mfspr r2, SPRG0 */
addis r6, 0, _ISR_Nest_level@ha
lwz r2, _ISR_Nest_level@l( r6 )
/*
* Check if stack switch is necessary
*/
cmpwi r2,0
bne nested
mfspr r1, SPRG1
nested:
/*
* Start Incrementing nesting level in R2
*/
addi r2,r2,1
addis r6, 0, _ISR_Nest_level@ha
stw r2, _ISR_Nest_level@l( r6 )
/*
* Start Incrementing _Thread_Dispatch_disable_level R4 = _Thread_Dispatch_disable_level
*/
lwz r6,_Thread_Dispatch_disable_level@l(r15)
/*
* store new nesting level in SPRG0
*/
/* mtspr SPRG0, r2 */
addi r6, r6, 1
mfmsr r5
/*
* store new _Thread_Dispatch_disable_level value
*/
stw r6, _Thread_Dispatch_disable_level@l(r15)
/*
* We are now running on the interrupt stack. External and decrementer
* exceptions are still disabled. I see no purpose trying to optimize
* further assembler code.
*/
/*
* Call C exception handler for decrementer Interrupt frame is passed just
* in case...
*/
addi r3, r14, 0x8
bl C_dispatch_irq_handler /* C_dispatch_irq_handler(cpu_interrupt_frame* r3, vector r4) */
/*
* start decrementing nesting level. Note : do not test result against 0
* value as an easy exit condition because if interrupt nesting level > 1
* then _Thread_Dispatch_disable_level > 1
*/
/* mfspr r2, SPRG0 */
addis r6, 0, _ISR_Nest_level@ha
lwz r2, _ISR_Nest_level@l( r6 )
/*
* start decrementing _Thread_Dispatch_disable_level
*/
lwz r3,_Thread_Dispatch_disable_level@l(r15)
addi r2, r2, -1 /* Continue decrementing nesting level */
addi r3, r3, -1 /* Continue decrementing _Thread_Dispatch_disable_level */
stw r2, _ISR_Nest_level@l( r6 )
/* mtspr SPRG0, r2 */ /* End decrementing nesting level */
stw r3,_Thread_Dispatch_disable_level@l(r15) /* End decrementing _Thread_Dispatch_disable_level */
cmpwi r3, 0
/*
* switch back to original stack (done here just optimize registers
* contention. Could have been done before...)
*/
addi r1, r14, 0
bne easy_exit /* if (_Thread_Dispatch_disable_level != 0) goto easy_exit */
/*
* Here we are running again on the thread system stack.
* We have interrupt nesting level = _Thread_Dispatch_disable_level = 0.
* Interrupt are still disabled. Time to check if scheduler request to
* do something with the current thread...
*/
addis r4, 0, _Context_Switch_necessary@ha
lwz r5, _Context_Switch_necessary@l(r4)
cmpwi r5, 0
bne switch
addis r6, 0, _ISR_Signals_to_thread_executing@ha
lwz r7, _ISR_Signals_to_thread_executing@l(r6)
cmpwi r7, 0
li r8, 0
beq easy_exit
stw r8, _ISR_Signals_to_thread_executing@l(r6)
/*
* going to call _ThreadProcessSignalsFromIrq
* Push a complete exception like frame...
*/
stmw r16, GPR16_OFFSET(r1)
addi r3, r1, 0x8
/*
* compute SP at exception entry
*/
addi r2, r1, EXCEPTION_FRAME_END
/*
* store it at the right place
*/
stw r2, GPR1_OFFSET(r1)
/*
* Call High Level signal handling code
*/
bl _ThreadProcessSignalsFromIrq
/*
* start restoring exception like frame
*/
lwz r31, EXC_CTR_OFFSET(r1)
lwz r30, EXC_XER_OFFSET(r1)
lwz r29, EXC_CR_OFFSET(r1)
lwz r28, EXC_LR_OFFSET(r1)
mtctr r31
mtxer r30
mtcr r29
mtlr r28
lmw r4, GPR4_OFFSET(r1)
lwz r2, GPR2_OFFSET(r1)
lwz r0, GPR0_OFFSET(r1)
/*
* Disable data and instruction translation. Make path non recoverable...
*/
mfmsr r3
xori r3, r3, MSR_RI | MSR_DR/*| MSR_IR */
mtmsr r3
SYNC
/*
* Restore rfi related settings
*/
lwz r3, SRR1_FRAME_OFFSET(r1)
mtsrr1 r3
lwz r3, SRR0_FRAME_OFFSET(r1)
mtsrr0 r3
lwz r3, GPR3_OFFSET(r1)
addi r1,r1, EXCEPTION_FRAME_END
SYNC
rfi
switch:
bl SYM (_Thread_Dispatch)
easy_exit:
/*
* start restoring interrupt frame
*/
lwz r3, EXC_CTR_OFFSET(r1)
lwz r4, EXC_XER_OFFSET(r1)
lwz r5, EXC_CR_OFFSET(r1)
lwz r6, EXC_LR_OFFSET(r1)
mtctr r3
mtxer r4
mtcr r5
mtlr r6
lwz r15, GPR15_OFFSET(r1)
lwz r14, GPR14_OFFSET(r1)
lwz r13, GPR13_OFFSET(r1)
lwz r12, GPR12_OFFSET(r1)
lwz r11, GPR11_OFFSET(r1)
lwz r10, GPR10_OFFSET(r1)
lwz r9, GPR9_OFFSET(r1)
lwz r8, GPR8_OFFSET(r1)
lwz r7, GPR7_OFFSET(r1)
lwz r6, GPR6_OFFSET(r1)
lwz r5, GPR5_OFFSET(r1)
/*
* Disable nested exception processing, data and instruction
* translation.
*/
mfmsr r3
xori r3, r3, MSR_RI | MSR_DR/*| MSR_IR */
mtmsr r3
SYNC
/*
* Restore rfi related settings
*/
lwz r4, SRR1_FRAME_OFFSET(r1)
lwz r2, SRR0_FRAME_OFFSET(r1)
lwz r3, GPR3_OFFSET(r1)
lwz r0, GPR0_OFFSET(r1)
mtsrr1 r4
mtsrr0 r2
lwz r4, GPR4_OFFSET(r1)
lwz r2, GPR2_OFFSET(r1)
addi r1,r1, EXCEPTION_FRAME_END
SYNC
rfi

View File

@@ -1,305 +0,0 @@
/*===============================================================*\
| Project: RTEMS generic MPC5200 BSP |
+-----------------------------------------------------------------+
| Partially based on the code references which are named below. |
| Adaptions, modifications, enhancements and any recent parts of |
| the code are: |
| Copyright (c) 2005 |
| Embedded Brains GmbH |
| Obere Lagerstr. 30 |
| D-82178 Puchheim |
| Germany |
| rtems@embedded-brains.de |
+-----------------------------------------------------------------+
| The license and distribution terms for this file may be |
| found in the file LICENSE in this distribution or at |
| |
| http://www.rtems.com/license/LICENSE. |
| |
+-----------------------------------------------------------------+
| this file contains the IRQ controller/system initialization |
\*===============================================================*/
/***********************************************************************/
/* */
/* Module: irq_init.c */
/* Date: 07/17/2003 */
/* Purpose: RTEMS MPC5x00 CPU interrupt initialization */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Description: This file contains the implementation of rtems */
/* initialization related to interrupt handling. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Code */
/* References: MBX8xx CPU interrupt initialization */
/* Module: irq_init.c */
/* Project: RTEMS 4.6.0pre1 / MBX8xx BSP */
/* Version 1.1 */
/* Date: 04/06/2001 */
/* */
/* Author(s) / Copyright(s): */
/* */
/* CopyRight (C) 2001 valette@crf.canon.fr */
/* */
/* The license and distribution terms for this file may be */
/* found in found in the file LICENSE in this distribution or at */
/* http://www.rtems.com/license/LICENSE. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Partially based on the code references which are named above. */
/* Adaptions, modifications, enhancements and any recent parts of */
/* the code are under the right of */
/* */
/* IPR Engineering, Dachauer Straße 38, D-80335 München */
/* Copyright(C) 2003 */
/* */
/*---------------------------------------------------------------------*/
/* */
/* IPR Engineering makes no representation or warranties with */
/* respect to the performance of this computer program, and */
/* specifically disclaims any responsibility for any damages, */
/* special or consequential, connected with the use of this program. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Version history: 1.0 */
/* */
/***********************************************************************/
#include <bsp.h>
#include <rtems.h>
#include "../irq/irq.h"
#include <rtems/bspIo.h>
#include <libcpu/raw_exception.h>
#include "../include/mpc5200.h"
extern unsigned int external_exception_vector_prolog_code_size;
extern void external_exception_vector_prolog_code(void);
extern unsigned int decrementer_exception_vector_prolog_code_size;
extern void decrementer_exception_vector_prolog_code(void);
extern unsigned int system_management_exception_vector_prolog_code_size;
extern void system_management_exception_vector_prolog_code(void);
extern void BSP_panic(char *s);
extern void _BSP_Fatal_error(unsigned int v);
/*
volatile unsigned int ppc_cached_irq_mask;
*/
/*
* default on/off function
*/
static void nop_func(void){}
/*
* default isOn function
*/
static int not_connected(void) {return 0;}
/*
* default possible isOn function
*/
static int connected(void) {return 1;}
static rtems_irq_connect_data rtemsIrq[BSP_IRQ_NUMBER];
static rtems_irq_global_settings initial_config;
static rtems_irq_connect_data defaultIrq =
{
/* vectorIdex, hdl , param, on , off , isOn */
0, nop_func, NULL , nop_func, nop_func, not_connected };
static rtems_irq_prio irqPrioTable[BSP_SIU_IRQ_NUMBER] =
{
/* per. int. priorities (0-7) / 4bit coding / msb is HI/LO selection */
/* msb = 0 -> non-critical per. int. is routed to main int. (LO_int) */
/* msb = 1 -> critical per. int. is routed to critical int. (HI_int) */
0xF, 0, 0, 0, /* smart_comm (do not change!), psc1, psc2, psc3 */
0, 0, 0, 0, /* irda, eth, usb, ata */
0, 0, 0, 0, /* pci_ctrl, pci_sc_rx, pci_sc_tx, res */
0, 0, 0, 0, /* res, spi_modf, spi_spif, i2c1 */
0, 0, 0, 0, /* i2c, can1, can2, ir_rx */
0, 0, /* ir_rx, xlb_arb */
/* main interrupt priorities (0-7) / 4bit coding / msb is INT/SMI selection */
/* msb = 0 -> main int. is routed to processor INT (low vector base 0x500 ) */
/* msb = 1 -> main int. is routed to processor SMI (low vector base 0x1400 ) */
0, 0, /* slice_tim2, irq1 */
0, 0, 0, 0, /* irq2, irq3, lo_int, rtc_pint */
0, 0, 0, 0, /* rtc_sint, gpio_std, gpio_wkup, tmr0 */
0, 0, 0, 0, /* tmr1, tmr2, tmr3, tmr4 */
0, 0, 0, /* tmr5, tmr6, tmr7 */
/* critical interrupt priorities (0-3) / 2bit coding / no special purpose of msb */
0, /* irq0 */
0, 0, 0 /* slice_tim1, hi_int, ccs_wkup */
};
uint32_t irqMaskTable[BSP_PER_IRQ_NUMBER + BSP_MAIN_IRQ_NUMBER];
/*
* setup irqMaskTable to support a priorized/nested interrupt environment
*/
void setup_irqMaskTable(void)
{
rtems_irq_prio prio = 0;
uint32_t i = 0, j = 0, mask = 0;
/* set up the priority dependent masks for peripheral interrupts */
for(i = BSP_PER_IRQ_LOWEST_OFFSET; i <= BSP_PER_IRQ_MAX_OFFSET; i++)
{
prio = irqPrioTable[i];
mask = 0;
for(j = BSP_PER_IRQ_LOWEST_OFFSET; j <= BSP_PER_IRQ_MAX_OFFSET; j++)
{
if(prio > irqPrioTable[j])
mask |= (1 << (31 - j + BSP_PER_IRQ_LOWEST_OFFSET));
if((prio == irqPrioTable[j]) && (j >= i))
mask |= (1 << (31 - j + BSP_PER_IRQ_LOWEST_OFFSET));
}
irqMaskTable[i] = mask;
}
/* set up the priority dependent masks for main interrupts */
for(i = BSP_MAIN_IRQ_LOWEST_OFFSET; i <= BSP_MAIN_IRQ_MAX_OFFSET; i++)
{
prio = irqPrioTable[i];
mask = 0;
for(j = BSP_MAIN_IRQ_LOWEST_OFFSET; j <= BSP_MAIN_IRQ_MAX_OFFSET; j++)
{
if(prio > irqPrioTable[j])
mask |= (1 << (16 - j + BSP_MAIN_IRQ_LOWEST_OFFSET));
if((prio == irqPrioTable[j]) && (j >= i))
mask |= (1 << (16 - j + BSP_MAIN_IRQ_LOWEST_OFFSET));
}
irqMaskTable[i] = mask;
}
}
/*
* Initialize MPC5x00 SIU interrupt management
*/
void BSP_SIU_irq_init(void)
{
/* disable all peripheral interrupts */
mpc5200.per_mask = 0xFFFFFC00;
/* peripheral interrupt priorities according to reset value */
mpc5200.per_pri_1 = 0xF0000000;
mpc5200.per_pri_2 = 0x00000000;
mpc5200.per_pri_3 = 0x00000000;
/* disable external interrupts IRQ0-4 / critical interrupts are routed to core_int */
mpc5200.ext_en_type = 0x0F000001;
/* disable main interrupts / crit. int. priorities according to reset values */
mpc5200.crit_pri_main_mask = 0x0001FFFF;
/* main priorities according to reset value */
mpc5200.main_pri_1 = 0;
mpc5200.main_pri_2 = 0;
/* reset all status indicators */
mpc5200.csa = 0x0001FFFF;
mpc5200.msa = 0x0001FFFF;
mpc5200.psa = 0x003FFFFF;
mpc5200.psa_be = 0x03000000;
setup_irqMaskTable();
}
void BSP_rtems_irq_mng_init(unsigned cpuId)
{
rtems_raw_except_connect_data vectorDesc;
int i;
#if (BENCHMARK_IRQ_PROCESSING == 1)
extern void BSP_initialize_IRQ_Timing(void);
void BSP_initialize_IRQ_Timing(void);
#endif
BSP_SIU_irq_init();
/*
* Initialize Rtems management interrupt table
*/
/*
* re-init the rtemsIrq table
*/
for (i = 0; i < BSP_IRQ_NUMBER; i++) {
rtemsIrq[i] = defaultIrq;
rtemsIrq[i].name = i;
}
/*
* Init initial Interrupt management config
*/
initial_config.irqNb = BSP_IRQ_NUMBER;
initial_config.defaultEntry = defaultIrq;
initial_config.irqHdlTbl = rtemsIrq;
initial_config.irqBase = BSP_LOWEST_OFFSET;
initial_config.irqPrioTbl = irqPrioTable;
if (!BSP_rtems_irq_mngt_set(&initial_config)) {
/*
* put something here that will show the failure...
*/
BSP_panic(
"Unable to initialize RTEMS interrupt Management!!! System locked\n"
);
}
/*
* We must connect the raw irq handler for the two
* expected interrupt sources : decrementer and external interrupts.
*/
vectorDesc.exceptIndex = ASM_DEC_VECTOR;
vectorDesc.hdl.vector = ASM_DEC_VECTOR;
vectorDesc.hdl.raw_hdl = decrementer_exception_vector_prolog_code;
vectorDesc.hdl.raw_hdl_size = (unsigned) &decrementer_exception_vector_prolog_code_size;
vectorDesc.on = nop_func;
vectorDesc.off = nop_func;
vectorDesc.isOn = connected;
if (!ppc_set_exception (&vectorDesc)) {
BSP_panic("Unable to initialize RTEMS decrementer raw exception\n");
}
vectorDesc.exceptIndex = ASM_EXT_VECTOR;
vectorDesc.hdl.vector = ASM_EXT_VECTOR;
vectorDesc.hdl.raw_hdl = external_exception_vector_prolog_code;
vectorDesc.hdl.raw_hdl_size = (unsigned) &external_exception_vector_prolog_code_size;
if (!ppc_set_exception (&vectorDesc)) {
BSP_panic("Unable to initialize RTEMS external raw exception\n");
}
vectorDesc.exceptIndex = ASM_60X_SYSMGMT_VECTOR;
vectorDesc.hdl.vector = ASM_60X_SYSMGMT_VECTOR;
vectorDesc.hdl.raw_hdl = system_management_exception_vector_prolog_code;
vectorDesc.hdl.raw_hdl_size = (unsigned) &system_management_exception_vector_prolog_code_size;
if (!ppc_set_exception (&vectorDesc)) {
BSP_panic("Unable to initialize RTEMS system management raw exception\n");
}
}

View File

@@ -0,0 +1,538 @@
/**
* @file
*
* @ingroup m
*
* @brief MSCAN support functions code.
*/
/*
* Copyright (c) 2008
* Embedded Brains GmbH
* Obere Lagerstr. 30
* D-82178 Puchheim
* Germany
* rtems@embedded-brains.de
*
* The license and distribution terms for this file may be found in the file
* LICENSE in this distribution or at http://www.rtems.com/license/LICENSE.
*/
#include <bsp.h>
#include <bsp/mscan-base.h>
#define MIN_NO_OF_TQ 7
#define TSEG_1 1
#define TSEG_2 2
#define NO_OF_TABLE_ENTRIES 4
#define SJW 3
#define CAN_MAX_NO_OF_TQ 25
#define CAN_MAX_NO_OF_TQ_TSEG1 15
#define CAN_MAX_NO_OF_TQ_TSEG2 7
#define CAN_MAX_NO_OF_TQ_SJW 2
/**
* Time segmant table.
*
* <table>
* <tr>
* <td>Number of time quantas</th>
* <td>Time Segment 1</th>
* <td>Time Segment 2</th>
* <td>Sync: Jump width</th>
* </tr>
* </table>
*/
static uint8_t can_time_segment_table
[CAN_MAX_NO_OF_TQ - MIN_NO_OF_TQ + 1] [NO_OF_TABLE_ENTRIES] = {
{7, 4, 2, 1},
{8, 5, 2, 1},
{9, 6, 2, 2},
{10, 6, 3, 2},
{11, 7, 3, 2},
{12, 8, 3, 2},
{13, 8, 4, 2},
{14, 9, 4, 2},
{15, 10, 4, 2},
{16, 10, 5, 2},
{17, 11, 5, 2},
{18, 12, 5, 2},
{19, 12, 6, 2},
{20, 13, 6, 2},
{21, 14, 6, 2},
{22, 14, 7, 2},
{23, 15, 7, 2},
{24, 15, 8, 2},
{25, 16, 8, 2}
};
/**
* @brief Calculates the MSCAN clock prescaler value.
*/
static uint8_t prescaler_calculation(
unsigned can_bit_rate,
unsigned can_clock_frq,
uint8_t *tq_no
)
{
/* local variables */
uint8_t presc_val,
tq_no_dev_min = 0;
uint32_t bit_rate,
bit_rate_dev,
frq_tq,
bit_rate_dev_min = 0xFFFFFFFF;
/* loop through all values of time quantas */
for (*tq_no = CAN_MAX_NO_OF_TQ; *tq_no >= MIN_NO_OF_TQ; (*tq_no)--) {
/* calculate time quanta freq. */
frq_tq = *tq_no * can_bit_rate;
/* calculate the optimized prescal. val. */
presc_val = (can_clock_frq + frq_tq / 2) / frq_tq;
/* calculate the bitrate */
bit_rate = can_clock_frq / (*tq_no * presc_val);
/* calculate the bitrate deviation */
if (can_bit_rate >= bit_rate) {
/* calculate the bitrate deviation */
bit_rate_dev = can_bit_rate - bit_rate;
} else {
/* calculate the bitrate deviation */
bit_rate_dev = bit_rate - can_bit_rate;
}
/* check the deviation freq. */
if (bit_rate_dev == 0) {
/* return if best match (zero deviation) */
return (uint8_t) (presc_val);
} else {
/* check for minimum of bit rate deviation */
if (bit_rate_dev < bit_rate_dev_min) {
/* recognize the minimum freq. deviation */
bit_rate_dev_min = bit_rate_dev;
/* recognize the no. of time quantas */
tq_no_dev_min = *tq_no;
}
}
}
/* get the no of tq's */
*tq_no = tq_no_dev_min;
/* calculate time quanta freq. */
frq_tq = *tq_no * can_bit_rate;
/* return the optimized prescaler value */
return (uint8_t) ((can_clock_frq + frq_tq / 2) / frq_tq);
}
/**
* @brief Sets the bit rate for the MSCAN module @a m to @a can_bit_rate
* in [bits/s].
*/
void mscan_set_bit_rate( mscan *m, unsigned can_bit_rate)
{
mscan_context context;
uint32_t prescale_val = 0;
uint8_t tq_no,
tseg_1,
tseg_2,
sseg;
/* Enter initialization mode */
mscan_initialization_mode_enter( m, &context);
/* get optimized prescaler value */
prescale_val = prescaler_calculation(can_bit_rate, IPB_CLOCK, &tq_no);
/* get time segment length from time segment table */
tseg_1 = can_time_segment_table[tq_no - MIN_NO_OF_TQ][TSEG_1];
tseg_2 = can_time_segment_table[tq_no - MIN_NO_OF_TQ][TSEG_2];
sseg = can_time_segment_table[tq_no - MIN_NO_OF_TQ][SJW];
/* Bus Timing Register 0 MSCAN_A/_B ------------------------------ */
/* [07]:SJW1 1 : Synchronization jump width, Bit1 */
/* [06]:SJW0 0 : Synchronization jump width, Bit0 */
/* SJW = 2 -> 3 Tq clock cycles */
/* [05]:BRP5 0 : Baud Rate Prescaler, Bit 5 */
/* [04]:BRP4 0 : Baud Rate Prescaler, Bit 4 */
/* [03]:BRP3 0 : Baud Rate Prescaler, Bit 3 */
/* [02]:BRP2 1 : Baud Rate Prescaler, Bit 2 */
/* [01]:BRP1 0 : Baud Rate Prescaler, Bit 1 */
/* [00]:BRP0 1 : Baud Rate Prescaler, Bit 0 */
m->btr0 = (BTR0_SJW(sseg - 1) | BTR0_BRP(prescale_val - 1));
/* Bus Timing Register 1 MSCAN_A/_B ------------------------------ */
/* [07]:SAMP 0 : One Sample per bit */
/* [06]:TSEG22 0 : Time Segment 2, Bit 2 */
/* [05]:TSEG21 1 : Time Segment 2, Bit 1 */
/* [04]:TSEG20 0 : Time Segment 2, Bit 0 */
/* -> PHASE_SEG2 = 3 Tq */
/* [03]:TSEG13 0 : Time Segment 1, Bit 3 */
/* [02]:TSEG12 1 : Time Segment 1, Bit 2 */
/* [01]:TSEG11 1 : Time Segment 1, Bit 1 */
/* [00]:TSEG10 0 : Time Segment 1, Bit 0 */
m->btr1 = (BTR1_TSEG2(tseg_2 - 1) | BTR1_TSEG1(tseg_1 - 1));
/* Leave initialization mode */
mscan_initialization_mode_leave( m, &context);
}
/**
* @brief Disables all interrupts for the MSCAN module @a m.
*/
void mscan_interrupts_disable( mscan *m)
{
m->rier = 0;
m->tier = 0;
}
/**
* @brief Enter initialization mode for the MSCAN module @a m.
*
* Saves the current MSCAN context in @a context.
*/
void mscan_initialization_mode_enter( mscan *m, mscan_context *context)
{
/* Save context */
context->ctl0 = m->ctl0 & CTL0_TIME;
context->rier = m->rier;
context->tier = m->tier;
/* Initialization mode not requested? */
if ((m->ctl0 & CTL0_INITRQ) == 0) {
/* Enter sleep mode to avoid error conditions */
mscan_sleep_mode_enter( m);
/* Request initialization mode */
m->ctl0 |= CTL0_INITRQ;
}
/* Wait for initialization mode acknowledge */
while ((m->ctl1 & CTL1_INITAK) == 0) {
/* Wait */
}
}
/**
* @brief Leave initialization mode for the MSCAN module @a m.
*
* Saves the previous MSCAN context saved in @a context.
*/
void mscan_initialization_mode_leave( mscan *m, const mscan_context *context)
{
/* Clear initialization mode request */
m->ctl0 &= ~CTL0_INITRQ;
/* Wait for clearing of initialization mode acknowledge */
while ((m->ctl1 & CTL1_INITAK) != 0) {
/* Wait */
}
/* Leave sleep mode */
mscan_sleep_mode_leave( m);
/* Restore context */
m->ctl0 |= context->ctl0;
m->rier |= context->rier;
m->tier |= context->tier;
}
/**
* @brief Enter sleep mode for the MSCAN module @a m.
*/
void mscan_sleep_mode_enter( mscan *m)
{
/* Request sleep mode */
m->ctl0 |= CTL0_SLPRQ;
/* Wait for sleep mode acknowledge */
while ((m->ctl1 & CTL1_SLPAK) == 0) {
/* Wait */
}
}
/**
* @brief Leave sleep mode for the MSCAN module @a m.
*/
void mscan_sleep_mode_leave( mscan *m)
{
/* Clear sleep mode request */
m->ctl0 &= ~CTL0_SLPRQ;
/* Wait for clearing of sleep mode acknowledge */
while ((m->ctl1 & CTL1_SLPAK) != 0) {
/* Wait */
}
}
/**
* @brief Enables and initializes the MSCAN module @a m.
*
* The module is set to listen only mode.
*/
void mscan_enable( mscan *m, unsigned bit_rate)
{
/* Disable the module */
mscan_disable( m);
/* Enable module in listen only */
m->ctl1 = CTL1_CANE | CTL1_LISTEN;
/* Close acceptance filters */
m->idac = IDAC_IDAM1 | IDAC_IDAM0;
/* Clear filter */
mscan_filter_clear( m);
/* Set bit rate and leave initialization mode */
mscan_set_bit_rate( m, bit_rate);
/* Clear all flags */
m->ctl0 = CTL0_RXFRM;
/* Disable interrupts */
mscan_interrupts_disable( m);
}
/**
* @brief Disables the MSCAN module @a m.
*
* The module is set to sleep mode and disabled afterwards.
*/
void mscan_disable( mscan *m)
{
mscan_context context;
/* Disable interrupts */
mscan_interrupts_disable( m);
/* Enter initialization mode */
mscan_initialization_mode_enter( m, &context);
/* Disable module */
m->ctl1 &= ~CTL1_CANE;
}
/**
* @brief Sets the filter ID and mask registers of the MSCAN module @a m to
* default values.
*/
void mscan_filter_clear( mscan *m)
{
mscan_context context;
mscan_initialization_mode_enter( m, &context);
/* Setup ID acceptance registers */
m->idar0 = MSCAN_FILTER_ID_DEFAULT;
m->idar1 = MSCAN_FILTER_ID_DEFAULT;
m->idar2 = MSCAN_FILTER_ID_DEFAULT;
m->idar3 = MSCAN_FILTER_ID_DEFAULT;
m->idar4 = MSCAN_FILTER_ID_DEFAULT;
m->idar5 = MSCAN_FILTER_ID_DEFAULT;
m->idar6 = MSCAN_FILTER_ID_DEFAULT;
m->idar7 = MSCAN_FILTER_ID_DEFAULT;
/* Setup ID mask registers */
m->idmr0 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr1 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr2 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr3 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr4 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr5 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr6 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
m->idmr7 = (uint8_t) MSCAN_FILTER_MASK_DEFAULT;
mscan_initialization_mode_leave( m, &context);
}
/**
* @brief Returns the number of active filters of the MSCAN module @a m.
*
* @see MSCAN_FILTER_NUMBER_MIN, MSCAN_FILTER_NUMBER_2, MSCAN_FILTER_NUMBER_4
* and MSCAN_FILTER_NUMBER_MAX.
*/
unsigned mscan_filter_number( mscan *m)
{
uint8_t idam = m->idac & IDAC_IDAM;
switch (idam) {
case 0:
return MSCAN_FILTER_NUMBER_2;
case IDAC_IDAM0:
return MSCAN_FILTER_NUMBER_4;
case IDAC_IDAM1:
return MSCAN_FILTER_NUMBER_MAX;
default:
return MSCAN_FILTER_NUMBER_MIN;
}
}
/**
* @brief Sets the number of active filters of the MSCAN module @a m to @a
* number and returns true if @a number is valid.
*
* @see MSCAN_FILTER_NUMBER_MIN, MSCAN_FILTER_NUMBER_2, MSCAN_FILTER_NUMBER_4
* and MSCAN_FILTER_NUMBER_MAX.
*/
bool mscan_set_filter_number( mscan *m, unsigned number)
{
mscan_context context;
uint8_t idac = IDAC_IDAM1 | IDAC_IDAM0;
switch (number) {
case MSCAN_FILTER_NUMBER_MIN:
break;
case MSCAN_FILTER_NUMBER_2:
idac = 0;
break;
case MSCAN_FILTER_NUMBER_4:
idac = IDAC_IDAM0;
break;
case MSCAN_FILTER_NUMBER_MAX:
idac = IDAC_IDAM1;
break;
default:
return false;
}
mscan_initialization_mode_enter( m, &context);
m->idac = idac;
mscan_initialization_mode_leave( m, &context);
/* Clear filter */
mscan_filter_clear( m);
return true;
}
/**
* @brief Returns the address of the CANIDAR register with index @a i of the
* MSCAN module @a m.
*
* @warning The index @a i is not checked if it is in range.
*/
uint8_t *mscan_id_acceptance_register( mscan *m, unsigned i)
{
uint8_t *idar [8] = {
&m->idar0,
&m->idar1,
&m->idar2,
&m->idar3,
&m->idar4,
&m->idar5,
&m->idar6,
&m->idar7
};
return idar [i];
}
/**
* @brief Returns the address of the CANIDMR register with index @a i of the
* MSCAN module @a m.
*
* @warning The index @a i is not checked if it is in range.
*/
uint8_t *mscan_id_mask_register( mscan *m, unsigned i)
{
uint8_t *idmr [8] = {
&m->idmr0,
&m->idmr1,
&m->idmr2,
&m->idmr3,
&m->idmr4,
&m->idmr5,
&m->idmr6,
&m->idmr7
};
return idmr [i];
}
/**
* @brief Sets or gets the filter ID and mask in @a id and @a mask depending on
* @a set of MSCAN module @a m. The filter is selected by the value of @a
* index.
*
* Returns true if the operation was successful.
*/
bool mscan_filter_operation(
mscan *m,
bool set,
unsigned index,
uint32_t *id,
uint32_t *mask
)
{
unsigned number = mscan_filter_number( m);
unsigned offset = MSCAN_FILTER_NUMBER_MAX / number;
unsigned shift = 24;
volatile uint8_t *idar = NULL;
volatile uint8_t *idmr = NULL;
if (!set) {
*id = MSCAN_FILTER_ID_DEFAULT;
*mask = MSCAN_FILTER_MASK_DEFAULT;
}
if (index < number) {
mscan_context context;
mscan_initialization_mode_enter( m, &context);
index *= offset;
offset += index;
while (index < offset) {
idar = mscan_id_acceptance_register( m, index);
idmr = mscan_id_mask_register( m, index);
if (set) {
*idar = (uint8_t) (*id >> shift);
*idmr = (uint8_t) (*mask >> shift);
} else {
*id = (*id & ~(0xffU << shift)) | (*idar << shift);
*mask = (*mask & ~(0xffU << shift)) | (*idmr << shift);
}
shift -= 8;
++index;
}
mscan_initialization_mode_leave( m, &context);
} else {
return false;
}
return true;
}
/**
* @brief Returns the receiver and transmitter error counter values in @a rec
* and @a tec of MSCAN module @a m.
*/
void mscan_get_error_counters( mscan *m, unsigned *rec, unsigned *tec)
{
mscan_context context;
mscan_initialization_mode_enter( m, &context);
*rec = m->rxerr;
*tec = m->txerr;
mscan_initialization_mode_leave( m, &context);
}

View File

@@ -28,6 +28,11 @@ $(PROJECT_INCLUDE)/$(dirstamp):
@: > $(PROJECT_INCLUDE)/$(dirstamp)
PREINSTALL_DIRS += $(PROJECT_INCLUDE)/$(dirstamp)
../../../libcpu/@RTEMS_CPU@/$(dirstamp):
@$(MKDIR_P) ../../../libcpu/@RTEMS_CPU@
@: > ../../../libcpu/@RTEMS_CPU@/$(dirstamp)
PREINSTALL_DIRS += ../../../libcpu/@RTEMS_CPU@/$(dirstamp)
$(PROJECT_LIB)/bsp_specs: bsp_specs $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/bsp_specs
PREINSTALL_FILES += $(PROJECT_LIB)/bsp_specs
@@ -48,10 +53,6 @@ $(PROJECT_INCLUDE)/i2c.h: include/i2c.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/i2c.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/i2c.h
$(PROJECT_INCLUDE)/mpc5200.h: include/mpc5200.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/mpc5200.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/mpc5200.h
$(PROJECT_INCLUDE)/tm27.h: include/tm27.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/tm27.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/tm27.h
@@ -85,6 +86,10 @@ $(PROJECT_LIB)/linkcmds: startup/linkcmds $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/linkcmds
PREINSTALL_FILES += $(PROJECT_LIB)/linkcmds
$(PROJECT_LIB)/linkcmds.base: startup/linkcmds.base $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/linkcmds.base
PREINSTALL_FILES += $(PROJECT_LIB)/linkcmds.base
$(PROJECT_LIB)/linkcmds.brs5l: startup/linkcmds.brs5l $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/linkcmds.brs5l
PREINSTALL_FILES += $(PROJECT_LIB)/linkcmds.brs5l
@@ -97,7 +102,23 @@ $(PROJECT_LIB)/linkcmds.pm520: startup/linkcmds.pm520 $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/linkcmds.pm520
PREINSTALL_FILES += $(PROJECT_LIB)/linkcmds.pm520
$(PROJECT_INCLUDE)/bsp/irq.h: irq/irq.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(PROJECT_INCLUDE)/bsp/vectors.h: $(libcpudir)/new-exceptions/bspsupport/vectors.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vectors.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vectors.h
$(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h: $(libcpudir)/new-exceptions/bspsupport/ppc_exc_bspsupp.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
$(PROJECT_INCLUDE)/bsp/irq-generic.h: ../../shared/include/irq-generic.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq-generic.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq-generic.h
$(PROJECT_INCLUDE)/bsp/irq-config.h: include/irq-config.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq-config.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq-config.h
$(PROJECT_INCLUDE)/bsp/irq.h: include/irq.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq.h
@@ -105,18 +126,26 @@ $(PROJECT_INCLUDE)/bsp/i2cdrv.h: include/i2cdrv.h $(PROJECT_INCLUDE)/bsp/$(dirst
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/i2cdrv.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/i2cdrv.h
$(PROJECT_INCLUDE)/bsp/mpc5200.h: include/mpc5200.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/mpc5200.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/mpc5200.h
$(PROJECT_INCLUDE)/bsp/i2c.h: include/i2c.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/i2c.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/i2c.h
$(PROJECT_INCLUDE)/bsp/mpc5200.h: include/mpc5200.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/mpc5200.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/mpc5200.h
$(PROJECT_INCLUDE)/bsp/mscan-base.h: include/mscan-base.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/mscan-base.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/mscan-base.h
$(PROJECT_INCLUDE)/bsp/u-boot.h: include/u-boot.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/u-boot.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/u-boot.h
$(PROJECT_INCLUDE)/bsp/mscan.h: mscan/mscan.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/mscan.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/mscan.h
$(PROJECT_INCLUDE)/bsp/nvram.h: nvram/nvram.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/nvram.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/nvram.h
@@ -125,7 +154,3 @@ $(PROJECT_INCLUDE)/bsp/slicetimer.h: slicetimer/slicetimer.h $(PROJECT_INCLUDE)/
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/slicetimer.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/slicetimer.h
$(PROJECT_INCLUDE)/bsp/vectors.h: vectors/vectors.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vectors.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vectors.h

View File

@@ -0,0 +1,320 @@
/**
* @file
*
* Derived from internal linker script of GNU ld (GNU Binutils) 2.18 for elf32ppc emulation.
*/
OUTPUT_FORMAT ("elf32-powerpc", "elf32-powerpc", "elf32-powerpc")
OUTPUT_ARCH (powerpc)
ENTRY (start)
bsp_ram_start = ORIGIN (RAM);
bsp_ram_end = ORIGIN (RAM) + LENGTH (RAM);
bsp_ram_size = LENGTH (RAM);
bsp_rom_start = ORIGIN (ROM);
bsp_rom_end = ORIGIN (ROM) + LENGTH (ROM);
bsp_rom_size = LENGTH (ROM);
bsp_dpram_start = ORIGIN (DPRAM);
bsp_dpram_end = ORIGIN (DPRAM) + LENGTH (DPRAM);
bsp_dpram_size = LENGTH (DPRAM);
bsp_section_align = 32;
SECTIONS {
/*
* BSP: MPC5200 registers
*/
.regs (NOLOAD) : {
MBAR = .;
mpc5200 = .;
} > REGS
/*
* BSP: Exception vectors
*/
.vectors 0x100 : {
*(.vectors)
} > RAM
/*
* BSP: The initial stack will live in this area - between the vectors
* and the text section.
*/
.text 0x10000 : {
/*
* BSP: Start of text section
*/
bsp_section_text_start = .;
/*
* BSP: System startup entry
*/
KEEP (*(.entry))
/*
* BSP: Moved into .text from .init
*/
KEEP (*(.init))
*(.text .stub .text.* .gnu.linkonce.t.*)
KEEP (*(.text.*personality*))
/* .gnu.warning sections are handled specially by elf32.em. */
*(.gnu.warning)
*(.glink)
/*
* BSP: Special FreeBSD sysctl sections
*/
. = ALIGN (16);
__start_set_sysctl_set = .;
*(set_sysctl_*);
__stop_set_sysctl_set = ABSOLUTE(.);
*(set_domain_*);
*(set_pseudo_*);
/*
* BSP: Moved into .text from .*
*/
*(.rodata .rodata.* .gnu.linkonce.r.*)
*(.rodata1)
*(.interp)
*(.note.gnu.build-id)
*(.hash)
*(.gnu.hash)
*(.dynsym)
*(.dynstr)
*(.gnu.version)
*(.gnu.version_d)
*(.gnu.version_r)
*(.eh_frame_hdr)
/*
* BSP: Magic PPC stuff
*/
*(.PPC.*)
/*
* BSP: Required by cpukit/score/src/threadhandler.c
*/
PROVIDE (_fini = .);
/*
* BSP: Moved into .text from .fini
*/
KEEP (*(.fini))
. = ALIGN (bsp_section_align);
PROVIDE (__etext = .);
PROVIDE (_etext = .);
PROVIDE (etext = .);
} > RAM
.sdata2 : {
PROVIDE (_SDA2_BASE_ = 32768);
*(.sdata2 .sdata2.* .gnu.linkonce.s2.*)
. = ALIGN (bsp_section_align);
} > RAM
.sbss2 : {
*(.sbss2 .sbss2.* .gnu.linkonce.sb2.*)
. = ALIGN (bsp_section_align);
/*
* BSP: End and size of text section
*/
bsp_section_text_end = .;
bsp_section_text_size = bsp_section_text_end - bsp_section_text_start;
} > RAM
.data : {
/*
* BSP: Start of data section
*/
bsp_section_data_start = .;
/*
* BSP: Moved into .data from .ctors
*/
/* gcc uses crtbegin.o to find the start of
the constructors, so we make sure it is
first. Because this is a wildcard, it
doesn't matter if the user does not
actually link against crtbegin.o; the
linker won't look for a file to match a
wildcard. The wildcard also means that it
doesn't matter which directory crtbegin.o
is in. */
KEEP (*crtbegin.o(.ctors))
KEEP (*crtbegin?.o(.ctors))
/* We don't want to include the .ctor section from
the crtend.o file until after the sorted ctors.
The .ctor section from the crtend file contains the
end of ctors marker and it must be last */
KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
KEEP (*(SORT(.ctors.*)))
KEEP (*(.ctors))
/*
* BSP: Moved into .data from .dtors
*/
KEEP (*crtbegin.o(.dtors))
KEEP (*crtbegin?.o(.dtors))
KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
KEEP (*(SORT(.dtors.*)))
KEEP (*(.dtors))
/*
* BSP: Moved into .data from .*
*/
*(.tdata .tdata.* .gnu.linkonce.td.*)
*(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon)
*(.data1)
KEEP (*(.eh_frame))
*(.gcc_except_table .gcc_except_table.*)
KEEP (*(.jcr))
*(.data.rel.ro.local* .gnu.linkonce.d.rel.ro.local.*) *(.data.rel.ro* .gnu.linkonce.d.rel.ro.*)
*(.fixup)
*(.got1)
*(.got2)
*(.dynamic)
*(.got)
*(.plt)
PROVIDE_HIDDEN (__preinit_array_start = .);
KEEP (*(.preinit_array))
PROVIDE_HIDDEN (__preinit_array_end = .);
PROVIDE_HIDDEN (__init_array_start = .);
KEEP (*(SORT(.init_array.*)))
KEEP (*(.init_array))
PROVIDE_HIDDEN (__init_array_end = .);
PROVIDE_HIDDEN (__fini_array_start = .);
KEEP (*(.fini_array))
KEEP (*(SORT(.fini_array.*)))
PROVIDE_HIDDEN (__fini_array_end = .);
*(.data .data.* .gnu.linkonce.d.*)
KEEP (*(.gnu.linkonce.d.*personality*))
SORT(CONSTRUCTORS)
. = ALIGN (bsp_section_align);
} > RAM
.sdata : {
PROVIDE (_SDA_BASE_ = 32768);
*(.sdata .sdata.* .gnu.linkonce.s.*)
. = ALIGN (bsp_section_align);
_edata = .;
PROVIDE (edata = .);
/*
* BSP: End and size of data section
*/
bsp_section_data_end = .;
bsp_section_data_size = bsp_section_data_end - bsp_section_data_start;
} > RAM
.sbss : {
/*
* BSP: Start of bss section
*/
bsp_section_bss_start = .;
__bss_start = .;
PROVIDE (__sbss_start = .); PROVIDE (___sbss_start = .);
*(.scommon)
*(.dynsbss)
*(.sbss .sbss.* .gnu.linkonce.sb.*)
PROVIDE (__sbss_end = .); PROVIDE (___sbss_end = .);
. = ALIGN (bsp_section_align);
} > RAM
.bss : {
*(COMMON)
*(.dynbss)
*(.bss .bss.* .gnu.linkonce.b.*)
. = ALIGN (bsp_section_align);
__end = .;
_end = .;
PROVIDE (end = .);
/*
* BSP: End and size of bss section
*/
bsp_section_bss_end = .;
bsp_section_bss_size = bsp_section_bss_end - bsp_section_bss_start;
} > RAM
/*
* BSP: Interrupt stack
*/
bsp_interrupt_stack_start = .;
bsp_interrupt_stack_end = bsp_interrupt_stack_start + 32k;
bsp_interrupt_stack_size = bsp_interrupt_stack_end - bsp_interrupt_stack_start;
. = bsp_interrupt_stack_end;
/*
* BSP: Work area start
*/
bsp_work_area_start = .;
/* Stabs debugging sections. */
.stab 0 : { *(.stab) }
.stabstr 0 : { *(.stabstr) }
.stab.excl 0 : { *(.stab.excl) }
.stab.exclstr 0 : { *(.stab.exclstr) }
.stab.index 0 : { *(.stab.index) }
.stab.indexstr 0 : { *(.stab.indexstr) }
.comment 0 : { *(.comment) }
/* DWARF debug sections.
Symbols in the DWARF debugging sections are relative to the beginning
of the section so we begin them at 0. */
/* DWARF 1 */
.debug 0 : { *(.debug) }
.line 0 : { *(.line) }
/* GNU DWARF 1 extensions */
.debug_srcinfo 0 : { *(.debug_srcinfo) }
.debug_sfnames 0 : { *(.debug_sfnames) }
/* DWARF 1.1 and DWARF 2 */
.debug_aranges 0 : { *(.debug_aranges) }
.debug_pubnames 0 : { *(.debug_pubnames) }
/* DWARF 2 */
.debug_info 0 : { *(.debug_info .gnu.linkonce.wi.*) }
.debug_abbrev 0 : { *(.debug_abbrev) }
.debug_line 0 : { *(.debug_line) }
.debug_frame 0 : { *(.debug_frame) }
.debug_str 0 : { *(.debug_str) }
.debug_loc 0 : { *(.debug_loc) }
.debug_macinfo 0 : { *(.debug_macinfo) }
/* SGI/MIPS DWARF 2 extensions */
.debug_weaknames 0 : { *(.debug_weaknames) }
.debug_funcnames 0 : { *(.debug_funcnames) }
.debug_typenames 0 : { *(.debug_typenames) }
.debug_varnames 0 : { *(.debug_varnames) }
/* DWARF 3 */
.debug_pubtypes 0 : { *(.debug_pubtypes) }
.debug_ranges 0 : { *(.debug_ranges) }
.gnu.attributes 0 : { KEEP (*(.gnu.attributes)) }
/DISCARD/ : {
*(.note.GNU-stack) *(.gnu_debuglink)
}
/*
* BSP: Catch all unknown sections
*/
.nirvana : {
*(*)
} > NIRVANA
}

View File

@@ -1,266 +0,0 @@
/*===============================================================*\
| Project: RTEMS generic MPC5200 BSP |
+-----------------------------------------------------------------+
| Partially based on the code references which are named below. |
| Adaptions, modifications, enhancements and any recent parts of |
| the code are: |
| Copyright (c) 2005 |
| Embedded Brains GmbH |
| Obere Lagerstr. 30 |
| D-82178 Puchheim |
| Germany |
| rtems@embedded-brains.de |
+-----------------------------------------------------------------+
| The license and distribution terms for this file may be |
| found in the file LICENSE in this distribution or at |
| |
| http://www.rtems.com/license/LICENSE. |
| |
+-----------------------------------------------------------------+
| this file contains the irq controller handler |
\*===============================================================*/
/***********************************************************************/
/* */
/* Module: vectors.s */
/* Date: 07/17/2003 */
/* Purpose: RTEMS assembly code for PowerPC exception veneers */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Description: */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Code */
/* References: This file contains the assembly code for the */
/* PowerPC exception veneers for RTEMS. */
/* Module: vectors.s */
/* Project: RTEMS 4.6.0pre1 / MCF8260ads BSP */
/* Version 1.2 */
/* Date: 04/18/2002 */
/* */
/* Author(s) / Copyright(s): */
/* */
/* (c) 1999, Eric Valette valette@crf.canon.fr */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Partially based on the code references which are named above. */
/* Adaptions, modifications, enhancements and any recent parts of */
/* the code are under the right of */
/* */
/* IPR Engineering, Dachauer Straße 38, D-80335 München */
/* Copyright(C) 2003 */
/* */
/*---------------------------------------------------------------------*/
/* */
/* IPR Engineering makes no representation or warranties with */
/* respect to the performance of this computer program, and */
/* specifically disclaims any responsibility for any damages, */
/* special or consequential, connected with the use of this program. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Version history: 1.0 */
/* */
/***********************************************************************/
#include <rtems/asm.h>
#include <bspopts.h>
#include <rtems/score/cpu.h>
#include "vectors.h"
#define SYNC \
sync; \
isync
.text
.p2align 5
PUBLIC_VAR(default_exception_vector_code_prolog)
SYM (default_exception_vector_code_prolog):
/*
* let room for exception frame
*/
stwu r1, - (EXCEPTION_FRAME_END)(r1)
stw r3, GPR3_OFFSET(r1)
stw r2, GPR2_OFFSET(r1)
mflr r2
stw r2, EXC_LR_OFFSET(r1)
bl 0f
0: /*
* r3 = exception vector entry point
* (256 * vector number) + few instructions
*/
mflr r3
/*
* r3 = r3 >> 8 = vector
*/
srwi r3,r3,8
ba push_normalized_frame
PUBLIC_VAR (default_exception_vector_code_prolog_size)
default_exception_vector_code_prolog_size= . - default_exception_vector_code_prolog
.p2align 5
PUBLIC_VAR (push_normalized_frame)
SYM (push_normalized_frame):
stw r3, EXCEPTION_NUMBER_OFFSET(r1)
stw r0, GPR0_OFFSET(r1)
mfsrr0 r2
stw r2, SRR0_FRAME_OFFSET(r1)
mfsrr1 r3
stw r3, SRR1_FRAME_OFFSET(r1)
/*
* Save general purpose registers
* Already saved in prolog : R1, R2, R3, LR.
* Saved a few line above : R0
*
* Manual says that "stmw" instruction may be slower than
* series of individual "stw" but who cares about performance
* for the DEFAULT exception handler?
*/
stmw r4, GPR4_OFFSET(r1) /* save R4->R31 */
mfcr r31
stw r31, EXC_CR_OFFSET(r1)
mfctr r30
stw r30, EXC_CTR_OFFSET(r1)
mfxer r28
stw r28, EXC_XER_OFFSET(r1)
/*
* compute SP at exception entry
*/
addi r2, r1, EXCEPTION_FRAME_END
/*
* store it at the right place
*/
stw r2, GPR1_OFFSET(r1)
/*
* Enable data and instruction address translation, exception nesting
*/
mfmsr r3
ori r3,r3, MSR_RI|MSR_DR /*| MSR_IR*/
mtmsr r3
SYNC
/*
* Call C exception handler
*/
/*
* store the execption frame address in r3 (first param)
*/
addi r3, r1, 0x8
/*
* globalExceptHdl(r3)
*/
addis r4, 0, globalExceptHdl@ha
lwz r5, globalExceptHdl@l(r4)
mtlr r5
blrl
/*
* Restore registers status
*/
lwz r31, EXC_CR_OFFSET(r1)
mtcr r31
lwz r30, EXC_CTR_OFFSET(r1)
mtctr r30
lwz r29, EXC_LR_OFFSET(r1)
mtlr r29
lwz r28, EXC_XER_OFFSET(r1)
mtxer r28
lmw r4, GPR4_OFFSET(r1)
lwz r2, GPR2_OFFSET(r1)
lwz r0, GPR0_OFFSET(r1)
/*
* Disable data and instruction translation. Make path non recoverable...
*/
mfmsr r3
xori r3, r3, MSR_RI|MSR_DR /*| MSR_IR */
mtmsr r3
SYNC
/*
* Restore rfi related settings
*/
lwz r3, SRR1_FRAME_OFFSET(r1)
mtsrr1 r3
lwz r3, SRR0_FRAME_OFFSET(r1)
mtsrr0 r3
lwz r3, GPR3_OFFSET(r1)
addi r1,r1, EXCEPTION_FRAME_END
SYNC
rfi
#if !defined(icecube)
.section .vectors,"awx",@progbits
PUBLIC_VAR (__vectors)
SYM (__vectors):
bl start
.rep 63
.long 0x04000400
.endr
__vec2: b __vec2
.rep 63
.long 0x04000400
.endr
__vec3: b __vec3
.rep 63
.long 0x04000400
.endr
__vec4: b __vec4
.rep 63
.long 0x04000400
.endr
__vec5: b __vec5
.rep 63
.long 0x04000400
.endr
__vec6: b __vec6
.rep 63
.long 0x04000400
.endr
__vec7: b __vec7
.rep 63
.long 0x04000400
.endr
__vec8: b __vec8
.rep 63
.long 0x04000400
.endr
__vec9: b __vec9
.rep 63
.long 0x04000400
.endr
__veca: b __veca
.rep 63
.long 0x04000400
.endr
__vecb: b __vecb
.rep 63
.long 0x04000400
.endr
__vecc: b __vecc
.rep 63
.long 0x04000400
.endr
__vecd: b __vecd
.rep 63
.long 0x04000400
.endr
__vece: b __vece
.rep 63
.long 0x04000400
.endr
__vecf: b __vecf
.rep 63+1024
.long 0x04000400
.endr
#endif

View File

@@ -1,152 +0,0 @@
/*---------------------------------------------------------------------------*/
/* Actually no changes made in this file but its presence is required in the */
/* cygwin /shared directory due to development purposes! */
/* */
/* IPR Engineering, 07/17/2003 */
/*---------------------------------------------------------------------------*/
/*
* vectors.h Exception frame related contant and API.
*
* This include file describe the data structure and the functions implemented
* by rtems to handle exceptions.
*
* CopyRight (C) 1999 valette@crf.canon.fr
*
* The license and distribution terms for this file may be
* found in found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* vectors.h,v 1.2 2002/05/14 17:10:17 joel Exp
*/
#ifndef LIBBSP_POWERPC_MCP750_VECTORS_H
#define LIBBSP_POWERPC_MCP750_VECTORS_H
/*
* The callee (high level exception code written in C)
* will store the Link Registers (return address) at entry r1 + 4 !!!.
* So let room for it!!!.
*/
#define LINK_REGISTER_CALLEE_UPDATE_ROOM 4
#define SRR0_FRAME_OFFSET 8
#define SRR1_FRAME_OFFSET 12
#define EXCEPTION_NUMBER_OFFSET 16
#define GPR0_OFFSET 20
#define GPR1_OFFSET 24
#define GPR2_OFFSET 28
#define GPR3_OFFSET 32
#define GPR4_OFFSET 36
#define GPR5_OFFSET 40
#define GPR6_OFFSET 44
#define GPR7_OFFSET 48
#define GPR8_OFFSET 52
#define GPR9_OFFSET 56
#define GPR10_OFFSET 60
#define GPR11_OFFSET 64
#define GPR12_OFFSET 68
#define GPR13_OFFSET 72
#define GPR14_OFFSET 76
#define GPR15_OFFSET 80
#define GPR16_OFFSET 84
#define GPR17_OFFSET 88
#define GPR18_OFFSET 92
#define GPR19_OFFSET 96
#define GPR20_OFFSET 100
#define GPR21_OFFSET 104
#define GPR22_OFFSET 108
#define GPR23_OFFSET 112
#define GPR24_OFFSET 116
#define GPR25_OFFSET 120
#define GPR26_OFFSET 124
#define GPR27_OFFSET 128
#define GPR28_OFFSET 132
#define GPR29_OFFSET 136
#define GPR30_OFFSET 140
#define GPR31_OFFSET 144
#define EXC_CR_OFFSET 148
#define EXC_CTR_OFFSET 152
#define EXC_XER_OFFSET 156
#define EXC_LR_OFFSET 160
#define EXC_MSR_OFFSET 164
#define EXC_DAR_OFFSET 168
/*
* maintain the EABI requested 8 bytes aligment
* As SVR4 ABI requires 16, make it 16 (as some
* exception may need more registers to be processed...)
*/
#define EXCEPTION_FRAME_END 176
#ifndef ASM
/*
* default raw exception handlers
*/
extern void default_exception_vector_code_prolog(void);
extern int default_exception_vector_code_prolog_size;
/* codemove is like memmove, but it also gets the cache line size
* as 4th parameter to synchronize them. If this last parameter is
* zero, it performs more or less like memmove. No copy is performed if
* source and destination addresses are equal. However the caches
* are synchronized. Note that the size is always rounded up to the
* next mutiple of 4.
*/
extern void * codemove(void *, const void *, unsigned int, unsigned long);
extern void initialize_exceptions(void);
typedef struct {
unsigned EXC_SRR0;
unsigned EXC_SRR1;
unsigned _EXC_number;
unsigned GPR0;
unsigned GPR1;
unsigned GPR2;
unsigned GPR3;
unsigned GPR4;
unsigned GPR5;
unsigned GPR6;
unsigned GPR7;
unsigned GPR8;
unsigned GPR9;
unsigned GPR10;
unsigned GPR11;
unsigned GPR12;
unsigned GPR13;
unsigned GPR14;
unsigned GPR15;
unsigned GPR16;
unsigned GPR17;
unsigned GPR18;
unsigned GPR19;
unsigned GPR20;
unsigned GPR21;
unsigned GPR22;
unsigned GPR23;
unsigned GPR24;
unsigned GPR25;
unsigned GPR26;
unsigned GPR27;
unsigned GPR28;
unsigned GPR29;
unsigned GPR30;
unsigned GPR31;
unsigned EXC_CR;
unsigned EXC_CTR;
unsigned EXC_XER;
unsigned EXC_LR;
unsigned EXC_MSR;
unsigned EXC_DAR;
}BSP_Exception_frame;
typedef void (*exception_handler_t) (BSP_Exception_frame* excPtr);
extern exception_handler_t globalExceptHdl;
/*
* Compatibility with pc386
*/
typedef BSP_Exception_frame CPU_Exception_frame;
typedef exception_handler_t cpuExcHandlerType;
#endif /* ASM */
#endif /* LIBBSP_POWERPC_MCP750_VECTORS_H */

View File

@@ -1,209 +0,0 @@
/*===============================================================*\
| Project: RTEMS generic MPC5200 BSP |
+-----------------------------------------------------------------+
| Partially based on the code references which are named below. |
| Adaptions, modifications, enhancements and any recent parts of |
| the code are: |
| Copyright (c) 2005 |
| Embedded Brains GmbH |
| Obere Lagerstr. 30 |
| D-82178 Puchheim |
| Germany |
| rtems@embedded-brains.de |
+-----------------------------------------------------------------+
| The license and distribution terms for this file may be |
| found in the file LICENSE in this distribution or at |
| |
| http://www.rtems.com/license/LICENSE. |
| |
+-----------------------------------------------------------------+
| this file contains the irq controller handler |
\*===============================================================*/
/***********************************************************************/
/* */
/* Module: vectors_init.c */
/* Date: 07/17/2003 */
/* Purpose: RTEMS exception handling initialization */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Description: This include file describe the data structure and */
/* the functions implemented by rtems to handle */
/* exceptions. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Code */
/* References: RTEMS exception handling initialization */
/* */
/* Module: vectors_init.c */
/* Project: RTEMS 4.6.0pre1 / MCF8260ads BSP */
/* Version 1.2 */
/* Date: 11/04/2002 */
/* */
/* Author(s) / Copyright(s): */
/* */
/* CopyRight (C) 1999 valette@crf.canon.fr */
/* */
/* The license and distribution terms for this file may be */
/* found in found in the file LICENSE in this distribution or at */
/* http://www.rtems.com/license/LICENSE. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Partially based on the code references which are named above. */
/* Adaptions, modifications, enhancements and any recent parts of */
/* the code are under the right of */
/* */
/* IPR Engineering, Dachauer Straße 38, D-80335 München */
/* Copyright(C) 2003 */
/* */
/*---------------------------------------------------------------------*/
/* */
/* IPR Engineering makes no representation or warranties with */
/* respect to the performance of this computer program, and */
/* specifically disclaims any responsibility for any damages, */
/* special or consequential, connected with the use of this program. */
/* */
/*---------------------------------------------------------------------*/
/* */
/* Version history: 1.0 */
/* */
/***********************************************************************/
#include "../vectors/vectors.h"
#include <libcpu/raw_exception.h>
#include <bsp.h>
#include <rtems/bspIo.h>
static rtems_raw_except_global_settings exception_config;
static rtems_raw_except_connect_data exception_table[LAST_VALID_EXC + 1];
exception_handler_t globalExceptHdl;
extern void CPU_print_stack(void);
void C_exception_handler(BSP_Exception_frame* excPtr)
{
int recoverable = 0;
printk("exception handler called for exception %d\n", excPtr->_EXC_number);
printk("\t Next PC or Address of fault = %x\n", excPtr->EXC_SRR0);
printk("\t Saved MSR = %x\n", excPtr->EXC_SRR1);
printk("\t R0 = %x\n", excPtr->GPR0);
printk("\t R1 = %x\n", excPtr->GPR1);
printk("\t R2 = %x\n", excPtr->GPR2);
printk("\t R3 = %x\n", excPtr->GPR3);
printk("\t R4 = %x\n", excPtr->GPR4);
printk("\t R5 = %x\n", excPtr->GPR5);
printk("\t R6 = %x\n", excPtr->GPR6);
printk("\t R7 = %x\n", excPtr->GPR7);
printk("\t R8 = %x\n", excPtr->GPR8);
printk("\t R9 = %x\n", excPtr->GPR9);
printk("\t R10 = %x\n", excPtr->GPR10);
printk("\t R11 = %x\n", excPtr->GPR11);
printk("\t R12 = %x\n", excPtr->GPR12);
printk("\t R13 = %x\n", excPtr->GPR13);
printk("\t R14 = %x\n", excPtr->GPR14);
printk("\t R15 = %x\n", excPtr->GPR15);
printk("\t R16 = %x\n", excPtr->GPR16);
printk("\t R17 = %x\n", excPtr->GPR17);
printk("\t R18 = %x\n", excPtr->GPR18);
printk("\t R19 = %x\n", excPtr->GPR19);
printk("\t R20 = %x\n", excPtr->GPR20);
printk("\t R21 = %x\n", excPtr->GPR21);
printk("\t R22 = %x\n", excPtr->GPR22);
printk("\t R23 = %x\n", excPtr->GPR23);
printk("\t R24 = %x\n", excPtr->GPR24);
printk("\t R25 = %x\n", excPtr->GPR25);
printk("\t R26 = %x\n", excPtr->GPR26);
printk("\t R27 = %x\n", excPtr->GPR27);
printk("\t R28 = %x\n", excPtr->GPR28);
printk("\t R29 = %x\n", excPtr->GPR29);
printk("\t R30 = %x\n", excPtr->GPR30);
printk("\t R31 = %x\n", excPtr->GPR31);
printk("\t CR = %x\n", excPtr->EXC_CR);
printk("\t CTR = %x\n", excPtr->EXC_CTR);
printk("\t XER = %x\n", excPtr->EXC_XER);
printk("\t LR = %x\n", excPtr->EXC_LR);
printk("\t MSR = %x\n", excPtr->EXC_MSR);
if(excPtr->_EXC_number == ASM_DEC_VECTOR)
recoverable = 1;
if(excPtr->_EXC_number == ASM_SYS_VECTOR)
recoverable = 1;
#if 0
#ifdef TEST_RAW_EXCEPTION_CODE
recoverable = 1;
#else
recoverable = 0;
#endif
#endif
CPU_print_stack();
if (!recoverable) {
printk("unrecoverable exception!!! Push reset button\n");
bsp_cleanup();
}
}
void nop_except_enable(const rtems_raw_except_connect_data* ptr)
{
}
int except_always_enabled(const rtems_raw_except_connect_data* ptr)
{
return 1;
}
void initialize_exceptions(void)
{
int i;
/*
* Initialize pointer used by low level execption handling
*/
globalExceptHdl = C_exception_handler;
/*
* Put default_exception_vector_code_prolog at relevant exception
* code entry addresses
*/
exception_config.exceptSize = LAST_VALID_EXC + 1;
exception_config.rawExceptHdlTbl = &exception_table[0];
exception_config.defaultRawEntry.exceptIndex = 0;
exception_config.defaultRawEntry.hdl.vector = 0;
exception_config.defaultRawEntry.hdl.raw_hdl = default_exception_vector_code_prolog;
/*
* Note that next line the '&' before default_exception_vector_code_prolog_size
* is not a bug as it is defined a .set directly in asm...
*/
exception_config.defaultRawEntry.hdl.raw_hdl_size =
(unsigned) &default_exception_vector_code_prolog_size;
for (i=0; i <= exception_config.exceptSize; i++) {
#if defined(SHOW_MORE_INIT_SETTINGS)
printk("installing exception number %d\n", i);
#endif
if (!ppc_vector_is_valid(i))
continue;
exception_table[i].exceptIndex = i;
exception_table[i].hdl = exception_config.defaultRawEntry.hdl;
exception_table[i].hdl.vector = i;
exception_table[i].on = nop_except_enable;
exception_table[i].off = nop_except_enable;
exception_table[i].isOn = except_always_enabled;
}
if (!ppc_init_exceptions(&exception_config))
BSP_panic("Exception handling initialization failed\n");
#if defined(SHOW_MORE_INIT_SETTINGS)
printk("Exception handling initialization done\n");
#endif
}