190075Sobrien/* Definitions for code generation pass of GNU compiler. 2169689Skan Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006 3169689Skan Free Software Foundation, Inc. 490075Sobrien 590075SobrienThis file is part of GCC. 690075Sobrien 790075SobrienGCC is free software; you can redistribute it and/or modify 890075Sobrienit under the terms of the GNU General Public License as published by 990075Sobrienthe Free Software Foundation; either version 2, or (at your option) 1090075Sobrienany later version. 1190075Sobrien 1290075SobrienGCC is distributed in the hope that it will be useful, 1390075Sobrienbut WITHOUT ANY WARRANTY; without even the implied warranty of 1490075SobrienMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 1590075SobrienGNU General Public License for more details. 1690075Sobrien 1790075SobrienYou should have received a copy of the GNU General Public License 1890075Sobrienalong with GCC; see the file COPYING. If not, write to 19169689Skanthe Free Software Foundation, 51 Franklin Street, Fifth Floor, 20169689SkanBoston, MA 02110-1301, USA. */ 2190075Sobrien 2290075Sobrien#ifndef GCC_OPTABS_H 2390075Sobrien#define GCC_OPTABS_H 2490075Sobrien 2590075Sobrien#include "insn-codes.h" 2690075Sobrien 2790075Sobrien/* Optabs are tables saying how to generate insn bodies 2890075Sobrien for various machine modes and numbers of operands. 2990075Sobrien Each optab applies to one operation. 3090075Sobrien For example, add_optab applies to addition. 3190075Sobrien 3290075Sobrien The insn_code slot is the enum insn_code that says how to 3390075Sobrien generate an insn for this operation on a particular machine mode. 3490075Sobrien It is CODE_FOR_nothing if there is no such insn on the target machine. 3590075Sobrien 3690075Sobrien The `lib_call' slot is the name of the library function that 3790075Sobrien can be used to perform the operation. 3890075Sobrien 3990075Sobrien A few optabs, such as move_optab and cmp_optab, are used 4090075Sobrien by special code. */ 4190075Sobrien 42132718Skanstruct optab_handlers GTY(()) 43132718Skan{ 44132718Skan enum insn_code insn_code; 45132718Skan rtx libfunc; 46132718Skan}; 47132718Skan 48117395Skanstruct optab GTY(()) 4990075Sobrien{ 5090075Sobrien enum rtx_code code; 51132718Skan struct optab_handlers handlers[NUM_MACHINE_MODES]; 52117395Skan}; 53117395Skantypedef struct optab * optab; 5490075Sobrien 55132718Skan/* A convert_optab is for some sort of conversion operation between 56132718Skan modes. The first array index is the destination mode, the second 57132718Skan is the source mode. */ 58132718Skanstruct convert_optab GTY(()) 59132718Skan{ 60132718Skan enum rtx_code code; 61132718Skan struct optab_handlers handlers[NUM_MACHINE_MODES][NUM_MACHINE_MODES]; 62132718Skan}; 63132718Skantypedef struct convert_optab *convert_optab; 64132718Skan 6590075Sobrien/* Given an enum insn_code, access the function to construct 6690075Sobrien the body of that kind of insn. */ 67132718Skan#define GEN_FCN(CODE) (insn_data[CODE].genfun) 6890075Sobrien 6990075Sobrien/* Enumeration of valid indexes into optab_table. */ 7090075Sobrienenum optab_index 7190075Sobrien{ 7290075Sobrien OTI_add, 7390075Sobrien OTI_addv, 7490075Sobrien OTI_sub, 7590075Sobrien OTI_subv, 7690075Sobrien 7790075Sobrien /* Signed and fp multiply */ 7890075Sobrien OTI_smul, 7990075Sobrien OTI_smulv, 8090075Sobrien /* Signed multiply, return high word */ 8190075Sobrien OTI_smul_highpart, 8290075Sobrien OTI_umul_highpart, 8390075Sobrien /* Signed multiply with result one machine mode wider than args */ 8490075Sobrien OTI_smul_widen, 8590075Sobrien OTI_umul_widen, 86169689Skan /* Widening multiply of one unsigned and one signed operand. */ 87169689Skan OTI_usmul_widen, 8890075Sobrien 8990075Sobrien /* Signed divide */ 9090075Sobrien OTI_sdiv, 9190075Sobrien OTI_sdivv, 9290075Sobrien /* Signed divide-and-remainder in one */ 9390075Sobrien OTI_sdivmod, 9490075Sobrien OTI_udiv, 9590075Sobrien OTI_udivmod, 9690075Sobrien /* Signed remainder */ 9790075Sobrien OTI_smod, 9890075Sobrien OTI_umod, 99169689Skan /* Floating point remainder functions */ 100169689Skan OTI_fmod, 101169689Skan OTI_drem, 10290075Sobrien /* Convert float to integer in float fmt */ 10390075Sobrien OTI_ftrunc, 10490075Sobrien 10590075Sobrien /* Logical and */ 10690075Sobrien OTI_and, 10790075Sobrien /* Logical or */ 10890075Sobrien OTI_ior, 10990075Sobrien /* Logical xor */ 11090075Sobrien OTI_xor, 11190075Sobrien 11290075Sobrien /* Arithmetic shift left */ 11390075Sobrien OTI_ashl, 11490075Sobrien /* Logical shift right */ 115132718Skan OTI_lshr, 11690075Sobrien /* Arithmetic shift right */ 11790075Sobrien OTI_ashr, 11890075Sobrien /* Rotate left */ 11990075Sobrien OTI_rotl, 12090075Sobrien /* Rotate right */ 12190075Sobrien OTI_rotr, 12290075Sobrien /* Signed and floating-point minimum value */ 12390075Sobrien OTI_smin, 12490075Sobrien /* Signed and floating-point maximum value */ 12590075Sobrien OTI_smax, 12690075Sobrien /* Unsigned minimum value */ 12790075Sobrien OTI_umin, 12890075Sobrien /* Unsigned maximum value */ 12990075Sobrien OTI_umax, 130132718Skan /* Power */ 131132718Skan OTI_pow, 132132718Skan /* Arc tangent of y/x */ 133132718Skan OTI_atan2, 13490075Sobrien 13590075Sobrien /* Move instruction. */ 13690075Sobrien OTI_mov, 13790075Sobrien /* Move, preserving high part of register. */ 13890075Sobrien OTI_movstrict, 139169689Skan /* Move, with a misaligned memory. */ 140169689Skan OTI_movmisalign, 14190075Sobrien 14290075Sobrien /* Unary operations */ 14390075Sobrien /* Negation */ 14490075Sobrien OTI_neg, 14590075Sobrien OTI_negv, 14690075Sobrien /* Abs value */ 14790075Sobrien OTI_abs, 14890075Sobrien OTI_absv, 149259563Spfg /* Byteswap */ 150259563Spfg OTI_bswap, 15190075Sobrien /* Bitwise not */ 15290075Sobrien OTI_one_cmpl, 153132718Skan /* Bit scanning and counting */ 15490075Sobrien OTI_ffs, 155132718Skan OTI_clz, 156132718Skan OTI_ctz, 157132718Skan OTI_popcount, 158132718Skan OTI_parity, 15990075Sobrien /* Square root */ 16090075Sobrien OTI_sqrt, 161169689Skan /* Sine-Cosine */ 162169689Skan OTI_sincos, 16390075Sobrien /* Sine */ 16490075Sobrien OTI_sin, 165169689Skan /* Inverse sine */ 166169689Skan OTI_asin, 16790075Sobrien /* Cosine */ 16890075Sobrien OTI_cos, 169169689Skan /* Inverse cosine */ 170169689Skan OTI_acos, 171117395Skan /* Exponential */ 172117395Skan OTI_exp, 173169689Skan /* Base-10 Exponential */ 174169689Skan OTI_exp10, 175169689Skan /* Base-2 Exponential */ 176169689Skan OTI_exp2, 177169689Skan /* Exponential - 1*/ 178169689Skan OTI_expm1, 179169689Skan /* Load exponent of a floating point number */ 180169689Skan OTI_ldexp, 181169689Skan /* Radix-independent exponent */ 182169689Skan OTI_logb, 183169689Skan OTI_ilogb, 184117395Skan /* Natural Logarithm */ 185117395Skan OTI_log, 186169689Skan /* Base-10 Logarithm */ 187169689Skan OTI_log10, 188169689Skan /* Base-2 Logarithm */ 189169689Skan OTI_log2, 190169689Skan /* logarithm of 1 plus argument */ 191169689Skan OTI_log1p, 192132718Skan /* Rounding functions */ 193132718Skan OTI_floor, 194169689Skan OTI_lfloor, 195132718Skan OTI_ceil, 196169689Skan OTI_lceil, 197169689Skan OTI_btrunc, 198132718Skan OTI_round, 199132718Skan OTI_nearbyint, 200169689Skan OTI_rint, 201169689Skan OTI_lrint, 202132718Skan /* Tangent */ 203132718Skan OTI_tan, 204132718Skan /* Inverse tangent */ 205132718Skan OTI_atan, 206169689Skan /* Copy sign */ 207169689Skan OTI_copysign, 20890075Sobrien 20990075Sobrien /* Compare insn; two operands. */ 21090075Sobrien OTI_cmp, 21190075Sobrien /* Used only for libcalls for unsigned comparisons. */ 21290075Sobrien OTI_ucmp, 21390075Sobrien /* tst insn; compare one operand against 0 */ 21490075Sobrien OTI_tst, 21590075Sobrien 216132718Skan /* Floating point comparison optabs - used primarily for libfuncs */ 217132718Skan OTI_eq, 218132718Skan OTI_ne, 219132718Skan OTI_gt, 220132718Skan OTI_ge, 221132718Skan OTI_lt, 222132718Skan OTI_le, 223132718Skan OTI_unord, 224132718Skan 22590075Sobrien /* String length */ 22690075Sobrien OTI_strlen, 22790075Sobrien 22890075Sobrien /* Combined compare & jump/store flags/move operations. */ 22990075Sobrien OTI_cbranch, 23090075Sobrien OTI_cmov, 23190075Sobrien OTI_cstore, 232132718Skan 23390075Sobrien /* Push instruction. */ 23490075Sobrien OTI_push, 23590075Sobrien 236132718Skan /* Conditional add instruction. */ 237132718Skan OTI_addcc, 238132718Skan 239169689Skan /* Reduction operations on a vector operand. */ 240169689Skan OTI_reduc_smax, 241169689Skan OTI_reduc_umax, 242169689Skan OTI_reduc_smin, 243169689Skan OTI_reduc_umin, 244169689Skan OTI_reduc_splus, 245169689Skan OTI_reduc_uplus, 246169689Skan 247169689Skan /* Summation, with result machine mode one or more wider than args. */ 248169689Skan OTI_ssum_widen, 249169689Skan OTI_usum_widen, 250169689Skan 251169689Skan /* Dot product, with result machine mode one or more wider than args. */ 252169689Skan OTI_sdot_prod, 253169689Skan OTI_udot_prod, 254169689Skan 255132718Skan /* Set specified field of vector operand. */ 256132718Skan OTI_vec_set, 257132718Skan /* Extract specified field of vector operand. */ 258132718Skan OTI_vec_extract, 259132718Skan /* Initialize vector operand. */ 260132718Skan OTI_vec_init, 261169689Skan /* Whole vector shift. The shift amount is in bits. */ 262169689Skan OTI_vec_shl, 263169689Skan OTI_vec_shr, 264169689Skan /* Extract specified elements from vectors, for vector load. */ 265169689Skan OTI_vec_realign_load, 266132718Skan 267169689Skan /* Perform a raise to the power of integer. */ 268169689Skan OTI_powi, 269169689Skan 27090075Sobrien OTI_MAX 27190075Sobrien}; 27290075Sobrien 273117395Skanextern GTY(()) optab optab_table[OTI_MAX]; 27490075Sobrien 27590075Sobrien#define add_optab (optab_table[OTI_add]) 27690075Sobrien#define sub_optab (optab_table[OTI_sub]) 27790075Sobrien#define smul_optab (optab_table[OTI_smul]) 27890075Sobrien#define addv_optab (optab_table[OTI_addv]) 27990075Sobrien#define subv_optab (optab_table[OTI_subv]) 28090075Sobrien#define smul_highpart_optab (optab_table[OTI_smul_highpart]) 28190075Sobrien#define umul_highpart_optab (optab_table[OTI_umul_highpart]) 28290075Sobrien#define smul_widen_optab (optab_table[OTI_smul_widen]) 28390075Sobrien#define umul_widen_optab (optab_table[OTI_umul_widen]) 284169689Skan#define usmul_widen_optab (optab_table[OTI_usmul_widen]) 28590075Sobrien#define sdiv_optab (optab_table[OTI_sdiv]) 28690075Sobrien#define smulv_optab (optab_table[OTI_smulv]) 28790075Sobrien#define sdivv_optab (optab_table[OTI_sdivv]) 28890075Sobrien#define sdivmod_optab (optab_table[OTI_sdivmod]) 28990075Sobrien#define udiv_optab (optab_table[OTI_udiv]) 29090075Sobrien#define udivmod_optab (optab_table[OTI_udivmod]) 29190075Sobrien#define smod_optab (optab_table[OTI_smod]) 29290075Sobrien#define umod_optab (optab_table[OTI_umod]) 293169689Skan#define fmod_optab (optab_table[OTI_fmod]) 294169689Skan#define drem_optab (optab_table[OTI_drem]) 29590075Sobrien#define ftrunc_optab (optab_table[OTI_ftrunc]) 29690075Sobrien#define and_optab (optab_table[OTI_and]) 29790075Sobrien#define ior_optab (optab_table[OTI_ior]) 29890075Sobrien#define xor_optab (optab_table[OTI_xor]) 29990075Sobrien#define ashl_optab (optab_table[OTI_ashl]) 30090075Sobrien#define lshr_optab (optab_table[OTI_lshr]) 30190075Sobrien#define ashr_optab (optab_table[OTI_ashr]) 30290075Sobrien#define rotl_optab (optab_table[OTI_rotl]) 30390075Sobrien#define rotr_optab (optab_table[OTI_rotr]) 30490075Sobrien#define smin_optab (optab_table[OTI_smin]) 30590075Sobrien#define smax_optab (optab_table[OTI_smax]) 30690075Sobrien#define umin_optab (optab_table[OTI_umin]) 30790075Sobrien#define umax_optab (optab_table[OTI_umax]) 308132718Skan#define pow_optab (optab_table[OTI_pow]) 309132718Skan#define atan2_optab (optab_table[OTI_atan2]) 31090075Sobrien 31190075Sobrien#define mov_optab (optab_table[OTI_mov]) 31290075Sobrien#define movstrict_optab (optab_table[OTI_movstrict]) 313169689Skan#define movmisalign_optab (optab_table[OTI_movmisalign]) 31490075Sobrien 31590075Sobrien#define neg_optab (optab_table[OTI_neg]) 31690075Sobrien#define negv_optab (optab_table[OTI_negv]) 31790075Sobrien#define abs_optab (optab_table[OTI_abs]) 31890075Sobrien#define absv_optab (optab_table[OTI_absv]) 31990075Sobrien#define one_cmpl_optab (optab_table[OTI_one_cmpl]) 320259563Spfg#define bswap_optab (optab_table[OTI_bswap]) 32190075Sobrien#define ffs_optab (optab_table[OTI_ffs]) 322132718Skan#define clz_optab (optab_table[OTI_clz]) 323132718Skan#define ctz_optab (optab_table[OTI_ctz]) 324132718Skan#define popcount_optab (optab_table[OTI_popcount]) 325132718Skan#define parity_optab (optab_table[OTI_parity]) 32690075Sobrien#define sqrt_optab (optab_table[OTI_sqrt]) 327169689Skan#define sincos_optab (optab_table[OTI_sincos]) 32890075Sobrien#define sin_optab (optab_table[OTI_sin]) 329169689Skan#define asin_optab (optab_table[OTI_asin]) 33090075Sobrien#define cos_optab (optab_table[OTI_cos]) 331169689Skan#define acos_optab (optab_table[OTI_acos]) 332117395Skan#define exp_optab (optab_table[OTI_exp]) 333169689Skan#define exp10_optab (optab_table[OTI_exp10]) 334169689Skan#define exp2_optab (optab_table[OTI_exp2]) 335169689Skan#define expm1_optab (optab_table[OTI_expm1]) 336169689Skan#define ldexp_optab (optab_table[OTI_ldexp]) 337169689Skan#define logb_optab (optab_table[OTI_logb]) 338169689Skan#define ilogb_optab (optab_table[OTI_ilogb]) 339117395Skan#define log_optab (optab_table[OTI_log]) 340169689Skan#define log10_optab (optab_table[OTI_log10]) 341169689Skan#define log2_optab (optab_table[OTI_log2]) 342169689Skan#define log1p_optab (optab_table[OTI_log1p]) 343132718Skan#define floor_optab (optab_table[OTI_floor]) 344169689Skan#define lfloor_optab (optab_table[OTI_lfloor]) 345132718Skan#define ceil_optab (optab_table[OTI_ceil]) 346169689Skan#define lceil_optab (optab_table[OTI_lceil]) 347169689Skan#define btrunc_optab (optab_table[OTI_btrunc]) 348132718Skan#define round_optab (optab_table[OTI_round]) 349132718Skan#define nearbyint_optab (optab_table[OTI_nearbyint]) 350169689Skan#define rint_optab (optab_table[OTI_rint]) 351169689Skan#define lrint_optab (optab_table[OTI_lrint]) 352132718Skan#define tan_optab (optab_table[OTI_tan]) 353132718Skan#define atan_optab (optab_table[OTI_atan]) 354169689Skan#define copysign_optab (optab_table[OTI_copysign]) 35590075Sobrien 35690075Sobrien#define cmp_optab (optab_table[OTI_cmp]) 35790075Sobrien#define ucmp_optab (optab_table[OTI_ucmp]) 35890075Sobrien#define tst_optab (optab_table[OTI_tst]) 35990075Sobrien 360132718Skan#define eq_optab (optab_table[OTI_eq]) 361132718Skan#define ne_optab (optab_table[OTI_ne]) 362132718Skan#define gt_optab (optab_table[OTI_gt]) 363132718Skan#define ge_optab (optab_table[OTI_ge]) 364132718Skan#define lt_optab (optab_table[OTI_lt]) 365132718Skan#define le_optab (optab_table[OTI_le]) 366132718Skan#define unord_optab (optab_table[OTI_unord]) 367132718Skan 36890075Sobrien#define strlen_optab (optab_table[OTI_strlen]) 36990075Sobrien 37090075Sobrien#define cbranch_optab (optab_table[OTI_cbranch]) 37190075Sobrien#define cmov_optab (optab_table[OTI_cmov]) 37290075Sobrien#define cstore_optab (optab_table[OTI_cstore]) 37390075Sobrien#define push_optab (optab_table[OTI_push]) 374132718Skan#define addcc_optab (optab_table[OTI_addcc]) 37590075Sobrien 376169689Skan#define reduc_smax_optab (optab_table[OTI_reduc_smax]) 377169689Skan#define reduc_umax_optab (optab_table[OTI_reduc_umax]) 378169689Skan#define reduc_smin_optab (optab_table[OTI_reduc_smin]) 379169689Skan#define reduc_umin_optab (optab_table[OTI_reduc_umin]) 380169689Skan#define reduc_splus_optab (optab_table[OTI_reduc_splus]) 381169689Skan#define reduc_uplus_optab (optab_table[OTI_reduc_uplus]) 382169689Skan 383169689Skan#define ssum_widen_optab (optab_table[OTI_ssum_widen]) 384169689Skan#define usum_widen_optab (optab_table[OTI_usum_widen]) 385169689Skan#define sdot_prod_optab (optab_table[OTI_sdot_prod]) 386169689Skan#define udot_prod_optab (optab_table[OTI_udot_prod]) 387169689Skan 388132718Skan#define vec_set_optab (optab_table[OTI_vec_set]) 389132718Skan#define vec_extract_optab (optab_table[OTI_vec_extract]) 390132718Skan#define vec_init_optab (optab_table[OTI_vec_init]) 391169689Skan#define vec_shl_optab (optab_table[OTI_vec_shl]) 392169689Skan#define vec_shr_optab (optab_table[OTI_vec_shr]) 393169689Skan#define vec_realign_load_optab (optab_table[OTI_vec_realign_load]) 39490075Sobrien 395169689Skan#define powi_optab (optab_table[OTI_powi]) 396169689Skan 397132718Skan/* Conversion optabs have their own table and indexes. */ 398132718Skanenum convert_optab_index 399132718Skan{ 400169689Skan COI_sext, 401169689Skan COI_zext, 402169689Skan COI_trunc, 40390075Sobrien 404169689Skan COI_sfix, 405169689Skan COI_ufix, 406132718Skan 407169689Skan COI_sfixtrunc, 408169689Skan COI_ufixtrunc, 409132718Skan 410169689Skan COI_sfloat, 411169689Skan COI_ufloat, 412132718Skan 413169689Skan COI_MAX 414132718Skan}; 415132718Skan 416169689Skanextern GTY(()) convert_optab convert_optab_table[COI_MAX]; 417132718Skan 418169689Skan#define sext_optab (convert_optab_table[COI_sext]) 419169689Skan#define zext_optab (convert_optab_table[COI_zext]) 420169689Skan#define trunc_optab (convert_optab_table[COI_trunc]) 421169689Skan#define sfix_optab (convert_optab_table[COI_sfix]) 422169689Skan#define ufix_optab (convert_optab_table[COI_ufix]) 423169689Skan#define sfixtrunc_optab (convert_optab_table[COI_sfixtrunc]) 424169689Skan#define ufixtrunc_optab (convert_optab_table[COI_ufixtrunc]) 425169689Skan#define sfloat_optab (convert_optab_table[COI_sfloat]) 426169689Skan#define ufloat_optab (convert_optab_table[COI_ufloat]) 427132718Skan 42890075Sobrien/* These arrays record the insn_code of insns that may be needed to 42990075Sobrien perform input and output reloads of special objects. They provide a 43090075Sobrien place to pass a scratch register. */ 43190075Sobrienextern enum insn_code reload_in_optab[NUM_MACHINE_MODES]; 43290075Sobrienextern enum insn_code reload_out_optab[NUM_MACHINE_MODES]; 43390075Sobrien 43490075Sobrien/* Contains the optab used for each rtx code. */ 435132718Skanextern GTY(()) optab code_to_optab[NUM_RTX_CODE + 1]; 43690075Sobrien 43790075Sobrien 438132718Skantypedef rtx (*rtxfun) (rtx); 43990075Sobrien 440169689Skan/* Indexed by the rtx-code for a conditional (e.g. EQ, LT,...) 44190075Sobrien gives the gen_function to make a branch to test that condition. */ 44290075Sobrien 44390075Sobrienextern rtxfun bcc_gen_fctn[NUM_RTX_CODE]; 44490075Sobrien 445169689Skan/* Indexed by the rtx-code for a conditional (e.g. EQ, LT,...) 44690075Sobrien gives the insn code to make a store-condition insn 44790075Sobrien to test that condition. */ 44890075Sobrien 44990075Sobrienextern enum insn_code setcc_gen_code[NUM_RTX_CODE]; 45090075Sobrien 45190075Sobrien#ifdef HAVE_conditional_move 45290075Sobrien/* Indexed by the machine mode, gives the insn code to make a conditional 45390075Sobrien move insn. */ 45490075Sobrien 45590075Sobrienextern enum insn_code movcc_gen_code[NUM_MACHINE_MODES]; 45690075Sobrien#endif 45790075Sobrien 458169689Skan/* Indexed by the machine mode, gives the insn code for vector conditional 459169689Skan operation. */ 460169689Skan 461169689Skanextern enum insn_code vcond_gen_code[NUM_MACHINE_MODES]; 462169689Skanextern enum insn_code vcondu_gen_code[NUM_MACHINE_MODES]; 463169689Skan 46490075Sobrien/* This array records the insn_code of insns to perform block moves. */ 465169689Skanextern enum insn_code movmem_optab[NUM_MACHINE_MODES]; 46690075Sobrien 467169689Skan/* This array records the insn_code of insns to perform block sets. */ 468169689Skanextern enum insn_code setmem_optab[NUM_MACHINE_MODES]; 46990075Sobrien 470132718Skan/* These arrays record the insn_code of two different kinds of insns 471132718Skan to perform block compares. */ 472132718Skanextern enum insn_code cmpstr_optab[NUM_MACHINE_MODES]; 473169689Skanextern enum insn_code cmpstrn_optab[NUM_MACHINE_MODES]; 474132718Skanextern enum insn_code cmpmem_optab[NUM_MACHINE_MODES]; 475132718Skan 476169689Skan/* Synchronization primitives. This first set is atomic operation for 477169689Skan which we don't care about the resulting value. */ 478169689Skanextern enum insn_code sync_add_optab[NUM_MACHINE_MODES]; 479169689Skanextern enum insn_code sync_sub_optab[NUM_MACHINE_MODES]; 480169689Skanextern enum insn_code sync_ior_optab[NUM_MACHINE_MODES]; 481169689Skanextern enum insn_code sync_and_optab[NUM_MACHINE_MODES]; 482169689Skanextern enum insn_code sync_xor_optab[NUM_MACHINE_MODES]; 483169689Skanextern enum insn_code sync_nand_optab[NUM_MACHINE_MODES]; 484169689Skan 485169689Skan/* This second set is atomic operations in which we return the value 486169689Skan that existed in memory before the operation. */ 487169689Skanextern enum insn_code sync_old_add_optab[NUM_MACHINE_MODES]; 488169689Skanextern enum insn_code sync_old_sub_optab[NUM_MACHINE_MODES]; 489169689Skanextern enum insn_code sync_old_ior_optab[NUM_MACHINE_MODES]; 490169689Skanextern enum insn_code sync_old_and_optab[NUM_MACHINE_MODES]; 491169689Skanextern enum insn_code sync_old_xor_optab[NUM_MACHINE_MODES]; 492169689Skanextern enum insn_code sync_old_nand_optab[NUM_MACHINE_MODES]; 493169689Skan 494169689Skan/* This third set is atomic operations in which we return the value 495169689Skan that resulted after performing the operation. */ 496169689Skanextern enum insn_code sync_new_add_optab[NUM_MACHINE_MODES]; 497169689Skanextern enum insn_code sync_new_sub_optab[NUM_MACHINE_MODES]; 498169689Skanextern enum insn_code sync_new_ior_optab[NUM_MACHINE_MODES]; 499169689Skanextern enum insn_code sync_new_and_optab[NUM_MACHINE_MODES]; 500169689Skanextern enum insn_code sync_new_xor_optab[NUM_MACHINE_MODES]; 501169689Skanextern enum insn_code sync_new_nand_optab[NUM_MACHINE_MODES]; 502169689Skan 503169689Skan/* Atomic compare and swap. */ 504169689Skanextern enum insn_code sync_compare_and_swap[NUM_MACHINE_MODES]; 505169689Skanextern enum insn_code sync_compare_and_swap_cc[NUM_MACHINE_MODES]; 506169689Skan 507169689Skan/* Atomic exchange with acquire semantics. */ 508169689Skanextern enum insn_code sync_lock_test_and_set[NUM_MACHINE_MODES]; 509169689Skan 510169689Skan/* Atomic clear with release semantics. */ 511169689Skanextern enum insn_code sync_lock_release[NUM_MACHINE_MODES]; 512169689Skan 51390075Sobrien/* Define functions given in optabs.c. */ 51490075Sobrien 515169689Skanextern rtx expand_widen_pattern_expr (tree exp, rtx op0, rtx op1, rtx wide_op, 516169689Skan rtx target, int unsignedp); 517169689Skan 518169689Skanextern rtx expand_ternary_op (enum machine_mode mode, optab ternary_optab, 519169689Skan rtx op0, rtx op1, rtx op2, rtx target, 520169689Skan int unsignedp); 521169689Skan 52290075Sobrien/* Expand a binary operation given optab and rtx operands. */ 523132718Skanextern rtx expand_binop (enum machine_mode, optab, rtx, rtx, rtx, int, 524132718Skan enum optab_methods); 52590075Sobrien 526169689Skanextern bool force_expand_binop (enum machine_mode, optab, rtx, rtx, rtx, int, 527169689Skan enum optab_methods); 528169689Skan 52990075Sobrien/* Expand a binary operation with both signed and unsigned forms. */ 530132718Skanextern rtx sign_expand_binop (enum machine_mode, optab, optab, rtx, rtx, 531132718Skan rtx, int, enum optab_methods); 53290075Sobrien 533169689Skan/* Generate code to perform an operation on one operand with two results. */ 534169689Skanextern int expand_twoval_unop (optab, rtx, rtx, rtx, int); 535169689Skan 53690075Sobrien/* Generate code to perform an operation on two operands with two results. */ 537132718Skanextern int expand_twoval_binop (optab, rtx, rtx, rtx, rtx, int); 53890075Sobrien 539169689Skan/* Generate code to perform an operation on two operands with two 540169689Skan results, using a library function. */ 541169689Skanextern bool expand_twoval_binop_libfunc (optab, rtx, rtx, rtx, rtx, 542169689Skan enum rtx_code); 543169689Skan 54490075Sobrien/* Expand a unary arithmetic operation given optab rtx operand. */ 545132718Skanextern rtx expand_unop (enum machine_mode, optab, rtx, rtx, int); 54690075Sobrien 54790075Sobrien/* Expand the absolute value operation. */ 548132718Skanextern rtx expand_abs_nojump (enum machine_mode, rtx, rtx, int); 549132718Skanextern rtx expand_abs (enum machine_mode, rtx, rtx, int, int); 55090075Sobrien 551169689Skan/* Expand the copysign operation. */ 552169689Skanextern rtx expand_copysign (rtx, rtx, rtx); 55390075Sobrien 55490075Sobrien/* Generate an instruction with a given INSN_CODE with an output and 55590075Sobrien an input. */ 556132718Skanextern void emit_unop_insn (int, rtx, rtx, enum rtx_code); 55790075Sobrien 55890075Sobrien/* Emit code to perform a series of operations on a multi-word quantity, one 55990075Sobrien word at a time. */ 560132718Skanextern rtx emit_no_conflict_block (rtx, rtx, rtx, rtx, rtx); 56190075Sobrien 56290075Sobrien/* Emit one rtl insn to compare two rtx's. */ 563132718Skanextern void emit_cmp_insn (rtx, rtx, enum rtx_code, rtx, enum machine_mode, 564132718Skan int); 56590075Sobrien 56690075Sobrien/* The various uses that a comparison can have; used by can_compare_p: 56790075Sobrien jumps, conditional moves, store flag operations. */ 56890075Sobrienenum can_compare_purpose 56990075Sobrien{ 57090075Sobrien ccp_jump, 57190075Sobrien ccp_cmov, 57290075Sobrien ccp_store_flag 57390075Sobrien}; 57490075Sobrien 575169689Skan/* Return the optab used for computing the given operation on the type 576169689Skan given by the second argument. */ 577169689Skanextern optab optab_for_tree_code (enum tree_code, tree); 578169689Skan 57990075Sobrien/* Nonzero if a compare of mode MODE can be done straightforwardly 58090075Sobrien (without splitting it into pieces). */ 581132718Skanextern int can_compare_p (enum rtx_code, enum machine_mode, 582132718Skan enum can_compare_purpose); 58390075Sobrien 58490075Sobrien/* Return the INSN_CODE to use for an extend operation. */ 585132718Skanextern enum insn_code can_extend_p (enum machine_mode, enum machine_mode, int); 58690075Sobrien 58790075Sobrien/* Generate the body of an insn to extend Y (with mode MFROM) 58890075Sobrien into X (with mode MTO). Do zero-extension if UNSIGNEDP is nonzero. */ 589132718Skanextern rtx gen_extend_insn (rtx, rtx, enum machine_mode, 590132718Skan enum machine_mode, int); 59190075Sobrien 592132718Skan/* Call this to reset the function entry for one optab. */ 593132718Skanextern void set_optab_libfunc (optab, enum machine_mode, const char *); 594132718Skanextern void set_conv_libfunc (convert_optab, enum machine_mode, 595132718Skan enum machine_mode, const char *); 596132718Skan 59790075Sobrien/* Generate code for a FLOAT_EXPR. */ 598132718Skanextern void expand_float (rtx, rtx, int); 59990075Sobrien 60090075Sobrien/* Generate code for a FIX_EXPR. */ 601132718Skanextern void expand_fix (rtx, rtx, int); 60290075Sobrien 603169689Skan/* Return tree if target supports vector operations for COND_EXPR. */ 604169689Skanbool expand_vec_cond_expr_p (tree, enum machine_mode); 605169689Skan 606169689Skan/* Generate code for VEC_COND_EXPR. */ 607169689Skanextern rtx expand_vec_cond_expr (tree, rtx); 608169689Skan 609169689Skan/* Generate code for VEC_LSHIFT_EXPR and VEC_RSHIFT_EXPR. */ 610169689Skanextern rtx expand_vec_shift_expr (tree, rtx); 611169689Skan 61290075Sobrien#endif /* GCC_OPTABS_H */ 613