/* Handle modules, which amounts to loading and saving symbols and
   their attendant structures.
   Copyright (C) 2000-2022 Free Software Foundation, Inc.
   Contributed by Andy Vaught

This file is part of GCC.

GCC 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.

GCC 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 GCC; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

/* The syntax of gfortran modules resembles that of lisp lists, i.e. a
   sequence of atoms, which can be left or right parenthesis, names,
   integers or strings.  Parenthesis are always matched which allows
   us to skip over sections at high speed without having to know
   anything about the internal structure of the lists.  A "name" is
   usually a fortran 95 identifier, but can also start with '@' in
   order to reference a hidden symbol.

   The first line of a module is an informational message about what
   created the module, the file it came from and when it was created.
   The second line is a warning for people not to edit the module.
   The rest of the module looks like:

   ( ( <Interface info for UPLUS> )
     ( <Interface info for UMINUS> )
     ...
   )
   ( ( <name of operator interface> <module of op interface> <i/f1> ... )
     ...
   )
   ( ( <name of generic interface> <module of generic interface> <i/f1> ... )
     ...
   )
   ( ( <common name> <symbol> <saved flag>)
     ...
   )

   ( equivalence list )

   ( <Symbol Number (in no particular order)>
     <True name of symbol>
     <Module name of symbol>
     ( <symbol information> )
     ...
   )
   ( <Symtree name>
     <Ambiguous flag>
     <Symbol number>
     ...
   )

   In general, symbols refer to other symbols by their symbol number,
   which are zero based.  Symbols are written to the module in no
   particular order.  */

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "options.h"
#include "tree.h"
#include "gfortran.h"
#include "stringpool.h"
#include "arith.h"
#include "match.h"
#include "parse.h" /* FIXME */
#include "constructor.h"
#include "cpp.h"
#include "scanner.h"
#include <zlib.h>

#define MODULE_EXTENSION ".mod"
#define SUBMODULE_EXTENSION ".smod"

/* Don't put any single quote (') in MOD_VERSION, if you want it to be
   recognized.  */
#define MOD_VERSION "15"


/* Structure that describes a position within a module file.  */

typedef struct
{
  int column, line;
  long pos;
}
module_locus;

/* Structure for list of symbols of intrinsic modules.  */
typedef struct
{
  int id;
  const char *name;
  int value;
  int standard;
}
intmod_sym;


typedef enum
{
  P_UNKNOWN = 0, P_OTHER, P_NAMESPACE, P_COMPONENT, P_SYMBOL
}
pointer_t;

/* The fixup structure lists pointers to pointers that have to
   be updated when a pointer value becomes known.  */

typedef struct fixup_t
{
  void **pointer;
  struct fixup_t *next;
}
fixup_t;


/* Structure for holding extra info needed for pointers being read.  */

enum gfc_rsym_state
{
  UNUSED,
  NEEDED,
  USED
};

enum gfc_wsym_state
{
  UNREFERENCED = 0,
  NEEDS_WRITE,
  WRITTEN
};

typedef struct pointer_info
{
  BBT_HEADER (pointer_info);
  HOST_WIDE_INT integer;
  pointer_t type;

  /* The first component of each member of the union is the pointer
     being stored.  */

  fixup_t *fixup;

  union
  {
    void *pointer;	/* Member for doing pointer searches.  */

    struct
    {
      gfc_symbol *sym;
      char *true_name, *module, *binding_label;
      fixup_t *stfixup;
      gfc_symtree *symtree;
      enum gfc_rsym_state state;
      int ns, referenced, renamed;
      module_locus where;
    }
    rsym;

    struct
    {
      gfc_symbol *sym;
      enum gfc_wsym_state state;
    }
    wsym;
  }
  u;

}
pointer_info;

#define gfc_get_pointer_info() XCNEW (pointer_info)


/* Local variables */

/* The gzFile for the module we're reading or writing.  */
static gzFile module_fp;

/* Fully qualified module path */
static char *module_fullpath = NULL;

/* The name of the module we're reading (USE'ing) or writing.  */
static const char *module_name;
/* The name of the .smod file that the submodule will write to.  */
static const char *submodule_name;

static gfc_use_list *module_list;

/* If we're reading an intrinsic module, this is its ID.  */
static intmod_id current_intmod;

/* Content of module.  */
static char* module_content;

static long module_pos;
static int module_line, module_column, only_flag;
static int prev_module_line, prev_module_column;

static enum
{ IO_INPUT, IO_OUTPUT }
iomode;

static gfc_use_rename *gfc_rename_list;
static pointer_info *pi_root;
static int symbol_number;	/* Counter for assigning symbol numbers */

/* Tells mio_expr_ref to make symbols for unused equivalence members.  */
static bool in_load_equiv;



/*****************************************************************/

/* Pointer/integer conversion.  Pointers between structures are stored
   as integers in the module file.  The next couple of subroutines
   handle this translation for reading and writing.  */

/* Recursively free the tree of pointer structures.  */

static void
free_pi_tree (pointer_info *p)
{
  if (p == NULL)
    return;

  if (p->fixup != NULL)
    gfc_internal_error ("free_pi_tree(): Unresolved fixup");

  free_pi_tree (p->left);
  free_pi_tree (p->right);

  if (iomode == IO_INPUT)
    {
      XDELETEVEC (p->u.rsym.true_name);
      XDELETEVEC (p->u.rsym.module);
      XDELETEVEC (p->u.rsym.binding_label);
    }

  free (p);
}


/* Compare pointers when searching by pointer.  Used when writing a
   module.  */

static int
compare_pointers (void *_sn1, void *_sn2)
{
  pointer_info *sn1, *sn2;

  sn1 = (pointer_info *) _sn1;
  sn2 = (pointer_info *) _sn2;

  if (sn1->u.pointer < sn2->u.pointer)
    return -1;
  if (sn1->u.pointer > sn2->u.pointer)
    return 1;

  return 0;
}


/* Compare integers when searching by integer.  Used when reading a
   module.  */

static int
compare_integers (void *_sn1, void *_sn2)
{
  pointer_info *sn1, *sn2;

  sn1 = (pointer_info *) _sn1;
  sn2 = (pointer_info *) _sn2;

  if (sn1->integer < sn2->integer)
    return -1;
  if (sn1->integer > sn2->integer)
    return 1;

  return 0;
}


/* Initialize the pointer_info tree.  */

static void
init_pi_tree (void)
{
  compare_fn compare;
  pointer_info *p;

  pi_root = NULL;
  compare = (iomode == IO_INPUT) ? compare_integers : compare_pointers;

  /* Pointer 0 is the NULL pointer.  */
  p = gfc_get_pointer_info ();
  p->u.pointer = NULL;
  p->integer = 0;
  p->type = P_OTHER;

  gfc_insert_bbt (&pi_root, p, compare);

  /* Pointer 1 is the current namespace.  */
  p = gfc_get_pointer_info ();
  p->u.pointer = gfc_current_ns;
  p->integer = 1;
  p->type = P_NAMESPACE;

  gfc_insert_bbt (&pi_root, p, compare);

  symbol_number = 2;
}


/* During module writing, call here with a pointer to something,
   returning the pointer_info node.  */

static pointer_info *
find_pointer (void *gp)
{
  pointer_info *p;

  p = pi_root;
  while (p != NULL)
    {
      if (p->u.pointer == gp)
	break;
      p = (gp < p->u.pointer) ? p->left : p->right;
    }

  return p;
}


/* Given a pointer while writing, returns the pointer_info tree node,
   creating it if it doesn't exist.  */

static pointer_info *
get_pointer (void *gp)
{
  pointer_info *p;

  p = find_pointer (gp);
  if (p != NULL)
    return p;

  /* Pointer doesn't have an integer.  Give it one.  */
  p = gfc_get_pointer_info ();

  p->u.pointer = gp;
  p->integer = symbol_number++;

  gfc_insert_bbt (&pi_root, p, compare_pointers);

  return p;
}


/* Given an integer during reading, find it in the pointer_info tree,
   creating the node if not found.  */

static pointer_info *
get_integer (HOST_WIDE_INT integer)
{
  pointer_info *p, t;
  int c;

  t.integer = integer;

  p = pi_root;
  while (p != NULL)
    {
      c = compare_integers (&t, p);
      if (c == 0)
	break;

      p = (c < 0) ? p->left : p->right;
    }

  if (p != NULL)
    return p;

  p = gfc_get_pointer_info ();
  p->integer = integer;
  p->u.pointer = NULL;

  gfc_insert_bbt (&pi_root, p, compare_integers);

  return p;
}


/* Resolve any fixups using a known pointer.  */

static void
resolve_fixups (fixup_t *f, void *gp)
{
  fixup_t *next;

  for (; f; f = next)
    {
      next = f->next;
      *(f->pointer) = gp;
      free (f);
    }
}


/* Convert a string such that it starts with a lower-case character. Used
   to convert the symtree name of a derived-type to the symbol name or to
   the name of the associated generic function.  */

const char *
gfc_dt_lower_string (const char *name)
{
  if (name[0] != (char) TOLOWER ((unsigned char) name[0]))
    return gfc_get_string ("%c%s", (char) TOLOWER ((unsigned char) name[0]),
			   &name[1]);
  return gfc_get_string ("%s", name);
}


/* Convert a string such that it starts with an upper-case character. Used to
   return the symtree-name for a derived type; the symbol name itself and the
   symtree/symbol name of the associated generic function start with a lower-
   case character.  */

const char *
gfc_dt_upper_string (const char *name)
{
  if (name[0] != (char) TOUPPER ((unsigned char) name[0]))
    return gfc_get_string ("%c%s", (char) TOUPPER ((unsigned char) name[0]),
			   &name[1]);
  return gfc_get_string ("%s", name);
}

/* Call here during module reading when we know what pointer to
   associate with an integer.  Any fixups that exist are resolved at
   this time.  */

static void
associate_integer_pointer (pointer_info *p, void *gp)
{
  if (p->u.pointer != NULL)
    gfc_internal_error ("associate_integer_pointer(): Already associated");

  p->u.pointer = gp;

  resolve_fixups (p->fixup, gp);

  p->fixup = NULL;
}


/* During module reading, given an integer and a pointer to a pointer,
   either store the pointer from an already-known value or create a
   fixup structure in order to store things later.  Returns zero if
   the reference has been actually stored, or nonzero if the reference
   must be fixed later (i.e., associate_integer_pointer must be called
   sometime later.  Returns the pointer_info structure.  */

static pointer_info *
add_fixup (HOST_WIDE_INT integer, void *gp)
{
  pointer_info *p;
  fixup_t *f;
  char **cp;

  p = get_integer (integer);

  if (p->integer == 0 || p->u.pointer != NULL)
    {
      cp = (char **) gp;
      *cp = (char *) p->u.pointer;
    }
  else
    {
      f = XCNEW (fixup_t);

      f->next = p->fixup;
      p->fixup = f;

      f->pointer = (void **) gp;
    }

  return p;
}


/*****************************************************************/

/* Parser related subroutines */

/* Free the rename list left behind by a USE statement.  */

static void
free_rename (gfc_use_rename *list)
{
  gfc_use_rename *next;

  for (; list; list = next)
    {
      next = list->next;
      free (list);
    }
}


/* Match a USE statement.  */

match
gfc_match_use (void)
{
  char name[GFC_MAX_SYMBOL_LEN + 1], module_nature[GFC_MAX_SYMBOL_LEN + 1];
  gfc_use_rename *tail = NULL, *new_use;
  interface_type type, type2;
  gfc_intrinsic_op op;
  match m;
  gfc_use_list *use_list;
  gfc_symtree *st;
  locus loc;

  use_list = gfc_get_use_list ();

  if (gfc_match (" , ") == MATCH_YES)
    {
      if ((m = gfc_match (" %n ::", module_nature)) == MATCH_YES)
	{
	  if (!gfc_notify_std (GFC_STD_F2003, "module "
			       "nature in USE statement at %C"))
	    goto cleanup;

	  if (strcmp (module_nature, "intrinsic") == 0)
	    use_list->intrinsic = true;
	  else
	    {
	      if (strcmp (module_nature, "non_intrinsic") == 0)
		use_list->non_intrinsic = true;
	      else
		{
		  gfc_error ("Module nature in USE statement at %C shall "
			     "be either INTRINSIC or NON_INTRINSIC");
		  goto cleanup;
		}
	    }
	}
      else
	{
	  /* Help output a better error message than "Unclassifiable
	     statement".  */
	  gfc_match (" %n", module_nature);
	  if (strcmp (module_nature, "intrinsic") == 0
	      || strcmp (module_nature, "non_intrinsic") == 0)
	    gfc_error ("\"::\" was expected after module nature at %C "
		       "but was not found");
	  free (use_list);
	  return m;
	}
    }
  else
    {
      m = gfc_match (" ::");
      if (m == MATCH_YES &&
	  !gfc_notify_std(GFC_STD_F2003, "\"USE :: module\" at %C"))
	goto cleanup;

      if (m != MATCH_YES)
	{
	  m = gfc_match ("% ");
	  if (m != MATCH_YES)
	    {
	      free (use_list);
	      return m;
	    }
	}
    }

  use_list->where = gfc_current_locus;

  m = gfc_match_name (name);
  if (m != MATCH_YES)
    {
      free (use_list);
      return m;
    }

  use_list->module_name = gfc_get_string ("%s", name);

  if (gfc_match_eos () == MATCH_YES)
    goto done;

  if (gfc_match_char (',') != MATCH_YES)
    goto syntax;

  if (gfc_match (" only :") == MATCH_YES)
    use_list->only_flag = true;

  if (gfc_match_eos () == MATCH_YES)
    goto done;

  for (;;)
    {
      /* Get a new rename struct and add it to the rename list.  */
      new_use = gfc_get_use_rename ();
      new_use->where = gfc_current_locus;
      new_use->found = 0;

      if (use_list->rename == NULL)
	use_list->rename = new_use;
      else
	tail->next = new_use;
      tail = new_use;

      /* See what kind of interface we're dealing with.  Assume it is
	 not an operator.  */
      new_use->op = INTRINSIC_NONE;
      if (gfc_match_generic_spec (&type, name, &op) == MATCH_ERROR)
	goto cleanup;

      switch (type)
	{
	case INTERFACE_NAMELESS:
	  gfc_error ("Missing generic specification in USE statement at %C");
	  goto cleanup;

	case INTERFACE_USER_OP:
	case INTERFACE_GENERIC:
	case INTERFACE_DTIO:
	  loc = gfc_current_locus;

	  m = gfc_match (" =>");

	  if (type == INTERFACE_USER_OP && m == MATCH_YES
	      && (!gfc_notify_std(GFC_STD_F2003, "Renaming "
				  "operators in USE statements at %C")))
	    goto cleanup;

	  if (type == INTERFACE_USER_OP)
	    new_use->op = INTRINSIC_USER;

	  if (use_list->only_flag)
	    {
	      if (m != MATCH_YES)
		strcpy (new_use->use_name, name);
	      else
		{
		  strcpy (new_use->local_name, name);
		  m = gfc_match_generic_spec (&type2, new_use->use_name, &op);
		  if (type != type2)
		    goto syntax;
		  if (m == MATCH_NO)
		    goto syntax;
		  if (m == MATCH_ERROR)
		    goto cleanup;
		}
	    }
	  else
	    {
	      if (m != MATCH_YES)
		goto syntax;
	      strcpy (new_use->local_name, name);

	      m = gfc_match_generic_spec (&type2, new_use->use_name, &op);
	      if (type != type2)
		goto syntax;
	      if (m == MATCH_NO)
		goto syntax;
	      if (m == MATCH_ERROR)
		goto cleanup;
	    }

	  st = gfc_find_symtree (gfc_current_ns->sym_root, name);
	  if (st && type != INTERFACE_USER_OP
	      && (st->n.sym->module != use_list->module_name
		  || strcmp (st->n.sym->name, new_use->use_name) != 0))
	    {
	      if (m == MATCH_YES)
		gfc_error ("Symbol %qs at %L conflicts with the rename symbol "
			   "at %L", name, &st->n.sym->declared_at, &loc);
	      else
		gfc_error ("Symbol %qs at %L conflicts with the symbol "
			   "at %L", name, &st->n.sym->declared_at, &loc);
	      goto cleanup;
	    }

	  if (strcmp (new_use->use_name, use_list->module_name) == 0
	      || strcmp (new_use->local_name, use_list->module_name) == 0)
	    {
	      gfc_error ("The name %qs at %C has already been used as "
			 "an external module name", use_list->module_name);
	      goto cleanup;
	    }
	  break;

	case INTERFACE_INTRINSIC_OP:
	  new_use->op = op;
	  break;

	default:
	  gcc_unreachable ();
	}

      if (gfc_match_eos () == MATCH_YES)
	break;
      if (gfc_match_char (',') != MATCH_YES)
	goto syntax;
    }

done:
  if (module_list)
    {
      gfc_use_list *last = module_list;
      while (last->next)
	last = last->next;
      last->next = use_list;
    }
  else
    module_list = use_list;

  return MATCH_YES;

syntax:
  gfc_syntax_error (ST_USE);

cleanup:
  free_rename (use_list->rename);
  free (use_list);
  return MATCH_ERROR;
}


/* Match a SUBMODULE statement.

   According to F2008:11.2.3.2, "The submodule identifier is the
   ordered pair whose first element is the ancestor module name and
   whose second element is the submodule name. 'Submodule_name' is
   used for the submodule filename and uses '@' as a separator, whilst
   the name of the symbol for the module uses '.' as a separator.
   The reasons for these choices are:
   (i) To follow another leading brand in the submodule filenames;
   (ii) Since '.' is not particularly visible in the filenames; and
   (iii) The linker does not permit '@' in mnemonics.  */

match
gfc_match_submodule (void)
{
  match m;
  char name[GFC_MAX_SYMBOL_LEN + 1];
  gfc_use_list *use_list;
  bool seen_colon = false;

  if (!gfc_notify_std (GFC_STD_F2008, "SUBMODULE declaration at %C"))
    return MATCH_ERROR;

  if (gfc_current_state () != COMP_NONE)
    {
      gfc_error ("SUBMODULE declaration at %C cannot appear within "
		 "another scoping unit");
      return MATCH_ERROR;
    }

  gfc_new_block = NULL;
  gcc_assert (module_list == NULL);

  if (gfc_match_char ('(') != MATCH_YES)
    goto syntax;

  while (1)
    {
      m = gfc_match (" %n", name);
      if (m != MATCH_YES)
	goto syntax;

      use_list = gfc_get_use_list ();
      use_list->where = gfc_current_locus;

      if (module_list)
	{
	  gfc_use_list *last = module_list;
	  while (last->next)
	    last = last->next;
	  last->next = use_list;
	  use_list->module_name
		= gfc_get_string ("%s.%s", module_list->module_name, name);
	  use_list->submodule_name
		= gfc_get_string ("%s@%s", module_list->module_name, name);
	}
      else
	{
	  module_list = use_list;
	  use_list->module_name = gfc_get_string ("%s", name);
	  use_list->submodule_name = use_list->module_name;
	}

      if (gfc_match_char (')') == MATCH_YES)
	break;

      if (gfc_match_char (':') != MATCH_YES
	  || seen_colon)
	goto syntax;

      seen_colon = true;
    }

  m = gfc_match (" %s%t", &gfc_new_block);
  if (m != MATCH_YES)
    goto syntax;

  submodule_name = gfc_get_string ("%s@%s", module_list->module_name,
				   gfc_new_block->name);

  gfc_new_block->name = gfc_get_string ("%s.%s",
					module_list->module_name,
					gfc_new_block->name);

  if (!gfc_add_flavor (&gfc_new_block->attr, FL_MODULE,
		       gfc_new_block->name, NULL))
    return MATCH_ERROR;

  /* Just retain the ultimate .(s)mod file for reading, since it
     contains all the information in its ancestors.  */
  use_list = module_list;
  for (; module_list->next; use_list = module_list)
    {
      module_list = use_list->next;
      free (use_list);
    }

  return MATCH_YES;

syntax:
  gfc_error ("Syntax error in SUBMODULE statement at %C");
  return MATCH_ERROR;
}


/* Given a name and a number, inst, return the inst name
   under which to load this symbol. Returns NULL if this
   symbol shouldn't be loaded. If inst is zero, returns
   the number of instances of this name. If interface is
   true, a user-defined operator is sought, otherwise only
   non-operators are sought.  */

static const char *
find_use_name_n (const char *name, int *inst, bool interface)
{
  gfc_use_rename *u;
  const char *low_name = NULL;
  int i;

  /* For derived types.  */
  if (name[0] != (char) TOLOWER ((unsigned char) name[0]))
    low_name = gfc_dt_lower_string (name);

  i = 0;
  for (u = gfc_rename_list; u; u = u->next)
    {
      if ((!low_name && strcmp (u->use_name, name) != 0)
	  || (low_name && strcmp (u->use_name, low_name) != 0)
	  || (u->op == INTRINSIC_USER && !interface)
	  || (u->op != INTRINSIC_USER &&  interface))
	continue;
      if (++i == *inst)
	break;
    }

  if (!*inst)
    {
      *inst = i;
      return NULL;
    }

  if (u == NULL)
    return only_flag ? NULL : name;

  u->found = 1;

  if (low_name)
    {
      if (u->local_name[0] == '\0')
	return name;
      return gfc_dt_upper_string (u->local_name);
    }

  return (u->local_name[0] != '\0') ? u->local_name : name;
}


/* Given a name, return the name under which to load this symbol.
   Returns NULL if this symbol shouldn't be loaded.  */

static const char *
find_use_name (const char *name, bool interface)
{
  int i = 1;
  return find_use_name_n (name, &i, interface);
}


/* Given a real name, return the number of use names associated with it.  */

static int
number_use_names (const char *name, bool interface)
{
  int i = 0;
  find_use_name_n (name, &i, interface);
  return i;
}


/* Try to find the operator in the current list.  */

static gfc_use_rename *
find_use_operator (gfc_intrinsic_op op)
{
  gfc_use_rename *u;

  for (u = gfc_rename_list; u; u = u->next)
    if (u->op == op)
      return u;

  return NULL;
}


/*****************************************************************/

/* The next couple of subroutines maintain a tree used to avoid a
   brute-force search for a combination of true name and module name.
   While symtree names, the name that a particular symbol is known by
   can changed with USE statements, we still have to keep track of the
   true names to generate the correct reference, and also avoid
   loading the same real symbol twice in a program unit.

   When we start reading, the true name tree is built and maintained
   as symbols are read.  The tree is searched as we load new symbols
   to see if it already exists someplace in the namespace.  */

typedef struct true_name
{
  BBT_HEADER (true_name);
  const char *name;
  gfc_symbol *sym;
}
true_name;

static true_name *true_name_root;


/* Compare two true_name structures.  */

static int
compare_true_names (void *_t1, void *_t2)
{
  true_name *t1, *t2;
  int c;

  t1 = (true_name *) _t1;
  t2 = (true_name *) _t2;

  c = ((t1->sym->module > t2->sym->module)
       - (t1->sym->module < t2->sym->module));
  if (c != 0)
    return c;

  return strcmp (t1->name, t2->name);
}


/* Given a true name, search the true name tree to see if it exists
   within the main namespace.  */

static gfc_symbol *
find_true_name (const char *name, const char *module)
{
  true_name t, *p;
  gfc_symbol sym;
  int c;

  t.name = gfc_get_string ("%s", name);
  if (module != NULL)
    sym.module = gfc_get_string ("%s", module);
  else
    sym.module = NULL;
  t.sym = &sym;

  p = true_name_root;
  while (p != NULL)
    {
      c = compare_true_names ((void *) (&t), (void *) p);
      if (c == 0)
	return p->sym;

      p = (c < 0) ? p->left : p->right;
    }

  return NULL;
}


/* Given a gfc_symbol pointer that is not in the true name tree, add it.  */

static void
add_true_name (gfc_symbol *sym)
{
  true_name *t;

  t = XCNEW (true_name);
  t->sym = sym;
  if (gfc_fl_struct (sym->attr.flavor))
    t->name = gfc_dt_upper_string (sym->name);
  else
    t->name = sym->name;

  gfc_insert_bbt (&true_name_root, t, compare_true_names);
}


/* Recursive function to build the initial true name tree by
   recursively traversing the current namespace.  */

static void
build_tnt (gfc_symtree *st)
{
  const char *name;
  if (st == NULL)
    return;

  build_tnt (st->left);
  build_tnt (st->right);

  if (gfc_fl_struct (st->n.sym->attr.flavor))
    name = gfc_dt_upper_string (st->n.sym->name);
  else
    name = st->n.sym->name;

  if (find_true_name (name, st->n.sym->module) != NULL)
    return;

  add_true_name (st->n.sym);
}


/* Initialize the true name tree with the current namespace.  */

static void
init_true_name_tree (void)
{
  true_name_root = NULL;
  build_tnt (gfc_current_ns->sym_root);
}


/* Recursively free a true name tree node.  */

static void
free_true_name (true_name *t)
{
  if (t == NULL)
    return;
  free_true_name (t->left);
  free_true_name (t->right);

  free (t);
}


/*****************************************************************/

/* Module reading and writing.  */

/* The following are versions similar to the ones in scanner.cc, but
   for dealing with compressed module files.  */

static gzFile
gzopen_included_file_1 (const char *name, gfc_directorylist *list,
                     bool module, bool system)
{
  char *fullname;
  gfc_directorylist *p;
  gzFile f;

  for (p = list; p; p = p->next)
    {
      if (module && !p->use_for_modules)
       continue;

      fullname = (char *) alloca(strlen (p->path) + strlen (name) + 2);
      strcpy (fullname, p->path);
      strcat (fullname, "/");
      strcat (fullname, name);

      f = gzopen (fullname, "r");
      if (f != NULL)
       {
         if (gfc_cpp_makedep ())
           gfc_cpp_add_dep (fullname, system);

	 free (module_fullpath);
	 module_fullpath = xstrdup (fullname);
         return f;
       }
    }

  return NULL;
}

static gzFile
gzopen_included_file (const char *name, bool include_cwd, bool module)
{
  gzFile f = NULL;

  if (IS_ABSOLUTE_PATH (name) || include_cwd)
    {
      f = gzopen (name, "r");
      if (f)
	{
	  if (gfc_cpp_makedep ())
	    gfc_cpp_add_dep (name, false);

	  free (module_fullpath);
	  module_fullpath = xstrdup (name);
	}
    }

  if (!f)
    f = gzopen_included_file_1 (name, include_dirs, module, false);

  return f;
}

