/* General Compile and inject code

   Copyright (C) 2014-2021 Free Software Foundation, Inc.

   This file is part of GDB.

   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 of the License, 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.  If not, see <http://www.gnu.org/licenses/>.  */

#include "defs.h"
#include "top.h"
#include "ui-out.h"
#include "command.h"
#include "cli/cli-script.h"
#include "cli/cli-utils.h"
#include "cli/cli-option.h"
#include "completer.h"
#include "gdbcmd.h"
#include "compile.h"
#include "compile-internal.h"
#include "compile-object-load.h"
#include "compile-object-run.h"
#include "language.h"
#include "frame.h"
#include "source.h"
#include "block.h"
#include "arch-utils.h"
#include "gdbsupport/filestuff.h"
#include "target.h"
#include "osabi.h"
#include "gdbsupport/gdb_wait.h"
#include "valprint.h"
#include "gdbsupport/gdb_optional.h"
#include "gdbsupport/gdb_unlinker.h"
#include "gdbsupport/pathstuff.h"
#include "gdbsupport/scoped_ignore_signal.h"



/* Initial filename for temporary files.  */

#define TMP_PREFIX "/tmp/gdbobj-"

/* Hold "compile" commands.  */

static struct cmd_list_element *compile_command_list;

/* Debug flag for "compile" commands.  */

bool compile_debug;

/* Object of this type are stored in the compiler's symbol_err_map.  */

struct symbol_error
{
  /* The symbol.  */

  const struct symbol *sym;

  /* The error message to emit.  This is malloc'd and owned by the
     hash table.  */

  char *message;
};

/* Hash a type_map_instance.  */

static hashval_t
hash_type_map_instance (const void *p)
{
  const struct type_map_instance *inst = (const struct type_map_instance *) p;

  return htab_hash_pointer (inst->type);
}

/* Check two type_map_instance objects for equality.  */

static int
eq_type_map_instance (const void *a, const void *b)
{
  const struct type_map_instance *insta = (const struct type_map_instance *) a;
  const struct type_map_instance *instb = (const struct type_map_instance *) b;

  return insta->type == instb->type;
}

/* Hash function for struct symbol_error.  */

static hashval_t
hash_symbol_error (const void *a)
{
  const struct symbol_error *se = (const struct symbol_error *) a;

  return htab_hash_pointer (se->sym);
}

/* Equality function for struct symbol_error.  */

static int
eq_symbol_error (const void *a, const void *b)
{
  const struct symbol_error *sea = (const struct symbol_error *) a;
  const struct symbol_error *seb = (const struct symbol_error *) b;

  return sea->sym == seb->sym;
}

/* Deletion function for struct symbol_error.  */

static void
del_symbol_error (void *a)
{
  struct symbol_error *se = (struct symbol_error *) a;

  xfree (se->message);
  xfree (se);
}

/* Constructor for compile_instance.  */

compile_instance::compile_instance (struct gcc_base_context *gcc_fe,
				    const char *options)
  : m_gcc_fe (gcc_fe), m_gcc_target_options (options),
    m_type_map (htab_create_alloc (10, hash_type_map_instance,
				   eq_type_map_instance,
				   xfree, xcalloc, xfree)),
    m_symbol_err_map (htab_create_alloc (10, hash_symbol_error,
					 eq_symbol_error, del_symbol_error,
					 xcalloc, xfree))
{
}

/* See compile-internal.h.  */

bool
compile_instance::get_cached_type (struct type *type, gcc_type *ret) const
{
  struct type_map_instance inst, *found;

  inst.type = type;
  found = (struct type_map_instance *) htab_find (m_type_map.get (), &inst);
  if (found != NULL)
    {
      *ret = found->gcc_type_handle;
      return true;
    }

  return false;
}

/* See compile-internal.h.  */

