/* tc-mmix.c -- Assembler for Don Knuth's MMIX.
   Copyright (C) 2001-2021 Free Software Foundation, Inc.

   This file is part of GAS, the GNU Assembler.

   GAS 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, or (at your option)
   any later version.

   GAS 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 GAS; see the file COPYING.  If not, write to
   the Free Software Foundation, 51 Franklin Street - Fifth Floor,
   Boston, MA 02110-1301, USA.  */

/* Knuth's assembler mmixal does not provide a relocatable format; mmo is
   to be considered a final link-format.  In the final link, we make mmo,
   but for relocatable files, we use ELF.

   One goal is to provide a superset of what mmixal does, including
   compatible syntax, but the main purpose is to serve GCC.  */


#include "as.h"
#include <limits.h>
#include "subsegs.h"
#include "elf/mmix.h"
#include "opcode/mmix.h"
#include "safe-ctype.h"
#include "dwarf2dbg.h"
#include "obstack.h"

/* Something to describe what we need to do with a fixup before output,
   for example assert something of what it became or make a relocation.  */

enum mmix_fixup_action
{
  mmix_fixup_byte,
  mmix_fixup_register,
  mmix_fixup_register_or_adjust_for_byte
};

static int get_spec_regno (char *);
static int get_operands (int, char *, expressionS *);
static int get_putget_operands (struct mmix_opcode *, char *, expressionS *);
static void s_prefix (int);
static void s_greg (int);
static void s_loc (int);
static void s_bspec (int);
static void s_espec (int);
static void mmix_s_local (int);
static void mmix_greg_internal (char *);
static void mmix_set_geta_branch_offset (char *, offsetT);
static void mmix_set_jmp_offset (char *, offsetT);
static void mmix_fill_nops (char *, int);
static int cmp_greg_symbol_fixes (const void *, const void *);
static int cmp_greg_val_greg_symbol_fixes (const void *, const void *);
static void mmix_handle_rest_of_empty_line (void);
static void mmix_discard_rest_of_line (void);
static void mmix_byte (void);
static void mmix_cons (int);

/* Continue the tradition of symbols.c; use control characters to enforce
   magic.  These are used when replacing e.g. 8F and 8B so we can handle
   such labels correctly with the common parser hooks.  */
#define MAGIC_FB_BACKWARD_CHAR '\003'
#define MAGIC_FB_FORWARD_CHAR '\004'

/* Copy the location of a frag to a fix.  */
#define COPY_FR_WHERE_TO_FX(FRAG, FIX)		\
 do						\
   {						\
     (FIX)->fx_file = (FRAG)->fr_file;		\
     (FIX)->fx_line = (FRAG)->fr_line;		\
   }						\
 while (0)

const char *md_shortopts = "x";
static int current_fb_label = -1;
static char *pending_label = NULL;

static bfd_vma lowest_text_loc = (bfd_vma) -1;
static int text_has_contents = 0;

/* The alignment of the previous instruction, and a boolean for whether we
   want to avoid aligning the next WYDE, TETRA, OCTA or insn.  */
static int last_alignment = 0;
static int want_unaligned = 0;

static bfd_vma lowest_data_loc = (bfd_vma) -1;
static int data_has_contents = 0;

/* The fragS of the instruction being assembled.  Only valid from within
   md_assemble.  */
fragS *mmix_opcode_frag = NULL;

/* Raw GREGs as appearing in input.  These may be fewer than the number
   after relaxing.  */
static int n_of_raw_gregs = 0;
static struct
 {
   char *label;
   expressionS exp;
 } mmix_raw_gregs[MAX_GREGS];

static struct loc_assert_s
 {
   segT old_seg;
   symbolS *loc_sym;
   fragS *frag;
   struct loc_assert_s *next;
 } *loc_asserts = NULL;

/* Fixups for all unique GREG registers.  We store the fixups here in
   md_convert_frag, then we use the array to convert
   BFD_RELOC_MMIX_BASE_PLUS_OFFSET fixups in tc_gen_reloc.  The index is
   just a running number and is not supposed to be correlated to a
   register number.  */
static fixS *mmix_gregs[MAX_GREGS];
static int n_of_cooked_gregs = 0;

/* Pointing to the register section we use for output.  */
static asection *real_reg_section;

/* For each symbol; unknown or section symbol, we keep a list of GREG
   definitions sorted on increasing offset.  It seems no use keeping count
   to allocate less room than the maximum number of gregs when we've found
   one for a section or symbol.  */
struct mmix_symbol_gregs
 {
   int n_gregs;
   struct mmix_symbol_greg_fixes
   {
     fixS *fix;

     /* A signed type, since we may have GREGs pointing slightly before the
	contents of a section.  */
     offsetT offs;
   } greg_fixes[MAX_GREGS];
 };

/* Should read insert a colon on something that starts in column 0 on
   this line?  */
static int label_without_colon_this_line = 1;

/* Should we automatically expand instructions into multiple insns in
   order to generate working code?  */
static int expand_op = 1;

/* Should we warn when expanding operands?  FIXME: test-cases for when -x
   is absent.  */
static int warn_on_expansion = 1;

/* Should we merge non-zero GREG register definitions?  */
static int merge_gregs = 1;

/* Should we pass on undefined BFD_RELOC_MMIX_BASE_PLUS_OFFSET relocs
   (missing suitable GREG definitions) to the linker?  */
static int allocate_undefined_gregs_in_linker = 0;

/* Should we emit built-in symbols?  */
static int predefined_syms = 1;

/* Should we allow anything but the listed special register name
   (e.g. equated symbols)?  */
static int equated_spec_regs = 1;

/* Do we require standard GNU syntax?  */
int mmix_gnu_syntax = 0;

/* Do we globalize all symbols?  */
int mmix_globalize_symbols = 0;

/* When expanding insns, do we want to expand PUSHJ as a call to a stub
   (or else as a series of insns)?  */
int pushj_stubs = 1;

/* Do we know that the next semicolon is at the end of the operands field
   (in mmixal mode; constant 1 in GNU mode)?  */
int mmix_next_semicolon_is_eoln = 1;

/* Do we have a BSPEC in progress?  */
static int doing_bspec = 0;
static const char *bspec_file;
static unsigned int bspec_line;

struct option md_longopts[] =
 {
#define OPTION_RELAX  (OPTION_MD_BASE)
#define OPTION_NOEXPAND  (OPTION_RELAX + 1)
#define OPTION_NOMERGEGREG  (OPTION_NOEXPAND + 1)
#define OPTION_NOSYMS  (OPTION_NOMERGEGREG + 1)
#define OPTION_GNU_SYNTAX  (OPTION_NOSYMS + 1)
#define OPTION_GLOBALIZE_SYMBOLS  (OPTION_GNU_SYNTAX + 1)
#define OPTION_FIXED_SPEC_REGS  (OPTION_GLOBALIZE_SYMBOLS + 1)
#define OPTION_LINKER_ALLOCATED_GREGS  (OPTION_FIXED_SPEC_REGS + 1)
#define OPTION_NOPUSHJSTUBS  (OPTION_LINKER_ALLOCATED_GREGS + 1)
   {"linkrelax", no_argument, NULL, OPTION_RELAX},
   {"no-expand", no_argument, NULL, OPTION_NOEXPAND},
   {"no-merge-gregs", no_argument, NULL, OPTION_NOMERGEGREG},
   {"no-predefined-syms", no_argument, NULL, OPTION_NOSYMS},
   {"gnu-syntax", no_argument, NULL, OPTION_GNU_SYNTAX},
   {"globalize-symbols", no_argument, NULL, OPTION_GLOBALIZE_SYMBOLS},
   {"fixed-special-register-names", no_argument, NULL,
    OPTION_FIXED_SPEC_REGS},
   {"linker-allocated-gregs", no_argument, NULL,
    OPTION_LINKER_ALLOCATED_GREGS},
   {"no-pushj-stubs", no_argument, NULL, OPTION_NOPUSHJSTUBS},
   {"no-stubs", no_argument, NULL, OPTION_NOPUSHJSTUBS},
   {NULL, no_argument, NULL, 0}
 };

size_t md_longopts_size = sizeof (md_longopts);

static htab_t mmix_opcode_hash;

/* We use these when implementing the PREFIX pseudo.  */
char *mmix_current_prefix;
struct obstack mmix_sym_obstack;


/* For MMIX, we encode the relax_substateT:s (in e.g. fr_substate) as one
   bit length, and the relax-type shifted on top of that.  There seems to
   be no point in making the relaxation more fine-grained; the linker does
   that better and we might interfere by changing non-optimal relaxations
   into other insns that cannot be relaxed as easily.

   Groups for MMIX relaxing:

   1. GETA
      extra length: zero or three insns.

   2. Bcc
      extra length: zero or five insns.

   3. PUSHJ
      extra length: zero or four insns.
      Special handling to deal with transition to PUSHJSTUB.

   4. JMP
      extra length: zero or four insns.

   5. GREG
      special handling, allocates a named global register unless another
      is within reach for all uses.

   6. PUSHJSTUB
      special handling (mostly) for external references; assumes the
      linker will generate a stub if target is no longer than 256k from
      the end of the section plus max size of previous stubs.  Zero or
      four insns.  */

#define STATE_GETA	(1)
#define STATE_BCC	(2)
#define STATE_PUSHJ	(3)
#define STATE_JMP	(4)
#define STATE_GREG	(5)
#define STATE_PUSHJSTUB	(6)

/* No fine-grainedness here.  */
#define STATE_LENGTH_MASK	    (1)

#define STATE_ZERO		    (0)
#define STATE_MAX		    (1)

/* More descriptive name for convenience.  */
/* FIXME: We should start on something different, not MAX.  */
#define STATE_UNDF		    STATE_MAX

/* FIXME: For GREG, we must have other definitions; UNDF == MAX isn't
   appropriate; we need it the other way round.  This value together with
   fragP->tc_frag_data shows what state the frag is in: tc_frag_data
   non-NULL means 0, NULL means 8 bytes.  */
#define STATE_GREG_UNDF ENCODE_RELAX (STATE_GREG, STATE_ZERO)
#define STATE_GREG_DEF ENCODE_RELAX (STATE_GREG, STATE_MAX)

/* These displacements are relative to the address following the opcode
   word of the instruction.  The catch-all states have zero for "reach"
   and "next" entries.  */

#define GETA_0F (65536 * 4 - 8)
#define GETA_0B (-65536 * 4 - 4)

#define GETA_MAX_LEN 4 * 4
#define GETA_3F 0
#define GETA_3B 0

#define BCC_0F GETA_0F
#define BCC_0B GETA_0B

#define BCC_MAX_LEN 6 * 4
#define BCC_5F GETA_3F
#define BCC_5B GETA_3B

#define PUSHJ_0F GETA_0F
#define PUSHJ_0B GETA_0B

#define PUSHJ_MAX_LEN 5 * 4
#define PUSHJ_4F GETA_3F
#define PUSHJ_4B GETA_3B

/* We'll very rarely have sections longer than LONG_MAX, but we'll make a
   feeble attempt at getting 64-bit values.  */
#define PUSHJSTUB_MAX ((offsetT) (((addressT) -1) >> 1))
#define PUSHJSTUB_MIN (-PUSHJSTUB_MAX - 1)

#define JMP_0F (65536 * 256 * 4 - 8)
#define JMP_0B (-65536 * 256 * 4 - 4)

#define JMP_MAX_LEN 5 * 4
#define JMP_4F 0
#define JMP_4B 0

#define RELAX_ENCODE_SHIFT 1
#define ENCODE_RELAX(what, length) (((what) << RELAX_ENCODE_SHIFT) + (length))

const relax_typeS mmix_relax_table[] =
 {
   /* Error sentinel (0, 0).  */
   {1,		1,		0,	0},

   /* Unused (0, 1).  */
   {1,		1,		0,	0},

   /* GETA (1, 0).  */
   {GETA_0F,	GETA_0B,	0,	ENCODE_RELAX (STATE_GETA, STATE_MAX)},

   /* GETA (1, 1).  */
   {GETA_3F,	GETA_3B,
		GETA_MAX_LEN - 4,	0},

   /* BCC (2, 0).  */
   {BCC_0F,	BCC_0B,		0,	ENCODE_RELAX (STATE_BCC, STATE_MAX)},

   /* BCC (2, 1).  */
   {BCC_5F,	BCC_5B,
		BCC_MAX_LEN - 4,	0},

   /* PUSHJ (3, 0).  Next state is actually PUSHJSTUB (6, 0).  */
   {PUSHJ_0F,	PUSHJ_0B,	0,	ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO)},

   /* PUSHJ (3, 1).  */
   {PUSHJ_4F,	PUSHJ_4B,
		PUSHJ_MAX_LEN - 4,	0},

   /* JMP (4, 0).  */
   {JMP_0F,	JMP_0B,		0,	ENCODE_RELAX (STATE_JMP, STATE_MAX)},

   /* JMP (4, 1).  */
   {JMP_4F,	JMP_4B,
		JMP_MAX_LEN - 4,	0},

   /* GREG (5, 0), (5, 1), though the table entry isn't used.  */
   {0, 0, 0, 0}, {0, 0, 0, 0},

   /* PUSHJSTUB (6, 0).  PUSHJ (3, 0) uses the range, so we set it to infinite.  */
   {PUSHJSTUB_MAX, PUSHJSTUB_MIN,
    		0,			ENCODE_RELAX (STATE_PUSHJ, STATE_MAX)},
   /* PUSHJSTUB (6, 1) isn't used.  */
   {0, 0,	PUSHJ_MAX_LEN, 		0}
};

const pseudo_typeS md_pseudo_table[] =
 {
   /* Support " .greg sym,expr" syntax.  */
   {"greg", s_greg, 0},

   /* Support " .bspec expr" syntax.  */
   {"bspec", s_bspec, 1},

   /* Support " .espec" syntax.  */
   {"espec", s_espec, 1},

   /* Support " .local $45" syntax.  */
   {"local", mmix_s_local, 1},

   {NULL, 0, 0}
 };

const char mmix_comment_chars[] = "%!";

/* A ':' is a valid symbol character in mmixal.  It's the prefix
   delimiter, but other than that, it works like a symbol character,
   except that we strip one off at the beginning of symbols.  An '@' is a
   symbol by itself (for the current location); space around it must not
   be stripped.  */
const char mmix_symbol_chars[] = ":@";

const char line_comment_chars[] = "*#";

const char line_separator_chars[] = ";";

const char EXP_CHARS[] = "eE";

const char FLT_CHARS[] = "rf";


/* Fill in the offset-related part of GETA or Bcc.  */

static void
mmix_set_geta_branch_offset (char *opcodep, offsetT value)
{
  if (value < 0)
    {
      value += 65536 * 4;
      opcodep[0] |= 1;
    }

  value /= 4;
  md_number_to_chars (opcodep + 2, value, 2);
}

/* Fill in the offset-related part of JMP.  */

static void
mmix_set_jmp_offset (char *opcodep, offsetT value)
{
  if (value < 0)
    {
      value += 65536 * 256 * 4;
      opcodep[0] |= 1;
    }

  value /= 4;
  md_number_to_chars (opcodep + 1, value, 3);
}

/* Fill in NOP:s for the expanded part of GETA/JMP/Bcc/PUSHJ.  */

static void
mmix_fill_nops (char *opcodep, int n)
{
  int i;

  for (i = 0; i < n; i++)
    md_number_to_chars (opcodep + i * 4, SWYM_INSN_BYTE << 24, 4);
}

/* See macro md_parse_name in tc-mmix.h.  */

int
mmix_current_location (void (*fn) (expressionS *), expressionS *exp)
{
  (*fn) (exp);

  return 1;
}

/* Get up to three operands, filling them into the exp array.
   General idea and code stolen from the tic80 port.  */

static int
get_operands (int max_operands, char *s, expressionS *exp)
{
  char *p = s;
  int numexp = 0;
  int nextchar = ',';

  while (nextchar == ',')
    {
      /* Skip leading whitespace */
      while (*p == ' ' || *p == '\t')
	p++;

      /* Check to see if we have any operands left to parse */
      if (*p == 0 || *p == '\n' || *p == '\r')
	{
	  break;
	}
      else if (numexp == max_operands)
	{
	  /* This seems more sane than saying "too many operands".  We'll
	     get here only if the trailing trash starts with a comma.  */
	  as_bad (_("invalid operands"));
	  mmix_discard_rest_of_line ();
	  return 0;
	}

      /* Begin operand parsing at the current scan point.  */

      input_line_pointer = p;
      expression (&exp[numexp]);

      if (exp[numexp].X_op == O_illegal)
	{
	  as_bad (_("invalid operands"));
	}
      else if (exp[numexp].X_op == O_absent)
	{
	  as_bad (_("missing operand"));
	}

      numexp++;
      p = input_line_pointer;

      /* Skip leading whitespace */
      while (*p == ' ' || *p == '\t')
	p++;
      nextchar = *p++;
    }

  /* If we allow "naked" comments, ignore the rest of the line.  */
  if (nextchar != ',')
    {
      mmix_handle_rest_of_empty_line ();
      input_line_pointer--;
    }

  /* Mark the end of the valid operands with an illegal expression.  */
  exp[numexp].X_op = O_illegal;

  return (numexp);
}

/* Get the value of a special register, or -1 if the name does not match
   one.  NAME is a null-terminated string.  */

