Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include "defs.h"
-#include "rs6k-opcode.h"
+#include "opcode/rs6k.h"
/* Print the rs6k instruction at address MEMADDR in debugged memory,
on STREAM. Returns length of the instruction, in bytes. */
CORE_ADDR memaddr;
FILE *stream;
{
- int pop, eop; /* primary and extended opcodes */
+ int pop, eop, probable_eop; /* primary and extended opcodes */
int min, max;
int best = -1; /* found best opcode index */
int oldbest = -1;
read_memory (memaddr, &the_insn, sizeof (the_insn));
pop = (unsigned)(the_insn >> 26);
- eop = ((the_insn) >> 1) & 0x3ff;
min = 0, max = NOPCODES-1;
while (min < max) {
min = best;
else {
- /* opcode matched, check extended opcode. */
+ /* Opcode matched, check extended opcode. */
if (rs6k_ops [best].e_opcode == -1) {
/* there is no valid extended opcode, what we've got is
goto insn_found;
}
- else if (eop < rs6k_ops [best].e_opcode) {
+ /* Largest possible value of extended opcode. */
+ probable_eop = ((the_insn) >> 1) & 0x3ff;
+
+ eop = probable_eop & eopMask [rs6k_ops [best].format];
+
+ if (eop < rs6k_ops [best].e_opcode) {
while (pop == rs6k_ops [best].p_opcode) {
if (eop == rs6k_ops [best].e_opcode) /* found it! */
goto insn_found;
--best;
+ eop = probable_eop & eopMask [rs6k_ops [best].format];
}
goto not_found;
}
if (eop == rs6k_ops [best].e_opcode) /* found it! */
goto insn_found;
++best;
+ eop = probable_eop & eopMask [rs6k_ops [best].format];
}
goto not_found;
}
/* parse the operand now. */
pp = rs6k_ops[insn_no].oprnd_format;
- while (1) {
+ while (*pp != 0) {
switch (*pp) {
case TO :
fprintf (stream, "%d", (insn_word >> 21) & 0x1f);
case LI :
tmp = (insn_word >> 16) & 0x1f;
+#if 0
+ /* This is wrong, wrong, wrong. The condition code only goes
+ from 0 to 3 (for the instructions which can use extended
+ mnemonics of this type), and the XX (lt, gt, eq etc.) goes
+ into the mnemonic, not as an operand.
+
+ Probably the best way to get this right in both assembler
+ and disassembler is to switch to a match/lose style opcode
+ table like the sparc. */
if (tmp > 11) {
fprintf (stream, "{unknown cond code: 0x%x}", insn_word);
tmp = 0;
}
fprintf (stream, "%s", cond_code [tmp]);
+#else
+ /* So for just always use the "bbf/bbt" form. This is perfectly
+ correct, just not necessarily as legible.
+
+ If tmp is not in the range 0-3, we can't use an XX form anyway. */
+ fprintf (stream, "%d", tmp);
+#endif
break;
case A2 :
}
++pp;
- if (*pp == '\0')
- break;
- else if (!nocomma)
+ if (*pp != '\0' && !nocomma)
fputc(',', stream);
}
}