void
compile_instance::insert_type (struct type *type, gcc_type gcc_type)
{
  struct type_map_instance inst, *add;
  void **slot;

  inst.type = type;
  inst.gcc_type_handle = gcc_type;
  slot = htab_find_slot (m_type_map.get (), &inst, INSERT);

  add = (struct type_map_instance *) *slot;
  /* The type might have already been inserted in order to handle
     recursive types.  */
  if (add != NULL && add->gcc_type_handle != gcc_type)
    error (_("Unexpected type id from GCC, check you use recent enough GCC."));

  if (add == NULL)
    {
      add = XNEW (struct type_map_instance);
      *add = inst;
      *slot = add;
    }
}

/* See compile-internal.h.  */

void
compile_instance::insert_symbol_error (const struct symbol *sym,
				       const char *text)
{
  struct symbol_error e;
  void **slot;

  e.sym = sym;
  slot = htab_find_slot (m_symbol_err_map.get (), &e, INSERT);
  if (*slot == NULL)
    {
      struct symbol_error *ep = XNEW (struct symbol_error);

      ep->sym = sym;
      ep->message = xstrdup (text);
      *slot = ep;
    }
}

/* See compile-internal.h.  */

void
compile_instance::error_symbol_once (const struct symbol *sym)
{
  struct symbol_error search;
  struct symbol_error *err;

  if (m_symbol_err_map == NULL)
    return;

  search.sym = sym;
  err = (struct symbol_error *) htab_find (m_symbol_err_map.get (), &search);
  if (err == NULL || err->message == NULL)
    return;

  gdb::unique_xmalloc_ptr<char> message (err->message);
  err->message = NULL;
  error (_("%s"), message.get ());
}

/* Implement "show debug compile".  */

static void
show_compile_debug (struct ui_file *file, int from_tty,
		    struct cmd_list_element *c, const char *value)
{
  fprintf_filtered (file, _("Compile debugging is %s.\n"), value);
}



/* Options for the compile command.  */

struct compile_options
{
  /* For -raw.  */
  bool raw = false;
};

using compile_flag_option_def
  = gdb::option::flag_option_def<compile_options>;

static const gdb::option::option_def compile_command_option_defs[] = {

  compile_flag_option_def {
    "raw",
    [] (compile_options *opts) { return &opts->raw; },
    N_("Suppress automatic 'void _gdb_expr () { CODE }' wrapping."),
  },

};

/* Create an option_def_group for the "compile" command's options,
   with OPTS as context.  */

static gdb::option::option_def_group
make_compile_options_def_group (compile_options *opts)
{
  return {{compile_command_option_defs}, opts};
}

/* Handle the input from the 'compile file' command.  The "compile
   file" command is used to evaluate an expression contained in a file
   that may contain calls to the GCC compiler.  */

static void
compile_file_command (const char *args, int from_tty)
{
  scoped_restore save_async = make_scoped_restore (&current_ui->async, 0);

  /* Check if a -raw option is provided.  */

  compile_options options;

  const gdb::option::option_def_group group
    = make_compile_options_def_group (&options);
  gdb::option::process_options
    (&args, gdb::option::PROCESS_OPTIONS_UNKNOWN_IS_ERROR,
     group);

  enum compile_i_scope_types scope
    = options.raw ? COMPILE_I_RAW_SCOPE : COMPILE_I_SIMPLE_SCOPE;

  args = skip_spaces (args);

  /* After processing options, check whether we have a filename.  */
  if (args == nullptr || args[0] == '\0')
    error (_("You must provide a filename for this command."));

  args = skip_spaces (args);
  gdb::unique_xmalloc_ptr<char> abspath = gdb_abspath (args);
  std::string buffer = string_printf ("#include \"%s\"\n", abspath.get ());
  eval_compile_command (NULL, buffer.c_str (), scope, NULL);
}

/* Completer for the "compile file" command.  */

