/*
**************************************************************************
*
* Component =
*
* Synopsis = rdbg/m68k/excep_f.c
*
* $Id$
*
**************************************************************************
*/
#include <rtems.h>
#include <rtems/error.h>
#include <assert.h>
#include <errno.h>
#include <rdbg/rdbg.h>
#include <rdbg/servrpc.h>
int
ExcepToSig (Exception_context * ctx)
{
int excep = getExcNum (ctx);
switch (excep) {
case 2:
return 10;
break; /* bus error */
case 3:
return 10;
break; /* address error */
case 4:
return 4;
break; /* illegal instruction */
case 5:
return 8;
break; /* zero divide */
case 6:
return 8;
break; /* chk instruction */
case 7:
return 8;
break; /* trapv instruction */
case 8:
return 11;
break; /* privilege violation */
case 9:
return 5;
break; /* trace trap */
case 10:
return 4;
break; /* line 1010 emulator */
case 11:
return 4;
break; /* line 1111 emulator */
/*
* Coprocessor protocol violation. Using a standard MMU or FPU
* this cannot be triggered by software. Call it a SIGBUS.
*/
case 13:
return 10;
break;
case 31:
return 2;
break; /* interrupt */
case 33:
return 5;
break; /* monitor breakpoint */
case 34:
return 2;
break; /* lets use this for SCC1 interrupt */
case 35:
return 5;
break; /* rdbg breakpoint */
case 36:
return 2;
break; /* enter RDBG */
/*
* This is a trap #8 instruction. Apparently it is someone's software
* convention for some sort of SIGFPE condition. Whose? How many
* people are being screwed by having this code the way it is?
* Is there a clean solution?
*/
case 40:
return 8;
break; /* floating point err */
case 47:
return 5;
break; /* rdbg breakpoint */
case 48:
return 8;
break; /* floating point err */
case 49:
return 8;
break; /* floating point err */
case 50:
return 8;
break; /* zero divide */
case 51:
return 8;
break; /* underflow */
case 52:
return 8;
break; /* operand error */
case 53:
return 8;
break; /* overflow */
case 54:
return 8;
break; /* NAN */
default:
return 7; /* "software generated" */
}
return SIGKILL;
}
/*----- Breakpoint Exception management -----*/
/*
* Handler for Breakpoint Exceptions :
* software breakpoints.
*/
void
BreakPointExcHdl (CPU_Exception_frame * ctx)
{
rtems_status_code status;
rtems_id continueSemId;
connect_rdbg_exception (); /* monitor stub changes trace vector */
if ((justSaveContext) && (ctx->vecnum == 47)) { /* break */
PushSavedExceptCtx (_Thread_Executing->Object.id, ctx);
justSaveContext = 0;
} else {
if (ctx->vecnum != 9) { /* trace */
NbSerializedCtx++;
rtems_semaphore_obtain (serializeSemId, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
NbSerializedCtx--;
}
currentTargetThread = _Thread_Executing->Object.id;
#ifdef DDEBUG
printk ("----------------------------------------------------------\n");
printk ("Exception %d caught at PC %x by thread %d\n",
ctx->vecnum, ctx->pc, _Thread_Executing->Object.id);
printk ("----------------------------------------------------------\n");
printk ("Processor execution context at time of the fault was :\n");
printk ("----------------------------------------------------------\n");
printk ("\t A0 = %x\n", ctx->a0);
printk ("\t A1 = %x\n", ctx->a1);
printk ("\t A2 = %x\n", ctx->a2);
printk ("\t A3 = %x\n", ctx->a3);
printk ("\t A4 = %x\n", ctx->a4);
printk ("\t A5 = %x\n", ctx->a5);
printk ("\t A6 = %x\n", ctx->a6);
printk ("\t A7 = %x\n", ctx->a7);
printk ("\t D0 = %x\n", ctx->d0);
printk ("\t D1 = %x\n", ctx->d1);
printk ("\t D2 = %x\n", ctx->d2);
printk ("\t D3 = %x\n", ctx->d3);
printk ("\t D4 = %x\n", ctx->d4);
printk ("\t D5 = %x\n", ctx->d5);
printk ("\t D6 = %x\n", ctx->d6);
printk ("\t D7 = %x\n", ctx->d7);
printk ("\t SR = %x\n", ctx->sr);
#endif
status = rtems_semaphore_create (rtems_build_name ('D', 'B', 'G', 'c'),
0,
RTEMS_FIFO |
RTEMS_COUNTING_SEMAPHORE |
RTEMS_NO_INHERIT_PRIORITY |
RTEMS_NO_PRIORITY_CEILING |
RTEMS_LOCAL, 0, &continueSemId);
if (status != RTEMS_SUCCESSFUL)
rtems_panic ("Can't create continue semaphore: `%s'\n",
rtems_status_text (status));
PushExceptCtx (_Thread_Executing->Object.id, continueSemId, ctx);
switch (ctx->vecnum) {
case 9: /* trace */
DPRINTF ((" TRACE EXCEPTION !!!\n"));
ctx->sr &= ~(1 << 15);
ExitForSingleStep--;
rtems_semaphore_release (wakeupEventSemId);
break;
case 47: /* trap #15 */
DPRINTF ((" BREAKPOINT EXCEPTION !!!\n"));
rtems_semaphore_release (wakeupEventSemId);
break;
case 36: /* trap #4 */
DPRINTF ((" ENTER RDBG !!!\n"));
rtems_semaphore_release (wakeupEventSemId);
break;
default:
DPRINTF ((" OTHER EXCEPTION !!!\n"));
rtems_semaphore_release (wakeupEventSemId);
break;
}
rtems_semaphore_obtain (continueSemId, RTEMS_WAIT, RTEMS_NO_TIMEOUT);
PopExceptCtx (_Thread_Executing->Object.id);
rtems_semaphore_delete (continueSemId);
}
connect_rdbg_exception (); /* monitor stub changes trace vector */
}