/* Part of CPP library.  File handling.
   Copyright (C) 1986-2026 Free Software Foundation, Inc.
   Written by Per Bothner, 1994.
   Based on CCCP program by Paul Rubin, June 1986
   Adapted to ANSI C, Richard Stallman, Jan 1987
   Split out of cpplib.c, Zack Weinberg, Oct 1998
   Reimplemented, Neil Booth, Jul 2003

This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 3, or (at your option) any
later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

#include "config.h"
#include "system.h"
#include "cpplib.h"
#include "internal.h"
#include "mkdeps.h"
#include "obstack.h"
#include "hashtab.h"
#include "md5.h"
#include <dirent.h>

/* Variable length record files on VMS will have a stat size that includes
   record control characters that won't be included in the read size.  */
#ifdef VMS
# define FAB_C_VAR 2 /* variable length records (see Starlet fabdef.h) */
# define STAT_SIZE_RELIABLE(ST) ((ST).st_fab_rfm != FAB_C_VAR)
#else
# define STAT_SIZE_RELIABLE(ST) true
#endif

#ifdef __DJGPP__
#include <io.h>
  /* For DJGPP redirected input is opened in text mode.  */
#  define set_stdin_to_binary_mode() \
     if (! isatty (0)) setmode (0, O_BINARY)
#else
#  define set_stdin_to_binary_mode() /* Nothing */
#endif

/* This structure represents a file searched for by CPP, whether it
   exists or not.  An instance may be pointed to by more than one
   cpp_file_hash_entry; at present no reference count is kept.  */
struct _cpp_file
{
  /* Filename as given to #include or command line switch.  */
  const char *name;

  /* The full path used to find the file.  */
  const char *path;

  /* The full path of the pch file.  */
  const char *pchname;

  /* The file's path with the basename stripped.  NULL if it hasn't
     been calculated yet.  */
  const char *dir_name;

  /* Chain through all files.  */
  struct _cpp_file *next_file;

  /* The contents of NAME after calling read_file().  */
  const uchar *buffer;

  /* Pointer to the real start of BUFFER.  read_file() might increment
     BUFFER; when freeing, this this pointer must be used instead.  */
  const uchar *buffer_start;

  /* The macro, if any, preventing re-inclusion.  */
  const cpp_hashnode *cmacro;

  /* The directory in the search path where FILE was found.  Used for
     #include_next and determining whether a header is a system
     header.  */
  cpp_dir *dir;

  /* As filled in by stat(2) for the file.  */
  struct stat st;

  /* Size for #embed, perhaps smaller than st.st_size.  */
  size_t limit;

  /* Offset for #embed.  */
  off_t offset;

  /* File descriptor.  Invalid if -1, otherwise open.  */
  int fd;

  /* Zero if this file was successfully opened and stat()-ed,
     otherwise errno obtained from failure.  */
  int err_no;

  /* Number of times the file has been stacked for preprocessing.  */
  unsigned short stack_count;

  /* If opened with #import or contains #pragma once.  */
  bool once_only : 1;

  /* If read() failed before.  */
  bool dont_read : 1;

  /* If BUFFER above contains the true contents of the file.  */
  bool buffer_valid : 1;

  /* If this file is implicitly preincluded.  */
  bool implicit_preinclude : 1;

  /* Set if a header wasn't found with __has_include or __has_include_next
     and error should be emitted if it is included normally.  */
  bool deferred_error : 1;

  /* File loaded from #embed.  */
  bool embed : 1;

  /* > 0: Known C++ Module header unit, <0: known not.  ==0, unknown  */
  int header_unit : 2;
};

/* A singly-linked list for all searches for a given file name, with
   its head pointed to by a slot in FILE_HASH.  The file name is what
   appeared between the quotes in a #include directive; it can be
   determined implicitly from the hash table location or explicitly
   from FILE->name.

   FILE is a structure containing details about the file that was
   found with that search, or details of how the search failed.

   START_DIR is the starting location of the search in the include
   chain.  The current directories for "" includes are also hashed in
   the hash table and therefore unique.  Files that are looked up
   without using a search path, such as absolute filenames and file
   names from the command line share a special starting directory so
   they don't cause cache hits with normal include-chain lookups.

   If START_DIR is NULL then the entry is for a directory, not a file,
   and the directory is in DIR.  Since the starting point in a file
   lookup chain is never NULL, this means that simple pointer
   comparisons against START_DIR can be made to determine cache hits
   in file lookups.

   If a cache lookup fails because of e.g. an extra "./" in the path,
   then nothing will break.  It is just less efficient as CPP will
   have to do more work re-preprocessing the file, and/or comparing
   its contents against earlier once-only files.
*/
struct cpp_file_hash_entry
{
  struct cpp_file_hash_entry *next;
  cpp_dir *start_dir;
  location_t location;
  union
  {
    _cpp_file *file;
    cpp_dir *dir;
  } u;
};

/* Number of entries to put in a cpp_file_hash_entry pool.  */
#define FILE_HASH_POOL_SIZE 127

/* A file hash entry pool.  We allocate cpp_file_hash_entry object from
   one of these.  */
struct file_hash_entry_pool
{
  /* Number of entries used from this pool.  */
  unsigned int file_hash_entries_used;
  /* Next pool in the chain; used when freeing.  */
  struct file_hash_entry_pool *next;
  /* The memory pool.  */
  struct cpp_file_hash_entry pool[FILE_HASH_POOL_SIZE];
};

static bool open_file (_cpp_file *file);
static bool pch_open_file (cpp_reader *pfile, _cpp_file *file,
			   bool *invalid_pch);
static bool find_file_in_dir (cpp_reader *pfile, _cpp_file *file,
			      bool *invalid_pch, location_t loc);
static bool read_file_guts (cpp_reader *pfile, _cpp_file *file,
			    location_t loc, const char *input_charset);
static bool read_file (cpp_reader *pfile, _cpp_file *file,
		       location_t loc);
static const char *dir_name_of_file (_cpp_file *file);
static void open_file_failed (cpp_reader *pfile, _cpp_file *file, int,
			      location_t);
static struct cpp_file_hash_entry *search_cache (struct cpp_file_hash_entry *head,
						 const cpp_dir *start_dir,
						 bool is_embed);
static _cpp_file *make_cpp_file (cpp_dir *, const char *fname);
static void destroy_cpp_file (_cpp_file *);
static cpp_dir *make_cpp_dir (cpp_reader *, const char *dir_name, int sysp);
static void allocate_file_hash_entries (cpp_reader *pfile);
static struct cpp_file_hash_entry *new_file_hash_entry (cpp_reader *pfile);
static int report_missing_guard (void **slot, void *b);
static hashval_t file_hash_hash (const void *p);
static int file_hash_eq (const void *p, const void *q);
static char *read_filename_string (int ch, FILE *f);
static void read_name_map (cpp_dir *dir);
static char *remap_filename (cpp_reader *pfile, _cpp_file *file);
static char *append_file_to_dir (const char *fname, cpp_dir *dir);
static bool validate_pch (cpp_reader *, _cpp_file *file, const char *pchname);
static int pchf_save_compare (const void *e1, const void *e2);
static int pchf_compare (const void *d_p, const void *e_p);
static bool check_file_against_entries (cpp_reader *, _cpp_file *, bool);
static void _cpp_post_stack_file (cpp_reader *, _cpp_file *, include_type, bool);

/* Given a filename in FILE->PATH, with the empty string interpreted
   as <stdin>, open it.

   On success FILE contains an open file descriptor and stat
   information for the file.  On failure the file descriptor is -1 and
   the appropriate errno is also stored in FILE.  Returns TRUE iff
   successful.

   We used to open files in nonblocking mode, but that caused more
   problems than it solved.  Do take care not to acquire a controlling
   terminal by mistake (this can't happen on sane systems, but
   paranoia is a virtue).

   Use the three-argument form of open even though we aren't
   specifying O_CREAT, to defend against broken system headers.

   O_BINARY tells some runtime libraries (notably DJGPP) not to do
   newline translation; we can handle DOS line breaks just fine
   ourselves.  */
static bool
open_file (_cpp_file *file)
{
  if (file->path[0] == '\0')
    {
      file->fd = 0;
      set_stdin_to_binary_mode ();
    }
  else
    file->fd = open (file->path, O_RDONLY | O_NOCTTY | O_BINARY, 0666);

  if (file->fd != -1)
    {
      if (fstat (file->fd, &file->st) == 0)
	{
	  if (!S_ISDIR (file->st.st_mode))
	    {
	      file->err_no = 0;
	      return true;
	    }

	  /* Ignore a directory and continue the search.  The file we're
	     looking for may be elsewhere in the search path.  */
	  errno = ENOENT;
	}

      close (file->fd);
      file->fd = -1;
    }
#if defined(_WIN32) && !defined(__CYGWIN__)
  else if (errno == EACCES)
    {
      /* On most UNIX systems, open succeeds on a directory.  Above,
         we check if we have opened a directory and if so, set errno
         to ENOENT.  However, on Windows, opening a directory
         fails with EACCES.  We want to return ENOENT in that
         case too.  */
      if (stat (file->path, &file->st) == 0
          && S_ISDIR (file->st.st_mode))
        errno = ENOENT;
      else
	/* The call to stat may have reset errno.  */
	errno = EACCES;
    }
#endif
  else if (errno == ENOTDIR)
    errno = ENOENT;

  file->err_no = errno;

  return false;
}

/* Temporary PCH intercept of opening a file.  Try to find a PCH file
   based on FILE->name and FILE->dir, and test those found for
   validity using PFILE->cb.valid_pch.  Return true iff a valid file is
   found.  Set *INVALID_PCH if a PCH file is found but wasn't valid.  */

static bool
pch_open_file (cpp_reader *pfile, _cpp_file *file, bool *invalid_pch)
{
  static const char extension[] = ".gch";
  const char *path = file->path;
  size_t len, flen;
  char *pchname;
  struct stat st;
  bool valid = false;

  /* No PCH on <stdin> or if not requested.  */
  if (file->name[0] == '\0' || !pfile->cb.valid_pch)
    return false;

  /* If the file is not included as first include from either the toplevel
     file or the command-line it is not a valid use of PCH.  */
  for (_cpp_file *f = pfile->all_files; f; f = f->next_file)
    if (f->implicit_preinclude)
      continue;
    else if (pfile->main_file == f)
      break;
    else
      return false;

  flen = strlen (path);
  len = flen + sizeof (extension);
  pchname = XNEWVEC (char, len);
  memcpy (pchname, path, flen);
  memcpy (pchname + flen, extension, sizeof (extension));

  if (stat (pchname, &st) == 0)
    {
      DIR *pchdir;
      struct dirent *d;
      size_t dlen, plen = len;

      if (!S_ISDIR (st.st_mode))
	valid = validate_pch (pfile, file, pchname);
      else if ((pchdir = opendir (pchname)) != NULL)
	{
	  pchname[plen - 1] = '/';
	  while ((d = readdir (pchdir)) != NULL)
	    {
	      dlen = strlen (d->d_name) + 1;
	      if ((strcmp (d->d_name, ".") == 0)
		  || (strcmp (d->d_name, "..") == 0))
		continue;
	      if (dlen + plen > len)
		{
		  len += dlen + 64;
		  pchname = XRESIZEVEC (char, pchname, len);
		}
	      memcpy (pchname + plen, d->d_name, dlen);
	      valid = validate_pch (pfile, file, pchname);
	      if (valid)
		break;
	    }
	  closedir (pchdir);
	}
      if (!valid)
	*invalid_pch = true;
    }

  if (valid)
    file->pchname = pchname;
  else
    free (pchname);

  return valid;
}