static void
compile_file_command_completer (struct cmd_list_element *ignore,
				completion_tracker &tracker,
				const char *text, const char *word)
{
  const gdb::option::option_def_group group
    = make_compile_options_def_group (nullptr);
  if (gdb::option::complete_options
      (tracker, &text, gdb::option::PROCESS_OPTIONS_UNKNOWN_IS_ERROR, group))
    return;

  word = advance_to_filename_complete_word_point (tracker, text);
  filename_completer (ignore, tracker, text, word);
}

/* Handle the input from the 'compile code' command.  The
   "compile code" command is used to evaluate an expression that may
   contain calls to the GCC compiler.  The language expected in this
   compile command is the language currently set in GDB.  */

static void
compile_code_command (const char *args, int from_tty)
{
  scoped_restore save_async = make_scoped_restore (&current_ui->async, 0);

  compile_options options;

  const gdb::option::option_def_group group
    = make_compile_options_def_group (&options);
  gdb::option::process_options
    (&args, gdb::option::PROCESS_OPTIONS_UNKNOWN_IS_ERROR, group);

  enum compile_i_scope_types scope
    = options.raw ? COMPILE_I_RAW_SCOPE : COMPILE_I_SIMPLE_SCOPE;

  if (args && *args)
    eval_compile_command (NULL, args, scope, NULL);
  else
    {
      counted_command_line l = get_command_line (compile_control, "");

      l->control_u.compile.scope = scope;
      execute_control_command_untraced (l.get ());
    }
}

/* Completer for the "compile code" command.  */

static void
compile_code_command_completer (struct cmd_list_element *ignore,
				completion_tracker &tracker,
				const char *text, const char *word)
{
  const gdb::option::option_def_group group
    = make_compile_options_def_group (nullptr);
  if (gdb::option::complete_options
      (tracker, &text, gdb::option::PROCESS_OPTIONS_UNKNOWN_IS_ERROR, group))
    return;

  word = advance_to_expression_complete_word_point (tracker, text);
  symbol_completer (ignore, tracker, text, word);
}

/* Callback for compile_print_command.  */

void
compile_print_value (struct value *val, void *data_voidp)
{
  const value_print_options *print_opts = (value_print_options *) data_voidp;

  print_value (val, *print_opts);
}

/* Handle the input from the 'compile print' command.  The "compile
   print" command is used to evaluate and print an expression that may
   contain calls to the GCC compiler.  The language expected in this
   compile command is the language currently set in GDB.  */

static void
compile_print_command (const char *arg, int from_tty)
{
  enum compile_i_scope_types scope = COMPILE_I_PRINT_ADDRESS_SCOPE;
  value_print_options print_opts;

  scoped_restore save_async = make_scoped_restore (&current_ui->async, 0);

  get_user_print_options (&print_opts);
  /* Override global settings with explicit options, if any.  */
  auto group = make_value_print_options_def_group (&print_opts);
  gdb::option::process_options
    (&arg, gdb::option::PROCESS_OPTIONS_REQUIRE_DELIMITER, group);

  print_command_parse_format (&arg, "compile print", &print_opts);

  /* Passing &PRINT_OPTS as SCOPE_DATA is safe as do_module_cleanup
     will not touch the stale pointer if compile_object_run has
     already quit.  */

  if (arg && *arg)
    eval_compile_command (NULL, arg, scope, &print_opts);
  else
    {
      counted_command_line l = get_command_line (compile_control, "");

      l->control_u.compile.scope = scope;
      l->control_u.compile.scope_data = &print_opts;
      execute_control_command_untraced (l.get ());
    }
}

/* A cleanup function to remove a directory and all its contents.  */

static void
do_rmdir (void *arg)
{
  const char *dir = (const char *) arg;
  char *zap;
  int wstat;

  gdb_assert (startswith (dir, TMP_PREFIX));
  zap = concat ("rm -rf ", dir, (char *) NULL);
  wstat = system (zap);
  if (wstat == -1 || !WIFEXITED (wstat) || WEXITSTATUS (wstat) != 0)
    warning (_("Could not remove temporary directory %s"), dir);
  XDELETEVEC (zap);
}

