summaryrefslogtreecommitdiff
path: root/opcodes/ns32k-dis.c
diff options
context:
space:
mode:
Diffstat (limited to 'opcodes/ns32k-dis.c')
-rw-r--r--opcodes/ns32k-dis.c895
1 files changed, 0 insertions, 895 deletions
diff --git a/opcodes/ns32k-dis.c b/opcodes/ns32k-dis.c
deleted file mode 100644
index 610e37305f7..00000000000
--- a/opcodes/ns32k-dis.c
+++ /dev/null
@@ -1,895 +0,0 @@
-/* Print National Semiconductor 32000 instructions.
- Copyright 1986, 1988, 1991, 1992, 1994, 1998
- Free Software Foundation, Inc.
-
-This file is part of opcodes library.
-
-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 2 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, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
-
-
-#include "bfd.h"
-#include "sysdep.h"
-#include "dis-asm.h"
-#if !defined(const) && !defined(__STDC__)
-#define const
-#endif
-#include "opcode/ns32k.h"
-#include "opintl.h"
-
-static disassemble_info *dis_info;
-
-/*
- * Hacks to get it to compile <= READ THESE AS FIXES NEEDED
- */
-#define INVALID_FLOAT(val, size) invalid_float((char *)val, size)
-
-static int print_insn_arg
- PARAMS ((int, int, int *, char *, bfd_vma, char *, int));
-static int get_displacement PARAMS ((char *, int *));
-static int invalid_float PARAMS ((char *, int));
-
-static long read_memory_integer(addr, nr)
- unsigned char *addr;
- int nr;
-{
- long val;
- int i;
- for (val = 0, i = nr - 1; i >= 0; i--) {
- val = (val << 8);
- val |= (0xff & *(addr + i));
- }
- return val;
-}
-
-/* 32000 instructions are never longer than this. */
-#define MAXLEN 62
-
-
-#include <setjmp.h>
-
-struct private
-{
- /* Points to first byte not fetched. */
- bfd_byte *max_fetched;
- bfd_byte the_buffer[MAXLEN];
- bfd_vma insn_start;
- jmp_buf bailout;
-};
-
-
-/* Make sure that bytes from INFO->PRIVATE_DATA->BUFFER (inclusive)
- to ADDR (exclusive) are valid. Returns 1 for success, longjmps
- on error. */
-#define FETCH_DATA(info, addr) \
- ((addr) <= ((struct private *)(info->private_data))->max_fetched \
- ? 1 : fetch_data ((info), (addr)))
-
-static int
-fetch_data (info, addr)
- struct disassemble_info *info;
- bfd_byte *addr;
-{
- int status;
- struct private *priv = (struct private *)info->private_data;
- bfd_vma start = priv->insn_start + (priv->max_fetched - priv->the_buffer);
-
- status = (*info->read_memory_func) (start,
- priv->max_fetched,
- addr - priv->max_fetched,
- info);
- if (status != 0)
- {
- (*info->memory_error_func) (status, start, info);
- longjmp (priv->bailout, 1);
- }
- else
- priv->max_fetched = addr;
- return 1;
-}
-/* Number of elements in the opcode table. */
-#define NOPCODES (sizeof ns32k_opcodes / sizeof ns32k_opcodes[0])
-
-#define NEXT_IS_ADDR '|'
-
-
-struct ns32k_option {
- char *pattern; /* the option itself */
- unsigned long value; /* binary value of the option */
- unsigned long match; /* these bits must match */
-};
-
-
-static const struct ns32k_option opt_u[]= /* restore, exit */
-{
- { "r0", 0x80, 0x80 },
- { "r1", 0x40, 0x40 },
- { "r2", 0x20, 0x20 },
- { "r3", 0x10, 0x10 },
- { "r4", 0x08, 0x08 },
- { "r5", 0x04, 0x04 },
- { "r6", 0x02, 0x02 },
- { "r7", 0x01, 0x01 },
- { 0 , 0x00, 0x00 }
-};
-
-static const struct ns32k_option opt_U[]= /* save, enter */
-{
- { "r0", 0x01, 0x01 },
- { "r1", 0x02, 0x02 },
- { "r2", 0x04, 0x04 },
- { "r3", 0x08, 0x08 },
- { "r4", 0x10, 0x10 },
- { "r5", 0x20, 0x20 },
- { "r6", 0x40, 0x40 },
- { "r7", 0x80, 0x80 },
- { 0 , 0x00, 0x00 }
-};
-
-static const struct ns32k_option opt_O[]= /* setcfg */
-{
- { "c", 0x8, 0x8 },
- { "m", 0x4, 0x4 },
- { "f", 0x2, 0x2 },
- { "i", 0x1, 0x1 },
- { 0 , 0x0, 0x0 }
-};
-
-static const struct ns32k_option opt_C[]= /* cinv */
-{
- { "a", 0x4, 0x4 },
- { "i", 0x2, 0x2 },
- { "d", 0x1, 0x1 },
- { 0 , 0x0, 0x0 }
-};
-
-static const struct ns32k_option opt_S[]= /* string inst */
-{
- { "b", 0x1, 0x1 },
- { "u", 0x6, 0x6 },
- { "w", 0x2, 0x2 },
- { 0 , 0x0, 0x0 }
-};
-
-static const struct ns32k_option list_P532[]= /* lpr spr */
-{
- { "us", 0x0, 0xf },
- { "dcr", 0x1, 0xf },
- { "bpc", 0x2, 0xf },
- { "dsr", 0x3, 0xf },
- { "car", 0x4, 0xf },
- { "fp", 0x8, 0xf },
- { "sp", 0x9, 0xf },
- { "sb", 0xa, 0xf },
- { "usp", 0xb, 0xf },
- { "cfg", 0xc, 0xf },
- { "psr", 0xd, 0xf },
- { "intbase", 0xe, 0xf },
- { "mod", 0xf, 0xf },
- { 0 , 0x00, 0xf }
-};
-
-static const struct ns32k_option list_M532[]= /* lmr smr */
-{
- { "mcr", 0x9, 0xf },
- { "msr", 0xa, 0xf },
- { "tear", 0xb, 0xf },
- { "ptb0", 0xc, 0xf },
- { "ptb1", 0xd, 0xf },
- { "ivar0", 0xe, 0xf },
- { "ivar1", 0xf, 0xf },
- { 0 , 0x0, 0xf }
-};
-
-static const struct ns32k_option list_P032[]= /* lpr spr */
-{
- { "upsr", 0x0, 0xf },
- { "fp", 0x8, 0xf },
- { "sp", 0x9, 0xf },
- { "sb", 0xa, 0xf },
- { "psr", 0xb, 0xf },
- { "intbase", 0xe, 0xf },
- { "mod", 0xf, 0xf },
- { 0 , 0x0, 0xf }
-};
-
-static const struct ns32k_option list_M032[]= /* lmr smr */
-{
- { "bpr0", 0x0, 0xf },
- { "bpr1", 0x1, 0xf },
- { "pf0", 0x4, 0xf },
- { "pf1", 0x5, 0xf },
- { "sc", 0x8, 0xf },
- { "msr", 0xa, 0xf },
- { "bcnt", 0xb, 0xf },
- { "ptb0", 0xc, 0xf },
- { "ptb1", 0xd, 0xf },
- { "eia", 0xf, 0xf },
- { 0 , 0x0, 0xf }
-};
-
-
-/*
- * figure out which options are present
- */
-static void
-optlist(options, optionP, result)
- int options;
- const struct ns32k_option *optionP;
- char *result;
-{
- if (options == 0) {
- sprintf(result, "[]");
- return;
- }
- sprintf(result, "[");
-
- for (; (options != 0) && optionP->pattern; optionP++) {
- if ((options & optionP->match) == optionP->value) {
- /* we found a match, update result and options */
- strcat(result, optionP->pattern);
- options &= ~optionP->value;
- if (options != 0) /* more options to come */
- strcat(result, ",");
- }
- }
- if (options != 0)
- strcat(result, "undefined");
-
- strcat(result, "]");
-}
-
-static void
-list_search (reg_value, optionP, result)
- int reg_value;
- const struct ns32k_option *optionP;
- char *result;
-{
- for (; optionP->pattern; optionP++) {
- if ((reg_value & optionP->match) == optionP->value) {
- sprintf(result, "%s", optionP->pattern);
- return;
- }
- }
- sprintf(result, "undefined");
-}
-
-/*
- * extract "count" bits starting "offset" bits
- * into buffer
- */
-
-static int
-bit_extract (buffer, offset, count)
- bfd_byte *buffer;
- int offset;
- int count;
-{
- int result;
- int bit;
-
- buffer += offset >> 3;
- offset &= 7;
- bit = 1;
- result = 0;
- while (count--)
- {
- FETCH_DATA(dis_info, buffer + 1);
- if ((*buffer & (1 << offset)))
- result |= bit;
- if (++offset == 8)
- {
- offset = 0;
- buffer++;
- }
- bit <<= 1;
- }
- return result;
-}
-
-/* Like bit extract but the buffer is valid and doen't need to be
- * fetched
- */
-static int
-bit_extract_simple (buffer, offset, count)
- bfd_byte *buffer;
- int offset;
- int count;
-{
- int result;
- int mask;
- int bit;
-
- buffer += offset >> 3;
- offset &= 7;
- bit = 1;
- result = 0;
- while (count--)
- {
- if ((*buffer & (1 << offset)))
- result |= bit;
- if (++offset == 8)
- {
- offset = 0;
- buffer++;
- }
- bit <<= 1;
- }
- return result;
-}
-
-static void
-bit_copy (buffer, offset, count, to)
- char *buffer;
- int offset;
- int count;
- char *to;
-{
- for(; count > 8; count -= 8, to++, offset += 8)
- *to = bit_extract (buffer, offset, 8);
- *to = bit_extract (buffer, offset, count);
-}
-
-
-static int
-sign_extend (value, bits)
- int value, bits;
-{
- value = value & ((1 << bits) - 1);
- return (value & (1 << (bits-1))
- ? value | (~((1 << bits) - 1))
- : value);
-}
-
-static void
-flip_bytes (ptr, count)
- char *ptr;
- int count;
-{
- char tmp;
-
- while (count > 0)
- {
- tmp = ptr[0];
- ptr[0] = ptr[count-1];
- ptr[count-1] = tmp;
- ptr++;
- count -= 2;
- }
-}
-
-/* Given a character C, does it represent a general addressing mode? */
-#define Is_gen(c) \
- ((c) == 'F' || (c) == 'L' || (c) == 'B' \
- || (c) == 'W' || (c) == 'D' || (c) == 'A' || (c) == 'I' || (c) == 'Z')
-
-/* Adressing modes. */
-#define Adrmod_index_byte 0x1c
-#define Adrmod_index_word 0x1d
-#define Adrmod_index_doubleword 0x1e
-#define Adrmod_index_quadword 0x1f
-
-/* Is MODE an indexed addressing mode? */
-#define Adrmod_is_index(mode) \
- (mode == Adrmod_index_byte \
- || mode == Adrmod_index_word \
- || mode == Adrmod_index_doubleword \
- || mode == Adrmod_index_quadword)
-
-
-/* Print the 32000 instruction at address MEMADDR in debugged memory,
- on STREAM. Returns length of the instruction, in bytes. */
-
-int
-print_insn_ns32k (memaddr, info)
- bfd_vma memaddr;
- disassemble_info *info;
-{
- register unsigned int i;
- register char *d;
- unsigned short first_word;
- int ioffset; /* bits into instruction */
- int aoffset; /* bits into arguments */
- char arg_bufs[MAX_ARGS+1][ARG_LEN];
- int argnum;
- int maxarg;
- struct private priv;
- bfd_byte *buffer = priv.the_buffer;
- dis_info = info;
-
- info->private_data = (PTR) &priv;
- priv.max_fetched = priv.the_buffer;
- priv.insn_start = memaddr;
- if (setjmp (priv.bailout) != 0)
- /* Error return. */
- return -1;
-
- /* Look for 8bit opcodes first. Other wise, fetching two bytes could take
- * us over the end of accessible data unnecessarilly
- */
- FETCH_DATA(info, buffer + 1);
- for (i = 0; i < NOPCODES; i++)
- if (ns32k_opcodes[i].opcode_id_size <= 8
- && ((buffer[0]
- & (((unsigned long) 1 << ns32k_opcodes[i].opcode_id_size) - 1))
- == ns32k_opcodes[i].opcode_seed))
- break;
- if (i == NOPCODES) {
- /* Maybe it is 9 to 16 bits big */
- FETCH_DATA(info, buffer + 2);
- first_word = read_memory_integer(buffer, 2);
-
- for (i = 0; i < NOPCODES; i++)
- if ((first_word
- & (((unsigned long) 1 << ns32k_opcodes[i].opcode_id_size) - 1))
- == ns32k_opcodes[i].opcode_seed)
- break;
-
- /* Handle undefined instructions. */
- if (i == NOPCODES)
- {
- (*dis_info->fprintf_func)(dis_info->stream, "0%o", buffer[0]);
- return 1;
- }
- }
-
- (*dis_info->fprintf_func)(dis_info->stream, "%s", ns32k_opcodes[i].name);
-
- ioffset = ns32k_opcodes[i].opcode_size;
- aoffset = ns32k_opcodes[i].opcode_size;
- d = ns32k_opcodes[i].operands;
-
- if (*d)
- {
- /* Offset in bits of the first thing beyond each index byte.
- Element 0 is for operand A and element 1 is for operand B.
- The rest are irrelevant, but we put them here so we don't
- index outside the array. */
- int index_offset[MAX_ARGS];
-
- /* 0 for operand A, 1 for operand B, greater for other args. */
- int whicharg = 0;
-
- (*dis_info->fprintf_func)(dis_info->stream, "\t");
-
- maxarg = 0;
-
- /* First we have to find and keep track of the index bytes,
- if we are using scaled indexed addressing mode, since the index
- bytes occur right after the basic instruction, not as part
- of the addressing extension. */
- if (Is_gen(d[1]))
- {
- int addr_mode = bit_extract (buffer, ioffset - 5, 5);
-
- if (Adrmod_is_index (addr_mode))
- {
- aoffset += 8;
- index_offset[0] = aoffset;
- }
- }
- if (d[2] && Is_gen(d[3]))
- {
- int addr_mode = bit_extract (buffer, ioffset - 10, 5);
-
- if (Adrmod_is_index (addr_mode))
- {
- aoffset += 8;
- index_offset[1] = aoffset;
- }
- }
-
- while (*d)
- {
- argnum = *d - '1';
- d++;
- if (argnum > maxarg && argnum < MAX_ARGS)
- maxarg = argnum;
- ioffset = print_insn_arg (*d, ioffset, &aoffset, buffer,
- memaddr, arg_bufs[argnum],
- index_offset[whicharg]);
- d++;
- whicharg++;
- }
- for (argnum = 0; argnum <= maxarg; argnum++)
- {
- bfd_vma addr;
- char *ch;
- for (ch = arg_bufs[argnum]; *ch;)
- {
- if (*ch == NEXT_IS_ADDR)
- {
- ++ch;
- addr = bfd_scan_vma (ch, NULL, 16);
- (*dis_info->print_address_func) (addr, dis_info);
- while (*ch && *ch != NEXT_IS_ADDR)
- ++ch;
- if (*ch)
- ++ch;
- }
- else
- (*dis_info->fprintf_func)(dis_info->stream, "%c", *ch++);
- }
- if (argnum < maxarg)
- (*dis_info->fprintf_func)(dis_info->stream, ", ");
- }
- }
- return aoffset / 8;
-}
-
-/* Print an instruction operand of category given by d. IOFFSET is
- the bit position below which small (<1 byte) parts of the operand can
- be found (usually in the basic instruction, but for indexed
- addressing it can be in the index byte). AOFFSETP is a pointer to the
- bit position of the addressing extension. BUFFER contains the
- instruction. ADDR is where BUFFER was read from. Put the disassembled
- version of the operand in RESULT. INDEX_OFFSET is the bit position
- of the index byte (it contains garbage if this operand is not a
- general operand using scaled indexed addressing mode). */
-
-static int
-print_insn_arg (d, ioffset, aoffsetp, buffer, addr, result, index_offset)
- int d;
- int ioffset, *aoffsetp;
- char *buffer;
- bfd_vma addr;
- char *result;
- int index_offset;
-{
- int addr_mode;
- float Fvalue;
- double Lvalue;
- int Ivalue;
- int disp1, disp2;
- int index;
- int size;
-
- switch (d)
- {
- case 'f':
- /* a "gen" operand but 5 bits from the end of instruction */
- ioffset -= 5;
- case 'Z':
- case 'F':
- case 'L':
- case 'I':
- case 'B':
- case 'W':
- case 'D':
- case 'A':
- addr_mode = bit_extract (buffer, ioffset-5, 5);
- ioffset -= 5;
- switch (addr_mode)
- {
- case 0x0: case 0x1: case 0x2: case 0x3:
- case 0x4: case 0x5: case 0x6: case 0x7:
- /* register mode R0 -- R7 */
- switch (d)
- {
- case 'F':
- case 'L':
- case 'Z':
- sprintf (result, "f%d", addr_mode);
- break;
- default:
- sprintf (result, "r%d", addr_mode);
- }
- break;
- case 0x8: case 0x9: case 0xa: case 0xb:
- case 0xc: case 0xd: case 0xe: case 0xf:
- /* Register relative disp(R0 -- R7) */
- disp1 = get_displacement (buffer, aoffsetp);
- sprintf (result, "%d(r%d)", disp1, addr_mode & 7);
- break;
- case 0x10:
- case 0x11:
- case 0x12:
- /* Memory relative disp2(disp1(FP, SP, SB)) */
- disp1 = get_displacement (buffer, aoffsetp);
- disp2 = get_displacement (buffer, aoffsetp);
- sprintf (result, "%d(%d(%s))", disp2, disp1,
- addr_mode==0x10?"fp":addr_mode==0x11?"sp":"sb");
- break;
- case 0x13:
- /* reserved */
- sprintf (result, "reserved");
- break;
- case 0x14:
- /* Immediate */
- switch (d)
- {
- case 'I': case 'Z': case 'A':
- /* I and Z are output operands and can`t be immediate
- * A is an address and we can`t have the address of
- * an immediate either. We don't know how much to increase
- * aoffsetp by since whatever generated this is broken
- * anyway!
- */
- sprintf (result, _("$<undefined>"));
- break;
- case 'B':
- Ivalue = bit_extract (buffer, *aoffsetp, 8);
- Ivalue = sign_extend (Ivalue, 8);
- *aoffsetp += 8;
- sprintf (result, "$%d", Ivalue);
- break;
- case 'W':
- Ivalue = bit_extract (buffer, *aoffsetp, 16);
- flip_bytes (&Ivalue, 2);
- *aoffsetp += 16;
- Ivalue = sign_extend (Ivalue, 16);
- sprintf (result, "$%d", Ivalue);
- break;
- case 'D':
- Ivalue = bit_extract (buffer, *aoffsetp, 32);
- flip_bytes (&Ivalue, 4);
- *aoffsetp += 32;
- sprintf (result, "$%d", Ivalue);
- break;
- case 'F':
- bit_copy (buffer, *aoffsetp, 32, (char *) &Fvalue);
- flip_bytes (&Fvalue, 4);
- *aoffsetp += 32;
- if (INVALID_FLOAT (&Fvalue, 4))
- sprintf (result, "<<invalid float 0x%.8x>>", *(int *) &Fvalue);
- else /* assume host has ieee float */
- sprintf (result, "$%g", Fvalue);
- break;
- case 'L':
- bit_copy (buffer, *aoffsetp, 64, (char *) &Lvalue);
- flip_bytes (&Lvalue, 8);
- *aoffsetp += 64;
- if (INVALID_FLOAT (&Lvalue, 8))
- sprintf (result, "<<invalid long 0x%.8x%.8x>>",
- *(((int *) &Lvalue) + 1), *(int *) &Lvalue);
- else /* assume host has ieee float */
- sprintf (result, "$%g", Lvalue);
- break;
- }
- break;
- case 0x15:
- /* Absolute @disp */
- disp1 = get_displacement (buffer, aoffsetp);
- sprintf (result, "@|%d|", disp1);
- break;
- case 0x16:
- /* External EXT(disp1) + disp2 (Mod table stuff) */
- disp1 = get_displacement (buffer, aoffsetp);
- disp2 = get_displacement (buffer, aoffsetp);
- sprintf (result, "EXT(%d) + %d", disp1, disp2);
- break;
- case 0x17:
- /* Top of stack tos */
- sprintf (result, "tos");
- break;
- case 0x18:
- /* Memory space disp(FP) */
- disp1 = get_displacement (buffer, aoffsetp);
- sprintf (result, "%d(fp)", disp1);
- break;
- case 0x19:
- /* Memory space disp(SP) */
- disp1 = get_displacement (buffer, aoffsetp);
- sprintf (result, "%d(sp)", disp1);
- break;
- case 0x1a:
- /* Memory space disp(SB) */
- disp1 = get_displacement (buffer, aoffsetp);
- sprintf (result, "%d(sb)", disp1);
- break;
- case 0x1b:
- /* Memory space disp(PC) */
- disp1 = get_displacement (buffer, aoffsetp);
- *result++ = NEXT_IS_ADDR;
- sprintf_vma (result, addr + disp1);
- result += strlen (result);
- *result++ = NEXT_IS_ADDR;
- *result = '\0';
- break;
- case 0x1c:
- case 0x1d:
- case 0x1e:
- case 0x1f:
- /* Scaled index basemode[R0 -- R7:B,W,D,Q] */
- index = bit_extract (buffer, index_offset - 8, 3);
- print_insn_arg (d, index_offset, aoffsetp, buffer, addr,
- result, 0);
- {
- static const char *ind = "bwdq";
- char *off;
-
- off = result + strlen (result);
- sprintf (off, "[r%d:%c]", index,
- ind[addr_mode & 3]);
- }
- break;
- }
- break;
- case 'H':
- case 'q':
- Ivalue = bit_extract (buffer, ioffset-4, 4);
- Ivalue = sign_extend (Ivalue, 4);
- sprintf (result, "%d", Ivalue);
- ioffset -= 4;
- break;
- case 'r':
- Ivalue = bit_extract (buffer, ioffset-3, 3);
- sprintf (result, "r%d", Ivalue&7);
- ioffset -= 3;
- break;
- case 'd':
- sprintf (result, "%d", get_displacement (buffer, aoffsetp));
- break;
- case 'b':
- Ivalue = get_displacement (buffer, aoffsetp);
- /*
- * Warning!! HACK ALERT!
- * Operand type 'b' is only used by the cmp{b,w,d} and
- * movm{b,w,d} instructions; we need to know whether
- * it's a `b' or `w' or `d' instruction; and for both
- * cmpm and movm it's stored at the same place so we
- * just grab two bits of the opcode and look at it...
- *
- */
- size = bit_extract(buffer, ioffset-6, 2);
- if (size == 0) /* 00 => b */
- size = 1;
- else if (size == 1) /* 01 => w */
- size = 2;
- else
- size = 4; /* 11 => d */
-
- sprintf (result, "%d", (Ivalue / size) + 1);
- break;
- case 'p':
- *result++ = NEXT_IS_ADDR;
- sprintf_vma (result, addr + get_displacement (buffer, aoffsetp));
- result += strlen (result);
- *result++ = NEXT_IS_ADDR;
- *result = '\0';
- break;
- case 'i':
- Ivalue = bit_extract (buffer, *aoffsetp, 8);
- *aoffsetp += 8;
- sprintf (result, "0x%x", Ivalue);
- break;
- case 'u':
- Ivalue = bit_extract (buffer, *aoffsetp, 8);
- optlist(Ivalue, opt_u, result);
- *aoffsetp += 8;
- break;
- case 'U':
- Ivalue = bit_extract(buffer, *aoffsetp, 8);
- optlist(Ivalue, opt_U, result);
- *aoffsetp += 8;
- break;
- case 'O':
- Ivalue = bit_extract(buffer, ioffset-9, 9);
- optlist(Ivalue, opt_O, result);
- ioffset -= 9;
- break;
- case 'C':
- Ivalue = bit_extract(buffer, ioffset-4, 4);
- optlist(Ivalue, opt_C, result);
- ioffset -= 4;
- break;
- case 'S':
- Ivalue = bit_extract(buffer, ioffset - 8, 8);
- optlist(Ivalue, opt_S, result);
- ioffset -= 8;
- break;
- case 'M':
- Ivalue = bit_extract(buffer, ioffset-4, 4);
- list_search(Ivalue, 0 ? list_M032 : list_M532, result);
- ioffset -= 4;
- break;
- case 'P':
- Ivalue = bit_extract(buffer, ioffset-4, 4);
- list_search(Ivalue, 0 ? list_P032 : list_P532, result);
- ioffset -= 4;
- break;
- case 'g':
- Ivalue = bit_extract(buffer, *aoffsetp, 3);
- sprintf(result, "%d", Ivalue);
- *aoffsetp += 3;
- break;
- case 'G':
- Ivalue = bit_extract(buffer, *aoffsetp, 5);
- sprintf(result, "%d", Ivalue + 1);
- *aoffsetp += 5;
- break;
- }
- return ioffset;
-}
-
-static int
-get_displacement (buffer, aoffsetp)
- char *buffer;
- int *aoffsetp;
-{
- int Ivalue;
- short Ivalue2;
-
- Ivalue = bit_extract (buffer, *aoffsetp, 8);
- switch (Ivalue & 0xc0)
- {
- case 0x00:
- case 0x40:
- Ivalue = sign_extend (Ivalue, 7);
- *aoffsetp += 8;
- break;
- case 0x80:
- Ivalue2 = bit_extract (buffer, *aoffsetp, 16);
- flip_bytes (&Ivalue2, 2);
- Ivalue = sign_extend (Ivalue2, 14);
- *aoffsetp += 16;
- break;
- case 0xc0:
- Ivalue = bit_extract (buffer, *aoffsetp, 32);
- flip_bytes (&Ivalue, 4);
- Ivalue = sign_extend (Ivalue, 30);
- *aoffsetp += 32;
- break;
- }
- return Ivalue;
-}
-
-
-#if 1 /* a version that should work on ns32k f's&d's on any machine */
-static int
-invalid_float (p, len)
- register char *p;
- register int len;
-{
- register int val;
-
- if ( len == 4 )
- val = (bit_extract_simple(p, 23, 8)/*exponent*/ == 0xff
- || (bit_extract_simple(p, 23, 8)/*exponent*/ == 0 &&
- bit_extract_simple(p, 0, 23)/*mantisa*/ != 0));
- else if ( len == 8 )
- val = (bit_extract_simple(p, 52, 11)/*exponent*/ == 0x7ff
- || (bit_extract_simple(p, 52, 11)/*exponent*/ == 0
- && (bit_extract_simple(p, 0, 32)/*low mantisa*/ != 0
- || bit_extract_simple(p, 32, 20)/*high mantisa*/ != 0)));
- else
- val = 1;
- return (val);
-}
-#else
-
-/* assumes the bytes have been swapped to local order */
-typedef union { double d;
- float f;
- struct { unsigned m:23, e:8, :1;} sf;
- struct { unsigned lm; unsigned m:20, e:11, :1;} sd;
- } float_type_u;
-
-static int
-invalid_float (p, len)
- register float_type_u *p;
- register int len;
-{
- register int val;
- if ( len == sizeof (float) )
- val = (p->sf.e == 0xff
- || (p->sf.e == 0 && p->sf.m != 0));
- else if ( len == sizeof (double) )
- val = (p->sd.e == 0x7ff
- || (p->sd.e == 0 && (p->sd.m != 0 || p->sd.lm != 0)));
- else
- val = 1;
- return (val);
-}
-#endif