/* Canonicalize the path to FILE.  Return the canonical form if it is
   shorter, otherwise return NULL.  This function does NOT free the
   memory pointed by FILE.  */

static char *
maybe_shorter_path (const char * file)
{
  char * file2 = lrealpath (file);
  if (file2 && strlen (file2) < strlen (file))
    {
      return file2;
    }
  else
    {
      free (file2);
      return NULL;
    }
}

/* Try to open the path FILE->name appended to FILE->dir.  This is
   where remap and PCH intercept the file lookup process.  Return true
   if the file was found, whether or not the open was successful.
   Set *INVALID_PCH to true if a PCH file is found but wasn't valid.
   Use LOC when emitting any diagnostics.  */

static bool
find_file_in_dir (cpp_reader *pfile, _cpp_file *file, bool *invalid_pch,
		  location_t loc)
{
  char *path;

  if (CPP_OPTION (pfile, remap) && (path = remap_filename (pfile, file)))
    ;
  else
    if (file->dir->construct)
      path = file->dir->construct (file->name, file->dir);
    else
      path = append_file_to_dir (file->name, file->dir);

  if (path)
    {
      hashval_t hv;
      char *copy;
      void **pp;

      /* We try to canonicalize system headers.  For DOS based file
       * system, we always try to shorten non-system headers, as DOS
       * has a tighter constraint on max path length.  */
      if ((CPP_OPTION (pfile, canonical_system_headers) && file->dir->sysp)
#ifdef HAVE_DOS_BASED_FILE_SYSTEM
	  || !file->dir->sysp
#endif
	 )
	{
	  char * canonical_path = maybe_shorter_path (path);
	  if (canonical_path)
	    {
	      /* The canonical path was newly allocated.  Let's free the
		 non-canonical one.  */
	      free (path);
	      path = canonical_path;
	    }
	}

      hv = htab_hash_string (path);
      if (htab_find_with_hash (pfile->nonexistent_file_hash, path, hv) != NULL)
	{
	  file->err_no = ENOENT;
	  return false;
	}

      file->path = path;
      if (!file->embed && pch_open_file (pfile, file, invalid_pch))
	return true;

      if (open_file (file))
	return true;

      if (file->err_no != ENOENT)
	{
	  open_file_failed (pfile, file, 0, loc);
	  return true;
	}

      /* We copy the path name onto an obstack partly so that we don't
	 leak the memory, but mostly so that we don't fragment the
	 heap.  */
      copy = (char *) obstack_copy0 (&pfile->nonexistent_file_ob, path,
				     strlen (path));
      free (path);
      pp = htab_find_slot_with_hash (pfile->nonexistent_file_hash,
				     copy, hv, INSERT);
      *pp = copy;

      file->path = file->name;
    }
  else
    {
      file->err_no = ENOENT;
      file->path = NULL;
    }

  return false;
}

/* Return true iff the missing_header callback found the given HEADER.  */
static bool
search_path_exhausted (cpp_reader *pfile, const char *header, _cpp_file *file)
{
  missing_header_cb func = pfile->cb.missing_header;

  /* When the regular search path doesn't work, try context dependent
     headers search paths.  */
  if (func
      && file->dir == NULL)
    {
      if ((file->path = func (pfile, header, &file->dir)) != NULL)
	{
	  if (open_file (file))
	    return true;
	  free ((void *)file->path);
	}
      file->path = file->name;
    }

  return false;
}

bool
_cpp_find_failed (_cpp_file *file)
{
  return file->err_no != 0;
}

/* Given a filename FNAME search for such a file in the include path
   starting from START_DIR.  If FNAME is the empty string it is
   interpreted as STDIN if START_DIR is PFILE->no_search_path.

   If the file is not found in the file cache fall back to the O/S and
   add the result to our cache.

   If the file was not found in the filesystem, or there was an error
   opening it, then ERR_NO is nonzero and FD is -1.  If the file was
   found, then ERR_NO is zero and FD could be -1 or an open file
   descriptor.  FD can be -1 if the file was found in the cache and
   had previously been closed.  To open it again pass the return value
   to open_file().

   If KIND is _cpp_FFK_PRE_INCLUDE then it is OK for the file to be
   missing.  If present, it is OK for a precompiled header to be
   included after it.

   Use LOC as the location for any errors.  */

_cpp_file *
_cpp_find_file (cpp_reader *pfile, const char *fname, cpp_dir *start_dir,
		int angle_brackets, _cpp_find_file_kind kind, location_t loc)
{
  bool invalid_pch = false;
  bool saw_bracket_include = false;
  bool saw_quote_include = false;
  bool saw_embed_include = false;
  struct cpp_dir *found_in_cache = NULL;
  bool is_embed = kind == _cpp_FFK_EMBED || kind == _cpp_FFK_HAS_EMBED;

  /* Ensure we get no confusion between cached files and directories.  */
  if (start_dir == NULL)
    cpp_error_at (pfile, CPP_DL_ICE, loc, "NULL directory in %<find_file%>");

  void **hash_slot
    = htab_find_slot_with_hash (pfile->file_hash, fname,
				htab_hash_string (fname), INSERT);

  /* First check the cache before we resort to memory allocation.  */
  cpp_file_hash_entry *entry
    = search_cache ((struct cpp_file_hash_entry *) *hash_slot, start_dir,
		    is_embed);
  if (entry)
    {
      if (entry->u.file->deferred_error
	  && (kind == _cpp_FFK_NORMAL || kind == _cpp_FFK_EMBED))
	{
	  open_file_failed (pfile, entry->u.file, angle_brackets, loc);
	  entry->u.file->deferred_error = false;
	}
      return entry->u.file;
    }

  _cpp_file *file = make_cpp_file (start_dir, fname);
  file->implicit_preinclude
    = (kind == _cpp_FFK_PRE_INCLUDE
       || (pfile->buffer && pfile->buffer->file->implicit_preinclude));
  file->embed = is_embed;

  if (kind == _cpp_FFK_FAKE)
    file->dont_read = true;
  else
    /* Try each path in the include chain.  */
    for (;;)
      {
	if (find_file_in_dir (pfile, file, &invalid_pch, loc))
	  break;

	if (is_embed
	    && file->dir == start_dir
	    && start_dir != pfile->embed_include
	    && start_dir != &pfile->no_search_path)
	  file->dir = pfile->embed_include;
	else
	  file->dir = file->dir->next;
	if (file->dir == NULL)
	  {
	    if (!is_embed
		&& search_path_exhausted (pfile, fname, file))
	      {
		/* Although this file must not go in the cache,
		   because the file found might depend on things (like
		   the current file) that aren't represented in the
		   cache, it still has to go in the list of all files
		   so that #import works.  */
		file->next_file = pfile->all_files;
		pfile->all_files = file;
		if (*hash_slot == NULL)
		  {
		    /* If *hash_slot is NULL, the above
		       htab_find_slot_with_hash call just created the
		       slot, but we aren't going to store there anything
		       of use, so need to remove the newly created entry.
		       htab_clear_slot requires that it is non-NULL, so
		       store some non-NULL but valid pointer there,
		       htab_clear_slot will immediately overwrite it.  */
		    *hash_slot = file;
		    htab_clear_slot (pfile->file_hash, hash_slot);
		  }
		return file;
	      }

	    if (invalid_pch)
	      {
		cpp_error (pfile, CPP_DL_ERROR,
			   "one or more PCH files were found,"
			   " but they were invalid");
		if (!cpp_get_options (pfile)->warn_invalid_pch)
		  cpp_error (pfile, CPP_DL_NOTE,
			     "use %<-Winvalid-pch%> for more information");
	      }

	    if (kind == _cpp_FFK_PRE_INCLUDE)
	      {
		free ((char *) file->name);
		free (file);
		if (*hash_slot == NULL)
		  {
		    /* See comment on the above htab_clear_slot call.  */
		    *hash_slot = &hash_slot;
		    htab_clear_slot (pfile->file_hash, hash_slot);
		  }
		return NULL;
	      }

	    if (kind != _cpp_FFK_HAS_INCLUDE && kind != _cpp_FFK_HAS_EMBED)
	      open_file_failed (pfile, file, angle_brackets, loc);
	    else
	      file->deferred_error = true;
	    break;
	  }

	/* Only check the cache for the starting location (done above)
	   and the quote and bracket chain heads because there are no
	   other possible starting points for searches.  */
	if (file->dir == pfile->bracket_include)
	  saw_bracket_include = true;
	else if (file->dir == pfile->quote_include)
	  saw_quote_include = true;
	else if (file->dir == pfile->embed_include)
	  saw_embed_include = true;
	else
	  continue;

	entry
	  = search_cache ((struct cpp_file_hash_entry *) *hash_slot,
			  file->dir, is_embed);
	if (entry)
	  {
	    found_in_cache = file->dir;
	    break;
	  }
      }

  if (entry)
    {
      /* Cache for START_DIR too, sharing the _cpp_file structure.  */
      free ((char *) file->name);
      free (file);
      file = entry->u.file;
    }
  else
    {
      /* This is a new file; put it in the list.  */
      file->next_file = pfile->all_files;
      pfile->all_files = file;
    }

  /* Store this new result in the hash table.  */
  entry = new_file_hash_entry (pfile);
  entry->next = (struct cpp_file_hash_entry *) *hash_slot;
  entry->start_dir = start_dir;
  entry->location = loc;
  entry->u.file = file;
  *hash_slot = (void *) entry;

  /* If we passed the quote or bracket chain heads, cache them also.
     This speeds up processing if there are lots of -I options.  */
  if (saw_bracket_include
      && pfile->bracket_include != start_dir
      && found_in_cache != pfile->bracket_include)
    {
      entry = new_file_hash_entry (pfile);
      entry->next = (struct cpp_file_hash_entry *) *hash_slot;
      entry->start_dir = pfile->bracket_include;
      entry->location = loc;
      entry->u.file = file;
      *hash_slot = (void *) entry;
    }
  if (saw_quote_include
      && pfile->quote_include != start_dir
      && found_in_cache != pfile->quote_include)
    {
      entry = new_file_hash_entry (pfile);
      entry->next = (struct cpp_file_hash_entry *) *hash_slot;
      entry->start_dir = pfile->quote_include;
      entry->location = loc;
      entry->u.file = file;
      *hash_slot = (void *) entry;
    }
  if (saw_embed_include
      && pfile->embed_include != start_dir
      && found_in_cache != pfile->embed_include)
    {
      entry = new_file_hash_entry (pfile);
      entry->next = (struct cpp_file_hash_entry *) *hash_slot;
      entry->start_dir = pfile->embed_include;
      entry->location = loc;
      entry->u.file = file;
      *hash_slot = (void *) entry;
    }

  return file;
}

/* Read a file into FILE->buffer, returning true on success.

   If FILE->fd is something weird, like a block device, we don't want
   to read it at all.  Don't even try to figure out what something is,
   except for plain files and block devices, since there is no
   reliable portable way of doing this.

   Use LOC for any diagnostics.

   PFILE may be NULL.  In this case, no diagnostics are issued.

   FIXME: Flush file cache and try again if we run out of memory.  */