static int
get_spec_regno (char *name)
{
  int i;

  if (name == NULL)
    return -1;

  if (*name == ':')
    name++;

  /* Well, it's a short array and we'll most often just match the first
     entry, rJ.  */
  for (i = 0; mmix_spec_regs[i].name != NULL; i++)
    if (strcmp (name, mmix_spec_regs[i].name) == 0)
      return mmix_spec_regs[i].number;

  return -1;
}

/* For GET and PUT, parse the register names "manually", so we don't use
   user labels.  */
static int
get_putget_operands (struct mmix_opcode *insn, char *operands,
		     expressionS *exp)
{
  expressionS *expp_reg;
  expressionS *expp_sreg;
  char *sregp = NULL;
  char *sregend = operands;
  char *p = operands;
  char c = *sregend;
  int regno;

  /* Skip leading whitespace */
  while (*p == ' ' || *p == '\t')
    p++;

  input_line_pointer = p;

  /* Initialize both possible operands to error state, in case we never
     get further.  */
  exp[0].X_op = O_illegal;
  exp[1].X_op = O_illegal;

  if (insn->operands == mmix_operands_get)
    {
      expp_reg = &exp[0];
      expp_sreg = &exp[1];

      expression (expp_reg);

      p = input_line_pointer;

      /* Skip whitespace */
      while (*p == ' ' || *p == '\t')
	p++;

      if (*p == ',')
	{
	  p++;

	  /* Skip whitespace */
	  while (*p == ' ' || *p == '\t')
	    p++;
	  sregp = p;
	  input_line_pointer = sregp;
	  c = get_symbol_name (&sregp);
	  sregend = input_line_pointer;
	  if (c == '"')
	    ++ input_line_pointer;
	}
    }
  else
    {
      expp_sreg = &exp[0];
      expp_reg = &exp[1];

      c = get_symbol_name (&sregp);
      sregend = input_line_pointer;
      restore_line_pointer (c);
      p = input_line_pointer;

      /* Skip whitespace */
      while (*p == ' ' || *p == '\t')
	p++;

      if (*p == ',')
	{
	  p++;

	  /* Skip whitespace */
	  while (*p == ' ' || *p == '\t')
	    p++;

	  input_line_pointer = p;
	  expression (expp_reg);
	}
      *sregend = 0;
    }

  regno = get_spec_regno (sregp);
  *sregend = c;

  /* Let the caller issue errors; we've made sure the operands are
     invalid.  */
  if (expp_reg->X_op != O_illegal
      && expp_reg->X_op != O_absent
      && regno != -1)
    {
      expp_sreg->X_op = O_register;
      expp_sreg->X_add_number = regno + 256;
    }

  return 2;
}

/* Handle MMIX-specific option.  */

int
md_parse_option (int c, const char *arg ATTRIBUTE_UNUSED)
{
  switch (c)
    {
    case 'x':
      warn_on_expansion = 0;
      allocate_undefined_gregs_in_linker = 1;
      break;

    case OPTION_RELAX:
      linkrelax = 1;
      break;

    case OPTION_NOEXPAND:
      expand_op = 0;
      break;

    case OPTION_NOMERGEGREG:
      merge_gregs = 0;
      break;

    case OPTION_NOSYMS:
      predefined_syms = 0;
      equated_spec_regs = 0;
      break;

    case OPTION_GNU_SYNTAX:
      mmix_gnu_syntax = 1;
      label_without_colon_this_line = 0;
      break;

    case OPTION_GLOBALIZE_SYMBOLS:
      mmix_globalize_symbols = 1;
      break;

    case OPTION_FIXED_SPEC_REGS:
      equated_spec_regs = 0;
      break;

    case OPTION_LINKER_ALLOCATED_GREGS:
      allocate_undefined_gregs_in_linker = 1;
      break;

    case OPTION_NOPUSHJSTUBS:
      pushj_stubs = 0;
      break;

    default:
      return 0;
    }

  return 1;
}

/* Display MMIX-specific help text.  */

void
md_show_usage (FILE * stream)
{
  fprintf (stream, _(" MMIX-specific command line options:\n"));
  fprintf (stream, _("\
  -fixed-special-register-names\n\
                          Allow only the original special register names.\n"));
  fprintf (stream, _("\
  -globalize-symbols      Make all symbols global.\n"));
  fprintf (stream, _("\
  -gnu-syntax             Turn off mmixal syntax compatibility.\n"));
  fprintf (stream, _("\
  -relax                  Create linker relaxable code.\n"));
  fprintf (stream, _("\
  -no-predefined-syms     Do not provide mmixal built-in constants.\n\
                          Implies -fixed-special-register-names.\n"));
  fprintf (stream, _("\
  -no-expand              Do not expand GETA, branches, PUSHJ or JUMP\n\
                          into multiple instructions.\n"));
  fprintf (stream, _("\
  -no-merge-gregs         Do not merge GREG definitions with nearby values.\n"));
  fprintf (stream, _("\
  -linker-allocated-gregs If there's no suitable GREG definition for the\
                          operands of an instruction, let the linker resolve.\n"));
  fprintf (stream, _("\
  -x                      Do not warn when an operand to GETA, a branch,\n\
                          PUSHJ or JUMP is not known to be within range.\n\
                          The linker will catch any errors.  Implies\n\
                          -linker-allocated-gregs."));
}

/* Step to end of line, but don't step over the end of the line.  */

static void
mmix_discard_rest_of_line (void)
{
  while (*input_line_pointer
	 && (! is_end_of_line[(unsigned char) *input_line_pointer]
	     || TC_EOL_IN_INSN (input_line_pointer)))
    input_line_pointer++;
}

/* Act as demand_empty_rest_of_line if we're in strict GNU syntax mode,
   otherwise just ignore the rest of the line (and skip the end-of-line
   delimiter).  */

static void
mmix_handle_rest_of_empty_line (void)
{
  if (mmix_gnu_syntax)
    demand_empty_rest_of_line ();
  else
    {
      mmix_discard_rest_of_line ();
      input_line_pointer++;
    }
}

/* Initialize GAS MMIX specifics.  */

void
mmix_md_begin (void)
{
  int i;
  const struct mmix_opcode *opcode;

  /* We assume nobody will use this, so don't allocate any room.  */
  obstack_begin (&mmix_sym_obstack, 0);

  /* This will break the day the "lex" thingy changes.  For now, it's the
     only way to make ':' part of a name, and a name beginner.  */
  lex_type[':'] = (LEX_NAME | LEX_BEGIN_NAME);

  mmix_opcode_hash = str_htab_create ();

  real_reg_section
    = bfd_make_section_old_way (stdoutput, MMIX_REG_SECTION_NAME);

  for (opcode = mmix_opcodes; opcode->name; opcode++)
    str_hash_insert (mmix_opcode_hash, opcode->name, opcode, 0);

  /* We always insert the ordinary registers 0..255 as registers.  */
  for (i = 0; i < 256; i++)
    {
      char buf[16];

      /* Alternatively, we could diddle with '$' and the following number,
	 but keeping the registers as symbols helps keep parsing simple.  */
      sprintf (buf, "$%d", i);
      symbol_table_insert (symbol_new (buf, reg_section,
				       &zero_address_frag, i));
    }

  /* Insert mmixal built-in names if allowed.  */
  if (predefined_syms)
    {
      for (i = 0; mmix_spec_regs[i].name != NULL; i++)
	symbol_table_insert (symbol_new (mmix_spec_regs[i].name,
					 reg_section,
					 &zero_address_frag,
					 mmix_spec_regs[i].number + 256));

      /* FIXME: Perhaps these should be recognized as specials; as field
	 names for those instructions.  */
      symbol_table_insert (symbol_new ("ROUND_CURRENT", reg_section,
				       &zero_address_frag, 512));
      symbol_table_insert (symbol_new ("ROUND_OFF", reg_section,
				       &zero_address_frag, 512 + 1));
      symbol_table_insert (symbol_new ("ROUND_UP", reg_section,
				       &zero_address_frag, 512 + 2));
      symbol_table_insert (symbol_new ("ROUND_DOWN", reg_section,
				       &zero_address_frag, 512 + 3));
      symbol_table_insert (symbol_new ("ROUND_NEAR", reg_section,
				       &zero_address_frag, 512 + 4));
    }
}

/* Assemble one insn in STR.  */

