1;; Machine description for DEC Alpha for GNU C compiler 2;; Copyright (C) 1992-2016 Free Software Foundation, Inc. 3;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu) 4;; 5;; This file is part of GCC. 6;; 7;; GCC is free software; you can redistribute it and/or modify 8;; it under the terms of the GNU General Public License as published by 9;; the Free Software Foundation; either version 3, or (at your option) 10;; any later version. 11;; 12;; GCC is distributed in the hope that it will be useful, 13;; but WITHOUT ANY WARRANTY; without even the implied warranty of 14;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15;; GNU General Public License for more details. 16;; 17;; You should have received a copy of the GNU General Public License 18;; along with GCC; see the file COPYING3. If not see 19;; <http://www.gnu.org/licenses/>. 20 21;;- See file "rtl.def" for documentation on define_insn, match_*, et. al. 22 23;; Uses of UNSPEC in this file: 24 25(define_c_enum "unspec" [ 26 UNSPEC_XFLT_COMPARE 27 UNSPEC_ARG_HOME 28 UNSPEC_LDGP1 29 UNSPEC_INSXH 30 UNSPEC_MSKXH 31 UNSPEC_CVTQL 32 UNSPEC_CVTLQ 33 UNSPEC_LDGP2 34 UNSPEC_LITERAL 35 UNSPEC_LITUSE 36 UNSPEC_SIBCALL 37 UNSPEC_SYMBOL 38 39 ;; TLS Support 40 UNSPEC_TLSGD_CALL 41 UNSPEC_TLSLDM_CALL 42 UNSPEC_TLSGD 43 UNSPEC_TLSLDM 44 UNSPEC_DTPREL 45 UNSPEC_TPREL 46 UNSPEC_TP 47 48 ;; Builtins 49 UNSPEC_CMPBGE 50 UNSPEC_ZAP 51 UNSPEC_AMASK 52 UNSPEC_IMPLVER 53 UNSPEC_PERR 54 UNSPEC_COPYSIGN 55 56 ;; Atomic operations 57 UNSPEC_MB 58 UNSPEC_ATOMIC 59 UNSPEC_CMPXCHG 60 UNSPEC_XCHG 61]) 62 63;; UNSPEC_VOLATILE: 64 65(define_c_enum "unspecv" [ 66 UNSPECV_IMB 67 UNSPECV_BLOCKAGE 68 UNSPECV_SETJMPR ; builtin_setjmp_receiver 69 UNSPECV_LONGJMP ; builtin_longjmp 70 UNSPECV_TRAPB 71 UNSPECV_PSPL ; prologue_stack_probe_loop 72 UNSPECV_REALIGN 73 UNSPECV_EHR ; exception_receiver 74 UNSPECV_MCOUNT 75 UNSPECV_FORCE_MOV 76 UNSPECV_LDGP1 77 UNSPECV_PLDGP2 ; prologue ldgp 78 UNSPECV_SET_TP 79 UNSPECV_RPCC 80 UNSPECV_SETJMPR_ER ; builtin_setjmp_receiver fragment 81 UNSPECV_LL ; load-locked 82 UNSPECV_SC ; store-conditional 83 UNSPECV_CMPXCHG 84]) 85 86;; On non-BWX targets, CQImode must be handled the similarly to HImode 87;; when generating reloads. 88(define_mode_iterator RELOAD12 [QI HI CQI]) 89(define_mode_attr reloadmode [(QI "qi") (HI "hi") (CQI "hi")]) 90 91;; Other mode iterators 92(define_mode_iterator IMODE [QI HI SI DI]) 93(define_mode_iterator I12MODE [QI HI]) 94(define_mode_iterator I124MODE [QI HI SI]) 95(define_mode_iterator I24MODE [HI SI]) 96(define_mode_iterator I248MODE [HI SI DI]) 97(define_mode_iterator I48MODE [SI DI]) 98 99(define_mode_attr DWI [(SI "DI") (DI "TI")]) 100(define_mode_attr modesuffix [(QI "b") (HI "w") (SI "l") (DI "q") 101 (V8QI "b8") (V4HI "w4") 102 (SF "%,") (DF "%-")]) 103(define_mode_attr vecmodesuffix [(QI "b8") (HI "w4")]) 104 105(define_code_iterator any_maxmin [smax smin umax umin]) 106 107(define_code_attr maxmin [(smax "maxs") (smin "mins") 108 (umax "maxu") (umin "minu")]) 109 110;; Where necessary, the suffixes _le and _be are used to distinguish between 111;; little-endian and big-endian patterns. 112;; 113;; Note that the Unicos/Mk assembler does not support the following 114;; opcodes: mov, fmov, nop, fnop, unop. 115 116;; Processor type -- this attribute must exactly match the processor_type 117;; enumeration in alpha.h. 118 119(define_attr "tune" "ev4,ev5,ev6" 120 (const (symbol_ref "((enum attr_tune) alpha_tune)"))) 121 122;; Define an insn type attribute. This is used in function unit delay 123;; computations, among other purposes. For the most part, we use the names 124;; defined in the EV4 documentation, but add a few that we have to know about 125;; separately. 126 127(define_attr "type" 128 "ild,fld,ldsym,ist,fst,ibr,callpal,fbr,jsr,iadd,ilog,shift,icmov,fcmov, 129 icmp,imul,fadd,fmul,fcpys,fdiv,fsqrt,misc,mvi,ftoi,itof,mb,ld_l,st_c, 130 multi,none" 131 (const_string "iadd")) 132 133;; Describe a user's asm statement. 134(define_asm_attributes 135 [(set_attr "type" "multi")]) 136 137;; Define the operand size an insn operates on. Used primarily by mul 138;; and div operations that have size dependent timings. 139 140(define_attr "opsize" "si,di,udi" 141 (const_string "di")) 142 143;; The TRAP attribute marks instructions that may generate traps 144;; (which are imprecise and may need a trapb if software completion 145;; is desired). 146 147(define_attr "trap" "no,yes" 148 (const_string "no")) 149 150;; The ROUND_SUFFIX attribute marks which instructions require a 151;; rounding-mode suffix. The value NONE indicates no suffix, 152;; the value NORMAL indicates a suffix controlled by alpha_fprm. 153 154(define_attr "round_suffix" "none,normal,c" 155 (const_string "none")) 156 157;; The TRAP_SUFFIX attribute marks instructions requiring a trap-mode suffix: 158;; NONE no suffix 159;; SU accepts only /su (cmpt et al) 160;; SUI accepts only /sui (cvtqt and cvtqs) 161;; V_SV accepts /v and /sv (cvtql only) 162;; V_SV_SVI accepts /v, /sv and /svi (cvttq only) 163;; U_SU_SUI accepts /u, /su and /sui (most fp instructions) 164;; 165;; The actual suffix emitted is controlled by alpha_fptm. 166 167(define_attr "trap_suffix" "none,su,sui,v_sv,v_sv_svi,u_su_sui" 168 (const_string "none")) 169 170;; The length of an instruction sequence in bytes. 171 172(define_attr "length" "" 173 (const_int 4)) 174 175;; The USEGP attribute marks instructions that have relocations that use 176;; the GP. 177 178(define_attr "usegp" "no,yes" 179 (cond [(eq_attr "type" "ldsym,jsr") 180 (const_string "yes") 181 (eq_attr "type" "ild,fld,ist,fst") 182 (symbol_ref "((enum attr_usegp) alpha_find_lo_sum_using_gp (insn))") 183 ] 184 (const_string "no"))) 185 186;; The CANNOT_COPY attribute marks instructions with relocations that 187;; cannot easily be duplicated. This includes insns with gpdisp relocs 188;; since they have to stay in 1-1 correspondence with one another. This 189;; also includes jsr insns, since they must stay in correspondence with 190;; the immediately following gpdisp instructions. 191 192(define_attr "cannot_copy" "false,true" 193 (const_string "false")) 194 195;; Used to control the "enabled" attribute on a per-instruction basis. 196;; For convenience, conflate ABI issues re loading of addresses with 197;; an "isa". 198(define_attr "isa" "base,bwx,max,fix,cix,vms,ner,er" 199 (const_string "base")) 200 201(define_attr "enabled" "" 202 (cond [(eq_attr "isa" "bwx") (symbol_ref "TARGET_BWX") 203 (eq_attr "isa" "max") (symbol_ref "TARGET_MAX") 204 (eq_attr "isa" "fix") (symbol_ref "TARGET_FIX") 205 (eq_attr "isa" "cix") (symbol_ref "TARGET_CIX") 206 (eq_attr "isa" "vms") (symbol_ref "TARGET_ABI_OPEN_VMS") 207 (eq_attr "isa" "ner") (symbol_ref "!TARGET_EXPLICIT_RELOCS") 208 (eq_attr "isa" "er") (symbol_ref "TARGET_EXPLICIT_RELOCS") 209 ] 210 (const_int 1))) 211 212;; Include scheduling descriptions. 213 214(include "ev4.md") 215(include "ev5.md") 216(include "ev6.md") 217 218 219;; Operand and operator predicates and constraints 220 221(include "predicates.md") 222(include "constraints.md") 223 224 225;; First define the arithmetic insns. Note that the 32-bit forms also 226;; sign-extend. 227 228;; Handle 32-64 bit extension from memory to a floating point register 229;; specially, since this occurs frequently in int->double conversions. 230;; 231;; Note that while we must retain the =f case in the insn for reload's 232;; benefit, it should be eliminated after reload, so we should never emit 233;; code for that case. But we don't reject the possibility. 234 235(define_expand "extendsidi2" 236 [(set (match_operand:DI 0 "register_operand") 237 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand")))]) 238 239(define_insn "*cvtlq" 240 [(set (match_operand:DI 0 "register_operand" "=f") 241 (unspec:DI [(match_operand:SF 1 "reg_or_0_operand" "fG")] 242 UNSPEC_CVTLQ))] 243 "" 244 "cvtlq %1,%0" 245 [(set_attr "type" "fadd")]) 246 247(define_insn "*extendsidi2_1" 248 [(set (match_operand:DI 0 "register_operand" "=r,r,!*f") 249 (sign_extend:DI 250 (match_operand:SI 1 "nonimmediate_operand" "r,m,m")))] 251 "" 252 "@ 253 addl $31,%1,%0 254 ldl %0,%1 255 lds %0,%1\;cvtlq %0,%0" 256 [(set_attr "type" "iadd,ild,fld") 257 (set_attr "length" "*,*,8")]) 258 259(define_split 260 [(set (match_operand:DI 0 "hard_fp_register_operand") 261 (sign_extend:DI (match_operand:SI 1 "memory_operand")))] 262 "reload_completed" 263 [(set (match_dup 2) (match_dup 1)) 264 (set (match_dup 0) (unspec:DI [(match_dup 2)] UNSPEC_CVTLQ))] 265{ 266 operands[1] = adjust_address (operands[1], SFmode, 0); 267 operands[2] = gen_rtx_REG (SFmode, REGNO (operands[0])); 268}) 269 270;; Optimize sign-extension of SImode loads. This shows up in the wake of 271;; reload when converting fp->int. 272 273(define_peephole2 274 [(set (match_operand:SI 0 "hard_int_register_operand") 275 (match_operand:SI 1 "memory_operand")) 276 (set (match_operand:DI 2 "hard_int_register_operand") 277 (sign_extend:DI (match_dup 0)))] 278 "true_regnum (operands[0]) == true_regnum (operands[2]) 279 || peep2_reg_dead_p (2, operands[0])" 280 [(set (match_dup 2) 281 (sign_extend:DI (match_dup 1)))]) 282 283(define_insn "addsi3" 284 [(set (match_operand:SI 0 "register_operand" "=r,r,r,r") 285 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ,rJ,rJ") 286 (match_operand:SI 2 "add_operand" "rI,O,K,L")))] 287 "" 288 "@ 289 addl %r1,%2,%0 290 subl %r1,%n2,%0 291 lda %0,%2(%r1) 292 ldah %0,%h2(%r1)") 293 294(define_split 295 [(set (match_operand:SI 0 "register_operand") 296 (plus:SI (match_operand:SI 1 "register_operand") 297 (match_operand:SI 2 "const_int_operand")))] 298 "! add_operand (operands[2], SImode)" 299 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 3))) 300 (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 4)))] 301{ 302 HOST_WIDE_INT val = INTVAL (operands[2]); 303 HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000); 304 HOST_WIDE_INT rest = val - low; 305 306 operands[3] = GEN_INT (rest); 307 operands[4] = GEN_INT (low); 308}) 309 310(define_insn "*addsi_se" 311 [(set (match_operand:DI 0 "register_operand" "=r,r") 312 (sign_extend:DI 313 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ") 314 (match_operand:SI 2 "sext_add_operand" "rI,O"))))] 315 "" 316 "@ 317 addl %r1,%2,%0 318 subl %r1,%n2,%0") 319 320(define_insn "*addsi_se2" 321 [(set (match_operand:DI 0 "register_operand" "=r,r") 322 (sign_extend:DI 323 (subreg:SI (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ") 324 (match_operand:DI 2 "sext_add_operand" "rI,O")) 325 0)))] 326 "" 327 "@ 328 addl %r1,%2,%0 329 subl %r1,%n2,%0") 330 331(define_split 332 [(set (match_operand:DI 0 "register_operand") 333 (sign_extend:DI 334 (plus:SI (match_operand:SI 1 "reg_not_elim_operand") 335 (match_operand:SI 2 "const_int_operand")))) 336 (clobber (match_operand:SI 3 "reg_not_elim_operand"))] 337 "! sext_add_operand (operands[2], SImode) && INTVAL (operands[2]) > 0 338 && INTVAL (operands[2]) % 4 == 0" 339 [(set (match_dup 3) (match_dup 4)) 340 (set (match_dup 0) (sign_extend:DI (plus:SI (mult:SI (match_dup 3) 341 (match_dup 5)) 342 (match_dup 1))))] 343{ 344 HOST_WIDE_INT val = INTVAL (operands[2]) / 4; 345 int mult = 4; 346 347 if (val % 2 == 0) 348 val /= 2, mult = 8; 349 350 operands[4] = GEN_INT (val); 351 operands[5] = GEN_INT (mult); 352}) 353 354(define_split 355 [(set (match_operand:DI 0 "register_operand") 356 (sign_extend:DI 357 (plus:SI (match_operator:SI 1 "comparison_operator" 358 [(match_operand 2) 359 (match_operand 3)]) 360 (match_operand:SI 4 "add_operand")))) 361 (clobber (match_operand:DI 5 "register_operand"))] 362 "" 363 [(set (match_dup 5) (match_dup 6)) 364 (set (match_dup 0) (sign_extend:DI (plus:SI (match_dup 7) (match_dup 4))))] 365{ 366 operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode, 367 operands[2], operands[3]); 368 operands[7] = gen_lowpart (SImode, operands[5]); 369}) 370 371(define_expand "adddi3" 372 [(set (match_operand:DI 0 "register_operand") 373 (plus:DI (match_operand:DI 1 "register_operand") 374 (match_operand:DI 2 "add_operand")))]) 375 376(define_insn "*adddi_er_lo16_dtp" 377 [(set (match_operand:DI 0 "register_operand" "=r") 378 (lo_sum:DI (match_operand:DI 1 "register_operand" "r") 379 (match_operand:DI 2 "dtp16_symbolic_operand")))] 380 "HAVE_AS_TLS" 381 "lda %0,%2(%1)\t\t!dtprel") 382 383(define_insn "*adddi_er_hi32_dtp" 384 [(set (match_operand:DI 0 "register_operand" "=r") 385 (plus:DI (match_operand:DI 1 "register_operand" "r") 386 (high:DI (match_operand:DI 2 "dtp32_symbolic_operand"))))] 387 "HAVE_AS_TLS" 388 "ldah %0,%2(%1)\t\t!dtprelhi") 389 390(define_insn "*adddi_er_lo32_dtp" 391 [(set (match_operand:DI 0 "register_operand" "=r") 392 (lo_sum:DI (match_operand:DI 1 "register_operand" "r") 393 (match_operand:DI 2 "dtp32_symbolic_operand")))] 394 "HAVE_AS_TLS" 395 "lda %0,%2(%1)\t\t!dtprello") 396 397(define_insn "*adddi_er_lo16_tp" 398 [(set (match_operand:DI 0 "register_operand" "=r") 399 (lo_sum:DI (match_operand:DI 1 "register_operand" "r") 400 (match_operand:DI 2 "tp16_symbolic_operand")))] 401 "HAVE_AS_TLS" 402 "lda %0,%2(%1)\t\t!tprel") 403 404(define_insn "*adddi_er_hi32_tp" 405 [(set (match_operand:DI 0 "register_operand" "=r") 406 (plus:DI (match_operand:DI 1 "register_operand" "r") 407 (high:DI (match_operand:DI 2 "tp32_symbolic_operand"))))] 408 "HAVE_AS_TLS" 409 "ldah %0,%2(%1)\t\t!tprelhi") 410 411(define_insn "*adddi_er_lo32_tp" 412 [(set (match_operand:DI 0 "register_operand" "=r") 413 (lo_sum:DI (match_operand:DI 1 "register_operand" "r") 414 (match_operand:DI 2 "tp32_symbolic_operand")))] 415 "HAVE_AS_TLS" 416 "lda %0,%2(%1)\t\t!tprello") 417 418(define_insn "*adddi_er_high_l" 419 [(set (match_operand:DI 0 "register_operand" "=r") 420 (plus:DI (match_operand:DI 1 "register_operand" "r") 421 (high:DI (match_operand:DI 2 "local_symbolic_operand"))))] 422 "TARGET_EXPLICIT_RELOCS && reload_completed" 423 "ldah %0,%2(%1)\t\t!gprelhigh" 424 [(set_attr "usegp" "yes")]) 425 426(define_split 427 [(set (match_operand:DI 0 "register_operand") 428 (high:DI (match_operand:DI 1 "local_symbolic_operand")))] 429 "TARGET_EXPLICIT_RELOCS && reload_completed" 430 [(set (match_dup 0) 431 (plus:DI (match_dup 2) (high:DI (match_dup 1))))] 432 "operands[2] = pic_offset_table_rtx;") 433 434;; We used to expend quite a lot of effort choosing addq/subq/lda. 435;; With complications like 436;; 437;; The NT stack unwind code can't handle a subq to adjust the stack 438;; (that's a bug, but not one we can do anything about). As of NT4.0 SP3, 439;; the exception handling code will loop if a subq is used and an 440;; exception occurs. 441;; 442;; The 19980616 change to emit prologues as RTL also confused some 443;; versions of GDB, which also interprets prologues. This has been 444;; fixed as of GDB 4.18, but it does not harm to unconditionally 445;; use lda here. 446;; 447;; and the fact that the three insns schedule exactly the same, it's 448;; just not worth the effort. 449 450(define_insn "*adddi_internal" 451 [(set (match_operand:DI 0 "register_operand" "=r,r,r") 452 (plus:DI (match_operand:DI 1 "register_operand" "%r,r,r") 453 (match_operand:DI 2 "add_operand" "r,K,L")))] 454 "" 455 "@ 456 addq %1,%2,%0 457 lda %0,%2(%1) 458 ldah %0,%h2(%1)") 459 460;; ??? Allow large constants when basing off the frame pointer or some 461;; virtual register that may eliminate to the frame pointer. This is 462;; done because register elimination offsets will change the hi/lo split, 463;; and if we split before reload, we will require additional instructions. 464 465(define_insn "*adddi_fp_hack" 466 [(set (match_operand:DI 0 "register_operand" "=r,r,r") 467 (plus:DI (match_operand:DI 1 "reg_no_subreg_operand" "r,r,r") 468 (match_operand:DI 2 "const_int_operand" "K,L,n")))] 469 "NONSTRICT_REG_OK_FP_BASE_P (operands[1]) 470 && INTVAL (operands[2]) >= 0 471 /* This is the largest constant an lda+ldah pair can add, minus 472 an upper bound on the displacement between SP and AP during 473 register elimination. See INITIAL_ELIMINATION_OFFSET. */ 474 && INTVAL (operands[2]) 475 < (0x7fff8000 476 - FIRST_PSEUDO_REGISTER * UNITS_PER_WORD 477 - ALPHA_ROUND(crtl->outgoing_args_size) 478 - (ALPHA_ROUND (get_frame_size () 479 + max_reg_num () * UNITS_PER_WORD 480 + crtl->args.pretend_args_size) 481 - crtl->args.pretend_args_size))" 482 "@ 483 lda %0,%2(%1) 484 ldah %0,%h2(%1) 485 #") 486 487;; Don't do this if we are adjusting SP since we don't want to do it 488;; in two steps. Don't split FP sources for the reason listed above. 489(define_split 490 [(set (match_operand:DI 0 "register_operand") 491 (plus:DI (match_operand:DI 1 "register_operand") 492 (match_operand:DI 2 "const_int_operand")))] 493 "! add_operand (operands[2], DImode) 494 && operands[0] != stack_pointer_rtx 495 && operands[1] != frame_pointer_rtx 496 && operands[1] != arg_pointer_rtx" 497 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 3))) 498 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))] 499{ 500 HOST_WIDE_INT val = INTVAL (operands[2]); 501 HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000); 502 HOST_WIDE_INT rest = val - low; 503 rtx rest_rtx = GEN_INT (rest); 504 505 operands[4] = GEN_INT (low); 506 if (satisfies_constraint_L (rest_rtx)) 507 operands[3] = rest_rtx; 508 else if (can_create_pseudo_p ()) 509 { 510 operands[3] = gen_reg_rtx (DImode); 511 emit_move_insn (operands[3], operands[2]); 512 emit_insn (gen_adddi3 (operands[0], operands[1], operands[3])); 513 DONE; 514 } 515 else 516 FAIL; 517}) 518 519(define_insn "*sadd<modesuffix>" 520 [(set (match_operand:I48MODE 0 "register_operand" "=r,r") 521 (plus:I48MODE 522 (mult:I48MODE (match_operand:I48MODE 1 "reg_not_elim_operand" "r,r") 523 (match_operand:I48MODE 2 "const48_operand" "I,I")) 524 (match_operand:I48MODE 3 "sext_add_operand" "rI,O")))] 525 "" 526 "@ 527 s%2add<modesuffix> %1,%3,%0 528 s%2sub<modesuffix> %1,%n3,%0") 529 530(define_insn "*saddl_se" 531 [(set (match_operand:DI 0 "register_operand" "=r,r") 532 (sign_extend:DI 533 (plus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r,r") 534 (match_operand:SI 2 "const48_operand" "I,I")) 535 (match_operand:SI 3 "sext_add_operand" "rI,O"))))] 536 "" 537 "@ 538 s%2addl %1,%3,%0 539 s%2subl %1,%n3,%0") 540 541(define_split 542 [(set (match_operand:DI 0 "register_operand") 543 (sign_extend:DI 544 (plus:SI (mult:SI (match_operator:SI 1 "comparison_operator" 545 [(match_operand 2) 546 (match_operand 3)]) 547 (match_operand:SI 4 "const48_operand")) 548 (match_operand:SI 5 "sext_add_operand")))) 549 (clobber (match_operand:DI 6 "reg_not_elim_operand"))] 550 "" 551 [(set (match_dup 6) (match_dup 7)) 552 (set (match_dup 0) 553 (sign_extend:DI (plus:SI (mult:SI (match_dup 8) (match_dup 4)) 554 (match_dup 5))))] 555{ 556 operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode, 557 operands[2], operands[3]); 558 operands[8] = gen_lowpart (SImode, operands[6]); 559}) 560 561(define_insn "addv<mode>3" 562 [(set (match_operand:I48MODE 0 "register_operand" "=r,r") 563 (plus:I48MODE (match_operand:I48MODE 1 "reg_or_0_operand" "%rJ,rJ") 564 (match_operand:I48MODE 2 "sext_add_operand" "rI,O"))) 565 (trap_if (ne (plus:<DWI> (sign_extend:<DWI> (match_dup 1)) 566 (sign_extend:<DWI> (match_dup 2))) 567 (sign_extend:<DWI> (plus:I48MODE (match_dup 1) 568 (match_dup 2)))) 569 (const_int 0))] 570 "" 571 "@ 572 add<modesuffix>v %r1,%2,%0 573 sub<modesuffix>v %r1,%n2,%0") 574 575(define_insn "neg<mode>2" 576 [(set (match_operand:I48MODE 0 "register_operand" "=r") 577 (neg:I48MODE (match_operand:I48MODE 1 "reg_or_8bit_operand" "rI")))] 578 "" 579 "sub<modesuffix> $31,%1,%0") 580 581(define_insn "*negsi_se" 582 [(set (match_operand:DI 0 "register_operand" "=r") 583 (sign_extend:DI (neg:SI 584 (match_operand:SI 1 "reg_or_8bit_operand" "rI"))))] 585 "" 586 "subl $31,%1,%0") 587 588(define_insn "negv<mode>2" 589 [(set (match_operand:I48MODE 0 "register_operand" "=r") 590 (neg:I48MODE (match_operand:I48MODE 1 "register_operand" "r"))) 591 (trap_if (ne (neg:<DWI> (sign_extend:<DWI> (match_dup 1))) 592 (sign_extend:<DWI> (neg:I48MODE (match_dup 1)))) 593 (const_int 0))] 594 "" 595 "sub<modesuffix>v $31,%1,%0") 596 597(define_insn "sub<mode>3" 598 [(set (match_operand:I48MODE 0 "register_operand" "=r") 599 (minus:I48MODE (match_operand:I48MODE 1 "reg_or_0_operand" "rJ") 600 (match_operand:I48MODE 2 "reg_or_8bit_operand" "rI")))] 601 "" 602 "sub<modesuffix> %r1,%2,%0") 603 604(define_insn "*subsi_se" 605 [(set (match_operand:DI 0 "register_operand" "=r") 606 (sign_extend:DI 607 (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ") 608 (match_operand:SI 2 "reg_or_8bit_operand" "rI"))))] 609 "" 610 "subl %r1,%2,%0") 611 612(define_insn "*subsi_se2" 613 [(set (match_operand:DI 0 "register_operand" "=r") 614 (sign_extend:DI 615 (subreg:SI (minus:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 616 (match_operand:DI 2 "reg_or_8bit_operand" "rI")) 617 0)))] 618 "" 619 "subl %r1,%2,%0") 620 621(define_insn "*ssub<modesuffix>" 622 [(set (match_operand:I48MODE 0 "register_operand" "=r") 623 (minus:I48MODE 624 (mult:I48MODE (match_operand:I48MODE 1 "reg_not_elim_operand" "r") 625 (match_operand:I48MODE 2 "const48_operand" "I")) 626 (match_operand:I48MODE 3 "reg_or_8bit_operand" "rI")))] 627 "" 628 "s%2sub<modesuffix> %1,%3,%0") 629 630(define_insn "*ssubl_se" 631 [(set (match_operand:DI 0 "register_operand" "=r") 632 (sign_extend:DI 633 (minus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r") 634 (match_operand:SI 2 "const48_operand" "I")) 635 (match_operand:SI 3 "reg_or_8bit_operand" "rI"))))] 636 "" 637 "s%2subl %1,%3,%0") 638 639(define_insn "subv<mode>3" 640 [(set (match_operand:I48MODE 0 "register_operand" "=r") 641 (minus:I48MODE (match_operand:I48MODE 1 "reg_or_0_operand" "rJ") 642 (match_operand:I48MODE 2 "reg_or_8bit_operand" "rI"))) 643 (trap_if (ne (minus:<DWI> (sign_extend:<DWI> (match_dup 1)) 644 (sign_extend:<DWI> (match_dup 2))) 645 (sign_extend:<DWI> (minus:I48MODE (match_dup 1) 646 (match_dup 2)))) 647 (const_int 0))] 648 "" 649 "sub<modesuffix>v %r1,%2,%0") 650 651(define_insn "mul<mode>3" 652 [(set (match_operand:I48MODE 0 "register_operand" "=r") 653 (mult:I48MODE (match_operand:I48MODE 1 "reg_or_0_operand" "%rJ") 654 (match_operand:I48MODE 2 "reg_or_8bit_operand" "rI")))] 655 "" 656 "mul<modesuffix> %r1,%2,%0" 657 [(set_attr "type" "imul") 658 (set_attr "opsize" "<mode>")]) 659 660(define_insn "*mulsi_se" 661 [(set (match_operand:DI 0 "register_operand" "=r") 662 (sign_extend:DI 663 (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ") 664 (match_operand:SI 2 "reg_or_8bit_operand" "rI"))))] 665 "" 666 "mull %r1,%2,%0" 667 [(set_attr "type" "imul") 668 (set_attr "opsize" "si")]) 669 670(define_insn "mulv<mode>3" 671 [(set (match_operand:I48MODE 0 "register_operand" "=r") 672 (mult:I48MODE (match_operand:I48MODE 1 "reg_or_0_operand" "%rJ") 673 (match_operand:I48MODE 2 "reg_or_8bit_operand" "rI"))) 674 (trap_if (ne (mult:<DWI> (sign_extend:<DWI> (match_dup 1)) 675 (sign_extend:<DWI> (match_dup 2))) 676 (sign_extend:<DWI> (mult:I48MODE (match_dup 1) 677 (match_dup 2)))) 678 (const_int 0))] 679 "" 680 "mul<modesuffix>v %r1,%2,%0" 681 [(set_attr "type" "imul") 682 (set_attr "opsize" "<mode>")]) 683 684(define_expand "umuldi3_highpart" 685 [(set (match_operand:DI 0 "register_operand") 686 (truncate:DI 687 (lshiftrt:TI 688 (mult:TI (zero_extend:TI 689 (match_operand:DI 1 "register_operand")) 690 (match_operand:DI 2 "reg_or_8bit_operand")) 691 (const_int 64))))] 692 "" 693{ 694 if (REG_P (operands[2])) 695 operands[2] = gen_rtx_ZERO_EXTEND (TImode, operands[2]); 696}) 697 698(define_insn "*umuldi3_highpart_reg" 699 [(set (match_operand:DI 0 "register_operand" "=r") 700 (truncate:DI 701 (lshiftrt:TI 702 (mult:TI (zero_extend:TI 703 (match_operand:DI 1 "register_operand" "r")) 704 (zero_extend:TI 705 (match_operand:DI 2 "register_operand" "r"))) 706 (const_int 64))))] 707 "" 708 "umulh %1,%2,%0" 709 [(set_attr "type" "imul") 710 (set_attr "opsize" "udi")]) 711 712(define_insn "*umuldi3_highpart_const" 713 [(set (match_operand:DI 0 "register_operand" "=r") 714 (truncate:DI 715 (lshiftrt:TI 716 (mult:TI (zero_extend:TI (match_operand:DI 1 "register_operand" "r")) 717 (match_operand:TI 2 "cint8_operand" "I")) 718 (const_int 64))))] 719 "" 720 "umulh %1,%2,%0" 721 [(set_attr "type" "imul") 722 (set_attr "opsize" "udi")]) 723 724(define_expand "umulditi3" 725 [(set (match_operand:TI 0 "register_operand") 726 (mult:TI 727 (zero_extend:TI (match_operand:DI 1 "reg_no_subreg_operand")) 728 (zero_extend:TI (match_operand:DI 2 "reg_no_subreg_operand"))))] 729 "" 730{ 731 rtx l = gen_reg_rtx (DImode), h = gen_reg_rtx (DImode); 732 emit_insn (gen_muldi3 (l, operands[1], operands[2])); 733 emit_insn (gen_umuldi3_highpart (h, operands[1], operands[2])); 734 emit_move_insn (gen_lowpart (DImode, operands[0]), l); 735 emit_move_insn (gen_highpart (DImode, operands[0]), h); 736 DONE; 737}) 738 739;; The divide and remainder operations take their inputs from r24 and 740;; r25, put their output in r27, and clobber r23 and r28 on all systems. 741;; 742;; ??? Force sign-extension here because some versions of OSF/1 and 743;; Interix/NT don't do the right thing if the inputs are not properly 744;; sign-extended. But Linux, for instance, does not have this 745;; problem. Is it worth the complication here to eliminate the sign 746;; extension? 747 748(define_code_iterator any_divmod [div mod udiv umod]) 749 750(define_expand "<code>si3" 751 [(set (match_dup 3) 752 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"))) 753 (set (match_dup 4) 754 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand"))) 755 (parallel [(set (match_dup 5) 756 (sign_extend:DI 757 (any_divmod:SI (match_dup 3) (match_dup 4)))) 758 (clobber (reg:DI 23)) 759 (clobber (reg:DI 28))]) 760 (set (match_operand:SI 0 "nonimmediate_operand") 761 (subreg:SI (match_dup 5) 0))] 762 "TARGET_ABI_OSF" 763{ 764 operands[3] = gen_reg_rtx (DImode); 765 operands[4] = gen_reg_rtx (DImode); 766 operands[5] = gen_reg_rtx (DImode); 767}) 768 769(define_expand "<code>di3" 770 [(parallel [(set (match_operand:DI 0 "register_operand") 771 (any_divmod:DI 772 (match_operand:DI 1 "register_operand") 773 (match_operand:DI 2 "register_operand"))) 774 (clobber (reg:DI 23)) 775 (clobber (reg:DI 28))])] 776 "TARGET_ABI_OSF") 777 778;; Lengths of 8 for ldq $t12,__divq($gp); jsr $t9,($t12),__divq as 779;; expanded by the assembler. 780 781(define_insn_and_split "*divmodsi_internal_er" 782 [(set (match_operand:DI 0 "register_operand" "=c") 783 (sign_extend:DI (match_operator:SI 3 "divmod_operator" 784 [(match_operand:DI 1 "register_operand" "a") 785 (match_operand:DI 2 "register_operand" "b")]))) 786 (clobber (reg:DI 23)) 787 (clobber (reg:DI 28))] 788 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 789 "#" 790 "&& reload_completed" 791 [(parallel [(set (match_dup 0) 792 (sign_extend:DI (match_dup 3))) 793 (use (match_dup 0)) 794 (use (match_dup 4)) 795 (clobber (reg:DI 23)) 796 (clobber (reg:DI 28))])] 797{ 798 const char *str; 799 switch (GET_CODE (operands[3])) 800 { 801 case DIV: 802 str = "__divl"; 803 break; 804 case UDIV: 805 str = "__divlu"; 806 break; 807 case MOD: 808 str = "__reml"; 809 break; 810 case UMOD: 811 str = "__remlu"; 812 break; 813 default: 814 gcc_unreachable (); 815 } 816 operands[4] = GEN_INT (alpha_next_sequence_number++); 817 emit_insn (gen_movdi_er_high_g (operands[0], pic_offset_table_rtx, 818 gen_rtx_SYMBOL_REF (DImode, str), 819 operands[4])); 820} 821 [(set_attr "type" "jsr") 822 (set_attr "length" "8")]) 823 824(define_insn "*divmodsi_internal_er_1" 825 [(set (match_operand:DI 0 "register_operand" "=c") 826 (sign_extend:DI (match_operator:SI 3 "divmod_operator" 827 [(match_operand:DI 1 "register_operand" "a") 828 (match_operand:DI 2 "register_operand" "b")]))) 829 (use (match_operand:DI 4 "register_operand" "c")) 830 (use (match_operand 5 "const_int_operand")) 831 (clobber (reg:DI 23)) 832 (clobber (reg:DI 28))] 833 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 834 "jsr $23,($27),__%E3%j5" 835 [(set_attr "type" "jsr") 836 (set_attr "length" "4")]) 837 838(define_insn "*divmodsi_internal" 839 [(set (match_operand:DI 0 "register_operand" "=c") 840 (sign_extend:DI (match_operator:SI 3 "divmod_operator" 841 [(match_operand:DI 1 "register_operand" "a") 842 (match_operand:DI 2 "register_operand" "b")]))) 843 (clobber (reg:DI 23)) 844 (clobber (reg:DI 28))] 845 "TARGET_ABI_OSF" 846 "%E3 %1,%2,%0" 847 [(set_attr "type" "jsr") 848 (set_attr "length" "8")]) 849 850(define_insn_and_split "*divmoddi_internal_er" 851 [(set (match_operand:DI 0 "register_operand" "=c") 852 (match_operator:DI 3 "divmod_operator" 853 [(match_operand:DI 1 "register_operand" "a") 854 (match_operand:DI 2 "register_operand" "b")])) 855 (clobber (reg:DI 23)) 856 (clobber (reg:DI 28))] 857 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 858 "#" 859 "&& reload_completed" 860 [(parallel [(set (match_dup 0) (match_dup 3)) 861 (use (match_dup 0)) 862 (use (match_dup 4)) 863 (clobber (reg:DI 23)) 864 (clobber (reg:DI 28))])] 865{ 866 const char *str; 867 switch (GET_CODE (operands[3])) 868 { 869 case DIV: 870 str = "__divq"; 871 break; 872 case UDIV: 873 str = "__divqu"; 874 break; 875 case MOD: 876 str = "__remq"; 877 break; 878 case UMOD: 879 str = "__remqu"; 880 break; 881 default: 882 gcc_unreachable (); 883 } 884 operands[4] = GEN_INT (alpha_next_sequence_number++); 885 emit_insn (gen_movdi_er_high_g (operands[0], pic_offset_table_rtx, 886 gen_rtx_SYMBOL_REF (DImode, str), 887 operands[4])); 888} 889 [(set_attr "type" "jsr") 890 (set_attr "length" "8")]) 891 892(define_insn "*divmoddi_internal_er_1" 893 [(set (match_operand:DI 0 "register_operand" "=c") 894 (match_operator:DI 3 "divmod_operator" 895 [(match_operand:DI 1 "register_operand" "a") 896 (match_operand:DI 2 "register_operand" "b")])) 897 (use (match_operand:DI 4 "register_operand" "c")) 898 (use (match_operand 5 "const_int_operand")) 899 (clobber (reg:DI 23)) 900 (clobber (reg:DI 28))] 901 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 902 "jsr $23,($27),__%E3%j5" 903 [(set_attr "type" "jsr") 904 (set_attr "length" "4")]) 905 906(define_insn "*divmoddi_internal" 907 [(set (match_operand:DI 0 "register_operand" "=c") 908 (match_operator:DI 3 "divmod_operator" 909 [(match_operand:DI 1 "register_operand" "a") 910 (match_operand:DI 2 "register_operand" "b")])) 911 (clobber (reg:DI 23)) 912 (clobber (reg:DI 28))] 913 "TARGET_ABI_OSF" 914 "%E3 %1,%2,%0" 915 [(set_attr "type" "jsr") 916 (set_attr "length" "8")]) 917 918;; Next are the basic logical operations. We only expose the DImode operations 919;; to the rtl expanders, but SImode versions exist for combine as well as for 920;; the atomic operation splitters. 921 922(define_insn "*andsi_internal" 923 [(set (match_operand:SI 0 "register_operand" "=r,r,r") 924 (and:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ,rJ") 925 (match_operand:SI 2 "and_operand" "rI,N,M")))] 926 "" 927 "@ 928 and %r1,%2,%0 929 bic %r1,%N2,%0 930 zapnot %r1,%m2,%0" 931 [(set_attr "type" "ilog,ilog,shift")]) 932 933(define_insn "anddi3" 934 [(set (match_operand:DI 0 "register_operand" "=r,r,r") 935 (and:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ,rJ") 936 (match_operand:DI 2 "and_operand" "rI,N,M")))] 937 "" 938 "@ 939 and %r1,%2,%0 940 bic %r1,%N2,%0 941 zapnot %r1,%m2,%0" 942 [(set_attr "type" "ilog,ilog,shift")]) 943 944;; There are times when we can split an AND into two AND insns. This occurs 945;; when we can first clear any bytes and then clear anything else. For 946;; example "I & 0xffff07" is "(I & 0xffffff) & 0xffffffffffffff07". 947;; Only do this when running on 64-bit host since the computations are 948;; too messy otherwise. 949 950(define_split 951 [(set (match_operand:DI 0 "register_operand") 952 (and:DI (match_operand:DI 1 "register_operand") 953 (match_operand:DI 2 "const_int_operand")))] 954 "! and_operand (operands[2], DImode)" 955 [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 3))) 956 (set (match_dup 0) (and:DI (match_dup 0) (match_dup 4)))] 957{ 958 unsigned HOST_WIDE_INT mask1 = INTVAL (operands[2]); 959 unsigned HOST_WIDE_INT mask2 = mask1; 960 int i; 961 962 /* For each byte that isn't all zeros, make it all ones. */ 963 for (i = 0; i < 64; i += 8) 964 if ((mask1 & ((HOST_WIDE_INT) 0xff << i)) != 0) 965 mask1 |= (HOST_WIDE_INT) 0xff << i; 966 967 /* Now turn on any bits we've just turned off. */ 968 mask2 |= ~ mask1; 969 970 operands[3] = GEN_INT (mask1); 971 operands[4] = GEN_INT (mask2); 972}) 973 974(define_insn "zero_extendqi<mode>2" 975 [(set (match_operand:I248MODE 0 "register_operand" "=r,r") 976 (zero_extend:I248MODE 977 (match_operand:QI 1 "reg_or_bwx_memory_operand" "r,m")))] 978 "" 979 "@ 980 and %1,0xff,%0 981 ldbu %0,%1" 982 [(set_attr "type" "ilog,ild") 983 (set_attr "isa" "*,bwx")]) 984 985(define_insn "zero_extendhi<mode>2" 986 [(set (match_operand:I48MODE 0 "register_operand" "=r,r") 987 (zero_extend:I48MODE 988 (match_operand:HI 1 "reg_or_bwx_memory_operand" "r,m")))] 989 "" 990 "@ 991 zapnot %1,3,%0 992 ldwu %0,%1" 993 [(set_attr "type" "shift,ild") 994 (set_attr "isa" "*,bwx")]) 995 996(define_insn "zero_extendsidi2" 997 [(set (match_operand:DI 0 "register_operand" "=r") 998 (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))] 999 "" 1000 "zapnot %1,15,%0" 1001 [(set_attr "type" "shift")]) 1002 1003(define_insn "andnot<mode>3" 1004 [(set (match_operand:I48MODE 0 "register_operand" "=r") 1005 (and:I48MODE 1006 (not:I48MODE (match_operand:I48MODE 1 "reg_or_8bit_operand" "rI")) 1007 (match_operand:I48MODE 2 "reg_or_0_operand" "rJ")))] 1008 "" 1009 "bic %r2,%1,%0" 1010 [(set_attr "type" "ilog")]) 1011 1012(define_insn "*iorsi_internal" 1013 [(set (match_operand:SI 0 "register_operand" "=r,r") 1014 (ior:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ") 1015 (match_operand:SI 2 "or_operand" "rI,N")))] 1016 "" 1017 "@ 1018 bis %r1,%2,%0 1019 ornot %r1,%N2,%0" 1020 [(set_attr "type" "ilog")]) 1021 1022(define_insn "iordi3" 1023 [(set (match_operand:DI 0 "register_operand" "=r,r") 1024 (ior:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ") 1025 (match_operand:DI 2 "or_operand" "rI,N")))] 1026 "" 1027 "@ 1028 bis %r1,%2,%0 1029 ornot %r1,%N2,%0" 1030 [(set_attr "type" "ilog")]) 1031 1032(define_insn "*one_cmplsi_internal" 1033 [(set (match_operand:SI 0 "register_operand" "=r") 1034 (not:SI (match_operand:SI 1 "reg_or_8bit_operand" "rI")))] 1035 "" 1036 "ornot $31,%1,%0" 1037 [(set_attr "type" "ilog")]) 1038 1039(define_insn "one_cmpldi2" 1040 [(set (match_operand:DI 0 "register_operand" "=r") 1041 (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI")))] 1042 "" 1043 "ornot $31,%1,%0" 1044 [(set_attr "type" "ilog")]) 1045 1046(define_insn "*iornot<mode>3" 1047 [(set (match_operand:I48MODE 0 "register_operand" "=r") 1048 (ior:I48MODE 1049 (not:I48MODE (match_operand:I48MODE 1 "reg_or_8bit_operand" "rI")) 1050 (match_operand:I48MODE 2 "reg_or_0_operand" "rJ")))] 1051 "" 1052 "ornot %r2,%1,%0" 1053 [(set_attr "type" "ilog")]) 1054 1055(define_insn "*xorsi_internal" 1056 [(set (match_operand:SI 0 "register_operand" "=r,r") 1057 (xor:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ") 1058 (match_operand:SI 2 "or_operand" "rI,N")))] 1059 "" 1060 "@ 1061 xor %r1,%2,%0 1062 eqv %r1,%N2,%0" 1063 [(set_attr "type" "ilog")]) 1064 1065(define_insn "xordi3" 1066 [(set (match_operand:DI 0 "register_operand" "=r,r") 1067 (xor:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ") 1068 (match_operand:DI 2 "or_operand" "rI,N")))] 1069 "" 1070 "@ 1071 xor %r1,%2,%0 1072 eqv %r1,%N2,%0" 1073 [(set_attr "type" "ilog")]) 1074 1075(define_insn "*xornot<mode>3" 1076 [(set (match_operand:I48MODE 0 "register_operand" "=r") 1077 (not:I48MODE (xor:I48MODE 1078 (match_operand:I48MODE 1 "register_operand" "%rJ") 1079 (match_operand:I48MODE 2 "register_operand" "rI"))))] 1080 "" 1081 "eqv %r1,%2,%0" 1082 [(set_attr "type" "ilog")]) 1083 1084;; Handle FFS and related insns iff we support CIX. 1085 1086(define_expand "ffsdi2" 1087 [(set (match_dup 2) 1088 (ctz:DI (match_operand:DI 1 "register_operand"))) 1089 (set (match_dup 3) 1090 (plus:DI (match_dup 2) (const_int 1))) 1091 (set (match_operand:DI 0 "register_operand") 1092 (if_then_else:DI (eq (match_dup 1) (const_int 0)) 1093 (const_int 0) (match_dup 3)))] 1094 "TARGET_CIX" 1095{ 1096 operands[2] = gen_reg_rtx (DImode); 1097 operands[3] = gen_reg_rtx (DImode); 1098}) 1099 1100(define_insn "clzdi2" 1101 [(set (match_operand:DI 0 "register_operand" "=r") 1102 (clz:DI (match_operand:DI 1 "register_operand" "r")))] 1103 "TARGET_CIX" 1104 "ctlz %1,%0" 1105 [(set_attr "type" "mvi")]) 1106 1107(define_insn "ctzdi2" 1108 [(set (match_operand:DI 0 "register_operand" "=r") 1109 (ctz:DI (match_operand:DI 1 "register_operand" "r")))] 1110 "TARGET_CIX" 1111 "cttz %1,%0" 1112 [(set_attr "type" "mvi")]) 1113 1114(define_insn "popcountdi2" 1115 [(set (match_operand:DI 0 "register_operand" "=r") 1116 (popcount:DI (match_operand:DI 1 "register_operand" "r")))] 1117 "TARGET_CIX" 1118 "ctpop %1,%0" 1119 [(set_attr "type" "mvi")]) 1120 1121(define_expand "bswapsi2" 1122 [(set (match_operand:SI 0 "register_operand") 1123 (bswap:SI (match_operand:SI 1 "register_operand")))] 1124 "!optimize_size" 1125{ 1126 rtx t0, t1; 1127 1128 t0 = gen_reg_rtx (DImode); 1129 t1 = gen_reg_rtx (DImode); 1130 1131 emit_insn (gen_inslh (t0, gen_lowpart (DImode, operands[1]), GEN_INT (7))); 1132 emit_insn (gen_inswl_const (t1, gen_lowpart (HImode, operands[1]), 1133 GEN_INT (24))); 1134 emit_insn (gen_iordi3 (t1, t0, t1)); 1135 emit_insn (gen_lshrdi3 (t0, t1, GEN_INT (16))); 1136 emit_insn (gen_anddi3 (t1, t1, alpha_expand_zap_mask (0x5))); 1137 emit_insn (gen_anddi3 (t0, t0, alpha_expand_zap_mask (0xa))); 1138 emit_insn (gen_addsi3 (operands[0], gen_lowpart (SImode, t0), 1139 gen_lowpart (SImode, t1))); 1140 DONE; 1141}) 1142 1143(define_expand "bswapdi2" 1144 [(set (match_operand:DI 0 "register_operand") 1145 (bswap:DI (match_operand:DI 1 "register_operand")))] 1146 "!optimize_size" 1147{ 1148 rtx t0, t1; 1149 1150 t0 = gen_reg_rtx (DImode); 1151 t1 = gen_reg_rtx (DImode); 1152 1153 /* This method of shifting and masking is not specific to Alpha, but 1154 is only profitable on Alpha because of our handy byte zap insn. */ 1155 1156 emit_insn (gen_lshrdi3 (t0, operands[1], GEN_INT (32))); 1157 emit_insn (gen_ashldi3 (t1, operands[1], GEN_INT (32))); 1158 emit_insn (gen_iordi3 (t1, t0, t1)); 1159 1160 emit_insn (gen_lshrdi3 (t0, t1, GEN_INT (16))); 1161 emit_insn (gen_ashldi3 (t1, t1, GEN_INT (16))); 1162 emit_insn (gen_anddi3 (t0, t0, alpha_expand_zap_mask (0xcc))); 1163 emit_insn (gen_anddi3 (t1, t1, alpha_expand_zap_mask (0x33))); 1164 emit_insn (gen_iordi3 (t1, t0, t1)); 1165 1166 emit_insn (gen_lshrdi3 (t0, t1, GEN_INT (8))); 1167 emit_insn (gen_ashldi3 (t1, t1, GEN_INT (8))); 1168 emit_insn (gen_anddi3 (t0, t0, alpha_expand_zap_mask (0xaa))); 1169 emit_insn (gen_anddi3 (t1, t1, alpha_expand_zap_mask (0x55))); 1170 emit_insn (gen_iordi3 (operands[0], t0, t1)); 1171 DONE; 1172}) 1173 1174;; Next come the shifts and the various extract and insert operations. 1175 1176(define_insn "ashldi3" 1177 [(set (match_operand:DI 0 "register_operand" "=r,r") 1178 (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ,rJ") 1179 (match_operand:DI 2 "reg_or_6bit_operand" "P,rS")))] 1180 "" 1181{ 1182 switch (which_alternative) 1183 { 1184 case 0: 1185 if (operands[2] == const1_rtx) 1186 return "addq %r1,%r1,%0"; 1187 else 1188 return "s%P2addq %r1,0,%0"; 1189 case 1: 1190 return "sll %r1,%2,%0"; 1191 default: 1192 gcc_unreachable (); 1193 } 1194} 1195 [(set_attr "type" "iadd,shift")]) 1196 1197(define_insn "*ashldi_se" 1198 [(set (match_operand:DI 0 "register_operand" "=r") 1199 (sign_extend:DI 1200 (subreg:SI (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1201 (match_operand:DI 2 "const_int_operand" "P")) 1202 0)))] 1203 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 3" 1204{ 1205 if (operands[2] == const1_rtx) 1206 return "addl %r1,%r1,%0"; 1207 else 1208 return "s%P2addl %r1,0,%0"; 1209} 1210 [(set_attr "type" "iadd")]) 1211 1212(define_insn "lshrdi3" 1213 [(set (match_operand:DI 0 "register_operand" "=r") 1214 (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1215 (match_operand:DI 2 "reg_or_6bit_operand" "rS")))] 1216 "" 1217 "srl %r1,%2,%0" 1218 [(set_attr "type" "shift")]) 1219 1220(define_insn "ashrdi3" 1221 [(set (match_operand:DI 0 "register_operand" "=r") 1222 (ashiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1223 (match_operand:DI 2 "reg_or_6bit_operand" "rS")))] 1224 "" 1225 "sra %r1,%2,%0" 1226 [(set_attr "type" "shift")]) 1227 1228(define_insn "extendqi<mode>2" 1229 [(set (match_operand:I24MODE 0 "register_operand" "=r") 1230 (sign_extend:I24MODE 1231 (match_operand:QI 1 "register_operand" "r")))] 1232 "TARGET_BWX" 1233 "sextb %1,%0" 1234 [(set_attr "type" "shift")]) 1235 1236(define_expand "extendqidi2" 1237 [(set (match_operand:DI 0 "register_operand") 1238 (sign_extend:DI (match_operand:QI 1 "general_operand")))] 1239 "" 1240{ 1241 if (TARGET_BWX) 1242 operands[1] = force_reg (QImode, operands[1]); 1243 else 1244 { 1245 rtx x, t1, t2, i56; 1246 1247 if (unaligned_memory_operand (operands[1], QImode)) 1248 { 1249 x = gen_unaligned_extendqidi (operands[0], XEXP (operands[1], 0)); 1250 alpha_set_memflags (x, operands[1]); 1251 emit_insn (x); 1252 DONE; 1253 } 1254 1255 t1 = gen_reg_rtx (DImode); 1256 t2 = gen_reg_rtx (DImode); 1257 i56 = GEN_INT (56); 1258 1259 x = gen_lowpart (DImode, force_reg (QImode, operands[1])); 1260 emit_move_insn (t1, x); 1261 emit_insn (gen_ashldi3 (t2, t1, i56)); 1262 emit_insn (gen_ashrdi3 (operands[0], t2, i56)); 1263 DONE; 1264 } 1265}) 1266 1267(define_insn "*extendqidi2_bwx" 1268 [(set (match_operand:DI 0 "register_operand" "=r") 1269 (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))] 1270 "TARGET_BWX" 1271 "sextb %1,%0" 1272 [(set_attr "type" "shift")]) 1273 1274(define_insn "extendhisi2" 1275 [(set (match_operand:SI 0 "register_operand" "=r") 1276 (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))] 1277 "TARGET_BWX" 1278 "sextw %1,%0" 1279 [(set_attr "type" "shift")]) 1280 1281(define_expand "extendhidi2" 1282 [(set (match_operand:DI 0 "register_operand") 1283 (sign_extend:DI (match_operand:HI 1 "general_operand")))] 1284 "" 1285{ 1286 if (TARGET_BWX) 1287 operands[1] = force_reg (HImode, operands[1]); 1288 else 1289 { 1290 rtx x, t1, t2, i48; 1291 1292 if (unaligned_memory_operand (operands[1], HImode)) 1293 { 1294 x = gen_unaligned_extendhidi (operands[0], XEXP (operands[1], 0)); 1295 alpha_set_memflags (x, operands[1]); 1296 emit_insn (x); 1297 DONE; 1298 } 1299 1300 t1 = gen_reg_rtx (DImode); 1301 t2 = gen_reg_rtx (DImode); 1302 i48 = GEN_INT (48); 1303 1304 x = gen_lowpart (DImode, force_reg (HImode, operands[1])); 1305 emit_move_insn (t1, x); 1306 emit_insn (gen_ashldi3 (t2, t1, i48)); 1307 emit_insn (gen_ashrdi3 (operands[0], t2, i48)); 1308 DONE; 1309 } 1310}) 1311 1312(define_insn "*extendhidi2_bwx" 1313 [(set (match_operand:DI 0 "register_operand" "=r") 1314 (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))] 1315 "TARGET_BWX" 1316 "sextw %1,%0" 1317 [(set_attr "type" "shift")]) 1318 1319;; Here's how we sign extend an unaligned byte and halfword. Doing this 1320;; as a pattern saves one instruction. The code is similar to that for 1321;; the unaligned loads (see below). 1322;; 1323;; Operand 1 is the address, operand 0 is the result. 1324 1325(define_expand "unaligned_extendqidi" 1326 [(set (match_dup 3) 1327 (mem:DI (and:DI (match_operand:DI 1 "address_operand") (const_int -8)))) 1328 (set (match_dup 4) 1329 (ashift:DI (match_dup 3) 1330 (minus:DI (const_int 64) 1331 (ashift:DI 1332 (and:DI (match_dup 2) (const_int 7)) 1333 (const_int 3))))) 1334 (set (match_operand:QI 0 "register_operand") 1335 (ashiftrt:DI (match_dup 4) (const_int 56)))] 1336 "" 1337{ 1338 operands[0] = gen_lowpart (DImode, operands[0]); 1339 operands[2] = get_unaligned_offset (operands[1], 1); 1340 operands[3] = gen_reg_rtx (DImode); 1341 operands[4] = gen_reg_rtx (DImode); 1342}) 1343 1344(define_expand "unaligned_extendhidi" 1345 [(set (match_dup 3) 1346 (mem:DI (and:DI (match_operand:DI 1 "address_operand") (const_int -8)))) 1347 (set (match_dup 4) 1348 (ashift:DI (match_dup 3) 1349 (minus:DI (const_int 64) 1350 (ashift:DI 1351 (and:DI (match_dup 2) (const_int 7)) 1352 (const_int 3))))) 1353 (set (match_operand:HI 0 "register_operand") 1354 (ashiftrt:DI (match_dup 4) (const_int 48)))] 1355 "" 1356{ 1357 operands[0] = gen_lowpart (DImode, operands[0]); 1358 operands[2] = get_unaligned_offset (operands[1], 2); 1359 operands[3] = gen_reg_rtx (DImode); 1360 operands[4] = gen_reg_rtx (DImode); 1361}) 1362 1363(define_insn "*extxl_const" 1364 [(set (match_operand:DI 0 "register_operand" "=r") 1365 (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1366 (match_operand:DI 2 "mode_width_operand" "n") 1367 (match_operand:DI 3 "mul8_operand" "I")))] 1368 "" 1369 "ext%M2l %r1,%s3,%0" 1370 [(set_attr "type" "shift")]) 1371 1372(define_insn "extxl" 1373 [(set (match_operand:DI 0 "register_operand" "=r") 1374 (zero_extract:DI 1375 (match_operand:DI 1 "reg_or_0_operand" "rJ") 1376 (match_operand:DI 2 "mode_width_operand" "n") 1377 (ashift:DI (match_operand:DI 3 "reg_or_8bit_operand" "rI") 1378 (const_int 3))))] 1379 "" 1380 "ext%M2l %r1,%3,%0" 1381 [(set_attr "type" "shift")]) 1382 1383;; Combine has some strange notion of preserving existing undefined behavior 1384;; in shifts larger than a word size. So capture these patterns that it 1385;; should have turned into zero_extracts. 1386 1387(define_insn "*extxl_1" 1388 [(set (match_operand:DI 0 "register_operand" "=r") 1389 (and:DI (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1390 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1391 (const_int 3))) 1392 (match_operand:DI 3 "mode_mask_operand" "n")))] 1393 "" 1394 "ext%U3l %1,%2,%0" 1395 [(set_attr "type" "shift")]) 1396 1397(define_insn "*extql_2" 1398 [(set (match_operand:DI 0 "register_operand" "=r") 1399 (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1400 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1401 (const_int 3))))] 1402 "" 1403 "extql %1,%2,%0" 1404 [(set_attr "type" "shift")]) 1405 1406(define_insn "extqh" 1407 [(set (match_operand:DI 0 "register_operand" "=r") 1408 (ashift:DI 1409 (match_operand:DI 1 "reg_or_0_operand" "rJ") 1410 (minus:DI (const_int 64) 1411 (ashift:DI 1412 (and:DI 1413 (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1414 (const_int 7)) 1415 (const_int 3)))))] 1416 "" 1417 "extqh %r1,%2,%0" 1418 [(set_attr "type" "shift")]) 1419 1420(define_insn "extwh" 1421 [(set (match_operand:DI 0 "register_operand" "=r") 1422 (ashift:DI 1423 (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1424 (const_int 65535)) 1425 (minus:DI (const_int 64) 1426 (ashift:DI 1427 (and:DI 1428 (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1429 (const_int 7)) 1430 (const_int 3)))))] 1431 "" 1432 "extwh %r1,%2,%0" 1433 [(set_attr "type" "shift")]) 1434 1435(define_insn "extlh" 1436 [(set (match_operand:DI 0 "register_operand" "=r") 1437 (ashift:DI 1438 (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1439 (const_int 2147483647)) 1440 (minus:DI (const_int 64) 1441 (ashift:DI 1442 (and:DI 1443 (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1444 (const_int 7)) 1445 (const_int 3)))))] 1446 "" 1447 "extlh %r1,%2,%0" 1448 [(set_attr "type" "shift")]) 1449 1450;; This converts an extXl into an extXh with an appropriate adjustment 1451;; to the address calculation. 1452 1453;;(define_split 1454;; [(set (match_operand:DI 0 "register_operand") 1455;; (ashift:DI (zero_extract:DI (match_operand:DI 1 "register_operand") 1456;; (match_operand:DI 2 "mode_width_operand") 1457;; (ashift:DI (match_operand:DI 3) 1458;; (const_int 3))) 1459;; (match_operand:DI 4 "const_int_operand"))) 1460;; (clobber (match_operand:DI 5 "register_operand"))] 1461;; "INTVAL (operands[4]) == 64 - INTVAL (operands[2])" 1462;; [(set (match_dup 5) (match_dup 6)) 1463;; (set (match_dup 0) 1464;; (ashift:DI (zero_extract:DI (match_dup 1) (match_dup 2) 1465;; (ashift:DI (plus:DI (match_dup 5) 1466;; (match_dup 7)) 1467;; (const_int 3))) 1468;; (match_dup 4)))] 1469;; " 1470;;{ 1471;; operands[6] = plus_constant (DImode, operands[3], 1472;; INTVAL (operands[2]) / BITS_PER_UNIT); 1473;; operands[7] = GEN_INT (- INTVAL (operands[2]) / BITS_PER_UNIT); 1474;;}") 1475 1476(define_insn "ins<modesuffix>l_const" 1477 [(set (match_operand:DI 0 "register_operand" "=r") 1478 (ashift:DI (zero_extend:DI 1479 (match_operand:I124MODE 1 "register_operand" "r")) 1480 (match_operand:DI 2 "mul8_operand" "I")))] 1481 "" 1482 "ins<modesuffix>l %1,%s2,%0" 1483 [(set_attr "type" "shift")]) 1484 1485(define_insn "ins<modesuffix>l" 1486 [(set (match_operand:DI 0 "register_operand" "=r") 1487 (ashift:DI (zero_extend:DI 1488 (match_operand:I124MODE 1 "register_operand" "r")) 1489 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1490 (const_int 3))))] 1491 "" 1492 "ins<modesuffix>l %1,%2,%0" 1493 [(set_attr "type" "shift")]) 1494 1495(define_insn "insql" 1496 [(set (match_operand:DI 0 "register_operand" "=r") 1497 (ashift:DI (match_operand:DI 1 "register_operand" "r") 1498 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI") 1499 (const_int 3))))] 1500 "" 1501 "insql %1,%2,%0" 1502 [(set_attr "type" "shift")]) 1503 1504;; Combine has this sometimes habit of moving the and outside of the 1505;; shift, making life more interesting. 1506 1507(define_insn "*insxl" 1508 [(set (match_operand:DI 0 "register_operand" "=r") 1509 (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r") 1510 (match_operand:DI 2 "mul8_operand" "I")) 1511 (match_operand:DI 3 "const_int_operand" "i")))] 1512 "((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2]) 1513 == (unsigned HOST_WIDE_INT) INTVAL (operands[3])) 1514 || ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2]) 1515 == (unsigned HOST_WIDE_INT) INTVAL (operands[3])) 1516 || ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2]) 1517 == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))" 1518{ 1519 if ((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2]) 1520 == (unsigned HOST_WIDE_INT) INTVAL (operands[3])) 1521 return "insbl %1,%s2,%0"; 1522 if ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2]) 1523 == (unsigned HOST_WIDE_INT) INTVAL (operands[3])) 1524 return "inswl %1,%s2,%0"; 1525 if ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2]) 1526 == (unsigned HOST_WIDE_INT) INTVAL (operands[3])) 1527 return "insll %1,%s2,%0"; 1528 1529 gcc_unreachable (); 1530} 1531 [(set_attr "type" "shift")]) 1532 1533;; We do not include the insXh insns because they are complex to express 1534;; and it does not appear that we would ever want to generate them. 1535;; 1536;; Since we need them for block moves, though, cop out and use unspec. 1537 1538(define_insn "insxh" 1539 [(set (match_operand:DI 0 "register_operand" "=r") 1540 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 1541 (match_operand:DI 2 "mode_width_operand" "n") 1542 (match_operand:DI 3 "reg_or_8bit_operand" "rI")] 1543 UNSPEC_INSXH))] 1544 "" 1545 "ins%M2h %1,%3,%0" 1546 [(set_attr "type" "shift")]) 1547 1548(define_insn "mskxl" 1549 [(set (match_operand:DI 0 "register_operand" "=r") 1550 (and:DI (not:DI (ashift:DI 1551 (match_operand:DI 2 "mode_mask_operand" "n") 1552 (ashift:DI 1553 (match_operand:DI 3 "reg_or_8bit_operand" "rI") 1554 (const_int 3)))) 1555 (match_operand:DI 1 "reg_or_0_operand" "rJ")))] 1556 "" 1557 "msk%U2l %r1,%3,%0" 1558 [(set_attr "type" "shift")]) 1559 1560;; We do not include the mskXh insns because it does not appear we would 1561;; ever generate one. 1562;; 1563;; Again, we do for block moves and we use unspec again. 1564 1565(define_insn "mskxh" 1566 [(set (match_operand:DI 0 "register_operand" "=r") 1567 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 1568 (match_operand:DI 2 "mode_width_operand" "n") 1569 (match_operand:DI 3 "reg_or_8bit_operand" "rI")] 1570 UNSPEC_MSKXH))] 1571 "" 1572 "msk%M2h %1,%3,%0" 1573 [(set_attr "type" "shift")]) 1574 1575;; Prefer AND + NE over LSHIFTRT + AND. 1576 1577(define_insn_and_split "*ze_and_ne" 1578 [(set (match_operand:DI 0 "register_operand" "=r") 1579 (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 1580 (const_int 1) 1581 (match_operand 2 "const_int_operand" "I")))] 1582 "(unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 8" 1583 "#" 1584 "(unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 8" 1585 [(set (match_dup 0) 1586 (and:DI (match_dup 1) (match_dup 3))) 1587 (set (match_dup 0) 1588 (ne:DI (match_dup 0) (const_int 0)))] 1589 "operands[3] = GEN_INT (1 << INTVAL (operands[2]));") 1590 1591;; Floating-point operations. All the double-precision insns can extend 1592;; from single, so indicate that. The exception are the ones that simply 1593;; play with the sign bits; it's not clear what to do there. 1594 1595(define_mode_iterator FMODE [SF DF]) 1596 1597(define_mode_attr opmode [(SF "si") (DF "di")]) 1598 1599(define_insn "abs<mode>2" 1600 [(set (match_operand:FMODE 0 "register_operand" "=f") 1601 (abs:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG")))] 1602 "TARGET_FP" 1603 "cpys $f31,%R1,%0" 1604 [(set_attr "type" "fcpys")]) 1605 1606(define_insn "*nabs<mode>2" 1607 [(set (match_operand:FMODE 0 "register_operand" "=f") 1608 (neg:FMODE 1609 (abs:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG"))))] 1610 "TARGET_FP" 1611 "cpysn $f31,%R1,%0" 1612 [(set_attr "type" "fadd")]) 1613 1614(define_expand "abstf2" 1615 [(parallel [(set (match_operand:TF 0 "register_operand") 1616 (abs:TF (match_operand:TF 1 "reg_or_0_operand"))) 1617 (use (match_dup 2))])] 1618 "TARGET_HAS_XFLOATING_LIBS" 1619 "operands[2] = force_reg (DImode, GEN_INT (HOST_WIDE_INT_1U << 63));") 1620 1621(define_insn_and_split "*abstf_internal" 1622 [(set (match_operand:TF 0 "register_operand" "=r") 1623 (abs:TF (match_operand:TF 1 "reg_or_0_operand" "rG"))) 1624 (use (match_operand:DI 2 "register_operand" "r"))] 1625 "TARGET_HAS_XFLOATING_LIBS" 1626 "#" 1627 "&& reload_completed" 1628 [(const_int 0)] 1629 "alpha_split_tfmode_frobsign (operands, gen_andnotdi3); DONE;") 1630 1631(define_insn "neg<mode>2" 1632 [(set (match_operand:FMODE 0 "register_operand" "=f") 1633 (neg:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG")))] 1634 "TARGET_FP" 1635 "cpysn %R1,%R1,%0" 1636 [(set_attr "type" "fadd")]) 1637 1638(define_expand "negtf2" 1639 [(parallel [(set (match_operand:TF 0 "register_operand") 1640 (neg:TF (match_operand:TF 1 "reg_or_0_operand"))) 1641 (use (match_dup 2))])] 1642 "TARGET_HAS_XFLOATING_LIBS" 1643 "operands[2] = force_reg (DImode, GEN_INT (HOST_WIDE_INT_1U << 63));") 1644 1645(define_insn_and_split "*negtf_internal" 1646 [(set (match_operand:TF 0 "register_operand" "=r") 1647 (neg:TF (match_operand:TF 1 "reg_or_0_operand" "rG"))) 1648 (use (match_operand:DI 2 "register_operand" "r"))] 1649 "TARGET_HAS_XFLOATING_LIBS" 1650 "#" 1651 "&& reload_completed" 1652 [(const_int 0)] 1653 "alpha_split_tfmode_frobsign (operands, gen_xordi3); DONE;") 1654 1655(define_insn "copysign<mode>3" 1656 [(set (match_operand:FMODE 0 "register_operand" "=f") 1657 (unspec:FMODE [(match_operand:FMODE 1 "reg_or_0_operand" "fG") 1658 (match_operand:FMODE 2 "reg_or_0_operand" "fG")] 1659 UNSPEC_COPYSIGN))] 1660 "TARGET_FP" 1661 "cpys %R2,%R1,%0" 1662 [(set_attr "type" "fadd")]) 1663 1664(define_insn "*ncopysign<mode>3" 1665 [(set (match_operand:FMODE 0 "register_operand" "=f") 1666 (neg:FMODE 1667 (unspec:FMODE [(match_operand:FMODE 1 "reg_or_0_operand" "fG") 1668 (match_operand:FMODE 2 "reg_or_0_operand" "fG")] 1669 UNSPEC_COPYSIGN)))] 1670 "TARGET_FP" 1671 "cpysn %R2,%R1,%0" 1672 [(set_attr "type" "fadd")]) 1673 1674(define_insn "*add<mode>3_ieee" 1675 [(set (match_operand:FMODE 0 "register_operand" "=&f") 1676 (plus:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "%fG") 1677 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1678 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1679 "add<modesuffix>%/ %R1,%R2,%0" 1680 [(set_attr "type" "fadd") 1681 (set_attr "trap" "yes") 1682 (set_attr "round_suffix" "normal") 1683 (set_attr "trap_suffix" "u_su_sui")]) 1684 1685(define_insn "add<mode>3" 1686 [(set (match_operand:FMODE 0 "register_operand" "=f") 1687 (plus:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "%fG") 1688 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1689 "TARGET_FP" 1690 "add<modesuffix>%/ %R1,%R2,%0" 1691 [(set_attr "type" "fadd") 1692 (set_attr "trap" "yes") 1693 (set_attr "round_suffix" "normal") 1694 (set_attr "trap_suffix" "u_su_sui")]) 1695 1696(define_insn "*adddf_ext1" 1697 [(set (match_operand:DF 0 "register_operand" "=f") 1698 (plus:DF (float_extend:DF 1699 (match_operand:SF 1 "reg_or_0_operand" "fG")) 1700 (match_operand:DF 2 "reg_or_0_operand" "fG")))] 1701 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1702 "add%-%/ %R1,%R2,%0" 1703 [(set_attr "type" "fadd") 1704 (set_attr "trap" "yes") 1705 (set_attr "round_suffix" "normal") 1706 (set_attr "trap_suffix" "u_su_sui")]) 1707 1708(define_insn "*adddf_ext2" 1709 [(set (match_operand:DF 0 "register_operand" "=f") 1710 (plus:DF (float_extend:DF 1711 (match_operand:SF 1 "reg_or_0_operand" "%fG")) 1712 (float_extend:DF 1713 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1714 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1715 "add%-%/ %R1,%R2,%0" 1716 [(set_attr "type" "fadd") 1717 (set_attr "trap" "yes") 1718 (set_attr "round_suffix" "normal") 1719 (set_attr "trap_suffix" "u_su_sui")]) 1720 1721(define_expand "addtf3" 1722 [(use (match_operand:TF 0 "register_operand")) 1723 (use (match_operand:TF 1 "general_operand")) 1724 (use (match_operand:TF 2 "general_operand"))] 1725 "TARGET_HAS_XFLOATING_LIBS" 1726 "alpha_emit_xfloating_arith (PLUS, operands); DONE;") 1727 1728(define_insn "*sub<mode>3_ieee" 1729 [(set (match_operand:FMODE 0 "register_operand" "=&f") 1730 (minus:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG") 1731 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1732 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1733 "sub<modesuffix>%/ %R1,%R2,%0" 1734 [(set_attr "type" "fadd") 1735 (set_attr "trap" "yes") 1736 (set_attr "round_suffix" "normal") 1737 (set_attr "trap_suffix" "u_su_sui")]) 1738 1739(define_insn "sub<mode>3" 1740 [(set (match_operand:FMODE 0 "register_operand" "=f") 1741 (minus:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG") 1742 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1743 "TARGET_FP" 1744 "sub<modesuffix>%/ %R1,%R2,%0" 1745 [(set_attr "type" "fadd") 1746 (set_attr "trap" "yes") 1747 (set_attr "round_suffix" "normal") 1748 (set_attr "trap_suffix" "u_su_sui")]) 1749 1750(define_insn "*subdf_ext1" 1751 [(set (match_operand:DF 0 "register_operand" "=f") 1752 (minus:DF (float_extend:DF 1753 (match_operand:SF 1 "reg_or_0_operand" "fG")) 1754 (match_operand:DF 2 "reg_or_0_operand" "fG")))] 1755 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1756 "sub%-%/ %R1,%R2,%0" 1757 [(set_attr "type" "fadd") 1758 (set_attr "trap" "yes") 1759 (set_attr "round_suffix" "normal") 1760 (set_attr "trap_suffix" "u_su_sui")]) 1761 1762(define_insn "*subdf_ext2" 1763 [(set (match_operand:DF 0 "register_operand" "=f") 1764 (minus:DF (match_operand:DF 1 "reg_or_0_operand" "fG") 1765 (float_extend:DF 1766 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1767 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1768 "sub%-%/ %R1,%R2,%0" 1769 [(set_attr "type" "fadd") 1770 (set_attr "trap" "yes") 1771 (set_attr "round_suffix" "normal") 1772 (set_attr "trap_suffix" "u_su_sui")]) 1773 1774(define_insn "*subdf_ext3" 1775 [(set (match_operand:DF 0 "register_operand" "=f") 1776 (minus:DF (float_extend:DF 1777 (match_operand:SF 1 "reg_or_0_operand" "fG")) 1778 (float_extend:DF 1779 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1780 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1781 "sub%-%/ %R1,%R2,%0" 1782 [(set_attr "type" "fadd") 1783 (set_attr "trap" "yes") 1784 (set_attr "round_suffix" "normal") 1785 (set_attr "trap_suffix" "u_su_sui")]) 1786 1787(define_expand "subtf3" 1788 [(use (match_operand:TF 0 "register_operand")) 1789 (use (match_operand:TF 1 "general_operand")) 1790 (use (match_operand:TF 2 "general_operand"))] 1791 "TARGET_HAS_XFLOATING_LIBS" 1792 "alpha_emit_xfloating_arith (MINUS, operands); DONE;") 1793 1794(define_insn "*mul<mode>3_ieee" 1795 [(set (match_operand:FMODE 0 "register_operand" "=&f") 1796 (mult:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "%fG") 1797 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1798 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1799 "mul<modesuffix>%/ %R1,%R2,%0" 1800 [(set_attr "type" "fmul") 1801 (set_attr "trap" "yes") 1802 (set_attr "round_suffix" "normal") 1803 (set_attr "trap_suffix" "u_su_sui")]) 1804 1805(define_insn "mul<mode>3" 1806 [(set (match_operand:FMODE 0 "register_operand" "=f") 1807 (mult:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "%fG") 1808 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1809 "TARGET_FP" 1810 "mul<modesuffix>%/ %R1,%R2,%0" 1811 [(set_attr "type" "fmul") 1812 (set_attr "trap" "yes") 1813 (set_attr "round_suffix" "normal") 1814 (set_attr "trap_suffix" "u_su_sui")]) 1815 1816(define_insn "*muldf_ext1" 1817 [(set (match_operand:DF 0 "register_operand" "=f") 1818 (mult:DF (float_extend:DF 1819 (match_operand:SF 1 "reg_or_0_operand" "fG")) 1820 (match_operand:DF 2 "reg_or_0_operand" "fG")))] 1821 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1822 "mul%-%/ %R1,%R2,%0" 1823 [(set_attr "type" "fmul") 1824 (set_attr "trap" "yes") 1825 (set_attr "round_suffix" "normal") 1826 (set_attr "trap_suffix" "u_su_sui")]) 1827 1828(define_insn "*muldf_ext2" 1829 [(set (match_operand:DF 0 "register_operand" "=f") 1830 (mult:DF (float_extend:DF 1831 (match_operand:SF 1 "reg_or_0_operand" "%fG")) 1832 (float_extend:DF 1833 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1834 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1835 "mul%-%/ %R1,%R2,%0" 1836 [(set_attr "type" "fmul") 1837 (set_attr "trap" "yes") 1838 (set_attr "round_suffix" "normal") 1839 (set_attr "trap_suffix" "u_su_sui")]) 1840 1841(define_expand "multf3" 1842 [(use (match_operand:TF 0 "register_operand")) 1843 (use (match_operand:TF 1 "general_operand")) 1844 (use (match_operand:TF 2 "general_operand"))] 1845 "TARGET_HAS_XFLOATING_LIBS" 1846 "alpha_emit_xfloating_arith (MULT, operands); DONE;") 1847 1848(define_insn "*div<mode>3_ieee" 1849 [(set (match_operand:FMODE 0 "register_operand" "=&f") 1850 (div:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG") 1851 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1852 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1853 "div<modesuffix>%/ %R1,%R2,%0" 1854 [(set_attr "type" "fdiv") 1855 (set_attr "opsize" "<opmode>") 1856 (set_attr "trap" "yes") 1857 (set_attr "round_suffix" "normal") 1858 (set_attr "trap_suffix" "u_su_sui")]) 1859 1860(define_insn "div<mode>3" 1861 [(set (match_operand:FMODE 0 "register_operand" "=f") 1862 (div:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG") 1863 (match_operand:FMODE 2 "reg_or_0_operand" "fG")))] 1864 "TARGET_FP" 1865 "div<modesuffix>%/ %R1,%R2,%0" 1866 [(set_attr "type" "fdiv") 1867 (set_attr "opsize" "<opmode>") 1868 (set_attr "trap" "yes") 1869 (set_attr "round_suffix" "normal") 1870 (set_attr "trap_suffix" "u_su_sui")]) 1871 1872(define_insn "*divdf_ext1" 1873 [(set (match_operand:DF 0 "register_operand" "=f") 1874 (div:DF (float_extend:DF (match_operand:SF 1 "reg_or_0_operand" "fG")) 1875 (match_operand:DF 2 "reg_or_0_operand" "fG")))] 1876 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1877 "div%-%/ %R1,%R2,%0" 1878 [(set_attr "type" "fdiv") 1879 (set_attr "trap" "yes") 1880 (set_attr "round_suffix" "normal") 1881 (set_attr "trap_suffix" "u_su_sui")]) 1882 1883(define_insn "*divdf_ext2" 1884 [(set (match_operand:DF 0 "register_operand" "=f") 1885 (div:DF (match_operand:DF 1 "reg_or_0_operand" "fG") 1886 (float_extend:DF 1887 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1888 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1889 "div%-%/ %R1,%R2,%0" 1890 [(set_attr "type" "fdiv") 1891 (set_attr "trap" "yes") 1892 (set_attr "round_suffix" "normal") 1893 (set_attr "trap_suffix" "u_su_sui")]) 1894 1895(define_insn "*divdf_ext3" 1896 [(set (match_operand:DF 0 "register_operand" "=f") 1897 (div:DF (float_extend:DF 1898 (match_operand:SF 1 "reg_or_0_operand" "fG")) 1899 (float_extend:DF 1900 (match_operand:SF 2 "reg_or_0_operand" "fG"))))] 1901 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1902 "div%-%/ %R1,%R2,%0" 1903 [(set_attr "type" "fdiv") 1904 (set_attr "trap" "yes") 1905 (set_attr "round_suffix" "normal") 1906 (set_attr "trap_suffix" "u_su_sui")]) 1907 1908(define_expand "divtf3" 1909 [(use (match_operand:TF 0 "register_operand")) 1910 (use (match_operand:TF 1 "general_operand")) 1911 (use (match_operand:TF 2 "general_operand"))] 1912 "TARGET_HAS_XFLOATING_LIBS" 1913 "alpha_emit_xfloating_arith (DIV, operands); DONE;") 1914 1915(define_insn "*sqrt<mode>2_ieee" 1916 [(set (match_operand:FMODE 0 "register_operand" "=&f") 1917 (sqrt:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG")))] 1918 "TARGET_FP && TARGET_FIX && alpha_fptm >= ALPHA_FPTM_SU" 1919 "sqrt<modesuffix>%/ %R1,%0" 1920 [(set_attr "type" "fsqrt") 1921 (set_attr "opsize" "<opmode>") 1922 (set_attr "trap" "yes") 1923 (set_attr "round_suffix" "normal") 1924 (set_attr "trap_suffix" "u_su_sui")]) 1925 1926(define_insn "sqrt<mode>2" 1927 [(set (match_operand:FMODE 0 "register_operand" "=f") 1928 (sqrt:FMODE (match_operand:FMODE 1 "reg_or_0_operand" "fG")))] 1929 "TARGET_FP && TARGET_FIX" 1930 "sqrt<modesuffix>%/ %R1,%0" 1931 [(set_attr "type" "fsqrt") 1932 (set_attr "opsize" "<opmode>") 1933 (set_attr "trap" "yes") 1934 (set_attr "round_suffix" "normal") 1935 (set_attr "trap_suffix" "u_su_sui")]) 1936 1937;; Define conversion operators between DFmode and SImode, using the cvtql 1938;; instruction. To allow combine et al to do useful things, we keep the 1939;; operation as a unit until after reload, at which point we split the 1940;; instructions. 1941;; 1942;; Note that we (attempt to) only consider this optimization when the 1943;; ultimate destination is memory. If we will be doing further integer 1944;; processing, it is cheaper to do the truncation in the int regs. 1945 1946(define_insn "*cvtql" 1947 [(set (match_operand:SF 0 "register_operand" "=f") 1948 (unspec:SF [(match_operand:DI 1 "reg_or_0_operand" "fG")] 1949 UNSPEC_CVTQL))] 1950 "TARGET_FP" 1951 "cvtql%/ %R1,%0" 1952 [(set_attr "type" "fadd") 1953 (set_attr "trap" "yes") 1954 (set_attr "trap_suffix" "v_sv")]) 1955 1956(define_insn_and_split "*fix_truncdfsi_ieee" 1957 [(set (match_operand:SI 0 "memory_operand" "=m") 1958 (subreg:SI 1959 (match_operator:DI 4 "fix_operator" 1960 [(match_operand:DF 1 "reg_or_0_operand" "fG")]) 0)) 1961 (clobber (match_scratch:DI 2 "=&f")) 1962 (clobber (match_scratch:SF 3 "=&f"))] 1963 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1964 "#" 1965 "&& reload_completed" 1966 [(set (match_dup 2) (match_op_dup 4 [(match_dup 1)])) 1967 (set (match_dup 3) (unspec:SF [(match_dup 2)] UNSPEC_CVTQL)) 1968 (set (match_dup 5) (match_dup 3))] 1969{ 1970 operands[5] = adjust_address (operands[0], SFmode, 0); 1971} 1972 [(set_attr "type" "fadd") 1973 (set_attr "trap" "yes")]) 1974 1975(define_insn_and_split "*fix_truncdfsi_internal" 1976 [(set (match_operand:SI 0 "memory_operand" "=m") 1977 (subreg:SI 1978 (match_operator:DI 3 "fix_operator" 1979 [(match_operand:DF 1 "reg_or_0_operand" "fG")]) 0)) 1980 (clobber (match_scratch:DI 2 "=f"))] 1981 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 1982 "#" 1983 "&& reload_completed" 1984 [(set (match_dup 2) (match_op_dup 3 [(match_dup 1)])) 1985 (set (match_dup 4) (unspec:SF [(match_dup 2)] UNSPEC_CVTQL)) 1986 (set (match_dup 5) (match_dup 4))] 1987{ 1988 operands[4] = gen_rtx_REG (SFmode, REGNO (operands[2])); 1989 operands[5] = adjust_address (operands[0], SFmode, 0); 1990} 1991 [(set_attr "type" "fadd") 1992 (set_attr "trap" "yes")]) 1993 1994(define_insn "*fix_truncdfdi_ieee" 1995 [(set (match_operand:DI 0 "reg_no_subreg_operand" "=&f") 1996 (match_operator:DI 2 "fix_operator" 1997 [(match_operand:DF 1 "reg_or_0_operand" "fG")]))] 1998 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 1999 "cvt%-q%/ %R1,%0" 2000 [(set_attr "type" "fadd") 2001 (set_attr "trap" "yes") 2002 (set_attr "round_suffix" "c") 2003 (set_attr "trap_suffix" "v_sv_svi")]) 2004 2005(define_insn "*fix_truncdfdi2" 2006 [(set (match_operand:DI 0 "reg_no_subreg_operand" "=f") 2007 (match_operator:DI 2 "fix_operator" 2008 [(match_operand:DF 1 "reg_or_0_operand" "fG")]))] 2009 "TARGET_FP" 2010 "cvt%-q%/ %R1,%0" 2011 [(set_attr "type" "fadd") 2012 (set_attr "trap" "yes") 2013 (set_attr "round_suffix" "c") 2014 (set_attr "trap_suffix" "v_sv_svi")]) 2015 2016(define_expand "fix_truncdfdi2" 2017 [(set (match_operand:DI 0 "reg_no_subreg_operand") 2018 (fix:DI (match_operand:DF 1 "reg_or_0_operand")))] 2019 "TARGET_FP") 2020 2021(define_expand "fixuns_truncdfdi2" 2022 [(set (match_operand:DI 0 "reg_no_subreg_operand") 2023 (unsigned_fix:DI (match_operand:DF 1 "reg_or_0_operand")))] 2024 "TARGET_FP") 2025 2026;; Likewise between SFmode and SImode. 2027 2028(define_insn_and_split "*fix_truncsfsi_ieee" 2029 [(set (match_operand:SI 0 "memory_operand" "=m") 2030 (subreg:SI 2031 (match_operator:DI 4 "fix_operator" 2032 [(float_extend:DF 2033 (match_operand:SF 1 "reg_or_0_operand" "fG"))]) 0)) 2034 (clobber (match_scratch:DI 2 "=&f")) 2035 (clobber (match_scratch:SF 3 "=&f"))] 2036 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2037 "#" 2038 "&& reload_completed" 2039 [(set (match_dup 2) (match_op_dup 4 [(float_extend:DF (match_dup 1))])) 2040 (set (match_dup 3) (unspec:SF [(match_dup 2)] UNSPEC_CVTQL)) 2041 (set (match_dup 5) (match_dup 3))] 2042 "operands[5] = adjust_address (operands[0], SFmode, 0);" 2043 [(set_attr "type" "fadd") 2044 (set_attr "trap" "yes")]) 2045 2046(define_insn_and_split "*fix_truncsfsi_internal" 2047 [(set (match_operand:SI 0 "memory_operand" "=m") 2048 (subreg:SI 2049 (match_operator:DI 3 "fix_operator" 2050 [(float_extend:DF 2051 (match_operand:SF 1 "reg_or_0_operand" "fG"))]) 0)) 2052 (clobber (match_scratch:DI 2 "=f"))] 2053 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2054 "#" 2055 "&& reload_completed" 2056 [(set (match_dup 2) (match_op_dup 3 [(float_extend:DF (match_dup 1))])) 2057 (set (match_dup 4) (unspec:SF [(match_dup 2)] UNSPEC_CVTQL)) 2058 (set (match_dup 5) (match_dup 4))] 2059{ 2060 operands[4] = gen_rtx_REG (SFmode, REGNO (operands[2])); 2061 operands[5] = adjust_address (operands[0], SFmode, 0); 2062} 2063 [(set_attr "type" "fadd") 2064 (set_attr "trap" "yes")]) 2065 2066(define_insn "*fix_truncsfdi_ieee" 2067 [(set (match_operand:DI 0 "reg_no_subreg_operand" "=&f") 2068 (match_operator:DI 2 "fix_operator" 2069 [(float_extend:DF (match_operand:SF 1 "reg_or_0_operand" "fG"))]))] 2070 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2071 "cvt%-q%/ %R1,%0" 2072 [(set_attr "type" "fadd") 2073 (set_attr "trap" "yes") 2074 (set_attr "round_suffix" "c") 2075 (set_attr "trap_suffix" "v_sv_svi")]) 2076 2077(define_insn "*fix_truncsfdi2" 2078 [(set (match_operand:DI 0 "reg_no_subreg_operand" "=f") 2079 (match_operator:DI 2 "fix_operator" 2080 [(float_extend:DF (match_operand:SF 1 "reg_or_0_operand" "fG"))]))] 2081 "TARGET_FP" 2082 "cvt%-q%/ %R1,%0" 2083 [(set_attr "type" "fadd") 2084 (set_attr "trap" "yes") 2085 (set_attr "round_suffix" "c") 2086 (set_attr "trap_suffix" "v_sv_svi")]) 2087 2088(define_expand "fix_truncsfdi2" 2089 [(set (match_operand:DI 0 "reg_no_subreg_operand") 2090 (fix:DI (float_extend:DF (match_operand:SF 1 "reg_or_0_operand"))))] 2091 "TARGET_FP") 2092 2093(define_expand "fixuns_truncsfdi2" 2094 [(set (match_operand:DI 0 "reg_no_subreg_operand") 2095 (unsigned_fix:DI 2096 (float_extend:DF (match_operand:SF 1 "reg_or_0_operand"))))] 2097 "TARGET_FP") 2098 2099(define_expand "fix_trunctfdi2" 2100 [(use (match_operand:DI 0 "register_operand")) 2101 (use (match_operand:TF 1 "general_operand"))] 2102 "TARGET_HAS_XFLOATING_LIBS" 2103 "alpha_emit_xfloating_cvt (FIX, operands); DONE;") 2104 2105(define_expand "fixuns_trunctfdi2" 2106 [(use (match_operand:DI 0 "register_operand")) 2107 (use (match_operand:TF 1 "general_operand"))] 2108 "TARGET_HAS_XFLOATING_LIBS" 2109 "alpha_emit_xfloating_cvt (UNSIGNED_FIX, operands); DONE;") 2110 2111(define_insn "*floatdisf_ieee" 2112 [(set (match_operand:SF 0 "register_operand" "=&f") 2113 (float:SF (match_operand:DI 1 "reg_no_subreg_operand" "f")))] 2114 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2115 "cvtq%,%/ %1,%0" 2116 [(set_attr "type" "fadd") 2117 (set_attr "trap" "yes") 2118 (set_attr "round_suffix" "normal") 2119 (set_attr "trap_suffix" "sui")]) 2120 2121(define_insn "floatdisf2" 2122 [(set (match_operand:SF 0 "register_operand" "=f") 2123 (float:SF (match_operand:DI 1 "reg_no_subreg_operand" "f")))] 2124 "TARGET_FP" 2125 "cvtq%,%/ %1,%0" 2126 [(set_attr "type" "fadd") 2127 (set_attr "trap" "yes") 2128 (set_attr "round_suffix" "normal") 2129 (set_attr "trap_suffix" "sui")]) 2130 2131(define_insn_and_split "*floatsisf2_ieee" 2132 [(set (match_operand:SF 0 "register_operand" "=&f") 2133 (float:SF (match_operand:SI 1 "memory_operand" "m"))) 2134 (clobber (match_scratch:DI 2 "=&f")) 2135 (clobber (match_scratch:SF 3 "=&f"))] 2136 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2137 "#" 2138 "&& reload_completed" 2139 [(set (match_dup 3) (match_dup 1)) 2140 (set (match_dup 2) (unspec:DI [(match_dup 3)] UNSPEC_CVTLQ)) 2141 (set (match_dup 0) (float:SF (match_dup 2)))] 2142 "operands[1] = adjust_address (operands[1], SFmode, 0);") 2143 2144(define_insn_and_split "*floatsisf2" 2145 [(set (match_operand:SF 0 "register_operand" "=f") 2146 (float:SF (match_operand:SI 1 "memory_operand" "m")))] 2147 "TARGET_FP" 2148 "#" 2149 "&& reload_completed" 2150 [(set (match_dup 0) (match_dup 1)) 2151 (set (match_dup 2) (unspec:DI [(match_dup 0)] UNSPEC_CVTLQ)) 2152 (set (match_dup 0) (float:SF (match_dup 2)))] 2153{ 2154 operands[1] = adjust_address (operands[1], SFmode, 0); 2155 operands[2] = gen_rtx_REG (DImode, REGNO (operands[0])); 2156}) 2157 2158(define_insn "*floatdidf_ieee" 2159 [(set (match_operand:DF 0 "register_operand" "=&f") 2160 (float:DF (match_operand:DI 1 "reg_no_subreg_operand" "f")))] 2161 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2162 "cvtq%-%/ %1,%0" 2163 [(set_attr "type" "fadd") 2164 (set_attr "trap" "yes") 2165 (set_attr "round_suffix" "normal") 2166 (set_attr "trap_suffix" "sui")]) 2167 2168(define_insn "floatdidf2" 2169 [(set (match_operand:DF 0 "register_operand" "=f") 2170 (float:DF (match_operand:DI 1 "reg_no_subreg_operand" "f")))] 2171 "TARGET_FP" 2172 "cvtq%-%/ %1,%0" 2173 [(set_attr "type" "fadd") 2174 (set_attr "trap" "yes") 2175 (set_attr "round_suffix" "normal") 2176 (set_attr "trap_suffix" "sui")]) 2177 2178(define_insn_and_split "*floatsidf2_ieee" 2179 [(set (match_operand:DF 0 "register_operand" "=&f") 2180 (float:DF (match_operand:SI 1 "memory_operand" "m"))) 2181 (clobber (match_scratch:DI 2 "=&f")) 2182 (clobber (match_scratch:SF 3 "=&f"))] 2183 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2184 "#" 2185 "&& reload_completed" 2186 [(set (match_dup 3) (match_dup 1)) 2187 (set (match_dup 2) (unspec:DI [(match_dup 3)] UNSPEC_CVTLQ)) 2188 (set (match_dup 0) (float:DF (match_dup 2)))] 2189 "operands[1] = adjust_address (operands[1], SFmode, 0);") 2190 2191(define_insn_and_split "*floatsidf2" 2192 [(set (match_operand:DF 0 "register_operand" "=f") 2193 (float:DF (match_operand:SI 1 "memory_operand" "m")))] 2194 "TARGET_FP" 2195 "#" 2196 "&& reload_completed" 2197 [(set (match_dup 3) (match_dup 1)) 2198 (set (match_dup 2) (unspec:DI [(match_dup 3)] UNSPEC_CVTLQ)) 2199 (set (match_dup 0) (float:DF (match_dup 2)))] 2200{ 2201 operands[1] = adjust_address (operands[1], SFmode, 0); 2202 operands[2] = gen_rtx_REG (DImode, REGNO (operands[0])); 2203 operands[3] = gen_rtx_REG (SFmode, REGNO (operands[0])); 2204}) 2205 2206(define_expand "floatditf2" 2207 [(use (match_operand:TF 0 "register_operand")) 2208 (use (match_operand:DI 1 "general_operand"))] 2209 "TARGET_HAS_XFLOATING_LIBS" 2210 "alpha_emit_xfloating_cvt (FLOAT, operands); DONE;") 2211 2212(define_expand "floatunsdisf2" 2213 [(use (match_operand:SF 0 "register_operand")) 2214 (use (match_operand:DI 1 "register_operand"))] 2215 "TARGET_FP" 2216 "alpha_emit_floatuns (operands); DONE;") 2217 2218(define_expand "floatunsdidf2" 2219 [(use (match_operand:DF 0 "register_operand")) 2220 (use (match_operand:DI 1 "register_operand"))] 2221 "TARGET_FP" 2222 "alpha_emit_floatuns (operands); DONE;") 2223 2224(define_expand "floatunsditf2" 2225 [(use (match_operand:TF 0 "register_operand")) 2226 (use (match_operand:DI 1 "general_operand"))] 2227 "TARGET_HAS_XFLOATING_LIBS" 2228 "alpha_emit_xfloating_cvt (UNSIGNED_FLOAT, operands); DONE;") 2229 2230(define_expand "extendsfdf2" 2231 [(set (match_operand:DF 0 "register_operand") 2232 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand")))] 2233 "TARGET_FP" 2234{ 2235 if (alpha_fptm >= ALPHA_FPTM_SU) 2236 operands[1] = force_reg (SFmode, operands[1]); 2237}) 2238 2239;; The Unicos/Mk assembler doesn't support cvtst, but we've already 2240;; asserted that alpha_fptm == ALPHA_FPTM_N. 2241 2242(define_insn "*extendsfdf2_ieee" 2243 [(set (match_operand:DF 0 "register_operand" "=&f") 2244 (float_extend:DF (match_operand:SF 1 "register_operand" "f")))] 2245 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2246 "cvtsts %1,%0" 2247 [(set_attr "type" "fadd") 2248 (set_attr "trap" "yes")]) 2249 2250(define_insn "*extendsfdf2_internal" 2251 [(set (match_operand:DF 0 "register_operand" "=f,f,m") 2252 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,m,f")))] 2253 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2254 "@ 2255 cpys %1,%1,%0 2256 ld%, %0,%1 2257 st%- %1,%0" 2258 [(set_attr "type" "fcpys,fld,fst")]) 2259 2260;; Use register_operand for operand 1 to prevent compress_float_constant 2261;; from doing something silly. When optimizing we'll put things back 2262;; together anyway. 2263(define_expand "extendsftf2" 2264 [(use (match_operand:TF 0 "register_operand")) 2265 (use (match_operand:SF 1 "register_operand"))] 2266 "TARGET_HAS_XFLOATING_LIBS" 2267{ 2268 rtx tmp = gen_reg_rtx (DFmode); 2269 emit_insn (gen_extendsfdf2 (tmp, operands[1])); 2270 emit_insn (gen_extenddftf2 (operands[0], tmp)); 2271 DONE; 2272}) 2273 2274(define_expand "extenddftf2" 2275 [(use (match_operand:TF 0 "register_operand")) 2276 (use (match_operand:DF 1 "register_operand"))] 2277 "TARGET_HAS_XFLOATING_LIBS" 2278 "alpha_emit_xfloating_cvt (FLOAT_EXTEND, operands); DONE;") 2279 2280(define_insn "*truncdfsf2_ieee" 2281 [(set (match_operand:SF 0 "register_operand" "=&f") 2282 (float_truncate:SF (match_operand:DF 1 "reg_or_0_operand" "fG")))] 2283 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2284 "cvt%-%,%/ %R1,%0" 2285 [(set_attr "type" "fadd") 2286 (set_attr "trap" "yes") 2287 (set_attr "round_suffix" "normal") 2288 (set_attr "trap_suffix" "u_su_sui")]) 2289 2290(define_insn "truncdfsf2" 2291 [(set (match_operand:SF 0 "register_operand" "=f") 2292 (float_truncate:SF (match_operand:DF 1 "reg_or_0_operand" "fG")))] 2293 "TARGET_FP" 2294 "cvt%-%,%/ %R1,%0" 2295 [(set_attr "type" "fadd") 2296 (set_attr "trap" "yes") 2297 (set_attr "round_suffix" "normal") 2298 (set_attr "trap_suffix" "u_su_sui")]) 2299 2300(define_expand "trunctfdf2" 2301 [(use (match_operand:DF 0 "register_operand")) 2302 (use (match_operand:TF 1 "general_operand"))] 2303 "TARGET_HAS_XFLOATING_LIBS" 2304 "alpha_emit_xfloating_cvt (FLOAT_TRUNCATE, operands); DONE;") 2305 2306(define_expand "trunctfsf2" 2307 [(use (match_operand:SF 0 "register_operand")) 2308 (use (match_operand:TF 1 "general_operand"))] 2309 "TARGET_FP && TARGET_HAS_XFLOATING_LIBS" 2310{ 2311 rtx tmpf, sticky, arg, lo, hi; 2312 2313 tmpf = gen_reg_rtx (DFmode); 2314 sticky = gen_reg_rtx (DImode); 2315 arg = copy_to_mode_reg (TFmode, operands[1]); 2316 lo = gen_lowpart (DImode, arg); 2317 hi = gen_highpart (DImode, arg); 2318 2319 /* Convert the low word of the TFmode value into a sticky rounding bit, 2320 then or it into the low bit of the high word. This leaves the sticky 2321 bit at bit 48 of the fraction, which is representable in DFmode, 2322 which prevents rounding error in the final conversion to SFmode. */ 2323 2324 emit_insn (gen_rtx_SET (sticky, gen_rtx_NE (DImode, lo, const0_rtx))); 2325 emit_insn (gen_iordi3 (hi, hi, sticky)); 2326 emit_insn (gen_trunctfdf2 (tmpf, arg)); 2327 emit_insn (gen_truncdfsf2 (operands[0], tmpf)); 2328 DONE; 2329}) 2330 2331;; Next are all the integer comparisons, and conditional moves and branches 2332;; and some of the related define_expand's and define_split's. 2333 2334(define_insn "*setcc_internal" 2335 [(set (match_operand 0 "register_operand" "=r") 2336 (match_operator 1 "alpha_comparison_operator" 2337 [(match_operand:DI 2 "register_operand" "r") 2338 (match_operand:DI 3 "reg_or_8bit_operand" "rI")]))] 2339 "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT 2340 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8 2341 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 2342 "cmp%C1 %2,%3,%0" 2343 [(set_attr "type" "icmp")]) 2344 2345;; Yes, we can technically support reg_or_8bit_operand in operand 2, 2346;; but that's non-canonical rtl and allowing that causes inefficiencies 2347;; from cse on. 2348(define_insn "*setcc_swapped_internal" 2349 [(set (match_operand 0 "register_operand" "=r") 2350 (match_operator 1 "alpha_swapped_comparison_operator" 2351 [(match_operand:DI 2 "register_operand" "r") 2352 (match_operand:DI 3 "reg_or_0_operand" "rJ")]))] 2353 "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT 2354 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8 2355 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 2356 "cmp%c1 %r3,%2,%0" 2357 [(set_attr "type" "icmp")]) 2358 2359;; Use match_operator rather than ne directly so that we can match 2360;; multiple integer modes. 2361(define_insn "*setne_internal" 2362 [(set (match_operand 0 "register_operand" "=r") 2363 (match_operator 1 "signed_comparison_operator" 2364 [(match_operand:DI 2 "register_operand" "r") 2365 (const_int 0)]))] 2366 "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT 2367 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8 2368 && GET_CODE (operands[1]) == NE 2369 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 2370 "cmpult $31,%2,%0" 2371 [(set_attr "type" "icmp")]) 2372 2373;; The mode folding trick can't be used with const_int operands, since 2374;; reload needs to know the proper mode. 2375;; 2376;; Use add_operand instead of the more seemingly natural reg_or_8bit_operand 2377;; in order to create more pairs of constants. As long as we're allowing 2378;; two constants at the same time, and will have to reload one of them... 2379 2380(define_insn "*mov<mode>cc_internal" 2381 [(set (match_operand:IMODE 0 "register_operand" "=r,r,r,r") 2382 (if_then_else:IMODE 2383 (match_operator 2 "signed_comparison_operator" 2384 [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J") 2385 (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")]) 2386 (match_operand:IMODE 1 "add_operand" "rI,0,rI,0") 2387 (match_operand:IMODE 5 "add_operand" "0,rI,0,rI")))] 2388 "(operands[3] == const0_rtx) ^ (operands[4] == const0_rtx)" 2389 "@ 2390 cmov%C2 %r3,%1,%0 2391 cmov%D2 %r3,%5,%0 2392 cmov%c2 %r4,%1,%0 2393 cmov%d2 %r4,%5,%0" 2394 [(set_attr "type" "icmov")]) 2395 2396(define_insn "*mov<mode>cc_lbc" 2397 [(set (match_operand:IMODE 0 "register_operand" "=r,r") 2398 (if_then_else:IMODE 2399 (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ") 2400 (const_int 1) 2401 (const_int 0)) 2402 (const_int 0)) 2403 (match_operand:IMODE 1 "reg_or_8bit_operand" "rI,0") 2404 (match_operand:IMODE 3 "reg_or_8bit_operand" "0,rI")))] 2405 "" 2406 "@ 2407 cmovlbc %r2,%1,%0 2408 cmovlbs %r2,%3,%0" 2409 [(set_attr "type" "icmov")]) 2410 2411(define_insn "*mov<mode>cc_lbs" 2412 [(set (match_operand:IMODE 0 "register_operand" "=r,r") 2413 (if_then_else:IMODE 2414 (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ") 2415 (const_int 1) 2416 (const_int 0)) 2417 (const_int 0)) 2418 (match_operand:IMODE 1 "reg_or_8bit_operand" "rI,0") 2419 (match_operand:IMODE 3 "reg_or_8bit_operand" "0,rI")))] 2420 "" 2421 "@ 2422 cmovlbs %r2,%1,%0 2423 cmovlbc %r2,%3,%0" 2424 [(set_attr "type" "icmov")]) 2425 2426;; For ABS, we have two choices, depending on whether the input and output 2427;; registers are the same or not. 2428(define_expand "absdi2" 2429 [(set (match_operand:DI 0 "register_operand") 2430 (abs:DI (match_operand:DI 1 "register_operand")))] 2431 "" 2432{ 2433 if (rtx_equal_p (operands[0], operands[1])) 2434 emit_insn (gen_absdi2_same (operands[0], gen_reg_rtx (DImode))); 2435 else 2436 emit_insn (gen_absdi2_diff (operands[0], operands[1])); 2437 DONE; 2438}) 2439 2440(define_expand "absdi2_same" 2441 [(set (match_operand:DI 1 "register_operand") 2442 (neg:DI (match_operand:DI 0 "register_operand"))) 2443 (set (match_dup 0) 2444 (if_then_else:DI (ge (match_dup 0) (const_int 0)) 2445 (match_dup 0) 2446 (match_dup 1)))]) 2447 2448(define_expand "absdi2_diff" 2449 [(set (match_operand:DI 0 "register_operand") 2450 (neg:DI (match_operand:DI 1 "register_operand"))) 2451 (set (match_dup 0) 2452 (if_then_else:DI (lt (match_dup 1) (const_int 0)) 2453 (match_dup 0) 2454 (match_dup 1)))]) 2455 2456(define_split 2457 [(set (match_operand:DI 0 "register_operand") 2458 (abs:DI (match_dup 0))) 2459 (clobber (match_operand:DI 1 "register_operand"))] 2460 "" 2461 [(set (match_dup 1) (neg:DI (match_dup 0))) 2462 (set (match_dup 0) (if_then_else:DI (ge (match_dup 0) (const_int 0)) 2463 (match_dup 0) (match_dup 1)))]) 2464 2465(define_split 2466 [(set (match_operand:DI 0 "register_operand") 2467 (abs:DI (match_operand:DI 1 "register_operand")))] 2468 "! rtx_equal_p (operands[0], operands[1])" 2469 [(set (match_dup 0) (neg:DI (match_dup 1))) 2470 (set (match_dup 0) (if_then_else:DI (lt (match_dup 1) (const_int 0)) 2471 (match_dup 0) (match_dup 1)))]) 2472 2473(define_split 2474 [(set (match_operand:DI 0 "register_operand") 2475 (neg:DI (abs:DI (match_dup 0)))) 2476 (clobber (match_operand:DI 1 "register_operand"))] 2477 "" 2478 [(set (match_dup 1) (neg:DI (match_dup 0))) 2479 (set (match_dup 0) (if_then_else:DI (le (match_dup 0) (const_int 0)) 2480 (match_dup 0) (match_dup 1)))]) 2481 2482(define_split 2483 [(set (match_operand:DI 0 "register_operand") 2484 (neg:DI (abs:DI (match_operand:DI 1 "register_operand"))))] 2485 "! rtx_equal_p (operands[0], operands[1])" 2486 [(set (match_dup 0) (neg:DI (match_dup 1))) 2487 (set (match_dup 0) (if_then_else:DI (gt (match_dup 1) (const_int 0)) 2488 (match_dup 0) (match_dup 1)))]) 2489 2490(define_insn "<code><mode>3" 2491 [(set (match_operand:I12MODE 0 "register_operand" "=r") 2492 (any_maxmin:I12MODE 2493 (match_operand:I12MODE 1 "reg_or_0_operand" "%rJ") 2494 (match_operand:I12MODE 2 "reg_or_8bit_operand" "rI")))] 2495 "TARGET_MAX" 2496 "<maxmin><vecmodesuffix> %r1,%2,%0" 2497 [(set_attr "type" "mvi")]) 2498 2499(define_expand "smaxdi3" 2500 [(set (match_dup 3) 2501 (le:DI (match_operand:DI 1 "reg_or_0_operand") 2502 (match_operand:DI 2 "reg_or_8bit_operand"))) 2503 (set (match_operand:DI 0 "register_operand") 2504 (if_then_else:DI (eq (match_dup 3) (const_int 0)) 2505 (match_dup 1) (match_dup 2)))] 2506 "" 2507 "operands[3] = gen_reg_rtx (DImode);") 2508 2509(define_split 2510 [(set (match_operand:DI 0 "register_operand") 2511 (smax:DI (match_operand:DI 1 "reg_or_0_operand") 2512 (match_operand:DI 2 "reg_or_8bit_operand"))) 2513 (clobber (match_operand:DI 3 "register_operand"))] 2514 "operands[2] != const0_rtx" 2515 [(set (match_dup 3) (le:DI (match_dup 1) (match_dup 2))) 2516 (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0)) 2517 (match_dup 1) (match_dup 2)))]) 2518 2519(define_insn "*smax_const0" 2520 [(set (match_operand:DI 0 "register_operand" "=r") 2521 (smax:DI (match_operand:DI 1 "register_operand" "0") 2522 (const_int 0)))] 2523 "" 2524 "cmovlt %0,0,%0" 2525 [(set_attr "type" "icmov")]) 2526 2527(define_expand "smindi3" 2528 [(set (match_dup 3) 2529 (lt:DI (match_operand:DI 1 "reg_or_0_operand") 2530 (match_operand:DI 2 "reg_or_8bit_operand"))) 2531 (set (match_operand:DI 0 "register_operand") 2532 (if_then_else:DI (ne (match_dup 3) (const_int 0)) 2533 (match_dup 1) (match_dup 2)))] 2534 "" 2535 "operands[3] = gen_reg_rtx (DImode);") 2536 2537(define_split 2538 [(set (match_operand:DI 0 "register_operand") 2539 (smin:DI (match_operand:DI 1 "reg_or_0_operand") 2540 (match_operand:DI 2 "reg_or_8bit_operand"))) 2541 (clobber (match_operand:DI 3 "register_operand"))] 2542 "operands[2] != const0_rtx" 2543 [(set (match_dup 3) (lt:DI (match_dup 1) (match_dup 2))) 2544 (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0)) 2545 (match_dup 1) (match_dup 2)))]) 2546 2547(define_insn "*smin_const0" 2548 [(set (match_operand:DI 0 "register_operand" "=r") 2549 (smin:DI (match_operand:DI 1 "register_operand" "0") 2550 (const_int 0)))] 2551 "" 2552 "cmovgt %0,0,%0" 2553 [(set_attr "type" "icmov")]) 2554 2555(define_expand "umaxdi3" 2556 [(set (match_dup 3) 2557 (leu:DI (match_operand:DI 1 "reg_or_0_operand") 2558 (match_operand:DI 2 "reg_or_8bit_operand"))) 2559 (set (match_operand:DI 0 "register_operand") 2560 (if_then_else:DI (eq (match_dup 3) (const_int 0)) 2561 (match_dup 1) (match_dup 2)))] 2562 "" 2563 "operands[3] = gen_reg_rtx (DImode);") 2564 2565(define_split 2566 [(set (match_operand:DI 0 "register_operand") 2567 (umax:DI (match_operand:DI 1 "reg_or_0_operand") 2568 (match_operand:DI 2 "reg_or_8bit_operand"))) 2569 (clobber (match_operand:DI 3 "register_operand"))] 2570 "operands[2] != const0_rtx" 2571 [(set (match_dup 3) (leu:DI (match_dup 1) (match_dup 2))) 2572 (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0)) 2573 (match_dup 1) (match_dup 2)))]) 2574 2575(define_expand "umindi3" 2576 [(set (match_dup 3) 2577 (ltu:DI (match_operand:DI 1 "reg_or_0_operand") 2578 (match_operand:DI 2 "reg_or_8bit_operand"))) 2579 (set (match_operand:DI 0 "register_operand") 2580 (if_then_else:DI (ne (match_dup 3) (const_int 0)) 2581 (match_dup 1) (match_dup 2)))] 2582 "" 2583 "operands[3] = gen_reg_rtx (DImode);") 2584 2585(define_split 2586 [(set (match_operand:DI 0 "register_operand") 2587 (umin:DI (match_operand:DI 1 "reg_or_0_operand") 2588 (match_operand:DI 2 "reg_or_8bit_operand"))) 2589 (clobber (match_operand:DI 3 "register_operand"))] 2590 "operands[2] != const0_rtx" 2591 [(set (match_dup 3) (ltu:DI (match_dup 1) (match_dup 2))) 2592 (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0)) 2593 (match_dup 1) (match_dup 2)))]) 2594 2595(define_insn "*bcc_normal" 2596 [(set (pc) 2597 (if_then_else 2598 (match_operator 1 "signed_comparison_operator" 2599 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 2600 (const_int 0)]) 2601 (label_ref (match_operand 0)) 2602 (pc)))] 2603 "" 2604 "b%C1 %r2,%0" 2605 [(set_attr "type" "ibr")]) 2606 2607(define_insn "*bcc_reverse" 2608 [(set (pc) 2609 (if_then_else 2610 (match_operator 1 "signed_comparison_operator" 2611 [(match_operand:DI 2 "register_operand" "r") 2612 (const_int 0)]) 2613 2614 (pc) 2615 (label_ref (match_operand 0))))] 2616 "" 2617 "b%c1 %2,%0" 2618 [(set_attr "type" "ibr")]) 2619 2620(define_insn "*blbs_normal" 2621 [(set (pc) 2622 (if_then_else 2623 (ne (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 2624 (const_int 1) 2625 (const_int 0)) 2626 (const_int 0)) 2627 (label_ref (match_operand 0)) 2628 (pc)))] 2629 "" 2630 "blbs %r1,%0" 2631 [(set_attr "type" "ibr")]) 2632 2633(define_insn "*blbc_normal" 2634 [(set (pc) 2635 (if_then_else 2636 (eq (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ") 2637 (const_int 1) 2638 (const_int 0)) 2639 (const_int 0)) 2640 (label_ref (match_operand 0)) 2641 (pc)))] 2642 "" 2643 "blbc %r1,%0" 2644 [(set_attr "type" "ibr")]) 2645 2646(define_split 2647 [(parallel 2648 [(set (pc) 2649 (if_then_else 2650 (match_operator 1 "comparison_operator" 2651 [(zero_extract:DI (match_operand:DI 2 "register_operand") 2652 (const_int 1) 2653 (match_operand:DI 3 "const_int_operand")) 2654 (const_int 0)]) 2655 (label_ref (match_operand 0)) 2656 (pc))) 2657 (clobber (match_operand:DI 4 "register_operand"))])] 2658 "INTVAL (operands[3]) != 0" 2659 [(set (match_dup 4) 2660 (lshiftrt:DI (match_dup 2) (match_dup 3))) 2661 (set (pc) 2662 (if_then_else (match_op_dup 1 2663 [(zero_extract:DI (match_dup 4) 2664 (const_int 1) 2665 (const_int 0)) 2666 (const_int 0)]) 2667 (label_ref (match_dup 0)) 2668 (pc)))] 2669 ) 2670 2671;; The following are the corresponding floating-point insns. Recall 2672;; we need to have variants that expand the arguments from SFmode 2673;; to DFmode. 2674 2675(define_insn "*cmpdf_ieee" 2676 [(set (match_operand:DF 0 "register_operand" "=&f") 2677 (match_operator:DF 1 "alpha_fp_comparison_operator" 2678 [(match_operand:DF 2 "reg_or_0_operand" "fG") 2679 (match_operand:DF 3 "reg_or_0_operand" "fG")]))] 2680 "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU" 2681 "cmp%-%C1%/ %R2,%R3,%0" 2682 [(set_attr "type" "fadd") 2683 (set_attr "trap" "yes") 2684 (set_attr "trap_suffix" "su")]) 2685 2686(define_insn "*cmpdf_internal" 2687 [(set (match_operand:DF 0 "register_operand" "=f") 2688 (match_operator:DF 1 "alpha_fp_comparison_operator" 2689 [(match_operand:DF 2 "reg_or_0_operand" "fG") 2690 (match_operand:DF 3 "reg_or_0_operand" "fG")]))] 2691 "TARGET_FP" 2692 "cmp%-%C1%/ %R2,%R3,%0" 2693 [(set_attr "type" "fadd") 2694 (set_attr "trap" "yes") 2695 (set_attr "trap_suffix" "su")]) 2696 2697(define_insn "*cmpdf_ext1" 2698 [(set (match_operand:DF 0 "register_operand" "=f") 2699 (match_operator:DF 1 "alpha_fp_comparison_operator" 2700 [(float_extend:DF 2701 (match_operand:SF 2 "reg_or_0_operand" "fG")) 2702 (match_operand:DF 3 "reg_or_0_operand" "fG")]))] 2703 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2704 "cmp%-%C1%/ %R2,%R3,%0" 2705 [(set_attr "type" "fadd") 2706 (set_attr "trap" "yes") 2707 (set_attr "trap_suffix" "su")]) 2708 2709(define_insn "*cmpdf_ext2" 2710 [(set (match_operand:DF 0 "register_operand" "=f") 2711 (match_operator:DF 1 "alpha_fp_comparison_operator" 2712 [(match_operand:DF 2 "reg_or_0_operand" "fG") 2713 (float_extend:DF 2714 (match_operand:SF 3 "reg_or_0_operand" "fG"))]))] 2715 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2716 "cmp%-%C1%/ %R2,%R3,%0" 2717 [(set_attr "type" "fadd") 2718 (set_attr "trap" "yes") 2719 (set_attr "trap_suffix" "su")]) 2720 2721(define_insn "*cmpdf_ext3" 2722 [(set (match_operand:DF 0 "register_operand" "=f") 2723 (match_operator:DF 1 "alpha_fp_comparison_operator" 2724 [(float_extend:DF 2725 (match_operand:SF 2 "reg_or_0_operand" "fG")) 2726 (float_extend:DF 2727 (match_operand:SF 3 "reg_or_0_operand" "fG"))]))] 2728 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2729 "cmp%-%C1%/ %R2,%R3,%0" 2730 [(set_attr "type" "fadd") 2731 (set_attr "trap" "yes") 2732 (set_attr "trap_suffix" "su")]) 2733 2734(define_insn "*mov<mode>cc_internal" 2735 [(set (match_operand:FMODE 0 "register_operand" "=f,f") 2736 (if_then_else:FMODE 2737 (match_operator 3 "signed_comparison_operator" 2738 [(match_operand:DF 4 "reg_or_0_operand" "fG,fG") 2739 (match_operand:DF 2 "const0_operand" "G,G")]) 2740 (match_operand:FMODE 1 "reg_or_0_operand" "fG,0") 2741 (match_operand:FMODE 5 "reg_or_0_operand" "0,fG")))] 2742 "TARGET_FP" 2743 "@ 2744 fcmov%C3 %R4,%R1,%0 2745 fcmov%D3 %R4,%R5,%0" 2746 [(set_attr "type" "fcmov")]) 2747 2748(define_insn "*movdfcc_ext1" 2749 [(set (match_operand:DF 0 "register_operand" "=f,f") 2750 (if_then_else:DF 2751 (match_operator 3 "signed_comparison_operator" 2752 [(match_operand:DF 4 "reg_or_0_operand" "fG,fG") 2753 (match_operand:DF 2 "const0_operand" "G,G")]) 2754 (float_extend:DF (match_operand:SF 1 "reg_or_0_operand" "fG,0")) 2755 (match_operand:DF 5 "reg_or_0_operand" "0,fG")))] 2756 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2757 "@ 2758 fcmov%C3 %R4,%R1,%0 2759 fcmov%D3 %R4,%R5,%0" 2760 [(set_attr "type" "fcmov")]) 2761 2762(define_insn "*movdfcc_ext2" 2763 [(set (match_operand:DF 0 "register_operand" "=f,f") 2764 (if_then_else:DF 2765 (match_operator 3 "signed_comparison_operator" 2766 [(float_extend:DF 2767 (match_operand:SF 4 "reg_or_0_operand" "fG,fG")) 2768 (match_operand:DF 2 "const0_operand" "G,G")]) 2769 (match_operand:DF 1 "reg_or_0_operand" "fG,0") 2770 (match_operand:DF 5 "reg_or_0_operand" "0,fG")))] 2771 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2772 "@ 2773 fcmov%C3 %R4,%R1,%0 2774 fcmov%D3 %R4,%R5,%0" 2775 [(set_attr "type" "fcmov")]) 2776 2777(define_insn "*movdfcc_ext3" 2778 [(set (match_operand:SF 0 "register_operand" "=f,f") 2779 (if_then_else:SF 2780 (match_operator 3 "signed_comparison_operator" 2781 [(float_extend:DF 2782 (match_operand:SF 4 "reg_or_0_operand" "fG,fG")) 2783 (match_operand:DF 2 "const0_operand" "G,G")]) 2784 (match_operand:SF 1 "reg_or_0_operand" "fG,0") 2785 (match_operand:SF 5 "reg_or_0_operand" "0,fG")))] 2786 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2787 "@ 2788 fcmov%C3 %R4,%R1,%0 2789 fcmov%D3 %R4,%R5,%0" 2790 [(set_attr "type" "fcmov")]) 2791 2792(define_insn "*movdfcc_ext4" 2793 [(set (match_operand:DF 0 "register_operand" "=f,f") 2794 (if_then_else:DF 2795 (match_operator 3 "signed_comparison_operator" 2796 [(float_extend:DF 2797 (match_operand:SF 4 "reg_or_0_operand" "fG,fG")) 2798 (match_operand:DF 2 "const0_operand" "G,G")]) 2799 (float_extend:DF (match_operand:SF 1 "reg_or_0_operand" "fG,0")) 2800 (match_operand:DF 5 "reg_or_0_operand" "0,fG")))] 2801 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2802 "@ 2803 fcmov%C3 %R4,%R1,%0 2804 fcmov%D3 %R4,%R5,%0" 2805 [(set_attr "type" "fcmov")]) 2806 2807(define_expand "smaxdf3" 2808 [(set (match_dup 3) 2809 (le:DF (match_operand:DF 1 "reg_or_0_operand") 2810 (match_operand:DF 2 "reg_or_0_operand"))) 2811 (set (match_operand:DF 0 "register_operand") 2812 (if_then_else:DF (eq (match_dup 3) (match_dup 4)) 2813 (match_dup 1) (match_dup 2)))] 2814 "TARGET_FP" 2815{ 2816 operands[3] = gen_reg_rtx (DFmode); 2817 operands[4] = CONST0_RTX (DFmode); 2818}) 2819 2820(define_expand "smindf3" 2821 [(set (match_dup 3) 2822 (lt:DF (match_operand:DF 1 "reg_or_0_operand") 2823 (match_operand:DF 2 "reg_or_0_operand"))) 2824 (set (match_operand:DF 0 "register_operand") 2825 (if_then_else:DF (ne (match_dup 3) (match_dup 4)) 2826 (match_dup 1) (match_dup 2)))] 2827 "TARGET_FP" 2828{ 2829 operands[3] = gen_reg_rtx (DFmode); 2830 operands[4] = CONST0_RTX (DFmode); 2831}) 2832 2833(define_expand "smaxsf3" 2834 [(set (match_dup 3) 2835 (le:DF (float_extend:DF (match_operand:SF 1 "reg_or_0_operand")) 2836 (float_extend:DF (match_operand:SF 2 "reg_or_0_operand")))) 2837 (set (match_operand:SF 0 "register_operand") 2838 (if_then_else:SF (eq (match_dup 3) (match_dup 4)) 2839 (match_dup 1) (match_dup 2)))] 2840 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2841{ 2842 operands[3] = gen_reg_rtx (DFmode); 2843 operands[4] = CONST0_RTX (DFmode); 2844}) 2845 2846(define_expand "sminsf3" 2847 [(set (match_dup 3) 2848 (lt:DF (float_extend:DF (match_operand:SF 1 "reg_or_0_operand")) 2849 (float_extend:DF (match_operand:SF 2 "reg_or_0_operand")))) 2850 (set (match_operand:SF 0 "register_operand") 2851 (if_then_else:SF (ne (match_dup 3) (match_dup 4)) 2852 (match_dup 1) (match_dup 2)))] 2853 "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU" 2854{ 2855 operands[3] = gen_reg_rtx (DFmode); 2856 operands[4] = CONST0_RTX (DFmode); 2857}) 2858 2859(define_insn "*fbcc_normal" 2860 [(set (pc) 2861 (if_then_else 2862 (match_operator 1 "signed_comparison_operator" 2863 [(match_operand:DF 2 "reg_or_0_operand" "fG") 2864 (match_operand:DF 3 "const0_operand" "G")]) 2865 (label_ref (match_operand 0)) 2866 (pc)))] 2867 "TARGET_FP" 2868 "fb%C1 %R2,%0" 2869 [(set_attr "type" "fbr")]) 2870 2871(define_insn "*fbcc_ext_normal" 2872 [(set (pc) 2873 (if_then_else 2874 (match_operator 1 "signed_comparison_operator" 2875 [(float_extend:DF 2876 (match_operand:SF 2 "reg_or_0_operand" "fG")) 2877 (match_operand:DF 3 "const0_operand" "G")]) 2878 (label_ref (match_operand 0)) 2879 (pc)))] 2880 "TARGET_FP" 2881 "fb%C1 %R2,%0" 2882 [(set_attr "type" "fbr")]) 2883 2884;; These are the main define_expand's used to make conditional branches 2885;; and compares. 2886 2887(define_expand "cbranchdf4" 2888 [(use (match_operator 0 "alpha_cbranch_operator" 2889 [(match_operand:DF 1 "reg_or_0_operand") 2890 (match_operand:DF 2 "reg_or_0_operand")])) 2891 (use (match_operand 3))] 2892 "TARGET_FP" 2893 "alpha_emit_conditional_branch (operands, DFmode); DONE;") 2894 2895(define_expand "cbranchtf4" 2896 [(use (match_operator 0 "alpha_cbranch_operator" 2897 [(match_operand:TF 1 "general_operand") 2898 (match_operand:TF 2 "general_operand")])) 2899 (use (match_operand 3))] 2900 "TARGET_HAS_XFLOATING_LIBS" 2901 "alpha_emit_conditional_branch (operands, TFmode); DONE;") 2902 2903(define_expand "cbranchdi4" 2904 [(use (match_operator 0 "alpha_cbranch_operator" 2905 [(match_operand:DI 1 "general_operand") 2906 (match_operand:DI 2 "general_operand")])) 2907 (use (match_operand 3))] 2908 "" 2909 "alpha_emit_conditional_branch (operands, DImode); DONE;") 2910 2911(define_expand "cstoredf4" 2912 [(use (match_operator:DI 1 "alpha_cbranch_operator" 2913 [(match_operand:DF 2 "reg_or_0_operand") 2914 (match_operand:DF 3 "reg_or_0_operand")])) 2915 (clobber (match_operand:DI 0 "register_operand"))] 2916 "TARGET_FP" 2917{ 2918 if (alpha_emit_setcc (operands, DFmode)) 2919 DONE; 2920 else 2921 FAIL; 2922}) 2923 2924(define_expand "cstoretf4" 2925 [(use (match_operator:DI 1 "alpha_cbranch_operator" 2926 [(match_operand:TF 2 "general_operand") 2927 (match_operand:TF 3 "general_operand")])) 2928 (clobber (match_operand:DI 0 "register_operand"))] 2929 "TARGET_HAS_XFLOATING_LIBS" 2930{ 2931 if (alpha_emit_setcc (operands, TFmode)) 2932 DONE; 2933 else 2934 FAIL; 2935}) 2936 2937(define_expand "cstoredi4" 2938 [(use (match_operator:DI 1 "alpha_cbranch_operator" 2939 [(match_operand:DI 2 "general_operand") 2940 (match_operand:DI 3 "general_operand")])) 2941 (clobber (match_operand:DI 0 "register_operand"))] 2942 "" 2943{ 2944 if (alpha_emit_setcc (operands, DImode)) 2945 DONE; 2946 else 2947 FAIL; 2948}) 2949 2950;; These are the main define_expand's used to make conditional moves. 2951 2952(define_expand "mov<mode>cc" 2953 [(set (match_operand:I48MODE 0 "register_operand") 2954 (if_then_else:I48MODE 2955 (match_operand 1 "comparison_operator") 2956 (match_operand:I48MODE 2 "reg_or_8bit_operand") 2957 (match_operand:I48MODE 3 "reg_or_8bit_operand")))] 2958 "" 2959{ 2960 operands[1] = alpha_emit_conditional_move (operands[1], <MODE>mode); 2961 if (operands[1] == 0) 2962 FAIL; 2963}) 2964 2965(define_expand "mov<mode>cc" 2966 [(set (match_operand:FMODE 0 "register_operand") 2967 (if_then_else:FMODE 2968 (match_operand 1 "comparison_operator") 2969 (match_operand:FMODE 2 "reg_or_8bit_operand") 2970 (match_operand:FMODE 3 "reg_or_8bit_operand")))] 2971 "" 2972{ 2973 operands[1] = alpha_emit_conditional_move (operands[1], <MODE>mode); 2974 if (operands[1] == 0) 2975 FAIL; 2976}) 2977 2978;; These define_split definitions are used in cases when comparisons have 2979;; not be stated in the correct way and we need to reverse the second 2980;; comparison. For example, x >= 7 has to be done as x < 6 with the 2981;; comparison that tests the result being reversed. We have one define_split 2982;; for each use of a comparison. They do not match valid insns and need 2983;; not generate valid insns. 2984;; 2985;; We can also handle equality comparisons (and inequality comparisons in 2986;; cases where the resulting add cannot overflow) by doing an add followed by 2987;; a comparison with zero. This is faster since the addition takes one 2988;; less cycle than a compare when feeding into a conditional move. 2989;; For this case, we also have an SImode pattern since we can merge the add 2990;; and sign extend and the order doesn't matter. 2991;; 2992;; We do not do this for floating-point, since it isn't clear how the "wrong" 2993;; operation could have been generated. 2994 2995(define_split 2996 [(set (match_operand:DI 0 "register_operand") 2997 (if_then_else:DI 2998 (match_operator 1 "comparison_operator" 2999 [(match_operand:DI 2 "reg_or_0_operand") 3000 (match_operand:DI 3 "reg_or_cint_operand")]) 3001 (match_operand:DI 4 "reg_or_cint_operand") 3002 (match_operand:DI 5 "reg_or_cint_operand"))) 3003 (clobber (match_operand:DI 6 "register_operand"))] 3004 "operands[3] != const0_rtx" 3005 [(set (match_dup 6) (match_dup 7)) 3006 (set (match_dup 0) 3007 (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))] 3008{ 3009 enum rtx_code code = GET_CODE (operands[1]); 3010 int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU); 3011 3012 /* If we are comparing for equality with a constant and that constant 3013 appears in the arm when the register equals the constant, use the 3014 register since that is more likely to match (and to produce better code 3015 if both would). */ 3016 3017 if (code == EQ && CONST_INT_P (operands[3]) 3018 && rtx_equal_p (operands[4], operands[3])) 3019 operands[4] = operands[2]; 3020 3021 else if (code == NE && CONST_INT_P (operands[3]) 3022 && rtx_equal_p (operands[5], operands[3])) 3023 operands[5] = operands[2]; 3024 3025 if (code == NE || code == EQ 3026 || (extended_count (operands[2], DImode, unsignedp) >= 1 3027 && extended_count (operands[3], DImode, unsignedp) >= 1)) 3028 { 3029 if (CONST_INT_P (operands[3])) 3030 operands[7] = gen_rtx_PLUS (DImode, operands[2], 3031 GEN_INT (- INTVAL (operands[3]))); 3032 else 3033 operands[7] = gen_rtx_MINUS (DImode, operands[2], operands[3]); 3034 3035 operands[8] = gen_rtx_fmt_ee (code, VOIDmode, operands[6], const0_rtx); 3036 } 3037 3038 else if (code == EQ || code == LE || code == LT 3039 || code == LEU || code == LTU) 3040 { 3041 operands[7] = gen_rtx_fmt_ee (code, DImode, operands[2], operands[3]); 3042 operands[8] = gen_rtx_NE (VOIDmode, operands[6], const0_rtx); 3043 } 3044 else 3045 { 3046 operands[7] = gen_rtx_fmt_ee (reverse_condition (code), DImode, 3047 operands[2], operands[3]); 3048 operands[8] = gen_rtx_EQ (VOIDmode, operands[6], const0_rtx); 3049 } 3050}) 3051 3052(define_split 3053 [(set (match_operand:DI 0 "register_operand") 3054 (if_then_else:DI 3055 (match_operator 1 "comparison_operator" 3056 [(match_operand:SI 2 "reg_or_0_operand") 3057 (match_operand:SI 3 "reg_or_cint_operand")]) 3058 (match_operand:DI 4 "reg_or_8bit_operand") 3059 (match_operand:DI 5 "reg_or_8bit_operand"))) 3060 (clobber (match_operand:DI 6 "register_operand"))] 3061 "operands[3] != const0_rtx 3062 && (GET_CODE (operands[1]) == EQ || GET_CODE (operands[1]) == NE)" 3063 [(set (match_dup 6) (match_dup 7)) 3064 (set (match_dup 0) 3065 (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))] 3066{ 3067 enum rtx_code code = GET_CODE (operands[1]); 3068 int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU); 3069 rtx tem; 3070 3071 if ((code != NE && code != EQ 3072 && ! (extended_count (operands[2], DImode, unsignedp) >= 1 3073 && extended_count (operands[3], DImode, unsignedp) >= 1))) 3074 FAIL; 3075 3076 if (CONST_INT_P (operands[3])) 3077 tem = gen_rtx_PLUS (SImode, operands[2], 3078 GEN_INT (- INTVAL (operands[3]))); 3079 else 3080 tem = gen_rtx_MINUS (SImode, operands[2], operands[3]); 3081 3082 operands[7] = gen_rtx_SIGN_EXTEND (DImode, tem); 3083 operands[8] = gen_rtx_fmt_ee (GET_CODE (operands[1]), VOIDmode, 3084 operands[6], const0_rtx); 3085}) 3086 3087;; Prefer to use cmp and arithmetic when possible instead of a cmove. 3088 3089(define_split 3090 [(set (match_operand 0 "register_operand") 3091 (if_then_else (match_operator 1 "signed_comparison_operator" 3092 [(match_operand:DI 2 "reg_or_0_operand") 3093 (const_int 0)]) 3094 (match_operand 3 "const_int_operand") 3095 (match_operand 4 "const_int_operand")))] 3096 "" 3097 [(const_int 0)] 3098{ 3099 if (alpha_split_conditional_move (GET_CODE (operands[1]), operands[0], 3100 operands[2], operands[3], operands[4])) 3101 DONE; 3102 else 3103 FAIL; 3104}) 3105 3106;; ??? Why combine is allowed to create such non-canonical rtl, I don't know. 3107;; Oh well, we match it in movcc, so it must be partially our fault. 3108(define_split 3109 [(set (match_operand 0 "register_operand") 3110 (if_then_else (match_operator 1 "signed_comparison_operator" 3111 [(const_int 0) 3112 (match_operand:DI 2 "reg_or_0_operand")]) 3113 (match_operand 3 "const_int_operand") 3114 (match_operand 4 "const_int_operand")))] 3115 "" 3116 [(const_int 0)] 3117{ 3118 if (alpha_split_conditional_move (swap_condition (GET_CODE (operands[1])), 3119 operands[0], operands[2], operands[3], 3120 operands[4])) 3121 DONE; 3122 else 3123 FAIL; 3124}) 3125 3126(define_insn_and_split "*cmp_sadd_di" 3127 [(set (match_operand:DI 0 "register_operand" "=r") 3128 (plus:DI (if_then_else:DI 3129 (match_operator 1 "alpha_zero_comparison_operator" 3130 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3131 (const_int 0)]) 3132 (match_operand:DI 3 "const48_operand" "I") 3133 (const_int 0)) 3134 (match_operand:DI 4 "sext_add_operand" "rIO"))) 3135 (clobber (match_scratch:DI 5 "=r"))] 3136 "" 3137 "#" 3138 "" 3139 [(set (match_dup 5) 3140 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3141 (set (match_dup 0) 3142 (plus:DI (mult:DI (match_dup 5) (match_dup 3)) 3143 (match_dup 4)))] 3144{ 3145 if (can_create_pseudo_p ()) 3146 operands[5] = gen_reg_rtx (DImode); 3147 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3148 operands[5] = operands[0]; 3149}) 3150 3151(define_insn_and_split "*cmp_sadd_si" 3152 [(set (match_operand:SI 0 "register_operand" "=r") 3153 (plus:SI (if_then_else:SI 3154 (match_operator 1 "alpha_zero_comparison_operator" 3155 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3156 (const_int 0)]) 3157 (match_operand:SI 3 "const48_operand" "I") 3158 (const_int 0)) 3159 (match_operand:SI 4 "sext_add_operand" "rIO"))) 3160 (clobber (match_scratch:DI 5 "=r"))] 3161 "" 3162 "#" 3163 "" 3164 [(set (match_dup 5) 3165 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3166 (set (match_dup 0) 3167 (plus:SI (mult:SI (match_dup 6) (match_dup 3)) 3168 (match_dup 4)))] 3169{ 3170 if (can_create_pseudo_p ()) 3171 operands[5] = gen_reg_rtx (DImode); 3172 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3173 operands[5] = gen_lowpart (DImode, operands[0]); 3174 3175 operands[6] = gen_lowpart (SImode, operands[5]); 3176}) 3177 3178(define_insn_and_split "*cmp_sadd_sidi" 3179 [(set (match_operand:DI 0 "register_operand" "=r") 3180 (sign_extend:DI 3181 (plus:SI (if_then_else:SI 3182 (match_operator 1 "alpha_zero_comparison_operator" 3183 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3184 (const_int 0)]) 3185 (match_operand:SI 3 "const48_operand" "I") 3186 (const_int 0)) 3187 (match_operand:SI 4 "sext_add_operand" "rIO")))) 3188 (clobber (match_scratch:DI 5 "=r"))] 3189 "" 3190 "#" 3191 "" 3192 [(set (match_dup 5) 3193 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3194 (set (match_dup 0) 3195 (sign_extend:DI (plus:SI (mult:SI (match_dup 6) (match_dup 3)) 3196 (match_dup 4))))] 3197{ 3198 if (can_create_pseudo_p ()) 3199 operands[5] = gen_reg_rtx (DImode); 3200 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3201 operands[5] = operands[0]; 3202 3203 operands[6] = gen_lowpart (SImode, operands[5]); 3204}) 3205 3206(define_insn_and_split "*cmp_ssub_di" 3207 [(set (match_operand:DI 0 "register_operand" "=r") 3208 (minus:DI (if_then_else:DI 3209 (match_operator 1 "alpha_zero_comparison_operator" 3210 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3211 (const_int 0)]) 3212 (match_operand:DI 3 "const48_operand" "I") 3213 (const_int 0)) 3214 (match_operand:DI 4 "reg_or_8bit_operand" "rI"))) 3215 (clobber (match_scratch:DI 5 "=r"))] 3216 "" 3217 "#" 3218 "" 3219 [(set (match_dup 5) 3220 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3221 (set (match_dup 0) 3222 (minus:DI (mult:DI (match_dup 5) (match_dup 3)) 3223 (match_dup 4)))] 3224{ 3225 if (can_create_pseudo_p ()) 3226 operands[5] = gen_reg_rtx (DImode); 3227 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3228 operands[5] = operands[0]; 3229}) 3230 3231(define_insn_and_split "*cmp_ssub_si" 3232 [(set (match_operand:SI 0 "register_operand" "=r") 3233 (minus:SI (if_then_else:SI 3234 (match_operator 1 "alpha_zero_comparison_operator" 3235 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3236 (const_int 0)]) 3237 (match_operand:SI 3 "const48_operand" "I") 3238 (const_int 0)) 3239 (match_operand:SI 4 "reg_or_8bit_operand" "rI"))) 3240 (clobber (match_scratch:DI 5 "=r"))] 3241 "" 3242 "#" 3243 "" 3244 [(set (match_dup 5) 3245 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3246 (set (match_dup 0) 3247 (minus:SI (mult:SI (match_dup 6) (match_dup 3)) 3248 (match_dup 4)))] 3249{ 3250 if (can_create_pseudo_p ()) 3251 operands[5] = gen_reg_rtx (DImode); 3252 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3253 operands[5] = gen_lowpart (DImode, operands[0]); 3254 3255 operands[6] = gen_lowpart (SImode, operands[5]); 3256}) 3257 3258(define_insn_and_split "*cmp_ssub_sidi" 3259 [(set (match_operand:DI 0 "register_operand" "=r") 3260 (sign_extend:DI 3261 (minus:SI (if_then_else:SI 3262 (match_operator 1 "alpha_zero_comparison_operator" 3263 [(match_operand:DI 2 "reg_or_0_operand" "rJ") 3264 (const_int 0)]) 3265 (match_operand:SI 3 "const48_operand" "I") 3266 (const_int 0)) 3267 (match_operand:SI 4 "reg_or_8bit_operand" "rI")))) 3268 (clobber (match_scratch:DI 5 "=r"))] 3269 "" 3270 "#" 3271 "" 3272 [(set (match_dup 5) 3273 (match_op_dup:DI 1 [(match_dup 2) (const_int 0)])) 3274 (set (match_dup 0) 3275 (sign_extend:DI (minus:SI (mult:SI (match_dup 6) (match_dup 3)) 3276 (match_dup 4))))] 3277{ 3278 if (can_create_pseudo_p ()) 3279 operands[5] = gen_reg_rtx (DImode); 3280 else if (reg_overlap_mentioned_p (operands[5], operands[4])) 3281 operands[5] = operands[0]; 3282 3283 operands[6] = gen_lowpart (SImode, operands[5]); 3284}) 3285 3286;; Here are the CALL and unconditional branch insns. Calls on NT and OSF 3287;; work differently, so we have different patterns for each. 3288 3289(define_expand "call" 3290 [(use (match_operand:DI 0)) 3291 (use (match_operand 1)) 3292 (use (match_operand 2)) 3293 (use (match_operand 3))] 3294 "" 3295{ 3296 if (TARGET_ABI_OPEN_VMS) 3297 emit_call_insn (gen_call_vms (operands[0], operands[2])); 3298 else 3299 emit_call_insn (gen_call_osf (operands[0], operands[1])); 3300 DONE; 3301}) 3302 3303(define_expand "sibcall" 3304 [(parallel [(call (mem:DI (match_operand 0)) 3305 (match_operand 1)) 3306 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)])] 3307 "TARGET_ABI_OSF" 3308{ 3309 gcc_assert (MEM_P (operands[0])); 3310 operands[0] = XEXP (operands[0], 0); 3311}) 3312 3313(define_expand "call_osf" 3314 [(parallel [(call (mem:DI (match_operand 0)) 3315 (match_operand 1)) 3316 (use (reg:DI 29)) 3317 (clobber (reg:DI 26))])] 3318 "" 3319{ 3320 gcc_assert (MEM_P (operands[0])); 3321 3322 operands[0] = XEXP (operands[0], 0); 3323 if (! call_operand (operands[0], Pmode)) 3324 operands[0] = copy_to_mode_reg (Pmode, operands[0]); 3325}) 3326 3327;; 3328;; call openvms/alpha 3329;; op 0: symbol ref for called function 3330;; op 1: next_arg_reg (argument information value for R25) 3331;; 3332(define_expand "call_vms" 3333 [(parallel [(call (mem:DI (match_operand 0)) 3334 (match_operand 1)) 3335 (use (match_dup 2)) 3336 (use (reg:DI 25)) 3337 (use (reg:DI 26)) 3338 (clobber (reg:DI 27))])] 3339 "" 3340{ 3341 gcc_assert (MEM_P (operands[0])); 3342 3343 operands[0] = XEXP (operands[0], 0); 3344 3345 /* Always load AI with argument information, then handle symbolic and 3346 indirect call differently. Load RA and set operands[2] to PV in 3347 both cases. */ 3348 3349 emit_move_insn (gen_rtx_REG (DImode, 25), operands[1]); 3350 if (GET_CODE (operands[0]) == SYMBOL_REF) 3351 { 3352 operands[2] = const0_rtx; 3353 } 3354 else 3355 { 3356 emit_move_insn (gen_rtx_REG (Pmode, 26), 3357 gen_rtx_MEM (Pmode, plus_constant (Pmode, 3358 operands[0], 8))); 3359 operands[2] = operands[0]; 3360 } 3361}) 3362 3363(define_expand "call_value" 3364 [(use (match_operand 0)) 3365 (use (match_operand:DI 1)) 3366 (use (match_operand 2)) 3367 (use (match_operand 3)) 3368 (use (match_operand 4))] 3369 "" 3370{ 3371 if (TARGET_ABI_OPEN_VMS) 3372 emit_call_insn (gen_call_value_vms (operands[0], operands[1], 3373 operands[3])); 3374 else 3375 emit_call_insn (gen_call_value_osf (operands[0], operands[1], 3376 operands[2])); 3377 DONE; 3378}) 3379 3380(define_expand "sibcall_value" 3381 [(parallel [(set (match_operand 0) 3382 (call (mem:DI (match_operand 1)) 3383 (match_operand 2))) 3384 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)])] 3385 "TARGET_ABI_OSF" 3386{ 3387 gcc_assert (MEM_P (operands[1])); 3388 operands[1] = XEXP (operands[1], 0); 3389}) 3390 3391(define_expand "call_value_osf" 3392 [(parallel [(set (match_operand 0) 3393 (call (mem:DI (match_operand 1)) 3394 (match_operand 2))) 3395 (use (reg:DI 29)) 3396 (clobber (reg:DI 26))])] 3397 "" 3398{ 3399 gcc_assert (MEM_P (operands[1])); 3400 3401 operands[1] = XEXP (operands[1], 0); 3402 if (! call_operand (operands[1], Pmode)) 3403 operands[1] = copy_to_mode_reg (Pmode, operands[1]); 3404}) 3405 3406(define_expand "call_value_vms" 3407 [(parallel [(set (match_operand 0) 3408 (call (mem:DI (match_operand:DI 1)) 3409 (match_operand 2))) 3410 (use (match_dup 3)) 3411 (use (reg:DI 25)) 3412 (use (reg:DI 26)) 3413 (clobber (reg:DI 27))])] 3414 "" 3415{ 3416 gcc_assert (MEM_P (operands[1])); 3417 3418 operands[1] = XEXP (operands[1], 0); 3419 3420 /* Always load AI with argument information, then handle symbolic and 3421 indirect call differently. Load RA and set operands[3] to PV in 3422 both cases. */ 3423 3424 emit_move_insn (gen_rtx_REG (DImode, 25), operands[2]); 3425 if (GET_CODE (operands[1]) == SYMBOL_REF) 3426 { 3427 operands[3] = const0_rtx; 3428 } 3429 else 3430 { 3431 emit_move_insn (gen_rtx_REG (Pmode, 26), 3432 gen_rtx_MEM (Pmode, plus_constant (Pmode, 3433 operands[1], 8))); 3434 operands[3] = operands[1]; 3435 } 3436}) 3437 3438(define_insn "*call_osf_1_er_noreturn" 3439 [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s")) 3440 (match_operand 1)) 3441 (use (reg:DI 29)) 3442 (clobber (reg:DI 26))] 3443 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF 3444 && find_reg_note (insn, REG_NORETURN, NULL_RTX)" 3445 "@ 3446 jsr $26,($27),0 3447 bsr $26,%0\t\t!samegp 3448 ldq $27,%0($29)\t\t!literal!%#\;jsr $26,($27),%0\t\t!lituse_jsr!%#" 3449 [(set_attr "type" "jsr") 3450 (set_attr "length" "*,*,8")]) 3451 3452(define_insn "*call_osf_1_er" 3453 [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s")) 3454 (match_operand 1)) 3455 (use (reg:DI 29)) 3456 (clobber (reg:DI 26))] 3457 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3458 "@ 3459 jsr $26,(%0),0\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%* 3460 bsr $26,%0\t\t!samegp 3461 ldq $27,%0($29)\t\t!literal!%#\;jsr $26,($27),%0\t\t!lituse_jsr!%#\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*" 3462 [(set_attr "type" "jsr") 3463 (set_attr "length" "12,*,16")]) 3464 3465;; We must use peep2 instead of a split because we need accurate life 3466;; information for $gp. Consider the case of { bar(); while (1); }. 3467(define_peephole2 3468 [(parallel [(call (mem:DI (match_operand:DI 0 "call_operand")) 3469 (match_operand 1)) 3470 (use (reg:DI 29)) 3471 (clobber (reg:DI 26))])] 3472 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed 3473 && ! samegp_function_operand (operands[0], Pmode) 3474 && (peep2_regno_dead_p (1, 29) 3475 || find_reg_note (insn, REG_NORETURN, NULL_RTX))" 3476 [(parallel [(call (mem:DI (match_dup 2)) 3477 (match_dup 1)) 3478 (use (reg:DI 29)) 3479 (use (match_dup 0)) 3480 (use (match_dup 3)) 3481 (clobber (reg:DI 26))])] 3482{ 3483 if (CONSTANT_P (operands[0])) 3484 { 3485 operands[2] = gen_rtx_REG (Pmode, 27); 3486 operands[3] = GEN_INT (alpha_next_sequence_number++); 3487 emit_insn (gen_movdi_er_high_g (operands[2], pic_offset_table_rtx, 3488 operands[0], operands[3])); 3489 } 3490 else 3491 { 3492 operands[2] = operands[0]; 3493 operands[0] = const0_rtx; 3494 operands[3] = const0_rtx; 3495 } 3496}) 3497 3498(define_peephole2 3499 [(parallel [(call (mem:DI (match_operand:DI 0 "call_operand")) 3500 (match_operand 1)) 3501 (use (reg:DI 29)) 3502 (clobber (reg:DI 26))])] 3503 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed 3504 && ! samegp_function_operand (operands[0], Pmode) 3505 && ! (peep2_regno_dead_p (1, 29) 3506 || find_reg_note (insn, REG_NORETURN, NULL_RTX))" 3507 [(parallel [(call (mem:DI (match_dup 2)) 3508 (match_dup 1)) 3509 (set (match_dup 5) 3510 (unspec:DI [(match_dup 5) (match_dup 3)] UNSPEC_LDGP1)) 3511 (use (match_dup 0)) 3512 (use (match_dup 4)) 3513 (clobber (reg:DI 26))]) 3514 (set (match_dup 5) 3515 (unspec:DI [(match_dup 5) (match_dup 3)] UNSPEC_LDGP2))] 3516{ 3517 if (CONSTANT_P (operands[0])) 3518 { 3519 operands[2] = gen_rtx_REG (Pmode, 27); 3520 operands[4] = GEN_INT (alpha_next_sequence_number++); 3521 emit_insn (gen_movdi_er_high_g (operands[2], pic_offset_table_rtx, 3522 operands[0], operands[4])); 3523 } 3524 else 3525 { 3526 operands[2] = operands[0]; 3527 operands[0] = const0_rtx; 3528 operands[4] = const0_rtx; 3529 } 3530 operands[3] = GEN_INT (alpha_next_sequence_number++); 3531 operands[5] = pic_offset_table_rtx; 3532}) 3533 3534(define_insn "*call_osf_2_er_nogp" 3535 [(call (mem:DI (match_operand:DI 0 "register_operand" "c")) 3536 (match_operand 1)) 3537 (use (reg:DI 29)) 3538 (use (match_operand 2)) 3539 (use (match_operand 3 "const_int_operand")) 3540 (clobber (reg:DI 26))] 3541 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3542 "jsr $26,(%0),%2%J3" 3543 [(set_attr "type" "jsr")]) 3544 3545(define_insn "*call_osf_2_er" 3546 [(call (mem:DI (match_operand:DI 0 "register_operand" "c")) 3547 (match_operand 1)) 3548 (set (reg:DI 29) 3549 (unspec:DI [(reg:DI 29) (match_operand 4 "const_int_operand")] 3550 UNSPEC_LDGP1)) 3551 (use (match_operand 2)) 3552 (use (match_operand 3 "const_int_operand")) 3553 (clobber (reg:DI 26))] 3554 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3555 "jsr $26,(%0),%2%J3\;ldah $29,0($26)\t\t!gpdisp!%4" 3556 [(set_attr "type" "jsr") 3557 (set_attr "cannot_copy" "true") 3558 (set_attr "length" "8")]) 3559 3560(define_insn "*call_osf_1_noreturn" 3561 [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s")) 3562 (match_operand 1)) 3563 (use (reg:DI 29)) 3564 (clobber (reg:DI 26))] 3565 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF 3566 && find_reg_note (insn, REG_NORETURN, NULL_RTX)" 3567 "@ 3568 jsr $26,($27),0 3569 bsr $26,$%0..ng 3570 jsr $26,%0" 3571 [(set_attr "type" "jsr") 3572 (set_attr "length" "*,*,8")]) 3573 3574(define_insn "*call_osf_1" 3575 [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s")) 3576 (match_operand 1)) 3577 (use (reg:DI 29)) 3578 (clobber (reg:DI 26))] 3579 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3580 "@ 3581 jsr $26,($27),0\;ldgp $29,0($26) 3582 bsr $26,$%0..ng 3583 jsr $26,%0\;ldgp $29,0($26)" 3584 [(set_attr "type" "jsr") 3585 (set_attr "length" "12,*,16")]) 3586 3587(define_insn "*sibcall_osf_1_er" 3588 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "R,s")) 3589 (match_operand 1)) 3590 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)] 3591 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3592 "@ 3593 br $31,%0\t\t!samegp 3594 ldq $27,%0($29)\t\t!literal!%#\;jmp $31,($27),%0\t\t!lituse_jsr!%#" 3595 [(set_attr "type" "jsr") 3596 (set_attr "length" "*,8")]) 3597 3598;; Note that the DEC assembler expands "jmp foo" with $at, which 3599;; doesn't do what we want. 3600(define_insn "*sibcall_osf_1" 3601 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "R,s")) 3602 (match_operand 1)) 3603 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)] 3604 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 3605 "@ 3606 br $31,$%0..ng 3607 lda $27,%0\;jmp $31,($27),%0" 3608 [(set_attr "type" "jsr") 3609 (set_attr "length" "*,8")]) 3610 3611; GAS relies on the order and position of instructions output below in order 3612; to generate relocs for VMS link to potentially optimize the call. 3613; Please do not molest. 3614(define_insn "*call_vms_1" 3615 [(call (mem:DI (match_operand:DI 0 "call_operand" "r,s")) 3616 (match_operand 1)) 3617 (use (match_operand:DI 2 "nonmemory_operand" "r,n")) 3618 (use (reg:DI 25)) 3619 (use (reg:DI 26)) 3620 (clobber (reg:DI 27))] 3621 "TARGET_ABI_OPEN_VMS" 3622{ 3623 switch (which_alternative) 3624 { 3625 case 0: 3626 return "mov %2,$27\;jsr $26,0\;ldq $27,0($29)"; 3627 case 1: 3628 operands [2] = alpha_use_linkage (operands [0], true, false); 3629 operands [3] = alpha_use_linkage (operands [0], false, false); 3630 return "ldq $26,%3\;ldq $27,%2\;jsr $26,%0\;ldq $27,0($29)"; 3631 default: 3632 gcc_unreachable (); 3633 } 3634} 3635 [(set_attr "type" "jsr") 3636 (set_attr "length" "12,16")]) 3637 3638;; Call subroutine returning any type. 3639 3640(define_expand "untyped_call" 3641 [(parallel [(call (match_operand 0) 3642 (const_int 0)) 3643 (match_operand 1) 3644 (match_operand 2)])] 3645 "" 3646{ 3647 int i; 3648 3649 emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx)); 3650 3651 for (i = 0; i < XVECLEN (operands[2], 0); i++) 3652 { 3653 rtx set = XVECEXP (operands[2], 0, i); 3654 emit_move_insn (SET_DEST (set), SET_SRC (set)); 3655 } 3656 3657 /* The optimizer does not know that the call sets the function value 3658 registers we stored in the result block. We avoid problems by 3659 claiming that all hard registers are used and clobbered at this 3660 point. */ 3661 emit_insn (gen_blockage ()); 3662 3663 DONE; 3664}) 3665 3666;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and 3667;; all of memory. This blocks insns from being moved across this point. 3668 3669(define_insn "blockage" 3670 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)] 3671 "" 3672 "" 3673 [(set_attr "length" "0") 3674 (set_attr "type" "none")]) 3675 3676(define_insn "jump" 3677 [(set (pc) 3678 (label_ref (match_operand 0)))] 3679 "" 3680 "br $31,%l0" 3681 [(set_attr "type" "ibr")]) 3682 3683(define_expand "return" 3684 [(return)] 3685 "direct_return ()") 3686 3687(define_insn "*return_internal" 3688 [(return)] 3689 "reload_completed" 3690 "ret $31,($26),1" 3691 [(set_attr "type" "ibr")]) 3692 3693(define_insn "indirect_jump" 3694 [(set (pc) (match_operand:DI 0 "register_operand" "r"))] 3695 "" 3696 "jmp $31,(%0),0" 3697 [(set_attr "type" "ibr")]) 3698 3699(define_expand "tablejump" 3700 [(parallel [(set (pc) 3701 (match_operand 0 "register_operand")) 3702 (use (label_ref:DI (match_operand 1)))])] 3703 "" 3704{ 3705 if (TARGET_ABI_OSF) 3706 { 3707 rtx dest = gen_reg_rtx (DImode); 3708 emit_insn (gen_extendsidi2 (dest, operands[0])); 3709 emit_insn (gen_adddi3 (dest, pic_offset_table_rtx, dest)); 3710 operands[0] = dest; 3711 } 3712}) 3713 3714(define_insn "*tablejump_internal" 3715 [(set (pc) 3716 (match_operand:DI 0 "register_operand" "r")) 3717 (use (label_ref (match_operand 1)))] 3718 "" 3719 "jmp $31,(%0),0" 3720 [(set_attr "type" "ibr")]) 3721 3722;; Cache flush. Used by alpha_trampoline_init. 0x86 is PAL_imb, but we don't 3723;; want to have to include pal.h in our .s file. 3724(define_insn "imb" 3725 [(unspec_volatile [(const_int 0)] UNSPECV_IMB)] 3726 "" 3727 "call_pal 0x86" 3728 [(set_attr "type" "callpal")]) 3729 3730(define_expand "clear_cache" 3731 [(match_operand:DI 0) ; region start 3732 (match_operand:DI 1)] ; region end 3733 "" 3734{ 3735 emit_insn (gen_imb ()); 3736 DONE; 3737}) 3738 3739;; BUGCHK is documented common to OSF/1 and VMS PALcode. 3740(define_insn "trap" 3741 [(trap_if (const_int 1) (const_int 0)) 3742 (use (reg:DI 29))] 3743 "" 3744 "call_pal 0x81" 3745 [(set_attr "type" "callpal")]) 3746 3747;; For userland, we load the thread pointer from the TCB. 3748;; For the kernel, we load the per-cpu private value. 3749 3750(define_insn "get_thread_pointerdi" 3751 [(set (match_operand:DI 0 "register_operand" "=v") 3752 (unspec:DI [(const_int 0)] UNSPEC_TP))] 3753 "TARGET_ABI_OSF" 3754{ 3755 if (TARGET_TLS_KERNEL) 3756 return "call_pal 0x32"; 3757 else 3758 return "call_pal 0x9e"; 3759} 3760 [(set_attr "type" "callpal")]) 3761 3762;; For completeness, and possibly a __builtin function, here's how to 3763;; set the thread pointer. Since we don't describe enough of this 3764;; quantity for CSE, we have to use a volatile unspec, and then there's 3765;; not much point in creating an R16_REG register class. 3766 3767(define_expand "set_thread_pointerdi" 3768 [(set (reg:DI 16) (match_operand:DI 0 "input_operand")) 3769 (unspec_volatile [(reg:DI 16)] UNSPECV_SET_TP)] 3770 "TARGET_ABI_OSF") 3771 3772(define_insn "*set_tp" 3773 [(unspec_volatile [(reg:DI 16)] UNSPECV_SET_TP)] 3774 "TARGET_ABI_OSF" 3775{ 3776 if (TARGET_TLS_KERNEL) 3777 return "call_pal 0x31"; 3778 else 3779 return "call_pal 0x9f"; 3780} 3781 [(set_attr "type" "callpal")]) 3782 3783;; Special builtins for establishing and reverting VMS condition handlers. 3784 3785(define_expand "builtin_establish_vms_condition_handler" 3786 [(set (reg:DI 0) (match_operand:DI 0 "register_operand")) 3787 (use (match_operand:DI 1 "address_operand"))] 3788 "TARGET_ABI_OPEN_VMS" 3789{ 3790 alpha_expand_builtin_establish_vms_condition_handler (operands[0], 3791 operands[1]); 3792}) 3793 3794(define_expand "builtin_revert_vms_condition_handler" 3795 [(set (reg:DI 0) (match_operand:DI 0 "register_operand"))] 3796 "TARGET_ABI_OPEN_VMS" 3797 "alpha_expand_builtin_revert_vms_condition_handler (operands[0]);") 3798 3799;; Finally, we have the basic data motion insns. The byte and word insns 3800;; are done via define_expand. Start with the floating-point insns, since 3801;; they are simpler. 3802 3803(define_expand "movsf" 3804 [(set (match_operand:SF 0 "nonimmediate_operand") 3805 (match_operand:SF 1 "general_operand"))] 3806 "" 3807{ 3808 if (MEM_P (operands[0]) 3809 && ! reg_or_0_operand (operands[1], SFmode)) 3810 operands[1] = force_reg (SFmode, operands[1]); 3811}) 3812 3813(define_insn "*movsf" 3814 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m,f,*r") 3815 (match_operand:SF 1 "input_operand" "fG,m,*rG,m,fG,*r,*r,f"))] 3816 "register_operand (operands[0], SFmode) 3817 || reg_or_0_operand (operands[1], SFmode)" 3818 "@ 3819 cpys %R1,%R1,%0 3820 ld%, %0,%1 3821 bis $31,%r1,%0 3822 ldl %0,%1 3823 st%, %R1,%0 3824 stl %r1,%0 3825 itofs %1,%0 3826 ftois %1,%0" 3827 [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist,itof,ftoi") 3828 (set_attr "isa" "*,*,*,*,*,*,fix,fix")]) 3829 3830(define_expand "movdf" 3831 [(set (match_operand:DF 0 "nonimmediate_operand") 3832 (match_operand:DF 1 "general_operand"))] 3833 "" 3834{ 3835 if (MEM_P (operands[0]) 3836 && ! reg_or_0_operand (operands[1], DFmode)) 3837 operands[1] = force_reg (DFmode, operands[1]); 3838}) 3839 3840(define_insn "*movdf" 3841 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m,f,*r") 3842 (match_operand:DF 1 "input_operand" "fG,m,*rG,m,fG,*r,*r,f"))] 3843 "register_operand (operands[0], DFmode) 3844 || reg_or_0_operand (operands[1], DFmode)" 3845 "@ 3846 cpys %R1,%R1,%0 3847 ld%- %0,%1 3848 bis $31,%r1,%0 3849 ldq %0,%1 3850 st%- %R1,%0 3851 stq %r1,%0 3852 itoft %1,%0 3853 ftoit %1,%0" 3854 [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist,itof,ftoi") 3855 (set_attr "isa" "*,*,*,*,*,*,fix,fix")]) 3856 3857;; Subregs suck for register allocation. Pretend we can move TFmode 3858;; data between general registers until after reload. 3859;; ??? Is this still true now that we have the lower-subreg pass? 3860 3861(define_expand "movtf" 3862 [(set (match_operand:TF 0 "nonimmediate_operand") 3863 (match_operand:TF 1 "general_operand"))] 3864 "" 3865{ 3866 if (MEM_P (operands[0]) 3867 && ! reg_or_0_operand (operands[1], TFmode)) 3868 operands[1] = force_reg (TFmode, operands[1]); 3869}) 3870 3871(define_insn_and_split "*movtf_internal" 3872 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o") 3873 (match_operand:TF 1 "input_operand" "roG,rG"))] 3874 "register_operand (operands[0], TFmode) 3875 || reg_or_0_operand (operands[1], TFmode)" 3876 "#" 3877 "reload_completed" 3878 [(set (match_dup 0) (match_dup 2)) 3879 (set (match_dup 1) (match_dup 3))] 3880 "alpha_split_tmode_pair (operands, TFmode, true);") 3881 3882;; We do two major things here: handle mem->mem and construct long 3883;; constants. 3884 3885(define_expand "movsi" 3886 [(set (match_operand:SI 0 "nonimmediate_operand") 3887 (match_operand:SI 1 "general_operand"))] 3888 "" 3889{ 3890 if (alpha_expand_mov (SImode, operands)) 3891 DONE; 3892}) 3893 3894(define_insn "*movsi" 3895 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,m,r") 3896 (match_operand:SI 1 "input_operand" "rJ,K,L,n,m,rJ,s"))] 3897 "register_operand (operands[0], SImode) 3898 || reg_or_0_operand (operands[1], SImode)" 3899 "@ 3900 bis $31,%r1,%0 3901 lda %0,%1($31) 3902 ldah %0,%h1($31) 3903 # 3904 ldl %0,%1 3905 stl %r1,%0 3906 lda %0,%1" 3907 [(set_attr "type" "ilog,iadd,iadd,multi,ild,ist,ldsym") 3908 (set_attr "isa" "*,*,*,*,*,*,vms")]) 3909 3910;; Split a load of a large constant into the appropriate two-insn 3911;; sequence. 3912 3913(define_split 3914 [(set (match_operand:SI 0 "register_operand") 3915 (match_operand:SI 1 "non_add_const_operand"))] 3916 "" 3917 [(const_int 0)] 3918{ 3919 if (alpha_split_const_mov (SImode, operands)) 3920 DONE; 3921 else 3922 FAIL; 3923}) 3924 3925(define_insn "*movdi_er_low_l" 3926 [(set (match_operand:DI 0 "register_operand" "=r") 3927 (lo_sum:DI (match_operand:DI 1 "register_operand" "r") 3928 (match_operand:DI 2 "local_symbolic_operand")))] 3929 "TARGET_EXPLICIT_RELOCS" 3930{ 3931 if (true_regnum (operands[1]) == 29) 3932 return "lda %0,%2(%1)\t\t!gprel"; 3933 else 3934 return "lda %0,%2(%1)\t\t!gprellow"; 3935} 3936 [(set_attr "usegp" "yes")]) 3937 3938(define_split 3939 [(set (match_operand:DI 0 "register_operand") 3940 (match_operand:DI 1 "small_symbolic_operand"))] 3941 "TARGET_EXPLICIT_RELOCS && reload_completed" 3942 [(set (match_dup 0) 3943 (lo_sum:DI (match_dup 2) (match_dup 1)))] 3944 "operands[2] = pic_offset_table_rtx;") 3945 3946(define_split 3947 [(set (match_operand:DI 0 "register_operand") 3948 (match_operand:DI 1 "local_symbolic_operand"))] 3949 "TARGET_EXPLICIT_RELOCS && reload_completed" 3950 [(set (match_dup 0) 3951 (plus:DI (match_dup 2) (high:DI (match_dup 1)))) 3952 (set (match_dup 0) 3953 (lo_sum:DI (match_dup 0) (match_dup 1)))] 3954 "operands[2] = pic_offset_table_rtx;") 3955 3956(define_split 3957 [(match_operand 0 "some_small_symbolic_operand")] 3958 "" 3959 [(match_dup 0)] 3960 "operands[0] = split_small_symbolic_operand (operands[0]);") 3961 3962;; Accepts any symbolic, not just global, since function calls that 3963;; don't go via bsr still use !literal in hopes of linker relaxation. 3964(define_insn "movdi_er_high_g" 3965 [(set (match_operand:DI 0 "register_operand" "=r") 3966 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 3967 (match_operand:DI 2 "symbolic_operand") 3968 (match_operand 3 "const_int_operand")] 3969 UNSPEC_LITERAL))] 3970 "TARGET_EXPLICIT_RELOCS" 3971{ 3972 if (INTVAL (operands[3]) == 0) 3973 return "ldq %0,%2(%1)\t\t!literal"; 3974 else 3975 return "ldq %0,%2(%1)\t\t!literal!%3"; 3976} 3977 [(set_attr "type" "ldsym")]) 3978 3979(define_split 3980 [(set (match_operand:DI 0 "register_operand") 3981 (match_operand:DI 1 "global_symbolic_operand"))] 3982 "TARGET_EXPLICIT_RELOCS && reload_completed" 3983 [(set (match_dup 0) 3984 (unspec:DI [(match_dup 2) 3985 (match_dup 1) 3986 (const_int 0)] UNSPEC_LITERAL))] 3987 "operands[2] = pic_offset_table_rtx;") 3988 3989(define_insn "movdi_er_tlsgd" 3990 [(set (match_operand:DI 0 "register_operand" "=r") 3991 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 3992 (match_operand:DI 2 "symbolic_operand") 3993 (match_operand 3 "const_int_operand")] 3994 UNSPEC_TLSGD))] 3995 "HAVE_AS_TLS" 3996{ 3997 if (INTVAL (operands[3]) == 0) 3998 return "lda %0,%2(%1)\t\t!tlsgd"; 3999 else 4000 return "lda %0,%2(%1)\t\t!tlsgd!%3"; 4001}) 4002 4003(define_insn "movdi_er_tlsldm" 4004 [(set (match_operand:DI 0 "register_operand" "=r") 4005 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 4006 (match_operand 2 "const_int_operand")] 4007 UNSPEC_TLSLDM))] 4008 "HAVE_AS_TLS" 4009{ 4010 if (INTVAL (operands[2]) == 0) 4011 return "lda %0,%&(%1)\t\t!tlsldm"; 4012 else 4013 return "lda %0,%&(%1)\t\t!tlsldm!%2"; 4014}) 4015 4016(define_insn "*movdi_er_gotdtp" 4017 [(set (match_operand:DI 0 "register_operand" "=r") 4018 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 4019 (match_operand:DI 2 "symbolic_operand")] 4020 UNSPEC_DTPREL))] 4021 "HAVE_AS_TLS" 4022 "ldq %0,%2(%1)\t\t!gotdtprel" 4023 [(set_attr "type" "ild") 4024 (set_attr "usegp" "yes")]) 4025 4026(define_split 4027 [(set (match_operand:DI 0 "register_operand") 4028 (match_operand:DI 1 "gotdtp_symbolic_operand"))] 4029 "HAVE_AS_TLS && reload_completed" 4030 [(set (match_dup 0) 4031 (unspec:DI [(match_dup 2) 4032 (match_dup 1)] UNSPEC_DTPREL))] 4033{ 4034 operands[1] = XVECEXP (XEXP (operands[1], 0), 0, 0); 4035 operands[2] = pic_offset_table_rtx; 4036}) 4037 4038(define_insn "*movdi_er_gottp" 4039 [(set (match_operand:DI 0 "register_operand" "=r") 4040 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 4041 (match_operand:DI 2 "symbolic_operand")] 4042 UNSPEC_TPREL))] 4043 "HAVE_AS_TLS" 4044 "ldq %0,%2(%1)\t\t!gottprel" 4045 [(set_attr "type" "ild") 4046 (set_attr "usegp" "yes")]) 4047 4048(define_split 4049 [(set (match_operand:DI 0 "register_operand") 4050 (match_operand:DI 1 "gottp_symbolic_operand"))] 4051 "HAVE_AS_TLS && reload_completed" 4052 [(set (match_dup 0) 4053 (unspec:DI [(match_dup 2) 4054 (match_dup 1)] UNSPEC_TPREL))] 4055{ 4056 operands[1] = XVECEXP (XEXP (operands[1], 0), 0, 0); 4057 operands[2] = pic_offset_table_rtx; 4058}) 4059 4060(define_insn "*movdi" 4061 [(set (match_operand:DI 0 "nonimmediate_operand" 4062 "=r,r,r,r,r,r,r,r, m, *f,*f, Q, r,*f") 4063 (match_operand:DI 1 "input_operand" 4064 "rJ,K,L,T,s,n,s,m,rJ,*fJ, Q,*f,*f, r"))] 4065 "register_operand (operands[0], DImode) 4066 || reg_or_0_operand (operands[1], DImode)" 4067 "@ 4068 mov %r1,%0 4069 lda %0,%1($31) 4070 ldah %0,%h1($31) 4071 # 4072 # 4073 # 4074 lda %0,%1 4075 ldq%A1 %0,%1 4076 stq%A0 %r1,%0 4077 fmov %R1,%0 4078 ldt %0,%1 4079 stt %R1,%0 4080 ftoit %1,%0 4081 itoft %1,%0" 4082 [(set_attr "type" "ilog,iadd,iadd,iadd,ldsym,multi,ldsym,ild,ist,fcpys,fld,fst,ftoi,itof") 4083 (set_attr "isa" "*,*,*,er,er,*,ner,*,*,*,*,*,fix,fix") 4084 (set_attr "usegp" "*,*,*,yes,*,*,*,*,*,*,*,*,*,*")]) 4085 4086;; VMS needs to set up "vms_base_regno" for unwinding. This move 4087;; often appears dead to the life analysis code, at which point we 4088;; die for emitting dead prologue instructions. Force this live. 4089 4090(define_insn "force_movdi" 4091 [(set (match_operand:DI 0 "register_operand" "=r") 4092 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")] 4093 UNSPECV_FORCE_MOV))] 4094 "" 4095 "mov %1,%0" 4096 [(set_attr "type" "ilog")]) 4097 4098;; We do three major things here: handle mem->mem, put 64-bit constants in 4099;; memory, and construct long 32-bit constants. 4100 4101(define_expand "movdi" 4102 [(set (match_operand:DI 0 "nonimmediate_operand") 4103 (match_operand:DI 1 "general_operand"))] 4104 "" 4105{ 4106 if (alpha_expand_mov (DImode, operands)) 4107 DONE; 4108}) 4109 4110;; Split a load of a large constant into the appropriate two-insn 4111;; sequence. 4112 4113(define_split 4114 [(set (match_operand:DI 0 "register_operand") 4115 (match_operand:DI 1 "non_add_const_operand"))] 4116 "" 4117 [(const_int 0)] 4118{ 4119 if (alpha_split_const_mov (DImode, operands)) 4120 DONE; 4121 else 4122 FAIL; 4123}) 4124 4125;; We need to prevent reload from splitting TImode moves, because it 4126;; might decide to overwrite a pointer with the value it points to. 4127;; In that case we have to do the loads in the appropriate order so 4128;; that the pointer is not destroyed too early. 4129 4130(define_insn_and_split "*movti_internal" 4131 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o") 4132 (match_operand:TI 1 "input_operand" "roJ,rJ"))] 4133 "(register_operand (operands[0], TImode) 4134 /* Prevent rematerialization of constants. */ 4135 && ! CONSTANT_P (operands[1])) 4136 || reg_or_0_operand (operands[1], TImode)" 4137 "#" 4138 "reload_completed" 4139 [(set (match_dup 0) (match_dup 2)) 4140 (set (match_dup 1) (match_dup 3))] 4141 "alpha_split_tmode_pair (operands, TImode, true);") 4142 4143(define_expand "movti" 4144 [(set (match_operand:TI 0 "nonimmediate_operand") 4145 (match_operand:TI 1 "general_operand"))] 4146 "" 4147{ 4148 if (MEM_P (operands[0]) 4149 && ! reg_or_0_operand (operands[1], TImode)) 4150 operands[1] = force_reg (TImode, operands[1]); 4151 4152 if (operands[1] == const0_rtx) 4153 ; 4154 /* We must put 64-bit constants in memory. We could keep the 4155 32-bit constants in TImode and rely on the splitter, but 4156 this doesn't seem to be worth the pain. */ 4157 else if (CONST_SCALAR_INT_P (operands[1])) 4158 { 4159 rtx in[2], out[2], target; 4160 4161 gcc_assert (can_create_pseudo_p ()); 4162 4163 split_double (operands[1], &in[0], &in[1]); 4164 4165 if (in[0] == const0_rtx) 4166 out[0] = const0_rtx; 4167 else 4168 { 4169 out[0] = gen_reg_rtx (DImode); 4170 emit_insn (gen_movdi (out[0], in[0])); 4171 } 4172 4173 if (in[1] == const0_rtx) 4174 out[1] = const0_rtx; 4175 else 4176 { 4177 out[1] = gen_reg_rtx (DImode); 4178 emit_insn (gen_movdi (out[1], in[1])); 4179 } 4180 4181 if (!REG_P (operands[0])) 4182 target = gen_reg_rtx (TImode); 4183 else 4184 target = operands[0]; 4185 4186 emit_insn (gen_movdi (operand_subword (target, 0, 0, TImode), out[0])); 4187 emit_insn (gen_movdi (operand_subword (target, 1, 0, TImode), out[1])); 4188 4189 if (target != operands[0]) 4190 emit_insn (gen_rtx_SET (operands[0], target)); 4191 4192 DONE; 4193 } 4194}) 4195 4196;; These are the partial-word cases. 4197;; 4198;; First we have the code to load an aligned word. Operand 0 is the register 4199;; in which to place the result. It's mode is QImode or HImode. Operand 1 4200;; is an SImode MEM at the low-order byte of the proper word. Operand 2 is the 4201;; number of bits within the word that the value is. Operand 3 is an SImode 4202;; scratch register. If operand 0 is a hard register, operand 3 may be the 4203;; same register. It is allowed to conflict with operand 1 as well. 4204 4205(define_expand "aligned_loadqi" 4206 [(set (match_operand:SI 3 "register_operand") 4207 (match_operand:SI 1 "memory_operand")) 4208 (set (match_operand:DI 0 "register_operand") 4209 (zero_extract:DI (subreg:DI (match_dup 3) 0) 4210 (const_int 8) 4211 (match_operand:DI 2 "const_int_operand")))]) 4212 4213(define_expand "aligned_loadhi" 4214 [(set (match_operand:SI 3 "register_operand") 4215 (match_operand:SI 1 "memory_operand")) 4216 (set (match_operand:DI 0 "register_operand") 4217 (zero_extract:DI (subreg:DI (match_dup 3) 0) 4218 (const_int 16) 4219 (match_operand:DI 2 "const_int_operand")))]) 4220 4221;; Similar for unaligned loads, where we use the sequence from the 4222;; Alpha Architecture manual. We have to distinguish between little-endian 4223;; and big-endian systems as the sequences are different. 4224;; 4225;; Operand 1 is the address. Operands 2 and 3 are temporaries, where 4226;; operand 3 can overlap the input and output registers. 4227 4228(define_expand "unaligned_loadqi" 4229 [(set (match_operand:DI 2 "register_operand") 4230 (mem:DI (and:DI (match_operand:DI 1 "address_operand") 4231 (const_int -8)))) 4232 (set (match_operand:DI 3 "register_operand") 4233 (match_dup 1)) 4234 (set (match_operand:DI 0 "register_operand") 4235 (zero_extract:DI (match_dup 2) 4236 (const_int 8) 4237 (ashift:DI (match_dup 3) (const_int 3))))]) 4238 4239(define_expand "unaligned_loadhi" 4240 [(set (match_operand:DI 2 "register_operand") 4241 (mem:DI (and:DI (match_operand:DI 1 "address_operand") 4242 (const_int -8)))) 4243 (set (match_operand:DI 3 "register_operand") 4244 (match_dup 1)) 4245 (set (match_operand:DI 0 "register_operand") 4246 (zero_extract:DI (match_dup 2) 4247 (const_int 16) 4248 (ashift:DI (match_dup 3) (const_int 3))))]) 4249 4250;; Storing an aligned byte or word requires two temporaries. Operand 0 is the 4251;; aligned SImode MEM. Operand 1 is the register containing the 4252;; byte or word to store. Operand 2 is the number of bits within the word that 4253;; the value should be placed. Operands 3 and 4 are SImode temporaries. 4254 4255(define_expand "aligned_store" 4256 [(set (match_operand:SI 3 "register_operand") 4257 (match_operand:SI 0 "memory_operand")) 4258 (set (subreg:DI (match_dup 3) 0) 4259 (and:DI (subreg:DI (match_dup 3) 0) (match_dup 5))) 4260 (set (subreg:DI (match_operand:SI 4 "register_operand") 0) 4261 (ashift:DI (zero_extend:DI (match_operand 1 "register_operand")) 4262 (match_operand:DI 2 "const_int_operand"))) 4263 (set (subreg:DI (match_dup 4) 0) 4264 (ior:DI (subreg:DI (match_dup 4) 0) (subreg:DI (match_dup 3) 0))) 4265 (set (match_dup 0) (match_dup 4))] 4266 "" 4267{ 4268 operands[5] = GEN_INT (~ (GET_MODE_MASK (GET_MODE (operands[1])) 4269 << INTVAL (operands[2]))); 4270}) 4271 4272;; For the unaligned byte and halfword cases, we use code similar to that 4273;; in the ;; Architecture book, but reordered to lower the number of registers 4274;; required. Operand 0 is the address. Operand 1 is the data to store. 4275;; Operands 2, 3, and 4 are DImode temporaries, where operands 2 and 4 may 4276;; be the same temporary, if desired. If the address is in a register, 4277;; operand 2 can be that register. 4278 4279(define_expand "unaligned_store<mode>" 4280 [(set (match_operand:DI 3 "register_operand") 4281 (mem:DI (and:DI (match_operand:DI 0 "address_operand") 4282 (const_int -8)))) 4283 (set (match_operand:DI 2 "register_operand") 4284 (match_dup 0)) 4285 (set (match_dup 3) 4286 (and:DI (not:DI (ashift:DI (match_dup 5) 4287 (ashift:DI (match_dup 2) (const_int 3)))) 4288 (match_dup 3))) 4289 (set (match_operand:DI 4 "register_operand") 4290 (ashift:DI (zero_extend:DI 4291 (match_operand:I12MODE 1 "register_operand")) 4292 (ashift:DI (match_dup 2) (const_int 3)))) 4293 (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3))) 4294 (set (mem:DI (and:DI (match_dup 0) (const_int -8))) 4295 (match_dup 4))] 4296 "" 4297 "operands[5] = GEN_INT (GET_MODE_MASK (<MODE>mode));") 4298 4299;; Here are the define_expand's for QI and HI moves that use the above 4300;; patterns. We have the normal sets, plus the ones that need scratch 4301;; registers for reload. 4302 4303(define_expand "mov<mode>" 4304 [(set (match_operand:I12MODE 0 "nonimmediate_operand") 4305 (match_operand:I12MODE 1 "general_operand"))] 4306 "" 4307{ 4308 if (TARGET_BWX 4309 ? alpha_expand_mov (<MODE>mode, operands) 4310 : alpha_expand_mov_nobwx (<MODE>mode, operands)) 4311 DONE; 4312}) 4313 4314(define_insn "*movqi" 4315 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,r,m") 4316 (match_operand:QI 1 "input_operand" "rJ,n,m,rJ"))] 4317 "register_operand (operands[0], QImode) 4318 || reg_or_0_operand (operands[1], QImode)" 4319 "@ 4320 bis $31,%r1,%0 4321 lda %0,%L1($31) 4322 ldbu %0,%1 4323 stb %r1,%0" 4324 [(set_attr "type" "ilog,iadd,ild,ist") 4325 (set_attr "isa" "*,*,bwx,bwx")]) 4326 4327(define_insn "*movhi" 4328 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m") 4329 (match_operand:HI 1 "input_operand" "rJ,n,m,rJ"))] 4330 "register_operand (operands[0], HImode) 4331 || reg_or_0_operand (operands[1], HImode)" 4332 "@ 4333 bis $31,%r1,%0 4334 lda %0,%L1($31) 4335 ldwu %0,%1 4336 stw %r1,%0" 4337 [(set_attr "type" "ilog,iadd,ild,ist") 4338 (set_attr "isa" "*,*,bwx,bwx")]) 4339 4340;; We need to hook into the extra support that we have for HImode 4341;; reloads when BWX insns are not available. 4342(define_expand "movcqi" 4343 [(set (match_operand:CQI 0 "nonimmediate_operand") 4344 (match_operand:CQI 1 "general_operand"))] 4345 "!TARGET_BWX" 4346{ 4347 if (GET_CODE (operands[0]) == CONCAT || GET_CODE (operands[1]) == CONCAT) 4348 ; 4349 else if (!any_memory_operand (operands[0], CQImode)) 4350 { 4351 if (!any_memory_operand (operands[1], CQImode)) 4352 { 4353 emit_move_insn (gen_lowpart (HImode, operands[0]), 4354 gen_lowpart (HImode, operands[1])); 4355 DONE; 4356 } 4357 if (aligned_memory_operand (operands[1], CQImode)) 4358 { 4359 bool done; 4360 do_aligned1: 4361 operands[1] = gen_lowpart (HImode, operands[1]); 4362 do_aligned2: 4363 operands[0] = gen_lowpart (HImode, operands[0]); 4364 done = alpha_expand_mov_nobwx (HImode, operands); 4365 gcc_assert (done); 4366 DONE; 4367 } 4368 } 4369 else if (aligned_memory_operand (operands[0], CQImode)) 4370 { 4371 if (MEM_P (operands[1])) 4372 { 4373 rtx x = gen_reg_rtx (HImode); 4374 emit_move_insn (gen_lowpart (CQImode, x), operands[1]); 4375 operands[1] = x; 4376 goto do_aligned2; 4377 } 4378 goto do_aligned1; 4379 } 4380 4381 gcc_assert (!reload_in_progress); 4382 emit_move_complex_parts (operands[0], operands[1]); 4383 DONE; 4384}) 4385 4386;; Here are the versions for reload. 4387;; 4388;; The aligned input case is recognized early in alpha_secondary_reload 4389;; in order to avoid allocating an unnecessary scratch register. 4390;; 4391;; Note that in the unaligned cases we know that the operand must not be 4392;; a pseudo-register because stack slots are always aligned references. 4393 4394(define_expand "reload_in<mode>" 4395 [(parallel [(match_operand:RELOAD12 0 "register_operand" "=r") 4396 (match_operand:RELOAD12 1 "any_memory_operand" "m") 4397 (match_operand:TI 2 "register_operand" "=&r")])] 4398 "!TARGET_BWX" 4399{ 4400 rtx scratch, seq, addr; 4401 unsigned regno = REGNO (operands[2]); 4402 4403 /* It is possible that one of the registers we got for operands[2] 4404 might coincide with that of operands[0] (which is why we made 4405 it TImode). Pick the other one to use as our scratch. */ 4406 if (regno == REGNO (operands[0])) 4407 regno++; 4408 scratch = gen_rtx_REG (DImode, regno); 4409 4410 addr = get_unaligned_address (operands[1]); 4411 operands[0] = gen_rtx_REG (DImode, REGNO (operands[0])); 4412 seq = gen_unaligned_load<reloadmode> (operands[0], addr, 4413 scratch, operands[0]); 4414 alpha_set_memflags (seq, operands[1]); 4415 4416 emit_insn (seq); 4417 DONE; 4418}) 4419 4420(define_expand "reload_out<mode>" 4421 [(parallel [(match_operand:RELOAD12 0 "any_memory_operand" "=m") 4422 (match_operand:RELOAD12 1 "register_operand" "r") 4423 (match_operand:TI 2 "register_operand" "=&r")])] 4424 "!TARGET_BWX" 4425{ 4426 unsigned regno = REGNO (operands[2]); 4427 4428 if (<MODE>mode == CQImode) 4429 { 4430 operands[0] = gen_lowpart (HImode, operands[0]); 4431 operands[1] = gen_lowpart (HImode, operands[1]); 4432 } 4433 4434 if (aligned_memory_operand (operands[0], <MODE>mode)) 4435 { 4436 emit_insn (gen_reload_out<reloadmode>_aligned 4437 (operands[0], operands[1], 4438 gen_rtx_REG (SImode, regno), 4439 gen_rtx_REG (SImode, regno + 1))); 4440 } 4441 else 4442 { 4443 rtx addr = get_unaligned_address (operands[0]); 4444 rtx scratch1 = gen_rtx_REG (DImode, regno); 4445 rtx scratch2 = gen_rtx_REG (DImode, regno + 1); 4446 rtx scratch3 = scratch1; 4447 rtx seq; 4448 4449 if (REG_P (addr)) 4450 scratch1 = addr; 4451 4452 seq = gen_unaligned_store<reloadmode> (addr, operands[1], scratch1, 4453 scratch2, scratch3); 4454 alpha_set_memflags (seq, operands[0]); 4455 emit_insn (seq); 4456 } 4457 DONE; 4458}) 4459 4460;; Helpers for the above. The way reload is structured, we can't 4461;; always get a proper address for a stack slot during reload_foo 4462;; expansion, so we must delay our address manipulations until after. 4463 4464(define_insn_and_split "reload_in<mode>_aligned" 4465 [(set (match_operand:I12MODE 0 "register_operand" "=r") 4466 (match_operand:I12MODE 1 "memory_operand" "m"))] 4467 "!TARGET_BWX && (reload_in_progress || reload_completed)" 4468 "#" 4469 "!TARGET_BWX && reload_completed" 4470 [(const_int 0)] 4471{ 4472 rtx aligned_mem, bitnum; 4473 get_aligned_mem (operands[1], &aligned_mem, &bitnum); 4474 emit_insn (gen_aligned_load<reloadmode> 4475 (gen_lowpart (DImode, operands[0]), aligned_mem, bitnum, 4476 gen_rtx_REG (SImode, REGNO (operands[0])))); 4477 DONE; 4478}) 4479 4480(define_insn_and_split "reload_out<mode>_aligned" 4481 [(set (match_operand:I12MODE 0 "memory_operand" "=m") 4482 (match_operand:I12MODE 1 "register_operand" "r")) 4483 (clobber (match_operand:SI 2 "register_operand" "=&r")) 4484 (clobber (match_operand:SI 3 "register_operand" "=&r"))] 4485 "!TARGET_BWX && (reload_in_progress || reload_completed)" 4486 "#" 4487 "!TARGET_BWX && reload_completed" 4488 [(const_int 0)] 4489{ 4490 rtx aligned_mem, bitnum; 4491 get_aligned_mem (operands[0], &aligned_mem, &bitnum); 4492 emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum, 4493 operands[2], operands[3])); 4494 DONE; 4495}) 4496 4497;; Vector operations 4498 4499(define_mode_iterator VEC [V8QI V4HI V2SI]) 4500(define_mode_iterator VEC12 [V8QI V4HI]) 4501 4502(define_expand "mov<mode>" 4503 [(set (match_operand:VEC 0 "nonimmediate_operand") 4504 (match_operand:VEC 1 "general_operand"))] 4505 "" 4506{ 4507 if (alpha_expand_mov (<MODE>mode, operands)) 4508 DONE; 4509}) 4510 4511(define_split 4512 [(set (match_operand:VEC 0 "register_operand") 4513 (match_operand:VEC 1 "non_zero_const_operand"))] 4514 "" 4515 [(const_int 0)] 4516{ 4517 if (alpha_split_const_mov (<MODE>mode, operands)) 4518 DONE; 4519 else 4520 FAIL; 4521}) 4522 4523 4524(define_expand "movmisalign<mode>" 4525 [(set (match_operand:VEC 0 "nonimmediate_operand") 4526 (match_operand:VEC 1 "general_operand"))] 4527 "" 4528{ 4529 alpha_expand_movmisalign (<MODE>mode, operands); 4530 DONE; 4531}) 4532 4533(define_insn "*mov<mode>_fix" 4534 [(set (match_operand:VEC 0 "nonimmediate_operand" "=r,r,r,m,*f,*f,m,r,*f") 4535 (match_operand:VEC 1 "input_operand" "rW,i,m,rW,*fW,m,*f,*f,r"))] 4536 "register_operand (operands[0], <MODE>mode) 4537 || reg_or_0_operand (operands[1], <MODE>mode)" 4538 "@ 4539 bis $31,%r1,%0 4540 # 4541 ldq %0,%1 4542 stq %r1,%0 4543 cpys %R1,%R1,%0 4544 ldt %0,%1 4545 stt %R1,%0 4546 ftoit %1,%0 4547 itoft %1,%0" 4548 [(set_attr "type" "ilog,multi,ild,ist,fcpys,fld,fst,ftoi,itof") 4549 (set_attr "isa" "*,*,*,*,*,*,*,fix,fix")]) 4550 4551(define_insn "<code><mode>3" 4552 [(set (match_operand:VEC12 0 "register_operand" "=r") 4553 (any_maxmin:VEC12 4554 (match_operand:VEC12 1 "reg_or_0_operand" "rW") 4555 (match_operand:VEC12 2 "reg_or_0_operand" "rW")))] 4556 "TARGET_MAX" 4557 "<maxmin><modesuffix> %r1,%r2,%0" 4558 [(set_attr "type" "mvi")]) 4559 4560(define_insn "one_cmpl<mode>2" 4561 [(set (match_operand:VEC 0 "register_operand" "=r") 4562 (not:VEC (match_operand:VEC 1 "register_operand" "r")))] 4563 "" 4564 "ornot $31,%1,%0" 4565 [(set_attr "type" "ilog")]) 4566 4567(define_insn "and<mode>3" 4568 [(set (match_operand:VEC 0 "register_operand" "=r") 4569 (and:VEC (match_operand:VEC 1 "register_operand" "r") 4570 (match_operand:VEC 2 "register_operand" "r")))] 4571 "" 4572 "and %1,%2,%0" 4573 [(set_attr "type" "ilog")]) 4574 4575(define_insn "*andnot<mode>3" 4576 [(set (match_operand:VEC 0 "register_operand" "=r") 4577 (and:VEC (not:VEC (match_operand:VEC 1 "register_operand" "r")) 4578 (match_operand:VEC 2 "register_operand" "r")))] 4579 "" 4580 "bic %2,%1,%0" 4581 [(set_attr "type" "ilog")]) 4582 4583(define_insn "ior<mode>3" 4584 [(set (match_operand:VEC 0 "register_operand" "=r") 4585 (ior:VEC (match_operand:VEC 1 "register_operand" "r") 4586 (match_operand:VEC 2 "register_operand" "r")))] 4587 "" 4588 "bis %1,%2,%0" 4589 [(set_attr "type" "ilog")]) 4590 4591(define_insn "*iornot<mode>3" 4592 [(set (match_operand:VEC 0 "register_operand" "=r") 4593 (ior:VEC (not:DI (match_operand:VEC 1 "register_operand" "r")) 4594 (match_operand:VEC 2 "register_operand" "r")))] 4595 "" 4596 "ornot %2,%1,%0" 4597 [(set_attr "type" "ilog")]) 4598 4599(define_insn "xor<mode>3" 4600 [(set (match_operand:VEC 0 "register_operand" "=r") 4601 (xor:VEC (match_operand:VEC 1 "register_operand" "r") 4602 (match_operand:VEC 2 "register_operand" "r")))] 4603 "" 4604 "xor %1,%2,%0" 4605 [(set_attr "type" "ilog")]) 4606 4607(define_insn "*xornot<mode>3" 4608 [(set (match_operand:VEC 0 "register_operand" "=r") 4609 (not:VEC (xor:VEC (match_operand:VEC 1 "register_operand" "r") 4610 (match_operand:VEC 2 "register_operand" "r"))))] 4611 "" 4612 "eqv %1,%2,%0" 4613 [(set_attr "type" "ilog")]) 4614 4615(define_expand "vec_shl_<mode>" 4616 [(set (match_operand:VEC 0 "register_operand") 4617 (ashift:DI (match_operand:VEC 1 "register_operand") 4618 (match_operand:DI 2 "reg_or_6bit_operand")))] 4619 "" 4620{ 4621 operands[0] = gen_lowpart (DImode, operands[0]); 4622 operands[1] = gen_lowpart (DImode, operands[1]); 4623}) 4624 4625(define_expand "vec_shr_<mode>" 4626 [(set (match_operand:VEC 0 "register_operand") 4627 (lshiftrt:DI (match_operand:VEC 1 "register_operand") 4628 (match_operand:DI 2 "reg_or_6bit_operand")))] 4629 "" 4630{ 4631 operands[0] = gen_lowpart (DImode, operands[0]); 4632 operands[1] = gen_lowpart (DImode, operands[1]); 4633}) 4634 4635;; Bit field extract patterns which use ext[wlq][lh] 4636 4637(define_expand "extvmisaligndi" 4638 [(set (match_operand:DI 0 "register_operand") 4639 (sign_extract:DI (match_operand:BLK 1 "memory_operand") 4640 (match_operand:DI 2 "const_int_operand") 4641 (match_operand:DI 3 "const_int_operand")))] 4642 "" 4643{ 4644 /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries. */ 4645 if (INTVAL (operands[3]) % 8 != 0 4646 || (INTVAL (operands[2]) != 16 4647 && INTVAL (operands[2]) != 32 4648 && INTVAL (operands[2]) != 64)) 4649 FAIL; 4650 4651 alpha_expand_unaligned_load (operands[0], operands[1], 4652 INTVAL (operands[2]) / 8, 4653 INTVAL (operands[3]) / 8, 1); 4654 DONE; 4655}) 4656 4657(define_expand "extzvdi" 4658 [(set (match_operand:DI 0 "register_operand") 4659 (zero_extract:DI (match_operand:DI 1 "register_operand") 4660 (match_operand:DI 2 "const_int_operand") 4661 (match_operand:DI 3 "const_int_operand")))] 4662 "" 4663{ 4664 /* We can do 8, 16, 32 and 64 bit fields, if aligned on byte boundaries. */ 4665 if (INTVAL (operands[3]) % 8 != 0 4666 || (INTVAL (operands[2]) != 8 4667 && INTVAL (operands[2]) != 16 4668 && INTVAL (operands[2]) != 32 4669 && INTVAL (operands[2]) != 64)) 4670 FAIL; 4671}) 4672 4673(define_expand "extzvmisaligndi" 4674 [(set (match_operand:DI 0 "register_operand") 4675 (zero_extract:DI (match_operand:BLK 1 "memory_operand") 4676 (match_operand:DI 2 "const_int_operand") 4677 (match_operand:DI 3 "const_int_operand")))] 4678 "" 4679{ 4680 /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries. 4681 We fail 8-bit fields, falling back on a simple byte load. */ 4682 if (INTVAL (operands[3]) % 8 != 0 4683 || (INTVAL (operands[2]) != 16 4684 && INTVAL (operands[2]) != 32 4685 && INTVAL (operands[2]) != 64)) 4686 FAIL; 4687 4688 alpha_expand_unaligned_load (operands[0], operands[1], 4689 INTVAL (operands[2]) / 8, 4690 INTVAL (operands[3]) / 8, 0); 4691 DONE; 4692}) 4693 4694(define_expand "insvmisaligndi" 4695 [(set (zero_extract:DI (match_operand:BLK 0 "memory_operand") 4696 (match_operand:DI 1 "const_int_operand") 4697 (match_operand:DI 2 "const_int_operand")) 4698 (match_operand:DI 3 "register_operand"))] 4699 "" 4700{ 4701 /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries. */ 4702 if (INTVAL (operands[2]) % 8 != 0 4703 || (INTVAL (operands[1]) != 16 4704 && INTVAL (operands[1]) != 32 4705 && INTVAL (operands[1]) != 64)) 4706 FAIL; 4707 4708 alpha_expand_unaligned_store (operands[0], operands[3], 4709 INTVAL (operands[1]) / 8, 4710 INTVAL (operands[2]) / 8); 4711 DONE; 4712}) 4713 4714;; Block move/clear, see alpha.c for more details. 4715;; Argument 0 is the destination 4716;; Argument 1 is the source 4717;; Argument 2 is the length 4718;; Argument 3 is the alignment 4719 4720(define_expand "movmemqi" 4721 [(parallel [(set (match_operand:BLK 0 "memory_operand") 4722 (match_operand:BLK 1 "memory_operand")) 4723 (use (match_operand:DI 2 "immediate_operand")) 4724 (use (match_operand:DI 3 "immediate_operand"))])] 4725 "" 4726{ 4727 if (alpha_expand_block_move (operands)) 4728 DONE; 4729 else 4730 FAIL; 4731}) 4732 4733(define_expand "movmemdi" 4734 [(parallel [(set (match_operand:BLK 0 "memory_operand") 4735 (match_operand:BLK 1 "memory_operand")) 4736 (use (match_operand:DI 2 "immediate_operand")) 4737 (use (match_operand:DI 3 "immediate_operand")) 4738 (use (match_dup 4)) 4739 (clobber (reg:DI 25)) 4740 (clobber (reg:DI 16)) 4741 (clobber (reg:DI 17)) 4742 (clobber (reg:DI 18)) 4743 (clobber (reg:DI 19)) 4744 (clobber (reg:DI 20)) 4745 (clobber (reg:DI 26)) 4746 (clobber (reg:DI 27))])] 4747 "TARGET_ABI_OPEN_VMS" 4748 "operands[4] = gen_rtx_SYMBOL_REF (Pmode, \"OTS$MOVE\");") 4749 4750(define_insn "*movmemdi_1" 4751 [(set (match_operand:BLK 0 "memory_operand" "=m,m") 4752 (match_operand:BLK 1 "memory_operand" "m,m")) 4753 (use (match_operand:DI 2 "nonmemory_operand" "r,i")) 4754 (use (match_operand:DI 3 "immediate_operand")) 4755 (use (match_operand:DI 4 "call_operand" "i,i")) 4756 (clobber (reg:DI 25)) 4757 (clobber (reg:DI 16)) 4758 (clobber (reg:DI 17)) 4759 (clobber (reg:DI 18)) 4760 (clobber (reg:DI 19)) 4761 (clobber (reg:DI 20)) 4762 (clobber (reg:DI 26)) 4763 (clobber (reg:DI 27))] 4764 "TARGET_ABI_OPEN_VMS" 4765{ 4766 operands [5] = alpha_use_linkage (operands [4], false, true); 4767 switch (which_alternative) 4768 { 4769 case 0: 4770 return "lda $16,%0\;bis $31,%2,$17\;lda $18,%1\;ldq $26,%5\;lda $25,3($31)\;jsr $26,%4\;ldq $27,0($29)"; 4771 case 1: 4772 return "lda $16,%0\;lda $17,%2($31)\;lda $18,%1\;ldq $26,%5\;lda $25,3($31)\;jsr $26,%4\;ldq $27,0($29)"; 4773 default: 4774 gcc_unreachable (); 4775 } 4776} 4777 [(set_attr "type" "multi") 4778 (set_attr "length" "28")]) 4779 4780(define_expand "setmemqi" 4781 [(parallel [(set (match_operand:BLK 0 "memory_operand") 4782 (match_operand 2 "const_int_operand")) 4783 (use (match_operand:DI 1 "immediate_operand")) 4784 (use (match_operand:DI 3 "immediate_operand"))])] 4785 "" 4786{ 4787 /* If value to set is not zero, use the library routine. */ 4788 if (operands[2] != const0_rtx) 4789 FAIL; 4790 4791 if (alpha_expand_block_clear (operands)) 4792 DONE; 4793 else 4794 FAIL; 4795}) 4796 4797(define_expand "setmemdi" 4798 [(parallel [(set (match_operand:BLK 0 "memory_operand") 4799 (match_operand 2 "const_int_operand")) 4800 (use (match_operand:DI 1 "immediate_operand")) 4801 (use (match_operand:DI 3 "immediate_operand")) 4802 (use (match_dup 4)) 4803 (clobber (reg:DI 25)) 4804 (clobber (reg:DI 16)) 4805 (clobber (reg:DI 17)) 4806 (clobber (reg:DI 26)) 4807 (clobber (reg:DI 27))])] 4808 "TARGET_ABI_OPEN_VMS" 4809{ 4810 /* If value to set is not zero, use the library routine. */ 4811 if (operands[2] != const0_rtx) 4812 FAIL; 4813 4814 operands[4] = gen_rtx_SYMBOL_REF (Pmode, "OTS$ZERO"); 4815}) 4816 4817(define_insn "*clrmemdi_1" 4818 [(set (match_operand:BLK 0 "memory_operand" "=m,m") 4819 (const_int 0)) 4820 (use (match_operand:DI 1 "nonmemory_operand" "r,i")) 4821 (use (match_operand:DI 2 "immediate_operand")) 4822 (use (match_operand:DI 3 "call_operand" "i,i")) 4823 (clobber (reg:DI 25)) 4824 (clobber (reg:DI 16)) 4825 (clobber (reg:DI 17)) 4826 (clobber (reg:DI 26)) 4827 (clobber (reg:DI 27))] 4828 "TARGET_ABI_OPEN_VMS" 4829{ 4830 operands [4] = alpha_use_linkage (operands [3], false, true); 4831 switch (which_alternative) 4832 { 4833 case 0: 4834 return "lda $16,%0\;bis $31,%1,$17\;ldq $26,%4\;lda $25,2($31)\;jsr $26,%3\;ldq $27,0($29)"; 4835 case 1: 4836 return "lda $16,%0\;lda $17,%1($31)\;ldq $26,%4\;lda $25,2($31)\;jsr $26,%3\;ldq $27,0($29)"; 4837 default: 4838 gcc_unreachable (); 4839 } 4840} 4841 [(set_attr "type" "multi") 4842 (set_attr "length" "24")]) 4843 4844 4845;; Subroutine of stack space allocation. Perform a stack probe. 4846(define_expand "stack_probe_internal" 4847 [(set (match_dup 1) (match_operand:DI 0 "const_int_operand"))] 4848 "" 4849{ 4850 operands[1] = gen_rtx_MEM (DImode, plus_constant (Pmode, stack_pointer_rtx, 4851 INTVAL (operands[0]))); 4852 MEM_VOLATILE_P (operands[1]) = 1; 4853 4854 operands[0] = const0_rtx; 4855}) 4856 4857;; This is how we allocate stack space. If we are allocating a 4858;; constant amount of space and we know it is less than 4096 4859;; bytes, we need do nothing. 4860;; 4861;; If it is more than 4096 bytes, we need to probe the stack 4862;; periodically. 4863(define_expand "allocate_stack" 4864 [(set (reg:DI 30) 4865 (plus:DI (reg:DI 30) 4866 (match_operand:DI 1 "reg_or_cint_operand"))) 4867 (set (match_operand:DI 0 "register_operand" "=r") 4868 (match_dup 2))] 4869 "" 4870{ 4871 if (CONST_INT_P (operands[1]) 4872 && INTVAL (operands[1]) < 32768) 4873 { 4874 if (INTVAL (operands[1]) >= 4096) 4875 { 4876 /* We do this the same way as in the prologue and generate explicit 4877 probes. Then we update the stack by the constant. */ 4878 4879 int probed = 4096; 4880 4881 emit_insn (gen_stack_probe_internal (GEN_INT (- probed))); 4882 while (probed + 8192 < INTVAL (operands[1])) 4883 emit_insn (gen_stack_probe_internal 4884 (GEN_INT (- (probed += 8192)))); 4885 4886 if (probed + 4096 < INTVAL (operands[1])) 4887 emit_insn (gen_stack_probe_internal 4888 (GEN_INT (- INTVAL(operands[1])))); 4889 } 4890 4891 operands[1] = GEN_INT (- INTVAL (operands[1])); 4892 operands[2] = virtual_stack_dynamic_rtx; 4893 } 4894 else 4895 { 4896 rtx_code_label *out_label = 0; 4897 rtx_code_label *loop_label = gen_label_rtx (); 4898 rtx want = gen_reg_rtx (Pmode); 4899 rtx tmp = gen_reg_rtx (Pmode); 4900 rtx memref, test; 4901 4902 emit_insn (gen_subdi3 (want, stack_pointer_rtx, 4903 force_reg (Pmode, operands[1]))); 4904 4905 if (!CONST_INT_P (operands[1])) 4906 { 4907 rtx limit = GEN_INT (4096); 4908 out_label = gen_label_rtx (); 4909 test = gen_rtx_LTU (VOIDmode, operands[1], limit); 4910 emit_jump_insn 4911 (gen_cbranchdi4 (test, operands[1], limit, out_label)); 4912 } 4913 4914 emit_insn (gen_adddi3 (tmp, stack_pointer_rtx, GEN_INT (-4096))); 4915 emit_label (loop_label); 4916 memref = gen_rtx_MEM (DImode, tmp); 4917 MEM_VOLATILE_P (memref) = 1; 4918 emit_move_insn (memref, const0_rtx); 4919 emit_insn (gen_adddi3 (tmp, tmp, GEN_INT(-8192))); 4920 test = gen_rtx_GTU (VOIDmode, tmp, want); 4921 emit_jump_insn (gen_cbranchdi4 (test, tmp, want, loop_label)); 4922 4923 memref = gen_rtx_MEM (DImode, want); 4924 MEM_VOLATILE_P (memref) = 1; 4925 emit_move_insn (memref, const0_rtx); 4926 4927 if (out_label) 4928 emit_label (out_label); 4929 4930 emit_move_insn (stack_pointer_rtx, want); 4931 emit_move_insn (operands[0], virtual_stack_dynamic_rtx); 4932 DONE; 4933 } 4934}) 4935 4936;; This is used by alpha_expand_prolog to do the same thing as above, 4937;; except we cannot at that time generate new basic blocks, so we hide 4938;; the loop in this one insn. 4939 4940(define_insn "prologue_stack_probe_loop" 4941 [(unspec_volatile [(match_operand:DI 0 "register_operand" "r") 4942 (match_operand:DI 1 "register_operand" "r")] 4943 UNSPECV_PSPL)] 4944 "" 4945{ 4946 operands[2] = gen_label_rtx (); 4947 (*targetm.asm_out.internal_label) (asm_out_file, "L", 4948 CODE_LABEL_NUMBER (operands[2])); 4949 4950 return "stq $31,-8192(%1)\;subq %0,1,%0\;lda %1,-8192(%1)\;bne %0,%l2"; 4951} 4952 [(set_attr "length" "16") 4953 (set_attr "type" "multi")]) 4954 4955(define_expand "prologue" 4956 [(const_int 0)] 4957 "" 4958{ 4959 alpha_expand_prologue (); 4960 DONE; 4961}) 4962 4963;; These take care of emitting the ldgp insn in the prologue. This will be 4964;; an lda/ldah pair and we want to align them properly. So we have two 4965;; unspec_volatile insns, the first of which emits the ldgp assembler macro 4966;; and the second of which emits nothing. However, both are marked as type 4967;; IADD (the default) so the alignment code in alpha.c does the right thing 4968;; with them. 4969 4970(define_expand "prologue_ldgp" 4971 [(set (match_dup 0) 4972 (unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1)) 4973 (set (match_dup 0) 4974 (unspec_volatile:DI [(match_dup 0) (match_dup 2)] UNSPECV_PLDGP2))] 4975 "" 4976{ 4977 operands[0] = pic_offset_table_rtx; 4978 operands[1] = gen_rtx_REG (Pmode, 27); 4979 operands[2] = (TARGET_EXPLICIT_RELOCS 4980 ? GEN_INT (alpha_next_sequence_number++) 4981 : const0_rtx); 4982}) 4983 4984(define_insn "*ldgp_er_1" 4985 [(set (match_operand:DI 0 "register_operand" "=r") 4986 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r") 4987 (match_operand 2 "const_int_operand")] 4988 UNSPECV_LDGP1))] 4989 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 4990 "ldah %0,0(%1)\t\t!gpdisp!%2" 4991 [(set_attr "cannot_copy" "true")]) 4992 4993(define_insn "*ldgp_er_2" 4994 [(set (match_operand:DI 0 "register_operand" "=r") 4995 (unspec:DI [(match_operand:DI 1 "register_operand" "r") 4996 (match_operand 2 "const_int_operand")] 4997 UNSPEC_LDGP2))] 4998 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 4999 "lda %0,0(%1)\t\t!gpdisp!%2" 5000 [(set_attr "cannot_copy" "true")]) 5001 5002(define_insn "*prologue_ldgp_er_2" 5003 [(set (match_operand:DI 0 "register_operand" "=r") 5004 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r") 5005 (match_operand 2 "const_int_operand")] 5006 UNSPECV_PLDGP2))] 5007 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 5008 "lda %0,0(%1)\t\t!gpdisp!%2\n$%~..ng:" 5009 [(set_attr "cannot_copy" "true")]) 5010 5011(define_insn "*prologue_ldgp_1" 5012 [(set (match_operand:DI 0 "register_operand" "=r") 5013 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r") 5014 (match_operand 2 "const_int_operand")] 5015 UNSPECV_LDGP1))] 5016 "" 5017 "ldgp %0,0(%1)\n$%~..ng:" 5018 [(set_attr "cannot_copy" "true")]) 5019 5020(define_insn "*prologue_ldgp_2" 5021 [(set (match_operand:DI 0 "register_operand" "=r") 5022 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r") 5023 (match_operand 2 "const_int_operand")] 5024 UNSPECV_PLDGP2))] 5025 "" 5026 ) 5027 5028;; The _mcount profiling hook has special calling conventions, and 5029;; does not clobber all the registers that a normal call would. So 5030;; hide the fact this is a call at all. 5031 5032(define_insn "prologue_mcount" 5033 [(unspec_volatile [(const_int 0)] UNSPECV_MCOUNT)] 5034 "" 5035{ 5036 if (TARGET_EXPLICIT_RELOCS) 5037 /* Note that we cannot use a lituse_jsr reloc, since _mcount 5038 cannot be called via the PLT. */ 5039 return "ldq $28,_mcount($29)\t\t!literal\;jsr $28,($28),_mcount"; 5040 else 5041 return "lda $28,_mcount\;jsr $28,($28),_mcount"; 5042} 5043 [(set_attr "type" "multi") 5044 (set_attr "length" "8")]) 5045 5046(define_insn "init_fp" 5047 [(set (match_operand:DI 0 "register_operand" "=r") 5048 (match_operand:DI 1 "register_operand" "r")) 5049 (clobber (mem:BLK (match_operand:DI 2 "register_operand" "=r")))] 5050 "" 5051 "bis $31,%1,%0") 5052 5053(define_expand "epilogue" 5054 [(return)] 5055 "" 5056 "alpha_expand_epilogue ();") 5057 5058(define_expand "sibcall_epilogue" 5059 [(return)] 5060 "TARGET_ABI_OSF" 5061{ 5062 alpha_expand_epilogue (); 5063 DONE; 5064}) 5065 5066(define_expand "builtin_longjmp" 5067 [(use (match_operand:DI 0 "register_operand" "r"))] 5068 "TARGET_ABI_OSF" 5069{ 5070 /* The elements of the buffer are, in order: */ 5071 rtx fp = gen_rtx_MEM (Pmode, operands[0]); 5072 rtx lab = gen_rtx_MEM (Pmode, plus_constant (Pmode, operands[0], 8)); 5073 rtx stack = gen_rtx_MEM (Pmode, plus_constant (Pmode, operands[0], 16)); 5074 rtx pv = gen_rtx_REG (Pmode, 27); 5075 5076 /* This bit is the same as expand_builtin_longjmp. */ 5077 emit_move_insn (hard_frame_pointer_rtx, fp); 5078 emit_move_insn (pv, lab); 5079 emit_stack_restore (SAVE_NONLOCAL, stack); 5080 emit_use (hard_frame_pointer_rtx); 5081 emit_use (stack_pointer_rtx); 5082 5083 /* Load the label we are jumping through into $27 so that we know 5084 where to look for it when we get back to setjmp's function for 5085 restoring the gp. */ 5086 emit_jump_insn (gen_builtin_longjmp_internal (pv)); 5087 emit_barrier (); 5088 DONE; 5089}) 5090 5091;; This is effectively a copy of indirect_jump, but constrained such 5092;; that register renaming cannot foil our cunning plan with $27. 5093(define_insn "builtin_longjmp_internal" 5094 [(set (pc) 5095 (unspec_volatile [(match_operand:DI 0 "register_operand" "c")] 5096 UNSPECV_LONGJMP))] 5097 "" 5098 "jmp $31,(%0),0" 5099 [(set_attr "type" "ibr")]) 5100 5101(define_expand "builtin_setjmp_receiver" 5102 [(unspec_volatile [(label_ref (match_operand 0))] UNSPECV_SETJMPR)] 5103 "TARGET_ABI_OSF") 5104 5105(define_insn_and_split "*builtin_setjmp_receiver_1" 5106 [(unspec_volatile [(match_operand 0)] UNSPECV_SETJMPR)] 5107 "TARGET_ABI_OSF" 5108{ 5109 if (TARGET_EXPLICIT_RELOCS) 5110 return "#"; 5111 else 5112 return "br $27,$LSJ%=\n$LSJ%=:\;ldgp $29,0($27)"; 5113} 5114 "&& TARGET_EXPLICIT_RELOCS && reload_completed" 5115 [(set (match_dup 1) 5116 (unspec_volatile:DI [(match_dup 2) (match_dup 3)] UNSPECV_LDGP1)) 5117 (set (match_dup 1) 5118 (unspec:DI [(match_dup 1) (match_dup 3)] UNSPEC_LDGP2))] 5119{ 5120 if (prev_nonnote_insn (curr_insn) != XEXP (operands[0], 0)) 5121 emit_insn (gen_rtx_UNSPEC_VOLATILE (VOIDmode, gen_rtvec (1, operands[0]), 5122 UNSPECV_SETJMPR_ER)); 5123 operands[1] = pic_offset_table_rtx; 5124 operands[2] = gen_rtx_REG (Pmode, 27); 5125 operands[3] = GEN_INT (alpha_next_sequence_number++); 5126} 5127 [(set_attr "length" "12") 5128 (set_attr "type" "multi")]) 5129 5130(define_insn "*builtin_setjmp_receiver_er_sl_1" 5131 [(unspec_volatile [(match_operand 0)] UNSPECV_SETJMPR_ER)] 5132 "TARGET_ABI_OSF && TARGET_EXPLICIT_RELOCS" 5133 "lda $27,$LSJ%=-%l0($27)\n$LSJ%=:") 5134 5135;; When flag_reorder_blocks_and_partition is in effect, compiler puts 5136;; exception landing pads in a cold section. To prevent inter-section offset 5137;; calculation, a jump to original landing pad is emitted in the place of the 5138;; original landing pad. Since landing pad is moved, RA-relative GP 5139;; calculation in the prologue of landing pad breaks. To solve this problem, 5140;; we use alternative GP load approach. 5141 5142(define_expand "exception_receiver" 5143 [(unspec_volatile [(match_dup 0)] UNSPECV_EHR)] 5144 "TARGET_ABI_OSF" 5145{ 5146 if (flag_reorder_blocks_and_partition) 5147 operands[0] = alpha_gp_save_rtx (); 5148 else 5149 operands[0] = const0_rtx; 5150}) 5151 5152(define_insn "*exception_receiver_2" 5153 [(unspec_volatile [(match_operand:DI 0 "memory_operand" "m")] UNSPECV_EHR)] 5154 "TARGET_ABI_OSF && flag_reorder_blocks_and_partition" 5155 "ldq $29,%0" 5156 [(set_attr "type" "ild")]) 5157 5158(define_insn_and_split "*exception_receiver_1" 5159 [(unspec_volatile [(const_int 0)] UNSPECV_EHR)] 5160 "TARGET_ABI_OSF" 5161{ 5162 if (TARGET_EXPLICIT_RELOCS) 5163 return "#"; 5164 else 5165 return "ldgp $29,0($26)"; 5166} 5167 "&& TARGET_EXPLICIT_RELOCS && reload_completed" 5168 [(set (match_dup 0) 5169 (unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1)) 5170 (set (match_dup 0) 5171 (unspec:DI [(match_dup 0) (match_dup 2)] UNSPEC_LDGP2))] 5172{ 5173 operands[0] = pic_offset_table_rtx; 5174 operands[1] = gen_rtx_REG (Pmode, 26); 5175 operands[2] = GEN_INT (alpha_next_sequence_number++); 5176} 5177 [(set_attr "length" "8") 5178 (set_attr "type" "multi")]) 5179 5180(define_expand "nonlocal_goto_receiver" 5181 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE) 5182 (set (reg:DI 27) (mem:DI (reg:DI 29))) 5183 (unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE) 5184 (use (reg:DI 27))] 5185 "TARGET_ABI_OPEN_VMS") 5186 5187(define_insn "arg_home" 5188 [(unspec [(const_int 0)] UNSPEC_ARG_HOME) 5189 (use (reg:DI 1)) 5190 (use (reg:DI 25)) 5191 (use (reg:DI 16)) 5192 (use (reg:DI 17)) 5193 (use (reg:DI 18)) 5194 (use (reg:DI 19)) 5195 (use (reg:DI 20)) 5196 (use (reg:DI 21)) 5197 (use (reg:DI 48)) 5198 (use (reg:DI 49)) 5199 (use (reg:DI 50)) 5200 (use (reg:DI 51)) 5201 (use (reg:DI 52)) 5202 (use (reg:DI 53)) 5203 (clobber (mem:BLK (const_int 0))) 5204 (clobber (reg:DI 24)) 5205 (clobber (reg:DI 25)) 5206 (clobber (reg:DI 0))] 5207 "TARGET_ABI_OPEN_VMS" 5208 "lda $0,OTS$HOME_ARGS\;ldq $0,8($0)\;jsr $0,OTS$HOME_ARGS" 5209 [(set_attr "length" "16") 5210 (set_attr "type" "multi")]) 5211 5212;; Prefetch data. 5213;; 5214;; On EV4, these instructions are nops -- no load occurs. 5215;; 5216;; On EV5, these instructions act as a normal load, and thus can trap 5217;; if the address is invalid. The OS may (or may not) handle this in 5218;; the entMM fault handler and suppress the fault. If so, then this 5219;; has the effect of a read prefetch instruction. 5220;; 5221;; On EV6, these become official prefetch instructions. 5222 5223(define_insn "prefetch" 5224 [(prefetch (match_operand:DI 0 "address_operand" "p") 5225 (match_operand:DI 1 "const_int_operand" "n") 5226 (match_operand:DI 2 "const_int_operand" "n"))] 5227 "TARGET_FIXUP_EV5_PREFETCH || alpha_cpu == PROCESSOR_EV6" 5228{ 5229 /* Interpret "no temporal locality" as this data should be evicted once 5230 it is used. The "evict next" alternatives load the data into the cache 5231 and leave the LRU eviction counter pointing to that block. */ 5232 static const char * const alt[2][2] = { 5233 { 5234 "ldq $31,%a0", /* read, evict next */ 5235 "ldl $31,%a0", /* read, evict last */ 5236 }, 5237 { 5238 "ldt $f31,%a0", /* write, evict next */ 5239 "lds $f31,%a0", /* write, evict last */ 5240 } 5241 }; 5242 5243 bool write = INTVAL (operands[1]) != 0; 5244 bool lru = INTVAL (operands[2]) != 0; 5245 5246 return alt[write][lru]; 5247} 5248 [(set_attr "type" "ild")]) 5249 5250;; Close the trap shadow of preceding instructions. This is generated 5251;; by alpha_reorg. 5252 5253(define_insn "trapb" 5254 [(unspec_volatile [(const_int 0)] UNSPECV_TRAPB)] 5255 "" 5256 "trapb" 5257 [(set_attr "type" "misc")]) 5258 5259;; No-op instructions used by machine-dependent reorg to preserve 5260;; alignment for instruction issue. 5261;; The Unicos/Mk assembler does not support these opcodes. 5262 5263(define_insn "nop" 5264 [(const_int 0)] 5265 "" 5266 "bis $31,$31,$31" 5267 [(set_attr "type" "ilog")]) 5268 5269(define_insn "fnop" 5270 [(const_int 1)] 5271 "TARGET_FP" 5272 "cpys $f31,$f31,$f31" 5273 [(set_attr "type" "fcpys")]) 5274 5275(define_insn "unop" 5276 [(const_int 2)] 5277 "" 5278 "ldq_u $31,0($30)") 5279 5280(define_insn "realign" 5281 [(unspec_volatile [(match_operand 0 "immediate_operand" "i")] 5282 UNSPECV_REALIGN)] 5283 "" 5284 ".align %0 #realign") 5285 5286;; Instructions to be emitted from __builtins. 5287 5288(define_insn "builtin_cmpbge" 5289 [(set (match_operand:DI 0 "register_operand" "=r") 5290 (unspec:DI [(match_operand:DI 1 "reg_or_0_operand" "rJ") 5291 (match_operand:DI 2 "reg_or_8bit_operand" "rI")] 5292 UNSPEC_CMPBGE))] 5293 "" 5294 "cmpbge %r1,%2,%0" 5295 ;; The EV6 data sheets list this as ILOG. OTOH, EV6 doesn't 5296 ;; actually differentiate between ILOG and ICMP in the schedule. 5297 [(set_attr "type" "icmp")]) 5298 5299(define_expand "extbl" 5300 [(match_operand:DI 0 "register_operand") 5301 (match_operand:DI 1 "reg_or_0_operand") 5302 (match_operand:DI 2 "reg_or_8bit_operand")] 5303 "" 5304{ 5305 emit_insn (gen_extxl (operands[0], operands[1], GEN_INT (8), operands[2])); 5306 DONE; 5307}) 5308 5309(define_expand "extwl" 5310 [(match_operand:DI 0 "register_operand") 5311 (match_operand:DI 1 "reg_or_0_operand") 5312 (match_operand:DI 2 "reg_or_8bit_operand")] 5313 "" 5314{ 5315 emit_insn (gen_extxl (operands[0], operands[1], GEN_INT (16), operands[2])); 5316 DONE; 5317}) 5318 5319(define_expand "extll" 5320 [(match_operand:DI 0 "register_operand") 5321 (match_operand:DI 1 "reg_or_0_operand") 5322 (match_operand:DI 2 "reg_or_8bit_operand")] 5323 "" 5324{ 5325 emit_insn (gen_extxl (operands[0], operands[1], GEN_INT (32), operands[2])); 5326 DONE; 5327}) 5328 5329(define_expand "extql" 5330 [(match_operand:DI 0 "register_operand") 5331 (match_operand:DI 1 "reg_or_0_operand") 5332 (match_operand:DI 2 "reg_or_8bit_operand")] 5333 "" 5334{ 5335 emit_insn (gen_extxl (operands[0], operands[1], GEN_INT (64), operands[2])); 5336 DONE; 5337}) 5338 5339(define_expand "builtin_insbl" 5340 [(match_operand:DI 0 "register_operand") 5341 (match_operand:DI 1 "register_operand") 5342 (match_operand:DI 2 "reg_or_8bit_operand")] 5343 "" 5344{ 5345 operands[1] = gen_lowpart (QImode, operands[1]); 5346 emit_insn (gen_insbl (operands[0], operands[1], operands[2])); 5347 DONE; 5348}) 5349 5350(define_expand "builtin_inswl" 5351 [(match_operand:DI 0 "register_operand") 5352 (match_operand:DI 1 "register_operand") 5353 (match_operand:DI 2 "reg_or_8bit_operand")] 5354 "" 5355{ 5356 operands[1] = gen_lowpart (HImode, operands[1]); 5357 emit_insn (gen_inswl (operands[0], operands[1], operands[2])); 5358 DONE; 5359}) 5360 5361(define_expand "builtin_insll" 5362 [(match_operand:DI 0 "register_operand") 5363 (match_operand:DI 1 "register_operand") 5364 (match_operand:DI 2 "reg_or_8bit_operand")] 5365 "" 5366{ 5367 operands[1] = gen_lowpart (SImode, operands[1]); 5368 emit_insn (gen_insll (operands[0], operands[1], operands[2])); 5369 DONE; 5370}) 5371 5372(define_expand "inswh" 5373 [(match_operand:DI 0 "register_operand") 5374 (match_operand:DI 1 "register_operand") 5375 (match_operand:DI 2 "reg_or_8bit_operand")] 5376 "" 5377{ 5378 emit_insn (gen_insxh (operands[0], operands[1], GEN_INT (16), operands[2])); 5379 DONE; 5380}) 5381 5382(define_expand "inslh" 5383 [(match_operand:DI 0 "register_operand") 5384 (match_operand:DI 1 "register_operand") 5385 (match_operand:DI 2 "reg_or_8bit_operand")] 5386 "" 5387{ 5388 emit_insn (gen_insxh (operands[0], operands[1], GEN_INT (32), operands[2])); 5389 DONE; 5390}) 5391 5392(define_expand "insqh" 5393 [(match_operand:DI 0 "register_operand") 5394 (match_operand:DI 1 "register_operand") 5395 (match_operand:DI 2 "reg_or_8bit_operand")] 5396 "" 5397{ 5398 emit_insn (gen_insxh (operands[0], operands[1], GEN_INT (64), operands[2])); 5399 DONE; 5400}) 5401 5402(define_expand "mskbl" 5403 [(match_operand:DI 0 "register_operand") 5404 (match_operand:DI 1 "reg_or_0_operand") 5405 (match_operand:DI 2 "reg_or_8bit_operand")] 5406 "" 5407{ 5408 rtx mask = GEN_INT (0xff); 5409 emit_insn (gen_mskxl (operands[0], operands[1], mask, operands[2])); 5410 DONE; 5411}) 5412 5413(define_expand "mskwl" 5414 [(match_operand:DI 0 "register_operand") 5415 (match_operand:DI 1 "reg_or_0_operand") 5416 (match_operand:DI 2 "reg_or_8bit_operand")] 5417 "" 5418{ 5419 rtx mask = GEN_INT (0xffff); 5420 emit_insn (gen_mskxl (operands[0], operands[1], mask, operands[2])); 5421 DONE; 5422}) 5423 5424(define_expand "mskll" 5425 [(match_operand:DI 0 "register_operand") 5426 (match_operand:DI 1 "reg_or_0_operand") 5427 (match_operand:DI 2 "reg_or_8bit_operand")] 5428 "" 5429{ 5430 rtx mask = gen_int_mode (0xffffffff, DImode); 5431 emit_insn (gen_mskxl (operands[0], operands[1], mask, operands[2])); 5432 DONE; 5433}) 5434 5435(define_expand "mskql" 5436 [(match_operand:DI 0 "register_operand") 5437 (match_operand:DI 1 "reg_or_0_operand") 5438 (match_operand:DI 2 "reg_or_8bit_operand")] 5439 "" 5440{ 5441 rtx mask = constm1_rtx; 5442 emit_insn (gen_mskxl (operands[0], operands[1], mask, operands[2])); 5443 DONE; 5444}) 5445 5446(define_expand "mskwh" 5447 [(match_operand:DI 0 "register_operand") 5448 (match_operand:DI 1 "register_operand") 5449 (match_operand:DI 2 "reg_or_8bit_operand")] 5450 "" 5451{ 5452 emit_insn (gen_mskxh (operands[0], operands[1], GEN_INT (16), operands[2])); 5453 DONE; 5454}) 5455 5456(define_expand "msklh" 5457 [(match_operand:DI 0 "register_operand") 5458 (match_operand:DI 1 "register_operand") 5459 (match_operand:DI 2 "reg_or_8bit_operand")] 5460 "" 5461{ 5462 emit_insn (gen_mskxh (operands[0], operands[1], GEN_INT (32), operands[2])); 5463 DONE; 5464}) 5465 5466(define_expand "mskqh" 5467 [(match_operand:DI 0 "register_operand") 5468 (match_operand:DI 1 "register_operand") 5469 (match_operand:DI 2 "reg_or_8bit_operand")] 5470 "" 5471{ 5472 emit_insn (gen_mskxh (operands[0], operands[1], GEN_INT (64), operands[2])); 5473 DONE; 5474}) 5475 5476(define_expand "builtin_zap" 5477 [(set (match_operand:DI 0 "register_operand") 5478 (and:DI (unspec:DI 5479 [(match_operand:DI 2 "reg_or_cint_operand")] 5480 UNSPEC_ZAP) 5481 (match_operand:DI 1 "reg_or_cint_operand")))] 5482 "" 5483{ 5484 if (CONST_INT_P (operands[2])) 5485 { 5486 rtx mask = alpha_expand_zap_mask (INTVAL (operands[2])); 5487 5488 if (mask == const0_rtx) 5489 { 5490 emit_move_insn (operands[0], const0_rtx); 5491 DONE; 5492 } 5493 if (mask == constm1_rtx) 5494 { 5495 emit_move_insn (operands[0], operands[1]); 5496 DONE; 5497 } 5498 5499 operands[1] = force_reg (DImode, operands[1]); 5500 emit_insn (gen_anddi3 (operands[0], operands[1], mask)); 5501 DONE; 5502 } 5503 5504 operands[1] = force_reg (DImode, operands[1]); 5505 operands[2] = gen_lowpart (QImode, operands[2]); 5506}) 5507 5508(define_insn "*builtin_zap_1" 5509 [(set (match_operand:DI 0 "register_operand" "=r,r,r,r") 5510 (and:DI (unspec:DI 5511 [(match_operand:QI 2 "reg_or_cint_operand" "n,n,r,r")] 5512 UNSPEC_ZAP) 5513 (match_operand:DI 1 "reg_or_cint_operand" "n,r,J,r")))] 5514 "" 5515 "@ 5516 # 5517 # 5518 bis $31,$31,%0 5519 zap %r1,%2,%0" 5520 [(set_attr "type" "shift,shift,ilog,shift")]) 5521 5522(define_split 5523 [(set (match_operand:DI 0 "register_operand") 5524 (and:DI (unspec:DI 5525 [(match_operand:QI 2 "const_int_operand")] 5526 UNSPEC_ZAP) 5527 (match_operand:DI 1 "const_int_operand")))] 5528 "" 5529 [(const_int 0)] 5530{ 5531 rtx mask = alpha_expand_zap_mask (INTVAL (operands[2])); 5532 5533 operands[1] = gen_int_mode (INTVAL (operands[1]) & INTVAL (mask), DImode); 5534 emit_move_insn (operands[0], operands[1]); 5535 DONE; 5536}) 5537 5538(define_split 5539 [(set (match_operand:DI 0 "register_operand") 5540 (and:DI (unspec:DI 5541 [(match_operand:QI 2 "const_int_operand")] 5542 UNSPEC_ZAP) 5543 (match_operand:DI 1 "register_operand")))] 5544 "" 5545 [(set (match_dup 0) 5546 (and:DI (match_dup 1) (match_dup 2)))] 5547{ 5548 operands[2] = alpha_expand_zap_mask (INTVAL (operands[2])); 5549 if (operands[2] == const0_rtx) 5550 { 5551 emit_move_insn (operands[0], const0_rtx); 5552 DONE; 5553 } 5554 if (operands[2] == constm1_rtx) 5555 { 5556 emit_move_insn (operands[0], operands[1]); 5557 DONE; 5558 } 5559}) 5560 5561(define_expand "builtin_zapnot" 5562 [(set (match_operand:DI 0 "register_operand") 5563 (and:DI (unspec:DI 5564 [(not:QI (match_operand:DI 2 "reg_or_cint_operand"))] 5565 UNSPEC_ZAP) 5566 (match_operand:DI 1 "reg_or_cint_operand")))] 5567 "" 5568{ 5569 if (CONST_INT_P (operands[2])) 5570 { 5571 rtx mask = alpha_expand_zap_mask (~ INTVAL (operands[2])); 5572 5573 if (mask == const0_rtx) 5574 { 5575 emit_move_insn (operands[0], const0_rtx); 5576 DONE; 5577 } 5578 if (mask == constm1_rtx) 5579 { 5580 emit_move_insn (operands[0], operands[1]); 5581 DONE; 5582 } 5583 5584 operands[1] = force_reg (DImode, operands[1]); 5585 emit_insn (gen_anddi3 (operands[0], operands[1], mask)); 5586 DONE; 5587 } 5588 5589 operands[1] = force_reg (DImode, operands[1]); 5590 operands[2] = gen_lowpart (QImode, operands[2]); 5591}) 5592 5593(define_insn "*builtin_zapnot_1" 5594 [(set (match_operand:DI 0 "register_operand" "=r") 5595 (and:DI (unspec:DI 5596 [(not:QI (match_operand:QI 2 "register_operand" "r"))] 5597 UNSPEC_ZAP) 5598 (match_operand:DI 1 "reg_or_0_operand" "rJ")))] 5599 "" 5600 "zapnot %r1,%2,%0" 5601 [(set_attr "type" "shift")]) 5602 5603(define_insn "builtin_amask" 5604 [(set (match_operand:DI 0 "register_operand" "=r") 5605 (unspec:DI [(match_operand:DI 1 "reg_or_8bit_operand" "rI")] 5606 UNSPEC_AMASK))] 5607 "" 5608 "amask %1,%0" 5609 [(set_attr "type" "ilog")]) 5610 5611(define_insn "builtin_implver" 5612 [(set (match_operand:DI 0 "register_operand" "=r") 5613 (unspec:DI [(const_int 0)] UNSPEC_IMPLVER))] 5614 "" 5615 "implver %0" 5616 [(set_attr "type" "ilog")]) 5617 5618(define_insn "builtin_rpcc" 5619 [(set (match_operand:DI 0 "register_operand" "=r") 5620 (unspec_volatile:DI [(const_int 0)] UNSPECV_RPCC))] 5621 "" 5622 "rpcc %0" 5623 [(set_attr "type" "ilog")]) 5624 5625(define_expand "builtin_minub8" 5626 [(match_operand:DI 0 "register_operand") 5627 (match_operand:DI 1 "reg_or_0_operand") 5628 (match_operand:DI 2 "reg_or_0_operand")] 5629 "TARGET_MAX" 5630{ 5631 alpha_expand_builtin_vector_binop (gen_uminv8qi3, V8QImode, operands[0], 5632 operands[1], operands[2]); 5633 DONE; 5634}) 5635 5636(define_expand "builtin_minsb8" 5637 [(match_operand:DI 0 "register_operand") 5638 (match_operand:DI 1 "reg_or_0_operand") 5639 (match_operand:DI 2 "reg_or_0_operand")] 5640 "TARGET_MAX" 5641{ 5642 alpha_expand_builtin_vector_binop (gen_sminv8qi3, V8QImode, operands[0], 5643 operands[1], operands[2]); 5644 DONE; 5645}) 5646 5647(define_expand "builtin_minuw4" 5648 [(match_operand:DI 0 "register_operand") 5649 (match_operand:DI 1 "reg_or_0_operand") 5650 (match_operand:DI 2 "reg_or_0_operand")] 5651 "TARGET_MAX" 5652{ 5653 alpha_expand_builtin_vector_binop (gen_uminv4hi3, V4HImode, operands[0], 5654 operands[1], operands[2]); 5655 DONE; 5656}) 5657 5658(define_expand "builtin_minsw4" 5659 [(match_operand:DI 0 "register_operand") 5660 (match_operand:DI 1 "reg_or_0_operand") 5661 (match_operand:DI 2 "reg_or_0_operand")] 5662 "TARGET_MAX" 5663{ 5664 alpha_expand_builtin_vector_binop (gen_sminv4hi3, V4HImode, operands[0], 5665 operands[1], operands[2]); 5666 DONE; 5667}) 5668 5669(define_expand "builtin_maxub8" 5670 [(match_operand:DI 0 "register_operand") 5671 (match_operand:DI 1 "reg_or_0_operand") 5672 (match_operand:DI 2 "reg_or_0_operand")] 5673 "TARGET_MAX" 5674{ 5675 alpha_expand_builtin_vector_binop (gen_umaxv8qi3, V8QImode, operands[0], 5676 operands[1], operands[2]); 5677 DONE; 5678}) 5679 5680(define_expand "builtin_maxsb8" 5681 [(match_operand:DI 0 "register_operand") 5682 (match_operand:DI 1 "reg_or_0_operand") 5683 (match_operand:DI 2 "reg_or_0_operand")] 5684 "TARGET_MAX" 5685{ 5686 alpha_expand_builtin_vector_binop (gen_smaxv8qi3, V8QImode, operands[0], 5687 operands[1], operands[2]); 5688 DONE; 5689}) 5690 5691(define_expand "builtin_maxuw4" 5692 [(match_operand:DI 0 "register_operand") 5693 (match_operand:DI 1 "reg_or_0_operand") 5694 (match_operand:DI 2 "reg_or_0_operand")] 5695 "TARGET_MAX" 5696{ 5697 alpha_expand_builtin_vector_binop (gen_umaxv4hi3, V4HImode, operands[0], 5698 operands[1], operands[2]); 5699 DONE; 5700}) 5701 5702(define_expand "builtin_maxsw4" 5703 [(match_operand:DI 0 "register_operand") 5704 (match_operand:DI 1 "reg_or_0_operand") 5705 (match_operand:DI 2 "reg_or_0_operand")] 5706 "TARGET_MAX" 5707{ 5708 alpha_expand_builtin_vector_binop (gen_smaxv4hi3, V4HImode, operands[0], 5709 operands[1], operands[2]); 5710 DONE; 5711}) 5712 5713(define_insn "builtin_perr" 5714 [(set (match_operand:DI 0 "register_operand" "=r") 5715 (unspec:DI [(match_operand:DI 1 "reg_or_0_operand" "%rJ") 5716 (match_operand:DI 2 "reg_or_8bit_operand" "rJ")] 5717 UNSPEC_PERR))] 5718 "TARGET_MAX" 5719 "perr %r1,%r2,%0" 5720 [(set_attr "type" "mvi")]) 5721 5722(define_expand "builtin_pklb" 5723 [(set (match_operand:DI 0 "register_operand") 5724 (vec_concat:V8QI 5725 (vec_concat:V4QI 5726 (truncate:V2QI (match_operand:DI 1 "register_operand")) 5727 (match_dup 2)) 5728 (match_dup 3)))] 5729 "TARGET_MAX" 5730{ 5731 operands[0] = gen_lowpart (V8QImode, operands[0]); 5732 operands[1] = gen_lowpart (V2SImode, operands[1]); 5733 operands[2] = CONST0_RTX (V2QImode); 5734 operands[3] = CONST0_RTX (V4QImode); 5735}) 5736 5737(define_insn "*pklb" 5738 [(set (match_operand:V8QI 0 "register_operand" "=r") 5739 (vec_concat:V8QI 5740 (vec_concat:V4QI 5741 (truncate:V2QI (match_operand:V2SI 1 "register_operand" "r")) 5742 (match_operand:V2QI 2 "const0_operand")) 5743 (match_operand:V4QI 3 "const0_operand")))] 5744 "TARGET_MAX" 5745 "pklb %r1,%0" 5746 [(set_attr "type" "mvi")]) 5747 5748(define_expand "builtin_pkwb" 5749 [(set (match_operand:DI 0 "register_operand") 5750 (vec_concat:V8QI 5751 (truncate:V4QI (match_operand:DI 1 "register_operand")) 5752 (match_dup 2)))] 5753 "TARGET_MAX" 5754{ 5755 operands[0] = gen_lowpart (V8QImode, operands[0]); 5756 operands[1] = gen_lowpart (V4HImode, operands[1]); 5757 operands[2] = CONST0_RTX (V4QImode); 5758}) 5759 5760(define_insn "*pkwb" 5761 [(set (match_operand:V8QI 0 "register_operand" "=r") 5762 (vec_concat:V8QI 5763 (truncate:V4QI (match_operand:V4HI 1 "register_operand" "r")) 5764 (match_operand:V4QI 2 "const0_operand")))] 5765 "TARGET_MAX" 5766 "pkwb %r1,%0" 5767 [(set_attr "type" "mvi")]) 5768 5769(define_expand "builtin_unpkbl" 5770 [(set (match_operand:DI 0 "register_operand") 5771 (zero_extend:V2SI 5772 (vec_select:V2QI (match_operand:DI 1 "register_operand") 5773 (parallel [(const_int 0) (const_int 1)]))))] 5774 "TARGET_MAX" 5775{ 5776 operands[0] = gen_lowpart (V2SImode, operands[0]); 5777 operands[1] = gen_lowpart (V8QImode, operands[1]); 5778}) 5779 5780(define_insn "*unpkbl" 5781 [(set (match_operand:V2SI 0 "register_operand" "=r") 5782 (zero_extend:V2SI 5783 (vec_select:V2QI (match_operand:V8QI 1 "reg_or_0_operand" "rW") 5784 (parallel [(const_int 0) (const_int 1)]))))] 5785 "TARGET_MAX" 5786 "unpkbl %r1,%0" 5787 [(set_attr "type" "mvi")]) 5788 5789(define_expand "builtin_unpkbw" 5790 [(set (match_operand:DI 0 "register_operand") 5791 (zero_extend:V4HI 5792 (vec_select:V4QI (match_operand:DI 1 "register_operand") 5793 (parallel [(const_int 0) 5794 (const_int 1) 5795 (const_int 2) 5796 (const_int 3)]))))] 5797 "TARGET_MAX" 5798{ 5799 operands[0] = gen_lowpart (V4HImode, operands[0]); 5800 operands[1] = gen_lowpart (V8QImode, operands[1]); 5801}) 5802 5803(define_insn "*unpkbw" 5804 [(set (match_operand:V4HI 0 "register_operand" "=r") 5805 (zero_extend:V4HI 5806 (vec_select:V4QI (match_operand:V8QI 1 "reg_or_0_operand" "rW") 5807 (parallel [(const_int 0) 5808 (const_int 1) 5809 (const_int 2) 5810 (const_int 3)]))))] 5811 "TARGET_MAX" 5812 "unpkbw %r1,%0" 5813 [(set_attr "type" "mvi")]) 5814 5815(include "sync.md") 5816 5817;; The call patterns are at the end of the file because their 5818;; wildcard operand0 interferes with nice recognition. 5819 5820(define_insn "*call_value_osf_1_er_noreturn" 5821 [(set (match_operand 0) 5822 (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s")) 5823 (match_operand 2))) 5824 (use (reg:DI 29)) 5825 (clobber (reg:DI 26))] 5826 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF 5827 && find_reg_note (insn, REG_NORETURN, NULL_RTX)" 5828 "@ 5829 jsr $26,($27),0 5830 bsr $26,%1\t\t!samegp 5831 ldq $27,%1($29)\t\t!literal!%#\;jsr $26,($27),%1\t\t!lituse_jsr!%#" 5832 [(set_attr "type" "jsr") 5833 (set_attr "length" "*,*,8")]) 5834 5835(define_insn "*call_value_osf_1_er" 5836 [(set (match_operand 0) 5837 (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s")) 5838 (match_operand 2))) 5839 (use (reg:DI 29)) 5840 (clobber (reg:DI 26))] 5841 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 5842 "@ 5843 jsr $26,(%1),0\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%* 5844 bsr $26,%1\t\t!samegp 5845 ldq $27,%1($29)\t\t!literal!%#\;jsr $26,($27),0\t\t!lituse_jsr!%#\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*" 5846 [(set_attr "type" "jsr") 5847 (set_attr "length" "12,*,16")]) 5848 5849;; We must use peep2 instead of a split because we need accurate life 5850;; information for $gp. Consider the case of { bar(); while (1); }. 5851(define_peephole2 5852 [(parallel [(set (match_operand 0) 5853 (call (mem:DI (match_operand:DI 1 "call_operand")) 5854 (match_operand 2))) 5855 (use (reg:DI 29)) 5856 (clobber (reg:DI 26))])] 5857 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed 5858 && ! samegp_function_operand (operands[1], Pmode) 5859 && (peep2_regno_dead_p (1, 29) 5860 || find_reg_note (insn, REG_NORETURN, NULL_RTX))" 5861 [(parallel [(set (match_dup 0) 5862 (call (mem:DI (match_dup 3)) 5863 (match_dup 2))) 5864 (use (reg:DI 29)) 5865 (use (match_dup 1)) 5866 (use (match_dup 4)) 5867 (clobber (reg:DI 26))])] 5868{ 5869 if (CONSTANT_P (operands[1])) 5870 { 5871 operands[3] = gen_rtx_REG (Pmode, 27); 5872 operands[4] = GEN_INT (alpha_next_sequence_number++); 5873 emit_insn (gen_movdi_er_high_g (operands[3], pic_offset_table_rtx, 5874 operands[1], operands[4])); 5875 } 5876 else 5877 { 5878 operands[3] = operands[1]; 5879 operands[1] = const0_rtx; 5880 operands[4] = const0_rtx; 5881 } 5882}) 5883 5884(define_peephole2 5885 [(parallel [(set (match_operand 0) 5886 (call (mem:DI (match_operand:DI 1 "call_operand")) 5887 (match_operand 2))) 5888 (use (reg:DI 29)) 5889 (clobber (reg:DI 26))])] 5890 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed 5891 && ! samegp_function_operand (operands[1], Pmode) 5892 && ! (peep2_regno_dead_p (1, 29) 5893 || find_reg_note (insn, REG_NORETURN, NULL_RTX))" 5894 [(parallel [(set (match_dup 0) 5895 (call (mem:DI (match_dup 3)) 5896 (match_dup 2))) 5897 (set (match_dup 6) 5898 (unspec:DI [(match_dup 6) (match_dup 4)] UNSPEC_LDGP1)) 5899 (use (match_dup 1)) 5900 (use (match_dup 5)) 5901 (clobber (reg:DI 26))]) 5902 (set (match_dup 6) 5903 (unspec:DI [(match_dup 6) (match_dup 4)] UNSPEC_LDGP2))] 5904{ 5905 if (CONSTANT_P (operands[1])) 5906 { 5907 operands[3] = gen_rtx_REG (Pmode, 27); 5908 operands[5] = GEN_INT (alpha_next_sequence_number++); 5909 emit_insn (gen_movdi_er_high_g (operands[3], pic_offset_table_rtx, 5910 operands[1], operands[5])); 5911 } 5912 else 5913 { 5914 operands[3] = operands[1]; 5915 operands[1] = const0_rtx; 5916 operands[5] = const0_rtx; 5917 } 5918 operands[4] = GEN_INT (alpha_next_sequence_number++); 5919 operands[6] = pic_offset_table_rtx; 5920}) 5921 5922(define_insn "*call_value_osf_2_er_nogp" 5923 [(set (match_operand 0) 5924 (call (mem:DI (match_operand:DI 1 "register_operand" "c")) 5925 (match_operand 2))) 5926 (use (reg:DI 29)) 5927 (use (match_operand 3)) 5928 (use (match_operand 4)) 5929 (clobber (reg:DI 26))] 5930 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 5931 "jsr $26,(%1),%3%J4" 5932 [(set_attr "type" "jsr")]) 5933 5934(define_insn "*call_value_osf_2_er" 5935 [(set (match_operand 0) 5936 (call (mem:DI (match_operand:DI 1 "register_operand" "c")) 5937 (match_operand 2))) 5938 (set (reg:DI 29) 5939 (unspec:DI [(reg:DI 29) (match_operand 5 "const_int_operand")] 5940 UNSPEC_LDGP1)) 5941 (use (match_operand 3)) 5942 (use (match_operand 4)) 5943 (clobber (reg:DI 26))] 5944 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 5945 "jsr $26,(%1),%3%J4\;ldah $29,0($26)\t\t!gpdisp!%5" 5946 [(set_attr "type" "jsr") 5947 (set_attr "cannot_copy" "true") 5948 (set_attr "length" "8")]) 5949 5950(define_insn "*call_value_osf_1_noreturn" 5951 [(set (match_operand 0) 5952 (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s")) 5953 (match_operand 2))) 5954 (use (reg:DI 29)) 5955 (clobber (reg:DI 26))] 5956 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF 5957 && find_reg_note (insn, REG_NORETURN, NULL_RTX)" 5958 "@ 5959 jsr $26,($27),0 5960 bsr $26,$%1..ng 5961 jsr $26,%1" 5962 [(set_attr "type" "jsr") 5963 (set_attr "length" "*,*,8")]) 5964 5965(define_int_iterator TLS_CALL 5966 [UNSPEC_TLSGD_CALL 5967 UNSPEC_TLSLDM_CALL]) 5968 5969(define_int_attr tls 5970 [(UNSPEC_TLSGD_CALL "tlsgd") 5971 (UNSPEC_TLSLDM_CALL "tlsldm")]) 5972 5973(define_insn "call_value_osf_<tls>" 5974 [(set (match_operand 0) 5975 (call (mem:DI (match_operand:DI 1 "symbolic_operand")) 5976 (const_int 0))) 5977 (unspec [(match_operand:DI 2 "const_int_operand")] TLS_CALL) 5978 (use (reg:DI 29)) 5979 (clobber (reg:DI 26))] 5980 "HAVE_AS_TLS" 5981 "ldq $27,%1($29)\t\t!literal!%2\;jsr $26,($27),%1\t\t!lituse_<tls>!%2\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*" 5982 [(set_attr "type" "jsr") 5983 (set_attr "length" "16")]) 5984 5985;; We must use peep2 instead of a split because we need accurate life 5986;; information for $gp. 5987(define_peephole2 5988 [(parallel 5989 [(set (match_operand 0) 5990 (call (mem:DI (match_operand:DI 1 "symbolic_operand")) 5991 (const_int 0))) 5992 (unspec [(match_operand:DI 2 "const_int_operand")] TLS_CALL) 5993 (use (reg:DI 29)) 5994 (clobber (reg:DI 26))])] 5995 "HAVE_AS_TLS && reload_completed 5996 && peep2_regno_dead_p (1, 29)" 5997 [(set (match_dup 3) 5998 (unspec:DI [(match_dup 5) 5999 (match_dup 1) 6000 (match_dup 2)] UNSPEC_LITERAL)) 6001 (parallel [(set (match_dup 0) 6002 (call (mem:DI (match_dup 3)) 6003 (const_int 0))) 6004 (use (match_dup 5)) 6005 (use (match_dup 1)) 6006 (use (unspec [(match_dup 2)] TLS_CALL)) 6007 (clobber (reg:DI 26))]) 6008 (set (match_dup 5) 6009 (unspec:DI [(match_dup 5) (match_dup 4)] UNSPEC_LDGP2))] 6010{ 6011 operands[3] = gen_rtx_REG (Pmode, 27); 6012 operands[4] = GEN_INT (alpha_next_sequence_number++); 6013 operands[5] = pic_offset_table_rtx; 6014}) 6015 6016(define_peephole2 6017 [(parallel 6018 [(set (match_operand 0) 6019 (call (mem:DI (match_operand:DI 1 "symbolic_operand")) 6020 (const_int 0))) 6021 (unspec [(match_operand:DI 2 "const_int_operand")] TLS_CALL) 6022 (use (reg:DI 29)) 6023 (clobber (reg:DI 26))])] 6024 "HAVE_AS_TLS && reload_completed 6025 && !peep2_regno_dead_p (1, 29)" 6026 [(set (match_dup 3) 6027 (unspec:DI [(match_dup 5) 6028 (match_dup 1) 6029 (match_dup 2)] UNSPEC_LITERAL)) 6030 (parallel [(set (match_dup 0) 6031 (call (mem:DI (match_dup 3)) 6032 (const_int 0))) 6033 (set (match_dup 5) 6034 (unspec:DI [(match_dup 5) (match_dup 4)] UNSPEC_LDGP1)) 6035 (use (match_dup 1)) 6036 (use (unspec [(match_dup 2)] TLS_CALL)) 6037 (clobber (reg:DI 26))]) 6038 (set (match_dup 5) 6039 (unspec:DI [(match_dup 5) (match_dup 4)] UNSPEC_LDGP2))] 6040{ 6041 operands[3] = gen_rtx_REG (Pmode, 27); 6042 operands[4] = GEN_INT (alpha_next_sequence_number++); 6043 operands[5] = pic_offset_table_rtx; 6044}) 6045 6046(define_insn "*call_value_osf_1" 6047 [(set (match_operand 0) 6048 (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s")) 6049 (match_operand 2))) 6050 (use (reg:DI 29)) 6051 (clobber (reg:DI 26))] 6052 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 6053 "@ 6054 jsr $26,($27),0\;ldgp $29,0($26) 6055 bsr $26,$%1..ng 6056 jsr $26,%1\;ldgp $29,0($26)" 6057 [(set_attr "type" "jsr") 6058 (set_attr "length" "12,*,16")]) 6059 6060(define_insn "*sibcall_value_osf_1_er" 6061 [(set (match_operand 0) 6062 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "R,s")) 6063 (match_operand 2))) 6064 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)] 6065 "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 6066 "@ 6067 br $31,%1\t\t!samegp 6068 ldq $27,%1($29)\t\t!literal!%#\;jmp $31,($27),%1\t\t!lituse_jsr!%#" 6069 [(set_attr "type" "jsr") 6070 (set_attr "length" "*,8")]) 6071 6072(define_insn "*sibcall_value_osf_1" 6073 [(set (match_operand 0) 6074 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "R,s")) 6075 (match_operand 2))) 6076 (unspec [(reg:DI 29)] UNSPEC_SIBCALL)] 6077 "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF" 6078 "@ 6079 br $31,$%1..ng 6080 lda $27,%1\;jmp $31,($27),%1" 6081 [(set_attr "type" "jsr") 6082 (set_attr "length" "*,8")]) 6083 6084; GAS relies on the order and position of instructions output below in order 6085; to generate relocs for VMS link to potentially optimize the call. 6086; Please do not molest. 6087(define_insn "*call_value_vms_1" 6088 [(set (match_operand 0) 6089 (call (mem:DI (match_operand:DI 1 "call_operand" "r,s")) 6090 (match_operand 2))) 6091 (use (match_operand:DI 3 "nonmemory_operand" "r,n")) 6092 (use (reg:DI 25)) 6093 (use (reg:DI 26)) 6094 (clobber (reg:DI 27))] 6095 "TARGET_ABI_OPEN_VMS" 6096{ 6097 switch (which_alternative) 6098 { 6099 case 0: 6100 return "mov %3,$27\;jsr $26,0\;ldq $27,0($29)"; 6101 case 1: 6102 operands [3] = alpha_use_linkage (operands [1], true, false); 6103 operands [4] = alpha_use_linkage (operands [1], false, false); 6104 return "ldq $26,%4\;ldq $27,%3\;jsr $26,%1\;ldq $27,0($29)"; 6105 default: 6106 gcc_unreachable (); 6107 } 6108} 6109 [(set_attr "type" "jsr") 6110 (set_attr "length" "12,16")]) 6111