Home | History | Annotate | Line # | Download | only in jit
      1  1.1  mrg /* Internals of libgccjit: classes for playing back recorded API calls.
      2  1.7  mrg    Copyright (C) 2013-2022 Free Software Foundation, Inc.
      3  1.1  mrg    Contributed by David Malcolm <dmalcolm (at) redhat.com>.
      4  1.1  mrg 
      5  1.1  mrg This file is part of GCC.
      6  1.1  mrg 
      7  1.1  mrg GCC is free software; you can redistribute it and/or modify it
      8  1.1  mrg under the terms of the GNU General Public License as published by
      9  1.1  mrg the Free Software Foundation; either version 3, or (at your option)
     10  1.1  mrg any later version.
     11  1.1  mrg 
     12  1.1  mrg GCC is distributed in the hope that it will be useful, but
     13  1.1  mrg WITHOUT ANY WARRANTY; without even the implied warranty of
     14  1.1  mrg MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     15  1.1  mrg General Public License for more details.
     16  1.1  mrg 
     17  1.1  mrg You should have received a copy of the GNU General Public License
     18  1.1  mrg along with GCC; see the file COPYING3.  If not see
     19  1.1  mrg <http://www.gnu.org/licenses/>.  */
     20  1.1  mrg 
     21  1.1  mrg #ifndef JIT_PLAYBACK_H
     22  1.1  mrg #define JIT_PLAYBACK_H
     23  1.1  mrg 
     24  1.1  mrg #include <utility> // for std::pair
     25  1.1  mrg 
     26  1.1  mrg #include "timevar.h"
     27  1.7  mrg #include "varasm.h"
     28  1.1  mrg 
     29  1.1  mrg #include "jit-recording.h"
     30  1.1  mrg 
     31  1.3  mrg struct diagnostic_context;
     32  1.3  mrg struct diagnostic_info;
     33  1.3  mrg 
     34  1.1  mrg namespace gcc {
     35  1.1  mrg 
     36  1.1  mrg namespace jit {
     37  1.1  mrg 
     38  1.1  mrg /**********************************************************************
     39  1.1  mrg  Playback.
     40  1.1  mrg  **********************************************************************/
     41  1.1  mrg 
     42  1.1  mrg namespace playback {
     43  1.1  mrg 
     44  1.1  mrg /* playback::context is an abstract base class.
     45  1.1  mrg 
     46  1.1  mrg    The two concrete subclasses are:
     47  1.1  mrg    - playback::compile_to_memory
     48  1.1  mrg    - playback::compile_to_file.  */
     49  1.1  mrg 
     50  1.1  mrg class context : public log_user
     51  1.1  mrg {
     52  1.1  mrg public:
     53  1.1  mrg   context (::gcc::jit::recording::context *ctxt);
     54  1.1  mrg   ~context ();
     55  1.1  mrg 
     56  1.1  mrg   void gt_ggc_mx ();
     57  1.1  mrg 
     58  1.1  mrg   void replay ();
     59  1.1  mrg 
     60  1.1  mrg   location *
     61  1.1  mrg   new_location (recording::location *rloc,
     62  1.1  mrg 		const char *filename,
     63  1.1  mrg 		int line,
     64  1.1  mrg 		int column);
     65  1.1  mrg 
     66  1.1  mrg   type *
     67  1.1  mrg   get_type (enum gcc_jit_types type);
     68  1.1  mrg 
     69  1.1  mrg   type *
     70  1.1  mrg   new_array_type (location *loc,
     71  1.1  mrg 		  type *element_type,
     72  1.1  mrg 		  int num_elements);
     73  1.1  mrg 
     74  1.1  mrg   field *
     75  1.1  mrg   new_field (location *loc,
     76  1.1  mrg 	     type *type,
     77  1.1  mrg 	     const char *name);
     78  1.1  mrg 
     79  1.6  mrg   field *
     80  1.6  mrg   new_bitfield (location *loc,
     81  1.6  mrg 		type *type,
     82  1.6  mrg 		int width,
     83  1.6  mrg 		const char *name);
     84  1.6  mrg 
     85  1.1  mrg   compound_type *
     86  1.1  mrg   new_compound_type (location *loc,
     87  1.1  mrg 		     const char *name,
     88  1.1  mrg 		     bool is_struct); /* else is union */
     89  1.1  mrg 
     90  1.1  mrg   type *
     91  1.1  mrg   new_function_type (type *return_type,
     92  1.1  mrg 		     const auto_vec<type *> *param_types,
     93  1.1  mrg 		     int is_variadic);
     94  1.1  mrg 
     95  1.1  mrg   param *
     96  1.1  mrg   new_param (location *loc,
     97  1.1  mrg 	     type *type,
     98  1.1  mrg 	     const char *name);
     99  1.1  mrg 
    100  1.1  mrg   function *
    101  1.1  mrg   new_function (location *loc,
    102  1.1  mrg 		enum gcc_jit_function_kind kind,
    103  1.1  mrg 		type *return_type,
    104  1.1  mrg 		const char *name,
    105  1.1  mrg 		const auto_vec<param *> *params,
    106  1.1  mrg 		int is_variadic,
    107  1.1  mrg 		enum built_in_function builtin_id);
    108  1.1  mrg 
    109  1.1  mrg   lvalue *
    110  1.1  mrg   new_global (location *loc,
    111  1.1  mrg 	      enum gcc_jit_global_kind kind,
    112  1.1  mrg 	      type *type,
    113  1.7  mrg 	      const char *name,
    114  1.7  mrg 	      enum global_var_flags flags);
    115  1.7  mrg 
    116  1.7  mrg   lvalue *
    117  1.7  mrg   new_global_initialized (location *loc,
    118  1.7  mrg                           enum gcc_jit_global_kind kind,
    119  1.7  mrg                           type *type,
    120  1.7  mrg                           size_t element_size,
    121  1.7  mrg                           size_t initializer_num_elem,
    122  1.7  mrg                           const void *initializer,
    123  1.7  mrg 			  const char *name,
    124  1.7  mrg 			  enum global_var_flags flags);
    125  1.7  mrg 
    126  1.7  mrg   rvalue *
    127  1.7  mrg   new_ctor (location *log,
    128  1.7  mrg 	    type *type,
    129  1.7  mrg 	    const auto_vec<field*> *fields,
    130  1.7  mrg 	    const auto_vec<rvalue*> *rvalues);
    131  1.7  mrg 
    132  1.7  mrg 
    133  1.7  mrg   void
    134  1.7  mrg   global_set_init_rvalue (lvalue* variable,
    135  1.7  mrg 			  rvalue* init);
    136  1.1  mrg 
    137  1.1  mrg   template <typename HOST_TYPE>
    138  1.1  mrg   rvalue *
    139  1.1  mrg   new_rvalue_from_const (type *type,
    140  1.1  mrg 			 HOST_TYPE value);
    141  1.1  mrg 
    142  1.1  mrg   rvalue *
    143  1.1  mrg   new_string_literal (const char *value);
    144  1.1  mrg 
    145  1.1  mrg   rvalue *
    146  1.4  mrg   new_rvalue_from_vector (location *loc,
    147  1.4  mrg 			  type *type,
    148  1.4  mrg 			  const auto_vec<rvalue *> &elements);
    149  1.4  mrg 
    150  1.4  mrg   rvalue *
    151  1.1  mrg   new_unary_op (location *loc,
    152  1.1  mrg 		enum gcc_jit_unary_op op,
    153  1.1  mrg 		type *result_type,
    154  1.1  mrg 		rvalue *a);
    155  1.1  mrg 
    156  1.1  mrg   rvalue *
    157  1.1  mrg   new_binary_op (location *loc,
    158  1.1  mrg 		 enum gcc_jit_binary_op op,
    159  1.1  mrg 		 type *result_type,
    160  1.1  mrg 		 rvalue *a, rvalue *b);
    161  1.1  mrg 
    162  1.1  mrg   rvalue *
    163  1.1  mrg   new_comparison (location *loc,
    164  1.1  mrg 		  enum gcc_jit_comparison op,
    165  1.1  mrg 		  rvalue *a, rvalue *b);
    166  1.1  mrg 
    167  1.1  mrg   rvalue *
    168  1.1  mrg   new_call (location *loc,
    169  1.1  mrg 	    function *func,
    170  1.3  mrg 	    const auto_vec<rvalue *> *args,
    171  1.3  mrg 	    bool require_tail_call);
    172  1.1  mrg 
    173  1.1  mrg   rvalue *
    174  1.1  mrg   new_call_through_ptr (location *loc,
    175  1.1  mrg 			rvalue *fn_ptr,
    176  1.3  mrg 			const auto_vec<rvalue *> *args,
    177  1.3  mrg 			bool require_tail_call);
    178  1.1  mrg 
    179  1.1  mrg   rvalue *
    180  1.1  mrg   new_cast (location *loc,
    181  1.1  mrg 	    rvalue *expr,
    182  1.1  mrg 	    type *type_);
    183  1.1  mrg 
    184  1.7  mrg   rvalue *
    185  1.7  mrg   new_bitcast (location *loc,
    186  1.7  mrg 	       rvalue *expr,
    187  1.7  mrg 	       type *type_);
    188  1.7  mrg 
    189  1.1  mrg   lvalue *
    190  1.1  mrg   new_array_access (location *loc,
    191  1.1  mrg 		    rvalue *ptr,
    192  1.1  mrg 		    rvalue *index);
    193  1.1  mrg 
    194  1.1  mrg   void
    195  1.1  mrg   set_str_option (enum gcc_jit_str_option opt,
    196  1.1  mrg 		  const char *value);
    197  1.1  mrg 
    198  1.1  mrg   void
    199  1.1  mrg   set_int_option (enum gcc_jit_int_option opt,
    200  1.1  mrg 		  int value);
    201  1.1  mrg 
    202  1.1  mrg   void
    203  1.1  mrg   set_bool_option (enum gcc_jit_bool_option opt,
    204  1.1  mrg 		   int value);
    205  1.1  mrg 
    206  1.1  mrg   const char *
    207  1.1  mrg   get_str_option (enum gcc_jit_str_option opt) const
    208  1.1  mrg   {
    209  1.1  mrg     return m_recording_ctxt->get_str_option (opt);
    210  1.1  mrg   }
    211  1.1  mrg 
    212  1.1  mrg   int
    213  1.1  mrg   get_int_option (enum gcc_jit_int_option opt) const
    214  1.1  mrg   {
    215  1.1  mrg     return m_recording_ctxt->get_int_option (opt);
    216  1.1  mrg   }
    217  1.1  mrg 
    218  1.1  mrg   int
    219  1.1  mrg   get_bool_option (enum gcc_jit_bool_option opt) const
    220  1.1  mrg   {
    221  1.1  mrg     return m_recording_ctxt->get_bool_option (opt);
    222  1.1  mrg   }
    223  1.1  mrg 
    224  1.3  mrg   int
    225  1.3  mrg   get_inner_bool_option (enum inner_bool_option opt) const
    226  1.3  mrg   {
    227  1.3  mrg     return m_recording_ctxt->get_inner_bool_option (opt);
    228  1.3  mrg   }
    229  1.3  mrg 
    230  1.1  mrg   builtins_manager *get_builtins_manager () const
    231  1.1  mrg   {
    232  1.1  mrg     return m_recording_ctxt->get_builtins_manager ();
    233  1.1  mrg   }
    234  1.1  mrg 
    235  1.1  mrg   void
    236  1.1  mrg   compile ();
    237  1.1  mrg 
    238  1.1  mrg   void
    239  1.1  mrg   add_error (location *loc, const char *fmt, ...)
    240  1.1  mrg       GNU_PRINTF(3, 4);
    241  1.1  mrg 
    242  1.1  mrg   void
    243  1.1  mrg   add_error_va (location *loc, const char *fmt, va_list ap)
    244  1.1  mrg       GNU_PRINTF(3, 0);
    245  1.1  mrg 
    246  1.1  mrg   const char *
    247  1.1  mrg   get_first_error () const;
    248  1.1  mrg 
    249  1.1  mrg   void
    250  1.3  mrg   add_diagnostic (struct diagnostic_context *context,
    251  1.3  mrg 		  struct diagnostic_info *diagnostic);
    252  1.3  mrg 
    253  1.3  mrg   void
    254  1.1  mrg   set_tree_location (tree t, location *loc);
    255  1.1  mrg 
    256  1.1  mrg   tree
    257  1.1  mrg   new_field_access (location *loc,
    258  1.1  mrg 		    tree datum,
    259  1.1  mrg 		    field *field);
    260  1.1  mrg 
    261  1.1  mrg   tree
    262  1.1  mrg   new_dereference (tree ptr, location *loc);
    263  1.1  mrg 
    264  1.1  mrg   tree
    265  1.1  mrg   as_truth_value (tree expr, location *loc);
    266  1.1  mrg 
    267  1.1  mrg   bool errors_occurred () const
    268  1.1  mrg   {
    269  1.1  mrg     return m_recording_ctxt->errors_occurred ();
    270  1.1  mrg   }
    271  1.1  mrg 
    272  1.3  mrg   timer *get_timer () const { return m_recording_ctxt->get_timer (); }
    273  1.1  mrg 
    274  1.7  mrg   void add_top_level_asm (const char *asm_stmts);
    275  1.7  mrg 
    276  1.1  mrg private:
    277  1.1  mrg   void dump_generated_code ();
    278  1.1  mrg 
    279  1.1  mrg   rvalue *
    280  1.1  mrg   build_call (location *loc,
    281  1.1  mrg 	      tree fn_ptr,
    282  1.3  mrg 	      const auto_vec<rvalue *> *args,
    283  1.3  mrg 	      bool require_tail_call);
    284  1.1  mrg 
    285  1.1  mrg   tree
    286  1.1  mrg   build_cast (location *loc,
    287  1.1  mrg 	      rvalue *expr,
    288  1.1  mrg 	      type *type_);
    289  1.1  mrg 
    290  1.1  mrg   source_file *
    291  1.1  mrg   get_source_file (const char *filename);
    292  1.1  mrg 
    293  1.7  mrg   tree
    294  1.7  mrg   get_tree_node_for_type (enum gcc_jit_types type_);
    295  1.7  mrg 
    296  1.1  mrg   void handle_locations ();
    297  1.1  mrg 
    298  1.7  mrg   void init_types ();
    299  1.7  mrg 
    300  1.1  mrg   const char * get_path_c_file () const;
    301  1.1  mrg   const char * get_path_s_file () const;
    302  1.1  mrg   const char * get_path_so_file () const;
    303  1.1  mrg 
    304  1.7  mrg   tree
    305  1.7  mrg   global_new_decl (location *loc,
    306  1.7  mrg                    enum gcc_jit_global_kind kind,
    307  1.7  mrg                    type *type,
    308  1.7  mrg 		   const char *name,
    309  1.7  mrg 		   enum global_var_flags flags);
    310  1.7  mrg   lvalue *
    311  1.7  mrg   global_finalize_lvalue (tree inner);
    312  1.7  mrg 
    313  1.1  mrg private:
    314  1.1  mrg 
    315  1.1  mrg   /* Functions for implementing "compile".  */
    316  1.1  mrg 
    317  1.1  mrg   void acquire_mutex ();
    318  1.1  mrg   void release_mutex ();
    319  1.1  mrg 
    320  1.1  mrg   void
    321  1.1  mrg   make_fake_args (vec <char *> *argvec,
    322  1.1  mrg 		  const char *ctxt_progname,
    323  1.1  mrg 		  vec <recording::requested_dump> *requested_dumps);
    324  1.1  mrg 
    325  1.1  mrg   void
    326  1.1  mrg   extract_any_requested_dumps
    327  1.1  mrg     (vec <recording::requested_dump> *requested_dumps);
    328  1.1  mrg 
    329  1.1  mrg   char *
    330  1.1  mrg   read_dump_file (const char *path);
    331  1.1  mrg 
    332  1.1  mrg   virtual void postprocess (const char *ctxt_progname) = 0;
    333  1.1  mrg 
    334  1.1  mrg protected:
    335  1.1  mrg   tempdir *get_tempdir () { return m_tempdir; }
    336  1.1  mrg 
    337  1.1  mrg   void
    338  1.1  mrg   convert_to_dso (const char *ctxt_progname);
    339  1.1  mrg 
    340  1.1  mrg   void
    341  1.1  mrg   invoke_driver (const char *ctxt_progname,
    342  1.1  mrg 		 const char *input_file,
    343  1.1  mrg 		 const char *output_file,
    344  1.1  mrg 		 timevar_id_t tv_id,
    345  1.1  mrg 		 bool shared,
    346  1.1  mrg 		 bool run_linker);
    347  1.1  mrg 
    348  1.1  mrg   void
    349  1.1  mrg   add_multilib_driver_arguments (vec <char *> *argvec);
    350  1.1  mrg 
    351  1.1  mrg   result *
    352  1.1  mrg   dlopen_built_dso ();
    353  1.1  mrg 
    354  1.3  mrg  private:
    355  1.3  mrg   void
    356  1.3  mrg   invoke_embedded_driver (const vec <char *> *argvec);
    357  1.3  mrg 
    358  1.3  mrg   void
    359  1.3  mrg   invoke_external_driver (const char *ctxt_progname,
    360  1.3  mrg 			  vec <char *> *argvec);
    361  1.3  mrg 
    362  1.1  mrg private:
    363  1.1  mrg   ::gcc::jit::recording::context *m_recording_ctxt;
    364  1.1  mrg 
    365  1.1  mrg   tempdir *m_tempdir;
    366  1.1  mrg 
    367  1.1  mrg   auto_vec<function *> m_functions;
    368  1.1  mrg   auto_vec<tree> m_globals;
    369  1.1  mrg   tree m_const_char_ptr;
    370  1.1  mrg 
    371  1.1  mrg   /* Source location handling.  */
    372  1.1  mrg   auto_vec<source_file *> m_source_files;
    373  1.1  mrg 
    374  1.1  mrg   auto_vec<std::pair<tree, location *> > m_cached_locations;
    375  1.1  mrg };
    376  1.1  mrg 
    377  1.1  mrg class compile_to_memory : public context
    378  1.1  mrg {
    379  1.1  mrg  public:
    380  1.1  mrg   compile_to_memory (recording::context *ctxt);
    381  1.3  mrg   void postprocess (const char *ctxt_progname) FINAL OVERRIDE;
    382  1.1  mrg 
    383  1.1  mrg   result *get_result_obj () const { return m_result; }
    384  1.1  mrg 
    385  1.1  mrg  private:
    386  1.1  mrg   result *m_result;
    387  1.1  mrg };
    388  1.1  mrg 
    389  1.1  mrg class compile_to_file : public context
    390  1.1  mrg {
    391  1.1  mrg  public:
    392  1.1  mrg   compile_to_file (recording::context *ctxt,
    393  1.1  mrg 		   enum gcc_jit_output_kind output_kind,
    394  1.1  mrg 		   const char *output_path);
    395  1.3  mrg   void postprocess (const char *ctxt_progname) FINAL OVERRIDE;
    396  1.1  mrg 
    397  1.1  mrg  private:
    398  1.1  mrg   void
    399  1.1  mrg   copy_file (const char *src_path,
    400  1.1  mrg 	     const char *dst_path);
    401  1.1  mrg 
    402  1.1  mrg  private:
    403  1.1  mrg   enum gcc_jit_output_kind m_output_kind;
    404  1.1  mrg   const char *m_output_path;
    405  1.1  mrg };
    406  1.1  mrg 
    407  1.1  mrg 
    408  1.1  mrg /* A temporary wrapper object.
    409  1.1  mrg    These objects are (mostly) only valid during replay.
    410  1.1  mrg    We allocate them on the GC heap, so that they will be cleaned
    411  1.1  mrg    the next time the GC collects.
    412  1.1  mrg    The exception is the "function" class, which is tracked and marked by
    413  1.1  mrg    the jit::context, since it needs to stay alive during post-processing
    414  1.1  mrg    (when the GC could run). */
    415  1.1  mrg class wrapper
    416  1.1  mrg {
    417  1.1  mrg public:
    418  1.1  mrg   /* Allocate in the GC heap.  */
    419  1.1  mrg   void *operator new (size_t sz);
    420  1.1  mrg 
    421  1.1  mrg   /* Some wrapper subclasses contain vec<> and so need to
    422  1.1  mrg      release them when they are GC-ed.  */
    423  1.1  mrg   virtual void finalizer () { }
    424  1.1  mrg 
    425  1.1  mrg };
    426  1.1  mrg 
    427  1.1  mrg class type : public wrapper
    428  1.1  mrg {
    429  1.1  mrg public:
    430  1.1  mrg   type (tree inner)
    431  1.1  mrg     : m_inner(inner)
    432  1.1  mrg   {}
    433  1.1  mrg 
    434  1.1  mrg   tree as_tree () const { return m_inner; }
    435  1.1  mrg 
    436  1.1  mrg   type *get_pointer () const { return new type (build_pointer_type (m_inner)); }
    437  1.1  mrg 
    438  1.1  mrg   type *get_const () const
    439  1.1  mrg   {
    440  1.1  mrg     return new type (build_qualified_type (m_inner, TYPE_QUAL_CONST));
    441  1.1  mrg   }
    442  1.1  mrg 
    443  1.1  mrg   type *get_volatile () const
    444  1.1  mrg   {
    445  1.1  mrg     return new type (build_qualified_type (m_inner, TYPE_QUAL_VOLATILE));
    446  1.1  mrg   }
    447  1.1  mrg 
    448  1.4  mrg   type *get_aligned (size_t alignment_in_bytes) const;
    449  1.4  mrg   type *get_vector (size_t num_units) const;
    450  1.4  mrg 
    451  1.1  mrg private:
    452  1.1  mrg   tree m_inner;
    453  1.1  mrg };
    454  1.1  mrg 
    455  1.1  mrg class compound_type : public type
    456  1.1  mrg {
    457  1.1  mrg public:
    458  1.1  mrg   compound_type (tree inner)
    459  1.1  mrg     : type (inner)
    460  1.1  mrg   {}
    461  1.1  mrg 
    462  1.1  mrg   void set_fields (const auto_vec<field *> *fields);
    463  1.1  mrg };
    464  1.1  mrg 
    465  1.1  mrg class field : public wrapper
    466  1.1  mrg {
    467  1.1  mrg public:
    468  1.1  mrg   field (tree inner)
    469  1.1  mrg     : m_inner(inner)
    470  1.1  mrg   {}
    471  1.1  mrg 
    472  1.1  mrg   tree as_tree () const { return m_inner; }
    473  1.1  mrg 
    474  1.1  mrg private:
    475  1.1  mrg   tree m_inner;
    476  1.1  mrg };
    477  1.1  mrg 
    478  1.6  mrg class bitfield : public field {};
    479  1.6  mrg 
    480  1.1  mrg class function : public wrapper
    481  1.1  mrg {
    482  1.1  mrg public:
    483  1.1  mrg   function(context *ctxt, tree fndecl, enum gcc_jit_function_kind kind);
    484  1.1  mrg 
    485  1.1  mrg   void gt_ggc_mx ();
    486  1.3  mrg   void finalizer () FINAL OVERRIDE;
    487  1.1  mrg 
    488  1.1  mrg   tree get_return_type_as_tree () const;
    489  1.1  mrg 
    490  1.1  mrg   tree as_fndecl () const { return m_inner_fndecl; }
    491  1.1  mrg 
    492  1.1  mrg   enum gcc_jit_function_kind get_kind () const { return m_kind; }
    493  1.1  mrg 
    494  1.1  mrg   lvalue *
    495  1.1  mrg   new_local (location *loc,
    496  1.1  mrg 	     type *type,
    497  1.1  mrg 	     const char *name);
    498  1.1  mrg 
    499  1.1  mrg   block*
    500  1.1  mrg   new_block (const char *name);
    501  1.1  mrg 
    502  1.4  mrg   rvalue *
    503  1.4  mrg   get_address (location *loc);
    504  1.4  mrg 
    505  1.1  mrg   void
    506  1.1  mrg   build_stmt_list ();
    507  1.1  mrg 
    508  1.1  mrg   void
    509  1.1  mrg   postprocess ();
    510  1.1  mrg 
    511  1.1  mrg public:
    512  1.1  mrg   context *m_ctxt;
    513  1.1  mrg 
    514  1.1  mrg public:
    515  1.1  mrg   void
    516  1.1  mrg   set_tree_location (tree t, location *loc)
    517  1.1  mrg   {
    518  1.1  mrg     m_ctxt->set_tree_location (t, loc);
    519  1.1  mrg   }
    520  1.1  mrg 
    521  1.1  mrg private:
    522  1.1  mrg   tree m_inner_fndecl;
    523  1.1  mrg   tree m_inner_block;
    524  1.1  mrg   tree m_inner_bind_expr;
    525  1.1  mrg   enum gcc_jit_function_kind m_kind;
    526  1.1  mrg   tree m_stmt_list;
    527  1.1  mrg   tree_stmt_iterator m_stmt_iter;
    528  1.1  mrg   vec<block *> m_blocks;
    529  1.1  mrg };
    530  1.1  mrg 
    531  1.1  mrg struct case_
    532  1.1  mrg {
    533  1.1  mrg   case_ (rvalue *min_value, rvalue *max_value, block *dest_block)
    534  1.1  mrg   : m_min_value (min_value),
    535  1.1  mrg     m_max_value (max_value),
    536  1.1  mrg     m_dest_block (dest_block)
    537  1.1  mrg   {}
    538  1.1  mrg 
    539  1.1  mrg   rvalue *m_min_value;
    540  1.1  mrg   rvalue *m_max_value;
    541  1.1  mrg   block *m_dest_block;
    542  1.1  mrg };
    543  1.1  mrg 
    544  1.7  mrg struct asm_operand
    545  1.7  mrg {
    546  1.7  mrg   asm_operand (const char *asm_symbolic_name,
    547  1.7  mrg 	       const char *constraint,
    548  1.7  mrg 	       tree expr)
    549  1.7  mrg   : m_asm_symbolic_name (asm_symbolic_name),
    550  1.7  mrg     m_constraint (constraint),
    551  1.7  mrg     m_expr (expr)
    552  1.7  mrg   {}
    553  1.7  mrg 
    554  1.7  mrg   const char *m_asm_symbolic_name;
    555  1.7  mrg   const char *m_constraint;
    556  1.7  mrg   tree m_expr;
    557  1.7  mrg };
    558  1.7  mrg 
    559  1.1  mrg class block : public wrapper
    560  1.1  mrg {
    561  1.1  mrg public:
    562  1.1  mrg   block (function *func,
    563  1.1  mrg 	 const char *name);
    564  1.1  mrg 
    565  1.3  mrg   void finalizer () FINAL OVERRIDE;
    566  1.1  mrg 
    567  1.1  mrg   tree as_label_decl () const { return m_label_decl; }
    568  1.1  mrg 
    569  1.1  mrg   function *get_function () const { return m_func; }
    570  1.1  mrg 
    571  1.1  mrg   void
    572  1.1  mrg   add_eval (location *loc,
    573  1.1  mrg 	    rvalue *rvalue);
    574  1.1  mrg 
    575  1.1  mrg   void
    576  1.1  mrg   add_assignment (location *loc,
    577  1.1  mrg 		  lvalue *lvalue,
    578  1.1  mrg 		  rvalue *rvalue);
    579  1.1  mrg 
    580  1.1  mrg   void
    581  1.1  mrg   add_comment (location *loc,
    582  1.1  mrg 	       const char *text);
    583  1.1  mrg 
    584  1.1  mrg   void
    585  1.1  mrg   add_conditional (location *loc,
    586  1.1  mrg 		   rvalue *boolval,
    587  1.1  mrg 		   block *on_true,
    588  1.1  mrg 		   block *on_false);
    589  1.1  mrg 
    590  1.1  mrg   block *
    591  1.1  mrg   add_block (location *loc,
    592  1.1  mrg 	     const char *name);
    593  1.1  mrg 
    594  1.1  mrg   void
    595  1.1  mrg   add_jump (location *loc,
    596  1.1  mrg 	    block *target);
    597  1.1  mrg 
    598  1.1  mrg   void
    599  1.1  mrg   add_return (location *loc,
    600  1.1  mrg 	      rvalue *rvalue);
    601  1.1  mrg 
    602  1.1  mrg   void
    603  1.1  mrg   add_switch (location *loc,
    604  1.1  mrg 	      rvalue *expr,
    605  1.1  mrg 	      block *default_block,
    606  1.1  mrg 	      const auto_vec <case_> *cases);
    607  1.1  mrg 
    608  1.7  mrg   void
    609  1.7  mrg   add_extended_asm (location *loc,
    610  1.7  mrg 		    const char *asm_template,
    611  1.7  mrg 		    bool is_volatile,
    612  1.7  mrg 		    bool is_inline,
    613  1.7  mrg 		    const auto_vec <asm_operand> *outputs,
    614  1.7  mrg 		    const auto_vec <asm_operand> *inputs,
    615  1.7  mrg 		    const auto_vec <const char *> *clobbers,
    616  1.7  mrg 		    const auto_vec <block *> *goto_blocks);
    617  1.7  mrg 
    618  1.1  mrg private:
    619  1.1  mrg   void
    620  1.1  mrg   set_tree_location (tree t, location *loc)
    621  1.1  mrg   {
    622  1.1  mrg     m_func->set_tree_location (t, loc);
    623  1.1  mrg   }
    624  1.1  mrg 
    625  1.1  mrg   void add_stmt (tree stmt)
    626  1.1  mrg   {
    627  1.1  mrg     /* TODO: use one stmt_list per block.  */
    628  1.1  mrg     m_stmts.safe_push (stmt);
    629  1.1  mrg   }
    630  1.1  mrg 
    631  1.1  mrg private:
    632  1.1  mrg   function *m_func;
    633  1.1  mrg   tree m_label_decl;
    634  1.1  mrg   vec<tree> m_stmts;
    635  1.1  mrg 
    636  1.1  mrg public: // for now
    637  1.1  mrg   tree m_label_expr;
    638  1.1  mrg 
    639  1.1  mrg   friend class function;
    640  1.1  mrg };
    641  1.1  mrg 
    642  1.1  mrg class rvalue : public wrapper
    643  1.1  mrg {
    644  1.1  mrg public:
    645  1.1  mrg   rvalue (context *ctxt, tree inner)
    646  1.1  mrg     : m_ctxt (ctxt),
    647  1.1  mrg       m_inner (inner)
    648  1.7  mrg   {
    649  1.7  mrg     /* Pre-mark tree nodes with TREE_VISITED so that they can be
    650  1.7  mrg        deeply unshared during gimplification (including across
    651  1.7  mrg        functions); this requires LANG_HOOKS_DEEP_UNSHARING to be true.  */
    652  1.7  mrg     TREE_VISITED (inner) = 1;
    653  1.7  mrg   }
    654  1.1  mrg 
    655  1.1  mrg   rvalue *
    656  1.1  mrg   as_rvalue () { return this; }
    657  1.1  mrg 
    658  1.1  mrg   tree as_tree () const { return m_inner; }
    659  1.1  mrg 
    660  1.1  mrg   context *get_context () const { return m_ctxt; }
    661  1.1  mrg 
    662  1.1  mrg   type *
    663  1.1  mrg   get_type () { return new type (TREE_TYPE (m_inner)); }
    664  1.1  mrg 
    665  1.1  mrg   rvalue *
    666  1.1  mrg   access_field (location *loc,
    667  1.1  mrg 		field *field);
    668  1.1  mrg 
    669  1.1  mrg   lvalue *
    670  1.1  mrg   dereference_field (location *loc,
    671  1.1  mrg 		     field *field);
    672  1.1  mrg 
    673  1.1  mrg   lvalue *
    674  1.1  mrg   dereference (location *loc);
    675  1.1  mrg 
    676  1.1  mrg private:
    677  1.1  mrg   context *m_ctxt;
    678  1.1  mrg   tree m_inner;
    679  1.1  mrg };
    680  1.1  mrg 
    681  1.1  mrg class lvalue : public rvalue
    682  1.1  mrg {
    683  1.1  mrg public:
    684  1.1  mrg   lvalue (context *ctxt, tree inner)
    685  1.1  mrg     : rvalue(ctxt, inner)
    686  1.1  mrg   {}
    687  1.1  mrg 
    688  1.1  mrg   lvalue *
    689  1.1  mrg   as_lvalue () { return this; }
    690  1.1  mrg 
    691  1.1  mrg   lvalue *
    692  1.1  mrg   access_field (location *loc,
    693  1.1  mrg 		field *field);
    694  1.1  mrg 
    695  1.1  mrg   rvalue *
    696  1.1  mrg   get_address (location *loc);
    697  1.1  mrg 
    698  1.7  mrg   void
    699  1.7  mrg   set_tls_model (enum tls_model tls_model)
    700  1.7  mrg   {
    701  1.7  mrg     set_decl_tls_model (as_tree (), tls_model);
    702  1.7  mrg   }
    703  1.7  mrg 
    704  1.7  mrg   void
    705  1.7  mrg   set_link_section (const char* name)
    706  1.7  mrg   {
    707  1.7  mrg     set_decl_section_name (as_tree (), name);
    708  1.7  mrg   }
    709  1.7  mrg 
    710  1.7  mrg   void
    711  1.7  mrg   set_register_name (const char* reg_name)
    712  1.7  mrg   {
    713  1.7  mrg     set_user_assembler_name (as_tree (), reg_name);
    714  1.7  mrg     DECL_REGISTER (as_tree ()) = 1;
    715  1.7  mrg     DECL_HARD_REGISTER (as_tree ()) = 1;
    716  1.7  mrg   }
    717  1.7  mrg 
    718  1.7  mrg   void
    719  1.7  mrg   set_alignment (int alignment)
    720  1.7  mrg   {
    721  1.7  mrg       SET_DECL_ALIGN (as_tree (), alignment * BITS_PER_UNIT);
    722  1.7  mrg       DECL_USER_ALIGN (as_tree ()) = 1;
    723  1.7  mrg   }
    724  1.7  mrg 
    725  1.6  mrg private:
    726  1.6  mrg   bool mark_addressable (location *loc);
    727  1.1  mrg };
    728  1.1  mrg 
    729  1.1  mrg class param : public lvalue
    730  1.1  mrg {
    731  1.1  mrg public:
    732  1.1  mrg   param (context *ctxt, tree inner)
    733  1.1  mrg     : lvalue(ctxt, inner)
    734  1.1  mrg   {}
    735  1.1  mrg };
    736  1.1  mrg 
    737  1.1  mrg /* Dealing with the linemap API.
    738  1.1  mrg 
    739  1.1  mrg    It appears that libcpp requires locations to be created as if by
    740  1.1  mrg    a tokenizer, creating them by filename, in ascending order of
    741  1.1  mrg    line/column, whereas our API doesn't impose any such constraints:
    742  1.1  mrg    we allow client code to create locations in arbitrary orders.
    743  1.1  mrg 
    744  1.1  mrg    To square this circle, we need to cache all location creation,
    745  1.1  mrg    grouping things up by filename/line, and then creating the linemap
    746  1.1  mrg    entries in a post-processing phase.  */
    747  1.1  mrg 
    748  1.1  mrg /* A set of locations, all sharing a filename */
    749  1.1  mrg class source_file : public wrapper
    750  1.1  mrg {
    751  1.1  mrg public:
    752  1.1  mrg   source_file (tree filename);
    753  1.3  mrg   void finalizer () FINAL OVERRIDE;
    754  1.1  mrg 
    755  1.1  mrg   source_line *
    756  1.1  mrg   get_source_line (int line_num);
    757  1.1  mrg 
    758  1.1  mrg   tree filename_as_tree () const { return m_filename; }
    759  1.1  mrg 
    760  1.1  mrg   const char*
    761  1.1  mrg   get_filename () const { return IDENTIFIER_POINTER (m_filename); }
    762  1.1  mrg 
    763  1.1  mrg   vec<source_line *> m_source_lines;
    764  1.1  mrg 
    765  1.1  mrg private:
    766  1.1  mrg   tree m_filename;
    767  1.1  mrg };
    768  1.1  mrg 
    769  1.1  mrg /* A source line, with one or more locations of interest.  */
    770  1.1  mrg class source_line : public wrapper
    771  1.1  mrg {
    772  1.1  mrg public:
    773  1.1  mrg   source_line (source_file *file, int line_num);
    774  1.3  mrg   void finalizer () FINAL OVERRIDE;
    775  1.1  mrg 
    776  1.1  mrg   location *
    777  1.1  mrg   get_location (recording::location *rloc, int column_num);
    778  1.1  mrg 
    779  1.1  mrg   int get_line_num () const { return m_line_num; }
    780  1.1  mrg 
    781  1.1  mrg   vec<location *> m_locations;
    782  1.1  mrg 
    783  1.1  mrg private:
    784  1.1  mrg   source_file *m_source_file;
    785  1.1  mrg   int m_line_num;
    786  1.1  mrg };
    787  1.1  mrg 
    788  1.1  mrg /* A specific location on a source line.  This is what we expose
    789  1.1  mrg    to the client API.  */
    790  1.1  mrg class location : public wrapper
    791  1.1  mrg {
    792  1.1  mrg public:
    793  1.1  mrg   location (recording::location *loc, source_line *line, int column_num);
    794  1.1  mrg 
    795  1.1  mrg   int get_column_num () const { return m_column_num; }
    796  1.1  mrg 
    797  1.1  mrg   recording::location *get_recording_loc () const { return m_recording_loc; }
    798  1.1  mrg 
    799  1.5  mrg   location_t m_srcloc;
    800  1.1  mrg 
    801  1.1  mrg private:
    802  1.1  mrg   recording::location *m_recording_loc;
    803  1.1  mrg   source_line *m_line;
    804  1.1  mrg   int m_column_num;
    805  1.1  mrg };
    806  1.1  mrg 
    807  1.1  mrg } // namespace gcc::jit::playback
    808  1.1  mrg 
    809  1.1  mrg extern playback::context *active_playback_ctxt;
    810  1.1  mrg 
    811  1.1  mrg } // namespace gcc::jit
    812  1.1  mrg 
    813  1.1  mrg } // namespace gcc
    814  1.1  mrg 
    815  1.1  mrg #endif /* JIT_PLAYBACK_H */
    816