void
md_assemble (char *str)
{
  char *operands = str;
  char modified_char = 0;
  struct mmix_opcode *instruction;
  fragS *opc_fragP = NULL;
  int max_operands = 3;

  /* Note that the struct frag member fr_literal in frags.h is char[], so
     I have to make this a plain char *.  */
  /* unsigned */ char *opcodep = NULL;

  expressionS exp[4];
  int n_operands = 0;

  /* Move to end of opcode.  */
  for (operands = str;
       is_part_of_name (*operands);
       ++operands)
    ;

  if (ISSPACE (*operands))
    {
      modified_char = *operands;
      *operands++ = '\0';
    }

  instruction = (struct mmix_opcode *) str_hash_find (mmix_opcode_hash, str);
  if (instruction == NULL)
    {
      as_bad (_("unknown opcode: `%s'"), str);

      /* Avoid "unhandled label" errors.  */
      pending_label = NULL;
      return;
    }

  /* Put back the character after the opcode.  */
  if (modified_char != 0)
    operands[-1] = modified_char;

  input_line_pointer = operands;

  /* Is this a mmixal pseudodirective?  */
  if (instruction->type == mmix_type_pseudo)
    {
      /* For mmixal compatibility, a label for an instruction (and
	 emitting pseudo) refers to the _aligned_ address.  We emit the
	 label here for the pseudos that don't handle it themselves.  When
	 having an fb-label, emit it here, and increment the counter after
	 the pseudo.  */
      switch (instruction->operands)
	{
	case mmix_operands_loc:
	case mmix_operands_byte:
	case mmix_operands_prefix:
	case mmix_operands_local:
	case mmix_operands_bspec:
	case mmix_operands_espec:
	  if (current_fb_label >= 0)
	    colon (fb_label_name (current_fb_label, 1));
	  else if (pending_label != NULL)
	    {
	      colon (pending_label);
	      pending_label = NULL;
	    }
	  break;

	default:
	  break;
	}

      /* Some of the pseudos emit contents, others don't.  Set a
	 contents-emitted flag when we emit something into .text   */
      switch (instruction->operands)
	{
	case mmix_operands_loc:
	  /* LOC */
	  s_loc (0);
	  break;

	case mmix_operands_byte:
	  /* BYTE */
	  mmix_byte ();
	  break;

	case mmix_operands_wyde:
	  /* WYDE */
	  mmix_cons (2);
	  break;

	case mmix_operands_tetra:
	  /* TETRA */
	  mmix_cons (4);
	  break;

	case mmix_operands_octa:
	  /* OCTA */
	  mmix_cons (8);
	  break;

	case mmix_operands_prefix:
	  /* PREFIX */
	  s_prefix (0);
	  break;

	case mmix_operands_local:
	  /* LOCAL */
	  mmix_s_local (0);
	  break;

	case mmix_operands_bspec:
	  /* BSPEC */
	  s_bspec (0);
	  break;

	case mmix_operands_espec:
	  /* ESPEC */
	  s_espec (0);
	  break;

	default:
	  BAD_CASE (instruction->operands);
	}

      /* These are all working like the pseudo functions in read.c:s_...,
	 in that they step over the end-of-line marker at the end of the
	 line.  We don't want that here.  */
      input_line_pointer--;

      /* Step up the fb-label counter if there was a definition on this
	 line.  */
      if (current_fb_label >= 0)
	{
	  fb_label_instance_inc (current_fb_label);
	  current_fb_label = -1;
	}

      /* Reset any don't-align-next-datum request, unless this was a LOC
         directive.  */
      if (instruction->operands != mmix_operands_loc)
	want_unaligned = 0;

      return;
    }

  /* Not a pseudo; we *will* emit contents.  */
  if (now_seg == data_section)
    {
      if (lowest_data_loc != (bfd_vma) -1 && (lowest_data_loc & 3) != 0)
	{
	  if (data_has_contents)
	    as_bad (_("specified location wasn't TETRA-aligned"));
	  else if (want_unaligned)
	    as_bad (_("unaligned data at an absolute location is not supported"));

	  lowest_data_loc &= ~(bfd_vma) 3;
	  lowest_data_loc += 4;
	}

      data_has_contents = 1;
    }
  else if (now_seg == text_section)
    {
      if (lowest_text_loc != (bfd_vma) -1 && (lowest_text_loc & 3) != 0)
	{
	  if (text_has_contents)
	    as_bad (_("specified location wasn't TETRA-aligned"));
	  else if (want_unaligned)
	    as_bad (_("unaligned data at an absolute location is not supported"));

	  lowest_text_loc &= ~(bfd_vma) 3;
	  lowest_text_loc += 4;
	}

      text_has_contents = 1;
    }

  /* After a sequence of BYTEs or WYDEs, we need to get to instruction
     alignment.  For other pseudos, a ".p2align 2" is supposed to be
     inserted by the user.  */
  if (last_alignment < 2 && ! want_unaligned)
    {
      frag_align (2, 0, 0);
      record_alignment (now_seg, 2);
      last_alignment = 2;
    }
  else
    /* Reset any don't-align-next-datum request.  */
    want_unaligned = 0;

  /* For mmixal compatibility, a label for an instruction (and emitting
     pseudo) refers to the _aligned_ address.  So we have to emit the
     label here.  */
  if (pending_label != NULL)
    {
      colon (pending_label);
      pending_label = NULL;
    }

  /* We assume that mmix_opcodes keeps having unique mnemonics for each
     opcode, so we don't have to iterate over more than one opcode; if the
     syntax does not match, then there's a syntax error.  */

  /* Operands have little or no context and are all comma-separated; it is
     easier to parse each expression first.   */
  switch (instruction->operands)
    {
    case mmix_operands_reg_yz:
    case mmix_operands_pop:
    case mmix_operands_regaddr:
    case mmix_operands_pushj:
    case mmix_operands_get:
    case mmix_operands_put:
    case mmix_operands_set:
    case mmix_operands_save:
    case mmix_operands_unsave:
      max_operands = 2;
      break;

    case mmix_operands_sync:
    case mmix_operands_jmp:
    case mmix_operands_resume:
      max_operands = 1;
      break;

      /* The original 3 is fine for the rest.  */
    default:
      break;
    }

  /* If this is GET or PUT, and we don't do allow those names to be
     equated, we need to parse the names ourselves, so we don't pick up a
     user label instead of the special register.  */
  if (! equated_spec_regs
      && (instruction->operands == mmix_operands_get
	  || instruction->operands == mmix_operands_put))
    n_operands = get_putget_operands (instruction, operands, exp);
  else
    n_operands = get_operands (max_operands, operands, exp);

  /* If there's a fb-label on the current line, set that label.  This must
     be done *after* evaluating expressions of operands, since neither a
     "1B" nor a "1F" refers to "1H" on the same line.  */
  if (current_fb_label >= 0)
    {
      fb_label_instance_inc (current_fb_label);
      colon (fb_label_name (current_fb_label, 0));
      current_fb_label = -1;
    }

  /* We also assume that the length of the instruction is at least 4, the
     size of an unexpanded instruction.  We need a self-contained frag
     since we want the relocation to point to the instruction, not the
     variant part.  */

  opcodep = frag_more (4);
  mmix_opcode_frag = opc_fragP = frag_now;
  frag_now->fr_opcode = opcodep;

  /* Mark start of insn for DWARF2 debug features.  */
  if (OUTPUT_FLAVOR == bfd_target_elf_flavour)
    dwarf2_emit_insn (4);

  md_number_to_chars (opcodep, instruction->match, 4);

  switch (instruction->operands)
    {
    case mmix_operands_jmp:
      if (n_operands == 0 && ! mmix_gnu_syntax)
	/* Zeros are in place - nothing needs to be done when we have no
	   operands.  */
	break;

      /* Add a frag for a JMP relaxation; we need room for max four
	 extra instructions.  We don't do any work around here to check if
	 we can determine the offset right away.  */
      if (n_operands != 1 || exp[0].X_op == O_register)
	{
	  as_bad (_("invalid operand to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (expand_op)
	frag_var (rs_machine_dependent, 4 * 4, 0,
		  ENCODE_RELAX (STATE_JMP, STATE_UNDF),
		  exp[0].X_add_symbol,
		  exp[0].X_add_number,
		  opcodep);
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     exp + 0, 1, BFD_RELOC_MMIX_ADDR27);
      break;

    case mmix_operands_pushj:
      /* We take care of PUSHJ in full here.  */
      if (n_operands != 2
	  || ((exp[0].X_op == O_constant || exp[0].X_op == O_register)
	      && (exp[0].X_add_number > 255 || exp[0].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[0].X_op == O_register || exp[0].X_op == O_constant)
	opcodep[1] = exp[0].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
		     1, exp + 0, 0, BFD_RELOC_MMIX_REG_OR_BYTE);

      if (expand_op)
	frag_var (rs_machine_dependent, PUSHJ_MAX_LEN - 4, 0,
		  ENCODE_RELAX (STATE_PUSHJ, STATE_UNDF),
		  exp[1].X_add_symbol,
		  exp[1].X_add_number,
		  opcodep);
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     exp + 1, 1, BFD_RELOC_MMIX_ADDR19);
      break;

    case mmix_operands_regaddr:
      /* GETA/branch: Add a frag for relaxation.  We don't do any work
	 around here to check if we can determine the offset right away.  */
      if (n_operands != 2 || exp[1].X_op == O_register)
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (! expand_op)
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     exp + 1, 1, BFD_RELOC_MMIX_ADDR19);
      else if (instruction->type == mmix_type_condbranch)
	frag_var (rs_machine_dependent, BCC_MAX_LEN - 4, 0,
		  ENCODE_RELAX (STATE_BCC, STATE_UNDF),
		  exp[1].X_add_symbol,
		  exp[1].X_add_number,
		  opcodep);
      else
	frag_var (rs_machine_dependent, GETA_MAX_LEN - 4, 0,
		  ENCODE_RELAX (STATE_GETA, STATE_UNDF),
		  exp[1].X_add_symbol,
		  exp[1].X_add_number,
		  opcodep);
      break;

    default:
      break;
    }

  switch (instruction->operands)
    {
    case mmix_operands_regs:
      /* We check the number of operands here, since we're in a
	 FALLTHROUGH sequence in the next switch.  */
      if (n_operands != 3 || exp[2].X_op == O_constant)
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}
      /* FALLTHROUGH.  */
    case mmix_operands_regs_z:
      if (n_operands != 3)
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}
      /* FALLTHROUGH.  */
    case mmix_operands_reg_yz:
    case mmix_operands_roundregs_z:
    case mmix_operands_roundregs:
    case mmix_operands_regs_z_opt:
    case mmix_operands_neg:
    case mmix_operands_regaddr:
    case mmix_operands_get:
    case mmix_operands_set:
    case mmix_operands_save:
      if (n_operands < 1
	  || (exp[0].X_op == O_register && exp[0].X_add_number > 255))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[0].X_op == O_register)
	opcodep[1] = exp[0].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
		     1, exp + 0, 0, BFD_RELOC_MMIX_REG);
      break;

    default:
      ;
    }

  /* A corresponding once-over for those who take an 8-bit constant as
     their first operand.  */
  switch (instruction->operands)
    {
    case mmix_operands_pushgo:
      /* PUSHGO: X is a constant, but can be expressed as a register.
	 We handle X here and use the common machinery of T,X,3,$ for
	 the rest of the operands.  */
      if (n_operands < 2
	  || ((exp[0].X_op == O_constant || exp[0].X_op == O_register)
	      && (exp[0].X_add_number > 255 || exp[0].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}
      else if (exp[0].X_op == O_constant || exp[0].X_op == O_register)
	opcodep[1] = exp[0].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
		     1, exp + 0, 0, BFD_RELOC_MMIX_REG_OR_BYTE);
      break;

    case mmix_operands_pop:
      if ((n_operands == 0 || n_operands == 1) && ! mmix_gnu_syntax)
	break;
      /* FALLTHROUGH.  */
    case mmix_operands_x_regs_z:
      if (n_operands < 1
	  || (exp[0].X_op == O_constant
	      && (exp[0].X_add_number > 255
		  || exp[0].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[0].X_op == O_constant)
	opcodep[1] = exp[0].X_add_number;
      else
	/* FIXME: This doesn't bring us unsignedness checking.  */
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
		     1, exp + 0, 0, BFD_RELOC_8);
    default:
      ;
    }

  /* Handle the rest.  */
  switch (instruction->operands)
    {
    case mmix_operands_set:
      /* SET: Either two registers, "$X,$Y", with Z field as zero, or
	 "$X,YZ", meaning change the opcode to SETL.  */
      if (n_operands != 2
	  || (exp[1].X_op == O_constant
	      && (exp[1].X_add_number > 0xffff || exp[1].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[1].X_op == O_constant)
	{
	  /* There's an ambiguity with "SET $0,Y" when Y isn't defined
	     yet.  To keep things simple, we assume that Y is then a
	     register, and only change the opcode if Y is defined at this
	     point.

	     There's no compatibility problem with mmixal, since it emits
	     errors if the field is not defined at this point.  */
	  md_number_to_chars (opcodep, SETL_INSN_BYTE, 1);

	  opcodep[2] = (exp[1].X_add_number >> 8) & 255;
	  opcodep[3] = exp[1].X_add_number & 255;
	  break;
	}
      /* FALLTHROUGH.  */
    case mmix_operands_x_regs_z:
      /* SYNCD: "X,$Y,$Z|Z".  */
      /* FALLTHROUGH.  */
    case mmix_operands_regs:
      /* Three registers, $X,$Y,$Z.  */
      /* FALLTHROUGH.  */
    case mmix_operands_regs_z:
      /* Operands "$X,$Y,$Z|Z", number of arguments checked above.  */
      /* FALLTHROUGH.  */
    case mmix_operands_pushgo:
      /* Operands "$X|X,$Y,$Z|Z", optional Z.  */
      /* FALLTHROUGH.  */
    case mmix_operands_regs_z_opt:
      /* Operands "$X,$Y,$Z|Z", with $Z|Z being optional, default 0.  Any
	 operands not completely decided yet are postponed to later in
	 assembly (but not until link-time yet).  */

      if ((n_operands != 2 && n_operands != 3)
	  || (exp[1].X_op == O_register && exp[1].X_add_number > 255)
	  || (n_operands == 3
	      && ((exp[2].X_op == O_register
		   && exp[2].X_add_number > 255
		   && mmix_gnu_syntax)
		  || (exp[2].X_op == O_constant
		      && (exp[2].X_add_number > 255
			  || exp[2].X_add_number < 0)))))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (n_operands == 2)
	{
	  symbolS *sym;
	  fixS *tmpfixP;

	  /* The last operand is immediate whenever we see just two
	     operands.  */
	  opcodep[0] |= IMM_OFFSET_BIT;

	  /* Now, we could either have an implied "0" as the Z operand, or
	     it could be the constant of a "base address plus offset".  It
	     depends on whether it is allowed; only memory operations, as
	     signified by instruction->type and "T" and "X" operand types,
	     and it depends on whether we find a register in the second
	     operand, exp[1].  */
	  if (exp[1].X_op == O_register && exp[1].X_add_number <= 255)
	    {
	      /* A zero then; all done.  */
	      opcodep[2] = exp[1].X_add_number;
	      break;
	    }

	  /* Not known as a register.  Is base address plus offset
	     allowed, or can we assume that it is a register anyway?  */
	  if ((instruction->operands != mmix_operands_regs_z_opt
	       && instruction->operands != mmix_operands_x_regs_z
	       && instruction->operands != mmix_operands_pushgo)
	      || (instruction->type != mmix_type_memaccess_octa
		  && instruction->type != mmix_type_memaccess_tetra
		  && instruction->type != mmix_type_memaccess_wyde
		  && instruction->type != mmix_type_memaccess_byte
		  && instruction->type != mmix_type_memaccess_block
		  && instruction->type != mmix_type_jsr
		  && instruction->type != mmix_type_branch))
	    {
	      fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
			   1, exp + 1, 0, BFD_RELOC_MMIX_REG);
	      break;
	    }

	  /* To avoid getting a NULL add_symbol for constants and then
	     catching a SEGV in write_relocs since it doesn't handle
	     constants well for relocs other than PC-relative, we need to
	     pass expressions as symbols and use fix_new, not fix_new_exp.  */
	  sym = make_expr_symbol (exp + 1);

	  /* Mark the symbol as being OK for a reloc.  */
	  symbol_get_bfdsym (sym)->flags |= BSF_KEEP;

	  /* Now we know it can be a "base address plus offset".  Add
	     proper fixup types so we can handle this later, when we've
	     parsed everything.  */
	  tmpfixP
	    = fix_new (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
		       1, sym, 0, 0, BFD_RELOC_MMIX_BASE_PLUS_OFFSET);
	  /* This is a non-trivial fixup: the ->fx_offset will not
	     reflect the stored value, so the generic overflow test
	     doesn't apply. */
	  tmpfixP->fx_no_overflow = 1;
	  break;
	}

      if (exp[1].X_op == O_register)
	opcodep[2] = exp[1].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
		     1, exp + 1, 0, BFD_RELOC_MMIX_REG);

      /* In mmixal compatibility mode, we allow special registers as
	 constants for the Z operand.  They have 256 added to their
	 register numbers, so the right thing will happen if we just treat
	 those as constants.  */
      if (exp[2].X_op == O_register && exp[2].X_add_number <= 255)
	opcodep[3] = exp[2].X_add_number;
      else if (exp[2].X_op == O_constant
	       || (exp[2].X_op == O_register && exp[2].X_add_number > 255))
	{
	  opcodep[3] = exp[2].X_add_number;
	  opcodep[0] |= IMM_OFFSET_BIT;
	}
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		     1, exp + 2, 0,
		     (instruction->operands == mmix_operands_set
		      || instruction->operands == mmix_operands_regs)
		     ? BFD_RELOC_MMIX_REG : BFD_RELOC_MMIX_REG_OR_BYTE);
      break;

    case mmix_operands_pop:
      /* POP, one eight and one 16-bit operand.  */
      if (n_operands == 0 && ! mmix_gnu_syntax)
	break;
      if (n_operands == 1 && ! mmix_gnu_syntax)
	goto a_single_24_bit_number_operand;
      /* FALLTHROUGH.  */
    case mmix_operands_reg_yz:
      /* A register and a 16-bit unsigned number.  */
      if (n_operands != 2
	  || exp[1].X_op == O_register
	  || (exp[1].X_op == O_constant
	      && (exp[1].X_add_number > 0xffff || exp[1].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[1].X_op == O_constant)
	{
	  opcodep[2] = (exp[1].X_add_number >> 8) & 255;
	  opcodep[3] = exp[1].X_add_number & 255;
	}
      else
	/* FIXME: This doesn't bring us unsignedness checking.  */
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
		     2, exp + 1, 0, BFD_RELOC_16);
      break;

    case mmix_operands_jmp:
      /* A JMP.  Everything is already done.  */
      break;

    case mmix_operands_roundregs:
      /* Two registers with optional rounding mode or constant in between.  */
      if ((n_operands == 3 && exp[2].X_op == O_constant)
	  || (n_operands == 2 && exp[1].X_op == O_constant))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}
      /* FALLTHROUGH.  */
    case mmix_operands_roundregs_z:
      /* Like FLOT, "$X,ROUND_MODE,$Z|Z", but the rounding mode is
	 optional and can be the corresponding constant.  */
      {
	/* Which exp index holds the second operand (not the rounding
	   mode).  */
	int op2no = n_operands - 1;

	if ((n_operands != 2 && n_operands != 3)
	    || ((exp[op2no].X_op == O_register
		 && exp[op2no].X_add_number > 255)
		|| (exp[op2no].X_op == O_constant
		    && (exp[op2no].X_add_number > 255
			|| exp[op2no].X_add_number < 0)))
	    || (n_operands == 3
		/* We don't allow for the rounding mode to be deferred; it
		   must be determined in the "first pass".  It cannot be a
		   symbol equated to a rounding mode, but defined after
		   the first use.  */
		&& ((exp[1].X_op == O_register
		     && exp[1].X_add_number < 512)
		    || (exp[1].X_op == O_constant
			&& (exp[1].X_add_number < 0
			    || exp[1].X_add_number > 4))
		    || (exp[1].X_op != O_register
			&& exp[1].X_op != O_constant))))
	  {
	    as_bad (_("invalid operands to opcode %s: `%s'"),
		    instruction->name, operands);
	    return;
	  }

	/* Add rounding mode if present.  */
	if (n_operands == 3)
	  opcodep[2] = exp[1].X_add_number & 255;

	if (exp[op2no].X_op == O_register)
	  opcodep[3] = exp[op2no].X_add_number;
	else if (exp[op2no].X_op == O_constant)
	  {
	    opcodep[3] = exp[op2no].X_add_number;
	    opcodep[0] |= IMM_OFFSET_BIT;
	  }
	else
	  fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		       1, exp + op2no, 0,
		       instruction->operands == mmix_operands_roundregs
		       ? BFD_RELOC_MMIX_REG
		       : BFD_RELOC_MMIX_REG_OR_BYTE);
	break;
      }

    case mmix_operands_sync:
    a_single_24_bit_number_operand:
      if (n_operands != 1
	  || exp[0].X_op == O_register
	  || (exp[0].X_op == O_constant
	      && (exp[0].X_add_number > 0xffffff || exp[0].X_add_number < 0)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[0].X_op == O_constant)
	{
	  opcodep[1] = (exp[0].X_add_number >> 16) & 255;
	  opcodep[2] = (exp[0].X_add_number >> 8) & 255;
	  opcodep[3] = exp[0].X_add_number & 255;
	}
      else
	/* FIXME: This doesn't bring us unsignedness checking.  */
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
		     3, exp + 0, 0, BFD_RELOC_24);
      break;

    case mmix_operands_neg:
      /* Operands "$X,Y,$Z|Z"; NEG or NEGU.  Y is optional, 0 is default.  */

      if ((n_operands != 3 && n_operands != 2)
	  || (n_operands == 3 && exp[1].X_op == O_register)
	  || ((exp[1].X_op == O_constant || exp[1].X_op == O_register)
	      && (exp[1].X_add_number > 255 || exp[1].X_add_number < 0))
	  || (n_operands == 3
	      && ((exp[2].X_op == O_register && exp[2].X_add_number > 255)
		  || (exp[2].X_op == O_constant
		      && (exp[2].X_add_number > 255
			  || exp[2].X_add_number < 0)))))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (n_operands == 2)
	{
	  if (exp[1].X_op == O_register)
	    opcodep[3] = exp[1].X_add_number;
	  else if (exp[1].X_op == O_constant)
	    {
	      opcodep[3] = exp[1].X_add_number;
	      opcodep[0] |= IMM_OFFSET_BIT;
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
			 1, exp + 1, 0, BFD_RELOC_MMIX_REG_OR_BYTE);
	  break;
	}

      if (exp[1].X_op == O_constant)
	opcodep[2] = exp[1].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
		     1, exp + 1, 0, BFD_RELOC_8);

      if (exp[2].X_op == O_register)
	opcodep[3] = exp[2].X_add_number;
      else if (exp[2].X_op == O_constant)
	{
	  opcodep[3] = exp[2].X_add_number;
	  opcodep[0] |= IMM_OFFSET_BIT;
	}
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		     1, exp + 2, 0, BFD_RELOC_MMIX_REG_OR_BYTE);
      break;

    case mmix_operands_regaddr:
      /* A GETA/branch-type.  */
      break;

    case mmix_operands_get:
      /* "$X,spec_reg"; GET.
	 Like with rounding modes, we demand that the special register or
	 symbol is already defined when we get here at the point of use.  */
      if (n_operands != 2
	  || (exp[1].X_op == O_register
	      && (exp[1].X_add_number < 256 || exp[1].X_add_number >= 512))
	  || (exp[1].X_op == O_constant
	      && (exp[1].X_add_number < 0 || exp[1].X_add_number > 256))
	  || (exp[1].X_op != O_constant && exp[1].X_op != O_register))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      opcodep[3] = exp[1].X_add_number - 256;
      break;

    case mmix_operands_put:
      /* "spec_reg,$Z|Z"; PUT.  */
      if (n_operands != 2
	  || (exp[0].X_op == O_register
	      && (exp[0].X_add_number < 256 || exp[0].X_add_number >= 512))
	  || (exp[0].X_op == O_constant
	      && (exp[0].X_add_number < 0 || exp[0].X_add_number > 256))
	  || (exp[0].X_op != O_constant && exp[0].X_op != O_register))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      opcodep[1] = exp[0].X_add_number - 256;

      /* Note that the Y field is zero.  */

      if (exp[1].X_op == O_register)
	opcodep[3] = exp[1].X_add_number;
      else if (exp[1].X_op == O_constant)
	{
	  opcodep[3] = exp[1].X_add_number;
	  opcodep[0] |= IMM_OFFSET_BIT;
	}
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		     1, exp + 1, 0, BFD_RELOC_MMIX_REG_OR_BYTE);
      break;

    case mmix_operands_save:
      /* "$X,0"; SAVE.  */
      if (n_operands != 2
	  || exp[1].X_op != O_constant
	  || exp[1].X_add_number != 0)
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}
      break;

    case mmix_operands_unsave:
      if (n_operands < 2 && ! mmix_gnu_syntax)
	{
	  if (n_operands == 1)
	    {
	      if (exp[0].X_op == O_register)
		opcodep[3] = exp[0].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
			     1, exp, 0, BFD_RELOC_MMIX_REG);
	    }
	  break;
	}

      /* "0,$Z"; UNSAVE.  */
      if (n_operands != 2
	  || exp[0].X_op != O_constant
	  || exp[0].X_add_number != 0
	  || exp[1].X_op == O_constant
	  || (exp[1].X_op == O_register
	      && exp[1].X_add_number > 255))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[1].X_op == O_register)
	opcodep[3] = exp[1].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		     1, exp + 1, 0, BFD_RELOC_MMIX_REG);
      break;

    case mmix_operands_xyz_opt:
      /* SWYM, TRIP, TRAP: zero, one, two or three operands.  It's
	 unspecified whether operands are registers or constants, but
	 when we find register syntax, we require operands to be literal and
	 within 0..255.  */
      if (n_operands == 0 && ! mmix_gnu_syntax)
	/* Zeros are in place - nothing needs to be done for zero
	   operands.  We don't allow this in GNU syntax mode, because it
	   was believed that the risk of missing to supply an operand is
	   higher than the benefit of not having to specify a zero.  */
	;
      else if (n_operands == 1 && exp[0].X_op != O_register)
	{
	  if (exp[0].X_op == O_constant)
	    {
	      if (exp[0].X_add_number > 255*256*256
		  || exp[0].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		{
		  opcodep[1] = (exp[0].X_add_number >> 16) & 255;
		  opcodep[2] = (exp[0].X_add_number >> 8) & 255;
		  opcodep[3] = exp[0].X_add_number & 255;
		}
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
			 3, exp, 0, BFD_RELOC_24);
	}
      else if (n_operands == 2
	       && exp[0].X_op != O_register
	       && exp[1].X_op != O_register)
	{
	  /* Two operands.  */

	  if (exp[0].X_op == O_constant)
	    {
	      if (exp[0].X_add_number > 255
		  || exp[0].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		opcodep[1] = exp[0].X_add_number & 255;
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
			 1, exp, 0, BFD_RELOC_8);

	  if (exp[1].X_op == O_constant)
	    {
	      if (exp[1].X_add_number > 255*256
		  || exp[1].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		{
		  opcodep[2] = (exp[1].X_add_number >> 8) & 255;
		  opcodep[3] = exp[1].X_add_number & 255;
		}
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
			 2, exp + 1, 0, BFD_RELOC_16);
	}
      else if (n_operands == 3
	       && exp[0].X_op != O_register
	       && exp[1].X_op != O_register
	       && exp[2].X_op != O_register)
	{
	  /* Three operands.  */

	  if (exp[0].X_op == O_constant)
	    {
	      if (exp[0].X_add_number > 255
		  || exp[0].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		opcodep[1] = exp[0].X_add_number & 255;
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
			 1, exp, 0, BFD_RELOC_8);

	  if (exp[1].X_op == O_constant)
	    {
	      if (exp[1].X_add_number > 255
		  || exp[1].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		opcodep[2] = exp[1].X_add_number & 255;
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
			 1, exp + 1, 0, BFD_RELOC_8);

	  if (exp[2].X_op == O_constant)
	    {
	      if (exp[2].X_add_number > 255
		  || exp[2].X_add_number < 0)
		{
		  as_bad (_("invalid operands to opcode %s: `%s'"),
			  instruction->name, operands);
		  return;
		}
	      else
		opcodep[3] = exp[2].X_add_number & 255;
	    }
	  else
	    fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
			 1, exp + 2, 0, BFD_RELOC_8);
	}
      else
	{
	  /* We can't get here for other cases.  */
	  gas_assert (n_operands <= 3);

	  /* The meaning of operands to TRIP and TRAP is not defined (and
	     SWYM operands aren't enforced in mmixal, so let's avoid
	     that).  We add combinations not handled above here as we find
	     them and as they're reported.  */
	  if (n_operands == 3)
	    {
	      /* Don't require non-register operands.  Always generate
		 fixups, so we don't have to copy lots of code and create
		 maintenance problems.  TRIP is supposed to be a rare
		 instruction, so the overhead should not matter.  We
		 aren't allowed to fix_new_exp for an expression which is
		 an O_register at this point, however.

		 Don't use BFD_RELOC_MMIX_REG_OR_BYTE as that modifies
		 the insn for a register in the Z field and we want
		 consistency.  */
	      if (exp[0].X_op == O_register)
		opcodep[1] = exp[0].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
			     1, exp, 0, BFD_RELOC_8);
	      if (exp[1].X_op == O_register)
		opcodep[2] = exp[1].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
			     1, exp + 1, 0, BFD_RELOC_8);
	      if (exp[2].X_op == O_register)
		opcodep[3] = exp[2].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
			     1, exp + 2, 0, BFD_RELOC_8);
	    }
	  else if (n_operands == 2)
	    {
	      if (exp[0].X_op == O_register)
		opcodep[1] = exp[0].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 1,
			     1, exp, 0, BFD_RELOC_8);
	      if (exp[1].X_op == O_register)
		opcodep[3] = exp[1].X_add_number;
	      else
		fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 2,
			     2, exp + 1, 0, BFD_RELOC_16);
	    }
	  else
	    {
	      /* We can't get here for other cases.  */
	      gas_assert (n_operands == 1 && exp[0].X_op == O_register);

	      opcodep[3] = exp[0].X_add_number;
	    }
	}
      break;

    case mmix_operands_resume:
      if (n_operands == 0 && ! mmix_gnu_syntax)
	break;

      if (n_operands != 1
	  || exp[0].X_op == O_register
	  || (exp[0].X_op == O_constant
	      && (exp[0].X_add_number < 0
		  || exp[0].X_add_number > 255)))
	{
	  as_bad (_("invalid operands to opcode %s: `%s'"),
		  instruction->name, operands);
	  return;
	}

      if (exp[0].X_op == O_constant)
	opcodep[3] = exp[0].X_add_number;
      else
	fix_new_exp (opc_fragP, opcodep - opc_fragP->fr_literal + 3,
		     1, exp + 0, 0, BFD_RELOC_8);
      break;

    case mmix_operands_pushj:
      /* All is done for PUSHJ already.  */
      break;

    default:
      BAD_CASE (instruction->operands);
    }
}