/* Return the name of the temporary directory to use for .o files, and
   arrange for the directory to be removed at shutdown.  */

static const char *
get_compile_file_tempdir (void)
{
  static char *tempdir_name;

#define TEMPLATE TMP_PREFIX "XXXXXX"
  char tname[sizeof (TEMPLATE)];

  if (tempdir_name != NULL)
    return tempdir_name;

  strcpy (tname, TEMPLATE);
#undef TEMPLATE
  tempdir_name = mkdtemp (tname);
  if (tempdir_name == NULL)
    perror_with_name (_("Could not make temporary directory"));

  tempdir_name = xstrdup (tempdir_name);
  make_final_cleanup (do_rmdir, tempdir_name);
  return tempdir_name;
}

/* Compute the names of source and object files to use.  */

static compile_file_names
get_new_file_names ()
{
  static int seq;
  const char *dir = get_compile_file_tempdir ();

  ++seq;

  return compile_file_names (string_printf ("%s%sout%d.c",
					    dir, SLASH_STRING, seq),
			     string_printf ("%s%sout%d.o",
					    dir, SLASH_STRING, seq));
}

/* Get the block and PC at which to evaluate an expression.  */

static const struct block *
get_expr_block_and_pc (CORE_ADDR *pc)
{
  const struct block *block = get_selected_block (pc);

  if (block == NULL)
    {
      struct symtab_and_line cursal = get_current_source_symtab_and_line ();

      if (cursal.symtab)
	block = BLOCKVECTOR_BLOCK (SYMTAB_BLOCKVECTOR (cursal.symtab),
				   STATIC_BLOCK);
      if (block != NULL)
	*pc = BLOCK_ENTRY_PC (block);
    }
  else
    *pc = BLOCK_ENTRY_PC (block);

  return block;
}

/* String for 'set compile-args' and 'show compile-args'.  */
static std::string compile_args =
  /* Override flags possibly coming from DW_AT_producer.  */
  "-O0 -gdwarf-4"
  /* We use -fPIE Otherwise GDB would need to reserve space large enough for
     any object file in the inferior in advance to get the final address when
     to link the object file to and additionally the default system linker
     script would need to be modified so that one can specify there the
     absolute target address.
     -fPIC is not used at is would require from GDB to generate .got.  */
  " -fPIE"
  /* We want warnings, except for some commonly happening for GDB commands.  */
  " -Wall "
  " -Wno-unused-but-set-variable"
  " -Wno-unused-variable"
  /* Override CU's possible -fstack-protector-strong.  */
  " -fno-stack-protector";

/* Parsed form of COMPILE_ARGS.  */
static gdb_argv compile_args_argv;

/* Implement 'set compile-args'.  */

static void
set_compile_args (const char *args, int from_tty, struct cmd_list_element *c)
{
  compile_args_argv = gdb_argv (compile_args.c_str ());
}

/* Implement 'show compile-args'.  */

static void
show_compile_args (struct ui_file *file, int from_tty,
		   struct cmd_list_element *c, const char *value)
{
  fprintf_filtered (file, _("Compile command command-line arguments "
			    "are \"%s\".\n"),
		    value);
}

/* String for 'set compile-gcc' and 'show compile-gcc'.  */
static std::string compile_gcc;

/* Implement 'show compile-gcc'.  */

static void
show_compile_gcc (struct ui_file *file, int from_tty,
		  struct cmd_list_element *c, const char *value)
{
  fprintf_filtered (file, _("Compile command GCC driver filename is \"%s\".\n"),
		    value);
}

/* Return DW_AT_producer parsed for get_selected_frame () (if any).
   Return NULL otherwise.

   GCC already filters its command-line arguments only for the suitable ones to
   put into DW_AT_producer - see GCC function gen_producer_string.  */

