Add support for instruction level tracing to the ARM simulator.
authorNick Clifton <nickc@redhat.com>
Fri, 14 Mar 2014 15:21:23 +0000 (15:21 +0000)
committerNick Clifton <nickc@redhat.com>
Fri, 14 Mar 2014 15:21:23 +0000 (15:21 +0000)
* wrapper.c (op_print): New function.
(sim_dis_read): New function.
(print_insn): New function - disassembles the given instruction.
(sim_trace): Note that tracing is now allowed.
(sim_create_inferior): Default to emulating v6.
Initialise the disassembler machinery.
(sim_target_parse_command_line): Add support for -t -d and -z
options.
(sim_target_display_usage): Note existence of -d and -z options.
(sim_open): Parse -t -d and -z options.
* armemu.h: Add exports of trace, disas and trace_funcs.
Add prototype for print_insn.
* armemu.c (ARMul_Emulate26): Add tracing code.
Delete unused variables.
* thumbemu (handle_v6_thumb_insn): Delete unused variable Rd.
Move Rm variable into switch cases.
Add tracing code.

* armcopro.c (XScale_cp15_init): Add a return value.
(XScale_cp13_init): Likewise.
(XScale_cp14_init): Likewise.
(XScale_cp15_LDC): Delete unused function.
(XScale_cp15_STC): Likewise.
* maverick.c: Delete comment inside comment.
(DSPInit): Delete unused function.
(DSPMCR4): Fix compile time warning about missing parenthesis.
(DSPMCR5): Likewise.
(DSPCDP6): Delete unused variable opcode2.

sim/arm/ChangeLog
sim/arm/armcopro.c
sim/arm/armemu.c
sim/arm/armemu.h
sim/arm/maverick.c
sim/arm/thumbemu.c
sim/arm/wrapper.c

index fe236cbc5ff2c857c7cbe5641e3f3690ff31e242..89f0531053537a700def455b24cc01fbf26745e0 100644 (file)
@@ -1,3 +1,34 @@
+2014-03-14  Nick Clifton  <nickc@redhat.com>
+
+       * wrapper.c (op_print): New function.
+       (sim_dis_read): New function.
+       (print_insn): New function - disassembles the given instruction.
+       (sim_trace): Note that tracing is now allowed.
+       (sim_create_inferior): Default to emulating v6.
+       Initialise the disassembler machinery.
+       (sim_target_parse_command_line): Add support for -t -d and -z
+       options.
+       (sim_target_display_usage): Note existence of -d and -z options.
+       (sim_open): Parse -t -d and -z options.
+       * armemu.h: Add exports of trace, disas and trace_funcs.
+       Add prototype for print_insn.
+       * armemu.c (ARMul_Emulate26): Add tracing code.
+       Delete unused variables.
+       * thumbemu (handle_v6_thumb_insn): Delete unused variable Rd.
+       Move Rm variable into switch cases.
+       Add tracing code.
+
+       * armcopro.c (XScale_cp15_init): Add a return value.
+       (XScale_cp13_init): Likewise.
+       (XScale_cp14_init): Likewise.
+       (XScale_cp15_LDC): Delete unused function.
+       (XScale_cp15_STC): Likewise.
+       * maverick.c: Delete comment inside comment.
+       (DSPInit): Delete unused function.
+       (DSPMCR4): Fix compile time warning about missing parenthesis.
+       (DSPMCR5): Likewise.
+       (DSPCDP6): Delete unused variable opcode2.
+
 2014-03-14  David McQuillan  <dmcq@tao-group.com>
 
        PR sim/8388
index 8194b313a68242f2b233c993e1f53ceafa50c10d..4c5da245e091fb64abe16aee46e269f73d451382 100644 (file)
@@ -85,6 +85,8 @@ XScale_cp15_init (ARMul_State * state ATTRIBUTE_UNUSED)
 
   /* Initialise the ARM Control Register.  */
   XScale_cp15_opcode_2_is_0_Regs[1] = 0x00000078;
+
+  return TRUE;
 }
 
 /* Check an access to a register.  */
@@ -370,34 +372,6 @@ read_cp15_reg (unsigned reg, unsigned opcode_2, unsigned CRm)
   return 0;
 }
 