/* For the benefit of insns that start with a digit, we assemble by way of
   tc_unrecognized_line too, through this function.  */

int
mmix_assemble_return_nonzero (char *str)
{
  int last_error_count = had_errors ();
  char *s2 = str;
  char c;

  /* Normal instruction handling downcases, so we must too.  */
  while (ISALNUM (*s2))
    {
      if (ISUPPER ((unsigned char) *s2))
	*s2 = TOLOWER (*s2);
      s2++;
    }

  /* Cut the line for sake of the assembly.  */
  for (s2 = str; *s2 && *s2 != '\n'; s2++)
    ;

  c = *s2;
  *s2 = 0;
  md_assemble (str);
  *s2 = c;

  return had_errors () == last_error_count;
}

/* The PREFIX pseudo.  */

static void
s_prefix (int unused ATTRIBUTE_UNUSED)
{
  char *p;
  int c;

  SKIP_WHITESPACE ();

  c = get_symbol_name (&p);
  
  /* Resetting prefix?  */
  if (*p == ':' && p[1] == 0)
    mmix_current_prefix = NULL;
  else
    {
      /* Put this prefix on the mmix symbols obstack.  We could malloc and
	 free it separately, but then we'd have to worry about that.
	 People using up memory on prefixes have other problems.  */
      obstack_grow (&mmix_sym_obstack, p, strlen (p) + 1);
      p = obstack_finish (&mmix_sym_obstack);

      /* Accumulate prefixes, and strip a leading ':'.  */
      if (mmix_current_prefix != NULL || *p == ':')
	p = mmix_prefix_name (p);

      mmix_current_prefix = p;
    }

  (void) restore_line_pointer (c);

  mmix_handle_rest_of_empty_line ();
}

/* We implement prefixes by using the tc_canonicalize_symbol_name hook,
   and store each prefixed name on a (separate) obstack.  This means that
   the name is on the "notes" obstack in non-prefixed form and on the
   mmix_sym_obstack in prefixed form, but currently it is not worth
   rewriting the whole GAS symbol handling to improve "hooking" to avoid
   that.  (It might be worth a rewrite for other reasons, though).  */

char *
mmix_prefix_name (char *shortname)
{
  if (*shortname == ':')
    return shortname + 1;

  if (mmix_current_prefix == NULL)
    as_fatal (_("internal: mmix_prefix_name but empty prefix"));

  if (*shortname == '$')
    return shortname;

  obstack_grow (&mmix_sym_obstack, mmix_current_prefix,
		strlen (mmix_current_prefix));
  obstack_grow (&mmix_sym_obstack, shortname, strlen (shortname) + 1);
  return obstack_finish (&mmix_sym_obstack);
}

/* The GREG pseudo.  At LABEL, we have the name of a symbol that we
   want to make a register symbol, and which should be initialized with
   the value in the expression at INPUT_LINE_POINTER (defaulting to 0).
   Either and (perhaps less meaningful) both may be missing.  LABEL must
   be persistent, perhaps allocated on an obstack.  */

static void
mmix_greg_internal (char *label)
{
  expressionS *expP = &mmix_raw_gregs[n_of_raw_gregs].exp;
  segT section;

  /* Don't set the section to register contents section before the
     expression has been parsed; it may refer to the current position.  */
  section = expression (expP);

  /* FIXME: Check that no expression refers to the register contents
     section.  May need to be done in elf64-mmix.c.  */
  if (expP->X_op == O_absent)
    {
      /* Default to zero if the expression was absent.  */
      expP->X_op = O_constant;
      expP->X_add_number = 0;
      expP->X_unsigned = 0;
      expP->X_add_symbol = NULL;
      expP->X_op_symbol = NULL;
    }

  if (section == undefined_section)
    {
      /* This is an error or a LOC with an expression involving
	 forward references.  For the expression to be correctly
	 evaluated, we need to force a proper symbol; gas loses track
	 of the segment for "local symbols".  */
      if (expP->X_op == O_add)
	{
	  symbol_get_value_expression (expP->X_op_symbol);
	  symbol_get_value_expression (expP->X_add_symbol);
	}
      else
	{
	  gas_assert (expP->X_op == O_symbol);
	  symbol_get_value_expression (expP->X_add_symbol);
	}
    }

  /* We must handle prefixes here, as we save the labels and expressions
     to be output later.  */
  mmix_raw_gregs[n_of_raw_gregs].label
    = mmix_current_prefix == NULL ? label : mmix_prefix_name (label);

  if (n_of_raw_gregs == MAX_GREGS - 1)
    as_bad (_("too many GREG registers allocated (max %d)"), MAX_GREGS);
  else
    n_of_raw_gregs++;

  mmix_handle_rest_of_empty_line ();
}

/* The ".greg label,expr" worker.  */

static void
s_greg (int unused ATTRIBUTE_UNUSED)
{
  char *p;
  char c;

  /* This will skip over what can be a symbol and zero out the next
     character, which we assume is a ',' or other meaningful delimiter.
     What comes after that is the initializer expression for the
     register.  */
  c = get_symbol_name (&p);

  if (c == '"')
    c = * ++ input_line_pointer;

  if (! is_end_of_line[(unsigned char) c])
    input_line_pointer++;

  if (*p)
    {
      /* The label must be persistent; it's not used until after all input
	 has been seen.  */
      obstack_grow (&mmix_sym_obstack, p, strlen (p) + 1);
      mmix_greg_internal (obstack_finish (&mmix_sym_obstack));
    }
  else
    mmix_greg_internal (NULL);
}

/* The "BSPEC expr" worker.  */

static void
s_bspec (int unused ATTRIBUTE_UNUSED)
{
  asection *expsec;
  asection *sec;
  char secname[sizeof (MMIX_OTHER_SPEC_SECTION_PREFIX) + 20]
    = MMIX_OTHER_SPEC_SECTION_PREFIX;
  expressionS exp;
  int n;

  /* Get a constant expression which we can evaluate *now*.  Supporting
     more complex (though assembly-time computable) expressions is
     feasible but Too Much Work for something of unknown usefulness like
     BSPEC-ESPEC.  */
  expsec = expression (&exp);
  mmix_handle_rest_of_empty_line ();

  /* Check that we don't have another BSPEC in progress.  */
  if (doing_bspec)
    {
      as_bad (_("BSPEC already active.  Nesting is not supported."));
      return;
    }

  if (exp.X_op != O_constant
      || expsec != absolute_section
      || exp.X_add_number < 0
      || exp.X_add_number > 65535)
    {
      as_bad (_("invalid BSPEC expression"));
      exp.X_add_number = 0;
    }

  n = (int) exp.X_add_number;

  sprintf (secname + strlen (MMIX_OTHER_SPEC_SECTION_PREFIX), "%d", n);
  sec = bfd_get_section_by_name (stdoutput, secname);
  if (sec == NULL)
    {
      /* We need a non-volatile name as it will be stored in the section
         struct.  */
      char *newsecname = xstrdup (secname);
      sec = bfd_make_section (stdoutput, newsecname);

      if (sec == NULL)
	as_fatal (_("can't create section %s"), newsecname);

      if (!bfd_set_section_flags (sec,
				  bfd_section_flags (sec) | SEC_READONLY))
	as_fatal (_("can't set section flags for section %s"), newsecname);
    }

  /* Tell ELF about the pending section change.  */
  obj_elf_section_change_hook ();
  subseg_set (sec, 0);

  /* Save position for missing ESPEC.  */
  bspec_file = as_where (&bspec_line);

  doing_bspec = 1;
}

/* The "ESPEC" worker.  */

static void
s_espec (int unused ATTRIBUTE_UNUSED)
{
  /* First, check that we *do* have a BSPEC in progress.  */
  if (! doing_bspec)
    {
      as_bad (_("ESPEC without preceding BSPEC"));
      return;
    }

  mmix_handle_rest_of_empty_line ();
  doing_bspec = 0;

  /* When we told ELF about the section change in s_bspec, it stored the
     previous section for us so we can get at it with the equivalent of a
     .previous pseudo.  */
  obj_elf_previous (0);
}

/* The " .local expr" and " local expr" worker.  We make a BFD_MMIX_LOCAL
   relocation against the current position against the expression.
   Implementing this by means of contents in a section lost.  */

static void
mmix_s_local (int unused ATTRIBUTE_UNUSED)
{
  expressionS exp;

  /* Don't set the section to register contents section before the
     expression has been parsed; it may refer to the current position in
     some contorted way.  */
  expression (&exp);

  if (exp.X_op == O_absent)
    {
      as_bad (_("missing local expression"));
      return;
    }
  else if (exp.X_op == O_register)
    {
      /* fix_new_exp doesn't like O_register.  Should be configurable.
	 We're fine with a constant here, though.  */
      exp.X_op = O_constant;
    }

  fix_new_exp (frag_now, 0, 0, &exp, 0, BFD_RELOC_MMIX_LOCAL);
  mmix_handle_rest_of_empty_line ();
}

/* Set fragP->fr_var to the initial guess of the size of a relaxable insn
   and return it.  Sizes of other instructions are not known.  This
   function may be called multiple times.  */

int
md_estimate_size_before_relax (fragS *fragP, segT segment)
{
  int length;

#define HANDLE_RELAXABLE(state)						\
 case ENCODE_RELAX (state, STATE_UNDF):					\
   if (fragP->fr_symbol != NULL						\
       && S_GET_SEGMENT (fragP->fr_symbol) == segment			\
       && !S_IS_WEAK (fragP->fr_symbol))				\
     {									\
       /* The symbol lies in the same segment - a relaxable case.  */	\
       fragP->fr_subtype						\
	 = ENCODE_RELAX (state, STATE_ZERO);				\
     }									\
   break;

  switch (fragP->fr_subtype)
    {
      HANDLE_RELAXABLE (STATE_GETA);
      HANDLE_RELAXABLE (STATE_BCC);
      HANDLE_RELAXABLE (STATE_JMP);

    case ENCODE_RELAX (STATE_PUSHJ, STATE_UNDF):
      if (fragP->fr_symbol != NULL
	  && S_GET_SEGMENT (fragP->fr_symbol) == segment
	  && !S_IS_WEAK (fragP->fr_symbol))
	/* The symbol lies in the same segment - a relaxable case.  */
	fragP->fr_subtype = ENCODE_RELAX (STATE_PUSHJ, STATE_ZERO);
      else if (pushj_stubs)
	/* If we're to generate stubs, assume we can reach a stub after
           the section.  */
	fragP->fr_subtype = ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO);
      /* FALLTHROUGH.  */
    case ENCODE_RELAX (STATE_PUSHJ, STATE_ZERO):
    case ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO):
      /* We need to distinguish different relaxation rounds.  */
      seg_info (segment)->tc_segment_info_data.last_stubfrag = fragP;
      break;

    case ENCODE_RELAX (STATE_GETA, STATE_ZERO):
    case ENCODE_RELAX (STATE_BCC, STATE_ZERO):
    case ENCODE_RELAX (STATE_JMP, STATE_ZERO):
      /* When relaxing a section for the second time, we don't need to do
	 anything except making sure that fr_var is set right.  */
      break;

    case STATE_GREG_DEF:
      length = fragP->tc_frag_data != NULL ? 0 : 8;
      fragP->fr_var = length;

      /* Don't consult the relax_table; it isn't valid for this
	 relaxation.  */
      return length;
      break;

    default:
      BAD_CASE (fragP->fr_subtype);
    }

  length = mmix_relax_table[fragP->fr_subtype].rlx_length;
  fragP->fr_var = length;

  return length;
}

/* Turn a string in input_line_pointer into a floating point constant of type
   type, and store the appropriate bytes in *litP.  The number of LITTLENUMS
   emitted is stored in *sizeP .  An error message is returned, or NULL on
   OK.  */

const char *
md_atof (int type, char *litP, int *sizeP)
{
  if (type == 'r')
    type = 'f';
  /* FIXME: Having 'f' in FLT_CHARS (and here) makes it
     problematic to also have a forward reference in an expression.
     The testsuite wants it, and it's customary.
     We'll deal with the real problems when they come; we share the
     problem with most other ports.  */
  return ieee_md_atof (type, litP, sizeP, true);
}

/* Convert variable-sized frags into one or more fixups.  */