static const char *
get_selected_pc_producer_options (void)
{
  CORE_ADDR pc = get_frame_pc (get_selected_frame (NULL));
  struct compunit_symtab *symtab = find_pc_compunit_symtab (pc);
  const char *cs;

  if (symtab == NULL || symtab->producer == NULL
      || !startswith (symtab->producer, "GNU "))
    return NULL;

  cs = symtab->producer;
  while (*cs != 0 && *cs != '-')
    cs = skip_spaces (skip_to_space (cs));
  if (*cs != '-')
    return NULL;
  return cs;
}

/* Filter out unwanted options from ARGV.  */

static void
filter_args (char **argv)
{
  char **destv;

  for (destv = argv; *argv != NULL; argv++)
    {
      /* -fpreprocessed may get in commonly from ccache.  */
      if (strcmp (*argv, "-fpreprocessed") == 0)
	{
	  xfree (*argv);
	  continue;
	}
      *destv++ = *argv;
    }
  *destv = NULL;
}

/* Produce final vector of GCC compilation options.

   The first element of the combined argument vector are arguments
   relating to the target size ("-m64", "-m32" etc.).  These are
   sourced from the inferior's architecture.

   The second element of the combined argument vector are arguments
   stored in the inferior DW_AT_producer section.  If these are stored
   in the inferior (there is no guarantee that they are), they are
   added to the vector.

   The third element of the combined argument vector are argument
   supplied by the language implementation provided by
   compile-{lang}-support.  These contain language specific arguments.

   The final element of the combined argument vector are arguments
   supplied by the "set compile-args" command.  These are always
   appended last so as to override any of the arguments automatically
   generated above.  */

static gdb_argv
get_args (const compile_instance *compiler, struct gdbarch *gdbarch)
{
  const char *cs_producer_options;
  gdb_argv result;

  std::string gcc_options = gdbarch_gcc_target_options (gdbarch);

  /* Make sure we have a non-empty set of options, otherwise GCC will
     error out trying to look for a filename that is an empty string.  */
  if (!gcc_options.empty ())
    result = gdb_argv (gcc_options.c_str ());

  cs_producer_options = get_selected_pc_producer_options ();
  if (cs_producer_options != NULL)
    {
      gdb_argv argv_producer (cs_producer_options);
      filter_args (argv_producer.get ());

      result.append (std::move (argv_producer));
    }

  result.append (gdb_argv (compiler->gcc_target_options ().c_str ()));
  result.append (compile_args_argv);

  return result;
}

/* A helper function suitable for use as the "print_callback" in the
   compiler object.  */

static void
print_callback (void *ignore, const char *message)
{
  fputs_filtered (message, gdb_stderr);
}

/* Process the compilation request.  On success it returns the object
   and source file names.  On an error condition, error () is
   called.  */

static compile_file_names
compile_to_object (struct command_line *cmd, const char *cmd_string,
		   enum compile_i_scope_types scope)
{
  const struct block *expr_block;
  CORE_ADDR trash_pc, expr_pc;
  int ok;
  struct gdbarch *gdbarch = get_current_arch ();
  std::string triplet_rx;

  if (!target_has_execution ())
    error (_("The program must be running for the compile command to "\
	     "work."));

  expr_block = get_expr_block_and_pc (&trash_pc);
  expr_pc = get_frame_address_in_block (get_selected_frame (NULL));

  /* Set up instance and context for the compiler.  */
  std::unique_ptr<compile_instance> compiler
    = current_language->get_compile_instance ();
  if (compiler == nullptr)
    error (_("No compiler support for language %s."),
	   current_language->name ());
  compiler->set_print_callback (print_callback, NULL);
  compiler->set_scope (scope);
  compiler->set_block (expr_block);

  /* From the provided expression, build a scope to pass to the
     compiler.  */

  string_file input_buf;
  const char *input;