static gzFile
gzopen_intrinsic_module (const char* name)
{
  gzFile f = NULL;

  if (IS_ABSOLUTE_PATH (name))
    {
      f = gzopen (name, "r");
      if (f)
	{
	  if (gfc_cpp_makedep ())
	    gfc_cpp_add_dep (name, true);

	  free (module_fullpath);
	  module_fullpath = xstrdup (name);
	}
    }

  if (!f)
    f = gzopen_included_file_1 (name, intrinsic_modules_dirs, true, true);

  return f;
}


enum atom_type
{
  ATOM_NAME, ATOM_LPAREN, ATOM_RPAREN, ATOM_INTEGER, ATOM_STRING
};

static atom_type last_atom;


/* The name buffer must be at least as long as a symbol name.  Right
   now it's not clear how we're going to store numeric constants--
   probably as a hexadecimal string, since this will allow the exact
   number to be preserved (this can't be done by a decimal
   representation).  Worry about that later.  TODO!  */

#define MAX_ATOM_SIZE 100

static HOST_WIDE_INT atom_int;
static char *atom_string, atom_name[MAX_ATOM_SIZE];


/* Report problems with a module.  Error reporting is not very
   elaborate, since this sorts of errors shouldn't really happen.
   This subroutine never returns.  */

static void bad_module (const char *) ATTRIBUTE_NORETURN;

static void
bad_module (const char *msgid)
{
  XDELETEVEC (module_content);
  module_content = NULL;

  switch (iomode)
    {
    case IO_INPUT:
      gfc_fatal_error ("Reading module %qs at line %d column %d: %s",
	  	       module_fullpath, module_line, module_column, msgid);
      break;
    case IO_OUTPUT:
      gfc_fatal_error ("Writing module %qs at line %d column %d: %s",
	  	       module_name, module_line, module_column, msgid);
      break;
    default:
      gfc_fatal_error ("Module %qs at line %d column %d: %s",
	  	       module_name, module_line, module_column, msgid);
      break;
    }
}


/* Set the module's input pointer.  */

static void
set_module_locus (module_locus *m)
{
  module_column = m->column;
  module_line = m->line;
  module_pos = m->pos;
}


/* Get the module's input pointer so that we can restore it later.  */

static void
get_module_locus (module_locus *m)
{
  m->column = module_column;
  m->line = module_line;
  m->pos = module_pos;
}

/* Peek at the next character in the module.  */

static int
module_peek_char (void)
{
  return module_content[module_pos];
}

/* Get the next character in the module, updating our reckoning of
   where we are.  */

static int
module_char (void)
{
  const char c = module_content[module_pos++];
  if (c == '\0')
    bad_module ("Unexpected EOF");

  prev_module_line = module_line;
  prev_module_column = module_column;

  if (c == '\n')
    {
      module_line++;
      module_column = 0;
    }

  module_column++;
  return c;
}

/* Unget a character while remembering the line and column.  Works for
   a single character only.  */

static void
module_unget_char (void)
{
  module_line = prev_module_line;
  module_column = prev_module_column;
  module_pos--;
}

/* Parse a string constant.  The delimiter is guaranteed to be a
   single quote.  */

static void
parse_string (void)
{
  int c;
  size_t cursz = 30;
  size_t len = 0;

  atom_string = XNEWVEC (char, cursz);

  for ( ; ; )
    {
      c = module_char ();

      if (c == '\'')
	{
	  int c2 = module_char ();
	  if (c2 != '\'')
	    {
	      module_unget_char ();
	      break;
	    }
	}

      if (len >= cursz)
	{
	  cursz *= 2;
	  atom_string = XRESIZEVEC (char, atom_string, cursz);
	}
      atom_string[len] = c;
      len++;
    }

  atom_string = XRESIZEVEC (char, atom_string, len + 1);
  atom_string[len] = '\0'; 	/* C-style string for debug purposes.  */
}


/* Parse an integer. Should fit in a HOST_WIDE_INT.  */

static void
parse_integer (int c)
{
  int sign = 1;

  atom_int = 0;
  switch (c)
    {
    case ('-'):
      sign = -1;
    case ('+'):
      break;
    default:
      atom_int = c - '0';
      break;
    }

  for (;;)
    {
      c = module_char ();
      if (!ISDIGIT (c))
	{
	  module_unget_char ();
	  break;
	}

      atom_int = 10 * atom_int + c - '0';
    }

  atom_int *= sign; 
}


/* Parse a name.  */

static void
parse_name (int c)
{
  char *p;
  int len;

  p = atom_name;

  *p++ = c;
  len = 1;

  for (;;)
    {
      c = module_char ();
      if (!ISALNUM (c) && c != '_' && c != '-')
	{
	  module_unget_char ();
	  break;
	}

      *p++ = c;
      if (++len > GFC_MAX_SYMBOL_LEN)
	bad_module ("Name too long");
    }

  *p = '\0';

}


/* Read the next atom in the module's input stream.  */

static atom_type
parse_atom (void)
{
  int c;

  do
    {
      c = module_char ();
    }
  while (c == ' ' || c == '\r' || c == '\n');

  switch (c)
    {
    case '(':
      return ATOM_LPAREN;

    case ')':
      return ATOM_RPAREN;

    case '\'':
      parse_string ();
      return ATOM_STRING;

    case '0':
    case '1':
    case '2':
    case '3':
    case '4':
    case '5':
    case '6':
    case '7':
    case '8':
    case '9':
      parse_integer (c);
      return ATOM_INTEGER;

    case '+':
    case '-':
      if (ISDIGIT (module_peek_char ()))
	{
	  parse_integer (c);
	  return ATOM_INTEGER;
	}
      else
	bad_module ("Bad name");

    case 'a':
    case 'b':
    case 'c':
    case 'd':
    case 'e':
    case 'f':
    case 'g':
    case 'h':
    case 'i':
    case 'j':
    case 'k':
    case 'l':
    case 'm':
    case 'n':
    case 'o':
    case 'p':
    case 'q':
    case 'r':
    case 's':
    case 't':
    case 'u':
    case 'v':
    case 'w':
    case 'x':
    case 'y':
    case 'z':
    case 'A':
    case 'B':
    case 'C':
    case 'D':
    case 'E':
    case 'F':
    case 'G':
    case 'H':
    case 'I':
    case 'J':
    case 'K':
    case 'L':
    case 'M':
    case 'N':
    case 'O':
    case 'P':
    case 'Q':
    case 'R':
    case 'S':
    case 'T':
    case 'U':
    case 'V':
    case 'W':
    case 'X':
    case 'Y':
    case 'Z':
      parse_name (c);
      return ATOM_NAME;

    default:
      bad_module ("Bad name");
    }

  /* Not reached.  */
}


/* Peek at the next atom on the input.  */

static atom_type
peek_atom (void)
{
  int c;

  do
    {
      c = module_char ();
    }
  while (c == ' ' || c == '\r' || c == '\n');

  switch (c)
    {
    case '(':
      module_unget_char ();
      return ATOM_LPAREN;

    case ')':
      module_unget_char ();
      return ATOM_RPAREN;

    case '\'':
      module_unget_char ();
      return ATOM_STRING;

    case '0':
    case '1':
    case '2':
    case '3':
    case '4':
    case '5':
    case '6':
    case '7':
    case '8':
    case '9':
      module_unget_char ();
      return ATOM_INTEGER;

    case '+':
    case '-':
      if (ISDIGIT (module_peek_char ()))
	{
	  module_unget_char ();
	  return ATOM_INTEGER;
	}
      else
	bad_module ("Bad name");

    case 'a':
    case 'b':
    case 'c':
    case 'd':
    case 'e':
    case 'f':
    case 'g':
    case 'h':
    case 'i':
    case 'j':
    case 'k':
    case 'l':
    case 'm':
    case 'n':
    case 'o':
    case 'p':
    case 'q':
    case 'r':
    case 's':
    case 't':
    case 'u':
    case 'v':
    case 'w':
    case 'x':
    case 'y':
    case 'z':
    case 'A':
    case 'B':
    case 'C':
    case 'D':
    case 'E':
    case 'F':
    case 'G':
    case 'H':
    case 'I':
    case 'J':
    case 'K':
    case 'L':
    case 'M':
    case 'N':
    case 'O':
    case 'P':
    case 'Q':
    case 'R':
    case 'S':
    case 'T':
    case 'U':
    case 'V':
    case 'W':
    case 'X':
    case 'Y':
    case 'Z':
      module_unget_char ();
      return ATOM_NAME;

    default:
      bad_module ("Bad name");
    }
}


/* Read the next atom from the input, requiring that it be a
   particular kind.  */

static void
require_atom (atom_type type)
{
  atom_type t;
  const char *p;
  int column, line;

  column = module_column;
  line = module_line;

  t = parse_atom ();
  if (t != type)
    {
      switch (type)
	{
	case ATOM_NAME:
	  p = _("Expected name");
	  break;
	case ATOM_LPAREN:
	  p = _("Expected left parenthesis");
	  break;
	case ATOM_RPAREN:
	  p = _("Expected right parenthesis");
	  break;
	case ATOM_INTEGER:
	  p = _("Expected integer");
	  break;
	case ATOM_STRING:
	  p = _("Expected string");
	  break;
	default:
	  gfc_internal_error ("require_atom(): bad atom type required");
	}

      module_column = column;
      module_line = line;
      bad_module (p);
    }
}


/* Given a pointer to an mstring array, require that the current input
   be one of the strings in the array.  We return the enum value.  */

static int
find_enum (const mstring *m)
{
  int i;

  i = gfc_string2code (m, atom_name);
  if (i >= 0)
    return i;

  bad_module ("find_enum(): Enum not found");

  /* Not reached.  */
}


/* Read a string. The caller is responsible for freeing.  */

static char*
read_string (void)
{
  char* p;
  require_atom (ATOM_STRING);
  p = atom_string;
  atom_string = NULL;
  return p;
}


/**************** Module output subroutines ***************************/

/* Output a character to a module file.  */

static void
write_char (char out)
{
  if (gzputc (module_fp, out) == EOF)
    gfc_fatal_error ("Error writing modules file: %s", xstrerror (errno));

  if (out != '\n')
    module_column++;
  else
    {
      module_column = 1;
      module_line++;
    }
}


/* Write an atom to a module.  The line wrapping isn't perfect, but it
   should work most of the time.  This isn't that big of a deal, since
   the file really isn't meant to be read by people anyway.  */

static void
write_atom (atom_type atom, const void *v)
{
  char buffer[32];

  /* Workaround -Wmaybe-uninitialized false positive during
     profiledbootstrap by initializing them.  */
  int len;
  HOST_WIDE_INT i = 0;
  const char *p;

  switch (atom)
    {
    case ATOM_STRING:
    case ATOM_NAME:
      p = (const char *) v;
      break;

    case ATOM_LPAREN:
      p = "(";
      break;

    case ATOM_RPAREN:
      p = ")";
      break;

    case ATOM_INTEGER:
      i = *((const HOST_WIDE_INT *) v);

      snprintf (buffer, sizeof (buffer), HOST_WIDE_INT_PRINT_DEC, i);
      p = buffer;
      break;

    default:
      gfc_internal_error ("write_atom(): Trying to write dab atom");

    }

  if(p == NULL || *p == '\0')
     len = 0;
  else
  len = strlen (p);

  if (atom != ATOM_RPAREN)
    {
      if (module_column + len > 72)
	write_char ('\n');
      else
	{

	  if (last_atom != ATOM_LPAREN && module_column != 1)
	    write_char (' ');
	}
    }

  if (atom == ATOM_STRING)
    write_char ('\'');

  while (p != NULL && *p)
    {
      if (atom == ATOM_STRING && *p == '\'')
	write_char ('\'');
      write_char (*p++);
    }

  if (atom == ATOM_STRING)
    write_char ('\'');

  last_atom = atom;
}



/***************** Mid-level I/O subroutines *****************/

/* These subroutines let their caller read or write atoms without
   caring about which of the two is actually happening.  This lets a
   subroutine concentrate on the actual format of the data being
   written.  */

static void mio_expr (gfc_expr **);
pointer_info *mio_symbol_ref (gfc_symbol **);
pointer_info *mio_interface_rest (gfc_interface **);
static void mio_symtree_ref (gfc_symtree **);

/* Read or write an enumerated value.  On writing, we return the input
   value for the convenience of callers.  We avoid using an integer
   pointer because enums are sometimes inside bitfields.  */

static int
mio_name (int t, const mstring *m)
{
  if (iomode == IO_OUTPUT)
    write_atom (ATOM_NAME, gfc_code2string (m, t));
  else
    {
      require_atom (ATOM_NAME);
      t = find_enum (m);
    }

  return t;
}

/* Specialization of mio_name.  */

#define DECL_MIO_NAME(TYPE) \
 static inline TYPE \
 MIO_NAME(TYPE) (TYPE t, const mstring *m) \
 { \
   return (TYPE) mio_name ((int) t, m); \
 }
#define MIO_NAME(TYPE) mio_name_##TYPE

static void
mio_lparen (void)
{
  if (iomode == IO_OUTPUT)
    write_atom (ATOM_LPAREN, NULL);
  else
    require_atom (ATOM_LPAREN);
}


static void
mio_rparen (void)
{
  if (iomode == IO_OUTPUT)
    write_atom (ATOM_RPAREN, NULL);
  else
    require_atom (ATOM_RPAREN);
}


static void
mio_integer (int *ip)
{
  if (iomode == IO_OUTPUT)
    {
      HOST_WIDE_INT hwi = *ip;
      write_atom (ATOM_INTEGER, &hwi);
    }
  else
    {
      require_atom (ATOM_INTEGER);
      *ip = atom_int;
    }
}

static void
mio_hwi (HOST_WIDE_INT *hwi)
{
  if (iomode == IO_OUTPUT)
    write_atom (ATOM_INTEGER, hwi);
  else
    {
      require_atom (ATOM_INTEGER);
      *hwi = atom_int;
    }
}


/* Read or write a gfc_intrinsic_op value.  */

static void
mio_intrinsic_op (gfc_intrinsic_op* op)
{
  /* FIXME: Would be nicer to do this via the operators symbolic name.  */
  if (iomode == IO_OUTPUT)
    {
      HOST_WIDE_INT converted = (HOST_WIDE_INT) *op;
      write_atom (ATOM_INTEGER, &converted);
    }
  else
    {
      require_atom (ATOM_INTEGER);
      *op = (gfc_intrinsic_op) atom_int;
    }
}


/* Read or write a character pointer that points to a string on the heap.  */

static const char *
mio_allocated_string (const char *s)
{
  if (iomode == IO_OUTPUT)
    {
      write_atom (ATOM_STRING, s);
      return s;
    }
  else
    {
      require_atom (ATOM_STRING);
      return atom_string;
    }
}


/* Functions for quoting and unquoting strings.  */

static char *
quote_string (const gfc_char_t *s, const size_t slength)
{
  const gfc_char_t *p;
  char *res, *q;
  size_t len = 0, i;

  /* Calculate the length we'll need: a backslash takes two ("\\"),
     non-printable characters take 10 ("\Uxxxxxxxx") and others take 1.  */
  for (p = s, i = 0; i < slength; p++, i++)
    {
      if (*p == '\\')
	len += 2;
      else if (!gfc_wide_is_printable (*p))
	len += 10;
      else
	len++;
    }

  q = res = XCNEWVEC (char, len + 1);
  for (p = s, i = 0; i < slength; p++, i++)
    {
      if (*p == '\\')
	*q++ = '\\', *q++ = '\\';
      else if (!gfc_wide_is_printable (*p))
	{
	  sprintf (q, "\\U%08" HOST_WIDE_INT_PRINT "x",
		   (unsigned HOST_WIDE_INT) *p);
	  q += 10;
	}
      else
	*q++ = (unsigned char) *p;
    }

  res[len] = '\0';
  return res;
}

static gfc_char_t *
unquote_string (const char *s)
{
  size_t len, i;
  const char *p;
  gfc_char_t *res;

  for (p = s, len = 0; *p; p++, len++)
    {
      if (*p != '\\')
	continue;

      if (p[1] == '\\')
	p++;
      else if (p[1] == 'U')
	p += 9; /* That is a "\U????????".  */
      else
	gfc_internal_error ("unquote_string(): got bad string");
    }

  res = gfc_get_wide_string (len + 1);
  for (i = 0, p = s; i < len; i++, p++)
    {
      gcc_assert (*p);

      if (*p != '\\')
	res[i] = (unsigned char) *p;
      else if (p[1] == '\\')
	{
	  res[i] = (unsigned char) '\\';
	  p++;
	}
      else
	{
	  /* We read the 8-digits hexadecimal constant that follows.  */
	  int j;
	  unsigned n;
	  gfc_char_t c = 0;

	  gcc_assert (p[1] == 'U');
	  for (j = 0; j < 8; j++)
	    {
	      c = c << 4;
	      gcc_assert (sscanf (&p[j+2], "%01x", &n) == 1);
	      c += n;
	    }

	  res[i] = c;
	  p += 9;
	}
    }

  res[len] = '\0';
  return res;
}


/* Read or write a character pointer that points to a wide string on the
   heap, performing quoting/unquoting of nonprintable characters using the
   form \U???????? (where each ? is a hexadecimal digit).
   Length is the length of the string, only known and used in output mode.  */

static const gfc_char_t *
mio_allocated_wide_string (const gfc_char_t *s, const size_t length)
{
  if (iomode == IO_OUTPUT)
    {
      char *quoted = quote_string (s, length);
      write_atom (ATOM_STRING, quoted);
      free (quoted);
      return s;
    }
  else
    {
      gfc_char_t *unquoted;

      require_atom (ATOM_STRING);
      unquoted = unquote_string (atom_string);
      free (atom_string);
      return unquoted;
    }
}


/* Read or write a string that is in static memory.  */

static void
mio_pool_string (const char **stringp)
{
  /* TODO: one could write the string only once, and refer to it via a
     fixup pointer.  */

  /* As a special case we have to deal with a NULL string.  This
     happens for the 'module' member of 'gfc_symbol's that are not in a
     module.  We read / write these as the empty string.  */
  if (iomode == IO_OUTPUT)
    {
      const char *p = *stringp == NULL ? "" : *stringp;
      write_atom (ATOM_STRING, p);
    }
  else
    {
      require_atom (ATOM_STRING);
      *stringp = (atom_string[0] == '\0'
		  ? NULL : gfc_get_string ("%s", atom_string));
      free (atom_string);
    }
}


/* Read or write a string that is inside of some already-allocated
   structure.  */

static void
mio_internal_string (char *string)
{
  if (iomode == IO_OUTPUT)
    write_atom (ATOM_STRING, string);
  else
    {
      require_atom (ATOM_STRING);
      strcpy (string, atom_string);
      free (atom_string);
    }
}


enum ab_attribute
{ AB_ALLOCATABLE, AB_DIMENSION, AB_EXTERNAL, AB_INTRINSIC, AB_OPTIONAL,
  AB_POINTER, AB_TARGET, AB_DUMMY, AB_RESULT, AB_DATA,
  AB_IN_NAMELIST, AB_IN_COMMON, AB_FUNCTION, AB_SUBROUTINE, AB_SEQUENCE,
  AB_ELEMENTAL, AB_PURE, AB_RECURSIVE, AB_GENERIC, AB_ALWAYS_EXPLICIT,
  AB_CRAY_POINTER, AB_CRAY_POINTEE, AB_THREADPRIVATE,
  AB_ALLOC_COMP, AB_POINTER_COMP, AB_PROC_POINTER_COMP, AB_PRIVATE_COMP,
  AB_VALUE, AB_VOLATILE, AB_PROTECTED, AB_LOCK_COMP, AB_EVENT_COMP,
  AB_IS_BIND_C, AB_IS_C_INTEROP, AB_IS_ISO_C, AB_ABSTRACT, AB_ZERO_COMP,
  AB_IS_CLASS, AB_PROCEDURE, AB_PROC_POINTER, AB_ASYNCHRONOUS, AB_CODIMENSION,
  AB_COARRAY_COMP, AB_VTYPE, AB_VTAB, AB_CONTIGUOUS, AB_CLASS_POINTER,
  AB_IMPLICIT_PURE, AB_ARTIFICIAL, AB_UNLIMITED_POLY, AB_OMP_DECLARE_TARGET,
  AB_ARRAY_OUTER_DEPENDENCY, AB_MODULE_PROCEDURE, AB_OACC_DECLARE_CREATE,
  AB_OACC_DECLARE_COPYIN, AB_OACC_DECLARE_DEVICEPTR,
  AB_OACC_DECLARE_DEVICE_RESIDENT, AB_OACC_DECLARE_LINK,
  AB_OMP_DECLARE_TARGET_LINK, AB_PDT_KIND, AB_PDT_LEN, AB_PDT_TYPE,
  AB_PDT_TEMPLATE, AB_PDT_ARRAY, AB_PDT_STRING,
  AB_OACC_ROUTINE_LOP_GANG, AB_OACC_ROUTINE_LOP_WORKER,
  AB_OACC_ROUTINE_LOP_VECTOR, AB_OACC_ROUTINE_LOP_SEQ,
  AB_OACC_ROUTINE_NOHOST,
  AB_OMP_REQ_REVERSE_OFFLOAD, AB_OMP_REQ_UNIFIED_ADDRESS,
  AB_OMP_REQ_UNIFIED_SHARED_MEMORY, AB_OMP_REQ_DYNAMIC_ALLOCATORS,
  AB_OMP_REQ_MEM_ORDER_SEQ_CST, AB_OMP_REQ_MEM_ORDER_ACQ_REL,
  AB_OMP_REQ_MEM_ORDER_RELAXED, AB_OMP_DEVICE_TYPE_NOHOST,
  AB_OMP_DEVICE_TYPE_HOST, AB_OMP_DEVICE_TYPE_ANY
};

static const mstring attr_bits[] =
{
    minit ("ALLOCATABLE", AB_ALLOCATABLE),
    minit ("ARTIFICIAL", AB_ARTIFICIAL),
    minit ("ASYNCHRONOUS", AB_ASYNCHRONOUS),
    minit ("DIMENSION", AB_DIMENSION),
    minit ("CODIMENSION", AB_CODIMENSION),
    minit ("CONTIGUOUS", AB_CONTIGUOUS),
    minit ("EXTERNAL", AB_EXTERNAL),
    minit ("INTRINSIC", AB_INTRINSIC),
    minit ("OPTIONAL", AB_OPTIONAL),
    minit ("POINTER", AB_POINTER),
    minit ("VOLATILE", AB_VOLATILE),
    minit ("TARGET", AB_TARGET),
    minit ("THREADPRIVATE", AB_THREADPRIVATE),
    minit ("DUMMY", AB_DUMMY),
    minit ("RESULT", AB_RESULT),
    minit ("DATA", AB_DATA),
    minit ("IN_NAMELIST", AB_IN_NAMELIST),
    minit ("IN_COMMON", AB_IN_COMMON),
    minit ("FUNCTION", AB_FUNCTION),
    minit ("SUBROUTINE", AB_SUBROUTINE),
    minit ("SEQUENCE", AB_SEQUENCE),
    minit ("ELEMENTAL", AB_ELEMENTAL),
    minit ("PURE", AB_PURE),
    minit ("RECURSIVE", AB_RECURSIVE),
    minit ("GENERIC", AB_GENERIC),
    minit ("ALWAYS_EXPLICIT", AB_ALWAYS_EXPLICIT),
    minit ("CRAY_POINTER", AB_CRAY_POINTER),
    minit ("CRAY_POINTEE", AB_CRAY_POINTEE),
    minit ("IS_BIND_C", AB_IS_BIND_C),
    minit ("IS_C_INTEROP", AB_IS_C_INTEROP),
    minit ("IS_ISO_C", AB_IS_ISO_C),
    minit ("VALUE", AB_VALUE),
    minit ("ALLOC_COMP", AB_ALLOC_COMP),
    minit ("COARRAY_COMP", AB_COARRAY_COMP),
    minit ("LOCK_COMP", AB_LOCK_COMP),
    minit ("EVENT_COMP", AB_EVENT_COMP),
    minit ("POINTER_COMP", AB_POINTER_COMP),
    minit ("PROC_POINTER_COMP", AB_PROC_POINTER_COMP),
    minit ("PRIVATE_COMP", AB_PRIVATE_COMP),
    minit ("ZERO_COMP", AB_ZERO_COMP),
    minit ("PROTECTED", AB_PROTECTED),
    minit ("ABSTRACT", AB_ABSTRACT),
    minit ("IS_CLASS", AB_IS_CLASS),
    minit ("PROCEDURE", AB_PROCEDURE),
    minit ("PROC_POINTER", AB_PROC_POINTER),
    minit ("VTYPE", AB_VTYPE),
    minit ("VTAB", AB_VTAB),
    minit ("CLASS_POINTER", AB_CLASS_POINTER),
    minit ("IMPLICIT_PURE", AB_IMPLICIT_PURE),
    minit ("UNLIMITED_POLY", AB_UNLIMITED_POLY),
    minit ("OMP_DECLARE_TARGET", AB_OMP_DECLARE_TARGET),
    minit ("ARRAY_OUTER_DEPENDENCY", AB_ARRAY_OUTER_DEPENDENCY),
    minit ("MODULE_PROCEDURE", AB_MODULE_PROCEDURE),
    minit ("OACC_DECLARE_CREATE", AB_OACC_DECLARE_CREATE),
    minit ("OACC_DECLARE_COPYIN", AB_OACC_DECLARE_COPYIN),
    minit ("OACC_DECLARE_DEVICEPTR", AB_OACC_DECLARE_DEVICEPTR),
    minit ("OACC_DECLARE_DEVICE_RESIDENT", AB_OACC_DECLARE_DEVICE_RESIDENT),
    minit ("OACC_DECLARE_LINK", AB_OACC_DECLARE_LINK),
    minit ("OMP_DECLARE_TARGET_LINK", AB_OMP_DECLARE_TARGET_LINK),
    minit ("PDT_KIND", AB_PDT_KIND),
    minit ("PDT_LEN", AB_PDT_LEN),
    minit ("PDT_TYPE", AB_PDT_TYPE),
    minit ("PDT_TEMPLATE", AB_PDT_TEMPLATE),
    minit ("PDT_ARRAY", AB_PDT_ARRAY),
    minit ("PDT_STRING", AB_PDT_STRING),
    minit ("OACC_ROUTINE_LOP_GANG", AB_OACC_ROUTINE_LOP_GANG),
    minit ("OACC_ROUTINE_LOP_WORKER", AB_OACC_ROUTINE_LOP_WORKER),
    minit ("OACC_ROUTINE_LOP_VECTOR", AB_OACC_ROUTINE_LOP_VECTOR),
    minit ("OACC_ROUTINE_LOP_SEQ", AB_OACC_ROUTINE_LOP_SEQ),
    minit ("OACC_ROUTINE_NOHOST", AB_OACC_ROUTINE_NOHOST),
    minit ("OMP_REQ_REVERSE_OFFLOAD", AB_OMP_REQ_REVERSE_OFFLOAD),
    minit ("OMP_REQ_UNIFIED_ADDRESS", AB_OMP_REQ_UNIFIED_ADDRESS),
    minit ("OMP_REQ_UNIFIED_SHARED_MEMORY", AB_OMP_REQ_UNIFIED_SHARED_MEMORY),
    minit ("OMP_REQ_DYNAMIC_ALLOCATORS", AB_OMP_REQ_DYNAMIC_ALLOCATORS),
    minit ("OMP_REQ_MEM_ORDER_SEQ_CST", AB_OMP_REQ_MEM_ORDER_SEQ_CST),
    minit ("OMP_REQ_MEM_ORDER_ACQ_REL", AB_OMP_REQ_MEM_ORDER_ACQ_REL),
    minit ("OMP_REQ_MEM_ORDER_RELAXED", AB_OMP_REQ_MEM_ORDER_RELAXED),
    minit ("OMP_DEVICE_TYPE_HOST", AB_OMP_DEVICE_TYPE_HOST),
    minit ("OMP_DEVICE_TYPE_NOHOST", AB_OMP_DEVICE_TYPE_NOHOST),
    minit ("OMP_DEVICE_TYPE_ANYHOST", AB_OMP_DEVICE_TYPE_ANY),
    minit (NULL, -1)
};