static bool
read_file_guts (cpp_reader *pfile, _cpp_file *file, location_t loc,
		const char *input_charset)
{
  ssize_t size, pad, total, count;
  uchar *buf;
  bool regular;

  if (S_ISBLK (file->st.st_mode))
    {
      if (pfile)
	cpp_error_at (pfile, CPP_DL_ERROR, loc,
		      "%s is a block device", file->path);
      return false;
    }

  regular = S_ISREG (file->st.st_mode) != 0;
  if (regular)
    {
      /* off_t might have a wider range than ssize_t - in other words,
	 the max size of a file might be bigger than the address
	 space.  We can't handle a file that large.  (Anyone with
	 a single source file bigger than 2GB needs to rethink
	 their coding style.)  Some systems (e.g. AIX 4.1) define
	 SSIZE_MAX to be much smaller than the actual range of the
	 type.  Use INTTYPE_MAXIMUM unconditionally to ensure this
	 does not bite us.  */
      if (file->st.st_size > INTTYPE_MAXIMUM (ssize_t))
	{
	  if (pfile)
	    cpp_error_at (pfile, CPP_DL_ERROR, loc,
			  "%s is too large", file->path);
	  return false;
	}

      size = file->st.st_size;
    }
  else
    /* 8 kilobytes is a sensible starting size.  It ought to be bigger
       than the kernel pipe buffer, and it's definitely bigger than
       the majority of C source files.  */
    size = 8 * 1024;

  pad = CPP_BUFFER_PADDING;
  /* The '+ PAD' here is space for the final '\n' and PAD-1 bytes of padding,
     allowing search_line_fast to use (possibly misaligned) vector loads.  */
  buf = XNEWVEC (uchar, size + pad);
  total = 0;
  while ((count = read (file->fd, buf + total, size - total)) > 0)
    {
      total += count;

      if (total == size)
	{
	  if (regular)
	    break;
	  size *= 2;
	  buf = XRESIZEVEC (uchar, buf, size + pad);
	}
    }

  if (count < 0)
    {
      if (pfile)
	cpp_errno_filename (pfile, CPP_DL_ERROR, file->path, loc);
      free (buf);
      return false;
    }

  if (pfile && regular && total != size && STAT_SIZE_RELIABLE (file->st))
    cpp_error_at (pfile, CPP_DL_WARNING, loc,
		  "%s is shorter than expected", file->path);

  file->buffer = _cpp_convert_input (pfile,
				     input_charset,
				     buf, size + pad, total,
				     &file->buffer_start,
				     &file->st.st_size);
  file->buffer_valid = file->buffer;
  return file->buffer_valid;
}

/* Convenience wrapper around read_file_guts that opens the file if
   necessary and closes the file descriptor after reading.  FILE must
   have been passed through find_file() at some stage.  Use LOC for
   any diagnostics.  Unlike read_file_guts(), PFILE may not be NULL.  */
static bool
read_file (cpp_reader *pfile, _cpp_file *file, location_t loc)
{
  /* If we already have its contents in memory, succeed immediately.  */
  if (file->buffer_valid)
    return true;

  /* If an earlier read failed for some reason don't try again.  */
  if (file->dont_read || file->err_no)
    return false;

  if (file->fd == -1 && !open_file (file))
    {
      open_file_failed (pfile, file, 0, loc);
      return false;
    }

  file->dont_read = !read_file_guts (pfile, file, loc,
				     CPP_OPTION (pfile, input_charset));
  close (file->fd);
  file->fd = -1;

  return !file->dont_read;
}

/* Returns TRUE if FILE is already known to be idempotent, and should
   therefore not be read again.  */
static bool
is_known_idempotent_file (cpp_reader *pfile, _cpp_file *file, bool import)
{
  /* Skip once-only files.  */
  if (file->once_only)
    return true;

  /* We must mark the file once-only if #import now, before header
     guard checks.  Otherwise, undefining the header guard might
     cause the file to be re-stacked.  */
  if (import)
    {
      _cpp_mark_file_once_only (pfile, file);

      /* Don't stack files that have been stacked before.  */
      if (file->stack_count)
	return true;
    }

  /* Skip if the file had a header guard and the macro is defined.
     PCH relies on this appearing before the PCH handler below.  */
  if (file->cmacro && cpp_macro_p (file->cmacro))
    return true;

  /* Handle PCH files immediately; don't stack them.  */
  if (file->pchname)
    {
      pfile->cb.read_pch (pfile, file->pchname, file->fd, file->path);
      file->fd = -1;
      free ((void *) file->pchname);
      file->pchname = NULL;
      return true;
    }

  return false;
}

/* Return TRUE if file has unique contents, so we should read process
   it.  The file's contents must already have been read.  */

static bool
has_unique_contents (cpp_reader *pfile, _cpp_file *file, bool import,
		     location_t loc)
{
  /* Check the file against the PCH file.  This is done before
     checking against files we've already seen, since it may save on
     I/O.  */
  if (check_file_against_entries (pfile, file, import))
    {
      /* If this isn't a #import, but yet we can't include the file,
	 that means that it was #import-ed in the PCH file,
	 so we can never include it again.  */
      if (! import)
	_cpp_mark_file_once_only (pfile, file);
      return false;
    }

  /* Now we've read the file's contents, we can stack it if there
     are no once-only files.  */
  if (!pfile->seen_once_only)
    return true;

  /* We may have read the file under a different name.  Look
     for likely candidates and compare file contents to be sure.  */
  for (_cpp_file *f = pfile->all_files; f; f = f->next_file)
    {
      if (f == file)
	continue; /* It'sa me!  */

      if (f->embed)
	continue;

      if ((import || f->once_only)
	  && f->err_no == 0
	  && f->st.st_mtime == file->st.st_mtime
	  && f->st.st_size == file->st.st_size)
	{
	  _cpp_file *ref_file;

	  if (f->buffer && !f->buffer_valid)
	    {
	      /* We already have a buffer but it is not valid, because
		 the file is still stacked.  Make a new one.  */
	      ref_file = make_cpp_file (f->dir, f->name);
	      ref_file->path = f->path;
	    }
	  else
	    /* The file is not stacked anymore.  We can reuse it.  */
	    ref_file = f;

	  bool same_file_p = (read_file (pfile, ref_file, loc)
			      /* Size might have changed in read_file().  */
			      && ref_file->st.st_size == file->st.st_size
			      && !memcmp (ref_file->buffer, file->buffer,
					  file->st.st_size));

	  if (f->buffer && !f->buffer_valid)
	    {
	      ref_file->path = 0;
	      destroy_cpp_file (ref_file);
	    }

	  if (same_file_p)
	    /* Already seen under a different name.  */
	    return false;
	}
    }

  return true;
}

/* Place the file referenced by FILE into a new buffer on the buffer
   stack if possible.  Returns true if a buffer is stacked.  Use LOC
   for any diagnostics.  */

bool
_cpp_stack_file (cpp_reader *pfile, _cpp_file *file, include_type type,
		 location_t loc)
{
  int sysp = 0;

  /* Not a header unit, and we know it.  */
  file->header_unit = -1;

  if (!read_file (pfile, file, loc))
    return false;

  if (!has_unique_contents (pfile, file, type == IT_IMPORT, loc))
    return false;

  if (pfile->buffer && file->dir)
    sysp = MAX (pfile->buffer->sysp, file->dir->sysp);

  /* Add the file to the dependencies on its first inclusion.  */
  if (CPP_OPTION (pfile, deps.style) > (sysp != 0)
      && !file->stack_count
      && !(pfile->main_file == file
	   && CPP_OPTION (pfile, deps.ignore_main_file)))
    deps_add_dep (pfile->deps, file->path);

  /* Clear buffer_valid since _cpp_clean_line messes it up.  */
  file->buffer_valid = false;
  file->stack_count++;

  /* Stack the buffer.  */
  cpp_buffer *buffer
    = cpp_push_buffer (pfile, file->buffer, file->st.st_size,
		       CPP_OPTION (pfile, preprocessed)
		       && !CPP_OPTION (pfile, directives_only));
  buffer->file = file;
  buffer->sysp = sysp;
  buffer->to_free = file->buffer_start;

  /* Initialize controlling macro state.  */
  pfile->mi_valid = true;
  pfile->mi_cmacro = 0;

  _cpp_post_stack_file (pfile, file, type, sysp);
  return true;
}

/* Like _cpp_stack_file, but for a file that's been replaced by the contents of
   BUF.  Used for C++ modules include -> import translation.  */

static bool
_cpp_stack_translated_file (cpp_reader *pfile, _cpp_file *file,
			    char *buf, include_type type)
{
  /* We don't increment the line number at the end of a buffer,
     because we don't usually need that location (we're popping an
     include file).  However in this case we do want to do the
     increment.  So push a writable buffer of two newlines to achieve
     that.  (We also need an extra newline, so this looks like a regular
     file, which we do that to to make sure we don't fall off the end in the
     middle of a line.  */
  if (type != IT_CMDLINE)
    {
      static uchar newlines[] = "\n\n\n";
      cpp_push_buffer (pfile, newlines, 2, true);
    }

  size_t len = strlen (buf);
  buf[len] = '\n'; /* See above  */
  cpp_buffer *buffer
    = cpp_push_buffer (pfile, reinterpret_cast<unsigned char *> (buf),
		       len, true);
  buffer->to_free = buffer->buf;
  if (type == IT_CMDLINE)
    /* Tell _cpp_pop_buffer to change files.  */
    buffer->file = file;

  file->header_unit = +1;
  _cpp_mark_file_once_only (pfile, file);

  _cpp_post_stack_file (pfile, file, type, false);
  return true;
}

/* The common epilogue of _cpp_stack_file and _cpp_stack_translated_file.  */

static void
_cpp_post_stack_file (cpp_reader *pfile, _cpp_file *file, include_type type,
		      bool sysp)
{
  /* In the case of a normal #include, we're now at the start of the
     line *following* the #include.  A separate location_t for this
     location makes no sense, until we do the LC_LEAVE.

     This does not apply if we found a PCH file, we're not a regular
     include, or we ran out of locations.  */
  bool decrement = (file->pchname == NULL
		    && type < IT_DIRECTIVE_HWM
		    && (pfile->line_table->highest_location
			!= LINE_MAP_MAX_LOCATION - 1));

  if (decrement)
    pfile->line_table->highest_location--;

  /* Normally a header unit becomes an __import directive in the current file,
     but with -include we need something to LC_LEAVE to trigger the file_change
     hook and continue to the next -include or the main source file.  */
  if (file->header_unit <= 0 || type == IT_CMDLINE)
    /* Add line map and do callbacks.  */
    _cpp_do_file_change (pfile, LC_ENTER, file->path,
		       /* With preamble injection, start on line zero,
			  so the preamble doesn't appear to have been
			  included from line 1.  Likewise when
			  starting preprocessed, we expect an initial
			  locating line.  */
			 type == IT_PRE_MAIN ? 0 : 1, sysp);
  else if (decrement)
    {
      /* Adjust the line back one so we appear on the #include line itself.  */
      const line_map_ordinary *map
	= LINEMAPS_LAST_ORDINARY_MAP (pfile->line_table);
      linenum_type line = SOURCE_LINE (map, pfile->line_table->highest_line);
      linemap_line_start (pfile->line_table, line - 1, 0);
    }
}