  if (cmd != NULL)
    {
      struct command_line *iter;

      for (iter = cmd->body_list_0.get (); iter; iter = iter->next)
	{
	  input_buf.puts (iter->line);
	  input_buf.puts ("\n");
	}

      input = input_buf.c_str ();
    }
  else if (cmd_string != NULL)
    input = cmd_string;
  else
    error (_("Neither a simple expression, or a multi-line specified."));

  std::string code
    = current_language->compute_program (compiler.get (), input, gdbarch,
					 expr_block, expr_pc);
  if (compile_debug)
    fprintf_unfiltered (gdb_stdlog, "debug output:\n\n%s", code.c_str ());

  compiler->set_verbose (compile_debug);

  if (!compile_gcc.empty ())
    {
      if (compiler->version () < GCC_FE_VERSION_1)
	error (_("Command 'set compile-gcc' requires GCC version 6 or higher "
		 "(libcc1 interface version 1 or higher)"));

      compiler->set_driver_filename (compile_gcc.c_str ());
    }
  else
    {
      const char *os_rx = osabi_triplet_regexp (gdbarch_osabi (gdbarch));
      const char *arch_rx = gdbarch_gnu_triplet_regexp (gdbarch);

      /* Allow triplets with or without vendor set.  */
      triplet_rx = std::string (arch_rx) + "(-[^-]*)?-";
      if (os_rx != nullptr)
	triplet_rx += os_rx;
      compiler->set_triplet_regexp (triplet_rx.c_str ());
    }

  /* Set compiler command-line arguments.  */
  gdb_argv argv_holder = get_args (compiler.get (), gdbarch);
  int argc = argv_holder.count ();
  char **argv = argv_holder.get ();

  gdb::unique_xmalloc_ptr<char> error_message
    = compiler->set_arguments (argc, argv, triplet_rx.c_str ());

  if (error_message != NULL)
    error ("%s", error_message.get ());

  if (compile_debug)
    {
      int argi;

      fprintf_unfiltered (gdb_stdlog, "Passing %d compiler options:\n", argc);
      for (argi = 0; argi < argc; argi++)
	fprintf_unfiltered (gdb_stdlog, "Compiler option %d: <%s>\n",
			    argi, argv[argi]);
    }

  compile_file_names fnames = get_new_file_names ();

  gdb::optional<gdb::unlinker> source_remover;

  {
    gdb_file_up src = gdb_fopen_cloexec (fnames.source_file (), "w");
    if (src == NULL)
      perror_with_name (_("Could not open source file for writing"));

    source_remover.emplace (fnames.source_file ());

    if (fputs (code.c_str (), src.get ()) == EOF)
      perror_with_name (_("Could not write to source file"));
  }

  if (compile_debug)
    fprintf_unfiltered (gdb_stdlog, "source file produced: %s\n\n",
			fnames.source_file ());

  /* If we don't do this, then GDB simply exits
     when the compiler dies.  */
  scoped_ignore_sigpipe ignore_sigpipe;

  /* Call the compiler and start the compilation process.  */
  compiler->set_source_file (fnames.source_file ());
  ok = compiler->compile (fnames.object_file (), compile_debug);
  if (!ok)
    error (_("Compilation failed."));

  if (compile_debug)
    fprintf_unfiltered (gdb_stdlog, "object file produced: %s\n\n",
			fnames.object_file ());

  /* Keep the source file.  */
  source_remover->keep ();
  return fnames;
}

/* The "compile" prefix command.  */

static void
compile_command (const char *args, int from_tty)
{
  /* If a sub-command is not specified to the compile prefix command,
     assume it is a direct code compilation.  */
  compile_code_command (args, from_tty);
}

/* See compile.h.  */

void
eval_compile_command (struct command_line *cmd, const char *cmd_string,
		      enum compile_i_scope_types scope, void *scope_data)
{
  compile_file_names fnames = compile_to_object (cmd, cmd_string, scope);

