/* Copyright (C) 2021-2024 Free Software Foundation, Inc.
   Contributed by Oracle.

   This file is part of GNU Binutils.

   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; if not, write to the Free Software
   Foundation, 51 Franklin Street - Fifth Floor, Boston,
   MA 02110-1301, USA.  */

#ifndef _COMMAND_H
#define _COMMAND_H


#include <stdio.h>
#include <sys/types.h>

#include "Metric.h"
#include "Hist_data.h"
#include "dbe_types.h"
#include "vec.h"
#include "enums.h"

// This enum lists all the commands parsed by er_print
//  The ordering here is not important, but LAST_CMD must
//  be defined as the last command for which a help line will exist
//  Command.cc has a matching list, and the ordering in
//  that list determines what shows up under the help and xhelp commands.
//  In particular, the entry for HELP is the last one printed
//  for the help command, and the entry for HHELP is the last
//  one printed for xhelp.

enum CmdType
{
  // Pathtree-related commands
  FUNCS = 0,
  HOTPCS,
  HOTLINES,
  FDETAIL,
  OBJECTS,
  LDETAIL,
  PDETAIL,
  SOURCE,
  DISASM,
  METRIC_LIST,
  METRICS,
  SORT,
  GPROF,
  GMETRIC_LIST,
  FSINGLE,
  CSINGLE,
  CPREPEND,
  CAPPEND,
  CRMFIRST,
  CRMLAST,
  CALLTREE,
  CALLFLAME,

  // Source/disassembly control commands
  SCOMPCOM,
  STHRESH,
  DCOMPCOM,
  COMPCOM,
  DTHRESH,

  // Heap trace-related commands
  LEAKS,
  ALLOCS,
  HEAP,
  HEAPSTAT,

  // I/O trace-related commands
  IOACTIVITY,
  IOVFD,
  IOCALLSTACK,
  IOSTAT,

  // Race detection related commands
  RACE_EVNTS,
  RACE_SUM,

  // Deadlock detection commands
  DEADLOCK_EVNTS,
  DEADLOCK_SUM,

  // DataSpace commands
  DOBJECTS,
  DO_SINGLE,
  DO_LAYOUT,
  DO_METRIC_LIST,

  // MemorySpace commands
  MEMOBJ,
  MEMOBJLIST,
  MEMOBJDEF,
  MEMOBJDROP,
  MACHINEMODEL,

  // Custom tab commands
  INDXOBJDEF,
  INDXOBJLIST,
  INDXOBJ,
  INDX_METRIC_LIST,

  // Old-style filtering commands
  OBJECT_LIST,
  OBJECT_SELECT,
  SAMPLE_LIST,
  SAMPLE_SELECT,
  THREAD_LIST,
  THREAD_SELECT,
  LWP_LIST,
  LWP_SELECT,
  CPU_LIST,
  CPU_SELECT,

  // Shared Object display commands
  OBJECT_SHOW,
  OBJECT_HIDE,
  OBJECT_API,
  OBJECTS_DEFAULT,

  // the new filtering commands
  FILTERS,

  // Miscellaneous commands
  COMPARE,
  PRINTMODE,
  HEADER,
  OVERVIEW_NEW,
  SAMPLE_DETAIL,
  STATISTICS,
  EXP_LIST,
  DESCRIBE,
  OUTFILE,
  APPENDFILE,
  LIMIT,
  NAMEFMT,
  VIEWMODE,
  EN_DESC,
  SETPATH,
  ADDPATH,
  PATHMAP,
  LIBDIRS,
  SCRIPT,
  VERSION_cmd,
  QUIT,
  PROCSTATS,

  // Experiments handling commands
  ADD_EXP,
  DROP_EXP,
  OPEN_EXP,

  // .rc-only Commands
  DMETRICS,
  DSORT,
  TLMODE,
  TLDATA,
  TABS,
  TIMELINE,
  MPI_TIMELINE,
  MPI_CHART,
  TIMELINE_CLASSIC_TBR,
  SOURCE_V2,
  DISASM_V2,
  RTABS,
  DUALSOURCE,
  SOURCEDISAM,

  HELP,             // this is the last of the commands listed with "help"
  IFREQ,
  DUMPNODES,
  DUMPSTACKS,
  DUMPUNK,
  DUMPFUNC,
  DUMPDOBJS,
  DUMPMAP,
  DUMPENTITIES,
  DUMP_PROFILE,
  DUMP_SYNC,
  DUMP_HWC,
  DUMP_HEAP,
  DUMP_IOTRACE,
  RACE_ACCS,
  DMPI_FUNCS,
  DMPI_MSGS,
  DMPI_EVENTS,
  DMEM,
  DUMP_GC,
  DKILL,
  IGNORE_NO_XHWCPROF,
  IGNORE_FS_WARN,
  QQUIT,
  HHELP,            // this is the last command listed with "xhelp"
  NO_CMD,           // Dummy command, used for headers in help
  DUMMY_CMD,        // Dummy command, used for help

  // unused commands
  LOADOBJECT,
  LOADOBJECT_LIST,
  LOADOBJECT_SELECT,

  // Internal-only Commands
  LAST_CMD,         // No more commands for which a help line is possible
  STDIN,
  COMMENT,
  WHOAMI,

  // Error return "commands"
  AMBIGUOUS_CMD,
  UNKNOWN_CMD
};

typedef struct
{
  const CmdType token;      // command key
  const char *str;          // command string
  const char *alt;          // alternate command string
  const char *arg;          // argument string for help
  const int arg_count;      // no. of arguments
  char **desc;              // description for help
} Cmdtable;

// Command class: never instantiated, completely static
class Command
{
public:

  // look up a string in the command table, return type, set number of args
  static CmdType get_command (char *cmd, int &arg_count, int &param);
  static const char *get_cmd_str (CmdType type);
  static void print_help (char *prog_name, bool cmd_line, bool usermode, FILE *outf);
  static char *get_err_string (Cmd_status err);

  static const char *DEFAULT_METRICS;   // default if no .rc files read
  static const char *DEFAULT_SORT;      // default if no .rc files read
  static const char *DEFAULT_CMD;       // token for default
  static const char *ALL_CMD;           // token for all
  static const char *ANY_CMD;           // token for any
  static const char *NONE_CMD;          // token for none
  static const char *HWC_CMD;           // token for all HWC
  static const char *BIT_CMD;           // token for any bit-derived metric

private:
  static const int user_no;             // the last user command
  static const int hidden_no;           // the last hidden command
  static const int command_no;          // the last parsable command

  static void init_desc ();
  static char *fmt_help (int nc, char head);
};

// Analyzer display tabs
struct DispTab
{
  DispTab (int ntype, int num, bool vis, CmdType token)
  {
    type = ntype;
    order = num;
    visible = vis;
    available = true;
    cmdtoken = token;
  }

  void setAvailability (bool val)       { available = val; }

  int type;             // Display type
  int order;            // Order in which tabs should appear in GUI
  bool visible;         // Is Tab visible
  bool available;       // Is tab available for this experiment
  CmdType cmdtoken;     // command token
  int param;            // command parameter (used for memory space)
};

#endif /* ! _COMMAND_H */