/* Mark FILE to be included once only.  */
void
_cpp_mark_file_once_only (cpp_reader *pfile, _cpp_file *file)
{
  pfile->seen_once_only = true;
  file->once_only = true;
}

/* Return the directory from which searching for FNAME should start,
   considering the directive TYPE and ANGLE_BRACKETS.  If there is
   nothing left in the path, returns NULL.  */
struct cpp_dir *
search_path_head (cpp_reader *pfile, const char *fname, int angle_brackets,
		  enum include_type type, bool suppress_diagnostic)
{
  cpp_dir *dir;
  _cpp_file *file;

  if (IS_ABSOLUTE_PATH (fname) || *fname == '\0')
    return &pfile->no_search_path;

  /* pfile->buffer is NULL when processing an -include command-line flag.  */
  file = pfile->buffer == NULL ? pfile->main_file : pfile->buffer->file;

  /* For #include_next, skip in the search path past the dir in which
     the current file was found, but if it was found via an absolute
     path use the normal search logic.  */
  if (type == IT_INCLUDE_NEXT && file->dir
      && file->dir != &pfile->no_search_path)
    dir = file->dir->next;
  else if (angle_brackets)
    dir = type == IT_EMBED ? pfile->embed_include : pfile->bracket_include;
  else if (type == IT_CMDLINE)
    /* -include and -imacros use the #include "" chain with the
       preprocessor's cwd prepended.  */
    return make_cpp_dir (pfile, "./", false);
  else if (pfile->quote_ignores_source_dir && type != IT_EMBED)
    dir = pfile->quote_include;
  else
    return make_cpp_dir (pfile, dir_name_of_file (file),
			 pfile->buffer ? pfile->buffer->sysp : 0);

  if (dir == NULL && !suppress_diagnostic)
    cpp_error (pfile, CPP_DL_ERROR,
	       "no include path in which to search for %s", fname);

  return dir;
}

/* Strip the basename from the file's path.  It ends with a slash if
   of nonzero length.  Note that this procedure also works for
   <stdin>, which is represented by the empty string.  */
static const char *
dir_name_of_file (_cpp_file *file)
{
  if (!file->dir_name)
    {
      size_t len = lbasename (file->path) - file->path;
      char *dir_name = XNEWVEC (char, len + 1);

      memcpy (dir_name, file->path, len);
      dir_name[len] = '\0';
      file->dir_name = dir_name;
    }

  return file->dir_name;
}

/* Handles #include-family directives (distinguished by TYPE),
   including HEADER, and the command line -imacros and -include.
   Returns true if a buffer was stacked.  */
bool
_cpp_stack_include (cpp_reader *pfile, const char *fname, int angle_brackets,
		    enum include_type type, location_t loc)
{
  /* For -include command-line flags we have type == IT_CMDLINE.
     When the first -include file is processed we have the case, where
     pfile->cur_token == pfile->cur_run->base, we are directly called up
     by the front end.  However in the case of the second -include file,
     we are called from _cpp_lex_token -> _cpp_get_fresh_line ->
     cpp_push_include, with pfile->cur_token != pfile->cur_run->base,
     and pfile->cur_token[-1].src_loc not (yet) initialized.
     However, when the include file cannot be found, we need src_loc to
     be initialized to some safe value: 0 means UNKNOWN_LOCATION.  */
  if (type == IT_CMDLINE && pfile->cur_token != pfile->cur_run->base)
    pfile->cur_token[-1].src_loc = 0;

  cpp_dir *dir = search_path_head (pfile, fname, angle_brackets, type);
  if (!dir)
    return false;

  _cpp_file *file = _cpp_find_file (pfile, fname, dir, angle_brackets,
				    type == IT_DEFAULT ? _cpp_FFK_PRE_INCLUDE
				    : _cpp_FFK_NORMAL, loc);
  if (type == IT_DEFAULT && file == NULL)
    return false;

  if (is_known_idempotent_file (pfile, file, type == IT_IMPORT))
    return false;

  /* Check C++ module include translation.  */
  char *buf = nullptr;
  if (!file->header_unit && type < IT_DEFAULT
      /* Do not include translate include-next.  */
      && type != IT_INCLUDE_NEXT
      && pfile->cb.translate_include)
    {
      const char *aname = nullptr;
      buf = (pfile->cb.translate_include
	     (pfile, pfile->line_table, loc, file,
	      angle_brackets, &aname));
      if (!buf && aname)
	{
	  _cpp_file *afile = _cpp_find_file (pfile, aname, dir, angle_brackets,
					     _cpp_FFK_NORMAL, loc);
	  if (afile && !afile->header_unit)
	    buf = (pfile->cb.translate_include
		   (pfile, pfile->line_table, loc,
		    afile, angle_brackets, nullptr));
	  if (buf)
	    file = afile;
	}
    }

  if (buf)
    return _cpp_stack_translated_file (pfile, file, buf, type);
  else
    return _cpp_stack_file (pfile, file, type, loc);
}

/* NAME is a header file name, find the _cpp_file, if any.  */

static _cpp_file *
test_header_unit (cpp_reader *pfile, const char *name, bool angle,
		  location_t loc)
{
  if (cpp_dir *dir = search_path_head (pfile, name, angle, IT_INCLUDE))
    return _cpp_find_file (pfile, name, dir, angle, _cpp_FFK_NORMAL, loc);

  return nullptr;
}

/* NAME is a header file name, find the path we'll use to open it and infer that
   it is a header-unit.  */

const char *
_cpp_find_header_unit (cpp_reader *pfile, const char *name, bool angle,
		       location_t loc)
{
  if (_cpp_file *file = test_header_unit (pfile, name, angle, loc))
    {
      if (file->fd > 0)
	{
	  /* Don't leave it open.  */
	  close (file->fd);
	  file->fd = 0;
	}

      file->header_unit = +1;
      _cpp_mark_file_once_only (pfile, file);

      return file->path;
    }

  return nullptr;
}

/* NAME is a header file name, find the path we'll use to open it.  But do not
   infer it is a header unit.  */

const char *
cpp_probe_header_unit (cpp_reader *pfile, const char *name, bool angle,
		       location_t loc)
{
  if (_cpp_file *file = test_header_unit (pfile, name, angle, loc))
    return file->path;

  return nullptr;
}

/* Helper function for _cpp_stack_embed.  Finish #embed/__has_embed processing
   after a file is found and data loaded into buffer.  */

static int
finish_embed (cpp_reader *pfile, _cpp_file *file,
	      struct cpp_embed_params *params)
{
  const uchar *buffer = file->buffer;
  size_t limit = file->limit;
  if (params->offset - file->offset > limit)
    limit = 0;
  else
    {
      buffer += params->offset - file->offset;
      limit -= params->offset - file->offset;
    }
  if (params->limit < limit)
    limit = params->limit;

  size_t embed_tokens = 0;
  if (CPP_OPTION (pfile, lang) != CLK_ASM
      && limit >= 64)
    embed_tokens = ((limit - 2) / INT_MAX) + (((limit - 2) % INT_MAX) != 0);

  size_t max = INTTYPE_MAXIMUM (size_t) / sizeof (cpp_token);
  if ((embed_tokens ? (embed_tokens > (max - 3) / 2) : (limit > max / 2))
      || (limit
	  ? (params->prefix.count > max
	     || params->suffix.count > max
	     || ((embed_tokens ? embed_tokens * 2 + 3 : limit * 2 - 1)
		 + params->prefix.count
		 + params->suffix.count > max))
	  : params->if_empty.count > max))
    {
      cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
		    "%s is too large", file->path);
      return 0;
    }

  size_t len = 0;
  for (size_t i = 0; i < limit; ++i)
    {
      if (buffer[i] < 10)
	len += 2;
      else if (buffer[i] < 100)
	len += 3;
#if UCHAR_MAX == 255
      else
	len += 4;
#else
      else if (buffer[i] < 1000)
	len += 4;
      else
	{
	  char buf[64];
	  len += sprintf (buf, "%d", buffer[i]) + 1;
	}
#endif
      if (len > INTTYPE_MAXIMUM (ssize_t))
	{
	  cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
			"%s is too large", file->path);
	  return 0;
	}
      if (embed_tokens && i == 0)
	i = limit - 2;
    }
  uchar *s = len ? _cpp_unaligned_alloc (pfile, len) : NULL;
  _cpp_buff *tok_buff = NULL;
  cpp_token *tok = &pfile->directive_result, *toks = tok;
  size_t count = 0;
  if (limit)
    count = (params->prefix.count
	     + (embed_tokens ? embed_tokens * 2 + 3 : limit * 2 - 1)
	     + params->suffix.count) - 1;
  else if (params->if_empty.count)
    count = params->if_empty.count - 1;
  if (count)
    {
      tok_buff = _cpp_get_buff (pfile, count * sizeof (cpp_token));
      toks = (cpp_token *) tok_buff->base;
    }
  cpp_embed_params_tokens *prefix
    = limit ? &params->prefix : &params->if_empty;
  if (prefix->count)
    {
      *tok = *prefix->base_run.base;
      tok = toks;
      tokenrun *cur_run = &prefix->base_run;
      while (cur_run)
	{
	  size_t cnt = (cur_run->next ? cur_run->limit
			: prefix->cur_token) - cur_run->base;
	  cpp_token *t = cur_run->base;
	  if (cur_run == &prefix->base_run)
	    {
	      t++;
	      cnt--;
	    }
	  memcpy (tok, t, cnt * sizeof (cpp_token));
	  tok += cnt;
	  cur_run = cur_run->next;
	}
    }
  for (size_t i = 0; i < limit; ++i)
    {
      tok->src_loc = params->loc;
      tok->type = CPP_NUMBER;
      tok->flags = NO_EXPAND;
      if (i == 0)
	tok->flags |= PREV_WHITE;
      tok->val.str.text = s;
      tok->val.str.len = sprintf ((char *) s, "%d", buffer[i]);
      s += tok->val.str.len + 1;
      if (tok == &pfile->directive_result)
	tok = toks;
      else
	tok++;
      if (i < limit - 1)
	{
	  tok->src_loc = params->loc;
	  tok->type = CPP_COMMA;
	  tok->flags = NO_EXPAND;
	  tok++;
	}
      if (i == 0 && embed_tokens)
	{
	  ++i;
	  for (size_t j = 0; j < embed_tokens; ++j)
	    {
	      tok->src_loc = params->loc;
	      tok->type = CPP_EMBED;
	      tok->flags = NO_EXPAND;
	      tok->val.str.text = &buffer[i];
	      tok->val.str.len
		= limit - 1 - i > INT_MAX ? INT_MAX : limit - 1 - i;
	      i += tok->val.str.len;
	      if (tok->val.str.len < 32 && j)
		{
		  /* Avoid CPP_EMBED with a fewer than 32 bytes, shrink the
		     previous CPP_EMBED by 64 and grow this one by 64.  */
		  tok[-2].val.str.len -= 64;
		  tok->val.str.text -= 64;
		  tok->val.str.len += 64;
		}
	      tok++;
	      tok->src_loc = params->loc;
	      tok->type = CPP_COMMA;
	      tok->flags = NO_EXPAND;
	      tok++;
	    }
	  --i;
	}
    }
  if (limit && params->suffix.count)
    {
      tokenrun *cur_run = &params->suffix.base_run;
      cpp_token *orig_tok = tok;
      while (cur_run)
	{
	  size_t cnt = (cur_run->next ? cur_run->limit
			: params->suffix.cur_token) - cur_run->base;
	  cpp_token *t = cur_run->base;
	  memcpy (tok, t, cnt * sizeof (cpp_token));
	  tok += cnt;
	  cur_run = cur_run->next;
	}
      orig_tok->flags |= PREV_WHITE;
    }
  pfile->directive_result.flags |= PREV_WHITE;
  if (count)
    {
      _cpp_push_token_context (pfile, NULL, toks, count);
      pfile->context->buff = tok_buff;
    }
  return limit ? 1 : 2;
}