/* For binding attributes.  */
static const mstring binding_passing[] =
{
    minit ("PASS", 0),
    minit ("NOPASS", 1),
    minit (NULL, -1)
};
static const mstring binding_overriding[] =
{
    minit ("OVERRIDABLE", 0),
    minit ("NON_OVERRIDABLE", 1),
    minit ("DEFERRED", 2),
    minit (NULL, -1)
};
static const mstring binding_generic[] =
{
    minit ("SPECIFIC", 0),
    minit ("GENERIC", 1),
    minit (NULL, -1)
};
static const mstring binding_ppc[] =
{
    minit ("NO_PPC", 0),
    minit ("PPC", 1),
    minit (NULL, -1)
};

/* Specialization of mio_name.  */
DECL_MIO_NAME (ab_attribute)
DECL_MIO_NAME (ar_type)
DECL_MIO_NAME (array_type)
DECL_MIO_NAME (bt)
DECL_MIO_NAME (expr_t)
DECL_MIO_NAME (gfc_access)
DECL_MIO_NAME (gfc_intrinsic_op)
DECL_MIO_NAME (ifsrc)
DECL_MIO_NAME (save_state)
DECL_MIO_NAME (procedure_type)
DECL_MIO_NAME (ref_type)
DECL_MIO_NAME (sym_flavor)
DECL_MIO_NAME (sym_intent)
DECL_MIO_NAME (inquiry_type)
#undef DECL_MIO_NAME

/* Verify OACC_ROUTINE_LOP_NONE.  */

static void
verify_OACC_ROUTINE_LOP_NONE (enum oacc_routine_lop lop)
{
  if (lop != OACC_ROUTINE_LOP_NONE)
    bad_module ("Unsupported: multiple OpenACC 'routine' levels of parallelism");
}

/* Symbol attributes are stored in list with the first three elements
   being the enumerated fields, while the remaining elements (if any)
   indicate the individual attribute bits.  The access field is not
   saved-- it controls what symbols are exported when a module is
   written.  */

static void
mio_symbol_attribute (symbol_attribute *attr)
{
  atom_type t;
  unsigned ext_attr,extension_level;

  mio_lparen ();

  attr->flavor = MIO_NAME (sym_flavor) (attr->flavor, flavors);
  attr->intent = MIO_NAME (sym_intent) (attr->intent, intents);
  attr->proc = MIO_NAME (procedure_type) (attr->proc, procedures);
  attr->if_source = MIO_NAME (ifsrc) (attr->if_source, ifsrc_types);
  attr->save = MIO_NAME (save_state) (attr->save, save_status);

  ext_attr = attr->ext_attr;
  mio_integer ((int *) &ext_attr);
  attr->ext_attr = ext_attr;

  extension_level = attr->extension;
  mio_integer ((int *) &extension_level);
  attr->extension = extension_level;

  if (iomode == IO_OUTPUT)
    {
      if (attr->allocatable)
	MIO_NAME (ab_attribute) (AB_ALLOCATABLE, attr_bits);
      if (attr->artificial)
	MIO_NAME (ab_attribute) (AB_ARTIFICIAL, attr_bits);
      if (attr->asynchronous)
	MIO_NAME (ab_attribute) (AB_ASYNCHRONOUS, attr_bits);
      if (attr->dimension)
	MIO_NAME (ab_attribute) (AB_DIMENSION, attr_bits);
      if (attr->codimension)
	MIO_NAME (ab_attribute) (AB_CODIMENSION, attr_bits);
      if (attr->contiguous)
	MIO_NAME (ab_attribute) (AB_CONTIGUOUS, attr_bits);
      if (attr->external)
	MIO_NAME (ab_attribute) (AB_EXTERNAL, attr_bits);
      if (attr->intrinsic)
	MIO_NAME (ab_attribute) (AB_INTRINSIC, attr_bits);
      if (attr->optional)
	MIO_NAME (ab_attribute) (AB_OPTIONAL, attr_bits);
      if (attr->pointer)
	MIO_NAME (ab_attribute) (AB_POINTER, attr_bits);
      if (attr->class_pointer)
	MIO_NAME (ab_attribute) (AB_CLASS_POINTER, attr_bits);
      if (attr->is_protected)
	MIO_NAME (ab_attribute) (AB_PROTECTED, attr_bits);
      if (attr->value)
	MIO_NAME (ab_attribute) (AB_VALUE, attr_bits);
      if (attr->volatile_)
	MIO_NAME (ab_attribute) (AB_VOLATILE, attr_bits);
      if (attr->target)
	MIO_NAME (ab_attribute) (AB_TARGET, attr_bits);
      if (attr->threadprivate)
	MIO_NAME (ab_attribute) (AB_THREADPRIVATE, attr_bits);
      if (attr->dummy)
	MIO_NAME (ab_attribute) (AB_DUMMY, attr_bits);
      if (attr->result)
	MIO_NAME (ab_attribute) (AB_RESULT, attr_bits);
      /* We deliberately don't preserve the "entry" flag.  */

      if (attr->data)
	MIO_NAME (ab_attribute) (AB_DATA, attr_bits);
      if (attr->in_namelist)
	MIO_NAME (ab_attribute) (AB_IN_NAMELIST, attr_bits);
      if (attr->in_common)
	MIO_NAME (ab_attribute) (AB_IN_COMMON, attr_bits);

      if (attr->function)
	MIO_NAME (ab_attribute) (AB_FUNCTION, attr_bits);
      if (attr->subroutine)
	MIO_NAME (ab_attribute) (AB_SUBROUTINE, attr_bits);
      if (attr->generic)
	MIO_NAME (ab_attribute) (AB_GENERIC, attr_bits);
      if (attr->abstract)
	MIO_NAME (ab_attribute) (AB_ABSTRACT, attr_bits);

      if (attr->sequence)
	MIO_NAME (ab_attribute) (AB_SEQUENCE, attr_bits);
      if (attr->elemental)
	MIO_NAME (ab_attribute) (AB_ELEMENTAL, attr_bits);
      if (attr->pure)
	MIO_NAME (ab_attribute) (AB_PURE, attr_bits);
      if (attr->implicit_pure)
	MIO_NAME (ab_attribute) (AB_IMPLICIT_PURE, attr_bits);
      if (attr->unlimited_polymorphic)
	MIO_NAME (ab_attribute) (AB_UNLIMITED_POLY, attr_bits);
      if (attr->recursive)
	MIO_NAME (ab_attribute) (AB_RECURSIVE, attr_bits);
      if (attr->always_explicit)
	MIO_NAME (ab_attribute) (AB_ALWAYS_EXPLICIT, attr_bits);
      if (attr->cray_pointer)
	MIO_NAME (ab_attribute) (AB_CRAY_POINTER, attr_bits);
      if (attr->cray_pointee)
	MIO_NAME (ab_attribute) (AB_CRAY_POINTEE, attr_bits);
      if (attr->is_bind_c)
	MIO_NAME(ab_attribute) (AB_IS_BIND_C, attr_bits);
      if (attr->is_c_interop)
	MIO_NAME(ab_attribute) (AB_IS_C_INTEROP, attr_bits);
      if (attr->is_iso_c)
	MIO_NAME(ab_attribute) (AB_IS_ISO_C, attr_bits);
      if (attr->alloc_comp)
	MIO_NAME (ab_attribute) (AB_ALLOC_COMP, attr_bits);
      if (attr->pointer_comp)
	MIO_NAME (ab_attribute) (AB_POINTER_COMP, attr_bits);
      if (attr->proc_pointer_comp)
	MIO_NAME (ab_attribute) (AB_PROC_POINTER_COMP, attr_bits);
      if (attr->private_comp)
	MIO_NAME (ab_attribute) (AB_PRIVATE_COMP, attr_bits);
      if (attr->coarray_comp)
	MIO_NAME (ab_attribute) (AB_COARRAY_COMP, attr_bits);
      if (attr->lock_comp)
	MIO_NAME (ab_attribute) (AB_LOCK_COMP, attr_bits);
      if (attr->event_comp)
	MIO_NAME (ab_attribute) (AB_EVENT_COMP, attr_bits);
      if (attr->zero_comp)
	MIO_NAME (ab_attribute) (AB_ZERO_COMP, attr_bits);
      if (attr->is_class)
	MIO_NAME (ab_attribute) (AB_IS_CLASS, attr_bits);
      if (attr->procedure)
	MIO_NAME (ab_attribute) (AB_PROCEDURE, attr_bits);
      if (attr->proc_pointer)
	MIO_NAME (ab_attribute) (AB_PROC_POINTER, attr_bits);
      if (attr->vtype)
	MIO_NAME (ab_attribute) (AB_VTYPE, attr_bits);
      if (attr->vtab)
	MIO_NAME (ab_attribute) (AB_VTAB, attr_bits);
      if (attr->omp_declare_target)
	MIO_NAME (ab_attribute) (AB_OMP_DECLARE_TARGET, attr_bits);
      if (attr->array_outer_dependency)
	MIO_NAME (ab_attribute) (AB_ARRAY_OUTER_DEPENDENCY, attr_bits);
      if (attr->module_procedure)
	MIO_NAME (ab_attribute) (AB_MODULE_PROCEDURE, attr_bits);
      if (attr->oacc_declare_create)
	MIO_NAME (ab_attribute) (AB_OACC_DECLARE_CREATE, attr_bits);
      if (attr->oacc_declare_copyin)
	MIO_NAME (ab_attribute) (AB_OACC_DECLARE_COPYIN, attr_bits);
      if (attr->oacc_declare_deviceptr)
	MIO_NAME (ab_attribute) (AB_OACC_DECLARE_DEVICEPTR, attr_bits);
      if (attr->oacc_declare_device_resident)
	MIO_NAME (ab_attribute) (AB_OACC_DECLARE_DEVICE_RESIDENT, attr_bits);
      if (attr->oacc_declare_link)
	MIO_NAME (ab_attribute) (AB_OACC_DECLARE_LINK, attr_bits);
      if (attr->omp_declare_target_link)
	MIO_NAME (ab_attribute) (AB_OMP_DECLARE_TARGET_LINK, attr_bits);
      if (attr->pdt_kind)
	MIO_NAME (ab_attribute) (AB_PDT_KIND, attr_bits);
      if (attr->pdt_len)
	MIO_NAME (ab_attribute) (AB_PDT_LEN, attr_bits);
      if (attr->pdt_type)
	MIO_NAME (ab_attribute) (AB_PDT_TYPE, attr_bits);
      if (attr->pdt_template)
	MIO_NAME (ab_attribute) (AB_PDT_TEMPLATE, attr_bits);
      if (attr->pdt_array)
	MIO_NAME (ab_attribute) (AB_PDT_ARRAY, attr_bits);
      if (attr->pdt_string)
	MIO_NAME (ab_attribute) (AB_PDT_STRING, attr_bits);
      switch (attr->oacc_routine_lop)
	{
	case OACC_ROUTINE_LOP_NONE:
	  /* This is the default anyway, and for maintaining compatibility with
	     the current MOD_VERSION, we're not emitting anything in that
	     case.  */
	  break;
	case OACC_ROUTINE_LOP_GANG:
	  MIO_NAME (ab_attribute) (AB_OACC_ROUTINE_LOP_GANG, attr_bits);
	  break;
	case OACC_ROUTINE_LOP_WORKER:
	  MIO_NAME (ab_attribute) (AB_OACC_ROUTINE_LOP_WORKER, attr_bits);
	  break;
	case OACC_ROUTINE_LOP_VECTOR:
	  MIO_NAME (ab_attribute) (AB_OACC_ROUTINE_LOP_VECTOR, attr_bits);
	  break;
	case OACC_ROUTINE_LOP_SEQ:
	  MIO_NAME (ab_attribute) (AB_OACC_ROUTINE_LOP_SEQ, attr_bits);
	  break;
	case OACC_ROUTINE_LOP_ERROR:
	  /* ... intentionally omitted here; it's only unsed internally.  */
	default:
	  gcc_unreachable ();
	}
      if (attr->oacc_routine_nohost)
	MIO_NAME (ab_attribute) (AB_OACC_ROUTINE_NOHOST, attr_bits);

      if (attr->flavor == FL_MODULE && gfc_current_ns->omp_requires)
	{
	  if (gfc_current_ns->omp_requires & OMP_REQ_REVERSE_OFFLOAD)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_REVERSE_OFFLOAD, attr_bits);
	  if (gfc_current_ns->omp_requires & OMP_REQ_UNIFIED_ADDRESS)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_UNIFIED_ADDRESS, attr_bits);
	  if (gfc_current_ns->omp_requires & OMP_REQ_UNIFIED_SHARED_MEMORY)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_UNIFIED_SHARED_MEMORY, attr_bits);
	  if (gfc_current_ns->omp_requires & OMP_REQ_DYNAMIC_ALLOCATORS)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_DYNAMIC_ALLOCATORS, attr_bits);
	  if ((gfc_current_ns->omp_requires & OMP_REQ_ATOMIC_MEM_ORDER_MASK)
	      == OMP_REQ_ATOMIC_MEM_ORDER_SEQ_CST)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_MEM_ORDER_SEQ_CST, attr_bits);
	  if ((gfc_current_ns->omp_requires & OMP_REQ_ATOMIC_MEM_ORDER_MASK)
	      == OMP_REQ_ATOMIC_MEM_ORDER_ACQ_REL)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_MEM_ORDER_ACQ_REL, attr_bits);
	  if ((gfc_current_ns->omp_requires & OMP_REQ_ATOMIC_MEM_ORDER_MASK)
	      == OMP_REQ_ATOMIC_MEM_ORDER_RELAXED)
	    MIO_NAME (ab_attribute) (AB_OMP_REQ_MEM_ORDER_RELAXED, attr_bits);
	}
      switch (attr->omp_device_type)
	{
	case OMP_DEVICE_TYPE_UNSET:
	  break;
	case OMP_DEVICE_TYPE_HOST:
	  MIO_NAME (ab_attribute) (AB_OMP_DEVICE_TYPE_HOST, attr_bits);
	  break;
	case OMP_DEVICE_TYPE_NOHOST:
	  MIO_NAME (ab_attribute) (AB_OMP_DEVICE_TYPE_NOHOST, attr_bits);
	  break;
	case OMP_DEVICE_TYPE_ANY:
	  MIO_NAME (ab_attribute) (AB_OMP_DEVICE_TYPE_ANY, attr_bits);
	  break;
	default:
	  gcc_unreachable ();
	}
      mio_rparen ();
    }
  else
    {
      for (;;)
	{
	  t = parse_atom ();
	  if (t == ATOM_RPAREN)
	    break;
	  if (t != ATOM_NAME)
	    bad_module ("Expected attribute bit name");

	  switch ((ab_attribute) find_enum (attr_bits))
	    {
	    case AB_ALLOCATABLE:
	      attr->allocatable = 1;
	      break;
	    case AB_ARTIFICIAL:
	      attr->artificial = 1;
	      break;
	    case AB_ASYNCHRONOUS:
	      attr->asynchronous = 1;
	      break;
	    case AB_DIMENSION:
	      attr->dimension = 1;
	      break;
	    case AB_CODIMENSION:
	      attr->codimension = 1;
	      break;
	    case AB_CONTIGUOUS:
	      attr->contiguous = 1;
	      break;
	    case AB_EXTERNAL:
	      attr->external = 1;
	      break;
	    case AB_INTRINSIC:
	      attr->intrinsic = 1;
	      break;
	    case AB_OPTIONAL:
	      attr->optional = 1;
	      break;
	    case AB_POINTER:
	      attr->pointer = 1;
	      break;
	    case AB_CLASS_POINTER:
	      attr->class_pointer = 1;
	      break;
	    case AB_PROTECTED:
	      attr->is_protected = 1;
	      break;
	    case AB_VALUE:
	      attr->value = 1;
	      break;
	    case AB_VOLATILE:
	      attr->volatile_ = 1;
	      break;
	    case AB_TARGET:
	      attr->target = 1;
	      break;
	    case AB_THREADPRIVATE:
	      attr->threadprivate = 1;
	      break;
	    case AB_DUMMY:
	      attr->dummy = 1;
	      break;
	    case AB_RESULT:
	      attr->result = 1;
	      break;
	    case AB_DATA:
	      attr->data = 1;
	      break;
	    case AB_IN_NAMELIST:
	      attr->in_namelist = 1;
	      break;
	    case AB_IN_COMMON:
	      attr->in_common = 1;
	      break;
	    case AB_FUNCTION:
	      attr->function = 1;
	      break;
	    case AB_SUBROUTINE:
	      attr->subroutine = 1;
	      break;
	    case AB_GENERIC:
	      attr->generic = 1;
	      break;
	    case AB_ABSTRACT:
	      attr->abstract = 1;
	      break;
	    case AB_SEQUENCE:
	      attr->sequence = 1;
	      break;
	    case AB_ELEMENTAL:
	      attr->elemental = 1;
	      break;
	    case AB_PURE:
	      attr->pure = 1;
	      break;
	    case AB_IMPLICIT_PURE:
	      attr->implicit_pure = 1;
	      break;
	    case AB_UNLIMITED_POLY:
	      attr->unlimited_polymorphic = 1;
	      break;
	    case AB_RECURSIVE:
	      attr->recursive = 1;
	      break;
	    case AB_ALWAYS_EXPLICIT:
	      attr->always_explicit = 1;
	      break;
	    case AB_CRAY_POINTER:
	      attr->cray_pointer = 1;
	      break;
	    case AB_CRAY_POINTEE:
	      attr->cray_pointee = 1;
	      break;
	    case AB_IS_BIND_C:
	      attr->is_bind_c = 1;
	      break;
	    case AB_IS_C_INTEROP:
	      attr->is_c_interop = 1;
	      break;
	    case AB_IS_ISO_C:
	      attr->is_iso_c = 1;
	      break;
	    case AB_ALLOC_COMP:
	      attr->alloc_comp = 1;
	      break;
	    case AB_COARRAY_COMP:
	      attr->coarray_comp = 1;
	      break;
	    case AB_LOCK_COMP:
	      attr->lock_comp = 1;
	      break;
	    case AB_EVENT_COMP:
	      attr->event_comp = 1;
	      break;
	    case AB_POINTER_COMP:
	      attr->pointer_comp = 1;
	      break;
	    case AB_PROC_POINTER_COMP:
	      attr->proc_pointer_comp = 1;
	      break;
	    case AB_PRIVATE_COMP:
	      attr->private_comp = 1;
	      break;
	    case AB_ZERO_COMP:
	      attr->zero_comp = 1;
	      break;
	    case AB_IS_CLASS:
	      attr->is_class = 1;
	      break;
	    case AB_PROCEDURE:
	      attr->procedure = 1;
	      break;
	    case AB_PROC_POINTER:
	      attr->proc_pointer = 1;
	      break;
	    case AB_VTYPE:
	      attr->vtype = 1;
	      break;
	    case AB_VTAB:
	      attr->vtab = 1;
	      break;
	    case AB_OMP_DECLARE_TARGET:
	      attr->omp_declare_target = 1;
	      break;
	    case AB_OMP_DECLARE_TARGET_LINK:
	      attr->omp_declare_target_link = 1;
	      break;
	    case AB_ARRAY_OUTER_DEPENDENCY:
	      attr->array_outer_dependency =1;
	      break;
	    case AB_MODULE_PROCEDURE:
	      attr->module_procedure =1;
	      break;
	    case AB_OACC_DECLARE_CREATE:
	      attr->oacc_declare_create = 1;
	      break;
	    case AB_OACC_DECLARE_COPYIN:
	      attr->oacc_declare_copyin = 1;
	      break;
	    case AB_OACC_DECLARE_DEVICEPTR:
	      attr->oacc_declare_deviceptr = 1;
	      break;
	    case AB_OACC_DECLARE_DEVICE_RESIDENT:
	      attr->oacc_declare_device_resident = 1;
	      break;
	    case AB_OACC_DECLARE_LINK:
	      attr->oacc_declare_link = 1;
	      break;
	    case AB_PDT_KIND:
	      attr->pdt_kind = 1;
	      break;
	    case AB_PDT_LEN:
	      attr->pdt_len = 1;
	      break;
	    case AB_PDT_TYPE:
	      attr->pdt_type = 1;
	      break;
	    case AB_PDT_TEMPLATE:
	      attr->pdt_template = 1;
	      break;
	    case AB_PDT_ARRAY:
	      attr->pdt_array = 1;
	      break;
	    case AB_PDT_STRING:
	      attr->pdt_string = 1;
	      break;
	    case AB_OACC_ROUTINE_LOP_GANG:
	      verify_OACC_ROUTINE_LOP_NONE (attr->oacc_routine_lop);
	      attr->oacc_routine_lop = OACC_ROUTINE_LOP_GANG;
	      break;
	    case AB_OACC_ROUTINE_LOP_WORKER:
	      verify_OACC_ROUTINE_LOP_NONE (attr->oacc_routine_lop);
	      attr->oacc_routine_lop = OACC_ROUTINE_LOP_WORKER;
	      break;
	    case AB_OACC_ROUTINE_LOP_VECTOR:
	      verify_OACC_ROUTINE_LOP_NONE (attr->oacc_routine_lop);
	      attr->oacc_routine_lop = OACC_ROUTINE_LOP_VECTOR;
	      break;
	    case AB_OACC_ROUTINE_LOP_SEQ:
	      verify_OACC_ROUTINE_LOP_NONE (attr->oacc_routine_lop);
	      attr->oacc_routine_lop = OACC_ROUTINE_LOP_SEQ;
	      break;
	    case AB_OACC_ROUTINE_NOHOST:
	      attr->oacc_routine_nohost = 1;
	      break;
	    case AB_OMP_REQ_REVERSE_OFFLOAD:
	      gfc_omp_requires_add_clause (OMP_REQ_REVERSE_OFFLOAD,
					   "reverse_offload",
					   &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_UNIFIED_ADDRESS:
	      gfc_omp_requires_add_clause (OMP_REQ_UNIFIED_ADDRESS,
					   "unified_address",
					   &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_UNIFIED_SHARED_MEMORY:
	      gfc_omp_requires_add_clause (OMP_REQ_UNIFIED_SHARED_MEMORY,
					   "unified_shared_memory",
					   &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_DYNAMIC_ALLOCATORS:
	      gfc_omp_requires_add_clause (OMP_REQ_DYNAMIC_ALLOCATORS,
					   "dynamic_allocators",
					   &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_MEM_ORDER_SEQ_CST:
	      gfc_omp_requires_add_clause (OMP_REQ_ATOMIC_MEM_ORDER_SEQ_CST,
					   "seq_cst", &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_MEM_ORDER_ACQ_REL:
	      gfc_omp_requires_add_clause (OMP_REQ_ATOMIC_MEM_ORDER_ACQ_REL,
					   "acq_rel", &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_REQ_MEM_ORDER_RELAXED:
	      gfc_omp_requires_add_clause (OMP_REQ_ATOMIC_MEM_ORDER_RELAXED,
					   "relaxed", &gfc_current_locus,
					   module_name);
	      break;
	    case AB_OMP_DEVICE_TYPE_HOST:
	      attr->omp_device_type = OMP_DEVICE_TYPE_HOST;
	      break;
	    case AB_OMP_DEVICE_TYPE_NOHOST:
	      attr->omp_device_type = OMP_DEVICE_TYPE_NOHOST;
	      break;
	    case AB_OMP_DEVICE_TYPE_ANY:
	      attr->omp_device_type = OMP_DEVICE_TYPE_ANY;
	      break;
	    }
	}
    }
}


static const mstring bt_types[] = {
    minit ("INTEGER", BT_INTEGER),
    minit ("REAL", BT_REAL),
    minit ("COMPLEX", BT_COMPLEX),
    minit ("LOGICAL", BT_LOGICAL),
    minit ("CHARACTER", BT_CHARACTER),
    minit ("UNION", BT_UNION),
    minit ("DERIVED", BT_DERIVED),
    minit ("CLASS", BT_CLASS),
    minit ("PROCEDURE", BT_PROCEDURE),
    minit ("UNKNOWN", BT_UNKNOWN),
    minit ("VOID", BT_VOID),
    minit ("ASSUMED", BT_ASSUMED),
    minit (NULL, -1)
};


static void
mio_charlen (gfc_charlen **clp)
{
  gfc_charlen *cl;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      cl = *clp;
      if (cl != NULL)
	mio_expr (&cl->length);
    }
  else
    {
      if (peek_atom () != ATOM_RPAREN)
	{
	  cl = gfc_new_charlen (gfc_current_ns, NULL);
	  mio_expr (&cl->length);
	  *clp = cl;
	}
    }

  mio_rparen ();
}


/* See if a name is a generated name.  */

static int
check_unique_name (const char *name)
{
  return *name == '@';
}


static void
mio_typespec (gfc_typespec *ts)
{
  mio_lparen ();

  ts->type = MIO_NAME (bt) (ts->type, bt_types);

  if (!gfc_bt_struct (ts->type) && ts->type != BT_CLASS)
    mio_integer (&ts->kind);
  else
    mio_symbol_ref (&ts->u.derived);

  mio_symbol_ref (&ts->interface);

  /* Add info for C interop and is_iso_c.  */
  mio_integer (&ts->is_c_interop);
  mio_integer (&ts->is_iso_c);

  /* If the typespec is for an identifier either from iso_c_binding, or
     a constant that was initialized to an identifier from it, use the
     f90_type.  Otherwise, use the ts->type, since it shouldn't matter.  */
  if (ts->is_iso_c)
    ts->f90_type = MIO_NAME (bt) (ts->f90_type, bt_types);
  else
    ts->f90_type = MIO_NAME (bt) (ts->type, bt_types);

  if (ts->type != BT_CHARACTER)
    {
      /* ts->u.cl is only valid for BT_CHARACTER.  */
      mio_lparen ();
      mio_rparen ();
    }
  else
    mio_charlen (&ts->u.cl);

  /* So as not to disturb the existing API, use an ATOM_NAME to
     transmit deferred characteristic for characters (F2003).  */
  if (iomode == IO_OUTPUT)
    {
      if (ts->type == BT_CHARACTER && ts->deferred)
	write_atom (ATOM_NAME, "DEFERRED_CL");
    }
  else if (peek_atom () != ATOM_RPAREN)
    {
      if (parse_atom () != ATOM_NAME)
	bad_module ("Expected string");
      ts->deferred = 1;
    }

  mio_rparen ();
}


static const mstring array_spec_types[] = {
    minit ("EXPLICIT", AS_EXPLICIT),
    minit ("ASSUMED_RANK", AS_ASSUMED_RANK),
    minit ("ASSUMED_SHAPE", AS_ASSUMED_SHAPE),
    minit ("DEFERRED", AS_DEFERRED),
    minit ("ASSUMED_SIZE", AS_ASSUMED_SIZE),
    minit (NULL, -1)
};


static void
mio_array_spec (gfc_array_spec **asp)
{
  gfc_array_spec *as;
  int i;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      int rank;

      if (*asp == NULL)
	goto done;
      as = *asp;

      /* mio_integer expects nonnegative values.  */
      rank = as->rank > 0 ? as->rank : 0;
      mio_integer (&rank);
    }
  else
    {
      if (peek_atom () == ATOM_RPAREN)
	{
	  *asp = NULL;
	  goto done;
	}

      *asp = as = gfc_get_array_spec ();
      mio_integer (&as->rank);
    }

  mio_integer (&as->corank);
  as->type = MIO_NAME (array_type) (as->type, array_spec_types);

  if (iomode == IO_INPUT && as->type == AS_ASSUMED_RANK)
    as->rank = -1;
  if (iomode == IO_INPUT && as->corank)
    as->cotype = (as->type == AS_DEFERRED) ? AS_DEFERRED : AS_EXPLICIT;

  if (as->rank + as->corank > 0)
    for (i = 0; i < as->rank + as->corank; i++)
      {
	mio_expr (&as->lower[i]);
	mio_expr (&as->upper[i]);
      }

done:
  mio_rparen ();
}


/* Given a pointer to an array reference structure (which lives in a
   gfc_ref structure), find the corresponding array specification
   structure.  Storing the pointer in the ref structure doesn't quite
   work when loading from a module. Generating code for an array
   reference also needs more information than just the array spec.  */

static const mstring array_ref_types[] = {
    minit ("FULL", AR_FULL),
    minit ("ELEMENT", AR_ELEMENT),
    minit ("SECTION", AR_SECTION),
    minit (NULL, -1)
};


static void
mio_array_ref (gfc_array_ref *ar)
{
  int i;

  mio_lparen ();
  ar->type = MIO_NAME (ar_type) (ar->type, array_ref_types);
  mio_integer (&ar->dimen);

  switch (ar->type)
    {
    case AR_FULL:
      break;

    case AR_ELEMENT:
      for (i = 0; i < ar->dimen; i++)
	mio_expr (&ar->start[i]);

      break;

    case AR_SECTION:
      for (i = 0; i < ar->dimen; i++)
	{
	  mio_expr (&ar->start[i]);
	  mio_expr (&ar->end[i]);
	  mio_expr (&ar->stride[i]);
	}

      break;

    case AR_UNKNOWN:
      gfc_internal_error ("mio_array_ref(): Unknown array ref");
    }

  /* Unfortunately, ar->dimen_type is an anonymous enumerated type so
     we can't call mio_integer directly.  Instead loop over each element
     and cast it to/from an integer.  */
  if (iomode == IO_OUTPUT)
    {
      for (i = 0; i < ar->dimen; i++)
	{
	  HOST_WIDE_INT tmp = (HOST_WIDE_INT)ar->dimen_type[i];
	  write_atom (ATOM_INTEGER, &tmp);
	}
    }
  else
    {
      for (i = 0; i < ar->dimen; i++)
	{
	  require_atom (ATOM_INTEGER);
	  ar->dimen_type[i] = (enum gfc_array_ref_dimen_type) atom_int;
	}
    }

  if (iomode == IO_INPUT)
    {
      ar->where = gfc_current_locus;

      for (i = 0; i < ar->dimen; i++)
	ar->c_where[i] = gfc_current_locus;
    }

  mio_rparen ();
}


/* Saves or restores a pointer.  The pointer is converted back and
   forth from an integer.  We return the pointer_info pointer so that
   the caller can take additional action based on the pointer type.  */

static pointer_info *
mio_pointer_ref (void *gp)
{
  pointer_info *p;

  if (iomode == IO_OUTPUT)
    {
      p = get_pointer (*((char **) gp));
      HOST_WIDE_INT hwi = p->integer;
      write_atom (ATOM_INTEGER, &hwi);
    }
  else
    {
      require_atom (ATOM_INTEGER);
      p = add_fixup (atom_int, gp);
    }

  return p;
}


/* Save and load references to components that occur within
   expressions.  We have to describe these references by a number and
   by name.  The number is necessary for forward references during
   reading, and the name is necessary if the symbol already exists in
   the namespace and is not loaded again.  */

static void
mio_component_ref (gfc_component **cp)
{
  pointer_info *p;

  p = mio_pointer_ref (cp);
  if (p->type == P_UNKNOWN)
    p->type = P_COMPONENT;
}


static void mio_namespace_ref (gfc_namespace **nsp);
static void mio_formal_arglist (gfc_formal_arglist **formal);
static void mio_typebound_proc (gfc_typebound_proc** proc);
static void mio_actual_arglist (gfc_actual_arglist **ap, bool pdt);

static void
mio_component (gfc_component *c, int vtype)
{
  pointer_info *p;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      p = get_pointer (c);
      mio_hwi (&p->integer);
    }
  else
    {
      HOST_WIDE_INT n;
      mio_hwi (&n);
      p = get_integer (n);
      associate_integer_pointer (p, c);
    }

  if (p->type == P_UNKNOWN)
    p->type = P_COMPONENT;

  mio_pool_string (&c->name);
  mio_typespec (&c->ts);
  mio_array_spec (&c->as);

  /* PDT templates store the expression for the kind of a component here.  */
  mio_expr (&c->kind_expr);

  /* PDT types store the component specification list here. */
  mio_actual_arglist (&c->param_list, true);

  mio_symbol_attribute (&c->attr);
  if (c->ts.type == BT_CLASS)
    c->attr.class_ok = 1;
  c->attr.access = MIO_NAME (gfc_access) (c->attr.access, access_types);

  if (!vtype || strcmp (c->name, "_final") == 0
      || strcmp (c->name, "_hash") == 0)
    mio_expr (&c->initializer);

  if (c->attr.proc_pointer)
    mio_typebound_proc (&c->tb);

  c->loc = gfc_current_locus;

  mio_rparen ();
}


static void
mio_component_list (gfc_component **cp, int vtype)
{
  gfc_component *c, *tail;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (c = *cp; c; c = c->next)
	mio_component (c, vtype);
    }
  else
    {
      *cp = NULL;
      tail = NULL;

      for (;;)
	{
	  if (peek_atom () == ATOM_RPAREN)
	    break;

	  c = gfc_get_component ();
	  mio_component (c, vtype);

	  if (tail == NULL)
	    *cp = c;
	  else
	    tail->next = c;

	  tail = c;
	}
    }

  mio_rparen ();
}


static void
mio_actual_arg (gfc_actual_arglist *a, bool pdt)
{
  mio_lparen ();
  mio_pool_string (&a->name);
  mio_expr (&a->expr);
  if (pdt)
    mio_integer ((int *)&a->spec_type);
  mio_rparen ();
}


static void
mio_actual_arglist (gfc_actual_arglist **ap, bool pdt)
{
  gfc_actual_arglist *a, *tail;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (a = *ap; a; a = a->next)
	mio_actual_arg (a, pdt);

    }
  else
    {
      tail = NULL;

      for (;;)
	{
	  if (peek_atom () != ATOM_LPAREN)
	    break;

	  a = gfc_get_actual_arglist ();

	  if (tail == NULL)
	    *ap = a;
	  else
	    tail->next = a;

	  tail = a;
	  mio_actual_arg (a, pdt);
	}
    }

  mio_rparen ();
}


