/* Declarations for variables relating to reading the source file.
   Used by parsers, lexical analyzers, and error message routines.
   Copyright (C) 1993-2024 Free Software Foundation, Inc.

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/>.  */

#ifndef GCC_INPUT_H
#define GCC_INPUT_H

#include "line-map.h"

class file_cache;

extern GTY(()) class line_maps *line_table;
extern GTY(()) class line_maps *saved_line_table;

/* A value which will never be used to represent a real location.  */
#define UNKNOWN_LOCATION ((location_t) 0)

/* The location for declarations in "<built-in>" */
#define BUILTINS_LOCATION ((location_t) 1)

/* Returns the translated string referring to the special location.  */
const char *special_fname_builtin ();

/* line-map.cc reserves RESERVED_LOCATION_COUNT to the user.  Ensure
   both UNKNOWN_LOCATION and BUILTINS_LOCATION fit into that.  */
STATIC_ASSERT (BUILTINS_LOCATION < RESERVED_LOCATION_COUNT);

/* Hasher for 'location_t' values satisfying '!RESERVED_LOCATION_P', thus able
   to use 'UNKNOWN_LOCATION'/'BUILTINS_LOCATION' as spare values for
   'Empty'/'Deleted'.  */
/* Per PR103157 "'gengtype': 'typedef' causing infinite-recursion code to be
   generated", don't use
       typedef int_hash<location_t, UNKNOWN_LOCATION, BUILTINS_LOCATION>
         location_hash;
   here.

   It works for a single-use case, but when using a 'struct'-based variant
       struct location_hash
         : int_hash<location_t, UNKNOWN_LOCATION, BUILTINS_LOCATION> {};
   in more than one place, 'gengtype' generates duplicate functions (thus:
   "error: redefinition of 'void gt_ggc_mx(location_hash&)'" etc.).
   Attempting to mark that one up with GTY options, we run into a 'gengtype'
   "parse error: expected '{', have '<'", which probably falls into category
   "understanding of C++ is limited", as documented in 'gcc/doc/gty.texi'.

   Thus, use a plain ol' '#define':
*/
#define location_hash int_hash<location_t, UNKNOWN_LOCATION, BUILTINS_LOCATION>

extern bool is_location_from_builtin_token (location_t);
extern expanded_location expand_location (location_t);

class cpp_char_column_policy;

extern int
location_compute_display_column (file_cache &fc,
				 expanded_location exploc,
				 const cpp_char_column_policy &policy);

/* A class capturing the bounds of a buffer, to allow for run-time
   bounds-checking in a checked build.  */

class char_span
{
 public:
  char_span (const char *ptr, size_t n_elts) : m_ptr (ptr), m_n_elts (n_elts) {}

  /* Test for a non-NULL pointer.  */
  operator bool() const { return m_ptr; }

  /* Get length, not including any 0-terminator (which may not be,
     in fact, present).  */
  size_t length () const { return m_n_elts; }

  const char *get_buffer () const { return m_ptr; }

  char operator[] (int idx) const
  {
    gcc_assert (idx >= 0);
    gcc_assert ((size_t)idx < m_n_elts);
    return m_ptr[idx];
  }

  char_span subspan (int offset, int n_elts) const
  {
    gcc_assert (offset >= 0);
    gcc_assert (offset < (int)m_n_elts);
    gcc_assert (n_elts >= 0);
    gcc_assert (offset + n_elts <= (int)m_n_elts);
    return char_span (m_ptr + offset, n_elts);
  }

  char *xstrdup () const
  {
    return ::xstrndup (m_ptr, m_n_elts);
  }

 private:
  const char *m_ptr;
  size_t m_n_elts;
};

extern char *
get_source_text_between (file_cache &, location_t, location_t);

/* Forward decl of slot within file_cache, so that the definition doesn't
   need to be in this header.  */
class file_cache_slot;

/* A cache of source files for use when emitting diagnostics
   (and in a few places in the C/C++ frontends).

   Results are only valid until the next call to the cache, as
   slots can be evicted.

   Filenames are stored by pointer, and so must outlive the cache
   instance.  */

class file_cache
{
 public:
  file_cache ();
  ~file_cache ();

  file_cache_slot *lookup_or_add_file (const char *file_path);
  void forcibly_evict_file (const char *file_path);

  /* See comments in diagnostic.h about the input conversion context.  */
  struct input_context
  {
    diagnostic_input_charset_callback ccb;
    bool should_skip_bom;
  };
  void initialize_input_context (diagnostic_input_charset_callback ccb,
				 bool should_skip_bom);