/* Helper function for initialization of base64_dec table.
   Can't rely on ASCII compatibility, so check each letter
   separately.  */

constexpr signed char
base64_dec_fn (unsigned char c)
{
  return (c == 'A' ? 0 : c == 'B' ? 1 : c == 'C' ? 2 : c == 'D' ? 3
	  : c == 'E' ? 4 : c == 'F' ? 5 : c == 'G' ? 6 : c == 'H' ? 7
	  : c == 'I' ? 8 : c == 'J' ? 9 : c == 'K' ? 10 : c == 'L' ? 11
	  : c == 'M' ? 12 : c == 'N' ? 13 : c == 'O' ? 14 : c == 'P' ? 15
	  : c == 'Q' ? 16 : c == 'R' ? 17 : c == 'S' ? 18 : c == 'T' ? 19
	  : c == 'U' ? 20 : c == 'V' ? 21 : c == 'W' ? 22 : c == 'X' ? 23
	  : c == 'Y' ? 24 : c == 'Z' ? 25
	  : c == 'a' ? 26 : c == 'b' ? 27 : c == 'c' ? 28 : c == 'd' ? 29
	  : c == 'e' ? 30 : c == 'f' ? 31 : c == 'g' ? 32 : c == 'h' ? 33
	  : c == 'i' ? 34 : c == 'j' ? 35 : c == 'k' ? 36 : c == 'l' ? 37
	  : c == 'm' ? 38 : c == 'n' ? 39 : c == 'o' ? 40 : c == 'p' ? 41
	  : c == 'q' ? 42 : c == 'r' ? 43 : c == 's' ? 44 : c == 't' ? 45
	  : c == 'u' ? 46 : c == 'v' ? 47 : c == 'w' ? 48 : c == 'x' ? 49
	  : c == 'y' ? 50 : c == 'z' ? 51
	  : c == '0' ? 52 : c == '1' ? 53 : c == '2' ? 54 : c == '3' ? 55
	  : c == '4' ? 56 : c == '5' ? 57 : c == '6' ? 58 : c == '7' ? 59
	  : c == '8' ? 60 : c == '9' ? 61 : c == '+' ? 62 : c == '/' ? 63
	  : -1);
}

/* base64 decoding table.  */

static constexpr signed char base64_dec[] = {
#define B64D0(x) base64_dec_fn (x)
#define B64D1(x) B64D0 (x), B64D0 (x + 1), B64D0 (x + 2), B64D0 (x + 3)
#define B64D2(x) B64D1 (x), B64D1 (x + 4), B64D1 (x + 8), B64D1 (x + 12)
#define B64D3(x) B64D2 (x), B64D2 (x + 16), B64D2 (x + 32), B64D2 (x + 48)
  B64D3 (0), B64D3 (64), B64D3 (128), B64D3 (192)
};

/* Helper function for _cpp_stack_embed.  Handle #embed/__has_embed with
   gnu::base64 parameter.  */

static int
finish_base64_embed (cpp_reader *pfile, const char *fname, bool angle,
		     struct cpp_embed_params *params)
{
  size_t len, end, i, j, base64_len = 0, cnt;
  uchar *buf = NULL, *q, pbuf[4], qbuf[3];
  const uchar *base64_str;
  if (angle || strcmp (fname, "."))
    {
      if (!params->has_embed)
	cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
		      "%<gnu::base64%> parameter can be only used with "
		      "%<\".\"%>");
      return 0;
    }
  tokenrun *cur_run = &params->base64.base_run;
  cpp_token *tend, *tok;
  while (cur_run)
    {
      tend = cur_run->next ? cur_run->limit : params->base64.cur_token;
      for (tok = cur_run->base; tok < tend; ++tok)
	{
	  if (tok->val.str.len < 2
	      || tok->val.str.text[0] != '"'
	      || tok->val.str.text[tok->val.str.len - 1] != '"')
	    {
	    fail:
	      cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
			    "%<gnu::base64%> argument not valid base64 "
			    "encoded string");
	      free (buf);
	      return 0;
	    }
	  if (tok->val.str.len - 2 > (~(size_t) 0) - base64_len)
	    goto fail;
	  base64_len += tok->val.str.len - 2;
	}
      cur_run = cur_run->next;
    }
  if ((base64_len & 3) != 0)
    goto fail;
  len = base64_len / 4 * 3;
  end = len;

  if (params->has_embed)
    q = qbuf;
  else
    {
      buf = XNEWVEC (uchar, len ? len : 1);
      q = buf;
    }
  cur_run = &params->base64.base_run;
  tend = cur_run->next ? cur_run->limit : params->base64.cur_token;
  tok = cur_run->base;
  base64_str = tok->val.str.text + 1;
  cnt = tok->val.str.len - 2;
  ++tok;
  for (i = 0; i < end; i += 3)
    {
      for (j = 0; j < 4; ++j)
	{
	  while (cnt == 0)
	    {
	      if (tok == tend)
		{
		  cur_run = cur_run->next;
		  tend = (cur_run->next ? cur_run->limit
			  : params->base64.cur_token);
		  tok = cur_run->base;
		}
	      base64_str = tok->val.str.text + 1;
	      cnt = tok->val.str.len - 2;
	      ++tok;
	    }
	  pbuf[j] = *base64_str;
	  base64_str++;
	  --cnt;
	}
      if (pbuf[3] == '=' && i + 3 >= end)
	{
	  end = len - 3;
	  --len;
	  if (pbuf[2] == '=')
	    --len;
	  break;
	}
      int a = base64_dec[pbuf[0]];
      int b = base64_dec[pbuf[1]];
      int c = base64_dec[pbuf[2]];
      int d = base64_dec[pbuf[3]];
      if (a == -1 || b == -1 || c == -1 || d == -1)
	goto fail;
      q[0] = (a << 2) | (b >> 4);
      q[1] = (b << 4) | (c >> 2);
      q[2] = (c << 6) | d;
      if (!params->has_embed)
	q += 3;
    }
  if (len != end)
    {
      int a = base64_dec[pbuf[0]];
      int b = base64_dec[pbuf[1]];
      if (a == -1 || b == -1)
	goto fail;
      q[0] = (a << 2) | (b >> 4);
      if (len - end == 2)
	{
	  int c = base64_dec[pbuf[2]];
	  if (c == -1)
	    goto fail;
	  q[1] = (b << 4) | (c >> 2);
	  if ((c & 3) != 0)
	    goto fail;
	}
      else if ((b & 15) != 0)
	goto fail;
    }
  if (params->has_embed)
    return len ? 1 : 2;
  _cpp_file *file = make_cpp_file (NULL, "");
  file->embed = 1;
  file->next_file = pfile->all_files;
  pfile->all_files = file;
  params->limit = -1;
  params->offset = 0;
  file->limit = len;
  file->buffer = buf;
  file->path = xstrdup ("<base64>");
  return finish_embed (pfile, file, params);
}

/* Try to load FNAME with #embed/__has_embed parameters PARAMS.
   If !PARAMS->has_embed, return new token in pfile->directive_result
   (first token) and rest in a pushed non-macro context.
   Returns 0 for not found/errors, 1 for non-empty resource and 2
   for empty resource.  */

int
_cpp_stack_embed (cpp_reader *pfile, const char *fname, bool angle,
		  struct cpp_embed_params *params)
{
  if (params->base64.count)
    return finish_base64_embed (pfile, fname, angle, params);
  cpp_dir *dir = search_path_head (pfile, fname, angle, IT_EMBED,
				   params->has_embed);
  if (!dir)
    return 0;
  _cpp_file *file = _cpp_find_file (pfile, fname, dir, angle,
				    params->has_embed
				    ? _cpp_FFK_HAS_EMBED : _cpp_FFK_EMBED,
				    params->loc);
  if (!file)
    return 0;
  if (file->dont_read || file->err_no)
    return 0;
  _cpp_file *orig_file = file;
  if (file->buffer_valid
      && (!S_ISREG (file->st.st_mode)
	  || file->offset + (cpp_num_part) 0 > params->offset
	  || (file->limit < file->st.st_size - file->offset + (size_t) 0
	      && (params->offset - file->offset > (cpp_num_part) file->limit
		  || file->limit - (params->offset
				    - file->offset) < params->limit))))
    {
      bool found = false;
      if (S_ISREG (file->st.st_mode))
	{
	  while (file->next_file
		 && file->next_file->embed
		 && file->next_file->buffer_valid
		 && file->next_file->dir == file->dir
		 && strcmp (file->name, file->next_file->name) == 0
		 && strcmp (file->path, file->next_file->path) == 0)
	    {
	      file = file->next_file;
	      if (file->offset + (cpp_num_part) 0 <= params->offset
		  && (file->limit >= (file->st.st_size - file->offset
				      + (size_t) 0)
		      || (params->offset
			  - file->offset <= (cpp_num_part) file->limit
			  && file->limit - (params->offset
					    - file->offset) >= params->limit)))
		{
		  found = true;
		  break;
		}
	    }
	}
      if (!found)
	{
	  _cpp_file *file2 = make_cpp_file (file->dir, file->name);
	  file2->path = xstrdup (file->path);
	  file2->next_file = file->next_file;
	  file2->embed = true;
	  file->next_file = file2;
	  file = file2;
	}
    }
  if (!file->buffer_valid)
    {
      if (file->fd == -1 && !open_file (file))
	{
	  if (params->has_embed)
	    file->deferred_error = true;
	  else
	    open_file_failed (pfile, file, 0, params->loc);
	  return 0;
	}
      if (S_ISBLK (file->st.st_mode))
	{
	  if (params->has_embed)
	    {
	      close (file->fd);
	      file->fd = -1;
	      return 0;
	    }
	  cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
			"%s is a block device", file->path);
	fail:
	  close (file->fd);
	  file->fd = -1;
	  file->dont_read = true;
	  return 0;
	}

      if (CPP_OPTION (pfile, deps.style)
	  && !params->has_embed
	  && file == orig_file
	  && file->path[0])
	deps_add_dep (pfile->deps, file->path);