void
md_convert_frag (bfd *abfd ATTRIBUTE_UNUSED, segT sec ATTRIBUTE_UNUSED,
		 fragS *fragP)
{
  /* Pointer to first byte in variable-sized part of the frag.  */
  char *var_partp;

  /* Pointer to first opcode byte in frag.  */
  char *opcodep;

  /* Size in bytes of variable-sized part of frag.  */
  int var_part_size = 0;

  /* This is part of *fragP.  It contains all information about addresses
     and offsets to varying parts.  */
  symbolS *symbolP;
  unsigned long var_part_offset;

  /* This is the frag for the opcode.  It, rather than fragP, must be used
     when emitting a frag for the opcode.  */
  fragS *opc_fragP = fragP->tc_frag_data;
  fixS *tmpfixP;

  /* Where, in file space, does addr point?  */
  bfd_vma target_address;
  bfd_vma opcode_address;

  know (fragP->fr_type == rs_machine_dependent);

  var_part_offset = fragP->fr_fix;
  var_partp = fragP->fr_literal + var_part_offset;
  opcodep = fragP->fr_opcode;

  symbolP = fragP->fr_symbol;

  target_address
    = ((symbolP ? S_GET_VALUE (symbolP) : 0) + fragP->fr_offset);

  /* The opcode that would be extended is the last four "fixed" bytes.  */
  opcode_address = fragP->fr_address + fragP->fr_fix - 4;

  switch (fragP->fr_subtype)
    {
    case ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO):
      /* Setting the unknown bits to 0 seems the most appropriate.  */
      mmix_set_geta_branch_offset (opcodep, 0);
      tmpfixP = fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
			 fragP->fr_symbol, fragP->fr_offset, 1,
			 BFD_RELOC_MMIX_PUSHJ_STUBBABLE);
      COPY_FR_WHERE_TO_FX (fragP, tmpfixP);
      var_part_size = 0;

      /* This is a non-trivial fixup; we'll be calling a generated
	 stub, whose address fits into the fixup.  The actual target,
	 as reflected by the fixup value, is further away than fits
	 into the fixup, so the generic overflow test doesn't
	 apply. */
      tmpfixP->fx_no_overflow = 1;
      break;

    case ENCODE_RELAX (STATE_GETA, STATE_ZERO):
    case ENCODE_RELAX (STATE_BCC, STATE_ZERO):
    case ENCODE_RELAX (STATE_PUSHJ, STATE_ZERO):
      mmix_set_geta_branch_offset (opcodep, target_address - opcode_address);
      if (linkrelax)
	{
	  tmpfixP
	    = fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		       fragP->fr_symbol, fragP->fr_offset, 1,
		       BFD_RELOC_MMIX_ADDR19);
	  COPY_FR_WHERE_TO_FX (fragP, tmpfixP);
	}
      var_part_size = 0;
      break;

    case ENCODE_RELAX (STATE_JMP, STATE_ZERO):
      mmix_set_jmp_offset (opcodep, target_address - opcode_address);
      if (linkrelax)
	{
	  tmpfixP
	    = fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		       fragP->fr_symbol, fragP->fr_offset, 1,
		       BFD_RELOC_MMIX_ADDR27);
	  COPY_FR_WHERE_TO_FX (fragP, tmpfixP);
	}
      var_part_size = 0;
      break;

    case STATE_GREG_DEF:
      if (fragP->tc_frag_data == NULL)
	{
	  /* We must initialize data that's supposed to be "fixed up" to
	     avoid emitting garbage, because md_apply_fix won't do
	     anything for undefined symbols.  */
	  md_number_to_chars (var_partp, 0, 8);
	  tmpfixP
	    = fix_new (fragP, var_partp - fragP->fr_literal, 8,
		       fragP->fr_symbol, fragP->fr_offset, 0, BFD_RELOC_64);
	  COPY_FR_WHERE_TO_FX (fragP, tmpfixP);
	  mmix_gregs[n_of_cooked_gregs++] = tmpfixP;
	  var_part_size = 8;
	}
      else
	var_part_size = 0;
      break;

#define HANDLE_MAX_RELOC(state, reloc)					\
  case ENCODE_RELAX (state, STATE_MAX):					\
    var_part_size							\
      = mmix_relax_table[ENCODE_RELAX (state, STATE_MAX)].rlx_length;	\
    mmix_fill_nops (var_partp, var_part_size / 4);			\
    if (warn_on_expansion)						\
      as_warn_where (fragP->fr_file, fragP->fr_line,			\
		     _("operand out of range, instruction expanded"));	\
    tmpfixP = fix_new (fragP, var_partp - fragP->fr_literal - 4, 8,	\
		       fragP->fr_symbol, fragP->fr_offset, 1, reloc);	\
    COPY_FR_WHERE_TO_FX (fragP, tmpfixP);				\
    break

      HANDLE_MAX_RELOC (STATE_GETA, BFD_RELOC_MMIX_GETA);
      HANDLE_MAX_RELOC (STATE_BCC, BFD_RELOC_MMIX_CBRANCH);
      HANDLE_MAX_RELOC (STATE_PUSHJ, BFD_RELOC_MMIX_PUSHJ);
      HANDLE_MAX_RELOC (STATE_JMP, BFD_RELOC_MMIX_JMP);

    default:
      BAD_CASE (fragP->fr_subtype);
      break;
    }

  fragP->fr_fix += var_part_size;
  fragP->fr_var = 0;
}

/* Applies the desired value to the specified location.
   Also sets up addends for RELA type relocations.
   Stolen from tc-mcore.c.

   Note that this function isn't called when linkrelax != 0.  */

