Back to home page

LXR

 
 

    


File indexing completed on 2025-05-11 08:23:58

0001 /**
0002  * @file
0003  *
0004  * @ingroup ppc_exc
0005  *
0006  * @brief PowerPC Exceptions implementation.
0007  */
0008 
0009 /*
0010  * Copyright (C) 1999 Eric Valette (valette@crf.canon.fr)
0011  *                    Canon Centre Recherche France.
0012  *
0013  * Copyright (C) 2009, 2011 embedded brains GmbH & Co. KG
0014  *
0015  * Enhanced by Jay Kulpinski <jskulpin@eng01.gdds.com>
0016  * to support 603, 603e, 604, 604e exceptions
0017  *
0018  * Moved to "libcpu/powerpc/new-exceptions" and consolidated
0019  * by Thomas Doerfler <Thomas.Doerfler@embedded-brains.de>
0020  * to be common for all PPCs with new exceptions.
0021  *
0022  * Derived from file "libcpu/powerpc/new-exceptions/raw_exception.c".
0023  *
0024  * The license and distribution terms for this file may be
0025  * found in the file LICENSE in this distribution or at
0026  * http://www.rtems.org/license/LICENSE.
0027  */
0028 
0029 #include <bsp/vectors.h>
0030 
0031 #define PPC_BASIC_VECS_WO_SYS \
0032   [ASM_RESET_VECTOR] = PPC_EXC_CLASSIC, \
0033   [ASM_MACH_VECTOR] = PPC_EXC_CLASSIC, \
0034   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC, \
0035   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC, \
0036   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC, \
0037   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC, \
0038   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC, \
0039   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC, \
0040   [ASM_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC, \
0041   [ASM_TRACE_VECTOR] = PPC_EXC_CLASSIC
0042 
0043 #define PPC_BASIC_VECS \
0044     PPC_BASIC_VECS_WO_SYS, \
0045     [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC
0046 
0047 static const ppc_exc_categories ppc_405_category_table = {
0048   [ASM_BOOKE_CRIT_VECTOR] = PPC_EXC_405_CRITICAL | PPC_EXC_ASYNC,
0049   [ASM_MACH_VECTOR] = PPC_EXC_405_CRITICAL,
0050   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC,
0051   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC,
0052   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0053   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0054   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0055   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC,
0056 
0057   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0058 
0059   [ASM_PPC405_APU_UNAVAIL_VECTOR] = PPC_EXC_CLASSIC,
0060 
0061   [ASM_BOOKE_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0062   [ASM_BOOKE_FIT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0063   [ASM_BOOKE_WDOG_VECTOR] = PPC_EXC_405_CRITICAL | PPC_EXC_ASYNC,
0064   [ASM_BOOKE_DTLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0065   [ASM_BOOKE_ITLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0066   [ASM_TRACE_VECTOR] = PPC_EXC_405_CRITICAL,
0067 };
0068 
0069 static const ppc_exc_categories ppc_booke_category_table = {
0070   [ASM_BOOKE_CRIT_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0071   [ASM_MACH_VECTOR] = PPC_EXC_E500_MACHCHK,
0072   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC,
0073   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC,
0074   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0075   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0076   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0077   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC,
0078   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0079   [ASM_BOOKE_APU_VECTOR] = PPC_EXC_CLASSIC,
0080   [ASM_BOOKE_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0081   [ASM_BOOKE_FIT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0082   [ASM_BOOKE_WDOG_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0083   [ASM_BOOKE_DTLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0084   [ASM_BOOKE_ITLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0085   [ASM_BOOKE_DEBUG_VECTOR] = PPC_EXC_BOOKE_CRITICAL,
0086 };
0087 
0088 static const ppc_exc_categories mpc_5xx_category_table = {
0089   [ASM_RESET_VECTOR] = PPC_EXC_CLASSIC,
0090   [ASM_MACH_VECTOR] = PPC_EXC_CLASSIC,
0091   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0092   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0093   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0094   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC,
0095   [ASM_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0096   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0097   [ASM_TRACE_VECTOR] = PPC_EXC_CLASSIC,
0098 
0099   [ASM_5XX_FLOATASSIST_VECTOR] = PPC_EXC_CLASSIC,
0100   [ASM_5XX_SOFTEMUL_VECTOR] = PPC_EXC_CLASSIC,
0101   [ASM_5XX_IPROT_VECTOR] = PPC_EXC_CLASSIC,
0102   [ASM_5XX_DPROT_VECTOR] = PPC_EXC_CLASSIC,
0103   [ASM_5XX_DBREAK_VECTOR] = PPC_EXC_CLASSIC,
0104   [ASM_5XX_IBREAK_VECTOR] = PPC_EXC_CLASSIC,
0105   [ASM_5XX_MEBREAK_VECTOR] = PPC_EXC_CLASSIC,
0106   [ASM_5XX_NMEBREAK_VECTOR] = PPC_EXC_CLASSIC,
0107 };
0108 
0109 static const ppc_exc_categories mpc_603_category_table = {
0110   PPC_BASIC_VECS,
0111 
0112   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0113   [ASM_60X_IMISS_VECTOR] = PPC_EXC_CLASSIC,
0114   [ASM_60X_DLMISS_VECTOR] = PPC_EXC_CLASSIC,
0115   [ASM_60X_DSMISS_VECTOR] = PPC_EXC_CLASSIC,
0116   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0117 };
0118 
0119 static const ppc_exc_categories mpc_604_category_table = {
0120   PPC_BASIC_VECS,
0121 
0122   [ASM_60X_PERFMON_VECTOR] = PPC_EXC_CLASSIC,
0123   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0124   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0125 };
0126 
0127 static const ppc_exc_categories mpc_604_altivec_category_table = {
0128   PPC_BASIC_VECS,
0129 
0130   [ASM_60X_PERFMON_VECTOR] = PPC_EXC_CLASSIC,
0131   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0132   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0133   [ASM_60X_VEC_VECTOR] = PPC_EXC_CLASSIC,
0134   [ASM_60X_VEC_ASSIST_VECTOR] = PPC_EXC_CLASSIC,
0135 };
0136 
0137 static const ppc_exc_categories mpc_750_category_table = {
0138   PPC_BASIC_VECS,
0139 
0140   [ASM_60X_PERFMON_VECTOR] = PPC_EXC_CLASSIC,
0141   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0142   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0143   [ASM_60X_ITM_VECTOR] = PPC_EXC_CLASSIC,
0144 };
0145 
0146 static const ppc_exc_categories mpc_750_altivec_category_table = {
0147   PPC_BASIC_VECS,
0148 
0149   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0150   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0151   [ASM_60X_ITM_VECTOR] = PPC_EXC_CLASSIC,
0152   [ASM_60X_VEC_VECTOR] = PPC_EXC_CLASSIC,
0153   [ASM_60X_VEC_ASSIST_VECTOR] = PPC_EXC_CLASSIC,
0154 };
0155 
0156 static const ppc_exc_categories mpc_860_category_table = {
0157   PPC_BASIC_VECS,
0158 
0159   [ASM_8XX_FLOATASSIST_VECTOR] = PPC_EXC_CLASSIC,
0160   [ASM_8XX_SOFTEMUL_VECTOR] = PPC_EXC_CLASSIC,
0161   [ASM_8XX_ITLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0162   [ASM_8XX_DTLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0163   [ASM_8XX_ITLBERROR_VECTOR] = PPC_EXC_CLASSIC,
0164   [ASM_8XX_DTLBERROR_VECTOR] = PPC_EXC_CLASSIC,
0165   [ASM_8XX_DBREAK_VECTOR] = PPC_EXC_CLASSIC,
0166   [ASM_8XX_IBREAK_VECTOR] = PPC_EXC_CLASSIC,
0167   [ASM_8XX_PERIFBREAK_VECTOR] = PPC_EXC_CLASSIC,
0168   [ASM_8XX_DEVPORT_VECTOR] = PPC_EXC_CLASSIC,
0169 };
0170 
0171 static const ppc_exc_categories e300_category_table = {
0172   [ASM_RESET_VECTOR] = PPC_EXC_CLASSIC,
0173   [ASM_MACH_VECTOR] = PPC_EXC_CLASSIC,
0174   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC,
0175   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC,
0176   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0177   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0178   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0179   [ASM_FLOAT_VECTOR] = PPC_EXC_NAKED,
0180   [ASM_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0181   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0182   [ASM_TRACE_VECTOR] = PPC_EXC_CLASSIC,
0183 
0184   [ASM_E300_CRIT_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0185   [ASM_E300_PERFMON_VECTOR] = PPC_EXC_CLASSIC,
0186   [ASM_E300_IMISS_VECTOR] = PPC_EXC_CLASSIC,
0187   [ASM_E300_DLMISS_VECTOR] = PPC_EXC_CLASSIC,
0188   [ASM_E300_DSMISS_VECTOR] = PPC_EXC_CLASSIC,
0189   [ASM_E300_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0190   [ASM_E300_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0191 };
0192 
0193 static const ppc_exc_categories e200_category_table = {
0194   [ASM_BOOKE_CRIT_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0195   [ASM_MACH_VECTOR] = PPC_EXC_BOOKE_CRITICAL,
0196   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC,
0197   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC,
0198   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0199   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0200   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0201   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC,
0202   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0203   [ASM_BOOKE_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0204   [ASM_BOOKE_FIT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0205   [ASM_BOOKE_WDOG_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0206   [ASM_BOOKE_DTLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0207   [ASM_BOOKE_ITLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0208 
0209   /* FIXME: Depending on HDI0 [DAPUEN] this is a critical or debug exception */
0210   [ASM_BOOKE_DEBUG_VECTOR] = PPC_EXC_BOOKE_CRITICAL,
0211 
0212   [ASM_E500_SPE_UNAVAILABLE_VECTOR] = PPC_EXC_CLASSIC,
0213   [ASM_E500_EMB_FP_DATA_VECTOR] = PPC_EXC_CLASSIC,
0214   [ASM_E500_EMB_FP_ROUND_VECTOR] = PPC_EXC_CLASSIC
0215 };
0216 
0217 static const ppc_exc_categories e500_category_table = {
0218   [ASM_BOOKE_CRIT_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0219   [ASM_MACH_VECTOR] = PPC_EXC_E500_MACHCHK,
0220   [ASM_PROT_VECTOR] = PPC_EXC_CLASSIC,
0221   [ASM_ISI_VECTOR] = PPC_EXC_CLASSIC,
0222   [ASM_EXT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0223   [ASM_ALIGN_VECTOR] = PPC_EXC_CLASSIC,
0224   [ASM_PROG_VECTOR] = PPC_EXC_CLASSIC,
0225   [ASM_FLOAT_VECTOR] = PPC_EXC_CLASSIC,
0226   [ASM_SYS_VECTOR] = PPC_EXC_CLASSIC,
0227   [ASM_BOOKE_APU_VECTOR] = PPC_EXC_CLASSIC,
0228   [ASM_BOOKE_DEC_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0229   [ASM_BOOKE_FIT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0230   [ASM_BOOKE_WDOG_VECTOR] = PPC_EXC_BOOKE_CRITICAL | PPC_EXC_ASYNC,
0231   [ASM_BOOKE_DTLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0232   [ASM_BOOKE_ITLBMISS_VECTOR] = PPC_EXC_CLASSIC,
0233   [ASM_BOOKE_DEBUG_VECTOR] = PPC_EXC_BOOKE_CRITICAL,
0234   [ASM_E500_SPE_UNAVAILABLE_VECTOR] = PPC_EXC_CLASSIC,
0235   [ASM_E500_EMB_FP_DATA_VECTOR] = PPC_EXC_CLASSIC,
0236   [ASM_E500_EMB_FP_ROUND_VECTOR] = PPC_EXC_CLASSIC,
0237   [ASM_E500_PERFMON_VECTOR] = PPC_EXC_CLASSIC
0238 };
0239 
0240 static const ppc_exc_categories psim_category_table = {
0241   PPC_BASIC_VECS_WO_SYS,
0242 
0243   [ASM_60X_SYSMGMT_VECTOR] = PPC_EXC_CLASSIC | PPC_EXC_ASYNC,
0244   [ASM_60X_IMISS_VECTOR] = PPC_EXC_CLASSIC,
0245   [ASM_60X_DLMISS_VECTOR] = PPC_EXC_CLASSIC,
0246   [ASM_60X_DSMISS_VECTOR] = PPC_EXC_CLASSIC,
0247   [ASM_60X_ADDR_VECTOR] = PPC_EXC_CLASSIC,
0248   [ASM_60X_VEC_VECTOR] = PPC_EXC_CLASSIC,
0249   [ASM_60X_VEC_ASSIST_VECTOR] = PPC_EXC_CLASSIC,
0250 };
0251 
0252 const ppc_exc_categories *ppc_exc_categories_for_cpu(ppc_cpu_id_t cpu)
0253 {
0254   if (ppc_cpu_has_altivec()) {
0255     switch (cpu) {
0256       case PPC_7400:
0257         return &mpc_750_altivec_category_table;
0258       case PPC_7455:
0259       case PPC_7457:
0260         return &mpc_604_altivec_category_table;
0261       default:
0262         break;
0263     }
0264   }
0265 
0266   switch (cpu) {
0267     case PPC_7400:
0268     case PPC_750:
0269     case PPC_750_IBM:
0270       return &mpc_750_category_table;
0271     case PPC_7455:
0272     case PPC_7457:
0273     case PPC_604:
0274     case PPC_604e:
0275     case PPC_604r:
0276       return &mpc_604_category_table;
0277     case PPC_603:
0278     case PPC_603e:
0279     case PPC_603le:
0280     case PPC_603ev:
0281     /* case PPC_8240: same value as 8260 */
0282     case PPC_8260:
0283     case PPC_8245:
0284       return &mpc_603_category_table;
0285     case PPC_e300c1:
0286     case PPC_e300c2:
0287     case PPC_e300c3:
0288       return &e300_category_table;
0289     case PPC_PSIM:
0290       return &psim_category_table;
0291     case PPC_8540:
0292     case PPC_e500v2:
0293     case PPC_e6500:
0294       return &e500_category_table;
0295     case PPC_e200z0:
0296     case PPC_e200z1:
0297     case PPC_e200z4:
0298     case PPC_e200z6:
0299     case PPC_e200z7:
0300       return &e200_category_table;
0301     case PPC_5XX:
0302       return &mpc_5xx_category_table;
0303     case PPC_860:
0304       return &mpc_860_category_table;
0305     case PPC_405:
0306     case PPC_405GP:
0307     case PPC_405EX:
0308       return &ppc_405_category_table;
0309     case PPC_440:
0310       return &ppc_booke_category_table;
0311     default:
0312       break;
0313   }
0314 
0315   return NULL;
0316 }
0317 
0318 ppc_exc_category ppc_exc_category_for_vector(const ppc_exc_categories *categories, unsigned vector)
0319 {
0320   if (vector <= LAST_VALID_EXC) {
0321     return (*categories) [vector];
0322   } else {
0323     return PPC_EXC_INVALID;
0324   }
0325 }