      bool regular = S_ISREG (file->st.st_mode) != 0;
      ssize_t size, total, count;
      uchar *buf;
      if (regular)
	{
	  cpp_num_part limit;
	  if (file->st.st_size + (cpp_num_part) 0 < params->offset)
	    limit = 0;
	  else if (file->st.st_size - params->offset < params->limit)
	    limit = file->st.st_size - params->offset;
	  else
	    limit = params->limit;
	  if (params->has_embed)
	    return limit != 0 ? 1 : 2;
	  if (limit > INTTYPE_MAXIMUM (ssize_t))
	    {
	      cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
			    "%s is too large", file->path);
	      goto fail;
	    }
	  if (lseek (file->fd, params->offset, SEEK_CUR)
	      != (off_t) params->offset)
	    {
	      cpp_errno_filename (pfile, CPP_DL_ERROR, file->path,
				  params->loc);
	      goto fail;
	    }
	  file->offset = params->offset;
	  file->limit = limit;
	  size = limit;
	}
      else if (params->has_embed)
	return 2;
      else if (params->limit > 8 * 1024)
	size = 8 * 1024;
      else
	size = params->limit;
      buf = XNEWVEC (uchar, size ? size : 1);
      total = 0;

      if (!regular && params->offset)
	{
	  uchar *buf2 = buf;
	  ssize_t size2 = size;
	  cpp_num_part total2 = params->offset;

	  if (params->offset > 8 * 1024 && size < 8 * 1024)
	    {
	      size2 = 32 * 1024;
	      buf2 = XNEWVEC (uchar, size2);
	    }
	  do
	    {
	      if ((cpp_num_part) size2 > total2)
		size2 = total2;
	      count = read (file->fd, buf2, size2);
	      if (count < 0)
		{
		  cpp_errno_filename (pfile, CPP_DL_ERROR, file->path,
				      params->loc);
		  if (buf2 != buf)
		    free (buf2);
		  free (buf);
		  goto fail;
		}
	      total2 -= count;
	    }
	  while (total2);
	  if (buf2 != buf)
	    free (buf2);
	}

      while ((count = read (file->fd, buf + total, size - total)) > 0)
	{
	  total += count;
	  if (total == size)
	    {
	      if (regular || size + (cpp_num_part) 0 == params->limit)
		break;
	      size = (size_t) size * 2;
	      if (size < 0)
		{
		  if (params->limit <= INTTYPE_MAXIMUM (ssize_t))
		    size = params->limit;
		  else
		    {
		      cpp_error_at (pfile, CPP_DL_ERROR, params->loc,
				    "%s is too large", file->path);
		      free (buf);
		      goto fail;
		    }
		}
	      else if (size + (cpp_num_part) 0 > params->limit)
		size = params->limit;
	      buf = XRESIZEVEC (uchar, buf, size);
	    }
	}

      if (count < 0)
	{
	  cpp_errno_filename (pfile, CPP_DL_ERROR, file->path, params->loc);
	  free (buf);
	  goto fail;
	}

      if (regular && total != size && STAT_SIZE_RELIABLE (file->st))
	{
	  cpp_error_at (pfile, CPP_DL_WARNING, params->loc,
			"%s is shorter than expected", file->path);
	  file->limit = total;
	}
      else if (!regular)
	{
	  file->offset = params->offset;
	  file->limit = total;
	}

      file->buffer_start = buf;
      file->buffer = buf;
      file->buffer_valid = 1;
      close (file->fd);
      file->fd = -1;
    }
  else if (params->has_embed)
    {
      if (params->offset - file->offset > file->limit)
	return 2;
      size_t limit = file->limit - (params->offset - file->offset);
      return limit && params->limit ? 1 : 2;
    }

  return finish_embed (pfile, file, params);
}

/* Retrofit the just-entered main file asif it was an include.  This
   will permit correct include_next use, and mark it as a system
   header if that's where it resides.  We use filesystem-appropriate
   prefix matching of the include path to locate the main file.  */
void
cpp_retrofit_as_include (cpp_reader *pfile)
{
  /* We should be the outermost.  */
  gcc_assert (!pfile->buffer->prev);

  if (const char *name = pfile->main_file->name)
    {
      /* Locate name on the include dir path, using a prefix match.  */
      size_t name_len = strlen (name);
      for (cpp_dir *dir = pfile->quote_include; dir; dir = dir->next)
	if (dir->len < name_len
	    && IS_DIR_SEPARATOR (name[dir->len])
	    && !filename_ncmp (name, dir->name, dir->len))
	  {
	    pfile->main_file->dir = dir;
	    if (dir->sysp)
	      cpp_make_system_header (pfile, 1, 0);
	    break;
	  }
    }

  /* Initialize controlling macro state.  */
  pfile->mi_valid = true;
  pfile->mi_cmacro = 0;
}

/* Could not open FILE.  The complication is dependency output.  */
static void
open_file_failed (cpp_reader *pfile, _cpp_file *file, int angle_brackets,
		  location_t loc)
{
  int sysp = pfile->line_table->highest_line > 1 && pfile->buffer ? pfile->buffer->sysp : 0;
  bool print_dep = CPP_OPTION (pfile, deps.style) > (angle_brackets || !!sysp);

  errno = file->err_no;
  if (print_dep && CPP_OPTION (pfile, deps.missing_files) && errno == ENOENT)
    {
      deps_add_dep (pfile->deps, file->name);
      /* If the preprocessor output (other than dependency information) is
         being used, we must also flag an error.  */
      if (CPP_OPTION (pfile, deps.need_preprocessor_output))
	cpp_errno_filename (pfile, CPP_DL_FATAL,
			    file->path ? file->path : file->name,
			    loc);
    }
  else
    {
      /* If we are not outputting dependencies, or if we are and dependencies
         were requested for this file, or if preprocessor output is needed
         in addition to dependency information, this is an error.

         Otherwise (outputting dependencies but not for this file, and not
         using the preprocessor output), we can still produce correct output
         so it's only a warning.  */
      if (CPP_OPTION (pfile, deps.style) == DEPS_NONE
          || print_dep
          || CPP_OPTION (pfile, deps.need_preprocessor_output))
	cpp_errno_filename (pfile, CPP_DL_FATAL,
			    file->path ? file->path : file->name,
			    loc);
      else
	cpp_errno_filename (pfile, CPP_DL_WARNING,
			    file->path ? file->path : file->name,
			    loc);
    }
}

/* Search in the chain beginning at HEAD for a file whose search path
   started at START_DIR != NULL.  */
static struct cpp_file_hash_entry *
search_cache (struct cpp_file_hash_entry *head, const cpp_dir *start_dir,
	      bool is_embed)
{
  while (head && (head->start_dir != start_dir
		  || head->u.file->embed != is_embed))
    head = head->next;

  return head;
}

/* Allocate a new _cpp_file structure.  */
static _cpp_file *
make_cpp_file (cpp_dir *dir, const char *fname)
{
  _cpp_file *file = XCNEW (_cpp_file);
  file->fd = -1;
  file->dir = dir;
  file->name = xstrdup (fname);

  return file;
}

/* Release a _cpp_file structure.  */
static void
destroy_cpp_file (_cpp_file *file)
{
  free ((void *) file->buffer_start);
  free ((void *) file->name);
  free ((void *) file->path);
  free (file);
}

/* Release all the files allocated by this reader.  */
static void
destroy_all_cpp_files (cpp_reader *pfile)
{
  _cpp_file *iter = pfile->all_files;
  while (iter)
    {
      _cpp_file *next = iter->next_file;
      destroy_cpp_file (iter);
      iter = next;
    }
}

/* A hash of directory names.  The directory names are the path names
   of files which contain a #include "", the included file name is
   appended to this directories.

   To avoid duplicate entries we follow the convention that all
   non-empty directory names should end in a '/'.  DIR_NAME must be
   stored in permanently allocated memory.  */
static cpp_dir *
make_cpp_dir (cpp_reader *pfile, const char *dir_name, int sysp)
{
  struct cpp_file_hash_entry *entry, **hash_slot;
  cpp_dir *dir;

  hash_slot = (struct cpp_file_hash_entry **)
    htab_find_slot_with_hash (pfile->dir_hash, dir_name,
			      htab_hash_string (dir_name),
			      INSERT);

  /* Have we already hashed this directory?  */
  for (entry = *hash_slot; entry; entry = entry->next)
    if (entry->start_dir == NULL)
      return entry->u.dir;

  dir = XCNEW (cpp_dir);
  dir->next = pfile->quote_include;
  dir->name = (char *) dir_name;
  dir->len = strlen (dir_name);
  dir->sysp = sysp;
  dir->construct = 0;

  /* Store this new result in the hash table.  */
  entry = new_file_hash_entry (pfile);
  entry->next = *hash_slot;
  entry->start_dir = NULL;
  entry->location = pfile->line_table->highest_location;
  entry->u.dir = dir;
  *hash_slot = entry;

  return dir;
}

/* Create a new block of memory for file hash entries.  */
static void
allocate_file_hash_entries (cpp_reader *pfile)
{
  struct file_hash_entry_pool *pool = XNEW (struct file_hash_entry_pool);
  pool->file_hash_entries_used = 0;
  pool->next = pfile->file_hash_entries;
  pfile->file_hash_entries = pool;
}

/* Return a new file hash entry.  */
static struct cpp_file_hash_entry *
new_file_hash_entry (cpp_reader *pfile)
{
  unsigned int idx;
  if (pfile->file_hash_entries->file_hash_entries_used == FILE_HASH_POOL_SIZE)
    allocate_file_hash_entries (pfile);

  idx = pfile->file_hash_entries->file_hash_entries_used++;
  return &pfile->file_hash_entries->pool[idx];
}

/* Free the file hash entry pools.  */
static void
free_file_hash_entries (cpp_reader *pfile)
{
  struct file_hash_entry_pool *iter = pfile->file_hash_entries;
  while (iter)
    {
      struct file_hash_entry_pool *next = iter->next;
      free (iter);
      iter = next;
    }
}

/* Returns TRUE if a file FNAME has ever been successfully opened.
   This routine is not intended to correctly handle filenames aliased
   by links or redundant . or .. traversals etc.  */
bool
cpp_included (cpp_reader *pfile, const char *fname)
{
  struct cpp_file_hash_entry *entry;

  entry = (struct cpp_file_hash_entry *)
     htab_find_with_hash (pfile->file_hash, fname, htab_hash_string (fname));

  while (entry && (entry->start_dir == NULL || entry->u.file->err_no))
    entry = entry->next;

  return entry != NULL;
}

/* Returns TRUE if a file FNAME has ever been successfully opened
   before LOCATION.  This routine is not intended to correctly handle
   filenames aliased by links or redundant . or .. traversals etc.  */
bool
cpp_included_before (cpp_reader *pfile, const char *fname,
		     location_t location)
{
  struct cpp_file_hash_entry *entry
    = (struct cpp_file_hash_entry *)
      htab_find_with_hash (pfile->file_hash, fname, htab_hash_string (fname));

  if (IS_ADHOC_LOC (location))
    location = get_location_from_adhoc_loc (pfile->line_table, location);

  while (entry && (entry->start_dir == NULL || entry->u.file->err_no
		   || entry->location > location))
    entry = entry->next;

  return entry != NULL;
}

/* Calculate the hash value of a file hash entry P.  */

static hashval_t
file_hash_hash (const void *p)
{
  struct cpp_file_hash_entry *entry = (struct cpp_file_hash_entry *) p;
  const char *hname;
  if (entry->start_dir)
    hname = entry->u.file->name;
  else
    hname = entry->u.dir->name;

  return htab_hash_string (hname);
}

/* Compare a string Q against a file hash entry P.  */
static int
file_hash_eq (const void *p, const void *q)
{
  struct cpp_file_hash_entry *entry = (struct cpp_file_hash_entry *) p;
  const char *fname = (const char *) q;
  const char *hname;

  if (entry->start_dir)
    hname = entry->u.file->name;
  else
    hname = entry->u.dir->name;

  return filename_cmp (hname, fname) == 0;
}