void
md_apply_fix (fixS *fixP, valueT *valP, segT segment)
{
  char *buf  = fixP->fx_where + fixP->fx_frag->fr_literal;
  /* Note: use offsetT because it is signed, valueT is unsigned.  */
  offsetT val  = (offsetT) * valP;
  segT symsec
    = (fixP->fx_addsy == NULL
       ? absolute_section : S_GET_SEGMENT (fixP->fx_addsy));

  /* If the fix is relative to a symbol which is not defined, or, (if
     pcrel), not in the same segment as the fix, we cannot resolve it
     here.  */
  if (fixP->fx_addsy != NULL
      && (! S_IS_DEFINED (fixP->fx_addsy)
	  || S_IS_WEAK (fixP->fx_addsy)
	  || (fixP->fx_pcrel && symsec != segment)
	  || (! fixP->fx_pcrel
	      && symsec != absolute_section
	      && ((fixP->fx_r_type != BFD_RELOC_MMIX_REG
		   && fixP->fx_r_type != BFD_RELOC_MMIX_REG_OR_BYTE)
		  || symsec != reg_section))))
    {
      fixP->fx_done = 0;
      return;
    }
  else if (fixP->fx_r_type == BFD_RELOC_MMIX_LOCAL
	   || fixP->fx_r_type == BFD_RELOC_VTABLE_INHERIT
	   || fixP->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
    {
      /* These are never "fixed".  */
      fixP->fx_done = 0;
      return;
    }
  else
    /* We assume every other relocation is "fixed".  */
    fixP->fx_done = 1;

  switch (fixP->fx_r_type)
    {
    case BFD_RELOC_64:
    case BFD_RELOC_32:
    case BFD_RELOC_24:
    case BFD_RELOC_16:
    case BFD_RELOC_8:
    case BFD_RELOC_64_PCREL:
    case BFD_RELOC_32_PCREL:
    case BFD_RELOC_24_PCREL:
    case BFD_RELOC_16_PCREL:
    case BFD_RELOC_8_PCREL:
      md_number_to_chars (buf, val, fixP->fx_size);
      break;

    case BFD_RELOC_MMIX_ADDR19:
      if (expand_op)
	{
	  /* This shouldn't happen.  */
	  BAD_CASE (fixP->fx_r_type);
	  break;
	}
      /* FALLTHROUGH.  */
    case BFD_RELOC_MMIX_GETA:
    case BFD_RELOC_MMIX_CBRANCH:
    case BFD_RELOC_MMIX_PUSHJ:
    case BFD_RELOC_MMIX_PUSHJ_STUBBABLE:
      /* If this fixup is out of range, punt to the linker to emit an
	 error.  This should only happen with -no-expand.  */
      if (val < -(((offsetT) 1 << 19)/2)
	  || val >= ((offsetT) 1 << 19)/2 - 1
	  || (val & 3) != 0)
	{
	  if (warn_on_expansion)
	    as_warn_where (fixP->fx_file, fixP->fx_line,
			   _("operand out of range"));
	  fixP->fx_done = 0;
	  val = 0;
	}
      mmix_set_geta_branch_offset (buf, val);
      break;

    case BFD_RELOC_MMIX_ADDR27:
      if (expand_op)
	{
	  /* This shouldn't happen.  */
	  BAD_CASE (fixP->fx_r_type);
	  break;
	}
      /* FALLTHROUGH.  */
    case BFD_RELOC_MMIX_JMP:
      /* If this fixup is out of range, punt to the linker to emit an
	 error.  This should only happen with -no-expand.  */
      if (val < -(((offsetT) 1 << 27)/2)
	  || val >= ((offsetT) 1 << 27)/2 - 1
	  || (val & 3) != 0)
	{
	  if (warn_on_expansion)
	    as_warn_where (fixP->fx_file, fixP->fx_line,
			   _("operand out of range"));
	  fixP->fx_done = 0;
	  val = 0;
	}
      mmix_set_jmp_offset (buf, val);
      break;

    case BFD_RELOC_MMIX_REG_OR_BYTE:
      if (fixP->fx_addsy != NULL
	  && (S_GET_SEGMENT (fixP->fx_addsy) != reg_section
	      || S_GET_VALUE (fixP->fx_addsy) > 255)
	  && S_GET_SEGMENT (fixP->fx_addsy) != absolute_section)
	{
	  as_bad_where (fixP->fx_file, fixP->fx_line,
			_("invalid operands"));
	  /* We don't want this "symbol" appearing in output, because
	     that will fail.  */
	  fixP->fx_done = 1;
	}

      buf[0] = val;

      /* If this reloc is for a Z field, we need to adjust
	 the opcode if we got a constant here.
	 FIXME: Can we make this more robust?  */

      if ((fixP->fx_where & 3) == 3
	  && (fixP->fx_addsy == NULL
	      || S_GET_SEGMENT (fixP->fx_addsy) == absolute_section))
	buf[-3] |= IMM_OFFSET_BIT;
      break;

    case BFD_RELOC_MMIX_REG:
      if (fixP->fx_addsy == NULL
	  || S_GET_SEGMENT (fixP->fx_addsy) != reg_section
	  || S_GET_VALUE (fixP->fx_addsy) > 255)
	{
	  as_bad_where (fixP->fx_file, fixP->fx_line,
			_("invalid operands"));
	  fixP->fx_done = 1;
	}

      *buf = val;
      break;

    case BFD_RELOC_MMIX_BASE_PLUS_OFFSET:
      /* These are never "fixed".  */
      fixP->fx_done = 0;
      return;

    case BFD_RELOC_MMIX_PUSHJ_1:
    case BFD_RELOC_MMIX_PUSHJ_2:
    case BFD_RELOC_MMIX_PUSHJ_3:
    case BFD_RELOC_MMIX_CBRANCH_J:
    case BFD_RELOC_MMIX_CBRANCH_1:
    case BFD_RELOC_MMIX_CBRANCH_2:
    case BFD_RELOC_MMIX_CBRANCH_3:
    case BFD_RELOC_MMIX_GETA_1:
    case BFD_RELOC_MMIX_GETA_2:
    case BFD_RELOC_MMIX_GETA_3:
    case BFD_RELOC_MMIX_JMP_1:
    case BFD_RELOC_MMIX_JMP_2:
    case BFD_RELOC_MMIX_JMP_3:
    default:
      BAD_CASE (fixP->fx_r_type);
      break;
    }

  if (fixP->fx_done)
    /* Make sure that for completed fixups we have the value around for
       use by e.g. mmix_frob_file.  */
    fixP->fx_offset = val;
}

/* A bsearch function for looking up a value against offsets for GREG
   definitions.  */

static int
cmp_greg_val_greg_symbol_fixes (const void *p1, const void *p2)
{
  offsetT val1 = *(offsetT *) p1;
  offsetT val2 = ((struct mmix_symbol_greg_fixes *) p2)->offs;

  if (val1 >= val2 && val1 < val2 + 255)
    return 0;

  if (val1 > val2)
    return 1;

  return -1;
}

/* Generate a machine-dependent relocation.  */

arelent *
tc_gen_reloc (asection *section ATTRIBUTE_UNUSED, fixS *fixP)
{
  bfd_signed_vma val
    = fixP->fx_offset
    + (fixP->fx_addsy != NULL
       && !S_IS_WEAK (fixP->fx_addsy)
       && !S_IS_COMMON (fixP->fx_addsy)
       ? S_GET_VALUE (fixP->fx_addsy) : 0);
  arelent *relP;
  bfd_reloc_code_real_type code = BFD_RELOC_NONE;
  char *buf  = fixP->fx_where + fixP->fx_frag->fr_literal;
  symbolS *addsy = fixP->fx_addsy;
  asection *addsec = addsy == NULL ? NULL : S_GET_SEGMENT (addsy);
  asymbol *baddsy = addsy != NULL ? symbol_get_bfdsym (addsy) : NULL;
  bfd_vma addend
    = val - (baddsy == NULL || S_IS_COMMON (addsy) || S_IS_WEAK (addsy)
	     ? 0 : bfd_asymbol_value (baddsy));

  /* A single " LOCAL expression" in the wrong section will not work when
     linking to MMO; relocations for zero-content sections are then
     ignored.  Normally, relocations would modify section contents, and
     you'd never think or be able to do something like that.  The
     relocation resulting from a LOCAL directive doesn't have an obvious
     and mandatory location.  I can't figure out a way to do this better
     than just helping the user around this limitation here; hopefully the
     code using the local expression is around.  Putting the LOCAL
     semantics in a relocation still seems right; a section didn't do.  */
  if (bfd_section_size (section) == 0)
    as_bad_where
      (fixP->fx_file, fixP->fx_line,
       fixP->fx_r_type == BFD_RELOC_MMIX_LOCAL
       /* The BFD_RELOC_MMIX_LOCAL-specific message is supposed to be
	  user-friendly, though a little bit non-substantial.  */
       ? _("directive LOCAL must be placed in code or data")
       : _("internal confusion: relocation in a section without contents"));

  /* FIXME: Range tests for all these.  */
  switch (fixP->fx_r_type)
    {
    case BFD_RELOC_64:
    case BFD_RELOC_32:
    case BFD_RELOC_24:
    case BFD_RELOC_16:
    case BFD_RELOC_8:
      code = fixP->fx_r_type;

      if (addsy == NULL || bfd_is_abs_section (addsec))
	{
	  /* Resolve this reloc now, as md_apply_fix would have done (not
	     called if -linkrelax).  There is no point in keeping a reloc
	     to an absolute symbol.  No reloc that is subject to
	     relaxation must be to an absolute symbol; difference
	     involving symbols in a specific section must be signalled as
	     an error if the relaxing cannot be expressed; having a reloc
	     to the resolved (now absolute) value does not help.  */
	  md_number_to_chars (buf, val, fixP->fx_size);
	  return NULL;
	}
      break;

    case BFD_RELOC_64_PCREL:
    case BFD_RELOC_32_PCREL:
    case BFD_RELOC_24_PCREL:
    case BFD_RELOC_16_PCREL:
    case BFD_RELOC_8_PCREL:
    case BFD_RELOC_MMIX_LOCAL:
    case BFD_RELOC_VTABLE_INHERIT:
    case BFD_RELOC_VTABLE_ENTRY:
    case BFD_RELOC_MMIX_GETA:
    case BFD_RELOC_MMIX_GETA_1:
    case BFD_RELOC_MMIX_GETA_2:
    case BFD_RELOC_MMIX_GETA_3:
    case BFD_RELOC_MMIX_CBRANCH:
    case BFD_RELOC_MMIX_CBRANCH_J:
    case BFD_RELOC_MMIX_CBRANCH_1:
    case BFD_RELOC_MMIX_CBRANCH_2:
    case BFD_RELOC_MMIX_CBRANCH_3:
    case BFD_RELOC_MMIX_PUSHJ:
    case BFD_RELOC_MMIX_PUSHJ_1:
    case BFD_RELOC_MMIX_PUSHJ_2:
    case BFD_RELOC_MMIX_PUSHJ_3:
    case BFD_RELOC_MMIX_PUSHJ_STUBBABLE:
    case BFD_RELOC_MMIX_JMP:
    case BFD_RELOC_MMIX_JMP_1:
    case BFD_RELOC_MMIX_JMP_2:
    case BFD_RELOC_MMIX_JMP_3:
    case BFD_RELOC_MMIX_ADDR19:
    case BFD_RELOC_MMIX_ADDR27:
      code = fixP->fx_r_type;
      break;

    case BFD_RELOC_MMIX_REG_OR_BYTE:
      /* If we have this kind of relocation to an unknown symbol or to the
	 register contents section (that is, to a register), then we can't
	 resolve the relocation here.  */
      if (addsy != NULL
	  && (bfd_is_und_section (addsec)
	      || strcmp (bfd_section_name (addsec),
			 MMIX_REG_CONTENTS_SECTION_NAME) == 0))
	{
	  code = fixP->fx_r_type;
	  break;
	}

      /* If the relocation is not to the register section or to the
	 absolute section (a numeric value), then we have an error.  */
      if (addsy != NULL
	  && (S_GET_SEGMENT (addsy) != real_reg_section
	      || val > 255
	      || val < 0)
	  && ! bfd_is_abs_section (addsec))
	goto badop;

      /* Set the "immediate" bit of the insn if this relocation is to Z
	 field when the value is a numeric value, i.e. not a register.  */
      if ((fixP->fx_where & 3) == 3
	  && (addsy == NULL || bfd_is_abs_section (addsec)))
	buf[-3] |= IMM_OFFSET_BIT;

      buf[0] = val;
      return NULL;

    case BFD_RELOC_MMIX_BASE_PLUS_OFFSET:
      if (addsy != NULL
	  && strcmp (bfd_section_name (addsec),
		     MMIX_REG_CONTENTS_SECTION_NAME) == 0)
	{
	  /* This changed into a register; the relocation is for the
	     register-contents section.  The constant part remains zero.  */
	  code = BFD_RELOC_MMIX_REG;
	  break;
	}

      /* If we've found out that this was indeed a register, then replace
	 with the register number.  The constant part is already zero.

	 If we encounter any other defined symbol, then we must find a
	 suitable register and emit a reloc.  */
      if (addsy == NULL || addsec != real_reg_section)
	{
	  struct mmix_symbol_gregs *gregs;
	  struct mmix_symbol_greg_fixes *fix;

	  if (S_IS_DEFINED (addsy)
	      && !bfd_is_com_section (addsec)
	      && !S_IS_WEAK (addsy))
	    {
	      if (! symbol_section_p (addsy) && ! bfd_is_abs_section (addsec))
		as_fatal (_("internal: BFD_RELOC_MMIX_BASE_PLUS_OFFSET not resolved to section"));

	      /* If this is an absolute symbol sufficiently near
		 lowest_data_loc, then we canonicalize on the data
		 section.  Note that val is signed here; we may subtract
		 lowest_data_loc which is unsigned.  Careful with those
		 comparisons.  */
	      if (lowest_data_loc != (bfd_vma) -1
		  && (bfd_vma) val + 256 > lowest_data_loc
		  && bfd_is_abs_section (addsec))
		{
		  val -= (offsetT) lowest_data_loc;
		  addsy = section_symbol (data_section);
		}
	      /* Likewise text section.  */
	      else if (lowest_text_loc != (bfd_vma) -1
		       && (bfd_vma) val + 256 > lowest_text_loc
		       && bfd_is_abs_section (addsec))
		{
		  val -= (offsetT) lowest_text_loc;
		  addsy = section_symbol (text_section);
		}
	    }

	  gregs = *symbol_get_tc (addsy);

	  /* If that symbol does not have any associated GREG definitions,
	     we can't do anything.  */
	  if (gregs == NULL
	      || (fix = bsearch (&val, gregs->greg_fixes, gregs->n_gregs,
				 sizeof (gregs->greg_fixes[0]),
				 cmp_greg_val_greg_symbol_fixes)) == NULL
	      /* The register must not point *after* the address we want.  */
	      || fix->offs > val
	      /* Neither must the register point more than 255 bytes
		 before the address we want.  */
	      || fix->offs + 255 < val)
	    {
	      /* We can either let the linker allocate GREGs
		 automatically, or emit an error.  */
	      if (allocate_undefined_gregs_in_linker)
		{
		  /* The values in baddsy and addend are right.  */
		  code = fixP->fx_r_type;
		  break;
		}
	      else
		as_bad_where (fixP->fx_file, fixP->fx_line,
			      _("no suitable GREG definition for operands"));
	      return NULL;
	    }
	  else
	    {
	      /* Transform the base-plus-offset reloc for the actual area
		 to a reloc for the register with the address of the area.
		 Put addend for register in Z operand.  */
	      buf[1] = val - fix->offs;
	      code = BFD_RELOC_MMIX_REG;
	      baddsy
		= (bfd_get_section_by_name (stdoutput,
					    MMIX_REG_CONTENTS_SECTION_NAME)
		   ->symbol);

	      addend = fix->fix->fx_frag->fr_address + fix->fix->fx_where;
	    }
	}
      else if (S_GET_VALUE (addsy) > 255)
	as_bad_where (fixP->fx_file, fixP->fx_line,
		      _("invalid operands"));
      else
	{
	  *buf = val;
	  return NULL;
	}
      break;

    case BFD_RELOC_MMIX_REG:
      if (addsy != NULL
	  && (bfd_is_und_section (addsec)
	      || strcmp (bfd_section_name (addsec),
			 MMIX_REG_CONTENTS_SECTION_NAME) == 0))
	{
	  code = fixP->fx_r_type;
	  break;
	}

      if (addsy != NULL
	  && (addsec != real_reg_section
	      || val > 255
	      || val < 0)
	  && ! bfd_is_und_section (addsec))
	/* Drop through to error message.  */
	;
      else
	{
	  buf[0] = val;
	  return NULL;
	}
      /* FALLTHROUGH.  */

      /* The others are supposed to be handled by md_apply_fix.
	 FIXME: ... which isn't called when -linkrelax.  Move over
	 md_apply_fix code here for everything reasonable.  */
    badop:
    default:
      as_bad_where
	(fixP->fx_file, fixP->fx_line,
	 _("operands were not reducible at assembly-time"));

      /* Unmark this symbol as used in a reloc, so we don't bump into a BFD
	 assert when trying to output reg_section.  FIXME: A gas bug.  */
      fixP->fx_addsy = NULL;
      return NULL;
    }

  relP = XNEW (arelent);
  gas_assert (relP != 0);
  relP->sym_ptr_ptr = XNEW (asymbol *);
  *relP->sym_ptr_ptr = baddsy;
  relP->address = fixP->fx_frag->fr_address + fixP->fx_where;

  relP->addend = addend;

  /* If this had been a.out, we would have had a kludge for weak symbols
     here.  */

  relP->howto = bfd_reloc_type_lookup (stdoutput, code);
  if (! relP->howto)
    {
      const char *name;

      name = S_GET_NAME (addsy);
      if (name == NULL)
	name = _("<unknown>");
      as_fatal (_("cannot generate relocation type for symbol %s, code %s"),
		name, bfd_get_reloc_code_name (code));
    }

  return relP;
}

/* Do some reformatting of a line.  FIXME: We could transform a mmixal
   line into traditional (GNU?) format, unless #NO_APP, and get rid of all
   ugly labels_without_colons etc.  */

void
mmix_handle_mmixal (void)
{
  char *insn;
  char *s = input_line_pointer;
  char *label = NULL;
  char c;

  if (pending_label != NULL)
    as_fatal (_("internal: unhandled label %s"), pending_label);

  if (mmix_gnu_syntax)
    return;

  /* If we're on a line with a label, check if it's a mmixal fb-label.
     Save an indicator and skip the label; it must be set only after all
     fb-labels of expressions are evaluated.  */
  if (ISDIGIT (s[0]) && s[1] == 'H' && ISSPACE (s[2]))
    {
      current_fb_label = s[0] - '0';

      /* We have to skip the label, but also preserve the newlineness of
	 the previous character, since the caller checks that.  It's a
	 mess we blame on the caller.  */
      s[1] = s[-1];
      s += 2;
      input_line_pointer = s;

      while (*s && ISSPACE (*s) && ! is_end_of_line[(unsigned int) *s])
	s++;

      /* For errors emitted here, the book-keeping is off by one; the
	 caller is about to bump the counters.  Adjust the error messages.  */
      if (is_end_of_line[(unsigned int) *s])
	{
	  unsigned int line;
	  const char * name = as_where (&line);
	  as_bad_where (name, line + 1,
			_("[0-9]H labels may not appear alone on a line"));
	  current_fb_label = -1;
	}
      if (*s == '.')
	{
	  unsigned int line;
	  const char * name  = as_where (&line);
	  as_bad_where (name, line + 1,
			_("[0-9]H labels do not mix with dot-pseudos"));
	  current_fb_label = -1;
	}

      /* Back off to the last space before the opcode so we don't handle
	 the opcode as a label.  */
      s--;
    }
  else
    current_fb_label = -1;

  if (*s == '.')
    {
      /* If the first character is a '.', then it's a pseudodirective, not a
	 label.  Make GAS not handle label-without-colon on this line.  We
	 also don't do mmixal-specific stuff on this line.  */
      label_without_colon_this_line = 0;
      return;
    }

  if (*s == 0 || is_end_of_line[(unsigned int) *s])
    /* We avoid handling empty lines here.  */
    return;

  if (is_name_beginner (*s))
    label = s;

  /* If there is a label, skip over it.  */
  while (*s && is_part_of_name (*s))
    s++;

  /* Find the start of the instruction or pseudo following the label,
     if there is one.  */
  for (insn = s;
       *insn && ISSPACE (*insn) && ! is_end_of_line[(unsigned int) *insn];
       insn++)
    /* Empty */
    ;

  /* Remove a trailing ":" off labels, as they'd otherwise be considered
     part of the name.  But don't do this for local labels.  */
  if (s != input_line_pointer && s[-1] == ':'
      && (s - 2 != input_line_pointer
	  || ! ISDIGIT (s[-2])))
    s[-1] = ' ';
  else if (label != NULL
	   /* For a lone label on a line, we don't attach it to the next
	      instruction or MMIXAL-pseudo (getting its alignment).  Thus
	      is acts like a "normal" :-ended label.  Ditto if it's
	      followed by a non-MMIXAL pseudo.  */
	   && !is_end_of_line[(unsigned int) *insn]
	   && *insn != '.')
    {
      /* For labels that don't end in ":", we save it so we can later give
	 it the same alignment and address as the associated instruction.  */

      /* Make room for the label including the ending nul.  */
      size_t len_0 = s - label + 1;

      /* Save this label on the MMIX symbol obstack.  Saving it on an
	 obstack is needless for "IS"-pseudos, but it's harmless and we
	 avoid a little code-cluttering.  */
      obstack_grow (&mmix_sym_obstack, label, len_0);
      pending_label = obstack_finish (&mmix_sym_obstack);
      pending_label[len_0 - 1] = 0;
    }

  /* If we have a non-MMIXAL pseudo, we have not business with the rest of
     the line.  */
  if (*insn == '.')
    return;

  /* Find local labels of operands.  Look for "[0-9][FB]" where the
     characters before and after are not part of words.  Break if a single
     or double quote is seen anywhere.  It means we can't have local
     labels as part of list with mixed quoted and unquoted members for
     mmixal compatibility but we can't have it all.  For the moment.
     Replace the '<N>B' or '<N>F' with MAGIC_FB_BACKWARD_CHAR<N> and
     MAGIC_FB_FORWARD_CHAR<N> respectively.  */

  /* First make sure we don't have any of the magic characters on the line
     appearing as input.  */
  while (*s)
    {
      c = *s++;
      if (is_end_of_line[(unsigned int) c])
	break;
      if (c == MAGIC_FB_BACKWARD_CHAR || c == MAGIC_FB_FORWARD_CHAR)
	as_bad (_("invalid characters in input"));
    }

  /* Scan again, this time looking for ';' after operands.  */
  s = insn;

  /* Skip the insn.  */
  while (*s
	 && ! ISSPACE (*s)
	 && *s != ';'
	 && ! is_end_of_line[(unsigned int) *s])
    s++;

  /* Skip the spaces after the insn.  */
  while (*s
	 && ISSPACE (*s)
	 && *s != ';'
	 && ! is_end_of_line[(unsigned int) *s])
    s++;

  /* Skip the operands.  While doing this, replace [0-9][BF] with
     (MAGIC_FB_BACKWARD_CHAR|MAGIC_FB_FORWARD_CHAR)[0-9].  */
  while ((c = *s) != 0
	 && ! ISSPACE (c)
	 && c != ';'
	 && ! is_end_of_line[(unsigned int) c])
    {
      if (c == '"')
	{
	  s++;

	  /* FIXME: Test-case for semi-colon in string.  */
	  while (*s
		 && *s != '"'
		 && (! is_end_of_line[(unsigned int) *s] || *s == ';'))
	    s++;

	  if (*s == '"')
	    s++;
	}
      else if (ISDIGIT (c))
	{
	  if ((s[1] != 'B' && s[1] != 'F')
	      || is_part_of_name (s[-1])
	      || is_part_of_name (s[2])
	      /* Don't treat e.g. #1F as a local-label reference.  */
	      || (s != input_line_pointer && s[-1] == '#'))
	    s++;
	  else
	    {
	      s[0] = (s[1] == 'B'
		      ? MAGIC_FB_BACKWARD_CHAR : MAGIC_FB_FORWARD_CHAR);
	      s[1] = c;
	    }
	}
      else
	s++;
    }

  /* Skip any spaces after the operands.  */
  while (*s
	 && ISSPACE (*s)
	 && *s != ';'
	 && !is_end_of_line[(unsigned int) *s])
    s++;

  /* If we're now looking at a semi-colon, then it's an end-of-line
     delimiter.  */
  mmix_next_semicolon_is_eoln = (*s == ';');

  /* Make IS into an EQU by replacing it with "= ".  Only match upper-case
     though; let lower-case be a syntax error.  */
  s = insn;
  if (s[0] == 'I' && s[1] == 'S' && ISSPACE (s[2]))
    {
      *s = '=';
      s[1] = ' ';

      /* Since labels can start without ":", we have to handle "X IS 42"
	 in full here, or "X" will be parsed as a label to be set at ".".  */
      input_line_pointer = s;

      /* Right after this function ends, line numbers will be bumped if
	 input_line_pointer[-1] = '\n'.  We want accurate line numbers for
	 the equals call, so we bump them before the call, and make sure
	 they aren't bumped afterwards.  */
      bump_line_counters ();

      /* A fb-label is valid as an IS-label.  */
      if (current_fb_label >= 0)
	{
	  char *fb_name;

	  /* We need to save this name on our symbol obstack, since the
	     string we got in fb_label_name is volatile and will change
	     with every call to fb_label_name, like those resulting from
	     parsing the IS-operand.  */
	  fb_name = fb_label_name (current_fb_label, 1);
	  obstack_grow (&mmix_sym_obstack, fb_name, strlen (fb_name) + 1);
	  equals (obstack_finish (&mmix_sym_obstack), 0);
	  fb_label_instance_inc (current_fb_label);
	  current_fb_label = -1;
	}
      else
	{
	  if (pending_label == NULL)
	    as_bad (_("empty label field for IS"));
	  else
	    equals (pending_label, 0);
	  pending_label = NULL;
	}

      /* For mmixal, we can have comments without a comment-start
	 character.   */
      mmix_handle_rest_of_empty_line ();
      input_line_pointer--;

      input_line_pointer[-1] = ' ';
    }
  else if (s[0] == 'G'
	   && s[1] == 'R'
	   && startswith (s, "GREG")
	   && (ISSPACE (s[4]) || is_end_of_line[(unsigned char) s[4]]))
    {
      input_line_pointer = s + 4;

      /* Right after this function ends, line numbers will be bumped if
	 input_line_pointer[-1] = '\n'.  We want accurate line numbers for
	 the s_greg call, so we bump them before the call, and make sure
	 they aren't bumped afterwards.  */
      bump_line_counters ();

      /* A fb-label is valid as a GREG-label.  */
      if (current_fb_label >= 0)
	{
	  char *fb_name;

	  /* We need to save this name on our symbol obstack, since the
	     string we got in fb_label_name is volatile and will change
	     with every call to fb_label_name, like those resulting from
	     parsing the IS-operand.  */
	  fb_name = fb_label_name (current_fb_label, 1);

	  /* Make sure we save the canonical name and don't get bitten by
             prefixes.  */
	  obstack_1grow (&mmix_sym_obstack, ':');
	  obstack_grow (&mmix_sym_obstack, fb_name, strlen (fb_name) + 1);
	  mmix_greg_internal (obstack_finish (&mmix_sym_obstack));
	  fb_label_instance_inc (current_fb_label);
	  current_fb_label = -1;
	}
      else
	mmix_greg_internal (pending_label);

      /* Back up before the end-of-line marker that was skipped in
	 mmix_greg_internal.  */
      input_line_pointer--;
      input_line_pointer[-1] = ' ';

      pending_label = NULL;
    }
  else if (pending_label != NULL)
    {
      input_line_pointer += strlen (pending_label);

      /* See comment above about getting line numbers bumped.  */
      input_line_pointer[-1] = '\n';
    }
}

/* Give the value of an fb-label rewritten as in mmix_handle_mmixal, when
   parsing an expression.

   On valid calls, input_line_pointer points at a MAGIC_FB_BACKWARD_CHAR
   or MAGIC_FB_BACKWARD_CHAR, followed by an ascii digit for the label.
   We fill in the label as an expression.  */

void
mmix_fb_label (expressionS *expP)
{
  symbolS *sym;
  char *fb_internal_name;

  /* This doesn't happen when not using mmixal syntax.  */
  if (mmix_gnu_syntax
      || (input_line_pointer[0] != MAGIC_FB_BACKWARD_CHAR
	  && input_line_pointer[0] != MAGIC_FB_FORWARD_CHAR))
    return;

  /* The current backward reference has augmentation 0.  A forward
     reference has augmentation 1, unless it's the same as a fb-label on
     _this_ line, in which case we add one more so we don't refer to it.
     This is the semantics of mmixal; it differs to that of common
     fb-labels which refer to a here-label on the current line as a
     backward reference.  */
  fb_internal_name
    = fb_label_name (input_line_pointer[1] - '0',
		     (input_line_pointer[0] == MAGIC_FB_FORWARD_CHAR ? 1 : 0)
		     + ((input_line_pointer[1] - '0' == current_fb_label
			 && input_line_pointer[0] == MAGIC_FB_FORWARD_CHAR)
			? 1 : 0));

  input_line_pointer += 2;
  sym = symbol_find_or_make (fb_internal_name);

  /* We don't have to clean up unrelated fields here; we just do what the
     expr machinery does, but *not* just what it does for [0-9][fb], since
     we need to treat those as ordinary symbols sometimes; see testcases
     err-byte2.s and fb-2.s.  */
  if (S_GET_SEGMENT (sym) == absolute_section)
    {
      expP->X_op = O_constant;
      expP->X_add_number = S_GET_VALUE (sym);
    }
  else
    {
      expP->X_op = O_symbol;
      expP->X_add_symbol = sym;
      expP->X_add_number = 0;
    }
}

/* See whether we need to force a relocation into the output file.
   This is used to force out switch and PC relative relocations when
   relaxing.  */

int
mmix_force_relocation (fixS *fixP)
{
  if (fixP->fx_r_type == BFD_RELOC_MMIX_LOCAL
      || fixP->fx_r_type == BFD_RELOC_MMIX_BASE_PLUS_OFFSET)
    return 1;

  if (linkrelax)
    return 1;

  /* All our pcrel relocations are must-keep.  Note that md_apply_fix is
     called *after* this, and will handle getting rid of the presumed
     reloc; a relocation isn't *forced* other than to be handled by
     md_apply_fix (or tc_gen_reloc if linkrelax).  */
  if (fixP->fx_pcrel)
    return 1;

  return generic_force_reloc (fixP);
}

/* The location from which a PC relative jump should be calculated,
   given a PC relative reloc.  */

long
md_pcrel_from_section (fixS *fixP, segT sec)
{
  if (fixP->fx_addsy != (symbolS *) NULL
      && (! S_IS_DEFINED (fixP->fx_addsy)
	  || S_GET_SEGMENT (fixP->fx_addsy) != sec))
    {
      /* The symbol is undefined (or is defined but not in this section).
	 Let the linker figure it out.  */
      return 0;
    }

  return (fixP->fx_frag->fr_address + fixP->fx_where);
}

/* Adjust the symbol table.  We make reg_section relative to the real
   register section.  */

void
mmix_adjust_symtab (void)
{
  symbolS *sym;
  symbolS *regsec = section_symbol (reg_section);

  for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
    if (S_GET_SEGMENT (sym) == reg_section)
      {
	if (sym == regsec)
	  {
	    if (S_IS_EXTERNAL (sym) || symbol_used_in_reloc_p (sym))
	      abort ();
	    symbol_remove (sym, &symbol_rootP, &symbol_lastP);
	  }
	else
	  /* Change section to the *real* register section, so it gets
	     proper treatment when writing it out.  Only do this for
	     global symbols.  This also means we don't have to check for
	     $0..$255.  */
	  S_SET_SEGMENT (sym, real_reg_section);
      }
}

/* This is the expansion of LABELS_WITHOUT_COLONS.
   We let md_start_line_hook tweak label_without_colon_this_line, and then
   this function returns the tweaked value, and sets it to 1 for the next
   line.  FIXME: Very, very brittle.  Not sure it works the way I
   thought at the time I first wrote this.  */

int
mmix_label_without_colon_this_line (void)
{
  int retval = label_without_colon_this_line;

  if (! mmix_gnu_syntax)
    label_without_colon_this_line = 1;

  return retval;
}

/* This is the expansion of md_relax_frag.  We go through the ordinary
   relax table function except when the frag is for a GREG.  Then we have
   to check whether there's another GREG by the same value that we can
   join with.  */

long
mmix_md_relax_frag (segT seg, fragS *fragP, long stretch)
{
  switch (fragP->fr_subtype)
    {
      /* Growth for this type has been handled by mmix_md_end and
	 correctly estimated, so there's nothing more to do here.  */
    case STATE_GREG_DEF:
      return 0;

    case ENCODE_RELAX (STATE_PUSHJ, STATE_ZERO):
      {
	/* We need to handle relaxation type ourselves, since relax_frag
	   doesn't update fr_subtype if there's no size increase in the
	   current section; when going from plain PUSHJ to a stub.  This
	   is otherwise functionally the same as relax_frag in write.c,
	   simplified for this case.  */
	offsetT aim;
	addressT target;
	addressT address;
	symbolS *symbolP;
	target = fragP->fr_offset;
	address = fragP->fr_address;
	symbolP = fragP->fr_symbol;

	if (symbolP)
	  {
	    fragS *sym_frag;

	    sym_frag = symbol_get_frag (symbolP);
	    know (S_GET_SEGMENT (symbolP) != absolute_section
		  || sym_frag == &zero_address_frag);
	    target += S_GET_VALUE (symbolP);

	    /* If frag has yet to be reached on this pass, assume it will
	       move by STRETCH just as we did.  If this is not so, it will
	       be because some frag between grows, and that will force
	       another pass.  */

	    if (stretch != 0
		&& sym_frag->relax_marker != fragP->relax_marker
		&& S_GET_SEGMENT (symbolP) == seg)
	      target += stretch;
	  }

	aim = target - address - fragP->fr_fix;
	if (aim >= PUSHJ_0B && aim <= PUSHJ_0F)
	  {
	    /* Target is reachable with a PUSHJ.  */
	    segment_info_type *seginfo = seg_info (seg);

	    /* If we're at the end of a relaxation round, clear the stub
	       counter as initialization for the next round.  */
	    if (fragP == seginfo->tc_segment_info_data.last_stubfrag)
	      seginfo->tc_segment_info_data.nstubs = 0;
	    return 0;
	  }

	/* Not reachable.  Try a stub.  */
	fragP->fr_subtype = ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO);
      }
      /* FALLTHROUGH.  */

      /* See if this PUSHJ is redirectable to a stub.  */
    case ENCODE_RELAX (STATE_PUSHJSTUB, STATE_ZERO):
      {
	segment_info_type *seginfo = seg_info (seg);
	fragS *lastfrag = seginfo->frchainP->frch_last;
	relax_substateT prev_type = fragP->fr_subtype;

	/* The last frag is always an empty frag, so it suffices to look
	   at its address to know the ending address of this section.  */
	know (lastfrag->fr_type == rs_fill
	      && lastfrag->fr_fix == 0
	      && lastfrag->fr_var == 0);

	/* For this PUSHJ to be relaxable into a call to a stub, the
	   distance must be no longer than 256k bytes from the PUSHJ to
	   the end of the section plus the maximum size of stubs so far.  */
	if ((lastfrag->fr_address
	     + stretch
	     + PUSHJ_MAX_LEN * seginfo->tc_segment_info_data.nstubs)
	    - (fragP->fr_address + fragP->fr_fix)
	    > GETA_0F
	    || !pushj_stubs)
	  fragP->fr_subtype = mmix_relax_table[prev_type].rlx_more;
	else
	  seginfo->tc_segment_info_data.nstubs++;

	/* If we're at the end of a relaxation round, clear the stub
	   counter as initialization for the next round.  */
	if (fragP == seginfo->tc_segment_info_data.last_stubfrag)
	  seginfo->tc_segment_info_data.nstubs = 0;

	return
	   (mmix_relax_table[fragP->fr_subtype].rlx_length
	    - mmix_relax_table[prev_type].rlx_length);
      }

    case ENCODE_RELAX (STATE_PUSHJ, STATE_MAX):
      {
	segment_info_type *seginfo = seg_info (seg);

	/* Need to cover all STATE_PUSHJ states to act on the last stub
	   frag (the end of this relax round; initialization for the
	   next).  */
	if (fragP == seginfo->tc_segment_info_data.last_stubfrag)
	  seginfo->tc_segment_info_data.nstubs = 0;

	return 0;
      }

    default:
      return relax_frag (seg, fragP, stretch);

    case STATE_GREG_UNDF:
      BAD_CASE (fragP->fr_subtype);
    }

  as_fatal (_("internal: unexpected relax type %d:%d"),
	    fragP->fr_type, fragP->fr_subtype);
  return 0;
}