  gdb::unlinker object_remover (fnames.object_file ());
  gdb::unlinker source_remover (fnames.source_file ());

  compile_module_up compile_module = compile_object_load (fnames, scope,
							  scope_data);
  if (compile_module == NULL)
    {
      gdb_assert (scope == COMPILE_I_PRINT_ADDRESS_SCOPE);
      eval_compile_command (cmd, cmd_string,
			    COMPILE_I_PRINT_VALUE_SCOPE, scope_data);
      return;
    }

  /* Keep the files.  */
  source_remover.keep ();
  object_remover.keep ();

  compile_object_run (std::move (compile_module));
}

/* See compile/compile-internal.h.  */

std::string
compile_register_name_mangled (struct gdbarch *gdbarch, int regnum)
{
  const char *regname = gdbarch_register_name (gdbarch, regnum);

  return string_printf ("__%s", regname);
}

/* See compile/compile-internal.h.  */

int
compile_register_name_demangle (struct gdbarch *gdbarch,
				 const char *regname)
{
  int regnum;

  if (regname[0] != '_' || regname[1] != '_')
    error (_("Invalid register name \"%s\"."), regname);
  regname += 2;

  for (regnum = 0; regnum < gdbarch_num_regs (gdbarch); regnum++)
    if (strcmp (regname, gdbarch_register_name (gdbarch, regnum)) == 0)
      return regnum;

  error (_("Cannot find gdbarch register \"%s\"."), regname);
}

/* Forwards to the plug-in.  */

#define FORWARD(OP,...) (m_gcc_fe->ops->OP (m_gcc_fe, ##__VA_ARGS__))

/* See compile-internal.h.  */

void
compile_instance::set_print_callback
  (void (*print_function) (void *, const char *), void *datum)
{
  FORWARD (set_print_callback, print_function, datum);
}

/* See compile-internal.h.  */

unsigned int
compile_instance::version () const
{
  return m_gcc_fe->ops->version;
}

/* See compile-internal.h.  */

void
compile_instance::set_verbose (int level)
{
  if (version () >= GCC_FE_VERSION_1)
    FORWARD (set_verbose, level);
}

/* See compile-internal.h.  */

void
compile_instance::set_driver_filename (const char *filename)
{
  if (version () >= GCC_FE_VERSION_1)
    FORWARD (set_driver_filename, filename);
}

/* See compile-internal.h.  */

void
compile_instance::set_triplet_regexp (const char *regexp)
{
  if (version () >= GCC_FE_VERSION_1)
    FORWARD (set_triplet_regexp, regexp);
}

/* See compile-internal.h.  */

gdb::unique_xmalloc_ptr<char>
compile_instance::set_arguments (int argc, char **argv, const char *regexp)
{
  if (version () >= GCC_FE_VERSION_1)
    return gdb::unique_xmalloc_ptr<char> (FORWARD (set_arguments, argc, argv));
  else
    return gdb::unique_xmalloc_ptr<char> (FORWARD (set_arguments_v0, regexp,
						   argc, argv));
}

/* See compile-internal.h.  */

void
compile_instance::set_source_file (const char *filename)
{
  FORWARD (set_source_file, filename);
}

/* See compile-internal.h.  */

bool
compile_instance::compile (const char *filename, int verbose_level)
{
  if (version () >= GCC_FE_VERSION_1)
    return FORWARD (compile, filename);
  else
    return FORWARD (compile_v0, filename, verbose_level);
}

#undef FORWARD

/* See compile.h.  */
cmd_list_element *compile_cmd_element = nullptr;