/* Read and write formal argument lists.  */

static void
mio_formal_arglist (gfc_formal_arglist **formal)
{
  gfc_formal_arglist *f, *tail;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (f = *formal; f; f = f->next)
	mio_symbol_ref (&f->sym);
    }
  else
    {
      *formal = tail = NULL;

      while (peek_atom () != ATOM_RPAREN)
	{
	  f = gfc_get_formal_arglist ();
	  mio_symbol_ref (&f->sym);

	  if (*formal == NULL)
	    *formal = f;
	  else
	    tail->next = f;

	  tail = f;
	}
    }

  mio_rparen ();
}


/* Save or restore a reference to a symbol node.  */

pointer_info *
mio_symbol_ref (gfc_symbol **symp)
{
  pointer_info *p;

  p = mio_pointer_ref (symp);
  if (p->type == P_UNKNOWN)
    p->type = P_SYMBOL;

  if (iomode == IO_OUTPUT)
    {
      if (p->u.wsym.state == UNREFERENCED)
	p->u.wsym.state = NEEDS_WRITE;
    }
  else
    {
      if (p->u.rsym.state == UNUSED)
	p->u.rsym.state = NEEDED;
    }
  return p;
}


/* Save or restore a reference to a symtree node.  */

static void
mio_symtree_ref (gfc_symtree **stp)
{
  pointer_info *p;
  fixup_t *f;

  if (iomode == IO_OUTPUT)
    mio_symbol_ref (&(*stp)->n.sym);
  else
    {
      require_atom (ATOM_INTEGER);
      p = get_integer (atom_int);

      /* An unused equivalence member; make a symbol and a symtree
	 for it.  */
      if (in_load_equiv && p->u.rsym.symtree == NULL)
	{
	  /* Since this is not used, it must have a unique name.  */
	  p->u.rsym.symtree = gfc_get_unique_symtree (gfc_current_ns);

	  /* Make the symbol.  */
	  if (p->u.rsym.sym == NULL)
	    {
	      p->u.rsym.sym = gfc_new_symbol (p->u.rsym.true_name,
					      gfc_current_ns);
	      p->u.rsym.sym->module = gfc_get_string ("%s", p->u.rsym.module);
	    }

	  p->u.rsym.symtree->n.sym = p->u.rsym.sym;
	  p->u.rsym.symtree->n.sym->refs++;
	  p->u.rsym.referenced = 1;

	  /* If the symbol is PRIVATE and in COMMON, load_commons will
	     generate a fixup symbol, which must be associated.  */
	  if (p->fixup)
	    resolve_fixups (p->fixup, p->u.rsym.sym);
	  p->fixup = NULL;
	}

      if (p->type == P_UNKNOWN)
	p->type = P_SYMBOL;

      if (p->u.rsym.state == UNUSED)
	p->u.rsym.state = NEEDED;

      if (p->u.rsym.symtree != NULL)
	{
	  *stp = p->u.rsym.symtree;
	}
      else
	{
	  f = XCNEW (fixup_t);

	  f->next = p->u.rsym.stfixup;
	  p->u.rsym.stfixup = f;

	  f->pointer = (void **) stp;
	}
    }
}


static void
mio_iterator (gfc_iterator **ip)
{
  gfc_iterator *iter;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      if (*ip == NULL)
	goto done;
    }
  else
    {
      if (peek_atom () == ATOM_RPAREN)
	{
	  *ip = NULL;
	  goto done;
	}

      *ip = gfc_get_iterator ();
    }

  iter = *ip;

  mio_expr (&iter->var);
  mio_expr (&iter->start);
  mio_expr (&iter->end);
  mio_expr (&iter->step);

done:
  mio_rparen ();
}


static void
mio_constructor (gfc_constructor_base *cp)
{
  gfc_constructor *c;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (c = gfc_constructor_first (*cp); c; c = gfc_constructor_next (c))
	{
	  mio_lparen ();
	  mio_expr (&c->expr);
	  mio_iterator (&c->iterator);
	  mio_rparen ();
	}
    }
  else
    {
      while (peek_atom () != ATOM_RPAREN)
	{
	  c = gfc_constructor_append_expr (cp, NULL, NULL);

	  mio_lparen ();
	  mio_expr (&c->expr);
	  mio_iterator (&c->iterator);
	  mio_rparen ();
	}
    }

  mio_rparen ();
}


static const mstring ref_types[] = {
    minit ("ARRAY", REF_ARRAY),
    minit ("COMPONENT", REF_COMPONENT),
    minit ("SUBSTRING", REF_SUBSTRING),
    minit ("INQUIRY", REF_INQUIRY),
    minit (NULL, -1)
};

static const mstring inquiry_types[] = {
    minit ("RE", INQUIRY_RE),
    minit ("IM", INQUIRY_IM),
    minit ("KIND", INQUIRY_KIND),
    minit ("LEN", INQUIRY_LEN),
    minit (NULL, -1)
};


static void
mio_ref (gfc_ref **rp)
{
  gfc_ref *r;

  mio_lparen ();

  r = *rp;
  r->type = MIO_NAME (ref_type) (r->type, ref_types);

  switch (r->type)
    {
    case REF_ARRAY:
      mio_array_ref (&r->u.ar);
      break;

    case REF_COMPONENT:
      mio_symbol_ref (&r->u.c.sym);
      mio_component_ref (&r->u.c.component);
      break;

    case REF_SUBSTRING:
      mio_expr (&r->u.ss.start);
      mio_expr (&r->u.ss.end);
      mio_charlen (&r->u.ss.length);
      break;

    case REF_INQUIRY:
      r->u.i = MIO_NAME (inquiry_type) (r->u.i, inquiry_types);
      break;
    }

  mio_rparen ();
}


static void
mio_ref_list (gfc_ref **rp)
{
  gfc_ref *ref, *head, *tail;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (ref = *rp; ref; ref = ref->next)
	mio_ref (&ref);
    }
  else
    {
      head = tail = NULL;

      while (peek_atom () != ATOM_RPAREN)
	{
	  if (head == NULL)
	    head = tail = gfc_get_ref ();
	  else
	    {
	      tail->next = gfc_get_ref ();
	      tail = tail->next;
	    }

	  mio_ref (&tail);
	}

      *rp = head;
    }

  mio_rparen ();
}


/* Read and write an integer value.  */

static void
mio_gmp_integer (mpz_t *integer)
{
  char *p;

  if (iomode == IO_INPUT)
    {
      if (parse_atom () != ATOM_STRING)
	bad_module ("Expected integer string");

      mpz_init (*integer);
      if (mpz_set_str (*integer, atom_string, 10))
	bad_module ("Error converting integer");

      free (atom_string);
    }
  else
    {
      p = mpz_get_str (NULL, 10, *integer);
      write_atom (ATOM_STRING, p);
      free (p);
    }
}


static void
mio_gmp_real (mpfr_t *real)
{
  mpfr_exp_t exponent;
  char *p;

  if (iomode == IO_INPUT)
    {
      if (parse_atom () != ATOM_STRING)
	bad_module ("Expected real string");

      mpfr_init (*real);
      mpfr_set_str (*real, atom_string, 16, GFC_RND_MODE);
      free (atom_string);
    }
  else
    {
      p = mpfr_get_str (NULL, &exponent, 16, 0, *real, GFC_RND_MODE);

      if (mpfr_nan_p (*real) || mpfr_inf_p (*real))
	{
	  write_atom (ATOM_STRING, p);
	  free (p);
	  return;
	}

      atom_string = XCNEWVEC (char, strlen (p) + 20);

      sprintf (atom_string, "0.%s@%ld", p, exponent);

      /* Fix negative numbers.  */
      if (atom_string[2] == '-')
	{
	  atom_string[0] = '-';
	  atom_string[1] = '0';
	  atom_string[2] = '.';
	}

      write_atom (ATOM_STRING, atom_string);

      free (atom_string);
      free (p);
    }
}


/* Save and restore the shape of an array constructor.  */

static void
mio_shape (mpz_t **pshape, int rank)
{
  mpz_t *shape;
  atom_type t;
  int n;

  /* A NULL shape is represented by ().  */
  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      shape = *pshape;
      if (!shape)
	{
	  mio_rparen ();
	  return;
	}
    }
  else
    {
      t = peek_atom ();
      if (t == ATOM_RPAREN)
	{
	  *pshape = NULL;
	  mio_rparen ();
	  return;
	}

      shape = gfc_get_shape (rank);
      *pshape = shape;
    }

  for (n = 0; n < rank; n++)
    mio_gmp_integer (&shape[n]);

  mio_rparen ();
}


static const mstring expr_types[] = {
    minit ("OP", EXPR_OP),
    minit ("FUNCTION", EXPR_FUNCTION),
    minit ("CONSTANT", EXPR_CONSTANT),
    minit ("VARIABLE", EXPR_VARIABLE),
    minit ("SUBSTRING", EXPR_SUBSTRING),
    minit ("STRUCTURE", EXPR_STRUCTURE),
    minit ("ARRAY", EXPR_ARRAY),
    minit ("NULL", EXPR_NULL),
    minit ("COMPCALL", EXPR_COMPCALL),
    minit (NULL, -1)
};

/* INTRINSIC_ASSIGN is missing because it is used as an index for
   generic operators, not in expressions.  INTRINSIC_USER is also
   replaced by the correct function name by the time we see it.  */

static const mstring intrinsics[] =
{
    minit ("UPLUS", INTRINSIC_UPLUS),
    minit ("UMINUS", INTRINSIC_UMINUS),
    minit ("PLUS", INTRINSIC_PLUS),
    minit ("MINUS", INTRINSIC_MINUS),
    minit ("TIMES", INTRINSIC_TIMES),
    minit ("DIVIDE", INTRINSIC_DIVIDE),
    minit ("POWER", INTRINSIC_POWER),
    minit ("CONCAT", INTRINSIC_CONCAT),
    minit ("AND", INTRINSIC_AND),
    minit ("OR", INTRINSIC_OR),
    minit ("EQV", INTRINSIC_EQV),
    minit ("NEQV", INTRINSIC_NEQV),
    minit ("EQ_SIGN", INTRINSIC_EQ),
    minit ("EQ", INTRINSIC_EQ_OS),
    minit ("NE_SIGN", INTRINSIC_NE),
    minit ("NE", INTRINSIC_NE_OS),
    minit ("GT_SIGN", INTRINSIC_GT),
    minit ("GT", INTRINSIC_GT_OS),
    minit ("GE_SIGN", INTRINSIC_GE),
    minit ("GE", INTRINSIC_GE_OS),
    minit ("LT_SIGN", INTRINSIC_LT),
    minit ("LT", INTRINSIC_LT_OS),
    minit ("LE_SIGN", INTRINSIC_LE),
    minit ("LE", INTRINSIC_LE_OS),
    minit ("NOT", INTRINSIC_NOT),
    minit ("PARENTHESES", INTRINSIC_PARENTHESES),
    minit ("USER", INTRINSIC_USER),
    minit (NULL, -1)
};


/* Remedy a couple of situations where the gfc_expr's can be defective.  */

static void
fix_mio_expr (gfc_expr *e)
{
  gfc_symtree *ns_st = NULL;
  const char *fname;

  if (iomode != IO_OUTPUT)
    return;

  if (e->symtree)
    {
      /* If this is a symtree for a symbol that came from a contained module
	 namespace, it has a unique name and we should look in the current
	 namespace to see if the required, non-contained symbol is available
	 yet. If so, the latter should be written.  */
      if (e->symtree->n.sym && check_unique_name (e->symtree->name))
	{
          const char *name = e->symtree->n.sym->name;
	  if (gfc_fl_struct (e->symtree->n.sym->attr.flavor))
	    name = gfc_dt_upper_string (name);
	  ns_st = gfc_find_symtree (gfc_current_ns->sym_root, name);
	}

      /* On the other hand, if the existing symbol is the module name or the
	 new symbol is a dummy argument, do not do the promotion.  */
      if (ns_st && ns_st->n.sym
	  && ns_st->n.sym->attr.flavor != FL_MODULE
	  && !e->symtree->n.sym->attr.dummy)
	e->symtree = ns_st;
    }
  else if (e->expr_type == EXPR_FUNCTION
	   && (e->value.function.name || e->value.function.isym))
    {
      gfc_symbol *sym;

      /* In some circumstances, a function used in an initialization
	 expression, in one use associated module, can fail to be
	 coupled to its symtree when used in a specification
	 expression in another module.  */
      fname = e->value.function.esym ? e->value.function.esym->name
				     : e->value.function.isym->name;
      e->symtree = gfc_find_symtree (gfc_current_ns->sym_root, fname);

      if (e->symtree)
	return;

      /* This is probably a reference to a private procedure from another
	 module.  To prevent a segfault, make a generic with no specific
	 instances.  If this module is used, without the required
	 specific coming from somewhere, the appropriate error message
	 is issued.  */
      gfc_get_symbol (fname, gfc_current_ns, &sym);
      sym->attr.flavor = FL_PROCEDURE;
      sym->attr.generic = 1;
      e->symtree = gfc_find_symtree (gfc_current_ns->sym_root, fname);
      gfc_commit_symbol (sym);
    }
}


/* Read and write expressions.  The form "()" is allowed to indicate a
   NULL expression.  */

static void
mio_expr (gfc_expr **ep)
{
  HOST_WIDE_INT hwi;
  gfc_expr *e;
  atom_type t;
  int flag;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      if (*ep == NULL)
	{
	  mio_rparen ();
	  return;
	}

      e = *ep;
      MIO_NAME (expr_t) (e->expr_type, expr_types);
    }
  else
    {
      t = parse_atom ();
      if (t == ATOM_RPAREN)
	{
	  *ep = NULL;
	  return;
	}

      if (t != ATOM_NAME)
	bad_module ("Expected expression type");

      e = *ep = gfc_get_expr ();
      e->where = gfc_current_locus;
      e->expr_type = (expr_t) find_enum (expr_types);
    }

  mio_typespec (&e->ts);
  mio_integer (&e->rank);

  fix_mio_expr (e);

  switch (e->expr_type)
    {
    case EXPR_OP:
      e->value.op.op
	= MIO_NAME (gfc_intrinsic_op) (e->value.op.op, intrinsics);

      switch (e->value.op.op)
	{
	case INTRINSIC_UPLUS:
	case INTRINSIC_UMINUS:
	case INTRINSIC_NOT:
	case INTRINSIC_PARENTHESES:
	  mio_expr (&e->value.op.op1);
	  break;

	case INTRINSIC_PLUS:
	case INTRINSIC_MINUS:
	case INTRINSIC_TIMES:
	case INTRINSIC_DIVIDE:
	case INTRINSIC_POWER:
	case INTRINSIC_CONCAT:
	case INTRINSIC_AND:
	case INTRINSIC_OR:
	case INTRINSIC_EQV:
	case INTRINSIC_NEQV:
	case INTRINSIC_EQ:
	case INTRINSIC_EQ_OS:
	case INTRINSIC_NE:
	case INTRINSIC_NE_OS:
	case INTRINSIC_GT:
	case INTRINSIC_GT_OS:
	case INTRINSIC_GE:
	case INTRINSIC_GE_OS:
	case INTRINSIC_LT:
	case INTRINSIC_LT_OS:
	case INTRINSIC_LE:
	case INTRINSIC_LE_OS:
	  mio_expr (&e->value.op.op1);
	  mio_expr (&e->value.op.op2);
	  break;

	case INTRINSIC_USER:
	  /* INTRINSIC_USER should not appear in resolved expressions,
	     though for UDRs we need to stream unresolved ones.  */
	  if (iomode == IO_OUTPUT)
	    write_atom (ATOM_STRING, e->value.op.uop->name);
	  else
	    {
	      char *name = read_string ();
	      const char *uop_name = find_use_name (name, true);
	      if (uop_name == NULL)
		{
		  size_t len = strlen (name);
		  char *name2 = XCNEWVEC (char, len + 2);
		  memcpy (name2, name, len);
		  name2[len] = ' ';
		  name2[len + 1] = '\0';
		  free (name);
		  uop_name = name = name2;
		}
	      e->value.op.uop = gfc_get_uop (uop_name);
	      free (name);
	    }
	  mio_expr (&e->value.op.op1);
	  mio_expr (&e->value.op.op2);
	  break;

	default:
	  bad_module ("Bad operator");
	}

      break;

    case EXPR_FUNCTION:
      mio_symtree_ref (&e->symtree);
      mio_actual_arglist (&e->value.function.actual, false);

      if (iomode == IO_OUTPUT)
	{
	  e->value.function.name
	    = mio_allocated_string (e->value.function.name);
	  if (e->value.function.esym)
	    flag = 1;
	  else if (e->ref)
	    flag = 2;
	  else if (e->value.function.isym == NULL)
	    flag = 3;
	  else
	    flag = 0;
	  mio_integer (&flag);
	  switch (flag)
	    {
	    case 1:
	      mio_symbol_ref (&e->value.function.esym);
	      break;
	    case 2:
	      mio_ref_list (&e->ref);
	      break;
	    case 3:
	      break;
	    default:
	      write_atom (ATOM_STRING, e->value.function.isym->name);
	    }
	}
      else
	{
	  require_atom (ATOM_STRING);
	  if (atom_string[0] == '\0')
	    e->value.function.name = NULL;
	  else
	    e->value.function.name = gfc_get_string ("%s", atom_string);
	  free (atom_string);

	  mio_integer (&flag);
	  switch (flag)
	    {
	    case 1:
	      mio_symbol_ref (&e->value.function.esym);
	      break;
	    case 2:
	      mio_ref_list (&e->ref);
	      break;
	    case 3:
	      break;
	    default:
	      require_atom (ATOM_STRING);
	      e->value.function.isym = gfc_find_function (atom_string);
	      free (atom_string);
	    }
	}

      break;

    case EXPR_VARIABLE:
      mio_symtree_ref (&e->symtree);
      mio_ref_list (&e->ref);
      break;

    case EXPR_SUBSTRING:
      e->value.character.string
	= CONST_CAST (gfc_char_t *,
		      mio_allocated_wide_string (e->value.character.string,
						 e->value.character.length));
      mio_ref_list (&e->ref);
      break;

    case EXPR_STRUCTURE:
    case EXPR_ARRAY:
      mio_constructor (&e->value.constructor);
      mio_shape (&e->shape, e->rank);
      break;

    case EXPR_CONSTANT:
      switch (e->ts.type)
	{
	case BT_INTEGER:
	  mio_gmp_integer (&e->value.integer);
	  break;

	case BT_REAL:
	  gfc_set_model_kind (e->ts.kind);
	  mio_gmp_real (&e->value.real);
	  break;

	case BT_COMPLEX:
	  gfc_set_model_kind (e->ts.kind);
	  mio_gmp_real (&mpc_realref (e->value.complex));
	  mio_gmp_real (&mpc_imagref (e->value.complex));
	  break;

	case BT_LOGICAL:
	  mio_integer (&e->value.logical);
	  break;

	case BT_CHARACTER:
	  hwi = e->value.character.length;
	  mio_hwi (&hwi);
	  e->value.character.length = hwi;
	  e->value.character.string
	    = CONST_CAST (gfc_char_t *,
			  mio_allocated_wide_string (e->value.character.string,
						     e->value.character.length));
	  break;

	default:
	  bad_module ("Bad type in constant expression");
	}

      break;

    case EXPR_NULL:
      break;

    case EXPR_COMPCALL:
    case EXPR_PPC:
    case EXPR_UNKNOWN:
      gcc_unreachable ();
      break;
    }

  /* PDT types store the expression specification list here. */
  mio_actual_arglist (&e->param_list, true);

  mio_rparen ();
}


