device-dependent library updates for Yocto
[keystone-rtos/fault_mgmt.git] / src / fault_mgmt.c
1 /**
2  *   @file  fault_mgmt.c
3  *
4  *   @brief   
5  *      The file implements the Fault Management library.
6  *
7  *  \par
8  *  NOTE:
9  *      (C) Copyright 2012-2015 Texas Instruments, Inc.
10  * 
11  *  Redistribution and use in source and binary forms, with or without 
12  *  modification, are permitted provided that the following conditions 
13  *  are met:
14  *
15  *    Redistributions of source code must retain the above copyright 
16  *    notice, this list of conditions and the following disclaimer.
17  *
18  *    Redistributions in binary form must reproduce the above copyright
19  *    notice, this list of conditions and the following disclaimer in the 
20  *    documentation and/or other materials provided with the   
21  *    distribution.
22  *
23  *    Neither the name of Texas Instruments Incorporated nor the names of
24  *    its contributors may be used to endorse or promote products derived
25  *    from this software without specific prior written permission.
26  *
27  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
28  *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 
29  *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
30  *  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 
31  *  OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 
32  *  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 
33  *  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
34  *  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
35  *  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 
36  *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 
37  *  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
38  *
39  */
41  
42 /**************************************************************************
43  *************************** Include Files ********************************
44  **************************************************************************/
46 /* Standard Include Files. */
47 #include <string.h>
48 #include <stdio.h>
50 /* BIOS/XDC Include Files. */
51 #include <ti/sysbios/family/c64p/Exception.h>
53 /* CSL Include Files. */
54 #include <ti/csl/csl_chip.h>
55 #include <ti/csl/csl_cacheAux.h>
56 #include <ti/csl/csl_ipcAux.h>
57 #include <ti/csl/csl_cppi.h>
58 #include <ti/csl/csl_cpsgmiiAux.h>
59 #include <ti/csl/csl_edma3Aux.h>
60 #include <ti/csl/csl_pscAux.h>
62 /* LLD Includes */
63 #include <ti/drv/cppi/cppi_drv.h>
64 #include <ti/drv/aif2/aif2.h>
66 /* FM API Include */
67 #include <ti/instrumentation/fault_mgmt/fault_mgmt.h>
69 /* FM Internal Include */
70 #include <ti/instrumentation/fault_mgmt/include/fm_loc.h>
71 #include <ti/instrumentation/fault_mgmt/include/fm_exclusionloc.h>
72 #include <ti/instrumentation/fault_mgmt/include/fm_cleanloc.h>
74 /* Fault Management OSAL File. */
75 #include <fault_mgmt_osal.h>
77 /**************************************************************************
78  ********************** Internal Data Structures **************************
79  **************************************************************************/
81 /* Note section name length in bytes (chars). */
82 #define NOTE_NAME_LEN 32
84 /* Structure specifying the ELF program header Note section header.
85  *           ELF Note Section:
86  *
87  *           byte      +0        +1       +2        +3
88  *                  +--------+--------+---------+--------+
89  *           namesz | # bytes in name field excluding pad|    
90  *                  +--------+--------+---------+--------+
91  *           descsz | # bytes in desc field excluding pad|
92  *                  +--------+--------+---------+--------+
93  *           type   |      Not Used (should be zero)     |
94  *                  +--------+--------+---------+--------+
95  *           name   | char 0 | char 1 | char 2  | char 3 |
96  *                  +--------+--------+---------+--------+
97  *                  | char 4 |  ...   | char n  |  pad   |      
98  *                  +--------+--------+---------+--------+
99  *           desc   |              word 0                |   
100  *                  +--------+--------+---------+--------+
101  *                  |              word 1                |
102  *                  +--------+--------+---------+--------+
103  */
104 typedef struct
106     uint32_t namesz;
107     uint32_t descsz;
108     uint32_t type;
109 } elfNoteHeader;
111 /**********************************************************************
112  ************************** Globals ***********************************
113  **********************************************************************/
115 #pragma DATA_ALIGN   (fault_mgmt_data, CACHE_L2_LINESIZE)
116 #pragma DATA_SECTION (fault_mgmt_data, ".note");
117 uint8_t          fault_mgmt_data[FAULT_MGMT_DATA_SIZE];
119 #if (!defined(DEVICE_K2H) && !defined(DEVICE_K2K) && \
120      !defined(DEVICE_K2L) && !defined(DEVICE_K2E))
121 /* Cache line aligned and padded */
122 #pragma DATA_ALIGN   (fmCleanupStatus, CACHE_L2_LINESIZE)
123 #pragma DATA_SECTION (fmCleanupStatus, ".fm_cleanup_status");
124 int32_t          fmCleanupStatus[32];
125 #endif /* !(K2H && K2K && K2L && K2E) */
127 /* Heap needed to initialize CPPI prior to IO halt execution */
128 uint8_t          tempCppiHeap[32000];
130 /* AIF configuration object.  Defined as global because it's a large object
131  * that may cause overflow in smaller stacks */
132 AIF_ConfigObj    localAifObj;
134 /**********************************************************************
135  ******************** External Variables ******************************
136  **********************************************************************/
138 /* CPPI Global configuration parameters */
139 extern Cppi_GlobalConfigParams cppiGblCfgParams[];
141 /**********************************************************************
142  ************************ Local Functions *****************************
143  **********************************************************************/
145 /* FUNCTION PURPOSE: Disables a given CPDMA channel
146  ***********************************************************************
147  * DESCRIPTION: Opens then disables a specified CPDMA channel
148  */
149 static void disableDmaCh(Cppi_Handle cppiHandle, int32_t dmaNum,
150                          int32_t chNum, uint32_t isRxCh)
152     Cppi_RxChInitCfg rxChCfg;
153     Cppi_TxChInitCfg txChCfg;
154     Cppi_ChHnd       chHandle;
155     uint8_t          isAllocated;
156     Cppi_Result      cppiResult;
158     if (isRxCh) {
159         memset((void *) &rxChCfg, 0, sizeof(rxChCfg));
160         rxChCfg.channelNum = chNum;
161         
162         if (chHandle = Cppi_rxChannelOpen(cppiHandle, &rxChCfg, &isAllocated)) {
163             if(cppiResult = Cppi_channelDisable(chHandle) != CPPI_SOK) {
164                 Fault_Mgmt_osalLog("IO Halt: Failed to disable cppi rx ch %d "
165                                    "with err %d\n", chNum, cppiResult);
166             }
167         } else {
168             Fault_Mgmt_osalLog("IO Halt: "
169                                "Failed to open DMA %d, RX channel %d\n",
170                                dmaNum, chNum);
171         }
172     } else {
173         memset((void *) &txChCfg, 0, sizeof(txChCfg));
174         txChCfg.channelNum = chNum;
176         if (chHandle = Cppi_txChannelOpenWithHwCfg(cppiHandle, &txChCfg,
177                                                    &isAllocated, 0)) {
178             if(cppiResult = Cppi_channelDisable(chHandle) != CPPI_SOK) {
179                 Fault_Mgmt_osalLog("IO Halt: Failed to disable cppi tx ch %d "
180                                    "with err %d\n", chNum, cppiResult);
181             }
182         } else {
183             Fault_Mgmt_osalLog("IO Halt: "
184                                "Failed to open DMA %d, TX channel %d\n",
185                                dmaNum, chNum);
186         }
187     }
190 /* FUNCTION PURPOSE: Creates the note header
191  ***********************************************************************
192  * DESCRIPTION: Creates the note header.  Only the fault data region 
193  *              size if calculated if NULL is provided for the 
194  *              fault data region pointer.
195  */
196 static uint32_t createNoteHeader(uint32_t **pFaultDataPtr)
198     elfNoteHeader  noteHeader;
199     char           elfNoteName[NOTE_NAME_LEN];
200     uint32_t       totalBytes = 0;
201     uint32_t      *locPtr = NULL;
203     if (pFaultDataPtr) {
204         locPtr = *pFaultDataPtr;
205     }
207     memset((void *)&noteHeader, 0, sizeof(noteHeader));
208     totalBytes = sizeof(noteHeader);
210     sprintf(elfNoteName, "Core%d", DNUM);
211     noteHeader.namesz = strlen(elfNoteName) + 1;
212     totalBytes += noteHeader.namesz;
213     if (locPtr) {
214         *locPtr++ = noteHeader.namesz;
215     }
216     
217     /* Calculate size of desc section.  Subtract out size of pointer to
218      * Exception_Context structure since that structure is added in entirety.
219      * Add an additional uint32_t for PC value that is added.  The PC is not
220      * tracked by the Exception Status or Context*/
221     noteHeader.descsz = (sizeof(ti_sysbios_family_c64p_Exception_Status) -
222                          sizeof(ti_sysbios_family_c64p_Exception_Context *)) +
223                         sizeof (ti_sysbios_family_c64p_Exception_Context) +
224                         sizeof (uint32_t);
225     totalBytes += noteHeader.descsz;
227     /* noteHeader type should always be 0 */
228     noteHeader.type = 0;
229     if (locPtr) {
230         *locPtr++ = noteHeader.descsz;
231         *locPtr++ = noteHeader.type;
232     }
234     if (locPtr) {
235         memcpy ((void *)locPtr, (void *)&elfNoteName[0], noteHeader.namesz);
236         locPtr += (noteHeader.namesz/sizeof(noteHeader.namesz));
237     }
238     
239     /* Account for name padding */
240     if (noteHeader.namesz % sizeof(noteHeader.namesz)) {
241         totalBytes += (sizeof(noteHeader.namesz) -
242                        (noteHeader.namesz % sizeof(noteHeader.namesz)));
243         if (locPtr) {
244             locPtr++;
245         }
246     }
248     if (locPtr) {
249         *pFaultDataPtr = locPtr;
250     }
251     return(totalBytes);
254 /**********************************************************************
255  ********************** FM-Visible Functions **************************
256  **********************************************************************/
258 /* FUNCTION PURPOSE: Checks if a wireless peripheral is powered on
259  ***********************************************************************
260  * DESCRIPTION: Checks if a wireless peripheral is powered on via the
261  *              PSC registers
262  */
263 uint32_t fmIsWirelessPeriphPoweredOnForCpdma(Cppi_CpDma dmaNum)
265 #ifndef DEVICE_K2E
266     uint32_t pwrDmnNum;
267     uint32_t moduleNum;
269     switch (dmaNum) {
270 #if (defined(DEVICE_K2H) || defined(DEVICE_K2K))
271         /* K2 devices */
272         case Cppi_CpDma_AIF_CPDMA:
273             pwrDmnNum = CSL_PSC_PD_AIF;
274             moduleNum = CSL_PSC_LPSC_AIF;
275             break;
276         case Cppi_CpDma_FFTC_A_CPDMA:
277             pwrDmnNum = CSL_PSC_PD_FFTC_01;
278             moduleNum = CSL_PSC_LPSC_FFTC_0;
279             break;
280         case Cppi_CpDma_FFTC_B_CPDMA:
281             pwrDmnNum = CSL_PSC_PD_FFTC_01;
282             moduleNum = CSL_PSC_LPSC_FFTC_1;
283             break;
284         case Cppi_CpDma_FFTC_C_CPDMA:
285             pwrDmnNum = CSL_PSC_PD_FFTC_2345;
286             moduleNum = CSL_PSC_LPSC_FFTC_2;
287             break;
288         case Cppi_CpDma_FFTC_D_CPDMA:
289             pwrDmnNum = CSL_PSC_PD_FFTC_2345;
290             moduleNum = CSL_PSC_LPSC_FFTC_3;
291             break;
292         case Cppi_CpDma_FFTC_E_CPDMA:
293             pwrDmnNum = CSL_PSC_PD_FFTC_2345;
294             moduleNum = CSL_PSC_LPSC_FFTC_4;
295             break;
296         case Cppi_CpDma_FFTC_F_CPDMA:
297             pwrDmnNum = CSL_PSC_PD_FFTC_2345;
298             moduleNum = CSL_PSC_LPSC_FFTC_5;
299             break;
300 #elif (defined(DEVICE_K2L))
301         case Cppi_CpDma_FFTC_A_CPDMA:
302             pwrDmnNum = CSL_PSC_PD_FFTC_0;
303             moduleNum = CSL_PSC_LPSC_FFTC_0;
304             break;
305 #elif (!defined(DEVICE_K2E))
306         /* Appleton */
307         case Cppi_CpDma_AIF_CPDMA:
308             pwrDmnNum = CSL_PSC_PD_AI;
309             moduleNum = CSL_PSC_LPSC_AI;
310             break;
311         case Cppi_CpDma_FFTC_A_CPDMA:
312         case Cppi_CpDma_FFTC_B_CPDMA:
313             pwrDmnNum = CSL_PSC_PD_FFTC_AB;
314             moduleNum = CSL_PSC_LPSC_FFTC_AB;
315             break;
316 #endif
317         case Cppi_CpDma_BCP_CPDMA:
318             pwrDmnNum = CSL_PSC_PD_BCP;
319             moduleNum = CSL_PSC_LPSC_BCP;
320             break;
321         default:
322             return (FM_TRUE);
323     }
325     /* Get peripheral PSC status */
326     if ((CSL_PSC_getPowerDomainState(pwrDmnNum) == PSC_PDSTATE_ON) &&
327         (CSL_PSC_getModuleState (moduleNum) == PSC_MODSTATE_ENABLE)) {
328         /* On */
329         return (FM_TRUE);
330     } else {
331         /* Off */
332         return (FM_FALSE);
333     }
334 #else
335     return (FM_TRUE);
336 #endif
339 /**********************************************************************
340  ********************** Application Visible APIs **********************
341  **********************************************************************/
343 #if (!defined(DEVICE_K2H) && !defined(DEVICE_K2K) && \
344      !defined(DEVICE_K2L) && !defined(DEVICE_K2E))
345 /* FUNCTION PURPOSE: Resets system peripherals to their power on reset state
346  ***********************************************************************
347  * DESCRIPTION: Can be called to reset system peripherals to their power on
348  *              reset state.  After a DSP local reset an application that
349  *              uses system peripherals can be loaded without fear of a 
350  *              corrupted peripheral state.
351  */
352 Fm_Result Fault_Mgmt_faultCleanup(Fm_GlobalConfigParams *fmGblCfgParams,
353                                   Fm_CleanupCfg *cleanupCfg)
355     uint32_t  numEntries;
356     int32_t   validateStatus;
357     uint32_t  fullInit = FM_TRUE;
358     Fm_Result retVal = FM_FAULT_CLEANUP_OK;
360     /* Writeback status so that Host can view it */
361     fmCleanupStatus[0] = FM_OK;
362     Fault_Mgmt_osalEndMemAccess(&fmCleanupStatus[0], sizeof(fmCleanupStatus));
364     /* Validate exclusion entries and return number of entries */
365     numEntries = fmExclusionValidateList(fmGblCfgParams,
366                                          cleanupCfg->excludedResources,
367                                          &validateStatus);
368     if (validateStatus < 0) {
369         Fault_Mgmt_osalLog("Fault Cleanup: Failed because entry %d (base 0) "
370                            "of exclusion list has invalid exResInfo field\n",
371                            numEntries);
372         retVal = validateStatus;
373         goto errorExit;
374     }
376     /* Do not do full initializtion of peripherals if there are excluded
377      * resources.  This means the peripherals have already been configured */
378     if (numEntries) {
379         fullInit = FM_FALSE;
380     }
382     /* Clean sems first since they may be used in LLD OSAL layers */
383     if ((retVal = fmCleanSemaphores(cleanupCfg->excludedResources,
384                                     numEntries)) != FM_FAULT_CLEANUP_OK) {
385         goto errorExit;
386     }
387     /* Stop all timers */
388     if ((retVal = fmCleanTimers(fmGblCfgParams, cleanupCfg->excludedResources,
389                                 numEntries)) != FM_FAULT_CLEANUP_OK) {
390         goto errorExit;
391     }
393     /* Init CPPI, QMSS, etc data structures for cleanup */
394     if ((retVal = fmCleanupInit(fullInit)) != FM_FAULT_CLEANUP_OK) {
395         goto errorExit;
396     }
398     /* Shut down all the wireless peripherals first (Expectation is any app
399      * using them will power them on at init) AIF gets cleaned first since it
400      * is the heartbeat for all wireless peripherals.  The wireless peripherals
401      * will be in an "idle" state after the AIF is cleaned */
402     if (cleanupCfg->cleanAif2) {
403         if ((retVal = fmCleanAif2()) != FM_FAULT_CLEANUP_OK) {
404             goto errorExit;
405         }
406     }
407     if (cleanupCfg->cleanTcp3d) {
408         if ((retVal = fmCleanTcp3d()) != FM_FAULT_CLEANUP_OK) {
409             goto errorExit;
410         }
411     }
412     if (cleanupCfg->cleanBcp) {
413         if ((retVal = fmCleanBcp()) != FM_FAULT_CLEANUP_OK) {
414             goto errorExit;
415         }
416     }
417     if (cleanupCfg->cleanFftc) {
418         if ((retVal = fmCleanFftc()) != FM_FAULT_CLEANUP_OK) {
419             goto errorExit;
420         }
421     }
422     if (cleanupCfg->cleanVcp) {
423         if ((retVal = fmCleanVcp()) != FM_FAULT_CLEANUP_OK) {
424             goto errorExit;
425         }
426     }
428     if (cleanupCfg->cleanCpdma) {
429         if ((retVal = fmCleanCppi(cleanupCfg->excludedResources,
430                                   numEntries)) != FM_FAULT_CLEANUP_OK) {
431             goto errorExit;
432         }
433     }
434     if (cleanupCfg->cleanEdma3) {
435         if ((retVal = fmCleanEdma3(fmGblCfgParams,
436                                    cleanupCfg->excludedResources,
437                                    numEntries,
438                                    FM_TRUE)) != FM_FAULT_CLEANUP_OK) {
439             goto errorExit;
440         }
441     }
442     if (cleanupCfg->cleanQmss) {
443         if ((retVal = fmCleanQmssQueue(fmGblCfgParams,
444                                        cleanupCfg->excludedResources,
445                                        numEntries)) != FM_FAULT_CLEANUP_OK) {
446             goto errorExit;
447         }
448     }
449     if (cleanupCfg->cleanPa) {
450         if ((retVal = fmCleanPa(fmGblCfgParams,
451                                 cleanupCfg->excludedResources,
452                                 numEntries)) != FM_FAULT_CLEANUP_OK) {
453             goto errorExit;
454         }
455     }
456     if (cleanupCfg->cleanSa) {
457         if ((retVal = fmCleanSa(cleanupCfg->excludedResources,
458                                 numEntries)) != FM_FAULT_CLEANUP_OK) {
459             goto errorExit;
460         }
461     }
462     /* Clean QMSS again in case of descriptor leakage during PA and SA
463      * cleanup */
464     if (cleanupCfg->cleanQmss) {
465         if ((retVal = fmCleanQmssQueue(fmGblCfgParams,
466                                        cleanupCfg->excludedResources,
467                                        numEntries)) != FM_FAULT_CLEANUP_OK) {
468             goto errorExit;
469         }
470     }
471     if (cleanupCfg->cleanQmss) {
472         if ((retVal = fmCleanQmssAccum(fmGblCfgParams,
473                                        cleanupCfg->excludedResources,
474                                        numEntries)) != FM_FAULT_CLEANUP_OK) {
475             goto errorExit;
476         }
477     }
478     /* Clean out all the CIC mappings after everything has been disabled */
479     if ((retVal = fmCleanCics(fmGblCfgParams, cleanupCfg->excludedResources,
480                               numEntries)) != FM_FAULT_CLEANUP_OK) {
481         goto errorExit;
482     }
483     /* Clean sems again at end to wipe fresh for application restart */
484     if ((retVal = fmCleanSemaphores(cleanupCfg->excludedResources,
485                                     numEntries)) != FM_FAULT_CLEANUP_OK) {
486         goto errorExit;
487     }
489 errorExit:
490     /* Writeback status so that Host can view it */
491     fmCleanupStatus[0] = retVal;
492     Fault_Mgmt_osalEndMemAccess(&fmCleanupStatus[0], sizeof(fmCleanupStatus));
494     return(retVal);
496 #endif /* !(K2H && K2K && K2L && K2E) */
498 /* FUNCTION PURPOSE: Halts certain IO processing mechanisms
499  ***********************************************************************
500  * DESCRIPTION: Stops hardware processing in the following IO:
501  *                  - EMDA3 DMA, QDMA, and INT channels
502  *                  - AIF PE/PD channels
503  *                  - SGMII switch
504  *                  - CPDMA tx/rx channels
505  */
506 Fm_Result Fault_Mgmt_haltIoProcessing(Fm_GlobalConfigParams *fmGblCfgParams,
507                                       Fm_HaltCfg *haltCfg)
509     uint32_t           numEntries;
510     int32_t            validateStatus;
511     Fm_ExclusionParams exclusionParams;  
512     int32_t            i, j;
513     Cppi_Result        cppiResult;
514     uint32_t           heapSize;
515     Cppi_InitCfg       cppiInitCfg;
516     Cppi_CpDmaInitCfg  dmaCfg;
517     Cppi_Handle        cppiHandle;
519     /* Validate exclusion entries and return number of entries */
520     numEntries = fmExclusionValidateList(fmGblCfgParams, 
521                                          haltCfg->excludedResources,
522                                          &validateStatus);
523     if (validateStatus < 0) {
524         Fault_Mgmt_osalLog("IO Halt: Failed because entry %d (base 0) of "
525                            "exclusion list has invalid exResInfo field\n",
526                            numEntries);
527         return(validateStatus);
528     }
530     memset(&exclusionParams, 0, sizeof(exclusionParams));
531     exclusionParams.exclusionList = haltCfg->excludedResources;
532     exclusionParams.numListEntries = numEntries;
534     if (haltCfg->haltEdma3) {
535         /* Reuse recovery function */
536         fmCleanEdma3(fmGblCfgParams, haltCfg->excludedResources, numEntries,
537                      FM_FALSE);
538     }
540     if (haltCfg->haltAif2) {
541 #if (!defined(DEVICE_K2L) && !defined(DEVICE_K2E))
542         /* Halts AIF2 peripheral resources.  Resources in the exclusion
543          * list will not be reset */
545         /* Disable all the AIF2 PE (TX) and PD (RX) channels. */
546         exclusionParams.resType = Fm_res_AifPeCh;
547         for (i = 0; i < fmGblCfgParams->maxAifPeCh; i++) {
548             exclusionParams.resourceNum = i;
549             if (!fmExclusionIsExcluded(&exclusionParams)) {
550                 AIF_disablePeCh(&localAifObj, i);
551             }
552         }
553         exclusionParams.resType = Fm_res_AifPdCh;
554         for (i = 0; i < fmGblCfgParams->maxAifPdCh; i++) {
555             exclusionParams.resourceNum = i;
556             if (!fmExclusionIsExcluded(&exclusionParams)) {
557                 AIF_disablePdCh(&localAifObj, i);
558             }
559         }
561         /* Reset the AIF2 timers */
562         AIF_resetFsync(&localAifObj);
563 #endif /* !(K2L && K2E) */
564     }
566     if (haltCfg->haltSGMII) {
567         /* Halt the RX/TX transmit logic by starting soft reset but not
568          * completing it */
569         CSL_SGMII_startRxTxSoftReset(0);
570         CSL_SGMII_startRxTxSoftReset(1);
571     }
573     if (haltCfg->haltCpdma) {
574         /* Setup CPPI */
575         cppiResult = Cppi_getHeapReq(cppiGblCfgParams, &heapSize);
576         if (sizeof(tempCppiHeap) < heapSize) {
577             Fault_Mgmt_osalLog("IO Halt: Temp heap needed to initalize CPPI is "
578                                "too small");
579         }
580         cppiInitCfg.heapParams.staticHeapBase = &tempCppiHeap[0];
581         cppiInitCfg.heapParams.staticHeapSize = heapSize;
582         cppiInitCfg.heapParams.heapAlignPow2  = 8;
583         cppiInitCfg.heapParams.dynamicHeapBlockSize = -1;
585         cppiResult = Cppi_initCfg(cppiGblCfgParams, &cppiInitCfg);
586         if (cppiResult != CPPI_SOK) {
587             Fault_Mgmt_osalLog("IO Halt: Failed CPPI init\n");
588             return(FM_ERROR_CPPI_INIT_FAILED);
589         }
591         memset(&exclusionParams, 0, sizeof(exclusionParams));
592         exclusionParams.exclusionList = haltCfg->excludedResources;
593         exclusionParams.numListEntries = numEntries;
594         
595         /* Disable CPPI channels */
596         for (i = 0; i < CPPI_MAX_CPDMA; i++) {
597             if (fmIsWirelessPeriphPoweredOnForCpdma((Cppi_CpDma) i)) {
598                 memset ((void *) &dmaCfg, 0, sizeof(dmaCfg));
599                 dmaCfg.dmaNum = (Cppi_CpDma) i;
601                 if (cppiHandle = Cppi_open(&dmaCfg)) {
602                     exclusionParams.u.cpdmaParams.dma = dmaCfg.dmaNum;
603                     exclusionParams.resType = Fm_res_CpdmaRxCh;
604                     for (j = 0; j < fmGetDmaMaxRxCh(dmaCfg.dmaNum); j++) {
605                         exclusionParams.resourceNum = j;
606                         if (!fmExclusionIsExcluded(&exclusionParams)) {
607                             disableDmaCh(cppiHandle, i, j, 1);
608                         }
609                     }
611                     exclusionParams.resType = Fm_res_CpdmaTxCh;
612                     for (j = 0; j < fmGetDmaMaxTxCh(dmaCfg.dmaNum); j++) {
613                         exclusionParams.resourceNum = j;
614                         if (!fmExclusionIsExcluded(&exclusionParams)) {
615                             disableDmaCh(cppiHandle, i, j, 0);
616                         }
617                     }
618                 }
619             }
620         }
621     }
623     return(FM_OK);
626 /* FUNCTION PURPOSE: Gets and stores the system register status
627  ***********************************************************************
628  * DESCRIPTION: Gets the system register status and stores it in the
629  *              fault management data region.
630  */
631 void Fault_Mgmt_getLastRegStatus(void)
633     Exception_Status  status;
634     uint32_t         *faultDataPtr = (uint32_t *)&fault_mgmt_data[0];
636     /* Make sure note section fits within the provided fault data region */
637     if (Fault_Mgmt_getSizes() > FAULT_MGMT_DATA_SIZE) {
638         Fault_Mgmt_osalLog("Get Last Reg Status: Failed - ELF Note data "
639                            "section is %d bytes.  Need %d bytes.\n",
640                            FAULT_MGMT_DATA_SIZE, Fault_Mgmt_getSizes());
641         return;
642     }
644     memset((void *)faultDataPtr, 0, FAULT_MGMT_DATA_SIZE);
646     createNoteHeader(&faultDataPtr);
648     /* Get the register status for the core dump. */
649     Exception_getLastStatus (&status);
651     /* Copy the execution context to fault management data memory and update
652      * number of bytes in the Note section. */
654     /* The very first data value in the "desc" field is the PC for the crash
655      * dump.  The PC value should correspond to the NMI return pointer that was
656      * stored in the NRP register when the DSP exception triggered the
657      * exception handler which runs in the NMI context */
658     *faultDataPtr++ = status.nrp;
660     *faultDataPtr++ = status.efr;
661     *faultDataPtr++ = status.nrp;
662     *faultDataPtr++ = status.ntsr;
663     /* Copy IERR from exception context to the status value.  According to the
664      * exception module it's tracked in two places.  However, it is only
665      * updated in one of them.  To avoid confusion on the host side when the
666      * fault is reported the valid value in the exception context is copied to
667      * the invalid value in the status context */
668     status.ierr = (uint32_t) status.excContext->IERR;
669     *faultDataPtr++ = status.ierr;
670     memcpy((void *)faultDataPtr, (void *)status.excContext,
671            sizeof(ti_sysbios_family_c64p_Exception_Context));
673     Fault_Mgmt_osalEndMemAccess(&fault_mgmt_data[0], FAULT_MGMT_DATA_SIZE);
675     return;
678 /* FUNCTION PURPOSE: Notifies Host of DSP fault
679  ***********************************************************************
680  * DESCRIPTION: Sends a notification to the Host via the IPC registers
681  *              that a certain DSP has encountered an exception.
682  */
683 void Fault_Mgmt_notify(void)
685     CSL_IPC_genHostInterrupt(FM_HOST_IPCGR_OFFSET + DNUM);
686     return;
689 /* FUNCTION PURPOSE: Notifies remote DSP core of DSP fault
690  ***********************************************************************
691  * DESCRIPTION: Sends a notification to a remote DSP core via the IPC
692  *              registers that a certain DSP has encountered an exception.
693  */
694 void Fault_Mgmt_notify_remote_core(uint32_t core_id)
696     CSL_IPC_genNMIEvent(core_id);
697     return;
700 /* FUNCTION PURPOSE: Returns the required fault management data region size
701  ***********************************************************************
702  * DESCRIPTION: Returns the required size of the fault management data
703  *              region containing the crash dump data.
704  */
705 uint32_t Fault_Mgmt_getSizes(void)
707     return(createNoteHeader(NULL));
710 /**
711 @}
712 */