/* Various things we punt until all input is seen.  */

void
mmix_md_end (void)
{
  fragS *fragP;
  symbolS *mainsym;
  asection *regsec;
  struct loc_assert_s *loc_assert;
  int i;

  /* The first frag of GREG:s going into the register contents section.  */
  fragS *mmix_reg_contents_frags = NULL;

  /* Reset prefix.  All labels reachable at this point must be
     canonicalized.  */
  mmix_current_prefix = NULL;

  if (doing_bspec)
    as_bad_where (bspec_file, bspec_line, _("BSPEC without ESPEC."));

  /* Emit the low LOC setting of .text.  */
  if (text_has_contents && lowest_text_loc != (bfd_vma) -1)
    {
      symbolS *symbolP;
      char locsymbol[sizeof (":") - 1
		    + sizeof (MMIX_LOC_SECTION_START_SYMBOL_PREFIX) - 1
		    + sizeof (".text")];

      /* An exercise in non-ISO-C-ness, this one.  */
      sprintf (locsymbol, ":%s%s", MMIX_LOC_SECTION_START_SYMBOL_PREFIX,
	       ".text");
      symbolP
	= symbol_new (locsymbol, absolute_section, &zero_address_frag,
		      lowest_text_loc);
      S_SET_EXTERNAL (symbolP);
    }

  /* Ditto .data.  */
  if (data_has_contents && lowest_data_loc != (bfd_vma) -1)
    {
      symbolS *symbolP;
      char locsymbol[sizeof (":") - 1
		     + sizeof (MMIX_LOC_SECTION_START_SYMBOL_PREFIX) - 1
		     + sizeof (".data")];

      sprintf (locsymbol, ":%s%s", MMIX_LOC_SECTION_START_SYMBOL_PREFIX,
	       ".data");
      symbolP
	= symbol_new (locsymbol, absolute_section, &zero_address_frag,
		      lowest_data_loc);
      S_SET_EXTERNAL (symbolP);
    }

  /* Unless GNU syntax mode, set "Main" to be a function, so the
     disassembler doesn't get confused when we write truly
     mmixal-compatible code (and don't use .type).  Similarly set it
     global (regardless of -globalize-symbols), so the linker sees it as
     the start symbol in ELF mode.  */
  mainsym = symbol_find (MMIX_START_SYMBOL_NAME);
  if (mainsym != NULL && ! mmix_gnu_syntax)
    {
      symbol_get_bfdsym (mainsym)->flags |= BSF_FUNCTION;
      S_SET_EXTERNAL (mainsym);
    }

  /* Check that we didn't LOC into the unknown, or rather that when it
     was unknown, we actually change sections.  */
  for (loc_assert = loc_asserts;
       loc_assert != NULL;
       loc_assert = loc_assert->next)
    {
      segT actual_seg;

      resolve_symbol_value (loc_assert->loc_sym);
      actual_seg = S_GET_SEGMENT (loc_assert->loc_sym);
      if (actual_seg != loc_assert->old_seg)
	{
	  const char *fnam;
	  unsigned int line;
	  int e_valid = expr_symbol_where (loc_assert->loc_sym, &fnam, &line);

	  gas_assert (e_valid == 1);
	  as_bad_where (fnam, line,
			_("LOC to section unknown or indeterminable "
			  "at first pass"));

	  /* Patch up the generic location data to avoid cascading
	     error messages from later passes.  (See original in
	     write.c:relax_segment.)  */
	  fragP = loc_assert->frag;
	  fragP->fr_type = rs_align;
	  fragP->fr_subtype = 0;
	  fragP->fr_offset = 0;
	  fragP->fr_fix = 0;
	}
    }

  if (n_of_raw_gregs != 0)
    {
      /* Emit GREGs.  They are collected in order of appearance, but must
	 be emitted in opposite order to both have section address regno*8
	 and the same allocation order (within a file) as mmixal.  */
      segT this_segment = now_seg;
      subsegT this_subsegment = now_subseg;

      regsec = bfd_make_section_old_way (stdoutput,
					 MMIX_REG_CONTENTS_SECTION_NAME);
      subseg_set (regsec, 0);

      /* Finally emit the initialization-value.  Emit a variable frag, which
	 we'll fix in md_estimate_size_before_relax.  We set the initializer
	 for the tc_frag_data field to NULL, so we can use that field for
	 relaxation purposes.  */
      mmix_opcode_frag = NULL;

      frag_grow (0);
      mmix_reg_contents_frags = frag_now;

      for (i = n_of_raw_gregs - 1; i >= 0; i--)
	{
	  if (mmix_raw_gregs[i].label != NULL)
	    /* There's a symbol.  Let it refer to this location in the
	       register contents section.  The symbol must be globalized
	       separately.  */
	    colon (mmix_raw_gregs[i].label);

	  frag_var (rs_machine_dependent, 8, 0, STATE_GREG_UNDF,
		    make_expr_symbol (&mmix_raw_gregs[i].exp), 0, NULL);
	}

      subseg_set (this_segment, this_subsegment);
    }

  regsec = bfd_get_section_by_name (stdoutput, MMIX_REG_CONTENTS_SECTION_NAME);
  /* Mark the section symbol as being OK for a reloc.  */
  if (regsec != NULL)
    regsec->symbol->flags |= BSF_KEEP;

  /* Iterate over frags resulting from GREGs and move those that evidently
     have the same value together and point one to another.

     This works in time O(N^2) but since the upper bound for non-error use
     is 223, it's best to keep this simpler algorithm.  */
  for (fragP = mmix_reg_contents_frags; fragP != NULL; fragP = fragP->fr_next)
    {
      fragS **fpp;
      fragS *fp = NULL;
      fragS *osymfrag;
      offsetT osymval;
      expressionS *oexpP;
      symbolS *symbolP = fragP->fr_symbol;

      if (fragP->fr_type != rs_machine_dependent
	  || fragP->fr_subtype != STATE_GREG_UNDF)
	continue;

      /* Whatever the outcome, we will have this GREG judged merged or
	 non-merged.  Since the tc_frag_data is NULL at this point, we
	 default to non-merged.  */
      fragP->fr_subtype = STATE_GREG_DEF;

      /* If we're not supposed to merge GREG definitions, then just don't
	 look for equivalents.  */
      if (! merge_gregs)
	continue;

      osymval = (offsetT) S_GET_VALUE (symbolP);
      osymfrag = symbol_get_frag (symbolP);

      /* If the symbol isn't defined, we can't say that another symbol
	 equals this frag, then.  FIXME: We can look at the "deepest"
	 defined name; if a = c and b = c then obviously a == b.  */
      if (! S_IS_DEFINED (symbolP))
	continue;

      oexpP = symbol_get_value_expression (fragP->fr_symbol);

      /* If the initialization value is zero, then we must not merge them.  */
      if (oexpP->X_op == O_constant && osymval == 0)
	continue;

      /* Iterate through the frags downward this one.  If we find one that
	 has the same non-zero value, move it to after this one and point
	 to it as the equivalent.  */
      for (fpp = &fragP->fr_next; *fpp != NULL; fpp = &fpp[0]->fr_next)
	{
	  fp = *fpp;

	  if (fp->fr_type != rs_machine_dependent
	      || fp->fr_subtype != STATE_GREG_UNDF)
	    continue;

	  /* Calling S_GET_VALUE may simplify the symbol, changing from
	     expr_section etc. so call it first.  */
	  if ((offsetT) S_GET_VALUE (fp->fr_symbol) == osymval
	      && symbol_get_frag (fp->fr_symbol) == osymfrag)
	    {
	      /* Move the frag links so the one we found equivalent comes
		 after the current one, carefully considering that
		 sometimes fpp == &fragP->fr_next and the moves must be a
		 NOP then.  */
	      *fpp = fp->fr_next;
	      fp->fr_next = fragP->fr_next;
	      fragP->fr_next = fp;
	      break;
	    }
	}

      if (*fpp != NULL)
	fragP->tc_frag_data = fp;
    }
}

/* qsort function for mmix_symbol_gregs.  */

static int
cmp_greg_symbol_fixes (const void *parg, const void *qarg)
{
  const struct mmix_symbol_greg_fixes *p
    = (const struct mmix_symbol_greg_fixes *) parg;
  const struct mmix_symbol_greg_fixes *q
    = (const struct mmix_symbol_greg_fixes *) qarg;

  return p->offs > q->offs ? 1 : p->offs < q->offs ? -1 : 0;
}

/* Collect GREG definitions from mmix_gregs and hang them as lists sorted
   on increasing offsets onto each section symbol or undefined symbol.

   Also, remove the register convenience section so it doesn't get output
   as an ELF section.  */