/* Compare entries in the nonexistent file hash table.  These are just
   strings.  */
static int
nonexistent_file_hash_eq (const void *p, const void *q)
{
  return filename_cmp ((const char *) p, (const char *) q) == 0;
}

/* Initialize everything in this source file.  */
void
_cpp_init_files (cpp_reader *pfile)
{
  pfile->file_hash = htab_create_alloc (127, file_hash_hash, file_hash_eq,
					NULL, xcalloc, free);
  pfile->dir_hash = htab_create_alloc (127, file_hash_hash, file_hash_eq,
					NULL, xcalloc, free);
  allocate_file_hash_entries (pfile);
  pfile->nonexistent_file_hash = htab_create_alloc (127, htab_hash_string,
						    nonexistent_file_hash_eq,
						    NULL, xcalloc, free);
  obstack_specify_allocation (&pfile->nonexistent_file_ob, 0, 0,
			      xmalloc, free);
}

/* Finalize everything in this source file.  */
void
_cpp_cleanup_files (cpp_reader *pfile)
{
  htab_delete (pfile->file_hash);
  htab_delete (pfile->dir_hash);
  htab_delete (pfile->nonexistent_file_hash);
  obstack_free (&pfile->nonexistent_file_ob, 0);
  free_file_hash_entries (pfile);
  destroy_all_cpp_files (pfile);
}

/* Make the parser forget about files it has seen.  This can be useful
   for resetting the parser to start another run.  */
void
cpp_clear_file_cache (cpp_reader *pfile)
{
  _cpp_cleanup_files (pfile);
  pfile->file_hash_entries = NULL;
  pfile->all_files = NULL;
  _cpp_init_files (pfile);
}

/* Enter a file name in the hash for the sake of cpp_included.  */
void
_cpp_fake_include (cpp_reader *pfile, const char *fname)
{
  /* It does not matter what are the contents of fake_source_dir, it will never
     be inspected; we just use its address to uniquely signify that this file
     was added as a fake include, so a later call to _cpp_find_file (to include
     the file for real) won't find the fake one in the hash table.  */
  static cpp_dir fake_source_dir;
  _cpp_find_file (pfile, fname, &fake_source_dir, 0, _cpp_FFK_FAKE, 0);
}

/* Not everyone who wants to set system-header-ness on a buffer can
   see the details of a buffer.  This is an exported interface because
   fix-header needs it.  */
void
cpp_make_system_header (cpp_reader *pfile, int syshdr, int externc)
{
  int flags = 0;
  const class line_maps *line_table = pfile->line_table;
  const line_map_ordinary *map = LINEMAPS_LAST_ORDINARY_MAP (line_table);
  /* 1 = system header, 2 = system header to be treated as C.  */
  if (syshdr)
    flags = 1 + (externc != 0);
  pfile->buffer->sysp = flags;
  _cpp_do_file_change (pfile, LC_RENAME, ORDINARY_MAP_FILE_NAME (map),
		       SOURCE_LINE (map, pfile->line_table->highest_line),
		       flags);
}

/* Allow the client to change the current file.  Used by the front end
   to achieve pseudo-file names like <built-in>.
   If REASON is LC_LEAVE, then NEW_NAME must be NULL.  */
void
cpp_change_file (cpp_reader *pfile, enum lc_reason reason,
		 const char *new_name)
{
  _cpp_do_file_change (pfile, reason, new_name, 1, 0);
}

struct report_missing_guard_data
{
  cpp_reader *pfile;
  const char **paths;
  size_t count;
};

/* Callback function for htab_traverse.  */
static int
report_missing_guard (void **slot, void *d)
{
  struct cpp_file_hash_entry *entry = (struct cpp_file_hash_entry *) *slot;
  struct report_missing_guard_data *data
    = (struct report_missing_guard_data *) d;

  /* Skip directories.  */
  if (entry->start_dir != NULL)
    {
      _cpp_file *file = entry->u.file;

      /* We don't want MI guard advice for the main file.  */
      if (!file->once_only
	  && file->cmacro == NULL
	  && file->stack_count == 1
	  && data->pfile->main_file != file)
	{
	  if (data->paths == NULL)
	    {
	      data->paths = XCNEWVEC (const char *, data->count);
	      data->count = 0;
	    }

	  data->paths[data->count++] = file->path;
	}
    }

  /* Keep traversing the hash table.  */
  return 1;
}

/* Comparison function for qsort.  */
static int
report_missing_guard_cmp (const void *p1, const void *p2)
{
  return strcmp (*(const char *const *) p1, *(const char *const *) p2);
}

/* Report on all files that might benefit from a multiple include guard.
   Triggered by -H.  */
void
_cpp_report_missing_guards (cpp_reader *pfile)
{
  struct report_missing_guard_data data;

  data.pfile = pfile;
  data.paths = NULL;
  data.count = htab_elements (pfile->file_hash);
  htab_traverse (pfile->file_hash, report_missing_guard, &data);

  if (data.paths != NULL)
    {
      size_t i;

      /* Sort the paths to avoid outputting them in hash table
	 order.  */
      qsort (data.paths, data.count, sizeof (const char *),
	     report_missing_guard_cmp);
      fputs (_("Multiple include guards may be useful for:\n"),
	     stderr);
      for (i = 0; i < data.count; i++)
	{
	  fputs (data.paths[i], stderr);
	  putc ('\n', stderr);
	}
      free (data.paths);
    }
}

/* Locate HEADER, and determine whether it is newer than the current
   file.  If it cannot be located or dated, return -1, if it is
   newer, return 1, otherwise 0.  */
int
_cpp_compare_file_date (cpp_reader *pfile, const char *fname,
			int angle_brackets)
{
  _cpp_file *file;
  struct cpp_dir *dir;

  dir = search_path_head (pfile, fname, angle_brackets, IT_INCLUDE);
  if (!dir)
    return -1;

  file = _cpp_find_file (pfile, fname, dir, angle_brackets, _cpp_FFK_NORMAL, 0);
  if (file->err_no)
    return -1;

  if (file->fd != -1)
    {
      close (file->fd);
      file->fd = -1;
    }

  return file->st.st_mtime > pfile->buffer->file->st.st_mtime;
}

/* Pushes the given file onto the buffer stack.  Returns nonzero if
   successful.  */
bool
cpp_push_include (cpp_reader *pfile, const char *fname)
{
  return _cpp_stack_include (pfile, fname, false, IT_CMDLINE,
			     pfile->line_table->highest_line);
}

/* Pushes the given file, implicitly included at the start of a
   compilation, onto the buffer stack but without any errors if the
   file is not found.  Returns nonzero if successful.  */
bool
cpp_push_default_include (cpp_reader *pfile, const char *fname)
{
  return _cpp_stack_include (pfile, fname, true, IT_DEFAULT,
			     pfile->line_table->highest_line);
}

/* Do appropriate cleanup when a file INC's buffer is popped off the
   input stack.  */
void
_cpp_pop_file_buffer (cpp_reader *pfile, _cpp_file *file,
		      const unsigned char *to_free)
{
  /* Record the inclusion-preventing macro, which could be NULL
     meaning no controlling macro.  */
  if (pfile->mi_valid && file->cmacro == NULL)
    {
      file->cmacro = pfile->mi_cmacro;
      if (pfile->mi_cmacro
	  && pfile->mi_def_cmacro
	  && pfile->cb.get_suggestion)
	{
	  auto mi_cmacro = (const char *) NODE_NAME (pfile->mi_cmacro);
	  auto mi_def_cmacro = (const char *) NODE_NAME (pfile->mi_def_cmacro);
	  const char *names[] = { mi_def_cmacro, NULL };
	  if (pfile->cb.get_suggestion (pfile, mi_cmacro, names)
	      && cpp_warning_with_line (pfile, CPP_W_HEADER_GUARD,
					pfile->mi_loc, 0,
					"header guard %qs followed by "
					"%<#define%> of a different macro",
					mi_cmacro))
	    cpp_error_at (pfile, CPP_DL_NOTE, pfile->mi_def_loc,
			  "%qs is defined here; did you mean %qs?",
			  mi_def_cmacro, mi_cmacro);
	}
    }

  /* Invalidate control macros in the #including file.  */
  pfile->mi_valid = false;

  if (to_free)
    {
      if (to_free == file->buffer_start)
	{
	  file->buffer_start = NULL;
	  file->buffer = NULL;
	  file->buffer_valid = false;
	}
      free ((void *) to_free);
    }
}

/* Return the file name associated with FILE.  */
const char *
_cpp_get_file_name (_cpp_file *file)
{
  return file->name;
}

/* Get the path associated with the _cpp_file F.  The path includes
   the base name from the include directive and the directory it was
   found in via the search path.  */

const char *
_cpp_get_file_path (_cpp_file *f)
{
  return f->path;
}

/* Interface to file statistics record in _cpp_file structure. */
struct stat *
_cpp_get_file_stat (_cpp_file *file)
{
  return &file->st;
}

/* Return the directory where FILE was found.  */
struct cpp_dir *
_cpp_get_file_dir (_cpp_file *file)
{
  return file->dir;
}

/* Set the include chain for "" to QUOTE, for <> to BRACKET.  If
   QUOTE_IGNORES_SOURCE_DIR, then "" includes do not look in the
   directory of the including file.

   If BRACKET does not lie in the QUOTE chain, it is set to QUOTE.

   EMBED is include chain for #embed <>.  */
void
cpp_set_include_chains (cpp_reader *pfile, cpp_dir *quote, cpp_dir *bracket,
			cpp_dir *embed, int quote_ignores_source_dir)
{
  pfile->quote_include = quote;
  pfile->bracket_include = quote;
  pfile->quote_ignores_source_dir = quote_ignores_source_dir;
  pfile->embed_include = embed;

  for (; quote; quote = quote->next)
    {
      quote->name_map = NULL;
      quote->len = strlen (quote->name);
      if (quote == bracket)
	pfile->bracket_include = bracket;
    }
  for (; embed; embed = embed->next)
    {
      embed->name_map = NULL;
      embed->len = strlen (embed->name);
    }
}

/* Append the file name to the directory to create the path, but don't
   turn / into // or // into ///; // may be a namespace escape.  */
static char *
append_file_to_dir (const char *fname, cpp_dir *dir)
{
  size_t dlen, flen;
  char *path;

  dlen = dir->len;
  flen = strlen (fname);
  path = XNEWVEC (char, dlen + 1 + flen + 1);
  memcpy (path, dir->name, dlen);
  if (dlen && !IS_DIR_SEPARATOR (path[dlen - 1]))
    path[dlen++] = '/';
  memcpy (&path[dlen], fname, flen + 1);

  return path;
}

/* Read a space delimited string of unlimited length from a stdio
   file F.  */
static char *
read_filename_string (int ch, FILE *f)
{
  char *alloc, *set;
  int len;

  len = 20;
  set = alloc = XNEWVEC (char, len + 1);
  if (! is_space (ch))
    {
      *set++ = ch;
      while ((ch = getc (f)) != EOF && ! is_space (ch))
	{
	  if (set - alloc == len)
	    {
	      len *= 2;
	      alloc = XRESIZEVEC (char, alloc, len + 1);
	      set = alloc + len / 2;
	    }
	  *set++ = ch;
	}
    }
  *set = '\0';
  ungetc (ch, f);
  return alloc;
}