-static unsigned
-XScale_cp15_LDC (ARMul_State * state, unsigned type, ARMword instr, ARMword data)
-{
-  unsigned reg = BITS (12, 15);
-  unsigned result;
-  
-  result = check_cp15_access (state, reg, 0, 0, 0);
-
-  if (result == ARMul_DONE && type == ARMul_DATA)
-    write_cp15_reg (state, reg, 0, 0, data);
-
-  return result;
-}
-
-static unsigned
-XScale_cp15_STC (ARMul_State * state, unsigned type, ARMword instr, ARMword * data)
-{
-  unsigned reg = BITS (12, 15);
-  unsigned result;
-
-  result = check_cp15_access (state, reg, 0, 0, 0);
-
-  if (result == ARMul_DONE && type == ARMul_DATA)
-    * data = read_cp15_reg (reg, 0, 0);
-
-  return result;
-}
-
 static unsigned
 XScale_cp15_MRC (ARMul_State * state,
                 unsigned      type ATTRIBUTE_UNUSED,
@@ -582,6 +556,8 @@ XScale_cp13_init (ARMul_State * state ATTRIBUTE_UNUSED)
       XScale_cp13_CR0_Regs[i] = 0;
       XScale_cp13_CR1_Regs[i] = 0;
     }
+
+  return TRUE;
 }
 
 /* Check an access to a register.  */
@@ -812,6 +788,8 @@ XScale_cp14_init (ARMul_State * state ATTRIBUTE_UNUSED)
 
   for (i = 16; i--;)
     XScale_cp14_Regs[i] = 0;
+
+  return TRUE;
 }
 
 /* Check an access to a register.  */
index 64c0146c1155cb3b47d954ac962c81b058218b0a..d535a4e90752a1199344f6515759e1b890ee4465 100644 (file)
@@ -1,7 +1,7 @@
 /*  armemu.c -- Main instruction emulation:  ARM7 Instruction Emulator.
     Copyright (C) 1994 Advanced RISC Machines Ltd.
     Modifications to add arch. v4 support by <jsmith@cygnus.com>.
-    
+
     This program is free software; you can redistribute it and/or modify
     it under the terms of the GNU General Public License as published by
     the Free Software Foundation; either version 3 of the License, or
@@ -314,7 +314,7 @@ handle_v6_insn (ARMul_State * state, ARMword instr)
       {
        ARMword Rm;
        int ror = -1;
-         
+
        switch (BITS (4, 11))
          {
          case 0x07: ror = 0; break;
@@ -580,11 +580,20 @@ ARMul_Emulate26 (ARMul_State * state)
 
       if (state->EventSet)
        ARMul_EnvokeEvent (state);
-#if 0 /* Enable this for a helpful bit of debugging when tracing is needed.  */
-      fprintf (stderr, "pc: %x, instr: %x\n", pc & ~1, instr);
-      if (instr == 0)
-       abort ();
-#endif
+
+      if (! TFLAG && trace)
+       {
+         fprintf (stderr, "pc: %x, ", pc & ~1);
+         if (! disas)
+           fprintf (stderr, "instr: %x\n", instr);
+       }
+
+      if (instr == 0 || pc < 0x10)
+       {
+         ARMul_Abort (state, ARMUndefinedInstrV);
+         state->Emulate = FALSE;
+       }
+
 #if 0 /* Enable this code to help track down stack alignment bugs.  */
       {
        static ARMword old_sp = -1;
@@ -628,8 +637,8 @@ ARMul_Emulate26 (ARMul_State * state)
            }
          if (state->Debug)
            {
-             fprintf (stderr, "sim: At %08lx Instr %08lx Mode %02lx\n", pc, instr,
-                      state->Mode);
+             fprintf (stderr, "sim: At %08lx Instr %08lx Mode %02lx\n",
+                      (long) pc, (long) instr, (long) state->Mode);
              (void) fgetc (stdin);
            }
        }
@@ -667,6 +676,14 @@ ARMul_Emulate26 (ARMul_State * state)
 
            case t_decoded:
              /* ARM instruction available.  */
+             if (disas || trace)
+               {
+                 fprintf (stderr, "  emulate as: ");
+                 if (trace)
+                   fprintf (stderr, "%08x ", new);
+                 if (! disas)
+                   fprintf (stderr, "\n");
+               }
              instr = new;
              /* So continue instruction decoding.  */
              break;
@@ -675,6 +692,8 @@ ARMul_Emulate26 (ARMul_State * state)
            }
        }
 #endif