/* Read and write namelists.  */

static void
mio_namelist (gfc_symbol *sym)
{
  gfc_namelist *n, *m;

  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      for (n = sym->namelist; n; n = n->next)
	mio_symbol_ref (&n->sym);
    }
  else
    {
      m = NULL;
      while (peek_atom () != ATOM_RPAREN)
	{
	  n = gfc_get_namelist ();
	  mio_symbol_ref (&n->sym);

	  if (sym->namelist == NULL)
	    sym->namelist = n;
	  else
	    m->next = n;

	  m = n;
	}
      sym->namelist_tail = m;
    }

  mio_rparen ();
}


/* Save/restore lists of gfc_interface structures.  When loading an
   interface, we are really appending to the existing list of
   interfaces.  Checking for duplicate and ambiguous interfaces has to
   be done later when all symbols have been loaded.  */

pointer_info *
mio_interface_rest (gfc_interface **ip)
{
  gfc_interface *tail, *p;
  pointer_info *pi = NULL;

  if (iomode == IO_OUTPUT)
    {
      if (ip != NULL)
	for (p = *ip; p; p = p->next)
	  mio_symbol_ref (&p->sym);
    }
  else
    {
      if (*ip == NULL)
	tail = NULL;
      else
	{
	  tail = *ip;
	  while (tail->next)
	    tail = tail->next;
	}

      for (;;)
	{
	  if (peek_atom () == ATOM_RPAREN)
	    break;

	  p = gfc_get_interface ();
	  p->where = gfc_current_locus;
	  pi = mio_symbol_ref (&p->sym);

	  if (tail == NULL)
	    *ip = p;
	  else
	    tail->next = p;

	  tail = p;
	}
    }

  mio_rparen ();
  return pi;
}


/* Save/restore a nameless operator interface.  */

static void
mio_interface (gfc_interface **ip)
{
  mio_lparen ();
  mio_interface_rest (ip);
}


/* Save/restore a named operator interface.  */

static void
mio_symbol_interface (const char **name, const char **module,
		      gfc_interface **ip)
{
  mio_lparen ();
  mio_pool_string (name);
  mio_pool_string (module);
  mio_interface_rest (ip);
}


static void
mio_namespace_ref (gfc_namespace **nsp)
{
  gfc_namespace *ns;
  pointer_info *p;

  p = mio_pointer_ref (nsp);

  if (p->type == P_UNKNOWN)
    p->type = P_NAMESPACE;

  if (iomode == IO_INPUT && p->integer != 0)
    {
      ns = (gfc_namespace *) p->u.pointer;
      if (ns == NULL)
	{
	  ns = gfc_get_namespace (NULL, 0);
	  associate_integer_pointer (p, ns);
	}
      else
	ns->refs++;
    }
}


/* Save/restore the f2k_derived namespace of a derived-type symbol.  */

static gfc_namespace* current_f2k_derived;

static void
mio_typebound_proc (gfc_typebound_proc** proc)
{
  int flag;
  int overriding_flag;

  if (iomode == IO_INPUT)
    {
      *proc = gfc_get_typebound_proc (NULL);
      (*proc)->where = gfc_current_locus;
    }
  gcc_assert (*proc);

  mio_lparen ();

  (*proc)->access = MIO_NAME (gfc_access) ((*proc)->access, access_types);

  /* IO the NON_OVERRIDABLE/DEFERRED combination.  */
  gcc_assert (!((*proc)->deferred && (*proc)->non_overridable));
  overriding_flag = ((*proc)->deferred << 1) | (*proc)->non_overridable;
  overriding_flag = mio_name (overriding_flag, binding_overriding);
  (*proc)->deferred = ((overriding_flag & 2) != 0);
  (*proc)->non_overridable = ((overriding_flag & 1) != 0);
  gcc_assert (!((*proc)->deferred && (*proc)->non_overridable));

  (*proc)->nopass = mio_name ((*proc)->nopass, binding_passing);
  (*proc)->is_generic = mio_name ((*proc)->is_generic, binding_generic);
  (*proc)->ppc = mio_name((*proc)->ppc, binding_ppc);

  mio_pool_string (&((*proc)->pass_arg));

  flag = (int) (*proc)->pass_arg_num;
  mio_integer (&flag);
  (*proc)->pass_arg_num = (unsigned) flag;

  if ((*proc)->is_generic)
    {
      gfc_tbp_generic* g;
      int iop;

      mio_lparen ();

      if (iomode == IO_OUTPUT)
	for (g = (*proc)->u.generic; g; g = g->next)
	  {
	    iop = (int) g->is_operator;
	    mio_integer (&iop);
	    mio_allocated_string (g->specific_st->name);
	  }
      else
	{
	  (*proc)->u.generic = NULL;
	  while (peek_atom () != ATOM_RPAREN)
	    {
	      gfc_symtree** sym_root;

	      g = gfc_get_tbp_generic ();
	      g->specific = NULL;

	      mio_integer (&iop);
	      g->is_operator = (bool) iop;

	      require_atom (ATOM_STRING);
	      sym_root = &current_f2k_derived->tb_sym_root;
	      g->specific_st = gfc_get_tbp_symtree (sym_root, atom_string);
	      free (atom_string);

	      g->next = (*proc)->u.generic;
	      (*proc)->u.generic = g;
	    }
	}

      mio_rparen ();
    }
  else if (!(*proc)->ppc)
    mio_symtree_ref (&(*proc)->u.specific);

  mio_rparen ();
}

/* Walker-callback function for this purpose.  */
static void
mio_typebound_symtree (gfc_symtree* st)
{
  if (iomode == IO_OUTPUT && !st->n.tb)
    return;

  if (iomode == IO_OUTPUT)
    {
      mio_lparen ();
      mio_allocated_string (st->name);
    }
  /* For IO_INPUT, the above is done in mio_f2k_derived.  */

  mio_typebound_proc (&st->n.tb);
  mio_rparen ();
}

/* IO a full symtree (in all depth).  */
static void
mio_full_typebound_tree (gfc_symtree** root)
{
  mio_lparen ();

  if (iomode == IO_OUTPUT)
    gfc_traverse_symtree (*root, &mio_typebound_symtree);
  else
    {
      while (peek_atom () == ATOM_LPAREN)
	{
	  gfc_symtree* st;

	  mio_lparen ();

	  require_atom (ATOM_STRING);
	  st = gfc_get_tbp_symtree (root, atom_string);
	  free (atom_string);

	  mio_typebound_symtree (st);
	}
    }

  mio_rparen ();
}

static void
mio_finalizer (gfc_finalizer **f)
{
  if (iomode == IO_OUTPUT)
    {
      gcc_assert (*f);
      gcc_assert ((*f)->proc_tree); /* Should already be resolved.  */
      mio_symtree_ref (&(*f)->proc_tree);
    }
  else
    {
      *f = gfc_get_finalizer ();
      (*f)->where = gfc_current_locus; /* Value should not matter.  */
      (*f)->next = NULL;

      mio_symtree_ref (&(*f)->proc_tree);
      (*f)->proc_sym = NULL;
    }
}

static void
mio_f2k_derived (gfc_namespace *f2k)
{
  current_f2k_derived = f2k;

  /* Handle the list of finalizer procedures.  */
  mio_lparen ();
  if (iomode == IO_OUTPUT)
    {
      gfc_finalizer *f;
      for (f = f2k->finalizers; f; f = f->next)
	mio_finalizer (&f);
    }
  else
    {
      f2k->finalizers = NULL;
      while (peek_atom () != ATOM_RPAREN)
	{
	  gfc_finalizer *cur = NULL;
	  mio_finalizer (&cur);
	  cur->next = f2k->finalizers;
	  f2k->finalizers = cur;
	}
    }
  mio_rparen ();

  /* Handle type-bound procedures.  */
  mio_full_typebound_tree (&f2k->tb_sym_root);

  /* Type-bound user operators.  */
  mio_full_typebound_tree (&f2k->tb_uop_root);

  /* Type-bound intrinsic operators.  */
  mio_lparen ();
  if (iomode == IO_OUTPUT)
    {
      int op;
      for (op = GFC_INTRINSIC_BEGIN; op != GFC_INTRINSIC_END; ++op)
	{
	  gfc_intrinsic_op realop;

	  if (op == INTRINSIC_USER || !f2k->tb_op[op])
	    continue;

	  mio_lparen ();
	  realop = (gfc_intrinsic_op) op;
	  mio_intrinsic_op (&realop);
	  mio_typebound_proc (&f2k->tb_op[op]);
	  mio_rparen ();
	}
    }
  else
    while (peek_atom () != ATOM_RPAREN)
      {
	gfc_intrinsic_op op = GFC_INTRINSIC_BEGIN; /* Silence GCC.  */

	mio_lparen ();
	mio_intrinsic_op (&op);
	mio_typebound_proc (&f2k->tb_op[op]);
	mio_rparen ();
      }
  mio_rparen ();
}

static void
mio_full_f2k_derived (gfc_symbol *sym)
{
  mio_lparen ();

  if (iomode == IO_OUTPUT)
    {
      if (sym->f2k_derived)
	mio_f2k_derived (sym->f2k_derived);
    }
  else
    {
      if (peek_atom () != ATOM_RPAREN)
	{
	  gfc_namespace *ns;

	  sym->f2k_derived = gfc_get_namespace (NULL, 0);

	  /* PDT templates make use of the mechanisms for formal args
	     and so the parameter symbols are stored in the formal
	     namespace.  Transfer the sym_root to f2k_derived and then
	     free the formal namespace since it is uneeded.  */
	  if (sym->attr.pdt_template && sym->formal && sym->formal->sym)
	    {
	      ns = sym->formal->sym->ns;
	      sym->f2k_derived->sym_root = ns->sym_root;
	      ns->sym_root = NULL;
	      ns->refs++;
	      gfc_free_namespace (ns);
	      ns = NULL;
	    }

	  mio_f2k_derived (sym->f2k_derived);
	}
      else
	gcc_assert (!sym->f2k_derived);
    }

  mio_rparen ();
}

static const mstring omp_declare_simd_clauses[] =
{
    minit ("INBRANCH", 0),
    minit ("NOTINBRANCH", 1),
    minit ("SIMDLEN", 2),
    minit ("UNIFORM", 3),
    minit ("LINEAR", 4),
    minit ("ALIGNED", 5),
    minit ("LINEAR_REF", 33),
    minit ("LINEAR_VAL", 34),
    minit ("LINEAR_UVAL", 35),
    minit (NULL, -1)
};

/* Handle !$omp declare simd.  */

static void
mio_omp_declare_simd (gfc_namespace *ns, gfc_omp_declare_simd **odsp)
{
  if (iomode == IO_OUTPUT)
    {
      if (*odsp == NULL)
	return;
    }
  else if (peek_atom () != ATOM_LPAREN)
    return;

  gfc_omp_declare_simd *ods = *odsp;

  mio_lparen ();
  if (iomode == IO_OUTPUT)
    {
      write_atom (ATOM_NAME, "OMP_DECLARE_SIMD");
      if (ods->clauses)
	{
	  gfc_omp_namelist *n;

	  if (ods->clauses->inbranch)
	    mio_name (0, omp_declare_simd_clauses);
	  if (ods->clauses->notinbranch)
	    mio_name (1, omp_declare_simd_clauses);
	  if (ods->clauses->simdlen_expr)
	    {
	      mio_name (2, omp_declare_simd_clauses);
	      mio_expr (&ods->clauses->simdlen_expr);
	    }
	  for (n = ods->clauses->lists[OMP_LIST_UNIFORM]; n; n = n->next)
	    {
	      mio_name (3, omp_declare_simd_clauses);
	      mio_symbol_ref (&n->sym);
	    }
	  for (n = ods->clauses->lists[OMP_LIST_LINEAR]; n; n = n->next)
	    {
	      if (n->u.linear.op == OMP_LINEAR_DEFAULT)
		mio_name (4, omp_declare_simd_clauses);
	      else
		mio_name (32 + n->u.linear.op, omp_declare_simd_clauses);
	      mio_symbol_ref (&n->sym);
	      mio_expr (&n->expr);
	    }
	  for (n = ods->clauses->lists[OMP_LIST_ALIGNED]; n; n = n->next)
	    {
	      mio_name (5, omp_declare_simd_clauses);
	      mio_symbol_ref (&n->sym);
	      mio_expr (&n->expr);
	    }
	}
    }
  else
    {
      gfc_omp_namelist **ptrs[3] = { NULL, NULL, NULL };

      require_atom (ATOM_NAME);
      *odsp = ods = gfc_get_omp_declare_simd ();
      ods->where = gfc_current_locus;
      ods->proc_name = ns->proc_name;
      if (peek_atom () == ATOM_NAME)
	{
	  ods->clauses = gfc_get_omp_clauses ();
	  ptrs[0] = &ods->clauses->lists[OMP_LIST_UNIFORM];
	  ptrs[1] = &ods->clauses->lists[OMP_LIST_LINEAR];
	  ptrs[2] = &ods->clauses->lists[OMP_LIST_ALIGNED];
	}
      while (peek_atom () == ATOM_NAME)
	{
	  gfc_omp_namelist *n;
	  int t = mio_name (0, omp_declare_simd_clauses);

	  switch (t)
	    {
	    case 0: ods->clauses->inbranch = true; break;
	    case 1: ods->clauses->notinbranch = true; break;
	    case 2: mio_expr (&ods->clauses->simdlen_expr); break;
	    case 3:
	    case 4:
	    case 5:
	      *ptrs[t - 3] = n = gfc_get_omp_namelist ();
	    finish_namelist:
	      n->where = gfc_current_locus;
	      ptrs[t - 3] = &n->next;
	      mio_symbol_ref (&n->sym);
	      if (t != 3)
		mio_expr (&n->expr);
	      break;
	    case 33:
	    case 34:
	    case 35:
	      *ptrs[1] = n = gfc_get_omp_namelist ();
	      n->u.linear.op = (enum gfc_omp_linear_op) (t - 32);
	      t = 4;
	      goto finish_namelist;
	    }
	}
    }

  mio_omp_declare_simd (ns, &ods->next);

  mio_rparen ();
}


static const mstring omp_declare_reduction_stmt[] =
{
    minit ("ASSIGN", 0),
    minit ("CALL", 1),
    minit (NULL, -1)
};


static void
mio_omp_udr_expr (gfc_omp_udr *udr, gfc_symbol **sym1, gfc_symbol **sym2,
		  gfc_namespace *ns, bool is_initializer)
{
  if (iomode == IO_OUTPUT)
    {
      if ((*sym1)->module == NULL)
	{
	  (*sym1)->module = module_name;
	  (*sym2)->module = module_name;
	}
      mio_symbol_ref (sym1);
      mio_symbol_ref (sym2);
      if (ns->code->op == EXEC_ASSIGN)
	{
	  mio_name (0, omp_declare_reduction_stmt);
	  mio_expr (&ns->code->expr1);
	  mio_expr (&ns->code->expr2);
	}
      else
	{
	  int flag;
	  mio_name (1, omp_declare_reduction_stmt);
	  mio_symtree_ref (&ns->code->symtree);
	  mio_actual_arglist (&ns->code->ext.actual, false);

	  flag = ns->code->resolved_isym != NULL;
	  mio_integer (&flag);
	  if (flag)
	    write_atom (ATOM_STRING, ns->code->resolved_isym->name);
	  else
	    mio_symbol_ref (&ns->code->resolved_sym);
	}
    }
  else
    {
      pointer_info *p1 = mio_symbol_ref (sym1);
      pointer_info *p2 = mio_symbol_ref (sym2);
      gfc_symbol *sym;
      gcc_assert (p1->u.rsym.ns == p2->u.rsym.ns);
      gcc_assert (p1->u.rsym.sym == NULL);
      /* Add hidden symbols to the symtree.  */
      pointer_info *q = get_integer (p1->u.rsym.ns);
      q->u.pointer = (void *) ns;
      sym = gfc_new_symbol (is_initializer ? "omp_priv" : "omp_out", ns);
      sym->ts = udr->ts;
      sym->module = gfc_get_string ("%s", p1->u.rsym.module);
      associate_integer_pointer (p1, sym);
      sym->attr.omp_udr_artificial_var = 1;
      gcc_assert (p2->u.rsym.sym == NULL);
      sym = gfc_new_symbol (is_initializer ? "omp_orig" : "omp_in", ns);
      sym->ts = udr->ts;
      sym->module = gfc_get_string ("%s", p2->u.rsym.module);
      associate_integer_pointer (p2, sym);
      sym->attr.omp_udr_artificial_var = 1;
      if (mio_name (0, omp_declare_reduction_stmt) == 0)
	{
	  ns->code = gfc_get_code (EXEC_ASSIGN);
	  mio_expr (&ns->code->expr1);
	  mio_expr (&ns->code->expr2);
	}
      else
	{
	  int flag;
	  ns->code = gfc_get_code (EXEC_CALL);
	  mio_symtree_ref (&ns->code->symtree);
	  mio_actual_arglist (&ns->code->ext.actual, false);

	  mio_integer (&flag);
	  if (flag)
	    {
	      require_atom (ATOM_STRING);
	      ns->code->resolved_isym = gfc_find_subroutine (atom_string);
	      free (atom_string);
	    }
	  else
	    mio_symbol_ref (&ns->code->resolved_sym);
	}
      ns->code->loc = gfc_current_locus;
      ns->omp_udr_ns = 1;
    }
}


/* Unlike most other routines, the address of the symbol node is already
   fixed on input and the name/module has already been filled in.
   If you update the symbol format here, don't forget to update read_module
   as well (look for "seek to the symbol's component list").   */

static void
mio_symbol (gfc_symbol *sym)
{
  int intmod = INTMOD_NONE;

  mio_lparen ();

  mio_symbol_attribute (&sym->attr);

  if (sym->attr.pdt_type)
    sym->name = gfc_dt_upper_string (sym->name);

  /* Note that components are always saved, even if they are supposed
     to be private.  Component access is checked during searching.  */
  mio_component_list (&sym->components, sym->attr.vtype);
  if (sym->components != NULL)
    sym->component_access
      = MIO_NAME (gfc_access) (sym->component_access, access_types);

  mio_typespec (&sym->ts);
  if (sym->ts.type == BT_CLASS)
    sym->attr.class_ok = 1;

  if (iomode == IO_OUTPUT)
    mio_namespace_ref (&sym->formal_ns);
  else
    {
      mio_namespace_ref (&sym->formal_ns);
      if (sym->formal_ns)
	sym->formal_ns->proc_name = sym;
    }

  /* Save/restore common block links.  */
  mio_symbol_ref (&sym->common_next);

  mio_formal_arglist (&sym->formal);

  if (sym->attr.flavor == FL_PARAMETER)
    mio_expr (&sym->value);

  mio_array_spec (&sym->as);

  mio_symbol_ref (&sym->result);

  if (sym->attr.cray_pointee)
    mio_symbol_ref (&sym->cp_pointer);

  /* Load/save the f2k_derived namespace of a derived-type symbol.  */
  mio_full_f2k_derived (sym);

  /* PDT types store the symbol specification list here. */
  mio_actual_arglist (&sym->param_list, true);

  mio_namelist (sym);

  /* Add the fields that say whether this is from an intrinsic module,
     and if so, what symbol it is within the module.  */
/*   mio_integer (&(sym->from_intmod)); */
  if (iomode == IO_OUTPUT)
    {
      intmod = sym->from_intmod;
      mio_integer (&intmod);
    }
  else
    {
      mio_integer (&intmod);
      if (current_intmod)
	sym->from_intmod = current_intmod;
      else
	sym->from_intmod = (intmod_id) intmod;
    }

  mio_integer (&(sym->intmod_sym_id));

  if (gfc_fl_struct (sym->attr.flavor))
    mio_integer (&(sym->hash_value));

  if (sym->formal_ns
      && sym->formal_ns->proc_name == sym
      && sym->formal_ns->entries == NULL)
    mio_omp_declare_simd (sym->formal_ns, &sym->formal_ns->omp_declare_simd);

  mio_rparen ();
}


/************************* Top level subroutines *************************/

/* A recursive function to look for a specific symbol by name and by
   module.  Whilst several symtrees might point to one symbol, its
   is sufficient for the purposes here than one exist.  Note that
   generic interfaces are distinguished as are symbols that have been
   renamed in another module.  */
static gfc_symtree *
find_symbol (gfc_symtree *st, const char *name,
	     const char *module, int generic)
{
  int c;
  gfc_symtree *retval, *s;

  if (st == NULL || st->n.sym == NULL)
    return NULL;

  c = strcmp (name, st->n.sym->name);
  if (c == 0 && st->n.sym->module
	     && strcmp (module, st->n.sym->module) == 0
	     && !check_unique_name (st->name))
    {
      s = gfc_find_symtree (gfc_current_ns->sym_root, name);

      /* Detect symbols that are renamed by use association in another
	 module by the absence of a symtree and null attr.use_rename,
	 since the latter is not transmitted in the module file.  */
      if (((!generic && !st->n.sym->attr.generic)
		|| (generic && st->n.sym->attr.generic))
	    && !(s == NULL && !st->n.sym->attr.use_rename))
	return st;
    }

  retval = find_symbol (st->left, name, module, generic);

  if (retval == NULL)
    retval = find_symbol (st->right, name, module, generic);

  return retval;
}


/* Skip a list between balanced left and right parens.
   By setting NEST_LEVEL one assumes that a number of NEST_LEVEL opening parens
   have been already parsed by hand, and the remaining of the content is to be
   skipped here.  The default value is 0 (balanced parens).  */

static void
skip_list (int nest_level = 0)
{
  int level;

  level = nest_level;
  do
    {
      switch (parse_atom ())
	{
	case ATOM_LPAREN:
	  level++;
	  break;

	case ATOM_RPAREN:
	  level--;
	  break;

	case ATOM_STRING:
	  free (atom_string);
	  break;

	case ATOM_NAME:
	case ATOM_INTEGER:
	  break;
	}
    }
  while (level > 0);
}


/* Load operator interfaces from the module.  Interfaces are unusual
   in that they attach themselves to existing symbols.  */

static void
load_operator_interfaces (void)
{
  const char *p;
  /* "module" must be large enough for the case of submodules in which the name
     has the form module.submodule */
  char name[GFC_MAX_SYMBOL_LEN + 1], module[2 * GFC_MAX_SYMBOL_LEN + 2];
  gfc_user_op *uop;
  pointer_info *pi = NULL;
  int n, i;

  mio_lparen ();

  while (peek_atom () != ATOM_RPAREN)
    {
      mio_lparen ();

      mio_internal_string (name);
      mio_internal_string (module);

      n = number_use_names (name, true);
      n = n ? n : 1;

      for (i = 1; i <= n; i++)
	{
	  /* Decide if we need to load this one or not.  */
	  p = find_use_name_n (name, &i, true);

	  if (p == NULL)
	    {
	      while (parse_atom () != ATOM_RPAREN);
	      continue;
	    }

	  if (i == 1)
	    {
	      uop = gfc_get_uop (p);
	      pi = mio_interface_rest (&uop->op);
	    }
	  else
	    {
	      if (gfc_find_uop (p, NULL))
		continue;
	      uop = gfc_get_uop (p);
	      uop->op = gfc_get_interface ();
	      uop->op->where = gfc_current_locus;
	      add_fixup (pi->integer, &uop->op->sym);
	    }
	}
    }

  mio_rparen ();
}


/* Load interfaces from the module.  Interfaces are unusual in that
   they attach themselves to existing symbols.  */

