Home | History | Annotate | Line # | Download | only in gcc
optabs.h revision 1.1.1.2
      1      1.1  mrg /* Definitions for code generation pass of GNU compiler.
      2  1.1.1.2  mrg    Copyright (C) 2001-2013 Free Software Foundation, Inc.
      3      1.1  mrg 
      4      1.1  mrg This file is part of GCC.
      5      1.1  mrg 
      6      1.1  mrg GCC is free software; you can redistribute it and/or modify
      7      1.1  mrg it under the terms of the GNU General Public License as published by
      8      1.1  mrg the Free Software Foundation; either version 3, or (at your option)
      9      1.1  mrg any later version.
     10      1.1  mrg 
     11      1.1  mrg GCC is distributed in the hope that it will be useful,
     12      1.1  mrg but WITHOUT ANY WARRANTY; without even the implied warranty of
     13      1.1  mrg MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     14      1.1  mrg GNU General Public License for more details.
     15      1.1  mrg 
     16      1.1  mrg You should have received a copy of the GNU General Public License
     17      1.1  mrg along with GCC; see the file COPYING3.  If not see
     18      1.1  mrg <http://www.gnu.org/licenses/>.  */
     19      1.1  mrg 
     20      1.1  mrg #ifndef GCC_OPTABS_H
     21      1.1  mrg #define GCC_OPTABS_H
     22      1.1  mrg 
     23      1.1  mrg #include "insn-codes.h"
     24  1.1.1.2  mrg #include "insn-opinit.h"
     25      1.1  mrg 
     26  1.1.1.2  mrg typedef enum optab_tag optab;
     27  1.1.1.2  mrg typedef enum optab_tag convert_optab;
     28  1.1.1.2  mrg typedef enum optab_tag direct_optab;
     29      1.1  mrg 
     30  1.1.1.2  mrg struct optab_libcall_d
     31      1.1  mrg {
     32      1.1  mrg   char libcall_suffix;
     33  1.1.1.2  mrg   const char *libcall_basename;
     34  1.1.1.2  mrg   void (*libcall_gen) (optab, const char *name,
     35  1.1.1.2  mrg 		       char suffix, enum machine_mode);
     36      1.1  mrg };
     37      1.1  mrg 
     38  1.1.1.2  mrg struct convert_optab_libcall_d
     39      1.1  mrg {
     40      1.1  mrg   const char *libcall_basename;
     41  1.1.1.2  mrg   void (*libcall_gen) (convert_optab, const char *name,
     42  1.1.1.2  mrg 		       enum machine_mode, enum machine_mode);
     43      1.1  mrg };
     44      1.1  mrg 
     45      1.1  mrg /* Given an enum insn_code, access the function to construct
     46      1.1  mrg    the body of that kind of insn.  */
     47      1.1  mrg #define GEN_FCN(CODE) (insn_data[CODE].genfun)
     48      1.1  mrg 
     49  1.1.1.2  mrg /* Contains the optab used for each rtx code, and vice-versa.  */
     50  1.1.1.2  mrg extern const optab code_to_optab_[NUM_RTX_CODE];
     51  1.1.1.2  mrg extern const enum rtx_code optab_to_code_[NUM_OPTABS];
     52      1.1  mrg 
     53  1.1.1.2  mrg static inline optab
     54  1.1.1.2  mrg code_to_optab (enum rtx_code code)
     55  1.1.1.2  mrg {
     56  1.1.1.2  mrg   return code_to_optab_[code];
     57  1.1.1.2  mrg }
     58      1.1  mrg 
     59  1.1.1.2  mrg static inline enum rtx_code
     60  1.1.1.2  mrg optab_to_code (optab op)
     61  1.1.1.2  mrg {
     62  1.1.1.2  mrg   return optab_to_code_[op];
     63  1.1.1.2  mrg }
     64      1.1  mrg 
     65  1.1.1.2  mrg extern const struct convert_optab_libcall_d convlib_def[NUM_CONVLIB_OPTABS];
     66  1.1.1.2  mrg extern const struct optab_libcall_d normlib_def[NUM_NORMLIB_OPTABS];
     67      1.1  mrg 
     68  1.1.1.2  mrg /* Returns the active icode for the given (encoded) optab.  */
     69  1.1.1.2  mrg extern enum insn_code raw_optab_handler (unsigned);
     70  1.1.1.2  mrg extern bool swap_optab_enable (optab, enum machine_mode, bool);
     71  1.1.1.2  mrg 
     72  1.1.1.2  mrg /* Target-dependent globals.  */
     73  1.1.1.2  mrg struct target_optabs {
     74  1.1.1.2  mrg   /* Patterns that are used by optabs that are enabled for this target.  */
     75  1.1.1.2  mrg   bool pat_enable[NUM_OPTAB_PATTERNS];
     76      1.1  mrg };
     77      1.1  mrg 
     78  1.1.1.2  mrg extern struct target_optabs default_target_optabs;
     79  1.1.1.2  mrg extern struct target_optabs *this_fn_optabs;
     80  1.1.1.2  mrg #if SWITCHABLE_TARGET
     81  1.1.1.2  mrg extern struct target_optabs *this_target_optabs;
     82  1.1.1.2  mrg #else
     83  1.1.1.2  mrg #define this_target_optabs (&default_target_optabs)
     84      1.1  mrg #endif
     85  1.1.1.2  mrg 
     86      1.1  mrg /* Define functions given in optabs.c.  */
     88      1.1  mrg 
     89      1.1  mrg extern rtx expand_widen_pattern_expr (sepops ops, rtx op0, rtx op1, rtx wide_op,
     90      1.1  mrg                                       rtx target, int unsignedp);
     91      1.1  mrg 
     92      1.1  mrg extern rtx expand_ternary_op (enum machine_mode mode, optab ternary_optab,
     93      1.1  mrg 			      rtx op0, rtx op1, rtx op2, rtx target,
     94      1.1  mrg 			      int unsignedp);
     95      1.1  mrg 
     96      1.1  mrg /* Expand a binary operation given optab and rtx operands.  */
     97      1.1  mrg extern rtx expand_binop (enum machine_mode, optab, rtx, rtx, rtx, int,
     98      1.1  mrg 			 enum optab_methods);
     99  1.1.1.2  mrg 
    100  1.1.1.2  mrg extern rtx simplify_expand_binop (enum machine_mode mode, optab binoptab,
    101  1.1.1.2  mrg 				  rtx op0, rtx op1, rtx target, int unsignedp,
    102  1.1.1.2  mrg 				  enum optab_methods methods);
    103      1.1  mrg 
    104      1.1  mrg extern bool force_expand_binop (enum machine_mode, optab, rtx, rtx, rtx, int,
    105      1.1  mrg 				enum optab_methods);
    106      1.1  mrg 
    107      1.1  mrg /* Expand a binary operation with both signed and unsigned forms.  */
    108      1.1  mrg extern rtx sign_expand_binop (enum machine_mode, optab, optab, rtx, rtx,
    109      1.1  mrg 			      rtx, int, enum optab_methods);
    110      1.1  mrg 
    111      1.1  mrg /* Generate code to perform an operation on one operand with two results.  */
    112      1.1  mrg extern int expand_twoval_unop (optab, rtx, rtx, rtx, int);
    113      1.1  mrg 
    114      1.1  mrg /* Generate code to perform an operation on two operands with two results.  */
    115      1.1  mrg extern int expand_twoval_binop (optab, rtx, rtx, rtx, rtx, int);
    116      1.1  mrg 
    117      1.1  mrg /* Generate code to perform an operation on two operands with two
    118      1.1  mrg    results, using a library function.  */
    119      1.1  mrg extern bool expand_twoval_binop_libfunc (optab, rtx, rtx, rtx, rtx,
    120      1.1  mrg 					 enum rtx_code);
    121      1.1  mrg 
    122      1.1  mrg /* Expand a unary arithmetic operation given optab rtx operand.  */
    123      1.1  mrg extern rtx expand_unop (enum machine_mode, optab, rtx, rtx, int);
    124      1.1  mrg 
    125      1.1  mrg /* Expand the absolute value operation.  */
    126      1.1  mrg extern rtx expand_abs_nojump (enum machine_mode, rtx, rtx, int);
    127      1.1  mrg extern rtx expand_abs (enum machine_mode, rtx, rtx, int, int);
    128      1.1  mrg 
    129      1.1  mrg /* Expand the one's complement absolute value operation.  */
    130      1.1  mrg extern rtx expand_one_cmpl_abs_nojump (enum machine_mode, rtx, rtx);
    131      1.1  mrg 
    132      1.1  mrg /* Expand the copysign operation.  */
    133      1.1  mrg extern rtx expand_copysign (rtx, rtx, rtx);
    134      1.1  mrg 
    135      1.1  mrg /* Generate an instruction with a given INSN_CODE with an output and
    136  1.1.1.2  mrg    an input.  */
    137  1.1.1.2  mrg extern void emit_unop_insn (enum insn_code, rtx, rtx, enum rtx_code);
    138  1.1.1.2  mrg extern bool maybe_emit_unop_insn (enum insn_code, rtx, rtx, enum rtx_code);
    139  1.1.1.2  mrg 
    140  1.1.1.2  mrg /* Find a widening optab even if it doesn't widen as much as we want.  */
    141  1.1.1.2  mrg #define find_widening_optab_handler(A,B,C,D) \
    142  1.1.1.2  mrg   find_widening_optab_handler_and_mode (A, B, C, D, NULL)
    143  1.1.1.2  mrg extern enum insn_code find_widening_optab_handler_and_mode (optab,
    144  1.1.1.2  mrg 							    enum machine_mode,
    145  1.1.1.2  mrg 							    enum machine_mode,
    146  1.1.1.2  mrg 							    int,
    147      1.1  mrg 							    enum machine_mode *);
    148      1.1  mrg 
    149      1.1  mrg /* An extra flag to control optab_for_tree_code's behavior.  This is needed to
    150      1.1  mrg    distinguish between machines with a vector shift that takes a scalar for the
    151      1.1  mrg    shift amount vs. machines that take a vector for the shift amount.  */
    152      1.1  mrg enum optab_subtype
    153      1.1  mrg {
    154      1.1  mrg   optab_default,
    155      1.1  mrg   optab_scalar,
    156      1.1  mrg   optab_vector
    157      1.1  mrg };
    158      1.1  mrg 
    159      1.1  mrg /* Return the optab used for computing the given operation on the type given by
    160      1.1  mrg    the second argument.  The third argument distinguishes between the types of
    161      1.1  mrg    vector shifts and rotates */
    162      1.1  mrg extern optab optab_for_tree_code (enum tree_code, const_tree, enum optab_subtype);
    163      1.1  mrg 
    164      1.1  mrg /* The various uses that a comparison can have; used by can_compare_p:
    165      1.1  mrg    jumps, conditional moves, store flag operations.  */
    166      1.1  mrg enum can_compare_purpose
    167      1.1  mrg {
    168      1.1  mrg   ccp_jump,
    169      1.1  mrg   ccp_cmov,
    170      1.1  mrg   ccp_store_flag
    171      1.1  mrg };
    172      1.1  mrg 
    173      1.1  mrg /* Nonzero if a compare of mode MODE can be done straightforwardly
    174      1.1  mrg    (without splitting it into pieces).  */
    175      1.1  mrg extern int can_compare_p (enum rtx_code, enum machine_mode,
    176      1.1  mrg 			  enum can_compare_purpose);
    177      1.1  mrg 
    178      1.1  mrg /* Return the INSN_CODE to use for an extend operation.  */
    179      1.1  mrg extern enum insn_code can_extend_p (enum machine_mode, enum machine_mode, int);
    180      1.1  mrg 
    181      1.1  mrg /* Generate the body of an insn to extend Y (with mode MFROM)
    182      1.1  mrg    into X (with mode MTO).  Do zero-extension if UNSIGNEDP is nonzero.  */
    183      1.1  mrg extern rtx gen_extend_insn (rtx, rtx, enum machine_mode,
    184      1.1  mrg 			    enum machine_mode, int);
    185      1.1  mrg 
    186      1.1  mrg /* Call this to reset the function entry for one optab.  */
    187      1.1  mrg extern void set_optab_libfunc (optab, enum machine_mode, const char *);
    188      1.1  mrg extern void set_conv_libfunc (convert_optab, enum machine_mode,
    189      1.1  mrg 			      enum machine_mode, const char *);
    190  1.1.1.2  mrg 
    191  1.1.1.2  mrg /* Call this to install all of the __sync libcalls up to size MAX.  */
    192  1.1.1.2  mrg extern void init_sync_libfuncs (int max);
    193      1.1  mrg 
    194      1.1  mrg /* Generate code for a FIXED_CONVERT_EXPR.  */
    195      1.1  mrg extern void expand_fixed_convert (rtx, rtx, int, int);
    196      1.1  mrg 
    197      1.1  mrg /* Generate code for a FLOAT_EXPR.  */
    198      1.1  mrg extern void expand_float (rtx, rtx, int);
    199  1.1.1.2  mrg 
    200  1.1.1.2  mrg /* Return the insn_code for a FLOAT_EXPR.  */
    201  1.1.1.2  mrg enum insn_code can_float_p (enum machine_mode, enum machine_mode, int);
    202  1.1.1.2  mrg 
    203  1.1.1.2  mrg /* Return true if there is an inline compare and swap pattern.  */
    204  1.1.1.2  mrg extern bool can_compare_and_swap_p (enum machine_mode, bool);
    205  1.1.1.2  mrg 
    206  1.1.1.2  mrg /* Return true if there is an inline atomic exchange pattern.  */
    207  1.1.1.2  mrg extern bool can_atomic_exchange_p (enum machine_mode, bool);
    208  1.1.1.2  mrg 
    209  1.1.1.2  mrg /* Generate code for a compare and swap.  */
    210  1.1.1.2  mrg extern bool expand_atomic_compare_and_swap (rtx *, rtx *, rtx, rtx, rtx, bool,
    211  1.1.1.2  mrg 					    enum memmodel, enum memmodel);
    212  1.1.1.2  mrg 
    213  1.1.1.2  mrg /* Generate memory barriers.  */
    214  1.1.1.2  mrg extern void expand_mem_thread_fence (enum memmodel);
    215  1.1.1.2  mrg extern void expand_mem_signal_fence (enum memmodel);
    216  1.1.1.2  mrg 
    217  1.1.1.2  mrg /* Check whether an operation represented by the code CODE is a
    218  1.1.1.2  mrg    convert operation that is supported by the target platform in
    219  1.1.1.2  mrg    vector form */
    220  1.1.1.2  mrg bool supportable_convert_operation (enum tree_code, tree, tree, tree *,
    221  1.1.1.2  mrg                                     enum tree_code *);
    222      1.1  mrg 
    223      1.1  mrg /* Generate code for a FIX_EXPR.  */
    224      1.1  mrg extern void expand_fix (rtx, rtx, int);
    225      1.1  mrg 
    226      1.1  mrg /* Generate code for float to integral conversion.  */
    227      1.1  mrg extern bool expand_sfix_optab (rtx, rtx, convert_optab);
    228  1.1.1.2  mrg 
    229  1.1.1.2  mrg /* Generate code for a widening multiply.  */
    230  1.1.1.2  mrg extern rtx expand_widening_mult (enum machine_mode, rtx, rtx, rtx, int, optab);
    231      1.1  mrg 
    232  1.1.1.2  mrg /* Return tree if target supports vector operations for COND_EXPR.  */
    233      1.1  mrg bool expand_vec_cond_expr_p (tree, tree);
    234      1.1  mrg 
    235      1.1  mrg /* Generate code for VEC_COND_EXPR.  */
    236      1.1  mrg extern rtx expand_vec_cond_expr (tree, tree, tree, tree, rtx);
    237      1.1  mrg /* Generate code for VEC_LSHIFT_EXPR and VEC_RSHIFT_EXPR.  */
    238      1.1  mrg extern rtx expand_vec_shift_expr (sepops, rtx);
    239  1.1.1.2  mrg 
    240  1.1.1.2  mrg /* Return tree if target supports vector operations for VEC_PERM_EXPR.  */
    241  1.1.1.2  mrg extern bool can_vec_perm_p (enum machine_mode, bool, const unsigned char *);
    242  1.1.1.2  mrg 
    243  1.1.1.2  mrg /* Generate code for VEC_PERM_EXPR.  */
    244  1.1.1.2  mrg extern rtx expand_vec_perm (enum machine_mode, rtx, rtx, rtx, rtx);
    245  1.1.1.2  mrg 
    246  1.1.1.2  mrg /* Return non-zero if target supports a given highpart multiplication.  */
    247  1.1.1.2  mrg extern int can_mult_highpart_p (enum machine_mode, bool);
    248  1.1.1.2  mrg 
    249  1.1.1.2  mrg /* Generate code for MULT_HIGHPART_EXPR.  */
    250  1.1.1.2  mrg extern rtx expand_mult_highpart (enum machine_mode, rtx, rtx, rtx, bool);
    251  1.1.1.2  mrg 
    252  1.1.1.2  mrg /* Return the insn used to implement mode MODE of OP, or CODE_FOR_nothing
    253  1.1.1.2  mrg    if the target does not have such an insn.  */
    254  1.1.1.2  mrg 
    255  1.1.1.2  mrg static inline enum insn_code
    256  1.1.1.2  mrg optab_handler (optab op, enum machine_mode mode)
    257  1.1.1.2  mrg {
    258  1.1.1.2  mrg   unsigned scode = (op << 16) | mode;
    259  1.1.1.2  mrg   gcc_assert (op > LAST_CONV_OPTAB);
    260  1.1.1.2  mrg   return raw_optab_handler (scode);
    261  1.1.1.2  mrg }
    262  1.1.1.2  mrg 
    263  1.1.1.2  mrg /* Return the insn used to perform conversion OP from mode FROM_MODE
    264  1.1.1.2  mrg    to mode TO_MODE; return CODE_FOR_nothing if the target does not have
    265  1.1.1.2  mrg    such an insn.  */
    266  1.1.1.2  mrg 
    267  1.1.1.2  mrg static inline enum insn_code
    268  1.1.1.2  mrg convert_optab_handler (convert_optab op, enum machine_mode to_mode,
    269  1.1.1.2  mrg 		       enum machine_mode from_mode)
    270  1.1.1.2  mrg {
    271  1.1.1.2  mrg   unsigned scode = (op << 16) | (from_mode << 8) | to_mode;
    272  1.1.1.2  mrg   gcc_assert (op > unknown_optab && op <= LAST_CONV_OPTAB);
    273  1.1.1.2  mrg   return raw_optab_handler (scode);
    274  1.1.1.2  mrg }
    275  1.1.1.2  mrg 
    276  1.1.1.2  mrg /* Like optab_handler, but for widening_operations that have a
    277  1.1.1.2  mrg    TO_MODE and a FROM_MODE.  */
    278  1.1.1.2  mrg 
    279  1.1.1.2  mrg static inline enum insn_code
    280  1.1.1.2  mrg widening_optab_handler (optab op, enum machine_mode to_mode,
    281  1.1.1.2  mrg 			enum machine_mode from_mode)
    282  1.1.1.2  mrg {
    283  1.1.1.2  mrg   unsigned scode = (op << 16) | to_mode;
    284  1.1.1.2  mrg   if (to_mode != from_mode && from_mode != VOIDmode)
    285  1.1.1.2  mrg     {
    286  1.1.1.2  mrg       /* ??? Why does find_widening_optab_handler_and_mode attempt to
    287  1.1.1.2  mrg 	 widen things that can't be widened?  E.g. add_optab... */
    288  1.1.1.2  mrg       if (op > LAST_CONV_OPTAB)
    289  1.1.1.2  mrg 	return CODE_FOR_nothing;
    290  1.1.1.2  mrg       scode |= from_mode << 8;
    291  1.1.1.2  mrg     }
    292  1.1.1.2  mrg   return raw_optab_handler (scode);
    293  1.1.1.2  mrg }
    294  1.1.1.2  mrg 
    295  1.1.1.2  mrg /* Return the insn used to implement mode MODE of OP, or CODE_FOR_nothing
    296  1.1.1.2  mrg    if the target does not have such an insn.  */
    297  1.1.1.2  mrg 
    298  1.1.1.2  mrg static inline enum insn_code
    299  1.1.1.2  mrg direct_optab_handler (direct_optab op, enum machine_mode mode)
    300  1.1.1.2  mrg {
    301  1.1.1.2  mrg   return optab_handler (op, mode);
    302  1.1.1.2  mrg }
    303  1.1.1.2  mrg 
    304  1.1.1.2  mrg /* Return true if UNOPTAB is for a trapping-on-overflow operation.  */
    305  1.1.1.2  mrg 
    306  1.1.1.2  mrg static inline bool
    307  1.1.1.2  mrg trapv_unoptab_p (optab unoptab)
    308  1.1.1.2  mrg {
    309  1.1.1.2  mrg   return (unoptab == negv_optab
    310  1.1.1.2  mrg 	  || unoptab == absv_optab);
    311  1.1.1.2  mrg }
    312  1.1.1.2  mrg 
    313  1.1.1.2  mrg /* Return true if BINOPTAB is for a trapping-on-overflow operation.  */
    314  1.1.1.2  mrg 
    315  1.1.1.2  mrg static inline bool
    316  1.1.1.2  mrg trapv_binoptab_p (optab binoptab)
    317  1.1.1.2  mrg {
    318  1.1.1.2  mrg   return (binoptab == addv_optab
    319  1.1.1.2  mrg 	  || binoptab == subv_optab
    320  1.1.1.2  mrg 	  || binoptab == smulv_optab);
    321      1.1  mrg }
    322      1.1  mrg 
    323      1.1  mrg extern rtx optab_libfunc (optab optab, enum machine_mode mode);
    324      1.1  mrg extern rtx convert_optab_libfunc (convert_optab optab, enum machine_mode mode1,
    325  1.1.1.2  mrg 			          enum machine_mode mode2);
    326  1.1.1.2  mrg 
    327  1.1.1.2  mrg /* Describes an instruction that inserts or extracts a bitfield.  */
    328  1.1.1.2  mrg struct extraction_insn
    329  1.1.1.2  mrg {
    330  1.1.1.2  mrg   /* The code of the instruction.  */
    331  1.1.1.2  mrg   enum insn_code icode;
    332  1.1.1.2  mrg 
    333  1.1.1.2  mrg   /* The mode that the structure operand should have.  This is byte_mode
    334  1.1.1.2  mrg      when using the legacy insv, extv and extzv patterns to access memory.  */
    335  1.1.1.2  mrg   enum machine_mode struct_mode;
    336  1.1.1.2  mrg 
    337  1.1.1.2  mrg   /* The mode of the field to be inserted or extracted, and by extension
    338  1.1.1.2  mrg      the mode of the insertion or extraction itself.  */
    339  1.1.1.2  mrg   enum machine_mode field_mode;
    340  1.1.1.2  mrg 
    341  1.1.1.2  mrg   /* The mode of the field's bit position.  This is only important
    342  1.1.1.2  mrg      when the position is variable rather than constant.  */
    343  1.1.1.2  mrg   enum machine_mode pos_mode;
    344  1.1.1.2  mrg };
    345  1.1.1.2  mrg 
    346  1.1.1.2  mrg /* Enumerates the possible extraction_insn operations.  */
    347  1.1.1.2  mrg enum extraction_pattern { EP_insv, EP_extv, EP_extzv };
    348  1.1.1.2  mrg 
    349  1.1.1.2  mrg extern bool get_best_reg_extraction_insn (extraction_insn *,
    350  1.1.1.2  mrg 					  enum extraction_pattern,
    351  1.1.1.2  mrg 					  unsigned HOST_WIDE_INT,
    352  1.1.1.2  mrg 					  enum machine_mode);
    353  1.1.1.2  mrg 
    354  1.1.1.2  mrg extern bool get_best_mem_extraction_insn (extraction_insn *,
    355  1.1.1.2  mrg 					  enum extraction_pattern,
    356  1.1.1.2  mrg 					  HOST_WIDE_INT, HOST_WIDE_INT,
    357  1.1.1.2  mrg 					  enum machine_mode);
    358  1.1.1.2  mrg 
    359  1.1.1.2  mrg extern bool insn_operand_matches (enum insn_code icode, unsigned int opno,
    360  1.1.1.2  mrg 				  rtx operand);
    361  1.1.1.2  mrg 
    362  1.1.1.2  mrg /* Describes the type of an expand_operand.  Each value is associated
    363  1.1.1.2  mrg    with a create_*_operand function; see the comments above those
    364  1.1.1.2  mrg    functions for details.  */
    365  1.1.1.2  mrg enum expand_operand_type {
    366  1.1.1.2  mrg   EXPAND_FIXED,
    367  1.1.1.2  mrg   EXPAND_OUTPUT,
    368  1.1.1.2  mrg   EXPAND_INPUT,
    369  1.1.1.2  mrg   EXPAND_CONVERT_TO,
    370  1.1.1.2  mrg   EXPAND_CONVERT_FROM,
    371  1.1.1.2  mrg   EXPAND_ADDRESS,
    372  1.1.1.2  mrg   EXPAND_INTEGER
    373  1.1.1.2  mrg };
    374  1.1.1.2  mrg 
    375  1.1.1.2  mrg /* Information about an operand for instruction expansion.  */
    376  1.1.1.2  mrg struct expand_operand {
    377  1.1.1.2  mrg   /* The type of operand.  */
    378  1.1.1.2  mrg   ENUM_BITFIELD (expand_operand_type) type : 8;
    379  1.1.1.2  mrg 
    380  1.1.1.2  mrg   /* True if any conversion should treat VALUE as being unsigned
    381  1.1.1.2  mrg      rather than signed.  Only meaningful for certain types.  */
    382  1.1.1.2  mrg   unsigned int unsigned_p : 1;
    383  1.1.1.2  mrg 
    384  1.1.1.2  mrg   /* Unused; available for future use.  */
    385  1.1.1.2  mrg   unsigned int unused : 7;
    386  1.1.1.2  mrg 
    387  1.1.1.2  mrg   /* The mode passed to the convert_*_operand function.  It has a
    388  1.1.1.2  mrg      type-dependent meaning.  */
    389  1.1.1.2  mrg   ENUM_BITFIELD (machine_mode) mode : 16;
    390  1.1.1.2  mrg 
    391  1.1.1.2  mrg   /* The value of the operand.  */
    392  1.1.1.2  mrg   rtx value;
    393  1.1.1.2  mrg };
    394  1.1.1.2  mrg 
    395  1.1.1.2  mrg /* Initialize OP with the given fields.  Initialise the other fields
    396  1.1.1.2  mrg    to their default values.  */
    397  1.1.1.2  mrg 
    398  1.1.1.2  mrg static inline void
    399  1.1.1.2  mrg create_expand_operand (struct expand_operand *op,
    400  1.1.1.2  mrg 		       enum expand_operand_type type,
    401  1.1.1.2  mrg 		       rtx value, enum machine_mode mode,
    402  1.1.1.2  mrg 		       bool unsigned_p)
    403  1.1.1.2  mrg {
    404  1.1.1.2  mrg   op->type = type;
    405  1.1.1.2  mrg   op->unsigned_p = unsigned_p;
    406  1.1.1.2  mrg   op->unused = 0;
    407  1.1.1.2  mrg   op->mode = mode;
    408  1.1.1.2  mrg   op->value = value;
    409  1.1.1.2  mrg }
    410  1.1.1.2  mrg 
    411  1.1.1.2  mrg /* Make OP describe an operand that must use rtx X, even if X is volatile.  */
    412  1.1.1.2  mrg 
    413  1.1.1.2  mrg static inline void
    414  1.1.1.2  mrg create_fixed_operand (struct expand_operand *op, rtx x)
    415  1.1.1.2  mrg {
    416  1.1.1.2  mrg   create_expand_operand (op, EXPAND_FIXED, x, VOIDmode, false);
    417  1.1.1.2  mrg }
    418  1.1.1.2  mrg 
    419  1.1.1.2  mrg /* Make OP describe an output operand that must have mode MODE.
    420  1.1.1.2  mrg    X, if nonnull, is a suggestion for where the output should be stored.
    421  1.1.1.2  mrg    It is OK for VALUE to be inconsistent with MODE, although it will just
    422  1.1.1.2  mrg    be ignored in that case.  */
    423  1.1.1.2  mrg 
    424  1.1.1.2  mrg static inline void
    425  1.1.1.2  mrg create_output_operand (struct expand_operand *op, rtx x,
    426  1.1.1.2  mrg 		       enum machine_mode mode)
    427  1.1.1.2  mrg {
    428  1.1.1.2  mrg   create_expand_operand (op, EXPAND_OUTPUT, x, mode, false);
    429  1.1.1.2  mrg }
    430  1.1.1.2  mrg 
    431  1.1.1.2  mrg /* Make OP describe an input operand that must have mode MODE and
    432  1.1.1.2  mrg    value VALUE; MODE cannot be VOIDmode.  The backend may request that
    433  1.1.1.2  mrg    VALUE be copied into a different kind of rtx before being passed
    434  1.1.1.2  mrg    as an operand.  */
    435  1.1.1.2  mrg 
    436  1.1.1.2  mrg static inline void
    437  1.1.1.2  mrg create_input_operand (struct expand_operand *op, rtx value,
    438  1.1.1.2  mrg 		      enum machine_mode mode)
    439  1.1.1.2  mrg {
    440  1.1.1.2  mrg   create_expand_operand (op, EXPAND_INPUT, value, mode, false);
    441  1.1.1.2  mrg }
    442  1.1.1.2  mrg 
    443  1.1.1.2  mrg /* Like create_input_operand, except that VALUE must first be converted
    444  1.1.1.2  mrg    to mode MODE.  UNSIGNED_P says whether VALUE is unsigned.  */
    445  1.1.1.2  mrg 
    446  1.1.1.2  mrg static inline void
    447  1.1.1.2  mrg create_convert_operand_to (struct expand_operand *op, rtx value,
    448  1.1.1.2  mrg 			   enum machine_mode mode, bool unsigned_p)
    449  1.1.1.2  mrg {
    450  1.1.1.2  mrg   create_expand_operand (op, EXPAND_CONVERT_TO, value, mode, unsigned_p);
    451  1.1.1.2  mrg }
    452  1.1.1.2  mrg 
    453  1.1.1.2  mrg /* Make OP describe an input operand that should have the same value
    454  1.1.1.2  mrg    as VALUE, after any mode conversion that the backend might request.
    455  1.1.1.2  mrg    If VALUE is a CONST_INT, it should be treated as having mode MODE.
    456  1.1.1.2  mrg    UNSIGNED_P says whether VALUE is unsigned.  */
    457  1.1.1.2  mrg 
    458  1.1.1.2  mrg static inline void
    459  1.1.1.2  mrg create_convert_operand_from (struct expand_operand *op, rtx value,
    460  1.1.1.2  mrg 			     enum machine_mode mode, bool unsigned_p)
    461  1.1.1.2  mrg {
    462  1.1.1.2  mrg   create_expand_operand (op, EXPAND_CONVERT_FROM, value, mode, unsigned_p);
    463  1.1.1.2  mrg }
    464  1.1.1.2  mrg 
    465  1.1.1.2  mrg extern void create_convert_operand_from_type (struct expand_operand *op,
    466  1.1.1.2  mrg 					      rtx value, tree type);
    467  1.1.1.2  mrg 
    468  1.1.1.2  mrg /* Make OP describe an input Pmode address operand.  VALUE is the value
    469  1.1.1.2  mrg    of the address, but it may need to be converted to Pmode first.  */
    470  1.1.1.2  mrg 
    471  1.1.1.2  mrg static inline void
    472  1.1.1.2  mrg create_address_operand (struct expand_operand *op, rtx value)
    473  1.1.1.2  mrg {
    474  1.1.1.2  mrg   create_expand_operand (op, EXPAND_ADDRESS, value, Pmode, false);
    475  1.1.1.2  mrg }
    476  1.1.1.2  mrg 
    477  1.1.1.2  mrg /* Make OP describe an input operand that has value INTVAL and that has
    478  1.1.1.2  mrg    no inherent mode.  This function should only be used for operands that
    479  1.1.1.2  mrg    are always expand-time constants.  The backend may request that INTVAL
    480  1.1.1.2  mrg    be copied into a different kind of rtx, but it must specify the mode
    481  1.1.1.2  mrg    of that rtx if so.  */
    482  1.1.1.2  mrg 
    483  1.1.1.2  mrg static inline void
    484  1.1.1.2  mrg create_integer_operand (struct expand_operand *op, HOST_WIDE_INT intval)
    485  1.1.1.2  mrg {
    486  1.1.1.2  mrg   create_expand_operand (op, EXPAND_INTEGER, GEN_INT (intval), VOIDmode, false);
    487  1.1.1.2  mrg }
    488  1.1.1.2  mrg 
    489  1.1.1.2  mrg extern bool valid_multiword_target_p (rtx);
    490  1.1.1.2  mrg 
    491  1.1.1.2  mrg extern bool maybe_legitimize_operands (enum insn_code icode,
    492  1.1.1.2  mrg 				       unsigned int opno, unsigned int nops,
    493  1.1.1.2  mrg 				       struct expand_operand *ops);
    494  1.1.1.2  mrg extern rtx maybe_gen_insn (enum insn_code icode, unsigned int nops,
    495  1.1.1.2  mrg 			   struct expand_operand *ops);
    496  1.1.1.2  mrg extern bool maybe_expand_insn (enum insn_code icode, unsigned int nops,
    497  1.1.1.2  mrg 			       struct expand_operand *ops);
    498  1.1.1.2  mrg extern bool maybe_expand_jump_insn (enum insn_code icode, unsigned int nops,
    499  1.1.1.2  mrg 				    struct expand_operand *ops);
    500  1.1.1.2  mrg extern void expand_insn (enum insn_code icode, unsigned int nops,
    501  1.1.1.2  mrg 			 struct expand_operand *ops);
    502  1.1.1.2  mrg extern void expand_jump_insn (enum insn_code icode, unsigned int nops,
    503  1.1.1.2  mrg 			      struct expand_operand *ops);
    504  1.1.1.2  mrg 
    505  1.1.1.2  mrg extern rtx prepare_operand (enum insn_code, rtx, int, enum machine_mode,
    506  1.1.1.2  mrg 			    enum machine_mode, int);
    507  1.1.1.2  mrg 
    508  1.1.1.2  mrg extern void gen_int_libfunc (optab, const char *, char, enum machine_mode);
    509  1.1.1.2  mrg extern void gen_fp_libfunc (optab, const char *, char, enum machine_mode);
    510  1.1.1.2  mrg extern void gen_fixed_libfunc (optab, const char *, char, enum machine_mode);
    511  1.1.1.2  mrg extern void gen_signed_fixed_libfunc (optab, const char *, char,
    512  1.1.1.2  mrg 				      enum machine_mode);
    513  1.1.1.2  mrg extern void gen_unsigned_fixed_libfunc (optab, const char *, char,
    514  1.1.1.2  mrg 					enum machine_mode);
    515  1.1.1.2  mrg extern void gen_int_fp_libfunc (optab, const char *, char, enum machine_mode);
    516  1.1.1.2  mrg extern void gen_intv_fp_libfunc (optab, const char *, char, enum machine_mode);
    517  1.1.1.2  mrg extern void gen_int_fp_fixed_libfunc (optab, const char *, char,
    518  1.1.1.2  mrg 				      enum machine_mode);
    519  1.1.1.2  mrg extern void gen_int_fp_signed_fixed_libfunc (optab, const char *, char,
    520  1.1.1.2  mrg 					     enum machine_mode);
    521  1.1.1.2  mrg extern void gen_int_fixed_libfunc (optab, const char *, char,
    522  1.1.1.2  mrg 				   enum machine_mode);
    523  1.1.1.2  mrg extern void gen_int_signed_fixed_libfunc (optab, const char *, char,
    524  1.1.1.2  mrg 					  enum machine_mode);
    525  1.1.1.2  mrg extern void gen_int_unsigned_fixed_libfunc (optab, const char *, char,
    526  1.1.1.2  mrg 					    enum machine_mode);
    527  1.1.1.2  mrg 
    528  1.1.1.2  mrg extern void gen_interclass_conv_libfunc (convert_optab, const char *,
    529  1.1.1.2  mrg 					 enum machine_mode, enum machine_mode);
    530  1.1.1.2  mrg extern void gen_int_to_fp_conv_libfunc (convert_optab, const char *,
    531  1.1.1.2  mrg 					enum machine_mode, enum machine_mode);
    532  1.1.1.2  mrg extern void gen_ufloat_conv_libfunc (convert_optab, const char *,
    533  1.1.1.2  mrg 				     enum machine_mode, enum machine_mode);
    534  1.1.1.2  mrg extern void gen_int_to_fp_nondecimal_conv_libfunc  (convert_optab,
    535  1.1.1.2  mrg 						    const char *,
    536  1.1.1.2  mrg 						    enum machine_mode,
    537  1.1.1.2  mrg 						    enum machine_mode);
    538  1.1.1.2  mrg extern void gen_fp_to_int_conv_libfunc (convert_optab, const char *,
    539  1.1.1.2  mrg 					enum machine_mode, enum machine_mode);
    540  1.1.1.2  mrg extern void gen_intraclass_conv_libfunc (convert_optab, const char *,
    541  1.1.1.2  mrg 					 enum machine_mode, enum machine_mode);
    542  1.1.1.2  mrg extern void gen_trunc_conv_libfunc (convert_optab, const char *,
    543  1.1.1.2  mrg 				    enum machine_mode, enum machine_mode);
    544  1.1.1.2  mrg extern void gen_extend_conv_libfunc (convert_optab, const char *,
    545  1.1.1.2  mrg 				     enum machine_mode, enum machine_mode);
    546  1.1.1.2  mrg extern void gen_fract_conv_libfunc (convert_optab, const char *,
    547  1.1.1.2  mrg 				    enum machine_mode, enum machine_mode);
    548  1.1.1.2  mrg extern void gen_fractuns_conv_libfunc (convert_optab, const char *,
    549  1.1.1.2  mrg 				       enum machine_mode, enum machine_mode);
    550  1.1.1.2  mrg extern void gen_satfract_conv_libfunc (convert_optab, const char *,
    551  1.1.1.2  mrg 				       enum machine_mode, enum machine_mode);
    552  1.1.1.2  mrg extern void gen_satfractuns_conv_libfunc (convert_optab, const char *,
    553  1.1.1.2  mrg 					  enum machine_mode,
    554  1.1.1.2  mrg 					  enum machine_mode);
    555      1.1  mrg 
    556               #endif /* GCC_OPTABS_H */
    557