+      if (disas)
+       print_insn (instr);
 
       /* Check the condition codes.  */
       if ((temp = TOPBITS (28)) == AL)
@@ -1654,7 +1673,6 @@ check_PMUintr:
                {
                  if (BITS (4, 7) == 0x7)
                    {
-                     ARMword value;
                      extern int SWI_vector_installed;
 
                      /* Hardware is allowed to optionally override this
@@ -1736,7 +1754,6 @@ check_PMUintr:
                      ARMdword op1 = state->Reg[BITS (0, 3)];
                      ARMdword op2 = state->Reg[BITS (8, 11)];
                      ARMdword dest;
-                     ARMdword result;
 
                      if (BIT (5))
                        op1 >>= 16;
@@ -1877,7 +1894,6 @@ check_PMUintr:
                      /* ElSegundo SMULxy insn.  */
                      ARMword op1 = state->Reg[BITS (0, 3)];
                      ARMword op2 = state->Reg[BITS (8, 11)];
-                     ARMword Rn = state->Reg[BITS (12, 15)];
 
                      if (BIT (5))
                        op1 >>= 16;
@@ -3459,7 +3475,6 @@ check_PMUintr:
              FLUSHPIPE;
              break;
 
-
              /* Branch and Link forward.  */
            case 0xb0:
            case 0xb1:
@@ -3477,9 +3492,10 @@ check_PMUintr:
 #endif
              state->Reg[15] = pc + 8 + POSBRANCH;
              FLUSHPIPE;
+             if (trace_funcs)
+               fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
              break;
 
-
              /* Branch and Link backward.  */
            case 0xb8:
            case 0xb9:
@@ -3497,9 +3513,10 @@ check_PMUintr:
 #endif
              state->Reg[15] = pc + 8 + NEGBRANCH;
              FLUSHPIPE;
+             if (trace_funcs)
+               fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
              break;
 
-
              /* Co-Processor Data Transfers.  */
            case 0xc4:
              if (state->is_v5)
@@ -4150,6 +4167,8 @@ WriteR15 (ARMul_State * state, ARMword src)
 #endif
 
   FLUSHPIPE;
+  if (trace_funcs)
+    fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
 }
 
 /* This routine handles writes to register 15 when the S bit is set.  */
@@ -4187,6 +4206,8 @@ WriteSR15 (ARMul_State * state, ARMword src)
   ARMul_R15Altered (state);
 #endif
   FLUSHPIPE;
+  if (trace_funcs)
+    fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
 }
 
 /* In machines capable of running in Thumb mode, BX, BLX, LDR and LDM
@@ -4208,6 +4229,8 @@ WriteR15Branch (ARMul_State * state, ARMword src)
       state->Reg[15] = src & 0xfffffffc;
     }
   FLUSHPIPE;
+  if (trace_funcs)
+    fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
 #else
   WriteR15 (state, src);
 #endif
index d61c85a983def1d9233b6fe6a1fea5f2f757c142..419f7990108016dcb7c85756d6275f3eb3657d37 100644 (file)
     along with this program; if not, see <http://www.gnu.org/licenses/>. */
 
 extern ARMword isize;
+extern int trace;
+extern int disas;
+extern int trace_funcs;
+extern void print_insn (ARMword);
 
 /* Condition code values.  */
 #define EQ 0
@@ -46,6 +50,10 @@ extern ARMword isize;
 #define CBIT (1L << 29)
 #define VBIT (1L << 28)
 #define SBIT (1L << 27)
+#define GE0 (1L << 16)
+#define GE1 (1L << 17)
+#define GE2 (1L << 18)
+#define GE3 (1L << 19)
 #define IBIT (1L << 7)
 #define FBIT (1L << 6)
 #define IFBITS (3L << 6)
index 2acf2b68f135b25027696d7fb316941c955238ba..b9a65172896288c584d561542de95001f38797d0 100644 (file)
@@ -20,7 +20,7 @@
 #include "ansidecl.h"
 #include "armemu.h"
 
-/*#define CIRRUS_DEBUG 1       /**/
+/*#define CIRRUS_DEBUG 1       */
 #if CIRRUS_DEBUG
 #  define printfdbg printf
 #else
@@ -97,13 +97,6 @@ cirrus_not_implemented (char * insn)
   exit (1);
 }
 
