1 /* Convex stuff for GDB.
2 Copyright (C) 1990, 1991 Free Software Foundation, Inc.
4 This file is part of GDB.
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
32 #include <sys/param.h>
35 #include <sys/ioctl.h>
36 #include <sys/pcntl.h>
37 #include <sys/thread.h>
45 exec_file_command (filename
, from_tty
)
53 /* Eliminate all traces of old exec file.
54 Mark text segment as empty. */
71 /* Now open and digest the file the user requested, if any. */
75 filename
= tilde_expand (filename
);
76 make_cleanup (free
, filename
);
78 execchan
= openp (getenv ("PATH"), 1, filename
, O_RDONLY
, 0,
81 perror_with_name (filename
);
83 if (myread (execchan
, &filehdr
, sizeof filehdr
) < 0)
84 perror_with_name (filename
);
86 if (! IS_SOFF_MAGIC (filehdr
.h_magic
))
87 error ("%s: not an executable file.", filename
);
89 if (myread (execchan
, &opthdr
, filehdr
.h_opthdr
) <= 0)
90 perror_with_name (filename
);
92 /* Read through the section headers.
93 For text, data, etc, record an entry in the exec file map.
94 Record text_start and text_end. */
96 lseek (execchan
, (long) filehdr
.h_scnptr
, 0);
98 for (n
= 0; n
< filehdr
.h_nscns
; n
++)
100 if (myread (execchan
, &scnhdr
, sizeof scnhdr
) < 0)
101 perror_with_name (filename
);
103 if ((scnhdr
.s_flags
& S_TYPMASK
) >= S_TEXT
104 && (scnhdr
.s_flags
& S_TYPMASK
) <= S_COMON
)
106 exec_map
[n_exec
].mem_addr
= scnhdr
.s_vaddr
;
107 exec_map
[n_exec
].mem_end
= scnhdr
.s_vaddr
+ scnhdr
.s_size
;
108 exec_map
[n_exec
].file_addr
= scnhdr
.s_scnptr
;
109 exec_map
[n_exec
].type
= scnhdr
.s_flags
& S_TYPMASK
;
112 if ((scnhdr
.s_flags
& S_TYPMASK
) == S_TEXT
)
114 text_start
= scnhdr
.s_vaddr
;
115 text_end
= scnhdr
.s_vaddr
+ scnhdr
.s_size
;
120 fstat (execchan
, &st_exec
);
121 exec_mtime
= st_exec
.st_mtime
;
126 printf_filtered ("No exec file now.\n");
128 /* Tell display code (if any) about the changed file name. */
129 if (exec_file_display_hook
)
130 (*exec_file_display_hook
) (filename
);
133 /* Read data from SOFF exec or core file.
134 Return 0 on success, EIO if address out of bounds. */
137 xfer_core_file (memaddr
, myaddr
, len
)
155 /* Determine which file the next bunch of addresses reside in,
156 and where in the file. Set the file's read/write pointer
157 to point at the proper place for the desired address
158 and set xferfile and xferchan for the correct file.
159 If desired address is nonexistent, leave them zero.
160 i is set to the number of bytes that can be handled
161 along with the next address. */
165 for (n
= 0; n
< n_core
; n
++)
167 if (memaddr
>= core_map
[n
].mem_addr
&& memaddr
< core_map
[n
].mem_end
168 && (core_map
[n
].thread
== -1
169 || core_map
[n
].thread
== inferior_thread
))
171 i
= min (len
, core_map
[n
].mem_end
- memaddr
);
172 fileptr
= core_map
[n
].file_addr
+ memaddr
- core_map
[n
].mem_addr
;
173 if (core_map
[n
].file_addr
)
175 xferfile
= &corefile
;
180 else if (core_map
[n
].mem_addr
>= memaddr
181 && core_map
[n
].mem_addr
< memaddr
+ i
)
182 i
= core_map
[n
].mem_addr
- memaddr
;
186 for (n
= 0; n
< n_exec
; n
++)
188 if (memaddr
>= exec_map
[n
].mem_addr
189 && memaddr
< exec_map
[n
].mem_end
)
191 i
= min (len
, exec_map
[n
].mem_end
- memaddr
);
192 fileptr
= exec_map
[n
].file_addr
+ memaddr
193 - exec_map
[n
].mem_addr
;
194 if (exec_map
[n
].file_addr
)
196 xferfile
= &execfile
;
201 else if (exec_map
[n
].mem_addr
>= memaddr
202 && exec_map
[n
].mem_addr
< memaddr
+ i
)
203 i
= exec_map
[n
].mem_addr
- memaddr
;
206 /* Now we know which file to use.
207 Set up its pointer and transfer the data. */
211 if (xferfile
== &execfile
)
212 error ("No program file to examine.");
214 error ("No core dump file or running program to examine.");
215 val
= lseek (xferchan
, fileptr
, 0);
217 perror_with_name (*xferfile
);
218 val
= myread (xferchan
, myaddr
, i
);
220 perror_with_name (*xferfile
);
222 /* If this address is for nonexistent memory,
223 read zeros if reading, or do nothing if writing. */
226 memset (myaddr
, '\0', i
);
238 /* Here from info files command to print an address map. */
242 struct pmap ptrs
[200];
245 /* ID strings for core and executable file sections */
247 static char *idstr
[] =
249 "0", "text", "data", "tdata", "bss", "tbss",
250 "common", "ttext", "ctx", "tctx", "10", "11", "12",
253 for (n
= 0; n
< n_core
; n
++)
255 core_map
[n
].which
= 0;
256 ptrs
[n
] = core_map
[n
];
258 for (n
= 0; n
< n_exec
; n
++)
260 exec_map
[n
].which
= 1;
261 ptrs
[n_core
+n
] = exec_map
[n
];
264 qsort (ptrs
, n_core
+ n_exec
, sizeof *ptrs
, ptr_cmp
);
266 for (n
= 0; n
< n_core
+ n_exec
; n
++)
268 struct pmap
*p
= &ptrs
[n
];
271 if (p
->mem_addr
< ptrs
[n
-1].mem_end
)
272 p
->mem_addr
= ptrs
[n
-1].mem_end
;
273 if (p
->mem_addr
>= p
->mem_end
)
276 printf_filtered ("%08x .. %08x %-6s %s\n",
277 p
->mem_addr
, p
->mem_end
, idstr
[p
->type
],
278 p
->which
? execfile
: corefile
);
282 /* Compare routine to put file sections in order.
283 Sort into increasing order on address, and put core file sections
284 before exec file sections if both files contain the same addresses. */
286 static ptr_cmp (a
, b
)
289 if (a
->mem_addr
!= b
->mem_addr
) return a
->mem_addr
- b
->mem_addr
;
290 return a
->which
- b
->which
;
293 /* Trapped internal variables are used to handle special registers.
294 A trapped i.v. calls a hook here every time it is dereferenced,
295 to provide a new value for the variable, and it calls a hook here
296 when a new value is assigned, to do something with the value.
298 The vector registers are $vl, $vs, $vm, $vN, $VN (N in 0..7).
299 The communication registers are $cN, $CN (N in 0..63).
300 They not handled as regular registers because it's expensive to
301 read them, and their size varies, and they have too many names. */
304 /* Return 1 if NAME is a trapped internal variable, else 0. */
307 is_trapped_internalvar (name
)
310 if ((name
[0] == 'c' || name
[0] == 'C')
311 && name
[1] >= '0' && name
[1] <= '9'
313 || (name
[2] >= '0' && name
[2] <= '9'
314 && name
[3] == '\0' && name
[1] != '0'))
315 && atoi (&name
[1]) < 64) return 1;
317 if ((name
[0] == 'v' || name
[0] == 'V')
318 && (((name
[1] & -8) == '0' && name
[2] == '\0')
319 || STREQ (name
, "vl")
320 || STREQ (name
, "vs")
321 || STREQ (name
, "vm")))
326 /* Return the value of trapped internal variable VAR */
329 value_of_trapped_internalvar (var
)
330 struct internalvar
*var
;
332 char *name
= var
->name
;
335 struct type
*range_type
;
336 long len
= *read_vector_register (VL_REGNUM
);
337 if (len
<= 0 || len
> 128) len
= 128;
339 if (STREQ (name
, "vl"))
341 val
= value_from_longest (builtin_type_int
,
342 (LONGEST
) *read_vector_register_1 (VL_REGNUM
));
344 else if (STREQ (name
, "vs"))
346 val
= value_from_longest (builtin_type_int
,
347 (LONGEST
) *read_vector_register_1 (VS_REGNUM
));
349 else if (STREQ (name
, "vm"))
353 memcpy (vm
, read_vector_register_1 (VM_REGNUM
), sizeof vm
);
355 create_range_type ((struct type
*) NULL
, builtin_type_int
, 0, len
- 1);
357 create_array_type ((struct type
*) NULL
, builtin_type_int
, range_type
);
358 val
= allocate_value (type
);
359 p
= (long *) VALUE_CONTENTS (val
);
360 for (i
= 0; i
< len
; i
++)
361 *p
++ = !! (vm
[3 - (i
>> 5)] & (1 << (i
& 037)));
363 else if (name
[0] == 'V')
366 create_range_type ((struct type
*) NULL
, builtin_type_int
0, len
- 1);
368 create_array_type ((struct type
*) NULL
, builtin_type_long_long
,
370 val
= allocate_value (type
);
371 memcpy (VALUE_CONTENTS (val
),
372 read_vector_register_1 (name
[1] - '0'),
375 else if (name
[0] == 'v')
379 create_range_type ((struct type
*) NULL
, builtin_type_int
0, len
- 1);
381 create_array_type ((struct type
*) NULL
, builtin_type_long
,
383 val
= allocate_value (type
);
384 p1
= read_vector_register_1 (name
[1] - '0');
385 p2
= (long *) VALUE_CONTENTS (val
);
386 while (--len
>= 0) {p1
++; *p2
++ = *p1
++;}
389 else if (name
[0] == 'c')
390 val
= value_from_longest (builtin_type_int
,
391 read_comm_register (atoi (&name
[1])));
392 else if (name
[0] == 'C')
393 val
= value_from_longest (builtin_type_long_long
,
394 read_comm_register (atoi (&name
[1])));
396 VALUE_LVAL (val
) = lval_internalvar
;
397 VALUE_INTERNALVAR (val
) = var
;
401 /* Handle a new value assigned to a trapped internal variable */
404 set_trapped_internalvar (var
, val
, bitpos
, bitsize
, offset
)
405 struct internalvar
*var
;
407 int bitpos
, bitsize
, offset
;
409 char *name
= var
->name
;
410 long long newval
= value_as_long (val
);
412 if (STREQ (name
, "vl"))
413 write_vector_register (VL_REGNUM
, 0, newval
);
414 else if (STREQ (name
, "vs"))
415 write_vector_register (VS_REGNUM
, 0, newval
);
416 else if (name
[0] == 'c' || name
[0] == 'C')
417 write_comm_register (atoi (&name
[1]), newval
);
418 else if (STREQ (name
, "vm"))
419 error ("can't assign to $vm");
422 offset
/= bitsize
/ 8;
423 write_vector_register (name
[1] - '0', offset
, newval
);
427 /* Print an integer value when no format was specified. gdb normally
428 prints these values in decimal, but the the leading 0x80000000 of
429 pointers produces intolerable 10-digit negative numbers.
430 If it looks like an address, print it in hex instead. */
432 decout (stream
, type
, val
)
439 switch (output_radix
)
442 if ((lv
== val
|| (unsigned) lv
== val
)
443 && ((lv
& 0xf0000000) == 0x80000000
444 || ((lv
& 0xf0000000) == 0xf0000000 && lv
< STACK_END_ADDR
)))
446 fprintf_filtered (stream
, "%#x", lv
);
451 fprintf_filtered (stream
, TYPE_UNSIGNED (type
) ? "%llu" : "%lld", val
);
455 if (TYPE_LENGTH (type
) <= sizeof lv
)
456 fprintf_filtered (stream
, "%#o", lv
);
458 fprintf_filtered (stream
, "%#llo", val
);
462 if (TYPE_LENGTH (type
) <= sizeof lv
)
463 fprintf_filtered (stream
, "%#x", lv
);
465 fprintf_filtered (stream
, "%#llx", val
);
470 /* Change the default output radix to 10 or 16, or set it to 0 (heuristic).
471 This command is mostly obsolete now that the print command allows
472 formats to apply to aggregates, but is still handy occasionally. */
475 set_base_command (arg
)
484 new_radix
= atoi (arg
);
485 if (new_radix
!= 10 && new_radix
!= 16 && new_radix
!= 8)
486 error ("base must be 8, 10 or 16, or null");
487 else output_radix
= new_radix
;
491 /* Turn pipelining on or off in the inferior. */
494 set_pipelining_command (arg
)
499 sequential
= !sequential
;
500 printf_filtered ("%s\n", sequential
? "off" : "on");
502 else if (STREQ (arg
, "on"))
504 else if (STREQ (arg
, "off"))
506 else error ("valid args are `on', to allow instructions to overlap, or\n\
507 `off', to prevent it and thereby pinpoint exceptions.");
510 /* Enable, disable, or force parallel execution in the inferior. */
513 set_parallel_command (arg
)
517 int prevparallel
= parallel
;
519 if (!strncmp (arg
, "fixed", strlen (arg
)))
521 else if (STREQ (arg
, "on"))
523 else if (STREQ (arg
, "off"))
525 else error ("valid args are `on', to allow multiple threads, or\n\
526 `fixed', to force multiple threads, or\n\
527 `off', to run with one thread only.");
529 if ((prevparallel
== 0) != (parallel
== 0) && inferior_pid
)
530 printf_filtered ("will take effect at next run.\n");
532 getrlimit (RLIMIT_CONCUR
, &rl
);
533 rl
.rlim_cur
= parallel
? rl
.rlim_max
: 1;
534 setrlimit (RLIMIT_CONCUR
, &rl
);
537 set_fixed_scheduling (inferior_pid
, parallel
== 2);
540 /* Add a new name for an existing command. */
546 static char *aliaserr
= "usage is `alias NEW OLD', no args allowed";
548 struct cmd_list_element
*new, *old
;
551 error_no_arg ("newname oldname");
553 new = lookup_cmd (&arg
, cmdlist
, "", -1);
554 if (new && !strncmp (newname
, new->name
, strlen (new->name
)))
558 || (*arg
>= 'a' && *arg
<= 'z')
559 || (*arg
>= 'A' && *arg
<= 'Z')
560 || (*arg
>= '0' && *arg
<= '9')))
567 || (*arg
>= 'a' && *arg
<= 'z')
568 || (*arg
>= 'A' && *arg
<= 'Z')
569 || (*arg
>= '0' && *arg
<= '9'))
571 if (*arg
!= ' ' && *arg
!= '\t')
577 old
= lookup_cmd (&arg
, cmdlist
, "", 0);
582 if (new && !strncmp (newname
, new->name
, strlen (new->name
)))
585 if (new->class == (int) class_user
|| new->class == (int) class_alias
)
586 tem
= "Redefine command \"%s\"? ";
588 tem
= "Really redefine built-in command \"%s\"? ";
589 if (!query (tem
, new->name
))
590 error ("Command \"%s\" not redefined.", new->name
);
593 add_com (newname
, class_alias
, old
->function
, old
->doc
);
598 /* Print the current thread number, and any threads with signals in the
605 if (have_inferior_p ())
607 ps
.pi_buffer
= (char *) &comm_registers
;
608 ps
.pi_nbytes
= sizeof comm_registers
;
610 ps
.pi_thread
= inferior_thread
;
611 ioctl (inferior_fd
, PIXRDCREGS
, &ps
);
614 /* FIXME: stop_signal is from target.h but stop_sigcode is a
615 convex-specific thing. */
616 printf_filtered ("Current thread %d stopped with signal %d.%d (%s).\n",
617 inferior_thread
, stop_signal
, stop_sigcode
,
618 subsig_name (stop_signal
, stop_sigcode
));
620 for (p
= signal_stack
; p
->pid
; p
--)
621 printf_filtered ("Thread %d stopped with signal %d.%d (%s).\n",
622 p
->thread
, p
->signo
, p
->subsig
,
623 subsig_name (p
->signo
, p
->subsig
));
625 if (iscrlbit (comm_registers
.crctl
.lbits
.cc
, 64+13))
626 printf_filtered ("New thread start pc %#x\n",
627 (long) (comm_registers
.crreg
.pcpsw
>> 32));
630 /* Return string describing a signal.subcode number */
633 subsig_name (signo
, subcode
)
636 static char *subsig4
[] = {
637 "error exit", "privileged instruction", "unknown",
638 "unknown", "undefined opcode",
640 static char *subsig5
[] = {0,
641 "breakpoint", "single step", "fork trap", "exec trap", "pfork trap",
642 "join trap", "idle trap", "last thread", "wfork trap",
643 "process breakpoint", "trap instruction",
645 static char *subsig8
[] = {0,
646 "int overflow", "int divide check", "float overflow",
647 "float divide check", "float underflow", "reserved operand",
648 "sqrt error", "exp error", "ln error", "sin error", "cos error",
650 static char *subsig10
[] = {0,
651 "invalid inward ring address", "invalid outward ring call",
652 "invalid inward ring return", "invalid syscall gate",
653 "invalid rtn frame length", "invalid comm reg address",
656 static char *subsig11
[] = {0,
657 "read access denied", "write access denied", "execute access denied",
658 "segment descriptor fault", "page table fault", "data reference fault",
659 "i/o access denied", "levt pte invalid",
662 static char **subsig_list
[] =
663 {0, 0, 0, 0, subsig4
, subsig5
, 0, 0, subsig8
, 0, subsig10
, subsig11
, 0};
668 if ((p
= strsignal (signo
)) == NULL
)
670 if (signo
>= (sizeof subsig_list
/ sizeof *subsig_list
)
671 || !subsig_list
[signo
])
673 for (i
= 1; subsig_list
[signo
][i
]; i
++)
675 return subsig_list
[signo
][subcode
];
680 /* Print a compact display of thread status, essentially x/i $pc
681 for all active threads. */
688 for (t
= 0; t
< n_threads
; t
++)
689 if (thread_state
[t
] == PI_TALIVE
)
691 printf_filtered ("%d%c %08x%c %d.%d ", t
,
692 (t
== inferior_thread
? '*' : ' '), thread_pc
[t
],
693 (thread_is_in_kernel
[t
] ? '#' : ' '),
694 thread_signal
[t
], thread_sigcode
[t
]);
695 print_insn (thread_pc
[t
], stdout
);
696 printf_filtered ("\n");
700 /* Change the current thread to ARG. */
702 set_thread_command (arg
)
713 thread
= parse_and_eval_address (arg
);
715 if (thread
< 0 || thread
> n_threads
|| thread_state
[thread
] != PI_TALIVE
)
716 error ("no such thread.");
718 select_thread (thread
);
720 stop_pc
= read_pc ();
721 flush_cached_frames ();
722 select_frame (get_current_frame (), 0);
723 print_stack_frame (selected_frame
, selected_frame_level
, -1);
726 /* Here on CONT command; gdb's dispatch address is changed to come here.
727 Set global variable ALL_CONTINUE to tell resume() that it should
728 start up all threads, and that a thread switch will not blow gdb's
732 convex_cont_command (proc_count_exp
, from_tty
)
733 char *proc_count_exp
;
737 cont_command (proc_count_exp
, from_tty
);
740 /* Here on 1CONT command. Resume only the current thread. */
742 one_cont_command (proc_count_exp
, from_tty
)
743 char *proc_count_exp
;
746 cont_command (proc_count_exp
, from_tty
);
749 /* Print the contents and lock bits of all communication registers,
750 or just register ARG if ARG is a communication register,
751 or the 3-word resource structure in memory at address ARG. */
753 comm_registers_info (arg
)
760 if (sscanf (arg
, "$c%d", ®num
) == 1) {
762 } else if (sscanf (arg
, "$C%d", ®num
) == 1) {
765 regnum
= parse_and_eval_address (arg
);
771 error ("%s: invalid register name.", arg
);
773 /* if we got a (user) address, examine the resource struct there */
778 read_memory (regnum
, buf
, sizeof buf
);
779 printf_filtered ("%08x %08x%08x%s\n", regnum
, buf
[1], buf
[2],
780 buf
[0] & 0xff ? " locked" : "");
785 ps
.pi_buffer
= (char *) &comm_registers
;
786 ps
.pi_nbytes
= sizeof comm_registers
;
788 ps
.pi_thread
= inferior_thread
;
789 ioctl (inferior_fd
, PIXRDCREGS
, &ps
);
791 for (i
= 0; i
< 64; i
++)
792 if (!arg
|| i
== regnum
)
793 printf_filtered ("%2d 0x8%03x %016llx%s\n", i
, i
,
794 comm_registers
.crreg
.r4
[i
],
795 (iscrlbit (comm_registers
.crctl
.lbits
.cc
, i
)
812 static struct pswbit pswbit
[] =
814 { 0x80000000, -1, "A carry" },
815 { 0x40000000, -1, "A integer overflow" },
816 { 0x20000000, -1, "A zero divide" },
817 { 0x10000000, -1, "Integer overflow enable" },
818 { 0x08000000, -1, "Trace" },
819 { 0x06000000, 25, "Frame length" },
820 { 0x01000000, -1, "Sequential" },
821 { 0x00800000, -1, "S carry" },
822 { 0x00400000, -1, "S integer overflow" },
823 { 0x00200000, -1, "S zero divide" },
824 { 0x00100000, -1, "Zero divide enable" },
825 { 0x00080000, -1, "Floating underflow" },
826 { 0x00040000, -1, "Floating overflow" },
827 { 0x00020000, -1, "Floating reserved operand" },
828 { 0x00010000, -1, "Floating zero divide" },
829 { 0x00008000, -1, "Floating error enable" },
830 { 0x00004000, -1, "Floating underflow enable" },
831 { 0x00002000, -1, "IEEE" },
832 { 0x00001000, -1, "Sequential stores" },
833 { 0x00000800, -1, "Intrinsic error" },
834 { 0x00000400, -1, "Intrinsic error enable" },
835 { 0x00000200, -1, "Trace thread creates" },
836 { 0x00000100, -1, "Thread init trap" },
837 { 0x000000e0, 5, "Reserved" },
838 { 0x0000001f, 0, "Intrinsic error code" },
846 psw
= parse_and_eval_address (arg
);
848 psw
= read_register (PS_REGNUM
);
850 for (p
= pswbit
; p
->bit
; p
++)
853 printf_filtered ("%08x %s %s\n", p
->bit
,
854 (psw
& p
->bit
) ? "yes" : "no ", p
->text
);
856 printf_filtered ("%08x %3d %s\n", p
->bit
,
857 (psw
& p
->bit
) >> p
->pos
, p
->text
);
863 /* reg (fmt_field, inst_field) --
864 the {first,second,third} operand of instruction as fmt_field = [ijk]
865 gets the value of the field from the [ijk] position of the instruction */
867 #define reg(a,b) ((char (*)[3])(op[fmt->a]))[inst.f0.b]
869 /* lit (fmt_field) -- field [ijk] is a literal (PSW, VL, eg) */
871 #define lit(i) op[fmt->i]
873 /* aj[j] -- name for A register j */
875 #define aj ((char (*)[3])(op[A]))
895 unsigned char byte
[8];
896 unsigned short half
[4];
898 short signed_half
[4];
902 int mask
; /* opcode mask */
903 int shift
; /* opcode align */
904 struct formstr
*formstr
[3]; /* ST, E0, E1 */
908 unsigned lop
:8, rop
:5; /* opcode */
909 unsigned fmt
:5; /* inst format */
910 unsigned i
:5, j
:5, k
:2; /* operand formats */
913 #include "opcode/convex.h"
915 CONST
unsigned char formdecode
[] = {
916 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
917 9,9,9,9,9,9,9,9,9,9,9,9,9,9,9,9,
918 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
919 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
920 2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,
921 2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,
922 3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,
923 4,4,4,4,4,4,4,4,5,5,5,5,6,6,7,8,
924 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
925 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
926 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
927 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
928 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
929 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
930 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
931 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
934 CONST
struct opform opdecode
[] = {
935 0x7e00, 9, format0
, e0_format0
, e1_format0
,
936 0x3f00, 8, format1
, e0_format1
, e1_format1
,
937 0x1fc0, 6, format2
, e0_format2
, e1_format2
,
938 0x0fc0, 6, format3
, e0_format3
, e1_format3
,
939 0x0700, 8, format4
, e0_format4
, e1_format4
,
940 0x03c0, 6, format5
, e0_format5
, e1_format5
,
941 0x01f8, 3, format6
, e0_format6
, e1_format6
,
942 0x00f8, 3, format7
, e0_format7
, e1_format7
,
943 0x0000, 0, formatx
, formatx
, formatx
,
944 0x0f80, 7, formatx
, formatx
, formatx
,
945 0x0f80, 7, formatx
, formatx
, formatx
,
948 /* Print the instruction at address MEMADDR in debugged memory,
949 on STREAM. Returns length of the instruction, in bytes. */
952 convex_print_insn (memaddr
, stream
)
958 register int format
, op1
, pfx
;
961 read_memory (memaddr
, &inst
, sizeof inst
);
963 /* Remove and note prefix, if present */
966 if ((pfx
& 0xfff0) == 0x7ef0)
968 pfx
= ((pfx
>> 3) & 1) + 1;
969 *(long long *) &inst
= *(long long *) &inst
.half
[1];
973 /* Split opcode into format.op1 and look up in appropriate table */
975 format
= formdecode
[inst
.byte
[0]];
976 op1
= (inst
.half
[0] & opdecode
[format
].mask
) >> opdecode
[format
].shift
;
981 else if (inst
.f1
.j
== 0)
982 fmt
= &format1a
[op1
];
983 else if (inst
.f1
.j
== 1)
984 fmt
= &format1b
[op1
];
989 fmt
= &opdecode
[format
].formstr
[pfx
][op1
];
996 fprintf (stream
, "0x%04x", pfx
? pfx
: inst
.half
[0]);
1003 fprintf (stream
, "%s%s%s", lop
[fmt
->lop
], rop
[fmt
->rop
],
1004 &" "[strlen(lop
[fmt
->lop
]) + strlen(rop
[fmt
->rop
])]);
1008 case rrr
: /* three register */
1009 fprintf (stream
, "%s,%s,%s", reg(i
,i
), reg(j
,j
), reg(k
,k
));
1012 case rr
: /* two register */
1013 fprintf (stream
, "%s,%s", reg(i
,j
), reg(j
,k
));
1016 case rxr
: /* two register, reversed i and j fields */
1017 fprintf (stream
, "%s,%s", reg(i
,k
), reg(j
,j
));
1020 case r
: /* one register */
1021 fprintf (stream
, "%s", reg(i
,k
));
1024 case nops
: /* no operands */
1027 case nr
: /* short immediate, one register */
1028 fprintf (stream
, "#%d,%s", inst
.f0
.j
, reg(i
,k
));
1031 case pcrel
: /* pc relative */
1032 print_address (memaddr
+ 2 * inst
.signed_byte
[1], stream
);
1035 case lr
: /* literal, one register */
1036 fprintf (stream
, "%s,%s", lit(i
), reg(j
,k
));
1039 case rxl
: /* one register, literal */
1040 fprintf (stream
, "%s,%s", reg(i
,k
), lit(j
));
1043 case rlr
: /* register, literal, register */
1044 fprintf (stream
, "%s,%s,%s", reg(i
,j
), lit(j
), reg(k
,k
));
1047 case rrl
: /* register, register, literal */
1048 fprintf (stream
, "%s,%s,%s", reg(i
,j
), reg(j
,k
), lit(k
));
1051 case iml
: /* immediate, literal */
1054 fprintf (stream
, "#%#x,%s",
1055 (inst
.signed_half
[1] << 16) + inst
.half
[2], lit(i
));
1060 fprintf (stream
, "#%d,%s", inst
.signed_half
[1], lit(i
));
1064 case imr
: /* immediate, register */
1067 fprintf (stream
, "#%#x,%s",
1068 (inst
.signed_half
[1] << 16) + inst
.half
[2], reg(i
,k
));
1073 fprintf (stream
, "#%d,%s", inst
.signed_half
[1], reg(i
,k
));
1077 case a1r
: /* memory, register */
1078 l
= print_effa (inst
, stream
);
1079 fprintf (stream
, ",%s", reg(i
,k
));
1082 case a1l
: /* memory, literal */
1083 l
= print_effa (inst
, stream
);
1084 fprintf (stream
, ",%s", lit(i
));
1087 case a2r
: /* register, memory */
1088 fprintf (stream
, "%s,", reg(i
,k
));
1089 return pfx
+ print_effa (inst
, stream
);
1091 case a2l
: /* literal, memory */
1092 fprintf (stream
, "%s,", lit(i
));
1093 return pfx
+ print_effa (inst
, stream
);
1095 case a3
: /* memory */
1096 return pfx
+ print_effa (inst
, stream
);
1098 case a4
: /* system call */
1105 unsigned int m
= (inst
.signed_half
[1] << 16) + inst
.half
[2];
1106 fprintf (stream
, "#%d,#%d", m
>> l
, m
& (-1 >> (32-l
)));
1111 unsigned int m
= inst
.signed_half
[1];
1112 fprintf (stream
, "#%d,#%d", m
>> l
, m
& (-1 >> (32-l
)));
1119 /* print effective address @nnn(aj), return instruction length */
1121 int print_effa (inst
, stream
)
1129 n
= (inst
.signed_half
[1] << 16) + inst
.half
[2];
1134 n
= inst
.signed_half
[1];
1143 print_address (n
, stream
);
1147 fprintf (stream
, (n
& 0xf0000000) == 0x80000000 ? "%#x(%s)" : "%d(%s)",
1155 _initialize_convex_dep ()
1157 add_com ("alias", class_support
, alias_command
,
1158 "Add a new name for an existing command.");
1160 add_cmd ("base", class_vars
, set_base_command
,
1161 "Change the integer output radix to 8, 10 or 16\n\
1162 or use just `set base' with no args to return to the ad-hoc default,\n\
1163 which is 16 for integers that look like addresses, 10 otherwise.",
1166 add_cmd ("pipeline", class_run
, set_pipelining_command
,
1167 "Enable or disable overlapped execution of instructions.\n\
1168 With `set pipe off', exceptions are reported with\n\
1169 $pc pointing at the instruction after the faulting one.\n\
1170 The default is `set pipe on', which runs faster.",
1173 add_cmd ("parallel", class_run
, set_parallel_command
,
1174 "Enable or disable multi-threaded execution of parallel code.\n\
1175 `set parallel off' means run the program on a single CPU.\n\
1176 `set parallel fixed' means run the program with all CPUs assigned to it.\n\
1177 `set parallel on' means run the program on any CPUs that are available.",
1180 add_com ("1cont", class_run
, one_cont_command
,
1181 "Continue the program, activating only the current thread.\n\
1182 Args are the same as the `cont' command.");
1184 add_com ("thread", class_run
, set_thread_command
,
1185 "Change the current thread, the one under scrutiny and control.\n\
1186 With no arg, show the active threads, the current one marked with *.");
1188 add_info ("threads", thread_info
,
1189 "List status of active threads.");
1191 add_info ("comm-registers", comm_registers_info
,
1192 "List communication registers and their contents.\n\
1193 A communication register name as argument means describe only that register.\n\
1194 An address as argument means describe the resource structure at that address.\n\
1195 `Locked' means that the register has been sent to but not yet received from.");
1197 add_info ("psw", psw_info
,
1198 "Display $ps, the processor status word, bit by bit.\n\
1199 An argument means display that value's interpretation as a psw.");
1201 add_cmd ("convex", no_class
, 0, "Convex-specific commands.\n\
1202 32-bit registers $pc $ps $sp $ap $fp $a1-5 $s0-7 $v0-7 $vl $vs $vm $c0-63\n\
1203 64-bit registers $S0-7 $V0-7 $C0-63\n\
1205 info threads display info on stopped threads waiting to signal\n\
1206 thread display list of active threads\n\
1207 thread N select thread N (its registers, stack, memory, etc.)\n\
1208 step, next, etc step selected thread only\n\
1209 1cont continue selected thread only\n\
1210 cont continue all threads\n\
1211 info comm-registers display contents of comm register(s) or a resource struct\n\
1212 info psw display processor status word $ps\n\
1213 set base N change integer radix used by `print' without a format\n\
1214 set pipeline off exceptions are precise, $pc points after the faulting insn\n\
1215 set pipeline on normal mode, $pc is somewhere ahead of faulting insn\n\
1216 set parallel off program runs on a single CPU\n\
1217 set parallel fixed all CPUs are assigned to the program\n\
1218 set parallel on normal mode, parallel execution on random available CPUs\n\
This page took 0.056615 seconds and 5 git commands to generate.