static void
load_generic_interfaces (void)
{
  const char *p;
  /* "module" must be large enough for the case of submodules in which the name
     has the form module.submodule */
  char name[GFC_MAX_SYMBOL_LEN + 1], module[2 * GFC_MAX_SYMBOL_LEN + 2];
  gfc_symbol *sym;
  gfc_interface *generic = NULL, *gen = NULL;
  int n, i, renamed;
  bool ambiguous_set = false;

  mio_lparen ();

  while (peek_atom () != ATOM_RPAREN)
    {
      mio_lparen ();

      mio_internal_string (name);
      mio_internal_string (module);

      n = number_use_names (name, false);
      renamed = n ? 1 : 0;
      n = n ? n : 1;

      for (i = 1; i <= n; i++)
	{
	  gfc_symtree *st;
	  /* Decide if we need to load this one or not.  */
	  p = find_use_name_n (name, &i, false);

	  if (!p || gfc_find_symbol (p, NULL, 0, &sym))
	    {
	      /* Skip the specific names for these cases.  */
	      while (i == 1 && parse_atom () != ATOM_RPAREN);

	      continue;
	    }

	  st = find_symbol (gfc_current_ns->sym_root,
			    name, module_name, 1);

	  /* If the symbol exists already and is being USEd without being
	     in an ONLY clause, do not load a new symtree(11.3.2).  */
	  if (!only_flag && st)
	    sym = st->n.sym;

	  if (!sym)
	    {
	      if (st)
		{
		  sym = st->n.sym;
		  if (strcmp (st->name, p) != 0)
		    {
	              st = gfc_new_symtree (&gfc_current_ns->sym_root, p);
		      st->n.sym = sym;
		      sym->refs++;
		    }
		}

	      /* Since we haven't found a valid generic interface, we had
		 better make one.  */
	      if (!sym)
		{
		  gfc_get_symbol (p, NULL, &sym);
		  sym->name = gfc_get_string ("%s", name);
		  sym->module = module_name;
		  sym->attr.flavor = FL_PROCEDURE;
		  sym->attr.generic = 1;
		  sym->attr.use_assoc = 1;
		}
	    }
	  else
	    {
	      /* Unless sym is a generic interface, this reference
		 is ambiguous.  */
	      if (st == NULL)
	        st = gfc_find_symtree (gfc_current_ns->sym_root, p);

	      sym = st->n.sym;

	      if (st && !sym->attr.generic
		     && !st->ambiguous
		     && sym->module
		     && strcmp (module, sym->module))
		{
		  ambiguous_set = true;
		  st->ambiguous = 1;
		}
	    }

	  sym->attr.use_only = only_flag;
	  sym->attr.use_rename = renamed;

	  if (i == 1)
	    {
	      mio_interface_rest (&sym->generic);
	      generic = sym->generic;
	    }
	  else if (!sym->generic)
	    {
	      sym->generic = generic;
	      sym->attr.generic_copy = 1;
	    }

	  /* If a procedure that is not generic has generic interfaces
	     that include itself, it is generic! We need to take care
	     to retain symbols ambiguous that were already so.  */
	  if (sym->attr.use_assoc
		&& !sym->attr.generic
		&& sym->attr.flavor == FL_PROCEDURE)
	    {
	      for (gen = generic; gen; gen = gen->next)
		{
		  if (gen->sym == sym)
		    {
		      sym->attr.generic = 1;
		      if (ambiguous_set)
		        st->ambiguous = 0;
		      break;
		    }
		}
	    }

	}
    }

  mio_rparen ();
}


/* Load common blocks.  */

static void
load_commons (void)
{
  char name[GFC_MAX_SYMBOL_LEN + 1];
  gfc_common_head *p;

  mio_lparen ();

  while (peek_atom () != ATOM_RPAREN)
    {
      int flags = 0;
      char* label;
      mio_lparen ();
      mio_internal_string (name);

      p = gfc_get_common (name, 1);

      mio_symbol_ref (&p->head);
      mio_integer (&flags);
      if (flags & 1)
	p->saved = 1;
      if (flags & 2)
	p->threadprivate = 1;
      p->omp_device_type = (gfc_omp_device_type) ((flags >> 2) & 3);
      p->use_assoc = 1;

      /* Get whether this was a bind(c) common or not.  */
      mio_integer (&p->is_bind_c);
      /* Get the binding label.  */
      label = read_string ();
      if (strlen (label))
	p->binding_label = IDENTIFIER_POINTER (get_identifier (label));
      XDELETEVEC (label);

      mio_rparen ();
    }

  mio_rparen ();
}


/* Load equivalences.  The flag in_load_equiv informs mio_expr_ref of this
   so that unused variables are not loaded and so that the expression can
   be safely freed.  */

static void
load_equiv (void)
{
  gfc_equiv *head, *tail, *end, *eq, *equiv;
  bool duplicate;

  mio_lparen ();
  in_load_equiv = true;

  end = gfc_current_ns->equiv;
  while (end != NULL && end->next != NULL)
    end = end->next;

  while (peek_atom () != ATOM_RPAREN) {
    mio_lparen ();
    head = tail = NULL;

    while(peek_atom () != ATOM_RPAREN)
      {
	if (head == NULL)
	  head = tail = gfc_get_equiv ();
	else
	  {
	    tail->eq = gfc_get_equiv ();
	    tail = tail->eq;
	  }

	mio_pool_string (&tail->module);
	mio_expr (&tail->expr);
      }

    /* Check for duplicate equivalences being loaded from different modules */
    duplicate = false;
    for (equiv = gfc_current_ns->equiv; equiv; equiv = equiv->next)
      {
	if (equiv->module && head->module
	    && strcmp (equiv->module, head->module) == 0)
	  {
	    duplicate = true;
	    break;
	  }
      }

    if (duplicate)
      {
	for (eq = head; eq; eq = head)
	  {
	    head = eq->eq;
	    gfc_free_expr (eq->expr);
	    free (eq);
	  }
      }

    if (end == NULL)
      gfc_current_ns->equiv = head;
    else
      end->next = head;

    if (head != NULL)
      end = head;

    mio_rparen ();
  }

  mio_rparen ();
  in_load_equiv = false;
}


/* This function loads OpenMP user defined reductions.  */
static void
load_omp_udrs (void)
{
  mio_lparen ();
  while (peek_atom () != ATOM_RPAREN)
    {
      const char *name = NULL, *newname;
      char *altname;
      gfc_typespec ts;
      gfc_symtree *st;
      gfc_omp_reduction_op rop = OMP_REDUCTION_USER;

      mio_lparen ();
      mio_pool_string (&name);
      gfc_clear_ts (&ts);
      mio_typespec (&ts);
      if (startswith (name, "operator "))
	{
	  const char *p = name + sizeof ("operator ") - 1;
	  if (strcmp (p, "+") == 0)
	    rop = OMP_REDUCTION_PLUS;
	  else if (strcmp (p, "*") == 0)
	    rop = OMP_REDUCTION_TIMES;
	  else if (strcmp (p, "-") == 0)
	    rop = OMP_REDUCTION_MINUS;
	  else if (strcmp (p, ".and.") == 0)
	    rop = OMP_REDUCTION_AND;
	  else if (strcmp (p, ".or.") == 0)
	    rop = OMP_REDUCTION_OR;
	  else if (strcmp (p, ".eqv.") == 0)
	    rop = OMP_REDUCTION_EQV;
	  else if (strcmp (p, ".neqv.") == 0)
	    rop = OMP_REDUCTION_NEQV;
	}
      altname = NULL;
      if (rop == OMP_REDUCTION_USER && name[0] == '.')
	{
	  size_t len = strlen (name + 1);
	  altname = XALLOCAVEC (char, len);
	  gcc_assert (name[len] == '.');
	  memcpy (altname, name + 1, len - 1);
	  altname[len - 1] = '\0';
	}
      newname = name;
      if (rop == OMP_REDUCTION_USER)
	newname = find_use_name (altname ? altname : name, !!altname);
      else if (only_flag && find_use_operator ((gfc_intrinsic_op) rop) == NULL)
	newname = NULL;
      if (newname == NULL)
	{
	  skip_list (1);
	  continue;
	}
      if (altname && newname != altname)
	{
	  size_t len = strlen (newname);
	  altname = XALLOCAVEC (char, len + 3);
	  altname[0] = '.';
	  memcpy (altname + 1, newname, len);
	  altname[len + 1] = '.';
	  altname[len + 2] = '\0';
	  name = gfc_get_string ("%s", altname);
	}
      st = gfc_find_symtree (gfc_current_ns->omp_udr_root, name);
      gfc_omp_udr *udr = gfc_omp_udr_find (st, &ts);
      if (udr)
	{
	  require_atom (ATOM_INTEGER);
	  pointer_info *p = get_integer (atom_int);
	  if (strcmp (p->u.rsym.module, udr->omp_out->module))
	    {
	      gfc_error ("Ambiguous !$OMP DECLARE REDUCTION from "
			 "module %s at %L",
			 p->u.rsym.module, &gfc_current_locus);
	      gfc_error ("Previous !$OMP DECLARE REDUCTION from module "
			 "%s at %L",
			 udr->omp_out->module, &udr->where);
	    }
	  skip_list (1);
	  continue;
	}
      udr = gfc_get_omp_udr ();
      udr->name = name;
      udr->rop = rop;
      udr->ts = ts;
      udr->where = gfc_current_locus;
      udr->combiner_ns = gfc_get_namespace (gfc_current_ns, 1);
      udr->combiner_ns->proc_name = gfc_current_ns->proc_name;
      mio_omp_udr_expr (udr, &udr->omp_out, &udr->omp_in, udr->combiner_ns,
			false);
      if (peek_atom () != ATOM_RPAREN)
	{
	  udr->initializer_ns = gfc_get_namespace (gfc_current_ns, 1);
	  udr->initializer_ns->proc_name = gfc_current_ns->proc_name;
	  mio_omp_udr_expr (udr, &udr->omp_priv, &udr->omp_orig,
			    udr->initializer_ns, true);
	}
      if (st)
	{
	  udr->next = st->n.omp_udr;
	  st->n.omp_udr = udr;
	}
      else
	{
	  st = gfc_new_symtree (&gfc_current_ns->omp_udr_root, name);
	  st->n.omp_udr = udr;
	}
      mio_rparen ();
    }
  mio_rparen ();
}


/* Recursive function to traverse the pointer_info tree and load a
   needed symbol.  We return nonzero if we load a symbol and stop the
   traversal, because the act of loading can alter the tree.  */

static int
load_needed (pointer_info *p)
{
  gfc_namespace *ns;
  pointer_info *q;
  gfc_symbol *sym;
  int rv;

  rv = 0;
  if (p == NULL)
    return rv;

  rv |= load_needed (p->left);
  rv |= load_needed (p->right);

  if (p->type != P_SYMBOL || p->u.rsym.state != NEEDED)
    return rv;

  p->u.rsym.state = USED;

  set_module_locus (&p->u.rsym.where);

  sym = p->u.rsym.sym;
  if (sym == NULL)
    {
      q = get_integer (p->u.rsym.ns);

      ns = (gfc_namespace *) q->u.pointer;
      if (ns == NULL)
	{
	  /* Create an interface namespace if necessary.  These are
	     the namespaces that hold the formal parameters of module
	     procedures.  */

	  ns = gfc_get_namespace (NULL, 0);
	  associate_integer_pointer (q, ns);
	}

      /* Use the module sym as 'proc_name' so that gfc_get_symbol_decl
	 doesn't go pear-shaped if the symbol is used.  */
      if (!ns->proc_name)
	gfc_find_symbol (p->u.rsym.module, gfc_current_ns,
				 1, &ns->proc_name);

      sym = gfc_new_symbol (p->u.rsym.true_name, ns);
      sym->name = gfc_dt_lower_string (p->u.rsym.true_name);
      sym->module = gfc_get_string ("%s", p->u.rsym.module);
      if (p->u.rsym.binding_label)
	sym->binding_label = IDENTIFIER_POINTER (get_identifier
						 (p->u.rsym.binding_label));

      associate_integer_pointer (p, sym);
    }

  mio_symbol (sym);
  sym->attr.use_assoc = 1;

  /* Unliked derived types, a STRUCTURE may share names with other symbols.
     We greedily converted the symbol name to lowercase before we knew its
     type, so now we must fix it. */
  if (sym->attr.flavor == FL_STRUCT)
    sym->name = gfc_dt_upper_string (sym->name);

  /* Mark as only or rename for later diagnosis for explicitly imported
     but not used warnings; don't mark internal symbols such as __vtab,
     __def_init etc. Only mark them if they have been explicitly loaded.  */

  if (only_flag && sym->name[0] != '_' && sym->name[1] != '_')
    {
      gfc_use_rename *u;

      /* Search the use/rename list for the variable; if the variable is
	 found, mark it.  */
      for (u = gfc_rename_list; u; u = u->next)
	{
	  if (strcmp (u->use_name, sym->name) == 0)
	    {
	      sym->attr.use_only = 1;
	      break;
	    }
	}
    }

  if (p->u.rsym.renamed)
    sym->attr.use_rename = 1;

  return 1;
}


/* Recursive function for cleaning up things after a module has been read.  */

static void
read_cleanup (pointer_info *p)
{
  gfc_symtree *st;
  pointer_info *q;

  if (p == NULL)
    return;

  read_cleanup (p->left);
  read_cleanup (p->right);

  if (p->type == P_SYMBOL && p->u.rsym.state == USED && !p->u.rsym.referenced)
    {
      gfc_namespace *ns;
      /* Add hidden symbols to the symtree.  */
      q = get_integer (p->u.rsym.ns);
      ns = (gfc_namespace *) q->u.pointer;

      if (!p->u.rsym.sym->attr.vtype
	    && !p->u.rsym.sym->attr.vtab)
	st = gfc_get_unique_symtree (ns);
      else
	{
	  /* There is no reason to use 'unique_symtrees' for vtabs or
	     vtypes - their name is fine for a symtree and reduces the
	     namespace pollution.  */
	  st = gfc_find_symtree (ns->sym_root, p->u.rsym.sym->name);
	  if (!st)
	    st = gfc_new_symtree (&ns->sym_root, p->u.rsym.sym->name);
	}

      st->n.sym = p->u.rsym.sym;
      st->n.sym->refs++;

      /* Fixup any symtree references.  */
      p->u.rsym.symtree = st;
      resolve_fixups (p->u.rsym.stfixup, st);
      p->u.rsym.stfixup = NULL;
    }

  /* Free unused symbols.  */
  if (p->type == P_SYMBOL && p->u.rsym.state == UNUSED)
    gfc_free_symbol (p->u.rsym.sym);
}


/* It is not quite enough to check for ambiguity in the symbols by
   the loaded symbol and the new symbol not being identical.  */
static bool
check_for_ambiguous (gfc_symtree *st, pointer_info *info)
{
  gfc_symbol *rsym;
  module_locus locus;
  symbol_attribute attr;
  gfc_symbol *st_sym;

  if (gfc_current_ns->proc_name && st->name == gfc_current_ns->proc_name->name)
    {
      gfc_error ("%qs of module %qs, imported at %C, is also the name of the "
		 "current program unit", st->name, module_name);
      return true;
    }

  st_sym = st->n.sym;
  rsym = info->u.rsym.sym;
  if (st_sym == rsym)
    return false;

  if (st_sym->attr.vtab || st_sym->attr.vtype)
    return false;

  /* If the existing symbol is generic from a different module and
     the new symbol is generic there can be no ambiguity.  */
  if (st_sym->attr.generic
	&& st_sym->module
	&& st_sym->module != module_name)
    {
      /* The new symbol's attributes have not yet been read.  Since
	 we need attr.generic, read it directly.  */
      get_module_locus (&locus);
      set_module_locus (&info->u.rsym.where);
      mio_lparen ();
      attr.generic = 0;
      mio_symbol_attribute (&attr);
      set_module_locus (&locus);
      if (attr.generic)
	return false;
    }

  return true;
}


/* Read a module file.  */

static void
read_module (void)
{
  module_locus operator_interfaces, user_operators, omp_udrs;
  const char *p;
  char name[GFC_MAX_SYMBOL_LEN + 1];
  int i;
  /* Workaround -Wmaybe-uninitialized false positive during
     profiledbootstrap by initializing them.  */
  int ambiguous = 0, j, nuse, symbol = 0;
  pointer_info *info, *q;
  gfc_use_rename *u = NULL;
  gfc_symtree *st;
  gfc_symbol *sym;

  get_module_locus (&operator_interfaces);	/* Skip these for now.  */
  skip_list ();

  get_module_locus (&user_operators);
  skip_list ();
  skip_list ();

  /* Skip commons and equivalences for now.  */
  skip_list ();
  skip_list ();

  /* Skip OpenMP UDRs.  */
  get_module_locus (&omp_udrs);
  skip_list ();

  mio_lparen ();

  /* Create the fixup nodes for all the symbols.  */

  while (peek_atom () != ATOM_RPAREN)
    {
      char* bind_label;
      require_atom (ATOM_INTEGER);
      info = get_integer (atom_int);

      info->type = P_SYMBOL;
      info->u.rsym.state = UNUSED;

      info->u.rsym.true_name = read_string ();
      info->u.rsym.module = read_string ();
      bind_label = read_string ();
      if (strlen (bind_label))
	info->u.rsym.binding_label = bind_label;
      else
	XDELETEVEC (bind_label);

      require_atom (ATOM_INTEGER);
      info->u.rsym.ns = atom_int;

      get_module_locus (&info->u.rsym.where);

      /* See if the symbol has already been loaded by a previous module.
	 If so, we reference the existing symbol and prevent it from
	 being loaded again.  This should not happen if the symbol being
	 read is an index for an assumed shape dummy array (ns != 1).  */

      sym = find_true_name (info->u.rsym.true_name, info->u.rsym.module);

      if (sym == NULL
	  || (sym->attr.flavor == FL_VARIABLE && info->u.rsym.ns !=1))
	{
	  skip_list ();
	  continue;
	}

      info->u.rsym.state = USED;
      info->u.rsym.sym = sym;
      /* The current symbol has already been loaded, so we can avoid loading
	 it again.  However, if it is a derived type, some of its components
	 can be used in expressions in the module.  To avoid the module loading
	 failing, we need to associate the module's component pointer indexes
	 with the existing symbol's component pointers.  */
      if (gfc_fl_struct (sym->attr.flavor))
	{
	  gfc_component *c;

	  /* First seek to the symbol's component list.  */
	  mio_lparen (); /* symbol opening.  */
	  skip_list (); /* skip symbol attribute.  */

	  mio_lparen (); /* component list opening.  */
	  for (c = sym->components; c; c = c->next)
	    {
	      pointer_info *p;
	      const char *comp_name = NULL;
	      int n = 0;

	      mio_lparen (); /* component opening.  */
	      mio_integer (&n);
	      p = get_integer (n);
	      if (p->u.pointer == NULL)
		associate_integer_pointer (p, c);
	      mio_pool_string (&comp_name);
	      if (comp_name != c->name)
		{
		  gfc_fatal_error ("Mismatch in components of derived type "
				   "%qs from %qs at %C: expecting %qs, "
				   "but got %qs", sym->name, sym->module,
				   c->name, comp_name);
		}
	      skip_list (1); /* component end.  */
	    }
	  mio_rparen (); /* component list closing.  */

	  skip_list (1); /* symbol end.  */
	}
      else
	skip_list ();

      /* Some symbols do not have a namespace (eg. formal arguments),
	 so the automatic "unique symtree" mechanism must be suppressed
	 by marking them as referenced.  */
      q = get_integer (info->u.rsym.ns);
      if (q->u.pointer == NULL)
	{
	  info->u.rsym.referenced = 1;
	  continue;
	}
    }

  mio_rparen ();

  /* Parse the symtree lists.  This lets us mark which symbols need to
     be loaded.  Renaming is also done at this point by replacing the
     symtree name.  */

  mio_lparen ();

  while (peek_atom () != ATOM_RPAREN)
    {
      mio_internal_string (name);
      mio_integer (&ambiguous);
      mio_integer (&symbol);

      info = get_integer (symbol);

      /* See how many use names there are.  If none, go through the start
	 of the loop at least once.  */
      nuse = number_use_names (name, false);
      info->u.rsym.renamed = nuse ? 1 : 0;

      if (nuse == 0)
	nuse = 1;

      for (j = 1; j <= nuse; j++)
	{
	  /* Get the jth local name for this symbol.  */
	  p = find_use_name_n (name, &j, false);

	  if (p == NULL && strcmp (name, module_name) == 0)
	    p = name;

	  /* Exception: Always import vtabs & vtypes.  */
	  if (p == NULL && name[0] == '_'
	      && (startswith (name, "__vtab_")
		  || startswith (name, "__vtype_")))
	    p = name;

	  /* Skip symtree nodes not in an ONLY clause, unless there
	     is an existing symtree loaded from another USE statement.  */
	  if (p == NULL)
	    {
	      st = gfc_find_symtree (gfc_current_ns->sym_root, name);
	      if (st != NULL
		  && strcmp (st->n.sym->name, info->u.rsym.true_name) == 0
		  && st->n.sym->module != NULL
		  && strcmp (st->n.sym->module, info->u.rsym.module) == 0)
		{
		  info->u.rsym.symtree = st;
		  info->u.rsym.sym = st->n.sym;
		}
	      continue;
	    }

	  /* If a symbol of the same name and module exists already,
	     this symbol, which is not in an ONLY clause, must not be
	     added to the namespace(11.3.2).  Note that find_symbol
	     only returns the first occurrence that it finds.  */
	  if (!only_flag && !info->u.rsym.renamed
		&& strcmp (name, module_name) != 0
		&& find_symbol (gfc_current_ns->sym_root, name,
				module_name, 0))
	    continue;

	  st = gfc_find_symtree (gfc_current_ns->sym_root, p);

	  if (st != NULL
	      && !(st->n.sym && st->n.sym->attr.used_in_submodule))
	    {
	      /* Check for ambiguous symbols.  */
	      if (check_for_ambiguous (st, info))
		st->ambiguous = 1;
	      else
		info->u.rsym.symtree = st;
	    }
	  else
	    {
	      if (st)
		{
		  /* This symbol is host associated from a module in a
		     submodule.  Hide it with a unique symtree.  */
		  gfc_symtree *s = gfc_get_unique_symtree (gfc_current_ns);
		  s->n.sym = st->n.sym;
		  st->n.sym = NULL;
		}
	      else
		{
		  /* Create a symtree node in the current namespace for this
		     symbol.  */
		  st = check_unique_name (p)
		       ? gfc_get_unique_symtree (gfc_current_ns)
		       : gfc_new_symtree (&gfc_current_ns->sym_root, p);
		  st->ambiguous = ambiguous;
		}

	      sym = info->u.rsym.sym;

	      /* Create a symbol node if it doesn't already exist.  */
	      if (sym == NULL)
		{
		  info->u.rsym.sym = gfc_new_symbol (info->u.rsym.true_name,
						     gfc_current_ns);
		  info->u.rsym.sym->name = gfc_dt_lower_string (info->u.rsym.true_name);
		  sym = info->u.rsym.sym;
		  sym->module = gfc_get_string ("%s", info->u.rsym.module);

		  if (info->u.rsym.binding_label)
		    {
		      tree id = get_identifier (info->u.rsym.binding_label);
		      sym->binding_label = IDENTIFIER_POINTER (id);
		    }
		}

	      st->n.sym = sym;
	      st->n.sym->refs++;

	      if (strcmp (name, p) != 0)
		sym->attr.use_rename = 1;

	      if (name[0] != '_'
		  || (!startswith (name, "__vtab_")
		      && !startswith (name, "__vtype_")))
		sym->attr.use_only = only_flag;

	      /* Store the symtree pointing to this symbol.  */
	      info->u.rsym.symtree = st;

	      if (info->u.rsym.state == UNUSED)
		info->u.rsym.state = NEEDED;
	      info->u.rsym.referenced = 1;
	    }
	}
    }

  mio_rparen ();

  /* Load intrinsic operator interfaces.  */
  set_module_locus (&operator_interfaces);
  mio_lparen ();

  for (i = GFC_INTRINSIC_BEGIN; i != GFC_INTRINSIC_END; i++)
    {
      gfc_use_rename *u = NULL, *v = NULL;
      int j = i;

      if (i == INTRINSIC_USER)
	continue;

      if (only_flag)
	{
	  u = find_use_operator ((gfc_intrinsic_op) i);

	  /* F2018:10.1.5.5.1 requires same interpretation of old and new-style
	     relational operators.  Special handling for USE, ONLY.  */
	  switch (i)
	    {
	    case INTRINSIC_EQ:
	      j = INTRINSIC_EQ_OS;
	      break;
	    case INTRINSIC_EQ_OS:
	      j = INTRINSIC_EQ;
	      break;
	    case INTRINSIC_NE:
	      j = INTRINSIC_NE_OS;
	      break;
	    case INTRINSIC_NE_OS:
	      j = INTRINSIC_NE;
	      break;
	    case INTRINSIC_GT:
	      j = INTRINSIC_GT_OS;
	      break;
	    case INTRINSIC_GT_OS:
	      j = INTRINSIC_GT;
	      break;
	    case INTRINSIC_GE:
	      j = INTRINSIC_GE_OS;
	      break;
	    case INTRINSIC_GE_OS:
	      j = INTRINSIC_GE;
	      break;
	    case INTRINSIC_LT:
	      j = INTRINSIC_LT_OS;
	      break;
	    case INTRINSIC_LT_OS:
	      j = INTRINSIC_LT;
	      break;
	    case INTRINSIC_LE:
	      j = INTRINSIC_LE_OS;
	      break;
	    case INTRINSIC_LE_OS:
	      j = INTRINSIC_LE;
	      break;
	    default:
	      break;
	    }

	  if (j != i)
	    v = find_use_operator ((gfc_intrinsic_op) j);

	  if (u == NULL && v == NULL)
	    {
	      skip_list ();
	      continue;
	    }

	  if (u)
	    u->found = 1;
	  if (v)
	    v->found = 1;
	}

      mio_interface (&gfc_current_ns->op[i]);
      if (!gfc_current_ns->op[i] && !gfc_current_ns->op[j])
	{
	  if (u)
	    u->found = 0;
	  if (v)
	    v->found = 0;
	}
    }

  mio_rparen ();

  /* Load generic and user operator interfaces.  These must follow the
     loading of symtree because otherwise symbols can be marked as
     ambiguous.  */

  set_module_locus (&user_operators);

  load_operator_interfaces ();
  load_generic_interfaces ();

  load_commons ();
  load_equiv ();

  /* Load OpenMP user defined reductions.  */
  set_module_locus (&omp_udrs);
  load_omp_udrs ();

  /* At this point, we read those symbols that are needed but haven't
     been loaded yet.  If one symbol requires another, the other gets
     marked as NEEDED if its previous state was UNUSED.  */

  while (load_needed (pi_root));

  /* Make sure all elements of the rename-list were found in the module.  */

  for (u = gfc_rename_list; u; u = u->next)
    {
      if (u->found)
	continue;

      if (u->op == INTRINSIC_NONE)
	{
	  gfc_error ("Symbol %qs referenced at %L not found in module %qs",
		     u->use_name, &u->where, module_name);
	  continue;
	}

      if (u->op == INTRINSIC_USER)
	{
	  gfc_error ("User operator %qs referenced at %L not found "
		     "in module %qs", u->use_name, &u->where, module_name);
	  continue;
	}

      gfc_error ("Intrinsic operator %qs referenced at %L not found "
		 "in module %qs", gfc_op2string (u->op), &u->where,
		 module_name);
    }

  /* Clean up symbol nodes that were never loaded, create references
     to hidden symbols.  */

  read_cleanup (pi_root);
}


/* Given an access type that is specific to an entity and the default
   access, return nonzero if the entity is publicly accessible.  If the
   element is declared as PUBLIC, then it is public; if declared
   PRIVATE, then private, and otherwise it is public unless the default
   access in this context has been declared PRIVATE.  */

static bool dump_smod = false;

static bool
check_access (gfc_access specific_access, gfc_access default_access)
{
  if (dump_smod)
    return true;

  if (specific_access == ACCESS_PUBLIC)
    return TRUE;
  if (specific_access == ACCESS_PRIVATE)
    return FALSE;

  if (flag_module_private)
    return default_access == ACCESS_PUBLIC;
  else
    return default_access != ACCESS_PRIVATE;
}


