wdbExcLib.c
上传用户:nvosite88
上传日期:2007-01-17
资源大小:4983k
文件大小:5k
源码类别:

VxWorks

开发平台:

C/C++

  1. /* wdbExcLib.c - handles exceptions */
  2. /* Copyright 1995-2001 Wind River Systems, Inc. */
  3. /*
  4. modification history
  5. --------------------
  6. 01c,14sep01,jhw  Fixed warnings from compiling with gnu -pedantic flag
  7. 01b,22may95,ms Only suspend the system if the agent is in system mode.
  8. 01a,14feb95,ms  written.
  9. */
  10. /*
  11. DESCPRIPTION
  12. This library handles the reporting of exceptions to the host.
  13. If multiple tasks have exceptions before the host uploads the info,
  14. then the exception events are queued.
  15. A maximum of five exception events can be queued at a time.
  16. */
  17. #include "wdb/wdb.h"
  18. #include "wdb/wdbLibP.h"
  19. #include "wdb/dll.h"
  20. #include "wdb/wdbSvcLib.h"
  21. #include "wdb/wdbRtIfLib.h"
  22. #include "wdb/wdbEvtLib.h"
  23. #include "wdb/wdbArchIfLib.h"
  24. /* definitions */
  25. #define MAX_EXC_EVENTS 5 /* max of 5 exception events at once */
  26. /* structures */
  27. typedef struct
  28.     {
  29.     dll_t node;
  30.     BOOL valid;
  31.     WDB_CTX context;
  32.     u_int excVector;
  33.     char * pESF;
  34.     } wdbExcInfoNode_t;
  35. /* local variables */
  36. static WDB_EVT_NODE wdbExcEvtNode;
  37. static dll_t wdbExcEvtList;
  38. static wdbExcInfoNode_t excInfoNode [MAX_EXC_EVENTS];
  39. /* forward declarations */
  40. static void wdbExcHook (WDB_CTX context, u_int vec, char *pESF, WDB_IU_REGS *);
  41. static void wdbExcGetEvent (void *arg, WDB_EVT_DATA *pEvtMsg);
  42. static void wdbExcDeqEvent (void *arg);
  43. /******************************************************************************
  44. *
  45. * wdbExcLibInit -
  46. */
  47. void wdbExcLibInit (void)
  48.     {
  49.     int ix;
  50.     /* initialize our event node */
  51.     wdbEventNodeInit (&wdbExcEvtNode, wdbExcGetEvent,
  52. wdbExcDeqEvent, NULL);
  53.     /* initialize the linked list of exceptions */
  54.     dll_init (&wdbExcEvtList);
  55.     for (ix = 0; ix < MAX_EXC_EVENTS; ix++)
  56. dll_insert (&excInfoNode[ix].node, &wdbExcEvtList);
  57.     /* add our exception hook to the run-time exception handler */
  58.     (*pWdbRtIf->excHookAdd)(wdbExcHook);
  59.     }
  60. /******************************************************************************
  61. *
  62. * wdbExcHook -
  63. */
  64. static void wdbExcHook
  65.     (
  66.     WDB_CTX context,
  67.     u_int vec,
  68.     char * pESF,
  69.     WDB_IU_REGS * pRegs
  70.     )
  71.     {
  72.     wdbExcInfoNode_t * pExcInfoNode;
  73.     int lockKey;
  74.     /* get a node off the queue */
  75.     lockKey = intLock();
  76.     pExcInfoNode = (wdbExcInfoNode_t *)dll_tail (&wdbExcEvtList);
  77.     /* if event list if full and this is a task exception, just return */
  78.     if ((pExcInfoNode->valid) && (context.contextType == WDB_CTX_TASK))
  79. {
  80. intUnlock (lockKey);
  81. return;
  82. }
  83.     pExcInfoNode->valid     = TRUE;
  84.     pExcInfoNode->context   = context;
  85.     pExcInfoNode->excVector = vec;
  86.     pExcInfoNode->pESF     = pESF;
  87.     dll_remove (&pExcInfoNode->node);
  88.     dll_insert (&pExcInfoNode->node, &wdbExcEvtList);
  89.     intUnlock (lockKey);
  90.     /* exception in task context */
  91.     if (wdbIsNowTasking())
  92. {
  93. wdbEventPost (&wdbExcEvtNode);
  94. return;
  95. }
  96.     /* exception in system context - suspend system before posting event */
  97.     wdbSuspendSystem (pRegs, wdbEventPost, (int)&wdbExcEvtNode);
  98.     /* NOTREACHED */
  99.     }
  100. /******************************************************************************
  101. *
  102. * wdbExcGetEvent - upload the exception event to the host.
  103. */
  104. void wdbExcGetEvent
  105.     (
  106.     void * arg,
  107.     WDB_EVT_DATA * pEvtData
  108.     )
  109.     {
  110.     wdbExcInfoNode_t * pNode;
  111.     wdbExcInfoNode_t * pTmpNode;
  112.     WDB_EXC_INFO * pExcInfo;
  113.     int lockKey;
  114.     /* get a node from the exception queue */
  115.     lockKey = intLock();
  116.     pNode   = (wdbExcInfoNode_t *) dll_head (&wdbExcEvtList);
  117.     dll_remove (&pNode->node);
  118.     intUnlock (lockKey);
  119.     /* give the node info to the host */
  120.     pExcInfo = (WDB_EXC_INFO *)&pEvtData->eventInfo;
  121.     pEvtData->evtType = WDB_EVT_EXC;
  122.     pExcInfo->numInts = 4;
  123.     pExcInfo->context = pNode->context;
  124.     pExcInfo->vec = pNode->excVector;
  125.     pExcInfo->pEsf = (TGT_ADDR_T) pNode->pESF;
  126.     /* mark the node invalid and put back in queue (after valid nodes) */
  127.     pNode->valid = FALSE;
  128.     lockKey = intLock();
  129.     for (pTmpNode =  (wdbExcInfoNode_t *) dll_head (&wdbExcEvtList);
  130.  pTmpNode != (wdbExcInfoNode_t *) dll_end  (&wdbExcEvtList);
  131.  pTmpNode =  (wdbExcInfoNode_t *) dll_next (&pTmpNode->node))
  132. {
  133. if (pTmpNode->valid == FALSE)
  134.     break;
  135. }
  136.     pTmpNode = (wdbExcInfoNode_t *) dll_prev (&pTmpNode->node);
  137.     dll_insert (&pNode->node, &pTmpNode->node);
  138.     intUnlock (lockKey);
  139.     }
  140. /******************************************************************************
  141. *
  142. * wdbExcDeqEvent - dequeue the event node.
  143. */
  144. void wdbExcDeqEvent
  145.     (
  146.     void *arg
  147.     )
  148.     {
  149.     int lockKey;
  150.     wdbExcInfoNode_t * pNode;
  151.     lockKey = intLock();
  152.     pNode = (wdbExcInfoNode_t *) dll_head (&wdbExcEvtList);
  153.     if (pNode->valid)
  154. {
  155. intUnlock (lockKey);
  156. wdbEventPost (&wdbExcEvtNode);
  157. return;
  158. }
  159.     intUnlock (lockKey);
  160.     }