-static unsigned
-DSPInit (ARMul_State * state)
-{
-  ARMul_ConsolePrint (state, ", DSP present");
-  return TRUE;
-}
-
 unsigned
 DSPMRC4 (ARMul_State * state ATTRIBUTE_UNUSED,
         unsigned      type  ATTRIBUTE_UNUSED,
@@ -270,8 +263,9 @@ DSPMRC5 (ARMul_State * state ATTRIBUTE_UNUSED,
        v = SubOverflow (DSPregs[SRC1_REG].lower.i, DSPregs[SRC2_REG].lower.i,
                         res);
        /* carry */
-       c = (NEG (a) && POS (b) ||
-            (NEG (a) && POS (res)) || (POS (b) && POS (res)));
+       c = (NEG (a) && POS (b))
+         || (NEG (a) && POS (res))
+         || (POS (b) && POS (res));
 
        *value = (n << 31) | (z << 30) | (c << 29) | (v << 28);
        break;
@@ -301,8 +295,9 @@ DSPMRC5 (ARMul_State * state ATTRIBUTE_UNUSED,
        v = ((NEG64 (a) && POS64 (b) && POS64 (res))
             || (POS64 (a) && NEG64 (b) && NEG64 (res)));
        /* carry */
-       c = (NEG64 (a) && POS64 (b) ||
-            (NEG64 (a) && POS64 (res)) || (POS64 (b) && POS64 (res)));
+       c =    (NEG64 (a) && POS64 (b))
+           || (NEG64 (a) && POS64 (res))
+           || (POS64 (b) && POS64 (res));
 
        *value = (n << 31) | (z << 30) | (c << 29) | (v << 28);
        break;
@@ -1167,10 +1162,6 @@ DSPCDP6 (ARMul_State * state,
         unsigned      type,
         ARMword       instr)
 {
-   int opcode2;
-
-   opcode2 = BITS (5,7);
-
    switch (BITS (20,21))
      {
      case 0:
index b8ef7df2e90ceb8ee187679d1177f62d220bea98..e4c91f6c30ee8f29f7b8313687d3c677006031d8 100644 (file)
@@ -5,12 +5,12 @@
     it under the terms of the GNU General Public License as published by
     the Free Software Foundation; either version 3 of the License, or
     (at your option) any later version.
+
     This program is distributed in the hope that it will be useful,
     but WITHOUT ANY WARRANTY; without even the implied warranty of
     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     GNU General Public License for more details.
+
     You should have received a copy of the GNU General Public License
     along with this program; if not, see <http://www.gnu.org/licenses/>. */
 
@@ -38,9 +38,6 @@ handle_v6_thumb_insn (ARMul_State * state,
                      ARMword       tinstr,
                      tdstate *     pvalid)
 {
-  ARMword Rd;
-  ARMword Rm;
-
   if (! state->is_v6)
     {
       * pvalid = t_undefined;
@@ -56,33 +53,48 @@ handle_v6_thumb_insn (ARMul_State * state,
     case 0xba40: /* rev16 */
     case 0xbac0: /* revsh */
     case 0xb650: /* setend */
-    default:  
+    default:
       printf ("Unhandled v6 thumb insn: %04x\n", tinstr);
       * pvalid = t_undefined;
       return;
 
     case 0xb200: /* sxth */
-      Rm = state->Reg [(tinstr & 0x38) >> 3];
-      if (Rm & 0x8000)
-       state->Reg [(tinstr & 0x7)] = (Rm & 0xffff) | 0xffff0000;
-      else
-       state->Reg [(tinstr & 0x7)] = Rm & 0xffff;
-      break;
+      {
+       ARMword Rm = state->Reg [(tinstr & 0x38) >> 3];
+
+       if (Rm & 0x8000)
+         state->Reg [(tinstr & 0x7)] = (Rm & 0xffff) | 0xffff0000;
+       else
+         state->Reg [(tinstr & 0x7)] = Rm & 0xffff;
+       break;
+      }
+
     case 0xb240: /* sxtb */
-      Rm = state->Reg [(tinstr & 0x38) >> 3];
-      if (Rm & 0x80)
-       state->Reg [(tinstr & 0x7)] = (Rm & 0xff) | 0xffffff00;
-      else
-       state->Reg [(tinstr & 0x7)] = Rm & 0xff;
-      break;
+      {
+       ARMword Rm = state->Reg [(tinstr & 0x38) >> 3];
+
+       if (Rm & 0x80)
+         state->Reg [(tinstr & 0x7)] = (Rm & 0xff) | 0xffffff00;
+       else
+         state->Reg [(tinstr & 0x7)] = Rm & 0xff;
+       break;
+      }
+
     case 0xb280: /* uxth */
-      Rm = state->Reg [(tinstr & 0x38) >> 3];
-      state->Reg [(tinstr & 0x7)] = Rm & 0xffff;
-      break;
+      {
+       ARMword Rm = state->Reg [(tinstr & 0x38) >> 3];
+
+       state->Reg [(tinstr & 0x7)] = Rm & 0xffff;
+       break;
+      }
+
     case 0xb2c0: /* uxtb */
-      Rm = state->Reg [(tinstr & 0x38) >> 3];
-      state->Reg [(tinstr & 0x7)] = Rm & 0xff;
-      break;
+      {
+       ARMword Rm = state->Reg [(tinstr & 0x38) >> 3];
+
+       state->Reg [(tinstr & 0x7)] = Rm & 0xff;
+       break;
+      }
     }
   /* Indicate that the instruction has been processed.  */
   * pvalid = t_branch;
@@ -113,6 +125,9 @@ ARMul_ThumbDecode (ARMul_State * state,
       tinstr &= 0xFFFF;
     }
 
+  if (trace)
+    fprintf (stderr, "pc: %x, Thumb instr: %x", pc & ~1, tinstr);
+
 #if 1                          /* debugging to catch non updates */
   *ainstr = 0xDEADC0DE;
 #endif
@@ -413,7 +428,7 @@ ARMul_ThumbDecode (ARMul_State * state,
        case 0x0e00:
          if (state->is_v5)
            {
-             /* This is normally an undefined instruction.  The v5t architecture 
+             /* This is normally an undefined instruction.  The v5t architecture
                 defines this particular pattern as a BKPT instruction, for
                 hardware assisted debugging.  We map onto the arm BKPT
                 instruction.  */
@@ -550,6 +565,8 @@ ARMul_ThumbDecode (ARMul_State * state,
            state->Reg[14] = (tmp | 1);
            valid = t_branch;
            FLUSHPIPE;
+           if (trace_funcs)
+             fprintf (stderr, " pc changed to %x\n", state->Reg[15]);
            break;
          }
        }
@@ -610,5 +627,8 @@ ARMul_ThumbDecode (ARMul_State * state,
       break;
     }
 
+  if (trace && valid != t_decoded)
+    fprintf (stderr, "\n");
+
   return valid;
 }
index 064962b12551e7592db184f30169ef87366ac097..228cbc8813de54dee5d31ab04e608a6032ac0d8f 100644 (file)
@@ -37,6 +37,7 @@
 #include "gdb/sim-arm.h"
 #include "gdb/signals.h"
 #include "libiberty.h"
+#include "iwmmxt.h"
 
 host_callback *sim_callback;
 
@@ -59,6 +60,54 @@ static int big_endian;
 
 int stop_simulator;
 
+#include "dis-asm.h"
+
+int trace = 0;
+int disas = 0;
+int trace_funcs = 0;
+
+static struct disassemble_info  info;
+static char opbuf[1000];
+
+static int
+op_printf (char *buf, char *fmt, ...)
+{
+  int ret;
+  va_list ap;
+
+  va_start (ap, fmt);
+  ret = vsprintf (opbuf + strlen (opbuf), fmt, ap);
+  va_end (ap);
+  return ret;
+}
+
+static int
+sim_dis_read (bfd_vma                     memaddr ATTRIBUTE_UNUSED,
+             bfd_byte *                  ptr,
+             unsigned int                length,
+             struct disassemble_info *   info)
+{
+  ARMword val = (ARMword) *((ARMword *) info->application_data);
+
+  while (length--)
+    {
+      * ptr ++ = val & 0xFF;
+      val >>= 8;
+    }
+  return 0;
+}
+
+void
+print_insn (ARMword instr)
+{
+  int size;
+
+  opbuf[0] = 0;
+  info.application_data = & instr;
+  size = print_insn_little_arm (0, & info);
+  fprintf (stderr, " %*s\n", size, opbuf);
+}
+
 /* Cirrus DSP registers.
 
    We need to define these registers outside of maverick.c because
@@ -192,10 +241,9 @@ sim_read (sd, addr, buffer, size)
 int
 sim_trace (sd)
      SIM_DESC sd ATTRIBUTE_UNUSED;
-{  
-  (*sim_callback->printf_filtered)
-    (sim_callback,
-     "This simulator does not support tracing\n");
+{
+  trace = 1;
+  sim_resume (sd, 0, 0);
   return 1;
 }
 
@@ -269,9 +317,9 @@ sim_create_inferior (sd, abfd, argv, env)
       /* We wouldn't set the machine type with earlier toolchains, so we
         explicitly select a processor capable of supporting all ARMs in
         32bit mode.  */
-      /* We choose the XScale rather than the iWMMXt, because the iWMMXt
-        removes the FPE emulator, since it conflicts with its coprocessors.
-        For the most generic ARM support, we want the FPE emulator in place.  */
+      ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_v6_Prop);
+      break;
+
     case bfd_mach_arm_XScale:
       ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_XScale_Prop | ARM_v6_Prop);
       break;
@@ -351,6 +399,16 @@ sim_create_inferior (sd, abfd, argv, env)
       ARMul_SetCPSR (state, SVC32MODE);
     }
   
+  memset (& info, 0, sizeof (info));
+  INIT_DISASSEMBLE_INFO (info, stdout, op_printf);
+  info.read_memory_func = sim_dis_read;
+  info.arch = bfd_get_arch (abfd);
+  info.mach = bfd_get_mach (abfd);
+  info.endian_code = BFD_ENDIAN_LITTLE;
+  if (info.mach == 0)
+    info.arch = bfd_arch_arm;
+  disassemble_init_for_target (& info);
+
   if (argv != NULL)
     {
       /* Set up the command line by laboriously stringing together
@@ -676,8 +734,6 @@ sim_fetch_register (sd, rn, memory, length)
   return length;
 }
 
-#ifdef SIM_TARGET_SWITCHES
-
 static void sim_target_parse_arg_array (char **);
 
 typedef struct
@@ -718,6 +774,34 @@ sim_target_parse_command_line (argc, argv)
       if ((ptr == NULL) || (* ptr != '-'))
        break;
 
+      if (strcmp (ptr, "-t") == 0)
+       {
+         trace = 1;
+         continue;
+       }
+      
+      if (strcmp (ptr, "-z") == 0)
+       {
+         /* Remove this option from the argv array.  */
+         for (arg = i; arg < argc; arg ++)
+           argv[arg] = argv[arg + 1];
+         argc --;
+         i --;
+         trace_funcs = 1;
+         continue;
+       }
+      
+      if (strcmp (ptr, "-d") == 0)
+       {
+         /* Remove this option from the argv array.  */
+         for (arg = i; arg < argc; arg ++)
+           argv[arg] = argv[arg + 1];
+         argc --;
+         i --;
+         disas = 1;
+         continue;
+       }
+
       if (strncmp (ptr, SWI_SWITCH, sizeof SWI_SWITCH - 1) != 0)
        continue;
 
@@ -789,8 +873,9 @@ sim_target_display_usage (help)
   fprintf (stream, "%s=<list>  Comma seperated list of SWI protocols to supoport.\n\
                 This list can contain: NONE, DEMON, ANGEL, REDBOOT and/or ALL.\n",
           SWI_SWITCH);
+  fprintf (stream, "-d\t\tEnable disassembly of instructions during tracing.\n");
+  fprintf (stream, "-z\t\tTrace entering and leaving functions.\n\n");
 }
-#endif
 
 SIM_DESC
 sim_open (kind, ptr, abfd, argv)
@@ -853,6 +938,21 @@ sim_open (kind, ptr, abfd, argv)
                break;
              }
          }
+       else if (argv[i][0] == '-' && argv[i][1] == 't')
+         {
+           trace = 1;
+           break;
+         }
+       else if (argv[i][0] == '-' && argv[i][1] == 'z')
+         {
+           trace_funcs = 1;
+           break;
+         }
+       else if (argv[i][0] == '-' && argv[i][1] == 'd')
+         {
+           disas = 1;
+           break;
+         }
        else if (argv[i][0] == '-' && argv[i][1] == 'm')
          {
            if (argv[i][2] != '\0')