void _initialize_compile ();
void
_initialize_compile ()
{
  struct cmd_list_element *c = NULL;

  compile_cmd_element = add_prefix_cmd ("compile", class_obscure,
					compile_command, _("\
Command to compile source code and inject it into the inferior."),
		  &compile_command_list, 1, &cmdlist);
  add_com_alias ("expression", compile_cmd_element, class_obscure, 0);

  const auto compile_opts = make_compile_options_def_group (nullptr);

  static const std::string compile_code_help
    = gdb::option::build_help (_("\
Compile, inject, and execute code.\n\
\n\
Usage: compile code [OPTION]... [CODE]\n\
\n\
Options:\n\
%OPTIONS%\n\
\n\
The source code may be specified as a simple one line expression, e.g.:\n\
\n\
    compile code printf(\"Hello world\\n\");\n\
\n\
Alternatively, you can type a multiline expression by invoking\n\
this command with no argument.  GDB will then prompt for the\n\
expression interactively; type a line containing \"end\" to\n\
indicate the end of the expression."),
			       compile_opts);

  c = add_cmd ("code", class_obscure, compile_code_command,
	       compile_code_help.c_str (),
	       &compile_command_list);
  set_cmd_completer_handle_brkchars (c, compile_code_command_completer);

static const std::string compile_file_help
    = gdb::option::build_help (_("\
Evaluate a file containing source code.\n\
\n\
Usage: compile file [OPTION].. [FILENAME]\n\
\n\
Options:\n\
%OPTIONS%"),
			       compile_opts);

  c = add_cmd ("file", class_obscure, compile_file_command,
	       compile_file_help.c_str (),
	       &compile_command_list);
  set_cmd_completer_handle_brkchars (c, compile_file_command_completer);

  const auto compile_print_opts = make_value_print_options_def_group (nullptr);

  static const std::string compile_print_help
    = gdb::option::build_help (_("\
Evaluate EXPR by using the compiler and print result.\n\
\n\
Usage: compile print [[OPTION]... --] [/FMT] [EXPR]\n\
\n\
Options:\n\
%OPTIONS%\n\
\n\
Note: because this command accepts arbitrary expressions, if you\n\
specify any command option, you must use a double dash (\"--\")\n\
to mark the end of option processing.  E.g.: \"compile print -o -- myobj\".\n\
\n\
The expression may be specified on the same line as the command, e.g.:\n\
\n\
    compile print i\n\
\n\
Alternatively, you can type a multiline expression by invoking\n\
this command with no argument.  GDB will then prompt for the\n\
expression interactively; type a line containing \"end\" to\n\
indicate the end of the expression.\n\
\n\
EXPR may be preceded with /FMT, where FMT is a format letter\n\
but no count or size letter (see \"x\" command)."),
			       compile_print_opts);

  c = add_cmd ("print", class_obscure, compile_print_command,
	       compile_print_help.c_str (),
	       &compile_command_list);
  set_cmd_completer_handle_brkchars (c, print_command_completer);

  add_setshow_boolean_cmd ("compile", class_maintenance, &compile_debug, _("\
Set compile command debugging."), _("\
Show compile command debugging."), _("\
When on, compile command debugging is enabled."),
			   NULL, show_compile_debug,
			   &setdebuglist, &showdebuglist);

  add_setshow_string_cmd ("compile-args", class_support,
			  &compile_args,
			  _("Set compile command GCC command-line arguments."),
			  _("Show compile command GCC command-line arguments."),
			  _("\
Use options like -I (include file directory) or ABI settings.\n\
String quoting is parsed like in shell, for example:\n\
  -mno-align-double \"-I/dir with a space/include\""),
			  set_compile_args, show_compile_args, &setlist, &showlist);


  /* Initialize compile_args_argv.  */
  set_compile_args (compile_args.c_str (), 0, NULL);

  add_setshow_optional_filename_cmd ("compile-gcc", class_support,
				     &compile_gcc,
				     _("Set compile command "
				       "GCC driver filename."),
				     _("Show compile command "
				       "GCC driver filename."),
				     _("\
It should be absolute filename of the gcc executable.\n\
If empty the default target triplet will be searched in $PATH."),
				     NULL, show_compile_gcc, &setlist,
				     &showlist);
}