bool
gfc_check_symbol_access (gfc_symbol *sym)
{
  if (sym->attr.vtab || sym->attr.vtype)
    return true;
  else
    return check_access (sym->attr.access, sym->ns->default_access);
}


/* A structure to remember which commons we've already written.  */

struct written_common
{
  BBT_HEADER(written_common);
  const char *name, *label;
};

static struct written_common *written_commons = NULL;

/* Comparison function used for balancing the binary tree.  */

static int
compare_written_commons (void *a1, void *b1)
{
  const char *aname = ((struct written_common *) a1)->name;
  const char *alabel = ((struct written_common *) a1)->label;
  const char *bname = ((struct written_common *) b1)->name;
  const char *blabel = ((struct written_common *) b1)->label;
  int c = strcmp (aname, bname);

  return (c != 0 ? c : strcmp (alabel, blabel));
}

/* Free a list of written commons.  */

static void
free_written_common (struct written_common *w)
{
  if (!w)
    return;

  if (w->left)
    free_written_common (w->left);
  if (w->right)
    free_written_common (w->right);

  free (w);
}

/* Write a common block to the module -- recursive helper function.  */

static void
write_common_0 (gfc_symtree *st, bool this_module)
{
  gfc_common_head *p;
  const char * name;
  int flags;
  const char *label;
  struct written_common *w;
  bool write_me = true;

  if (st == NULL)
    return;

  write_common_0 (st->left, this_module);

  /* We will write out the binding label, or "" if no label given.  */
  name = st->n.common->name;
  p = st->n.common;
  label = (p->is_bind_c && p->binding_label) ? p->binding_label : "";

  /* Check if we've already output this common.  */
  w = written_commons;
  while (w)
    {
      int c = strcmp (name, w->name);
      c = (c != 0 ? c : strcmp (label, w->label));
      if (c == 0)
	write_me = false;

      w = (c < 0) ? w->left : w->right;
    }

  if (this_module && p->use_assoc)
    write_me = false;

  if (write_me)
    {
      /* Write the common to the module.  */
      mio_lparen ();
      mio_pool_string (&name);

      mio_symbol_ref (&p->head);
      flags = p->saved ? 1 : 0;
      if (p->threadprivate)
	flags |= 2;
      flags |= p->omp_device_type << 2;
      mio_integer (&flags);

      /* Write out whether the common block is bind(c) or not.  */
      mio_integer (&(p->is_bind_c));

      mio_pool_string (&label);
      mio_rparen ();

      /* Record that we have written this common.  */
      w = XCNEW (struct written_common);
      w->name = p->name;
      w->label = label;
      gfc_insert_bbt (&written_commons, w, compare_written_commons);
    }

  write_common_0 (st->right, this_module);
}


/* Write a common, by initializing the list of written commons, calling
   the recursive function write_common_0() and cleaning up afterwards.  */

static void
write_common (gfc_symtree *st)
{
  written_commons = NULL;
  write_common_0 (st, true);
  write_common_0 (st, false);
  free_written_common (written_commons);
  written_commons = NULL;
}


/* Write the blank common block to the module.  */

static void
write_blank_common (void)
{
  const char * name = BLANK_COMMON_NAME;
  int saved;
  /* TODO: Blank commons are not bind(c).  The F2003 standard probably says
     this, but it hasn't been checked.  Just making it so for now.  */
  int is_bind_c = 0;

  if (gfc_current_ns->blank_common.head == NULL)
    return;

  mio_lparen ();

  mio_pool_string (&name);

  mio_symbol_ref (&gfc_current_ns->blank_common.head);
  saved = gfc_current_ns->blank_common.saved;
  mio_integer (&saved);

  /* Write out whether the common block is bind(c) or not.  */
  mio_integer (&is_bind_c);

  /* Write out an empty binding label.  */
  write_atom (ATOM_STRING, "");

  mio_rparen ();
}


/* Write equivalences to the module.  */

static void
write_equiv (void)
{
  gfc_equiv *eq, *e;
  int num;

  num = 0;
  for (eq = gfc_current_ns->equiv; eq; eq = eq->next)
    {
      mio_lparen ();

      for (e = eq; e; e = e->eq)
	{
	  if (e->module == NULL)
	    e->module = gfc_get_string ("%s.eq.%d", module_name, num);
	  mio_allocated_string (e->module);
	  mio_expr (&e->expr);
	}

      num++;
      mio_rparen ();
    }
}


/* Write a symbol to the module.  */

static void
write_symbol (int n, gfc_symbol *sym)
{
  const char *label;

  if (sym->attr.flavor == FL_UNKNOWN || sym->attr.flavor == FL_LABEL)
    gfc_internal_error ("write_symbol(): bad module symbol %qs", sym->name);

  mio_integer (&n);

  if (gfc_fl_struct (sym->attr.flavor))
    {
      const char *name;
      name = gfc_dt_upper_string (sym->name);
      mio_pool_string (&name);
    }
  else
    mio_pool_string (&sym->name);

  mio_pool_string (&sym->module);
  if ((sym->attr.is_bind_c || sym->attr.is_iso_c) && sym->binding_label)
    {
      label = sym->binding_label;
      mio_pool_string (&label);
    }
  else
    write_atom (ATOM_STRING, "");

  mio_pointer_ref (&sym->ns);

  mio_symbol (sym);
  write_char ('\n');
}


/* Recursive traversal function to write the initial set of symbols to
   the module.  We check to see if the symbol should be written
   according to the access specification.  */

static void
write_symbol0 (gfc_symtree *st)
{
  gfc_symbol *sym;
  pointer_info *p;
  bool dont_write = false;

  if (st == NULL)
    return;

  write_symbol0 (st->left);

  sym = st->n.sym;
  if (sym->module == NULL)
    sym->module = module_name;

  if (sym->attr.flavor == FL_PROCEDURE && sym->attr.generic
      && !sym->attr.subroutine && !sym->attr.function)
    dont_write = true;

  if (!gfc_check_symbol_access (sym))
    dont_write = true;

  if (!dont_write)
    {
      p = get_pointer (sym);
      if (p->type == P_UNKNOWN)
	p->type = P_SYMBOL;

      if (p->u.wsym.state != WRITTEN)
	{
	  write_symbol (p->integer, sym);
	  p->u.wsym.state = WRITTEN;
	}
    }

  write_symbol0 (st->right);
}


static void
write_omp_udr (gfc_omp_udr *udr)
{
  switch (udr->rop)
    {
    case OMP_REDUCTION_USER:
      /* Non-operators can't be used outside of the module.  */
      if (udr->name[0] != '.')
	return;
      else
	{
	  gfc_symtree *st;
	  size_t len = strlen (udr->name + 1);
	  char *name = XALLOCAVEC (char, len);
	  memcpy (name, udr->name, len - 1);
	  name[len - 1] = '\0';
	  st = gfc_find_symtree (gfc_current_ns->uop_root, name);
	  /* If corresponding user operator is private, don't write
	     the UDR.  */
	  if (st != NULL)
	    {
	      gfc_user_op *uop = st->n.uop;
	      if (!check_access (uop->access, uop->ns->default_access))
		return;
	    }
	}
      break;
    case OMP_REDUCTION_PLUS:
    case OMP_REDUCTION_MINUS:
    case OMP_REDUCTION_TIMES:
    case OMP_REDUCTION_AND:
    case OMP_REDUCTION_OR:
    case OMP_REDUCTION_EQV:
    case OMP_REDUCTION_NEQV:
      /* If corresponding operator is private, don't write the UDR.  */
      if (!check_access (gfc_current_ns->operator_access[udr->rop],
			 gfc_current_ns->default_access))
	return;
      break;
    default:
      break;
    }
  if (udr->ts.type == BT_DERIVED || udr->ts.type == BT_CLASS)
    {
      /* If derived type is private, don't write the UDR.  */
      if (!gfc_check_symbol_access (udr->ts.u.derived))
	return;
    }

  mio_lparen ();
  mio_pool_string (&udr->name);
  mio_typespec (&udr->ts);
  mio_omp_udr_expr (udr, &udr->omp_out, &udr->omp_in, udr->combiner_ns, false);
  if (udr->initializer_ns)
    mio_omp_udr_expr (udr, &udr->omp_priv, &udr->omp_orig,
		      udr->initializer_ns, true);
  mio_rparen ();
}


static void
write_omp_udrs (gfc_symtree *st)
{
  if (st == NULL)
    return;

  write_omp_udrs (st->left);
  gfc_omp_udr *udr;
  for (udr = st->n.omp_udr; udr; udr = udr->next)
    write_omp_udr (udr);
  write_omp_udrs (st->right);
}


/* Type for the temporary tree used when writing secondary symbols.  */

struct sorted_pointer_info
{
  BBT_HEADER (sorted_pointer_info);

  pointer_info *p;
};

#define gfc_get_sorted_pointer_info() XCNEW (sorted_pointer_info)

/* Recursively traverse the temporary tree, free its contents.  */

static void
free_sorted_pointer_info_tree (sorted_pointer_info *p)
{
  if (!p)
    return;

  free_sorted_pointer_info_tree (p->left);
  free_sorted_pointer_info_tree (p->right);

  free (p);
}

/* Comparison function for the temporary tree.  */

static int
compare_sorted_pointer_info (void *_spi1, void *_spi2)
{
  sorted_pointer_info *spi1, *spi2;
  spi1 = (sorted_pointer_info *)_spi1;
  spi2 = (sorted_pointer_info *)_spi2;

  if (spi1->p->integer < spi2->p->integer)
    return -1;
  if (spi1->p->integer > spi2->p->integer)
    return 1;
  return 0;
}


/* Finds the symbols that need to be written and collects them in the
   sorted_pi tree so that they can be traversed in an order
   independent of memory addresses.  */

static void
find_symbols_to_write(sorted_pointer_info **tree, pointer_info *p)
{
  if (!p)
    return;

  if (p->type == P_SYMBOL && p->u.wsym.state == NEEDS_WRITE)
    {
      sorted_pointer_info *sp = gfc_get_sorted_pointer_info();
      sp->p = p;

      gfc_insert_bbt (tree, sp, compare_sorted_pointer_info);
   }

  find_symbols_to_write (tree, p->left);
  find_symbols_to_write (tree, p->right);
}


/* Recursive function that traverses the tree of symbols that need to be
   written and writes them in order.  */

static void
write_symbol1_recursion (sorted_pointer_info *sp)
{
  if (!sp)
    return;

  write_symbol1_recursion (sp->left);

  pointer_info *p1 = sp->p;
  gcc_assert (p1->type == P_SYMBOL && p1->u.wsym.state == NEEDS_WRITE);

  p1->u.wsym.state = WRITTEN;
  write_symbol (p1->integer, p1->u.wsym.sym);
  p1->u.wsym.sym->attr.public_used = 1;

  write_symbol1_recursion (sp->right);
}


/* Write the secondary set of symbols to the module file.  These are
   symbols that were not public yet are needed by the public symbols
   or another dependent symbol.  The act of writing a symbol can add
   symbols to the pointer_info tree, so we return nonzero if a symbol
   was written and pass that information upwards.  The caller will
   then call this function again until nothing was written.  It uses
   the utility functions and a temporary tree to ensure a reproducible
   ordering of the symbol output and thus the module file.  */

static int
write_symbol1 (pointer_info *p)
{
  if (!p)
    return 0;

  /* Put symbols that need to be written into a tree sorted on the
     integer field.  */

  sorted_pointer_info *spi_root = NULL;
  find_symbols_to_write (&spi_root, p);

  /* No symbols to write, return.  */
  if (!spi_root)
    return 0;

  /* Otherwise, write and free the tree again.  */
  write_symbol1_recursion (spi_root);
  free_sorted_pointer_info_tree (spi_root);

  return 1;
}


/* Write operator interfaces associated with a symbol.  */

static void
write_operator (gfc_user_op *uop)
{
  static char nullstring[] = "";
  const char *p = nullstring;

  if (uop->op == NULL || !check_access (uop->access, uop->ns->default_access))
    return;

  mio_symbol_interface (&uop->name, &p, &uop->op);
}


/* Write generic interfaces from the namespace sym_root.  */

static void
write_generic (gfc_symtree *st)
{
  gfc_symbol *sym;

  if (st == NULL)
    return;

  write_generic (st->left);

  sym = st->n.sym;
  if (sym && !check_unique_name (st->name)
      && sym->generic && gfc_check_symbol_access (sym))
    {
      if (!sym->module)
	sym->module = module_name;

      mio_symbol_interface (&st->name, &sym->module, &sym->generic);
    }

  write_generic (st->right);
}


static void
write_symtree (gfc_symtree *st)
{
  gfc_symbol *sym;
  pointer_info *p;

  sym = st->n.sym;

  /* A symbol in an interface body must not be visible in the
     module file.  */
  if (sym->ns != gfc_current_ns
	&& sym->ns->proc_name
	&& sym->ns->proc_name->attr.if_source == IFSRC_IFBODY)
    return;

  if (!gfc_check_symbol_access (sym)
      || (sym->attr.flavor == FL_PROCEDURE && sym->attr.generic
	  && !sym->attr.subroutine && !sym->attr.function))
    return;

  if (check_unique_name (st->name))
    return;

  /* From F2003 onwards, intrinsic procedures are no longer subject to
     the restriction, "that an elemental intrinsic function here be of
     type integer or character and each argument must be an initialization
     expr of type integer or character" is lifted so that intrinsic
     procedures can be over-ridden. This requires that the intrinsic
     symbol not appear in the module file, thereby preventing ambiguity
     when USEd.  */
  if (strcmp (sym->module, "(intrinsic)") == 0
      && (gfc_option.allow_std & GFC_STD_F2003))
    return;

  p = find_pointer (sym);
  if (p == NULL)
    gfc_internal_error ("write_symtree(): Symbol not written");

  mio_pool_string (&st->name);
  mio_integer (&st->ambiguous);
  mio_hwi (&p->integer);
}


static void
write_module (void)
{
  int i;

  /* Initialize the column counter. */
  module_column = 1;
  
  /* Write the operator interfaces.  */
  mio_lparen ();

  for (i = GFC_INTRINSIC_BEGIN; i != GFC_INTRINSIC_END; i++)
    {
      if (i == INTRINSIC_USER)
	continue;

      mio_interface (check_access (gfc_current_ns->operator_access[i],
				   gfc_current_ns->default_access)
		     ? &gfc_current_ns->op[i] : NULL);
    }

  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  gfc_traverse_user_op (gfc_current_ns, write_operator);
  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  write_generic (gfc_current_ns->sym_root);
  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  write_blank_common ();
  write_common (gfc_current_ns->common_root);
  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  write_equiv ();
  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  write_omp_udrs (gfc_current_ns->omp_udr_root);
  mio_rparen ();
  write_char ('\n');
  write_char ('\n');

  /* Write symbol information.  First we traverse all symbols in the
     primary namespace, writing those that need to be written.
     Sometimes writing one symbol will cause another to need to be
     written.  A list of these symbols ends up on the write stack, and
     we end by popping the bottom of the stack and writing the symbol
     until the stack is empty.  */

  mio_lparen ();

  write_symbol0 (gfc_current_ns->sym_root);
  while (write_symbol1 (pi_root))
    /* Nothing.  */;

  mio_rparen ();

  write_char ('\n');
  write_char ('\n');

  mio_lparen ();
  gfc_traverse_symtree (gfc_current_ns->sym_root, write_symtree);
  mio_rparen ();
}


/* Read a CRC32 sum from the gzip trailer of a module file.  Returns
   true on success, false on failure.  */

static bool
read_crc32_from_module_file (const char* filename, uLong* crc)
{
  FILE *file;
  char buf[4];
  unsigned int val;

  /* Open the file in binary mode.  */
  if ((file = fopen (filename, "rb")) == NULL)
    return false;

  /* The gzip crc32 value is found in the [END-8, END-4] bytes of the
     file. See RFC 1952.  */
  if (fseek (file, -8, SEEK_END) != 0)
    {
      fclose (file);
      return false;
    }

  /* Read the CRC32.  */
  if (fread (buf, 1, 4, file) != 4)
    {
      fclose (file);
      return false;
    }

  /* Close the file.  */
  fclose (file);

  val = (buf[0] & 0xFF) + ((buf[1] & 0xFF) << 8) + ((buf[2] & 0xFF) << 16)
    + ((buf[3] & 0xFF) << 24);
  *crc = val;

  /* For debugging, the CRC value printed in hexadecimal should match
     the CRC printed by "zcat -l -v filename".
     printf("CRC of file %s is %x\n", filename, val); */

  return true;
}


/* Given module, dump it to disk.  If there was an error while
   processing the module, dump_flag will be set to zero and we delete
   the module file, even if it was already there.  */

static void
dump_module (const char *name, int dump_flag)
{
  int n;
  char *filename, *filename_tmp;
  uLong crc, crc_old;

  module_name = gfc_get_string ("%s", name);

  if (dump_smod)
    {
      name = submodule_name;
      n = strlen (name) + strlen (SUBMODULE_EXTENSION) + 1;
    }
  else
    n = strlen (name) + strlen (MODULE_EXTENSION) + 1;

  if (gfc_option.module_dir != NULL)
    {
      n += strlen (gfc_option.module_dir);
      filename = (char *) alloca (n);
      strcpy (filename, gfc_option.module_dir);
      strcat (filename, name);
    }
  else
    {
      filename = (char *) alloca (n);
      strcpy (filename, name);
    }

  if (dump_smod)
    strcat (filename, SUBMODULE_EXTENSION);
  else
  strcat (filename, MODULE_EXTENSION);

  /* Name of the temporary file used to write the module.  */
  filename_tmp = (char *) alloca (n + 1);
  strcpy (filename_tmp, filename);
  strcat (filename_tmp, "0");

  /* There was an error while processing the module.  We delete the
     module file, even if it was already there.  */
  if (!dump_flag)
    {
      remove (filename);
      return;
    }

  if (gfc_cpp_makedep ())
    gfc_cpp_add_target (filename);

  /* Write the module to the temporary file.  */
  module_fp = gzopen (filename_tmp, "w");
  if (module_fp == NULL)
    gfc_fatal_error ("Cannot open module file %qs for writing at %C: %s",
		     filename_tmp, xstrerror (errno));

  /* Use lbasename to ensure module files are reproducible regardless
     of the build path (see the reproducible builds project).  */
  gzprintf (module_fp, "GFORTRAN module version '%s' created from %s\n",
	    MOD_VERSION, lbasename (gfc_source_file));

  /* Write the module itself.  */
  iomode = IO_OUTPUT;

  init_pi_tree ();

  write_module ();

  free_pi_tree (pi_root);
  pi_root = NULL;

  write_char ('\n');

  if (gzclose (module_fp))
    gfc_fatal_error ("Error writing module file %qs for writing: %s",
		     filename_tmp, xstrerror (errno));

  /* Read the CRC32 from the gzip trailers of the module files and
     compare.  */
  if (!read_crc32_from_module_file (filename_tmp, &crc)
      || !read_crc32_from_module_file (filename, &crc_old)
      || crc_old != crc)
    {
      /* Module file have changed, replace the old one.  */
      if (remove (filename) && errno != ENOENT)
	gfc_fatal_error ("Cannot delete module file %qs: %s", filename,
			 xstrerror (errno));
      if (rename (filename_tmp, filename))
	gfc_fatal_error ("Cannot rename module file %qs to %qs: %s",
			 filename_tmp, filename, xstrerror (errno));
    }
  else
    {
      if (remove (filename_tmp))
	gfc_fatal_error ("Cannot delete temporary module file %qs: %s",
			 filename_tmp, xstrerror (errno));
    }
}


/* Suppress the output of a .smod file by module, if no module
   procedures have been seen.  */
static bool no_module_procedures;

static void
check_for_module_procedures (gfc_symbol *sym)
{
  if (sym && sym->attr.module_procedure)
    no_module_procedures = false;
}


void
gfc_dump_module (const char *name, int dump_flag)
{
  if (gfc_state_stack->state == COMP_SUBMODULE)
    dump_smod = true;
  else
    dump_smod =false;

  no_module_procedures = true;
  gfc_traverse_ns (gfc_current_ns, check_for_module_procedures);

  dump_module (name, dump_flag);

  if (no_module_procedures || dump_smod)
    return;

  /* Write a submodule file from a module.  The 'dump_smod' flag switches
     off the check for PRIVATE entities.  */
  dump_smod = true;
  submodule_name = module_name;
  dump_module (name, dump_flag);
  dump_smod = false;
}

static void
create_intrinsic_function (const char *name, int id,
			   const char *modname, intmod_id module,
			   bool subroutine, gfc_symbol *result_type)
{
  gfc_intrinsic_sym *isym;
  gfc_symtree *tmp_symtree;
  gfc_symbol *sym;

  tmp_symtree = gfc_find_symtree (gfc_current_ns->sym_root, name);
  if (tmp_symtree)
    {
      if (tmp_symtree->n.sym && tmp_symtree->n.sym->module
	  && strcmp (modname, tmp_symtree->n.sym->module) == 0)
	return;
      gfc_error ("Symbol %qs at %C already declared", name);
      return;
    }

  gfc_get_sym_tree (name, gfc_current_ns, &tmp_symtree, false);
  sym = tmp_symtree->n.sym;

  if (subroutine)
    {
      gfc_isym_id isym_id = gfc_isym_id_by_intmod (module, id);
      isym = gfc_intrinsic_subroutine_by_id (isym_id);
      sym->attr.subroutine = 1;
    }
  else
    {
      gfc_isym_id isym_id = gfc_isym_id_by_intmod (module, id);
      isym = gfc_intrinsic_function_by_id (isym_id);

      sym->attr.function = 1;
      if (result_type)
	{
	  sym->ts.type = BT_DERIVED;
	  sym->ts.u.derived = result_type;
	  sym->ts.is_c_interop = 1;
	  isym->ts.f90_type = BT_VOID;
	  isym->ts.type = BT_DERIVED;
	  isym->ts.f90_type = BT_VOID;
	  isym->ts.u.derived = result_type;
	  isym->ts.is_c_interop = 1;
	}
    }
  gcc_assert (isym);

  sym->attr.flavor = FL_PROCEDURE;
  sym->attr.intrinsic = 1;

  sym->module = gfc_get_string ("%s", modname);
  sym->attr.use_assoc = 1;
  sym->from_intmod = module;
  sym->intmod_sym_id = id;
}


/* Import the intrinsic ISO_C_BINDING module, generating symbols in
   the current namespace for all named constants, pointer types, and
   procedures in the module unless the only clause was used or a rename
   list was provided.  */