/* Read the file name map file for DIR.  */
static void
read_name_map (cpp_dir *dir)
{
  static const char FILE_NAME_MAP_FILE[] = "header.gcc";
  char *name;
  FILE *f;
  size_t len, count = 0, room = 9;

  len = dir->len;
  name = (char *) alloca (len + sizeof (FILE_NAME_MAP_FILE) + 1);
  memcpy (name, dir->name, len);
  if (len && !IS_DIR_SEPARATOR (name[len - 1]))
    name[len++] = '/';
  strcpy (name + len, FILE_NAME_MAP_FILE);
  f = fopen (name, "r");

  dir->name_map = XNEWVEC (const char *, room);

  /* Silently return NULL if we cannot open.  */
  if (f)
    {
      int ch;

      while ((ch = getc (f)) != EOF)
	{
	  char *to;

	  if (is_space (ch))
	    continue;

	  if (count + 2 > room)
	    {
	      room += 8;
	      dir->name_map = XRESIZEVEC (const char *, dir->name_map, room);
	    }

	  dir->name_map[count] = read_filename_string (ch, f);
	  while ((ch = getc (f)) != EOF && is_hspace (ch))
	    ;

	  to = read_filename_string (ch, f);
	  if (IS_ABSOLUTE_PATH (to))
	    dir->name_map[count + 1] = to;
	  else
	    {
	      dir->name_map[count + 1] = append_file_to_dir (to, dir);
	      free (to);
	    }

	  count += 2;
	  while ((ch = getc (f)) != '\n')
	    if (ch == EOF)
	      break;
	}

      fclose (f);
    }

  /* Terminate the list of maps.  */
  dir->name_map[count] = NULL;
}

/* Remap a FILE's name based on the file_name_map, if any, for
   FILE->dir.  If the file name has any directory separators,
   recursively check those directories too.  */
static char *
remap_filename (cpp_reader *pfile, _cpp_file *file)
{
  const char *fname, *p;
  char *new_dir, *p3;
  cpp_dir *dir;
  size_t index, len;

  dir = file->dir;
  fname = file->name;

  for (;;)
    {
      if (!dir->name_map)
	read_name_map (dir);

      for (index = 0; dir->name_map[index]; index += 2)
	if (!filename_cmp (dir->name_map[index], fname))
	    return xstrdup (dir->name_map[index + 1]);
      if (IS_ABSOLUTE_PATH (fname))
	return NULL;
      p = strchr (fname, '/');
#ifdef HAVE_DOS_BASED_FILE_SYSTEM
      {
	const char *p2 = strchr (fname, '\\');
	if (!p || (p2 && p > p2))
	  p = p2;
      }
#endif
      if (!p || p == fname)
	return NULL;

      len = dir->len + (p - fname + 1);
      new_dir = XNEWVEC (char, len + 2);
      p3 = new_dir + dir->len;
      memcpy (new_dir, dir->name, dir->len);
      if (dir->len && !IS_DIR_SEPARATOR (dir->name[dir->len - 1]))
	{
	  *p3++ = '/';
	  len++;
	}
      memcpy (p3, fname, p - fname + 1);
      new_dir[len] = '\0';

      dir = make_cpp_dir (pfile, new_dir, dir->sysp);
      fname = p + 1;
    }
}

/* Returns true if PCHNAME is a valid PCH file for FILE.  */
static bool
validate_pch (cpp_reader *pfile, _cpp_file *file, const char *pchname)
{
  const char *saved_path = file->path;
  bool valid = false;

  file->path = pchname;
  if (open_file (file))
    {
      valid = 1 & pfile->cb.valid_pch (pfile, pchname, file->fd);

      if (!valid)
	{
	  close (file->fd);
	  file->fd = -1;
	}

      if (CPP_OPTION (pfile, print_include_names))
	{
	  unsigned int i;
	  for (i = 1; i < pfile->line_table->depth; i++)
	    putc ('.', stderr);
	  fprintf (stderr, "%c %s\n",
		   valid ? '!' : 'x', pchname);
	}
    }

  file->path = saved_path;
  return valid;
}

/* Get the cpp_buffer currently associated with the cpp_reader
   PFILE.  */

cpp_buffer *
cpp_get_buffer (cpp_reader *pfile)
{
  return pfile->buffer;
}

/* Get the _cpp_file associated with the cpp_buffer B.  */

_cpp_file *
cpp_get_file (cpp_buffer *b)
{
  return b->file;
}

/* Get the previous cpp_buffer given a cpp_buffer B.  The previous
   buffer is the buffer that included the given buffer.  */

cpp_buffer *
cpp_get_prev (cpp_buffer *b)
{
  return b->prev;
}

/* This data structure holds the list of header files that were seen
   while the PCH was being built.  The 'entries' field is kept sorted
   in memcmp() order; yes, this means that on little-endian systems,
   it's sorted initially by the least-significant byte of 'size', but
   that's OK.  The code does rely on having entries with the same size
   next to each other.  */

struct pchf_entry {
  /* The size of this file.  This is used to save running a MD5 checksum
     if the sizes don't match.  */
  off_t size;
  /* The MD5 checksum of this file.  */
  unsigned char sum[16];
  /* Is this file to be included only once?  */
  bool once_only;
};

struct pchf_data {
  /* Number of pchf_entry structures.  */
  size_t count;

  /* Are there any values with once_only set?
     This is used as an optimisation, it means we don't have to search
     the structure if we're processing a regular #include.  */
  bool have_once_only;

  struct pchf_entry entries[1];
};

static struct pchf_data *pchf;

/* A qsort ordering function for pchf_entry structures.  */

static int
pchf_save_compare (const void *e1, const void *e2)
{
  return memcmp (e1, e2, sizeof (struct pchf_entry));
}

/* Create and write to F a pchf_data structure.  */

bool
_cpp_save_file_entries (cpp_reader *pfile, FILE *fp)
{
  size_t count = 0;
  struct pchf_data *result;
  size_t result_size;
  _cpp_file *f;
  bool ret;

  for (f = pfile->all_files; f; f = f->next_file)
    ++count;

  result_size = (sizeof (struct pchf_data)
		 + sizeof (struct pchf_entry) * (count - 1));
  result = XCNEWVAR (struct pchf_data, result_size);

  result->count = 0;
  result->have_once_only = false;

  for (f = pfile->all_files; f; f = f->next_file)
    {
      size_t count;

      /* This should probably never happen, since if a read error occurred
	 the PCH file shouldn't be written...  */
      if (f->dont_read || f->err_no)
	continue;

      if (f->stack_count == 0)
	continue;

      count = result->count++;

      result->entries[count].once_only = f->once_only;
      /* |= is avoided in the next line because of an HP C compiler bug */
      result->have_once_only = result->have_once_only | f->once_only;
      if (f->buffer_valid)
	md5_buffer ((const char *)f->buffer,
		    f->st.st_size, result->entries[count].sum);
      else
	{
	  FILE *ff;
	  int oldfd = f->fd;

	  if (!open_file (f))
	    {
	      open_file_failed (pfile, f, 0, 0);
	      free (result);
	      return false;
	    }
	  ff = fdopen (f->fd, "rb");
	  md5_stream (ff, result->entries[count].sum);
	  fclose (ff);
	  f->fd = oldfd;
	}
      result->entries[count].size = f->st.st_size;
    }

  result_size = (sizeof (struct pchf_data)
                 + sizeof (struct pchf_entry) * (result->count - 1));

  qsort (result->entries, result->count, sizeof (struct pchf_entry),
	 pchf_save_compare);

  ret = fwrite (result, result_size, 1, fp) == 1;
  free (result);
  return ret;
}

/* Read the pchf_data structure from F.  */

bool
_cpp_read_file_entries (cpp_reader *pfile ATTRIBUTE_UNUSED, FILE *f)
{
  struct pchf_data d;

  if (fread (&d, sizeof (struct pchf_data) - sizeof (struct pchf_entry), 1, f)
       != 1)
    return false;

  pchf = XNEWVAR (struct pchf_data, sizeof (struct pchf_data)
		  + sizeof (struct pchf_entry) * (d.count - 1));
  memcpy (pchf, &d, sizeof (struct pchf_data) - sizeof (struct pchf_entry));
  if (fread (pchf->entries, sizeof (struct pchf_entry), d.count, f)
      != d.count)
    return false;
  return true;
}

/* The parameters for pchf_compare.  */

struct pchf_compare_data
{
  /* The size of the file we're looking for.  */
  off_t size;

  /* The MD5 checksum of the file, if it's been computed.  */
  unsigned char sum[16];

  /* Is SUM valid?  */
  bool sum_computed;

  /* Do we need to worry about entries that don't have ONCE_ONLY set?  */
  bool check_included;

  /* The file that we're searching for.  */
  _cpp_file *f;
};

/* bsearch comparison function; look for D_P in E_P.  */

static int
pchf_compare (const void *d_p, const void *e_p)
{
  const struct pchf_entry *e = (const struct pchf_entry *)e_p;
  struct pchf_compare_data *d = (struct pchf_compare_data *)d_p;
  int result;

  result = memcmp (&d->size, &e->size, sizeof (off_t));
  if (result != 0)
    return result;

  if (! d->sum_computed)
    {
      _cpp_file *const f = d->f;

      md5_buffer ((const char *)f->buffer, f->st.st_size, d->sum);
      d->sum_computed = true;
    }

  result = memcmp (d->sum, e->sum, 16);
  if (result != 0)
    return result;

  if (d->check_included || e->once_only)
    return 0;
  else
    return 1;
}

/* Check that F is not in a list read from a PCH file (if any).
   Assumes that f->buffer_valid is true.  Return TRUE if the file
   should not be read.  */

static bool
check_file_against_entries (cpp_reader *pfile ATTRIBUTE_UNUSED,
			    _cpp_file *f,
			    bool check_included)
{
  struct pchf_compare_data d;

  if (pchf == NULL
      || (! check_included && ! pchf->have_once_only))
    return false;

  d.size = f->st.st_size;
  d.sum_computed = false;
  d.f = f;
  d.check_included = check_included;
  return bsearch (&d, pchf->entries, pchf->count, sizeof (struct pchf_entry),
		  pchf_compare) != NULL;
}

/* Return true if the file FNAME is found in the appropriate include file path
   as indicated by ANGLE_BRACKETS.  */

bool
_cpp_has_header (cpp_reader *pfile, const char *fname, int angle_brackets,
		 enum include_type type)
{
  cpp_dir *start_dir = search_path_head (pfile, fname, angle_brackets, type,
					 /* suppress_diagnostic = */ true);
  if (!start_dir)
    return false;
  _cpp_file *file = _cpp_find_file (pfile, fname, start_dir, angle_brackets,
				    _cpp_FFK_HAS_INCLUDE, 0);
  return file->err_no != ENOENT;
}

/* Read a file and convert to input charset, the same as if it were being read
   by a cpp_reader.  */

cpp_converted_source
cpp_get_converted_source (const char *fname, const char *input_charset)
{
  cpp_converted_source res = {};
  _cpp_file file = {};
  file.fd = -1;
  file.name = lbasename (fname);
  file.path = fname;
  if (!open_file (&file))
    return res;
  const bool ok = read_file_guts (NULL, &file, 0, input_charset);
  close (file.fd);
  if (!ok)
    return res;
  res.to_free = (char *) file.buffer_start;
  res.data = (char *) file.buffer;
  res.len = file.st.st_size;
  return res;
}