void
mmix_frob_file (void)
{
  int i;
  struct mmix_symbol_gregs *all_greg_symbols[MAX_GREGS];
  int n_greg_symbols = 0;

  /* Collect all greg fixups and decorate each corresponding symbol with
     the greg fixups for it.  */
  for (i = 0; i < n_of_cooked_gregs; i++)
    {
      offsetT offs;
      symbolS *sym;
      struct mmix_symbol_gregs *gregs;
      fixS *fixP;

      fixP = mmix_gregs[i];
      know (fixP->fx_r_type == BFD_RELOC_64);

      /* This case isn't doable in general anyway, methinks.  */
      if (fixP->fx_subsy != NULL)
	{
	  as_bad_subtract (fixP);
	  continue;
	}

      sym = fixP->fx_addsy;
      offs = (offsetT) fixP->fx_offset;

      /* If the symbol is defined, then it must be resolved to a section
	 symbol at this time, or else we don't know how to handle it.  */
      if (S_IS_DEFINED (sym)
	  && !bfd_is_com_section (S_GET_SEGMENT (sym))
	  && !S_IS_WEAK (sym))
	{
	  if (! symbol_section_p (sym)
	      && ! bfd_is_abs_section (S_GET_SEGMENT (sym)))
	    as_fatal (_("internal: GREG expression not resolved to section"));

	  offs += S_GET_VALUE (sym);
	}

      /* If this is an absolute symbol sufficiently near lowest_data_loc,
	 then we canonicalize on the data section.  Note that offs is
	 signed here; we may subtract lowest_data_loc which is unsigned.
	 Careful with those comparisons.  */
      if (lowest_data_loc != (bfd_vma) -1
	  && (bfd_vma) offs + 256 > lowest_data_loc
	  && bfd_is_abs_section (S_GET_SEGMENT (sym)))
	{
	  offs -= (offsetT) lowest_data_loc;
	  sym = section_symbol (data_section);
	}
      /* Likewise text section.  */
      else if (lowest_text_loc != (bfd_vma) -1
	       && (bfd_vma) offs + 256 > lowest_text_loc
	       && bfd_is_abs_section (S_GET_SEGMENT (sym)))
	{
	  offs -= (offsetT) lowest_text_loc;
	  sym = section_symbol (text_section);
	}

      gregs = *symbol_get_tc (sym);

      if (gregs == NULL)
	{
	  gregs = XNEW (struct mmix_symbol_gregs);
	  gregs->n_gregs = 0;
	  symbol_set_tc (sym, &gregs);
	  all_greg_symbols[n_greg_symbols++] = gregs;
	}

      gregs->greg_fixes[gregs->n_gregs].fix = fixP;
      gregs->greg_fixes[gregs->n_gregs++].offs = offs;
    }

  /* For each symbol having a GREG definition, sort those definitions on
     offset.  */
  for (i = 0; i < n_greg_symbols; i++)
    qsort (all_greg_symbols[i]->greg_fixes, all_greg_symbols[i]->n_gregs,
	   sizeof (all_greg_symbols[i]->greg_fixes[0]), cmp_greg_symbol_fixes);

  if (real_reg_section != NULL)
    {
      /* FIXME: Pass error state gracefully.  */
      if (bfd_section_flags (real_reg_section) & SEC_HAS_CONTENTS)
	as_fatal (_("register section has contents\n"));

      bfd_section_list_remove (stdoutput, real_reg_section);
      --stdoutput->section_count;
    }

}

/* Provide an expression for a built-in name provided when-used.
   Either a symbol that is a handler; living in 0x10*[1..8] and having
   name [DVWIOUZX]_Handler, or a mmixal built-in symbol.

   If the name isn't a built-in name and parsed into *EXPP, return zero.  */

int
mmix_parse_predefined_name (char *name, expressionS *expP)
{
  char *canon_name;
  const char *handler_charp;
  const char handler_chars[] = "DVWIOUZX";
  symbolS *symp;

  if (! predefined_syms)
    return 0;

  canon_name = tc_canonicalize_symbol_name (name);

  if (canon_name[1] == '_'
      && strcmp (canon_name + 2, "Handler") == 0
      && (handler_charp = strchr (handler_chars, *canon_name)) != NULL)
    {
      /* If the symbol doesn't exist, provide one relative to the .text
	 section.

	 FIXME: We should provide separate sections, mapped in the linker
	 script.  */
      symp = symbol_find (name);
      if (symp == NULL)
	symp = symbol_new (name, text_section, &zero_address_frag,
			   0x10 * (handler_charp + 1 - handler_chars));
    }
  else
    {
      /* These symbols appear when referenced; needed for
         mmixal-compatible programs.  */
      unsigned int i;

      static const struct
      {
	const char *name;
	valueT val;
      } predefined_abs_syms[] =
	{
	  {"Data_Segment", (valueT) 0x20 << 56},
	  {"Pool_Segment", (valueT) 0x40 << 56},
	  {"Stack_Segment", (valueT) 0x60 << 56},
	  {"StdIn", 0},
	  {"StdOut", 1},
	  {"StdErr", 2},
	  {"TextRead", 0},
	  {"TextWrite", 1},
	  {"BinaryRead", 2},
	  {"BinaryWrite", 3},
	  {"BinaryReadWrite", 4},
	  {"Halt", 0},
	  {"Fopen", 1},
	  {"Fclose", 2},
	  {"Fread", 3},
	  {"Fgets", 4},
	  {"Fgetws", 5},
	  {"Fwrite", 6},
	  {"Fputs", 7},
	  {"Fputws", 8},
	  {"Fseek", 9},
	  {"Ftell", 10},
	  {"D_BIT", 0x80},
	  {"V_BIT", 0x40},
	  {"W_BIT", 0x20},
	  {"I_BIT", 0x10},
	  {"O_BIT", 0x08},
	  {"U_BIT", 0x04},
	  {"Z_BIT", 0x02},
	  {"X_BIT", 0x01},
	  {"Inf", 0x7ff00000}
	};

      /* If it's already in the symbol table, we shouldn't do anything.  */
      symp = symbol_find (name);
      if (symp != NULL)
	return 0;

      for (i = 0;
	   i < sizeof (predefined_abs_syms) / sizeof (predefined_abs_syms[0]);
	   i++)
	if (strcmp (canon_name, predefined_abs_syms[i].name) == 0)
	  {
	    symbol_table_insert (symbol_new (predefined_abs_syms[i].name,
					     absolute_section,
					     &zero_address_frag,
					     predefined_abs_syms[i].val));

	    /* Let gas find the symbol we just created, through its
               ordinary lookup.  */
	    return 0;
	  }

      /* Not one of those symbols.  Let gas handle it.  */
      return 0;
    }

  expP->X_op = O_symbol;
  expP->X_add_number = 0;
  expP->X_add_symbol = symp;
  expP->X_op_symbol = NULL;

  return 1;
}

/* Just check that we don't have a BSPEC/ESPEC pair active when changing
   sections "normally", and get knowledge about alignment from the new
   section.  */

void
mmix_md_elf_section_change_hook (void)
{
  if (doing_bspec)
    as_bad (_("section change from within a BSPEC/ESPEC pair is not supported"));

  last_alignment = bfd_section_alignment (now_seg);
  want_unaligned = 0;
}

/* The LOC worker.  This is like s_org, but we have to support changing
   section too.   */

static void
s_loc (int ignore ATTRIBUTE_UNUSED)
{
  segT section;
  expressionS exp;
  char *p;
  symbolS *sym;
  offsetT off;

  /* Must not have a BSPEC in progress.  */
  if (doing_bspec)
    {
      as_bad (_("directive LOC from within a BSPEC/ESPEC pair is not supported"));
      return;
    }

  section = expression (&exp);

  if (exp.X_op == O_illegal
      || exp.X_op == O_absent
      || exp.X_op == O_big)
    {
      as_bad (_("invalid LOC expression"));
      return;
    }

  if (section == undefined_section)
    {
      /* This is an error or a LOC with an expression involving
	 forward references.  For the expression to be correctly
	 evaluated, we need to force a proper symbol; gas loses track
	 of the segment for "local symbols".  */
      if (exp.X_op == O_add)
	{
	  symbol_get_value_expression (exp.X_op_symbol);
	  symbol_get_value_expression (exp.X_add_symbol);
	}
      else
	{
	  gas_assert (exp.X_op == O_symbol);
	  symbol_get_value_expression (exp.X_add_symbol);
	}
    }

  if (section == absolute_section)
    {
      /* Translate a constant into a suitable section.  */

      if (exp.X_add_number < ((offsetT) 0x20 << 56))
	{
	  /* Lower than Data_Segment or in the reserved area (the
	     segment number is >= 0x80, appearing negative) - assume
	     it's .text.  */
	  section = text_section;

	  /* Save the lowest seen location, so we can pass on this
	     information to the linker.  We don't actually org to this
	     location here, we just pass on information to the linker so
	     it can put the code there for us.  */

	  /* If there was already a loc (that has to be set lower than
	     this one), we org at (this - lower).  There's an implicit
	     "LOC 0" before any entered code.  FIXME: handled by spurious
	     settings of text_has_contents.  */
	  if (lowest_text_loc != (bfd_vma) -1
	      && (bfd_vma) exp.X_add_number < lowest_text_loc)
	    {
	      as_bad (_("LOC expression stepping backwards is not supported"));
	      exp.X_op = O_absent;
	    }
	  else
	    {
	      if (text_has_contents && lowest_text_loc == (bfd_vma) -1)
		lowest_text_loc = 0;

	      if (lowest_text_loc == (bfd_vma) -1)
		{
		  lowest_text_loc = exp.X_add_number;

		  /* We want only to change the section, not set an offset.  */
		  exp.X_op = O_absent;
		}
	      else
		exp.X_add_number -= lowest_text_loc;
	    }
	}
      else
	{
	  /* Do the same for the .data section, except we don't have
	     to worry about exp.X_add_number carrying a sign.  */
	  section = data_section;

	  if (exp.X_add_number < (offsetT) lowest_data_loc)
	    {
	      as_bad (_("LOC expression stepping backwards is not supported"));
	      exp.X_op = O_absent;
	    }
	  else
	    {
	      if (data_has_contents && lowest_data_loc == (bfd_vma) -1)
		lowest_data_loc = (bfd_vma) 0x20 << 56;

	      if (lowest_data_loc == (bfd_vma) -1)
		{
		  lowest_data_loc = exp.X_add_number;

		  /* We want only to change the section, not set an offset.  */
		  exp.X_op = O_absent;
		}
	      else
		exp.X_add_number -= lowest_data_loc;
	    }
	}
    }

  /* If we can't deduce the section, it must be the current one.
     Below, we arrange to assert this.  */
  if (section != now_seg && section != undefined_section)
    {
      obj_elf_section_change_hook ();
      subseg_set (section, 0);

      /* Call our section change hooks using the official hook.  */
      md_elf_section_change_hook ();
    }

  if (exp.X_op != O_absent)
    {
      symbolS *esym = NULL;

      if (exp.X_op != O_constant && exp.X_op != O_symbol)
	{
	  /* Handle complex expressions.  */
	  esym = sym = make_expr_symbol (&exp);
	  off = 0;
	}
      else
	{
	  sym = exp.X_add_symbol;
	  off = exp.X_add_number;

	  if (section == undefined_section)
	    {
	      /* We need an expr_symbol when tracking sections.  In
		 order to make this an expr_symbol with file and line
		 tracked, we have to make the exp non-trivial; not an
		 O_symbol with .X_add_number == 0.  The constant part
		 is unused.  */
	      exp.X_add_number = 1;
	      esym = make_expr_symbol (&exp);
	    }
	}

      /* Track the LOC's where we couldn't deduce the section: assert
	 that we weren't supposed to change section.  */
      if (section == undefined_section)
	{
	  struct loc_assert_s *next = loc_asserts;
	  loc_asserts = XNEW (struct loc_assert_s);
	  loc_asserts->next = next;
	  loc_asserts->old_seg = now_seg;
	  loc_asserts->loc_sym = esym;
	  loc_asserts->frag = frag_now;
	}

      p = frag_var (rs_org, 1, 1, (relax_substateT) 0, sym, off, (char *) 0);
      *p = 0;
    }

  mmix_handle_rest_of_empty_line ();
}

/* The BYTE worker.  We have to support sequences of mixed "strings",
   numbers and other constant "first-pass" reducible expressions separated
   by comma.  */

static void
mmix_byte (void)
{
  unsigned int c;

  if (now_seg == text_section)
    text_has_contents = 1;
  else if (now_seg == data_section)
    data_has_contents = 1;

  do
    {
      SKIP_WHITESPACE ();
      switch (*input_line_pointer)
	{
	case '\"':
	  ++input_line_pointer;
	  while (is_a_char (c = next_char_of_string ()))
	    {
	      FRAG_APPEND_1_CHAR (c);
	    }

	  if (input_line_pointer[-1] != '\"')
	    {
	      /* We will only get here in rare cases involving #NO_APP,
		 where the unterminated string is not recognized by the
		 preformatting pass.  */
	      as_bad (_("unterminated string"));
	      mmix_discard_rest_of_line ();
	      return;
	    }
	  break;

	default:
	  {
	    expressionS exp;
	    segT expseg = expression (&exp);

	    /* We have to allow special register names as constant numbers.  */
	    if ((expseg != absolute_section && expseg != reg_section)
		|| (exp.X_op != O_constant
		    && (exp.X_op != O_register
			|| exp.X_add_number <= 255)))
	      {
		as_bad (_("BYTE expression not a pure number"));
		mmix_discard_rest_of_line ();
		return;
	      }
	    else if ((exp.X_add_number > 255 && exp.X_op != O_register)
		     || exp.X_add_number < 0)
	      {
		/* Note that mmixal does not allow negative numbers in
		   BYTE sequences, so neither should we.  */
		as_bad (_("BYTE expression not in the range 0..255"));
		mmix_discard_rest_of_line ();
		return;
	      }

	    FRAG_APPEND_1_CHAR (exp.X_add_number);
	  }
	  break;
	}

      SKIP_WHITESPACE ();
      c = *input_line_pointer++;
    }
  while (c == ',');

  input_line_pointer--;

  if (mmix_gnu_syntax)
    demand_empty_rest_of_line ();
  else
    {
      mmix_discard_rest_of_line ();
      /* Do like demand_empty_rest_of_line and step over the end-of-line
         boundary.  */
      input_line_pointer++;
    }

  /* Make sure we align for the next instruction.  */
  last_alignment = 0;
}

/* Like cons_worker, but we have to ignore "naked comments", not barf on
   them.  Implements WYDE, TETRA and OCTA.  We're a little bit more
   lenient than mmix_byte but FIXME: they should eventually merge.  */

static void
mmix_cons (int nbytes)
{
  expressionS exp;

  /* If we don't have any contents, then it's ok to have a specified start
     address that is not a multiple of the max data size.  We will then
     align it as necessary when we get here.  Otherwise, it's a fatal sin.  */
  if (now_seg == text_section)
    {
      if (lowest_text_loc != (bfd_vma) -1
	  && (lowest_text_loc & (nbytes - 1)) != 0)
	{
	  if (text_has_contents)
	    as_bad (_("data item with alignment larger than location"));
	  else if (want_unaligned)
	    as_bad (_("unaligned data at an absolute location is not supported"));

	  lowest_text_loc &= ~((bfd_vma) nbytes - 1);
	  lowest_text_loc += (bfd_vma) nbytes;
	}

      text_has_contents = 1;
    }
  else if (now_seg == data_section)
    {
      if (lowest_data_loc != (bfd_vma) -1
	  && (lowest_data_loc & (nbytes - 1)) != 0)
	{
	  if (data_has_contents)
	    as_bad (_("data item with alignment larger than location"));
	  else if (want_unaligned)
	    as_bad (_("unaligned data at an absolute location is not supported"));

	  lowest_data_loc &= ~((bfd_vma) nbytes - 1);
	  lowest_data_loc += (bfd_vma) nbytes;
	}

      data_has_contents = 1;
    }

  /* Always align these unless asked not to (valid for the current pseudo).  */
  if (! want_unaligned)
    {
      last_alignment = nbytes == 2 ? 1 : (nbytes == 4 ? 2 : 3);
      frag_align (last_alignment, 0, 0);
      record_alignment (now_seg, last_alignment);
    }

  /* For mmixal compatibility, a label for an instruction (and emitting
     pseudo) refers to the _aligned_ address.  So we have to emit the
     label here.  */
  if (current_fb_label >= 0)
    colon (fb_label_name (current_fb_label, 1));
  else if (pending_label != NULL)
    {
      colon (pending_label);
      pending_label = NULL;
    }

  SKIP_WHITESPACE ();

  if (is_end_of_line[(unsigned int) *input_line_pointer])
    {
      /* Default to zero if the expression was absent.  */

      exp.X_op = O_constant;
      exp.X_add_number = 0;
      exp.X_unsigned = 0;
      exp.X_add_symbol = NULL;
      exp.X_op_symbol = NULL;
      emit_expr (&exp, (unsigned int) nbytes);
    }
  else
    do
      {
	unsigned int c;

	switch (*input_line_pointer)
	  {
	    /* We support strings here too; each character takes up nbytes
	       bytes.  */
	  case '\"':
	    ++input_line_pointer;
	    while (is_a_char (c = next_char_of_string ()))
	      {
		exp.X_op = O_constant;
		exp.X_add_number = c;
		exp.X_unsigned = 1;
		emit_expr (&exp, (unsigned int) nbytes);
	      }

	    if (input_line_pointer[-1] != '\"')
	      {
		/* We will only get here in rare cases involving #NO_APP,
		   where the unterminated string is not recognized by the
		   preformatting pass.  */
		as_bad (_("unterminated string"));
		mmix_discard_rest_of_line ();
		return;
	      }
	    break;

	  default:
	    {
	      expression (&exp);
	      emit_expr (&exp, (unsigned int) nbytes);
	      SKIP_WHITESPACE ();
	    }
	    break;
	  }
      }
    while (*input_line_pointer++ == ',');

  input_line_pointer--;		/* Put terminator back into stream.  */

  mmix_handle_rest_of_empty_line ();

  /* We don't need to step up the counter for the current_fb_label here;
     that's handled by the caller.  */
}

/* The md_do_align worker.  At present, we just record an alignment to
   nullify the automatic alignment we do for WYDE, TETRA and OCTA, as gcc
   does not use the unaligned macros when attribute packed is used.
   Arguably this is a GCC bug.  */

void
mmix_md_do_align (int n, char *fill ATTRIBUTE_UNUSED,
		  int len ATTRIBUTE_UNUSED, int max ATTRIBUTE_UNUSED)
{
  last_alignment = n;
  want_unaligned = n == 0;
}