static void
import_iso_c_binding_module (void)
{
  gfc_symbol *mod_sym = NULL, *return_type;
  gfc_symtree *mod_symtree = NULL, *tmp_symtree;
  gfc_symtree *c_ptr = NULL, *c_funptr = NULL;
  const char *iso_c_module_name = "__iso_c_binding";
  gfc_use_rename *u;
  int i;
  bool want_c_ptr = false, want_c_funptr = false;

  /* Look only in the current namespace.  */
  mod_symtree = gfc_find_symtree (gfc_current_ns->sym_root, iso_c_module_name);

  if (mod_symtree == NULL)
    {
      /* symtree doesn't already exist in current namespace.  */
      gfc_get_sym_tree (iso_c_module_name, gfc_current_ns, &mod_symtree,
			false);

      if (mod_symtree != NULL)
	mod_sym = mod_symtree->n.sym;
      else
	gfc_internal_error ("import_iso_c_binding_module(): Unable to "
			    "create symbol for %s", iso_c_module_name);

      mod_sym->attr.flavor = FL_MODULE;
      mod_sym->attr.intrinsic = 1;
      mod_sym->module = gfc_get_string ("%s", iso_c_module_name);
      mod_sym->from_intmod = INTMOD_ISO_C_BINDING;
    }

  /* Check whether C_PTR or C_FUNPTR are in the include list, if so, load it;
     check also whether C_NULL_(FUN)PTR or C_(FUN)LOC are requested, which
     need C_(FUN)PTR.  */
  for (u = gfc_rename_list; u; u = u->next)
    {
      if (strcmp (c_interop_kinds_table[ISOCBINDING_NULL_PTR].name,
		  u->use_name) == 0)
        want_c_ptr = true;
      else if (strcmp (c_interop_kinds_table[ISOCBINDING_LOC].name,
		       u->use_name) == 0)
        want_c_ptr = true;
      else if (strcmp (c_interop_kinds_table[ISOCBINDING_NULL_FUNPTR].name,
		       u->use_name) == 0)
        want_c_funptr = true;
      else if (strcmp (c_interop_kinds_table[ISOCBINDING_FUNLOC].name,
		       u->use_name) == 0)
        want_c_funptr = true;
      else if (strcmp (c_interop_kinds_table[ISOCBINDING_PTR].name,
                       u->use_name) == 0)
	{
	  c_ptr = generate_isocbinding_symbol (iso_c_module_name,
                                               (iso_c_binding_symbol)
							ISOCBINDING_PTR,
                                               u->local_name[0] ? u->local_name
                                                                : u->use_name,
                                               NULL, false);
	}
      else if (strcmp (c_interop_kinds_table[ISOCBINDING_FUNPTR].name,
                       u->use_name) == 0)
	{
	  c_funptr
	     = generate_isocbinding_symbol (iso_c_module_name,
					    (iso_c_binding_symbol)
							ISOCBINDING_FUNPTR,
					     u->local_name[0] ? u->local_name
							      : u->use_name,
					     NULL, false);
	}
    }

  if ((want_c_ptr || !only_flag) && !c_ptr)
    c_ptr = generate_isocbinding_symbol (iso_c_module_name,
					 (iso_c_binding_symbol)
							ISOCBINDING_PTR,
					 NULL, NULL, only_flag);
  if ((want_c_funptr || !only_flag) && !c_funptr)
    c_funptr = generate_isocbinding_symbol (iso_c_module_name,
					    (iso_c_binding_symbol)
							ISOCBINDING_FUNPTR,
					    NULL, NULL, only_flag);

  /* Generate the symbols for the named constants representing
     the kinds for intrinsic data types.  */
  for (i = 0; i < ISOCBINDING_NUMBER; i++)
    {
      bool found = false;
      for (u = gfc_rename_list; u; u = u->next)
	if (strcmp (c_interop_kinds_table[i].name, u->use_name) == 0)
	  {
	    bool not_in_std;
	    const char *name;
	    u->found = 1;
	    found = true;

	    switch (i)
	      {
#define NAMED_FUNCTION(a,b,c,d) \
	        case a: \
		  not_in_std = (gfc_option.allow_std & d) == 0; \
		  name = b; \
		  break;
#define NAMED_SUBROUTINE(a,b,c,d) \
	        case a: \
		  not_in_std = (gfc_option.allow_std & d) == 0; \
		  name = b; \
		  break;
#define NAMED_INTCST(a,b,c,d) \
	        case a: \
		  not_in_std = (gfc_option.allow_std & d) == 0; \
		  name = b; \
		  break;
#define NAMED_REALCST(a,b,c,d) \
	        case a: \
		  not_in_std = (gfc_option.allow_std & d) == 0; \
		  name = b; \
		  break;
#define NAMED_CMPXCST(a,b,c,d) \
	        case a: \
		  not_in_std = (gfc_option.allow_std & d) == 0; \
		  name = b; \
		  break;
#include "iso-c-binding.def"
		default:
		  not_in_std = false;
		  name = "";
	      }

	    if (not_in_std)
	      {
		gfc_error ("The symbol %qs, referenced at %L, is not "
			   "in the selected standard", name, &u->where);
		continue;
	      }

	    switch (i)
	      {
#define NAMED_FUNCTION(a,b,c,d) \
	        case a: \
		  if (a == ISOCBINDING_LOC) \
		    return_type = c_ptr->n.sym; \
		  else if (a == ISOCBINDING_FUNLOC) \
		    return_type = c_funptr->n.sym; \
		  else \
		    return_type = NULL; \
		  create_intrinsic_function (u->local_name[0] \
					     ? u->local_name : u->use_name, \
					     a, iso_c_module_name, \
					     INTMOD_ISO_C_BINDING, false, \
					     return_type); \
		  break;
#define NAMED_SUBROUTINE(a,b,c,d) \
	        case a: \
		  create_intrinsic_function (u->local_name[0] ? u->local_name \
							      : u->use_name, \
                                             a, iso_c_module_name, \
                                             INTMOD_ISO_C_BINDING, true, NULL); \
		  break;
#include "iso-c-binding.def"

		case ISOCBINDING_PTR:
		case ISOCBINDING_FUNPTR:
		  /* Already handled above.  */
		  break;
		default:
		  if (i == ISOCBINDING_NULL_PTR)
		    tmp_symtree = c_ptr;
		  else if (i == ISOCBINDING_NULL_FUNPTR)
		    tmp_symtree = c_funptr;
		  else
		    tmp_symtree = NULL;
		  generate_isocbinding_symbol (iso_c_module_name,
					       (iso_c_binding_symbol) i,
					       u->local_name[0]
					       ? u->local_name : u->use_name,
					       tmp_symtree, false);
	      }
	  }

      if (!found && !only_flag)
	{
	  /* Skip, if the symbol is not in the enabled standard.  */
	  switch (i)
	    {
#define NAMED_FUNCTION(a,b,c,d) \
	      case a: \
		if ((gfc_option.allow_std & d) == 0) \
		  continue; \
		break;
#define NAMED_SUBROUTINE(a,b,c,d) \
	      case a: \
		if ((gfc_option.allow_std & d) == 0) \
		  continue; \
		break;
#define NAMED_INTCST(a,b,c,d) \
	      case a: \
		if ((gfc_option.allow_std & d) == 0) \
		  continue; \
		break;
#define NAMED_REALCST(a,b,c,d) \
	      case a: \
		if ((gfc_option.allow_std & d) == 0) \
		  continue; \
		break;
#define NAMED_CMPXCST(a,b,c,d) \
	      case a: \
		if ((gfc_option.allow_std & d) == 0) \
		  continue; \
		break;
#include "iso-c-binding.def"
	      default:
		; /* Not GFC_STD_* versioned.  */
	    }

	  switch (i)
	    {
#define NAMED_FUNCTION(a,b,c,d) \
	      case a: \
		if (a == ISOCBINDING_LOC) \
		  return_type = c_ptr->n.sym; \
		else if (a == ISOCBINDING_FUNLOC) \
		  return_type = c_funptr->n.sym; \
		else \
		  return_type = NULL; \
		create_intrinsic_function (b, a, iso_c_module_name, \
					   INTMOD_ISO_C_BINDING, false, \
					   return_type); \
		break;
#define NAMED_SUBROUTINE(a,b,c,d) \
	      case a: \
		create_intrinsic_function (b, a, iso_c_module_name, \
					   INTMOD_ISO_C_BINDING, true, NULL); \
		  break;
#include "iso-c-binding.def"

	      case ISOCBINDING_PTR:
	      case ISOCBINDING_FUNPTR:
		/* Already handled above.  */
		break;
	      default:
		if (i == ISOCBINDING_NULL_PTR)
		  tmp_symtree = c_ptr;
		else if (i == ISOCBINDING_NULL_FUNPTR)
		  tmp_symtree = c_funptr;
		else
		  tmp_symtree = NULL;
		generate_isocbinding_symbol (iso_c_module_name,
					     (iso_c_binding_symbol) i, NULL,
					     tmp_symtree, false);
	    }
	}
   }

   for (u = gfc_rename_list; u; u = u->next)
     {
      if (u->found)
	continue;

      gfc_error ("Symbol %qs referenced at %L not found in intrinsic "
		 "module ISO_C_BINDING", u->use_name, &u->where);
     }
}


/* Add an integer named constant from a given module.  */

static void
create_int_parameter (const char *name, int value, const char *modname,
		      intmod_id module, int id)
{
  gfc_symtree *tmp_symtree;
  gfc_symbol *sym;

  tmp_symtree = gfc_find_symtree (gfc_current_ns->sym_root, name);
  if (tmp_symtree != NULL)
    {
      if (strcmp (modname, tmp_symtree->n.sym->module) == 0)
	return;
      else
	gfc_error ("Symbol %qs already declared", name);
    }

  gfc_get_sym_tree (name, gfc_current_ns, &tmp_symtree, false);
  sym = tmp_symtree->n.sym;

  sym->module = gfc_get_string ("%s", modname);
  sym->attr.flavor = FL_PARAMETER;
  sym->ts.type = BT_INTEGER;
  sym->ts.kind = gfc_default_integer_kind;
  sym->value = gfc_get_int_expr (gfc_default_integer_kind, NULL, value);
  sym->attr.use_assoc = 1;
  sym->from_intmod = module;
  sym->intmod_sym_id = id;
}


/* Value is already contained by the array constructor, but not
   yet the shape.  */

static void
create_int_parameter_array (const char *name, int size, gfc_expr *value,
			    const char *modname, intmod_id module, int id)
{
  gfc_symtree *tmp_symtree;
  gfc_symbol *sym;

  tmp_symtree = gfc_find_symtree (gfc_current_ns->sym_root, name);
  if (tmp_symtree != NULL)
    {
      if (strcmp (modname, tmp_symtree->n.sym->module) == 0)
	return;
      else
	gfc_error ("Symbol %qs already declared", name);
    }

  gfc_get_sym_tree (name, gfc_current_ns, &tmp_symtree, false);
  sym = tmp_symtree->n.sym;

  sym->module = gfc_get_string ("%s", modname);
  sym->attr.flavor = FL_PARAMETER;
  sym->ts.type = BT_INTEGER;
  sym->ts.kind = gfc_default_integer_kind;
  sym->attr.use_assoc = 1;
  sym->from_intmod = module;
  sym->intmod_sym_id = id;
  sym->attr.dimension = 1;
  sym->as = gfc_get_array_spec ();
  sym->as->rank = 1;
  sym->as->type = AS_EXPLICIT;
  sym->as->lower[0] = gfc_get_int_expr (gfc_default_integer_kind, NULL, 1);
  sym->as->upper[0] = gfc_get_int_expr (gfc_default_integer_kind, NULL, size);

  sym->value = value;
  sym->value->shape = gfc_get_shape (1);
  mpz_init_set_ui (sym->value->shape[0], size);
}


/* Add an derived type for a given module.  */

static void
create_derived_type (const char *name, const char *modname,
		      intmod_id module, int id)
{
  gfc_symtree *tmp_symtree;
  gfc_symbol *sym, *dt_sym;
  gfc_interface *intr, *head;

  tmp_symtree = gfc_find_symtree (gfc_current_ns->sym_root, name);
  if (tmp_symtree != NULL)
    {
      if (strcmp (modname, tmp_symtree->n.sym->module) == 0)
	return;
      else
	gfc_error ("Symbol %qs already declared", name);
    }

  gfc_get_sym_tree (name, gfc_current_ns, &tmp_symtree, false);
  sym = tmp_symtree->n.sym;
  sym->module = gfc_get_string ("%s", modname);
  sym->from_intmod = module;
  sym->intmod_sym_id = id;
  sym->attr.flavor = FL_PROCEDURE;
  sym->attr.function = 1;
  sym->attr.generic = 1;

  gfc_get_sym_tree (gfc_dt_upper_string (sym->name),
		    gfc_current_ns, &tmp_symtree, false);
  dt_sym = tmp_symtree->n.sym;
  dt_sym->name = gfc_get_string ("%s", sym->name);
  dt_sym->attr.flavor = FL_DERIVED;
  dt_sym->attr.private_comp = 1;
  dt_sym->attr.zero_comp = 1;
  dt_sym->attr.use_assoc = 1;
  dt_sym->module = gfc_get_string ("%s", modname);
  dt_sym->from_intmod = module;
  dt_sym->intmod_sym_id = id;

  head = sym->generic;
  intr = gfc_get_interface ();
  intr->sym = dt_sym;
  intr->where = gfc_current_locus;
  intr->next = head;
  sym->generic = intr;
  sym->attr.if_source = IFSRC_DECL;
}


/* Read the contents of the module file into a temporary buffer.  */

static void
read_module_to_tmpbuf ()
{
  /* We don't know the uncompressed size, so enlarge the buffer as
     needed.  */
  int cursz = 4096;
  int rsize = cursz;
  int len = 0;

  module_content = XNEWVEC (char, cursz);

  while (1)
    {
      int nread = gzread (module_fp, module_content + len, rsize);
      len += nread;
      if (nread < rsize)
	break;
      cursz *= 2;
      module_content = XRESIZEVEC (char, module_content, cursz);
      rsize = cursz - len;
    }

  module_content = XRESIZEVEC (char, module_content, len + 1);
  module_content[len] = '\0';

  module_pos = 0;
}


/* USE the ISO_FORTRAN_ENV intrinsic module.  */

static void
use_iso_fortran_env_module (void)
{
  static char mod[] = "iso_fortran_env";
  gfc_use_rename *u;
  gfc_symbol *mod_sym;
  gfc_symtree *mod_symtree;
  gfc_expr *expr;
  int i, j;

  intmod_sym symbol[] = {
#define NAMED_INTCST(a,b,c,d) { a, b, 0, d },
#define NAMED_KINDARRAY(a,b,c,d) { a, b, 0, d },
#define NAMED_DERIVED_TYPE(a,b,c,d) { a, b, 0, d },
#define NAMED_FUNCTION(a,b,c,d) { a, b, c, d },
#define NAMED_SUBROUTINE(a,b,c,d) { a, b, c, d },
#include "iso-fortran-env.def"
    { ISOFORTRANENV_INVALID, NULL, -1234, 0 } };

  i = 0;
#define NAMED_INTCST(a,b,c,d) symbol[i++].value = c;
#include "iso-fortran-env.def"

  /* Generate the symbol for the module itself.  */
  mod_symtree = gfc_find_symtree (gfc_current_ns->sym_root, mod);
  if (mod_symtree == NULL)
    {
      gfc_get_sym_tree (mod, gfc_current_ns, &mod_symtree, false);
      gcc_assert (mod_symtree);
      mod_sym = mod_symtree->n.sym;

      mod_sym->attr.flavor = FL_MODULE;
      mod_sym->attr.intrinsic = 1;
      mod_sym->module = gfc_get_string ("%s", mod);
      mod_sym->from_intmod = INTMOD_ISO_FORTRAN_ENV;
    }
  else
    if (!mod_symtree->n.sym->attr.intrinsic)
      gfc_error ("Use of intrinsic module %qs at %C conflicts with "
		 "non-intrinsic module name used previously", mod);

  /* Generate the symbols for the module integer named constants.  */

  for (i = 0; symbol[i].name; i++)
    {
      bool found = false;
      for (u = gfc_rename_list; u; u = u->next)
	{
	  if (strcmp (symbol[i].name, u->use_name) == 0)
	    {
	      found = true;
	      u->found = 1;

	      if (!gfc_notify_std (symbol[i].standard, "The symbol %qs, "
				   "referenced at %L, is not in the selected "
				   "standard", symbol[i].name, &u->where))
	        continue;

	      if ((flag_default_integer || flag_default_real_8)
		  && symbol[i].id == ISOFORTRANENV_NUMERIC_STORAGE_SIZE)
		gfc_warning_now (0, "Use of the NUMERIC_STORAGE_SIZE named "
				 "constant from intrinsic module "
				 "ISO_FORTRAN_ENV at %L is incompatible with "
				 "option %qs", &u->where,
				 flag_default_integer
				   ? "-fdefault-integer-8"
				   : "-fdefault-real-8");
	      switch (symbol[i].id)
		{
#define NAMED_INTCST(a,b,c,d) \
		case a:
#include "iso-fortran-env.def"
		  create_int_parameter (u->local_name[0] ? u->local_name
							 : u->use_name,
					symbol[i].value, mod,
					INTMOD_ISO_FORTRAN_ENV, symbol[i].id);
		  break;

#define NAMED_KINDARRAY(a,b,KINDS,d) \
		case a:\
		  expr = gfc_get_array_expr (BT_INTEGER, \
					     gfc_default_integer_kind,\
					     NULL); \
		  for (j = 0; KINDS[j].kind != 0; j++) \
		    gfc_constructor_append_expr (&expr->value.constructor, \
			gfc_get_int_expr (gfc_default_integer_kind, NULL, \
					  KINDS[j].kind), NULL); \
		  create_int_parameter_array (u->local_name[0] ? u->local_name \
							 : u->use_name, \
					      j, expr, mod, \
					      INTMOD_ISO_FORTRAN_ENV, \
					      symbol[i].id); \
		  break;
#include "iso-fortran-env.def"

#define NAMED_DERIVED_TYPE(a,b,TYPE,STD) \
		case a:
#include "iso-fortran-env.def"
                  create_derived_type (u->local_name[0] ? u->local_name
							: u->use_name,
				       mod, INTMOD_ISO_FORTRAN_ENV,
				       symbol[i].id);
		  break;

#define NAMED_FUNCTION(a,b,c,d) \
		case a:
#include "iso-fortran-env.def"
		  create_intrinsic_function (u->local_name[0] ? u->local_name
							      : u->use_name,
					     symbol[i].id, mod,
					     INTMOD_ISO_FORTRAN_ENV, false,
					     NULL);
		  break;

		default:
		  gcc_unreachable ();
		}
	    }
	}

      if (!found && !only_flag)
	{
	  if ((gfc_option.allow_std & symbol[i].standard) == 0)
	    continue;

	  if ((flag_default_integer || flag_default_real_8)
	      && symbol[i].id == ISOFORTRANENV_NUMERIC_STORAGE_SIZE)
	    gfc_warning_now (0,
			     "Use of the NUMERIC_STORAGE_SIZE named constant "
			     "from intrinsic module ISO_FORTRAN_ENV at %C is "
			     "incompatible with option %s",
			     flag_default_integer
				? "-fdefault-integer-8" : "-fdefault-real-8");

	  switch (symbol[i].id)
	    {
#define NAMED_INTCST(a,b,c,d) \
	    case a:
#include "iso-fortran-env.def"
	      create_int_parameter (symbol[i].name, symbol[i].value, mod,
				    INTMOD_ISO_FORTRAN_ENV, symbol[i].id);
	      break;

#define NAMED_KINDARRAY(a,b,KINDS,d) \
	    case a:\
	      expr = gfc_get_array_expr (BT_INTEGER, gfc_default_integer_kind, \
					 NULL); \
	      for (j = 0; KINDS[j].kind != 0; j++) \
		gfc_constructor_append_expr (&expr->value.constructor, \
                      gfc_get_int_expr (gfc_default_integer_kind, NULL, \
                                        KINDS[j].kind), NULL); \
            create_int_parameter_array (symbol[i].name, j, expr, mod, \
                                        INTMOD_ISO_FORTRAN_ENV, symbol[i].id);\
            break;
#include "iso-fortran-env.def"

#define NAMED_DERIVED_TYPE(a,b,TYPE,STD) \
	  case a:
#include "iso-fortran-env.def"
	    create_derived_type (symbol[i].name, mod, INTMOD_ISO_FORTRAN_ENV,
				 symbol[i].id);
	    break;

#define NAMED_FUNCTION(a,b,c,d) \
		case a:
#include "iso-fortran-env.def"
		  create_intrinsic_function (symbol[i].name, symbol[i].id, mod,
					     INTMOD_ISO_FORTRAN_ENV, false,
					     NULL);
		  break;

	  default:
	    gcc_unreachable ();
	  }
	}
    }

  for (u = gfc_rename_list; u; u = u->next)
    {
      if (u->found)
	continue;

      gfc_error ("Symbol %qs referenced at %L not found in intrinsic "
		     "module ISO_FORTRAN_ENV", u->use_name, &u->where);
    }
}


/* Process a USE directive.  */

static void
gfc_use_module (gfc_use_list *module)
{
  char *filename;
  gfc_state_data *p;
  int c, line, start;
  gfc_symtree *mod_symtree;
  gfc_use_list *use_stmt;
  locus old_locus = gfc_current_locus;

  gfc_current_locus = module->where;
  module_name = module->module_name;
  gfc_rename_list = module->rename;
  only_flag = module->only_flag;
  current_intmod = INTMOD_NONE;

  if (!only_flag)
    gfc_warning_now (OPT_Wuse_without_only,
		     "USE statement at %C has no ONLY qualifier");

  if (gfc_state_stack->state == COMP_MODULE
      || module->submodule_name == NULL)
    {
      filename = XALLOCAVEC (char, strlen (module_name)
				   + strlen (MODULE_EXTENSION) + 1);
      strcpy (filename, module_name);
      strcat (filename, MODULE_EXTENSION);
    }
  else
    {
      filename = XALLOCAVEC (char, strlen (module->submodule_name)
				   + strlen (SUBMODULE_EXTENSION) + 1);
      strcpy (filename, module->submodule_name);
      strcat (filename, SUBMODULE_EXTENSION);
    }

  /* First, try to find an non-intrinsic module, unless the USE statement
     specified that the module is intrinsic.  */
  module_fp = NULL;
  if (!module->intrinsic)
    module_fp = gzopen_included_file (filename, true, true);

  /* Then, see if it's an intrinsic one, unless the USE statement
     specified that the module is non-intrinsic.  */
  if (module_fp == NULL && !module->non_intrinsic)
    {
      if (strcmp (module_name, "iso_fortran_env") == 0
	  && gfc_notify_std (GFC_STD_F2003, "ISO_FORTRAN_ENV "
			     "intrinsic module at %C"))
       {
	 use_iso_fortran_env_module ();
	 free_rename (module->rename);
	 module->rename = NULL;
	 gfc_current_locus = old_locus;
	 module->intrinsic = true;
	 return;
       }

      if (strcmp (module_name, "iso_c_binding") == 0
	  && gfc_notify_std (GFC_STD_F2003, "ISO_C_BINDING module at %C"))
	{
	  import_iso_c_binding_module();
	  free_rename (module->rename);
	  module->rename = NULL;
	  gfc_current_locus = old_locus;
	  module->intrinsic = true;
	  return;
	}

      module_fp = gzopen_intrinsic_module (filename);

      if (module_fp == NULL && module->intrinsic)
	gfc_fatal_error ("Cannot find an intrinsic module named %qs at %C",
			 module_name);

      /* Check for the IEEE modules, so we can mark their symbols
	 accordingly when we read them.  */
      if (strcmp (module_name, "ieee_features") == 0
	  && gfc_notify_std (GFC_STD_F2003, "IEEE_FEATURES module at %C"))
	{
	  current_intmod = INTMOD_IEEE_FEATURES;
	}
      else if (strcmp (module_name, "ieee_exceptions") == 0
	       && gfc_notify_std (GFC_STD_F2003,
				  "IEEE_EXCEPTIONS module at %C"))
	{
	  current_intmod = INTMOD_IEEE_EXCEPTIONS;
	}
      else if (strcmp (module_name, "ieee_arithmetic") == 0
	       && gfc_notify_std (GFC_STD_F2003,
				  "IEEE_ARITHMETIC module at %C"))
	{
	  current_intmod = INTMOD_IEEE_ARITHMETIC;
	}
    }

  if (module_fp == NULL)
    {
      if (gfc_state_stack->state != COMP_SUBMODULE
	  && module->submodule_name == NULL)
	gfc_fatal_error ("Cannot open module file %qs for reading at %C: %s",
			 filename, xstrerror (errno));
      else
	gfc_fatal_error ("Module file %qs has not been generated, either "
			 "because the module does not contain a MODULE "
			 "PROCEDURE or there is an error in the module.",
			 filename);
    }

  /* Check that we haven't already USEd an intrinsic module with the
     same name.  */

  mod_symtree = gfc_find_symtree (gfc_current_ns->sym_root, module_name);
  if (mod_symtree && mod_symtree->n.sym->attr.intrinsic)
    gfc_error ("Use of non-intrinsic module %qs at %C conflicts with "
	       "intrinsic module name used previously", module_name);

  iomode = IO_INPUT;
  module_line = 1;
  module_column = 1;
  start = 0;

  read_module_to_tmpbuf ();
  gzclose (module_fp);

  /* Skip the first line of the module, after checking that this is
     a gfortran module file.  */
  line = 0;
  while (line < 1)
    {
      c = module_char ();
      if (c == EOF)
	bad_module ("Unexpected end of module");
      if (start++ < 3)
	parse_name (c);
      if ((start == 1 && strcmp (atom_name, "GFORTRAN") != 0)
	  || (start == 2 && strcmp (atom_name, " module") != 0))
	gfc_fatal_error ("File %qs opened at %C is not a GNU Fortran"
			 " module file", module_fullpath);
      if (start == 3)
	{
	  if (strcmp (atom_name, " version") != 0
	      || module_char () != ' '
	      || parse_atom () != ATOM_STRING
	      || strcmp (atom_string, MOD_VERSION))
	    gfc_fatal_error ("Cannot read module file %qs opened at %C,"
			     " because it was created by a different"
			     " version of GNU Fortran", module_fullpath);

	  free (atom_string);
	}

      if (c == '\n')
	line++;
    }

  /* Make sure we're not reading the same module that we may be building.  */
  for (p = gfc_state_stack; p; p = p->previous)
    if ((p->state == COMP_MODULE || p->state == COMP_SUBMODULE)
	 && strcmp (p->sym->name, module_name) == 0)
      {
	if (p->state == COMP_SUBMODULE)
	  gfc_fatal_error ("Cannot USE a submodule that is currently built");
	else
	  gfc_fatal_error ("Cannot USE a module that is currently built");
      }

  init_pi_tree ();
  init_true_name_tree ();

  read_module ();

  free_true_name (true_name_root);
  true_name_root = NULL;

  free_pi_tree (pi_root);
  pi_root = NULL;

  XDELETEVEC (module_content);
  module_content = NULL;

  use_stmt = gfc_get_use_list ();
  *use_stmt = *module;
  use_stmt->next = gfc_current_ns->use_stmts;
  gfc_current_ns->use_stmts = use_stmt;

  gfc_current_locus = old_locus;
}


/* Remove duplicated intrinsic operators from the rename list.  */

static void
rename_list_remove_duplicate (gfc_use_rename *list)
{
  gfc_use_rename *seek, *last;

  for (; list; list = list->next)
    if (list->op != INTRINSIC_USER && list->op != INTRINSIC_NONE)
      {
	last = list;
	for (seek = list->next; seek; seek = last->next)
	  {
	    if (list->op == seek->op)
	      {
		last->next = seek->next;
		free (seek);
	      }
	    else
	      last = seek;
	  }
      }
}


/* Process all USE directives.  */

void
gfc_use_modules (void)
{
  gfc_use_list *next, *seek, *last;

  for (next = module_list; next; next = next->next)
    {
      bool non_intrinsic = next->non_intrinsic;
      bool intrinsic = next->intrinsic;
      bool neither = !non_intrinsic && !intrinsic;

      for (seek = next->next; seek; seek = seek->next)
	{
	  if (next->module_name != seek->module_name)
	    continue;

	  if (seek->non_intrinsic)
	    non_intrinsic = true;
	  else if (seek->intrinsic)
	    intrinsic = true;
	  else
	    neither = true;
	}

      if (intrinsic && neither && !non_intrinsic)
	{
	  char *filename;
          FILE *fp;

	  filename = XALLOCAVEC (char,
				 strlen (next->module_name)
				 + strlen (MODULE_EXTENSION) + 1);
	  strcpy (filename, next->module_name);
	  strcat (filename, MODULE_EXTENSION);
	  fp = gfc_open_included_file (filename, true, true);
	  if (fp != NULL)
	    {
	      non_intrinsic = true;
	      fclose (fp);
	    }
	}

      last = next;
      for (seek = next->next; seek; seek = last->next)
	{
	  if (next->module_name != seek->module_name)
	    {
	      last = seek;
	      continue;
	    }

	  if ((!next->intrinsic && !seek->intrinsic)
	      || (next->intrinsic && seek->intrinsic)
	      || !non_intrinsic)
	    {
	      if (!seek->only_flag)
		next->only_flag = false;
	      if (seek->rename)
		{
		  gfc_use_rename *r = seek->rename;
		  while (r->next)
		    r = r->next;
		  r->next = next->rename;
		  next->rename = seek->rename;
		}
	      last->next = seek->next;
	      free (seek);
	    }
	  else
	    last = seek;
	}
    }

  for (; module_list; module_list = next)
    {
      next = module_list->next;
      rename_list_remove_duplicate (module_list->rename);
      gfc_use_module (module_list);
      free (module_list);
    }
  gfc_rename_list = NULL;
}


void
gfc_free_use_stmts (gfc_use_list *use_stmts)
{
  gfc_use_list *next;
  for (; use_stmts; use_stmts = next)
    {
      gfc_use_rename *next_rename;

      for (; use_stmts->rename; use_stmts->rename = next_rename)
	{
	  next_rename = use_stmts->rename->next;
	  free (use_stmts->rename);
	}
      next = use_stmts->next;
      free (use_stmts);
    }
}


void
gfc_module_init_2 (void)
{
  last_atom = ATOM_LPAREN;
  gfc_rename_list = NULL;
  module_list = NULL;
}


void
gfc_module_done_2 (void)
{
  free_rename (gfc_rename_list);
  gfc_rename_list = NULL;
}