  char_span get_source_file_content (const char *file_path);
  char_span get_source_line (const char *file_path, int line);
  bool missing_trailing_newline_p (const char *file_path);

 private:
  file_cache_slot *evicted_cache_tab_entry (unsigned *highest_use_count);
  file_cache_slot *add_file (const char *file_path);
  file_cache_slot *lookup_file (const char *file_path);

 private:
  static const size_t num_file_slots = 16;
  file_cache_slot *m_file_slots;
  input_context in_context;
};

extern expanded_location
expand_location_to_spelling_point (location_t,
				   enum location_aspect aspect
				     = LOCATION_ASPECT_CARET);
extern location_t expansion_point_location_if_in_system_header (location_t);
extern location_t expansion_point_location (location_t);

extern location_t input_location;

extern location_t location_with_discriminator (location_t, int);
extern bool has_discriminator (location_t);
extern int get_discriminator_from_loc (location_t);

#define LOCATION_FILE(LOC) ((expand_location (LOC)).file)
#define LOCATION_LINE(LOC) ((expand_location (LOC)).line)
#define LOCATION_COLUMN(LOC)((expand_location (LOC)).column)
#define LOCATION_LOCUS(LOC) \
  ((IS_ADHOC_LOC (LOC)) ? get_location_from_adhoc_loc (line_table, LOC) \
   : (LOC))
#define LOCATION_BLOCK(LOC) \
  ((tree) ((IS_ADHOC_LOC (LOC)) ? get_data_from_adhoc_loc (line_table, (LOC)) \
   : NULL))
#define RESERVED_LOCATION_P(LOC) \
  (LOCATION_LOCUS (LOC) < RESERVED_LOCATION_COUNT)

/* Return a positive value if LOCATION is the locus of a token that is
   located in a system header, O otherwise. It returns 1 if LOCATION
   is the locus of a token that is located in a system header, and 2
   if LOCATION is the locus of a token located in a C system header
   that therefore needs to be extern "C" protected in C++.

   Note that this function returns 1 if LOCATION belongs to a token
   that is part of a macro replacement-list defined in a system
   header, but expanded in a non-system file.  */

inline int
in_system_header_at (location_t loc)
{
  return linemap_location_in_system_header_p (line_table, loc);
}

/* Return true if LOCATION is the locus of a token that
   comes from a macro expansion, false otherwise.  */

inline bool
from_macro_expansion_at (location_t loc)
{
  return linemap_location_from_macro_expansion_p (line_table, loc);
}

/* Return true if LOCATION is the locus of a token that comes from
   a macro definition, false otherwise.  This differs from from_macro_expansion_at
   in its treatment of macro arguments, for which this returns false.  */

inline bool
from_macro_definition_at (location_t loc)
{
  return linemap_location_from_macro_definition_p (line_table, loc);
}

inline location_t
get_pure_location (location_t loc)
{
  return get_pure_location (line_table, loc);
}

/* Get the start of any range encoded within location LOC.  */

inline location_t
get_start (location_t loc)
{
  return get_range_from_loc (line_table, loc).m_start;
}

/* Get the endpoint of any range encoded within location LOC.  */

inline location_t
get_finish (location_t loc)
{
  return get_range_from_loc (line_table, loc).m_finish;
}

extern location_t make_location (location_t caret,
				 location_t start, location_t finish);
extern location_t make_location (location_t caret, source_range src_range);

void dump_line_table_statistics (void);

void dump_location_info (FILE *stream);

class GTY(()) string_concat
{
public:
  string_concat (int num, location_t *locs);

  int m_num;
  location_t * GTY ((atomic)) m_locs;
};

class GTY(()) string_concat_db
{
 public:
  string_concat_db ();
  void record_string_concatenation (int num, location_t *locs);

  bool get_string_concatenation (location_t loc,
				 int *out_num,
				 location_t **out_locs);

 private:
  static location_t get_key_loc (location_t loc);

  /* For the fields to be private, we must grant access to the
     generated code in gtype-desc.cc.  */

  friend void ::gt_ggc_mx_string_concat_db (void *x_p);
  friend void ::gt_pch_nx_string_concat_db (void *x_p);
  friend void ::gt_pch_p_16string_concat_db (void *this_obj, void *x_p,
					     gt_pointer_operator op,
					     void *cookie);

  hash_map <location_hash, string_concat *> *m_table;
};

#endif
