/* Handle modules, which amounts to loading and saving symbols and
   their attendant structures.
   Copyright (C) 2000-2020 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;

	  st = gfc_find_symtree (gfc_current_ns->sym_root, name);
	  if (st && type != INTERFACE_USER_OP)
	    {
	      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 (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;
	    }

	  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 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.c, 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) + 1);
      strcpy (fullname, p->path);
      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;
}


/* 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)
{
  atom_int = c - '0';

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

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

}


/* 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 '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 '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
};

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 (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 ();
	}

      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;
	    }
	}
    }
}


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);

  /* 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;
  char name[GFC_MAX_SYMBOL_LEN + 1], module[GFC_MAX_SYMBOL_LEN + 1];
  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;
  char name[GFC_MAX_SYMBOL_LEN + 1], module[GFC_MAX_SYMBOL_LEN + 1];
  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->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 (gfc_str_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 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] == '_'
	      && (gfc_str_startswith (name, "__vtab_")
		  || gfc_str_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] != '_'
		  || (!gfc_str_startswith (name, "__vtab_")
		      && !gfc_str_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++)
    {
      if (i == INTRINSIC_USER)
	continue;

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

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

	  u->found = 1;
	}

      mio_interface (&gfc_current_ns->op[i]);
      if (u && !gfc_current_ns->op[i])
	u->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;
      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;

  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;
}
