1;; GCC machine description for IA-32 and x86-64. 2;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 3;; 2001, 2002, 2003, 2004, 2005, 2006 4;; Free Software Foundation, Inc. 5;; Mostly by William Schelter. 6;; x86_64 support added by Jan Hubicka 7;; 8;; This file is part of GCC. 9;; 10;; GCC is free software; you can redistribute it and/or modify 11;; it under the terms of the GNU General Public License as published by 12;; the Free Software Foundation; either version 2, or (at your option) 13;; any later version. 14;; 15;; GCC is distributed in the hope that it will be useful, 16;; but WITHOUT ANY WARRANTY; without even the implied warranty of 17;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18;; GNU General Public License for more details. 19;; 20;; You should have received a copy of the GNU General Public License 21;; along with GCC; see the file COPYING. If not, write to 22;; the Free Software Foundation, 51 Franklin Street, Fifth Floor, 23;; Boston, MA 02110-1301, USA. */ 24;; 25;; The original PO technology requires these to be ordered by speed, 26;; so that assigner will pick the fastest. 27;; 28;; See file "rtl.def" for documentation on define_insn, match_*, et. al. 29;; 30;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register 31;; constraint letters. 32;; 33;; The special asm out single letter directives following a '%' are: 34;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of 35;; operands[1]. 36;; 'L' Print the opcode suffix for a 32-bit integer opcode. 37;; 'W' Print the opcode suffix for a 16-bit integer opcode. 38;; 'B' Print the opcode suffix for an 8-bit integer opcode. 39;; 'Q' Print the opcode suffix for a 64-bit float opcode. 40;; 'S' Print the opcode suffix for a 32-bit float opcode. 41;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode. 42;; 'J' Print the appropriate jump operand. 43;; 44;; 'b' Print the QImode name of the register for the indicated operand. 45;; %b0 would print %al if operands[0] is reg 0. 46;; 'w' Likewise, print the HImode name of the register. 47;; 'k' Likewise, print the SImode name of the register. 48;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh. 49;; 'y' Print "st(0)" instead of "st" as a register. 50 51;; UNSPEC usage: 52 53(define_constants 54 [; Relocation specifiers 55 (UNSPEC_GOT 0) 56 (UNSPEC_GOTOFF 1) 57 (UNSPEC_GOTPCREL 2) 58 (UNSPEC_GOTTPOFF 3) 59 (UNSPEC_TPOFF 4) 60 (UNSPEC_NTPOFF 5) 61 (UNSPEC_DTPOFF 6) 62 (UNSPEC_GOTNTPOFF 7) 63 (UNSPEC_INDNTPOFF 8) 64 65 ; Prologue support 66 (UNSPEC_STACK_ALLOC 11) 67 (UNSPEC_SET_GOT 12) 68 (UNSPEC_SSE_PROLOGUE_SAVE 13) 69 (UNSPEC_REG_SAVE 14) 70 (UNSPEC_DEF_CFA 15) 71 72 ; TLS support 73 (UNSPEC_TP 16) 74 (UNSPEC_TLS_GD 17) 75 (UNSPEC_TLS_LD_BASE 18) 76 (UNSPEC_TLSDESC 19) 77 78 ; Other random patterns 79 (UNSPEC_SCAS 20) 80 (UNSPEC_FNSTSW 21) 81 (UNSPEC_SAHF 22) 82 (UNSPEC_FSTCW 23) 83 (UNSPEC_ADD_CARRY 24) 84 (UNSPEC_FLDCW 25) 85 (UNSPEC_REP 26) 86 (UNSPEC_EH_RETURN 27) 87 (UNSPEC_LD_MPIC 28) ; load_macho_picbase 88 89 ; For SSE/MMX support: 90 (UNSPEC_FIX_NOTRUNC 30) 91 (UNSPEC_MASKMOV 31) 92 (UNSPEC_MOVMSK 32) 93 (UNSPEC_MOVNT 33) 94 (UNSPEC_MOVU 34) 95 (UNSPEC_RCP 35) 96 (UNSPEC_RSQRT 36) 97 (UNSPEC_SFENCE 37) 98 (UNSPEC_NOP 38) ; prevents combiner cleverness 99 (UNSPEC_PFRCP 39) 100 (UNSPEC_PFRCPIT1 40) 101 (UNSPEC_PFRCPIT2 41) 102 (UNSPEC_PFRSQRT 42) 103 (UNSPEC_PFRSQIT1 43) 104 (UNSPEC_MFENCE 44) 105 (UNSPEC_LFENCE 45) 106 (UNSPEC_PSADBW 46) 107 (UNSPEC_LDQQU 47) 108 109 ; Generic math support 110 (UNSPEC_COPYSIGN 50) 111 (UNSPEC_IEEE_MIN 51) ; not commutative 112 (UNSPEC_IEEE_MAX 52) ; not commutative 113 114 ; x87 Floating point 115 (UNSPEC_SIN 60) 116 (UNSPEC_COS 61) 117 (UNSPEC_FPATAN 62) 118 (UNSPEC_FYL2X 63) 119 (UNSPEC_FYL2XP1 64) 120 (UNSPEC_FRNDINT 65) 121 (UNSPEC_FIST 66) 122 (UNSPEC_F2XM1 67) 123 124 ; x87 Rounding 125 (UNSPEC_FRNDINT_FLOOR 70) 126 (UNSPEC_FRNDINT_CEIL 71) 127 (UNSPEC_FRNDINT_TRUNC 72) 128 (UNSPEC_FRNDINT_MASK_PM 73) 129 (UNSPEC_FIST_FLOOR 74) 130 (UNSPEC_FIST_CEIL 75) 131 132 ; x87 Double output FP 133 (UNSPEC_SINCOS_COS 80) 134 (UNSPEC_SINCOS_SIN 81) 135 (UNSPEC_TAN_ONE 82) 136 (UNSPEC_TAN_TAN 83) 137 (UNSPEC_XTRACT_FRACT 84) 138 (UNSPEC_XTRACT_EXP 85) 139 (UNSPEC_FSCALE_FRACT 86) 140 (UNSPEC_FSCALE_EXP 87) 141 (UNSPEC_FPREM_F 88) 142 (UNSPEC_FPREM_U 89) 143 (UNSPEC_FPREM1_F 90) 144 (UNSPEC_FPREM1_U 91) 145 146 ; SSP patterns 147 (UNSPEC_SP_SET 100) 148 (UNSPEC_SP_TEST 101) 149 (UNSPEC_SP_TLS_SET 102) 150 (UNSPEC_SP_TLS_TEST 103) 151 152 ; SSSE3 153 (UNSPEC_PSHUFB 120) 154 (UNSPEC_PSIGN 121) 155 (UNSPEC_PALIGNR 122) 156 157 ; For SSE4A support 158 (UNSPEC_EXTRQI 130) 159 (UNSPEC_EXTRQ 131) 160 (UNSPEC_INSERTQI 132) 161 (UNSPEC_INSERTQ 133) 162 ]) 163 164(define_constants 165 [(UNSPECV_BLOCKAGE 0) 166 (UNSPECV_STACK_PROBE 1) 167 (UNSPECV_EMMS 2) 168 (UNSPECV_LDMXCSR 3) 169 (UNSPECV_STMXCSR 4) 170 (UNSPECV_FEMMS 5) 171 (UNSPECV_CLFLUSH 6) 172 (UNSPECV_ALIGN 7) 173 (UNSPECV_MONITOR 8) 174 (UNSPECV_MWAIT 9) 175 (UNSPECV_CMPXCHG_1 10) 176 (UNSPECV_CMPXCHG_2 11) 177 (UNSPECV_XCHG 12) 178 (UNSPECV_LOCK 13) 179 ]) 180 181;; Registers by name. 182(define_constants 183 [(BP_REG 6) 184 (SP_REG 7) 185 (FLAGS_REG 17) 186 (FPSR_REG 18) 187 (DIRFLAG_REG 19) 188 ]) 189 190;; Insns whose names begin with "x86_" are emitted by gen_FOO calls 191;; from i386.c. 192 193;; In C guard expressions, put expressions which may be compile-time 194;; constants first. This allows for better optimization. For 195;; example, write "TARGET_64BIT && reload_completed", not 196;; "reload_completed && TARGET_64BIT". 197 198 199;; Processor type. This attribute must exactly match the processor_type 200;; enumeration in i386.h. 201(define_attr "cpu" "i386,i486,pentium,pentiumpro,geode,k6,athlon,pentium4,k8, 202 nocona,core2,generic32,generic64,amdfam10" 203 (const (symbol_ref "ix86_tune"))) 204 205;; A basic instruction type. Refinements due to arguments to be 206;; provided in other attributes. 207(define_attr "type" 208 "other,multi, 209 alu,alu1,negnot,imov,imovx,lea, 210 incdec,ishift,ishift1,rotate,rotate1,imul,idiv, 211 icmp,test,ibr,setcc,icmov, 212 push,pop,call,callv,leave, 213 str,bitmanip,cld, 214 fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint, 215 sselog,sselog1,sseiadd,sseishft,sseimul, 216 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,sseins, 217 mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft" 218 (const_string "other")) 219 220;; Main data type used by the insn 221(define_attr "mode" 222 "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF" 223 (const_string "unknown")) 224 225;; The CPU unit operations uses. 226(define_attr "unit" "integer,i387,sse,mmx,unknown" 227 (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint") 228 (const_string "i387") 229 (eq_attr "type" "sselog,sselog1,sseiadd,sseishft,sseimul, 230 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,sseins") 231 (const_string "sse") 232 (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft") 233 (const_string "mmx") 234 (eq_attr "type" "other") 235 (const_string "unknown")] 236 (const_string "integer"))) 237 238;; The (bounding maximum) length of an instruction immediate. 239(define_attr "length_immediate" "" 240 (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave, 241 bitmanip") 242 (const_int 0) 243 (eq_attr "unit" "i387,sse,mmx") 244 (const_int 0) 245 (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1, 246 imul,icmp,push,pop") 247 (symbol_ref "ix86_attr_length_immediate_default(insn,1)") 248 (eq_attr "type" "imov,test") 249 (symbol_ref "ix86_attr_length_immediate_default(insn,0)") 250 (eq_attr "type" "call") 251 (if_then_else (match_operand 0 "constant_call_address_operand" "") 252 (const_int 4) 253 (const_int 0)) 254 (eq_attr "type" "callv") 255 (if_then_else (match_operand 1 "constant_call_address_operand" "") 256 (const_int 4) 257 (const_int 0)) 258 ;; We don't know the size before shorten_branches. Expect 259 ;; the instruction to fit for better scheduling. 260 (eq_attr "type" "ibr") 261 (const_int 1) 262 ] 263 (symbol_ref "/* Update immediate_length and other attributes! */ 264 gcc_unreachable (),1"))) 265 266;; The (bounding maximum) length of an instruction address. 267(define_attr "length_address" "" 268 (cond [(eq_attr "type" "str,cld,other,multi,fxch") 269 (const_int 0) 270 (and (eq_attr "type" "call") 271 (match_operand 0 "constant_call_address_operand" "")) 272 (const_int 0) 273 (and (eq_attr "type" "callv") 274 (match_operand 1 "constant_call_address_operand" "")) 275 (const_int 0) 276 ] 277 (symbol_ref "ix86_attr_length_address_default (insn)"))) 278 279;; Set when length prefix is used. 280(define_attr "prefix_data16" "" 281 (if_then_else (ior (eq_attr "mode" "HI") 282 (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF"))) 283 (const_int 1) 284 (const_int 0))) 285 286;; Set when string REP prefix is used. 287(define_attr "prefix_rep" "" 288 (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF")) 289 (const_int 1) 290 (const_int 0))) 291 292;; Set when 0f opcode prefix is used. 293(define_attr "prefix_0f" "" 294 (if_then_else 295 (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip") 296 (eq_attr "unit" "sse,mmx")) 297 (const_int 1) 298 (const_int 0))) 299 300;; Set when REX opcode prefix is used. 301(define_attr "prefix_rex" "" 302 (cond [(and (eq_attr "mode" "DI") 303 (eq_attr "type" "!push,pop,call,callv,leave,ibr")) 304 (const_int 1) 305 (and (eq_attr "mode" "QI") 306 (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)") 307 (const_int 0))) 308 (const_int 1) 309 (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)") 310 (const_int 0)) 311 (const_int 1) 312 ] 313 (const_int 0))) 314 315;; Set when modrm byte is used. 316(define_attr "modrm" "" 317 (cond [(eq_attr "type" "str,cld,leave") 318 (const_int 0) 319 (eq_attr "unit" "i387") 320 (const_int 0) 321 (and (eq_attr "type" "incdec") 322 (ior (match_operand:SI 1 "register_operand" "") 323 (match_operand:HI 1 "register_operand" ""))) 324 (const_int 0) 325 (and (eq_attr "type" "push") 326 (not (match_operand 1 "memory_operand" ""))) 327 (const_int 0) 328 (and (eq_attr "type" "pop") 329 (not (match_operand 0 "memory_operand" ""))) 330 (const_int 0) 331 (and (eq_attr "type" "imov") 332 (ior (and (match_operand 0 "register_operand" "") 333 (match_operand 1 "immediate_operand" "")) 334 (ior (and (match_operand 0 "ax_reg_operand" "") 335 (match_operand 1 "memory_displacement_only_operand" "")) 336 (and (match_operand 0 "memory_displacement_only_operand" "") 337 (match_operand 1 "ax_reg_operand" ""))))) 338 (const_int 0) 339 (and (eq_attr "type" "call") 340 (match_operand 0 "constant_call_address_operand" "")) 341 (const_int 0) 342 (and (eq_attr "type" "callv") 343 (match_operand 1 "constant_call_address_operand" "")) 344 (const_int 0) 345 ] 346 (const_int 1))) 347 348;; The (bounding maximum) length of an instruction in bytes. 349;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences. 350;; Later we may want to split them and compute proper length as for 351;; other insns. 352(define_attr "length" "" 353 (cond [(eq_attr "type" "other,multi,fistp,frndint") 354 (const_int 16) 355 (eq_attr "type" "fcmp") 356 (const_int 4) 357 (eq_attr "unit" "i387") 358 (plus (const_int 2) 359 (plus (attr "prefix_data16") 360 (attr "length_address")))] 361 (plus (plus (attr "modrm") 362 (plus (attr "prefix_0f") 363 (plus (attr "prefix_rex") 364 (const_int 1)))) 365 (plus (attr "prefix_rep") 366 (plus (attr "prefix_data16") 367 (plus (attr "length_immediate") 368 (attr "length_address"))))))) 369 370;; The `memory' attribute is `none' if no memory is referenced, `load' or 371;; `store' if there is a simple memory reference therein, or `unknown' 372;; if the instruction is complex. 373 374(define_attr "memory" "none,load,store,both,unknown" 375 (cond [(eq_attr "type" "other,multi,str") 376 (const_string "unknown") 377 (eq_attr "type" "lea,fcmov,fpspc,cld") 378 (const_string "none") 379 (eq_attr "type" "fistp,leave") 380 (const_string "both") 381 (eq_attr "type" "frndint") 382 (const_string "load") 383 (eq_attr "type" "push") 384 (if_then_else (match_operand 1 "memory_operand" "") 385 (const_string "both") 386 (const_string "store")) 387 (eq_attr "type" "pop") 388 (if_then_else (match_operand 0 "memory_operand" "") 389 (const_string "both") 390 (const_string "load")) 391 (eq_attr "type" "setcc") 392 (if_then_else (match_operand 0 "memory_operand" "") 393 (const_string "store") 394 (const_string "none")) 395 (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp") 396 (if_then_else (ior (match_operand 0 "memory_operand" "") 397 (match_operand 1 "memory_operand" "")) 398 (const_string "load") 399 (const_string "none")) 400 (eq_attr "type" "ibr") 401 (if_then_else (match_operand 0 "memory_operand" "") 402 (const_string "load") 403 (const_string "none")) 404 (eq_attr "type" "call") 405 (if_then_else (match_operand 0 "constant_call_address_operand" "") 406 (const_string "none") 407 (const_string "load")) 408 (eq_attr "type" "callv") 409 (if_then_else (match_operand 1 "constant_call_address_operand" "") 410 (const_string "none") 411 (const_string "load")) 412 (and (eq_attr "type" "alu1,negnot,ishift1,sselog1") 413 (match_operand 1 "memory_operand" "")) 414 (const_string "both") 415 (and (match_operand 0 "memory_operand" "") 416 (match_operand 1 "memory_operand" "")) 417 (const_string "both") 418 (match_operand 0 "memory_operand" "") 419 (const_string "store") 420 (match_operand 1 "memory_operand" "") 421 (const_string "load") 422 (and (eq_attr "type" 423 "!alu1,negnot,ishift1, 424 imov,imovx,icmp,test,bitmanip, 425 fmov,fcmp,fsgn, 426 sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,sselog1, 427 mmx,mmxmov,mmxcmp,mmxcvt") 428 (match_operand 2 "memory_operand" "")) 429 (const_string "load") 430 (and (eq_attr "type" "icmov") 431 (match_operand 3 "memory_operand" "")) 432 (const_string "load") 433 ] 434 (const_string "none"))) 435 436;; Indicates if an instruction has both an immediate and a displacement. 437 438(define_attr "imm_disp" "false,true,unknown" 439 (cond [(eq_attr "type" "other,multi") 440 (const_string "unknown") 441 (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1") 442 (and (match_operand 0 "memory_displacement_operand" "") 443 (match_operand 1 "immediate_operand" ""))) 444 (const_string "true") 445 (and (eq_attr "type" "alu,ishift,rotate,imul,idiv") 446 (and (match_operand 0 "memory_displacement_operand" "") 447 (match_operand 2 "immediate_operand" ""))) 448 (const_string "true") 449 ] 450 (const_string "false"))) 451 452;; Indicates if an FP operation has an integer source. 453 454(define_attr "fp_int_src" "false,true" 455 (const_string "false")) 456 457;; Defines rounding mode of an FP operation. 458 459(define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any" 460 (const_string "any")) 461 462;; Describe a user's asm statement. 463(define_asm_attributes 464 [(set_attr "length" "128") 465 (set_attr "type" "multi")]) 466 467;; All x87 floating point modes 468(define_mode_macro X87MODEF [SF DF XF]) 469 470;; All integer modes handled by x87 fisttp operator. 471(define_mode_macro X87MODEI [HI SI DI]) 472 473;; All integer modes handled by integer x87 operators. 474(define_mode_macro X87MODEI12 [HI SI]) 475 476;; All SSE floating point modes 477(define_mode_macro SSEMODEF [SF DF]) 478 479;; All integer modes handled by SSE cvtts?2si* operators. 480(define_mode_macro SSEMODEI24 [SI DI]) 481 482 483;; Scheduling descriptions 484 485(include "pentium.md") 486(include "ppro.md") 487(include "k6.md") 488(include "athlon.md") 489(include "geode.md") 490 491 492;; Operand and operator predicates and constraints 493 494(include "predicates.md") 495(include "constraints.md") 496 497 498;; Compare instructions. 499 500;; All compare insns have expanders that save the operands away without 501;; actually generating RTL. The bCOND or sCOND (emitted immediately 502;; after the cmp) will actually emit the cmpM. 503 504(define_expand "cmpti" 505 [(set (reg:CC FLAGS_REG) 506 (compare:CC (match_operand:TI 0 "nonimmediate_operand" "") 507 (match_operand:TI 1 "x86_64_general_operand" "")))] 508 "TARGET_64BIT" 509{ 510 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 511 operands[0] = force_reg (TImode, operands[0]); 512 ix86_compare_op0 = operands[0]; 513 ix86_compare_op1 = operands[1]; 514 DONE; 515}) 516 517(define_expand "cmpdi" 518 [(set (reg:CC FLAGS_REG) 519 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "") 520 (match_operand:DI 1 "x86_64_general_operand" "")))] 521 "" 522{ 523 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 524 operands[0] = force_reg (DImode, operands[0]); 525 ix86_compare_op0 = operands[0]; 526 ix86_compare_op1 = operands[1]; 527 DONE; 528}) 529 530(define_expand "cmpsi" 531 [(set (reg:CC FLAGS_REG) 532 (compare:CC (match_operand:SI 0 "cmpsi_operand" "") 533 (match_operand:SI 1 "general_operand" "")))] 534 "" 535{ 536 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 537 operands[0] = force_reg (SImode, operands[0]); 538 ix86_compare_op0 = operands[0]; 539 ix86_compare_op1 = operands[1]; 540 DONE; 541}) 542 543(define_expand "cmphi" 544 [(set (reg:CC FLAGS_REG) 545 (compare:CC (match_operand:HI 0 "nonimmediate_operand" "") 546 (match_operand:HI 1 "general_operand" "")))] 547 "" 548{ 549 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 550 operands[0] = force_reg (HImode, operands[0]); 551 ix86_compare_op0 = operands[0]; 552 ix86_compare_op1 = operands[1]; 553 DONE; 554}) 555 556(define_expand "cmpqi" 557 [(set (reg:CC FLAGS_REG) 558 (compare:CC (match_operand:QI 0 "nonimmediate_operand" "") 559 (match_operand:QI 1 "general_operand" "")))] 560 "TARGET_QIMODE_MATH" 561{ 562 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 563 operands[0] = force_reg (QImode, operands[0]); 564 ix86_compare_op0 = operands[0]; 565 ix86_compare_op1 = operands[1]; 566 DONE; 567}) 568 569(define_insn "cmpdi_ccno_1_rex64" 570 [(set (reg FLAGS_REG) 571 (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr") 572 (match_operand:DI 1 "const0_operand" "n,n")))] 573 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)" 574 "@ 575 test{q}\t{%0, %0|%0, %0} 576 cmp{q}\t{%1, %0|%0, %1}" 577 [(set_attr "type" "test,icmp") 578 (set_attr "length_immediate" "0,1") 579 (set_attr "mode" "DI")]) 580 581(define_insn "*cmpdi_minus_1_rex64" 582 [(set (reg FLAGS_REG) 583 (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r") 584 (match_operand:DI 1 "x86_64_general_operand" "re,mr")) 585 (const_int 0)))] 586 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)" 587 "cmp{q}\t{%1, %0|%0, %1}" 588 [(set_attr "type" "icmp") 589 (set_attr "mode" "DI")]) 590 591(define_expand "cmpdi_1_rex64" 592 [(set (reg:CC FLAGS_REG) 593 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "") 594 (match_operand:DI 1 "general_operand" "")))] 595 "TARGET_64BIT" 596 "") 597 598(define_insn "cmpdi_1_insn_rex64" 599 [(set (reg FLAGS_REG) 600 (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r") 601 (match_operand:DI 1 "x86_64_general_operand" "re,mr")))] 602 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)" 603 "cmp{q}\t{%1, %0|%0, %1}" 604 [(set_attr "type" "icmp") 605 (set_attr "mode" "DI")]) 606 607 608(define_insn "*cmpsi_ccno_1" 609 [(set (reg FLAGS_REG) 610 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr") 611 (match_operand:SI 1 "const0_operand" "n,n")))] 612 "ix86_match_ccmode (insn, CCNOmode)" 613 "@ 614 test{l}\t{%0, %0|%0, %0} 615 cmp{l}\t{%1, %0|%0, %1}" 616 [(set_attr "type" "test,icmp") 617 (set_attr "length_immediate" "0,1") 618 (set_attr "mode" "SI")]) 619 620(define_insn "*cmpsi_minus_1" 621 [(set (reg FLAGS_REG) 622 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r") 623 (match_operand:SI 1 "general_operand" "ri,mr")) 624 (const_int 0)))] 625 "ix86_match_ccmode (insn, CCGOCmode)" 626 "cmp{l}\t{%1, %0|%0, %1}" 627 [(set_attr "type" "icmp") 628 (set_attr "mode" "SI")]) 629 630(define_expand "cmpsi_1" 631 [(set (reg:CC FLAGS_REG) 632 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r") 633 (match_operand:SI 1 "general_operand" "ri,mr")))] 634 "" 635 "") 636 637(define_insn "*cmpsi_1_insn" 638 [(set (reg FLAGS_REG) 639 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r") 640 (match_operand:SI 1 "general_operand" "ri,mr")))] 641 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 642 && ix86_match_ccmode (insn, CCmode)" 643 "cmp{l}\t{%1, %0|%0, %1}" 644 [(set_attr "type" "icmp") 645 (set_attr "mode" "SI")]) 646 647(define_insn "*cmphi_ccno_1" 648 [(set (reg FLAGS_REG) 649 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr") 650 (match_operand:HI 1 "const0_operand" "n,n")))] 651 "ix86_match_ccmode (insn, CCNOmode)" 652 "@ 653 test{w}\t{%0, %0|%0, %0} 654 cmp{w}\t{%1, %0|%0, %1}" 655 [(set_attr "type" "test,icmp") 656 (set_attr "length_immediate" "0,1") 657 (set_attr "mode" "HI")]) 658 659(define_insn "*cmphi_minus_1" 660 [(set (reg FLAGS_REG) 661 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r") 662 (match_operand:HI 1 "general_operand" "ri,mr")) 663 (const_int 0)))] 664 "ix86_match_ccmode (insn, CCGOCmode)" 665 "cmp{w}\t{%1, %0|%0, %1}" 666 [(set_attr "type" "icmp") 667 (set_attr "mode" "HI")]) 668 669(define_insn "*cmphi_1" 670 [(set (reg FLAGS_REG) 671 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r") 672 (match_operand:HI 1 "general_operand" "ri,mr")))] 673 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 674 && ix86_match_ccmode (insn, CCmode)" 675 "cmp{w}\t{%1, %0|%0, %1}" 676 [(set_attr "type" "icmp") 677 (set_attr "mode" "HI")]) 678 679(define_insn "*cmpqi_ccno_1" 680 [(set (reg FLAGS_REG) 681 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq") 682 (match_operand:QI 1 "const0_operand" "n,n")))] 683 "ix86_match_ccmode (insn, CCNOmode)" 684 "@ 685 test{b}\t{%0, %0|%0, %0} 686 cmp{b}\t{$0, %0|%0, 0}" 687 [(set_attr "type" "test,icmp") 688 (set_attr "length_immediate" "0,1") 689 (set_attr "mode" "QI")]) 690 691(define_insn "*cmpqi_1" 692 [(set (reg FLAGS_REG) 693 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q") 694 (match_operand:QI 1 "general_operand" "qi,mq")))] 695 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 696 && ix86_match_ccmode (insn, CCmode)" 697 "cmp{b}\t{%1, %0|%0, %1}" 698 [(set_attr "type" "icmp") 699 (set_attr "mode" "QI")]) 700 701(define_insn "*cmpqi_minus_1" 702 [(set (reg FLAGS_REG) 703 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q") 704 (match_operand:QI 1 "general_operand" "qi,mq")) 705 (const_int 0)))] 706 "ix86_match_ccmode (insn, CCGOCmode)" 707 "cmp{b}\t{%1, %0|%0, %1}" 708 [(set_attr "type" "icmp") 709 (set_attr "mode" "QI")]) 710 711(define_insn "*cmpqi_ext_1" 712 [(set (reg FLAGS_REG) 713 (compare 714 (match_operand:QI 0 "general_operand" "Qm") 715 (subreg:QI 716 (zero_extract:SI 717 (match_operand 1 "ext_register_operand" "Q") 718 (const_int 8) 719 (const_int 8)) 0)))] 720 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)" 721 "cmp{b}\t{%h1, %0|%0, %h1}" 722 [(set_attr "type" "icmp") 723 (set_attr "mode" "QI")]) 724 725(define_insn "*cmpqi_ext_1_rex64" 726 [(set (reg FLAGS_REG) 727 (compare 728 (match_operand:QI 0 "register_operand" "Q") 729 (subreg:QI 730 (zero_extract:SI 731 (match_operand 1 "ext_register_operand" "Q") 732 (const_int 8) 733 (const_int 8)) 0)))] 734 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)" 735 "cmp{b}\t{%h1, %0|%0, %h1}" 736 [(set_attr "type" "icmp") 737 (set_attr "mode" "QI")]) 738 739(define_insn "*cmpqi_ext_2" 740 [(set (reg FLAGS_REG) 741 (compare 742 (subreg:QI 743 (zero_extract:SI 744 (match_operand 0 "ext_register_operand" "Q") 745 (const_int 8) 746 (const_int 8)) 0) 747 (match_operand:QI 1 "const0_operand" "n")))] 748 "ix86_match_ccmode (insn, CCNOmode)" 749 "test{b}\t%h0, %h0" 750 [(set_attr "type" "test") 751 (set_attr "length_immediate" "0") 752 (set_attr "mode" "QI")]) 753 754(define_expand "cmpqi_ext_3" 755 [(set (reg:CC FLAGS_REG) 756 (compare:CC 757 (subreg:QI 758 (zero_extract:SI 759 (match_operand 0 "ext_register_operand" "") 760 (const_int 8) 761 (const_int 8)) 0) 762 (match_operand:QI 1 "general_operand" "")))] 763 "" 764 "") 765 766(define_insn "cmpqi_ext_3_insn" 767 [(set (reg FLAGS_REG) 768 (compare 769 (subreg:QI 770 (zero_extract:SI 771 (match_operand 0 "ext_register_operand" "Q") 772 (const_int 8) 773 (const_int 8)) 0) 774 (match_operand:QI 1 "general_operand" "Qmn")))] 775 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)" 776 "cmp{b}\t{%1, %h0|%h0, %1}" 777 [(set_attr "type" "icmp") 778 (set_attr "mode" "QI")]) 779 780(define_insn "cmpqi_ext_3_insn_rex64" 781 [(set (reg FLAGS_REG) 782 (compare 783 (subreg:QI 784 (zero_extract:SI 785 (match_operand 0 "ext_register_operand" "Q") 786 (const_int 8) 787 (const_int 8)) 0) 788 (match_operand:QI 1 "nonmemory_operand" "Qn")))] 789 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)" 790 "cmp{b}\t{%1, %h0|%h0, %1}" 791 [(set_attr "type" "icmp") 792 (set_attr "mode" "QI")]) 793 794(define_insn "*cmpqi_ext_4" 795 [(set (reg FLAGS_REG) 796 (compare 797 (subreg:QI 798 (zero_extract:SI 799 (match_operand 0 "ext_register_operand" "Q") 800 (const_int 8) 801 (const_int 8)) 0) 802 (subreg:QI 803 (zero_extract:SI 804 (match_operand 1 "ext_register_operand" "Q") 805 (const_int 8) 806 (const_int 8)) 0)))] 807 "ix86_match_ccmode (insn, CCmode)" 808 "cmp{b}\t{%h1, %h0|%h0, %h1}" 809 [(set_attr "type" "icmp") 810 (set_attr "mode" "QI")]) 811 812;; These implement float point compares. 813;; %%% See if we can get away with VOIDmode operands on the actual insns, 814;; which would allow mix and match FP modes on the compares. Which is what 815;; the old patterns did, but with many more of them. 816 817(define_expand "cmpxf" 818 [(set (reg:CC FLAGS_REG) 819 (compare:CC (match_operand:XF 0 "nonmemory_operand" "") 820 (match_operand:XF 1 "nonmemory_operand" "")))] 821 "TARGET_80387" 822{ 823 ix86_compare_op0 = operands[0]; 824 ix86_compare_op1 = operands[1]; 825 DONE; 826}) 827 828(define_expand "cmpdf" 829 [(set (reg:CC FLAGS_REG) 830 (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "") 831 (match_operand:DF 1 "cmp_fp_expander_operand" "")))] 832 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 833{ 834 ix86_compare_op0 = operands[0]; 835 ix86_compare_op1 = operands[1]; 836 DONE; 837}) 838 839(define_expand "cmpsf" 840 [(set (reg:CC FLAGS_REG) 841 (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "") 842 (match_operand:SF 1 "cmp_fp_expander_operand" "")))] 843 "TARGET_80387 || TARGET_SSE_MATH" 844{ 845 ix86_compare_op0 = operands[0]; 846 ix86_compare_op1 = operands[1]; 847 DONE; 848}) 849 850;; FP compares, step 1: 851;; Set the FP condition codes. 852;; 853;; CCFPmode compare with exceptions 854;; CCFPUmode compare with no exceptions 855 856;; We may not use "#" to split and emit these, since the REG_DEAD notes 857;; used to manage the reg stack popping would not be preserved. 858 859(define_insn "*cmpfp_0" 860 [(set (match_operand:HI 0 "register_operand" "=a") 861 (unspec:HI 862 [(compare:CCFP 863 (match_operand 1 "register_operand" "f") 864 (match_operand 2 "const0_operand" "X"))] 865 UNSPEC_FNSTSW))] 866 "TARGET_80387 867 && FLOAT_MODE_P (GET_MODE (operands[1])) 868 && GET_MODE (operands[1]) == GET_MODE (operands[2])" 869 "* return output_fp_compare (insn, operands, 0, 0);" 870 [(set_attr "type" "multi") 871 (set_attr "unit" "i387") 872 (set (attr "mode") 873 (cond [(match_operand:SF 1 "" "") 874 (const_string "SF") 875 (match_operand:DF 1 "" "") 876 (const_string "DF") 877 ] 878 (const_string "XF")))]) 879 880(define_insn "*cmpfp_sf" 881 [(set (match_operand:HI 0 "register_operand" "=a") 882 (unspec:HI 883 [(compare:CCFP 884 (match_operand:SF 1 "register_operand" "f") 885 (match_operand:SF 2 "nonimmediate_operand" "fm"))] 886 UNSPEC_FNSTSW))] 887 "TARGET_80387" 888 "* return output_fp_compare (insn, operands, 0, 0);" 889 [(set_attr "type" "multi") 890 (set_attr "unit" "i387") 891 (set_attr "mode" "SF")]) 892 893(define_insn "*cmpfp_df" 894 [(set (match_operand:HI 0 "register_operand" "=a") 895 (unspec:HI 896 [(compare:CCFP 897 (match_operand:DF 1 "register_operand" "f") 898 (match_operand:DF 2 "nonimmediate_operand" "fm"))] 899 UNSPEC_FNSTSW))] 900 "TARGET_80387" 901 "* return output_fp_compare (insn, operands, 0, 0);" 902 [(set_attr "type" "multi") 903 (set_attr "unit" "i387") 904 (set_attr "mode" "DF")]) 905 906(define_insn "*cmpfp_xf" 907 [(set (match_operand:HI 0 "register_operand" "=a") 908 (unspec:HI 909 [(compare:CCFP 910 (match_operand:XF 1 "register_operand" "f") 911 (match_operand:XF 2 "register_operand" "f"))] 912 UNSPEC_FNSTSW))] 913 "TARGET_80387" 914 "* return output_fp_compare (insn, operands, 0, 0);" 915 [(set_attr "type" "multi") 916 (set_attr "unit" "i387") 917 (set_attr "mode" "XF")]) 918 919(define_insn "*cmpfp_u" 920 [(set (match_operand:HI 0 "register_operand" "=a") 921 (unspec:HI 922 [(compare:CCFPU 923 (match_operand 1 "register_operand" "f") 924 (match_operand 2 "register_operand" "f"))] 925 UNSPEC_FNSTSW))] 926 "TARGET_80387 927 && FLOAT_MODE_P (GET_MODE (operands[1])) 928 && GET_MODE (operands[1]) == GET_MODE (operands[2])" 929 "* return output_fp_compare (insn, operands, 0, 1);" 930 [(set_attr "type" "multi") 931 (set_attr "unit" "i387") 932 (set (attr "mode") 933 (cond [(match_operand:SF 1 "" "") 934 (const_string "SF") 935 (match_operand:DF 1 "" "") 936 (const_string "DF") 937 ] 938 (const_string "XF")))]) 939 940(define_insn "*cmpfp_<mode>" 941 [(set (match_operand:HI 0 "register_operand" "=a") 942 (unspec:HI 943 [(compare:CCFP 944 (match_operand 1 "register_operand" "f") 945 (match_operator 3 "float_operator" 946 [(match_operand:X87MODEI12 2 "memory_operand" "m")]))] 947 UNSPEC_FNSTSW))] 948 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP 949 && FLOAT_MODE_P (GET_MODE (operands[1])) 950 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))" 951 "* return output_fp_compare (insn, operands, 0, 0);" 952 [(set_attr "type" "multi") 953 (set_attr "unit" "i387") 954 (set_attr "fp_int_src" "true") 955 (set_attr "mode" "<MODE>")]) 956 957;; FP compares, step 2 958;; Move the fpsw to ax. 959 960(define_insn "x86_fnstsw_1" 961 [(set (match_operand:HI 0 "register_operand" "=a") 962 (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))] 963 "TARGET_80387" 964 "fnstsw\t%0" 965 [(set_attr "length" "2") 966 (set_attr "mode" "SI") 967 (set_attr "unit" "i387")]) 968 969;; FP compares, step 3 970;; Get ax into flags, general case. 971 972(define_insn "x86_sahf_1" 973 [(set (reg:CC FLAGS_REG) 974 (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))] 975 "!TARGET_64BIT" 976 "sahf" 977 [(set_attr "length" "1") 978 (set_attr "athlon_decode" "vector") 979 (set_attr "amdfam10_decode" "direct") 980 (set_attr "mode" "SI")]) 981 982;; Pentium Pro can do steps 1 through 3 in one go. 983;; comi*, ucomi*, fcomi*, ficomi*,fucomi* (i387 instructions set condition codes) 984(define_insn "*cmpfp_i_mixed" 985 [(set (reg:CCFP FLAGS_REG) 986 (compare:CCFP (match_operand 0 "register_operand" "f,x") 987 (match_operand 1 "nonimmediate_operand" "f,xm")))] 988 "TARGET_MIX_SSE_I387 989 && SSE_FLOAT_MODE_P (GET_MODE (operands[0])) 990 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 991 "* return output_fp_compare (insn, operands, 1, 0);" 992 [(set_attr "type" "fcmp,ssecomi") 993 (set (attr "mode") 994 (if_then_else (match_operand:SF 1 "" "") 995 (const_string "SF") 996 (const_string "DF"))) 997 (set_attr "athlon_decode" "vector") 998 (set_attr "amdfam10_decode" "direct")]) 999 1000(define_insn "*cmpfp_i_sse" 1001 [(set (reg:CCFP FLAGS_REG) 1002 (compare:CCFP (match_operand 0 "register_operand" "x") 1003 (match_operand 1 "nonimmediate_operand" "xm")))] 1004 "TARGET_SSE_MATH 1005 && SSE_FLOAT_MODE_P (GET_MODE (operands[0])) 1006 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 1007 "* return output_fp_compare (insn, operands, 1, 0);" 1008 [(set_attr "type" "ssecomi") 1009 (set (attr "mode") 1010 (if_then_else (match_operand:SF 1 "" "") 1011 (const_string "SF") 1012 (const_string "DF"))) 1013 (set_attr "athlon_decode" "vector") 1014 (set_attr "amdfam10_decode" "direct")]) 1015 1016(define_insn "*cmpfp_i_i387" 1017 [(set (reg:CCFP FLAGS_REG) 1018 (compare:CCFP (match_operand 0 "register_operand" "f") 1019 (match_operand 1 "register_operand" "f")))] 1020 "TARGET_80387 && TARGET_CMOVE 1021 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))) 1022 && FLOAT_MODE_P (GET_MODE (operands[0])) 1023 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 1024 "* return output_fp_compare (insn, operands, 1, 0);" 1025 [(set_attr "type" "fcmp") 1026 (set (attr "mode") 1027 (cond [(match_operand:SF 1 "" "") 1028 (const_string "SF") 1029 (match_operand:DF 1 "" "") 1030 (const_string "DF") 1031 ] 1032 (const_string "XF"))) 1033 (set_attr "athlon_decode" "vector") 1034 (set_attr "amdfam10_decode" "direct")]) 1035 1036(define_insn "*cmpfp_iu_mixed" 1037 [(set (reg:CCFPU FLAGS_REG) 1038 (compare:CCFPU (match_operand 0 "register_operand" "f,x") 1039 (match_operand 1 "nonimmediate_operand" "f,xm")))] 1040 "TARGET_MIX_SSE_I387 1041 && SSE_FLOAT_MODE_P (GET_MODE (operands[0])) 1042 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 1043 "* return output_fp_compare (insn, operands, 1, 1);" 1044 [(set_attr "type" "fcmp,ssecomi") 1045 (set (attr "mode") 1046 (if_then_else (match_operand:SF 1 "" "") 1047 (const_string "SF") 1048 (const_string "DF"))) 1049 (set_attr "athlon_decode" "vector") 1050 (set_attr "amdfam10_decode" "direct")]) 1051 1052(define_insn "*cmpfp_iu_sse" 1053 [(set (reg:CCFPU FLAGS_REG) 1054 (compare:CCFPU (match_operand 0 "register_operand" "x") 1055 (match_operand 1 "nonimmediate_operand" "xm")))] 1056 "TARGET_SSE_MATH 1057 && SSE_FLOAT_MODE_P (GET_MODE (operands[0])) 1058 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 1059 "* return output_fp_compare (insn, operands, 1, 1);" 1060 [(set_attr "type" "ssecomi") 1061 (set (attr "mode") 1062 (if_then_else (match_operand:SF 1 "" "") 1063 (const_string "SF") 1064 (const_string "DF"))) 1065 (set_attr "athlon_decode" "vector") 1066 (set_attr "amdfam10_decode" "direct")]) 1067 1068(define_insn "*cmpfp_iu_387" 1069 [(set (reg:CCFPU FLAGS_REG) 1070 (compare:CCFPU (match_operand 0 "register_operand" "f") 1071 (match_operand 1 "register_operand" "f")))] 1072 "TARGET_80387 && TARGET_CMOVE 1073 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))) 1074 && FLOAT_MODE_P (GET_MODE (operands[0])) 1075 && GET_MODE (operands[0]) == GET_MODE (operands[1])" 1076 "* return output_fp_compare (insn, operands, 1, 1);" 1077 [(set_attr "type" "fcmp") 1078 (set (attr "mode") 1079 (cond [(match_operand:SF 1 "" "") 1080 (const_string "SF") 1081 (match_operand:DF 1 "" "") 1082 (const_string "DF") 1083 ] 1084 (const_string "XF"))) 1085 (set_attr "athlon_decode" "vector") 1086 (set_attr "amdfam10_decode" "direct")]) 1087 1088;; Move instructions. 1089 1090;; General case of fullword move. 1091 1092(define_expand "movsi" 1093 [(set (match_operand:SI 0 "nonimmediate_operand" "") 1094 (match_operand:SI 1 "general_operand" ""))] 1095 "" 1096 "ix86_expand_move (SImode, operands); DONE;") 1097 1098;; Push/pop instructions. They are separate since autoinc/dec is not a 1099;; general_operand. 1100;; 1101;; %%% We don't use a post-inc memory reference because x86 is not a 1102;; general AUTO_INC_DEC host, which impacts how it is treated in flow. 1103;; Changing this impacts compiler performance on other non-AUTO_INC_DEC 1104;; targets without our curiosities, and it is just as easy to represent 1105;; this differently. 1106 1107(define_insn "*pushsi2" 1108 [(set (match_operand:SI 0 "push_operand" "=<") 1109 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))] 1110 "!TARGET_64BIT" 1111 "push{l}\t%1" 1112 [(set_attr "type" "push") 1113 (set_attr "mode" "SI")]) 1114 1115;; For 64BIT abi we always round up to 8 bytes. 1116(define_insn "*pushsi2_rex64" 1117 [(set (match_operand:SI 0 "push_operand" "=X") 1118 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))] 1119 "TARGET_64BIT" 1120 "push{q}\t%q1" 1121 [(set_attr "type" "push") 1122 (set_attr "mode" "SI")]) 1123 1124(define_insn "*pushsi2_prologue" 1125 [(set (match_operand:SI 0 "push_operand" "=<") 1126 (match_operand:SI 1 "general_no_elim_operand" "ri*m")) 1127 (clobber (mem:BLK (scratch)))] 1128 "!TARGET_64BIT" 1129 "push{l}\t%1" 1130 [(set_attr "type" "push") 1131 (set_attr "mode" "SI")]) 1132 1133(define_insn "*popsi1_epilogue" 1134 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m") 1135 (mem:SI (reg:SI SP_REG))) 1136 (set (reg:SI SP_REG) 1137 (plus:SI (reg:SI SP_REG) (const_int 4))) 1138 (clobber (mem:BLK (scratch)))] 1139 "!TARGET_64BIT" 1140 "pop{l}\t%0" 1141 [(set_attr "type" "pop") 1142 (set_attr "mode" "SI")]) 1143 1144(define_insn "popsi1" 1145 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m") 1146 (mem:SI (reg:SI SP_REG))) 1147 (set (reg:SI SP_REG) 1148 (plus:SI (reg:SI SP_REG) (const_int 4)))] 1149 "!TARGET_64BIT" 1150 "pop{l}\t%0" 1151 [(set_attr "type" "pop") 1152 (set_attr "mode" "SI")]) 1153 1154(define_insn "*movsi_xor" 1155 [(set (match_operand:SI 0 "register_operand" "=r") 1156 (match_operand:SI 1 "const0_operand" "i")) 1157 (clobber (reg:CC FLAGS_REG))] 1158 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)" 1159 "xor{l}\t{%0, %0|%0, %0}" 1160 [(set_attr "type" "alu1") 1161 (set_attr "mode" "SI") 1162 (set_attr "length_immediate" "0")]) 1163 1164(define_insn "*movsi_or" 1165 [(set (match_operand:SI 0 "register_operand" "=r") 1166 (match_operand:SI 1 "immediate_operand" "i")) 1167 (clobber (reg:CC FLAGS_REG))] 1168 "reload_completed 1169 && operands[1] == constm1_rtx 1170 && (TARGET_PENTIUM || optimize_size)" 1171{ 1172 operands[1] = constm1_rtx; 1173 return "or{l}\t{%1, %0|%0, %1}"; 1174} 1175 [(set_attr "type" "alu1") 1176 (set_attr "mode" "SI") 1177 (set_attr "length_immediate" "1")]) 1178 1179(define_insn "*movsi_1" 1180 [(set (match_operand:SI 0 "nonimmediate_operand" 1181 "=r ,m ,*y,*y,?rm,?*y,*x,*x,?r,m ,?*Y,*x") 1182 (match_operand:SI 1 "general_operand" 1183 "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Y,*x,r ,m "))] 1184 "!(MEM_P (operands[0]) && MEM_P (operands[1]))" 1185{ 1186 switch (get_attr_type (insn)) 1187 { 1188 case TYPE_SSELOG1: 1189 if (get_attr_mode (insn) == MODE_TI) 1190 return "pxor\t%0, %0"; 1191 return "xorps\t%0, %0"; 1192 1193 case TYPE_SSEMOV: 1194 switch (get_attr_mode (insn)) 1195 { 1196 case MODE_TI: 1197 return "movdqa\t{%1, %0|%0, %1}"; 1198 case MODE_V4SF: 1199 return "movaps\t{%1, %0|%0, %1}"; 1200 case MODE_SI: 1201 return "movd\t{%1, %0|%0, %1}"; 1202 case MODE_SF: 1203 return "movss\t{%1, %0|%0, %1}"; 1204 default: 1205 gcc_unreachable (); 1206 } 1207 1208 case TYPE_MMXADD: 1209 return "pxor\t%0, %0"; 1210 1211 case TYPE_MMXMOV: 1212 if (get_attr_mode (insn) == MODE_DI) 1213 return "movq\t{%1, %0|%0, %1}"; 1214 return "movd\t{%1, %0|%0, %1}"; 1215 1216 case TYPE_LEA: 1217 return "lea{l}\t{%1, %0|%0, %1}"; 1218 1219 default: 1220 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1])); 1221 return "mov{l}\t{%1, %0|%0, %1}"; 1222 } 1223} 1224 [(set (attr "type") 1225 (cond [(eq_attr "alternative" "2") 1226 (const_string "mmxadd") 1227 (eq_attr "alternative" "3,4,5") 1228 (const_string "mmxmov") 1229 (eq_attr "alternative" "6") 1230 (const_string "sselog1") 1231 (eq_attr "alternative" "7,8,9,10,11") 1232 (const_string "ssemov") 1233 (match_operand:DI 1 "pic_32bit_operand" "") 1234 (const_string "lea") 1235 ] 1236 (const_string "imov"))) 1237 (set (attr "mode") 1238 (cond [(eq_attr "alternative" "2,3") 1239 (const_string "DI") 1240 (eq_attr "alternative" "6,7") 1241 (if_then_else 1242 (eq (symbol_ref "TARGET_SSE2") (const_int 0)) 1243 (const_string "V4SF") 1244 (const_string "TI")) 1245 (and (eq_attr "alternative" "8,9,10,11") 1246 (eq (symbol_ref "TARGET_SSE2") (const_int 0))) 1247 (const_string "SF") 1248 ] 1249 (const_string "SI")))]) 1250 1251;; Stores and loads of ax to arbitrary constant address. 1252;; We fake an second form of instruction to force reload to load address 1253;; into register when rax is not available 1254(define_insn "*movabssi_1_rex64" 1255 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r")) 1256 (match_operand:SI 1 "nonmemory_operand" "a,er"))] 1257 "TARGET_64BIT && ix86_check_movabs (insn, 0)" 1258 "@ 1259 movabs{l}\t{%1, %P0|%P0, %1} 1260 mov{l}\t{%1, %a0|%a0, %1}" 1261 [(set_attr "type" "imov") 1262 (set_attr "modrm" "0,*") 1263 (set_attr "length_address" "8,0") 1264 (set_attr "length_immediate" "0,*") 1265 (set_attr "memory" "store") 1266 (set_attr "mode" "SI")]) 1267 1268(define_insn "*movabssi_2_rex64" 1269 [(set (match_operand:SI 0 "register_operand" "=a,r") 1270 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))] 1271 "TARGET_64BIT && ix86_check_movabs (insn, 1)" 1272 "@ 1273 movabs{l}\t{%P1, %0|%0, %P1} 1274 mov{l}\t{%a1, %0|%0, %a1}" 1275 [(set_attr "type" "imov") 1276 (set_attr "modrm" "0,*") 1277 (set_attr "length_address" "8,0") 1278 (set_attr "length_immediate" "0") 1279 (set_attr "memory" "load") 1280 (set_attr "mode" "SI")]) 1281 1282(define_insn "*swapsi" 1283 [(set (match_operand:SI 0 "register_operand" "+r") 1284 (match_operand:SI 1 "register_operand" "+r")) 1285 (set (match_dup 1) 1286 (match_dup 0))] 1287 "" 1288 "xchg{l}\t%1, %0" 1289 [(set_attr "type" "imov") 1290 (set_attr "mode" "SI") 1291 (set_attr "pent_pair" "np") 1292 (set_attr "athlon_decode" "vector") 1293 (set_attr "amdfam10_decode" "double")]) 1294 1295(define_expand "movhi" 1296 [(set (match_operand:HI 0 "nonimmediate_operand" "") 1297 (match_operand:HI 1 "general_operand" ""))] 1298 "" 1299 "ix86_expand_move (HImode, operands); DONE;") 1300 1301(define_insn "*pushhi2" 1302 [(set (match_operand:HI 0 "push_operand" "=X") 1303 (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))] 1304 "!TARGET_64BIT" 1305 "push{l}\t%k1" 1306 [(set_attr "type" "push") 1307 (set_attr "mode" "SI")]) 1308 1309;; For 64BIT abi we always round up to 8 bytes. 1310(define_insn "*pushhi2_rex64" 1311 [(set (match_operand:HI 0 "push_operand" "=X") 1312 (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))] 1313 "TARGET_64BIT" 1314 "push{q}\t%q1" 1315 [(set_attr "type" "push") 1316 (set_attr "mode" "DI")]) 1317 1318(define_insn "*movhi_1" 1319 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m") 1320 (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))] 1321 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM" 1322{ 1323 switch (get_attr_type (insn)) 1324 { 1325 case TYPE_IMOVX: 1326 /* movzwl is faster than movw on p2 due to partial word stalls, 1327 though not as fast as an aligned movl. */ 1328 return "movz{wl|x}\t{%1, %k0|%k0, %1}"; 1329 default: 1330 if (get_attr_mode (insn) == MODE_SI) 1331 return "mov{l}\t{%k1, %k0|%k0, %k1}"; 1332 else 1333 return "mov{w}\t{%1, %0|%0, %1}"; 1334 } 1335} 1336 [(set (attr "type") 1337 (cond [(ne (symbol_ref "optimize_size") (const_int 0)) 1338 (const_string "imov") 1339 (and (eq_attr "alternative" "0") 1340 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL") 1341 (const_int 0)) 1342 (eq (symbol_ref "TARGET_HIMODE_MATH") 1343 (const_int 0)))) 1344 (const_string "imov") 1345 (and (eq_attr "alternative" "1,2") 1346 (match_operand:HI 1 "aligned_operand" "")) 1347 (const_string "imov") 1348 (and (ne (symbol_ref "TARGET_MOVX") 1349 (const_int 0)) 1350 (eq_attr "alternative" "0,2")) 1351 (const_string "imovx") 1352 ] 1353 (const_string "imov"))) 1354 (set (attr "mode") 1355 (cond [(eq_attr "type" "imovx") 1356 (const_string "SI") 1357 (and (eq_attr "alternative" "1,2") 1358 (match_operand:HI 1 "aligned_operand" "")) 1359 (const_string "SI") 1360 (and (eq_attr "alternative" "0") 1361 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL") 1362 (const_int 0)) 1363 (eq (symbol_ref "TARGET_HIMODE_MATH") 1364 (const_int 0)))) 1365 (const_string "SI") 1366 ] 1367 (const_string "HI")))]) 1368 1369;; Stores and loads of ax to arbitrary constant address. 1370;; We fake an second form of instruction to force reload to load address 1371;; into register when rax is not available 1372(define_insn "*movabshi_1_rex64" 1373 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r")) 1374 (match_operand:HI 1 "nonmemory_operand" "a,er"))] 1375 "TARGET_64BIT && ix86_check_movabs (insn, 0)" 1376 "@ 1377 movabs{w}\t{%1, %P0|%P0, %1} 1378 mov{w}\t{%1, %a0|%a0, %1}" 1379 [(set_attr "type" "imov") 1380 (set_attr "modrm" "0,*") 1381 (set_attr "length_address" "8,0") 1382 (set_attr "length_immediate" "0,*") 1383 (set_attr "memory" "store") 1384 (set_attr "mode" "HI")]) 1385 1386(define_insn "*movabshi_2_rex64" 1387 [(set (match_operand:HI 0 "register_operand" "=a,r") 1388 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))] 1389 "TARGET_64BIT && ix86_check_movabs (insn, 1)" 1390 "@ 1391 movabs{w}\t{%P1, %0|%0, %P1} 1392 mov{w}\t{%a1, %0|%0, %a1}" 1393 [(set_attr "type" "imov") 1394 (set_attr "modrm" "0,*") 1395 (set_attr "length_address" "8,0") 1396 (set_attr "length_immediate" "0") 1397 (set_attr "memory" "load") 1398 (set_attr "mode" "HI")]) 1399 1400(define_insn "*swaphi_1" 1401 [(set (match_operand:HI 0 "register_operand" "+r") 1402 (match_operand:HI 1 "register_operand" "+r")) 1403 (set (match_dup 1) 1404 (match_dup 0))] 1405 "!TARGET_PARTIAL_REG_STALL || optimize_size" 1406 "xchg{l}\t%k1, %k0" 1407 [(set_attr "type" "imov") 1408 (set_attr "mode" "SI") 1409 (set_attr "pent_pair" "np") 1410 (set_attr "athlon_decode" "vector") 1411 (set_attr "amdfam10_decode" "double")]) 1412 1413;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10 1414(define_insn "*swaphi_2" 1415 [(set (match_operand:HI 0 "register_operand" "+r") 1416 (match_operand:HI 1 "register_operand" "+r")) 1417 (set (match_dup 1) 1418 (match_dup 0))] 1419 "TARGET_PARTIAL_REG_STALL" 1420 "xchg{w}\t%1, %0" 1421 [(set_attr "type" "imov") 1422 (set_attr "mode" "HI") 1423 (set_attr "pent_pair" "np") 1424 (set_attr "athlon_decode" "vector")]) 1425 1426(define_expand "movstricthi" 1427 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "")) 1428 (match_operand:HI 1 "general_operand" ""))] 1429 "! TARGET_PARTIAL_REG_STALL || optimize_size" 1430{ 1431 /* Don't generate memory->memory moves, go through a register */ 1432 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 1433 operands[1] = force_reg (HImode, operands[1]); 1434}) 1435 1436(define_insn "*movstricthi_1" 1437 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r")) 1438 (match_operand:HI 1 "general_operand" "rn,m"))] 1439 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 1440 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 1441 "mov{w}\t{%1, %0|%0, %1}" 1442 [(set_attr "type" "imov") 1443 (set_attr "mode" "HI")]) 1444 1445(define_insn "*movstricthi_xor" 1446 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r")) 1447 (match_operand:HI 1 "const0_operand" "i")) 1448 (clobber (reg:CC FLAGS_REG))] 1449 "reload_completed 1450 && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)" 1451 "xor{w}\t{%0, %0|%0, %0}" 1452 [(set_attr "type" "alu1") 1453 (set_attr "mode" "HI") 1454 (set_attr "length_immediate" "0")]) 1455 1456(define_expand "movqi" 1457 [(set (match_operand:QI 0 "nonimmediate_operand" "") 1458 (match_operand:QI 1 "general_operand" ""))] 1459 "" 1460 "ix86_expand_move (QImode, operands); DONE;") 1461 1462;; emit_push_insn when it calls move_by_pieces requires an insn to 1463;; "push a byte". But actually we use pushl, which has the effect 1464;; of rounding the amount pushed up to a word. 1465 1466(define_insn "*pushqi2" 1467 [(set (match_operand:QI 0 "push_operand" "=X") 1468 (match_operand:QI 1 "nonmemory_no_elim_operand" "rn"))] 1469 "!TARGET_64BIT" 1470 "push{l}\t%k1" 1471 [(set_attr "type" "push") 1472 (set_attr "mode" "SI")]) 1473 1474;; For 64BIT abi we always round up to 8 bytes. 1475(define_insn "*pushqi2_rex64" 1476 [(set (match_operand:QI 0 "push_operand" "=X") 1477 (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))] 1478 "TARGET_64BIT" 1479 "push{q}\t%q1" 1480 [(set_attr "type" "push") 1481 (set_attr "mode" "DI")]) 1482 1483;; Situation is quite tricky about when to choose full sized (SImode) move 1484;; over QImode moves. For Q_REG -> Q_REG move we use full size only for 1485;; partial register dependency machines (such as AMD Athlon), where QImode 1486;; moves issue extra dependency and for partial register stalls machines 1487;; that don't use QImode patterns (and QImode move cause stall on the next 1488;; instruction). 1489;; 1490;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial 1491;; register stall machines with, where we use QImode instructions, since 1492;; partial register stall can be caused there. Then we use movzx. 1493(define_insn "*movqi_1" 1494 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m") 1495 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,qm,qn"))] 1496 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM" 1497{ 1498 switch (get_attr_type (insn)) 1499 { 1500 case TYPE_IMOVX: 1501 gcc_assert (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM); 1502 return "movz{bl|x}\t{%1, %k0|%k0, %1}"; 1503 default: 1504 if (get_attr_mode (insn) == MODE_SI) 1505 return "mov{l}\t{%k1, %k0|%k0, %k1}"; 1506 else 1507 return "mov{b}\t{%1, %0|%0, %1}"; 1508 } 1509} 1510 [(set (attr "type") 1511 (cond [(and (eq_attr "alternative" "5") 1512 (not (match_operand:QI 1 "aligned_operand" ""))) 1513 (const_string "imovx") 1514 (ne (symbol_ref "optimize_size") (const_int 0)) 1515 (const_string "imov") 1516 (and (eq_attr "alternative" "3") 1517 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL") 1518 (const_int 0)) 1519 (eq (symbol_ref "TARGET_QIMODE_MATH") 1520 (const_int 0)))) 1521 (const_string "imov") 1522 (eq_attr "alternative" "3,5") 1523 (const_string "imovx") 1524 (and (ne (symbol_ref "TARGET_MOVX") 1525 (const_int 0)) 1526 (eq_attr "alternative" "2")) 1527 (const_string "imovx") 1528 ] 1529 (const_string "imov"))) 1530 (set (attr "mode") 1531 (cond [(eq_attr "alternative" "3,4,5") 1532 (const_string "SI") 1533 (eq_attr "alternative" "6") 1534 (const_string "QI") 1535 (eq_attr "type" "imovx") 1536 (const_string "SI") 1537 (and (eq_attr "type" "imov") 1538 (and (eq_attr "alternative" "0,1") 1539 (and (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY") 1540 (const_int 0)) 1541 (and (eq (symbol_ref "optimize_size") 1542 (const_int 0)) 1543 (eq (symbol_ref "TARGET_PARTIAL_REG_STALL") 1544 (const_int 0)))))) 1545 (const_string "SI") 1546 ;; Avoid partial register stalls when not using QImode arithmetic 1547 (and (eq_attr "type" "imov") 1548 (and (eq_attr "alternative" "0,1") 1549 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL") 1550 (const_int 0)) 1551 (eq (symbol_ref "TARGET_QIMODE_MATH") 1552 (const_int 0))))) 1553 (const_string "SI") 1554 ] 1555 (const_string "QI")))]) 1556 1557(define_expand "reload_outqi" 1558 [(parallel [(match_operand:QI 0 "" "=m") 1559 (match_operand:QI 1 "register_operand" "r") 1560 (match_operand:QI 2 "register_operand" "=&q")])] 1561 "" 1562{ 1563 rtx op0, op1, op2; 1564 op0 = operands[0]; op1 = operands[1]; op2 = operands[2]; 1565 1566 gcc_assert (!reg_overlap_mentioned_p (op2, op0)); 1567 if (! q_regs_operand (op1, QImode)) 1568 { 1569 emit_insn (gen_movqi (op2, op1)); 1570 op1 = op2; 1571 } 1572 emit_insn (gen_movqi (op0, op1)); 1573 DONE; 1574}) 1575 1576(define_insn "*swapqi_1" 1577 [(set (match_operand:QI 0 "register_operand" "+r") 1578 (match_operand:QI 1 "register_operand" "+r")) 1579 (set (match_dup 1) 1580 (match_dup 0))] 1581 "!TARGET_PARTIAL_REG_STALL || optimize_size" 1582 "xchg{l}\t%k1, %k0" 1583 [(set_attr "type" "imov") 1584 (set_attr "mode" "SI") 1585 (set_attr "pent_pair" "np") 1586 (set_attr "athlon_decode" "vector") 1587 (set_attr "amdfam10_decode" "vector")]) 1588 1589;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10 1590(define_insn "*swapqi_2" 1591 [(set (match_operand:QI 0 "register_operand" "+q") 1592 (match_operand:QI 1 "register_operand" "+q")) 1593 (set (match_dup 1) 1594 (match_dup 0))] 1595 "TARGET_PARTIAL_REG_STALL" 1596 "xchg{b}\t%1, %0" 1597 [(set_attr "type" "imov") 1598 (set_attr "mode" "QI") 1599 (set_attr "pent_pair" "np") 1600 (set_attr "athlon_decode" "vector")]) 1601 1602(define_expand "movstrictqi" 1603 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "")) 1604 (match_operand:QI 1 "general_operand" ""))] 1605 "! TARGET_PARTIAL_REG_STALL || optimize_size" 1606{ 1607 /* Don't generate memory->memory moves, go through a register. */ 1608 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 1609 operands[1] = force_reg (QImode, operands[1]); 1610}) 1611 1612(define_insn "*movstrictqi_1" 1613 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q")) 1614 (match_operand:QI 1 "general_operand" "*qn,m"))] 1615 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 1616 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 1617 "mov{b}\t{%1, %0|%0, %1}" 1618 [(set_attr "type" "imov") 1619 (set_attr "mode" "QI")]) 1620 1621(define_insn "*movstrictqi_xor" 1622 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q")) 1623 (match_operand:QI 1 "const0_operand" "i")) 1624 (clobber (reg:CC FLAGS_REG))] 1625 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)" 1626 "xor{b}\t{%0, %0|%0, %0}" 1627 [(set_attr "type" "alu1") 1628 (set_attr "mode" "QI") 1629 (set_attr "length_immediate" "0")]) 1630 1631(define_insn "*movsi_extv_1" 1632 [(set (match_operand:SI 0 "register_operand" "=R") 1633 (sign_extract:SI (match_operand 1 "ext_register_operand" "Q") 1634 (const_int 8) 1635 (const_int 8)))] 1636 "" 1637 "movs{bl|x}\t{%h1, %0|%0, %h1}" 1638 [(set_attr "type" "imovx") 1639 (set_attr "mode" "SI")]) 1640 1641(define_insn "*movhi_extv_1" 1642 [(set (match_operand:HI 0 "register_operand" "=R") 1643 (sign_extract:HI (match_operand 1 "ext_register_operand" "Q") 1644 (const_int 8) 1645 (const_int 8)))] 1646 "" 1647 "movs{bl|x}\t{%h1, %k0|%k0, %h1}" 1648 [(set_attr "type" "imovx") 1649 (set_attr "mode" "SI")]) 1650 1651(define_insn "*movqi_extv_1" 1652 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r") 1653 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q") 1654 (const_int 8) 1655 (const_int 8)))] 1656 "!TARGET_64BIT" 1657{ 1658 switch (get_attr_type (insn)) 1659 { 1660 case TYPE_IMOVX: 1661 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}"; 1662 default: 1663 return "mov{b}\t{%h1, %0|%0, %h1}"; 1664 } 1665} 1666 [(set (attr "type") 1667 (if_then_else (and (match_operand:QI 0 "register_operand" "") 1668 (ior (not (match_operand:QI 0 "q_regs_operand" "")) 1669 (ne (symbol_ref "TARGET_MOVX") 1670 (const_int 0)))) 1671 (const_string "imovx") 1672 (const_string "imov"))) 1673 (set (attr "mode") 1674 (if_then_else (eq_attr "type" "imovx") 1675 (const_string "SI") 1676 (const_string "QI")))]) 1677 1678(define_insn "*movqi_extv_1_rex64" 1679 [(set (match_operand:QI 0 "register_operand" "=Q,?R") 1680 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q") 1681 (const_int 8) 1682 (const_int 8)))] 1683 "TARGET_64BIT" 1684{ 1685 switch (get_attr_type (insn)) 1686 { 1687 case TYPE_IMOVX: 1688 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}"; 1689 default: 1690 return "mov{b}\t{%h1, %0|%0, %h1}"; 1691 } 1692} 1693 [(set (attr "type") 1694 (if_then_else (and (match_operand:QI 0 "register_operand" "") 1695 (ior (not (match_operand:QI 0 "q_regs_operand" "")) 1696 (ne (symbol_ref "TARGET_MOVX") 1697 (const_int 0)))) 1698 (const_string "imovx") 1699 (const_string "imov"))) 1700 (set (attr "mode") 1701 (if_then_else (eq_attr "type" "imovx") 1702 (const_string "SI") 1703 (const_string "QI")))]) 1704 1705;; Stores and loads of ax to arbitrary constant address. 1706;; We fake an second form of instruction to force reload to load address 1707;; into register when rax is not available 1708(define_insn "*movabsqi_1_rex64" 1709 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r")) 1710 (match_operand:QI 1 "nonmemory_operand" "a,er"))] 1711 "TARGET_64BIT && ix86_check_movabs (insn, 0)" 1712 "@ 1713 movabs{b}\t{%1, %P0|%P0, %1} 1714 mov{b}\t{%1, %a0|%a0, %1}" 1715 [(set_attr "type" "imov") 1716 (set_attr "modrm" "0,*") 1717 (set_attr "length_address" "8,0") 1718 (set_attr "length_immediate" "0,*") 1719 (set_attr "memory" "store") 1720 (set_attr "mode" "QI")]) 1721 1722(define_insn "*movabsqi_2_rex64" 1723 [(set (match_operand:QI 0 "register_operand" "=a,r") 1724 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))] 1725 "TARGET_64BIT && ix86_check_movabs (insn, 1)" 1726 "@ 1727 movabs{b}\t{%P1, %0|%0, %P1} 1728 mov{b}\t{%a1, %0|%0, %a1}" 1729 [(set_attr "type" "imov") 1730 (set_attr "modrm" "0,*") 1731 (set_attr "length_address" "8,0") 1732 (set_attr "length_immediate" "0") 1733 (set_attr "memory" "load") 1734 (set_attr "mode" "QI")]) 1735 1736(define_insn "*movdi_extzv_1" 1737 [(set (match_operand:DI 0 "register_operand" "=R") 1738 (zero_extract:DI (match_operand 1 "ext_register_operand" "Q") 1739 (const_int 8) 1740 (const_int 8)))] 1741 "TARGET_64BIT" 1742 "movz{bl|x}\t{%h1, %k0|%k0, %h1}" 1743 [(set_attr "type" "imovx") 1744 (set_attr "mode" "DI")]) 1745 1746(define_insn "*movsi_extzv_1" 1747 [(set (match_operand:SI 0 "register_operand" "=R") 1748 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q") 1749 (const_int 8) 1750 (const_int 8)))] 1751 "" 1752 "movz{bl|x}\t{%h1, %0|%0, %h1}" 1753 [(set_attr "type" "imovx") 1754 (set_attr "mode" "SI")]) 1755 1756(define_insn "*movqi_extzv_2" 1757 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R") 1758 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q") 1759 (const_int 8) 1760 (const_int 8)) 0))] 1761 "!TARGET_64BIT" 1762{ 1763 switch (get_attr_type (insn)) 1764 { 1765 case TYPE_IMOVX: 1766 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}"; 1767 default: 1768 return "mov{b}\t{%h1, %0|%0, %h1}"; 1769 } 1770} 1771 [(set (attr "type") 1772 (if_then_else (and (match_operand:QI 0 "register_operand" "") 1773 (ior (not (match_operand:QI 0 "q_regs_operand" "")) 1774 (ne (symbol_ref "TARGET_MOVX") 1775 (const_int 0)))) 1776 (const_string "imovx") 1777 (const_string "imov"))) 1778 (set (attr "mode") 1779 (if_then_else (eq_attr "type" "imovx") 1780 (const_string "SI") 1781 (const_string "QI")))]) 1782 1783(define_insn "*movqi_extzv_2_rex64" 1784 [(set (match_operand:QI 0 "register_operand" "=Q,?R") 1785 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q") 1786 (const_int 8) 1787 (const_int 8)) 0))] 1788 "TARGET_64BIT" 1789{ 1790 switch (get_attr_type (insn)) 1791 { 1792 case TYPE_IMOVX: 1793 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}"; 1794 default: 1795 return "mov{b}\t{%h1, %0|%0, %h1}"; 1796 } 1797} 1798 [(set (attr "type") 1799 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" "")) 1800 (ne (symbol_ref "TARGET_MOVX") 1801 (const_int 0))) 1802 (const_string "imovx") 1803 (const_string "imov"))) 1804 (set (attr "mode") 1805 (if_then_else (eq_attr "type" "imovx") 1806 (const_string "SI") 1807 (const_string "QI")))]) 1808 1809(define_insn "movsi_insv_1" 1810 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") 1811 (const_int 8) 1812 (const_int 8)) 1813 (match_operand:SI 1 "general_operand" "Qmn"))] 1814 "!TARGET_64BIT" 1815 "mov{b}\t{%b1, %h0|%h0, %b1}" 1816 [(set_attr "type" "imov") 1817 (set_attr "mode" "QI")]) 1818 1819(define_insn "movdi_insv_1_rex64" 1820 [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q") 1821 (const_int 8) 1822 (const_int 8)) 1823 (match_operand:DI 1 "nonmemory_operand" "Qn"))] 1824 "TARGET_64BIT" 1825 "mov{b}\t{%b1, %h0|%h0, %b1}" 1826 [(set_attr "type" "imov") 1827 (set_attr "mode" "QI")]) 1828 1829(define_insn "*movqi_insv_2" 1830 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") 1831 (const_int 8) 1832 (const_int 8)) 1833 (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q") 1834 (const_int 8)))] 1835 "" 1836 "mov{b}\t{%h1, %h0|%h0, %h1}" 1837 [(set_attr "type" "imov") 1838 (set_attr "mode" "QI")]) 1839 1840(define_expand "movdi" 1841 [(set (match_operand:DI 0 "nonimmediate_operand" "") 1842 (match_operand:DI 1 "general_operand" ""))] 1843 "" 1844 "ix86_expand_move (DImode, operands); DONE;") 1845 1846(define_insn "*pushdi" 1847 [(set (match_operand:DI 0 "push_operand" "=<") 1848 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))] 1849 "!TARGET_64BIT" 1850 "#") 1851 1852(define_insn "*pushdi2_rex64" 1853 [(set (match_operand:DI 0 "push_operand" "=<,!<") 1854 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))] 1855 "TARGET_64BIT" 1856 "@ 1857 push{q}\t%1 1858 #" 1859 [(set_attr "type" "push,multi") 1860 (set_attr "mode" "DI")]) 1861 1862;; Convert impossible pushes of immediate to existing instructions. 1863;; First try to get scratch register and go through it. In case this 1864;; fails, push sign extended lower part first and then overwrite 1865;; upper part by 32bit move. 1866(define_peephole2 1867 [(match_scratch:DI 2 "r") 1868 (set (match_operand:DI 0 "push_operand" "") 1869 (match_operand:DI 1 "immediate_operand" ""))] 1870 "TARGET_64BIT && !symbolic_operand (operands[1], DImode) 1871 && !x86_64_immediate_operand (operands[1], DImode)" 1872 [(set (match_dup 2) (match_dup 1)) 1873 (set (match_dup 0) (match_dup 2))] 1874 "") 1875 1876;; We need to define this as both peepholer and splitter for case 1877;; peephole2 pass is not run. 1878;; "&& 1" is needed to keep it from matching the previous pattern. 1879(define_peephole2 1880 [(set (match_operand:DI 0 "push_operand" "") 1881 (match_operand:DI 1 "immediate_operand" ""))] 1882 "TARGET_64BIT && !symbolic_operand (operands[1], DImode) 1883 && !x86_64_immediate_operand (operands[1], DImode) && 1" 1884 [(set (match_dup 0) (match_dup 1)) 1885 (set (match_dup 2) (match_dup 3))] 1886 "split_di (operands + 1, 1, operands + 2, operands + 3); 1887 operands[1] = gen_lowpart (DImode, operands[2]); 1888 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx, 1889 GEN_INT (4))); 1890 ") 1891 1892(define_split 1893 [(set (match_operand:DI 0 "push_operand" "") 1894 (match_operand:DI 1 "immediate_operand" ""))] 1895 "TARGET_64BIT && ((optimize > 0 && flag_peephole2) 1896 ? flow2_completed : reload_completed) 1897 && !symbolic_operand (operands[1], DImode) 1898 && !x86_64_immediate_operand (operands[1], DImode)" 1899 [(set (match_dup 0) (match_dup 1)) 1900 (set (match_dup 2) (match_dup 3))] 1901 "split_di (operands + 1, 1, operands + 2, operands + 3); 1902 operands[1] = gen_lowpart (DImode, operands[2]); 1903 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx, 1904 GEN_INT (4))); 1905 ") 1906 1907(define_insn "*pushdi2_prologue_rex64" 1908 [(set (match_operand:DI 0 "push_operand" "=<") 1909 (match_operand:DI 1 "general_no_elim_operand" "re*m")) 1910 (clobber (mem:BLK (scratch)))] 1911 "TARGET_64BIT" 1912 "push{q}\t%1" 1913 [(set_attr "type" "push") 1914 (set_attr "mode" "DI")]) 1915 1916(define_insn "*popdi1_epilogue_rex64" 1917 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m") 1918 (mem:DI (reg:DI SP_REG))) 1919 (set (reg:DI SP_REG) 1920 (plus:DI (reg:DI SP_REG) (const_int 8))) 1921 (clobber (mem:BLK (scratch)))] 1922 "TARGET_64BIT" 1923 "pop{q}\t%0" 1924 [(set_attr "type" "pop") 1925 (set_attr "mode" "DI")]) 1926 1927(define_insn "popdi1" 1928 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m") 1929 (mem:DI (reg:DI SP_REG))) 1930 (set (reg:DI SP_REG) 1931 (plus:DI (reg:DI SP_REG) (const_int 8)))] 1932 "TARGET_64BIT" 1933 "pop{q}\t%0" 1934 [(set_attr "type" "pop") 1935 (set_attr "mode" "DI")]) 1936 1937(define_insn "*movdi_xor_rex64" 1938 [(set (match_operand:DI 0 "register_operand" "=r") 1939 (match_operand:DI 1 "const0_operand" "i")) 1940 (clobber (reg:CC FLAGS_REG))] 1941 "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size) 1942 && reload_completed" 1943 "xor{l}\t{%k0, %k0|%k0, %k0}" 1944 [(set_attr "type" "alu1") 1945 (set_attr "mode" "SI") 1946 (set_attr "length_immediate" "0")]) 1947 1948(define_insn "*movdi_or_rex64" 1949 [(set (match_operand:DI 0 "register_operand" "=r") 1950 (match_operand:DI 1 "const_int_operand" "i")) 1951 (clobber (reg:CC FLAGS_REG))] 1952 "TARGET_64BIT && (TARGET_PENTIUM || optimize_size) 1953 && reload_completed 1954 && operands[1] == constm1_rtx" 1955{ 1956 operands[1] = constm1_rtx; 1957 return "or{q}\t{%1, %0|%0, %1}"; 1958} 1959 [(set_attr "type" "alu1") 1960 (set_attr "mode" "DI") 1961 (set_attr "length_immediate" "1")]) 1962 1963(define_insn "*movdi_2" 1964 [(set (match_operand:DI 0 "nonimmediate_operand" 1965 "=r ,o ,*y,m*y,*y,*Y,m ,*Y,*Y,*x,m ,*x,*x") 1966 (match_operand:DI 1 "general_operand" 1967 "riFo,riF,C ,*y ,m ,C ,*Y,*Y,m ,C ,*x,*x,m "))] 1968 "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))" 1969 "@ 1970 # 1971 # 1972 pxor\t%0, %0 1973 movq\t{%1, %0|%0, %1} 1974 movq\t{%1, %0|%0, %1} 1975 pxor\t%0, %0 1976 movq\t{%1, %0|%0, %1} 1977 movdqa\t{%1, %0|%0, %1} 1978 movq\t{%1, %0|%0, %1} 1979 xorps\t%0, %0 1980 movlps\t{%1, %0|%0, %1} 1981 movaps\t{%1, %0|%0, %1} 1982 movlps\t{%1, %0|%0, %1}" 1983 [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov") 1984 (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")]) 1985 1986(define_split 1987 [(set (match_operand:DI 0 "push_operand" "") 1988 (match_operand:DI 1 "general_operand" ""))] 1989 "!TARGET_64BIT && reload_completed 1990 && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))" 1991 [(const_int 0)] 1992 "ix86_split_long_move (operands); DONE;") 1993 1994;; %%% This multiword shite has got to go. 1995(define_split 1996 [(set (match_operand:DI 0 "nonimmediate_operand" "") 1997 (match_operand:DI 1 "general_operand" ""))] 1998 "!TARGET_64BIT && reload_completed 1999 && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0])) 2000 && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))" 2001 [(const_int 0)] 2002 "ix86_split_long_move (operands); DONE;") 2003 2004(define_insn "*movdi_1_rex64" 2005 [(set (match_operand:DI 0 "nonimmediate_operand" 2006 "=r,r ,r,m ,!m,*y,*y,?rm,?*y,*x,*x,?rm,?*x,?*x,?*y") 2007 (match_operand:DI 1 "general_operand" 2008 "Z ,rem,i,re,n ,C ,*y,*y ,rm ,C ,*x,*x ,rm ,*y ,*x"))] 2009 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))" 2010{ 2011 switch (get_attr_type (insn)) 2012 { 2013 case TYPE_SSECVT: 2014 if (which_alternative == 13) 2015 return "movq2dq\t{%1, %0|%0, %1}"; 2016 else 2017 return "movdq2q\t{%1, %0|%0, %1}"; 2018 case TYPE_SSEMOV: 2019 if (get_attr_mode (insn) == MODE_TI) 2020 return "movdqa\t{%1, %0|%0, %1}"; 2021 /* FALLTHRU */ 2022 case TYPE_MMXMOV: 2023 /* Moves from and into integer register is done using movd opcode with 2024 REX prefix. */ 2025 if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1])) 2026 return "movd\t{%1, %0|%0, %1}"; 2027 return "movq\t{%1, %0|%0, %1}"; 2028 case TYPE_SSELOG1: 2029 case TYPE_MMXADD: 2030 return "pxor\t%0, %0"; 2031 case TYPE_MULTI: 2032 return "#"; 2033 case TYPE_LEA: 2034 return "lea{q}\t{%a1, %0|%0, %a1}"; 2035 default: 2036 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1])); 2037 if (get_attr_mode (insn) == MODE_SI) 2038 return "mov{l}\t{%k1, %k0|%k0, %k1}"; 2039 else if (which_alternative == 2) 2040 return "movabs{q}\t{%1, %0|%0, %1}"; 2041 else 2042 return "mov{q}\t{%1, %0|%0, %1}"; 2043 } 2044} 2045 [(set (attr "type") 2046 (cond [(eq_attr "alternative" "5") 2047 (const_string "mmxadd") 2048 (eq_attr "alternative" "6,7,8") 2049 (const_string "mmxmov") 2050 (eq_attr "alternative" "9") 2051 (const_string "sselog1") 2052 (eq_attr "alternative" "10,11,12") 2053 (const_string "ssemov") 2054 (eq_attr "alternative" "13,14") 2055 (const_string "ssecvt") 2056 (eq_attr "alternative" "4") 2057 (const_string "multi") 2058 (match_operand:DI 1 "pic_32bit_operand" "") 2059 (const_string "lea") 2060 ] 2061 (const_string "imov"))) 2062 (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*") 2063 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*") 2064 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI")]) 2065 2066;; Stores and loads of ax to arbitrary constant address. 2067;; We fake an second form of instruction to force reload to load address 2068;; into register when rax is not available 2069(define_insn "*movabsdi_1_rex64" 2070 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r")) 2071 (match_operand:DI 1 "nonmemory_operand" "a,er"))] 2072 "TARGET_64BIT && ix86_check_movabs (insn, 0)" 2073 "@ 2074 movabs{q}\t{%1, %P0|%P0, %1} 2075 mov{q}\t{%1, %a0|%a0, %1}" 2076 [(set_attr "type" "imov") 2077 (set_attr "modrm" "0,*") 2078 (set_attr "length_address" "8,0") 2079 (set_attr "length_immediate" "0,*") 2080 (set_attr "memory" "store") 2081 (set_attr "mode" "DI")]) 2082 2083(define_insn "*movabsdi_2_rex64" 2084 [(set (match_operand:DI 0 "register_operand" "=a,r") 2085 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))] 2086 "TARGET_64BIT && ix86_check_movabs (insn, 1)" 2087 "@ 2088 movabs{q}\t{%P1, %0|%0, %P1} 2089 mov{q}\t{%a1, %0|%0, %a1}" 2090 [(set_attr "type" "imov") 2091 (set_attr "modrm" "0,*") 2092 (set_attr "length_address" "8,0") 2093 (set_attr "length_immediate" "0") 2094 (set_attr "memory" "load") 2095 (set_attr "mode" "DI")]) 2096 2097;; Convert impossible stores of immediate to existing instructions. 2098;; First try to get scratch register and go through it. In case this 2099;; fails, move by 32bit parts. 2100(define_peephole2 2101 [(match_scratch:DI 2 "r") 2102 (set (match_operand:DI 0 "memory_operand" "") 2103 (match_operand:DI 1 "immediate_operand" ""))] 2104 "TARGET_64BIT && !symbolic_operand (operands[1], DImode) 2105 && !x86_64_immediate_operand (operands[1], DImode)" 2106 [(set (match_dup 2) (match_dup 1)) 2107 (set (match_dup 0) (match_dup 2))] 2108 "") 2109 2110;; We need to define this as both peepholer and splitter for case 2111;; peephole2 pass is not run. 2112;; "&& 1" is needed to keep it from matching the previous pattern. 2113(define_peephole2 2114 [(set (match_operand:DI 0 "memory_operand" "") 2115 (match_operand:DI 1 "immediate_operand" ""))] 2116 "TARGET_64BIT && !symbolic_operand (operands[1], DImode) 2117 && !x86_64_immediate_operand (operands[1], DImode) && 1" 2118 [(set (match_dup 2) (match_dup 3)) 2119 (set (match_dup 4) (match_dup 5))] 2120 "split_di (operands, 2, operands + 2, operands + 4);") 2121 2122(define_split 2123 [(set (match_operand:DI 0 "memory_operand" "") 2124 (match_operand:DI 1 "immediate_operand" ""))] 2125 "TARGET_64BIT && ((optimize > 0 && flag_peephole2) 2126 ? flow2_completed : reload_completed) 2127 && !symbolic_operand (operands[1], DImode) 2128 && !x86_64_immediate_operand (operands[1], DImode)" 2129 [(set (match_dup 2) (match_dup 3)) 2130 (set (match_dup 4) (match_dup 5))] 2131 "split_di (operands, 2, operands + 2, operands + 4);") 2132 2133(define_insn "*swapdi_rex64" 2134 [(set (match_operand:DI 0 "register_operand" "+r") 2135 (match_operand:DI 1 "register_operand" "+r")) 2136 (set (match_dup 1) 2137 (match_dup 0))] 2138 "TARGET_64BIT" 2139 "xchg{q}\t%1, %0" 2140 [(set_attr "type" "imov") 2141 (set_attr "mode" "DI") 2142 (set_attr "pent_pair" "np") 2143 (set_attr "athlon_decode" "vector") 2144 (set_attr "amdfam10_decode" "double")]) 2145 2146(define_expand "movti" 2147 [(set (match_operand:TI 0 "nonimmediate_operand" "") 2148 (match_operand:TI 1 "nonimmediate_operand" ""))] 2149 "TARGET_SSE || TARGET_64BIT" 2150{ 2151 if (TARGET_64BIT) 2152 ix86_expand_move (TImode, operands); 2153 else 2154 ix86_expand_vector_move (TImode, operands); 2155 DONE; 2156}) 2157 2158(define_insn "*movti_internal" 2159 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m") 2160 (match_operand:TI 1 "vector_move_operand" "C,xm,x"))] 2161 "TARGET_SSE && !TARGET_64BIT 2162 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 2163{ 2164 switch (which_alternative) 2165 { 2166 case 0: 2167 if (get_attr_mode (insn) == MODE_V4SF) 2168 return "xorps\t%0, %0"; 2169 else 2170 return "pxor\t%0, %0"; 2171 case 1: 2172 case 2: 2173 if (get_attr_mode (insn) == MODE_V4SF) 2174 return "movaps\t{%1, %0|%0, %1}"; 2175 else 2176 return "movdqa\t{%1, %0|%0, %1}"; 2177 default: 2178 gcc_unreachable (); 2179 } 2180} 2181 [(set_attr "type" "sselog1,ssemov,ssemov") 2182 (set (attr "mode") 2183 (cond [(ior (eq (symbol_ref "TARGET_SSE2") (const_int 0)) 2184 (ne (symbol_ref "optimize_size") (const_int 0))) 2185 (const_string "V4SF") 2186 (and (eq_attr "alternative" "2") 2187 (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES") 2188 (const_int 0))) 2189 (const_string "V4SF")] 2190 (const_string "TI")))]) 2191 2192(define_insn "*movti_rex64" 2193 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm") 2194 (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))] 2195 "TARGET_64BIT 2196 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 2197{ 2198 switch (which_alternative) 2199 { 2200 case 0: 2201 case 1: 2202 return "#"; 2203 case 2: 2204 if (get_attr_mode (insn) == MODE_V4SF) 2205 return "xorps\t%0, %0"; 2206 else 2207 return "pxor\t%0, %0"; 2208 case 3: 2209 case 4: 2210 if (get_attr_mode (insn) == MODE_V4SF) 2211 return "movaps\t{%1, %0|%0, %1}"; 2212 else 2213 return "movdqa\t{%1, %0|%0, %1}"; 2214 default: 2215 gcc_unreachable (); 2216 } 2217} 2218 [(set_attr "type" "*,*,sselog1,ssemov,ssemov") 2219 (set (attr "mode") 2220 (cond [(eq_attr "alternative" "2,3") 2221 (if_then_else 2222 (ne (symbol_ref "optimize_size") 2223 (const_int 0)) 2224 (const_string "V4SF") 2225 (const_string "TI")) 2226 (eq_attr "alternative" "4") 2227 (if_then_else 2228 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES") 2229 (const_int 0)) 2230 (ne (symbol_ref "optimize_size") 2231 (const_int 0))) 2232 (const_string "V4SF") 2233 (const_string "TI"))] 2234 (const_string "DI")))]) 2235 2236(define_split 2237 [(set (match_operand:TI 0 "nonimmediate_operand" "") 2238 (match_operand:TI 1 "general_operand" ""))] 2239 "reload_completed && !SSE_REG_P (operands[0]) 2240 && !SSE_REG_P (operands[1])" 2241 [(const_int 0)] 2242 "ix86_split_long_move (operands); DONE;") 2243 2244(define_expand "movsf" 2245 [(set (match_operand:SF 0 "nonimmediate_operand" "") 2246 (match_operand:SF 1 "general_operand" ""))] 2247 "" 2248 "ix86_expand_move (SFmode, operands); DONE;") 2249 2250(define_insn "*pushsf" 2251 [(set (match_operand:SF 0 "push_operand" "=<,<,<") 2252 (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))] 2253 "!TARGET_64BIT" 2254{ 2255 /* Anything else should be already split before reg-stack. */ 2256 gcc_assert (which_alternative == 1); 2257 return "push{l}\t%1"; 2258} 2259 [(set_attr "type" "multi,push,multi") 2260 (set_attr "unit" "i387,*,*") 2261 (set_attr "mode" "SF,SI,SF")]) 2262 2263(define_insn "*pushsf_rex64" 2264 [(set (match_operand:SF 0 "push_operand" "=X,X,X") 2265 (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))] 2266 "TARGET_64BIT" 2267{ 2268 /* Anything else should be already split before reg-stack. */ 2269 gcc_assert (which_alternative == 1); 2270 return "push{q}\t%q1"; 2271} 2272 [(set_attr "type" "multi,push,multi") 2273 (set_attr "unit" "i387,*,*") 2274 (set_attr "mode" "SF,DI,SF")]) 2275 2276(define_split 2277 [(set (match_operand:SF 0 "push_operand" "") 2278 (match_operand:SF 1 "memory_operand" ""))] 2279 "reload_completed 2280 && GET_CODE (operands[1]) == MEM 2281 && constant_pool_reference_p (operands[1])" 2282 [(set (match_dup 0) 2283 (match_dup 1))] 2284 "operands[1] = avoid_constant_pool_reference (operands[1]);") 2285 2286 2287;; %%% Kill this when call knows how to work this out. 2288(define_split 2289 [(set (match_operand:SF 0 "push_operand" "") 2290 (match_operand:SF 1 "any_fp_register_operand" ""))] 2291 "!TARGET_64BIT" 2292 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4))) 2293 (set (mem:SF (reg:SI SP_REG)) (match_dup 1))]) 2294 2295(define_split 2296 [(set (match_operand:SF 0 "push_operand" "") 2297 (match_operand:SF 1 "any_fp_register_operand" ""))] 2298 "TARGET_64BIT" 2299 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8))) 2300 (set (mem:SF (reg:DI SP_REG)) (match_dup 1))]) 2301 2302(define_insn "*movsf_1" 2303 [(set (match_operand:SF 0 "nonimmediate_operand" 2304 "=f,m ,f,r ,m ,x,x,x ,m ,!*y,!rm,!*y") 2305 (match_operand:SF 1 "general_operand" 2306 "fm,f,G ,rmF,Fr,C ,x ,xm,x,rm ,*y ,*y"))] 2307 "!(MEM_P (operands[0]) && MEM_P (operands[1])) 2308 && (reload_in_progress || reload_completed 2309 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE) 2310 || GET_CODE (operands[1]) != CONST_DOUBLE 2311 || memory_operand (operands[0], SFmode))" 2312{ 2313 switch (which_alternative) 2314 { 2315 case 0: 2316 return output_387_reg_move (insn, operands); 2317 2318 case 1: 2319 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 2320 return "fstp%z0\t%y0"; 2321 else 2322 return "fst%z0\t%y0"; 2323 2324 case 2: 2325 return standard_80387_constant_opcode (operands[1]); 2326 2327 case 3: 2328 case 4: 2329 return "mov{l}\t{%1, %0|%0, %1}"; 2330 case 5: 2331 if (get_attr_mode (insn) == MODE_TI) 2332 return "pxor\t%0, %0"; 2333 else 2334 return "xorps\t%0, %0"; 2335 case 6: 2336 if (get_attr_mode (insn) == MODE_V4SF) 2337 return "movaps\t{%1, %0|%0, %1}"; 2338 else 2339 return "movss\t{%1, %0|%0, %1}"; 2340 case 7: 2341 case 8: 2342 return "movss\t{%1, %0|%0, %1}"; 2343 2344 case 9: 2345 case 10: 2346 return "movd\t{%1, %0|%0, %1}"; 2347 2348 case 11: 2349 return "movq\t{%1, %0|%0, %1}"; 2350 2351 default: 2352 gcc_unreachable (); 2353 } 2354} 2355 [(set_attr "type" "fmov,fmov,fmov,imov,imov,sselog1,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov") 2356 (set (attr "mode") 2357 (cond [(eq_attr "alternative" "3,4,9,10") 2358 (const_string "SI") 2359 (eq_attr "alternative" "5") 2360 (if_then_else 2361 (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR") 2362 (const_int 0)) 2363 (ne (symbol_ref "TARGET_SSE2") 2364 (const_int 0))) 2365 (eq (symbol_ref "optimize_size") 2366 (const_int 0))) 2367 (const_string "TI") 2368 (const_string "V4SF")) 2369 /* For architectures resolving dependencies on 2370 whole SSE registers use APS move to break dependency 2371 chains, otherwise use short move to avoid extra work. 2372 2373 Do the same for architectures resolving dependencies on 2374 the parts. While in DF mode it is better to always handle 2375 just register parts, the SF mode is different due to lack 2376 of instructions to load just part of the register. It is 2377 better to maintain the whole registers in single format 2378 to avoid problems on using packed logical operations. */ 2379 (eq_attr "alternative" "6") 2380 (if_then_else 2381 (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY") 2382 (const_int 0)) 2383 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS") 2384 (const_int 0))) 2385 (const_string "V4SF") 2386 (const_string "SF")) 2387 (eq_attr "alternative" "11") 2388 (const_string "DI")] 2389 (const_string "SF")))]) 2390 2391(define_insn "*swapsf" 2392 [(set (match_operand:SF 0 "fp_register_operand" "+f") 2393 (match_operand:SF 1 "fp_register_operand" "+f")) 2394 (set (match_dup 1) 2395 (match_dup 0))] 2396 "reload_completed || TARGET_80387" 2397{ 2398 if (STACK_TOP_P (operands[0])) 2399 return "fxch\t%1"; 2400 else 2401 return "fxch\t%0"; 2402} 2403 [(set_attr "type" "fxch") 2404 (set_attr "mode" "SF")]) 2405 2406(define_expand "movdf" 2407 [(set (match_operand:DF 0 "nonimmediate_operand" "") 2408 (match_operand:DF 1 "general_operand" ""))] 2409 "" 2410 "ix86_expand_move (DFmode, operands); DONE;") 2411 2412;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size. 2413;; Size of pushdf using integer instructions is 2+2*memory operand size 2414;; On the average, pushdf using integers can be still shorter. Allow this 2415;; pattern for optimize_size too. 2416 2417(define_insn "*pushdf_nointeger" 2418 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<") 2419 (match_operand:DF 1 "general_no_elim_operand" "f,Fo,*r,Y"))] 2420 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES" 2421{ 2422 /* This insn should be already split before reg-stack. */ 2423 gcc_unreachable (); 2424} 2425 [(set_attr "type" "multi") 2426 (set_attr "unit" "i387,*,*,*") 2427 (set_attr "mode" "DF,SI,SI,DF")]) 2428 2429(define_insn "*pushdf_integer" 2430 [(set (match_operand:DF 0 "push_operand" "=<,<,<") 2431 (match_operand:DF 1 "general_no_elim_operand" "f,rFo,Y"))] 2432 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES" 2433{ 2434 /* This insn should be already split before reg-stack. */ 2435 gcc_unreachable (); 2436} 2437 [(set_attr "type" "multi") 2438 (set_attr "unit" "i387,*,*") 2439 (set_attr "mode" "DF,SI,DF")]) 2440 2441;; %%% Kill this when call knows how to work this out. 2442(define_split 2443 [(set (match_operand:DF 0 "push_operand" "") 2444 (match_operand:DF 1 "any_fp_register_operand" ""))] 2445 "!TARGET_64BIT && reload_completed" 2446 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8))) 2447 (set (mem:DF (reg:SI SP_REG)) (match_dup 1))] 2448 "") 2449 2450(define_split 2451 [(set (match_operand:DF 0 "push_operand" "") 2452 (match_operand:DF 1 "any_fp_register_operand" ""))] 2453 "TARGET_64BIT && reload_completed" 2454 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8))) 2455 (set (mem:DF (reg:DI SP_REG)) (match_dup 1))] 2456 "") 2457 2458(define_split 2459 [(set (match_operand:DF 0 "push_operand" "") 2460 (match_operand:DF 1 "general_operand" ""))] 2461 "reload_completed" 2462 [(const_int 0)] 2463 "ix86_split_long_move (operands); DONE;") 2464 2465;; Moving is usually shorter when only FP registers are used. This separate 2466;; movdf pattern avoids the use of integer registers for FP operations 2467;; when optimizing for size. 2468 2469(define_insn "*movdf_nointeger" 2470 [(set (match_operand:DF 0 "nonimmediate_operand" 2471 "=f,m,f,*r ,o ,Y*x,Y*x,Y*x ,m ") 2472 (match_operand:DF 1 "general_operand" 2473 "fm,f,G,*roF,F*r,C ,Y*x,mY*x,Y*x"))] 2474 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2475 && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT) 2476 && (reload_in_progress || reload_completed 2477 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE) 2478 || GET_CODE (operands[1]) != CONST_DOUBLE 2479 || memory_operand (operands[0], DFmode))" 2480{ 2481 switch (which_alternative) 2482 { 2483 case 0: 2484 return output_387_reg_move (insn, operands); 2485 2486 case 1: 2487 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 2488 return "fstp%z0\t%y0"; 2489 else 2490 return "fst%z0\t%y0"; 2491 2492 case 2: 2493 return standard_80387_constant_opcode (operands[1]); 2494 2495 case 3: 2496 case 4: 2497 return "#"; 2498 case 5: 2499 switch (get_attr_mode (insn)) 2500 { 2501 case MODE_V4SF: 2502 return "xorps\t%0, %0"; 2503 case MODE_V2DF: 2504 return "xorpd\t%0, %0"; 2505 case MODE_TI: 2506 return "pxor\t%0, %0"; 2507 default: 2508 gcc_unreachable (); 2509 } 2510 case 6: 2511 case 7: 2512 case 8: 2513 switch (get_attr_mode (insn)) 2514 { 2515 case MODE_V4SF: 2516 return "movaps\t{%1, %0|%0, %1}"; 2517 case MODE_V2DF: 2518 return "movapd\t{%1, %0|%0, %1}"; 2519 case MODE_TI: 2520 return "movdqa\t{%1, %0|%0, %1}"; 2521 case MODE_DI: 2522 return "movq\t{%1, %0|%0, %1}"; 2523 case MODE_DF: 2524 return "movsd\t{%1, %0|%0, %1}"; 2525 case MODE_V1DF: 2526 return "movlpd\t{%1, %0|%0, %1}"; 2527 case MODE_V2SF: 2528 return "movlps\t{%1, %0|%0, %1}"; 2529 default: 2530 gcc_unreachable (); 2531 } 2532 2533 default: 2534 gcc_unreachable (); 2535 } 2536} 2537 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov") 2538 (set (attr "mode") 2539 (cond [(eq_attr "alternative" "0,1,2") 2540 (const_string "DF") 2541 (eq_attr "alternative" "3,4") 2542 (const_string "SI") 2543 2544 /* For SSE1, we have many fewer alternatives. */ 2545 (eq (symbol_ref "TARGET_SSE2") (const_int 0)) 2546 (cond [(eq_attr "alternative" "5,6") 2547 (const_string "V4SF") 2548 ] 2549 (const_string "V2SF")) 2550 2551 /* xorps is one byte shorter. */ 2552 (eq_attr "alternative" "5") 2553 (cond [(ne (symbol_ref "optimize_size") 2554 (const_int 0)) 2555 (const_string "V4SF") 2556 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR") 2557 (const_int 0)) 2558 (const_string "TI") 2559 ] 2560 (const_string "V2DF")) 2561 2562 /* For architectures resolving dependencies on 2563 whole SSE registers use APD move to break dependency 2564 chains, otherwise use short move to avoid extra work. 2565 2566 movaps encodes one byte shorter. */ 2567 (eq_attr "alternative" "6") 2568 (cond 2569 [(ne (symbol_ref "optimize_size") 2570 (const_int 0)) 2571 (const_string "V4SF") 2572 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY") 2573 (const_int 0)) 2574 (const_string "V2DF") 2575 ] 2576 (const_string "DF")) 2577 /* For architectures resolving dependencies on register 2578 parts we may avoid extra work to zero out upper part 2579 of register. */ 2580 (eq_attr "alternative" "7") 2581 (if_then_else 2582 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS") 2583 (const_int 0)) 2584 (const_string "V1DF") 2585 (const_string "DF")) 2586 ] 2587 (const_string "DF")))]) 2588 2589(define_insn "*movdf_integer" 2590 [(set (match_operand:DF 0 "nonimmediate_operand" 2591 "=f,m,f,r ,o ,Y*x,Y*x,Y*x,m ") 2592 (match_operand:DF 1 "general_operand" 2593 "fm,f,G,roF,Fr,C ,Y*x,m ,Y*x"))] 2594 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2595 && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT) 2596 && (reload_in_progress || reload_completed 2597 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE) 2598 || GET_CODE (operands[1]) != CONST_DOUBLE 2599 || memory_operand (operands[0], DFmode))" 2600{ 2601 switch (which_alternative) 2602 { 2603 case 0: 2604 return output_387_reg_move (insn, operands); 2605 2606 case 1: 2607 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 2608 return "fstp%z0\t%y0"; 2609 else 2610 return "fst%z0\t%y0"; 2611 2612 case 2: 2613 return standard_80387_constant_opcode (operands[1]); 2614 2615 case 3: 2616 case 4: 2617 return "#"; 2618 2619 case 5: 2620 switch (get_attr_mode (insn)) 2621 { 2622 case MODE_V4SF: 2623 return "xorps\t%0, %0"; 2624 case MODE_V2DF: 2625 return "xorpd\t%0, %0"; 2626 case MODE_TI: 2627 return "pxor\t%0, %0"; 2628 default: 2629 gcc_unreachable (); 2630 } 2631 case 6: 2632 case 7: 2633 case 8: 2634 switch (get_attr_mode (insn)) 2635 { 2636 case MODE_V4SF: 2637 return "movaps\t{%1, %0|%0, %1}"; 2638 case MODE_V2DF: 2639 return "movapd\t{%1, %0|%0, %1}"; 2640 case MODE_TI: 2641 return "movdqa\t{%1, %0|%0, %1}"; 2642 case MODE_DI: 2643 return "movq\t{%1, %0|%0, %1}"; 2644 case MODE_DF: 2645 return "movsd\t{%1, %0|%0, %1}"; 2646 case MODE_V1DF: 2647 return "movlpd\t{%1, %0|%0, %1}"; 2648 case MODE_V2SF: 2649 return "movlps\t{%1, %0|%0, %1}"; 2650 default: 2651 gcc_unreachable (); 2652 } 2653 2654 default: 2655 gcc_unreachable(); 2656 } 2657} 2658 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov") 2659 (set (attr "mode") 2660 (cond [(eq_attr "alternative" "0,1,2") 2661 (const_string "DF") 2662 (eq_attr "alternative" "3,4") 2663 (const_string "SI") 2664 2665 /* For SSE1, we have many fewer alternatives. */ 2666 (eq (symbol_ref "TARGET_SSE2") (const_int 0)) 2667 (cond [(eq_attr "alternative" "5,6") 2668 (const_string "V4SF") 2669 ] 2670 (const_string "V2SF")) 2671 2672 /* xorps is one byte shorter. */ 2673 (eq_attr "alternative" "5") 2674 (cond [(ne (symbol_ref "optimize_size") 2675 (const_int 0)) 2676 (const_string "V4SF") 2677 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR") 2678 (const_int 0)) 2679 (const_string "TI") 2680 ] 2681 (const_string "V2DF")) 2682 2683 /* For architectures resolving dependencies on 2684 whole SSE registers use APD move to break dependency 2685 chains, otherwise use short move to avoid extra work. 2686 2687 movaps encodes one byte shorter. */ 2688 (eq_attr "alternative" "6") 2689 (cond 2690 [(ne (symbol_ref "optimize_size") 2691 (const_int 0)) 2692 (const_string "V4SF") 2693 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY") 2694 (const_int 0)) 2695 (const_string "V2DF") 2696 ] 2697 (const_string "DF")) 2698 /* For architectures resolving dependencies on register 2699 parts we may avoid extra work to zero out upper part 2700 of register. */ 2701 (eq_attr "alternative" "7") 2702 (if_then_else 2703 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS") 2704 (const_int 0)) 2705 (const_string "V1DF") 2706 (const_string "DF")) 2707 ] 2708 (const_string "DF")))]) 2709 2710(define_split 2711 [(set (match_operand:DF 0 "nonimmediate_operand" "") 2712 (match_operand:DF 1 "general_operand" ""))] 2713 "reload_completed 2714 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2715 && ! (ANY_FP_REG_P (operands[0]) || 2716 (GET_CODE (operands[0]) == SUBREG 2717 && ANY_FP_REG_P (SUBREG_REG (operands[0])))) 2718 && ! (ANY_FP_REG_P (operands[1]) || 2719 (GET_CODE (operands[1]) == SUBREG 2720 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))" 2721 [(const_int 0)] 2722 "ix86_split_long_move (operands); DONE;") 2723 2724(define_insn "*swapdf" 2725 [(set (match_operand:DF 0 "fp_register_operand" "+f") 2726 (match_operand:DF 1 "fp_register_operand" "+f")) 2727 (set (match_dup 1) 2728 (match_dup 0))] 2729 "reload_completed || TARGET_80387" 2730{ 2731 if (STACK_TOP_P (operands[0])) 2732 return "fxch\t%1"; 2733 else 2734 return "fxch\t%0"; 2735} 2736 [(set_attr "type" "fxch") 2737 (set_attr "mode" "DF")]) 2738 2739(define_expand "movxf" 2740 [(set (match_operand:XF 0 "nonimmediate_operand" "") 2741 (match_operand:XF 1 "general_operand" ""))] 2742 "" 2743 "ix86_expand_move (XFmode, operands); DONE;") 2744 2745;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size. 2746;; Size of pushdf using integer instructions is 3+3*memory operand size 2747;; Pushing using integer instructions is longer except for constants 2748;; and direct memory references. 2749;; (assuming that any given constant is pushed only once, but this ought to be 2750;; handled elsewhere). 2751 2752(define_insn "*pushxf_nointeger" 2753 [(set (match_operand:XF 0 "push_operand" "=X,X,X") 2754 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))] 2755 "optimize_size" 2756{ 2757 /* This insn should be already split before reg-stack. */ 2758 gcc_unreachable (); 2759} 2760 [(set_attr "type" "multi") 2761 (set_attr "unit" "i387,*,*") 2762 (set_attr "mode" "XF,SI,SI")]) 2763 2764(define_insn "*pushxf_integer" 2765 [(set (match_operand:XF 0 "push_operand" "=<,<") 2766 (match_operand:XF 1 "general_no_elim_operand" "f,ro"))] 2767 "!optimize_size" 2768{ 2769 /* This insn should be already split before reg-stack. */ 2770 gcc_unreachable (); 2771} 2772 [(set_attr "type" "multi") 2773 (set_attr "unit" "i387,*") 2774 (set_attr "mode" "XF,SI")]) 2775 2776(define_split 2777 [(set (match_operand 0 "push_operand" "") 2778 (match_operand 1 "general_operand" ""))] 2779 "reload_completed 2780 && (GET_MODE (operands[0]) == XFmode 2781 || GET_MODE (operands[0]) == DFmode) 2782 && !ANY_FP_REG_P (operands[1])" 2783 [(const_int 0)] 2784 "ix86_split_long_move (operands); DONE;") 2785 2786(define_split 2787 [(set (match_operand:XF 0 "push_operand" "") 2788 (match_operand:XF 1 "any_fp_register_operand" ""))] 2789 "!TARGET_64BIT" 2790 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2))) 2791 (set (mem:XF (reg:SI SP_REG)) (match_dup 1))] 2792 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 2793 2794(define_split 2795 [(set (match_operand:XF 0 "push_operand" "") 2796 (match_operand:XF 1 "any_fp_register_operand" ""))] 2797 "TARGET_64BIT" 2798 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2))) 2799 (set (mem:XF (reg:DI SP_REG)) (match_dup 1))] 2800 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 2801 2802;; Do not use integer registers when optimizing for size 2803(define_insn "*movxf_nointeger" 2804 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o") 2805 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))] 2806 "optimize_size 2807 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2808 && (reload_in_progress || reload_completed 2809 || GET_CODE (operands[1]) != CONST_DOUBLE 2810 || memory_operand (operands[0], XFmode))" 2811{ 2812 switch (which_alternative) 2813 { 2814 case 0: 2815 return output_387_reg_move (insn, operands); 2816 2817 case 1: 2818 /* There is no non-popping store to memory for XFmode. So if 2819 we need one, follow the store with a load. */ 2820 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 2821 return "fstp%z0\t%y0\;fld%z0\t%y0"; 2822 else 2823 return "fstp%z0\t%y0"; 2824 2825 case 2: 2826 return standard_80387_constant_opcode (operands[1]); 2827 2828 case 3: case 4: 2829 return "#"; 2830 default: 2831 gcc_unreachable (); 2832 } 2833} 2834 [(set_attr "type" "fmov,fmov,fmov,multi,multi") 2835 (set_attr "mode" "XF,XF,XF,SI,SI")]) 2836 2837(define_insn "*movxf_integer" 2838 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,r,o") 2839 (match_operand:XF 1 "general_operand" "fm,f,G,roF,Fr"))] 2840 "!optimize_size 2841 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2842 && (reload_in_progress || reload_completed 2843 || GET_CODE (operands[1]) != CONST_DOUBLE 2844 || memory_operand (operands[0], XFmode))" 2845{ 2846 switch (which_alternative) 2847 { 2848 case 0: 2849 return output_387_reg_move (insn, operands); 2850 2851 case 1: 2852 /* There is no non-popping store to memory for XFmode. So if 2853 we need one, follow the store with a load. */ 2854 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 2855 return "fstp%z0\t%y0\;fld%z0\t%y0"; 2856 else 2857 return "fstp%z0\t%y0"; 2858 2859 case 2: 2860 return standard_80387_constant_opcode (operands[1]); 2861 2862 case 3: case 4: 2863 return "#"; 2864 2865 default: 2866 gcc_unreachable (); 2867 } 2868} 2869 [(set_attr "type" "fmov,fmov,fmov,multi,multi") 2870 (set_attr "mode" "XF,XF,XF,SI,SI")]) 2871 2872(define_split 2873 [(set (match_operand 0 "nonimmediate_operand" "") 2874 (match_operand 1 "general_operand" ""))] 2875 "reload_completed 2876 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 2877 && GET_MODE (operands[0]) == XFmode 2878 && ! (ANY_FP_REG_P (operands[0]) || 2879 (GET_CODE (operands[0]) == SUBREG 2880 && ANY_FP_REG_P (SUBREG_REG (operands[0])))) 2881 && ! (ANY_FP_REG_P (operands[1]) || 2882 (GET_CODE (operands[1]) == SUBREG 2883 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))" 2884 [(const_int 0)] 2885 "ix86_split_long_move (operands); DONE;") 2886 2887(define_split 2888 [(set (match_operand 0 "register_operand" "") 2889 (match_operand 1 "memory_operand" ""))] 2890 "reload_completed 2891 && GET_CODE (operands[1]) == MEM 2892 && (GET_MODE (operands[0]) == XFmode 2893 || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode) 2894 && constant_pool_reference_p (operands[1])" 2895 [(set (match_dup 0) (match_dup 1))] 2896{ 2897 rtx c = avoid_constant_pool_reference (operands[1]); 2898 rtx r = operands[0]; 2899 2900 if (GET_CODE (r) == SUBREG) 2901 r = SUBREG_REG (r); 2902 2903 if (SSE_REG_P (r)) 2904 { 2905 if (!standard_sse_constant_p (c)) 2906 FAIL; 2907 } 2908 else if (FP_REG_P (r)) 2909 { 2910 if (!standard_80387_constant_p (c)) 2911 FAIL; 2912 } 2913 else if (MMX_REG_P (r)) 2914 FAIL; 2915 2916 operands[1] = c; 2917}) 2918 2919(define_insn "swapxf" 2920 [(set (match_operand:XF 0 "register_operand" "+f") 2921 (match_operand:XF 1 "register_operand" "+f")) 2922 (set (match_dup 1) 2923 (match_dup 0))] 2924 "TARGET_80387" 2925{ 2926 if (STACK_TOP_P (operands[0])) 2927 return "fxch\t%1"; 2928 else 2929 return "fxch\t%0"; 2930} 2931 [(set_attr "type" "fxch") 2932 (set_attr "mode" "XF")]) 2933 2934(define_expand "movtf" 2935 [(set (match_operand:TF 0 "nonimmediate_operand" "") 2936 (match_operand:TF 1 "nonimmediate_operand" ""))] 2937 "TARGET_64BIT" 2938{ 2939 ix86_expand_move (TFmode, operands); 2940 DONE; 2941}) 2942 2943(define_insn "*movtf_internal" 2944 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm") 2945 (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))] 2946 "TARGET_64BIT 2947 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 2948{ 2949 switch (which_alternative) 2950 { 2951 case 0: 2952 case 1: 2953 return "#"; 2954 case 2: 2955 if (get_attr_mode (insn) == MODE_V4SF) 2956 return "xorps\t%0, %0"; 2957 else 2958 return "pxor\t%0, %0"; 2959 case 3: 2960 case 4: 2961 if (get_attr_mode (insn) == MODE_V4SF) 2962 return "movaps\t{%1, %0|%0, %1}"; 2963 else 2964 return "movdqa\t{%1, %0|%0, %1}"; 2965 default: 2966 gcc_unreachable (); 2967 } 2968} 2969 [(set_attr "type" "*,*,sselog1,ssemov,ssemov") 2970 (set (attr "mode") 2971 (cond [(eq_attr "alternative" "2,3") 2972 (if_then_else 2973 (ne (symbol_ref "optimize_size") 2974 (const_int 0)) 2975 (const_string "V4SF") 2976 (const_string "TI")) 2977 (eq_attr "alternative" "4") 2978 (if_then_else 2979 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES") 2980 (const_int 0)) 2981 (ne (symbol_ref "optimize_size") 2982 (const_int 0))) 2983 (const_string "V4SF") 2984 (const_string "TI"))] 2985 (const_string "DI")))]) 2986 2987(define_split 2988 [(set (match_operand:TF 0 "nonimmediate_operand" "") 2989 (match_operand:TF 1 "general_operand" ""))] 2990 "reload_completed && !SSE_REG_P (operands[0]) 2991 && !SSE_REG_P (operands[1])" 2992 [(const_int 0)] 2993 "ix86_split_long_move (operands); DONE;") 2994 2995;; Zero extension instructions 2996 2997(define_expand "zero_extendhisi2" 2998 [(set (match_operand:SI 0 "register_operand" "") 2999 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))] 3000 "" 3001{ 3002 if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size) 3003 { 3004 operands[1] = force_reg (HImode, operands[1]); 3005 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1])); 3006 DONE; 3007 } 3008}) 3009 3010(define_insn "zero_extendhisi2_and" 3011 [(set (match_operand:SI 0 "register_operand" "=r") 3012 (zero_extend:SI (match_operand:HI 1 "register_operand" "0"))) 3013 (clobber (reg:CC FLAGS_REG))] 3014 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size" 3015 "#" 3016 [(set_attr "type" "alu1") 3017 (set_attr "mode" "SI")]) 3018 3019(define_split 3020 [(set (match_operand:SI 0 "register_operand" "") 3021 (zero_extend:SI (match_operand:HI 1 "register_operand" ""))) 3022 (clobber (reg:CC FLAGS_REG))] 3023 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size" 3024 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535))) 3025 (clobber (reg:CC FLAGS_REG))])] 3026 "") 3027 3028(define_insn "*zero_extendhisi2_movzwl" 3029 [(set (match_operand:SI 0 "register_operand" "=r") 3030 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))] 3031 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size" 3032 "movz{wl|x}\t{%1, %0|%0, %1}" 3033 [(set_attr "type" "imovx") 3034 (set_attr "mode" "SI")]) 3035 3036(define_expand "zero_extendqihi2" 3037 [(parallel 3038 [(set (match_operand:HI 0 "register_operand" "") 3039 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))) 3040 (clobber (reg:CC FLAGS_REG))])] 3041 "" 3042 "") 3043 3044(define_insn "*zero_extendqihi2_and" 3045 [(set (match_operand:HI 0 "register_operand" "=r,?&q") 3046 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm"))) 3047 (clobber (reg:CC FLAGS_REG))] 3048 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size" 3049 "#" 3050 [(set_attr "type" "alu1") 3051 (set_attr "mode" "HI")]) 3052 3053(define_insn "*zero_extendqihi2_movzbw_and" 3054 [(set (match_operand:HI 0 "register_operand" "=r,r") 3055 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0"))) 3056 (clobber (reg:CC FLAGS_REG))] 3057 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size" 3058 "#" 3059 [(set_attr "type" "imovx,alu1") 3060 (set_attr "mode" "HI")]) 3061 3062; zero extend to SImode here to avoid partial register stalls 3063(define_insn "*zero_extendqihi2_movzbl" 3064 [(set (match_operand:HI 0 "register_operand" "=r") 3065 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))] 3066 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed" 3067 "movz{bl|x}\t{%1, %k0|%k0, %k1}" 3068 [(set_attr "type" "imovx") 3069 (set_attr "mode" "SI")]) 3070 3071;; For the movzbw case strip only the clobber 3072(define_split 3073 [(set (match_operand:HI 0 "register_operand" "") 3074 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))) 3075 (clobber (reg:CC FLAGS_REG))] 3076 "reload_completed 3077 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) 3078 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))" 3079 [(set (match_operand:HI 0 "register_operand" "") 3080 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))]) 3081 3082;; When source and destination does not overlap, clear destination 3083;; first and then do the movb 3084(define_split 3085 [(set (match_operand:HI 0 "register_operand" "") 3086 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))) 3087 (clobber (reg:CC FLAGS_REG))] 3088 "reload_completed 3089 && ANY_QI_REG_P (operands[0]) 3090 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size) 3091 && !reg_overlap_mentioned_p (operands[0], operands[1])" 3092 [(set (match_dup 0) (const_int 0)) 3093 (set (strict_low_part (match_dup 2)) (match_dup 1))] 3094 "operands[2] = gen_lowpart (QImode, operands[0]);") 3095 3096;; Rest is handled by single and. 3097(define_split 3098 [(set (match_operand:HI 0 "register_operand" "") 3099 (zero_extend:HI (match_operand:QI 1 "register_operand" ""))) 3100 (clobber (reg:CC FLAGS_REG))] 3101 "reload_completed 3102 && true_regnum (operands[0]) == true_regnum (operands[1])" 3103 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255))) 3104 (clobber (reg:CC FLAGS_REG))])] 3105 "") 3106 3107(define_expand "zero_extendqisi2" 3108 [(parallel 3109 [(set (match_operand:SI 0 "register_operand" "") 3110 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" ""))) 3111 (clobber (reg:CC FLAGS_REG))])] 3112 "" 3113 "") 3114 3115(define_insn "*zero_extendqisi2_and" 3116 [(set (match_operand:SI 0 "register_operand" "=r,?&q") 3117 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm"))) 3118 (clobber (reg:CC FLAGS_REG))] 3119 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size" 3120 "#" 3121 [(set_attr "type" "alu1") 3122 (set_attr "mode" "SI")]) 3123 3124(define_insn "*zero_extendqisi2_movzbw_and" 3125 [(set (match_operand:SI 0 "register_operand" "=r,r") 3126 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0"))) 3127 (clobber (reg:CC FLAGS_REG))] 3128 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size" 3129 "#" 3130 [(set_attr "type" "imovx,alu1") 3131 (set_attr "mode" "SI")]) 3132 3133(define_insn "*zero_extendqisi2_movzbw" 3134 [(set (match_operand:SI 0 "register_operand" "=r") 3135 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))] 3136 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed" 3137 "movz{bl|x}\t{%1, %0|%0, %1}" 3138 [(set_attr "type" "imovx") 3139 (set_attr "mode" "SI")]) 3140 3141;; For the movzbl case strip only the clobber 3142(define_split 3143 [(set (match_operand:SI 0 "register_operand" "") 3144 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" ""))) 3145 (clobber (reg:CC FLAGS_REG))] 3146 "reload_completed 3147 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) 3148 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))" 3149 [(set (match_dup 0) 3150 (zero_extend:SI (match_dup 1)))]) 3151 3152;; When source and destination does not overlap, clear destination 3153;; first and then do the movb 3154(define_split 3155 [(set (match_operand:SI 0 "register_operand" "") 3156 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" ""))) 3157 (clobber (reg:CC FLAGS_REG))] 3158 "reload_completed 3159 && ANY_QI_REG_P (operands[0]) 3160 && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM) 3161 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size) 3162 && !reg_overlap_mentioned_p (operands[0], operands[1])" 3163 [(set (match_dup 0) (const_int 0)) 3164 (set (strict_low_part (match_dup 2)) (match_dup 1))] 3165 "operands[2] = gen_lowpart (QImode, operands[0]);") 3166 3167;; Rest is handled by single and. 3168(define_split 3169 [(set (match_operand:SI 0 "register_operand" "") 3170 (zero_extend:SI (match_operand:QI 1 "register_operand" ""))) 3171 (clobber (reg:CC FLAGS_REG))] 3172 "reload_completed 3173 && true_regnum (operands[0]) == true_regnum (operands[1])" 3174 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255))) 3175 (clobber (reg:CC FLAGS_REG))])] 3176 "") 3177 3178;; %%% Kill me once multi-word ops are sane. 3179(define_expand "zero_extendsidi2" 3180 [(set (match_operand:DI 0 "register_operand" "=r") 3181 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))] 3182 "" 3183 "if (!TARGET_64BIT) 3184 { 3185 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1])); 3186 DONE; 3187 } 3188 ") 3189 3190(define_insn "zero_extendsidi2_32" 3191 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,?*y,?*Y") 3192 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm"))) 3193 (clobber (reg:CC FLAGS_REG))] 3194 "!TARGET_64BIT" 3195 "@ 3196 # 3197 # 3198 # 3199 movd\t{%1, %0|%0, %1} 3200 movd\t{%1, %0|%0, %1}" 3201 [(set_attr "mode" "SI,SI,SI,DI,TI") 3202 (set_attr "type" "multi,multi,multi,mmxmov,ssemov")]) 3203 3204(define_insn "zero_extendsidi2_rex64" 3205 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*y,?*Y") 3206 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))] 3207 "TARGET_64BIT" 3208 "@ 3209 mov\t{%k1, %k0|%k0, %k1} 3210 # 3211 movd\t{%1, %0|%0, %1} 3212 movd\t{%1, %0|%0, %1}" 3213 [(set_attr "type" "imovx,imov,mmxmov,ssemov") 3214 (set_attr "mode" "SI,DI,SI,SI")]) 3215 3216(define_split 3217 [(set (match_operand:DI 0 "memory_operand" "") 3218 (zero_extend:DI (match_dup 0)))] 3219 "TARGET_64BIT" 3220 [(set (match_dup 4) (const_int 0))] 3221 "split_di (&operands[0], 1, &operands[3], &operands[4]);") 3222 3223(define_split 3224 [(set (match_operand:DI 0 "register_operand" "") 3225 (zero_extend:DI (match_operand:SI 1 "register_operand" ""))) 3226 (clobber (reg:CC FLAGS_REG))] 3227 "!TARGET_64BIT && reload_completed 3228 && true_regnum (operands[0]) == true_regnum (operands[1])" 3229 [(set (match_dup 4) (const_int 0))] 3230 "split_di (&operands[0], 1, &operands[3], &operands[4]);") 3231 3232(define_split 3233 [(set (match_operand:DI 0 "nonimmediate_operand" "") 3234 (zero_extend:DI (match_operand:SI 1 "general_operand" ""))) 3235 (clobber (reg:CC FLAGS_REG))] 3236 "!TARGET_64BIT && reload_completed 3237 && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])" 3238 [(set (match_dup 3) (match_dup 1)) 3239 (set (match_dup 4) (const_int 0))] 3240 "split_di (&operands[0], 1, &operands[3], &operands[4]);") 3241 3242(define_insn "zero_extendhidi2" 3243 [(set (match_operand:DI 0 "register_operand" "=r") 3244 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))] 3245 "TARGET_64BIT" 3246 "movz{wl|x}\t{%1, %k0|%k0, %1}" 3247 [(set_attr "type" "imovx") 3248 (set_attr "mode" "DI")]) 3249 3250(define_insn "zero_extendqidi2" 3251 [(set (match_operand:DI 0 "register_operand" "=r") 3252 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))] 3253 "TARGET_64BIT" 3254 "movz{bl|x}\t{%1, %k0|%k0, %1}" 3255 [(set_attr "type" "imovx") 3256 (set_attr "mode" "DI")]) 3257 3258;; Sign extension instructions 3259 3260(define_expand "extendsidi2" 3261 [(parallel [(set (match_operand:DI 0 "register_operand" "") 3262 (sign_extend:DI (match_operand:SI 1 "register_operand" ""))) 3263 (clobber (reg:CC FLAGS_REG)) 3264 (clobber (match_scratch:SI 2 ""))])] 3265 "" 3266{ 3267 if (TARGET_64BIT) 3268 { 3269 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1])); 3270 DONE; 3271 } 3272}) 3273 3274(define_insn "*extendsidi2_1" 3275 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o") 3276 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r"))) 3277 (clobber (reg:CC FLAGS_REG)) 3278 (clobber (match_scratch:SI 2 "=X,X,X,&r"))] 3279 "!TARGET_64BIT" 3280 "#") 3281 3282(define_insn "extendsidi2_rex64" 3283 [(set (match_operand:DI 0 "register_operand" "=*a,r") 3284 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))] 3285 "TARGET_64BIT" 3286 "@ 3287 {cltq|cdqe} 3288 movs{lq|x}\t{%1,%0|%0, %1}" 3289 [(set_attr "type" "imovx") 3290 (set_attr "mode" "DI") 3291 (set_attr "prefix_0f" "0") 3292 (set_attr "modrm" "0,1")]) 3293 3294(define_insn "extendhidi2" 3295 [(set (match_operand:DI 0 "register_operand" "=r") 3296 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))] 3297 "TARGET_64BIT" 3298 "movs{wq|x}\t{%1,%0|%0, %1}" 3299 [(set_attr "type" "imovx") 3300 (set_attr "mode" "DI")]) 3301 3302(define_insn "extendqidi2" 3303 [(set (match_operand:DI 0 "register_operand" "=r") 3304 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))] 3305 "TARGET_64BIT" 3306 "movs{bq|x}\t{%1,%0|%0, %1}" 3307 [(set_attr "type" "imovx") 3308 (set_attr "mode" "DI")]) 3309 3310;; Extend to memory case when source register does die. 3311(define_split 3312 [(set (match_operand:DI 0 "memory_operand" "") 3313 (sign_extend:DI (match_operand:SI 1 "register_operand" ""))) 3314 (clobber (reg:CC FLAGS_REG)) 3315 (clobber (match_operand:SI 2 "register_operand" ""))] 3316 "(reload_completed 3317 && dead_or_set_p (insn, operands[1]) 3318 && !reg_mentioned_p (operands[1], operands[0]))" 3319 [(set (match_dup 3) (match_dup 1)) 3320 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31))) 3321 (clobber (reg:CC FLAGS_REG))]) 3322 (set (match_dup 4) (match_dup 1))] 3323 "split_di (&operands[0], 1, &operands[3], &operands[4]);") 3324 3325;; Extend to memory case when source register does not die. 3326(define_split 3327 [(set (match_operand:DI 0 "memory_operand" "") 3328 (sign_extend:DI (match_operand:SI 1 "register_operand" ""))) 3329 (clobber (reg:CC FLAGS_REG)) 3330 (clobber (match_operand:SI 2 "register_operand" ""))] 3331 "reload_completed" 3332 [(const_int 0)] 3333{ 3334 split_di (&operands[0], 1, &operands[3], &operands[4]); 3335 3336 emit_move_insn (operands[3], operands[1]); 3337 3338 /* Generate a cltd if possible and doing so it profitable. */ 3339 if (true_regnum (operands[1]) == 0 3340 && true_regnum (operands[2]) == 1 3341 && (optimize_size || TARGET_USE_CLTD)) 3342 { 3343 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31))); 3344 } 3345 else 3346 { 3347 emit_move_insn (operands[2], operands[1]); 3348 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31))); 3349 } 3350 emit_move_insn (operands[4], operands[2]); 3351 DONE; 3352}) 3353 3354;; Extend to register case. Optimize case where source and destination 3355;; registers match and cases where we can use cltd. 3356(define_split 3357 [(set (match_operand:DI 0 "register_operand" "") 3358 (sign_extend:DI (match_operand:SI 1 "register_operand" ""))) 3359 (clobber (reg:CC FLAGS_REG)) 3360 (clobber (match_scratch:SI 2 ""))] 3361 "reload_completed" 3362 [(const_int 0)] 3363{ 3364 split_di (&operands[0], 1, &operands[3], &operands[4]); 3365 3366 if (true_regnum (operands[3]) != true_regnum (operands[1])) 3367 emit_move_insn (operands[3], operands[1]); 3368 3369 /* Generate a cltd if possible and doing so it profitable. */ 3370 if (true_regnum (operands[3]) == 0 3371 && (optimize_size || TARGET_USE_CLTD)) 3372 { 3373 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31))); 3374 DONE; 3375 } 3376 3377 if (true_regnum (operands[4]) != true_regnum (operands[1])) 3378 emit_move_insn (operands[4], operands[1]); 3379 3380 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31))); 3381 DONE; 3382}) 3383 3384(define_insn "extendhisi2" 3385 [(set (match_operand:SI 0 "register_operand" "=*a,r") 3386 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))] 3387 "" 3388{ 3389 switch (get_attr_prefix_0f (insn)) 3390 { 3391 case 0: 3392 return "{cwtl|cwde}"; 3393 default: 3394 return "movs{wl|x}\t{%1,%0|%0, %1}"; 3395 } 3396} 3397 [(set_attr "type" "imovx") 3398 (set_attr "mode" "SI") 3399 (set (attr "prefix_0f") 3400 ;; movsx is short decodable while cwtl is vector decoded. 3401 (if_then_else (and (eq_attr "cpu" "!k6") 3402 (eq_attr "alternative" "0")) 3403 (const_string "0") 3404 (const_string "1"))) 3405 (set (attr "modrm") 3406 (if_then_else (eq_attr "prefix_0f" "0") 3407 (const_string "0") 3408 (const_string "1")))]) 3409 3410(define_insn "*extendhisi2_zext" 3411 [(set (match_operand:DI 0 "register_operand" "=*a,r") 3412 (zero_extend:DI 3413 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))] 3414 "TARGET_64BIT" 3415{ 3416 switch (get_attr_prefix_0f (insn)) 3417 { 3418 case 0: 3419 return "{cwtl|cwde}"; 3420 default: 3421 return "movs{wl|x}\t{%1,%k0|%k0, %1}"; 3422 } 3423} 3424 [(set_attr "type" "imovx") 3425 (set_attr "mode" "SI") 3426 (set (attr "prefix_0f") 3427 ;; movsx is short decodable while cwtl is vector decoded. 3428 (if_then_else (and (eq_attr "cpu" "!k6") 3429 (eq_attr "alternative" "0")) 3430 (const_string "0") 3431 (const_string "1"))) 3432 (set (attr "modrm") 3433 (if_then_else (eq_attr "prefix_0f" "0") 3434 (const_string "0") 3435 (const_string "1")))]) 3436 3437(define_insn "extendqihi2" 3438 [(set (match_operand:HI 0 "register_operand" "=*a,r") 3439 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))] 3440 "" 3441{ 3442 switch (get_attr_prefix_0f (insn)) 3443 { 3444 case 0: 3445 return "{cbtw|cbw}"; 3446 default: 3447 return "movs{bw|x}\t{%1,%0|%0, %1}"; 3448 } 3449} 3450 [(set_attr "type" "imovx") 3451 (set_attr "mode" "HI") 3452 (set (attr "prefix_0f") 3453 ;; movsx is short decodable while cwtl is vector decoded. 3454 (if_then_else (and (eq_attr "cpu" "!k6") 3455 (eq_attr "alternative" "0")) 3456 (const_string "0") 3457 (const_string "1"))) 3458 (set (attr "modrm") 3459 (if_then_else (eq_attr "prefix_0f" "0") 3460 (const_string "0") 3461 (const_string "1")))]) 3462 3463(define_insn "extendqisi2" 3464 [(set (match_operand:SI 0 "register_operand" "=r") 3465 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))] 3466 "" 3467 "movs{bl|x}\t{%1,%0|%0, %1}" 3468 [(set_attr "type" "imovx") 3469 (set_attr "mode" "SI")]) 3470 3471(define_insn "*extendqisi2_zext" 3472 [(set (match_operand:DI 0 "register_operand" "=r") 3473 (zero_extend:DI 3474 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))] 3475 "TARGET_64BIT" 3476 "movs{bl|x}\t{%1,%k0|%k0, %1}" 3477 [(set_attr "type" "imovx") 3478 (set_attr "mode" "SI")]) 3479 3480;; Conversions between float and double. 3481 3482;; These are all no-ops in the model used for the 80387. So just 3483;; emit moves. 3484 3485;; %%% Kill these when call knows how to work out a DFmode push earlier. 3486(define_insn "*dummy_extendsfdf2" 3487 [(set (match_operand:DF 0 "push_operand" "=<") 3488 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))] 3489 "0" 3490 "#") 3491 3492(define_split 3493 [(set (match_operand:DF 0 "push_operand" "") 3494 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))] 3495 "!TARGET_64BIT" 3496 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8))) 3497 (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))]) 3498 3499(define_split 3500 [(set (match_operand:DF 0 "push_operand" "") 3501 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))] 3502 "TARGET_64BIT" 3503 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8))) 3504 (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))]) 3505 3506(define_insn "*dummy_extendsfxf2" 3507 [(set (match_operand:XF 0 "push_operand" "=<") 3508 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))] 3509 "0" 3510 "#") 3511 3512(define_split 3513 [(set (match_operand:XF 0 "push_operand" "") 3514 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))] 3515 "" 3516 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2))) 3517 (set (mem:XF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))] 3518 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 3519 3520(define_split 3521 [(set (match_operand:XF 0 "push_operand" "") 3522 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))] 3523 "TARGET_64BIT" 3524 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2))) 3525 (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))] 3526 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 3527 3528(define_split 3529 [(set (match_operand:XF 0 "push_operand" "") 3530 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))] 3531 "" 3532 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2))) 3533 (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))] 3534 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 3535 3536(define_split 3537 [(set (match_operand:XF 0 "push_operand" "") 3538 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))] 3539 "TARGET_64BIT" 3540 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2))) 3541 (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))] 3542 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);") 3543 3544(define_expand "extendsfdf2" 3545 [(set (match_operand:DF 0 "nonimmediate_operand" "") 3546 (float_extend:DF (match_operand:SF 1 "general_operand" "")))] 3547 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 3548{ 3549 /* ??? Needed for compress_float_constant since all fp constants 3550 are LEGITIMATE_CONSTANT_P. */ 3551 if (GET_CODE (operands[1]) == CONST_DOUBLE) 3552 { 3553 if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387) 3554 && standard_80387_constant_p (operands[1]) > 0) 3555 { 3556 operands[1] = simplify_const_unary_operation 3557 (FLOAT_EXTEND, DFmode, operands[1], SFmode); 3558 emit_move_insn_1 (operands[0], operands[1]); 3559 DONE; 3560 } 3561 operands[1] = validize_mem (force_const_mem (SFmode, operands[1])); 3562 } 3563 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 3564 operands[1] = force_reg (SFmode, operands[1]); 3565}) 3566 3567(define_insn "*extendsfdf2_mixed" 3568 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,Y") 3569 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f,mY")))] 3570 "TARGET_SSE2 && TARGET_MIX_SSE_I387 3571 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 3572{ 3573 switch (which_alternative) 3574 { 3575 case 0: 3576 return output_387_reg_move (insn, operands); 3577 3578 case 1: 3579 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3580 return "fstp%z0\t%y0"; 3581 else 3582 return "fst%z0\t%y0"; 3583 3584 case 2: 3585 return "cvtss2sd\t{%1, %0|%0, %1}"; 3586 3587 default: 3588 gcc_unreachable (); 3589 } 3590} 3591 [(set_attr "type" "fmov,fmov,ssecvt") 3592 (set_attr "mode" "SF,XF,DF")]) 3593 3594(define_insn "*extendsfdf2_sse" 3595 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y") 3596 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))] 3597 "TARGET_SSE2 && TARGET_SSE_MATH 3598 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 3599 "cvtss2sd\t{%1, %0|%0, %1}" 3600 [(set_attr "type" "ssecvt") 3601 (set_attr "mode" "DF")]) 3602 3603(define_insn "*extendsfdf2_i387" 3604 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m") 3605 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))] 3606 "TARGET_80387 3607 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 3608{ 3609 switch (which_alternative) 3610 { 3611 case 0: 3612 return output_387_reg_move (insn, operands); 3613 3614 case 1: 3615 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3616 return "fstp%z0\t%y0"; 3617 else 3618 return "fst%z0\t%y0"; 3619 3620 default: 3621 gcc_unreachable (); 3622 } 3623} 3624 [(set_attr "type" "fmov") 3625 (set_attr "mode" "SF,XF")]) 3626 3627(define_expand "extendsfxf2" 3628 [(set (match_operand:XF 0 "nonimmediate_operand" "") 3629 (float_extend:XF (match_operand:SF 1 "general_operand" "")))] 3630 "TARGET_80387" 3631{ 3632 /* ??? Needed for compress_float_constant since all fp constants 3633 are LEGITIMATE_CONSTANT_P. */ 3634 if (GET_CODE (operands[1]) == CONST_DOUBLE) 3635 { 3636 if (standard_80387_constant_p (operands[1]) > 0) 3637 { 3638 operands[1] = simplify_const_unary_operation 3639 (FLOAT_EXTEND, XFmode, operands[1], SFmode); 3640 emit_move_insn_1 (operands[0], operands[1]); 3641 DONE; 3642 } 3643 operands[1] = validize_mem (force_const_mem (SFmode, operands[1])); 3644 } 3645 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 3646 operands[1] = force_reg (SFmode, operands[1]); 3647}) 3648 3649(define_insn "*extendsfxf2_i387" 3650 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m") 3651 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))] 3652 "TARGET_80387 3653 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 3654{ 3655 switch (which_alternative) 3656 { 3657 case 0: 3658 return output_387_reg_move (insn, operands); 3659 3660 case 1: 3661 /* There is no non-popping store to memory for XFmode. So if 3662 we need one, follow the store with a load. */ 3663 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3664 return "fstp%z0\t%y0"; 3665 else 3666 return "fstp%z0\t%y0\n\tfld%z0\t%y0"; 3667 3668 default: 3669 gcc_unreachable (); 3670 } 3671} 3672 [(set_attr "type" "fmov") 3673 (set_attr "mode" "SF,XF")]) 3674 3675(define_expand "extenddfxf2" 3676 [(set (match_operand:XF 0 "nonimmediate_operand" "") 3677 (float_extend:XF (match_operand:DF 1 "general_operand" "")))] 3678 "TARGET_80387" 3679{ 3680 /* ??? Needed for compress_float_constant since all fp constants 3681 are LEGITIMATE_CONSTANT_P. */ 3682 if (GET_CODE (operands[1]) == CONST_DOUBLE) 3683 { 3684 if (standard_80387_constant_p (operands[1]) > 0) 3685 { 3686 operands[1] = simplify_const_unary_operation 3687 (FLOAT_EXTEND, XFmode, operands[1], DFmode); 3688 emit_move_insn_1 (operands[0], operands[1]); 3689 DONE; 3690 } 3691 operands[1] = validize_mem (force_const_mem (DFmode, operands[1])); 3692 } 3693 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM) 3694 operands[1] = force_reg (DFmode, operands[1]); 3695}) 3696 3697(define_insn "*extenddfxf2_i387" 3698 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m") 3699 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))] 3700 "TARGET_80387 3701 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 3702{ 3703 switch (which_alternative) 3704 { 3705 case 0: 3706 return output_387_reg_move (insn, operands); 3707 3708 case 1: 3709 /* There is no non-popping store to memory for XFmode. So if 3710 we need one, follow the store with a load. */ 3711 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3712 return "fstp%z0\t%y0\n\tfld%z0\t%y0"; 3713 else 3714 return "fstp%z0\t%y0"; 3715 3716 default: 3717 gcc_unreachable (); 3718 } 3719} 3720 [(set_attr "type" "fmov") 3721 (set_attr "mode" "DF,XF")]) 3722 3723;; %%% This seems bad bad news. 3724;; This cannot output into an f-reg because there is no way to be sure 3725;; of truncating in that case. Otherwise this is just like a simple move 3726;; insn. So we pretend we can output to a reg in order to get better 3727;; register preferencing, but we really use a stack slot. 3728 3729;; Conversion from DFmode to SFmode. 3730 3731(define_expand "truncdfsf2" 3732 [(set (match_operand:SF 0 "nonimmediate_operand" "") 3733 (float_truncate:SF 3734 (match_operand:DF 1 "nonimmediate_operand" "")))] 3735 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 3736{ 3737 if (MEM_P (operands[0]) && MEM_P (operands[1])) 3738 operands[1] = force_reg (DFmode, operands[1]); 3739 3740 if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387) 3741 ; 3742 else if (flag_unsafe_math_optimizations) 3743 ; 3744 else 3745 { 3746 rtx temp = assign_386_stack_local (SFmode, SLOT_VIRTUAL); 3747 emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp)); 3748 DONE; 3749 } 3750}) 3751 3752(define_expand "truncdfsf2_with_temp" 3753 [(parallel [(set (match_operand:SF 0 "" "") 3754 (float_truncate:SF (match_operand:DF 1 "" ""))) 3755 (clobber (match_operand:SF 2 "" ""))])] 3756 "") 3757 3758(define_insn "*truncdfsf_fast_mixed" 3759 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f,Y") 3760 (float_truncate:SF 3761 (match_operand:DF 1 "nonimmediate_operand" "f ,f,Ym")))] 3762 "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations" 3763{ 3764 switch (which_alternative) 3765 { 3766 case 0: 3767 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3768 return "fstp%z0\t%y0"; 3769 else 3770 return "fst%z0\t%y0"; 3771 case 1: 3772 return output_387_reg_move (insn, operands); 3773 case 2: 3774 return "cvtsd2ss\t{%1, %0|%0, %1}"; 3775 default: 3776 gcc_unreachable (); 3777 } 3778} 3779 [(set_attr "type" "fmov,fmov,ssecvt") 3780 (set_attr "mode" "SF")]) 3781 3782;; Yes, this one doesn't depend on flag_unsafe_math_optimizations, 3783;; because nothing we do here is unsafe. 3784(define_insn "*truncdfsf_fast_sse" 3785 [(set (match_operand:SF 0 "nonimmediate_operand" "=Y") 3786 (float_truncate:SF 3787 (match_operand:DF 1 "nonimmediate_operand" "Ym")))] 3788 "TARGET_SSE2 && TARGET_SSE_MATH" 3789 "cvtsd2ss\t{%1, %0|%0, %1}" 3790 [(set_attr "type" "ssecvt") 3791 (set_attr "mode" "SF")]) 3792 3793(define_insn "*truncdfsf_fast_i387" 3794 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm") 3795 (float_truncate:SF 3796 (match_operand:DF 1 "nonimmediate_operand" "f")))] 3797 "TARGET_80387 && flag_unsafe_math_optimizations" 3798 "* return output_387_reg_move (insn, operands);" 3799 [(set_attr "type" "fmov") 3800 (set_attr "mode" "SF")]) 3801 3802(define_insn "*truncdfsf_mixed" 3803 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r,Y") 3804 (float_truncate:SF 3805 (match_operand:DF 1 "nonimmediate_operand" "f ,f ,Ym"))) 3806 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,X"))] 3807 "TARGET_MIX_SSE_I387" 3808{ 3809 switch (which_alternative) 3810 { 3811 case 0: 3812 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3813 return "fstp%z0\t%y0"; 3814 else 3815 return "fst%z0\t%y0"; 3816 case 1: 3817 return "#"; 3818 case 2: 3819 return "cvtsd2ss\t{%1, %0|%0, %1}"; 3820 default: 3821 gcc_unreachable (); 3822 } 3823} 3824 [(set_attr "type" "fmov,multi,ssecvt") 3825 (set_attr "unit" "*,i387,*") 3826 (set_attr "mode" "SF")]) 3827 3828(define_insn "*truncdfsf_i387" 3829 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r") 3830 (float_truncate:SF 3831 (match_operand:DF 1 "nonimmediate_operand" "f,f"))) 3832 (clobber (match_operand:SF 2 "memory_operand" "=X,m"))] 3833 "TARGET_80387" 3834{ 3835 switch (which_alternative) 3836 { 3837 case 0: 3838 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3839 return "fstp%z0\t%y0"; 3840 else 3841 return "fst%z0\t%y0"; 3842 case 1: 3843 return "#"; 3844 default: 3845 gcc_unreachable (); 3846 } 3847} 3848 [(set_attr "type" "fmov,multi") 3849 (set_attr "unit" "*,i387") 3850 (set_attr "mode" "SF")]) 3851 3852(define_insn "*truncdfsf2_i387_1" 3853 [(set (match_operand:SF 0 "memory_operand" "=m") 3854 (float_truncate:SF 3855 (match_operand:DF 1 "register_operand" "f")))] 3856 "TARGET_80387 3857 && !(TARGET_SSE2 && TARGET_SSE_MATH) 3858 && !TARGET_MIX_SSE_I387" 3859{ 3860 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3861 return "fstp%z0\t%y0"; 3862 else 3863 return "fst%z0\t%y0"; 3864} 3865 [(set_attr "type" "fmov") 3866 (set_attr "mode" "SF")]) 3867 3868(define_split 3869 [(set (match_operand:SF 0 "register_operand" "") 3870 (float_truncate:SF 3871 (match_operand:DF 1 "fp_register_operand" ""))) 3872 (clobber (match_operand 2 "" ""))] 3873 "reload_completed" 3874 [(set (match_dup 2) (match_dup 1)) 3875 (set (match_dup 0) (match_dup 2))] 3876{ 3877 operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1])); 3878}) 3879 3880;; Conversion from XFmode to SFmode. 3881 3882(define_expand "truncxfsf2" 3883 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "") 3884 (float_truncate:SF 3885 (match_operand:XF 1 "register_operand" ""))) 3886 (clobber (match_dup 2))])] 3887 "TARGET_80387" 3888{ 3889 if (flag_unsafe_math_optimizations) 3890 { 3891 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SFmode); 3892 emit_insn (gen_truncxfsf2_i387_noop (reg, operands[1])); 3893 if (reg != operands[0]) 3894 emit_move_insn (operands[0], reg); 3895 DONE; 3896 } 3897 else 3898 operands[2] = assign_386_stack_local (SFmode, SLOT_VIRTUAL); 3899}) 3900 3901(define_insn "*truncxfsf2_mixed" 3902 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?r,?x") 3903 (float_truncate:SF 3904 (match_operand:XF 1 "register_operand" "f,f,f,f"))) 3905 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))] 3906 "TARGET_MIX_SSE_I387" 3907{ 3908 gcc_assert (!which_alternative); 3909 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3910 return "fstp%z0\t%y0"; 3911 else 3912 return "fst%z0\t%y0"; 3913} 3914 [(set_attr "type" "fmov,multi,multi,multi") 3915 (set_attr "unit" "*,i387,i387,i387") 3916 (set_attr "mode" "SF")]) 3917 3918(define_insn "truncxfsf2_i387_noop" 3919 [(set (match_operand:SF 0 "register_operand" "=f") 3920 (float_truncate:SF (match_operand:XF 1 "register_operand" "f")))] 3921 "TARGET_80387 && flag_unsafe_math_optimizations" 3922{ 3923 return output_387_reg_move (insn, operands); 3924} 3925 [(set_attr "type" "fmov") 3926 (set_attr "mode" "SF")]) 3927 3928(define_insn "*truncxfsf2_i387" 3929 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?r") 3930 (float_truncate:SF 3931 (match_operand:XF 1 "register_operand" "f,f,f"))) 3932 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m"))] 3933 "TARGET_80387" 3934{ 3935 gcc_assert (!which_alternative); 3936 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3937 return "fstp%z0\t%y0"; 3938 else 3939 return "fst%z0\t%y0"; 3940} 3941 [(set_attr "type" "fmov,multi,multi") 3942 (set_attr "unit" "*,i387,i387") 3943 (set_attr "mode" "SF")]) 3944 3945(define_insn "*truncxfsf2_i387_1" 3946 [(set (match_operand:SF 0 "memory_operand" "=m") 3947 (float_truncate:SF 3948 (match_operand:XF 1 "register_operand" "f")))] 3949 "TARGET_80387" 3950{ 3951 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 3952 return "fstp%z0\t%y0"; 3953 else 3954 return "fst%z0\t%y0"; 3955} 3956 [(set_attr "type" "fmov") 3957 (set_attr "mode" "SF")]) 3958 3959(define_split 3960 [(set (match_operand:SF 0 "register_operand" "") 3961 (float_truncate:SF 3962 (match_operand:XF 1 "register_operand" ""))) 3963 (clobber (match_operand:SF 2 "memory_operand" ""))] 3964 "TARGET_80387 && reload_completed" 3965 [(set (match_dup 2) (float_truncate:SF (match_dup 1))) 3966 (set (match_dup 0) (match_dup 2))] 3967 "") 3968 3969(define_split 3970 [(set (match_operand:SF 0 "memory_operand" "") 3971 (float_truncate:SF 3972 (match_operand:XF 1 "register_operand" ""))) 3973 (clobber (match_operand:SF 2 "memory_operand" ""))] 3974 "TARGET_80387" 3975 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))] 3976 "") 3977 3978;; Conversion from XFmode to DFmode. 3979 3980(define_expand "truncxfdf2" 3981 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "") 3982 (float_truncate:DF 3983 (match_operand:XF 1 "register_operand" ""))) 3984 (clobber (match_dup 2))])] 3985 "TARGET_80387" 3986{ 3987 if (flag_unsafe_math_optimizations) 3988 { 3989 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DFmode); 3990 emit_insn (gen_truncxfdf2_i387_noop (reg, operands[1])); 3991 if (reg != operands[0]) 3992 emit_move_insn (operands[0], reg); 3993 DONE; 3994 } 3995 else 3996 operands[2] = assign_386_stack_local (DFmode, SLOT_VIRTUAL); 3997}) 3998 3999(define_insn "*truncxfdf2_mixed" 4000 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?r,?Y") 4001 (float_truncate:DF 4002 (match_operand:XF 1 "register_operand" "f,f,f,f"))) 4003 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))] 4004 "TARGET_SSE2 && TARGET_MIX_SSE_I387" 4005{ 4006 gcc_assert (!which_alternative); 4007 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 4008 return "fstp%z0\t%y0"; 4009 else 4010 return "fst%z0\t%y0"; 4011} 4012 [(set_attr "type" "fmov,multi,multi,multi") 4013 (set_attr "unit" "*,i387,i387,i387") 4014 (set_attr "mode" "DF")]) 4015 4016(define_insn "truncxfdf2_i387_noop" 4017 [(set (match_operand:DF 0 "register_operand" "=f") 4018 (float_truncate:DF (match_operand:XF 1 "register_operand" "f")))] 4019 "TARGET_80387 && flag_unsafe_math_optimizations" 4020{ 4021 return output_387_reg_move (insn, operands); 4022} 4023 [(set_attr "type" "fmov") 4024 (set_attr "mode" "DF")]) 4025 4026(define_insn "*truncxfdf2_i387" 4027 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?r") 4028 (float_truncate:DF 4029 (match_operand:XF 1 "register_operand" "f,f,f"))) 4030 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m"))] 4031 "TARGET_80387" 4032{ 4033 gcc_assert (!which_alternative); 4034 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 4035 return "fstp%z0\t%y0"; 4036 else 4037 return "fst%z0\t%y0"; 4038} 4039 [(set_attr "type" "fmov,multi,multi") 4040 (set_attr "unit" "*,i387,i387") 4041 (set_attr "mode" "DF")]) 4042 4043(define_insn "*truncxfdf2_i387_1" 4044 [(set (match_operand:DF 0 "memory_operand" "=m") 4045 (float_truncate:DF 4046 (match_operand:XF 1 "register_operand" "f")))] 4047 "TARGET_80387" 4048{ 4049 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1]))) 4050 return "fstp%z0\t%y0"; 4051 else 4052 return "fst%z0\t%y0"; 4053} 4054 [(set_attr "type" "fmov") 4055 (set_attr "mode" "DF")]) 4056 4057(define_split 4058 [(set (match_operand:DF 0 "register_operand" "") 4059 (float_truncate:DF 4060 (match_operand:XF 1 "register_operand" ""))) 4061 (clobber (match_operand:DF 2 "memory_operand" ""))] 4062 "TARGET_80387 && reload_completed" 4063 [(set (match_dup 2) (float_truncate:DF (match_dup 1))) 4064 (set (match_dup 0) (match_dup 2))] 4065 "") 4066 4067(define_split 4068 [(set (match_operand:DF 0 "memory_operand" "") 4069 (float_truncate:DF 4070 (match_operand:XF 1 "register_operand" ""))) 4071 (clobber (match_operand:DF 2 "memory_operand" ""))] 4072 "TARGET_80387" 4073 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))] 4074 "") 4075 4076;; Signed conversion to DImode. 4077 4078(define_expand "fix_truncxfdi2" 4079 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "") 4080 (fix:DI (match_operand:XF 1 "register_operand" ""))) 4081 (clobber (reg:CC FLAGS_REG))])] 4082 "TARGET_80387" 4083{ 4084 if (TARGET_FISTTP) 4085 { 4086 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1])); 4087 DONE; 4088 } 4089}) 4090 4091(define_expand "fix_trunc<mode>di2" 4092 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "") 4093 (fix:DI (match_operand:SSEMODEF 1 "register_operand" ""))) 4094 (clobber (reg:CC FLAGS_REG))])] 4095 "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))" 4096{ 4097 if (TARGET_FISTTP 4098 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)) 4099 { 4100 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1])); 4101 DONE; 4102 } 4103 if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)) 4104 { 4105 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode); 4106 emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1])); 4107 if (out != operands[0]) 4108 emit_move_insn (operands[0], out); 4109 DONE; 4110 } 4111}) 4112 4113;; Signed conversion to SImode. 4114 4115(define_expand "fix_truncxfsi2" 4116 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") 4117 (fix:SI (match_operand:XF 1 "register_operand" ""))) 4118 (clobber (reg:CC FLAGS_REG))])] 4119 "TARGET_80387" 4120{ 4121 if (TARGET_FISTTP) 4122 { 4123 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1])); 4124 DONE; 4125 } 4126}) 4127 4128(define_expand "fix_trunc<mode>si2" 4129 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") 4130 (fix:SI (match_operand:SSEMODEF 1 "register_operand" ""))) 4131 (clobber (reg:CC FLAGS_REG))])] 4132 "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)" 4133{ 4134 if (TARGET_FISTTP 4135 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)) 4136 { 4137 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1])); 4138 DONE; 4139 } 4140 if (SSE_FLOAT_MODE_P (<MODE>mode)) 4141 { 4142 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode); 4143 emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1])); 4144 if (out != operands[0]) 4145 emit_move_insn (operands[0], out); 4146 DONE; 4147 } 4148}) 4149 4150;; Signed conversion to HImode. 4151 4152(define_expand "fix_trunc<mode>hi2" 4153 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "") 4154 (fix:HI (match_operand:X87MODEF 1 "register_operand" ""))) 4155 (clobber (reg:CC FLAGS_REG))])] 4156 "TARGET_80387 4157 && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))" 4158{ 4159 if (TARGET_FISTTP) 4160 { 4161 emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1])); 4162 DONE; 4163 } 4164}) 4165 4166;; When SSE is available, it is always faster to use it! 4167(define_insn "fix_truncsfdi_sse" 4168 [(set (match_operand:DI 0 "register_operand" "=r,r") 4169 (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))] 4170 "TARGET_64BIT && TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)" 4171 "cvttss2si{q}\t{%1, %0|%0, %1}" 4172 [(set_attr "type" "sseicvt") 4173 (set_attr "mode" "SF") 4174 (set_attr "athlon_decode" "double,vector") 4175 (set_attr "amdfam10_decode" "double,double")]) 4176 4177(define_insn "fix_truncdfdi_sse" 4178 [(set (match_operand:DI 0 "register_operand" "=r,r") 4179 (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))] 4180 "TARGET_64BIT && TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)" 4181 "cvttsd2si{q}\t{%1, %0|%0, %1}" 4182 [(set_attr "type" "sseicvt") 4183 (set_attr "mode" "DF") 4184 (set_attr "athlon_decode" "double,vector") 4185 (set_attr "amdfam10_decode" "double,double")]) 4186 4187(define_insn "fix_truncsfsi_sse" 4188 [(set (match_operand:SI 0 "register_operand" "=r,r") 4189 (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))] 4190 "TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)" 4191 "cvttss2si\t{%1, %0|%0, %1}" 4192 [(set_attr "type" "sseicvt") 4193 (set_attr "mode" "DF") 4194 (set_attr "athlon_decode" "double,vector") 4195 (set_attr "amdfam10_decode" "double,double")]) 4196 4197(define_insn "fix_truncdfsi_sse" 4198 [(set (match_operand:SI 0 "register_operand" "=r,r") 4199 (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))] 4200 "TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)" 4201 "cvttsd2si\t{%1, %0|%0, %1}" 4202 [(set_attr "type" "sseicvt") 4203 (set_attr "mode" "DF") 4204 (set_attr "athlon_decode" "double,vector") 4205 (set_attr "amdfam10_decode" "double,double")]) 4206 4207;; Avoid vector decoded forms of the instruction. 4208(define_peephole2 4209 [(match_scratch:DF 2 "Y") 4210 (set (match_operand:SSEMODEI24 0 "register_operand" "") 4211 (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))] 4212 "(TARGET_K8 || TARGET_GENERIC64) && !optimize_size" 4213 [(set (match_dup 2) (match_dup 1)) 4214 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))] 4215 "") 4216 4217(define_peephole2 4218 [(match_scratch:SF 2 "x") 4219 (set (match_operand:SSEMODEI24 0 "register_operand" "") 4220 (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))] 4221 "(TARGET_K8 || TARGET_GENERIC64) && !optimize_size" 4222 [(set (match_dup 2) (match_dup 1)) 4223 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))] 4224 "") 4225 4226(define_insn_and_split "fix_trunc<mode>_fisttp_i387_1" 4227 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r") 4228 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))] 4229 "TARGET_FISTTP 4230 && FLOAT_MODE_P (GET_MODE (operands[1])) 4231 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 4232 && (TARGET_64BIT || <MODE>mode != DImode)) 4233 && TARGET_SSE_MATH) 4234 && !(reload_completed || reload_in_progress)" 4235 "#" 4236 "&& 1" 4237 [(const_int 0)] 4238{ 4239 if (memory_operand (operands[0], VOIDmode)) 4240 emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1])); 4241 else 4242 { 4243 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP); 4244 emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0], 4245 operands[1], 4246 operands[2])); 4247 } 4248 DONE; 4249} 4250 [(set_attr "type" "fisttp") 4251 (set_attr "mode" "<MODE>")]) 4252 4253(define_insn "fix_trunc<mode>_i387_fisttp" 4254 [(set (match_operand:X87MODEI 0 "memory_operand" "=m") 4255 (fix:X87MODEI (match_operand 1 "register_operand" "f"))) 4256 (clobber (match_scratch:XF 2 "=&1f"))] 4257 "TARGET_FISTTP 4258 && FLOAT_MODE_P (GET_MODE (operands[1])) 4259 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 4260 && (TARGET_64BIT || <MODE>mode != DImode)) 4261 && TARGET_SSE_MATH)" 4262 "* return output_fix_trunc (insn, operands, 1);" 4263 [(set_attr "type" "fisttp") 4264 (set_attr "mode" "<MODE>")]) 4265 4266(define_insn "fix_trunc<mode>_i387_fisttp_with_temp" 4267 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r") 4268 (fix:X87MODEI (match_operand 1 "register_operand" "f,f"))) 4269 (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m")) 4270 (clobber (match_scratch:XF 3 "=&1f,&1f"))] 4271 "TARGET_FISTTP 4272 && FLOAT_MODE_P (GET_MODE (operands[1])) 4273 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 4274 && (TARGET_64BIT || <MODE>mode != DImode)) 4275 && TARGET_SSE_MATH)" 4276 "#" 4277 [(set_attr "type" "fisttp") 4278 (set_attr "mode" "<MODE>")]) 4279 4280(define_split 4281 [(set (match_operand:X87MODEI 0 "register_operand" "") 4282 (fix:X87MODEI (match_operand 1 "register_operand" ""))) 4283 (clobber (match_operand:X87MODEI 2 "memory_operand" "")) 4284 (clobber (match_scratch 3 ""))] 4285 "reload_completed" 4286 [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1))) 4287 (clobber (match_dup 3))]) 4288 (set (match_dup 0) (match_dup 2))] 4289 "") 4290 4291(define_split 4292 [(set (match_operand:X87MODEI 0 "memory_operand" "") 4293 (fix:X87MODEI (match_operand 1 "register_operand" ""))) 4294 (clobber (match_operand:X87MODEI 2 "memory_operand" "")) 4295 (clobber (match_scratch 3 ""))] 4296 "reload_completed" 4297 [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1))) 4298 (clobber (match_dup 3))])] 4299 "") 4300 4301;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description 4302;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control 4303;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG 4304;; clobbering insns can be used. Look at emit_i387_cw_initialization () 4305;; function in i386.c. 4306(define_insn_and_split "*fix_trunc<mode>_i387_1" 4307 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r") 4308 (fix:X87MODEI (match_operand 1 "register_operand" "f,f"))) 4309 (clobber (reg:CC FLAGS_REG))] 4310 "TARGET_80387 && !TARGET_FISTTP 4311 && FLOAT_MODE_P (GET_MODE (operands[1])) 4312 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 4313 && (TARGET_64BIT || <MODE>mode != DImode)) 4314 && !(reload_completed || reload_in_progress)" 4315 "#" 4316 "&& 1" 4317 [(const_int 0)] 4318{ 4319 ix86_optimize_mode_switching[I387_TRUNC] = 1; 4320 4321 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 4322 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC); 4323 if (memory_operand (operands[0], VOIDmode)) 4324 emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1], 4325 operands[2], operands[3])); 4326 else 4327 { 4328 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP); 4329 emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1], 4330 operands[2], operands[3], 4331 operands[4])); 4332 } 4333 DONE; 4334} 4335 [(set_attr "type" "fistp") 4336 (set_attr "i387_cw" "trunc") 4337 (set_attr "mode" "<MODE>")]) 4338 4339(define_insn "fix_truncdi_i387" 4340 [(set (match_operand:DI 0 "memory_operand" "=m") 4341 (fix:DI (match_operand 1 "register_operand" "f"))) 4342 (use (match_operand:HI 2 "memory_operand" "m")) 4343 (use (match_operand:HI 3 "memory_operand" "m")) 4344 (clobber (match_scratch:XF 4 "=&1f"))] 4345 "TARGET_80387 && !TARGET_FISTTP 4346 && FLOAT_MODE_P (GET_MODE (operands[1])) 4347 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))" 4348 "* return output_fix_trunc (insn, operands, 0);" 4349 [(set_attr "type" "fistp") 4350 (set_attr "i387_cw" "trunc") 4351 (set_attr "mode" "DI")]) 4352 4353(define_insn "fix_truncdi_i387_with_temp" 4354 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r") 4355 (fix:DI (match_operand 1 "register_operand" "f,f"))) 4356 (use (match_operand:HI 2 "memory_operand" "m,m")) 4357 (use (match_operand:HI 3 "memory_operand" "m,m")) 4358 (clobber (match_operand:DI 4 "memory_operand" "=m,m")) 4359 (clobber (match_scratch:XF 5 "=&1f,&1f"))] 4360 "TARGET_80387 && !TARGET_FISTTP 4361 && FLOAT_MODE_P (GET_MODE (operands[1])) 4362 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))" 4363 "#" 4364 [(set_attr "type" "fistp") 4365 (set_attr "i387_cw" "trunc") 4366 (set_attr "mode" "DI")]) 4367 4368(define_split 4369 [(set (match_operand:DI 0 "register_operand" "") 4370 (fix:DI (match_operand 1 "register_operand" ""))) 4371 (use (match_operand:HI 2 "memory_operand" "")) 4372 (use (match_operand:HI 3 "memory_operand" "")) 4373 (clobber (match_operand:DI 4 "memory_operand" "")) 4374 (clobber (match_scratch 5 ""))] 4375 "reload_completed" 4376 [(parallel [(set (match_dup 4) (fix:DI (match_dup 1))) 4377 (use (match_dup 2)) 4378 (use (match_dup 3)) 4379 (clobber (match_dup 5))]) 4380 (set (match_dup 0) (match_dup 4))] 4381 "") 4382 4383(define_split 4384 [(set (match_operand:DI 0 "memory_operand" "") 4385 (fix:DI (match_operand 1 "register_operand" ""))) 4386 (use (match_operand:HI 2 "memory_operand" "")) 4387 (use (match_operand:HI 3 "memory_operand" "")) 4388 (clobber (match_operand:DI 4 "memory_operand" "")) 4389 (clobber (match_scratch 5 ""))] 4390 "reload_completed" 4391 [(parallel [(set (match_dup 0) (fix:DI (match_dup 1))) 4392 (use (match_dup 2)) 4393 (use (match_dup 3)) 4394 (clobber (match_dup 5))])] 4395 "") 4396 4397(define_insn "fix_trunc<mode>_i387" 4398 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m") 4399 (fix:X87MODEI12 (match_operand 1 "register_operand" "f"))) 4400 (use (match_operand:HI 2 "memory_operand" "m")) 4401 (use (match_operand:HI 3 "memory_operand" "m"))] 4402 "TARGET_80387 && !TARGET_FISTTP 4403 && FLOAT_MODE_P (GET_MODE (operands[1])) 4404 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))" 4405 "* return output_fix_trunc (insn, operands, 0);" 4406 [(set_attr "type" "fistp") 4407 (set_attr "i387_cw" "trunc") 4408 (set_attr "mode" "<MODE>")]) 4409 4410(define_insn "fix_trunc<mode>_i387_with_temp" 4411 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r") 4412 (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f"))) 4413 (use (match_operand:HI 2 "memory_operand" "m,m")) 4414 (use (match_operand:HI 3 "memory_operand" "m,m")) 4415 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))] 4416 "TARGET_80387 && !TARGET_FISTTP 4417 && FLOAT_MODE_P (GET_MODE (operands[1])) 4418 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))" 4419 "#" 4420 [(set_attr "type" "fistp") 4421 (set_attr "i387_cw" "trunc") 4422 (set_attr "mode" "<MODE>")]) 4423 4424(define_split 4425 [(set (match_operand:X87MODEI12 0 "register_operand" "") 4426 (fix:X87MODEI12 (match_operand 1 "register_operand" ""))) 4427 (use (match_operand:HI 2 "memory_operand" "")) 4428 (use (match_operand:HI 3 "memory_operand" "")) 4429 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 4430 "reload_completed" 4431 [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1))) 4432 (use (match_dup 2)) 4433 (use (match_dup 3))]) 4434 (set (match_dup 0) (match_dup 4))] 4435 "") 4436 4437(define_split 4438 [(set (match_operand:X87MODEI12 0 "memory_operand" "") 4439 (fix:X87MODEI12 (match_operand 1 "register_operand" ""))) 4440 (use (match_operand:HI 2 "memory_operand" "")) 4441 (use (match_operand:HI 3 "memory_operand" "")) 4442 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 4443 "reload_completed" 4444 [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1))) 4445 (use (match_dup 2)) 4446 (use (match_dup 3))])] 4447 "") 4448 4449(define_insn "x86_fnstcw_1" 4450 [(set (match_operand:HI 0 "memory_operand" "=m") 4451 (unspec:HI [(reg:HI FPSR_REG)] UNSPEC_FSTCW))] 4452 "TARGET_80387" 4453 "fnstcw\t%0" 4454 [(set_attr "length" "2") 4455 (set_attr "mode" "HI") 4456 (set_attr "unit" "i387")]) 4457 4458(define_insn "x86_fldcw_1" 4459 [(set (reg:HI FPSR_REG) 4460 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))] 4461 "TARGET_80387" 4462 "fldcw\t%0" 4463 [(set_attr "length" "2") 4464 (set_attr "mode" "HI") 4465 (set_attr "unit" "i387") 4466 (set_attr "athlon_decode" "vector") 4467 (set_attr "amdfam10_decode" "vector")]) 4468 4469;; Conversion between fixed point and floating point. 4470 4471;; Even though we only accept memory inputs, the backend _really_ 4472;; wants to be able to do this between registers. 4473 4474(define_expand "floathisf2" 4475 [(set (match_operand:SF 0 "register_operand" "") 4476 (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))] 4477 "TARGET_80387 || TARGET_SSE_MATH" 4478{ 4479 if (TARGET_SSE_MATH) 4480 { 4481 emit_insn (gen_floatsisf2 (operands[0], 4482 convert_to_mode (SImode, operands[1], 0))); 4483 DONE; 4484 } 4485}) 4486 4487(define_insn "*floathisf2_i387" 4488 [(set (match_operand:SF 0 "register_operand" "=f,f") 4489 (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))] 4490 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)" 4491 "@ 4492 fild%z1\t%1 4493 #" 4494 [(set_attr "type" "fmov,multi") 4495 (set_attr "mode" "SF") 4496 (set_attr "unit" "*,i387") 4497 (set_attr "fp_int_src" "true")]) 4498 4499(define_expand "floatsisf2" 4500 [(set (match_operand:SF 0 "register_operand" "") 4501 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))] 4502 "TARGET_80387 || TARGET_SSE_MATH" 4503 "") 4504 4505(define_insn "*floatsisf2_mixed" 4506 [(set (match_operand:SF 0 "register_operand" "=f,?f,x,x") 4507 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))] 4508 "TARGET_MIX_SSE_I387" 4509 "@ 4510 fild%z1\t%1 4511 # 4512 cvtsi2ss\t{%1, %0|%0, %1} 4513 cvtsi2ss\t{%1, %0|%0, %1}" 4514 [(set_attr "type" "fmov,multi,sseicvt,sseicvt") 4515 (set_attr "mode" "SF") 4516 (set_attr "unit" "*,i387,*,*") 4517 (set_attr "athlon_decode" "*,*,vector,double") 4518 (set_attr "amdfam10_decode" "*,*,vector,double") 4519 (set_attr "fp_int_src" "true")]) 4520 4521(define_insn "*floatsisf2_sse" 4522 [(set (match_operand:SF 0 "register_operand" "=x,x") 4523 (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))] 4524 "TARGET_SSE_MATH" 4525 "cvtsi2ss\t{%1, %0|%0, %1}" 4526 [(set_attr "type" "sseicvt") 4527 (set_attr "mode" "SF") 4528 (set_attr "athlon_decode" "vector,double") 4529 (set_attr "amdfam10_decode" "vector,double") 4530 (set_attr "fp_int_src" "true")]) 4531 4532(define_insn "*floatsisf2_i387" 4533 [(set (match_operand:SF 0 "register_operand" "=f,f") 4534 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))] 4535 "TARGET_80387" 4536 "@ 4537 fild%z1\t%1 4538 #" 4539 [(set_attr "type" "fmov,multi") 4540 (set_attr "mode" "SF") 4541 (set_attr "unit" "*,i387") 4542 (set_attr "fp_int_src" "true")]) 4543 4544(define_expand "floatdisf2" 4545 [(set (match_operand:SF 0 "register_operand" "") 4546 (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))] 4547 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)" 4548 "") 4549 4550(define_insn "*floatdisf2_mixed" 4551 [(set (match_operand:SF 0 "register_operand" "=f,?f,x,x") 4552 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))] 4553 "TARGET_64BIT && TARGET_MIX_SSE_I387" 4554 "@ 4555 fild%z1\t%1 4556 # 4557 cvtsi2ss{q}\t{%1, %0|%0, %1} 4558 cvtsi2ss{q}\t{%1, %0|%0, %1}" 4559 [(set_attr "type" "fmov,multi,sseicvt,sseicvt") 4560 (set_attr "mode" "SF") 4561 (set_attr "unit" "*,i387,*,*") 4562 (set_attr "athlon_decode" "*,*,vector,double") 4563 (set_attr "amdfam10_decode" "*,*,vector,double") 4564 (set_attr "fp_int_src" "true")]) 4565 4566(define_insn "*floatdisf2_sse" 4567 [(set (match_operand:SF 0 "register_operand" "=x,x") 4568 (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))] 4569 "TARGET_64BIT && TARGET_SSE_MATH" 4570 "cvtsi2ss{q}\t{%1, %0|%0, %1}" 4571 [(set_attr "type" "sseicvt") 4572 (set_attr "mode" "SF") 4573 (set_attr "athlon_decode" "vector,double") 4574 (set_attr "amdfam10_decode" "vector,double") 4575 (set_attr "fp_int_src" "true")]) 4576 4577(define_insn "*floatdisf2_i387" 4578 [(set (match_operand:SF 0 "register_operand" "=f,f") 4579 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))] 4580 "TARGET_80387" 4581 "@ 4582 fild%z1\t%1 4583 #" 4584 [(set_attr "type" "fmov,multi") 4585 (set_attr "mode" "SF") 4586 (set_attr "unit" "*,i387") 4587 (set_attr "fp_int_src" "true")]) 4588 4589(define_expand "floathidf2" 4590 [(set (match_operand:DF 0 "register_operand" "") 4591 (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))] 4592 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 4593{ 4594 if (TARGET_SSE2 && TARGET_SSE_MATH) 4595 { 4596 emit_insn (gen_floatsidf2 (operands[0], 4597 convert_to_mode (SImode, operands[1], 0))); 4598 DONE; 4599 } 4600}) 4601 4602(define_insn "*floathidf2_i387" 4603 [(set (match_operand:DF 0 "register_operand" "=f,f") 4604 (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))] 4605 "TARGET_80387 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)" 4606 "@ 4607 fild%z1\t%1 4608 #" 4609 [(set_attr "type" "fmov,multi") 4610 (set_attr "mode" "DF") 4611 (set_attr "unit" "*,i387") 4612 (set_attr "fp_int_src" "true")]) 4613 4614(define_expand "floatsidf2" 4615 [(set (match_operand:DF 0 "register_operand" "") 4616 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))] 4617 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 4618 "") 4619 4620(define_insn "*floatsidf2_mixed" 4621 [(set (match_operand:DF 0 "register_operand" "=f,?f,Y,Y") 4622 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))] 4623 "TARGET_SSE2 && TARGET_MIX_SSE_I387" 4624 "@ 4625 fild%z1\t%1 4626 # 4627 cvtsi2sd\t{%1, %0|%0, %1} 4628 cvtsi2sd\t{%1, %0|%0, %1}" 4629 [(set_attr "type" "fmov,multi,sseicvt,sseicvt") 4630 (set_attr "mode" "DF") 4631 (set_attr "unit" "*,i387,*,*") 4632 (set_attr "athlon_decode" "*,*,double,direct") 4633 (set_attr "amdfam10_decode" "*,*,vector,double") 4634 (set_attr "fp_int_src" "true")]) 4635 4636(define_insn "*floatsidf2_sse" 4637 [(set (match_operand:DF 0 "register_operand" "=Y,Y") 4638 (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))] 4639 "TARGET_SSE2 && TARGET_SSE_MATH" 4640 "cvtsi2sd\t{%1, %0|%0, %1}" 4641 [(set_attr "type" "sseicvt") 4642 (set_attr "mode" "DF") 4643 (set_attr "athlon_decode" "double,direct") 4644 (set_attr "amdfam10_decode" "vector,double") 4645 (set_attr "fp_int_src" "true")]) 4646 4647(define_insn "*floatsidf2_i387" 4648 [(set (match_operand:DF 0 "register_operand" "=f,f") 4649 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))] 4650 "TARGET_80387" 4651 "@ 4652 fild%z1\t%1 4653 #" 4654 [(set_attr "type" "fmov,multi") 4655 (set_attr "mode" "DF") 4656 (set_attr "unit" "*,i387") 4657 (set_attr "fp_int_src" "true")]) 4658 4659(define_expand "floatdidf2" 4660 [(set (match_operand:DF 0 "register_operand" "") 4661 (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))] 4662 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)" 4663 "") 4664 4665(define_insn "*floatdidf2_mixed" 4666 [(set (match_operand:DF 0 "register_operand" "=f,?f,Y,Y") 4667 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))] 4668 "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387" 4669 "@ 4670 fild%z1\t%1 4671 # 4672 cvtsi2sd{q}\t{%1, %0|%0, %1} 4673 cvtsi2sd{q}\t{%1, %0|%0, %1}" 4674 [(set_attr "type" "fmov,multi,sseicvt,sseicvt") 4675 (set_attr "mode" "DF") 4676 (set_attr "unit" "*,i387,*,*") 4677 (set_attr "athlon_decode" "*,*,double,direct") 4678 (set_attr "amdfam10_decode" "*,*,vector,double") 4679 (set_attr "fp_int_src" "true")]) 4680 4681(define_insn "*floatdidf2_sse" 4682 [(set (match_operand:DF 0 "register_operand" "=Y,Y") 4683 (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))] 4684 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH" 4685 "cvtsi2sd{q}\t{%1, %0|%0, %1}" 4686 [(set_attr "type" "sseicvt") 4687 (set_attr "mode" "DF") 4688 (set_attr "athlon_decode" "double,direct") 4689 (set_attr "amdfam10_decode" "vector,double") 4690 (set_attr "fp_int_src" "true")]) 4691 4692(define_insn "*floatdidf2_i387" 4693 [(set (match_operand:DF 0 "register_operand" "=f,f") 4694 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))] 4695 "TARGET_80387" 4696 "@ 4697 fild%z1\t%1 4698 #" 4699 [(set_attr "type" "fmov,multi") 4700 (set_attr "mode" "DF") 4701 (set_attr "unit" "*,i387") 4702 (set_attr "fp_int_src" "true")]) 4703 4704(define_insn "floathixf2" 4705 [(set (match_operand:XF 0 "register_operand" "=f,f") 4706 (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))] 4707 "TARGET_80387" 4708 "@ 4709 fild%z1\t%1 4710 #" 4711 [(set_attr "type" "fmov,multi") 4712 (set_attr "mode" "XF") 4713 (set_attr "unit" "*,i387") 4714 (set_attr "fp_int_src" "true")]) 4715 4716(define_insn "floatsixf2" 4717 [(set (match_operand:XF 0 "register_operand" "=f,f") 4718 (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))] 4719 "TARGET_80387" 4720 "@ 4721 fild%z1\t%1 4722 #" 4723 [(set_attr "type" "fmov,multi") 4724 (set_attr "mode" "XF") 4725 (set_attr "unit" "*,i387") 4726 (set_attr "fp_int_src" "true")]) 4727 4728(define_insn "floatdixf2" 4729 [(set (match_operand:XF 0 "register_operand" "=f,f") 4730 (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))] 4731 "TARGET_80387" 4732 "@ 4733 fild%z1\t%1 4734 #" 4735 [(set_attr "type" "fmov,multi") 4736 (set_attr "mode" "XF") 4737 (set_attr "unit" "*,i387") 4738 (set_attr "fp_int_src" "true")]) 4739 4740;; %%% Kill these when reload knows how to do it. 4741(define_split 4742 [(set (match_operand 0 "fp_register_operand" "") 4743 (float (match_operand 1 "register_operand" "")))] 4744 "reload_completed 4745 && TARGET_80387 4746 && FLOAT_MODE_P (GET_MODE (operands[0]))" 4747 [(const_int 0)] 4748{ 4749 operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]); 4750 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]); 4751 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2])); 4752 ix86_free_from_memory (GET_MODE (operands[1])); 4753 DONE; 4754}) 4755 4756(define_expand "floatunssisf2" 4757 [(use (match_operand:SF 0 "register_operand" "")) 4758 (use (match_operand:SI 1 "register_operand" ""))] 4759 "!TARGET_64BIT && TARGET_SSE_MATH" 4760 "x86_emit_floatuns (operands); DONE;") 4761 4762(define_expand "floatunsdisf2" 4763 [(use (match_operand:SF 0 "register_operand" "")) 4764 (use (match_operand:DI 1 "register_operand" ""))] 4765 "TARGET_64BIT && TARGET_SSE_MATH" 4766 "x86_emit_floatuns (operands); DONE;") 4767 4768(define_expand "floatunsdidf2" 4769 [(use (match_operand:DF 0 "register_operand" "")) 4770 (use (match_operand:DI 1 "register_operand" ""))] 4771 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH" 4772 "x86_emit_floatuns (operands); DONE;") 4773 4774;; SSE extract/set expanders 4775 4776 4777;; Add instructions 4778 4779;; %%% splits for addditi3 4780 4781(define_expand "addti3" 4782 [(set (match_operand:TI 0 "nonimmediate_operand" "") 4783 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "") 4784 (match_operand:TI 2 "x86_64_general_operand" ""))) 4785 (clobber (reg:CC FLAGS_REG))] 4786 "TARGET_64BIT" 4787 "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;") 4788 4789(define_insn "*addti3_1" 4790 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o") 4791 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0") 4792 (match_operand:TI 2 "x86_64_general_operand" "roe,re"))) 4793 (clobber (reg:CC FLAGS_REG))] 4794 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)" 4795 "#") 4796 4797(define_split 4798 [(set (match_operand:TI 0 "nonimmediate_operand" "") 4799 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "") 4800 (match_operand:TI 2 "x86_64_general_operand" ""))) 4801 (clobber (reg:CC FLAGS_REG))] 4802 "TARGET_64BIT && reload_completed" 4803 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)] 4804 UNSPEC_ADD_CARRY)) 4805 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]) 4806 (parallel [(set (match_dup 3) 4807 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0)) 4808 (match_dup 4)) 4809 (match_dup 5))) 4810 (clobber (reg:CC FLAGS_REG))])] 4811 "split_ti (operands+0, 1, operands+0, operands+3); 4812 split_ti (operands+1, 1, operands+1, operands+4); 4813 split_ti (operands+2, 1, operands+2, operands+5);") 4814 4815;; %%% splits for addsidi3 4816; [(set (match_operand:DI 0 "nonimmediate_operand" "") 4817; (plus:DI (match_operand:DI 1 "general_operand" "") 4818; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))] 4819 4820(define_expand "adddi3" 4821 [(set (match_operand:DI 0 "nonimmediate_operand" "") 4822 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "") 4823 (match_operand:DI 2 "x86_64_general_operand" ""))) 4824 (clobber (reg:CC FLAGS_REG))] 4825 "" 4826 "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;") 4827 4828(define_insn "*adddi3_1" 4829 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o") 4830 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 4831 (match_operand:DI 2 "general_operand" "roiF,riF"))) 4832 (clobber (reg:CC FLAGS_REG))] 4833 "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)" 4834 "#") 4835 4836(define_split 4837 [(set (match_operand:DI 0 "nonimmediate_operand" "") 4838 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "") 4839 (match_operand:DI 2 "general_operand" ""))) 4840 (clobber (reg:CC FLAGS_REG))] 4841 "!TARGET_64BIT && reload_completed" 4842 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)] 4843 UNSPEC_ADD_CARRY)) 4844 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]) 4845 (parallel [(set (match_dup 3) 4846 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0)) 4847 (match_dup 4)) 4848 (match_dup 5))) 4849 (clobber (reg:CC FLAGS_REG))])] 4850 "split_di (operands+0, 1, operands+0, operands+3); 4851 split_di (operands+1, 1, operands+1, operands+4); 4852 split_di (operands+2, 1, operands+2, operands+5);") 4853 4854(define_insn "adddi3_carry_rex64" 4855 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 4856 (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "") 4857 (match_operand:DI 1 "nonimmediate_operand" "%0,0")) 4858 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))) 4859 (clobber (reg:CC FLAGS_REG))] 4860 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)" 4861 "adc{q}\t{%2, %0|%0, %2}" 4862 [(set_attr "type" "alu") 4863 (set_attr "pent_pair" "pu") 4864 (set_attr "mode" "DI")]) 4865 4866(define_insn "*adddi3_cc_rex64" 4867 [(set (reg:CC FLAGS_REG) 4868 (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0") 4869 (match_operand:DI 2 "x86_64_general_operand" "re,rm")] 4870 UNSPEC_ADD_CARRY)) 4871 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 4872 (plus:DI (match_dup 1) (match_dup 2)))] 4873 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)" 4874 "add{q}\t{%2, %0|%0, %2}" 4875 [(set_attr "type" "alu") 4876 (set_attr "mode" "DI")]) 4877 4878(define_insn "addqi3_carry" 4879 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q") 4880 (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "") 4881 (match_operand:QI 1 "nonimmediate_operand" "%0,0")) 4882 (match_operand:QI 2 "general_operand" "qi,qm"))) 4883 (clobber (reg:CC FLAGS_REG))] 4884 "ix86_binary_operator_ok (PLUS, QImode, operands)" 4885 "adc{b}\t{%2, %0|%0, %2}" 4886 [(set_attr "type" "alu") 4887 (set_attr "pent_pair" "pu") 4888 (set_attr "mode" "QI")]) 4889 4890(define_insn "addhi3_carry" 4891 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 4892 (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "") 4893 (match_operand:HI 1 "nonimmediate_operand" "%0,0")) 4894 (match_operand:HI 2 "general_operand" "ri,rm"))) 4895 (clobber (reg:CC FLAGS_REG))] 4896 "ix86_binary_operator_ok (PLUS, HImode, operands)" 4897 "adc{w}\t{%2, %0|%0, %2}" 4898 [(set_attr "type" "alu") 4899 (set_attr "pent_pair" "pu") 4900 (set_attr "mode" "HI")]) 4901 4902(define_insn "addsi3_carry" 4903 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 4904 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "") 4905 (match_operand:SI 1 "nonimmediate_operand" "%0,0")) 4906 (match_operand:SI 2 "general_operand" "ri,rm"))) 4907 (clobber (reg:CC FLAGS_REG))] 4908 "ix86_binary_operator_ok (PLUS, SImode, operands)" 4909 "adc{l}\t{%2, %0|%0, %2}" 4910 [(set_attr "type" "alu") 4911 (set_attr "pent_pair" "pu") 4912 (set_attr "mode" "SI")]) 4913 4914(define_insn "*addsi3_carry_zext" 4915 [(set (match_operand:DI 0 "register_operand" "=r") 4916 (zero_extend:DI 4917 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "") 4918 (match_operand:SI 1 "nonimmediate_operand" "%0")) 4919 (match_operand:SI 2 "general_operand" "rim")))) 4920 (clobber (reg:CC FLAGS_REG))] 4921 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)" 4922 "adc{l}\t{%2, %k0|%k0, %2}" 4923 [(set_attr "type" "alu") 4924 (set_attr "pent_pair" "pu") 4925 (set_attr "mode" "SI")]) 4926 4927(define_insn "*addsi3_cc" 4928 [(set (reg:CC FLAGS_REG) 4929 (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0") 4930 (match_operand:SI 2 "general_operand" "ri,rm")] 4931 UNSPEC_ADD_CARRY)) 4932 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 4933 (plus:SI (match_dup 1) (match_dup 2)))] 4934 "ix86_binary_operator_ok (PLUS, SImode, operands)" 4935 "add{l}\t{%2, %0|%0, %2}" 4936 [(set_attr "type" "alu") 4937 (set_attr "mode" "SI")]) 4938 4939(define_insn "addqi3_cc" 4940 [(set (reg:CC FLAGS_REG) 4941 (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0") 4942 (match_operand:QI 2 "general_operand" "qi,qm")] 4943 UNSPEC_ADD_CARRY)) 4944 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q") 4945 (plus:QI (match_dup 1) (match_dup 2)))] 4946 "ix86_binary_operator_ok (PLUS, QImode, operands)" 4947 "add{b}\t{%2, %0|%0, %2}" 4948 [(set_attr "type" "alu") 4949 (set_attr "mode" "QI")]) 4950 4951(define_expand "addsi3" 4952 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") 4953 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "") 4954 (match_operand:SI 2 "general_operand" ""))) 4955 (clobber (reg:CC FLAGS_REG))])] 4956 "" 4957 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;") 4958 4959(define_insn "*lea_1" 4960 [(set (match_operand:SI 0 "register_operand" "=r") 4961 (match_operand:SI 1 "no_seg_address_operand" "p"))] 4962 "!TARGET_64BIT" 4963 "lea{l}\t{%a1, %0|%0, %a1}" 4964 [(set_attr "type" "lea") 4965 (set_attr "mode" "SI")]) 4966 4967(define_insn "*lea_1_rex64" 4968 [(set (match_operand:SI 0 "register_operand" "=r") 4969 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))] 4970 "TARGET_64BIT" 4971 "lea{l}\t{%a1, %0|%0, %a1}" 4972 [(set_attr "type" "lea") 4973 (set_attr "mode" "SI")]) 4974 4975(define_insn "*lea_1_zext" 4976 [(set (match_operand:DI 0 "register_operand" "=r") 4977 (zero_extend:DI 4978 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))] 4979 "TARGET_64BIT" 4980 "lea{l}\t{%a1, %k0|%k0, %a1}" 4981 [(set_attr "type" "lea") 4982 (set_attr "mode" "SI")]) 4983 4984(define_insn "*lea_2_rex64" 4985 [(set (match_operand:DI 0 "register_operand" "=r") 4986 (match_operand:DI 1 "no_seg_address_operand" "p"))] 4987 "TARGET_64BIT" 4988 "lea{q}\t{%a1, %0|%0, %a1}" 4989 [(set_attr "type" "lea") 4990 (set_attr "mode" "DI")]) 4991 4992;; The lea patterns for non-Pmodes needs to be matched by several 4993;; insns converted to real lea by splitters. 4994 4995(define_insn_and_split "*lea_general_1" 4996 [(set (match_operand 0 "register_operand" "=r") 4997 (plus (plus (match_operand 1 "index_register_operand" "l") 4998 (match_operand 2 "register_operand" "r")) 4999 (match_operand 3 "immediate_operand" "i")))] 5000 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode 5001 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode)) 5002 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 5003 && GET_MODE (operands[0]) == GET_MODE (operands[1]) 5004 && GET_MODE (operands[0]) == GET_MODE (operands[2]) 5005 && (GET_MODE (operands[0]) == GET_MODE (operands[3]) 5006 || GET_MODE (operands[3]) == VOIDmode)" 5007 "#" 5008 "&& reload_completed" 5009 [(const_int 0)] 5010{ 5011 rtx pat; 5012 operands[0] = gen_lowpart (SImode, operands[0]); 5013 operands[1] = gen_lowpart (Pmode, operands[1]); 5014 operands[2] = gen_lowpart (Pmode, operands[2]); 5015 operands[3] = gen_lowpart (Pmode, operands[3]); 5016 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]), 5017 operands[3]); 5018 if (Pmode != SImode) 5019 pat = gen_rtx_SUBREG (SImode, pat, 0); 5020 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat)); 5021 DONE; 5022} 5023 [(set_attr "type" "lea") 5024 (set_attr "mode" "SI")]) 5025 5026(define_insn_and_split "*lea_general_1_zext" 5027 [(set (match_operand:DI 0 "register_operand" "=r") 5028 (zero_extend:DI 5029 (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l") 5030 (match_operand:SI 2 "register_operand" "r")) 5031 (match_operand:SI 3 "immediate_operand" "i"))))] 5032 "TARGET_64BIT" 5033 "#" 5034 "&& reload_completed" 5035 [(set (match_dup 0) 5036 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1) 5037 (match_dup 2)) 5038 (match_dup 3)) 0)))] 5039{ 5040 operands[1] = gen_lowpart (Pmode, operands[1]); 5041 operands[2] = gen_lowpart (Pmode, operands[2]); 5042 operands[3] = gen_lowpart (Pmode, operands[3]); 5043} 5044 [(set_attr "type" "lea") 5045 (set_attr "mode" "SI")]) 5046 5047(define_insn_and_split "*lea_general_2" 5048 [(set (match_operand 0 "register_operand" "=r") 5049 (plus (mult (match_operand 1 "index_register_operand" "l") 5050 (match_operand 2 "const248_operand" "i")) 5051 (match_operand 3 "nonmemory_operand" "ri")))] 5052 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode 5053 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode)) 5054 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 5055 && GET_MODE (operands[0]) == GET_MODE (operands[1]) 5056 && (GET_MODE (operands[0]) == GET_MODE (operands[3]) 5057 || GET_MODE (operands[3]) == VOIDmode)" 5058 "#" 5059 "&& reload_completed" 5060 [(const_int 0)] 5061{ 5062 rtx pat; 5063 operands[0] = gen_lowpart (SImode, operands[0]); 5064 operands[1] = gen_lowpart (Pmode, operands[1]); 5065 operands[3] = gen_lowpart (Pmode, operands[3]); 5066 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]), 5067 operands[3]); 5068 if (Pmode != SImode) 5069 pat = gen_rtx_SUBREG (SImode, pat, 0); 5070 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat)); 5071 DONE; 5072} 5073 [(set_attr "type" "lea") 5074 (set_attr "mode" "SI")]) 5075 5076(define_insn_and_split "*lea_general_2_zext" 5077 [(set (match_operand:DI 0 "register_operand" "=r") 5078 (zero_extend:DI 5079 (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l") 5080 (match_operand:SI 2 "const248_operand" "n")) 5081 (match_operand:SI 3 "nonmemory_operand" "ri"))))] 5082 "TARGET_64BIT" 5083 "#" 5084 "&& reload_completed" 5085 [(set (match_dup 0) 5086 (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1) 5087 (match_dup 2)) 5088 (match_dup 3)) 0)))] 5089{ 5090 operands[1] = gen_lowpart (Pmode, operands[1]); 5091 operands[3] = gen_lowpart (Pmode, operands[3]); 5092} 5093 [(set_attr "type" "lea") 5094 (set_attr "mode" "SI")]) 5095 5096(define_insn_and_split "*lea_general_3" 5097 [(set (match_operand 0 "register_operand" "=r") 5098 (plus (plus (mult (match_operand 1 "index_register_operand" "l") 5099 (match_operand 2 "const248_operand" "i")) 5100 (match_operand 3 "register_operand" "r")) 5101 (match_operand 4 "immediate_operand" "i")))] 5102 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode 5103 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode)) 5104 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 5105 && GET_MODE (operands[0]) == GET_MODE (operands[1]) 5106 && GET_MODE (operands[0]) == GET_MODE (operands[3])" 5107 "#" 5108 "&& reload_completed" 5109 [(const_int 0)] 5110{ 5111 rtx pat; 5112 operands[0] = gen_lowpart (SImode, operands[0]); 5113 operands[1] = gen_lowpart (Pmode, operands[1]); 5114 operands[3] = gen_lowpart (Pmode, operands[3]); 5115 operands[4] = gen_lowpart (Pmode, operands[4]); 5116 pat = gen_rtx_PLUS (Pmode, 5117 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], 5118 operands[2]), 5119 operands[3]), 5120 operands[4]); 5121 if (Pmode != SImode) 5122 pat = gen_rtx_SUBREG (SImode, pat, 0); 5123 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat)); 5124 DONE; 5125} 5126 [(set_attr "type" "lea") 5127 (set_attr "mode" "SI")]) 5128 5129(define_insn_and_split "*lea_general_3_zext" 5130 [(set (match_operand:DI 0 "register_operand" "=r") 5131 (zero_extend:DI 5132 (plus:SI (plus:SI (mult:SI 5133 (match_operand:SI 1 "index_register_operand" "l") 5134 (match_operand:SI 2 "const248_operand" "n")) 5135 (match_operand:SI 3 "register_operand" "r")) 5136 (match_operand:SI 4 "immediate_operand" "i"))))] 5137 "TARGET_64BIT" 5138 "#" 5139 "&& reload_completed" 5140 [(set (match_dup 0) 5141 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1) 5142 (match_dup 2)) 5143 (match_dup 3)) 5144 (match_dup 4)) 0)))] 5145{ 5146 operands[1] = gen_lowpart (Pmode, operands[1]); 5147 operands[3] = gen_lowpart (Pmode, operands[3]); 5148 operands[4] = gen_lowpart (Pmode, operands[4]); 5149} 5150 [(set_attr "type" "lea") 5151 (set_attr "mode" "SI")]) 5152 5153(define_insn "*adddi_1_rex64" 5154 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r") 5155 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r") 5156 (match_operand:DI 2 "x86_64_general_operand" "rme,re,le"))) 5157 (clobber (reg:CC FLAGS_REG))] 5158 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)" 5159{ 5160 switch (get_attr_type (insn)) 5161 { 5162 case TYPE_LEA: 5163 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0)); 5164 return "lea{q}\t{%a2, %0|%0, %a2}"; 5165 5166 case TYPE_INCDEC: 5167 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5168 if (operands[2] == const1_rtx) 5169 return "inc{q}\t%0"; 5170 else 5171 { 5172 gcc_assert (operands[2] == constm1_rtx); 5173 return "dec{q}\t%0"; 5174 } 5175 5176 default: 5177 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5178 5179 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5180 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5181 if (GET_CODE (operands[2]) == CONST_INT 5182 /* Avoid overflows. */ 5183 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))) 5184 && (INTVAL (operands[2]) == 128 5185 || (INTVAL (operands[2]) < 0 5186 && INTVAL (operands[2]) != -128))) 5187 { 5188 operands[2] = GEN_INT (-INTVAL (operands[2])); 5189 return "sub{q}\t{%2, %0|%0, %2}"; 5190 } 5191 return "add{q}\t{%2, %0|%0, %2}"; 5192 } 5193} 5194 [(set (attr "type") 5195 (cond [(eq_attr "alternative" "2") 5196 (const_string "lea") 5197 ; Current assemblers are broken and do not allow @GOTOFF in 5198 ; ought but a memory context. 5199 (match_operand:DI 2 "pic_symbolic_operand" "") 5200 (const_string "lea") 5201 (match_operand:DI 2 "incdec_operand" "") 5202 (const_string "incdec") 5203 ] 5204 (const_string "alu"))) 5205 (set_attr "mode" "DI")]) 5206 5207;; Convert lea to the lea pattern to avoid flags dependency. 5208(define_split 5209 [(set (match_operand:DI 0 "register_operand" "") 5210 (plus:DI (match_operand:DI 1 "register_operand" "") 5211 (match_operand:DI 2 "x86_64_nonmemory_operand" ""))) 5212 (clobber (reg:CC FLAGS_REG))] 5213 "TARGET_64BIT && reload_completed 5214 && true_regnum (operands[0]) != true_regnum (operands[1])" 5215 [(set (match_dup 0) 5216 (plus:DI (match_dup 1) 5217 (match_dup 2)))] 5218 "") 5219 5220(define_insn "*adddi_2_rex64" 5221 [(set (reg FLAGS_REG) 5222 (compare 5223 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 5224 (match_operand:DI 2 "x86_64_general_operand" "rme,re")) 5225 (const_int 0))) 5226 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm") 5227 (plus:DI (match_dup 1) (match_dup 2)))] 5228 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 5229 && ix86_binary_operator_ok (PLUS, DImode, operands) 5230 /* Current assemblers are broken and do not allow @GOTOFF in 5231 ought but a memory context. */ 5232 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5233{ 5234 switch (get_attr_type (insn)) 5235 { 5236 case TYPE_INCDEC: 5237 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5238 if (operands[2] == const1_rtx) 5239 return "inc{q}\t%0"; 5240 else 5241 { 5242 gcc_assert (operands[2] == constm1_rtx); 5243 return "dec{q}\t%0"; 5244 } 5245 5246 default: 5247 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5248 /* ???? We ought to handle there the 32bit case too 5249 - do we need new constraint? */ 5250 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5251 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5252 if (GET_CODE (operands[2]) == CONST_INT 5253 /* Avoid overflows. */ 5254 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))) 5255 && (INTVAL (operands[2]) == 128 5256 || (INTVAL (operands[2]) < 0 5257 && INTVAL (operands[2]) != -128))) 5258 { 5259 operands[2] = GEN_INT (-INTVAL (operands[2])); 5260 return "sub{q}\t{%2, %0|%0, %2}"; 5261 } 5262 return "add{q}\t{%2, %0|%0, %2}"; 5263 } 5264} 5265 [(set (attr "type") 5266 (if_then_else (match_operand:DI 2 "incdec_operand" "") 5267 (const_string "incdec") 5268 (const_string "alu"))) 5269 (set_attr "mode" "DI")]) 5270 5271(define_insn "*adddi_3_rex64" 5272 [(set (reg FLAGS_REG) 5273 (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme")) 5274 (match_operand:DI 1 "x86_64_general_operand" "%0"))) 5275 (clobber (match_scratch:DI 0 "=r"))] 5276 "TARGET_64BIT 5277 && ix86_match_ccmode (insn, CCZmode) 5278 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM) 5279 /* Current assemblers are broken and do not allow @GOTOFF in 5280 ought but a memory context. */ 5281 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5282{ 5283 switch (get_attr_type (insn)) 5284 { 5285 case TYPE_INCDEC: 5286 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5287 if (operands[2] == const1_rtx) 5288 return "inc{q}\t%0"; 5289 else 5290 { 5291 gcc_assert (operands[2] == constm1_rtx); 5292 return "dec{q}\t%0"; 5293 } 5294 5295 default: 5296 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5297 /* ???? We ought to handle there the 32bit case too 5298 - do we need new constraint? */ 5299 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5300 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5301 if (GET_CODE (operands[2]) == CONST_INT 5302 /* Avoid overflows. */ 5303 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))) 5304 && (INTVAL (operands[2]) == 128 5305 || (INTVAL (operands[2]) < 0 5306 && INTVAL (operands[2]) != -128))) 5307 { 5308 operands[2] = GEN_INT (-INTVAL (operands[2])); 5309 return "sub{q}\t{%2, %0|%0, %2}"; 5310 } 5311 return "add{q}\t{%2, %0|%0, %2}"; 5312 } 5313} 5314 [(set (attr "type") 5315 (if_then_else (match_operand:DI 2 "incdec_operand" "") 5316 (const_string "incdec") 5317 (const_string "alu"))) 5318 (set_attr "mode" "DI")]) 5319 5320; For comparisons against 1, -1 and 128, we may generate better code 5321; by converting cmp to add, inc or dec as done by peephole2. This pattern 5322; is matched then. We can't accept general immediate, because for 5323; case of overflows, the result is messed up. 5324; This pattern also don't hold of 0x8000000000000000, since the value overflows 5325; when negated. 5326; Also carry flag is reversed compared to cmp, so this conversion is valid 5327; only for comparisons not depending on it. 5328(define_insn "*adddi_4_rex64" 5329 [(set (reg FLAGS_REG) 5330 (compare (match_operand:DI 1 "nonimmediate_operand" "0") 5331 (match_operand:DI 2 "x86_64_immediate_operand" "e"))) 5332 (clobber (match_scratch:DI 0 "=rm"))] 5333 "TARGET_64BIT 5334 && ix86_match_ccmode (insn, CCGCmode)" 5335{ 5336 switch (get_attr_type (insn)) 5337 { 5338 case TYPE_INCDEC: 5339 if (operands[2] == constm1_rtx) 5340 return "inc{q}\t%0"; 5341 else 5342 { 5343 gcc_assert (operands[2] == const1_rtx); 5344 return "dec{q}\t%0"; 5345 } 5346 5347 default: 5348 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5349 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5350 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5351 if ((INTVAL (operands[2]) == -128 5352 || (INTVAL (operands[2]) > 0 5353 && INTVAL (operands[2]) != 128)) 5354 /* Avoid overflows. */ 5355 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))) 5356 return "sub{q}\t{%2, %0|%0, %2}"; 5357 operands[2] = GEN_INT (-INTVAL (operands[2])); 5358 return "add{q}\t{%2, %0|%0, %2}"; 5359 } 5360} 5361 [(set (attr "type") 5362 (if_then_else (match_operand:DI 2 "incdec_operand" "") 5363 (const_string "incdec") 5364 (const_string "alu"))) 5365 (set_attr "mode" "DI")]) 5366 5367(define_insn "*adddi_5_rex64" 5368 [(set (reg FLAGS_REG) 5369 (compare 5370 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0") 5371 (match_operand:DI 2 "x86_64_general_operand" "rme")) 5372 (const_int 0))) 5373 (clobber (match_scratch:DI 0 "=r"))] 5374 "TARGET_64BIT 5375 && ix86_match_ccmode (insn, CCGOCmode) 5376 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM) 5377 /* Current assemblers are broken and do not allow @GOTOFF in 5378 ought but a memory context. */ 5379 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5380{ 5381 switch (get_attr_type (insn)) 5382 { 5383 case TYPE_INCDEC: 5384 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5385 if (operands[2] == const1_rtx) 5386 return "inc{q}\t%0"; 5387 else 5388 { 5389 gcc_assert (operands[2] == constm1_rtx); 5390 return "dec{q}\t%0"; 5391 } 5392 5393 default: 5394 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5395 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5396 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5397 if (GET_CODE (operands[2]) == CONST_INT 5398 /* Avoid overflows. */ 5399 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))) 5400 && (INTVAL (operands[2]) == 128 5401 || (INTVAL (operands[2]) < 0 5402 && INTVAL (operands[2]) != -128))) 5403 { 5404 operands[2] = GEN_INT (-INTVAL (operands[2])); 5405 return "sub{q}\t{%2, %0|%0, %2}"; 5406 } 5407 return "add{q}\t{%2, %0|%0, %2}"; 5408 } 5409} 5410 [(set (attr "type") 5411 (if_then_else (match_operand:DI 2 "incdec_operand" "") 5412 (const_string "incdec") 5413 (const_string "alu"))) 5414 (set_attr "mode" "DI")]) 5415 5416 5417(define_insn "*addsi_1" 5418 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r") 5419 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r") 5420 (match_operand:SI 2 "general_operand" "rmni,rni,lni"))) 5421 (clobber (reg:CC FLAGS_REG))] 5422 "ix86_binary_operator_ok (PLUS, SImode, operands)" 5423{ 5424 switch (get_attr_type (insn)) 5425 { 5426 case TYPE_LEA: 5427 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0)); 5428 return "lea{l}\t{%a2, %0|%0, %a2}"; 5429 5430 case TYPE_INCDEC: 5431 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5432 if (operands[2] == const1_rtx) 5433 return "inc{l}\t%0"; 5434 else 5435 { 5436 gcc_assert (operands[2] == constm1_rtx); 5437 return "dec{l}\t%0"; 5438 } 5439 5440 default: 5441 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5442 5443 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5444 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5445 if (GET_CODE (operands[2]) == CONST_INT 5446 && (INTVAL (operands[2]) == 128 5447 || (INTVAL (operands[2]) < 0 5448 && INTVAL (operands[2]) != -128))) 5449 { 5450 operands[2] = GEN_INT (-INTVAL (operands[2])); 5451 return "sub{l}\t{%2, %0|%0, %2}"; 5452 } 5453 return "add{l}\t{%2, %0|%0, %2}"; 5454 } 5455} 5456 [(set (attr "type") 5457 (cond [(eq_attr "alternative" "2") 5458 (const_string "lea") 5459 ; Current assemblers are broken and do not allow @GOTOFF in 5460 ; ought but a memory context. 5461 (match_operand:SI 2 "pic_symbolic_operand" "") 5462 (const_string "lea") 5463 (match_operand:SI 2 "incdec_operand" "") 5464 (const_string "incdec") 5465 ] 5466 (const_string "alu"))) 5467 (set_attr "mode" "SI")]) 5468 5469;; Convert lea to the lea pattern to avoid flags dependency. 5470(define_split 5471 [(set (match_operand 0 "register_operand" "") 5472 (plus (match_operand 1 "register_operand" "") 5473 (match_operand 2 "nonmemory_operand" ""))) 5474 (clobber (reg:CC FLAGS_REG))] 5475 "reload_completed 5476 && true_regnum (operands[0]) != true_regnum (operands[1])" 5477 [(const_int 0)] 5478{ 5479 rtx pat; 5480 /* In -fPIC mode the constructs like (const (unspec [symbol_ref])) 5481 may confuse gen_lowpart. */ 5482 if (GET_MODE (operands[0]) != Pmode) 5483 { 5484 operands[1] = gen_lowpart (Pmode, operands[1]); 5485 operands[2] = gen_lowpart (Pmode, operands[2]); 5486 } 5487 operands[0] = gen_lowpart (SImode, operands[0]); 5488 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]); 5489 if (Pmode != SImode) 5490 pat = gen_rtx_SUBREG (SImode, pat, 0); 5491 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat)); 5492 DONE; 5493}) 5494 5495;; It may seem that nonimmediate operand is proper one for operand 1. 5496;; The addsi_1 pattern allows nonimmediate operand at that place and 5497;; we take care in ix86_binary_operator_ok to not allow two memory 5498;; operands so proper swapping will be done in reload. This allow 5499;; patterns constructed from addsi_1 to match. 5500(define_insn "addsi_1_zext" 5501 [(set (match_operand:DI 0 "register_operand" "=r,r") 5502 (zero_extend:DI 5503 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r") 5504 (match_operand:SI 2 "general_operand" "rmni,lni")))) 5505 (clobber (reg:CC FLAGS_REG))] 5506 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)" 5507{ 5508 switch (get_attr_type (insn)) 5509 { 5510 case TYPE_LEA: 5511 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0)); 5512 return "lea{l}\t{%a2, %k0|%k0, %a2}"; 5513 5514 case TYPE_INCDEC: 5515 if (operands[2] == const1_rtx) 5516 return "inc{l}\t%k0"; 5517 else 5518 { 5519 gcc_assert (operands[2] == constm1_rtx); 5520 return "dec{l}\t%k0"; 5521 } 5522 5523 default: 5524 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5525 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5526 if (GET_CODE (operands[2]) == CONST_INT 5527 && (INTVAL (operands[2]) == 128 5528 || (INTVAL (operands[2]) < 0 5529 && INTVAL (operands[2]) != -128))) 5530 { 5531 operands[2] = GEN_INT (-INTVAL (operands[2])); 5532 return "sub{l}\t{%2, %k0|%k0, %2}"; 5533 } 5534 return "add{l}\t{%2, %k0|%k0, %2}"; 5535 } 5536} 5537 [(set (attr "type") 5538 (cond [(eq_attr "alternative" "1") 5539 (const_string "lea") 5540 ; Current assemblers are broken and do not allow @GOTOFF in 5541 ; ought but a memory context. 5542 (match_operand:SI 2 "pic_symbolic_operand" "") 5543 (const_string "lea") 5544 (match_operand:SI 2 "incdec_operand" "") 5545 (const_string "incdec") 5546 ] 5547 (const_string "alu"))) 5548 (set_attr "mode" "SI")]) 5549 5550;; Convert lea to the lea pattern to avoid flags dependency. 5551(define_split 5552 [(set (match_operand:DI 0 "register_operand" "") 5553 (zero_extend:DI 5554 (plus:SI (match_operand:SI 1 "register_operand" "") 5555 (match_operand:SI 2 "nonmemory_operand" "")))) 5556 (clobber (reg:CC FLAGS_REG))] 5557 "TARGET_64BIT && reload_completed 5558 && true_regnum (operands[0]) != true_regnum (operands[1])" 5559 [(set (match_dup 0) 5560 (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))] 5561{ 5562 operands[1] = gen_lowpart (Pmode, operands[1]); 5563 operands[2] = gen_lowpart (Pmode, operands[2]); 5564}) 5565 5566(define_insn "*addsi_2" 5567 [(set (reg FLAGS_REG) 5568 (compare 5569 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 5570 (match_operand:SI 2 "general_operand" "rmni,rni")) 5571 (const_int 0))) 5572 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm") 5573 (plus:SI (match_dup 1) (match_dup 2)))] 5574 "ix86_match_ccmode (insn, CCGOCmode) 5575 && ix86_binary_operator_ok (PLUS, SImode, operands) 5576 /* Current assemblers are broken and do not allow @GOTOFF in 5577 ought but a memory context. */ 5578 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5579{ 5580 switch (get_attr_type (insn)) 5581 { 5582 case TYPE_INCDEC: 5583 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5584 if (operands[2] == const1_rtx) 5585 return "inc{l}\t%0"; 5586 else 5587 { 5588 gcc_assert (operands[2] == constm1_rtx); 5589 return "dec{l}\t%0"; 5590 } 5591 5592 default: 5593 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5594 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5595 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5596 if (GET_CODE (operands[2]) == CONST_INT 5597 && (INTVAL (operands[2]) == 128 5598 || (INTVAL (operands[2]) < 0 5599 && INTVAL (operands[2]) != -128))) 5600 { 5601 operands[2] = GEN_INT (-INTVAL (operands[2])); 5602 return "sub{l}\t{%2, %0|%0, %2}"; 5603 } 5604 return "add{l}\t{%2, %0|%0, %2}"; 5605 } 5606} 5607 [(set (attr "type") 5608 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5609 (const_string "incdec") 5610 (const_string "alu"))) 5611 (set_attr "mode" "SI")]) 5612 5613;; See comment for addsi_1_zext why we do use nonimmediate_operand 5614(define_insn "*addsi_2_zext" 5615 [(set (reg FLAGS_REG) 5616 (compare 5617 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 5618 (match_operand:SI 2 "general_operand" "rmni")) 5619 (const_int 0))) 5620 (set (match_operand:DI 0 "register_operand" "=r") 5621 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))] 5622 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 5623 && ix86_binary_operator_ok (PLUS, SImode, operands) 5624 /* Current assemblers are broken and do not allow @GOTOFF in 5625 ought but a memory context. */ 5626 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5627{ 5628 switch (get_attr_type (insn)) 5629 { 5630 case TYPE_INCDEC: 5631 if (operands[2] == const1_rtx) 5632 return "inc{l}\t%k0"; 5633 else 5634 { 5635 gcc_assert (operands[2] == constm1_rtx); 5636 return "dec{l}\t%k0"; 5637 } 5638 5639 default: 5640 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5641 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5642 if (GET_CODE (operands[2]) == CONST_INT 5643 && (INTVAL (operands[2]) == 128 5644 || (INTVAL (operands[2]) < 0 5645 && INTVAL (operands[2]) != -128))) 5646 { 5647 operands[2] = GEN_INT (-INTVAL (operands[2])); 5648 return "sub{l}\t{%2, %k0|%k0, %2}"; 5649 } 5650 return "add{l}\t{%2, %k0|%k0, %2}"; 5651 } 5652} 5653 [(set (attr "type") 5654 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5655 (const_string "incdec") 5656 (const_string "alu"))) 5657 (set_attr "mode" "SI")]) 5658 5659(define_insn "*addsi_3" 5660 [(set (reg FLAGS_REG) 5661 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni")) 5662 (match_operand:SI 1 "nonimmediate_operand" "%0"))) 5663 (clobber (match_scratch:SI 0 "=r"))] 5664 "ix86_match_ccmode (insn, CCZmode) 5665 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM) 5666 /* Current assemblers are broken and do not allow @GOTOFF in 5667 ought but a memory context. */ 5668 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5669{ 5670 switch (get_attr_type (insn)) 5671 { 5672 case TYPE_INCDEC: 5673 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5674 if (operands[2] == const1_rtx) 5675 return "inc{l}\t%0"; 5676 else 5677 { 5678 gcc_assert (operands[2] == constm1_rtx); 5679 return "dec{l}\t%0"; 5680 } 5681 5682 default: 5683 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5684 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5685 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5686 if (GET_CODE (operands[2]) == CONST_INT 5687 && (INTVAL (operands[2]) == 128 5688 || (INTVAL (operands[2]) < 0 5689 && INTVAL (operands[2]) != -128))) 5690 { 5691 operands[2] = GEN_INT (-INTVAL (operands[2])); 5692 return "sub{l}\t{%2, %0|%0, %2}"; 5693 } 5694 return "add{l}\t{%2, %0|%0, %2}"; 5695 } 5696} 5697 [(set (attr "type") 5698 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5699 (const_string "incdec") 5700 (const_string "alu"))) 5701 (set_attr "mode" "SI")]) 5702 5703;; See comment for addsi_1_zext why we do use nonimmediate_operand 5704(define_insn "*addsi_3_zext" 5705 [(set (reg FLAGS_REG) 5706 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni")) 5707 (match_operand:SI 1 "nonimmediate_operand" "%0"))) 5708 (set (match_operand:DI 0 "register_operand" "=r") 5709 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))] 5710 "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode) 5711 && ix86_binary_operator_ok (PLUS, SImode, operands) 5712 /* Current assemblers are broken and do not allow @GOTOFF in 5713 ought but a memory context. */ 5714 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5715{ 5716 switch (get_attr_type (insn)) 5717 { 5718 case TYPE_INCDEC: 5719 if (operands[2] == const1_rtx) 5720 return "inc{l}\t%k0"; 5721 else 5722 { 5723 gcc_assert (operands[2] == constm1_rtx); 5724 return "dec{l}\t%k0"; 5725 } 5726 5727 default: 5728 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5729 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5730 if (GET_CODE (operands[2]) == CONST_INT 5731 && (INTVAL (operands[2]) == 128 5732 || (INTVAL (operands[2]) < 0 5733 && INTVAL (operands[2]) != -128))) 5734 { 5735 operands[2] = GEN_INT (-INTVAL (operands[2])); 5736 return "sub{l}\t{%2, %k0|%k0, %2}"; 5737 } 5738 return "add{l}\t{%2, %k0|%k0, %2}"; 5739 } 5740} 5741 [(set (attr "type") 5742 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5743 (const_string "incdec") 5744 (const_string "alu"))) 5745 (set_attr "mode" "SI")]) 5746 5747; For comparisons against 1, -1 and 128, we may generate better code 5748; by converting cmp to add, inc or dec as done by peephole2. This pattern 5749; is matched then. We can't accept general immediate, because for 5750; case of overflows, the result is messed up. 5751; This pattern also don't hold of 0x80000000, since the value overflows 5752; when negated. 5753; Also carry flag is reversed compared to cmp, so this conversion is valid 5754; only for comparisons not depending on it. 5755(define_insn "*addsi_4" 5756 [(set (reg FLAGS_REG) 5757 (compare (match_operand:SI 1 "nonimmediate_operand" "0") 5758 (match_operand:SI 2 "const_int_operand" "n"))) 5759 (clobber (match_scratch:SI 0 "=rm"))] 5760 "ix86_match_ccmode (insn, CCGCmode) 5761 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000" 5762{ 5763 switch (get_attr_type (insn)) 5764 { 5765 case TYPE_INCDEC: 5766 if (operands[2] == constm1_rtx) 5767 return "inc{l}\t%0"; 5768 else 5769 { 5770 gcc_assert (operands[2] == const1_rtx); 5771 return "dec{l}\t%0"; 5772 } 5773 5774 default: 5775 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5776 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5777 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5778 if ((INTVAL (operands[2]) == -128 5779 || (INTVAL (operands[2]) > 0 5780 && INTVAL (operands[2]) != 128))) 5781 return "sub{l}\t{%2, %0|%0, %2}"; 5782 operands[2] = GEN_INT (-INTVAL (operands[2])); 5783 return "add{l}\t{%2, %0|%0, %2}"; 5784 } 5785} 5786 [(set (attr "type") 5787 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5788 (const_string "incdec") 5789 (const_string "alu"))) 5790 (set_attr "mode" "SI")]) 5791 5792(define_insn "*addsi_5" 5793 [(set (reg FLAGS_REG) 5794 (compare 5795 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 5796 (match_operand:SI 2 "general_operand" "rmni")) 5797 (const_int 0))) 5798 (clobber (match_scratch:SI 0 "=r"))] 5799 "ix86_match_ccmode (insn, CCGOCmode) 5800 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM) 5801 /* Current assemblers are broken and do not allow @GOTOFF in 5802 ought but a memory context. */ 5803 && ! pic_symbolic_operand (operands[2], VOIDmode)" 5804{ 5805 switch (get_attr_type (insn)) 5806 { 5807 case TYPE_INCDEC: 5808 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5809 if (operands[2] == const1_rtx) 5810 return "inc{l}\t%0"; 5811 else 5812 { 5813 gcc_assert (operands[2] == constm1_rtx); 5814 return "dec{l}\t%0"; 5815 } 5816 5817 default: 5818 gcc_assert (rtx_equal_p (operands[0], operands[1])); 5819 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5820 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5821 if (GET_CODE (operands[2]) == CONST_INT 5822 && (INTVAL (operands[2]) == 128 5823 || (INTVAL (operands[2]) < 0 5824 && INTVAL (operands[2]) != -128))) 5825 { 5826 operands[2] = GEN_INT (-INTVAL (operands[2])); 5827 return "sub{l}\t{%2, %0|%0, %2}"; 5828 } 5829 return "add{l}\t{%2, %0|%0, %2}"; 5830 } 5831} 5832 [(set (attr "type") 5833 (if_then_else (match_operand:SI 2 "incdec_operand" "") 5834 (const_string "incdec") 5835 (const_string "alu"))) 5836 (set_attr "mode" "SI")]) 5837 5838(define_expand "addhi3" 5839 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "") 5840 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "") 5841 (match_operand:HI 2 "general_operand" ""))) 5842 (clobber (reg:CC FLAGS_REG))])] 5843 "TARGET_HIMODE_MATH" 5844 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;") 5845 5846;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah 5847;; type optimizations enabled by define-splits. This is not important 5848;; for PII, and in fact harmful because of partial register stalls. 5849 5850(define_insn "*addhi_1_lea" 5851 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r") 5852 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r") 5853 (match_operand:HI 2 "general_operand" "ri,rm,lni"))) 5854 (clobber (reg:CC FLAGS_REG))] 5855 "!TARGET_PARTIAL_REG_STALL 5856 && ix86_binary_operator_ok (PLUS, HImode, operands)" 5857{ 5858 switch (get_attr_type (insn)) 5859 { 5860 case TYPE_LEA: 5861 return "#"; 5862 case TYPE_INCDEC: 5863 if (operands[2] == const1_rtx) 5864 return "inc{w}\t%0"; 5865 else 5866 { 5867 gcc_assert (operands[2] == constm1_rtx); 5868 return "dec{w}\t%0"; 5869 } 5870 5871 default: 5872 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5873 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5874 if (GET_CODE (operands[2]) == CONST_INT 5875 && (INTVAL (operands[2]) == 128 5876 || (INTVAL (operands[2]) < 0 5877 && INTVAL (operands[2]) != -128))) 5878 { 5879 operands[2] = GEN_INT (-INTVAL (operands[2])); 5880 return "sub{w}\t{%2, %0|%0, %2}"; 5881 } 5882 return "add{w}\t{%2, %0|%0, %2}"; 5883 } 5884} 5885 [(set (attr "type") 5886 (if_then_else (eq_attr "alternative" "2") 5887 (const_string "lea") 5888 (if_then_else (match_operand:HI 2 "incdec_operand" "") 5889 (const_string "incdec") 5890 (const_string "alu")))) 5891 (set_attr "mode" "HI,HI,SI")]) 5892 5893(define_insn "*addhi_1" 5894 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 5895 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 5896 (match_operand:HI 2 "general_operand" "ri,rm"))) 5897 (clobber (reg:CC FLAGS_REG))] 5898 "TARGET_PARTIAL_REG_STALL 5899 && ix86_binary_operator_ok (PLUS, HImode, operands)" 5900{ 5901 switch (get_attr_type (insn)) 5902 { 5903 case TYPE_INCDEC: 5904 if (operands[2] == const1_rtx) 5905 return "inc{w}\t%0"; 5906 else 5907 { 5908 gcc_assert (operands[2] == constm1_rtx); 5909 return "dec{w}\t%0"; 5910 } 5911 5912 default: 5913 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5914 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5915 if (GET_CODE (operands[2]) == CONST_INT 5916 && (INTVAL (operands[2]) == 128 5917 || (INTVAL (operands[2]) < 0 5918 && INTVAL (operands[2]) != -128))) 5919 { 5920 operands[2] = GEN_INT (-INTVAL (operands[2])); 5921 return "sub{w}\t{%2, %0|%0, %2}"; 5922 } 5923 return "add{w}\t{%2, %0|%0, %2}"; 5924 } 5925} 5926 [(set (attr "type") 5927 (if_then_else (match_operand:HI 2 "incdec_operand" "") 5928 (const_string "incdec") 5929 (const_string "alu"))) 5930 (set_attr "mode" "HI")]) 5931 5932(define_insn "*addhi_2" 5933 [(set (reg FLAGS_REG) 5934 (compare 5935 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 5936 (match_operand:HI 2 "general_operand" "rmni,rni")) 5937 (const_int 0))) 5938 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm") 5939 (plus:HI (match_dup 1) (match_dup 2)))] 5940 "ix86_match_ccmode (insn, CCGOCmode) 5941 && ix86_binary_operator_ok (PLUS, HImode, operands)" 5942{ 5943 switch (get_attr_type (insn)) 5944 { 5945 case TYPE_INCDEC: 5946 if (operands[2] == const1_rtx) 5947 return "inc{w}\t%0"; 5948 else 5949 { 5950 gcc_assert (operands[2] == constm1_rtx); 5951 return "dec{w}\t%0"; 5952 } 5953 5954 default: 5955 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5956 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5957 if (GET_CODE (operands[2]) == CONST_INT 5958 && (INTVAL (operands[2]) == 128 5959 || (INTVAL (operands[2]) < 0 5960 && INTVAL (operands[2]) != -128))) 5961 { 5962 operands[2] = GEN_INT (-INTVAL (operands[2])); 5963 return "sub{w}\t{%2, %0|%0, %2}"; 5964 } 5965 return "add{w}\t{%2, %0|%0, %2}"; 5966 } 5967} 5968 [(set (attr "type") 5969 (if_then_else (match_operand:HI 2 "incdec_operand" "") 5970 (const_string "incdec") 5971 (const_string "alu"))) 5972 (set_attr "mode" "HI")]) 5973 5974(define_insn "*addhi_3" 5975 [(set (reg FLAGS_REG) 5976 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni")) 5977 (match_operand:HI 1 "nonimmediate_operand" "%0"))) 5978 (clobber (match_scratch:HI 0 "=r"))] 5979 "ix86_match_ccmode (insn, CCZmode) 5980 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 5981{ 5982 switch (get_attr_type (insn)) 5983 { 5984 case TYPE_INCDEC: 5985 if (operands[2] == const1_rtx) 5986 return "inc{w}\t%0"; 5987 else 5988 { 5989 gcc_assert (operands[2] == constm1_rtx); 5990 return "dec{w}\t%0"; 5991 } 5992 5993 default: 5994 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 5995 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 5996 if (GET_CODE (operands[2]) == CONST_INT 5997 && (INTVAL (operands[2]) == 128 5998 || (INTVAL (operands[2]) < 0 5999 && INTVAL (operands[2]) != -128))) 6000 { 6001 operands[2] = GEN_INT (-INTVAL (operands[2])); 6002 return "sub{w}\t{%2, %0|%0, %2}"; 6003 } 6004 return "add{w}\t{%2, %0|%0, %2}"; 6005 } 6006} 6007 [(set (attr "type") 6008 (if_then_else (match_operand:HI 2 "incdec_operand" "") 6009 (const_string "incdec") 6010 (const_string "alu"))) 6011 (set_attr "mode" "HI")]) 6012 6013; See comments above addsi_4 for details. 6014(define_insn "*addhi_4" 6015 [(set (reg FLAGS_REG) 6016 (compare (match_operand:HI 1 "nonimmediate_operand" "0") 6017 (match_operand:HI 2 "const_int_operand" "n"))) 6018 (clobber (match_scratch:HI 0 "=rm"))] 6019 "ix86_match_ccmode (insn, CCGCmode) 6020 && (INTVAL (operands[2]) & 0xffff) != 0x8000" 6021{ 6022 switch (get_attr_type (insn)) 6023 { 6024 case TYPE_INCDEC: 6025 if (operands[2] == constm1_rtx) 6026 return "inc{w}\t%0"; 6027 else 6028 { 6029 gcc_assert (operands[2] == const1_rtx); 6030 return "dec{w}\t%0"; 6031 } 6032 6033 default: 6034 gcc_assert (rtx_equal_p (operands[0], operands[1])); 6035 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 6036 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 6037 if ((INTVAL (operands[2]) == -128 6038 || (INTVAL (operands[2]) > 0 6039 && INTVAL (operands[2]) != 128))) 6040 return "sub{w}\t{%2, %0|%0, %2}"; 6041 operands[2] = GEN_INT (-INTVAL (operands[2])); 6042 return "add{w}\t{%2, %0|%0, %2}"; 6043 } 6044} 6045 [(set (attr "type") 6046 (if_then_else (match_operand:HI 2 "incdec_operand" "") 6047 (const_string "incdec") 6048 (const_string "alu"))) 6049 (set_attr "mode" "SI")]) 6050 6051 6052(define_insn "*addhi_5" 6053 [(set (reg FLAGS_REG) 6054 (compare 6055 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0") 6056 (match_operand:HI 2 "general_operand" "rmni")) 6057 (const_int 0))) 6058 (clobber (match_scratch:HI 0 "=r"))] 6059 "ix86_match_ccmode (insn, CCGOCmode) 6060 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 6061{ 6062 switch (get_attr_type (insn)) 6063 { 6064 case TYPE_INCDEC: 6065 if (operands[2] == const1_rtx) 6066 return "inc{w}\t%0"; 6067 else 6068 { 6069 gcc_assert (operands[2] == constm1_rtx); 6070 return "dec{w}\t%0"; 6071 } 6072 6073 default: 6074 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 6075 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 6076 if (GET_CODE (operands[2]) == CONST_INT 6077 && (INTVAL (operands[2]) == 128 6078 || (INTVAL (operands[2]) < 0 6079 && INTVAL (operands[2]) != -128))) 6080 { 6081 operands[2] = GEN_INT (-INTVAL (operands[2])); 6082 return "sub{w}\t{%2, %0|%0, %2}"; 6083 } 6084 return "add{w}\t{%2, %0|%0, %2}"; 6085 } 6086} 6087 [(set (attr "type") 6088 (if_then_else (match_operand:HI 2 "incdec_operand" "") 6089 (const_string "incdec") 6090 (const_string "alu"))) 6091 (set_attr "mode" "HI")]) 6092 6093(define_expand "addqi3" 6094 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "") 6095 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "") 6096 (match_operand:QI 2 "general_operand" ""))) 6097 (clobber (reg:CC FLAGS_REG))])] 6098 "TARGET_QIMODE_MATH" 6099 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;") 6100 6101;; %%% Potential partial reg stall on alternative 2. What to do? 6102(define_insn "*addqi_1_lea" 6103 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r") 6104 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r") 6105 (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln"))) 6106 (clobber (reg:CC FLAGS_REG))] 6107 "!TARGET_PARTIAL_REG_STALL 6108 && ix86_binary_operator_ok (PLUS, QImode, operands)" 6109{ 6110 int widen = (which_alternative == 2); 6111 switch (get_attr_type (insn)) 6112 { 6113 case TYPE_LEA: 6114 return "#"; 6115 case TYPE_INCDEC: 6116 if (operands[2] == const1_rtx) 6117 return widen ? "inc{l}\t%k0" : "inc{b}\t%0"; 6118 else 6119 { 6120 gcc_assert (operands[2] == constm1_rtx); 6121 return widen ? "dec{l}\t%k0" : "dec{b}\t%0"; 6122 } 6123 6124 default: 6125 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 6126 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 6127 if (GET_CODE (operands[2]) == CONST_INT 6128 && (INTVAL (operands[2]) == 128 6129 || (INTVAL (operands[2]) < 0 6130 && INTVAL (operands[2]) != -128))) 6131 { 6132 operands[2] = GEN_INT (-INTVAL (operands[2])); 6133 if (widen) 6134 return "sub{l}\t{%2, %k0|%k0, %2}"; 6135 else 6136 return "sub{b}\t{%2, %0|%0, %2}"; 6137 } 6138 if (widen) 6139 return "add{l}\t{%k2, %k0|%k0, %k2}"; 6140 else 6141 return "add{b}\t{%2, %0|%0, %2}"; 6142 } 6143} 6144 [(set (attr "type") 6145 (if_then_else (eq_attr "alternative" "3") 6146 (const_string "lea") 6147 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6148 (const_string "incdec") 6149 (const_string "alu")))) 6150 (set_attr "mode" "QI,QI,SI,SI")]) 6151 6152(define_insn "*addqi_1" 6153 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r") 6154 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0") 6155 (match_operand:QI 2 "general_operand" "qn,qmn,rn"))) 6156 (clobber (reg:CC FLAGS_REG))] 6157 "TARGET_PARTIAL_REG_STALL 6158 && ix86_binary_operator_ok (PLUS, QImode, operands)" 6159{ 6160 int widen = (which_alternative == 2); 6161 switch (get_attr_type (insn)) 6162 { 6163 case TYPE_INCDEC: 6164 if (operands[2] == const1_rtx) 6165 return widen ? "inc{l}\t%k0" : "inc{b}\t%0"; 6166 else 6167 { 6168 gcc_assert (operands[2] == constm1_rtx); 6169 return widen ? "dec{l}\t%k0" : "dec{b}\t%0"; 6170 } 6171 6172 default: 6173 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. 6174 Exceptions: -128 encodes smaller than 128, so swap sign and op. */ 6175 if (GET_CODE (operands[2]) == CONST_INT 6176 && (INTVAL (operands[2]) == 128 6177 || (INTVAL (operands[2]) < 0 6178 && INTVAL (operands[2]) != -128))) 6179 { 6180 operands[2] = GEN_INT (-INTVAL (operands[2])); 6181 if (widen) 6182 return "sub{l}\t{%2, %k0|%k0, %2}"; 6183 else 6184 return "sub{b}\t{%2, %0|%0, %2}"; 6185 } 6186 if (widen) 6187 return "add{l}\t{%k2, %k0|%k0, %k2}"; 6188 else 6189 return "add{b}\t{%2, %0|%0, %2}"; 6190 } 6191} 6192 [(set (attr "type") 6193 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6194 (const_string "incdec") 6195 (const_string "alu"))) 6196 (set_attr "mode" "QI,QI,SI")]) 6197 6198(define_insn "*addqi_1_slp" 6199 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q")) 6200 (plus:QI (match_dup 0) 6201 (match_operand:QI 1 "general_operand" "qn,qnm"))) 6202 (clobber (reg:CC FLAGS_REG))] 6203 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 6204 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 6205{ 6206 switch (get_attr_type (insn)) 6207 { 6208 case TYPE_INCDEC: 6209 if (operands[1] == const1_rtx) 6210 return "inc{b}\t%0"; 6211 else 6212 { 6213 gcc_assert (operands[1] == constm1_rtx); 6214 return "dec{b}\t%0"; 6215 } 6216 6217 default: 6218 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. */ 6219 if (GET_CODE (operands[1]) == CONST_INT 6220 && INTVAL (operands[1]) < 0) 6221 { 6222 operands[1] = GEN_INT (-INTVAL (operands[1])); 6223 return "sub{b}\t{%1, %0|%0, %1}"; 6224 } 6225 return "add{b}\t{%1, %0|%0, %1}"; 6226 } 6227} 6228 [(set (attr "type") 6229 (if_then_else (match_operand:QI 1 "incdec_operand" "") 6230 (const_string "incdec") 6231 (const_string "alu1"))) 6232 (set (attr "memory") 6233 (if_then_else (match_operand 1 "memory_operand" "") 6234 (const_string "load") 6235 (const_string "none"))) 6236 (set_attr "mode" "QI")]) 6237 6238(define_insn "*addqi_2" 6239 [(set (reg FLAGS_REG) 6240 (compare 6241 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0") 6242 (match_operand:QI 2 "general_operand" "qmni,qni")) 6243 (const_int 0))) 6244 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm") 6245 (plus:QI (match_dup 1) (match_dup 2)))] 6246 "ix86_match_ccmode (insn, CCGOCmode) 6247 && ix86_binary_operator_ok (PLUS, QImode, operands)" 6248{ 6249 switch (get_attr_type (insn)) 6250 { 6251 case TYPE_INCDEC: 6252 if (operands[2] == const1_rtx) 6253 return "inc{b}\t%0"; 6254 else 6255 { 6256 gcc_assert (operands[2] == constm1_rtx 6257 || (GET_CODE (operands[2]) == CONST_INT 6258 && INTVAL (operands[2]) == 255)); 6259 return "dec{b}\t%0"; 6260 } 6261 6262 default: 6263 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */ 6264 if (GET_CODE (operands[2]) == CONST_INT 6265 && INTVAL (operands[2]) < 0) 6266 { 6267 operands[2] = GEN_INT (-INTVAL (operands[2])); 6268 return "sub{b}\t{%2, %0|%0, %2}"; 6269 } 6270 return "add{b}\t{%2, %0|%0, %2}"; 6271 } 6272} 6273 [(set (attr "type") 6274 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6275 (const_string "incdec") 6276 (const_string "alu"))) 6277 (set_attr "mode" "QI")]) 6278 6279(define_insn "*addqi_3" 6280 [(set (reg FLAGS_REG) 6281 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni")) 6282 (match_operand:QI 1 "nonimmediate_operand" "%0"))) 6283 (clobber (match_scratch:QI 0 "=q"))] 6284 "ix86_match_ccmode (insn, CCZmode) 6285 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 6286{ 6287 switch (get_attr_type (insn)) 6288 { 6289 case TYPE_INCDEC: 6290 if (operands[2] == const1_rtx) 6291 return "inc{b}\t%0"; 6292 else 6293 { 6294 gcc_assert (operands[2] == constm1_rtx 6295 || (GET_CODE (operands[2]) == CONST_INT 6296 && INTVAL (operands[2]) == 255)); 6297 return "dec{b}\t%0"; 6298 } 6299 6300 default: 6301 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */ 6302 if (GET_CODE (operands[2]) == CONST_INT 6303 && INTVAL (operands[2]) < 0) 6304 { 6305 operands[2] = GEN_INT (-INTVAL (operands[2])); 6306 return "sub{b}\t{%2, %0|%0, %2}"; 6307 } 6308 return "add{b}\t{%2, %0|%0, %2}"; 6309 } 6310} 6311 [(set (attr "type") 6312 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6313 (const_string "incdec") 6314 (const_string "alu"))) 6315 (set_attr "mode" "QI")]) 6316 6317; See comments above addsi_4 for details. 6318(define_insn "*addqi_4" 6319 [(set (reg FLAGS_REG) 6320 (compare (match_operand:QI 1 "nonimmediate_operand" "0") 6321 (match_operand:QI 2 "const_int_operand" "n"))) 6322 (clobber (match_scratch:QI 0 "=qm"))] 6323 "ix86_match_ccmode (insn, CCGCmode) 6324 && (INTVAL (operands[2]) & 0xff) != 0x80" 6325{ 6326 switch (get_attr_type (insn)) 6327 { 6328 case TYPE_INCDEC: 6329 if (operands[2] == constm1_rtx 6330 || (GET_CODE (operands[2]) == CONST_INT 6331 && INTVAL (operands[2]) == 255)) 6332 return "inc{b}\t%0"; 6333 else 6334 { 6335 gcc_assert (operands[2] == const1_rtx); 6336 return "dec{b}\t%0"; 6337 } 6338 6339 default: 6340 gcc_assert (rtx_equal_p (operands[0], operands[1])); 6341 if (INTVAL (operands[2]) < 0) 6342 { 6343 operands[2] = GEN_INT (-INTVAL (operands[2])); 6344 return "add{b}\t{%2, %0|%0, %2}"; 6345 } 6346 return "sub{b}\t{%2, %0|%0, %2}"; 6347 } 6348} 6349 [(set (attr "type") 6350 (if_then_else (match_operand:HI 2 "incdec_operand" "") 6351 (const_string "incdec") 6352 (const_string "alu"))) 6353 (set_attr "mode" "QI")]) 6354 6355 6356(define_insn "*addqi_5" 6357 [(set (reg FLAGS_REG) 6358 (compare 6359 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0") 6360 (match_operand:QI 2 "general_operand" "qmni")) 6361 (const_int 0))) 6362 (clobber (match_scratch:QI 0 "=q"))] 6363 "ix86_match_ccmode (insn, CCGOCmode) 6364 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 6365{ 6366 switch (get_attr_type (insn)) 6367 { 6368 case TYPE_INCDEC: 6369 if (operands[2] == const1_rtx) 6370 return "inc{b}\t%0"; 6371 else 6372 { 6373 gcc_assert (operands[2] == constm1_rtx 6374 || (GET_CODE (operands[2]) == CONST_INT 6375 && INTVAL (operands[2]) == 255)); 6376 return "dec{b}\t%0"; 6377 } 6378 6379 default: 6380 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */ 6381 if (GET_CODE (operands[2]) == CONST_INT 6382 && INTVAL (operands[2]) < 0) 6383 { 6384 operands[2] = GEN_INT (-INTVAL (operands[2])); 6385 return "sub{b}\t{%2, %0|%0, %2}"; 6386 } 6387 return "add{b}\t{%2, %0|%0, %2}"; 6388 } 6389} 6390 [(set (attr "type") 6391 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6392 (const_string "incdec") 6393 (const_string "alu"))) 6394 (set_attr "mode" "QI")]) 6395 6396 6397(define_insn "addqi_ext_1" 6398 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 6399 (const_int 8) 6400 (const_int 8)) 6401 (plus:SI 6402 (zero_extract:SI 6403 (match_operand 1 "ext_register_operand" "0") 6404 (const_int 8) 6405 (const_int 8)) 6406 (match_operand:QI 2 "general_operand" "Qmn"))) 6407 (clobber (reg:CC FLAGS_REG))] 6408 "!TARGET_64BIT" 6409{ 6410 switch (get_attr_type (insn)) 6411 { 6412 case TYPE_INCDEC: 6413 if (operands[2] == const1_rtx) 6414 return "inc{b}\t%h0"; 6415 else 6416 { 6417 gcc_assert (operands[2] == constm1_rtx 6418 || (GET_CODE (operands[2]) == CONST_INT 6419 && INTVAL (operands[2]) == 255)); 6420 return "dec{b}\t%h0"; 6421 } 6422 6423 default: 6424 return "add{b}\t{%2, %h0|%h0, %2}"; 6425 } 6426} 6427 [(set (attr "type") 6428 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6429 (const_string "incdec") 6430 (const_string "alu"))) 6431 (set_attr "mode" "QI")]) 6432 6433(define_insn "*addqi_ext_1_rex64" 6434 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 6435 (const_int 8) 6436 (const_int 8)) 6437 (plus:SI 6438 (zero_extract:SI 6439 (match_operand 1 "ext_register_operand" "0") 6440 (const_int 8) 6441 (const_int 8)) 6442 (match_operand:QI 2 "nonmemory_operand" "Qn"))) 6443 (clobber (reg:CC FLAGS_REG))] 6444 "TARGET_64BIT" 6445{ 6446 switch (get_attr_type (insn)) 6447 { 6448 case TYPE_INCDEC: 6449 if (operands[2] == const1_rtx) 6450 return "inc{b}\t%h0"; 6451 else 6452 { 6453 gcc_assert (operands[2] == constm1_rtx 6454 || (GET_CODE (operands[2]) == CONST_INT 6455 && INTVAL (operands[2]) == 255)); 6456 return "dec{b}\t%h0"; 6457 } 6458 6459 default: 6460 return "add{b}\t{%2, %h0|%h0, %2}"; 6461 } 6462} 6463 [(set (attr "type") 6464 (if_then_else (match_operand:QI 2 "incdec_operand" "") 6465 (const_string "incdec") 6466 (const_string "alu"))) 6467 (set_attr "mode" "QI")]) 6468 6469(define_insn "*addqi_ext_2" 6470 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 6471 (const_int 8) 6472 (const_int 8)) 6473 (plus:SI 6474 (zero_extract:SI 6475 (match_operand 1 "ext_register_operand" "%0") 6476 (const_int 8) 6477 (const_int 8)) 6478 (zero_extract:SI 6479 (match_operand 2 "ext_register_operand" "Q") 6480 (const_int 8) 6481 (const_int 8)))) 6482 (clobber (reg:CC FLAGS_REG))] 6483 "" 6484 "add{b}\t{%h2, %h0|%h0, %h2}" 6485 [(set_attr "type" "alu") 6486 (set_attr "mode" "QI")]) 6487 6488;; The patterns that match these are at the end of this file. 6489 6490(define_expand "addxf3" 6491 [(set (match_operand:XF 0 "register_operand" "") 6492 (plus:XF (match_operand:XF 1 "register_operand" "") 6493 (match_operand:XF 2 "register_operand" "")))] 6494 "TARGET_80387" 6495 "") 6496 6497(define_expand "adddf3" 6498 [(set (match_operand:DF 0 "register_operand" "") 6499 (plus:DF (match_operand:DF 1 "register_operand" "") 6500 (match_operand:DF 2 "nonimmediate_operand" "")))] 6501 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 6502 "") 6503 6504(define_expand "addsf3" 6505 [(set (match_operand:SF 0 "register_operand" "") 6506 (plus:SF (match_operand:SF 1 "register_operand" "") 6507 (match_operand:SF 2 "nonimmediate_operand" "")))] 6508 "TARGET_80387 || TARGET_SSE_MATH" 6509 "") 6510 6511;; Subtract instructions 6512 6513;; %%% splits for subditi3 6514 6515(define_expand "subti3" 6516 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "") 6517 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "") 6518 (match_operand:TI 2 "x86_64_general_operand" ""))) 6519 (clobber (reg:CC FLAGS_REG))])] 6520 "TARGET_64BIT" 6521 "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;") 6522 6523(define_insn "*subti3_1" 6524 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o") 6525 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0") 6526 (match_operand:TI 2 "x86_64_general_operand" "roe,re"))) 6527 (clobber (reg:CC FLAGS_REG))] 6528 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)" 6529 "#") 6530 6531(define_split 6532 [(set (match_operand:TI 0 "nonimmediate_operand" "") 6533 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "") 6534 (match_operand:TI 2 "x86_64_general_operand" ""))) 6535 (clobber (reg:CC FLAGS_REG))] 6536 "TARGET_64BIT && reload_completed" 6537 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2))) 6538 (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))]) 6539 (parallel [(set (match_dup 3) 6540 (minus:DI (match_dup 4) 6541 (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0)) 6542 (match_dup 5)))) 6543 (clobber (reg:CC FLAGS_REG))])] 6544 "split_ti (operands+0, 1, operands+0, operands+3); 6545 split_ti (operands+1, 1, operands+1, operands+4); 6546 split_ti (operands+2, 1, operands+2, operands+5);") 6547 6548;; %%% splits for subsidi3 6549 6550(define_expand "subdi3" 6551 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "") 6552 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "") 6553 (match_operand:DI 2 "x86_64_general_operand" ""))) 6554 (clobber (reg:CC FLAGS_REG))])] 6555 "" 6556 "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;") 6557 6558(define_insn "*subdi3_1" 6559 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o") 6560 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 6561 (match_operand:DI 2 "general_operand" "roiF,riF"))) 6562 (clobber (reg:CC FLAGS_REG))] 6563 "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)" 6564 "#") 6565 6566(define_split 6567 [(set (match_operand:DI 0 "nonimmediate_operand" "") 6568 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "") 6569 (match_operand:DI 2 "general_operand" ""))) 6570 (clobber (reg:CC FLAGS_REG))] 6571 "!TARGET_64BIT && reload_completed" 6572 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2))) 6573 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))]) 6574 (parallel [(set (match_dup 3) 6575 (minus:SI (match_dup 4) 6576 (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0)) 6577 (match_dup 5)))) 6578 (clobber (reg:CC FLAGS_REG))])] 6579 "split_di (operands+0, 1, operands+0, operands+3); 6580 split_di (operands+1, 1, operands+1, operands+4); 6581 split_di (operands+2, 1, operands+2, operands+5);") 6582 6583(define_insn "subdi3_carry_rex64" 6584 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 6585 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 6586 (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "") 6587 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))) 6588 (clobber (reg:CC FLAGS_REG))] 6589 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)" 6590 "sbb{q}\t{%2, %0|%0, %2}" 6591 [(set_attr "type" "alu") 6592 (set_attr "pent_pair" "pu") 6593 (set_attr "mode" "DI")]) 6594 6595(define_insn "*subdi_1_rex64" 6596 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 6597 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 6598 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))) 6599 (clobber (reg:CC FLAGS_REG))] 6600 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)" 6601 "sub{q}\t{%2, %0|%0, %2}" 6602 [(set_attr "type" "alu") 6603 (set_attr "mode" "DI")]) 6604 6605(define_insn "*subdi_2_rex64" 6606 [(set (reg FLAGS_REG) 6607 (compare 6608 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 6609 (match_operand:DI 2 "x86_64_general_operand" "re,rm")) 6610 (const_int 0))) 6611 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 6612 (minus:DI (match_dup 1) (match_dup 2)))] 6613 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 6614 && ix86_binary_operator_ok (MINUS, DImode, operands)" 6615 "sub{q}\t{%2, %0|%0, %2}" 6616 [(set_attr "type" "alu") 6617 (set_attr "mode" "DI")]) 6618 6619(define_insn "*subdi_3_rex63" 6620 [(set (reg FLAGS_REG) 6621 (compare (match_operand:DI 1 "nonimmediate_operand" "0,0") 6622 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))) 6623 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 6624 (minus:DI (match_dup 1) (match_dup 2)))] 6625 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode) 6626 && ix86_binary_operator_ok (MINUS, SImode, operands)" 6627 "sub{q}\t{%2, %0|%0, %2}" 6628 [(set_attr "type" "alu") 6629 (set_attr "mode" "DI")]) 6630 6631(define_insn "subqi3_carry" 6632 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q") 6633 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 6634 (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "") 6635 (match_operand:QI 2 "general_operand" "qi,qm")))) 6636 (clobber (reg:CC FLAGS_REG))] 6637 "ix86_binary_operator_ok (MINUS, QImode, operands)" 6638 "sbb{b}\t{%2, %0|%0, %2}" 6639 [(set_attr "type" "alu") 6640 (set_attr "pent_pair" "pu") 6641 (set_attr "mode" "QI")]) 6642 6643(define_insn "subhi3_carry" 6644 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 6645 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 6646 (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "") 6647 (match_operand:HI 2 "general_operand" "ri,rm")))) 6648 (clobber (reg:CC FLAGS_REG))] 6649 "ix86_binary_operator_ok (MINUS, HImode, operands)" 6650 "sbb{w}\t{%2, %0|%0, %2}" 6651 [(set_attr "type" "alu") 6652 (set_attr "pent_pair" "pu") 6653 (set_attr "mode" "HI")]) 6654 6655(define_insn "subsi3_carry" 6656 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 6657 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 6658 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "") 6659 (match_operand:SI 2 "general_operand" "ri,rm")))) 6660 (clobber (reg:CC FLAGS_REG))] 6661 "ix86_binary_operator_ok (MINUS, SImode, operands)" 6662 "sbb{l}\t{%2, %0|%0, %2}" 6663 [(set_attr "type" "alu") 6664 (set_attr "pent_pair" "pu") 6665 (set_attr "mode" "SI")]) 6666 6667(define_insn "subsi3_carry_zext" 6668 [(set (match_operand:DI 0 "register_operand" "=rm,r") 6669 (zero_extend:DI 6670 (minus:SI (match_operand:SI 1 "register_operand" "0,0") 6671 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "") 6672 (match_operand:SI 2 "general_operand" "ri,rm"))))) 6673 (clobber (reg:CC FLAGS_REG))] 6674 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)" 6675 "sbb{l}\t{%2, %k0|%k0, %2}" 6676 [(set_attr "type" "alu") 6677 (set_attr "pent_pair" "pu") 6678 (set_attr "mode" "SI")]) 6679 6680(define_expand "subsi3" 6681 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") 6682 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "") 6683 (match_operand:SI 2 "general_operand" ""))) 6684 (clobber (reg:CC FLAGS_REG))])] 6685 "" 6686 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;") 6687 6688(define_insn "*subsi_1" 6689 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 6690 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 6691 (match_operand:SI 2 "general_operand" "ri,rm"))) 6692 (clobber (reg:CC FLAGS_REG))] 6693 "ix86_binary_operator_ok (MINUS, SImode, operands)" 6694 "sub{l}\t{%2, %0|%0, %2}" 6695 [(set_attr "type" "alu") 6696 (set_attr "mode" "SI")]) 6697 6698(define_insn "*subsi_1_zext" 6699 [(set (match_operand:DI 0 "register_operand" "=r") 6700 (zero_extend:DI 6701 (minus:SI (match_operand:SI 1 "register_operand" "0") 6702 (match_operand:SI 2 "general_operand" "rim")))) 6703 (clobber (reg:CC FLAGS_REG))] 6704 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)" 6705 "sub{l}\t{%2, %k0|%k0, %2}" 6706 [(set_attr "type" "alu") 6707 (set_attr "mode" "SI")]) 6708 6709(define_insn "*subsi_2" 6710 [(set (reg FLAGS_REG) 6711 (compare 6712 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 6713 (match_operand:SI 2 "general_operand" "ri,rm")) 6714 (const_int 0))) 6715 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 6716 (minus:SI (match_dup 1) (match_dup 2)))] 6717 "ix86_match_ccmode (insn, CCGOCmode) 6718 && ix86_binary_operator_ok (MINUS, SImode, operands)" 6719 "sub{l}\t{%2, %0|%0, %2}" 6720 [(set_attr "type" "alu") 6721 (set_attr "mode" "SI")]) 6722 6723(define_insn "*subsi_2_zext" 6724 [(set (reg FLAGS_REG) 6725 (compare 6726 (minus:SI (match_operand:SI 1 "register_operand" "0") 6727 (match_operand:SI 2 "general_operand" "rim")) 6728 (const_int 0))) 6729 (set (match_operand:DI 0 "register_operand" "=r") 6730 (zero_extend:DI 6731 (minus:SI (match_dup 1) 6732 (match_dup 2))))] 6733 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 6734 && ix86_binary_operator_ok (MINUS, SImode, operands)" 6735 "sub{l}\t{%2, %k0|%k0, %2}" 6736 [(set_attr "type" "alu") 6737 (set_attr "mode" "SI")]) 6738 6739(define_insn "*subsi_3" 6740 [(set (reg FLAGS_REG) 6741 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0") 6742 (match_operand:SI 2 "general_operand" "ri,rm"))) 6743 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 6744 (minus:SI (match_dup 1) (match_dup 2)))] 6745 "ix86_match_ccmode (insn, CCmode) 6746 && ix86_binary_operator_ok (MINUS, SImode, operands)" 6747 "sub{l}\t{%2, %0|%0, %2}" 6748 [(set_attr "type" "alu") 6749 (set_attr "mode" "SI")]) 6750 6751(define_insn "*subsi_3_zext" 6752 [(set (reg FLAGS_REG) 6753 (compare (match_operand:SI 1 "register_operand" "0") 6754 (match_operand:SI 2 "general_operand" "rim"))) 6755 (set (match_operand:DI 0 "register_operand" "=r") 6756 (zero_extend:DI 6757 (minus:SI (match_dup 1) 6758 (match_dup 2))))] 6759 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode) 6760 && ix86_binary_operator_ok (MINUS, SImode, operands)" 6761 "sub{l}\t{%2, %1|%1, %2}" 6762 [(set_attr "type" "alu") 6763 (set_attr "mode" "DI")]) 6764 6765(define_expand "subhi3" 6766 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "") 6767 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "") 6768 (match_operand:HI 2 "general_operand" ""))) 6769 (clobber (reg:CC FLAGS_REG))])] 6770 "TARGET_HIMODE_MATH" 6771 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;") 6772 6773(define_insn "*subhi_1" 6774 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 6775 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 6776 (match_operand:HI 2 "general_operand" "ri,rm"))) 6777 (clobber (reg:CC FLAGS_REG))] 6778 "ix86_binary_operator_ok (MINUS, HImode, operands)" 6779 "sub{w}\t{%2, %0|%0, %2}" 6780 [(set_attr "type" "alu") 6781 (set_attr "mode" "HI")]) 6782 6783(define_insn "*subhi_2" 6784 [(set (reg FLAGS_REG) 6785 (compare 6786 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 6787 (match_operand:HI 2 "general_operand" "ri,rm")) 6788 (const_int 0))) 6789 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 6790 (minus:HI (match_dup 1) (match_dup 2)))] 6791 "ix86_match_ccmode (insn, CCGOCmode) 6792 && ix86_binary_operator_ok (MINUS, HImode, operands)" 6793 "sub{w}\t{%2, %0|%0, %2}" 6794 [(set_attr "type" "alu") 6795 (set_attr "mode" "HI")]) 6796 6797(define_insn "*subhi_3" 6798 [(set (reg FLAGS_REG) 6799 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0") 6800 (match_operand:HI 2 "general_operand" "ri,rm"))) 6801 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 6802 (minus:HI (match_dup 1) (match_dup 2)))] 6803 "ix86_match_ccmode (insn, CCmode) 6804 && ix86_binary_operator_ok (MINUS, HImode, operands)" 6805 "sub{w}\t{%2, %0|%0, %2}" 6806 [(set_attr "type" "alu") 6807 (set_attr "mode" "HI")]) 6808 6809(define_expand "subqi3" 6810 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "") 6811 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "") 6812 (match_operand:QI 2 "general_operand" ""))) 6813 (clobber (reg:CC FLAGS_REG))])] 6814 "TARGET_QIMODE_MATH" 6815 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;") 6816 6817(define_insn "*subqi_1" 6818 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q") 6819 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 6820 (match_operand:QI 2 "general_operand" "qn,qmn"))) 6821 (clobber (reg:CC FLAGS_REG))] 6822 "ix86_binary_operator_ok (MINUS, QImode, operands)" 6823 "sub{b}\t{%2, %0|%0, %2}" 6824 [(set_attr "type" "alu") 6825 (set_attr "mode" "QI")]) 6826 6827(define_insn "*subqi_1_slp" 6828 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q")) 6829 (minus:QI (match_dup 0) 6830 (match_operand:QI 1 "general_operand" "qn,qmn"))) 6831 (clobber (reg:CC FLAGS_REG))] 6832 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 6833 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 6834 "sub{b}\t{%1, %0|%0, %1}" 6835 [(set_attr "type" "alu1") 6836 (set_attr "mode" "QI")]) 6837 6838(define_insn "*subqi_2" 6839 [(set (reg FLAGS_REG) 6840 (compare 6841 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 6842 (match_operand:QI 2 "general_operand" "qi,qm")) 6843 (const_int 0))) 6844 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q") 6845 (minus:HI (match_dup 1) (match_dup 2)))] 6846 "ix86_match_ccmode (insn, CCGOCmode) 6847 && ix86_binary_operator_ok (MINUS, QImode, operands)" 6848 "sub{b}\t{%2, %0|%0, %2}" 6849 [(set_attr "type" "alu") 6850 (set_attr "mode" "QI")]) 6851 6852(define_insn "*subqi_3" 6853 [(set (reg FLAGS_REG) 6854 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0") 6855 (match_operand:QI 2 "general_operand" "qi,qm"))) 6856 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q") 6857 (minus:HI (match_dup 1) (match_dup 2)))] 6858 "ix86_match_ccmode (insn, CCmode) 6859 && ix86_binary_operator_ok (MINUS, QImode, operands)" 6860 "sub{b}\t{%2, %0|%0, %2}" 6861 [(set_attr "type" "alu") 6862 (set_attr "mode" "QI")]) 6863 6864;; The patterns that match these are at the end of this file. 6865 6866(define_expand "subxf3" 6867 [(set (match_operand:XF 0 "register_operand" "") 6868 (minus:XF (match_operand:XF 1 "register_operand" "") 6869 (match_operand:XF 2 "register_operand" "")))] 6870 "TARGET_80387" 6871 "") 6872 6873(define_expand "subdf3" 6874 [(set (match_operand:DF 0 "register_operand" "") 6875 (minus:DF (match_operand:DF 1 "register_operand" "") 6876 (match_operand:DF 2 "nonimmediate_operand" "")))] 6877 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 6878 "") 6879 6880(define_expand "subsf3" 6881 [(set (match_operand:SF 0 "register_operand" "") 6882 (minus:SF (match_operand:SF 1 "register_operand" "") 6883 (match_operand:SF 2 "nonimmediate_operand" "")))] 6884 "TARGET_80387 || TARGET_SSE_MATH" 6885 "") 6886 6887;; Multiply instructions 6888 6889(define_expand "muldi3" 6890 [(parallel [(set (match_operand:DI 0 "register_operand" "") 6891 (mult:DI (match_operand:DI 1 "register_operand" "") 6892 (match_operand:DI 2 "x86_64_general_operand" ""))) 6893 (clobber (reg:CC FLAGS_REG))])] 6894 "TARGET_64BIT" 6895 "") 6896 6897;; On AMDFAM10 6898;; IMUL reg64, reg64, imm8 Direct 6899;; IMUL reg64, mem64, imm8 VectorPath 6900;; IMUL reg64, reg64, imm32 Direct 6901;; IMUL reg64, mem64, imm32 VectorPath 6902;; IMUL reg64, reg64 Direct 6903;; IMUL reg64, mem64 Direct 6904 6905(define_insn "*muldi3_1_rex64" 6906 [(set (match_operand:DI 0 "register_operand" "=r,r,r") 6907 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0") 6908 (match_operand:DI 2 "x86_64_general_operand" "K,e,mr"))) 6909 (clobber (reg:CC FLAGS_REG))] 6910 "TARGET_64BIT 6911 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 6912 "@ 6913 imul{q}\t{%2, %1, %0|%0, %1, %2} 6914 imul{q}\t{%2, %1, %0|%0, %1, %2} 6915 imul{q}\t{%2, %0|%0, %2}" 6916 [(set_attr "type" "imul") 6917 (set_attr "prefix_0f" "0,0,1") 6918 (set (attr "athlon_decode") 6919 (cond [(eq_attr "cpu" "athlon") 6920 (const_string "vector") 6921 (eq_attr "alternative" "1") 6922 (const_string "vector") 6923 (and (eq_attr "alternative" "2") 6924 (match_operand 1 "memory_operand" "")) 6925 (const_string "vector")] 6926 (const_string "direct"))) 6927 (set (attr "amdfam10_decode") 6928 (cond [(and (eq_attr "alternative" "0,1") 6929 (match_operand 1 "memory_operand" "")) 6930 (const_string "vector")] 6931 (const_string "direct"))) 6932 (set_attr "mode" "DI")]) 6933 6934(define_expand "mulsi3" 6935 [(parallel [(set (match_operand:SI 0 "register_operand" "") 6936 (mult:SI (match_operand:SI 1 "register_operand" "") 6937 (match_operand:SI 2 "general_operand" ""))) 6938 (clobber (reg:CC FLAGS_REG))])] 6939 "" 6940 "") 6941 6942;; On AMDFAM10 6943;; IMUL reg32, reg32, imm8 Direct 6944;; IMUL reg32, mem32, imm8 VectorPath 6945;; IMUL reg32, reg32, imm32 Direct 6946;; IMUL reg32, mem32, imm32 VectorPath 6947;; IMUL reg32, reg32 Direct 6948;; IMUL reg32, mem32 Direct 6949 6950(define_insn "*mulsi3_1" 6951 [(set (match_operand:SI 0 "register_operand" "=r,r,r") 6952 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0") 6953 (match_operand:SI 2 "general_operand" "K,i,mr"))) 6954 (clobber (reg:CC FLAGS_REG))] 6955 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM" 6956 "@ 6957 imul{l}\t{%2, %1, %0|%0, %1, %2} 6958 imul{l}\t{%2, %1, %0|%0, %1, %2} 6959 imul{l}\t{%2, %0|%0, %2}" 6960 [(set_attr "type" "imul") 6961 (set_attr "prefix_0f" "0,0,1") 6962 (set (attr "athlon_decode") 6963 (cond [(eq_attr "cpu" "athlon") 6964 (const_string "vector") 6965 (eq_attr "alternative" "1") 6966 (const_string "vector") 6967 (and (eq_attr "alternative" "2") 6968 (match_operand 1 "memory_operand" "")) 6969 (const_string "vector")] 6970 (const_string "direct"))) 6971 (set (attr "amdfam10_decode") 6972 (cond [(and (eq_attr "alternative" "0,1") 6973 (match_operand 1 "memory_operand" "")) 6974 (const_string "vector")] 6975 (const_string "direct"))) 6976 (set_attr "mode" "SI")]) 6977 6978(define_insn "*mulsi3_1_zext" 6979 [(set (match_operand:DI 0 "register_operand" "=r,r,r") 6980 (zero_extend:DI 6981 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0") 6982 (match_operand:SI 2 "general_operand" "K,i,mr")))) 6983 (clobber (reg:CC FLAGS_REG))] 6984 "TARGET_64BIT 6985 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 6986 "@ 6987 imul{l}\t{%2, %1, %k0|%k0, %1, %2} 6988 imul{l}\t{%2, %1, %k0|%k0, %1, %2} 6989 imul{l}\t{%2, %k0|%k0, %2}" 6990 [(set_attr "type" "imul") 6991 (set_attr "prefix_0f" "0,0,1") 6992 (set (attr "athlon_decode") 6993 (cond [(eq_attr "cpu" "athlon") 6994 (const_string "vector") 6995 (eq_attr "alternative" "1") 6996 (const_string "vector") 6997 (and (eq_attr "alternative" "2") 6998 (match_operand 1 "memory_operand" "")) 6999 (const_string "vector")] 7000 (const_string "direct"))) 7001 (set (attr "amdfam10_decode") 7002 (cond [(and (eq_attr "alternative" "0,1") 7003 (match_operand 1 "memory_operand" "")) 7004 (const_string "vector")] 7005 (const_string "direct"))) 7006 (set_attr "mode" "SI")]) 7007 7008(define_expand "mulhi3" 7009 [(parallel [(set (match_operand:HI 0 "register_operand" "") 7010 (mult:HI (match_operand:HI 1 "register_operand" "") 7011 (match_operand:HI 2 "general_operand" ""))) 7012 (clobber (reg:CC FLAGS_REG))])] 7013 "TARGET_HIMODE_MATH" 7014 "") 7015 7016;; On AMDFAM10 7017;; IMUL reg16, reg16, imm8 VectorPath 7018;; IMUL reg16, mem16, imm8 VectorPath 7019;; IMUL reg16, reg16, imm16 VectorPath 7020;; IMUL reg16, mem16, imm16 VectorPath 7021;; IMUL reg16, reg16 Direct 7022;; IMUL reg16, mem16 Direct 7023(define_insn "*mulhi3_1" 7024 [(set (match_operand:HI 0 "register_operand" "=r,r,r") 7025 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0") 7026 (match_operand:HI 2 "general_operand" "K,i,mr"))) 7027 (clobber (reg:CC FLAGS_REG))] 7028 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM" 7029 "@ 7030 imul{w}\t{%2, %1, %0|%0, %1, %2} 7031 imul{w}\t{%2, %1, %0|%0, %1, %2} 7032 imul{w}\t{%2, %0|%0, %2}" 7033 [(set_attr "type" "imul") 7034 (set_attr "prefix_0f" "0,0,1") 7035 (set (attr "athlon_decode") 7036 (cond [(eq_attr "cpu" "athlon") 7037 (const_string "vector") 7038 (eq_attr "alternative" "1,2") 7039 (const_string "vector")] 7040 (const_string "direct"))) 7041 (set (attr "amdfam10_decode") 7042 (cond [(eq_attr "alternative" "0,1") 7043 (const_string "vector")] 7044 (const_string "direct"))) 7045 (set_attr "mode" "HI")]) 7046 7047(define_expand "mulqi3" 7048 [(parallel [(set (match_operand:QI 0 "register_operand" "") 7049 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "") 7050 (match_operand:QI 2 "register_operand" ""))) 7051 (clobber (reg:CC FLAGS_REG))])] 7052 "TARGET_QIMODE_MATH" 7053 "") 7054 7055;;On AMDFAM10 7056;; MUL reg8 Direct 7057;; MUL mem8 Direct 7058 7059(define_insn "*mulqi3_1" 7060 [(set (match_operand:QI 0 "register_operand" "=a") 7061 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0") 7062 (match_operand:QI 2 "nonimmediate_operand" "qm"))) 7063 (clobber (reg:CC FLAGS_REG))] 7064 "TARGET_QIMODE_MATH 7065 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7066 "mul{b}\t%2" 7067 [(set_attr "type" "imul") 7068 (set_attr "length_immediate" "0") 7069 (set (attr "athlon_decode") 7070 (if_then_else (eq_attr "cpu" "athlon") 7071 (const_string "vector") 7072 (const_string "direct"))) 7073 (set_attr "amdfam10_decode" "direct") 7074 (set_attr "mode" "QI")]) 7075 7076(define_expand "umulqihi3" 7077 [(parallel [(set (match_operand:HI 0 "register_operand" "") 7078 (mult:HI (zero_extend:HI 7079 (match_operand:QI 1 "nonimmediate_operand" "")) 7080 (zero_extend:HI 7081 (match_operand:QI 2 "register_operand" "")))) 7082 (clobber (reg:CC FLAGS_REG))])] 7083 "TARGET_QIMODE_MATH" 7084 "") 7085 7086(define_insn "*umulqihi3_1" 7087 [(set (match_operand:HI 0 "register_operand" "=a") 7088 (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0")) 7089 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm")))) 7090 (clobber (reg:CC FLAGS_REG))] 7091 "TARGET_QIMODE_MATH 7092 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7093 "mul{b}\t%2" 7094 [(set_attr "type" "imul") 7095 (set_attr "length_immediate" "0") 7096 (set (attr "athlon_decode") 7097 (if_then_else (eq_attr "cpu" "athlon") 7098 (const_string "vector") 7099 (const_string "direct"))) 7100 (set_attr "amdfam10_decode" "direct") 7101 (set_attr "mode" "QI")]) 7102 7103(define_expand "mulqihi3" 7104 [(parallel [(set (match_operand:HI 0 "register_operand" "") 7105 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")) 7106 (sign_extend:HI (match_operand:QI 2 "register_operand" "")))) 7107 (clobber (reg:CC FLAGS_REG))])] 7108 "TARGET_QIMODE_MATH" 7109 "") 7110 7111(define_insn "*mulqihi3_insn" 7112 [(set (match_operand:HI 0 "register_operand" "=a") 7113 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0")) 7114 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm")))) 7115 (clobber (reg:CC FLAGS_REG))] 7116 "TARGET_QIMODE_MATH 7117 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7118 "imul{b}\t%2" 7119 [(set_attr "type" "imul") 7120 (set_attr "length_immediate" "0") 7121 (set (attr "athlon_decode") 7122 (if_then_else (eq_attr "cpu" "athlon") 7123 (const_string "vector") 7124 (const_string "direct"))) 7125 (set_attr "amdfam10_decode" "direct") 7126 (set_attr "mode" "QI")]) 7127 7128(define_expand "umulditi3" 7129 [(parallel [(set (match_operand:TI 0 "register_operand" "") 7130 (mult:TI (zero_extend:TI 7131 (match_operand:DI 1 "nonimmediate_operand" "")) 7132 (zero_extend:TI 7133 (match_operand:DI 2 "register_operand" "")))) 7134 (clobber (reg:CC FLAGS_REG))])] 7135 "TARGET_64BIT" 7136 "") 7137 7138(define_insn "*umulditi3_insn" 7139 [(set (match_operand:TI 0 "register_operand" "=A") 7140 (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0")) 7141 (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm")))) 7142 (clobber (reg:CC FLAGS_REG))] 7143 "TARGET_64BIT 7144 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7145 "mul{q}\t%2" 7146 [(set_attr "type" "imul") 7147 (set_attr "length_immediate" "0") 7148 (set (attr "athlon_decode") 7149 (if_then_else (eq_attr "cpu" "athlon") 7150 (const_string "vector") 7151 (const_string "double"))) 7152 (set_attr "amdfam10_decode" "double") 7153 (set_attr "mode" "DI")]) 7154 7155;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers 7156(define_expand "umulsidi3" 7157 [(parallel [(set (match_operand:DI 0 "register_operand" "") 7158 (mult:DI (zero_extend:DI 7159 (match_operand:SI 1 "nonimmediate_operand" "")) 7160 (zero_extend:DI 7161 (match_operand:SI 2 "register_operand" "")))) 7162 (clobber (reg:CC FLAGS_REG))])] 7163 "!TARGET_64BIT" 7164 "") 7165 7166(define_insn "*umulsidi3_insn" 7167 [(set (match_operand:DI 0 "register_operand" "=A") 7168 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0")) 7169 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm")))) 7170 (clobber (reg:CC FLAGS_REG))] 7171 "!TARGET_64BIT 7172 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7173 "mul{l}\t%2" 7174 [(set_attr "type" "imul") 7175 (set_attr "length_immediate" "0") 7176 (set (attr "athlon_decode") 7177 (if_then_else (eq_attr "cpu" "athlon") 7178 (const_string "vector") 7179 (const_string "double"))) 7180 (set_attr "amdfam10_decode" "double") 7181 (set_attr "mode" "SI")]) 7182 7183(define_expand "mulditi3" 7184 [(parallel [(set (match_operand:TI 0 "register_operand" "") 7185 (mult:TI (sign_extend:TI 7186 (match_operand:DI 1 "nonimmediate_operand" "")) 7187 (sign_extend:TI 7188 (match_operand:DI 2 "register_operand" "")))) 7189 (clobber (reg:CC FLAGS_REG))])] 7190 "TARGET_64BIT" 7191 "") 7192 7193(define_insn "*mulditi3_insn" 7194 [(set (match_operand:TI 0 "register_operand" "=A") 7195 (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0")) 7196 (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm")))) 7197 (clobber (reg:CC FLAGS_REG))] 7198 "TARGET_64BIT 7199 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7200 "imul{q}\t%2" 7201 [(set_attr "type" "imul") 7202 (set_attr "length_immediate" "0") 7203 (set (attr "athlon_decode") 7204 (if_then_else (eq_attr "cpu" "athlon") 7205 (const_string "vector") 7206 (const_string "double"))) 7207 (set_attr "amdfam10_decode" "double") 7208 (set_attr "mode" "DI")]) 7209 7210(define_expand "mulsidi3" 7211 [(parallel [(set (match_operand:DI 0 "register_operand" "") 7212 (mult:DI (sign_extend:DI 7213 (match_operand:SI 1 "nonimmediate_operand" "")) 7214 (sign_extend:DI 7215 (match_operand:SI 2 "register_operand" "")))) 7216 (clobber (reg:CC FLAGS_REG))])] 7217 "!TARGET_64BIT" 7218 "") 7219 7220(define_insn "*mulsidi3_insn" 7221 [(set (match_operand:DI 0 "register_operand" "=A") 7222 (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0")) 7223 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm")))) 7224 (clobber (reg:CC FLAGS_REG))] 7225 "!TARGET_64BIT 7226 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7227 "imul{l}\t%2" 7228 [(set_attr "type" "imul") 7229 (set_attr "length_immediate" "0") 7230 (set (attr "athlon_decode") 7231 (if_then_else (eq_attr "cpu" "athlon") 7232 (const_string "vector") 7233 (const_string "double"))) 7234 (set_attr "amdfam10_decode" "double") 7235 (set_attr "mode" "SI")]) 7236 7237(define_expand "umuldi3_highpart" 7238 [(parallel [(set (match_operand:DI 0 "register_operand" "") 7239 (truncate:DI 7240 (lshiftrt:TI 7241 (mult:TI (zero_extend:TI 7242 (match_operand:DI 1 "nonimmediate_operand" "")) 7243 (zero_extend:TI 7244 (match_operand:DI 2 "register_operand" ""))) 7245 (const_int 64)))) 7246 (clobber (match_scratch:DI 3 "")) 7247 (clobber (reg:CC FLAGS_REG))])] 7248 "TARGET_64BIT" 7249 "") 7250 7251(define_insn "*umuldi3_highpart_rex64" 7252 [(set (match_operand:DI 0 "register_operand" "=d") 7253 (truncate:DI 7254 (lshiftrt:TI 7255 (mult:TI (zero_extend:TI 7256 (match_operand:DI 1 "nonimmediate_operand" "%a")) 7257 (zero_extend:TI 7258 (match_operand:DI 2 "nonimmediate_operand" "rm"))) 7259 (const_int 64)))) 7260 (clobber (match_scratch:DI 3 "=1")) 7261 (clobber (reg:CC FLAGS_REG))] 7262 "TARGET_64BIT 7263 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7264 "mul{q}\t%2" 7265 [(set_attr "type" "imul") 7266 (set_attr "length_immediate" "0") 7267 (set (attr "athlon_decode") 7268 (if_then_else (eq_attr "cpu" "athlon") 7269 (const_string "vector") 7270 (const_string "double"))) 7271 (set_attr "amdfam10_decode" "double") 7272 (set_attr "mode" "DI")]) 7273 7274(define_expand "umulsi3_highpart" 7275 [(parallel [(set (match_operand:SI 0 "register_operand" "") 7276 (truncate:SI 7277 (lshiftrt:DI 7278 (mult:DI (zero_extend:DI 7279 (match_operand:SI 1 "nonimmediate_operand" "")) 7280 (zero_extend:DI 7281 (match_operand:SI 2 "register_operand" ""))) 7282 (const_int 32)))) 7283 (clobber (match_scratch:SI 3 "")) 7284 (clobber (reg:CC FLAGS_REG))])] 7285 "" 7286 "") 7287 7288(define_insn "*umulsi3_highpart_insn" 7289 [(set (match_operand:SI 0 "register_operand" "=d") 7290 (truncate:SI 7291 (lshiftrt:DI 7292 (mult:DI (zero_extend:DI 7293 (match_operand:SI 1 "nonimmediate_operand" "%a")) 7294 (zero_extend:DI 7295 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7296 (const_int 32)))) 7297 (clobber (match_scratch:SI 3 "=1")) 7298 (clobber (reg:CC FLAGS_REG))] 7299 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM" 7300 "mul{l}\t%2" 7301 [(set_attr "type" "imul") 7302 (set_attr "length_immediate" "0") 7303 (set (attr "athlon_decode") 7304 (if_then_else (eq_attr "cpu" "athlon") 7305 (const_string "vector") 7306 (const_string "double"))) 7307 (set_attr "amdfam10_decode" "double") 7308 (set_attr "mode" "SI")]) 7309 7310(define_insn "*umulsi3_highpart_zext" 7311 [(set (match_operand:DI 0 "register_operand" "=d") 7312 (zero_extend:DI (truncate:SI 7313 (lshiftrt:DI 7314 (mult:DI (zero_extend:DI 7315 (match_operand:SI 1 "nonimmediate_operand" "%a")) 7316 (zero_extend:DI 7317 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7318 (const_int 32))))) 7319 (clobber (match_scratch:SI 3 "=1")) 7320 (clobber (reg:CC FLAGS_REG))] 7321 "TARGET_64BIT 7322 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7323 "mul{l}\t%2" 7324 [(set_attr "type" "imul") 7325 (set_attr "length_immediate" "0") 7326 (set (attr "athlon_decode") 7327 (if_then_else (eq_attr "cpu" "athlon") 7328 (const_string "vector") 7329 (const_string "double"))) 7330 (set_attr "amdfam10_decode" "double") 7331 (set_attr "mode" "SI")]) 7332 7333(define_expand "smuldi3_highpart" 7334 [(parallel [(set (match_operand:DI 0 "register_operand" "=d") 7335 (truncate:DI 7336 (lshiftrt:TI 7337 (mult:TI (sign_extend:TI 7338 (match_operand:DI 1 "nonimmediate_operand" "")) 7339 (sign_extend:TI 7340 (match_operand:DI 2 "register_operand" ""))) 7341 (const_int 64)))) 7342 (clobber (match_scratch:DI 3 "")) 7343 (clobber (reg:CC FLAGS_REG))])] 7344 "TARGET_64BIT" 7345 "") 7346 7347(define_insn "*smuldi3_highpart_rex64" 7348 [(set (match_operand:DI 0 "register_operand" "=d") 7349 (truncate:DI 7350 (lshiftrt:TI 7351 (mult:TI (sign_extend:TI 7352 (match_operand:DI 1 "nonimmediate_operand" "%a")) 7353 (sign_extend:TI 7354 (match_operand:DI 2 "nonimmediate_operand" "rm"))) 7355 (const_int 64)))) 7356 (clobber (match_scratch:DI 3 "=1")) 7357 (clobber (reg:CC FLAGS_REG))] 7358 "TARGET_64BIT 7359 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7360 "imul{q}\t%2" 7361 [(set_attr "type" "imul") 7362 (set (attr "athlon_decode") 7363 (if_then_else (eq_attr "cpu" "athlon") 7364 (const_string "vector") 7365 (const_string "double"))) 7366 (set_attr "amdfam10_decode" "double") 7367 (set_attr "mode" "DI")]) 7368 7369(define_expand "smulsi3_highpart" 7370 [(parallel [(set (match_operand:SI 0 "register_operand" "") 7371 (truncate:SI 7372 (lshiftrt:DI 7373 (mult:DI (sign_extend:DI 7374 (match_operand:SI 1 "nonimmediate_operand" "")) 7375 (sign_extend:DI 7376 (match_operand:SI 2 "register_operand" ""))) 7377 (const_int 32)))) 7378 (clobber (match_scratch:SI 3 "")) 7379 (clobber (reg:CC FLAGS_REG))])] 7380 "" 7381 "") 7382 7383(define_insn "*smulsi3_highpart_insn" 7384 [(set (match_operand:SI 0 "register_operand" "=d") 7385 (truncate:SI 7386 (lshiftrt:DI 7387 (mult:DI (sign_extend:DI 7388 (match_operand:SI 1 "nonimmediate_operand" "%a")) 7389 (sign_extend:DI 7390 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7391 (const_int 32)))) 7392 (clobber (match_scratch:SI 3 "=1")) 7393 (clobber (reg:CC FLAGS_REG))] 7394 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM" 7395 "imul{l}\t%2" 7396 [(set_attr "type" "imul") 7397 (set (attr "athlon_decode") 7398 (if_then_else (eq_attr "cpu" "athlon") 7399 (const_string "vector") 7400 (const_string "double"))) 7401 (set_attr "amdfam10_decode" "double") 7402 (set_attr "mode" "SI")]) 7403 7404(define_insn "*smulsi3_highpart_zext" 7405 [(set (match_operand:DI 0 "register_operand" "=d") 7406 (zero_extend:DI (truncate:SI 7407 (lshiftrt:DI 7408 (mult:DI (sign_extend:DI 7409 (match_operand:SI 1 "nonimmediate_operand" "%a")) 7410 (sign_extend:DI 7411 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7412 (const_int 32))))) 7413 (clobber (match_scratch:SI 3 "=1")) 7414 (clobber (reg:CC FLAGS_REG))] 7415 "TARGET_64BIT 7416 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 7417 "imul{l}\t%2" 7418 [(set_attr "type" "imul") 7419 (set (attr "athlon_decode") 7420 (if_then_else (eq_attr "cpu" "athlon") 7421 (const_string "vector") 7422 (const_string "double"))) 7423 (set_attr "amdfam10_decode" "double") 7424 (set_attr "mode" "SI")]) 7425 7426;; The patterns that match these are at the end of this file. 7427 7428(define_expand "mulxf3" 7429 [(set (match_operand:XF 0 "register_operand" "") 7430 (mult:XF (match_operand:XF 1 "register_operand" "") 7431 (match_operand:XF 2 "register_operand" "")))] 7432 "TARGET_80387" 7433 "") 7434 7435(define_expand "muldf3" 7436 [(set (match_operand:DF 0 "register_operand" "") 7437 (mult:DF (match_operand:DF 1 "register_operand" "") 7438 (match_operand:DF 2 "nonimmediate_operand" "")))] 7439 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 7440 "") 7441 7442(define_expand "mulsf3" 7443 [(set (match_operand:SF 0 "register_operand" "") 7444 (mult:SF (match_operand:SF 1 "register_operand" "") 7445 (match_operand:SF 2 "nonimmediate_operand" "")))] 7446 "TARGET_80387 || TARGET_SSE_MATH" 7447 "") 7448 7449;; Divide instructions 7450 7451(define_insn "divqi3" 7452 [(set (match_operand:QI 0 "register_operand" "=a") 7453 (div:QI (match_operand:HI 1 "register_operand" "0") 7454 (match_operand:QI 2 "nonimmediate_operand" "qm"))) 7455 (clobber (reg:CC FLAGS_REG))] 7456 "TARGET_QIMODE_MATH" 7457 "idiv{b}\t%2" 7458 [(set_attr "type" "idiv") 7459 (set_attr "mode" "QI")]) 7460 7461(define_insn "udivqi3" 7462 [(set (match_operand:QI 0 "register_operand" "=a") 7463 (udiv:QI (match_operand:HI 1 "register_operand" "0") 7464 (match_operand:QI 2 "nonimmediate_operand" "qm"))) 7465 (clobber (reg:CC FLAGS_REG))] 7466 "TARGET_QIMODE_MATH" 7467 "div{b}\t%2" 7468 [(set_attr "type" "idiv") 7469 (set_attr "mode" "QI")]) 7470 7471;; The patterns that match these are at the end of this file. 7472 7473(define_expand "divxf3" 7474 [(set (match_operand:XF 0 "register_operand" "") 7475 (div:XF (match_operand:XF 1 "register_operand" "") 7476 (match_operand:XF 2 "register_operand" "")))] 7477 "TARGET_80387" 7478 "") 7479 7480(define_expand "divdf3" 7481 [(set (match_operand:DF 0 "register_operand" "") 7482 (div:DF (match_operand:DF 1 "register_operand" "") 7483 (match_operand:DF 2 "nonimmediate_operand" "")))] 7484 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 7485 "") 7486 7487(define_expand "divsf3" 7488 [(set (match_operand:SF 0 "register_operand" "") 7489 (div:SF (match_operand:SF 1 "register_operand" "") 7490 (match_operand:SF 2 "nonimmediate_operand" "")))] 7491 "TARGET_80387 || TARGET_SSE_MATH" 7492 "") 7493 7494;; Remainder instructions. 7495 7496(define_expand "divmoddi4" 7497 [(parallel [(set (match_operand:DI 0 "register_operand" "") 7498 (div:DI (match_operand:DI 1 "register_operand" "") 7499 (match_operand:DI 2 "nonimmediate_operand" ""))) 7500 (set (match_operand:DI 3 "register_operand" "") 7501 (mod:DI (match_dup 1) (match_dup 2))) 7502 (clobber (reg:CC FLAGS_REG))])] 7503 "TARGET_64BIT" 7504 "") 7505 7506;; Allow to come the parameter in eax or edx to avoid extra moves. 7507;; Penalize eax case slightly because it results in worse scheduling 7508;; of code. 7509(define_insn "*divmoddi4_nocltd_rex64" 7510 [(set (match_operand:DI 0 "register_operand" "=&a,?a") 7511 (div:DI (match_operand:DI 2 "register_operand" "1,0") 7512 (match_operand:DI 3 "nonimmediate_operand" "rm,rm"))) 7513 (set (match_operand:DI 1 "register_operand" "=&d,&d") 7514 (mod:DI (match_dup 2) (match_dup 3))) 7515 (clobber (reg:CC FLAGS_REG))] 7516 "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD" 7517 "#" 7518 [(set_attr "type" "multi")]) 7519 7520(define_insn "*divmoddi4_cltd_rex64" 7521 [(set (match_operand:DI 0 "register_operand" "=a") 7522 (div:DI (match_operand:DI 2 "register_operand" "a") 7523 (match_operand:DI 3 "nonimmediate_operand" "rm"))) 7524 (set (match_operand:DI 1 "register_operand" "=&d") 7525 (mod:DI (match_dup 2) (match_dup 3))) 7526 (clobber (reg:CC FLAGS_REG))] 7527 "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)" 7528 "#" 7529 [(set_attr "type" "multi")]) 7530 7531(define_insn "*divmoddi_noext_rex64" 7532 [(set (match_operand:DI 0 "register_operand" "=a") 7533 (div:DI (match_operand:DI 1 "register_operand" "0") 7534 (match_operand:DI 2 "nonimmediate_operand" "rm"))) 7535 (set (match_operand:DI 3 "register_operand" "=d") 7536 (mod:DI (match_dup 1) (match_dup 2))) 7537 (use (match_operand:DI 4 "register_operand" "3")) 7538 (clobber (reg:CC FLAGS_REG))] 7539 "TARGET_64BIT" 7540 "idiv{q}\t%2" 7541 [(set_attr "type" "idiv") 7542 (set_attr "mode" "DI")]) 7543 7544(define_split 7545 [(set (match_operand:DI 0 "register_operand" "") 7546 (div:DI (match_operand:DI 1 "register_operand" "") 7547 (match_operand:DI 2 "nonimmediate_operand" ""))) 7548 (set (match_operand:DI 3 "register_operand" "") 7549 (mod:DI (match_dup 1) (match_dup 2))) 7550 (clobber (reg:CC FLAGS_REG))] 7551 "TARGET_64BIT && reload_completed" 7552 [(parallel [(set (match_dup 3) 7553 (ashiftrt:DI (match_dup 4) (const_int 63))) 7554 (clobber (reg:CC FLAGS_REG))]) 7555 (parallel [(set (match_dup 0) 7556 (div:DI (reg:DI 0) (match_dup 2))) 7557 (set (match_dup 3) 7558 (mod:DI (reg:DI 0) (match_dup 2))) 7559 (use (match_dup 3)) 7560 (clobber (reg:CC FLAGS_REG))])] 7561{ 7562 /* Avoid use of cltd in favor of a mov+shift. */ 7563 if (!TARGET_USE_CLTD && !optimize_size) 7564 { 7565 if (true_regnum (operands[1])) 7566 emit_move_insn (operands[0], operands[1]); 7567 else 7568 emit_move_insn (operands[3], operands[1]); 7569 operands[4] = operands[3]; 7570 } 7571 else 7572 { 7573 gcc_assert (!true_regnum (operands[1])); 7574 operands[4] = operands[1]; 7575 } 7576}) 7577 7578 7579(define_expand "divmodsi4" 7580 [(parallel [(set (match_operand:SI 0 "register_operand" "") 7581 (div:SI (match_operand:SI 1 "register_operand" "") 7582 (match_operand:SI 2 "nonimmediate_operand" ""))) 7583 (set (match_operand:SI 3 "register_operand" "") 7584 (mod:SI (match_dup 1) (match_dup 2))) 7585 (clobber (reg:CC FLAGS_REG))])] 7586 "" 7587 "") 7588 7589;; Allow to come the parameter in eax or edx to avoid extra moves. 7590;; Penalize eax case slightly because it results in worse scheduling 7591;; of code. 7592(define_insn "*divmodsi4_nocltd" 7593 [(set (match_operand:SI 0 "register_operand" "=&a,?a") 7594 (div:SI (match_operand:SI 2 "register_operand" "1,0") 7595 (match_operand:SI 3 "nonimmediate_operand" "rm,rm"))) 7596 (set (match_operand:SI 1 "register_operand" "=&d,&d") 7597 (mod:SI (match_dup 2) (match_dup 3))) 7598 (clobber (reg:CC FLAGS_REG))] 7599 "!optimize_size && !TARGET_USE_CLTD" 7600 "#" 7601 [(set_attr "type" "multi")]) 7602 7603(define_insn "*divmodsi4_cltd" 7604 [(set (match_operand:SI 0 "register_operand" "=a") 7605 (div:SI (match_operand:SI 2 "register_operand" "a") 7606 (match_operand:SI 3 "nonimmediate_operand" "rm"))) 7607 (set (match_operand:SI 1 "register_operand" "=&d") 7608 (mod:SI (match_dup 2) (match_dup 3))) 7609 (clobber (reg:CC FLAGS_REG))] 7610 "optimize_size || TARGET_USE_CLTD" 7611 "#" 7612 [(set_attr "type" "multi")]) 7613 7614(define_insn "*divmodsi_noext" 7615 [(set (match_operand:SI 0 "register_operand" "=a") 7616 (div:SI (match_operand:SI 1 "register_operand" "0") 7617 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7618 (set (match_operand:SI 3 "register_operand" "=d") 7619 (mod:SI (match_dup 1) (match_dup 2))) 7620 (use (match_operand:SI 4 "register_operand" "3")) 7621 (clobber (reg:CC FLAGS_REG))] 7622 "" 7623 "idiv{l}\t%2" 7624 [(set_attr "type" "idiv") 7625 (set_attr "mode" "SI")]) 7626 7627(define_split 7628 [(set (match_operand:SI 0 "register_operand" "") 7629 (div:SI (match_operand:SI 1 "register_operand" "") 7630 (match_operand:SI 2 "nonimmediate_operand" ""))) 7631 (set (match_operand:SI 3 "register_operand" "") 7632 (mod:SI (match_dup 1) (match_dup 2))) 7633 (clobber (reg:CC FLAGS_REG))] 7634 "reload_completed" 7635 [(parallel [(set (match_dup 3) 7636 (ashiftrt:SI (match_dup 4) (const_int 31))) 7637 (clobber (reg:CC FLAGS_REG))]) 7638 (parallel [(set (match_dup 0) 7639 (div:SI (reg:SI 0) (match_dup 2))) 7640 (set (match_dup 3) 7641 (mod:SI (reg:SI 0) (match_dup 2))) 7642 (use (match_dup 3)) 7643 (clobber (reg:CC FLAGS_REG))])] 7644{ 7645 /* Avoid use of cltd in favor of a mov+shift. */ 7646 if (!TARGET_USE_CLTD && !optimize_size) 7647 { 7648 if (true_regnum (operands[1])) 7649 emit_move_insn (operands[0], operands[1]); 7650 else 7651 emit_move_insn (operands[3], operands[1]); 7652 operands[4] = operands[3]; 7653 } 7654 else 7655 { 7656 gcc_assert (!true_regnum (operands[1])); 7657 operands[4] = operands[1]; 7658 } 7659}) 7660;; %%% Split me. 7661(define_insn "divmodhi4" 7662 [(set (match_operand:HI 0 "register_operand" "=a") 7663 (div:HI (match_operand:HI 1 "register_operand" "0") 7664 (match_operand:HI 2 "nonimmediate_operand" "rm"))) 7665 (set (match_operand:HI 3 "register_operand" "=&d") 7666 (mod:HI (match_dup 1) (match_dup 2))) 7667 (clobber (reg:CC FLAGS_REG))] 7668 "TARGET_HIMODE_MATH" 7669 "cwtd\;idiv{w}\t%2" 7670 [(set_attr "type" "multi") 7671 (set_attr "length_immediate" "0") 7672 (set_attr "mode" "SI")]) 7673 7674(define_insn "udivmoddi4" 7675 [(set (match_operand:DI 0 "register_operand" "=a") 7676 (udiv:DI (match_operand:DI 1 "register_operand" "0") 7677 (match_operand:DI 2 "nonimmediate_operand" "rm"))) 7678 (set (match_operand:DI 3 "register_operand" "=&d") 7679 (umod:DI (match_dup 1) (match_dup 2))) 7680 (clobber (reg:CC FLAGS_REG))] 7681 "TARGET_64BIT" 7682 "xor{q}\t%3, %3\;div{q}\t%2" 7683 [(set_attr "type" "multi") 7684 (set_attr "length_immediate" "0") 7685 (set_attr "mode" "DI")]) 7686 7687(define_insn "*udivmoddi4_noext" 7688 [(set (match_operand:DI 0 "register_operand" "=a") 7689 (udiv:DI (match_operand:DI 1 "register_operand" "0") 7690 (match_operand:DI 2 "nonimmediate_operand" "rm"))) 7691 (set (match_operand:DI 3 "register_operand" "=d") 7692 (umod:DI (match_dup 1) (match_dup 2))) 7693 (use (match_dup 3)) 7694 (clobber (reg:CC FLAGS_REG))] 7695 "TARGET_64BIT" 7696 "div{q}\t%2" 7697 [(set_attr "type" "idiv") 7698 (set_attr "mode" "DI")]) 7699 7700(define_split 7701 [(set (match_operand:DI 0 "register_operand" "") 7702 (udiv:DI (match_operand:DI 1 "register_operand" "") 7703 (match_operand:DI 2 "nonimmediate_operand" ""))) 7704 (set (match_operand:DI 3 "register_operand" "") 7705 (umod:DI (match_dup 1) (match_dup 2))) 7706 (clobber (reg:CC FLAGS_REG))] 7707 "TARGET_64BIT && reload_completed" 7708 [(set (match_dup 3) (const_int 0)) 7709 (parallel [(set (match_dup 0) 7710 (udiv:DI (match_dup 1) (match_dup 2))) 7711 (set (match_dup 3) 7712 (umod:DI (match_dup 1) (match_dup 2))) 7713 (use (match_dup 3)) 7714 (clobber (reg:CC FLAGS_REG))])] 7715 "") 7716 7717(define_insn "udivmodsi4" 7718 [(set (match_operand:SI 0 "register_operand" "=a") 7719 (udiv:SI (match_operand:SI 1 "register_operand" "0") 7720 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7721 (set (match_operand:SI 3 "register_operand" "=&d") 7722 (umod:SI (match_dup 1) (match_dup 2))) 7723 (clobber (reg:CC FLAGS_REG))] 7724 "" 7725 "xor{l}\t%3, %3\;div{l}\t%2" 7726 [(set_attr "type" "multi") 7727 (set_attr "length_immediate" "0") 7728 (set_attr "mode" "SI")]) 7729 7730(define_insn "*udivmodsi4_noext" 7731 [(set (match_operand:SI 0 "register_operand" "=a") 7732 (udiv:SI (match_operand:SI 1 "register_operand" "0") 7733 (match_operand:SI 2 "nonimmediate_operand" "rm"))) 7734 (set (match_operand:SI 3 "register_operand" "=d") 7735 (umod:SI (match_dup 1) (match_dup 2))) 7736 (use (match_dup 3)) 7737 (clobber (reg:CC FLAGS_REG))] 7738 "" 7739 "div{l}\t%2" 7740 [(set_attr "type" "idiv") 7741 (set_attr "mode" "SI")]) 7742 7743(define_split 7744 [(set (match_operand:SI 0 "register_operand" "") 7745 (udiv:SI (match_operand:SI 1 "register_operand" "") 7746 (match_operand:SI 2 "nonimmediate_operand" ""))) 7747 (set (match_operand:SI 3 "register_operand" "") 7748 (umod:SI (match_dup 1) (match_dup 2))) 7749 (clobber (reg:CC FLAGS_REG))] 7750 "reload_completed" 7751 [(set (match_dup 3) (const_int 0)) 7752 (parallel [(set (match_dup 0) 7753 (udiv:SI (match_dup 1) (match_dup 2))) 7754 (set (match_dup 3) 7755 (umod:SI (match_dup 1) (match_dup 2))) 7756 (use (match_dup 3)) 7757 (clobber (reg:CC FLAGS_REG))])] 7758 "") 7759 7760(define_expand "udivmodhi4" 7761 [(set (match_dup 4) (const_int 0)) 7762 (parallel [(set (match_operand:HI 0 "register_operand" "") 7763 (udiv:HI (match_operand:HI 1 "register_operand" "") 7764 (match_operand:HI 2 "nonimmediate_operand" ""))) 7765 (set (match_operand:HI 3 "register_operand" "") 7766 (umod:HI (match_dup 1) (match_dup 2))) 7767 (use (match_dup 4)) 7768 (clobber (reg:CC FLAGS_REG))])] 7769 "TARGET_HIMODE_MATH" 7770 "operands[4] = gen_reg_rtx (HImode);") 7771 7772(define_insn "*udivmodhi_noext" 7773 [(set (match_operand:HI 0 "register_operand" "=a") 7774 (udiv:HI (match_operand:HI 1 "register_operand" "0") 7775 (match_operand:HI 2 "nonimmediate_operand" "rm"))) 7776 (set (match_operand:HI 3 "register_operand" "=d") 7777 (umod:HI (match_dup 1) (match_dup 2))) 7778 (use (match_operand:HI 4 "register_operand" "3")) 7779 (clobber (reg:CC FLAGS_REG))] 7780 "" 7781 "div{w}\t%2" 7782 [(set_attr "type" "idiv") 7783 (set_attr "mode" "HI")]) 7784 7785;; We cannot use div/idiv for double division, because it causes 7786;; "division by zero" on the overflow and that's not what we expect 7787;; from truncate. Because true (non truncating) double division is 7788;; never generated, we can't create this insn anyway. 7789; 7790;(define_insn "" 7791; [(set (match_operand:SI 0 "register_operand" "=a") 7792; (truncate:SI 7793; (udiv:DI (match_operand:DI 1 "register_operand" "A") 7794; (zero_extend:DI 7795; (match_operand:SI 2 "nonimmediate_operand" "rm"))))) 7796; (set (match_operand:SI 3 "register_operand" "=d") 7797; (truncate:SI 7798; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2))))) 7799; (clobber (reg:CC FLAGS_REG))] 7800; "" 7801; "div{l}\t{%2, %0|%0, %2}" 7802; [(set_attr "type" "idiv")]) 7803 7804;;- Logical AND instructions 7805 7806;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al. 7807;; Note that this excludes ah. 7808 7809(define_insn "*testdi_1_rex64" 7810 [(set (reg FLAGS_REG) 7811 (compare 7812 (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm") 7813 (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re")) 7814 (const_int 0)))] 7815 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 7816 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 7817 "@ 7818 test{l}\t{%k1, %k0|%k0, %k1} 7819 test{l}\t{%k1, %k0|%k0, %k1} 7820 test{q}\t{%1, %0|%0, %1} 7821 test{q}\t{%1, %0|%0, %1} 7822 test{q}\t{%1, %0|%0, %1}" 7823 [(set_attr "type" "test") 7824 (set_attr "modrm" "0,1,0,1,1") 7825 (set_attr "mode" "SI,SI,DI,DI,DI") 7826 (set_attr "pent_pair" "uv,np,uv,np,uv")]) 7827 7828(define_insn "testsi_1" 7829 [(set (reg FLAGS_REG) 7830 (compare 7831 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm") 7832 (match_operand:SI 1 "general_operand" "in,in,rin")) 7833 (const_int 0)))] 7834 "ix86_match_ccmode (insn, CCNOmode) 7835 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 7836 "test{l}\t{%1, %0|%0, %1}" 7837 [(set_attr "type" "test") 7838 (set_attr "modrm" "0,1,1") 7839 (set_attr "mode" "SI") 7840 (set_attr "pent_pair" "uv,np,uv")]) 7841 7842(define_expand "testsi_ccno_1" 7843 [(set (reg:CCNO FLAGS_REG) 7844 (compare:CCNO 7845 (and:SI (match_operand:SI 0 "nonimmediate_operand" "") 7846 (match_operand:SI 1 "nonmemory_operand" "")) 7847 (const_int 0)))] 7848 "" 7849 "") 7850 7851(define_insn "*testhi_1" 7852 [(set (reg FLAGS_REG) 7853 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm") 7854 (match_operand:HI 1 "general_operand" "n,n,rn")) 7855 (const_int 0)))] 7856 "ix86_match_ccmode (insn, CCNOmode) 7857 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 7858 "test{w}\t{%1, %0|%0, %1}" 7859 [(set_attr "type" "test") 7860 (set_attr "modrm" "0,1,1") 7861 (set_attr "mode" "HI") 7862 (set_attr "pent_pair" "uv,np,uv")]) 7863 7864(define_expand "testqi_ccz_1" 7865 [(set (reg:CCZ FLAGS_REG) 7866 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "") 7867 (match_operand:QI 1 "nonmemory_operand" "")) 7868 (const_int 0)))] 7869 "" 7870 "") 7871 7872(define_insn "*testqi_1_maybe_si" 7873 [(set (reg FLAGS_REG) 7874 (compare 7875 (and:QI 7876 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r") 7877 (match_operand:QI 1 "general_operand" "n,n,qn,n")) 7878 (const_int 0)))] 7879 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 7880 && ix86_match_ccmode (insn, 7881 GET_CODE (operands[1]) == CONST_INT 7882 && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)" 7883{ 7884 if (which_alternative == 3) 7885 { 7886 if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0) 7887 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff); 7888 return "test{l}\t{%1, %k0|%k0, %1}"; 7889 } 7890 return "test{b}\t{%1, %0|%0, %1}"; 7891} 7892 [(set_attr "type" "test") 7893 (set_attr "modrm" "0,1,1,1") 7894 (set_attr "mode" "QI,QI,QI,SI") 7895 (set_attr "pent_pair" "uv,np,uv,np")]) 7896 7897(define_insn "*testqi_1" 7898 [(set (reg FLAGS_REG) 7899 (compare 7900 (and:QI 7901 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm") 7902 (match_operand:QI 1 "general_operand" "n,n,qn")) 7903 (const_int 0)))] 7904 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM) 7905 && ix86_match_ccmode (insn, CCNOmode)" 7906 "test{b}\t{%1, %0|%0, %1}" 7907 [(set_attr "type" "test") 7908 (set_attr "modrm" "0,1,1") 7909 (set_attr "mode" "QI") 7910 (set_attr "pent_pair" "uv,np,uv")]) 7911 7912(define_expand "testqi_ext_ccno_0" 7913 [(set (reg:CCNO FLAGS_REG) 7914 (compare:CCNO 7915 (and:SI 7916 (zero_extract:SI 7917 (match_operand 0 "ext_register_operand" "") 7918 (const_int 8) 7919 (const_int 8)) 7920 (match_operand 1 "const_int_operand" "")) 7921 (const_int 0)))] 7922 "" 7923 "") 7924 7925(define_insn "*testqi_ext_0" 7926 [(set (reg FLAGS_REG) 7927 (compare 7928 (and:SI 7929 (zero_extract:SI 7930 (match_operand 0 "ext_register_operand" "Q") 7931 (const_int 8) 7932 (const_int 8)) 7933 (match_operand 1 "const_int_operand" "n")) 7934 (const_int 0)))] 7935 "ix86_match_ccmode (insn, CCNOmode)" 7936 "test{b}\t{%1, %h0|%h0, %1}" 7937 [(set_attr "type" "test") 7938 (set_attr "mode" "QI") 7939 (set_attr "length_immediate" "1") 7940 (set_attr "pent_pair" "np")]) 7941 7942(define_insn "*testqi_ext_1" 7943 [(set (reg FLAGS_REG) 7944 (compare 7945 (and:SI 7946 (zero_extract:SI 7947 (match_operand 0 "ext_register_operand" "Q") 7948 (const_int 8) 7949 (const_int 8)) 7950 (zero_extend:SI 7951 (match_operand:QI 1 "general_operand" "Qm"))) 7952 (const_int 0)))] 7953 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 7954 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 7955 "test{b}\t{%1, %h0|%h0, %1}" 7956 [(set_attr "type" "test") 7957 (set_attr "mode" "QI")]) 7958 7959(define_insn "*testqi_ext_1_rex64" 7960 [(set (reg FLAGS_REG) 7961 (compare 7962 (and:SI 7963 (zero_extract:SI 7964 (match_operand 0 "ext_register_operand" "Q") 7965 (const_int 8) 7966 (const_int 8)) 7967 (zero_extend:SI 7968 (match_operand:QI 1 "register_operand" "Q"))) 7969 (const_int 0)))] 7970 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)" 7971 "test{b}\t{%1, %h0|%h0, %1}" 7972 [(set_attr "type" "test") 7973 (set_attr "mode" "QI")]) 7974 7975(define_insn "*testqi_ext_2" 7976 [(set (reg FLAGS_REG) 7977 (compare 7978 (and:SI 7979 (zero_extract:SI 7980 (match_operand 0 "ext_register_operand" "Q") 7981 (const_int 8) 7982 (const_int 8)) 7983 (zero_extract:SI 7984 (match_operand 1 "ext_register_operand" "Q") 7985 (const_int 8) 7986 (const_int 8))) 7987 (const_int 0)))] 7988 "ix86_match_ccmode (insn, CCNOmode)" 7989 "test{b}\t{%h1, %h0|%h0, %h1}" 7990 [(set_attr "type" "test") 7991 (set_attr "mode" "QI")]) 7992 7993;; Combine likes to form bit extractions for some tests. Humor it. 7994(define_insn "*testqi_ext_3" 7995 [(set (reg FLAGS_REG) 7996 (compare (zero_extract:SI 7997 (match_operand 0 "nonimmediate_operand" "rm") 7998 (match_operand:SI 1 "const_int_operand" "") 7999 (match_operand:SI 2 "const_int_operand" "")) 8000 (const_int 0)))] 8001 "ix86_match_ccmode (insn, CCNOmode) 8002 && INTVAL (operands[1]) > 0 8003 && INTVAL (operands[2]) >= 0 8004 && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32 8005 && (GET_MODE (operands[0]) == SImode 8006 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode) 8007 || GET_MODE (operands[0]) == HImode 8008 || GET_MODE (operands[0]) == QImode)" 8009 "#") 8010 8011(define_insn "*testqi_ext_3_rex64" 8012 [(set (reg FLAGS_REG) 8013 (compare (zero_extract:DI 8014 (match_operand 0 "nonimmediate_operand" "rm") 8015 (match_operand:DI 1 "const_int_operand" "") 8016 (match_operand:DI 2 "const_int_operand" "")) 8017 (const_int 0)))] 8018 "TARGET_64BIT 8019 && ix86_match_ccmode (insn, CCNOmode) 8020 && INTVAL (operands[1]) > 0 8021 && INTVAL (operands[2]) >= 0 8022 /* Ensure that resulting mask is zero or sign extended operand. */ 8023 && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32 8024 || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64 8025 && INTVAL (operands[1]) > 32)) 8026 && (GET_MODE (operands[0]) == SImode 8027 || GET_MODE (operands[0]) == DImode 8028 || GET_MODE (operands[0]) == HImode 8029 || GET_MODE (operands[0]) == QImode)" 8030 "#") 8031 8032(define_split 8033 [(set (match_operand 0 "flags_reg_operand" "") 8034 (match_operator 1 "compare_operator" 8035 [(zero_extract 8036 (match_operand 2 "nonimmediate_operand" "") 8037 (match_operand 3 "const_int_operand" "") 8038 (match_operand 4 "const_int_operand" "")) 8039 (const_int 0)]))] 8040 "ix86_match_ccmode (insn, CCNOmode)" 8041 [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))] 8042{ 8043 rtx val = operands[2]; 8044 HOST_WIDE_INT len = INTVAL (operands[3]); 8045 HOST_WIDE_INT pos = INTVAL (operands[4]); 8046 HOST_WIDE_INT mask; 8047 enum machine_mode mode, submode; 8048 8049 mode = GET_MODE (val); 8050 if (GET_CODE (val) == MEM) 8051 { 8052 /* ??? Combine likes to put non-volatile mem extractions in QImode 8053 no matter the size of the test. So find a mode that works. */ 8054 if (! MEM_VOLATILE_P (val)) 8055 { 8056 mode = smallest_mode_for_size (pos + len, MODE_INT); 8057 val = adjust_address (val, mode, 0); 8058 } 8059 } 8060 else if (GET_CODE (val) == SUBREG 8061 && (submode = GET_MODE (SUBREG_REG (val)), 8062 GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode)) 8063 && pos + len <= GET_MODE_BITSIZE (submode)) 8064 { 8065 /* Narrow a paradoxical subreg to prevent partial register stalls. */ 8066 mode = submode; 8067 val = SUBREG_REG (val); 8068 } 8069 else if (mode == HImode && pos + len <= 8) 8070 { 8071 /* Small HImode tests can be converted to QImode. */ 8072 mode = QImode; 8073 val = gen_lowpart (QImode, val); 8074 } 8075 8076 if (len == HOST_BITS_PER_WIDE_INT) 8077 mask = -1; 8078 else 8079 mask = ((HOST_WIDE_INT)1 << len) - 1; 8080 mask <<= pos; 8081 8082 operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode)); 8083}) 8084 8085;; Convert HImode/SImode test instructions with immediate to QImode ones. 8086;; i386 does not allow to encode test with 8bit sign extended immediate, so 8087;; this is relatively important trick. 8088;; Do the conversion only post-reload to avoid limiting of the register class 8089;; to QI regs. 8090(define_split 8091 [(set (match_operand 0 "flags_reg_operand" "") 8092 (match_operator 1 "compare_operator" 8093 [(and (match_operand 2 "register_operand" "") 8094 (match_operand 3 "const_int_operand" "")) 8095 (const_int 0)]))] 8096 "reload_completed 8097 && QI_REG_P (operands[2]) 8098 && GET_MODE (operands[2]) != QImode 8099 && ((ix86_match_ccmode (insn, CCZmode) 8100 && !(INTVAL (operands[3]) & ~(255 << 8))) 8101 || (ix86_match_ccmode (insn, CCNOmode) 8102 && !(INTVAL (operands[3]) & ~(127 << 8))))" 8103 [(set (match_dup 0) 8104 (match_op_dup 1 8105 [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8)) 8106 (match_dup 3)) 8107 (const_int 0)]))] 8108 "operands[2] = gen_lowpart (SImode, operands[2]); 8109 operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);") 8110 8111(define_split 8112 [(set (match_operand 0 "flags_reg_operand" "") 8113 (match_operator 1 "compare_operator" 8114 [(and (match_operand 2 "nonimmediate_operand" "") 8115 (match_operand 3 "const_int_operand" "")) 8116 (const_int 0)]))] 8117 "reload_completed 8118 && GET_MODE (operands[2]) != QImode 8119 && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2])) 8120 && ((ix86_match_ccmode (insn, CCZmode) 8121 && !(INTVAL (operands[3]) & ~255)) 8122 || (ix86_match_ccmode (insn, CCNOmode) 8123 && !(INTVAL (operands[3]) & ~127)))" 8124 [(set (match_dup 0) 8125 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3)) 8126 (const_int 0)]))] 8127 "operands[2] = gen_lowpart (QImode, operands[2]); 8128 operands[3] = gen_lowpart (QImode, operands[3]);") 8129 8130 8131;; %%% This used to optimize known byte-wide and operations to memory, 8132;; and sometimes to QImode registers. If this is considered useful, 8133;; it should be done with splitters. 8134 8135(define_expand "anddi3" 8136 [(set (match_operand:DI 0 "nonimmediate_operand" "") 8137 (and:DI (match_operand:DI 1 "nonimmediate_operand" "") 8138 (match_operand:DI 2 "x86_64_szext_general_operand" ""))) 8139 (clobber (reg:CC FLAGS_REG))] 8140 "TARGET_64BIT" 8141 "ix86_expand_binary_operator (AND, DImode, operands); DONE;") 8142 8143(define_insn "*anddi_1_rex64" 8144 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r") 8145 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm") 8146 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L"))) 8147 (clobber (reg:CC FLAGS_REG))] 8148 "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)" 8149{ 8150 switch (get_attr_type (insn)) 8151 { 8152 case TYPE_IMOVX: 8153 { 8154 enum machine_mode mode; 8155 8156 gcc_assert (GET_CODE (operands[2]) == CONST_INT); 8157 if (INTVAL (operands[2]) == 0xff) 8158 mode = QImode; 8159 else 8160 { 8161 gcc_assert (INTVAL (operands[2]) == 0xffff); 8162 mode = HImode; 8163 } 8164 8165 operands[1] = gen_lowpart (mode, operands[1]); 8166 if (mode == QImode) 8167 return "movz{bq|x}\t{%1,%0|%0, %1}"; 8168 else 8169 return "movz{wq|x}\t{%1,%0|%0, %1}"; 8170 } 8171 8172 default: 8173 gcc_assert (rtx_equal_p (operands[0], operands[1])); 8174 if (get_attr_mode (insn) == MODE_SI) 8175 return "and{l}\t{%k2, %k0|%k0, %k2}"; 8176 else 8177 return "and{q}\t{%2, %0|%0, %2}"; 8178 } 8179} 8180 [(set_attr "type" "alu,alu,alu,imovx") 8181 (set_attr "length_immediate" "*,*,*,0") 8182 (set_attr "mode" "SI,DI,DI,DI")]) 8183 8184(define_insn "*anddi_2" 8185 [(set (reg FLAGS_REG) 8186 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0") 8187 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re")) 8188 (const_int 0))) 8189 (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm") 8190 (and:DI (match_dup 1) (match_dup 2)))] 8191 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 8192 && ix86_binary_operator_ok (AND, DImode, operands)" 8193 "@ 8194 and{l}\t{%k2, %k0|%k0, %k2} 8195 and{q}\t{%2, %0|%0, %2} 8196 and{q}\t{%2, %0|%0, %2}" 8197 [(set_attr "type" "alu") 8198 (set_attr "mode" "SI,DI,DI")]) 8199 8200(define_expand "andsi3" 8201 [(set (match_operand:SI 0 "nonimmediate_operand" "") 8202 (and:SI (match_operand:SI 1 "nonimmediate_operand" "") 8203 (match_operand:SI 2 "general_operand" ""))) 8204 (clobber (reg:CC FLAGS_REG))] 8205 "" 8206 "ix86_expand_binary_operator (AND, SImode, operands); DONE;") 8207 8208(define_insn "*andsi_1" 8209 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r") 8210 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm") 8211 (match_operand:SI 2 "general_operand" "ri,rm,L"))) 8212 (clobber (reg:CC FLAGS_REG))] 8213 "ix86_binary_operator_ok (AND, SImode, operands)" 8214{ 8215 switch (get_attr_type (insn)) 8216 { 8217 case TYPE_IMOVX: 8218 { 8219 enum machine_mode mode; 8220 8221 gcc_assert (GET_CODE (operands[2]) == CONST_INT); 8222 if (INTVAL (operands[2]) == 0xff) 8223 mode = QImode; 8224 else 8225 { 8226 gcc_assert (INTVAL (operands[2]) == 0xffff); 8227 mode = HImode; 8228 } 8229 8230 operands[1] = gen_lowpart (mode, operands[1]); 8231 if (mode == QImode) 8232 return "movz{bl|x}\t{%1,%0|%0, %1}"; 8233 else 8234 return "movz{wl|x}\t{%1,%0|%0, %1}"; 8235 } 8236 8237 default: 8238 gcc_assert (rtx_equal_p (operands[0], operands[1])); 8239 return "and{l}\t{%2, %0|%0, %2}"; 8240 } 8241} 8242 [(set_attr "type" "alu,alu,imovx") 8243 (set_attr "length_immediate" "*,*,0") 8244 (set_attr "mode" "SI")]) 8245 8246(define_split 8247 [(set (match_operand 0 "register_operand" "") 8248 (and (match_dup 0) 8249 (const_int -65536))) 8250 (clobber (reg:CC FLAGS_REG))] 8251 "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)" 8252 [(set (strict_low_part (match_dup 1)) (const_int 0))] 8253 "operands[1] = gen_lowpart (HImode, operands[0]);") 8254 8255(define_split 8256 [(set (match_operand 0 "ext_register_operand" "") 8257 (and (match_dup 0) 8258 (const_int -256))) 8259 (clobber (reg:CC FLAGS_REG))] 8260 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed" 8261 [(set (strict_low_part (match_dup 1)) (const_int 0))] 8262 "operands[1] = gen_lowpart (QImode, operands[0]);") 8263 8264(define_split 8265 [(set (match_operand 0 "ext_register_operand" "") 8266 (and (match_dup 0) 8267 (const_int -65281))) 8268 (clobber (reg:CC FLAGS_REG))] 8269 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed" 8270 [(parallel [(set (zero_extract:SI (match_dup 0) 8271 (const_int 8) 8272 (const_int 8)) 8273 (xor:SI 8274 (zero_extract:SI (match_dup 0) 8275 (const_int 8) 8276 (const_int 8)) 8277 (zero_extract:SI (match_dup 0) 8278 (const_int 8) 8279 (const_int 8)))) 8280 (clobber (reg:CC FLAGS_REG))])] 8281 "operands[0] = gen_lowpart (SImode, operands[0]);") 8282 8283;; See comment for addsi_1_zext why we do use nonimmediate_operand 8284(define_insn "*andsi_1_zext" 8285 [(set (match_operand:DI 0 "register_operand" "=r") 8286 (zero_extend:DI 8287 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8288 (match_operand:SI 2 "general_operand" "rim")))) 8289 (clobber (reg:CC FLAGS_REG))] 8290 "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)" 8291 "and{l}\t{%2, %k0|%k0, %2}" 8292 [(set_attr "type" "alu") 8293 (set_attr "mode" "SI")]) 8294 8295(define_insn "*andsi_2" 8296 [(set (reg FLAGS_REG) 8297 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 8298 (match_operand:SI 2 "general_operand" "rim,ri")) 8299 (const_int 0))) 8300 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm") 8301 (and:SI (match_dup 1) (match_dup 2)))] 8302 "ix86_match_ccmode (insn, CCNOmode) 8303 && ix86_binary_operator_ok (AND, SImode, operands)" 8304 "and{l}\t{%2, %0|%0, %2}" 8305 [(set_attr "type" "alu") 8306 (set_attr "mode" "SI")]) 8307 8308;; See comment for addsi_1_zext why we do use nonimmediate_operand 8309(define_insn "*andsi_2_zext" 8310 [(set (reg FLAGS_REG) 8311 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8312 (match_operand:SI 2 "general_operand" "rim")) 8313 (const_int 0))) 8314 (set (match_operand:DI 0 "register_operand" "=r") 8315 (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))] 8316 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 8317 && ix86_binary_operator_ok (AND, SImode, operands)" 8318 "and{l}\t{%2, %k0|%k0, %2}" 8319 [(set_attr "type" "alu") 8320 (set_attr "mode" "SI")]) 8321 8322(define_expand "andhi3" 8323 [(set (match_operand:HI 0 "nonimmediate_operand" "") 8324 (and:HI (match_operand:HI 1 "nonimmediate_operand" "") 8325 (match_operand:HI 2 "general_operand" ""))) 8326 (clobber (reg:CC FLAGS_REG))] 8327 "TARGET_HIMODE_MATH" 8328 "ix86_expand_binary_operator (AND, HImode, operands); DONE;") 8329 8330(define_insn "*andhi_1" 8331 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r") 8332 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm") 8333 (match_operand:HI 2 "general_operand" "ri,rm,L"))) 8334 (clobber (reg:CC FLAGS_REG))] 8335 "ix86_binary_operator_ok (AND, HImode, operands)" 8336{ 8337 switch (get_attr_type (insn)) 8338 { 8339 case TYPE_IMOVX: 8340 gcc_assert (GET_CODE (operands[2]) == CONST_INT); 8341 gcc_assert (INTVAL (operands[2]) == 0xff); 8342 return "movz{bl|x}\t{%b1, %k0|%k0, %b1}"; 8343 8344 default: 8345 gcc_assert (rtx_equal_p (operands[0], operands[1])); 8346 8347 return "and{w}\t{%2, %0|%0, %2}"; 8348 } 8349} 8350 [(set_attr "type" "alu,alu,imovx") 8351 (set_attr "length_immediate" "*,*,0") 8352 (set_attr "mode" "HI,HI,SI")]) 8353 8354(define_insn "*andhi_2" 8355 [(set (reg FLAGS_REG) 8356 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 8357 (match_operand:HI 2 "general_operand" "rim,ri")) 8358 (const_int 0))) 8359 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm") 8360 (and:HI (match_dup 1) (match_dup 2)))] 8361 "ix86_match_ccmode (insn, CCNOmode) 8362 && ix86_binary_operator_ok (AND, HImode, operands)" 8363 "and{w}\t{%2, %0|%0, %2}" 8364 [(set_attr "type" "alu") 8365 (set_attr "mode" "HI")]) 8366 8367(define_expand "andqi3" 8368 [(set (match_operand:QI 0 "nonimmediate_operand" "") 8369 (and:QI (match_operand:QI 1 "nonimmediate_operand" "") 8370 (match_operand:QI 2 "general_operand" ""))) 8371 (clobber (reg:CC FLAGS_REG))] 8372 "TARGET_QIMODE_MATH" 8373 "ix86_expand_binary_operator (AND, QImode, operands); DONE;") 8374 8375;; %%% Potential partial reg stall on alternative 2. What to do? 8376(define_insn "*andqi_1" 8377 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r") 8378 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0") 8379 (match_operand:QI 2 "general_operand" "qi,qmi,ri"))) 8380 (clobber (reg:CC FLAGS_REG))] 8381 "ix86_binary_operator_ok (AND, QImode, operands)" 8382 "@ 8383 and{b}\t{%2, %0|%0, %2} 8384 and{b}\t{%2, %0|%0, %2} 8385 and{l}\t{%k2, %k0|%k0, %k2}" 8386 [(set_attr "type" "alu") 8387 (set_attr "mode" "QI,QI,SI")]) 8388 8389(define_insn "*andqi_1_slp" 8390 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q")) 8391 (and:QI (match_dup 0) 8392 (match_operand:QI 1 "general_operand" "qi,qmi"))) 8393 (clobber (reg:CC FLAGS_REG))] 8394 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 8395 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 8396 "and{b}\t{%1, %0|%0, %1}" 8397 [(set_attr "type" "alu1") 8398 (set_attr "mode" "QI")]) 8399 8400(define_insn "*andqi_2_maybe_si" 8401 [(set (reg FLAGS_REG) 8402 (compare (and:QI 8403 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0") 8404 (match_operand:QI 2 "general_operand" "qim,qi,i")) 8405 (const_int 0))) 8406 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r") 8407 (and:QI (match_dup 1) (match_dup 2)))] 8408 "ix86_binary_operator_ok (AND, QImode, operands) 8409 && ix86_match_ccmode (insn, 8410 GET_CODE (operands[2]) == CONST_INT 8411 && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)" 8412{ 8413 if (which_alternative == 2) 8414 { 8415 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0) 8416 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff); 8417 return "and{l}\t{%2, %k0|%k0, %2}"; 8418 } 8419 return "and{b}\t{%2, %0|%0, %2}"; 8420} 8421 [(set_attr "type" "alu") 8422 (set_attr "mode" "QI,QI,SI")]) 8423 8424(define_insn "*andqi_2" 8425 [(set (reg FLAGS_REG) 8426 (compare (and:QI 8427 (match_operand:QI 1 "nonimmediate_operand" "%0,0") 8428 (match_operand:QI 2 "general_operand" "qim,qi")) 8429 (const_int 0))) 8430 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm") 8431 (and:QI (match_dup 1) (match_dup 2)))] 8432 "ix86_match_ccmode (insn, CCNOmode) 8433 && ix86_binary_operator_ok (AND, QImode, operands)" 8434 "and{b}\t{%2, %0|%0, %2}" 8435 [(set_attr "type" "alu") 8436 (set_attr "mode" "QI")]) 8437 8438(define_insn "*andqi_2_slp" 8439 [(set (reg FLAGS_REG) 8440 (compare (and:QI 8441 (match_operand:QI 0 "nonimmediate_operand" "+q,qm") 8442 (match_operand:QI 1 "nonimmediate_operand" "qmi,qi")) 8443 (const_int 0))) 8444 (set (strict_low_part (match_dup 0)) 8445 (and:QI (match_dup 0) (match_dup 1)))] 8446 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 8447 && ix86_match_ccmode (insn, CCNOmode) 8448 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 8449 "and{b}\t{%1, %0|%0, %1}" 8450 [(set_attr "type" "alu1") 8451 (set_attr "mode" "QI")]) 8452 8453;; ??? A bug in recog prevents it from recognizing a const_int as an 8454;; operand to zero_extend in andqi_ext_1. It was checking explicitly 8455;; for a QImode operand, which of course failed. 8456 8457(define_insn "andqi_ext_0" 8458 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8459 (const_int 8) 8460 (const_int 8)) 8461 (and:SI 8462 (zero_extract:SI 8463 (match_operand 1 "ext_register_operand" "0") 8464 (const_int 8) 8465 (const_int 8)) 8466 (match_operand 2 "const_int_operand" "n"))) 8467 (clobber (reg:CC FLAGS_REG))] 8468 "" 8469 "and{b}\t{%2, %h0|%h0, %2}" 8470 [(set_attr "type" "alu") 8471 (set_attr "length_immediate" "1") 8472 (set_attr "mode" "QI")]) 8473 8474;; Generated by peephole translating test to and. This shows up 8475;; often in fp comparisons. 8476 8477(define_insn "*andqi_ext_0_cc" 8478 [(set (reg FLAGS_REG) 8479 (compare 8480 (and:SI 8481 (zero_extract:SI 8482 (match_operand 1 "ext_register_operand" "0") 8483 (const_int 8) 8484 (const_int 8)) 8485 (match_operand 2 "const_int_operand" "n")) 8486 (const_int 0))) 8487 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8488 (const_int 8) 8489 (const_int 8)) 8490 (and:SI 8491 (zero_extract:SI 8492 (match_dup 1) 8493 (const_int 8) 8494 (const_int 8)) 8495 (match_dup 2)))] 8496 "ix86_match_ccmode (insn, CCNOmode)" 8497 "and{b}\t{%2, %h0|%h0, %2}" 8498 [(set_attr "type" "alu") 8499 (set_attr "length_immediate" "1") 8500 (set_attr "mode" "QI")]) 8501 8502(define_insn "*andqi_ext_1" 8503 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8504 (const_int 8) 8505 (const_int 8)) 8506 (and:SI 8507 (zero_extract:SI 8508 (match_operand 1 "ext_register_operand" "0") 8509 (const_int 8) 8510 (const_int 8)) 8511 (zero_extend:SI 8512 (match_operand:QI 2 "general_operand" "Qm")))) 8513 (clobber (reg:CC FLAGS_REG))] 8514 "!TARGET_64BIT" 8515 "and{b}\t{%2, %h0|%h0, %2}" 8516 [(set_attr "type" "alu") 8517 (set_attr "length_immediate" "0") 8518 (set_attr "mode" "QI")]) 8519 8520(define_insn "*andqi_ext_1_rex64" 8521 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8522 (const_int 8) 8523 (const_int 8)) 8524 (and:SI 8525 (zero_extract:SI 8526 (match_operand 1 "ext_register_operand" "0") 8527 (const_int 8) 8528 (const_int 8)) 8529 (zero_extend:SI 8530 (match_operand 2 "ext_register_operand" "Q")))) 8531 (clobber (reg:CC FLAGS_REG))] 8532 "TARGET_64BIT" 8533 "and{b}\t{%2, %h0|%h0, %2}" 8534 [(set_attr "type" "alu") 8535 (set_attr "length_immediate" "0") 8536 (set_attr "mode" "QI")]) 8537 8538(define_insn "*andqi_ext_2" 8539 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8540 (const_int 8) 8541 (const_int 8)) 8542 (and:SI 8543 (zero_extract:SI 8544 (match_operand 1 "ext_register_operand" "%0") 8545 (const_int 8) 8546 (const_int 8)) 8547 (zero_extract:SI 8548 (match_operand 2 "ext_register_operand" "Q") 8549 (const_int 8) 8550 (const_int 8)))) 8551 (clobber (reg:CC FLAGS_REG))] 8552 "" 8553 "and{b}\t{%h2, %h0|%h0, %h2}" 8554 [(set_attr "type" "alu") 8555 (set_attr "length_immediate" "0") 8556 (set_attr "mode" "QI")]) 8557 8558;; Convert wide AND instructions with immediate operand to shorter QImode 8559;; equivalents when possible. 8560;; Don't do the splitting with memory operands, since it introduces risk 8561;; of memory mismatch stalls. We may want to do the splitting for optimizing 8562;; for size, but that can (should?) be handled by generic code instead. 8563(define_split 8564 [(set (match_operand 0 "register_operand" "") 8565 (and (match_operand 1 "register_operand" "") 8566 (match_operand 2 "const_int_operand" ""))) 8567 (clobber (reg:CC FLAGS_REG))] 8568 "reload_completed 8569 && QI_REG_P (operands[0]) 8570 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 8571 && !(~INTVAL (operands[2]) & ~(255 << 8)) 8572 && GET_MODE (operands[0]) != QImode" 8573 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8)) 8574 (and:SI (zero_extract:SI (match_dup 1) 8575 (const_int 8) (const_int 8)) 8576 (match_dup 2))) 8577 (clobber (reg:CC FLAGS_REG))])] 8578 "operands[0] = gen_lowpart (SImode, operands[0]); 8579 operands[1] = gen_lowpart (SImode, operands[1]); 8580 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);") 8581 8582;; Since AND can be encoded with sign extended immediate, this is only 8583;; profitable when 7th bit is not set. 8584(define_split 8585 [(set (match_operand 0 "register_operand" "") 8586 (and (match_operand 1 "general_operand" "") 8587 (match_operand 2 "const_int_operand" ""))) 8588 (clobber (reg:CC FLAGS_REG))] 8589 "reload_completed 8590 && ANY_QI_REG_P (operands[0]) 8591 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 8592 && !(~INTVAL (operands[2]) & ~255) 8593 && !(INTVAL (operands[2]) & 128) 8594 && GET_MODE (operands[0]) != QImode" 8595 [(parallel [(set (strict_low_part (match_dup 0)) 8596 (and:QI (match_dup 1) 8597 (match_dup 2))) 8598 (clobber (reg:CC FLAGS_REG))])] 8599 "operands[0] = gen_lowpart (QImode, operands[0]); 8600 operands[1] = gen_lowpart (QImode, operands[1]); 8601 operands[2] = gen_lowpart (QImode, operands[2]);") 8602 8603;; Logical inclusive OR instructions 8604 8605;; %%% This used to optimize known byte-wide and operations to memory. 8606;; If this is considered useful, it should be done with splitters. 8607 8608(define_expand "iordi3" 8609 [(set (match_operand:DI 0 "nonimmediate_operand" "") 8610 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "") 8611 (match_operand:DI 2 "x86_64_general_operand" ""))) 8612 (clobber (reg:CC FLAGS_REG))] 8613 "TARGET_64BIT" 8614 "ix86_expand_binary_operator (IOR, DImode, operands); DONE;") 8615 8616(define_insn "*iordi_1_rex64" 8617 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 8618 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 8619 (match_operand:DI 2 "x86_64_general_operand" "re,rme"))) 8620 (clobber (reg:CC FLAGS_REG))] 8621 "TARGET_64BIT 8622 && ix86_binary_operator_ok (IOR, DImode, operands)" 8623 "or{q}\t{%2, %0|%0, %2}" 8624 [(set_attr "type" "alu") 8625 (set_attr "mode" "DI")]) 8626 8627(define_insn "*iordi_2_rex64" 8628 [(set (reg FLAGS_REG) 8629 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 8630 (match_operand:DI 2 "x86_64_general_operand" "rem,re")) 8631 (const_int 0))) 8632 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm") 8633 (ior:DI (match_dup 1) (match_dup 2)))] 8634 "TARGET_64BIT 8635 && ix86_match_ccmode (insn, CCNOmode) 8636 && ix86_binary_operator_ok (IOR, DImode, operands)" 8637 "or{q}\t{%2, %0|%0, %2}" 8638 [(set_attr "type" "alu") 8639 (set_attr "mode" "DI")]) 8640 8641(define_insn "*iordi_3_rex64" 8642 [(set (reg FLAGS_REG) 8643 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0") 8644 (match_operand:DI 2 "x86_64_general_operand" "rem")) 8645 (const_int 0))) 8646 (clobber (match_scratch:DI 0 "=r"))] 8647 "TARGET_64BIT 8648 && ix86_match_ccmode (insn, CCNOmode) 8649 && ix86_binary_operator_ok (IOR, DImode, operands)" 8650 "or{q}\t{%2, %0|%0, %2}" 8651 [(set_attr "type" "alu") 8652 (set_attr "mode" "DI")]) 8653 8654 8655(define_expand "iorsi3" 8656 [(set (match_operand:SI 0 "nonimmediate_operand" "") 8657 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "") 8658 (match_operand:SI 2 "general_operand" ""))) 8659 (clobber (reg:CC FLAGS_REG))] 8660 "" 8661 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;") 8662 8663(define_insn "*iorsi_1" 8664 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 8665 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 8666 (match_operand:SI 2 "general_operand" "ri,rmi"))) 8667 (clobber (reg:CC FLAGS_REG))] 8668 "ix86_binary_operator_ok (IOR, SImode, operands)" 8669 "or{l}\t{%2, %0|%0, %2}" 8670 [(set_attr "type" "alu") 8671 (set_attr "mode" "SI")]) 8672 8673;; See comment for addsi_1_zext why we do use nonimmediate_operand 8674(define_insn "*iorsi_1_zext" 8675 [(set (match_operand:DI 0 "register_operand" "=rm") 8676 (zero_extend:DI 8677 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8678 (match_operand:SI 2 "general_operand" "rim")))) 8679 (clobber (reg:CC FLAGS_REG))] 8680 "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)" 8681 "or{l}\t{%2, %k0|%k0, %2}" 8682 [(set_attr "type" "alu") 8683 (set_attr "mode" "SI")]) 8684 8685(define_insn "*iorsi_1_zext_imm" 8686 [(set (match_operand:DI 0 "register_operand" "=rm") 8687 (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0")) 8688 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z"))) 8689 (clobber (reg:CC FLAGS_REG))] 8690 "TARGET_64BIT" 8691 "or{l}\t{%2, %k0|%k0, %2}" 8692 [(set_attr "type" "alu") 8693 (set_attr "mode" "SI")]) 8694 8695(define_insn "*iorsi_2" 8696 [(set (reg FLAGS_REG) 8697 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 8698 (match_operand:SI 2 "general_operand" "rim,ri")) 8699 (const_int 0))) 8700 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm") 8701 (ior:SI (match_dup 1) (match_dup 2)))] 8702 "ix86_match_ccmode (insn, CCNOmode) 8703 && ix86_binary_operator_ok (IOR, SImode, operands)" 8704 "or{l}\t{%2, %0|%0, %2}" 8705 [(set_attr "type" "alu") 8706 (set_attr "mode" "SI")]) 8707 8708;; See comment for addsi_1_zext why we do use nonimmediate_operand 8709;; ??? Special case for immediate operand is missing - it is tricky. 8710(define_insn "*iorsi_2_zext" 8711 [(set (reg FLAGS_REG) 8712 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8713 (match_operand:SI 2 "general_operand" "rim")) 8714 (const_int 0))) 8715 (set (match_operand:DI 0 "register_operand" "=r") 8716 (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))] 8717 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 8718 && ix86_binary_operator_ok (IOR, SImode, operands)" 8719 "or{l}\t{%2, %k0|%k0, %2}" 8720 [(set_attr "type" "alu") 8721 (set_attr "mode" "SI")]) 8722 8723(define_insn "*iorsi_2_zext_imm" 8724 [(set (reg FLAGS_REG) 8725 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8726 (match_operand 2 "x86_64_zext_immediate_operand" "Z")) 8727 (const_int 0))) 8728 (set (match_operand:DI 0 "register_operand" "=r") 8729 (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))] 8730 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 8731 && ix86_binary_operator_ok (IOR, SImode, operands)" 8732 "or{l}\t{%2, %k0|%k0, %2}" 8733 [(set_attr "type" "alu") 8734 (set_attr "mode" "SI")]) 8735 8736(define_insn "*iorsi_3" 8737 [(set (reg FLAGS_REG) 8738 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 8739 (match_operand:SI 2 "general_operand" "rim")) 8740 (const_int 0))) 8741 (clobber (match_scratch:SI 0 "=r"))] 8742 "ix86_match_ccmode (insn, CCNOmode) 8743 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 8744 "or{l}\t{%2, %0|%0, %2}" 8745 [(set_attr "type" "alu") 8746 (set_attr "mode" "SI")]) 8747 8748(define_expand "iorhi3" 8749 [(set (match_operand:HI 0 "nonimmediate_operand" "") 8750 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "") 8751 (match_operand:HI 2 "general_operand" ""))) 8752 (clobber (reg:CC FLAGS_REG))] 8753 "TARGET_HIMODE_MATH" 8754 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;") 8755 8756(define_insn "*iorhi_1" 8757 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m") 8758 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 8759 (match_operand:HI 2 "general_operand" "rmi,ri"))) 8760 (clobber (reg:CC FLAGS_REG))] 8761 "ix86_binary_operator_ok (IOR, HImode, operands)" 8762 "or{w}\t{%2, %0|%0, %2}" 8763 [(set_attr "type" "alu") 8764 (set_attr "mode" "HI")]) 8765 8766(define_insn "*iorhi_2" 8767 [(set (reg FLAGS_REG) 8768 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 8769 (match_operand:HI 2 "general_operand" "rim,ri")) 8770 (const_int 0))) 8771 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm") 8772 (ior:HI (match_dup 1) (match_dup 2)))] 8773 "ix86_match_ccmode (insn, CCNOmode) 8774 && ix86_binary_operator_ok (IOR, HImode, operands)" 8775 "or{w}\t{%2, %0|%0, %2}" 8776 [(set_attr "type" "alu") 8777 (set_attr "mode" "HI")]) 8778 8779(define_insn "*iorhi_3" 8780 [(set (reg FLAGS_REG) 8781 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0") 8782 (match_operand:HI 2 "general_operand" "rim")) 8783 (const_int 0))) 8784 (clobber (match_scratch:HI 0 "=r"))] 8785 "ix86_match_ccmode (insn, CCNOmode) 8786 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 8787 "or{w}\t{%2, %0|%0, %2}" 8788 [(set_attr "type" "alu") 8789 (set_attr "mode" "HI")]) 8790 8791(define_expand "iorqi3" 8792 [(set (match_operand:QI 0 "nonimmediate_operand" "") 8793 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "") 8794 (match_operand:QI 2 "general_operand" ""))) 8795 (clobber (reg:CC FLAGS_REG))] 8796 "TARGET_QIMODE_MATH" 8797 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;") 8798 8799;; %%% Potential partial reg stall on alternative 2. What to do? 8800(define_insn "*iorqi_1" 8801 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r") 8802 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0") 8803 (match_operand:QI 2 "general_operand" "qmi,qi,ri"))) 8804 (clobber (reg:CC FLAGS_REG))] 8805 "ix86_binary_operator_ok (IOR, QImode, operands)" 8806 "@ 8807 or{b}\t{%2, %0|%0, %2} 8808 or{b}\t{%2, %0|%0, %2} 8809 or{l}\t{%k2, %k0|%k0, %k2}" 8810 [(set_attr "type" "alu") 8811 (set_attr "mode" "QI,QI,SI")]) 8812 8813(define_insn "*iorqi_1_slp" 8814 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m")) 8815 (ior:QI (match_dup 0) 8816 (match_operand:QI 1 "general_operand" "qmi,qi"))) 8817 (clobber (reg:CC FLAGS_REG))] 8818 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 8819 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 8820 "or{b}\t{%1, %0|%0, %1}" 8821 [(set_attr "type" "alu1") 8822 (set_attr "mode" "QI")]) 8823 8824(define_insn "*iorqi_2" 8825 [(set (reg FLAGS_REG) 8826 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0") 8827 (match_operand:QI 2 "general_operand" "qim,qi")) 8828 (const_int 0))) 8829 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm") 8830 (ior:QI (match_dup 1) (match_dup 2)))] 8831 "ix86_match_ccmode (insn, CCNOmode) 8832 && ix86_binary_operator_ok (IOR, QImode, operands)" 8833 "or{b}\t{%2, %0|%0, %2}" 8834 [(set_attr "type" "alu") 8835 (set_attr "mode" "QI")]) 8836 8837(define_insn "*iorqi_2_slp" 8838 [(set (reg FLAGS_REG) 8839 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm") 8840 (match_operand:QI 1 "general_operand" "qim,qi")) 8841 (const_int 0))) 8842 (set (strict_low_part (match_dup 0)) 8843 (ior:QI (match_dup 0) (match_dup 1)))] 8844 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 8845 && ix86_match_ccmode (insn, CCNOmode) 8846 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 8847 "or{b}\t{%1, %0|%0, %1}" 8848 [(set_attr "type" "alu1") 8849 (set_attr "mode" "QI")]) 8850 8851(define_insn "*iorqi_3" 8852 [(set (reg FLAGS_REG) 8853 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0") 8854 (match_operand:QI 2 "general_operand" "qim")) 8855 (const_int 0))) 8856 (clobber (match_scratch:QI 0 "=q"))] 8857 "ix86_match_ccmode (insn, CCNOmode) 8858 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 8859 "or{b}\t{%2, %0|%0, %2}" 8860 [(set_attr "type" "alu") 8861 (set_attr "mode" "QI")]) 8862 8863(define_insn "iorqi_ext_0" 8864 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8865 (const_int 8) 8866 (const_int 8)) 8867 (ior:SI 8868 (zero_extract:SI 8869 (match_operand 1 "ext_register_operand" "0") 8870 (const_int 8) 8871 (const_int 8)) 8872 (match_operand 2 "const_int_operand" "n"))) 8873 (clobber (reg:CC FLAGS_REG))] 8874 "(!TARGET_PARTIAL_REG_STALL || optimize_size)" 8875 "or{b}\t{%2, %h0|%h0, %2}" 8876 [(set_attr "type" "alu") 8877 (set_attr "length_immediate" "1") 8878 (set_attr "mode" "QI")]) 8879 8880(define_insn "*iorqi_ext_1" 8881 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8882 (const_int 8) 8883 (const_int 8)) 8884 (ior:SI 8885 (zero_extract:SI 8886 (match_operand 1 "ext_register_operand" "0") 8887 (const_int 8) 8888 (const_int 8)) 8889 (zero_extend:SI 8890 (match_operand:QI 2 "general_operand" "Qm")))) 8891 (clobber (reg:CC FLAGS_REG))] 8892 "!TARGET_64BIT 8893 && (!TARGET_PARTIAL_REG_STALL || optimize_size)" 8894 "or{b}\t{%2, %h0|%h0, %2}" 8895 [(set_attr "type" "alu") 8896 (set_attr "length_immediate" "0") 8897 (set_attr "mode" "QI")]) 8898 8899(define_insn "*iorqi_ext_1_rex64" 8900 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8901 (const_int 8) 8902 (const_int 8)) 8903 (ior:SI 8904 (zero_extract:SI 8905 (match_operand 1 "ext_register_operand" "0") 8906 (const_int 8) 8907 (const_int 8)) 8908 (zero_extend:SI 8909 (match_operand 2 "ext_register_operand" "Q")))) 8910 (clobber (reg:CC FLAGS_REG))] 8911 "TARGET_64BIT 8912 && (!TARGET_PARTIAL_REG_STALL || optimize_size)" 8913 "or{b}\t{%2, %h0|%h0, %2}" 8914 [(set_attr "type" "alu") 8915 (set_attr "length_immediate" "0") 8916 (set_attr "mode" "QI")]) 8917 8918(define_insn "*iorqi_ext_2" 8919 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 8920 (const_int 8) 8921 (const_int 8)) 8922 (ior:SI 8923 (zero_extract:SI (match_operand 1 "ext_register_operand" "0") 8924 (const_int 8) 8925 (const_int 8)) 8926 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q") 8927 (const_int 8) 8928 (const_int 8)))) 8929 (clobber (reg:CC FLAGS_REG))] 8930 "(!TARGET_PARTIAL_REG_STALL || optimize_size)" 8931 "ior{b}\t{%h2, %h0|%h0, %h2}" 8932 [(set_attr "type" "alu") 8933 (set_attr "length_immediate" "0") 8934 (set_attr "mode" "QI")]) 8935 8936(define_split 8937 [(set (match_operand 0 "register_operand" "") 8938 (ior (match_operand 1 "register_operand" "") 8939 (match_operand 2 "const_int_operand" ""))) 8940 (clobber (reg:CC FLAGS_REG))] 8941 "reload_completed 8942 && QI_REG_P (operands[0]) 8943 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 8944 && !(INTVAL (operands[2]) & ~(255 << 8)) 8945 && GET_MODE (operands[0]) != QImode" 8946 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8)) 8947 (ior:SI (zero_extract:SI (match_dup 1) 8948 (const_int 8) (const_int 8)) 8949 (match_dup 2))) 8950 (clobber (reg:CC FLAGS_REG))])] 8951 "operands[0] = gen_lowpart (SImode, operands[0]); 8952 operands[1] = gen_lowpart (SImode, operands[1]); 8953 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);") 8954 8955;; Since OR can be encoded with sign extended immediate, this is only 8956;; profitable when 7th bit is set. 8957(define_split 8958 [(set (match_operand 0 "register_operand" "") 8959 (ior (match_operand 1 "general_operand" "") 8960 (match_operand 2 "const_int_operand" ""))) 8961 (clobber (reg:CC FLAGS_REG))] 8962 "reload_completed 8963 && ANY_QI_REG_P (operands[0]) 8964 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 8965 && !(INTVAL (operands[2]) & ~255) 8966 && (INTVAL (operands[2]) & 128) 8967 && GET_MODE (operands[0]) != QImode" 8968 [(parallel [(set (strict_low_part (match_dup 0)) 8969 (ior:QI (match_dup 1) 8970 (match_dup 2))) 8971 (clobber (reg:CC FLAGS_REG))])] 8972 "operands[0] = gen_lowpart (QImode, operands[0]); 8973 operands[1] = gen_lowpart (QImode, operands[1]); 8974 operands[2] = gen_lowpart (QImode, operands[2]);") 8975 8976;; Logical XOR instructions 8977 8978;; %%% This used to optimize known byte-wide and operations to memory. 8979;; If this is considered useful, it should be done with splitters. 8980 8981(define_expand "xordi3" 8982 [(set (match_operand:DI 0 "nonimmediate_operand" "") 8983 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "") 8984 (match_operand:DI 2 "x86_64_general_operand" ""))) 8985 (clobber (reg:CC FLAGS_REG))] 8986 "TARGET_64BIT" 8987 "ix86_expand_binary_operator (XOR, DImode, operands); DONE;") 8988 8989(define_insn "*xordi_1_rex64" 8990 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 8991 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 8992 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))) 8993 (clobber (reg:CC FLAGS_REG))] 8994 "TARGET_64BIT 8995 && ix86_binary_operator_ok (XOR, DImode, operands)" 8996 "@ 8997 xor{q}\t{%2, %0|%0, %2} 8998 xor{q}\t{%2, %0|%0, %2}" 8999 [(set_attr "type" "alu") 9000 (set_attr "mode" "DI,DI")]) 9001 9002(define_insn "*xordi_2_rex64" 9003 [(set (reg FLAGS_REG) 9004 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0") 9005 (match_operand:DI 2 "x86_64_general_operand" "rem,re")) 9006 (const_int 0))) 9007 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm") 9008 (xor:DI (match_dup 1) (match_dup 2)))] 9009 "TARGET_64BIT 9010 && ix86_match_ccmode (insn, CCNOmode) 9011 && ix86_binary_operator_ok (XOR, DImode, operands)" 9012 "@ 9013 xor{q}\t{%2, %0|%0, %2} 9014 xor{q}\t{%2, %0|%0, %2}" 9015 [(set_attr "type" "alu") 9016 (set_attr "mode" "DI,DI")]) 9017 9018(define_insn "*xordi_3_rex64" 9019 [(set (reg FLAGS_REG) 9020 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0") 9021 (match_operand:DI 2 "x86_64_general_operand" "rem")) 9022 (const_int 0))) 9023 (clobber (match_scratch:DI 0 "=r"))] 9024 "TARGET_64BIT 9025 && ix86_match_ccmode (insn, CCNOmode) 9026 && ix86_binary_operator_ok (XOR, DImode, operands)" 9027 "xor{q}\t{%2, %0|%0, %2}" 9028 [(set_attr "type" "alu") 9029 (set_attr "mode" "DI")]) 9030 9031(define_expand "xorsi3" 9032 [(set (match_operand:SI 0 "nonimmediate_operand" "") 9033 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "") 9034 (match_operand:SI 2 "general_operand" ""))) 9035 (clobber (reg:CC FLAGS_REG))] 9036 "" 9037 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;") 9038 9039(define_insn "*xorsi_1" 9040 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 9041 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 9042 (match_operand:SI 2 "general_operand" "ri,rm"))) 9043 (clobber (reg:CC FLAGS_REG))] 9044 "ix86_binary_operator_ok (XOR, SImode, operands)" 9045 "xor{l}\t{%2, %0|%0, %2}" 9046 [(set_attr "type" "alu") 9047 (set_attr "mode" "SI")]) 9048 9049;; See comment for addsi_1_zext why we do use nonimmediate_operand 9050;; Add speccase for immediates 9051(define_insn "*xorsi_1_zext" 9052 [(set (match_operand:DI 0 "register_operand" "=r") 9053 (zero_extend:DI 9054 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 9055 (match_operand:SI 2 "general_operand" "rim")))) 9056 (clobber (reg:CC FLAGS_REG))] 9057 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)" 9058 "xor{l}\t{%2, %k0|%k0, %2}" 9059 [(set_attr "type" "alu") 9060 (set_attr "mode" "SI")]) 9061 9062(define_insn "*xorsi_1_zext_imm" 9063 [(set (match_operand:DI 0 "register_operand" "=r") 9064 (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0")) 9065 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z"))) 9066 (clobber (reg:CC FLAGS_REG))] 9067 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)" 9068 "xor{l}\t{%2, %k0|%k0, %2}" 9069 [(set_attr "type" "alu") 9070 (set_attr "mode" "SI")]) 9071 9072(define_insn "*xorsi_2" 9073 [(set (reg FLAGS_REG) 9074 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0") 9075 (match_operand:SI 2 "general_operand" "rim,ri")) 9076 (const_int 0))) 9077 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm") 9078 (xor:SI (match_dup 1) (match_dup 2)))] 9079 "ix86_match_ccmode (insn, CCNOmode) 9080 && ix86_binary_operator_ok (XOR, SImode, operands)" 9081 "xor{l}\t{%2, %0|%0, %2}" 9082 [(set_attr "type" "alu") 9083 (set_attr "mode" "SI")]) 9084 9085;; See comment for addsi_1_zext why we do use nonimmediate_operand 9086;; ??? Special case for immediate operand is missing - it is tricky. 9087(define_insn "*xorsi_2_zext" 9088 [(set (reg FLAGS_REG) 9089 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 9090 (match_operand:SI 2 "general_operand" "rim")) 9091 (const_int 0))) 9092 (set (match_operand:DI 0 "register_operand" "=r") 9093 (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))] 9094 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 9095 && ix86_binary_operator_ok (XOR, SImode, operands)" 9096 "xor{l}\t{%2, %k0|%k0, %2}" 9097 [(set_attr "type" "alu") 9098 (set_attr "mode" "SI")]) 9099 9100(define_insn "*xorsi_2_zext_imm" 9101 [(set (reg FLAGS_REG) 9102 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 9103 (match_operand 2 "x86_64_zext_immediate_operand" "Z")) 9104 (const_int 0))) 9105 (set (match_operand:DI 0 "register_operand" "=r") 9106 (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))] 9107 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 9108 && ix86_binary_operator_ok (XOR, SImode, operands)" 9109 "xor{l}\t{%2, %k0|%k0, %2}" 9110 [(set_attr "type" "alu") 9111 (set_attr "mode" "SI")]) 9112 9113(define_insn "*xorsi_3" 9114 [(set (reg FLAGS_REG) 9115 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0") 9116 (match_operand:SI 2 "general_operand" "rim")) 9117 (const_int 0))) 9118 (clobber (match_scratch:SI 0 "=r"))] 9119 "ix86_match_ccmode (insn, CCNOmode) 9120 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 9121 "xor{l}\t{%2, %0|%0, %2}" 9122 [(set_attr "type" "alu") 9123 (set_attr "mode" "SI")]) 9124 9125(define_expand "xorhi3" 9126 [(set (match_operand:HI 0 "nonimmediate_operand" "") 9127 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "") 9128 (match_operand:HI 2 "general_operand" ""))) 9129 (clobber (reg:CC FLAGS_REG))] 9130 "TARGET_HIMODE_MATH" 9131 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;") 9132 9133(define_insn "*xorhi_1" 9134 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m") 9135 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 9136 (match_operand:HI 2 "general_operand" "rmi,ri"))) 9137 (clobber (reg:CC FLAGS_REG))] 9138 "ix86_binary_operator_ok (XOR, HImode, operands)" 9139 "xor{w}\t{%2, %0|%0, %2}" 9140 [(set_attr "type" "alu") 9141 (set_attr "mode" "HI")]) 9142 9143(define_insn "*xorhi_2" 9144 [(set (reg FLAGS_REG) 9145 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0") 9146 (match_operand:HI 2 "general_operand" "rim,ri")) 9147 (const_int 0))) 9148 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm") 9149 (xor:HI (match_dup 1) (match_dup 2)))] 9150 "ix86_match_ccmode (insn, CCNOmode) 9151 && ix86_binary_operator_ok (XOR, HImode, operands)" 9152 "xor{w}\t{%2, %0|%0, %2}" 9153 [(set_attr "type" "alu") 9154 (set_attr "mode" "HI")]) 9155 9156(define_insn "*xorhi_3" 9157 [(set (reg FLAGS_REG) 9158 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0") 9159 (match_operand:HI 2 "general_operand" "rim")) 9160 (const_int 0))) 9161 (clobber (match_scratch:HI 0 "=r"))] 9162 "ix86_match_ccmode (insn, CCNOmode) 9163 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 9164 "xor{w}\t{%2, %0|%0, %2}" 9165 [(set_attr "type" "alu") 9166 (set_attr "mode" "HI")]) 9167 9168(define_expand "xorqi3" 9169 [(set (match_operand:QI 0 "nonimmediate_operand" "") 9170 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "") 9171 (match_operand:QI 2 "general_operand" ""))) 9172 (clobber (reg:CC FLAGS_REG))] 9173 "TARGET_QIMODE_MATH" 9174 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;") 9175 9176;; %%% Potential partial reg stall on alternative 2. What to do? 9177(define_insn "*xorqi_1" 9178 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r") 9179 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0") 9180 (match_operand:QI 2 "general_operand" "qmi,qi,ri"))) 9181 (clobber (reg:CC FLAGS_REG))] 9182 "ix86_binary_operator_ok (XOR, QImode, operands)" 9183 "@ 9184 xor{b}\t{%2, %0|%0, %2} 9185 xor{b}\t{%2, %0|%0, %2} 9186 xor{l}\t{%k2, %k0|%k0, %k2}" 9187 [(set_attr "type" "alu") 9188 (set_attr "mode" "QI,QI,SI")]) 9189 9190(define_insn "*xorqi_1_slp" 9191 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q")) 9192 (xor:QI (match_dup 0) 9193 (match_operand:QI 1 "general_operand" "qi,qmi"))) 9194 (clobber (reg:CC FLAGS_REG))] 9195 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 9196 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 9197 "xor{b}\t{%1, %0|%0, %1}" 9198 [(set_attr "type" "alu1") 9199 (set_attr "mode" "QI")]) 9200 9201(define_insn "xorqi_ext_0" 9202 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 9203 (const_int 8) 9204 (const_int 8)) 9205 (xor:SI 9206 (zero_extract:SI 9207 (match_operand 1 "ext_register_operand" "0") 9208 (const_int 8) 9209 (const_int 8)) 9210 (match_operand 2 "const_int_operand" "n"))) 9211 (clobber (reg:CC FLAGS_REG))] 9212 "(!TARGET_PARTIAL_REG_STALL || optimize_size)" 9213 "xor{b}\t{%2, %h0|%h0, %2}" 9214 [(set_attr "type" "alu") 9215 (set_attr "length_immediate" "1") 9216 (set_attr "mode" "QI")]) 9217 9218(define_insn "*xorqi_ext_1" 9219 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 9220 (const_int 8) 9221 (const_int 8)) 9222 (xor:SI 9223 (zero_extract:SI 9224 (match_operand 1 "ext_register_operand" "0") 9225 (const_int 8) 9226 (const_int 8)) 9227 (zero_extend:SI 9228 (match_operand:QI 2 "general_operand" "Qm")))) 9229 (clobber (reg:CC FLAGS_REG))] 9230 "!TARGET_64BIT 9231 && (!TARGET_PARTIAL_REG_STALL || optimize_size)" 9232 "xor{b}\t{%2, %h0|%h0, %2}" 9233 [(set_attr "type" "alu") 9234 (set_attr "length_immediate" "0") 9235 (set_attr "mode" "QI")]) 9236 9237(define_insn "*xorqi_ext_1_rex64" 9238 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 9239 (const_int 8) 9240 (const_int 8)) 9241 (xor:SI 9242 (zero_extract:SI 9243 (match_operand 1 "ext_register_operand" "0") 9244 (const_int 8) 9245 (const_int 8)) 9246 (zero_extend:SI 9247 (match_operand 2 "ext_register_operand" "Q")))) 9248 (clobber (reg:CC FLAGS_REG))] 9249 "TARGET_64BIT 9250 && (!TARGET_PARTIAL_REG_STALL || optimize_size)" 9251 "xor{b}\t{%2, %h0|%h0, %2}" 9252 [(set_attr "type" "alu") 9253 (set_attr "length_immediate" "0") 9254 (set_attr "mode" "QI")]) 9255 9256(define_insn "*xorqi_ext_2" 9257 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 9258 (const_int 8) 9259 (const_int 8)) 9260 (xor:SI 9261 (zero_extract:SI (match_operand 1 "ext_register_operand" "0") 9262 (const_int 8) 9263 (const_int 8)) 9264 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q") 9265 (const_int 8) 9266 (const_int 8)))) 9267 (clobber (reg:CC FLAGS_REG))] 9268 "(!TARGET_PARTIAL_REG_STALL || optimize_size)" 9269 "xor{b}\t{%h2, %h0|%h0, %h2}" 9270 [(set_attr "type" "alu") 9271 (set_attr "length_immediate" "0") 9272 (set_attr "mode" "QI")]) 9273 9274(define_insn "*xorqi_cc_1" 9275 [(set (reg FLAGS_REG) 9276 (compare 9277 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0") 9278 (match_operand:QI 2 "general_operand" "qim,qi")) 9279 (const_int 0))) 9280 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm") 9281 (xor:QI (match_dup 1) (match_dup 2)))] 9282 "ix86_match_ccmode (insn, CCNOmode) 9283 && ix86_binary_operator_ok (XOR, QImode, operands)" 9284 "xor{b}\t{%2, %0|%0, %2}" 9285 [(set_attr "type" "alu") 9286 (set_attr "mode" "QI")]) 9287 9288(define_insn "*xorqi_2_slp" 9289 [(set (reg FLAGS_REG) 9290 (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm") 9291 (match_operand:QI 1 "general_operand" "qim,qi")) 9292 (const_int 0))) 9293 (set (strict_low_part (match_dup 0)) 9294 (xor:QI (match_dup 0) (match_dup 1)))] 9295 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 9296 && ix86_match_ccmode (insn, CCNOmode) 9297 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 9298 "xor{b}\t{%1, %0|%0, %1}" 9299 [(set_attr "type" "alu1") 9300 (set_attr "mode" "QI")]) 9301 9302(define_insn "*xorqi_cc_2" 9303 [(set (reg FLAGS_REG) 9304 (compare 9305 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0") 9306 (match_operand:QI 2 "general_operand" "qim")) 9307 (const_int 0))) 9308 (clobber (match_scratch:QI 0 "=q"))] 9309 "ix86_match_ccmode (insn, CCNOmode) 9310 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 9311 "xor{b}\t{%2, %0|%0, %2}" 9312 [(set_attr "type" "alu") 9313 (set_attr "mode" "QI")]) 9314 9315(define_insn "*xorqi_cc_ext_1" 9316 [(set (reg FLAGS_REG) 9317 (compare 9318 (xor:SI 9319 (zero_extract:SI 9320 (match_operand 1 "ext_register_operand" "0") 9321 (const_int 8) 9322 (const_int 8)) 9323 (match_operand:QI 2 "general_operand" "qmn")) 9324 (const_int 0))) 9325 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q") 9326 (const_int 8) 9327 (const_int 8)) 9328 (xor:SI 9329 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8)) 9330 (match_dup 2)))] 9331 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)" 9332 "xor{b}\t{%2, %h0|%h0, %2}" 9333 [(set_attr "type" "alu") 9334 (set_attr "mode" "QI")]) 9335 9336(define_insn "*xorqi_cc_ext_1_rex64" 9337 [(set (reg FLAGS_REG) 9338 (compare 9339 (xor:SI 9340 (zero_extract:SI 9341 (match_operand 1 "ext_register_operand" "0") 9342 (const_int 8) 9343 (const_int 8)) 9344 (match_operand:QI 2 "nonmemory_operand" "Qn")) 9345 (const_int 0))) 9346 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q") 9347 (const_int 8) 9348 (const_int 8)) 9349 (xor:SI 9350 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8)) 9351 (match_dup 2)))] 9352 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)" 9353 "xor{b}\t{%2, %h0|%h0, %2}" 9354 [(set_attr "type" "alu") 9355 (set_attr "mode" "QI")]) 9356 9357(define_expand "xorqi_cc_ext_1" 9358 [(parallel [ 9359 (set (reg:CCNO FLAGS_REG) 9360 (compare:CCNO 9361 (xor:SI 9362 (zero_extract:SI 9363 (match_operand 1 "ext_register_operand" "") 9364 (const_int 8) 9365 (const_int 8)) 9366 (match_operand:QI 2 "general_operand" "")) 9367 (const_int 0))) 9368 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "") 9369 (const_int 8) 9370 (const_int 8)) 9371 (xor:SI 9372 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8)) 9373 (match_dup 2)))])] 9374 "" 9375 "") 9376 9377(define_split 9378 [(set (match_operand 0 "register_operand" "") 9379 (xor (match_operand 1 "register_operand" "") 9380 (match_operand 2 "const_int_operand" ""))) 9381 (clobber (reg:CC FLAGS_REG))] 9382 "reload_completed 9383 && QI_REG_P (operands[0]) 9384 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 9385 && !(INTVAL (operands[2]) & ~(255 << 8)) 9386 && GET_MODE (operands[0]) != QImode" 9387 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8)) 9388 (xor:SI (zero_extract:SI (match_dup 1) 9389 (const_int 8) (const_int 8)) 9390 (match_dup 2))) 9391 (clobber (reg:CC FLAGS_REG))])] 9392 "operands[0] = gen_lowpart (SImode, operands[0]); 9393 operands[1] = gen_lowpart (SImode, operands[1]); 9394 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);") 9395 9396;; Since XOR can be encoded with sign extended immediate, this is only 9397;; profitable when 7th bit is set. 9398(define_split 9399 [(set (match_operand 0 "register_operand" "") 9400 (xor (match_operand 1 "general_operand" "") 9401 (match_operand 2 "const_int_operand" ""))) 9402 (clobber (reg:CC FLAGS_REG))] 9403 "reload_completed 9404 && ANY_QI_REG_P (operands[0]) 9405 && (!TARGET_PARTIAL_REG_STALL || optimize_size) 9406 && !(INTVAL (operands[2]) & ~255) 9407 && (INTVAL (operands[2]) & 128) 9408 && GET_MODE (operands[0]) != QImode" 9409 [(parallel [(set (strict_low_part (match_dup 0)) 9410 (xor:QI (match_dup 1) 9411 (match_dup 2))) 9412 (clobber (reg:CC FLAGS_REG))])] 9413 "operands[0] = gen_lowpart (QImode, operands[0]); 9414 operands[1] = gen_lowpart (QImode, operands[1]); 9415 operands[2] = gen_lowpart (QImode, operands[2]);") 9416 9417;; Negation instructions 9418 9419(define_expand "negti2" 9420 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "") 9421 (neg:TI (match_operand:TI 1 "nonimmediate_operand" ""))) 9422 (clobber (reg:CC FLAGS_REG))])] 9423 "TARGET_64BIT" 9424 "ix86_expand_unary_operator (NEG, TImode, operands); DONE;") 9425 9426(define_insn "*negti2_1" 9427 [(set (match_operand:TI 0 "nonimmediate_operand" "=ro") 9428 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "0"))) 9429 (clobber (reg:CC FLAGS_REG))] 9430 "TARGET_64BIT 9431 && ix86_unary_operator_ok (NEG, TImode, operands)" 9432 "#") 9433 9434(define_split 9435 [(set (match_operand:TI 0 "nonimmediate_operand" "") 9436 (neg:TI (match_operand:TI 1 "nonimmediate_operand" ""))) 9437 (clobber (reg:CC FLAGS_REG))] 9438 "TARGET_64BIT && reload_completed" 9439 [(parallel 9440 [(set (reg:CCZ FLAGS_REG) 9441 (compare:CCZ (neg:DI (match_dup 2)) (const_int 0))) 9442 (set (match_dup 0) (neg:DI (match_dup 2)))]) 9443 (parallel 9444 [(set (match_dup 1) 9445 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0)) 9446 (match_dup 3)) 9447 (const_int 0))) 9448 (clobber (reg:CC FLAGS_REG))]) 9449 (parallel 9450 [(set (match_dup 1) 9451 (neg:DI (match_dup 1))) 9452 (clobber (reg:CC FLAGS_REG))])] 9453 "split_ti (operands+1, 1, operands+2, operands+3); 9454 split_ti (operands+0, 1, operands+0, operands+1);") 9455 9456(define_expand "negdi2" 9457 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "") 9458 (neg:DI (match_operand:DI 1 "nonimmediate_operand" ""))) 9459 (clobber (reg:CC FLAGS_REG))])] 9460 "" 9461 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;") 9462 9463(define_insn "*negdi2_1" 9464 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro") 9465 (neg:DI (match_operand:DI 1 "general_operand" "0"))) 9466 (clobber (reg:CC FLAGS_REG))] 9467 "!TARGET_64BIT 9468 && ix86_unary_operator_ok (NEG, DImode, operands)" 9469 "#") 9470 9471(define_split 9472 [(set (match_operand:DI 0 "nonimmediate_operand" "") 9473 (neg:DI (match_operand:DI 1 "general_operand" ""))) 9474 (clobber (reg:CC FLAGS_REG))] 9475 "!TARGET_64BIT && reload_completed" 9476 [(parallel 9477 [(set (reg:CCZ FLAGS_REG) 9478 (compare:CCZ (neg:SI (match_dup 2)) (const_int 0))) 9479 (set (match_dup 0) (neg:SI (match_dup 2)))]) 9480 (parallel 9481 [(set (match_dup 1) 9482 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0)) 9483 (match_dup 3)) 9484 (const_int 0))) 9485 (clobber (reg:CC FLAGS_REG))]) 9486 (parallel 9487 [(set (match_dup 1) 9488 (neg:SI (match_dup 1))) 9489 (clobber (reg:CC FLAGS_REG))])] 9490 "split_di (operands+1, 1, operands+2, operands+3); 9491 split_di (operands+0, 1, operands+0, operands+1);") 9492 9493(define_insn "*negdi2_1_rex64" 9494 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 9495 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))) 9496 (clobber (reg:CC FLAGS_REG))] 9497 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)" 9498 "neg{q}\t%0" 9499 [(set_attr "type" "negnot") 9500 (set_attr "mode" "DI")]) 9501 9502;; The problem with neg is that it does not perform (compare x 0), 9503;; it really performs (compare 0 x), which leaves us with the zero 9504;; flag being the only useful item. 9505 9506(define_insn "*negdi2_cmpz_rex64" 9507 [(set (reg:CCZ FLAGS_REG) 9508 (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")) 9509 (const_int 0))) 9510 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 9511 (neg:DI (match_dup 1)))] 9512 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)" 9513 "neg{q}\t%0" 9514 [(set_attr "type" "negnot") 9515 (set_attr "mode" "DI")]) 9516 9517 9518(define_expand "negsi2" 9519 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "") 9520 (neg:SI (match_operand:SI 1 "nonimmediate_operand" ""))) 9521 (clobber (reg:CC FLAGS_REG))])] 9522 "" 9523 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;") 9524 9525(define_insn "*negsi2_1" 9526 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 9527 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))) 9528 (clobber (reg:CC FLAGS_REG))] 9529 "ix86_unary_operator_ok (NEG, SImode, operands)" 9530 "neg{l}\t%0" 9531 [(set_attr "type" "negnot") 9532 (set_attr "mode" "SI")]) 9533 9534;; Combine is quite creative about this pattern. 9535(define_insn "*negsi2_1_zext" 9536 [(set (match_operand:DI 0 "register_operand" "=r") 9537 (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0") 9538 (const_int 32))) 9539 (const_int 32))) 9540 (clobber (reg:CC FLAGS_REG))] 9541 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)" 9542 "neg{l}\t%k0" 9543 [(set_attr "type" "negnot") 9544 (set_attr "mode" "SI")]) 9545 9546;; The problem with neg is that it does not perform (compare x 0), 9547;; it really performs (compare 0 x), which leaves us with the zero 9548;; flag being the only useful item. 9549 9550(define_insn "*negsi2_cmpz" 9551 [(set (reg:CCZ FLAGS_REG) 9552 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")) 9553 (const_int 0))) 9554 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 9555 (neg:SI (match_dup 1)))] 9556 "ix86_unary_operator_ok (NEG, SImode, operands)" 9557 "neg{l}\t%0" 9558 [(set_attr "type" "negnot") 9559 (set_attr "mode" "SI")]) 9560 9561(define_insn "*negsi2_cmpz_zext" 9562 [(set (reg:CCZ FLAGS_REG) 9563 (compare:CCZ (lshiftrt:DI 9564 (neg:DI (ashift:DI 9565 (match_operand:DI 1 "register_operand" "0") 9566 (const_int 32))) 9567 (const_int 32)) 9568 (const_int 0))) 9569 (set (match_operand:DI 0 "register_operand" "=r") 9570 (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1) 9571 (const_int 32))) 9572 (const_int 32)))] 9573 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)" 9574 "neg{l}\t%k0" 9575 [(set_attr "type" "negnot") 9576 (set_attr "mode" "SI")]) 9577 9578(define_expand "neghi2" 9579 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "") 9580 (neg:HI (match_operand:HI 1 "nonimmediate_operand" ""))) 9581 (clobber (reg:CC FLAGS_REG))])] 9582 "TARGET_HIMODE_MATH" 9583 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;") 9584 9585(define_insn "*neghi2_1" 9586 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 9587 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))) 9588 (clobber (reg:CC FLAGS_REG))] 9589 "ix86_unary_operator_ok (NEG, HImode, operands)" 9590 "neg{w}\t%0" 9591 [(set_attr "type" "negnot") 9592 (set_attr "mode" "HI")]) 9593 9594(define_insn "*neghi2_cmpz" 9595 [(set (reg:CCZ FLAGS_REG) 9596 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")) 9597 (const_int 0))) 9598 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 9599 (neg:HI (match_dup 1)))] 9600 "ix86_unary_operator_ok (NEG, HImode, operands)" 9601 "neg{w}\t%0" 9602 [(set_attr "type" "negnot") 9603 (set_attr "mode" "HI")]) 9604 9605(define_expand "negqi2" 9606 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "") 9607 (neg:QI (match_operand:QI 1 "nonimmediate_operand" ""))) 9608 (clobber (reg:CC FLAGS_REG))])] 9609 "TARGET_QIMODE_MATH" 9610 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;") 9611 9612(define_insn "*negqi2_1" 9613 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 9614 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))) 9615 (clobber (reg:CC FLAGS_REG))] 9616 "ix86_unary_operator_ok (NEG, QImode, operands)" 9617 "neg{b}\t%0" 9618 [(set_attr "type" "negnot") 9619 (set_attr "mode" "QI")]) 9620 9621(define_insn "*negqi2_cmpz" 9622 [(set (reg:CCZ FLAGS_REG) 9623 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")) 9624 (const_int 0))) 9625 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 9626 (neg:QI (match_dup 1)))] 9627 "ix86_unary_operator_ok (NEG, QImode, operands)" 9628 "neg{b}\t%0" 9629 [(set_attr "type" "negnot") 9630 (set_attr "mode" "QI")]) 9631 9632;; Changing of sign for FP values is doable using integer unit too. 9633 9634(define_expand "negsf2" 9635 [(set (match_operand:SF 0 "nonimmediate_operand" "") 9636 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))] 9637 "TARGET_80387 || TARGET_SSE_MATH" 9638 "ix86_expand_fp_absneg_operator (NEG, SFmode, operands); DONE;") 9639 9640(define_expand "abssf2" 9641 [(set (match_operand:SF 0 "nonimmediate_operand" "") 9642 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "")))] 9643 "TARGET_80387 || TARGET_SSE_MATH" 9644 "ix86_expand_fp_absneg_operator (ABS, SFmode, operands); DONE;") 9645 9646(define_insn "*absnegsf2_mixed" 9647 [(set (match_operand:SF 0 "nonimmediate_operand" "=x ,x,f,rm") 9648 (match_operator:SF 3 "absneg_operator" 9649 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0,0 ")])) 9650 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm ,0,X,X ")) 9651 (clobber (reg:CC FLAGS_REG))] 9652 "TARGET_SSE_MATH && TARGET_MIX_SSE_I387 9653 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)" 9654 "#") 9655 9656(define_insn "*absnegsf2_sse" 9657 [(set (match_operand:SF 0 "nonimmediate_operand" "=x,x,rm") 9658 (match_operator:SF 3 "absneg_operator" 9659 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0")])) 9660 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,X")) 9661 (clobber (reg:CC FLAGS_REG))] 9662 "TARGET_SSE_MATH 9663 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)" 9664 "#") 9665 9666(define_insn "*absnegsf2_i387" 9667 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,rm") 9668 (match_operator:SF 3 "absneg_operator" 9669 [(match_operand:SF 1 "nonimmediate_operand" "0,0")])) 9670 (use (match_operand 2 "" "")) 9671 (clobber (reg:CC FLAGS_REG))] 9672 "TARGET_80387 && !TARGET_SSE_MATH 9673 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)" 9674 "#") 9675 9676(define_expand "copysignsf3" 9677 [(match_operand:SF 0 "register_operand" "") 9678 (match_operand:SF 1 "nonmemory_operand" "") 9679 (match_operand:SF 2 "register_operand" "")] 9680 "TARGET_SSE_MATH" 9681{ 9682 ix86_expand_copysign (operands); 9683 DONE; 9684}) 9685 9686(define_insn_and_split "copysignsf3_const" 9687 [(set (match_operand:SF 0 "register_operand" "=x") 9688 (unspec:SF 9689 [(match_operand:V4SF 1 "vector_move_operand" "xmC") 9690 (match_operand:SF 2 "register_operand" "0") 9691 (match_operand:V4SF 3 "nonimmediate_operand" "xm")] 9692 UNSPEC_COPYSIGN))] 9693 "TARGET_SSE_MATH" 9694 "#" 9695 "&& reload_completed" 9696 [(const_int 0)] 9697{ 9698 ix86_split_copysign_const (operands); 9699 DONE; 9700}) 9701 9702(define_insn "copysignsf3_var" 9703 [(set (match_operand:SF 0 "register_operand" "=x, x, x, x,x") 9704 (unspec:SF 9705 [(match_operand:SF 2 "register_operand" " x, 0, 0, x,x") 9706 (match_operand:SF 3 "register_operand" " 1, 1, x, 1,x") 9707 (match_operand:V4SF 4 "nonimmediate_operand" " X,xm,xm, 0,0") 9708 (match_operand:V4SF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")] 9709 UNSPEC_COPYSIGN)) 9710 (clobber (match_scratch:V4SF 1 "=x, x, x, x,x"))] 9711 "TARGET_SSE_MATH" 9712 "#") 9713 9714(define_split 9715 [(set (match_operand:SF 0 "register_operand" "") 9716 (unspec:SF 9717 [(match_operand:SF 2 "register_operand" "") 9718 (match_operand:SF 3 "register_operand" "") 9719 (match_operand:V4SF 4 "" "") 9720 (match_operand:V4SF 5 "" "")] 9721 UNSPEC_COPYSIGN)) 9722 (clobber (match_scratch:V4SF 1 ""))] 9723 "TARGET_SSE_MATH && reload_completed" 9724 [(const_int 0)] 9725{ 9726 ix86_split_copysign_var (operands); 9727 DONE; 9728}) 9729 9730(define_expand "negdf2" 9731 [(set (match_operand:DF 0 "nonimmediate_operand" "") 9732 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))] 9733 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 9734 "ix86_expand_fp_absneg_operator (NEG, DFmode, operands); DONE;") 9735 9736(define_expand "absdf2" 9737 [(set (match_operand:DF 0 "nonimmediate_operand" "") 9738 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "")))] 9739 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 9740 "ix86_expand_fp_absneg_operator (ABS, DFmode, operands); DONE;") 9741 9742(define_insn "*absnegdf2_mixed" 9743 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,Y,f,rm") 9744 (match_operator:DF 3 "absneg_operator" 9745 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0,0")])) 9746 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,X,X")) 9747 (clobber (reg:CC FLAGS_REG))] 9748 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387 9749 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)" 9750 "#") 9751 9752(define_insn "*absnegdf2_sse" 9753 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,Y,rm") 9754 (match_operator:DF 3 "absneg_operator" 9755 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0 ")])) 9756 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,X ")) 9757 (clobber (reg:CC FLAGS_REG))] 9758 "TARGET_SSE2 && TARGET_SSE_MATH 9759 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)" 9760 "#") 9761 9762(define_insn "*absnegdf2_i387" 9763 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,rm") 9764 (match_operator:DF 3 "absneg_operator" 9765 [(match_operand:DF 1 "nonimmediate_operand" "0,0")])) 9766 (use (match_operand 2 "" "")) 9767 (clobber (reg:CC FLAGS_REG))] 9768 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH) 9769 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)" 9770 "#") 9771 9772(define_expand "copysigndf3" 9773 [(match_operand:DF 0 "register_operand" "") 9774 (match_operand:DF 1 "nonmemory_operand" "") 9775 (match_operand:DF 2 "register_operand" "")] 9776 "TARGET_SSE2 && TARGET_SSE_MATH" 9777{ 9778 ix86_expand_copysign (operands); 9779 DONE; 9780}) 9781 9782(define_insn_and_split "copysigndf3_const" 9783 [(set (match_operand:DF 0 "register_operand" "=x") 9784 (unspec:DF 9785 [(match_operand:V2DF 1 "vector_move_operand" "xmC") 9786 (match_operand:DF 2 "register_operand" "0") 9787 (match_operand:V2DF 3 "nonimmediate_operand" "xm")] 9788 UNSPEC_COPYSIGN))] 9789 "TARGET_SSE2 && TARGET_SSE_MATH" 9790 "#" 9791 "&& reload_completed" 9792 [(const_int 0)] 9793{ 9794 ix86_split_copysign_const (operands); 9795 DONE; 9796}) 9797 9798(define_insn "copysigndf3_var" 9799 [(set (match_operand:DF 0 "register_operand" "=x, x, x, x,x") 9800 (unspec:DF 9801 [(match_operand:DF 2 "register_operand" " x, 0, 0, x,x") 9802 (match_operand:DF 3 "register_operand" " 1, 1, x, 1,x") 9803 (match_operand:V2DF 4 "nonimmediate_operand" " X,xm,xm, 0,0") 9804 (match_operand:V2DF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")] 9805 UNSPEC_COPYSIGN)) 9806 (clobber (match_scratch:V2DF 1 "=x, x, x, x,x"))] 9807 "TARGET_SSE2 && TARGET_SSE_MATH" 9808 "#") 9809 9810(define_split 9811 [(set (match_operand:DF 0 "register_operand" "") 9812 (unspec:DF 9813 [(match_operand:DF 2 "register_operand" "") 9814 (match_operand:DF 3 "register_operand" "") 9815 (match_operand:V2DF 4 "" "") 9816 (match_operand:V2DF 5 "" "")] 9817 UNSPEC_COPYSIGN)) 9818 (clobber (match_scratch:V2DF 1 ""))] 9819 "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed" 9820 [(const_int 0)] 9821{ 9822 ix86_split_copysign_var (operands); 9823 DONE; 9824}) 9825 9826(define_expand "negxf2" 9827 [(set (match_operand:XF 0 "nonimmediate_operand" "") 9828 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))] 9829 "TARGET_80387" 9830 "ix86_expand_fp_absneg_operator (NEG, XFmode, operands); DONE;") 9831 9832(define_expand "absxf2" 9833 [(set (match_operand:XF 0 "nonimmediate_operand" "") 9834 (abs:XF (match_operand:XF 1 "nonimmediate_operand" "")))] 9835 "TARGET_80387" 9836 "ix86_expand_fp_absneg_operator (ABS, XFmode, operands); DONE;") 9837 9838(define_insn "*absnegxf2_i387" 9839 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,?rm") 9840 (match_operator:XF 3 "absneg_operator" 9841 [(match_operand:XF 1 "nonimmediate_operand" "0,0")])) 9842 (use (match_operand 2 "" "")) 9843 (clobber (reg:CC FLAGS_REG))] 9844 "TARGET_80387 9845 && ix86_unary_operator_ok (GET_CODE (operands[3]), XFmode, operands)" 9846 "#") 9847 9848;; Splitters for fp abs and neg. 9849 9850(define_split 9851 [(set (match_operand 0 "fp_register_operand" "") 9852 (match_operator 1 "absneg_operator" [(match_dup 0)])) 9853 (use (match_operand 2 "" "")) 9854 (clobber (reg:CC FLAGS_REG))] 9855 "reload_completed" 9856 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))]) 9857 9858(define_split 9859 [(set (match_operand 0 "register_operand" "") 9860 (match_operator 3 "absneg_operator" 9861 [(match_operand 1 "register_operand" "")])) 9862 (use (match_operand 2 "nonimmediate_operand" "")) 9863 (clobber (reg:CC FLAGS_REG))] 9864 "reload_completed && SSE_REG_P (operands[0])" 9865 [(set (match_dup 0) (match_dup 3))] 9866{ 9867 enum machine_mode mode = GET_MODE (operands[0]); 9868 enum machine_mode vmode = GET_MODE (operands[2]); 9869 rtx tmp; 9870 9871 operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0); 9872 operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0); 9873 if (operands_match_p (operands[0], operands[2])) 9874 { 9875 tmp = operands[1]; 9876 operands[1] = operands[2]; 9877 operands[2] = tmp; 9878 } 9879 if (GET_CODE (operands[3]) == ABS) 9880 tmp = gen_rtx_AND (vmode, operands[1], operands[2]); 9881 else 9882 tmp = gen_rtx_XOR (vmode, operands[1], operands[2]); 9883 operands[3] = tmp; 9884}) 9885 9886(define_split 9887 [(set (match_operand:SF 0 "register_operand" "") 9888 (match_operator:SF 1 "absneg_operator" [(match_dup 0)])) 9889 (use (match_operand:V4SF 2 "" "")) 9890 (clobber (reg:CC FLAGS_REG))] 9891 "reload_completed" 9892 [(parallel [(set (match_dup 0) (match_dup 1)) 9893 (clobber (reg:CC FLAGS_REG))])] 9894{ 9895 rtx tmp; 9896 operands[0] = gen_lowpart (SImode, operands[0]); 9897 if (GET_CODE (operands[1]) == ABS) 9898 { 9899 tmp = gen_int_mode (0x7fffffff, SImode); 9900 tmp = gen_rtx_AND (SImode, operands[0], tmp); 9901 } 9902 else 9903 { 9904 tmp = gen_int_mode (0x80000000, SImode); 9905 tmp = gen_rtx_XOR (SImode, operands[0], tmp); 9906 } 9907 operands[1] = tmp; 9908}) 9909 9910(define_split 9911 [(set (match_operand:DF 0 "register_operand" "") 9912 (match_operator:DF 1 "absneg_operator" [(match_dup 0)])) 9913 (use (match_operand 2 "" "")) 9914 (clobber (reg:CC FLAGS_REG))] 9915 "reload_completed" 9916 [(parallel [(set (match_dup 0) (match_dup 1)) 9917 (clobber (reg:CC FLAGS_REG))])] 9918{ 9919 rtx tmp; 9920 if (TARGET_64BIT) 9921 { 9922 tmp = gen_lowpart (DImode, operands[0]); 9923 tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63)); 9924 operands[0] = tmp; 9925 9926 if (GET_CODE (operands[1]) == ABS) 9927 tmp = const0_rtx; 9928 else 9929 tmp = gen_rtx_NOT (DImode, tmp); 9930 } 9931 else 9932 { 9933 operands[0] = gen_highpart (SImode, operands[0]); 9934 if (GET_CODE (operands[1]) == ABS) 9935 { 9936 tmp = gen_int_mode (0x7fffffff, SImode); 9937 tmp = gen_rtx_AND (SImode, operands[0], tmp); 9938 } 9939 else 9940 { 9941 tmp = gen_int_mode (0x80000000, SImode); 9942 tmp = gen_rtx_XOR (SImode, operands[0], tmp); 9943 } 9944 } 9945 operands[1] = tmp; 9946}) 9947 9948(define_split 9949 [(set (match_operand:XF 0 "register_operand" "") 9950 (match_operator:XF 1 "absneg_operator" [(match_dup 0)])) 9951 (use (match_operand 2 "" "")) 9952 (clobber (reg:CC FLAGS_REG))] 9953 "reload_completed" 9954 [(parallel [(set (match_dup 0) (match_dup 1)) 9955 (clobber (reg:CC FLAGS_REG))])] 9956{ 9957 rtx tmp; 9958 operands[0] = gen_rtx_REG (SImode, 9959 true_regnum (operands[0]) 9960 + (TARGET_64BIT ? 1 : 2)); 9961 if (GET_CODE (operands[1]) == ABS) 9962 { 9963 tmp = GEN_INT (0x7fff); 9964 tmp = gen_rtx_AND (SImode, operands[0], tmp); 9965 } 9966 else 9967 { 9968 tmp = GEN_INT (0x8000); 9969 tmp = gen_rtx_XOR (SImode, operands[0], tmp); 9970 } 9971 operands[1] = tmp; 9972}) 9973 9974(define_split 9975 [(set (match_operand 0 "memory_operand" "") 9976 (match_operator 1 "absneg_operator" [(match_dup 0)])) 9977 (use (match_operand 2 "" "")) 9978 (clobber (reg:CC FLAGS_REG))] 9979 "reload_completed" 9980 [(parallel [(set (match_dup 0) (match_dup 1)) 9981 (clobber (reg:CC FLAGS_REG))])] 9982{ 9983 enum machine_mode mode = GET_MODE (operands[0]); 9984 int size = mode == XFmode ? 10 : GET_MODE_SIZE (mode); 9985 rtx tmp; 9986 9987 operands[0] = adjust_address (operands[0], QImode, size - 1); 9988 if (GET_CODE (operands[1]) == ABS) 9989 { 9990 tmp = gen_int_mode (0x7f, QImode); 9991 tmp = gen_rtx_AND (QImode, operands[0], tmp); 9992 } 9993 else 9994 { 9995 tmp = gen_int_mode (0x80, QImode); 9996 tmp = gen_rtx_XOR (QImode, operands[0], tmp); 9997 } 9998 operands[1] = tmp; 9999}) 10000 10001;; Conditionalize these after reload. If they match before reload, we 10002;; lose the clobber and ability to use integer instructions. 10003 10004(define_insn "*negsf2_1" 10005 [(set (match_operand:SF 0 "register_operand" "=f") 10006 (neg:SF (match_operand:SF 1 "register_operand" "0")))] 10007 "TARGET_80387 && (reload_completed || !TARGET_SSE_MATH)" 10008 "fchs" 10009 [(set_attr "type" "fsgn") 10010 (set_attr "mode" "SF")]) 10011 10012(define_insn "*negdf2_1" 10013 [(set (match_operand:DF 0 "register_operand" "=f") 10014 (neg:DF (match_operand:DF 1 "register_operand" "0")))] 10015 "TARGET_80387 && (reload_completed || !(TARGET_SSE2 && TARGET_SSE_MATH))" 10016 "fchs" 10017 [(set_attr "type" "fsgn") 10018 (set_attr "mode" "DF")]) 10019 10020(define_insn "*negxf2_1" 10021 [(set (match_operand:XF 0 "register_operand" "=f") 10022 (neg:XF (match_operand:XF 1 "register_operand" "0")))] 10023 "TARGET_80387" 10024 "fchs" 10025 [(set_attr "type" "fsgn") 10026 (set_attr "mode" "XF")]) 10027 10028(define_insn "*abssf2_1" 10029 [(set (match_operand:SF 0 "register_operand" "=f") 10030 (abs:SF (match_operand:SF 1 "register_operand" "0")))] 10031 "TARGET_80387 && (reload_completed || !TARGET_SSE_MATH)" 10032 "fabs" 10033 [(set_attr "type" "fsgn") 10034 (set_attr "mode" "SF")]) 10035 10036(define_insn "*absdf2_1" 10037 [(set (match_operand:DF 0 "register_operand" "=f") 10038 (abs:DF (match_operand:DF 1 "register_operand" "0")))] 10039 "TARGET_80387 && (reload_completed || !(TARGET_SSE2 && TARGET_SSE_MATH))" 10040 "fabs" 10041 [(set_attr "type" "fsgn") 10042 (set_attr "mode" "DF")]) 10043 10044(define_insn "*absxf2_1" 10045 [(set (match_operand:XF 0 "register_operand" "=f") 10046 (abs:XF (match_operand:XF 1 "register_operand" "0")))] 10047 "TARGET_80387" 10048 "fabs" 10049 [(set_attr "type" "fsgn") 10050 (set_attr "mode" "DF")]) 10051 10052(define_insn "*negextendsfdf2" 10053 [(set (match_operand:DF 0 "register_operand" "=f") 10054 (neg:DF (float_extend:DF 10055 (match_operand:SF 1 "register_operand" "0"))))] 10056 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)" 10057 "fchs" 10058 [(set_attr "type" "fsgn") 10059 (set_attr "mode" "DF")]) 10060 10061(define_insn "*negextenddfxf2" 10062 [(set (match_operand:XF 0 "register_operand" "=f") 10063 (neg:XF (float_extend:XF 10064 (match_operand:DF 1 "register_operand" "0"))))] 10065 "TARGET_80387" 10066 "fchs" 10067 [(set_attr "type" "fsgn") 10068 (set_attr "mode" "XF")]) 10069 10070(define_insn "*negextendsfxf2" 10071 [(set (match_operand:XF 0 "register_operand" "=f") 10072 (neg:XF (float_extend:XF 10073 (match_operand:SF 1 "register_operand" "0"))))] 10074 "TARGET_80387" 10075 "fchs" 10076 [(set_attr "type" "fsgn") 10077 (set_attr "mode" "XF")]) 10078 10079(define_insn "*absextendsfdf2" 10080 [(set (match_operand:DF 0 "register_operand" "=f") 10081 (abs:DF (float_extend:DF 10082 (match_operand:SF 1 "register_operand" "0"))))] 10083 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)" 10084 "fabs" 10085 [(set_attr "type" "fsgn") 10086 (set_attr "mode" "DF")]) 10087 10088(define_insn "*absextenddfxf2" 10089 [(set (match_operand:XF 0 "register_operand" "=f") 10090 (abs:XF (float_extend:XF 10091 (match_operand:DF 1 "register_operand" "0"))))] 10092 "TARGET_80387" 10093 "fabs" 10094 [(set_attr "type" "fsgn") 10095 (set_attr "mode" "XF")]) 10096 10097(define_insn "*absextendsfxf2" 10098 [(set (match_operand:XF 0 "register_operand" "=f") 10099 (abs:XF (float_extend:XF 10100 (match_operand:SF 1 "register_operand" "0"))))] 10101 "TARGET_80387" 10102 "fabs" 10103 [(set_attr "type" "fsgn") 10104 (set_attr "mode" "XF")]) 10105 10106;; One complement instructions 10107 10108(define_expand "one_cmpldi2" 10109 [(set (match_operand:DI 0 "nonimmediate_operand" "") 10110 (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))] 10111 "TARGET_64BIT" 10112 "ix86_expand_unary_operator (NOT, DImode, operands); DONE;") 10113 10114(define_insn "*one_cmpldi2_1_rex64" 10115 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 10116 (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))] 10117 "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)" 10118 "not{q}\t%0" 10119 [(set_attr "type" "negnot") 10120 (set_attr "mode" "DI")]) 10121 10122(define_insn "*one_cmpldi2_2_rex64" 10123 [(set (reg FLAGS_REG) 10124 (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")) 10125 (const_int 0))) 10126 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 10127 (not:DI (match_dup 1)))] 10128 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 10129 && ix86_unary_operator_ok (NOT, DImode, operands)" 10130 "#" 10131 [(set_attr "type" "alu1") 10132 (set_attr "mode" "DI")]) 10133 10134(define_split 10135 [(set (match_operand 0 "flags_reg_operand" "") 10136 (match_operator 2 "compare_operator" 10137 [(not:DI (match_operand:DI 3 "nonimmediate_operand" "")) 10138 (const_int 0)])) 10139 (set (match_operand:DI 1 "nonimmediate_operand" "") 10140 (not:DI (match_dup 3)))] 10141 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)" 10142 [(parallel [(set (match_dup 0) 10143 (match_op_dup 2 10144 [(xor:DI (match_dup 3) (const_int -1)) 10145 (const_int 0)])) 10146 (set (match_dup 1) 10147 (xor:DI (match_dup 3) (const_int -1)))])] 10148 "") 10149 10150(define_expand "one_cmplsi2" 10151 [(set (match_operand:SI 0 "nonimmediate_operand" "") 10152 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))] 10153 "" 10154 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;") 10155 10156(define_insn "*one_cmplsi2_1" 10157 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 10158 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))] 10159 "ix86_unary_operator_ok (NOT, SImode, operands)" 10160 "not{l}\t%0" 10161 [(set_attr "type" "negnot") 10162 (set_attr "mode" "SI")]) 10163 10164;; ??? Currently never generated - xor is used instead. 10165(define_insn "*one_cmplsi2_1_zext" 10166 [(set (match_operand:DI 0 "register_operand" "=r") 10167 (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))] 10168 "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)" 10169 "not{l}\t%k0" 10170 [(set_attr "type" "negnot") 10171 (set_attr "mode" "SI")]) 10172 10173(define_insn "*one_cmplsi2_2" 10174 [(set (reg FLAGS_REG) 10175 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")) 10176 (const_int 0))) 10177 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 10178 (not:SI (match_dup 1)))] 10179 "ix86_match_ccmode (insn, CCNOmode) 10180 && ix86_unary_operator_ok (NOT, SImode, operands)" 10181 "#" 10182 [(set_attr "type" "alu1") 10183 (set_attr "mode" "SI")]) 10184 10185(define_split 10186 [(set (match_operand 0 "flags_reg_operand" "") 10187 (match_operator 2 "compare_operator" 10188 [(not:SI (match_operand:SI 3 "nonimmediate_operand" "")) 10189 (const_int 0)])) 10190 (set (match_operand:SI 1 "nonimmediate_operand" "") 10191 (not:SI (match_dup 3)))] 10192 "ix86_match_ccmode (insn, CCNOmode)" 10193 [(parallel [(set (match_dup 0) 10194 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1)) 10195 (const_int 0)])) 10196 (set (match_dup 1) 10197 (xor:SI (match_dup 3) (const_int -1)))])] 10198 "") 10199 10200;; ??? Currently never generated - xor is used instead. 10201(define_insn "*one_cmplsi2_2_zext" 10202 [(set (reg FLAGS_REG) 10203 (compare (not:SI (match_operand:SI 1 "register_operand" "0")) 10204 (const_int 0))) 10205 (set (match_operand:DI 0 "register_operand" "=r") 10206 (zero_extend:DI (not:SI (match_dup 1))))] 10207 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode) 10208 && ix86_unary_operator_ok (NOT, SImode, operands)" 10209 "#" 10210 [(set_attr "type" "alu1") 10211 (set_attr "mode" "SI")]) 10212 10213(define_split 10214 [(set (match_operand 0 "flags_reg_operand" "") 10215 (match_operator 2 "compare_operator" 10216 [(not:SI (match_operand:SI 3 "register_operand" "")) 10217 (const_int 0)])) 10218 (set (match_operand:DI 1 "register_operand" "") 10219 (zero_extend:DI (not:SI (match_dup 3))))] 10220 "ix86_match_ccmode (insn, CCNOmode)" 10221 [(parallel [(set (match_dup 0) 10222 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1)) 10223 (const_int 0)])) 10224 (set (match_dup 1) 10225 (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])] 10226 "") 10227 10228(define_expand "one_cmplhi2" 10229 [(set (match_operand:HI 0 "nonimmediate_operand" "") 10230 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))] 10231 "TARGET_HIMODE_MATH" 10232 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;") 10233 10234(define_insn "*one_cmplhi2_1" 10235 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 10236 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))] 10237 "ix86_unary_operator_ok (NOT, HImode, operands)" 10238 "not{w}\t%0" 10239 [(set_attr "type" "negnot") 10240 (set_attr "mode" "HI")]) 10241 10242(define_insn "*one_cmplhi2_2" 10243 [(set (reg FLAGS_REG) 10244 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")) 10245 (const_int 0))) 10246 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 10247 (not:HI (match_dup 1)))] 10248 "ix86_match_ccmode (insn, CCNOmode) 10249 && ix86_unary_operator_ok (NEG, HImode, operands)" 10250 "#" 10251 [(set_attr "type" "alu1") 10252 (set_attr "mode" "HI")]) 10253 10254(define_split 10255 [(set (match_operand 0 "flags_reg_operand" "") 10256 (match_operator 2 "compare_operator" 10257 [(not:HI (match_operand:HI 3 "nonimmediate_operand" "")) 10258 (const_int 0)])) 10259 (set (match_operand:HI 1 "nonimmediate_operand" "") 10260 (not:HI (match_dup 3)))] 10261 "ix86_match_ccmode (insn, CCNOmode)" 10262 [(parallel [(set (match_dup 0) 10263 (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1)) 10264 (const_int 0)])) 10265 (set (match_dup 1) 10266 (xor:HI (match_dup 3) (const_int -1)))])] 10267 "") 10268 10269;; %%% Potential partial reg stall on alternative 1. What to do? 10270(define_expand "one_cmplqi2" 10271 [(set (match_operand:QI 0 "nonimmediate_operand" "") 10272 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))] 10273 "TARGET_QIMODE_MATH" 10274 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;") 10275 10276(define_insn "*one_cmplqi2_1" 10277 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r") 10278 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))] 10279 "ix86_unary_operator_ok (NOT, QImode, operands)" 10280 "@ 10281 not{b}\t%0 10282 not{l}\t%k0" 10283 [(set_attr "type" "negnot") 10284 (set_attr "mode" "QI,SI")]) 10285 10286(define_insn "*one_cmplqi2_2" 10287 [(set (reg FLAGS_REG) 10288 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0")) 10289 (const_int 0))) 10290 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 10291 (not:QI (match_dup 1)))] 10292 "ix86_match_ccmode (insn, CCNOmode) 10293 && ix86_unary_operator_ok (NOT, QImode, operands)" 10294 "#" 10295 [(set_attr "type" "alu1") 10296 (set_attr "mode" "QI")]) 10297 10298(define_split 10299 [(set (match_operand 0 "flags_reg_operand" "") 10300 (match_operator 2 "compare_operator" 10301 [(not:QI (match_operand:QI 3 "nonimmediate_operand" "")) 10302 (const_int 0)])) 10303 (set (match_operand:QI 1 "nonimmediate_operand" "") 10304 (not:QI (match_dup 3)))] 10305 "ix86_match_ccmode (insn, CCNOmode)" 10306 [(parallel [(set (match_dup 0) 10307 (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1)) 10308 (const_int 0)])) 10309 (set (match_dup 1) 10310 (xor:QI (match_dup 3) (const_int -1)))])] 10311 "") 10312 10313;; Arithmetic shift instructions 10314 10315;; DImode shifts are implemented using the i386 "shift double" opcode, 10316;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count 10317;; is variable, then the count is in %cl and the "imm" operand is dropped 10318;; from the assembler input. 10319;; 10320;; This instruction shifts the target reg/mem as usual, but instead of 10321;; shifting in zeros, bits are shifted in from reg operand. If the insn 10322;; is a left shift double, bits are taken from the high order bits of 10323;; reg, else if the insn is a shift right double, bits are taken from the 10324;; low order bits of reg. So if %eax is "1234" and %edx is "5678", 10325;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345". 10326;; 10327;; Since sh[lr]d does not change the `reg' operand, that is done 10328;; separately, making all shifts emit pairs of shift double and normal 10329;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to 10330;; support a 63 bit shift, each shift where the count is in a reg expands 10331;; to a pair of shifts, a branch, a shift by 32 and a label. 10332;; 10333;; If the shift count is a constant, we need never emit more than one 10334;; shift pair, instead using moves and sign extension for counts greater 10335;; than 31. 10336 10337(define_expand "ashlti3" 10338 [(parallel [(set (match_operand:TI 0 "register_operand" "") 10339 (ashift:TI (match_operand:TI 1 "register_operand" "") 10340 (match_operand:QI 2 "nonmemory_operand" ""))) 10341 (clobber (reg:CC FLAGS_REG))])] 10342 "TARGET_64BIT" 10343{ 10344 if (! immediate_operand (operands[2], QImode)) 10345 { 10346 emit_insn (gen_ashlti3_1 (operands[0], operands[1], operands[2])); 10347 DONE; 10348 } 10349 ix86_expand_binary_operator (ASHIFT, TImode, operands); 10350 DONE; 10351}) 10352 10353(define_insn "ashlti3_1" 10354 [(set (match_operand:TI 0 "register_operand" "=r") 10355 (ashift:TI (match_operand:TI 1 "register_operand" "0") 10356 (match_operand:QI 2 "register_operand" "c"))) 10357 (clobber (match_scratch:DI 3 "=&r")) 10358 (clobber (reg:CC FLAGS_REG))] 10359 "TARGET_64BIT" 10360 "#" 10361 [(set_attr "type" "multi")]) 10362 10363(define_insn "*ashlti3_2" 10364 [(set (match_operand:TI 0 "register_operand" "=r") 10365 (ashift:TI (match_operand:TI 1 "register_operand" "0") 10366 (match_operand:QI 2 "immediate_operand" "O"))) 10367 (clobber (reg:CC FLAGS_REG))] 10368 "TARGET_64BIT" 10369 "#" 10370 [(set_attr "type" "multi")]) 10371 10372(define_split 10373 [(set (match_operand:TI 0 "register_operand" "") 10374 (ashift:TI (match_operand:TI 1 "nonmemory_operand" "") 10375 (match_operand:QI 2 "register_operand" ""))) 10376 (clobber (match_scratch:DI 3 "")) 10377 (clobber (reg:CC FLAGS_REG))] 10378 "TARGET_64BIT && reload_completed" 10379 [(const_int 0)] 10380 "ix86_split_ashl (operands, operands[3], TImode); DONE;") 10381 10382(define_split 10383 [(set (match_operand:TI 0 "register_operand" "") 10384 (ashift:TI (match_operand:TI 1 "register_operand" "") 10385 (match_operand:QI 2 "immediate_operand" ""))) 10386 (clobber (reg:CC FLAGS_REG))] 10387 "TARGET_64BIT && reload_completed" 10388 [(const_int 0)] 10389 "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;") 10390 10391(define_insn "x86_64_shld" 10392 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m") 10393 (ior:DI (ashift:DI (match_dup 0) 10394 (match_operand:QI 2 "nonmemory_operand" "J,c")) 10395 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r") 10396 (minus:QI (const_int 64) (match_dup 2))))) 10397 (clobber (reg:CC FLAGS_REG))] 10398 "TARGET_64BIT" 10399 "@ 10400 shld{q}\t{%2, %1, %0|%0, %1, %2} 10401 shld{q}\t{%s2%1, %0|%0, %1, %2}" 10402 [(set_attr "type" "ishift") 10403 (set_attr "prefix_0f" "1") 10404 (set_attr "mode" "DI") 10405 (set_attr "athlon_decode" "vector") 10406 (set_attr "amdfam10_decode" "vector")]) 10407 10408(define_expand "x86_64_shift_adj" 10409 [(set (reg:CCZ FLAGS_REG) 10410 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "") 10411 (const_int 64)) 10412 (const_int 0))) 10413 (set (match_operand:DI 0 "register_operand" "") 10414 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0)) 10415 (match_operand:DI 1 "register_operand" "") 10416 (match_dup 0))) 10417 (set (match_dup 1) 10418 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0)) 10419 (match_operand:DI 3 "register_operand" "r") 10420 (match_dup 1)))] 10421 "TARGET_64BIT" 10422 "") 10423 10424(define_expand "ashldi3" 10425 [(set (match_operand:DI 0 "shiftdi_operand" "") 10426 (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "") 10427 (match_operand:QI 2 "nonmemory_operand" "")))] 10428 "" 10429 "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;") 10430 10431(define_insn "*ashldi3_1_rex64" 10432 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r") 10433 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l") 10434 (match_operand:QI 2 "nonmemory_operand" "cJ,M"))) 10435 (clobber (reg:CC FLAGS_REG))] 10436 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)" 10437{ 10438 switch (get_attr_type (insn)) 10439 { 10440 case TYPE_ALU: 10441 gcc_assert (operands[2] == const1_rtx); 10442 gcc_assert (rtx_equal_p (operands[0], operands[1])); 10443 return "add{q}\t{%0, %0|%0, %0}"; 10444 10445 case TYPE_LEA: 10446 gcc_assert (GET_CODE (operands[2]) == CONST_INT); 10447 gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3); 10448 operands[1] = gen_rtx_MULT (DImode, operands[1], 10449 GEN_INT (1 << INTVAL (operands[2]))); 10450 return "lea{q}\t{%a1, %0|%0, %a1}"; 10451 10452 default: 10453 if (REG_P (operands[2])) 10454 return "sal{q}\t{%b2, %0|%0, %b2}"; 10455 else if (operands[2] == const1_rtx 10456 && (TARGET_SHIFT1 || optimize_size)) 10457 return "sal{q}\t%0"; 10458 else 10459 return "sal{q}\t{%2, %0|%0, %2}"; 10460 } 10461} 10462 [(set (attr "type") 10463 (cond [(eq_attr "alternative" "1") 10464 (const_string "lea") 10465 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10466 (const_int 0)) 10467 (match_operand 0 "register_operand" "")) 10468 (match_operand 2 "const1_operand" "")) 10469 (const_string "alu") 10470 ] 10471 (const_string "ishift"))) 10472 (set_attr "mode" "DI")]) 10473 10474;; Convert lea to the lea pattern to avoid flags dependency. 10475(define_split 10476 [(set (match_operand:DI 0 "register_operand" "") 10477 (ashift:DI (match_operand:DI 1 "index_register_operand" "") 10478 (match_operand:QI 2 "immediate_operand" ""))) 10479 (clobber (reg:CC FLAGS_REG))] 10480 "TARGET_64BIT && reload_completed 10481 && true_regnum (operands[0]) != true_regnum (operands[1])" 10482 [(set (match_dup 0) 10483 (mult:DI (match_dup 1) 10484 (match_dup 2)))] 10485 "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);") 10486 10487;; This pattern can't accept a variable shift count, since shifts by 10488;; zero don't affect the flags. We assume that shifts by constant 10489;; zero are optimized away. 10490(define_insn "*ashldi3_cmp_rex64" 10491 [(set (reg FLAGS_REG) 10492 (compare 10493 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0") 10494 (match_operand:QI 2 "immediate_operand" "e")) 10495 (const_int 0))) 10496 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 10497 (ashift:DI (match_dup 1) (match_dup 2)))] 10498 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 10499 && ix86_binary_operator_ok (ASHIFT, DImode, operands) 10500 && (optimize_size 10501 || !TARGET_PARTIAL_FLAG_REG_STALL 10502 || (operands[2] == const1_rtx 10503 && (TARGET_SHIFT1 10504 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))" 10505{ 10506 switch (get_attr_type (insn)) 10507 { 10508 case TYPE_ALU: 10509 gcc_assert (operands[2] == const1_rtx); 10510 return "add{q}\t{%0, %0|%0, %0}"; 10511 10512 default: 10513 if (REG_P (operands[2])) 10514 return "sal{q}\t{%b2, %0|%0, %b2}"; 10515 else if (operands[2] == const1_rtx 10516 && (TARGET_SHIFT1 || optimize_size)) 10517 return "sal{q}\t%0"; 10518 else 10519 return "sal{q}\t{%2, %0|%0, %2}"; 10520 } 10521} 10522 [(set (attr "type") 10523 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10524 (const_int 0)) 10525 (match_operand 0 "register_operand" "")) 10526 (match_operand 2 "const1_operand" "")) 10527 (const_string "alu") 10528 ] 10529 (const_string "ishift"))) 10530 (set_attr "mode" "DI")]) 10531 10532(define_insn "*ashldi3_cconly_rex64" 10533 [(set (reg FLAGS_REG) 10534 (compare 10535 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0") 10536 (match_operand:QI 2 "immediate_operand" "e")) 10537 (const_int 0))) 10538 (clobber (match_scratch:DI 0 "=r"))] 10539 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 10540 && ix86_binary_operator_ok (ASHIFT, DImode, operands) 10541 && (optimize_size 10542 || !TARGET_PARTIAL_FLAG_REG_STALL 10543 || (operands[2] == const1_rtx 10544 && (TARGET_SHIFT1 10545 || TARGET_DOUBLE_WITH_ADD)))" 10546{ 10547 switch (get_attr_type (insn)) 10548 { 10549 case TYPE_ALU: 10550 gcc_assert (operands[2] == const1_rtx); 10551 return "add{q}\t{%0, %0|%0, %0}"; 10552 10553 default: 10554 if (REG_P (operands[2])) 10555 return "sal{q}\t{%b2, %0|%0, %b2}"; 10556 else if (operands[2] == const1_rtx 10557 && (TARGET_SHIFT1 || optimize_size)) 10558 return "sal{q}\t%0"; 10559 else 10560 return "sal{q}\t{%2, %0|%0, %2}"; 10561 } 10562} 10563 [(set (attr "type") 10564 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10565 (const_int 0)) 10566 (match_operand 0 "register_operand" "")) 10567 (match_operand 2 "const1_operand" "")) 10568 (const_string "alu") 10569 ] 10570 (const_string "ishift"))) 10571 (set_attr "mode" "DI")]) 10572 10573(define_insn "*ashldi3_1" 10574 [(set (match_operand:DI 0 "register_operand" "=&r,r") 10575 (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0") 10576 (match_operand:QI 2 "nonmemory_operand" "Jc,Jc"))) 10577 (clobber (reg:CC FLAGS_REG))] 10578 "!TARGET_64BIT" 10579 "#" 10580 [(set_attr "type" "multi")]) 10581 10582;; By default we don't ask for a scratch register, because when DImode 10583;; values are manipulated, registers are already at a premium. But if 10584;; we have one handy, we won't turn it away. 10585(define_peephole2 10586 [(match_scratch:SI 3 "r") 10587 (parallel [(set (match_operand:DI 0 "register_operand" "") 10588 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "") 10589 (match_operand:QI 2 "nonmemory_operand" ""))) 10590 (clobber (reg:CC FLAGS_REG))]) 10591 (match_dup 3)] 10592 "!TARGET_64BIT && TARGET_CMOVE" 10593 [(const_int 0)] 10594 "ix86_split_ashl (operands, operands[3], DImode); DONE;") 10595 10596(define_split 10597 [(set (match_operand:DI 0 "register_operand" "") 10598 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "") 10599 (match_operand:QI 2 "nonmemory_operand" ""))) 10600 (clobber (reg:CC FLAGS_REG))] 10601 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2) 10602 ? flow2_completed : reload_completed)" 10603 [(const_int 0)] 10604 "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;") 10605 10606(define_insn "x86_shld_1" 10607 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m") 10608 (ior:SI (ashift:SI (match_dup 0) 10609 (match_operand:QI 2 "nonmemory_operand" "I,c")) 10610 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r") 10611 (minus:QI (const_int 32) (match_dup 2))))) 10612 (clobber (reg:CC FLAGS_REG))] 10613 "" 10614 "@ 10615 shld{l}\t{%2, %1, %0|%0, %1, %2} 10616 shld{l}\t{%s2%1, %0|%0, %1, %2}" 10617 [(set_attr "type" "ishift") 10618 (set_attr "prefix_0f" "1") 10619 (set_attr "mode" "SI") 10620 (set_attr "pent_pair" "np") 10621 (set_attr "athlon_decode" "vector") 10622 (set_attr "amdfam10_decode" "vector")]) 10623 10624(define_expand "x86_shift_adj_1" 10625 [(set (reg:CCZ FLAGS_REG) 10626 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "") 10627 (const_int 32)) 10628 (const_int 0))) 10629 (set (match_operand:SI 0 "register_operand" "") 10630 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0)) 10631 (match_operand:SI 1 "register_operand" "") 10632 (match_dup 0))) 10633 (set (match_dup 1) 10634 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0)) 10635 (match_operand:SI 3 "register_operand" "r") 10636 (match_dup 1)))] 10637 "TARGET_CMOVE" 10638 "") 10639 10640(define_expand "x86_shift_adj_2" 10641 [(use (match_operand:SI 0 "register_operand" "")) 10642 (use (match_operand:SI 1 "register_operand" "")) 10643 (use (match_operand:QI 2 "register_operand" ""))] 10644 "" 10645{ 10646 rtx label = gen_label_rtx (); 10647 rtx tmp; 10648 10649 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32))); 10650 10651 tmp = gen_rtx_REG (CCZmode, FLAGS_REG); 10652 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx); 10653 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp, 10654 gen_rtx_LABEL_REF (VOIDmode, label), 10655 pc_rtx); 10656 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp)); 10657 JUMP_LABEL (tmp) = label; 10658 10659 emit_move_insn (operands[0], operands[1]); 10660 ix86_expand_clear (operands[1]); 10661 10662 emit_label (label); 10663 LABEL_NUSES (label) = 1; 10664 10665 DONE; 10666}) 10667 10668(define_expand "ashlsi3" 10669 [(set (match_operand:SI 0 "nonimmediate_operand" "") 10670 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "") 10671 (match_operand:QI 2 "nonmemory_operand" ""))) 10672 (clobber (reg:CC FLAGS_REG))] 10673 "" 10674 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;") 10675 10676(define_insn "*ashlsi3_1" 10677 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r") 10678 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l") 10679 (match_operand:QI 2 "nonmemory_operand" "cI,M"))) 10680 (clobber (reg:CC FLAGS_REG))] 10681 "ix86_binary_operator_ok (ASHIFT, SImode, operands)" 10682{ 10683 switch (get_attr_type (insn)) 10684 { 10685 case TYPE_ALU: 10686 gcc_assert (operands[2] == const1_rtx); 10687 gcc_assert (rtx_equal_p (operands[0], operands[1])); 10688 return "add{l}\t{%0, %0|%0, %0}"; 10689 10690 case TYPE_LEA: 10691 return "#"; 10692 10693 default: 10694 if (REG_P (operands[2])) 10695 return "sal{l}\t{%b2, %0|%0, %b2}"; 10696 else if (operands[2] == const1_rtx 10697 && (TARGET_SHIFT1 || optimize_size)) 10698 return "sal{l}\t%0"; 10699 else 10700 return "sal{l}\t{%2, %0|%0, %2}"; 10701 } 10702} 10703 [(set (attr "type") 10704 (cond [(eq_attr "alternative" "1") 10705 (const_string "lea") 10706 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10707 (const_int 0)) 10708 (match_operand 0 "register_operand" "")) 10709 (match_operand 2 "const1_operand" "")) 10710 (const_string "alu") 10711 ] 10712 (const_string "ishift"))) 10713 (set_attr "mode" "SI")]) 10714 10715;; Convert lea to the lea pattern to avoid flags dependency. 10716(define_split 10717 [(set (match_operand 0 "register_operand" "") 10718 (ashift (match_operand 1 "index_register_operand" "") 10719 (match_operand:QI 2 "const_int_operand" ""))) 10720 (clobber (reg:CC FLAGS_REG))] 10721 "reload_completed 10722 && true_regnum (operands[0]) != true_regnum (operands[1]) 10723 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4" 10724 [(const_int 0)] 10725{ 10726 rtx pat; 10727 enum machine_mode mode = GET_MODE (operands[0]); 10728 10729 if (GET_MODE_SIZE (mode) < 4) 10730 operands[0] = gen_lowpart (SImode, operands[0]); 10731 if (mode != Pmode) 10732 operands[1] = gen_lowpart (Pmode, operands[1]); 10733 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode); 10734 10735 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]); 10736 if (Pmode != SImode) 10737 pat = gen_rtx_SUBREG (SImode, pat, 0); 10738 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat)); 10739 DONE; 10740}) 10741 10742;; Rare case of shifting RSP is handled by generating move and shift 10743(define_split 10744 [(set (match_operand 0 "register_operand" "") 10745 (ashift (match_operand 1 "register_operand" "") 10746 (match_operand:QI 2 "const_int_operand" ""))) 10747 (clobber (reg:CC FLAGS_REG))] 10748 "reload_completed 10749 && true_regnum (operands[0]) != true_regnum (operands[1])" 10750 [(const_int 0)] 10751{ 10752 rtx pat, clob; 10753 emit_move_insn (operands[0], operands[1]); 10754 pat = gen_rtx_SET (VOIDmode, operands[0], 10755 gen_rtx_ASHIFT (GET_MODE (operands[0]), 10756 operands[0], operands[2])); 10757 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG)); 10758 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob))); 10759 DONE; 10760}) 10761 10762(define_insn "*ashlsi3_1_zext" 10763 [(set (match_operand:DI 0 "register_operand" "=r,r") 10764 (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l") 10765 (match_operand:QI 2 "nonmemory_operand" "cI,M")))) 10766 (clobber (reg:CC FLAGS_REG))] 10767 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)" 10768{ 10769 switch (get_attr_type (insn)) 10770 { 10771 case TYPE_ALU: 10772 gcc_assert (operands[2] == const1_rtx); 10773 return "add{l}\t{%k0, %k0|%k0, %k0}"; 10774 10775 case TYPE_LEA: 10776 return "#"; 10777 10778 default: 10779 if (REG_P (operands[2])) 10780 return "sal{l}\t{%b2, %k0|%k0, %b2}"; 10781 else if (operands[2] == const1_rtx 10782 && (TARGET_SHIFT1 || optimize_size)) 10783 return "sal{l}\t%k0"; 10784 else 10785 return "sal{l}\t{%2, %k0|%k0, %2}"; 10786 } 10787} 10788 [(set (attr "type") 10789 (cond [(eq_attr "alternative" "1") 10790 (const_string "lea") 10791 (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10792 (const_int 0)) 10793 (match_operand 2 "const1_operand" "")) 10794 (const_string "alu") 10795 ] 10796 (const_string "ishift"))) 10797 (set_attr "mode" "SI")]) 10798 10799;; Convert lea to the lea pattern to avoid flags dependency. 10800(define_split 10801 [(set (match_operand:DI 0 "register_operand" "") 10802 (zero_extend:DI (ashift (match_operand 1 "register_operand" "") 10803 (match_operand:QI 2 "const_int_operand" "")))) 10804 (clobber (reg:CC FLAGS_REG))] 10805 "TARGET_64BIT && reload_completed 10806 && true_regnum (operands[0]) != true_regnum (operands[1])" 10807 [(set (match_dup 0) (zero_extend:DI 10808 (subreg:SI (mult:SI (match_dup 1) 10809 (match_dup 2)) 0)))] 10810{ 10811 operands[1] = gen_lowpart (Pmode, operands[1]); 10812 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode); 10813}) 10814 10815;; This pattern can't accept a variable shift count, since shifts by 10816;; zero don't affect the flags. We assume that shifts by constant 10817;; zero are optimized away. 10818(define_insn "*ashlsi3_cmp" 10819 [(set (reg FLAGS_REG) 10820 (compare 10821 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0") 10822 (match_operand:QI 2 "const_1_to_31_operand" "I")) 10823 (const_int 0))) 10824 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 10825 (ashift:SI (match_dup 1) (match_dup 2)))] 10826 "ix86_match_ccmode (insn, CCGOCmode) 10827 && ix86_binary_operator_ok (ASHIFT, SImode, operands) 10828 && (optimize_size 10829 || !TARGET_PARTIAL_FLAG_REG_STALL 10830 || (operands[2] == const1_rtx 10831 && (TARGET_SHIFT1 10832 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))" 10833{ 10834 switch (get_attr_type (insn)) 10835 { 10836 case TYPE_ALU: 10837 gcc_assert (operands[2] == const1_rtx); 10838 return "add{l}\t{%0, %0|%0, %0}"; 10839 10840 default: 10841 if (REG_P (operands[2])) 10842 return "sal{l}\t{%b2, %0|%0, %b2}"; 10843 else if (operands[2] == const1_rtx 10844 && (TARGET_SHIFT1 || optimize_size)) 10845 return "sal{l}\t%0"; 10846 else 10847 return "sal{l}\t{%2, %0|%0, %2}"; 10848 } 10849} 10850 [(set (attr "type") 10851 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10852 (const_int 0)) 10853 (match_operand 0 "register_operand" "")) 10854 (match_operand 2 "const1_operand" "")) 10855 (const_string "alu") 10856 ] 10857 (const_string "ishift"))) 10858 (set_attr "mode" "SI")]) 10859 10860(define_insn "*ashlsi3_cconly" 10861 [(set (reg FLAGS_REG) 10862 (compare 10863 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0") 10864 (match_operand:QI 2 "const_1_to_31_operand" "I")) 10865 (const_int 0))) 10866 (clobber (match_scratch:SI 0 "=r"))] 10867 "ix86_match_ccmode (insn, CCGOCmode) 10868 && ix86_binary_operator_ok (ASHIFT, SImode, operands) 10869 && (optimize_size 10870 || !TARGET_PARTIAL_FLAG_REG_STALL 10871 || (operands[2] == const1_rtx 10872 && (TARGET_SHIFT1 10873 || TARGET_DOUBLE_WITH_ADD)))" 10874{ 10875 switch (get_attr_type (insn)) 10876 { 10877 case TYPE_ALU: 10878 gcc_assert (operands[2] == const1_rtx); 10879 return "add{l}\t{%0, %0|%0, %0}"; 10880 10881 default: 10882 if (REG_P (operands[2])) 10883 return "sal{l}\t{%b2, %0|%0, %b2}"; 10884 else if (operands[2] == const1_rtx 10885 && (TARGET_SHIFT1 || optimize_size)) 10886 return "sal{l}\t%0"; 10887 else 10888 return "sal{l}\t{%2, %0|%0, %2}"; 10889 } 10890} 10891 [(set (attr "type") 10892 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10893 (const_int 0)) 10894 (match_operand 0 "register_operand" "")) 10895 (match_operand 2 "const1_operand" "")) 10896 (const_string "alu") 10897 ] 10898 (const_string "ishift"))) 10899 (set_attr "mode" "SI")]) 10900 10901(define_insn "*ashlsi3_cmp_zext" 10902 [(set (reg FLAGS_REG) 10903 (compare 10904 (ashift:SI (match_operand:SI 1 "register_operand" "0") 10905 (match_operand:QI 2 "const_1_to_31_operand" "I")) 10906 (const_int 0))) 10907 (set (match_operand:DI 0 "register_operand" "=r") 10908 (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))] 10909 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 10910 && ix86_binary_operator_ok (ASHIFT, SImode, operands) 10911 && (optimize_size 10912 || !TARGET_PARTIAL_FLAG_REG_STALL 10913 || (operands[2] == const1_rtx 10914 && (TARGET_SHIFT1 10915 || TARGET_DOUBLE_WITH_ADD)))" 10916{ 10917 switch (get_attr_type (insn)) 10918 { 10919 case TYPE_ALU: 10920 gcc_assert (operands[2] == const1_rtx); 10921 return "add{l}\t{%k0, %k0|%k0, %k0}"; 10922 10923 default: 10924 if (REG_P (operands[2])) 10925 return "sal{l}\t{%b2, %k0|%k0, %b2}"; 10926 else if (operands[2] == const1_rtx 10927 && (TARGET_SHIFT1 || optimize_size)) 10928 return "sal{l}\t%k0"; 10929 else 10930 return "sal{l}\t{%2, %k0|%k0, %2}"; 10931 } 10932} 10933 [(set (attr "type") 10934 (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10935 (const_int 0)) 10936 (match_operand 2 "const1_operand" "")) 10937 (const_string "alu") 10938 ] 10939 (const_string "ishift"))) 10940 (set_attr "mode" "SI")]) 10941 10942(define_expand "ashlhi3" 10943 [(set (match_operand:HI 0 "nonimmediate_operand" "") 10944 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "") 10945 (match_operand:QI 2 "nonmemory_operand" ""))) 10946 (clobber (reg:CC FLAGS_REG))] 10947 "TARGET_HIMODE_MATH" 10948 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;") 10949 10950(define_insn "*ashlhi3_1_lea" 10951 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r") 10952 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l") 10953 (match_operand:QI 2 "nonmemory_operand" "cI,M"))) 10954 (clobber (reg:CC FLAGS_REG))] 10955 "!TARGET_PARTIAL_REG_STALL 10956 && ix86_binary_operator_ok (ASHIFT, HImode, operands)" 10957{ 10958 switch (get_attr_type (insn)) 10959 { 10960 case TYPE_LEA: 10961 return "#"; 10962 case TYPE_ALU: 10963 gcc_assert (operands[2] == const1_rtx); 10964 return "add{w}\t{%0, %0|%0, %0}"; 10965 10966 default: 10967 if (REG_P (operands[2])) 10968 return "sal{w}\t{%b2, %0|%0, %b2}"; 10969 else if (operands[2] == const1_rtx 10970 && (TARGET_SHIFT1 || optimize_size)) 10971 return "sal{w}\t%0"; 10972 else 10973 return "sal{w}\t{%2, %0|%0, %2}"; 10974 } 10975} 10976 [(set (attr "type") 10977 (cond [(eq_attr "alternative" "1") 10978 (const_string "lea") 10979 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 10980 (const_int 0)) 10981 (match_operand 0 "register_operand" "")) 10982 (match_operand 2 "const1_operand" "")) 10983 (const_string "alu") 10984 ] 10985 (const_string "ishift"))) 10986 (set_attr "mode" "HI,SI")]) 10987 10988(define_insn "*ashlhi3_1" 10989 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 10990 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0") 10991 (match_operand:QI 2 "nonmemory_operand" "cI"))) 10992 (clobber (reg:CC FLAGS_REG))] 10993 "TARGET_PARTIAL_REG_STALL 10994 && ix86_binary_operator_ok (ASHIFT, HImode, operands)" 10995{ 10996 switch (get_attr_type (insn)) 10997 { 10998 case TYPE_ALU: 10999 gcc_assert (operands[2] == const1_rtx); 11000 return "add{w}\t{%0, %0|%0, %0}"; 11001 11002 default: 11003 if (REG_P (operands[2])) 11004 return "sal{w}\t{%b2, %0|%0, %b2}"; 11005 else if (operands[2] == const1_rtx 11006 && (TARGET_SHIFT1 || optimize_size)) 11007 return "sal{w}\t%0"; 11008 else 11009 return "sal{w}\t{%2, %0|%0, %2}"; 11010 } 11011} 11012 [(set (attr "type") 11013 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11014 (const_int 0)) 11015 (match_operand 0 "register_operand" "")) 11016 (match_operand 2 "const1_operand" "")) 11017 (const_string "alu") 11018 ] 11019 (const_string "ishift"))) 11020 (set_attr "mode" "HI")]) 11021 11022;; This pattern can't accept a variable shift count, since shifts by 11023;; zero don't affect the flags. We assume that shifts by constant 11024;; zero are optimized away. 11025(define_insn "*ashlhi3_cmp" 11026 [(set (reg FLAGS_REG) 11027 (compare 11028 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11029 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11030 (const_int 0))) 11031 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 11032 (ashift:HI (match_dup 1) (match_dup 2)))] 11033 "ix86_match_ccmode (insn, CCGOCmode) 11034 && ix86_binary_operator_ok (ASHIFT, HImode, operands) 11035 && (optimize_size 11036 || !TARGET_PARTIAL_FLAG_REG_STALL 11037 || (operands[2] == const1_rtx 11038 && (TARGET_SHIFT1 11039 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))" 11040{ 11041 switch (get_attr_type (insn)) 11042 { 11043 case TYPE_ALU: 11044 gcc_assert (operands[2] == const1_rtx); 11045 return "add{w}\t{%0, %0|%0, %0}"; 11046 11047 default: 11048 if (REG_P (operands[2])) 11049 return "sal{w}\t{%b2, %0|%0, %b2}"; 11050 else if (operands[2] == const1_rtx 11051 && (TARGET_SHIFT1 || optimize_size)) 11052 return "sal{w}\t%0"; 11053 else 11054 return "sal{w}\t{%2, %0|%0, %2}"; 11055 } 11056} 11057 [(set (attr "type") 11058 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11059 (const_int 0)) 11060 (match_operand 0 "register_operand" "")) 11061 (match_operand 2 "const1_operand" "")) 11062 (const_string "alu") 11063 ] 11064 (const_string "ishift"))) 11065 (set_attr "mode" "HI")]) 11066 11067(define_insn "*ashlhi3_cconly" 11068 [(set (reg FLAGS_REG) 11069 (compare 11070 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11071 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11072 (const_int 0))) 11073 (clobber (match_scratch:HI 0 "=r"))] 11074 "ix86_match_ccmode (insn, CCGOCmode) 11075 && ix86_binary_operator_ok (ASHIFT, HImode, operands) 11076 && (optimize_size 11077 || !TARGET_PARTIAL_FLAG_REG_STALL 11078 || (operands[2] == const1_rtx 11079 && (TARGET_SHIFT1 11080 || TARGET_DOUBLE_WITH_ADD)))" 11081{ 11082 switch (get_attr_type (insn)) 11083 { 11084 case TYPE_ALU: 11085 gcc_assert (operands[2] == const1_rtx); 11086 return "add{w}\t{%0, %0|%0, %0}"; 11087 11088 default: 11089 if (REG_P (operands[2])) 11090 return "sal{w}\t{%b2, %0|%0, %b2}"; 11091 else if (operands[2] == const1_rtx 11092 && (TARGET_SHIFT1 || optimize_size)) 11093 return "sal{w}\t%0"; 11094 else 11095 return "sal{w}\t{%2, %0|%0, %2}"; 11096 } 11097} 11098 [(set (attr "type") 11099 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11100 (const_int 0)) 11101 (match_operand 0 "register_operand" "")) 11102 (match_operand 2 "const1_operand" "")) 11103 (const_string "alu") 11104 ] 11105 (const_string "ishift"))) 11106 (set_attr "mode" "HI")]) 11107 11108(define_expand "ashlqi3" 11109 [(set (match_operand:QI 0 "nonimmediate_operand" "") 11110 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "") 11111 (match_operand:QI 2 "nonmemory_operand" ""))) 11112 (clobber (reg:CC FLAGS_REG))] 11113 "TARGET_QIMODE_MATH" 11114 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;") 11115 11116;; %%% Potential partial reg stall on alternative 2. What to do? 11117 11118(define_insn "*ashlqi3_1_lea" 11119 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r") 11120 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l") 11121 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M"))) 11122 (clobber (reg:CC FLAGS_REG))] 11123 "!TARGET_PARTIAL_REG_STALL 11124 && ix86_binary_operator_ok (ASHIFT, QImode, operands)" 11125{ 11126 switch (get_attr_type (insn)) 11127 { 11128 case TYPE_LEA: 11129 return "#"; 11130 case TYPE_ALU: 11131 gcc_assert (operands[2] == const1_rtx); 11132 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1])) 11133 return "add{l}\t{%k0, %k0|%k0, %k0}"; 11134 else 11135 return "add{b}\t{%0, %0|%0, %0}"; 11136 11137 default: 11138 if (REG_P (operands[2])) 11139 { 11140 if (get_attr_mode (insn) == MODE_SI) 11141 return "sal{l}\t{%b2, %k0|%k0, %b2}"; 11142 else 11143 return "sal{b}\t{%b2, %0|%0, %b2}"; 11144 } 11145 else if (operands[2] == const1_rtx 11146 && (TARGET_SHIFT1 || optimize_size)) 11147 { 11148 if (get_attr_mode (insn) == MODE_SI) 11149 return "sal{l}\t%0"; 11150 else 11151 return "sal{b}\t%0"; 11152 } 11153 else 11154 { 11155 if (get_attr_mode (insn) == MODE_SI) 11156 return "sal{l}\t{%2, %k0|%k0, %2}"; 11157 else 11158 return "sal{b}\t{%2, %0|%0, %2}"; 11159 } 11160 } 11161} 11162 [(set (attr "type") 11163 (cond [(eq_attr "alternative" "2") 11164 (const_string "lea") 11165 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11166 (const_int 0)) 11167 (match_operand 0 "register_operand" "")) 11168 (match_operand 2 "const1_operand" "")) 11169 (const_string "alu") 11170 ] 11171 (const_string "ishift"))) 11172 (set_attr "mode" "QI,SI,SI")]) 11173 11174(define_insn "*ashlqi3_1" 11175 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r") 11176 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 11177 (match_operand:QI 2 "nonmemory_operand" "cI,cI"))) 11178 (clobber (reg:CC FLAGS_REG))] 11179 "TARGET_PARTIAL_REG_STALL 11180 && ix86_binary_operator_ok (ASHIFT, QImode, operands)" 11181{ 11182 switch (get_attr_type (insn)) 11183 { 11184 case TYPE_ALU: 11185 gcc_assert (operands[2] == const1_rtx); 11186 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1])) 11187 return "add{l}\t{%k0, %k0|%k0, %k0}"; 11188 else 11189 return "add{b}\t{%0, %0|%0, %0}"; 11190 11191 default: 11192 if (REG_P (operands[2])) 11193 { 11194 if (get_attr_mode (insn) == MODE_SI) 11195 return "sal{l}\t{%b2, %k0|%k0, %b2}"; 11196 else 11197 return "sal{b}\t{%b2, %0|%0, %b2}"; 11198 } 11199 else if (operands[2] == const1_rtx 11200 && (TARGET_SHIFT1 || optimize_size)) 11201 { 11202 if (get_attr_mode (insn) == MODE_SI) 11203 return "sal{l}\t%0"; 11204 else 11205 return "sal{b}\t%0"; 11206 } 11207 else 11208 { 11209 if (get_attr_mode (insn) == MODE_SI) 11210 return "sal{l}\t{%2, %k0|%k0, %2}"; 11211 else 11212 return "sal{b}\t{%2, %0|%0, %2}"; 11213 } 11214 } 11215} 11216 [(set (attr "type") 11217 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11218 (const_int 0)) 11219 (match_operand 0 "register_operand" "")) 11220 (match_operand 2 "const1_operand" "")) 11221 (const_string "alu") 11222 ] 11223 (const_string "ishift"))) 11224 (set_attr "mode" "QI,SI")]) 11225 11226;; This pattern can't accept a variable shift count, since shifts by 11227;; zero don't affect the flags. We assume that shifts by constant 11228;; zero are optimized away. 11229(define_insn "*ashlqi3_cmp" 11230 [(set (reg FLAGS_REG) 11231 (compare 11232 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11233 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11234 (const_int 0))) 11235 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 11236 (ashift:QI (match_dup 1) (match_dup 2)))] 11237 "ix86_match_ccmode (insn, CCGOCmode) 11238 && ix86_binary_operator_ok (ASHIFT, QImode, operands) 11239 && (optimize_size 11240 || !TARGET_PARTIAL_FLAG_REG_STALL 11241 || (operands[2] == const1_rtx 11242 && (TARGET_SHIFT1 11243 || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))" 11244{ 11245 switch (get_attr_type (insn)) 11246 { 11247 case TYPE_ALU: 11248 gcc_assert (operands[2] == const1_rtx); 11249 return "add{b}\t{%0, %0|%0, %0}"; 11250 11251 default: 11252 if (REG_P (operands[2])) 11253 return "sal{b}\t{%b2, %0|%0, %b2}"; 11254 else if (operands[2] == const1_rtx 11255 && (TARGET_SHIFT1 || optimize_size)) 11256 return "sal{b}\t%0"; 11257 else 11258 return "sal{b}\t{%2, %0|%0, %2}"; 11259 } 11260} 11261 [(set (attr "type") 11262 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11263 (const_int 0)) 11264 (match_operand 0 "register_operand" "")) 11265 (match_operand 2 "const1_operand" "")) 11266 (const_string "alu") 11267 ] 11268 (const_string "ishift"))) 11269 (set_attr "mode" "QI")]) 11270 11271(define_insn "*ashlqi3_cconly" 11272 [(set (reg FLAGS_REG) 11273 (compare 11274 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11275 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11276 (const_int 0))) 11277 (clobber (match_scratch:QI 0 "=q"))] 11278 "ix86_match_ccmode (insn, CCGOCmode) 11279 && ix86_binary_operator_ok (ASHIFT, QImode, operands) 11280 && (optimize_size 11281 || !TARGET_PARTIAL_FLAG_REG_STALL 11282 || (operands[2] == const1_rtx 11283 && (TARGET_SHIFT1 11284 || TARGET_DOUBLE_WITH_ADD)))" 11285{ 11286 switch (get_attr_type (insn)) 11287 { 11288 case TYPE_ALU: 11289 gcc_assert (operands[2] == const1_rtx); 11290 return "add{b}\t{%0, %0|%0, %0}"; 11291 11292 default: 11293 if (REG_P (operands[2])) 11294 return "sal{b}\t{%b2, %0|%0, %b2}"; 11295 else if (operands[2] == const1_rtx 11296 && (TARGET_SHIFT1 || optimize_size)) 11297 return "sal{b}\t%0"; 11298 else 11299 return "sal{b}\t{%2, %0|%0, %2}"; 11300 } 11301} 11302 [(set (attr "type") 11303 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD") 11304 (const_int 0)) 11305 (match_operand 0 "register_operand" "")) 11306 (match_operand 2 "const1_operand" "")) 11307 (const_string "alu") 11308 ] 11309 (const_string "ishift"))) 11310 (set_attr "mode" "QI")]) 11311 11312;; See comment above `ashldi3' about how this works. 11313 11314(define_expand "ashrti3" 11315 [(parallel [(set (match_operand:TI 0 "register_operand" "") 11316 (ashiftrt:TI (match_operand:TI 1 "register_operand" "") 11317 (match_operand:QI 2 "nonmemory_operand" ""))) 11318 (clobber (reg:CC FLAGS_REG))])] 11319 "TARGET_64BIT" 11320{ 11321 if (! immediate_operand (operands[2], QImode)) 11322 { 11323 emit_insn (gen_ashrti3_1 (operands[0], operands[1], operands[2])); 11324 DONE; 11325 } 11326 ix86_expand_binary_operator (ASHIFTRT, TImode, operands); 11327 DONE; 11328}) 11329 11330(define_insn "ashrti3_1" 11331 [(set (match_operand:TI 0 "register_operand" "=r") 11332 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0") 11333 (match_operand:QI 2 "register_operand" "c"))) 11334 (clobber (match_scratch:DI 3 "=&r")) 11335 (clobber (reg:CC FLAGS_REG))] 11336 "TARGET_64BIT" 11337 "#" 11338 [(set_attr "type" "multi")]) 11339 11340(define_insn "*ashrti3_2" 11341 [(set (match_operand:TI 0 "register_operand" "=r") 11342 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0") 11343 (match_operand:QI 2 "immediate_operand" "O"))) 11344 (clobber (reg:CC FLAGS_REG))] 11345 "TARGET_64BIT" 11346 "#" 11347 [(set_attr "type" "multi")]) 11348 11349(define_split 11350 [(set (match_operand:TI 0 "register_operand" "") 11351 (ashiftrt:TI (match_operand:TI 1 "register_operand" "") 11352 (match_operand:QI 2 "register_operand" ""))) 11353 (clobber (match_scratch:DI 3 "")) 11354 (clobber (reg:CC FLAGS_REG))] 11355 "TARGET_64BIT && reload_completed" 11356 [(const_int 0)] 11357 "ix86_split_ashr (operands, operands[3], TImode); DONE;") 11358 11359(define_split 11360 [(set (match_operand:TI 0 "register_operand" "") 11361 (ashiftrt:TI (match_operand:TI 1 "register_operand" "") 11362 (match_operand:QI 2 "immediate_operand" ""))) 11363 (clobber (reg:CC FLAGS_REG))] 11364 "TARGET_64BIT && reload_completed" 11365 [(const_int 0)] 11366 "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;") 11367 11368(define_insn "x86_64_shrd" 11369 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m") 11370 (ior:DI (ashiftrt:DI (match_dup 0) 11371 (match_operand:QI 2 "nonmemory_operand" "J,c")) 11372 (ashift:DI (match_operand:DI 1 "register_operand" "r,r") 11373 (minus:QI (const_int 64) (match_dup 2))))) 11374 (clobber (reg:CC FLAGS_REG))] 11375 "TARGET_64BIT" 11376 "@ 11377 shrd{q}\t{%2, %1, %0|%0, %1, %2} 11378 shrd{q}\t{%s2%1, %0|%0, %1, %2}" 11379 [(set_attr "type" "ishift") 11380 (set_attr "prefix_0f" "1") 11381 (set_attr "mode" "DI") 11382 (set_attr "athlon_decode" "vector") 11383 (set_attr "amdfam10_decode" "vector")]) 11384 11385(define_expand "ashrdi3" 11386 [(set (match_operand:DI 0 "shiftdi_operand" "") 11387 (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "") 11388 (match_operand:QI 2 "nonmemory_operand" "")))] 11389 "" 11390 "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;") 11391 11392(define_insn "*ashrdi3_63_rex64" 11393 [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm") 11394 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0") 11395 (match_operand:DI 2 "const_int_operand" "i,i"))) 11396 (clobber (reg:CC FLAGS_REG))] 11397 "TARGET_64BIT && INTVAL (operands[2]) == 63 11398 && (TARGET_USE_CLTD || optimize_size) 11399 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)" 11400 "@ 11401 {cqto|cqo} 11402 sar{q}\t{%2, %0|%0, %2}" 11403 [(set_attr "type" "imovx,ishift") 11404 (set_attr "prefix_0f" "0,*") 11405 (set_attr "length_immediate" "0,*") 11406 (set_attr "modrm" "0,1") 11407 (set_attr "mode" "DI")]) 11408 11409(define_insn "*ashrdi3_1_one_bit_rex64" 11410 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 11411 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 11412 (match_operand:QI 2 "const1_operand" ""))) 11413 (clobber (reg:CC FLAGS_REG))] 11414 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands) 11415 && (TARGET_SHIFT1 || optimize_size)" 11416 "sar{q}\t%0" 11417 [(set_attr "type" "ishift") 11418 (set (attr "length") 11419 (if_then_else (match_operand:DI 0 "register_operand" "") 11420 (const_string "2") 11421 (const_string "*")))]) 11422 11423(define_insn "*ashrdi3_1_rex64" 11424 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm") 11425 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 11426 (match_operand:QI 2 "nonmemory_operand" "J,c"))) 11427 (clobber (reg:CC FLAGS_REG))] 11428 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)" 11429 "@ 11430 sar{q}\t{%2, %0|%0, %2} 11431 sar{q}\t{%b2, %0|%0, %b2}" 11432 [(set_attr "type" "ishift") 11433 (set_attr "mode" "DI")]) 11434 11435;; This pattern can't accept a variable shift count, since shifts by 11436;; zero don't affect the flags. We assume that shifts by constant 11437;; zero are optimized away. 11438(define_insn "*ashrdi3_one_bit_cmp_rex64" 11439 [(set (reg FLAGS_REG) 11440 (compare 11441 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 11442 (match_operand:QI 2 "const1_operand" "")) 11443 (const_int 0))) 11444 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 11445 (ashiftrt:DI (match_dup 1) (match_dup 2)))] 11446 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 11447 && (TARGET_SHIFT1 || optimize_size) 11448 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)" 11449 "sar{q}\t%0" 11450 [(set_attr "type" "ishift") 11451 (set (attr "length") 11452 (if_then_else (match_operand:DI 0 "register_operand" "") 11453 (const_string "2") 11454 (const_string "*")))]) 11455 11456(define_insn "*ashrdi3_one_bit_cconly_rex64" 11457 [(set (reg FLAGS_REG) 11458 (compare 11459 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 11460 (match_operand:QI 2 "const1_operand" "")) 11461 (const_int 0))) 11462 (clobber (match_scratch:DI 0 "=r"))] 11463 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 11464 && (TARGET_SHIFT1 || optimize_size) 11465 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)" 11466 "sar{q}\t%0" 11467 [(set_attr "type" "ishift") 11468 (set_attr "length" "2")]) 11469 11470;; This pattern can't accept a variable shift count, since shifts by 11471;; zero don't affect the flags. We assume that shifts by constant 11472;; zero are optimized away. 11473(define_insn "*ashrdi3_cmp_rex64" 11474 [(set (reg FLAGS_REG) 11475 (compare 11476 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 11477 (match_operand:QI 2 "const_int_operand" "n")) 11478 (const_int 0))) 11479 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 11480 (ashiftrt:DI (match_dup 1) (match_dup 2)))] 11481 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 11482 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands) 11483 && (optimize_size 11484 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11485 "sar{q}\t{%2, %0|%0, %2}" 11486 [(set_attr "type" "ishift") 11487 (set_attr "mode" "DI")]) 11488 11489(define_insn "*ashrdi3_cconly_rex64" 11490 [(set (reg FLAGS_REG) 11491 (compare 11492 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 11493 (match_operand:QI 2 "const_int_operand" "n")) 11494 (const_int 0))) 11495 (clobber (match_scratch:DI 0 "=r"))] 11496 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 11497 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands) 11498 && (optimize_size 11499 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11500 "sar{q}\t{%2, %0|%0, %2}" 11501 [(set_attr "type" "ishift") 11502 (set_attr "mode" "DI")]) 11503 11504(define_insn "*ashrdi3_1" 11505 [(set (match_operand:DI 0 "register_operand" "=r") 11506 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0") 11507 (match_operand:QI 2 "nonmemory_operand" "Jc"))) 11508 (clobber (reg:CC FLAGS_REG))] 11509 "!TARGET_64BIT" 11510 "#" 11511 [(set_attr "type" "multi")]) 11512 11513;; By default we don't ask for a scratch register, because when DImode 11514;; values are manipulated, registers are already at a premium. But if 11515;; we have one handy, we won't turn it away. 11516(define_peephole2 11517 [(match_scratch:SI 3 "r") 11518 (parallel [(set (match_operand:DI 0 "register_operand" "") 11519 (ashiftrt:DI (match_operand:DI 1 "register_operand" "") 11520 (match_operand:QI 2 "nonmemory_operand" ""))) 11521 (clobber (reg:CC FLAGS_REG))]) 11522 (match_dup 3)] 11523 "!TARGET_64BIT && TARGET_CMOVE" 11524 [(const_int 0)] 11525 "ix86_split_ashr (operands, operands[3], DImode); DONE;") 11526 11527(define_split 11528 [(set (match_operand:DI 0 "register_operand" "") 11529 (ashiftrt:DI (match_operand:DI 1 "register_operand" "") 11530 (match_operand:QI 2 "nonmemory_operand" ""))) 11531 (clobber (reg:CC FLAGS_REG))] 11532 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2) 11533 ? flow2_completed : reload_completed)" 11534 [(const_int 0)] 11535 "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;") 11536 11537(define_insn "x86_shrd_1" 11538 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m") 11539 (ior:SI (ashiftrt:SI (match_dup 0) 11540 (match_operand:QI 2 "nonmemory_operand" "I,c")) 11541 (ashift:SI (match_operand:SI 1 "register_operand" "r,r") 11542 (minus:QI (const_int 32) (match_dup 2))))) 11543 (clobber (reg:CC FLAGS_REG))] 11544 "" 11545 "@ 11546 shrd{l}\t{%2, %1, %0|%0, %1, %2} 11547 shrd{l}\t{%s2%1, %0|%0, %1, %2}" 11548 [(set_attr "type" "ishift") 11549 (set_attr "prefix_0f" "1") 11550 (set_attr "pent_pair" "np") 11551 (set_attr "mode" "SI")]) 11552 11553(define_expand "x86_shift_adj_3" 11554 [(use (match_operand:SI 0 "register_operand" "")) 11555 (use (match_operand:SI 1 "register_operand" "")) 11556 (use (match_operand:QI 2 "register_operand" ""))] 11557 "" 11558{ 11559 rtx label = gen_label_rtx (); 11560 rtx tmp; 11561 11562 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32))); 11563 11564 tmp = gen_rtx_REG (CCZmode, FLAGS_REG); 11565 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx); 11566 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp, 11567 gen_rtx_LABEL_REF (VOIDmode, label), 11568 pc_rtx); 11569 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp)); 11570 JUMP_LABEL (tmp) = label; 11571 11572 emit_move_insn (operands[0], operands[1]); 11573 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31))); 11574 11575 emit_label (label); 11576 LABEL_NUSES (label) = 1; 11577 11578 DONE; 11579}) 11580 11581(define_insn "ashrsi3_31" 11582 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm") 11583 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0") 11584 (match_operand:SI 2 "const_int_operand" "i,i"))) 11585 (clobber (reg:CC FLAGS_REG))] 11586 "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size) 11587 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11588 "@ 11589 {cltd|cdq} 11590 sar{l}\t{%2, %0|%0, %2}" 11591 [(set_attr "type" "imovx,ishift") 11592 (set_attr "prefix_0f" "0,*") 11593 (set_attr "length_immediate" "0,*") 11594 (set_attr "modrm" "0,1") 11595 (set_attr "mode" "SI")]) 11596 11597(define_insn "*ashrsi3_31_zext" 11598 [(set (match_operand:DI 0 "register_operand" "=*d,r") 11599 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0") 11600 (match_operand:SI 2 "const_int_operand" "i,i")))) 11601 (clobber (reg:CC FLAGS_REG))] 11602 "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size) 11603 && INTVAL (operands[2]) == 31 11604 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11605 "@ 11606 {cltd|cdq} 11607 sar{l}\t{%2, %k0|%k0, %2}" 11608 [(set_attr "type" "imovx,ishift") 11609 (set_attr "prefix_0f" "0,*") 11610 (set_attr "length_immediate" "0,*") 11611 (set_attr "modrm" "0,1") 11612 (set_attr "mode" "SI")]) 11613 11614(define_expand "ashrsi3" 11615 [(set (match_operand:SI 0 "nonimmediate_operand" "") 11616 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "") 11617 (match_operand:QI 2 "nonmemory_operand" ""))) 11618 (clobber (reg:CC FLAGS_REG))] 11619 "" 11620 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;") 11621 11622(define_insn "*ashrsi3_1_one_bit" 11623 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 11624 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 11625 (match_operand:QI 2 "const1_operand" ""))) 11626 (clobber (reg:CC FLAGS_REG))] 11627 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands) 11628 && (TARGET_SHIFT1 || optimize_size)" 11629 "sar{l}\t%0" 11630 [(set_attr "type" "ishift") 11631 (set (attr "length") 11632 (if_then_else (match_operand:SI 0 "register_operand" "") 11633 (const_string "2") 11634 (const_string "*")))]) 11635 11636(define_insn "*ashrsi3_1_one_bit_zext" 11637 [(set (match_operand:DI 0 "register_operand" "=r") 11638 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0") 11639 (match_operand:QI 2 "const1_operand" "")))) 11640 (clobber (reg:CC FLAGS_REG))] 11641 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands) 11642 && (TARGET_SHIFT1 || optimize_size)" 11643 "sar{l}\t%k0" 11644 [(set_attr "type" "ishift") 11645 (set_attr "length" "2")]) 11646 11647(define_insn "*ashrsi3_1" 11648 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm") 11649 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 11650 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 11651 (clobber (reg:CC FLAGS_REG))] 11652 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11653 "@ 11654 sar{l}\t{%2, %0|%0, %2} 11655 sar{l}\t{%b2, %0|%0, %b2}" 11656 [(set_attr "type" "ishift") 11657 (set_attr "mode" "SI")]) 11658 11659(define_insn "*ashrsi3_1_zext" 11660 [(set (match_operand:DI 0 "register_operand" "=r,r") 11661 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0") 11662 (match_operand:QI 2 "nonmemory_operand" "I,c")))) 11663 (clobber (reg:CC FLAGS_REG))] 11664 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11665 "@ 11666 sar{l}\t{%2, %k0|%k0, %2} 11667 sar{l}\t{%b2, %k0|%k0, %b2}" 11668 [(set_attr "type" "ishift") 11669 (set_attr "mode" "SI")]) 11670 11671;; This pattern can't accept a variable shift count, since shifts by 11672;; zero don't affect the flags. We assume that shifts by constant 11673;; zero are optimized away. 11674(define_insn "*ashrsi3_one_bit_cmp" 11675 [(set (reg FLAGS_REG) 11676 (compare 11677 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 11678 (match_operand:QI 2 "const1_operand" "")) 11679 (const_int 0))) 11680 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 11681 (ashiftrt:SI (match_dup 1) (match_dup 2)))] 11682 "ix86_match_ccmode (insn, CCGOCmode) 11683 && (TARGET_SHIFT1 || optimize_size) 11684 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11685 "sar{l}\t%0" 11686 [(set_attr "type" "ishift") 11687 (set (attr "length") 11688 (if_then_else (match_operand:SI 0 "register_operand" "") 11689 (const_string "2") 11690 (const_string "*")))]) 11691 11692(define_insn "*ashrsi3_one_bit_cconly" 11693 [(set (reg FLAGS_REG) 11694 (compare 11695 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 11696 (match_operand:QI 2 "const1_operand" "")) 11697 (const_int 0))) 11698 (clobber (match_scratch:SI 0 "=r"))] 11699 "ix86_match_ccmode (insn, CCGOCmode) 11700 && (TARGET_SHIFT1 || optimize_size) 11701 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11702 "sar{l}\t%0" 11703 [(set_attr "type" "ishift") 11704 (set_attr "length" "2")]) 11705 11706(define_insn "*ashrsi3_one_bit_cmp_zext" 11707 [(set (reg FLAGS_REG) 11708 (compare 11709 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0") 11710 (match_operand:QI 2 "const1_operand" "")) 11711 (const_int 0))) 11712 (set (match_operand:DI 0 "register_operand" "=r") 11713 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))] 11714 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode) 11715 && (TARGET_SHIFT1 || optimize_size) 11716 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)" 11717 "sar{l}\t%k0" 11718 [(set_attr "type" "ishift") 11719 (set_attr "length" "2")]) 11720 11721;; This pattern can't accept a variable shift count, since shifts by 11722;; zero don't affect the flags. We assume that shifts by constant 11723;; zero are optimized away. 11724(define_insn "*ashrsi3_cmp" 11725 [(set (reg FLAGS_REG) 11726 (compare 11727 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 11728 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11729 (const_int 0))) 11730 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 11731 (ashiftrt:SI (match_dup 1) (match_dup 2)))] 11732 "ix86_match_ccmode (insn, CCGOCmode) 11733 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands) 11734 && (optimize_size 11735 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11736 "sar{l}\t{%2, %0|%0, %2}" 11737 [(set_attr "type" "ishift") 11738 (set_attr "mode" "SI")]) 11739 11740(define_insn "*ashrsi3_cconly" 11741 [(set (reg FLAGS_REG) 11742 (compare 11743 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 11744 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11745 (const_int 0))) 11746 (clobber (match_scratch:SI 0 "=r"))] 11747 "ix86_match_ccmode (insn, CCGOCmode) 11748 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands) 11749 && (optimize_size 11750 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11751 "sar{l}\t{%2, %0|%0, %2}" 11752 [(set_attr "type" "ishift") 11753 (set_attr "mode" "SI")]) 11754 11755(define_insn "*ashrsi3_cmp_zext" 11756 [(set (reg FLAGS_REG) 11757 (compare 11758 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0") 11759 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11760 (const_int 0))) 11761 (set (match_operand:DI 0 "register_operand" "=r") 11762 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))] 11763 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 11764 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands) 11765 && (optimize_size 11766 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11767 "sar{l}\t{%2, %k0|%k0, %2}" 11768 [(set_attr "type" "ishift") 11769 (set_attr "mode" "SI")]) 11770 11771(define_expand "ashrhi3" 11772 [(set (match_operand:HI 0 "nonimmediate_operand" "") 11773 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "") 11774 (match_operand:QI 2 "nonmemory_operand" ""))) 11775 (clobber (reg:CC FLAGS_REG))] 11776 "TARGET_HIMODE_MATH" 11777 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;") 11778 11779(define_insn "*ashrhi3_1_one_bit" 11780 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 11781 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11782 (match_operand:QI 2 "const1_operand" ""))) 11783 (clobber (reg:CC FLAGS_REG))] 11784 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands) 11785 && (TARGET_SHIFT1 || optimize_size)" 11786 "sar{w}\t%0" 11787 [(set_attr "type" "ishift") 11788 (set (attr "length") 11789 (if_then_else (match_operand 0 "register_operand" "") 11790 (const_string "2") 11791 (const_string "*")))]) 11792 11793(define_insn "*ashrhi3_1" 11794 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm") 11795 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 11796 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 11797 (clobber (reg:CC FLAGS_REG))] 11798 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)" 11799 "@ 11800 sar{w}\t{%2, %0|%0, %2} 11801 sar{w}\t{%b2, %0|%0, %b2}" 11802 [(set_attr "type" "ishift") 11803 (set_attr "mode" "HI")]) 11804 11805;; This pattern can't accept a variable shift count, since shifts by 11806;; zero don't affect the flags. We assume that shifts by constant 11807;; zero are optimized away. 11808(define_insn "*ashrhi3_one_bit_cmp" 11809 [(set (reg FLAGS_REG) 11810 (compare 11811 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11812 (match_operand:QI 2 "const1_operand" "")) 11813 (const_int 0))) 11814 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 11815 (ashiftrt:HI (match_dup 1) (match_dup 2)))] 11816 "ix86_match_ccmode (insn, CCGOCmode) 11817 && (TARGET_SHIFT1 || optimize_size) 11818 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)" 11819 "sar{w}\t%0" 11820 [(set_attr "type" "ishift") 11821 (set (attr "length") 11822 (if_then_else (match_operand 0 "register_operand" "") 11823 (const_string "2") 11824 (const_string "*")))]) 11825 11826(define_insn "*ashrhi3_one_bit_cconly" 11827 [(set (reg FLAGS_REG) 11828 (compare 11829 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11830 (match_operand:QI 2 "const1_operand" "")) 11831 (const_int 0))) 11832 (clobber (match_scratch:HI 0 "=r"))] 11833 "ix86_match_ccmode (insn, CCGOCmode) 11834 && (TARGET_SHIFT1 || optimize_size) 11835 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)" 11836 "sar{w}\t%0" 11837 [(set_attr "type" "ishift") 11838 (set_attr "length" "2")]) 11839 11840;; This pattern can't accept a variable shift count, since shifts by 11841;; zero don't affect the flags. We assume that shifts by constant 11842;; zero are optimized away. 11843(define_insn "*ashrhi3_cmp" 11844 [(set (reg FLAGS_REG) 11845 (compare 11846 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11847 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11848 (const_int 0))) 11849 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 11850 (ashiftrt:HI (match_dup 1) (match_dup 2)))] 11851 "ix86_match_ccmode (insn, CCGOCmode) 11852 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands) 11853 && (optimize_size 11854 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11855 "sar{w}\t{%2, %0|%0, %2}" 11856 [(set_attr "type" "ishift") 11857 (set_attr "mode" "HI")]) 11858 11859(define_insn "*ashrhi3_cconly" 11860 [(set (reg FLAGS_REG) 11861 (compare 11862 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 11863 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11864 (const_int 0))) 11865 (clobber (match_scratch:HI 0 "=r"))] 11866 "ix86_match_ccmode (insn, CCGOCmode) 11867 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands) 11868 && (optimize_size 11869 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11870 "sar{w}\t{%2, %0|%0, %2}" 11871 [(set_attr "type" "ishift") 11872 (set_attr "mode" "HI")]) 11873 11874(define_expand "ashrqi3" 11875 [(set (match_operand:QI 0 "nonimmediate_operand" "") 11876 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "") 11877 (match_operand:QI 2 "nonmemory_operand" ""))) 11878 (clobber (reg:CC FLAGS_REG))] 11879 "TARGET_QIMODE_MATH" 11880 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;") 11881 11882(define_insn "*ashrqi3_1_one_bit" 11883 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 11884 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11885 (match_operand:QI 2 "const1_operand" ""))) 11886 (clobber (reg:CC FLAGS_REG))] 11887 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands) 11888 && (TARGET_SHIFT1 || optimize_size)" 11889 "sar{b}\t%0" 11890 [(set_attr "type" "ishift") 11891 (set (attr "length") 11892 (if_then_else (match_operand 0 "register_operand" "") 11893 (const_string "2") 11894 (const_string "*")))]) 11895 11896(define_insn "*ashrqi3_1_one_bit_slp" 11897 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm")) 11898 (ashiftrt:QI (match_dup 0) 11899 (match_operand:QI 1 "const1_operand" ""))) 11900 (clobber (reg:CC FLAGS_REG))] 11901 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands) 11902 && (! TARGET_PARTIAL_REG_STALL || optimize_size) 11903 && (TARGET_SHIFT1 || optimize_size)" 11904 "sar{b}\t%0" 11905 [(set_attr "type" "ishift1") 11906 (set (attr "length") 11907 (if_then_else (match_operand 0 "register_operand" "") 11908 (const_string "2") 11909 (const_string "*")))]) 11910 11911(define_insn "*ashrqi3_1" 11912 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm") 11913 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 11914 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 11915 (clobber (reg:CC FLAGS_REG))] 11916 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)" 11917 "@ 11918 sar{b}\t{%2, %0|%0, %2} 11919 sar{b}\t{%b2, %0|%0, %b2}" 11920 [(set_attr "type" "ishift") 11921 (set_attr "mode" "QI")]) 11922 11923(define_insn "*ashrqi3_1_slp" 11924 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm")) 11925 (ashiftrt:QI (match_dup 0) 11926 (match_operand:QI 1 "nonmemory_operand" "I,c"))) 11927 (clobber (reg:CC FLAGS_REG))] 11928 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 11929 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 11930 "@ 11931 sar{b}\t{%1, %0|%0, %1} 11932 sar{b}\t{%b1, %0|%0, %b1}" 11933 [(set_attr "type" "ishift1") 11934 (set_attr "mode" "QI")]) 11935 11936;; This pattern can't accept a variable shift count, since shifts by 11937;; zero don't affect the flags. We assume that shifts by constant 11938;; zero are optimized away. 11939(define_insn "*ashrqi3_one_bit_cmp" 11940 [(set (reg FLAGS_REG) 11941 (compare 11942 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11943 (match_operand:QI 2 "const1_operand" "I")) 11944 (const_int 0))) 11945 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 11946 (ashiftrt:QI (match_dup 1) (match_dup 2)))] 11947 "ix86_match_ccmode (insn, CCGOCmode) 11948 && (TARGET_SHIFT1 || optimize_size) 11949 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)" 11950 "sar{b}\t%0" 11951 [(set_attr "type" "ishift") 11952 (set (attr "length") 11953 (if_then_else (match_operand 0 "register_operand" "") 11954 (const_string "2") 11955 (const_string "*")))]) 11956 11957(define_insn "*ashrqi3_one_bit_cconly" 11958 [(set (reg FLAGS_REG) 11959 (compare 11960 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11961 (match_operand:QI 2 "const1_operand" "I")) 11962 (const_int 0))) 11963 (clobber (match_scratch:QI 0 "=q"))] 11964 "ix86_match_ccmode (insn, CCGOCmode) 11965 && (TARGET_SHIFT1 || optimize_size) 11966 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)" 11967 "sar{b}\t%0" 11968 [(set_attr "type" "ishift") 11969 (set_attr "length" "2")]) 11970 11971;; This pattern can't accept a variable shift count, since shifts by 11972;; zero don't affect the flags. We assume that shifts by constant 11973;; zero are optimized away. 11974(define_insn "*ashrqi3_cmp" 11975 [(set (reg FLAGS_REG) 11976 (compare 11977 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11978 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11979 (const_int 0))) 11980 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 11981 (ashiftrt:QI (match_dup 1) (match_dup 2)))] 11982 "ix86_match_ccmode (insn, CCGOCmode) 11983 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands) 11984 && (optimize_size 11985 || !TARGET_PARTIAL_FLAG_REG_STALL)" 11986 "sar{b}\t{%2, %0|%0, %2}" 11987 [(set_attr "type" "ishift") 11988 (set_attr "mode" "QI")]) 11989 11990(define_insn "*ashrqi3_cconly" 11991 [(set (reg FLAGS_REG) 11992 (compare 11993 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 11994 (match_operand:QI 2 "const_1_to_31_operand" "I")) 11995 (const_int 0))) 11996 (clobber (match_scratch:QI 0 "=q"))] 11997 "ix86_match_ccmode (insn, CCGOCmode) 11998 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands) 11999 && (optimize_size 12000 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12001 "sar{b}\t{%2, %0|%0, %2}" 12002 [(set_attr "type" "ishift") 12003 (set_attr "mode" "QI")]) 12004 12005 12006;; Logical shift instructions 12007 12008;; See comment above `ashldi3' about how this works. 12009 12010(define_expand "lshrti3" 12011 [(parallel [(set (match_operand:TI 0 "register_operand" "") 12012 (lshiftrt:TI (match_operand:TI 1 "register_operand" "") 12013 (match_operand:QI 2 "nonmemory_operand" ""))) 12014 (clobber (reg:CC FLAGS_REG))])] 12015 "TARGET_64BIT" 12016{ 12017 if (! immediate_operand (operands[2], QImode)) 12018 { 12019 emit_insn (gen_lshrti3_1 (operands[0], operands[1], operands[2])); 12020 DONE; 12021 } 12022 ix86_expand_binary_operator (LSHIFTRT, TImode, operands); 12023 DONE; 12024}) 12025 12026(define_insn "lshrti3_1" 12027 [(set (match_operand:TI 0 "register_operand" "=r") 12028 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0") 12029 (match_operand:QI 2 "register_operand" "c"))) 12030 (clobber (match_scratch:DI 3 "=&r")) 12031 (clobber (reg:CC FLAGS_REG))] 12032 "TARGET_64BIT" 12033 "#" 12034 [(set_attr "type" "multi")]) 12035 12036(define_insn "*lshrti3_2" 12037 [(set (match_operand:TI 0 "register_operand" "=r") 12038 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0") 12039 (match_operand:QI 2 "immediate_operand" "O"))) 12040 (clobber (reg:CC FLAGS_REG))] 12041 "TARGET_64BIT" 12042 "#" 12043 [(set_attr "type" "multi")]) 12044 12045(define_split 12046 [(set (match_operand:TI 0 "register_operand" "") 12047 (lshiftrt:TI (match_operand:TI 1 "register_operand" "") 12048 (match_operand:QI 2 "register_operand" ""))) 12049 (clobber (match_scratch:DI 3 "")) 12050 (clobber (reg:CC FLAGS_REG))] 12051 "TARGET_64BIT && reload_completed" 12052 [(const_int 0)] 12053 "ix86_split_lshr (operands, operands[3], TImode); DONE;") 12054 12055(define_split 12056 [(set (match_operand:TI 0 "register_operand" "") 12057 (lshiftrt:TI (match_operand:TI 1 "register_operand" "") 12058 (match_operand:QI 2 "immediate_operand" ""))) 12059 (clobber (reg:CC FLAGS_REG))] 12060 "TARGET_64BIT && reload_completed" 12061 [(const_int 0)] 12062 "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;") 12063 12064(define_expand "lshrdi3" 12065 [(set (match_operand:DI 0 "shiftdi_operand" "") 12066 (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "") 12067 (match_operand:QI 2 "nonmemory_operand" "")))] 12068 "" 12069 "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;") 12070 12071(define_insn "*lshrdi3_1_one_bit_rex64" 12072 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 12073 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12074 (match_operand:QI 2 "const1_operand" ""))) 12075 (clobber (reg:CC FLAGS_REG))] 12076 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12077 && (TARGET_SHIFT1 || optimize_size)" 12078 "shr{q}\t%0" 12079 [(set_attr "type" "ishift") 12080 (set (attr "length") 12081 (if_then_else (match_operand:DI 0 "register_operand" "") 12082 (const_string "2") 12083 (const_string "*")))]) 12084 12085(define_insn "*lshrdi3_1_rex64" 12086 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm") 12087 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 12088 (match_operand:QI 2 "nonmemory_operand" "J,c"))) 12089 (clobber (reg:CC FLAGS_REG))] 12090 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12091 "@ 12092 shr{q}\t{%2, %0|%0, %2} 12093 shr{q}\t{%b2, %0|%0, %b2}" 12094 [(set_attr "type" "ishift") 12095 (set_attr "mode" "DI")]) 12096 12097;; This pattern can't accept a variable shift count, since shifts by 12098;; zero don't affect the flags. We assume that shifts by constant 12099;; zero are optimized away. 12100(define_insn "*lshrdi3_cmp_one_bit_rex64" 12101 [(set (reg FLAGS_REG) 12102 (compare 12103 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12104 (match_operand:QI 2 "const1_operand" "")) 12105 (const_int 0))) 12106 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 12107 (lshiftrt:DI (match_dup 1) (match_dup 2)))] 12108 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12109 && (TARGET_SHIFT1 || optimize_size) 12110 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12111 "shr{q}\t%0" 12112 [(set_attr "type" "ishift") 12113 (set (attr "length") 12114 (if_then_else (match_operand:DI 0 "register_operand" "") 12115 (const_string "2") 12116 (const_string "*")))]) 12117 12118(define_insn "*lshrdi3_cconly_one_bit_rex64" 12119 [(set (reg FLAGS_REG) 12120 (compare 12121 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12122 (match_operand:QI 2 "const1_operand" "")) 12123 (const_int 0))) 12124 (clobber (match_scratch:DI 0 "=r"))] 12125 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12126 && (TARGET_SHIFT1 || optimize_size) 12127 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12128 "shr{q}\t%0" 12129 [(set_attr "type" "ishift") 12130 (set_attr "length" "2")]) 12131 12132;; This pattern can't accept a variable shift count, since shifts by 12133;; zero don't affect the flags. We assume that shifts by constant 12134;; zero are optimized away. 12135(define_insn "*lshrdi3_cmp_rex64" 12136 [(set (reg FLAGS_REG) 12137 (compare 12138 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12139 (match_operand:QI 2 "const_int_operand" "e")) 12140 (const_int 0))) 12141 (set (match_operand:DI 0 "nonimmediate_operand" "=rm") 12142 (lshiftrt:DI (match_dup 1) (match_dup 2)))] 12143 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12144 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12145 && (optimize_size 12146 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12147 "shr{q}\t{%2, %0|%0, %2}" 12148 [(set_attr "type" "ishift") 12149 (set_attr "mode" "DI")]) 12150 12151(define_insn "*lshrdi3_cconly_rex64" 12152 [(set (reg FLAGS_REG) 12153 (compare 12154 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12155 (match_operand:QI 2 "const_int_operand" "e")) 12156 (const_int 0))) 12157 (clobber (match_scratch:DI 0 "=r"))] 12158 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12159 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12160 && (optimize_size 12161 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12162 "shr{q}\t{%2, %0|%0, %2}" 12163 [(set_attr "type" "ishift") 12164 (set_attr "mode" "DI")]) 12165 12166(define_insn "*lshrdi3_1" 12167 [(set (match_operand:DI 0 "register_operand" "=r") 12168 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0") 12169 (match_operand:QI 2 "nonmemory_operand" "Jc"))) 12170 (clobber (reg:CC FLAGS_REG))] 12171 "!TARGET_64BIT" 12172 "#" 12173 [(set_attr "type" "multi")]) 12174 12175;; By default we don't ask for a scratch register, because when DImode 12176;; values are manipulated, registers are already at a premium. But if 12177;; we have one handy, we won't turn it away. 12178(define_peephole2 12179 [(match_scratch:SI 3 "r") 12180 (parallel [(set (match_operand:DI 0 "register_operand" "") 12181 (lshiftrt:DI (match_operand:DI 1 "register_operand" "") 12182 (match_operand:QI 2 "nonmemory_operand" ""))) 12183 (clobber (reg:CC FLAGS_REG))]) 12184 (match_dup 3)] 12185 "!TARGET_64BIT && TARGET_CMOVE" 12186 [(const_int 0)] 12187 "ix86_split_lshr (operands, operands[3], DImode); DONE;") 12188 12189(define_split 12190 [(set (match_operand:DI 0 "register_operand" "") 12191 (lshiftrt:DI (match_operand:DI 1 "register_operand" "") 12192 (match_operand:QI 2 "nonmemory_operand" ""))) 12193 (clobber (reg:CC FLAGS_REG))] 12194 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2) 12195 ? flow2_completed : reload_completed)" 12196 [(const_int 0)] 12197 "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;") 12198 12199(define_expand "lshrsi3" 12200 [(set (match_operand:SI 0 "nonimmediate_operand" "") 12201 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "") 12202 (match_operand:QI 2 "nonmemory_operand" ""))) 12203 (clobber (reg:CC FLAGS_REG))] 12204 "" 12205 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;") 12206 12207(define_insn "*lshrsi3_1_one_bit" 12208 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 12209 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12210 (match_operand:QI 2 "const1_operand" ""))) 12211 (clobber (reg:CC FLAGS_REG))] 12212 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12213 && (TARGET_SHIFT1 || optimize_size)" 12214 "shr{l}\t%0" 12215 [(set_attr "type" "ishift") 12216 (set (attr "length") 12217 (if_then_else (match_operand:SI 0 "register_operand" "") 12218 (const_string "2") 12219 (const_string "*")))]) 12220 12221(define_insn "*lshrsi3_1_one_bit_zext" 12222 [(set (match_operand:DI 0 "register_operand" "=r") 12223 (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0")) 12224 (match_operand:QI 2 "const1_operand" ""))) 12225 (clobber (reg:CC FLAGS_REG))] 12226 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12227 && (TARGET_SHIFT1 || optimize_size)" 12228 "shr{l}\t%k0" 12229 [(set_attr "type" "ishift") 12230 (set_attr "length" "2")]) 12231 12232(define_insn "*lshrsi3_1" 12233 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm") 12234 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 12235 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12236 (clobber (reg:CC FLAGS_REG))] 12237 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12238 "@ 12239 shr{l}\t{%2, %0|%0, %2} 12240 shr{l}\t{%b2, %0|%0, %b2}" 12241 [(set_attr "type" "ishift") 12242 (set_attr "mode" "SI")]) 12243 12244(define_insn "*lshrsi3_1_zext" 12245 [(set (match_operand:DI 0 "register_operand" "=r,r") 12246 (zero_extend:DI 12247 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 12248 (match_operand:QI 2 "nonmemory_operand" "I,c")))) 12249 (clobber (reg:CC FLAGS_REG))] 12250 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12251 "@ 12252 shr{l}\t{%2, %k0|%k0, %2} 12253 shr{l}\t{%b2, %k0|%k0, %b2}" 12254 [(set_attr "type" "ishift") 12255 (set_attr "mode" "SI")]) 12256 12257;; This pattern can't accept a variable shift count, since shifts by 12258;; zero don't affect the flags. We assume that shifts by constant 12259;; zero are optimized away. 12260(define_insn "*lshrsi3_one_bit_cmp" 12261 [(set (reg FLAGS_REG) 12262 (compare 12263 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12264 (match_operand:QI 2 "const1_operand" "")) 12265 (const_int 0))) 12266 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 12267 (lshiftrt:SI (match_dup 1) (match_dup 2)))] 12268 "ix86_match_ccmode (insn, CCGOCmode) 12269 && (TARGET_SHIFT1 || optimize_size) 12270 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12271 "shr{l}\t%0" 12272 [(set_attr "type" "ishift") 12273 (set (attr "length") 12274 (if_then_else (match_operand:SI 0 "register_operand" "") 12275 (const_string "2") 12276 (const_string "*")))]) 12277 12278(define_insn "*lshrsi3_one_bit_cconly" 12279 [(set (reg FLAGS_REG) 12280 (compare 12281 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12282 (match_operand:QI 2 "const1_operand" "")) 12283 (const_int 0))) 12284 (clobber (match_scratch:SI 0 "=r"))] 12285 "ix86_match_ccmode (insn, CCGOCmode) 12286 && (TARGET_SHIFT1 || optimize_size) 12287 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12288 "shr{l}\t%0" 12289 [(set_attr "type" "ishift") 12290 (set_attr "length" "2")]) 12291 12292(define_insn "*lshrsi3_cmp_one_bit_zext" 12293 [(set (reg FLAGS_REG) 12294 (compare 12295 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0") 12296 (match_operand:QI 2 "const1_operand" "")) 12297 (const_int 0))) 12298 (set (match_operand:DI 0 "register_operand" "=r") 12299 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))] 12300 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12301 && (TARGET_SHIFT1 || optimize_size) 12302 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12303 "shr{l}\t%k0" 12304 [(set_attr "type" "ishift") 12305 (set_attr "length" "2")]) 12306 12307;; This pattern can't accept a variable shift count, since shifts by 12308;; zero don't affect the flags. We assume that shifts by constant 12309;; zero are optimized away. 12310(define_insn "*lshrsi3_cmp" 12311 [(set (reg FLAGS_REG) 12312 (compare 12313 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12314 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12315 (const_int 0))) 12316 (set (match_operand:SI 0 "nonimmediate_operand" "=rm") 12317 (lshiftrt:SI (match_dup 1) (match_dup 2)))] 12318 "ix86_match_ccmode (insn, CCGOCmode) 12319 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12320 && (optimize_size 12321 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12322 "shr{l}\t{%2, %0|%0, %2}" 12323 [(set_attr "type" "ishift") 12324 (set_attr "mode" "SI")]) 12325 12326(define_insn "*lshrsi3_cconly" 12327 [(set (reg FLAGS_REG) 12328 (compare 12329 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12330 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12331 (const_int 0))) 12332 (clobber (match_scratch:SI 0 "=r"))] 12333 "ix86_match_ccmode (insn, CCGOCmode) 12334 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12335 && (optimize_size 12336 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12337 "shr{l}\t{%2, %0|%0, %2}" 12338 [(set_attr "type" "ishift") 12339 (set_attr "mode" "SI")]) 12340 12341(define_insn "*lshrsi3_cmp_zext" 12342 [(set (reg FLAGS_REG) 12343 (compare 12344 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0") 12345 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12346 (const_int 0))) 12347 (set (match_operand:DI 0 "register_operand" "=r") 12348 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))] 12349 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode) 12350 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12351 && (optimize_size 12352 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12353 "shr{l}\t{%2, %k0|%k0, %2}" 12354 [(set_attr "type" "ishift") 12355 (set_attr "mode" "SI")]) 12356 12357(define_expand "lshrhi3" 12358 [(set (match_operand:HI 0 "nonimmediate_operand" "") 12359 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "") 12360 (match_operand:QI 2 "nonmemory_operand" ""))) 12361 (clobber (reg:CC FLAGS_REG))] 12362 "TARGET_HIMODE_MATH" 12363 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;") 12364 12365(define_insn "*lshrhi3_1_one_bit" 12366 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 12367 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12368 (match_operand:QI 2 "const1_operand" ""))) 12369 (clobber (reg:CC FLAGS_REG))] 12370 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12371 && (TARGET_SHIFT1 || optimize_size)" 12372 "shr{w}\t%0" 12373 [(set_attr "type" "ishift") 12374 (set (attr "length") 12375 (if_then_else (match_operand 0 "register_operand" "") 12376 (const_string "2") 12377 (const_string "*")))]) 12378 12379(define_insn "*lshrhi3_1" 12380 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm") 12381 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 12382 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12383 (clobber (reg:CC FLAGS_REG))] 12384 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12385 "@ 12386 shr{w}\t{%2, %0|%0, %2} 12387 shr{w}\t{%b2, %0|%0, %b2}" 12388 [(set_attr "type" "ishift") 12389 (set_attr "mode" "HI")]) 12390 12391;; This pattern can't accept a variable shift count, since shifts by 12392;; zero don't affect the flags. We assume that shifts by constant 12393;; zero are optimized away. 12394(define_insn "*lshrhi3_one_bit_cmp" 12395 [(set (reg FLAGS_REG) 12396 (compare 12397 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12398 (match_operand:QI 2 "const1_operand" "")) 12399 (const_int 0))) 12400 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 12401 (lshiftrt:HI (match_dup 1) (match_dup 2)))] 12402 "ix86_match_ccmode (insn, CCGOCmode) 12403 && (TARGET_SHIFT1 || optimize_size) 12404 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12405 "shr{w}\t%0" 12406 [(set_attr "type" "ishift") 12407 (set (attr "length") 12408 (if_then_else (match_operand:SI 0 "register_operand" "") 12409 (const_string "2") 12410 (const_string "*")))]) 12411 12412(define_insn "*lshrhi3_one_bit_cconly" 12413 [(set (reg FLAGS_REG) 12414 (compare 12415 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12416 (match_operand:QI 2 "const1_operand" "")) 12417 (const_int 0))) 12418 (clobber (match_scratch:HI 0 "=r"))] 12419 "ix86_match_ccmode (insn, CCGOCmode) 12420 && (TARGET_SHIFT1 || optimize_size) 12421 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)" 12422 "shr{w}\t%0" 12423 [(set_attr "type" "ishift") 12424 (set_attr "length" "2")]) 12425 12426;; This pattern can't accept a variable shift count, since shifts by 12427;; zero don't affect the flags. We assume that shifts by constant 12428;; zero are optimized away. 12429(define_insn "*lshrhi3_cmp" 12430 [(set (reg FLAGS_REG) 12431 (compare 12432 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12433 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12434 (const_int 0))) 12435 (set (match_operand:HI 0 "nonimmediate_operand" "=rm") 12436 (lshiftrt:HI (match_dup 1) (match_dup 2)))] 12437 "ix86_match_ccmode (insn, CCGOCmode) 12438 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12439 && (optimize_size 12440 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12441 "shr{w}\t{%2, %0|%0, %2}" 12442 [(set_attr "type" "ishift") 12443 (set_attr "mode" "HI")]) 12444 12445(define_insn "*lshrhi3_cconly" 12446 [(set (reg FLAGS_REG) 12447 (compare 12448 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12449 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12450 (const_int 0))) 12451 (clobber (match_scratch:HI 0 "=r"))] 12452 "ix86_match_ccmode (insn, CCGOCmode) 12453 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands) 12454 && (optimize_size 12455 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12456 "shr{w}\t{%2, %0|%0, %2}" 12457 [(set_attr "type" "ishift") 12458 (set_attr "mode" "HI")]) 12459 12460(define_expand "lshrqi3" 12461 [(set (match_operand:QI 0 "nonimmediate_operand" "") 12462 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "") 12463 (match_operand:QI 2 "nonmemory_operand" ""))) 12464 (clobber (reg:CC FLAGS_REG))] 12465 "TARGET_QIMODE_MATH" 12466 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;") 12467 12468(define_insn "*lshrqi3_1_one_bit" 12469 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 12470 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12471 (match_operand:QI 2 "const1_operand" ""))) 12472 (clobber (reg:CC FLAGS_REG))] 12473 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands) 12474 && (TARGET_SHIFT1 || optimize_size)" 12475 "shr{b}\t%0" 12476 [(set_attr "type" "ishift") 12477 (set (attr "length") 12478 (if_then_else (match_operand 0 "register_operand" "") 12479 (const_string "2") 12480 (const_string "*")))]) 12481 12482(define_insn "*lshrqi3_1_one_bit_slp" 12483 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm")) 12484 (lshiftrt:QI (match_dup 0) 12485 (match_operand:QI 1 "const1_operand" ""))) 12486 (clobber (reg:CC FLAGS_REG))] 12487 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 12488 && (TARGET_SHIFT1 || optimize_size)" 12489 "shr{b}\t%0" 12490 [(set_attr "type" "ishift1") 12491 (set (attr "length") 12492 (if_then_else (match_operand 0 "register_operand" "") 12493 (const_string "2") 12494 (const_string "*")))]) 12495 12496(define_insn "*lshrqi3_1" 12497 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm") 12498 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 12499 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12500 (clobber (reg:CC FLAGS_REG))] 12501 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)" 12502 "@ 12503 shr{b}\t{%2, %0|%0, %2} 12504 shr{b}\t{%b2, %0|%0, %b2}" 12505 [(set_attr "type" "ishift") 12506 (set_attr "mode" "QI")]) 12507 12508(define_insn "*lshrqi3_1_slp" 12509 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm")) 12510 (lshiftrt:QI (match_dup 0) 12511 (match_operand:QI 1 "nonmemory_operand" "I,c"))) 12512 (clobber (reg:CC FLAGS_REG))] 12513 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 12514 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 12515 "@ 12516 shr{b}\t{%1, %0|%0, %1} 12517 shr{b}\t{%b1, %0|%0, %b1}" 12518 [(set_attr "type" "ishift1") 12519 (set_attr "mode" "QI")]) 12520 12521;; This pattern can't accept a variable shift count, since shifts by 12522;; zero don't affect the flags. We assume that shifts by constant 12523;; zero are optimized away. 12524(define_insn "*lshrqi2_one_bit_cmp" 12525 [(set (reg FLAGS_REG) 12526 (compare 12527 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12528 (match_operand:QI 2 "const1_operand" "")) 12529 (const_int 0))) 12530 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 12531 (lshiftrt:QI (match_dup 1) (match_dup 2)))] 12532 "ix86_match_ccmode (insn, CCGOCmode) 12533 && (TARGET_SHIFT1 || optimize_size) 12534 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)" 12535 "shr{b}\t%0" 12536 [(set_attr "type" "ishift") 12537 (set (attr "length") 12538 (if_then_else (match_operand:SI 0 "register_operand" "") 12539 (const_string "2") 12540 (const_string "*")))]) 12541 12542(define_insn "*lshrqi2_one_bit_cconly" 12543 [(set (reg FLAGS_REG) 12544 (compare 12545 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12546 (match_operand:QI 2 "const1_operand" "")) 12547 (const_int 0))) 12548 (clobber (match_scratch:QI 0 "=q"))] 12549 "ix86_match_ccmode (insn, CCGOCmode) 12550 && (TARGET_SHIFT1 || optimize_size) 12551 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)" 12552 "shr{b}\t%0" 12553 [(set_attr "type" "ishift") 12554 (set_attr "length" "2")]) 12555 12556;; This pattern can't accept a variable shift count, since shifts by 12557;; zero don't affect the flags. We assume that shifts by constant 12558;; zero are optimized away. 12559(define_insn "*lshrqi2_cmp" 12560 [(set (reg FLAGS_REG) 12561 (compare 12562 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12563 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12564 (const_int 0))) 12565 (set (match_operand:QI 0 "nonimmediate_operand" "=qm") 12566 (lshiftrt:QI (match_dup 1) (match_dup 2)))] 12567 "ix86_match_ccmode (insn, CCGOCmode) 12568 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands) 12569 && (optimize_size 12570 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12571 "shr{b}\t{%2, %0|%0, %2}" 12572 [(set_attr "type" "ishift") 12573 (set_attr "mode" "QI")]) 12574 12575(define_insn "*lshrqi2_cconly" 12576 [(set (reg FLAGS_REG) 12577 (compare 12578 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12579 (match_operand:QI 2 "const_1_to_31_operand" "I")) 12580 (const_int 0))) 12581 (clobber (match_scratch:QI 0 "=q"))] 12582 "ix86_match_ccmode (insn, CCGOCmode) 12583 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands) 12584 && (optimize_size 12585 || !TARGET_PARTIAL_FLAG_REG_STALL)" 12586 "shr{b}\t{%2, %0|%0, %2}" 12587 [(set_attr "type" "ishift") 12588 (set_attr "mode" "QI")]) 12589 12590;; Rotate instructions 12591 12592(define_expand "rotldi3" 12593 [(set (match_operand:DI 0 "shiftdi_operand" "") 12594 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "") 12595 (match_operand:QI 2 "nonmemory_operand" ""))) 12596 (clobber (reg:CC FLAGS_REG))] 12597 "" 12598{ 12599 if (TARGET_64BIT) 12600 { 12601 ix86_expand_binary_operator (ROTATE, DImode, operands); 12602 DONE; 12603 } 12604 if (!const_1_to_31_operand (operands[2], VOIDmode)) 12605 FAIL; 12606 emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2])); 12607 DONE; 12608}) 12609 12610;; Implement rotation using two double-precision shift instructions 12611;; and a scratch register. 12612(define_insn_and_split "ix86_rotldi3" 12613 [(set (match_operand:DI 0 "register_operand" "=r") 12614 (rotate:DI (match_operand:DI 1 "register_operand" "0") 12615 (match_operand:QI 2 "const_1_to_31_operand" "I"))) 12616 (clobber (reg:CC FLAGS_REG)) 12617 (clobber (match_scratch:SI 3 "=&r"))] 12618 "!TARGET_64BIT" 12619 "" 12620 "&& reload_completed" 12621 [(set (match_dup 3) (match_dup 4)) 12622 (parallel 12623 [(set (match_dup 4) 12624 (ior:SI (ashift:SI (match_dup 4) (match_dup 2)) 12625 (lshiftrt:SI (match_dup 5) 12626 (minus:QI (const_int 32) (match_dup 2))))) 12627 (clobber (reg:CC FLAGS_REG))]) 12628 (parallel 12629 [(set (match_dup 5) 12630 (ior:SI (ashift:SI (match_dup 5) (match_dup 2)) 12631 (lshiftrt:SI (match_dup 3) 12632 (minus:QI (const_int 32) (match_dup 2))))) 12633 (clobber (reg:CC FLAGS_REG))])] 12634 "split_di (operands, 1, operands + 4, operands + 5);") 12635 12636(define_insn "*rotlsi3_1_one_bit_rex64" 12637 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 12638 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12639 (match_operand:QI 2 "const1_operand" ""))) 12640 (clobber (reg:CC FLAGS_REG))] 12641 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands) 12642 && (TARGET_SHIFT1 || optimize_size)" 12643 "rol{q}\t%0" 12644 [(set_attr "type" "rotate") 12645 (set (attr "length") 12646 (if_then_else (match_operand:DI 0 "register_operand" "") 12647 (const_string "2") 12648 (const_string "*")))]) 12649 12650(define_insn "*rotldi3_1_rex64" 12651 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm") 12652 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 12653 (match_operand:QI 2 "nonmemory_operand" "e,c"))) 12654 (clobber (reg:CC FLAGS_REG))] 12655 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)" 12656 "@ 12657 rol{q}\t{%2, %0|%0, %2} 12658 rol{q}\t{%b2, %0|%0, %b2}" 12659 [(set_attr "type" "rotate") 12660 (set_attr "mode" "DI")]) 12661 12662(define_expand "rotlsi3" 12663 [(set (match_operand:SI 0 "nonimmediate_operand" "") 12664 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "") 12665 (match_operand:QI 2 "nonmemory_operand" ""))) 12666 (clobber (reg:CC FLAGS_REG))] 12667 "" 12668 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;") 12669 12670(define_insn "*rotlsi3_1_one_bit" 12671 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 12672 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12673 (match_operand:QI 2 "const1_operand" ""))) 12674 (clobber (reg:CC FLAGS_REG))] 12675 "ix86_binary_operator_ok (ROTATE, SImode, operands) 12676 && (TARGET_SHIFT1 || optimize_size)" 12677 "rol{l}\t%0" 12678 [(set_attr "type" "rotate") 12679 (set (attr "length") 12680 (if_then_else (match_operand:SI 0 "register_operand" "") 12681 (const_string "2") 12682 (const_string "*")))]) 12683 12684(define_insn "*rotlsi3_1_one_bit_zext" 12685 [(set (match_operand:DI 0 "register_operand" "=r") 12686 (zero_extend:DI 12687 (rotate:SI (match_operand:SI 1 "register_operand" "0") 12688 (match_operand:QI 2 "const1_operand" "")))) 12689 (clobber (reg:CC FLAGS_REG))] 12690 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands) 12691 && (TARGET_SHIFT1 || optimize_size)" 12692 "rol{l}\t%k0" 12693 [(set_attr "type" "rotate") 12694 (set_attr "length" "2")]) 12695 12696(define_insn "*rotlsi3_1" 12697 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm") 12698 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 12699 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12700 (clobber (reg:CC FLAGS_REG))] 12701 "ix86_binary_operator_ok (ROTATE, SImode, operands)" 12702 "@ 12703 rol{l}\t{%2, %0|%0, %2} 12704 rol{l}\t{%b2, %0|%0, %b2}" 12705 [(set_attr "type" "rotate") 12706 (set_attr "mode" "SI")]) 12707 12708(define_insn "*rotlsi3_1_zext" 12709 [(set (match_operand:DI 0 "register_operand" "=r,r") 12710 (zero_extend:DI 12711 (rotate:SI (match_operand:SI 1 "register_operand" "0,0") 12712 (match_operand:QI 2 "nonmemory_operand" "I,c")))) 12713 (clobber (reg:CC FLAGS_REG))] 12714 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)" 12715 "@ 12716 rol{l}\t{%2, %k0|%k0, %2} 12717 rol{l}\t{%b2, %k0|%k0, %b2}" 12718 [(set_attr "type" "rotate") 12719 (set_attr "mode" "SI")]) 12720 12721(define_expand "rotlhi3" 12722 [(set (match_operand:HI 0 "nonimmediate_operand" "") 12723 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "") 12724 (match_operand:QI 2 "nonmemory_operand" ""))) 12725 (clobber (reg:CC FLAGS_REG))] 12726 "TARGET_HIMODE_MATH" 12727 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;") 12728 12729(define_insn "*rotlhi3_1_one_bit" 12730 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 12731 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12732 (match_operand:QI 2 "const1_operand" ""))) 12733 (clobber (reg:CC FLAGS_REG))] 12734 "ix86_binary_operator_ok (ROTATE, HImode, operands) 12735 && (TARGET_SHIFT1 || optimize_size)" 12736 "rol{w}\t%0" 12737 [(set_attr "type" "rotate") 12738 (set (attr "length") 12739 (if_then_else (match_operand 0 "register_operand" "") 12740 (const_string "2") 12741 (const_string "*")))]) 12742 12743(define_insn "*rotlhi3_1" 12744 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm") 12745 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 12746 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12747 (clobber (reg:CC FLAGS_REG))] 12748 "ix86_binary_operator_ok (ROTATE, HImode, operands)" 12749 "@ 12750 rol{w}\t{%2, %0|%0, %2} 12751 rol{w}\t{%b2, %0|%0, %b2}" 12752 [(set_attr "type" "rotate") 12753 (set_attr "mode" "HI")]) 12754 12755(define_expand "rotlqi3" 12756 [(set (match_operand:QI 0 "nonimmediate_operand" "") 12757 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "") 12758 (match_operand:QI 2 "nonmemory_operand" ""))) 12759 (clobber (reg:CC FLAGS_REG))] 12760 "TARGET_QIMODE_MATH" 12761 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;") 12762 12763(define_insn "*rotlqi3_1_one_bit_slp" 12764 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm")) 12765 (rotate:QI (match_dup 0) 12766 (match_operand:QI 1 "const1_operand" ""))) 12767 (clobber (reg:CC FLAGS_REG))] 12768 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 12769 && (TARGET_SHIFT1 || optimize_size)" 12770 "rol{b}\t%0" 12771 [(set_attr "type" "rotate1") 12772 (set (attr "length") 12773 (if_then_else (match_operand 0 "register_operand" "") 12774 (const_string "2") 12775 (const_string "*")))]) 12776 12777(define_insn "*rotlqi3_1_one_bit" 12778 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 12779 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12780 (match_operand:QI 2 "const1_operand" ""))) 12781 (clobber (reg:CC FLAGS_REG))] 12782 "ix86_binary_operator_ok (ROTATE, QImode, operands) 12783 && (TARGET_SHIFT1 || optimize_size)" 12784 "rol{b}\t%0" 12785 [(set_attr "type" "rotate") 12786 (set (attr "length") 12787 (if_then_else (match_operand 0 "register_operand" "") 12788 (const_string "2") 12789 (const_string "*")))]) 12790 12791(define_insn "*rotlqi3_1_slp" 12792 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm")) 12793 (rotate:QI (match_dup 0) 12794 (match_operand:QI 1 "nonmemory_operand" "I,c"))) 12795 (clobber (reg:CC FLAGS_REG))] 12796 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 12797 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 12798 "@ 12799 rol{b}\t{%1, %0|%0, %1} 12800 rol{b}\t{%b1, %0|%0, %b1}" 12801 [(set_attr "type" "rotate1") 12802 (set_attr "mode" "QI")]) 12803 12804(define_insn "*rotlqi3_1" 12805 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm") 12806 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 12807 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12808 (clobber (reg:CC FLAGS_REG))] 12809 "ix86_binary_operator_ok (ROTATE, QImode, operands)" 12810 "@ 12811 rol{b}\t{%2, %0|%0, %2} 12812 rol{b}\t{%b2, %0|%0, %b2}" 12813 [(set_attr "type" "rotate") 12814 (set_attr "mode" "QI")]) 12815 12816(define_expand "rotrdi3" 12817 [(set (match_operand:DI 0 "shiftdi_operand" "") 12818 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "") 12819 (match_operand:QI 2 "nonmemory_operand" ""))) 12820 (clobber (reg:CC FLAGS_REG))] 12821 "" 12822{ 12823 if (TARGET_64BIT) 12824 { 12825 ix86_expand_binary_operator (ROTATERT, DImode, operands); 12826 DONE; 12827 } 12828 if (!const_1_to_31_operand (operands[2], VOIDmode)) 12829 FAIL; 12830 emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2])); 12831 DONE; 12832}) 12833 12834;; Implement rotation using two double-precision shift instructions 12835;; and a scratch register. 12836(define_insn_and_split "ix86_rotrdi3" 12837 [(set (match_operand:DI 0 "register_operand" "=r") 12838 (rotatert:DI (match_operand:DI 1 "register_operand" "0") 12839 (match_operand:QI 2 "const_1_to_31_operand" "I"))) 12840 (clobber (reg:CC FLAGS_REG)) 12841 (clobber (match_scratch:SI 3 "=&r"))] 12842 "!TARGET_64BIT" 12843 "" 12844 "&& reload_completed" 12845 [(set (match_dup 3) (match_dup 4)) 12846 (parallel 12847 [(set (match_dup 4) 12848 (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2)) 12849 (ashift:SI (match_dup 5) 12850 (minus:QI (const_int 32) (match_dup 2))))) 12851 (clobber (reg:CC FLAGS_REG))]) 12852 (parallel 12853 [(set (match_dup 5) 12854 (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2)) 12855 (ashift:SI (match_dup 3) 12856 (minus:QI (const_int 32) (match_dup 2))))) 12857 (clobber (reg:CC FLAGS_REG))])] 12858 "split_di (operands, 1, operands + 4, operands + 5);") 12859 12860(define_insn "*rotrdi3_1_one_bit_rex64" 12861 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm") 12862 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0") 12863 (match_operand:QI 2 "const1_operand" ""))) 12864 (clobber (reg:CC FLAGS_REG))] 12865 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands) 12866 && (TARGET_SHIFT1 || optimize_size)" 12867 "ror{q}\t%0" 12868 [(set_attr "type" "rotate") 12869 (set (attr "length") 12870 (if_then_else (match_operand:DI 0 "register_operand" "") 12871 (const_string "2") 12872 (const_string "*")))]) 12873 12874(define_insn "*rotrdi3_1_rex64" 12875 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm") 12876 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0") 12877 (match_operand:QI 2 "nonmemory_operand" "J,c"))) 12878 (clobber (reg:CC FLAGS_REG))] 12879 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)" 12880 "@ 12881 ror{q}\t{%2, %0|%0, %2} 12882 ror{q}\t{%b2, %0|%0, %b2}" 12883 [(set_attr "type" "rotate") 12884 (set_attr "mode" "DI")]) 12885 12886(define_expand "rotrsi3" 12887 [(set (match_operand:SI 0 "nonimmediate_operand" "") 12888 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "") 12889 (match_operand:QI 2 "nonmemory_operand" ""))) 12890 (clobber (reg:CC FLAGS_REG))] 12891 "" 12892 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;") 12893 12894(define_insn "*rotrsi3_1_one_bit" 12895 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm") 12896 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0") 12897 (match_operand:QI 2 "const1_operand" ""))) 12898 (clobber (reg:CC FLAGS_REG))] 12899 "ix86_binary_operator_ok (ROTATERT, SImode, operands) 12900 && (TARGET_SHIFT1 || optimize_size)" 12901 "ror{l}\t%0" 12902 [(set_attr "type" "rotate") 12903 (set (attr "length") 12904 (if_then_else (match_operand:SI 0 "register_operand" "") 12905 (const_string "2") 12906 (const_string "*")))]) 12907 12908(define_insn "*rotrsi3_1_one_bit_zext" 12909 [(set (match_operand:DI 0 "register_operand" "=r") 12910 (zero_extend:DI 12911 (rotatert:SI (match_operand:SI 1 "register_operand" "0") 12912 (match_operand:QI 2 "const1_operand" "")))) 12913 (clobber (reg:CC FLAGS_REG))] 12914 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands) 12915 && (TARGET_SHIFT1 || optimize_size)" 12916 "ror{l}\t%k0" 12917 [(set_attr "type" "rotate") 12918 (set (attr "length") 12919 (if_then_else (match_operand:SI 0 "register_operand" "") 12920 (const_string "2") 12921 (const_string "*")))]) 12922 12923(define_insn "*rotrsi3_1" 12924 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm") 12925 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0") 12926 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12927 (clobber (reg:CC FLAGS_REG))] 12928 "ix86_binary_operator_ok (ROTATERT, SImode, operands)" 12929 "@ 12930 ror{l}\t{%2, %0|%0, %2} 12931 ror{l}\t{%b2, %0|%0, %b2}" 12932 [(set_attr "type" "rotate") 12933 (set_attr "mode" "SI")]) 12934 12935(define_insn "*rotrsi3_1_zext" 12936 [(set (match_operand:DI 0 "register_operand" "=r,r") 12937 (zero_extend:DI 12938 (rotatert:SI (match_operand:SI 1 "register_operand" "0,0") 12939 (match_operand:QI 2 "nonmemory_operand" "I,c")))) 12940 (clobber (reg:CC FLAGS_REG))] 12941 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)" 12942 "@ 12943 ror{l}\t{%2, %k0|%k0, %2} 12944 ror{l}\t{%b2, %k0|%k0, %b2}" 12945 [(set_attr "type" "rotate") 12946 (set_attr "mode" "SI")]) 12947 12948(define_expand "rotrhi3" 12949 [(set (match_operand:HI 0 "nonimmediate_operand" "") 12950 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "") 12951 (match_operand:QI 2 "nonmemory_operand" ""))) 12952 (clobber (reg:CC FLAGS_REG))] 12953 "TARGET_HIMODE_MATH" 12954 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;") 12955 12956(define_insn "*rotrhi3_one_bit" 12957 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm") 12958 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0") 12959 (match_operand:QI 2 "const1_operand" ""))) 12960 (clobber (reg:CC FLAGS_REG))] 12961 "ix86_binary_operator_ok (ROTATERT, HImode, operands) 12962 && (TARGET_SHIFT1 || optimize_size)" 12963 "ror{w}\t%0" 12964 [(set_attr "type" "rotate") 12965 (set (attr "length") 12966 (if_then_else (match_operand 0 "register_operand" "") 12967 (const_string "2") 12968 (const_string "*")))]) 12969 12970(define_insn "*rotrhi3" 12971 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm") 12972 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0") 12973 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 12974 (clobber (reg:CC FLAGS_REG))] 12975 "ix86_binary_operator_ok (ROTATERT, HImode, operands)" 12976 "@ 12977 ror{w}\t{%2, %0|%0, %2} 12978 ror{w}\t{%b2, %0|%0, %b2}" 12979 [(set_attr "type" "rotate") 12980 (set_attr "mode" "HI")]) 12981 12982(define_expand "rotrqi3" 12983 [(set (match_operand:QI 0 "nonimmediate_operand" "") 12984 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "") 12985 (match_operand:QI 2 "nonmemory_operand" ""))) 12986 (clobber (reg:CC FLAGS_REG))] 12987 "TARGET_QIMODE_MATH" 12988 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;") 12989 12990(define_insn "*rotrqi3_1_one_bit" 12991 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 12992 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0") 12993 (match_operand:QI 2 "const1_operand" ""))) 12994 (clobber (reg:CC FLAGS_REG))] 12995 "ix86_binary_operator_ok (ROTATERT, QImode, operands) 12996 && (TARGET_SHIFT1 || optimize_size)" 12997 "ror{b}\t%0" 12998 [(set_attr "type" "rotate") 12999 (set (attr "length") 13000 (if_then_else (match_operand 0 "register_operand" "") 13001 (const_string "2") 13002 (const_string "*")))]) 13003 13004(define_insn "*rotrqi3_1_one_bit_slp" 13005 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm")) 13006 (rotatert:QI (match_dup 0) 13007 (match_operand:QI 1 "const1_operand" ""))) 13008 (clobber (reg:CC FLAGS_REG))] 13009 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 13010 && (TARGET_SHIFT1 || optimize_size)" 13011 "ror{b}\t%0" 13012 [(set_attr "type" "rotate1") 13013 (set (attr "length") 13014 (if_then_else (match_operand 0 "register_operand" "") 13015 (const_string "2") 13016 (const_string "*")))]) 13017 13018(define_insn "*rotrqi3_1" 13019 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm") 13020 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0") 13021 (match_operand:QI 2 "nonmemory_operand" "I,c"))) 13022 (clobber (reg:CC FLAGS_REG))] 13023 "ix86_binary_operator_ok (ROTATERT, QImode, operands)" 13024 "@ 13025 ror{b}\t{%2, %0|%0, %2} 13026 ror{b}\t{%b2, %0|%0, %b2}" 13027 [(set_attr "type" "rotate") 13028 (set_attr "mode" "QI")]) 13029 13030(define_insn "*rotrqi3_1_slp" 13031 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm")) 13032 (rotatert:QI (match_dup 0) 13033 (match_operand:QI 1 "nonmemory_operand" "I,c"))) 13034 (clobber (reg:CC FLAGS_REG))] 13035 "(! TARGET_PARTIAL_REG_STALL || optimize_size) 13036 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)" 13037 "@ 13038 ror{b}\t{%1, %0|%0, %1} 13039 ror{b}\t{%b1, %0|%0, %b1}" 13040 [(set_attr "type" "rotate1") 13041 (set_attr "mode" "QI")]) 13042 13043;; Bit set / bit test instructions 13044 13045(define_expand "extv" 13046 [(set (match_operand:SI 0 "register_operand" "") 13047 (sign_extract:SI (match_operand:SI 1 "register_operand" "") 13048 (match_operand:SI 2 "const8_operand" "") 13049 (match_operand:SI 3 "const8_operand" "")))] 13050 "" 13051{ 13052 /* Handle extractions from %ah et al. */ 13053 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8) 13054 FAIL; 13055 13056 /* From mips.md: extract_bit_field doesn't verify that our source 13057 matches the predicate, so check it again here. */ 13058 if (! ext_register_operand (operands[1], VOIDmode)) 13059 FAIL; 13060}) 13061 13062(define_expand "extzv" 13063 [(set (match_operand:SI 0 "register_operand" "") 13064 (zero_extract:SI (match_operand 1 "ext_register_operand" "") 13065 (match_operand:SI 2 "const8_operand" "") 13066 (match_operand:SI 3 "const8_operand" "")))] 13067 "" 13068{ 13069 /* Handle extractions from %ah et al. */ 13070 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8) 13071 FAIL; 13072 13073 /* From mips.md: extract_bit_field doesn't verify that our source 13074 matches the predicate, so check it again here. */ 13075 if (! ext_register_operand (operands[1], VOIDmode)) 13076 FAIL; 13077}) 13078 13079(define_expand "insv" 13080 [(set (zero_extract (match_operand 0 "ext_register_operand" "") 13081 (match_operand 1 "const8_operand" "") 13082 (match_operand 2 "const8_operand" "")) 13083 (match_operand 3 "register_operand" ""))] 13084 "" 13085{ 13086 /* Handle insertions to %ah et al. */ 13087 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8) 13088 FAIL; 13089 13090 /* From mips.md: insert_bit_field doesn't verify that our source 13091 matches the predicate, so check it again here. */ 13092 if (! ext_register_operand (operands[0], VOIDmode)) 13093 FAIL; 13094 13095 if (TARGET_64BIT) 13096 emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3])); 13097 else 13098 emit_insn (gen_movsi_insv_1 (operands[0], operands[3])); 13099 13100 DONE; 13101}) 13102 13103;; %%% bts, btr, btc, bt. 13104;; In general these instructions are *slow* when applied to memory, 13105;; since they enforce atomic operation. When applied to registers, 13106;; it depends on the cpu implementation. They're never faster than 13107;; the corresponding and/ior/xor operations, so with 32-bit there's 13108;; no point. But in 64-bit, we can't hold the relevant immediates 13109;; within the instruction itself, so operating on bits in the high 13110;; 32-bits of a register becomes easier. 13111;; 13112;; These are slow on Nocona, but fast on Athlon64. We do require the use 13113;; of btrq and btcq for corner cases of post-reload expansion of absdf and 13114;; negdf respectively, so they can never be disabled entirely. 13115 13116(define_insn "*btsq" 13117 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r") 13118 (const_int 1) 13119 (match_operand:DI 1 "const_0_to_63_operand" "")) 13120 (const_int 1)) 13121 (clobber (reg:CC FLAGS_REG))] 13122 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)" 13123 "bts{q} %1,%0" 13124 [(set_attr "type" "alu1")]) 13125 13126(define_insn "*btrq" 13127 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r") 13128 (const_int 1) 13129 (match_operand:DI 1 "const_0_to_63_operand" "")) 13130 (const_int 0)) 13131 (clobber (reg:CC FLAGS_REG))] 13132 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)" 13133 "btr{q} %1,%0" 13134 [(set_attr "type" "alu1")]) 13135 13136(define_insn "*btcq" 13137 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r") 13138 (const_int 1) 13139 (match_operand:DI 1 "const_0_to_63_operand" "")) 13140 (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1)))) 13141 (clobber (reg:CC FLAGS_REG))] 13142 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)" 13143 "btc{q} %1,%0" 13144 [(set_attr "type" "alu1")]) 13145 13146;; Allow Nocona to avoid these instructions if a register is available. 13147 13148(define_peephole2 13149 [(match_scratch:DI 2 "r") 13150 (parallel [(set (zero_extract:DI 13151 (match_operand:DI 0 "register_operand" "") 13152 (const_int 1) 13153 (match_operand:DI 1 "const_0_to_63_operand" "")) 13154 (const_int 1)) 13155 (clobber (reg:CC FLAGS_REG))])] 13156 "TARGET_64BIT && !TARGET_USE_BT" 13157 [(const_int 0)] 13158{ 13159 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo; 13160 rtx op1; 13161 13162 if (HOST_BITS_PER_WIDE_INT >= 64) 13163 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13164 else if (i < HOST_BITS_PER_WIDE_INT) 13165 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13166 else 13167 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT); 13168 13169 op1 = immed_double_const (lo, hi, DImode); 13170 if (i >= 31) 13171 { 13172 emit_move_insn (operands[2], op1); 13173 op1 = operands[2]; 13174 } 13175 13176 emit_insn (gen_iordi3 (operands[0], operands[0], op1)); 13177 DONE; 13178}) 13179 13180(define_peephole2 13181 [(match_scratch:DI 2 "r") 13182 (parallel [(set (zero_extract:DI 13183 (match_operand:DI 0 "register_operand" "") 13184 (const_int 1) 13185 (match_operand:DI 1 "const_0_to_63_operand" "")) 13186 (const_int 0)) 13187 (clobber (reg:CC FLAGS_REG))])] 13188 "TARGET_64BIT && !TARGET_USE_BT" 13189 [(const_int 0)] 13190{ 13191 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo; 13192 rtx op1; 13193 13194 if (HOST_BITS_PER_WIDE_INT >= 64) 13195 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13196 else if (i < HOST_BITS_PER_WIDE_INT) 13197 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13198 else 13199 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT); 13200 13201 op1 = immed_double_const (~lo, ~hi, DImode); 13202 if (i >= 32) 13203 { 13204 emit_move_insn (operands[2], op1); 13205 op1 = operands[2]; 13206 } 13207 13208 emit_insn (gen_anddi3 (operands[0], operands[0], op1)); 13209 DONE; 13210}) 13211 13212(define_peephole2 13213 [(match_scratch:DI 2 "r") 13214 (parallel [(set (zero_extract:DI 13215 (match_operand:DI 0 "register_operand" "") 13216 (const_int 1) 13217 (match_operand:DI 1 "const_0_to_63_operand" "")) 13218 (not:DI (zero_extract:DI 13219 (match_dup 0) (const_int 1) (match_dup 1)))) 13220 (clobber (reg:CC FLAGS_REG))])] 13221 "TARGET_64BIT && !TARGET_USE_BT" 13222 [(const_int 0)] 13223{ 13224 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo; 13225 rtx op1; 13226 13227 if (HOST_BITS_PER_WIDE_INT >= 64) 13228 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13229 else if (i < HOST_BITS_PER_WIDE_INT) 13230 lo = (HOST_WIDE_INT)1 << i, hi = 0; 13231 else 13232 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT); 13233 13234 op1 = immed_double_const (lo, hi, DImode); 13235 if (i >= 31) 13236 { 13237 emit_move_insn (operands[2], op1); 13238 op1 = operands[2]; 13239 } 13240 13241 emit_insn (gen_xordi3 (operands[0], operands[0], op1)); 13242 DONE; 13243}) 13244 13245;; Store-flag instructions. 13246 13247;; For all sCOND expanders, also expand the compare or test insn that 13248;; generates cc0. Generate an equality comparison if `seq' or `sne'. 13249 13250;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way 13251;; to avoid partial register stalls. Otherwise do things the setcc+movzx 13252;; way, which can later delete the movzx if only QImode is needed. 13253 13254(define_expand "seq" 13255 [(set (match_operand:QI 0 "register_operand" "") 13256 (eq:QI (reg:CC FLAGS_REG) (const_int 0)))] 13257 "" 13258 "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;") 13259 13260(define_expand "sne" 13261 [(set (match_operand:QI 0 "register_operand" "") 13262 (ne:QI (reg:CC FLAGS_REG) (const_int 0)))] 13263 "" 13264 "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;") 13265 13266(define_expand "sgt" 13267 [(set (match_operand:QI 0 "register_operand" "") 13268 (gt:QI (reg:CC FLAGS_REG) (const_int 0)))] 13269 "" 13270 "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;") 13271 13272(define_expand "sgtu" 13273 [(set (match_operand:QI 0 "register_operand" "") 13274 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))] 13275 "" 13276 "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;") 13277 13278(define_expand "slt" 13279 [(set (match_operand:QI 0 "register_operand" "") 13280 (lt:QI (reg:CC FLAGS_REG) (const_int 0)))] 13281 "" 13282 "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;") 13283 13284(define_expand "sltu" 13285 [(set (match_operand:QI 0 "register_operand" "") 13286 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))] 13287 "" 13288 "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;") 13289 13290(define_expand "sge" 13291 [(set (match_operand:QI 0 "register_operand" "") 13292 (ge:QI (reg:CC FLAGS_REG) (const_int 0)))] 13293 "" 13294 "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;") 13295 13296(define_expand "sgeu" 13297 [(set (match_operand:QI 0 "register_operand" "") 13298 (geu:QI (reg:CC FLAGS_REG) (const_int 0)))] 13299 "" 13300 "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;") 13301 13302(define_expand "sle" 13303 [(set (match_operand:QI 0 "register_operand" "") 13304 (le:QI (reg:CC FLAGS_REG) (const_int 0)))] 13305 "" 13306 "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;") 13307 13308(define_expand "sleu" 13309 [(set (match_operand:QI 0 "register_operand" "") 13310 (leu:QI (reg:CC FLAGS_REG) (const_int 0)))] 13311 "" 13312 "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;") 13313 13314(define_expand "sunordered" 13315 [(set (match_operand:QI 0 "register_operand" "") 13316 (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))] 13317 "TARGET_80387 || TARGET_SSE" 13318 "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;") 13319 13320(define_expand "sordered" 13321 [(set (match_operand:QI 0 "register_operand" "") 13322 (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))] 13323 "TARGET_80387" 13324 "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;") 13325 13326(define_expand "suneq" 13327 [(set (match_operand:QI 0 "register_operand" "") 13328 (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))] 13329 "TARGET_80387 || TARGET_SSE" 13330 "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;") 13331 13332(define_expand "sunge" 13333 [(set (match_operand:QI 0 "register_operand" "") 13334 (unge:QI (reg:CC FLAGS_REG) (const_int 0)))] 13335 "TARGET_80387 || TARGET_SSE" 13336 "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;") 13337 13338(define_expand "sungt" 13339 [(set (match_operand:QI 0 "register_operand" "") 13340 (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))] 13341 "TARGET_80387 || TARGET_SSE" 13342 "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;") 13343 13344(define_expand "sunle" 13345 [(set (match_operand:QI 0 "register_operand" "") 13346 (unle:QI (reg:CC FLAGS_REG) (const_int 0)))] 13347 "TARGET_80387 || TARGET_SSE" 13348 "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;") 13349 13350(define_expand "sunlt" 13351 [(set (match_operand:QI 0 "register_operand" "") 13352 (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))] 13353 "TARGET_80387 || TARGET_SSE" 13354 "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;") 13355 13356(define_expand "sltgt" 13357 [(set (match_operand:QI 0 "register_operand" "") 13358 (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))] 13359 "TARGET_80387 || TARGET_SSE" 13360 "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;") 13361 13362(define_insn "*setcc_1" 13363 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm") 13364 (match_operator:QI 1 "ix86_comparison_operator" 13365 [(reg FLAGS_REG) (const_int 0)]))] 13366 "" 13367 "set%C1\t%0" 13368 [(set_attr "type" "setcc") 13369 (set_attr "mode" "QI")]) 13370 13371(define_insn "*setcc_2" 13372 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm")) 13373 (match_operator:QI 1 "ix86_comparison_operator" 13374 [(reg FLAGS_REG) (const_int 0)]))] 13375 "" 13376 "set%C1\t%0" 13377 [(set_attr "type" "setcc") 13378 (set_attr "mode" "QI")]) 13379 13380;; In general it is not safe to assume too much about CCmode registers, 13381;; so simplify-rtx stops when it sees a second one. Under certain 13382;; conditions this is safe on x86, so help combine not create 13383;; 13384;; seta %al 13385;; testb %al, %al 13386;; sete %al 13387 13388(define_split 13389 [(set (match_operand:QI 0 "nonimmediate_operand" "") 13390 (ne:QI (match_operator 1 "ix86_comparison_operator" 13391 [(reg FLAGS_REG) (const_int 0)]) 13392 (const_int 0)))] 13393 "" 13394 [(set (match_dup 0) (match_dup 1))] 13395{ 13396 PUT_MODE (operands[1], QImode); 13397}) 13398 13399(define_split 13400 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "")) 13401 (ne:QI (match_operator 1 "ix86_comparison_operator" 13402 [(reg FLAGS_REG) (const_int 0)]) 13403 (const_int 0)))] 13404 "" 13405 [(set (match_dup 0) (match_dup 1))] 13406{ 13407 PUT_MODE (operands[1], QImode); 13408}) 13409 13410(define_split 13411 [(set (match_operand:QI 0 "nonimmediate_operand" "") 13412 (eq:QI (match_operator 1 "ix86_comparison_operator" 13413 [(reg FLAGS_REG) (const_int 0)]) 13414 (const_int 0)))] 13415 "" 13416 [(set (match_dup 0) (match_dup 1))] 13417{ 13418 rtx new_op1 = copy_rtx (operands[1]); 13419 operands[1] = new_op1; 13420 PUT_MODE (new_op1, QImode); 13421 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1), 13422 GET_MODE (XEXP (new_op1, 0)))); 13423 13424 /* Make sure that (a) the CCmode we have for the flags is strong 13425 enough for the reversed compare or (b) we have a valid FP compare. */ 13426 if (! ix86_comparison_operator (new_op1, VOIDmode)) 13427 FAIL; 13428}) 13429 13430(define_split 13431 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "")) 13432 (eq:QI (match_operator 1 "ix86_comparison_operator" 13433 [(reg FLAGS_REG) (const_int 0)]) 13434 (const_int 0)))] 13435 "" 13436 [(set (match_dup 0) (match_dup 1))] 13437{ 13438 rtx new_op1 = copy_rtx (operands[1]); 13439 operands[1] = new_op1; 13440 PUT_MODE (new_op1, QImode); 13441 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1), 13442 GET_MODE (XEXP (new_op1, 0)))); 13443 13444 /* Make sure that (a) the CCmode we have for the flags is strong 13445 enough for the reversed compare or (b) we have a valid FP compare. */ 13446 if (! ix86_comparison_operator (new_op1, VOIDmode)) 13447 FAIL; 13448}) 13449 13450;; The SSE store flag instructions saves 0 or 0xffffffff to the result. 13451;; subsequent logical operations are used to imitate conditional moves. 13452;; 0xffffffff is NaN, but not in normalized form, so we can't represent 13453;; it directly. 13454 13455(define_insn "*sse_setccsf" 13456 [(set (match_operand:SF 0 "register_operand" "=x") 13457 (match_operator:SF 1 "sse_comparison_operator" 13458 [(match_operand:SF 2 "register_operand" "0") 13459 (match_operand:SF 3 "nonimmediate_operand" "xm")]))] 13460 "TARGET_SSE" 13461 "cmp%D1ss\t{%3, %0|%0, %3}" 13462 [(set_attr "type" "ssecmp") 13463 (set_attr "mode" "SF")]) 13464 13465(define_insn "*sse_setccdf" 13466 [(set (match_operand:DF 0 "register_operand" "=Y") 13467 (match_operator:DF 1 "sse_comparison_operator" 13468 [(match_operand:DF 2 "register_operand" "0") 13469 (match_operand:DF 3 "nonimmediate_operand" "Ym")]))] 13470 "TARGET_SSE2" 13471 "cmp%D1sd\t{%3, %0|%0, %3}" 13472 [(set_attr "type" "ssecmp") 13473 (set_attr "mode" "DF")]) 13474 13475;; Basic conditional jump instructions. 13476;; We ignore the overflow flag for signed branch instructions. 13477 13478;; For all bCOND expanders, also expand the compare or test insn that 13479;; generates reg FLAGS_REG. Generate an equality comparison if `beq' or `bne'. 13480 13481(define_expand "beq" 13482 [(set (pc) 13483 (if_then_else (match_dup 1) 13484 (label_ref (match_operand 0 "" "")) 13485 (pc)))] 13486 "" 13487 "ix86_expand_branch (EQ, operands[0]); DONE;") 13488 13489(define_expand "bne" 13490 [(set (pc) 13491 (if_then_else (match_dup 1) 13492 (label_ref (match_operand 0 "" "")) 13493 (pc)))] 13494 "" 13495 "ix86_expand_branch (NE, operands[0]); DONE;") 13496 13497(define_expand "bgt" 13498 [(set (pc) 13499 (if_then_else (match_dup 1) 13500 (label_ref (match_operand 0 "" "")) 13501 (pc)))] 13502 "" 13503 "ix86_expand_branch (GT, operands[0]); DONE;") 13504 13505(define_expand "bgtu" 13506 [(set (pc) 13507 (if_then_else (match_dup 1) 13508 (label_ref (match_operand 0 "" "")) 13509 (pc)))] 13510 "" 13511 "ix86_expand_branch (GTU, operands[0]); DONE;") 13512 13513(define_expand "blt" 13514 [(set (pc) 13515 (if_then_else (match_dup 1) 13516 (label_ref (match_operand 0 "" "")) 13517 (pc)))] 13518 "" 13519 "ix86_expand_branch (LT, operands[0]); DONE;") 13520 13521(define_expand "bltu" 13522 [(set (pc) 13523 (if_then_else (match_dup 1) 13524 (label_ref (match_operand 0 "" "")) 13525 (pc)))] 13526 "" 13527 "ix86_expand_branch (LTU, operands[0]); DONE;") 13528 13529(define_expand "bge" 13530 [(set (pc) 13531 (if_then_else (match_dup 1) 13532 (label_ref (match_operand 0 "" "")) 13533 (pc)))] 13534 "" 13535 "ix86_expand_branch (GE, operands[0]); DONE;") 13536 13537(define_expand "bgeu" 13538 [(set (pc) 13539 (if_then_else (match_dup 1) 13540 (label_ref (match_operand 0 "" "")) 13541 (pc)))] 13542 "" 13543 "ix86_expand_branch (GEU, operands[0]); DONE;") 13544 13545(define_expand "ble" 13546 [(set (pc) 13547 (if_then_else (match_dup 1) 13548 (label_ref (match_operand 0 "" "")) 13549 (pc)))] 13550 "" 13551 "ix86_expand_branch (LE, operands[0]); DONE;") 13552 13553(define_expand "bleu" 13554 [(set (pc) 13555 (if_then_else (match_dup 1) 13556 (label_ref (match_operand 0 "" "")) 13557 (pc)))] 13558 "" 13559 "ix86_expand_branch (LEU, operands[0]); DONE;") 13560 13561(define_expand "bunordered" 13562 [(set (pc) 13563 (if_then_else (match_dup 1) 13564 (label_ref (match_operand 0 "" "")) 13565 (pc)))] 13566 "TARGET_80387 || TARGET_SSE_MATH" 13567 "ix86_expand_branch (UNORDERED, operands[0]); DONE;") 13568 13569(define_expand "bordered" 13570 [(set (pc) 13571 (if_then_else (match_dup 1) 13572 (label_ref (match_operand 0 "" "")) 13573 (pc)))] 13574 "TARGET_80387 || TARGET_SSE_MATH" 13575 "ix86_expand_branch (ORDERED, operands[0]); DONE;") 13576 13577(define_expand "buneq" 13578 [(set (pc) 13579 (if_then_else (match_dup 1) 13580 (label_ref (match_operand 0 "" "")) 13581 (pc)))] 13582 "TARGET_80387 || TARGET_SSE_MATH" 13583 "ix86_expand_branch (UNEQ, operands[0]); DONE;") 13584 13585(define_expand "bunge" 13586 [(set (pc) 13587 (if_then_else (match_dup 1) 13588 (label_ref (match_operand 0 "" "")) 13589 (pc)))] 13590 "TARGET_80387 || TARGET_SSE_MATH" 13591 "ix86_expand_branch (UNGE, operands[0]); DONE;") 13592 13593(define_expand "bungt" 13594 [(set (pc) 13595 (if_then_else (match_dup 1) 13596 (label_ref (match_operand 0 "" "")) 13597 (pc)))] 13598 "TARGET_80387 || TARGET_SSE_MATH" 13599 "ix86_expand_branch (UNGT, operands[0]); DONE;") 13600 13601(define_expand "bunle" 13602 [(set (pc) 13603 (if_then_else (match_dup 1) 13604 (label_ref (match_operand 0 "" "")) 13605 (pc)))] 13606 "TARGET_80387 || TARGET_SSE_MATH" 13607 "ix86_expand_branch (UNLE, operands[0]); DONE;") 13608 13609(define_expand "bunlt" 13610 [(set (pc) 13611 (if_then_else (match_dup 1) 13612 (label_ref (match_operand 0 "" "")) 13613 (pc)))] 13614 "TARGET_80387 || TARGET_SSE_MATH" 13615 "ix86_expand_branch (UNLT, operands[0]); DONE;") 13616 13617(define_expand "bltgt" 13618 [(set (pc) 13619 (if_then_else (match_dup 1) 13620 (label_ref (match_operand 0 "" "")) 13621 (pc)))] 13622 "TARGET_80387 || TARGET_SSE_MATH" 13623 "ix86_expand_branch (LTGT, operands[0]); DONE;") 13624 13625(define_insn "*jcc_1" 13626 [(set (pc) 13627 (if_then_else (match_operator 1 "ix86_comparison_operator" 13628 [(reg FLAGS_REG) (const_int 0)]) 13629 (label_ref (match_operand 0 "" "")) 13630 (pc)))] 13631 "" 13632 "%+j%C1\t%l0" 13633 [(set_attr "type" "ibr") 13634 (set_attr "modrm" "0") 13635 (set (attr "length") 13636 (if_then_else (and (ge (minus (match_dup 0) (pc)) 13637 (const_int -126)) 13638 (lt (minus (match_dup 0) (pc)) 13639 (const_int 128))) 13640 (const_int 2) 13641 (const_int 6)))]) 13642 13643(define_insn "*jcc_2" 13644 [(set (pc) 13645 (if_then_else (match_operator 1 "ix86_comparison_operator" 13646 [(reg FLAGS_REG) (const_int 0)]) 13647 (pc) 13648 (label_ref (match_operand 0 "" ""))))] 13649 "" 13650 "%+j%c1\t%l0" 13651 [(set_attr "type" "ibr") 13652 (set_attr "modrm" "0") 13653 (set (attr "length") 13654 (if_then_else (and (ge (minus (match_dup 0) (pc)) 13655 (const_int -126)) 13656 (lt (minus (match_dup 0) (pc)) 13657 (const_int 128))) 13658 (const_int 2) 13659 (const_int 6)))]) 13660 13661;; In general it is not safe to assume too much about CCmode registers, 13662;; so simplify-rtx stops when it sees a second one. Under certain 13663;; conditions this is safe on x86, so help combine not create 13664;; 13665;; seta %al 13666;; testb %al, %al 13667;; je Lfoo 13668 13669(define_split 13670 [(set (pc) 13671 (if_then_else (ne (match_operator 0 "ix86_comparison_operator" 13672 [(reg FLAGS_REG) (const_int 0)]) 13673 (const_int 0)) 13674 (label_ref (match_operand 1 "" "")) 13675 (pc)))] 13676 "" 13677 [(set (pc) 13678 (if_then_else (match_dup 0) 13679 (label_ref (match_dup 1)) 13680 (pc)))] 13681{ 13682 PUT_MODE (operands[0], VOIDmode); 13683}) 13684 13685(define_split 13686 [(set (pc) 13687 (if_then_else (eq (match_operator 0 "ix86_comparison_operator" 13688 [(reg FLAGS_REG) (const_int 0)]) 13689 (const_int 0)) 13690 (label_ref (match_operand 1 "" "")) 13691 (pc)))] 13692 "" 13693 [(set (pc) 13694 (if_then_else (match_dup 0) 13695 (label_ref (match_dup 1)) 13696 (pc)))] 13697{ 13698 rtx new_op0 = copy_rtx (operands[0]); 13699 operands[0] = new_op0; 13700 PUT_MODE (new_op0, VOIDmode); 13701 PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0), 13702 GET_MODE (XEXP (new_op0, 0)))); 13703 13704 /* Make sure that (a) the CCmode we have for the flags is strong 13705 enough for the reversed compare or (b) we have a valid FP compare. */ 13706 if (! ix86_comparison_operator (new_op0, VOIDmode)) 13707 FAIL; 13708}) 13709 13710;; Define combination compare-and-branch fp compare instructions to use 13711;; during early optimization. Splitting the operation apart early makes 13712;; for bad code when we want to reverse the operation. 13713 13714(define_insn "*fp_jcc_1_mixed" 13715 [(set (pc) 13716 (if_then_else (match_operator 0 "comparison_operator" 13717 [(match_operand 1 "register_operand" "f,x") 13718 (match_operand 2 "nonimmediate_operand" "f,xm")]) 13719 (label_ref (match_operand 3 "" "")) 13720 (pc))) 13721 (clobber (reg:CCFP FPSR_REG)) 13722 (clobber (reg:CCFP FLAGS_REG))] 13723 "TARGET_MIX_SSE_I387 13724 && SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 13725 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13726 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13727 "#") 13728 13729(define_insn "*fp_jcc_1_sse" 13730 [(set (pc) 13731 (if_then_else (match_operator 0 "comparison_operator" 13732 [(match_operand 1 "register_operand" "x") 13733 (match_operand 2 "nonimmediate_operand" "xm")]) 13734 (label_ref (match_operand 3 "" "")) 13735 (pc))) 13736 (clobber (reg:CCFP FPSR_REG)) 13737 (clobber (reg:CCFP FLAGS_REG))] 13738 "TARGET_SSE_MATH 13739 && SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 13740 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13741 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13742 "#") 13743 13744(define_insn "*fp_jcc_1_387" 13745 [(set (pc) 13746 (if_then_else (match_operator 0 "comparison_operator" 13747 [(match_operand 1 "register_operand" "f") 13748 (match_operand 2 "register_operand" "f")]) 13749 (label_ref (match_operand 3 "" "")) 13750 (pc))) 13751 (clobber (reg:CCFP FPSR_REG)) 13752 (clobber (reg:CCFP FLAGS_REG))] 13753 "TARGET_CMOVE && TARGET_80387 13754 && FLOAT_MODE_P (GET_MODE (operands[1])) 13755 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13756 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13757 "#") 13758 13759(define_insn "*fp_jcc_2_mixed" 13760 [(set (pc) 13761 (if_then_else (match_operator 0 "comparison_operator" 13762 [(match_operand 1 "register_operand" "f,x") 13763 (match_operand 2 "nonimmediate_operand" "f,xm")]) 13764 (pc) 13765 (label_ref (match_operand 3 "" "")))) 13766 (clobber (reg:CCFP FPSR_REG)) 13767 (clobber (reg:CCFP FLAGS_REG))] 13768 "TARGET_MIX_SSE_I387 13769 && SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 13770 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13771 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13772 "#") 13773 13774(define_insn "*fp_jcc_2_sse" 13775 [(set (pc) 13776 (if_then_else (match_operator 0 "comparison_operator" 13777 [(match_operand 1 "register_operand" "x") 13778 (match_operand 2 "nonimmediate_operand" "xm")]) 13779 (pc) 13780 (label_ref (match_operand 3 "" "")))) 13781 (clobber (reg:CCFP FPSR_REG)) 13782 (clobber (reg:CCFP FLAGS_REG))] 13783 "TARGET_SSE_MATH 13784 && SSE_FLOAT_MODE_P (GET_MODE (operands[1])) 13785 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13786 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13787 "#") 13788 13789(define_insn "*fp_jcc_2_387" 13790 [(set (pc) 13791 (if_then_else (match_operator 0 "comparison_operator" 13792 [(match_operand 1 "register_operand" "f") 13793 (match_operand 2 "register_operand" "f")]) 13794 (pc) 13795 (label_ref (match_operand 3 "" "")))) 13796 (clobber (reg:CCFP FPSR_REG)) 13797 (clobber (reg:CCFP FLAGS_REG))] 13798 "TARGET_CMOVE && TARGET_80387 13799 && FLOAT_MODE_P (GET_MODE (operands[1])) 13800 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13801 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13802 "#") 13803 13804(define_insn "*fp_jcc_3_387" 13805 [(set (pc) 13806 (if_then_else (match_operator 0 "comparison_operator" 13807 [(match_operand 1 "register_operand" "f") 13808 (match_operand 2 "nonimmediate_operand" "fm")]) 13809 (label_ref (match_operand 3 "" "")) 13810 (pc))) 13811 (clobber (reg:CCFP FPSR_REG)) 13812 (clobber (reg:CCFP FLAGS_REG)) 13813 (clobber (match_scratch:HI 4 "=a"))] 13814 "TARGET_80387 13815 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode) 13816 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13817 && !ix86_use_fcomi_compare (GET_CODE (operands[0])) 13818 && SELECT_CC_MODE (GET_CODE (operands[0]), 13819 operands[1], operands[2]) == CCFPmode 13820 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13821 "#") 13822 13823(define_insn "*fp_jcc_4_387" 13824 [(set (pc) 13825 (if_then_else (match_operator 0 "comparison_operator" 13826 [(match_operand 1 "register_operand" "f") 13827 (match_operand 2 "nonimmediate_operand" "fm")]) 13828 (pc) 13829 (label_ref (match_operand 3 "" "")))) 13830 (clobber (reg:CCFP FPSR_REG)) 13831 (clobber (reg:CCFP FLAGS_REG)) 13832 (clobber (match_scratch:HI 4 "=a"))] 13833 "TARGET_80387 13834 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode) 13835 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13836 && !ix86_use_fcomi_compare (GET_CODE (operands[0])) 13837 && SELECT_CC_MODE (GET_CODE (operands[0]), 13838 operands[1], operands[2]) == CCFPmode 13839 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13840 "#") 13841 13842(define_insn "*fp_jcc_5_387" 13843 [(set (pc) 13844 (if_then_else (match_operator 0 "comparison_operator" 13845 [(match_operand 1 "register_operand" "f") 13846 (match_operand 2 "register_operand" "f")]) 13847 (label_ref (match_operand 3 "" "")) 13848 (pc))) 13849 (clobber (reg:CCFP FPSR_REG)) 13850 (clobber (reg:CCFP FLAGS_REG)) 13851 (clobber (match_scratch:HI 4 "=a"))] 13852 "TARGET_80387 13853 && FLOAT_MODE_P (GET_MODE (operands[1])) 13854 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13855 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13856 "#") 13857 13858(define_insn "*fp_jcc_6_387" 13859 [(set (pc) 13860 (if_then_else (match_operator 0 "comparison_operator" 13861 [(match_operand 1 "register_operand" "f") 13862 (match_operand 2 "register_operand" "f")]) 13863 (pc) 13864 (label_ref (match_operand 3 "" "")))) 13865 (clobber (reg:CCFP FPSR_REG)) 13866 (clobber (reg:CCFP FLAGS_REG)) 13867 (clobber (match_scratch:HI 4 "=a"))] 13868 "TARGET_80387 13869 && FLOAT_MODE_P (GET_MODE (operands[1])) 13870 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13871 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13872 "#") 13873 13874(define_insn "*fp_jcc_7_387" 13875 [(set (pc) 13876 (if_then_else (match_operator 0 "comparison_operator" 13877 [(match_operand 1 "register_operand" "f") 13878 (match_operand 2 "const0_operand" "X")]) 13879 (label_ref (match_operand 3 "" "")) 13880 (pc))) 13881 (clobber (reg:CCFP FPSR_REG)) 13882 (clobber (reg:CCFP FLAGS_REG)) 13883 (clobber (match_scratch:HI 4 "=a"))] 13884 "TARGET_80387 13885 && FLOAT_MODE_P (GET_MODE (operands[1])) 13886 && GET_MODE (operands[1]) == GET_MODE (operands[2]) 13887 && !ix86_use_fcomi_compare (GET_CODE (operands[0])) 13888 && SELECT_CC_MODE (GET_CODE (operands[0]), 13889 operands[1], operands[2]) == CCFPmode 13890 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))" 13891 "#") 13892 13893;; The order of operands in *fp_jcc_8_387 is forced by combine in 13894;; simplify_comparison () function. Float operator is treated as RTX_OBJ 13895;; with a precedence over other operators and is always put in the first 13896;; place. Swap condition and operands to match ficom instruction. 13897 13898(define_insn "*fp_jcc_8<mode>_387" 13899 [(set (pc) 13900 (if_then_else (match_operator 0 "comparison_operator" 13901 [(match_operator 1 "float_operator" 13902 [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")]) 13903 (match_operand 3 "register_operand" "f,f")]) 13904 (label_ref (match_operand 4 "" "")) 13905 (pc))) 13906 (clobber (reg:CCFP FPSR_REG)) 13907 (clobber (reg:CCFP FLAGS_REG)) 13908 (clobber (match_scratch:HI 5 "=a,a"))] 13909 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP 13910 && FLOAT_MODE_P (GET_MODE (operands[3])) 13911 && GET_MODE (operands[1]) == GET_MODE (operands[3]) 13912 && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0]))) 13913 && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode 13914 && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))" 13915 "#") 13916 13917(define_split 13918 [(set (pc) 13919 (if_then_else (match_operator 0 "comparison_operator" 13920 [(match_operand 1 "register_operand" "") 13921 (match_operand 2 "nonimmediate_operand" "")]) 13922 (match_operand 3 "" "") 13923 (match_operand 4 "" ""))) 13924 (clobber (reg:CCFP FPSR_REG)) 13925 (clobber (reg:CCFP FLAGS_REG))] 13926 "reload_completed" 13927 [(const_int 0)] 13928{ 13929 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2], 13930 operands[3], operands[4], NULL_RTX, NULL_RTX); 13931 DONE; 13932}) 13933 13934(define_split 13935 [(set (pc) 13936 (if_then_else (match_operator 0 "comparison_operator" 13937 [(match_operand 1 "register_operand" "") 13938 (match_operand 2 "general_operand" "")]) 13939 (match_operand 3 "" "") 13940 (match_operand 4 "" ""))) 13941 (clobber (reg:CCFP FPSR_REG)) 13942 (clobber (reg:CCFP FLAGS_REG)) 13943 (clobber (match_scratch:HI 5 "=a"))] 13944 "reload_completed" 13945 [(const_int 0)] 13946{ 13947 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2], 13948 operands[3], operands[4], operands[5], NULL_RTX); 13949 DONE; 13950}) 13951 13952(define_split 13953 [(set (pc) 13954 (if_then_else (match_operator 0 "comparison_operator" 13955 [(match_operator 1 "float_operator" 13956 [(match_operand:X87MODEI12 2 "memory_operand" "")]) 13957 (match_operand 3 "register_operand" "")]) 13958 (match_operand 4 "" "") 13959 (match_operand 5 "" ""))) 13960 (clobber (reg:CCFP FPSR_REG)) 13961 (clobber (reg:CCFP FLAGS_REG)) 13962 (clobber (match_scratch:HI 6 "=a"))] 13963 "reload_completed" 13964 [(const_int 0)] 13965{ 13966 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]); 13967 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])), 13968 operands[3], operands[7], 13969 operands[4], operands[5], operands[6], NULL_RTX); 13970 DONE; 13971}) 13972 13973;; %%% Kill this when reload knows how to do it. 13974(define_split 13975 [(set (pc) 13976 (if_then_else (match_operator 0 "comparison_operator" 13977 [(match_operator 1 "float_operator" 13978 [(match_operand:X87MODEI12 2 "register_operand" "")]) 13979 (match_operand 3 "register_operand" "")]) 13980 (match_operand 4 "" "") 13981 (match_operand 5 "" ""))) 13982 (clobber (reg:CCFP FPSR_REG)) 13983 (clobber (reg:CCFP FLAGS_REG)) 13984 (clobber (match_scratch:HI 6 "=a"))] 13985 "reload_completed" 13986 [(const_int 0)] 13987{ 13988 operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]); 13989 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]); 13990 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])), 13991 operands[3], operands[7], 13992 operands[4], operands[5], operands[6], operands[2]); 13993 DONE; 13994}) 13995 13996;; Unconditional and other jump instructions 13997 13998(define_insn "jump" 13999 [(set (pc) 14000 (label_ref (match_operand 0 "" "")))] 14001 "" 14002 "jmp\t%l0" 14003 [(set_attr "type" "ibr") 14004 (set (attr "length") 14005 (if_then_else (and (ge (minus (match_dup 0) (pc)) 14006 (const_int -126)) 14007 (lt (minus (match_dup 0) (pc)) 14008 (const_int 128))) 14009 (const_int 2) 14010 (const_int 5))) 14011 (set_attr "modrm" "0")]) 14012 14013(define_expand "indirect_jump" 14014 [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))] 14015 "" 14016 "") 14017 14018(define_insn "*indirect_jump" 14019 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))] 14020 "!TARGET_64BIT" 14021 "jmp\t%A0" 14022 [(set_attr "type" "ibr") 14023 (set_attr "length_immediate" "0")]) 14024 14025(define_insn "*indirect_jump_rtx64" 14026 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))] 14027 "TARGET_64BIT" 14028 "jmp\t%A0" 14029 [(set_attr "type" "ibr") 14030 (set_attr "length_immediate" "0")]) 14031 14032(define_expand "tablejump" 14033 [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm")) 14034 (use (label_ref (match_operand 1 "" "")))])] 14035 "" 14036{ 14037 /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit) 14038 relative. Convert the relative address to an absolute address. */ 14039 if (flag_pic) 14040 { 14041 rtx op0, op1; 14042 enum rtx_code code; 14043 14044 if (TARGET_64BIT) 14045 { 14046 code = PLUS; 14047 op0 = operands[0]; 14048 op1 = gen_rtx_LABEL_REF (Pmode, operands[1]); 14049 } 14050 else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA) 14051 { 14052 code = PLUS; 14053 op0 = operands[0]; 14054 op1 = pic_offset_table_rtx; 14055 } 14056 else 14057 { 14058 code = MINUS; 14059 op0 = pic_offset_table_rtx; 14060 op1 = operands[0]; 14061 } 14062 14063 operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0, 14064 OPTAB_DIRECT); 14065 } 14066}) 14067 14068(define_insn "*tablejump_1" 14069 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm")) 14070 (use (label_ref (match_operand 1 "" "")))] 14071 "!TARGET_64BIT" 14072 "jmp\t%A0" 14073 [(set_attr "type" "ibr") 14074 (set_attr "length_immediate" "0")]) 14075 14076(define_insn "*tablejump_1_rtx64" 14077 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm")) 14078 (use (label_ref (match_operand 1 "" "")))] 14079 "TARGET_64BIT" 14080 "jmp\t%A0" 14081 [(set_attr "type" "ibr") 14082 (set_attr "length_immediate" "0")]) 14083 14084;; Convert setcc + movzbl to xor + setcc if operands don't overlap. 14085 14086(define_peephole2 14087 [(set (reg FLAGS_REG) (match_operand 0 "" "")) 14088 (set (match_operand:QI 1 "register_operand" "") 14089 (match_operator:QI 2 "ix86_comparison_operator" 14090 [(reg FLAGS_REG) (const_int 0)])) 14091 (set (match_operand 3 "q_regs_operand" "") 14092 (zero_extend (match_dup 1)))] 14093 "(peep2_reg_dead_p (3, operands[1]) 14094 || operands_match_p (operands[1], operands[3])) 14095 && ! reg_overlap_mentioned_p (operands[3], operands[0])" 14096 [(set (match_dup 4) (match_dup 0)) 14097 (set (strict_low_part (match_dup 5)) 14098 (match_dup 2))] 14099{ 14100 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG); 14101 operands[5] = gen_lowpart (QImode, operands[3]); 14102 ix86_expand_clear (operands[3]); 14103}) 14104 14105;; Similar, but match zero_extendhisi2_and, which adds a clobber. 14106 14107(define_peephole2 14108 [(set (reg FLAGS_REG) (match_operand 0 "" "")) 14109 (set (match_operand:QI 1 "register_operand" "") 14110 (match_operator:QI 2 "ix86_comparison_operator" 14111 [(reg FLAGS_REG) (const_int 0)])) 14112 (parallel [(set (match_operand 3 "q_regs_operand" "") 14113 (zero_extend (match_dup 1))) 14114 (clobber (reg:CC FLAGS_REG))])] 14115 "(peep2_reg_dead_p (3, operands[1]) 14116 || operands_match_p (operands[1], operands[3])) 14117 && ! reg_overlap_mentioned_p (operands[3], operands[0])" 14118 [(set (match_dup 4) (match_dup 0)) 14119 (set (strict_low_part (match_dup 5)) 14120 (match_dup 2))] 14121{ 14122 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG); 14123 operands[5] = gen_lowpart (QImode, operands[3]); 14124 ix86_expand_clear (operands[3]); 14125}) 14126 14127;; Call instructions. 14128 14129;; The predicates normally associated with named expanders are not properly 14130;; checked for calls. This is a bug in the generic code, but it isn't that 14131;; easy to fix. Ignore it for now and be prepared to fix things up. 14132 14133;; Call subroutine returning no value. 14134 14135(define_expand "call_pop" 14136 [(parallel [(call (match_operand:QI 0 "" "") 14137 (match_operand:SI 1 "" "")) 14138 (set (reg:SI SP_REG) 14139 (plus:SI (reg:SI SP_REG) 14140 (match_operand:SI 3 "" "")))])] 14141 "!TARGET_64BIT" 14142{ 14143 ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0); 14144 DONE; 14145}) 14146 14147(define_insn "*call_pop_0" 14148 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" "")) 14149 (match_operand:SI 1 "" "")) 14150 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) 14151 (match_operand:SI 2 "immediate_operand" "")))] 14152 "!TARGET_64BIT" 14153{ 14154 if (SIBLING_CALL_P (insn)) 14155 return "jmp\t%P0"; 14156 else 14157 return "call\t%P0"; 14158} 14159 [(set_attr "type" "call")]) 14160 14161(define_insn "*call_pop_1" 14162 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm")) 14163 (match_operand:SI 1 "" "")) 14164 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) 14165 (match_operand:SI 2 "immediate_operand" "i")))] 14166 "!TARGET_64BIT" 14167{ 14168 if (constant_call_address_operand (operands[0], Pmode)) 14169 { 14170 if (SIBLING_CALL_P (insn)) 14171 return "jmp\t%P0"; 14172 else 14173 return "call\t%P0"; 14174 } 14175 if (SIBLING_CALL_P (insn)) 14176 return "jmp\t%A0"; 14177 else 14178 return "call\t%A0"; 14179} 14180 [(set_attr "type" "call")]) 14181 14182(define_expand "call" 14183 [(call (match_operand:QI 0 "" "") 14184 (match_operand 1 "" "")) 14185 (use (match_operand 2 "" ""))] 14186 "" 14187{ 14188 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0); 14189 DONE; 14190}) 14191 14192(define_expand "sibcall" 14193 [(call (match_operand:QI 0 "" "") 14194 (match_operand 1 "" "")) 14195 (use (match_operand 2 "" ""))] 14196 "" 14197{ 14198 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1); 14199 DONE; 14200}) 14201 14202(define_insn "*call_0" 14203 [(call (mem:QI (match_operand 0 "constant_call_address_operand" "")) 14204 (match_operand 1 "" ""))] 14205 "" 14206{ 14207 if (SIBLING_CALL_P (insn)) 14208 return "jmp\t%P0"; 14209 else 14210 return "call\t%P0"; 14211} 14212 [(set_attr "type" "call")]) 14213 14214(define_insn "*call_1" 14215 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm")) 14216 (match_operand 1 "" ""))] 14217 "!SIBLING_CALL_P (insn) && !TARGET_64BIT" 14218{ 14219 if (constant_call_address_operand (operands[0], Pmode)) 14220 return "call\t%P0"; 14221 return "call\t%A0"; 14222} 14223 [(set_attr "type" "call")]) 14224 14225(define_insn "*sibcall_1" 14226 [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a")) 14227 (match_operand 1 "" ""))] 14228 "SIBLING_CALL_P (insn) && !TARGET_64BIT" 14229{ 14230 if (constant_call_address_operand (operands[0], Pmode)) 14231 return "jmp\t%P0"; 14232 return "jmp\t%A0"; 14233} 14234 [(set_attr "type" "call")]) 14235 14236(define_insn "*call_1_rex64" 14237 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm")) 14238 (match_operand 1 "" ""))] 14239 "!SIBLING_CALL_P (insn) && TARGET_64BIT" 14240{ 14241 if (constant_call_address_operand (operands[0], Pmode)) 14242 return "call\t%P0"; 14243 return "call\t%A0"; 14244} 14245 [(set_attr "type" "call")]) 14246 14247(define_insn "*sibcall_1_rex64" 14248 [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" "")) 14249 (match_operand 1 "" ""))] 14250 "SIBLING_CALL_P (insn) && TARGET_64BIT" 14251 "jmp\t%P0" 14252 [(set_attr "type" "call")]) 14253 14254(define_insn "*sibcall_1_rex64_v" 14255 [(call (mem:QI (reg:DI 40)) 14256 (match_operand 0 "" ""))] 14257 "SIBLING_CALL_P (insn) && TARGET_64BIT" 14258 "jmp\t*%%r11" 14259 [(set_attr "type" "call")]) 14260 14261 14262;; Call subroutine, returning value in operand 0 14263 14264(define_expand "call_value_pop" 14265 [(parallel [(set (match_operand 0 "" "") 14266 (call (match_operand:QI 1 "" "") 14267 (match_operand:SI 2 "" ""))) 14268 (set (reg:SI SP_REG) 14269 (plus:SI (reg:SI SP_REG) 14270 (match_operand:SI 4 "" "")))])] 14271 "!TARGET_64BIT" 14272{ 14273 ix86_expand_call (operands[0], operands[1], operands[2], 14274 operands[3], operands[4], 0); 14275 DONE; 14276}) 14277 14278(define_expand "call_value" 14279 [(set (match_operand 0 "" "") 14280 (call (match_operand:QI 1 "" "") 14281 (match_operand:SI 2 "" ""))) 14282 (use (match_operand:SI 3 "" ""))] 14283 ;; Operand 2 not used on the i386. 14284 "" 14285{ 14286 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0); 14287 DONE; 14288}) 14289 14290(define_expand "sibcall_value" 14291 [(set (match_operand 0 "" "") 14292 (call (match_operand:QI 1 "" "") 14293 (match_operand:SI 2 "" ""))) 14294 (use (match_operand:SI 3 "" ""))] 14295 ;; Operand 2 not used on the i386. 14296 "" 14297{ 14298 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1); 14299 DONE; 14300}) 14301 14302;; Call subroutine returning any type. 14303 14304(define_expand "untyped_call" 14305 [(parallel [(call (match_operand 0 "" "") 14306 (const_int 0)) 14307 (match_operand 1 "" "") 14308 (match_operand 2 "" "")])] 14309 "" 14310{ 14311 int i; 14312 14313 /* In order to give reg-stack an easier job in validating two 14314 coprocessor registers as containing a possible return value, 14315 simply pretend the untyped call returns a complex long double 14316 value. */ 14317 14318 ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387 14319 ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL), 14320 operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1), 14321 NULL, 0); 14322 14323 for (i = 0; i < XVECLEN (operands[2], 0); i++) 14324 { 14325 rtx set = XVECEXP (operands[2], 0, i); 14326 emit_move_insn (SET_DEST (set), SET_SRC (set)); 14327 } 14328 14329 /* The optimizer does not know that the call sets the function value 14330 registers we stored in the result block. We avoid problems by 14331 claiming that all hard registers are used and clobbered at this 14332 point. */ 14333 emit_insn (gen_blockage (const0_rtx)); 14334 14335 DONE; 14336}) 14337 14338;; Prologue and epilogue instructions 14339 14340;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and 14341;; all of memory. This blocks insns from being moved across this point. 14342 14343(define_insn "blockage" 14344 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)] 14345 "" 14346 "" 14347 [(set_attr "length" "0")]) 14348 14349;; Insn emitted into the body of a function to return from a function. 14350;; This is only done if the function's epilogue is known to be simple. 14351;; See comments for ix86_can_use_return_insn_p in i386.c. 14352 14353(define_expand "return" 14354 [(return)] 14355 "ix86_can_use_return_insn_p ()" 14356{ 14357 if (current_function_pops_args) 14358 { 14359 rtx popc = GEN_INT (current_function_pops_args); 14360 emit_jump_insn (gen_return_pop_internal (popc)); 14361 DONE; 14362 } 14363}) 14364 14365(define_insn "return_internal" 14366 [(return)] 14367 "reload_completed" 14368 "ret" 14369 [(set_attr "length" "1") 14370 (set_attr "length_immediate" "0") 14371 (set_attr "modrm" "0")]) 14372 14373;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET 14374;; instruction Athlon and K8 have. 14375 14376(define_insn "return_internal_long" 14377 [(return) 14378 (unspec [(const_int 0)] UNSPEC_REP)] 14379 "reload_completed" 14380 "rep {;} ret" 14381 [(set_attr "length" "1") 14382 (set_attr "length_immediate" "0") 14383 (set_attr "prefix_rep" "1") 14384 (set_attr "modrm" "0")]) 14385 14386(define_insn "return_pop_internal" 14387 [(return) 14388 (use (match_operand:SI 0 "const_int_operand" ""))] 14389 "reload_completed" 14390 "ret\t%0" 14391 [(set_attr "length" "3") 14392 (set_attr "length_immediate" "2") 14393 (set_attr "modrm" "0")]) 14394 14395(define_insn "return_indirect_internal" 14396 [(return) 14397 (use (match_operand:SI 0 "register_operand" "r"))] 14398 "reload_completed" 14399 "jmp\t%A0" 14400 [(set_attr "type" "ibr") 14401 (set_attr "length_immediate" "0")]) 14402 14403(define_insn "nop" 14404 [(const_int 0)] 14405 "" 14406 "nop" 14407 [(set_attr "length" "1") 14408 (set_attr "length_immediate" "0") 14409 (set_attr "modrm" "0")]) 14410 14411;; Align to 16-byte boundary, max skip in op0. Used to avoid 14412;; branch prediction penalty for the third jump in a 16-byte 14413;; block on K8. 14414 14415(define_insn "align" 14416 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)] 14417 "" 14418{ 14419#ifdef ASM_OUTPUT_MAX_SKIP_ALIGN 14420 ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0])); 14421#else 14422 /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that. 14423 The align insn is used to avoid 3 jump instructions in the row to improve 14424 branch prediction and the benefits hardly outweigh the cost of extra 8 14425 nops on the average inserted by full alignment pseudo operation. */ 14426#endif 14427 return ""; 14428} 14429 [(set_attr "length" "16")]) 14430 14431(define_expand "prologue" 14432 [(const_int 1)] 14433 "" 14434 "ix86_expand_prologue (); DONE;") 14435 14436(define_insn "set_got" 14437 [(set (match_operand:SI 0 "register_operand" "=r") 14438 (unspec:SI [(const_int 0)] UNSPEC_SET_GOT)) 14439 (clobber (reg:CC FLAGS_REG))] 14440 "!TARGET_64BIT" 14441 { return output_set_got (operands[0], NULL_RTX); } 14442 [(set_attr "type" "multi") 14443 (set_attr "length" "12")]) 14444 14445(define_insn "set_got_labelled" 14446 [(set (match_operand:SI 0 "register_operand" "=r") 14447 (unspec:SI [(label_ref (match_operand 1 "" ""))] 14448 UNSPEC_SET_GOT)) 14449 (clobber (reg:CC FLAGS_REG))] 14450 "!TARGET_64BIT" 14451 { return output_set_got (operands[0], operands[1]); } 14452 [(set_attr "type" "multi") 14453 (set_attr "length" "12")]) 14454 14455(define_insn "set_got_rex64" 14456 [(set (match_operand:DI 0 "register_operand" "=r") 14457 (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))] 14458 "TARGET_64BIT" 14459 "lea{q}\t_GLOBAL_OFFSET_TABLE_(%%rip), %0" 14460 [(set_attr "type" "lea") 14461 (set_attr "length" "6")]) 14462 14463(define_expand "epilogue" 14464 [(const_int 1)] 14465 "" 14466 "ix86_expand_epilogue (1); DONE;") 14467 14468(define_expand "sibcall_epilogue" 14469 [(const_int 1)] 14470 "" 14471 "ix86_expand_epilogue (0); DONE;") 14472 14473(define_expand "eh_return" 14474 [(use (match_operand 0 "register_operand" ""))] 14475 "" 14476{ 14477 rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0]; 14478 14479 /* Tricky bit: we write the address of the handler to which we will 14480 be returning into someone else's stack frame, one word below the 14481 stack address we wish to restore. */ 14482 tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa); 14483 tmp = plus_constant (tmp, -UNITS_PER_WORD); 14484 tmp = gen_rtx_MEM (Pmode, tmp); 14485 emit_move_insn (tmp, ra); 14486 14487 if (Pmode == SImode) 14488 emit_jump_insn (gen_eh_return_si (sa)); 14489 else 14490 emit_jump_insn (gen_eh_return_di (sa)); 14491 emit_barrier (); 14492 DONE; 14493}) 14494 14495(define_insn_and_split "eh_return_si" 14496 [(set (pc) 14497 (unspec [(match_operand:SI 0 "register_operand" "c")] 14498 UNSPEC_EH_RETURN))] 14499 "!TARGET_64BIT" 14500 "#" 14501 "reload_completed" 14502 [(const_int 1)] 14503 "ix86_expand_epilogue (2); DONE;") 14504 14505(define_insn_and_split "eh_return_di" 14506 [(set (pc) 14507 (unspec [(match_operand:DI 0 "register_operand" "c")] 14508 UNSPEC_EH_RETURN))] 14509 "TARGET_64BIT" 14510 "#" 14511 "reload_completed" 14512 [(const_int 1)] 14513 "ix86_expand_epilogue (2); DONE;") 14514 14515(define_insn "leave" 14516 [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4))) 14517 (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG))) 14518 (clobber (mem:BLK (scratch)))] 14519 "!TARGET_64BIT" 14520 "leave" 14521 [(set_attr "type" "leave")]) 14522 14523(define_insn "leave_rex64" 14524 [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8))) 14525 (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG))) 14526 (clobber (mem:BLK (scratch)))] 14527 "TARGET_64BIT" 14528 "leave" 14529 [(set_attr "type" "leave")]) 14530 14531(define_expand "ffssi2" 14532 [(parallel 14533 [(set (match_operand:SI 0 "register_operand" "") 14534 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" ""))) 14535 (clobber (match_scratch:SI 2 "")) 14536 (clobber (reg:CC FLAGS_REG))])] 14537 "" 14538 "") 14539 14540(define_insn_and_split "*ffs_cmove" 14541 [(set (match_operand:SI 0 "register_operand" "=r") 14542 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))) 14543 (clobber (match_scratch:SI 2 "=&r")) 14544 (clobber (reg:CC FLAGS_REG))] 14545 "TARGET_CMOVE" 14546 "#" 14547 "&& reload_completed" 14548 [(set (match_dup 2) (const_int -1)) 14549 (parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0))) 14550 (set (match_dup 0) (ctz:SI (match_dup 1)))]) 14551 (set (match_dup 0) (if_then_else:SI 14552 (eq (reg:CCZ FLAGS_REG) (const_int 0)) 14553 (match_dup 2) 14554 (match_dup 0))) 14555 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1))) 14556 (clobber (reg:CC FLAGS_REG))])] 14557 "") 14558 14559(define_insn_and_split "*ffs_no_cmove" 14560 [(set (match_operand:SI 0 "nonimmediate_operand" "=r") 14561 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))) 14562 (clobber (match_scratch:SI 2 "=&q")) 14563 (clobber (reg:CC FLAGS_REG))] 14564 "" 14565 "#" 14566 "reload_completed" 14567 [(parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0))) 14568 (set (match_dup 0) (ctz:SI (match_dup 1)))]) 14569 (set (strict_low_part (match_dup 3)) 14570 (eq:QI (reg:CCZ FLAGS_REG) (const_int 0))) 14571 (parallel [(set (match_dup 2) (neg:SI (match_dup 2))) 14572 (clobber (reg:CC FLAGS_REG))]) 14573 (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2))) 14574 (clobber (reg:CC FLAGS_REG))]) 14575 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1))) 14576 (clobber (reg:CC FLAGS_REG))])] 14577{ 14578 operands[3] = gen_lowpart (QImode, operands[2]); 14579 ix86_expand_clear (operands[2]); 14580}) 14581 14582(define_insn "*ffssi_1" 14583 [(set (reg:CCZ FLAGS_REG) 14584 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm") 14585 (const_int 0))) 14586 (set (match_operand:SI 0 "register_operand" "=r") 14587 (ctz:SI (match_dup 1)))] 14588 "" 14589 "bsf{l}\t{%1, %0|%0, %1}" 14590 [(set_attr "prefix_0f" "1")]) 14591 14592(define_expand "ffsdi2" 14593 [(parallel 14594 [(set (match_operand:DI 0 "register_operand" "") 14595 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" ""))) 14596 (clobber (match_scratch:DI 2 "")) 14597 (clobber (reg:CC FLAGS_REG))])] 14598 "TARGET_64BIT && TARGET_CMOVE" 14599 "") 14600 14601(define_insn_and_split "*ffs_rex64" 14602 [(set (match_operand:DI 0 "register_operand" "=r") 14603 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))) 14604 (clobber (match_scratch:DI 2 "=&r")) 14605 (clobber (reg:CC FLAGS_REG))] 14606 "TARGET_64BIT && TARGET_CMOVE" 14607 "#" 14608 "&& reload_completed" 14609 [(set (match_dup 2) (const_int -1)) 14610 (parallel [(set (reg:CCZ FLAGS_REG) 14611 (compare:CCZ (match_dup 1) (const_int 0))) 14612 (set (match_dup 0) (ctz:DI (match_dup 1)))]) 14613 (set (match_dup 0) (if_then_else:DI 14614 (eq (reg:CCZ FLAGS_REG) (const_int 0)) 14615 (match_dup 2) 14616 (match_dup 0))) 14617 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1))) 14618 (clobber (reg:CC FLAGS_REG))])] 14619 "") 14620 14621(define_insn "*ffsdi_1" 14622 [(set (reg:CCZ FLAGS_REG) 14623 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm") 14624 (const_int 0))) 14625 (set (match_operand:DI 0 "register_operand" "=r") 14626 (ctz:DI (match_dup 1)))] 14627 "TARGET_64BIT" 14628 "bsf{q}\t{%1, %0|%0, %1}" 14629 [(set_attr "prefix_0f" "1")]) 14630 14631(define_insn "ctzsi2" 14632 [(set (match_operand:SI 0 "register_operand" "=r") 14633 (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))) 14634 (clobber (reg:CC FLAGS_REG))] 14635 "" 14636 "bsf{l}\t{%1, %0|%0, %1}" 14637 [(set_attr "prefix_0f" "1")]) 14638 14639(define_insn "ctzdi2" 14640 [(set (match_operand:DI 0 "register_operand" "=r") 14641 (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))) 14642 (clobber (reg:CC FLAGS_REG))] 14643 "TARGET_64BIT" 14644 "bsf{q}\t{%1, %0|%0, %1}" 14645 [(set_attr "prefix_0f" "1")]) 14646 14647(define_expand "clzsi2" 14648 [(parallel 14649 [(set (match_operand:SI 0 "register_operand" "") 14650 (minus:SI (const_int 31) 14651 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "")))) 14652 (clobber (reg:CC FLAGS_REG))]) 14653 (parallel 14654 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31))) 14655 (clobber (reg:CC FLAGS_REG))])] 14656 "" 14657{ 14658 if (TARGET_ABM) 14659 { 14660 emit_insn (gen_clzsi2_abm (operands[0], operands[1])); 14661 DONE; 14662 } 14663}) 14664 14665(define_insn "clzsi2_abm" 14666 [(set (match_operand:SI 0 "register_operand" "=r") 14667 (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))) 14668 (clobber (reg:CC FLAGS_REG))] 14669 "TARGET_ABM" 14670 "lzcnt{l}\t{%1, %0|%0, %1}" 14671 [(set_attr "prefix_rep" "1") 14672 (set_attr "type" "bitmanip") 14673 (set_attr "mode" "SI")]) 14674 14675(define_insn "*bsr" 14676 [(set (match_operand:SI 0 "register_operand" "=r") 14677 (minus:SI (const_int 31) 14678 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))) 14679 (clobber (reg:CC FLAGS_REG))] 14680 "" 14681 "bsr{l}\t{%1, %0|%0, %1}" 14682 [(set_attr "prefix_0f" "1") 14683 (set_attr "mode" "SI")]) 14684 14685(define_insn "popcountsi2" 14686 [(set (match_operand:SI 0 "register_operand" "=r") 14687 (popcount:SI (match_operand:SI 1 "nonimmediate_operand" ""))) 14688 (clobber (reg:CC FLAGS_REG))] 14689 "TARGET_POPCNT" 14690 "popcnt{l}\t{%1, %0|%0, %1}" 14691 [(set_attr "prefix_rep" "1") 14692 (set_attr "type" "bitmanip") 14693 (set_attr "mode" "SI")]) 14694 14695(define_insn "*popcountsi2_cmp" 14696 [(set (reg FLAGS_REG) 14697 (compare 14698 (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm")) 14699 (const_int 0))) 14700 (set (match_operand:SI 0 "register_operand" "=r") 14701 (popcount:SI (match_dup 1)))] 14702 "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)" 14703 "popcnt{l}\t{%1, %0|%0, %1}" 14704 [(set_attr "prefix_rep" "1") 14705 (set_attr "type" "bitmanip") 14706 (set_attr "mode" "SI")]) 14707 14708(define_insn "*popcountsi2_cmp_zext" 14709 [(set (reg FLAGS_REG) 14710 (compare 14711 (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm")) 14712 (const_int 0))) 14713 (set (match_operand:DI 0 "register_operand" "=r") 14714 (zero_extend:DI(popcount:SI (match_dup 1))))] 14715 "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)" 14716 "popcnt{l}\t{%1, %0|%0, %1}" 14717 [(set_attr "prefix_rep" "1") 14718 (set_attr "type" "bitmanip") 14719 (set_attr "mode" "SI")]) 14720 14721(define_insn "bswapsi2" 14722 [(set (match_operand:SI 0 "register_operand" "=r") 14723 (bswap:SI (match_operand:SI 1 "register_operand" "0"))) 14724 (clobber (reg:CC FLAGS_REG))] 14725 "TARGET_BSWAP" 14726 "bswap\t%k0" 14727 [(set_attr "prefix_0f" "1") 14728 (set_attr "length" "2")]) 14729 14730(define_insn "bswapdi2" 14731 [(set (match_operand:DI 0 "register_operand" "=r") 14732 (bswap:DI (match_operand:DI 1 "register_operand" "0"))) 14733 (clobber (reg:CC FLAGS_REG))] 14734 "TARGET_64BIT && TARGET_BSWAP" 14735 "bswap\t%0" 14736 [(set_attr "prefix_0f" "1") 14737 (set_attr "length" "3")]) 14738 14739(define_expand "clzdi2" 14740 [(parallel 14741 [(set (match_operand:DI 0 "register_operand" "") 14742 (minus:DI (const_int 63) 14743 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "")))) 14744 (clobber (reg:CC FLAGS_REG))]) 14745 (parallel 14746 [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63))) 14747 (clobber (reg:CC FLAGS_REG))])] 14748 "TARGET_64BIT" 14749{ 14750 if (TARGET_ABM) 14751 { 14752 emit_insn (gen_clzdi2_abm (operands[0], operands[1])); 14753 DONE; 14754 } 14755}) 14756 14757(define_insn "clzdi2_abm" 14758 [(set (match_operand:DI 0 "register_operand" "=r") 14759 (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))) 14760 (clobber (reg:CC FLAGS_REG))] 14761 "TARGET_64BIT && TARGET_ABM" 14762 "lzcnt{q}\t{%1, %0|%0, %1}" 14763 [(set_attr "prefix_rep" "1") 14764 (set_attr "type" "bitmanip") 14765 (set_attr "mode" "DI")]) 14766 14767(define_insn "*bsr_rex64" 14768 [(set (match_operand:DI 0 "register_operand" "=r") 14769 (minus:DI (const_int 63) 14770 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))) 14771 (clobber (reg:CC FLAGS_REG))] 14772 "TARGET_64BIT" 14773 "bsr{q}\t{%1, %0|%0, %1}" 14774 [(set_attr "prefix_0f" "1") 14775 (set_attr "mode" "DI")]) 14776 14777(define_insn "popcountdi2" 14778 [(set (match_operand:DI 0 "register_operand" "=r") 14779 (popcount:DI (match_operand:DI 1 "nonimmediate_operand" ""))) 14780 (clobber (reg:CC FLAGS_REG))] 14781 "TARGET_64BIT && TARGET_POPCNT" 14782 "popcnt{q}\t{%1, %0|%0, %1}" 14783 [(set_attr "prefix_rep" "1") 14784 (set_attr "type" "bitmanip") 14785 (set_attr "mode" "DI")]) 14786 14787(define_insn "*popcountdi2_cmp" 14788 [(set (reg FLAGS_REG) 14789 (compare 14790 (popcount:DI (match_operand:DI 1 "nonimmediate_operand" "rm")) 14791 (const_int 0))) 14792 (set (match_operand:DI 0 "register_operand" "=r") 14793 (popcount:DI (match_dup 1)))] 14794 "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)" 14795 "popcnt{q}\t{%1, %0|%0, %1}" 14796 [(set_attr "prefix_rep" "1") 14797 (set_attr "type" "bitmanip") 14798 (set_attr "mode" "DI")]) 14799 14800(define_expand "clzhi2" 14801 [(parallel 14802 [(set (match_operand:HI 0 "register_operand" "") 14803 (minus:HI (const_int 15) 14804 (clz:HI (match_operand:HI 1 "nonimmediate_operand" "")))) 14805 (clobber (reg:CC FLAGS_REG))]) 14806 (parallel 14807 [(set (match_dup 0) (xor:HI (match_dup 0) (const_int 15))) 14808 (clobber (reg:CC FLAGS_REG))])] 14809 "" 14810{ 14811 if (TARGET_ABM) 14812 { 14813 emit_insn (gen_clzhi2_abm (operands[0], operands[1])); 14814 DONE; 14815 } 14816}) 14817 14818(define_insn "clzhi2_abm" 14819 [(set (match_operand:HI 0 "register_operand" "=r") 14820 (clz:HI (match_operand:HI 1 "nonimmediate_operand" ""))) 14821 (clobber (reg:CC FLAGS_REG))] 14822 "TARGET_ABM" 14823 "lzcnt{w}\t{%1, %0|%0, %1}" 14824 [(set_attr "prefix_rep" "1") 14825 (set_attr "type" "bitmanip") 14826 (set_attr "mode" "HI")]) 14827 14828(define_insn "*bsrhi" 14829 [(set (match_operand:HI 0 "register_operand" "=r") 14830 (minus:HI (const_int 15) 14831 (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm")))) 14832 (clobber (reg:CC FLAGS_REG))] 14833 "" 14834 "bsr{w}\t{%1, %0|%0, %1}" 14835 [(set_attr "prefix_0f" "1") 14836 (set_attr "mode" "HI")]) 14837 14838(define_insn "popcounthi2" 14839 [(set (match_operand:HI 0 "register_operand" "=r") 14840 (popcount:HI (match_operand:HI 1 "nonimmediate_operand" ""))) 14841 (clobber (reg:CC FLAGS_REG))] 14842 "TARGET_POPCNT" 14843 "popcnt{w}\t{%1, %0|%0, %1}" 14844 [(set_attr "prefix_rep" "1") 14845 (set_attr "type" "bitmanip") 14846 (set_attr "mode" "HI")]) 14847 14848(define_insn "*popcounthi2_cmp" 14849 [(set (reg FLAGS_REG) 14850 (compare 14851 (popcount:HI (match_operand:HI 1 "nonimmediate_operand" "rm")) 14852 (const_int 0))) 14853 (set (match_operand:HI 0 "register_operand" "=r") 14854 (popcount:HI (match_dup 1)))] 14855 "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)" 14856 "popcnt{w}\t{%1, %0|%0, %1}" 14857 [(set_attr "prefix_rep" "1") 14858 (set_attr "type" "bitmanip") 14859 (set_attr "mode" "HI")]) 14860 14861;; Thread-local storage patterns for ELF. 14862;; 14863;; Note that these code sequences must appear exactly as shown 14864;; in order to allow linker relaxation. 14865 14866(define_insn "*tls_global_dynamic_32_gnu" 14867 [(set (match_operand:SI 0 "register_operand" "=a") 14868 (unspec:SI [(match_operand:SI 1 "register_operand" "b") 14869 (match_operand:SI 2 "tls_symbolic_operand" "") 14870 (match_operand:SI 3 "call_insn_operand" "")] 14871 UNSPEC_TLS_GD)) 14872 (clobber (match_scratch:SI 4 "=d")) 14873 (clobber (match_scratch:SI 5 "=c")) 14874 (clobber (reg:CC FLAGS_REG))] 14875 "!TARGET_64BIT && TARGET_GNU_TLS" 14876 "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3" 14877 [(set_attr "type" "multi") 14878 (set_attr "length" "12")]) 14879 14880(define_insn "*tls_global_dynamic_32_sun" 14881 [(set (match_operand:SI 0 "register_operand" "=a") 14882 (unspec:SI [(match_operand:SI 1 "register_operand" "b") 14883 (match_operand:SI 2 "tls_symbolic_operand" "") 14884 (match_operand:SI 3 "call_insn_operand" "")] 14885 UNSPEC_TLS_GD)) 14886 (clobber (match_scratch:SI 4 "=d")) 14887 (clobber (match_scratch:SI 5 "=c")) 14888 (clobber (reg:CC FLAGS_REG))] 14889 "!TARGET_64BIT && TARGET_SUN_TLS" 14890 "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]} 14891 push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop" 14892 [(set_attr "type" "multi") 14893 (set_attr "length" "14")]) 14894 14895(define_expand "tls_global_dynamic_32" 14896 [(parallel [(set (match_operand:SI 0 "register_operand" "") 14897 (unspec:SI 14898 [(match_dup 2) 14899 (match_operand:SI 1 "tls_symbolic_operand" "") 14900 (match_dup 3)] 14901 UNSPEC_TLS_GD)) 14902 (clobber (match_scratch:SI 4 "")) 14903 (clobber (match_scratch:SI 5 "")) 14904 (clobber (reg:CC FLAGS_REG))])] 14905 "" 14906{ 14907 if (flag_pic) 14908 operands[2] = pic_offset_table_rtx; 14909 else 14910 { 14911 operands[2] = gen_reg_rtx (Pmode); 14912 emit_insn (gen_set_got (operands[2])); 14913 } 14914 if (TARGET_GNU2_TLS) 14915 { 14916 emit_insn (gen_tls_dynamic_gnu2_32 14917 (operands[0], operands[1], operands[2])); 14918 DONE; 14919 } 14920 operands[3] = ix86_tls_get_addr (); 14921}) 14922 14923(define_insn "*tls_global_dynamic_64" 14924 [(set (match_operand:DI 0 "register_operand" "=a") 14925 (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" "")) 14926 (match_operand:DI 3 "" ""))) 14927 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")] 14928 UNSPEC_TLS_GD)] 14929 "TARGET_64BIT" 14930 ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2" 14931 [(set_attr "type" "multi") 14932 (set_attr "length" "16")]) 14933 14934(define_expand "tls_global_dynamic_64" 14935 [(parallel [(set (match_operand:DI 0 "register_operand" "") 14936 (call:DI (mem:QI (match_dup 2)) (const_int 0))) 14937 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")] 14938 UNSPEC_TLS_GD)])] 14939 "" 14940{ 14941 if (TARGET_GNU2_TLS) 14942 { 14943 emit_insn (gen_tls_dynamic_gnu2_64 14944 (operands[0], operands[1])); 14945 DONE; 14946 } 14947 operands[2] = ix86_tls_get_addr (); 14948}) 14949 14950(define_insn "*tls_local_dynamic_base_32_gnu" 14951 [(set (match_operand:SI 0 "register_operand" "=a") 14952 (unspec:SI [(match_operand:SI 1 "register_operand" "b") 14953 (match_operand:SI 2 "call_insn_operand" "")] 14954 UNSPEC_TLS_LD_BASE)) 14955 (clobber (match_scratch:SI 3 "=d")) 14956 (clobber (match_scratch:SI 4 "=c")) 14957 (clobber (reg:CC FLAGS_REG))] 14958 "!TARGET_64BIT && TARGET_GNU_TLS" 14959 "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2" 14960 [(set_attr "type" "multi") 14961 (set_attr "length" "11")]) 14962 14963(define_insn "*tls_local_dynamic_base_32_sun" 14964 [(set (match_operand:SI 0 "register_operand" "=a") 14965 (unspec:SI [(match_operand:SI 1 "register_operand" "b") 14966 (match_operand:SI 2 "call_insn_operand" "")] 14967 UNSPEC_TLS_LD_BASE)) 14968 (clobber (match_scratch:SI 3 "=d")) 14969 (clobber (match_scratch:SI 4 "=c")) 14970 (clobber (reg:CC FLAGS_REG))] 14971 "!TARGET_64BIT && TARGET_SUN_TLS" 14972 "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]} 14973 push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3" 14974 [(set_attr "type" "multi") 14975 (set_attr "length" "13")]) 14976 14977(define_expand "tls_local_dynamic_base_32" 14978 [(parallel [(set (match_operand:SI 0 "register_operand" "") 14979 (unspec:SI [(match_dup 1) (match_dup 2)] 14980 UNSPEC_TLS_LD_BASE)) 14981 (clobber (match_scratch:SI 3 "")) 14982 (clobber (match_scratch:SI 4 "")) 14983 (clobber (reg:CC FLAGS_REG))])] 14984 "" 14985{ 14986 if (flag_pic) 14987 operands[1] = pic_offset_table_rtx; 14988 else 14989 { 14990 operands[1] = gen_reg_rtx (Pmode); 14991 emit_insn (gen_set_got (operands[1])); 14992 } 14993 if (TARGET_GNU2_TLS) 14994 { 14995 emit_insn (gen_tls_dynamic_gnu2_32 14996 (operands[0], ix86_tls_module_base (), operands[1])); 14997 DONE; 14998 } 14999 operands[2] = ix86_tls_get_addr (); 15000}) 15001 15002(define_insn "*tls_local_dynamic_base_64" 15003 [(set (match_operand:DI 0 "register_operand" "=a") 15004 (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" "")) 15005 (match_operand:DI 2 "" ""))) 15006 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)] 15007 "TARGET_64BIT" 15008 "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1" 15009 [(set_attr "type" "multi") 15010 (set_attr "length" "12")]) 15011 15012(define_expand "tls_local_dynamic_base_64" 15013 [(parallel [(set (match_operand:DI 0 "register_operand" "") 15014 (call:DI (mem:QI (match_dup 1)) (const_int 0))) 15015 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])] 15016 "" 15017{ 15018 if (TARGET_GNU2_TLS) 15019 { 15020 emit_insn (gen_tls_dynamic_gnu2_64 15021 (operands[0], ix86_tls_module_base ())); 15022 DONE; 15023 } 15024 operands[1] = ix86_tls_get_addr (); 15025}) 15026 15027;; Local dynamic of a single variable is a lose. Show combine how 15028;; to convert that back to global dynamic. 15029 15030(define_insn_and_split "*tls_local_dynamic_32_once" 15031 [(set (match_operand:SI 0 "register_operand" "=a") 15032 (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b") 15033 (match_operand:SI 2 "call_insn_operand" "")] 15034 UNSPEC_TLS_LD_BASE) 15035 (const:SI (unspec:SI 15036 [(match_operand:SI 3 "tls_symbolic_operand" "")] 15037 UNSPEC_DTPOFF)))) 15038 (clobber (match_scratch:SI 4 "=d")) 15039 (clobber (match_scratch:SI 5 "=c")) 15040 (clobber (reg:CC FLAGS_REG))] 15041 "" 15042 "#" 15043 "" 15044 [(parallel [(set (match_dup 0) 15045 (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)] 15046 UNSPEC_TLS_GD)) 15047 (clobber (match_dup 4)) 15048 (clobber (match_dup 5)) 15049 (clobber (reg:CC FLAGS_REG))])] 15050 "") 15051 15052;; Load and add the thread base pointer from %gs:0. 15053 15054(define_insn "*load_tp_si" 15055 [(set (match_operand:SI 0 "register_operand" "=r") 15056 (unspec:SI [(const_int 0)] UNSPEC_TP))] 15057 "!TARGET_64BIT" 15058 "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}" 15059 [(set_attr "type" "imov") 15060 (set_attr "modrm" "0") 15061 (set_attr "length" "7") 15062 (set_attr "memory" "load") 15063 (set_attr "imm_disp" "false")]) 15064 15065(define_insn "*add_tp_si" 15066 [(set (match_operand:SI 0 "register_operand" "=r") 15067 (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP) 15068 (match_operand:SI 1 "register_operand" "0"))) 15069 (clobber (reg:CC FLAGS_REG))] 15070 "!TARGET_64BIT" 15071 "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}" 15072 [(set_attr "type" "alu") 15073 (set_attr "modrm" "0") 15074 (set_attr "length" "7") 15075 (set_attr "memory" "load") 15076 (set_attr "imm_disp" "false")]) 15077 15078(define_insn "*load_tp_di" 15079 [(set (match_operand:DI 0 "register_operand" "=r") 15080 (unspec:DI [(const_int 0)] UNSPEC_TP))] 15081 "TARGET_64BIT" 15082 "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}" 15083 [(set_attr "type" "imov") 15084 (set_attr "modrm" "0") 15085 (set_attr "length" "7") 15086 (set_attr "memory" "load") 15087 (set_attr "imm_disp" "false")]) 15088 15089(define_insn "*add_tp_di" 15090 [(set (match_operand:DI 0 "register_operand" "=r") 15091 (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP) 15092 (match_operand:DI 1 "register_operand" "0"))) 15093 (clobber (reg:CC FLAGS_REG))] 15094 "TARGET_64BIT" 15095 "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}" 15096 [(set_attr "type" "alu") 15097 (set_attr "modrm" "0") 15098 (set_attr "length" "7") 15099 (set_attr "memory" "load") 15100 (set_attr "imm_disp" "false")]) 15101 15102;; GNU2 TLS patterns can be split. 15103 15104(define_expand "tls_dynamic_gnu2_32" 15105 [(set (match_dup 3) 15106 (plus:SI (match_operand:SI 2 "register_operand" "") 15107 (const:SI 15108 (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")] 15109 UNSPEC_TLSDESC)))) 15110 (parallel 15111 [(set (match_operand:SI 0 "register_operand" "") 15112 (unspec:SI [(match_dup 1) (match_dup 3) 15113 (match_dup 2) (reg:SI SP_REG)] 15114 UNSPEC_TLSDESC)) 15115 (clobber (reg:CC FLAGS_REG))])] 15116 "!TARGET_64BIT && TARGET_GNU2_TLS" 15117{ 15118 operands[3] = no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode); 15119 ix86_tls_descriptor_calls_expanded_in_cfun = true; 15120}) 15121 15122(define_insn "*tls_dynamic_lea_32" 15123 [(set (match_operand:SI 0 "register_operand" "=r") 15124 (plus:SI (match_operand:SI 1 "register_operand" "b") 15125 (const:SI 15126 (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")] 15127 UNSPEC_TLSDESC))))] 15128 "!TARGET_64BIT && TARGET_GNU2_TLS" 15129 "lea{l}\t{%a2@TLSDESC(%1), %0|%0, %a2@TLSDESC[%1]}" 15130 [(set_attr "type" "lea") 15131 (set_attr "mode" "SI") 15132 (set_attr "length" "6") 15133 (set_attr "length_address" "4")]) 15134 15135(define_insn "*tls_dynamic_call_32" 15136 [(set (match_operand:SI 0 "register_operand" "=a") 15137 (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "") 15138 (match_operand:SI 2 "register_operand" "0") 15139 ;; we have to make sure %ebx still points to the GOT 15140 (match_operand:SI 3 "register_operand" "b") 15141 (reg:SI SP_REG)] 15142 UNSPEC_TLSDESC)) 15143 (clobber (reg:CC FLAGS_REG))] 15144 "!TARGET_64BIT && TARGET_GNU2_TLS" 15145 "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}" 15146 [(set_attr "type" "call") 15147 (set_attr "length" "2") 15148 (set_attr "length_address" "0")]) 15149 15150(define_insn_and_split "*tls_dynamic_gnu2_combine_32" 15151 [(set (match_operand:SI 0 "register_operand" "=&a") 15152 (plus:SI 15153 (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "") 15154 (match_operand:SI 4 "" "") 15155 (match_operand:SI 2 "register_operand" "b") 15156 (reg:SI SP_REG)] 15157 UNSPEC_TLSDESC) 15158 (const:SI (unspec:SI 15159 [(match_operand:SI 1 "tls_symbolic_operand" "")] 15160 UNSPEC_DTPOFF)))) 15161 (clobber (reg:CC FLAGS_REG))] 15162 "!TARGET_64BIT && TARGET_GNU2_TLS" 15163 "#" 15164 "" 15165 [(set (match_dup 0) (match_dup 5))] 15166{ 15167 operands[5] = no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode); 15168 emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2])); 15169}) 15170 15171(define_expand "tls_dynamic_gnu2_64" 15172 [(set (match_dup 2) 15173 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")] 15174 UNSPEC_TLSDESC)) 15175 (parallel 15176 [(set (match_operand:DI 0 "register_operand" "") 15177 (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)] 15178 UNSPEC_TLSDESC)) 15179 (clobber (reg:CC FLAGS_REG))])] 15180 "TARGET_64BIT && TARGET_GNU2_TLS" 15181{ 15182 operands[2] = no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode); 15183 ix86_tls_descriptor_calls_expanded_in_cfun = true; 15184}) 15185 15186(define_insn "*tls_dynamic_lea_64" 15187 [(set (match_operand:DI 0 "register_operand" "=r") 15188 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")] 15189 UNSPEC_TLSDESC))] 15190 "TARGET_64BIT && TARGET_GNU2_TLS" 15191 "lea{q}\t{%a1@TLSDESC(%%rip), %0|%0, %a1@TLSDESC[%%rip]}" 15192 [(set_attr "type" "lea") 15193 (set_attr "mode" "DI") 15194 (set_attr "length" "7") 15195 (set_attr "length_address" "4")]) 15196 15197(define_insn "*tls_dynamic_call_64" 15198 [(set (match_operand:DI 0 "register_operand" "=a") 15199 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "") 15200 (match_operand:DI 2 "register_operand" "0") 15201 (reg:DI SP_REG)] 15202 UNSPEC_TLSDESC)) 15203 (clobber (reg:CC FLAGS_REG))] 15204 "TARGET_64BIT && TARGET_GNU2_TLS" 15205 "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}" 15206 [(set_attr "type" "call") 15207 (set_attr "length" "2") 15208 (set_attr "length_address" "0")]) 15209 15210(define_insn_and_split "*tls_dynamic_gnu2_combine_64" 15211 [(set (match_operand:DI 0 "register_operand" "=&a") 15212 (plus:DI 15213 (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "") 15214 (match_operand:DI 3 "" "") 15215 (reg:DI SP_REG)] 15216 UNSPEC_TLSDESC) 15217 (const:DI (unspec:DI 15218 [(match_operand:DI 1 "tls_symbolic_operand" "")] 15219 UNSPEC_DTPOFF)))) 15220 (clobber (reg:CC FLAGS_REG))] 15221 "TARGET_64BIT && TARGET_GNU2_TLS" 15222 "#" 15223 "" 15224 [(set (match_dup 0) (match_dup 4))] 15225{ 15226 operands[4] = no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode); 15227 emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1])); 15228}) 15229 15230;; 15231 15232;; These patterns match the binary 387 instructions for addM3, subM3, 15233;; mulM3 and divM3. There are three patterns for each of DFmode and 15234;; SFmode. The first is the normal insn, the second the same insn but 15235;; with one operand a conversion, and the third the same insn but with 15236;; the other operand a conversion. The conversion may be SFmode or 15237;; SImode if the target mode DFmode, but only SImode if the target mode 15238;; is SFmode. 15239 15240;; Gcc is slightly more smart about handling normal two address instructions 15241;; so use special patterns for add and mull. 15242 15243(define_insn "*fop_sf_comm_mixed" 15244 [(set (match_operand:SF 0 "register_operand" "=f,x") 15245 (match_operator:SF 3 "binary_fp_operator" 15246 [(match_operand:SF 1 "nonimmediate_operand" "%0,0") 15247 (match_operand:SF 2 "nonimmediate_operand" "fm,xm")]))] 15248 "TARGET_MIX_SSE_I387 15249 && COMMUTATIVE_ARITH_P (operands[3]) 15250 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15251 "* return output_387_binary_op (insn, operands);" 15252 [(set (attr "type") 15253 (if_then_else (eq_attr "alternative" "1") 15254 (if_then_else (match_operand:SF 3 "mult_operator" "") 15255 (const_string "ssemul") 15256 (const_string "sseadd")) 15257 (if_then_else (match_operand:SF 3 "mult_operator" "") 15258 (const_string "fmul") 15259 (const_string "fop")))) 15260 (set_attr "mode" "SF")]) 15261 15262(define_insn "*fop_sf_comm_sse" 15263 [(set (match_operand:SF 0 "register_operand" "=x") 15264 (match_operator:SF 3 "binary_fp_operator" 15265 [(match_operand:SF 1 "nonimmediate_operand" "%0") 15266 (match_operand:SF 2 "nonimmediate_operand" "xm")]))] 15267 "TARGET_SSE_MATH 15268 && COMMUTATIVE_ARITH_P (operands[3]) 15269 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15270 "* return output_387_binary_op (insn, operands);" 15271 [(set (attr "type") 15272 (if_then_else (match_operand:SF 3 "mult_operator" "") 15273 (const_string "ssemul") 15274 (const_string "sseadd"))) 15275 (set_attr "mode" "SF")]) 15276 15277(define_insn "*fop_sf_comm_i387" 15278 [(set (match_operand:SF 0 "register_operand" "=f") 15279 (match_operator:SF 3 "binary_fp_operator" 15280 [(match_operand:SF 1 "nonimmediate_operand" "%0") 15281 (match_operand:SF 2 "nonimmediate_operand" "fm")]))] 15282 "TARGET_80387 15283 && COMMUTATIVE_ARITH_P (operands[3]) 15284 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15285 "* return output_387_binary_op (insn, operands);" 15286 [(set (attr "type") 15287 (if_then_else (match_operand:SF 3 "mult_operator" "") 15288 (const_string "fmul") 15289 (const_string "fop"))) 15290 (set_attr "mode" "SF")]) 15291 15292(define_insn "*fop_sf_1_mixed" 15293 [(set (match_operand:SF 0 "register_operand" "=f,f,x") 15294 (match_operator:SF 3 "binary_fp_operator" 15295 [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0") 15296 (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm")]))] 15297 "TARGET_MIX_SSE_I387 15298 && !COMMUTATIVE_ARITH_P (operands[3]) 15299 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15300 "* return output_387_binary_op (insn, operands);" 15301 [(set (attr "type") 15302 (cond [(and (eq_attr "alternative" "2") 15303 (match_operand:SF 3 "mult_operator" "")) 15304 (const_string "ssemul") 15305 (and (eq_attr "alternative" "2") 15306 (match_operand:SF 3 "div_operator" "")) 15307 (const_string "ssediv") 15308 (eq_attr "alternative" "2") 15309 (const_string "sseadd") 15310 (match_operand:SF 3 "mult_operator" "") 15311 (const_string "fmul") 15312 (match_operand:SF 3 "div_operator" "") 15313 (const_string "fdiv") 15314 ] 15315 (const_string "fop"))) 15316 (set_attr "mode" "SF")]) 15317 15318(define_insn "*fop_sf_1_sse" 15319 [(set (match_operand:SF 0 "register_operand" "=x") 15320 (match_operator:SF 3 "binary_fp_operator" 15321 [(match_operand:SF 1 "register_operand" "0") 15322 (match_operand:SF 2 "nonimmediate_operand" "xm")]))] 15323 "TARGET_SSE_MATH 15324 && !COMMUTATIVE_ARITH_P (operands[3])" 15325 "* return output_387_binary_op (insn, operands);" 15326 [(set (attr "type") 15327 (cond [(match_operand:SF 3 "mult_operator" "") 15328 (const_string "ssemul") 15329 (match_operand:SF 3 "div_operator" "") 15330 (const_string "ssediv") 15331 ] 15332 (const_string "sseadd"))) 15333 (set_attr "mode" "SF")]) 15334 15335;; This pattern is not fully shadowed by the pattern above. 15336(define_insn "*fop_sf_1_i387" 15337 [(set (match_operand:SF 0 "register_operand" "=f,f") 15338 (match_operator:SF 3 "binary_fp_operator" 15339 [(match_operand:SF 1 "nonimmediate_operand" "0,fm") 15340 (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))] 15341 "TARGET_80387 && !TARGET_SSE_MATH 15342 && !COMMUTATIVE_ARITH_P (operands[3]) 15343 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15344 "* return output_387_binary_op (insn, operands);" 15345 [(set (attr "type") 15346 (cond [(match_operand:SF 3 "mult_operator" "") 15347 (const_string "fmul") 15348 (match_operand:SF 3 "div_operator" "") 15349 (const_string "fdiv") 15350 ] 15351 (const_string "fop"))) 15352 (set_attr "mode" "SF")]) 15353 15354;; ??? Add SSE splitters for these! 15355(define_insn "*fop_sf_2<mode>_i387" 15356 [(set (match_operand:SF 0 "register_operand" "=f,f") 15357 (match_operator:SF 3 "binary_fp_operator" 15358 [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r")) 15359 (match_operand:SF 2 "register_operand" "0,0")]))] 15360 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH" 15361 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15362 [(set (attr "type") 15363 (cond [(match_operand:SF 3 "mult_operator" "") 15364 (const_string "fmul") 15365 (match_operand:SF 3 "div_operator" "") 15366 (const_string "fdiv") 15367 ] 15368 (const_string "fop"))) 15369 (set_attr "fp_int_src" "true") 15370 (set_attr "mode" "<MODE>")]) 15371 15372(define_insn "*fop_sf_3<mode>_i387" 15373 [(set (match_operand:SF 0 "register_operand" "=f,f") 15374 (match_operator:SF 3 "binary_fp_operator" 15375 [(match_operand:SF 1 "register_operand" "0,0") 15376 (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))] 15377 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH" 15378 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15379 [(set (attr "type") 15380 (cond [(match_operand:SF 3 "mult_operator" "") 15381 (const_string "fmul") 15382 (match_operand:SF 3 "div_operator" "") 15383 (const_string "fdiv") 15384 ] 15385 (const_string "fop"))) 15386 (set_attr "fp_int_src" "true") 15387 (set_attr "mode" "<MODE>")]) 15388 15389(define_insn "*fop_df_comm_mixed" 15390 [(set (match_operand:DF 0 "register_operand" "=f,Y") 15391 (match_operator:DF 3 "binary_fp_operator" 15392 [(match_operand:DF 1 "nonimmediate_operand" "%0,0") 15393 (match_operand:DF 2 "nonimmediate_operand" "fm,Ym")]))] 15394 "TARGET_SSE2 && TARGET_MIX_SSE_I387 15395 && COMMUTATIVE_ARITH_P (operands[3]) 15396 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15397 "* return output_387_binary_op (insn, operands);" 15398 [(set (attr "type") 15399 (if_then_else (eq_attr "alternative" "1") 15400 (if_then_else (match_operand:DF 3 "mult_operator" "") 15401 (const_string "ssemul") 15402 (const_string "sseadd")) 15403 (if_then_else (match_operand:DF 3 "mult_operator" "") 15404 (const_string "fmul") 15405 (const_string "fop")))) 15406 (set_attr "mode" "DF")]) 15407 15408(define_insn "*fop_df_comm_sse" 15409 [(set (match_operand:DF 0 "register_operand" "=Y") 15410 (match_operator:DF 3 "binary_fp_operator" 15411 [(match_operand:DF 1 "nonimmediate_operand" "%0") 15412 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))] 15413 "TARGET_SSE2 && TARGET_SSE_MATH 15414 && COMMUTATIVE_ARITH_P (operands[3]) 15415 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15416 "* return output_387_binary_op (insn, operands);" 15417 [(set (attr "type") 15418 (if_then_else (match_operand:DF 3 "mult_operator" "") 15419 (const_string "ssemul") 15420 (const_string "sseadd"))) 15421 (set_attr "mode" "DF")]) 15422 15423(define_insn "*fop_df_comm_i387" 15424 [(set (match_operand:DF 0 "register_operand" "=f") 15425 (match_operator:DF 3 "binary_fp_operator" 15426 [(match_operand:DF 1 "nonimmediate_operand" "%0") 15427 (match_operand:DF 2 "nonimmediate_operand" "fm")]))] 15428 "TARGET_80387 15429 && COMMUTATIVE_ARITH_P (operands[3]) 15430 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15431 "* return output_387_binary_op (insn, operands);" 15432 [(set (attr "type") 15433 (if_then_else (match_operand:DF 3 "mult_operator" "") 15434 (const_string "fmul") 15435 (const_string "fop"))) 15436 (set_attr "mode" "DF")]) 15437 15438(define_insn "*fop_df_1_mixed" 15439 [(set (match_operand:DF 0 "register_operand" "=f,f,Y") 15440 (match_operator:DF 3 "binary_fp_operator" 15441 [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0") 15442 (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym")]))] 15443 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387 15444 && !COMMUTATIVE_ARITH_P (operands[3]) 15445 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15446 "* return output_387_binary_op (insn, operands);" 15447 [(set (attr "type") 15448 (cond [(and (eq_attr "alternative" "2") 15449 (match_operand:DF 3 "mult_operator" "")) 15450 (const_string "ssemul") 15451 (and (eq_attr "alternative" "2") 15452 (match_operand:DF 3 "div_operator" "")) 15453 (const_string "ssediv") 15454 (eq_attr "alternative" "2") 15455 (const_string "sseadd") 15456 (match_operand:DF 3 "mult_operator" "") 15457 (const_string "fmul") 15458 (match_operand:DF 3 "div_operator" "") 15459 (const_string "fdiv") 15460 ] 15461 (const_string "fop"))) 15462 (set_attr "mode" "DF")]) 15463 15464(define_insn "*fop_df_1_sse" 15465 [(set (match_operand:DF 0 "register_operand" "=Y") 15466 (match_operator:DF 3 "binary_fp_operator" 15467 [(match_operand:DF 1 "register_operand" "0") 15468 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))] 15469 "TARGET_SSE2 && TARGET_SSE_MATH 15470 && !COMMUTATIVE_ARITH_P (operands[3])" 15471 "* return output_387_binary_op (insn, operands);" 15472 [(set_attr "mode" "DF") 15473 (set (attr "type") 15474 (cond [(match_operand:DF 3 "mult_operator" "") 15475 (const_string "ssemul") 15476 (match_operand:DF 3 "div_operator" "") 15477 (const_string "ssediv") 15478 ] 15479 (const_string "sseadd")))]) 15480 15481;; This pattern is not fully shadowed by the pattern above. 15482(define_insn "*fop_df_1_i387" 15483 [(set (match_operand:DF 0 "register_operand" "=f,f") 15484 (match_operator:DF 3 "binary_fp_operator" 15485 [(match_operand:DF 1 "nonimmediate_operand" "0,fm") 15486 (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))] 15487 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH) 15488 && !COMMUTATIVE_ARITH_P (operands[3]) 15489 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15490 "* return output_387_binary_op (insn, operands);" 15491 [(set (attr "type") 15492 (cond [(match_operand:DF 3 "mult_operator" "") 15493 (const_string "fmul") 15494 (match_operand:DF 3 "div_operator" "") 15495 (const_string "fdiv") 15496 ] 15497 (const_string "fop"))) 15498 (set_attr "mode" "DF")]) 15499 15500;; ??? Add SSE splitters for these! 15501(define_insn "*fop_df_2<mode>_i387" 15502 [(set (match_operand:DF 0 "register_operand" "=f,f") 15503 (match_operator:DF 3 "binary_fp_operator" 15504 [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r")) 15505 (match_operand:DF 2 "register_operand" "0,0")]))] 15506 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP 15507 && !(TARGET_SSE2 && TARGET_SSE_MATH)" 15508 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15509 [(set (attr "type") 15510 (cond [(match_operand:DF 3 "mult_operator" "") 15511 (const_string "fmul") 15512 (match_operand:DF 3 "div_operator" "") 15513 (const_string "fdiv") 15514 ] 15515 (const_string "fop"))) 15516 (set_attr "fp_int_src" "true") 15517 (set_attr "mode" "<MODE>")]) 15518 15519(define_insn "*fop_df_3<mode>_i387" 15520 [(set (match_operand:DF 0 "register_operand" "=f,f") 15521 (match_operator:DF 3 "binary_fp_operator" 15522 [(match_operand:DF 1 "register_operand" "0,0") 15523 (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))] 15524 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP 15525 && !(TARGET_SSE2 && TARGET_SSE_MATH)" 15526 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15527 [(set (attr "type") 15528 (cond [(match_operand:DF 3 "mult_operator" "") 15529 (const_string "fmul") 15530 (match_operand:DF 3 "div_operator" "") 15531 (const_string "fdiv") 15532 ] 15533 (const_string "fop"))) 15534 (set_attr "fp_int_src" "true") 15535 (set_attr "mode" "<MODE>")]) 15536 15537(define_insn "*fop_df_4_i387" 15538 [(set (match_operand:DF 0 "register_operand" "=f,f") 15539 (match_operator:DF 3 "binary_fp_operator" 15540 [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0")) 15541 (match_operand:DF 2 "register_operand" "0,f")]))] 15542 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH) 15543 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)" 15544 "* return output_387_binary_op (insn, operands);" 15545 [(set (attr "type") 15546 (cond [(match_operand:DF 3 "mult_operator" "") 15547 (const_string "fmul") 15548 (match_operand:DF 3 "div_operator" "") 15549 (const_string "fdiv") 15550 ] 15551 (const_string "fop"))) 15552 (set_attr "mode" "SF")]) 15553 15554(define_insn "*fop_df_5_i387" 15555 [(set (match_operand:DF 0 "register_operand" "=f,f") 15556 (match_operator:DF 3 "binary_fp_operator" 15557 [(match_operand:DF 1 "register_operand" "0,f") 15558 (float_extend:DF 15559 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))] 15560 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)" 15561 "* return output_387_binary_op (insn, operands);" 15562 [(set (attr "type") 15563 (cond [(match_operand:DF 3 "mult_operator" "") 15564 (const_string "fmul") 15565 (match_operand:DF 3 "div_operator" "") 15566 (const_string "fdiv") 15567 ] 15568 (const_string "fop"))) 15569 (set_attr "mode" "SF")]) 15570 15571(define_insn "*fop_df_6_i387" 15572 [(set (match_operand:DF 0 "register_operand" "=f,f") 15573 (match_operator:DF 3 "binary_fp_operator" 15574 [(float_extend:DF 15575 (match_operand:SF 1 "register_operand" "0,f")) 15576 (float_extend:DF 15577 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))] 15578 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)" 15579 "* return output_387_binary_op (insn, operands);" 15580 [(set (attr "type") 15581 (cond [(match_operand:DF 3 "mult_operator" "") 15582 (const_string "fmul") 15583 (match_operand:DF 3 "div_operator" "") 15584 (const_string "fdiv") 15585 ] 15586 (const_string "fop"))) 15587 (set_attr "mode" "SF")]) 15588 15589(define_insn "*fop_xf_comm_i387" 15590 [(set (match_operand:XF 0 "register_operand" "=f") 15591 (match_operator:XF 3 "binary_fp_operator" 15592 [(match_operand:XF 1 "register_operand" "%0") 15593 (match_operand:XF 2 "register_operand" "f")]))] 15594 "TARGET_80387 15595 && COMMUTATIVE_ARITH_P (operands[3])" 15596 "* return output_387_binary_op (insn, operands);" 15597 [(set (attr "type") 15598 (if_then_else (match_operand:XF 3 "mult_operator" "") 15599 (const_string "fmul") 15600 (const_string "fop"))) 15601 (set_attr "mode" "XF")]) 15602 15603(define_insn "*fop_xf_1_i387" 15604 [(set (match_operand:XF 0 "register_operand" "=f,f") 15605 (match_operator:XF 3 "binary_fp_operator" 15606 [(match_operand:XF 1 "register_operand" "0,f") 15607 (match_operand:XF 2 "register_operand" "f,0")]))] 15608 "TARGET_80387 15609 && !COMMUTATIVE_ARITH_P (operands[3])" 15610 "* return output_387_binary_op (insn, operands);" 15611 [(set (attr "type") 15612 (cond [(match_operand:XF 3 "mult_operator" "") 15613 (const_string "fmul") 15614 (match_operand:XF 3 "div_operator" "") 15615 (const_string "fdiv") 15616 ] 15617 (const_string "fop"))) 15618 (set_attr "mode" "XF")]) 15619 15620(define_insn "*fop_xf_2<mode>_i387" 15621 [(set (match_operand:XF 0 "register_operand" "=f,f") 15622 (match_operator:XF 3 "binary_fp_operator" 15623 [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r")) 15624 (match_operand:XF 2 "register_operand" "0,0")]))] 15625 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP" 15626 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15627 [(set (attr "type") 15628 (cond [(match_operand:XF 3 "mult_operator" "") 15629 (const_string "fmul") 15630 (match_operand:XF 3 "div_operator" "") 15631 (const_string "fdiv") 15632 ] 15633 (const_string "fop"))) 15634 (set_attr "fp_int_src" "true") 15635 (set_attr "mode" "<MODE>")]) 15636 15637(define_insn "*fop_xf_3<mode>_i387" 15638 [(set (match_operand:XF 0 "register_operand" "=f,f") 15639 (match_operator:XF 3 "binary_fp_operator" 15640 [(match_operand:XF 1 "register_operand" "0,0") 15641 (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))] 15642 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP" 15643 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);" 15644 [(set (attr "type") 15645 (cond [(match_operand:XF 3 "mult_operator" "") 15646 (const_string "fmul") 15647 (match_operand:XF 3 "div_operator" "") 15648 (const_string "fdiv") 15649 ] 15650 (const_string "fop"))) 15651 (set_attr "fp_int_src" "true") 15652 (set_attr "mode" "<MODE>")]) 15653 15654(define_insn "*fop_xf_4_i387" 15655 [(set (match_operand:XF 0 "register_operand" "=f,f") 15656 (match_operator:XF 3 "binary_fp_operator" 15657 [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0")) 15658 (match_operand:XF 2 "register_operand" "0,f")]))] 15659 "TARGET_80387" 15660 "* return output_387_binary_op (insn, operands);" 15661 [(set (attr "type") 15662 (cond [(match_operand:XF 3 "mult_operator" "") 15663 (const_string "fmul") 15664 (match_operand:XF 3 "div_operator" "") 15665 (const_string "fdiv") 15666 ] 15667 (const_string "fop"))) 15668 (set_attr "mode" "SF")]) 15669 15670(define_insn "*fop_xf_5_i387" 15671 [(set (match_operand:XF 0 "register_operand" "=f,f") 15672 (match_operator:XF 3 "binary_fp_operator" 15673 [(match_operand:XF 1 "register_operand" "0,f") 15674 (float_extend:XF 15675 (match_operand 2 "nonimmediate_operand" "fm,0"))]))] 15676 "TARGET_80387" 15677 "* return output_387_binary_op (insn, operands);" 15678 [(set (attr "type") 15679 (cond [(match_operand:XF 3 "mult_operator" "") 15680 (const_string "fmul") 15681 (match_operand:XF 3 "div_operator" "") 15682 (const_string "fdiv") 15683 ] 15684 (const_string "fop"))) 15685 (set_attr "mode" "SF")]) 15686 15687(define_insn "*fop_xf_6_i387" 15688 [(set (match_operand:XF 0 "register_operand" "=f,f") 15689 (match_operator:XF 3 "binary_fp_operator" 15690 [(float_extend:XF 15691 (match_operand 1 "register_operand" "0,f")) 15692 (float_extend:XF 15693 (match_operand 2 "nonimmediate_operand" "fm,0"))]))] 15694 "TARGET_80387" 15695 "* return output_387_binary_op (insn, operands);" 15696 [(set (attr "type") 15697 (cond [(match_operand:XF 3 "mult_operator" "") 15698 (const_string "fmul") 15699 (match_operand:XF 3 "div_operator" "") 15700 (const_string "fdiv") 15701 ] 15702 (const_string "fop"))) 15703 (set_attr "mode" "SF")]) 15704 15705(define_split 15706 [(set (match_operand 0 "register_operand" "") 15707 (match_operator 3 "binary_fp_operator" 15708 [(float (match_operand:X87MODEI12 1 "register_operand" "")) 15709 (match_operand 2 "register_operand" "")]))] 15710 "TARGET_80387 && reload_completed 15711 && FLOAT_MODE_P (GET_MODE (operands[0]))" 15712 [(const_int 0)] 15713{ 15714 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]); 15715 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]); 15716 emit_insn (gen_rtx_SET (VOIDmode, operands[0], 15717 gen_rtx_fmt_ee (GET_CODE (operands[3]), 15718 GET_MODE (operands[3]), 15719 operands[4], 15720 operands[2]))); 15721 ix86_free_from_memory (GET_MODE (operands[1])); 15722 DONE; 15723}) 15724 15725(define_split 15726 [(set (match_operand 0 "register_operand" "") 15727 (match_operator 3 "binary_fp_operator" 15728 [(match_operand 1 "register_operand" "") 15729 (float (match_operand:X87MODEI12 2 "register_operand" ""))]))] 15730 "TARGET_80387 && reload_completed 15731 && FLOAT_MODE_P (GET_MODE (operands[0]))" 15732 [(const_int 0)] 15733{ 15734 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]); 15735 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]); 15736 emit_insn (gen_rtx_SET (VOIDmode, operands[0], 15737 gen_rtx_fmt_ee (GET_CODE (operands[3]), 15738 GET_MODE (operands[3]), 15739 operands[1], 15740 operands[4]))); 15741 ix86_free_from_memory (GET_MODE (operands[2])); 15742 DONE; 15743}) 15744 15745;; FPU special functions. 15746 15747(define_expand "sqrtsf2" 15748 [(set (match_operand:SF 0 "register_operand" "") 15749 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))] 15750 "TARGET_USE_FANCY_MATH_387 || TARGET_SSE_MATH" 15751{ 15752 if (!TARGET_SSE_MATH) 15753 operands[1] = force_reg (SFmode, operands[1]); 15754}) 15755 15756(define_insn "*sqrtsf2_mixed" 15757 [(set (match_operand:SF 0 "register_operand" "=f,x") 15758 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0,xm")))] 15759 "TARGET_USE_FANCY_MATH_387 && TARGET_MIX_SSE_I387" 15760 "@ 15761 fsqrt 15762 sqrtss\t{%1, %0|%0, %1}" 15763 [(set_attr "type" "fpspc,sse") 15764 (set_attr "mode" "SF,SF") 15765 (set_attr "athlon_decode" "direct,*") 15766 (set_attr "amdfam10_decode" "direct,*")]) 15767 15768(define_insn "*sqrtsf2_sse" 15769 [(set (match_operand:SF 0 "register_operand" "=x") 15770 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))] 15771 "TARGET_SSE_MATH" 15772 "sqrtss\t{%1, %0|%0, %1}" 15773 [(set_attr "type" "sse") 15774 (set_attr "mode" "SF") 15775 (set_attr "athlon_decode" "*") 15776 (set_attr "amdfam10_decode" "*")]) 15777 15778(define_insn "*sqrtsf2_i387" 15779 [(set (match_operand:SF 0 "register_operand" "=f") 15780 (sqrt:SF (match_operand:SF 1 "register_operand" "0")))] 15781 "TARGET_USE_FANCY_MATH_387" 15782 "fsqrt" 15783 [(set_attr "type" "fpspc") 15784 (set_attr "mode" "SF") 15785 (set_attr "athlon_decode" "direct") 15786 (set_attr "amdfam10_decode" "direct")]) 15787 15788(define_expand "sqrtdf2" 15789 [(set (match_operand:DF 0 "register_operand" "") 15790 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))] 15791 "TARGET_USE_FANCY_MATH_387 || (TARGET_SSE2 && TARGET_SSE_MATH)" 15792{ 15793 if (!(TARGET_SSE2 && TARGET_SSE_MATH)) 15794 operands[1] = force_reg (DFmode, operands[1]); 15795}) 15796 15797(define_insn "*sqrtdf2_mixed" 15798 [(set (match_operand:DF 0 "register_operand" "=f,Y") 15799 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0,Ym")))] 15800 "TARGET_USE_FANCY_MATH_387 && TARGET_SSE2 && TARGET_MIX_SSE_I387" 15801 "@ 15802 fsqrt 15803 sqrtsd\t{%1, %0|%0, %1}" 15804 [(set_attr "type" "fpspc,sse") 15805 (set_attr "mode" "DF,DF") 15806 (set_attr "athlon_decode" "direct,*") 15807 (set_attr "amdfam10_decode" "direct,*")]) 15808 15809(define_insn "*sqrtdf2_sse" 15810 [(set (match_operand:DF 0 "register_operand" "=Y") 15811 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))] 15812 "TARGET_SSE2 && TARGET_SSE_MATH" 15813 "sqrtsd\t{%1, %0|%0, %1}" 15814 [(set_attr "type" "sse") 15815 (set_attr "mode" "DF") 15816 (set_attr "athlon_decode" "*") 15817 (set_attr "amdfam10_decode" "*")]) 15818 15819(define_insn "*sqrtdf2_i387" 15820 [(set (match_operand:DF 0 "register_operand" "=f") 15821 (sqrt:DF (match_operand:DF 1 "register_operand" "0")))] 15822 "TARGET_USE_FANCY_MATH_387" 15823 "fsqrt" 15824 [(set_attr "type" "fpspc") 15825 (set_attr "mode" "DF") 15826 (set_attr "athlon_decode" "direct") 15827 (set_attr "amdfam10_decode" "direct")]) 15828 15829(define_insn "*sqrtextendsfdf2_i387" 15830 [(set (match_operand:DF 0 "register_operand" "=f") 15831 (sqrt:DF (float_extend:DF 15832 (match_operand:SF 1 "register_operand" "0"))))] 15833 "TARGET_USE_FANCY_MATH_387 15834 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)" 15835 "fsqrt" 15836 [(set_attr "type" "fpspc") 15837 (set_attr "mode" "DF") 15838 (set_attr "athlon_decode" "direct") 15839 (set_attr "amdfam10_decode" "direct")]) 15840 15841(define_insn "sqrtxf2" 15842 [(set (match_operand:XF 0 "register_operand" "=f") 15843 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))] 15844 "TARGET_USE_FANCY_MATH_387" 15845 "fsqrt" 15846 [(set_attr "type" "fpspc") 15847 (set_attr "mode" "XF") 15848 (set_attr "athlon_decode" "direct") 15849 (set_attr "amdfam10_decode" "direct")]) 15850 15851(define_insn "*sqrtextendsfxf2_i387" 15852 [(set (match_operand:XF 0 "register_operand" "=f") 15853 (sqrt:XF (float_extend:XF 15854 (match_operand:SF 1 "register_operand" "0"))))] 15855 "TARGET_USE_FANCY_MATH_387" 15856 "fsqrt" 15857 [(set_attr "type" "fpspc") 15858 (set_attr "mode" "XF") 15859 (set_attr "athlon_decode" "direct") 15860 (set_attr "amdfam10_decode" "direct")]) 15861 15862(define_insn "*sqrtextenddfxf2_i387" 15863 [(set (match_operand:XF 0 "register_operand" "=f") 15864 (sqrt:XF (float_extend:XF 15865 (match_operand:DF 1 "register_operand" "0"))))] 15866 "TARGET_USE_FANCY_MATH_387" 15867 "fsqrt" 15868 [(set_attr "type" "fpspc") 15869 (set_attr "mode" "XF") 15870 (set_attr "athlon_decode" "direct") 15871 (set_attr "amdfam10_decode" "direct")]) 15872 15873(define_insn "fpremxf4" 15874 [(set (match_operand:XF 0 "register_operand" "=f") 15875 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 15876 (match_operand:XF 3 "register_operand" "1")] 15877 UNSPEC_FPREM_F)) 15878 (set (match_operand:XF 1 "register_operand" "=u") 15879 (unspec:XF [(match_dup 2) (match_dup 3)] 15880 UNSPEC_FPREM_U)) 15881 (set (reg:CCFP FPSR_REG) 15882 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))] 15883 "TARGET_USE_FANCY_MATH_387 15884 && flag_unsafe_math_optimizations" 15885 "fprem" 15886 [(set_attr "type" "fpspc") 15887 (set_attr "mode" "XF")]) 15888 15889(define_expand "fmodsf3" 15890 [(use (match_operand:SF 0 "register_operand" "")) 15891 (use (match_operand:SF 1 "register_operand" "")) 15892 (use (match_operand:SF 2 "register_operand" ""))] 15893 "TARGET_USE_FANCY_MATH_387 15894 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 15895 && flag_unsafe_math_optimizations" 15896{ 15897 rtx label = gen_label_rtx (); 15898 15899 rtx op1 = gen_reg_rtx (XFmode); 15900 rtx op2 = gen_reg_rtx (XFmode); 15901 15902 emit_insn(gen_extendsfxf2 (op1, operands[1])); 15903 emit_insn(gen_extendsfxf2 (op2, operands[2])); 15904 15905 emit_label (label); 15906 15907 emit_insn (gen_fpremxf4 (op1, op2, op1, op2)); 15908 ix86_emit_fp_unordered_jump (label); 15909 15910 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1)); 15911 DONE; 15912}) 15913 15914(define_expand "fmoddf3" 15915 [(use (match_operand:DF 0 "register_operand" "")) 15916 (use (match_operand:DF 1 "register_operand" "")) 15917 (use (match_operand:DF 2 "register_operand" ""))] 15918 "TARGET_USE_FANCY_MATH_387 15919 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 15920 && flag_unsafe_math_optimizations" 15921{ 15922 rtx label = gen_label_rtx (); 15923 15924 rtx op1 = gen_reg_rtx (XFmode); 15925 rtx op2 = gen_reg_rtx (XFmode); 15926 15927 emit_insn (gen_extenddfxf2 (op1, operands[1])); 15928 emit_insn (gen_extenddfxf2 (op2, operands[2])); 15929 15930 emit_label (label); 15931 15932 emit_insn (gen_fpremxf4 (op1, op2, op1, op2)); 15933 ix86_emit_fp_unordered_jump (label); 15934 15935 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1)); 15936 DONE; 15937}) 15938 15939(define_expand "fmodxf3" 15940 [(use (match_operand:XF 0 "register_operand" "")) 15941 (use (match_operand:XF 1 "register_operand" "")) 15942 (use (match_operand:XF 2 "register_operand" ""))] 15943 "TARGET_USE_FANCY_MATH_387 15944 && flag_unsafe_math_optimizations" 15945{ 15946 rtx label = gen_label_rtx (); 15947 15948 emit_label (label); 15949 15950 emit_insn (gen_fpremxf4 (operands[1], operands[2], 15951 operands[1], operands[2])); 15952 ix86_emit_fp_unordered_jump (label); 15953 15954 emit_move_insn (operands[0], operands[1]); 15955 DONE; 15956}) 15957 15958(define_insn "fprem1xf4" 15959 [(set (match_operand:XF 0 "register_operand" "=f") 15960 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 15961 (match_operand:XF 3 "register_operand" "1")] 15962 UNSPEC_FPREM1_F)) 15963 (set (match_operand:XF 1 "register_operand" "=u") 15964 (unspec:XF [(match_dup 2) (match_dup 3)] 15965 UNSPEC_FPREM1_U)) 15966 (set (reg:CCFP FPSR_REG) 15967 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))] 15968 "TARGET_USE_FANCY_MATH_387 15969 && flag_unsafe_math_optimizations" 15970 "fprem1" 15971 [(set_attr "type" "fpspc") 15972 (set_attr "mode" "XF")]) 15973 15974(define_expand "dremsf3" 15975 [(use (match_operand:SF 0 "register_operand" "")) 15976 (use (match_operand:SF 1 "register_operand" "")) 15977 (use (match_operand:SF 2 "register_operand" ""))] 15978 "TARGET_USE_FANCY_MATH_387 15979 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 15980 && flag_unsafe_math_optimizations" 15981{ 15982 rtx label = gen_label_rtx (); 15983 15984 rtx op1 = gen_reg_rtx (XFmode); 15985 rtx op2 = gen_reg_rtx (XFmode); 15986 15987 emit_insn(gen_extendsfxf2 (op1, operands[1])); 15988 emit_insn(gen_extendsfxf2 (op2, operands[2])); 15989 15990 emit_label (label); 15991 15992 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2)); 15993 ix86_emit_fp_unordered_jump (label); 15994 15995 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1)); 15996 DONE; 15997}) 15998 15999(define_expand "dremdf3" 16000 [(use (match_operand:DF 0 "register_operand" "")) 16001 (use (match_operand:DF 1 "register_operand" "")) 16002 (use (match_operand:DF 2 "register_operand" ""))] 16003 "TARGET_USE_FANCY_MATH_387 16004 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16005 && flag_unsafe_math_optimizations" 16006{ 16007 rtx label = gen_label_rtx (); 16008 16009 rtx op1 = gen_reg_rtx (XFmode); 16010 rtx op2 = gen_reg_rtx (XFmode); 16011 16012 emit_insn (gen_extenddfxf2 (op1, operands[1])); 16013 emit_insn (gen_extenddfxf2 (op2, operands[2])); 16014 16015 emit_label (label); 16016 16017 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2)); 16018 ix86_emit_fp_unordered_jump (label); 16019 16020 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1)); 16021 DONE; 16022}) 16023 16024(define_expand "dremxf3" 16025 [(use (match_operand:XF 0 "register_operand" "")) 16026 (use (match_operand:XF 1 "register_operand" "")) 16027 (use (match_operand:XF 2 "register_operand" ""))] 16028 "TARGET_USE_FANCY_MATH_387 16029 && flag_unsafe_math_optimizations" 16030{ 16031 rtx label = gen_label_rtx (); 16032 16033 emit_label (label); 16034 16035 emit_insn (gen_fprem1xf4 (operands[1], operands[2], 16036 operands[1], operands[2])); 16037 ix86_emit_fp_unordered_jump (label); 16038 16039 emit_move_insn (operands[0], operands[1]); 16040 DONE; 16041}) 16042 16043(define_insn "*sindf2" 16044 [(set (match_operand:DF 0 "register_operand" "=f") 16045 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))] 16046 "TARGET_USE_FANCY_MATH_387 16047 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16048 && flag_unsafe_math_optimizations" 16049 "fsin" 16050 [(set_attr "type" "fpspc") 16051 (set_attr "mode" "DF")]) 16052 16053(define_insn "*sinsf2" 16054 [(set (match_operand:SF 0 "register_operand" "=f") 16055 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))] 16056 "TARGET_USE_FANCY_MATH_387 16057 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16058 && flag_unsafe_math_optimizations" 16059 "fsin" 16060 [(set_attr "type" "fpspc") 16061 (set_attr "mode" "SF")]) 16062 16063(define_insn "*sinextendsfdf2" 16064 [(set (match_operand:DF 0 "register_operand" "=f") 16065 (unspec:DF [(float_extend:DF 16066 (match_operand:SF 1 "register_operand" "0"))] 16067 UNSPEC_SIN))] 16068 "TARGET_USE_FANCY_MATH_387 16069 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16070 && flag_unsafe_math_optimizations" 16071 "fsin" 16072 [(set_attr "type" "fpspc") 16073 (set_attr "mode" "DF")]) 16074 16075(define_insn "*sinxf2" 16076 [(set (match_operand:XF 0 "register_operand" "=f") 16077 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))] 16078 "TARGET_USE_FANCY_MATH_387 16079 && flag_unsafe_math_optimizations" 16080 "fsin" 16081 [(set_attr "type" "fpspc") 16082 (set_attr "mode" "XF")]) 16083 16084(define_insn "*cosdf2" 16085 [(set (match_operand:DF 0 "register_operand" "=f") 16086 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))] 16087 "TARGET_USE_FANCY_MATH_387 16088 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16089 && flag_unsafe_math_optimizations" 16090 "fcos" 16091 [(set_attr "type" "fpspc") 16092 (set_attr "mode" "DF")]) 16093 16094(define_insn "*cossf2" 16095 [(set (match_operand:SF 0 "register_operand" "=f") 16096 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))] 16097 "TARGET_USE_FANCY_MATH_387 16098 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16099 && flag_unsafe_math_optimizations" 16100 "fcos" 16101 [(set_attr "type" "fpspc") 16102 (set_attr "mode" "SF")]) 16103 16104(define_insn "*cosextendsfdf2" 16105 [(set (match_operand:DF 0 "register_operand" "=f") 16106 (unspec:DF [(float_extend:DF 16107 (match_operand:SF 1 "register_operand" "0"))] 16108 UNSPEC_COS))] 16109 "TARGET_USE_FANCY_MATH_387 16110 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16111 && flag_unsafe_math_optimizations" 16112 "fcos" 16113 [(set_attr "type" "fpspc") 16114 (set_attr "mode" "DF")]) 16115 16116(define_insn "*cosxf2" 16117 [(set (match_operand:XF 0 "register_operand" "=f") 16118 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))] 16119 "TARGET_USE_FANCY_MATH_387 16120 && flag_unsafe_math_optimizations" 16121 "fcos" 16122 [(set_attr "type" "fpspc") 16123 (set_attr "mode" "XF")]) 16124 16125;; With sincos pattern defined, sin and cos builtin function will be 16126;; expanded to sincos pattern with one of its outputs left unused. 16127;; Cse pass will detected, if two sincos patterns can be combined, 16128;; otherwise sincos pattern will be split back to sin or cos pattern, 16129;; depending on the unused output. 16130 16131(define_insn "sincosdf3" 16132 [(set (match_operand:DF 0 "register_operand" "=f") 16133 (unspec:DF [(match_operand:DF 2 "register_operand" "0")] 16134 UNSPEC_SINCOS_COS)) 16135 (set (match_operand:DF 1 "register_operand" "=u") 16136 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16137 "TARGET_USE_FANCY_MATH_387 16138 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16139 && flag_unsafe_math_optimizations" 16140 "fsincos" 16141 [(set_attr "type" "fpspc") 16142 (set_attr "mode" "DF")]) 16143 16144(define_split 16145 [(set (match_operand:DF 0 "register_operand" "") 16146 (unspec:DF [(match_operand:DF 2 "register_operand" "")] 16147 UNSPEC_SINCOS_COS)) 16148 (set (match_operand:DF 1 "register_operand" "") 16149 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16150 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0])) 16151 && !reload_completed && !reload_in_progress" 16152 [(set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_SIN))] 16153 "") 16154 16155(define_split 16156 [(set (match_operand:DF 0 "register_operand" "") 16157 (unspec:DF [(match_operand:DF 2 "register_operand" "")] 16158 UNSPEC_SINCOS_COS)) 16159 (set (match_operand:DF 1 "register_operand" "") 16160 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16161 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1])) 16162 && !reload_completed && !reload_in_progress" 16163 [(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_COS))] 16164 "") 16165 16166(define_insn "sincossf3" 16167 [(set (match_operand:SF 0 "register_operand" "=f") 16168 (unspec:SF [(match_operand:SF 2 "register_operand" "0")] 16169 UNSPEC_SINCOS_COS)) 16170 (set (match_operand:SF 1 "register_operand" "=u") 16171 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16172 "TARGET_USE_FANCY_MATH_387 16173 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16174 && flag_unsafe_math_optimizations" 16175 "fsincos" 16176 [(set_attr "type" "fpspc") 16177 (set_attr "mode" "SF")]) 16178 16179(define_split 16180 [(set (match_operand:SF 0 "register_operand" "") 16181 (unspec:SF [(match_operand:SF 2 "register_operand" "")] 16182 UNSPEC_SINCOS_COS)) 16183 (set (match_operand:SF 1 "register_operand" "") 16184 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16185 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0])) 16186 && !reload_completed && !reload_in_progress" 16187 [(set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_SIN))] 16188 "") 16189 16190(define_split 16191 [(set (match_operand:SF 0 "register_operand" "") 16192 (unspec:SF [(match_operand:SF 2 "register_operand" "")] 16193 UNSPEC_SINCOS_COS)) 16194 (set (match_operand:SF 1 "register_operand" "") 16195 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16196 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1])) 16197 && !reload_completed && !reload_in_progress" 16198 [(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_COS))] 16199 "") 16200 16201(define_insn "*sincosextendsfdf3" 16202 [(set (match_operand:DF 0 "register_operand" "=f") 16203 (unspec:DF [(float_extend:DF 16204 (match_operand:SF 2 "register_operand" "0"))] 16205 UNSPEC_SINCOS_COS)) 16206 (set (match_operand:DF 1 "register_operand" "=u") 16207 (unspec:DF [(float_extend:DF 16208 (match_dup 2))] UNSPEC_SINCOS_SIN))] 16209 "TARGET_USE_FANCY_MATH_387 16210 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16211 && flag_unsafe_math_optimizations" 16212 "fsincos" 16213 [(set_attr "type" "fpspc") 16214 (set_attr "mode" "DF")]) 16215 16216(define_split 16217 [(set (match_operand:DF 0 "register_operand" "") 16218 (unspec:DF [(float_extend:DF 16219 (match_operand:SF 2 "register_operand" ""))] 16220 UNSPEC_SINCOS_COS)) 16221 (set (match_operand:DF 1 "register_operand" "") 16222 (unspec:DF [(float_extend:DF 16223 (match_dup 2))] UNSPEC_SINCOS_SIN))] 16224 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0])) 16225 && !reload_completed && !reload_in_progress" 16226 [(set (match_dup 1) (unspec:DF [(float_extend:DF 16227 (match_dup 2))] UNSPEC_SIN))] 16228 "") 16229 16230(define_split 16231 [(set (match_operand:DF 0 "register_operand" "") 16232 (unspec:DF [(float_extend:DF 16233 (match_operand:SF 2 "register_operand" ""))] 16234 UNSPEC_SINCOS_COS)) 16235 (set (match_operand:DF 1 "register_operand" "") 16236 (unspec:DF [(float_extend:DF 16237 (match_dup 2))] UNSPEC_SINCOS_SIN))] 16238 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1])) 16239 && !reload_completed && !reload_in_progress" 16240 [(set (match_dup 0) (unspec:DF [(float_extend:DF 16241 (match_dup 2))] UNSPEC_COS))] 16242 "") 16243 16244(define_insn "sincosxf3" 16245 [(set (match_operand:XF 0 "register_operand" "=f") 16246 (unspec:XF [(match_operand:XF 2 "register_operand" "0")] 16247 UNSPEC_SINCOS_COS)) 16248 (set (match_operand:XF 1 "register_operand" "=u") 16249 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16250 "TARGET_USE_FANCY_MATH_387 16251 && flag_unsafe_math_optimizations" 16252 "fsincos" 16253 [(set_attr "type" "fpspc") 16254 (set_attr "mode" "XF")]) 16255 16256(define_split 16257 [(set (match_operand:XF 0 "register_operand" "") 16258 (unspec:XF [(match_operand:XF 2 "register_operand" "")] 16259 UNSPEC_SINCOS_COS)) 16260 (set (match_operand:XF 1 "register_operand" "") 16261 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16262 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0])) 16263 && !reload_completed && !reload_in_progress" 16264 [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))] 16265 "") 16266 16267(define_split 16268 [(set (match_operand:XF 0 "register_operand" "") 16269 (unspec:XF [(match_operand:XF 2 "register_operand" "")] 16270 UNSPEC_SINCOS_COS)) 16271 (set (match_operand:XF 1 "register_operand" "") 16272 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))] 16273 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1])) 16274 && !reload_completed && !reload_in_progress" 16275 [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))] 16276 "") 16277 16278(define_insn "*tandf3_1" 16279 [(set (match_operand:DF 0 "register_operand" "=f") 16280 (unspec:DF [(match_operand:DF 2 "register_operand" "0")] 16281 UNSPEC_TAN_ONE)) 16282 (set (match_operand:DF 1 "register_operand" "=u") 16283 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))] 16284 "TARGET_USE_FANCY_MATH_387 16285 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16286 && flag_unsafe_math_optimizations" 16287 "fptan" 16288 [(set_attr "type" "fpspc") 16289 (set_attr "mode" "DF")]) 16290 16291;; optimize sequence: fptan 16292;; fstp %st(0) 16293;; fld1 16294;; into fptan insn. 16295 16296(define_peephole2 16297 [(parallel[(set (match_operand:DF 0 "register_operand" "") 16298 (unspec:DF [(match_operand:DF 2 "register_operand" "")] 16299 UNSPEC_TAN_ONE)) 16300 (set (match_operand:DF 1 "register_operand" "") 16301 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))]) 16302 (set (match_dup 0) 16303 (match_operand:DF 3 "immediate_operand" ""))] 16304 "standard_80387_constant_p (operands[3]) == 2" 16305 [(parallel[(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_TAN_ONE)) 16306 (set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])] 16307 "") 16308 16309(define_expand "tandf2" 16310 [(parallel [(set (match_dup 2) 16311 (unspec:DF [(match_operand:DF 1 "register_operand" "")] 16312 UNSPEC_TAN_ONE)) 16313 (set (match_operand:DF 0 "register_operand" "") 16314 (unspec:DF [(match_dup 1)] UNSPEC_TAN_TAN))])] 16315 "TARGET_USE_FANCY_MATH_387 16316 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16317 && flag_unsafe_math_optimizations" 16318{ 16319 operands[2] = gen_reg_rtx (DFmode); 16320}) 16321 16322(define_insn "*tansf3_1" 16323 [(set (match_operand:SF 0 "register_operand" "=f") 16324 (unspec:SF [(match_operand:SF 2 "register_operand" "0")] 16325 UNSPEC_TAN_ONE)) 16326 (set (match_operand:SF 1 "register_operand" "=u") 16327 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))] 16328 "TARGET_USE_FANCY_MATH_387 16329 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16330 && flag_unsafe_math_optimizations" 16331 "fptan" 16332 [(set_attr "type" "fpspc") 16333 (set_attr "mode" "SF")]) 16334 16335;; optimize sequence: fptan 16336;; fstp %st(0) 16337;; fld1 16338;; into fptan insn. 16339 16340(define_peephole2 16341 [(parallel[(set (match_operand:SF 0 "register_operand" "") 16342 (unspec:SF [(match_operand:SF 2 "register_operand" "")] 16343 UNSPEC_TAN_ONE)) 16344 (set (match_operand:SF 1 "register_operand" "") 16345 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))]) 16346 (set (match_dup 0) 16347 (match_operand:SF 3 "immediate_operand" ""))] 16348 "standard_80387_constant_p (operands[3]) == 2" 16349 [(parallel[(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_TAN_ONE)) 16350 (set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])] 16351 "") 16352 16353(define_expand "tansf2" 16354 [(parallel [(set (match_dup 2) 16355 (unspec:SF [(match_operand:SF 1 "register_operand" "")] 16356 UNSPEC_TAN_ONE)) 16357 (set (match_operand:SF 0 "register_operand" "") 16358 (unspec:SF [(match_dup 1)] UNSPEC_TAN_TAN))])] 16359 "TARGET_USE_FANCY_MATH_387 16360 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16361 && flag_unsafe_math_optimizations" 16362{ 16363 operands[2] = gen_reg_rtx (SFmode); 16364}) 16365 16366(define_insn "*tanxf3_1" 16367 [(set (match_operand:XF 0 "register_operand" "=f") 16368 (unspec:XF [(match_operand:XF 2 "register_operand" "0")] 16369 UNSPEC_TAN_ONE)) 16370 (set (match_operand:XF 1 "register_operand" "=u") 16371 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))] 16372 "TARGET_USE_FANCY_MATH_387 16373 && flag_unsafe_math_optimizations" 16374 "fptan" 16375 [(set_attr "type" "fpspc") 16376 (set_attr "mode" "XF")]) 16377 16378;; optimize sequence: fptan 16379;; fstp %st(0) 16380;; fld1 16381;; into fptan insn. 16382 16383(define_peephole2 16384 [(parallel[(set (match_operand:XF 0 "register_operand" "") 16385 (unspec:XF [(match_operand:XF 2 "register_operand" "")] 16386 UNSPEC_TAN_ONE)) 16387 (set (match_operand:XF 1 "register_operand" "") 16388 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))]) 16389 (set (match_dup 0) 16390 (match_operand:XF 3 "immediate_operand" ""))] 16391 "standard_80387_constant_p (operands[3]) == 2" 16392 [(parallel[(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_TAN_ONE)) 16393 (set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])] 16394 "") 16395 16396(define_expand "tanxf2" 16397 [(parallel [(set (match_dup 2) 16398 (unspec:XF [(match_operand:XF 1 "register_operand" "")] 16399 UNSPEC_TAN_ONE)) 16400 (set (match_operand:XF 0 "register_operand" "") 16401 (unspec:XF [(match_dup 1)] UNSPEC_TAN_TAN))])] 16402 "TARGET_USE_FANCY_MATH_387 16403 && flag_unsafe_math_optimizations" 16404{ 16405 operands[2] = gen_reg_rtx (XFmode); 16406}) 16407 16408(define_insn "atan2df3_1" 16409 [(set (match_operand:DF 0 "register_operand" "=f") 16410 (unspec:DF [(match_operand:DF 2 "register_operand" "0") 16411 (match_operand:DF 1 "register_operand" "u")] 16412 UNSPEC_FPATAN)) 16413 (clobber (match_scratch:DF 3 "=1"))] 16414 "TARGET_USE_FANCY_MATH_387 16415 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16416 && flag_unsafe_math_optimizations" 16417 "fpatan" 16418 [(set_attr "type" "fpspc") 16419 (set_attr "mode" "DF")]) 16420 16421(define_expand "atan2df3" 16422 [(use (match_operand:DF 0 "register_operand" "")) 16423 (use (match_operand:DF 2 "register_operand" "")) 16424 (use (match_operand:DF 1 "register_operand" ""))] 16425 "TARGET_USE_FANCY_MATH_387 16426 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16427 && flag_unsafe_math_optimizations" 16428{ 16429 rtx copy = gen_reg_rtx (DFmode); 16430 emit_move_insn (copy, operands[1]); 16431 emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2])); 16432 DONE; 16433}) 16434 16435(define_expand "atandf2" 16436 [(parallel [(set (match_operand:DF 0 "register_operand" "") 16437 (unspec:DF [(match_dup 2) 16438 (match_operand:DF 1 "register_operand" "")] 16439 UNSPEC_FPATAN)) 16440 (clobber (match_scratch:DF 3 ""))])] 16441 "TARGET_USE_FANCY_MATH_387 16442 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16443 && flag_unsafe_math_optimizations" 16444{ 16445 operands[2] = gen_reg_rtx (DFmode); 16446 emit_move_insn (operands[2], CONST1_RTX (DFmode)); /* fld1 */ 16447}) 16448 16449(define_insn "atan2sf3_1" 16450 [(set (match_operand:SF 0 "register_operand" "=f") 16451 (unspec:SF [(match_operand:SF 2 "register_operand" "0") 16452 (match_operand:SF 1 "register_operand" "u")] 16453 UNSPEC_FPATAN)) 16454 (clobber (match_scratch:SF 3 "=1"))] 16455 "TARGET_USE_FANCY_MATH_387 16456 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16457 && flag_unsafe_math_optimizations" 16458 "fpatan" 16459 [(set_attr "type" "fpspc") 16460 (set_attr "mode" "SF")]) 16461 16462(define_expand "atan2sf3" 16463 [(use (match_operand:SF 0 "register_operand" "")) 16464 (use (match_operand:SF 2 "register_operand" "")) 16465 (use (match_operand:SF 1 "register_operand" ""))] 16466 "TARGET_USE_FANCY_MATH_387 16467 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16468 && flag_unsafe_math_optimizations" 16469{ 16470 rtx copy = gen_reg_rtx (SFmode); 16471 emit_move_insn (copy, operands[1]); 16472 emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2])); 16473 DONE; 16474}) 16475 16476(define_expand "atansf2" 16477 [(parallel [(set (match_operand:SF 0 "register_operand" "") 16478 (unspec:SF [(match_dup 2) 16479 (match_operand:SF 1 "register_operand" "")] 16480 UNSPEC_FPATAN)) 16481 (clobber (match_scratch:SF 3 ""))])] 16482 "TARGET_USE_FANCY_MATH_387 16483 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16484 && flag_unsafe_math_optimizations" 16485{ 16486 operands[2] = gen_reg_rtx (SFmode); 16487 emit_move_insn (operands[2], CONST1_RTX (SFmode)); /* fld1 */ 16488}) 16489 16490(define_insn "atan2xf3_1" 16491 [(set (match_operand:XF 0 "register_operand" "=f") 16492 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 16493 (match_operand:XF 1 "register_operand" "u")] 16494 UNSPEC_FPATAN)) 16495 (clobber (match_scratch:XF 3 "=1"))] 16496 "TARGET_USE_FANCY_MATH_387 16497 && flag_unsafe_math_optimizations" 16498 "fpatan" 16499 [(set_attr "type" "fpspc") 16500 (set_attr "mode" "XF")]) 16501 16502(define_expand "atan2xf3" 16503 [(use (match_operand:XF 0 "register_operand" "")) 16504 (use (match_operand:XF 2 "register_operand" "")) 16505 (use (match_operand:XF 1 "register_operand" ""))] 16506 "TARGET_USE_FANCY_MATH_387 16507 && flag_unsafe_math_optimizations" 16508{ 16509 rtx copy = gen_reg_rtx (XFmode); 16510 emit_move_insn (copy, operands[1]); 16511 emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2])); 16512 DONE; 16513}) 16514 16515(define_expand "atanxf2" 16516 [(parallel [(set (match_operand:XF 0 "register_operand" "") 16517 (unspec:XF [(match_dup 2) 16518 (match_operand:XF 1 "register_operand" "")] 16519 UNSPEC_FPATAN)) 16520 (clobber (match_scratch:XF 3 ""))])] 16521 "TARGET_USE_FANCY_MATH_387 16522 && flag_unsafe_math_optimizations" 16523{ 16524 operands[2] = gen_reg_rtx (XFmode); 16525 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */ 16526}) 16527 16528(define_expand "asindf2" 16529 [(set (match_dup 2) 16530 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16531 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2))) 16532 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3))) 16533 (set (match_dup 6) (sqrt:XF (match_dup 5))) 16534 (parallel [(set (match_dup 7) 16535 (unspec:XF [(match_dup 6) (match_dup 2)] 16536 UNSPEC_FPATAN)) 16537 (clobber (match_scratch:XF 8 ""))]) 16538 (set (match_operand:DF 0 "register_operand" "") 16539 (float_truncate:DF (match_dup 7)))] 16540 "TARGET_USE_FANCY_MATH_387 16541 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16542 && flag_unsafe_math_optimizations" 16543{ 16544 int i; 16545 16546 for (i=2; i<8; i++) 16547 operands[i] = gen_reg_rtx (XFmode); 16548 16549 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */ 16550}) 16551 16552(define_expand "asinsf2" 16553 [(set (match_dup 2) 16554 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16555 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2))) 16556 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3))) 16557 (set (match_dup 6) (sqrt:XF (match_dup 5))) 16558 (parallel [(set (match_dup 7) 16559 (unspec:XF [(match_dup 6) (match_dup 2)] 16560 UNSPEC_FPATAN)) 16561 (clobber (match_scratch:XF 8 ""))]) 16562 (set (match_operand:SF 0 "register_operand" "") 16563 (float_truncate:SF (match_dup 7)))] 16564 "TARGET_USE_FANCY_MATH_387 16565 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16566 && flag_unsafe_math_optimizations" 16567{ 16568 int i; 16569 16570 for (i=2; i<8; i++) 16571 operands[i] = gen_reg_rtx (XFmode); 16572 16573 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */ 16574}) 16575 16576(define_expand "asinxf2" 16577 [(set (match_dup 2) 16578 (mult:XF (match_operand:XF 1 "register_operand" "") 16579 (match_dup 1))) 16580 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2))) 16581 (set (match_dup 5) (sqrt:XF (match_dup 4))) 16582 (parallel [(set (match_operand:XF 0 "register_operand" "") 16583 (unspec:XF [(match_dup 5) (match_dup 1)] 16584 UNSPEC_FPATAN)) 16585 (clobber (match_scratch:XF 6 ""))])] 16586 "TARGET_USE_FANCY_MATH_387 16587 && flag_unsafe_math_optimizations" 16588{ 16589 int i; 16590 16591 for (i=2; i<6; i++) 16592 operands[i] = gen_reg_rtx (XFmode); 16593 16594 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */ 16595}) 16596 16597(define_expand "acosdf2" 16598 [(set (match_dup 2) 16599 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16600 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2))) 16601 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3))) 16602 (set (match_dup 6) (sqrt:XF (match_dup 5))) 16603 (parallel [(set (match_dup 7) 16604 (unspec:XF [(match_dup 2) (match_dup 6)] 16605 UNSPEC_FPATAN)) 16606 (clobber (match_scratch:XF 8 ""))]) 16607 (set (match_operand:DF 0 "register_operand" "") 16608 (float_truncate:DF (match_dup 7)))] 16609 "TARGET_USE_FANCY_MATH_387 16610 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16611 && flag_unsafe_math_optimizations" 16612{ 16613 int i; 16614 16615 for (i=2; i<8; i++) 16616 operands[i] = gen_reg_rtx (XFmode); 16617 16618 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */ 16619}) 16620 16621(define_expand "acossf2" 16622 [(set (match_dup 2) 16623 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16624 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2))) 16625 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3))) 16626 (set (match_dup 6) (sqrt:XF (match_dup 5))) 16627 (parallel [(set (match_dup 7) 16628 (unspec:XF [(match_dup 2) (match_dup 6)] 16629 UNSPEC_FPATAN)) 16630 (clobber (match_scratch:XF 8 ""))]) 16631 (set (match_operand:SF 0 "register_operand" "") 16632 (float_truncate:SF (match_dup 7)))] 16633 "TARGET_USE_FANCY_MATH_387 16634 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16635 && flag_unsafe_math_optimizations" 16636{ 16637 int i; 16638 16639 for (i=2; i<8; i++) 16640 operands[i] = gen_reg_rtx (XFmode); 16641 16642 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */ 16643}) 16644 16645(define_expand "acosxf2" 16646 [(set (match_dup 2) 16647 (mult:XF (match_operand:XF 1 "register_operand" "") 16648 (match_dup 1))) 16649 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2))) 16650 (set (match_dup 5) (sqrt:XF (match_dup 4))) 16651 (parallel [(set (match_operand:XF 0 "register_operand" "") 16652 (unspec:XF [(match_dup 1) (match_dup 5)] 16653 UNSPEC_FPATAN)) 16654 (clobber (match_scratch:XF 6 ""))])] 16655 "TARGET_USE_FANCY_MATH_387 16656 && flag_unsafe_math_optimizations" 16657{ 16658 int i; 16659 16660 for (i=2; i<6; i++) 16661 operands[i] = gen_reg_rtx (XFmode); 16662 16663 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */ 16664}) 16665 16666(define_insn "fyl2x_xf3" 16667 [(set (match_operand:XF 0 "register_operand" "=f") 16668 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 16669 (match_operand:XF 1 "register_operand" "u")] 16670 UNSPEC_FYL2X)) 16671 (clobber (match_scratch:XF 3 "=1"))] 16672 "TARGET_USE_FANCY_MATH_387 16673 && flag_unsafe_math_optimizations" 16674 "fyl2x" 16675 [(set_attr "type" "fpspc") 16676 (set_attr "mode" "XF")]) 16677 16678(define_expand "logsf2" 16679 [(set (match_dup 2) 16680 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16681 (parallel [(set (match_dup 4) 16682 (unspec:XF [(match_dup 2) 16683 (match_dup 3)] UNSPEC_FYL2X)) 16684 (clobber (match_scratch:XF 5 ""))]) 16685 (set (match_operand:SF 0 "register_operand" "") 16686 (float_truncate:SF (match_dup 4)))] 16687 "TARGET_USE_FANCY_MATH_387 16688 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16689 && flag_unsafe_math_optimizations" 16690{ 16691 rtx temp; 16692 16693 operands[2] = gen_reg_rtx (XFmode); 16694 operands[3] = gen_reg_rtx (XFmode); 16695 operands[4] = gen_reg_rtx (XFmode); 16696 16697 temp = standard_80387_constant_rtx (4); /* fldln2 */ 16698 emit_move_insn (operands[3], temp); 16699}) 16700 16701(define_expand "logdf2" 16702 [(set (match_dup 2) 16703 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16704 (parallel [(set (match_dup 4) 16705 (unspec:XF [(match_dup 2) 16706 (match_dup 3)] UNSPEC_FYL2X)) 16707 (clobber (match_scratch:XF 5 ""))]) 16708 (set (match_operand:DF 0 "register_operand" "") 16709 (float_truncate:DF (match_dup 4)))] 16710 "TARGET_USE_FANCY_MATH_387 16711 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16712 && flag_unsafe_math_optimizations" 16713{ 16714 rtx temp; 16715 16716 operands[2] = gen_reg_rtx (XFmode); 16717 operands[3] = gen_reg_rtx (XFmode); 16718 operands[4] = gen_reg_rtx (XFmode); 16719 16720 temp = standard_80387_constant_rtx (4); /* fldln2 */ 16721 emit_move_insn (operands[3], temp); 16722}) 16723 16724(define_expand "logxf2" 16725 [(parallel [(set (match_operand:XF 0 "register_operand" "") 16726 (unspec:XF [(match_operand:XF 1 "register_operand" "") 16727 (match_dup 2)] UNSPEC_FYL2X)) 16728 (clobber (match_scratch:XF 3 ""))])] 16729 "TARGET_USE_FANCY_MATH_387 16730 && flag_unsafe_math_optimizations" 16731{ 16732 rtx temp; 16733 16734 operands[2] = gen_reg_rtx (XFmode); 16735 temp = standard_80387_constant_rtx (4); /* fldln2 */ 16736 emit_move_insn (operands[2], temp); 16737}) 16738 16739(define_expand "log10sf2" 16740 [(set (match_dup 2) 16741 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16742 (parallel [(set (match_dup 4) 16743 (unspec:XF [(match_dup 2) 16744 (match_dup 3)] UNSPEC_FYL2X)) 16745 (clobber (match_scratch:XF 5 ""))]) 16746 (set (match_operand:SF 0 "register_operand" "") 16747 (float_truncate:SF (match_dup 4)))] 16748 "TARGET_USE_FANCY_MATH_387 16749 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16750 && flag_unsafe_math_optimizations" 16751{ 16752 rtx temp; 16753 16754 operands[2] = gen_reg_rtx (XFmode); 16755 operands[3] = gen_reg_rtx (XFmode); 16756 operands[4] = gen_reg_rtx (XFmode); 16757 16758 temp = standard_80387_constant_rtx (3); /* fldlg2 */ 16759 emit_move_insn (operands[3], temp); 16760}) 16761 16762(define_expand "log10df2" 16763 [(set (match_dup 2) 16764 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16765 (parallel [(set (match_dup 4) 16766 (unspec:XF [(match_dup 2) 16767 (match_dup 3)] UNSPEC_FYL2X)) 16768 (clobber (match_scratch:XF 5 ""))]) 16769 (set (match_operand:DF 0 "register_operand" "") 16770 (float_truncate:DF (match_dup 4)))] 16771 "TARGET_USE_FANCY_MATH_387 16772 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16773 && flag_unsafe_math_optimizations" 16774{ 16775 rtx temp; 16776 16777 operands[2] = gen_reg_rtx (XFmode); 16778 operands[3] = gen_reg_rtx (XFmode); 16779 operands[4] = gen_reg_rtx (XFmode); 16780 16781 temp = standard_80387_constant_rtx (3); /* fldlg2 */ 16782 emit_move_insn (operands[3], temp); 16783}) 16784 16785(define_expand "log10xf2" 16786 [(parallel [(set (match_operand:XF 0 "register_operand" "") 16787 (unspec:XF [(match_operand:XF 1 "register_operand" "") 16788 (match_dup 2)] UNSPEC_FYL2X)) 16789 (clobber (match_scratch:XF 3 ""))])] 16790 "TARGET_USE_FANCY_MATH_387 16791 && flag_unsafe_math_optimizations" 16792{ 16793 rtx temp; 16794 16795 operands[2] = gen_reg_rtx (XFmode); 16796 temp = standard_80387_constant_rtx (3); /* fldlg2 */ 16797 emit_move_insn (operands[2], temp); 16798}) 16799 16800(define_expand "log2sf2" 16801 [(set (match_dup 2) 16802 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16803 (parallel [(set (match_dup 4) 16804 (unspec:XF [(match_dup 2) 16805 (match_dup 3)] UNSPEC_FYL2X)) 16806 (clobber (match_scratch:XF 5 ""))]) 16807 (set (match_operand:SF 0 "register_operand" "") 16808 (float_truncate:SF (match_dup 4)))] 16809 "TARGET_USE_FANCY_MATH_387 16810 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16811 && flag_unsafe_math_optimizations" 16812{ 16813 operands[2] = gen_reg_rtx (XFmode); 16814 operands[3] = gen_reg_rtx (XFmode); 16815 operands[4] = gen_reg_rtx (XFmode); 16816 16817 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */ 16818}) 16819 16820(define_expand "log2df2" 16821 [(set (match_dup 2) 16822 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16823 (parallel [(set (match_dup 4) 16824 (unspec:XF [(match_dup 2) 16825 (match_dup 3)] UNSPEC_FYL2X)) 16826 (clobber (match_scratch:XF 5 ""))]) 16827 (set (match_operand:DF 0 "register_operand" "") 16828 (float_truncate:DF (match_dup 4)))] 16829 "TARGET_USE_FANCY_MATH_387 16830 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16831 && flag_unsafe_math_optimizations" 16832{ 16833 operands[2] = gen_reg_rtx (XFmode); 16834 operands[3] = gen_reg_rtx (XFmode); 16835 operands[4] = gen_reg_rtx (XFmode); 16836 16837 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */ 16838}) 16839 16840(define_expand "log2xf2" 16841 [(parallel [(set (match_operand:XF 0 "register_operand" "") 16842 (unspec:XF [(match_operand:XF 1 "register_operand" "") 16843 (match_dup 2)] UNSPEC_FYL2X)) 16844 (clobber (match_scratch:XF 3 ""))])] 16845 "TARGET_USE_FANCY_MATH_387 16846 && flag_unsafe_math_optimizations" 16847{ 16848 operands[2] = gen_reg_rtx (XFmode); 16849 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */ 16850}) 16851 16852(define_insn "fyl2xp1_xf3" 16853 [(set (match_operand:XF 0 "register_operand" "=f") 16854 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 16855 (match_operand:XF 1 "register_operand" "u")] 16856 UNSPEC_FYL2XP1)) 16857 (clobber (match_scratch:XF 3 "=1"))] 16858 "TARGET_USE_FANCY_MATH_387 16859 && flag_unsafe_math_optimizations" 16860 "fyl2xp1" 16861 [(set_attr "type" "fpspc") 16862 (set_attr "mode" "XF")]) 16863 16864(define_expand "log1psf2" 16865 [(use (match_operand:SF 0 "register_operand" "")) 16866 (use (match_operand:SF 1 "register_operand" ""))] 16867 "TARGET_USE_FANCY_MATH_387 16868 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16869 && flag_unsafe_math_optimizations" 16870{ 16871 rtx op0 = gen_reg_rtx (XFmode); 16872 rtx op1 = gen_reg_rtx (XFmode); 16873 16874 emit_insn (gen_extendsfxf2 (op1, operands[1])); 16875 ix86_emit_i387_log1p (op0, op1); 16876 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 16877 DONE; 16878}) 16879 16880(define_expand "log1pdf2" 16881 [(use (match_operand:DF 0 "register_operand" "")) 16882 (use (match_operand:DF 1 "register_operand" ""))] 16883 "TARGET_USE_FANCY_MATH_387 16884 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16885 && flag_unsafe_math_optimizations" 16886{ 16887 rtx op0 = gen_reg_rtx (XFmode); 16888 rtx op1 = gen_reg_rtx (XFmode); 16889 16890 emit_insn (gen_extenddfxf2 (op1, operands[1])); 16891 ix86_emit_i387_log1p (op0, op1); 16892 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 16893 DONE; 16894}) 16895 16896(define_expand "log1pxf2" 16897 [(use (match_operand:XF 0 "register_operand" "")) 16898 (use (match_operand:XF 1 "register_operand" ""))] 16899 "TARGET_USE_FANCY_MATH_387 16900 && flag_unsafe_math_optimizations" 16901{ 16902 ix86_emit_i387_log1p (operands[0], operands[1]); 16903 DONE; 16904}) 16905 16906(define_insn "*fxtractxf3" 16907 [(set (match_operand:XF 0 "register_operand" "=f") 16908 (unspec:XF [(match_operand:XF 2 "register_operand" "0")] 16909 UNSPEC_XTRACT_FRACT)) 16910 (set (match_operand:XF 1 "register_operand" "=u") 16911 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))] 16912 "TARGET_USE_FANCY_MATH_387 16913 && flag_unsafe_math_optimizations" 16914 "fxtract" 16915 [(set_attr "type" "fpspc") 16916 (set_attr "mode" "XF")]) 16917 16918(define_expand "logbsf2" 16919 [(set (match_dup 2) 16920 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 16921 (parallel [(set (match_dup 3) 16922 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT)) 16923 (set (match_dup 4) 16924 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]) 16925 (set (match_operand:SF 0 "register_operand" "") 16926 (float_truncate:SF (match_dup 4)))] 16927 "TARGET_USE_FANCY_MATH_387 16928 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16929 && flag_unsafe_math_optimizations" 16930{ 16931 operands[2] = gen_reg_rtx (XFmode); 16932 operands[3] = gen_reg_rtx (XFmode); 16933 operands[4] = gen_reg_rtx (XFmode); 16934}) 16935 16936(define_expand "logbdf2" 16937 [(set (match_dup 2) 16938 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 16939 (parallel [(set (match_dup 3) 16940 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT)) 16941 (set (match_dup 4) 16942 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]) 16943 (set (match_operand:DF 0 "register_operand" "") 16944 (float_truncate:DF (match_dup 4)))] 16945 "TARGET_USE_FANCY_MATH_387 16946 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 16947 && flag_unsafe_math_optimizations" 16948{ 16949 operands[2] = gen_reg_rtx (XFmode); 16950 operands[3] = gen_reg_rtx (XFmode); 16951 operands[4] = gen_reg_rtx (XFmode); 16952}) 16953 16954(define_expand "logbxf2" 16955 [(parallel [(set (match_dup 2) 16956 (unspec:XF [(match_operand:XF 1 "register_operand" "")] 16957 UNSPEC_XTRACT_FRACT)) 16958 (set (match_operand:XF 0 "register_operand" "") 16959 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])] 16960 "TARGET_USE_FANCY_MATH_387 16961 && flag_unsafe_math_optimizations" 16962{ 16963 operands[2] = gen_reg_rtx (XFmode); 16964}) 16965 16966(define_expand "ilogbsi2" 16967 [(parallel [(set (match_dup 2) 16968 (unspec:XF [(match_operand:XF 1 "register_operand" "")] 16969 UNSPEC_XTRACT_FRACT)) 16970 (set (match_operand:XF 3 "register_operand" "") 16971 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))]) 16972 (parallel [(set (match_operand:SI 0 "register_operand" "") 16973 (fix:SI (match_dup 3))) 16974 (clobber (reg:CC FLAGS_REG))])] 16975 "TARGET_USE_FANCY_MATH_387 16976 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 16977 && flag_unsafe_math_optimizations" 16978{ 16979 operands[2] = gen_reg_rtx (XFmode); 16980 operands[3] = gen_reg_rtx (XFmode); 16981}) 16982 16983(define_insn "*f2xm1xf2" 16984 [(set (match_operand:XF 0 "register_operand" "=f") 16985 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 16986 UNSPEC_F2XM1))] 16987 "TARGET_USE_FANCY_MATH_387 16988 && flag_unsafe_math_optimizations" 16989 "f2xm1" 16990 [(set_attr "type" "fpspc") 16991 (set_attr "mode" "XF")]) 16992 16993(define_insn "*fscalexf4" 16994 [(set (match_operand:XF 0 "register_operand" "=f") 16995 (unspec:XF [(match_operand:XF 2 "register_operand" "0") 16996 (match_operand:XF 3 "register_operand" "1")] 16997 UNSPEC_FSCALE_FRACT)) 16998 (set (match_operand:XF 1 "register_operand" "=u") 16999 (unspec:XF [(match_dup 2) (match_dup 3)] 17000 UNSPEC_FSCALE_EXP))] 17001 "TARGET_USE_FANCY_MATH_387 17002 && flag_unsafe_math_optimizations" 17003 "fscale" 17004 [(set_attr "type" "fpspc") 17005 (set_attr "mode" "XF")]) 17006 17007(define_expand "expsf2" 17008 [(set (match_dup 2) 17009 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 17010 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17011 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17012 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17013 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17014 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8))) 17015 (parallel [(set (match_dup 10) 17016 (unspec:XF [(match_dup 9) (match_dup 5)] 17017 UNSPEC_FSCALE_FRACT)) 17018 (set (match_dup 11) 17019 (unspec:XF [(match_dup 9) (match_dup 5)] 17020 UNSPEC_FSCALE_EXP))]) 17021 (set (match_operand:SF 0 "register_operand" "") 17022 (float_truncate:SF (match_dup 10)))] 17023 "TARGET_USE_FANCY_MATH_387 17024 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17025 && flag_unsafe_math_optimizations" 17026{ 17027 rtx temp; 17028 int i; 17029 17030 for (i=2; i<12; i++) 17031 operands[i] = gen_reg_rtx (XFmode); 17032 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17033 emit_move_insn (operands[3], temp); 17034 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */ 17035}) 17036 17037(define_expand "expdf2" 17038 [(set (match_dup 2) 17039 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 17040 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17041 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17042 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17043 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17044 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8))) 17045 (parallel [(set (match_dup 10) 17046 (unspec:XF [(match_dup 9) (match_dup 5)] 17047 UNSPEC_FSCALE_FRACT)) 17048 (set (match_dup 11) 17049 (unspec:XF [(match_dup 9) (match_dup 5)] 17050 UNSPEC_FSCALE_EXP))]) 17051 (set (match_operand:DF 0 "register_operand" "") 17052 (float_truncate:DF (match_dup 10)))] 17053 "TARGET_USE_FANCY_MATH_387 17054 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17055 && flag_unsafe_math_optimizations" 17056{ 17057 rtx temp; 17058 int i; 17059 17060 for (i=2; i<12; i++) 17061 operands[i] = gen_reg_rtx (XFmode); 17062 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17063 emit_move_insn (operands[3], temp); 17064 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */ 17065}) 17066 17067(define_expand "expxf2" 17068 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "") 17069 (match_dup 2))) 17070 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT)) 17071 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4))) 17072 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1)) 17073 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7))) 17074 (parallel [(set (match_operand:XF 0 "register_operand" "") 17075 (unspec:XF [(match_dup 8) (match_dup 4)] 17076 UNSPEC_FSCALE_FRACT)) 17077 (set (match_dup 9) 17078 (unspec:XF [(match_dup 8) (match_dup 4)] 17079 UNSPEC_FSCALE_EXP))])] 17080 "TARGET_USE_FANCY_MATH_387 17081 && flag_unsafe_math_optimizations" 17082{ 17083 rtx temp; 17084 int i; 17085 17086 for (i=2; i<10; i++) 17087 operands[i] = gen_reg_rtx (XFmode); 17088 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17089 emit_move_insn (operands[2], temp); 17090 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */ 17091}) 17092 17093(define_expand "exp10sf2" 17094 [(set (match_dup 2) 17095 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 17096 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17097 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17098 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17099 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17100 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8))) 17101 (parallel [(set (match_dup 10) 17102 (unspec:XF [(match_dup 9) (match_dup 5)] 17103 UNSPEC_FSCALE_FRACT)) 17104 (set (match_dup 11) 17105 (unspec:XF [(match_dup 9) (match_dup 5)] 17106 UNSPEC_FSCALE_EXP))]) 17107 (set (match_operand:SF 0 "register_operand" "") 17108 (float_truncate:SF (match_dup 10)))] 17109 "TARGET_USE_FANCY_MATH_387 17110 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17111 && flag_unsafe_math_optimizations" 17112{ 17113 rtx temp; 17114 int i; 17115 17116 for (i=2; i<12; i++) 17117 operands[i] = gen_reg_rtx (XFmode); 17118 temp = standard_80387_constant_rtx (6); /* fldl2t */ 17119 emit_move_insn (operands[3], temp); 17120 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */ 17121}) 17122 17123(define_expand "exp10df2" 17124 [(set (match_dup 2) 17125 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 17126 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17127 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17128 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17129 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17130 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8))) 17131 (parallel [(set (match_dup 10) 17132 (unspec:XF [(match_dup 9) (match_dup 5)] 17133 UNSPEC_FSCALE_FRACT)) 17134 (set (match_dup 11) 17135 (unspec:XF [(match_dup 9) (match_dup 5)] 17136 UNSPEC_FSCALE_EXP))]) 17137 (set (match_operand:DF 0 "register_operand" "") 17138 (float_truncate:DF (match_dup 10)))] 17139 "TARGET_USE_FANCY_MATH_387 17140 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17141 && flag_unsafe_math_optimizations" 17142{ 17143 rtx temp; 17144 int i; 17145 17146 for (i=2; i<12; i++) 17147 operands[i] = gen_reg_rtx (XFmode); 17148 temp = standard_80387_constant_rtx (6); /* fldl2t */ 17149 emit_move_insn (operands[3], temp); 17150 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */ 17151}) 17152 17153(define_expand "exp10xf2" 17154 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "") 17155 (match_dup 2))) 17156 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT)) 17157 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4))) 17158 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1)) 17159 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7))) 17160 (parallel [(set (match_operand:XF 0 "register_operand" "") 17161 (unspec:XF [(match_dup 8) (match_dup 4)] 17162 UNSPEC_FSCALE_FRACT)) 17163 (set (match_dup 9) 17164 (unspec:XF [(match_dup 8) (match_dup 4)] 17165 UNSPEC_FSCALE_EXP))])] 17166 "TARGET_USE_FANCY_MATH_387 17167 && flag_unsafe_math_optimizations" 17168{ 17169 rtx temp; 17170 int i; 17171 17172 for (i=2; i<10; i++) 17173 operands[i] = gen_reg_rtx (XFmode); 17174 temp = standard_80387_constant_rtx (6); /* fldl2t */ 17175 emit_move_insn (operands[2], temp); 17176 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */ 17177}) 17178 17179(define_expand "exp2sf2" 17180 [(set (match_dup 2) 17181 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 17182 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT)) 17183 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3))) 17184 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1)) 17185 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6))) 17186 (parallel [(set (match_dup 8) 17187 (unspec:XF [(match_dup 7) (match_dup 3)] 17188 UNSPEC_FSCALE_FRACT)) 17189 (set (match_dup 9) 17190 (unspec:XF [(match_dup 7) (match_dup 3)] 17191 UNSPEC_FSCALE_EXP))]) 17192 (set (match_operand:SF 0 "register_operand" "") 17193 (float_truncate:SF (match_dup 8)))] 17194 "TARGET_USE_FANCY_MATH_387 17195 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17196 && flag_unsafe_math_optimizations" 17197{ 17198 int i; 17199 17200 for (i=2; i<10; i++) 17201 operands[i] = gen_reg_rtx (XFmode); 17202 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */ 17203}) 17204 17205(define_expand "exp2df2" 17206 [(set (match_dup 2) 17207 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 17208 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT)) 17209 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3))) 17210 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1)) 17211 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6))) 17212 (parallel [(set (match_dup 8) 17213 (unspec:XF [(match_dup 7) (match_dup 3)] 17214 UNSPEC_FSCALE_FRACT)) 17215 (set (match_dup 9) 17216 (unspec:XF [(match_dup 7) (match_dup 3)] 17217 UNSPEC_FSCALE_EXP))]) 17218 (set (match_operand:DF 0 "register_operand" "") 17219 (float_truncate:DF (match_dup 8)))] 17220 "TARGET_USE_FANCY_MATH_387 17221 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17222 && flag_unsafe_math_optimizations" 17223{ 17224 int i; 17225 17226 for (i=2; i<10; i++) 17227 operands[i] = gen_reg_rtx (XFmode); 17228 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */ 17229}) 17230 17231(define_expand "exp2xf2" 17232 [(set (match_dup 2) (match_operand:XF 1 "register_operand" "")) 17233 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT)) 17234 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3))) 17235 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1)) 17236 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6))) 17237 (parallel [(set (match_operand:XF 0 "register_operand" "") 17238 (unspec:XF [(match_dup 7) (match_dup 3)] 17239 UNSPEC_FSCALE_FRACT)) 17240 (set (match_dup 8) 17241 (unspec:XF [(match_dup 7) (match_dup 3)] 17242 UNSPEC_FSCALE_EXP))])] 17243 "TARGET_USE_FANCY_MATH_387 17244 && flag_unsafe_math_optimizations" 17245{ 17246 int i; 17247 17248 for (i=2; i<9; i++) 17249 operands[i] = gen_reg_rtx (XFmode); 17250 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */ 17251}) 17252 17253(define_expand "expm1df2" 17254 [(set (match_dup 2) 17255 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 17256 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17257 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17258 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17259 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17260 (parallel [(set (match_dup 8) 17261 (unspec:XF [(match_dup 7) (match_dup 5)] 17262 UNSPEC_FSCALE_FRACT)) 17263 (set (match_dup 9) 17264 (unspec:XF [(match_dup 7) (match_dup 5)] 17265 UNSPEC_FSCALE_EXP))]) 17266 (parallel [(set (match_dup 11) 17267 (unspec:XF [(match_dup 10) (match_dup 9)] 17268 UNSPEC_FSCALE_FRACT)) 17269 (set (match_dup 12) 17270 (unspec:XF [(match_dup 10) (match_dup 9)] 17271 UNSPEC_FSCALE_EXP))]) 17272 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10))) 17273 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8))) 17274 (set (match_operand:DF 0 "register_operand" "") 17275 (float_truncate:DF (match_dup 14)))] 17276 "TARGET_USE_FANCY_MATH_387 17277 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17278 && flag_unsafe_math_optimizations" 17279{ 17280 rtx temp; 17281 int i; 17282 17283 for (i=2; i<15; i++) 17284 operands[i] = gen_reg_rtx (XFmode); 17285 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17286 emit_move_insn (operands[3], temp); 17287 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */ 17288}) 17289 17290(define_expand "expm1sf2" 17291 [(set (match_dup 2) 17292 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 17293 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3))) 17294 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT)) 17295 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5))) 17296 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1)) 17297 (parallel [(set (match_dup 8) 17298 (unspec:XF [(match_dup 7) (match_dup 5)] 17299 UNSPEC_FSCALE_FRACT)) 17300 (set (match_dup 9) 17301 (unspec:XF [(match_dup 7) (match_dup 5)] 17302 UNSPEC_FSCALE_EXP))]) 17303 (parallel [(set (match_dup 11) 17304 (unspec:XF [(match_dup 10) (match_dup 9)] 17305 UNSPEC_FSCALE_FRACT)) 17306 (set (match_dup 12) 17307 (unspec:XF [(match_dup 10) (match_dup 9)] 17308 UNSPEC_FSCALE_EXP))]) 17309 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10))) 17310 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8))) 17311 (set (match_operand:SF 0 "register_operand" "") 17312 (float_truncate:SF (match_dup 14)))] 17313 "TARGET_USE_FANCY_MATH_387 17314 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17315 && flag_unsafe_math_optimizations" 17316{ 17317 rtx temp; 17318 int i; 17319 17320 for (i=2; i<15; i++) 17321 operands[i] = gen_reg_rtx (XFmode); 17322 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17323 emit_move_insn (operands[3], temp); 17324 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */ 17325}) 17326 17327(define_expand "expm1xf2" 17328 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "") 17329 (match_dup 2))) 17330 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT)) 17331 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4))) 17332 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1)) 17333 (parallel [(set (match_dup 7) 17334 (unspec:XF [(match_dup 6) (match_dup 4)] 17335 UNSPEC_FSCALE_FRACT)) 17336 (set (match_dup 8) 17337 (unspec:XF [(match_dup 6) (match_dup 4)] 17338 UNSPEC_FSCALE_EXP))]) 17339 (parallel [(set (match_dup 10) 17340 (unspec:XF [(match_dup 9) (match_dup 8)] 17341 UNSPEC_FSCALE_FRACT)) 17342 (set (match_dup 11) 17343 (unspec:XF [(match_dup 9) (match_dup 8)] 17344 UNSPEC_FSCALE_EXP))]) 17345 (set (match_dup 12) (minus:XF (match_dup 10) (match_dup 9))) 17346 (set (match_operand:XF 0 "register_operand" "") 17347 (plus:XF (match_dup 12) (match_dup 7)))] 17348 "TARGET_USE_FANCY_MATH_387 17349 && flag_unsafe_math_optimizations" 17350{ 17351 rtx temp; 17352 int i; 17353 17354 for (i=2; i<13; i++) 17355 operands[i] = gen_reg_rtx (XFmode); 17356 temp = standard_80387_constant_rtx (5); /* fldl2e */ 17357 emit_move_insn (operands[2], temp); 17358 emit_move_insn (operands[9], CONST1_RTX (XFmode)); /* fld1 */ 17359}) 17360 17361(define_expand "ldexpdf3" 17362 [(set (match_dup 3) 17363 (float_extend:XF (match_operand:DF 1 "register_operand" ""))) 17364 (set (match_dup 4) 17365 (float:XF (match_operand:SI 2 "register_operand" ""))) 17366 (parallel [(set (match_dup 5) 17367 (unspec:XF [(match_dup 3) (match_dup 4)] 17368 UNSPEC_FSCALE_FRACT)) 17369 (set (match_dup 6) 17370 (unspec:XF [(match_dup 3) (match_dup 4)] 17371 UNSPEC_FSCALE_EXP))]) 17372 (set (match_operand:DF 0 "register_operand" "") 17373 (float_truncate:DF (match_dup 5)))] 17374 "TARGET_USE_FANCY_MATH_387 17375 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17376 && flag_unsafe_math_optimizations" 17377{ 17378 int i; 17379 17380 for (i=3; i<7; i++) 17381 operands[i] = gen_reg_rtx (XFmode); 17382}) 17383 17384(define_expand "ldexpsf3" 17385 [(set (match_dup 3) 17386 (float_extend:XF (match_operand:SF 1 "register_operand" ""))) 17387 (set (match_dup 4) 17388 (float:XF (match_operand:SI 2 "register_operand" ""))) 17389 (parallel [(set (match_dup 5) 17390 (unspec:XF [(match_dup 3) (match_dup 4)] 17391 UNSPEC_FSCALE_FRACT)) 17392 (set (match_dup 6) 17393 (unspec:XF [(match_dup 3) (match_dup 4)] 17394 UNSPEC_FSCALE_EXP))]) 17395 (set (match_operand:SF 0 "register_operand" "") 17396 (float_truncate:SF (match_dup 5)))] 17397 "TARGET_USE_FANCY_MATH_387 17398 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17399 && flag_unsafe_math_optimizations" 17400{ 17401 int i; 17402 17403 for (i=3; i<7; i++) 17404 operands[i] = gen_reg_rtx (XFmode); 17405}) 17406 17407(define_expand "ldexpxf3" 17408 [(set (match_dup 3) 17409 (float:XF (match_operand:SI 2 "register_operand" ""))) 17410 (parallel [(set (match_operand:XF 0 " register_operand" "") 17411 (unspec:XF [(match_operand:XF 1 "register_operand" "") 17412 (match_dup 3)] 17413 UNSPEC_FSCALE_FRACT)) 17414 (set (match_dup 4) 17415 (unspec:XF [(match_dup 1) (match_dup 3)] 17416 UNSPEC_FSCALE_EXP))])] 17417 "TARGET_USE_FANCY_MATH_387 17418 && flag_unsafe_math_optimizations" 17419{ 17420 int i; 17421 17422 for (i=3; i<5; i++) 17423 operands[i] = gen_reg_rtx (XFmode); 17424}) 17425 17426 17427(define_insn "frndintxf2" 17428 [(set (match_operand:XF 0 "register_operand" "=f") 17429 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 17430 UNSPEC_FRNDINT))] 17431 "TARGET_USE_FANCY_MATH_387 17432 && flag_unsafe_math_optimizations" 17433 "frndint" 17434 [(set_attr "type" "fpspc") 17435 (set_attr "mode" "XF")]) 17436 17437(define_expand "rintdf2" 17438 [(use (match_operand:DF 0 "register_operand" "")) 17439 (use (match_operand:DF 1 "register_operand" ""))] 17440 "TARGET_USE_FANCY_MATH_387 17441 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17442 && flag_unsafe_math_optimizations" 17443{ 17444 rtx op0 = gen_reg_rtx (XFmode); 17445 rtx op1 = gen_reg_rtx (XFmode); 17446 17447 emit_insn (gen_extenddfxf2 (op1, operands[1])); 17448 emit_insn (gen_frndintxf2 (op0, op1)); 17449 17450 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 17451 DONE; 17452}) 17453 17454(define_expand "rintsf2" 17455 [(use (match_operand:SF 0 "register_operand" "")) 17456 (use (match_operand:SF 1 "register_operand" ""))] 17457 "TARGET_USE_FANCY_MATH_387 17458 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17459 && flag_unsafe_math_optimizations" 17460{ 17461 rtx op0 = gen_reg_rtx (XFmode); 17462 rtx op1 = gen_reg_rtx (XFmode); 17463 17464 emit_insn (gen_extendsfxf2 (op1, operands[1])); 17465 emit_insn (gen_frndintxf2 (op0, op1)); 17466 17467 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 17468 DONE; 17469}) 17470 17471(define_expand "rintxf2" 17472 [(use (match_operand:XF 0 "register_operand" "")) 17473 (use (match_operand:XF 1 "register_operand" ""))] 17474 "TARGET_USE_FANCY_MATH_387 17475 && flag_unsafe_math_optimizations" 17476{ 17477 emit_insn (gen_frndintxf2 (operands[0], operands[1])); 17478 DONE; 17479}) 17480 17481(define_insn_and_split "*fistdi2_1" 17482 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r") 17483 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")] 17484 UNSPEC_FIST))] 17485 "TARGET_USE_FANCY_MATH_387 17486 && flag_unsafe_math_optimizations 17487 && !(reload_completed || reload_in_progress)" 17488 "#" 17489 "&& 1" 17490 [(const_int 0)] 17491{ 17492 if (memory_operand (operands[0], VOIDmode)) 17493 emit_insn (gen_fistdi2 (operands[0], operands[1])); 17494 else 17495 { 17496 operands[2] = assign_386_stack_local (DImode, SLOT_TEMP); 17497 emit_insn (gen_fistdi2_with_temp (operands[0], operands[1], 17498 operands[2])); 17499 } 17500 DONE; 17501} 17502 [(set_attr "type" "fpspc") 17503 (set_attr "mode" "DI")]) 17504 17505(define_insn "fistdi2" 17506 [(set (match_operand:DI 0 "memory_operand" "=m") 17507 (unspec:DI [(match_operand:XF 1 "register_operand" "f")] 17508 UNSPEC_FIST)) 17509 (clobber (match_scratch:XF 2 "=&1f"))] 17510 "TARGET_USE_FANCY_MATH_387 17511 && flag_unsafe_math_optimizations" 17512 "* return output_fix_trunc (insn, operands, 0);" 17513 [(set_attr "type" "fpspc") 17514 (set_attr "mode" "DI")]) 17515 17516(define_insn "fistdi2_with_temp" 17517 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r") 17518 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")] 17519 UNSPEC_FIST)) 17520 (clobber (match_operand:DI 2 "memory_operand" "=m,m")) 17521 (clobber (match_scratch:XF 3 "=&1f,&1f"))] 17522 "TARGET_USE_FANCY_MATH_387 17523 && flag_unsafe_math_optimizations" 17524 "#" 17525 [(set_attr "type" "fpspc") 17526 (set_attr "mode" "DI")]) 17527 17528(define_split 17529 [(set (match_operand:DI 0 "register_operand" "") 17530 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 17531 UNSPEC_FIST)) 17532 (clobber (match_operand:DI 2 "memory_operand" "")) 17533 (clobber (match_scratch 3 ""))] 17534 "reload_completed" 17535 [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST)) 17536 (clobber (match_dup 3))]) 17537 (set (match_dup 0) (match_dup 2))] 17538 "") 17539 17540(define_split 17541 [(set (match_operand:DI 0 "memory_operand" "") 17542 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 17543 UNSPEC_FIST)) 17544 (clobber (match_operand:DI 2 "memory_operand" "")) 17545 (clobber (match_scratch 3 ""))] 17546 "reload_completed" 17547 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST)) 17548 (clobber (match_dup 3))])] 17549 "") 17550 17551(define_insn_and_split "*fist<mode>2_1" 17552 [(set (match_operand:X87MODEI12 0 "register_operand" "=r") 17553 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")] 17554 UNSPEC_FIST))] 17555 "TARGET_USE_FANCY_MATH_387 17556 && flag_unsafe_math_optimizations 17557 && !(reload_completed || reload_in_progress)" 17558 "#" 17559 "&& 1" 17560 [(const_int 0)] 17561{ 17562 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP); 17563 emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1], 17564 operands[2])); 17565 DONE; 17566} 17567 [(set_attr "type" "fpspc") 17568 (set_attr "mode" "<MODE>")]) 17569 17570(define_insn "fist<mode>2" 17571 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m") 17572 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")] 17573 UNSPEC_FIST))] 17574 "TARGET_USE_FANCY_MATH_387 17575 && flag_unsafe_math_optimizations" 17576 "* return output_fix_trunc (insn, operands, 0);" 17577 [(set_attr "type" "fpspc") 17578 (set_attr "mode" "<MODE>")]) 17579 17580(define_insn "fist<mode>2_with_temp" 17581 [(set (match_operand:X87MODEI12 0 "register_operand" "=r") 17582 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")] 17583 UNSPEC_FIST)) 17584 (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))] 17585 "TARGET_USE_FANCY_MATH_387 17586 && flag_unsafe_math_optimizations" 17587 "#" 17588 [(set_attr "type" "fpspc") 17589 (set_attr "mode" "<MODE>")]) 17590 17591(define_split 17592 [(set (match_operand:X87MODEI12 0 "register_operand" "") 17593 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 17594 UNSPEC_FIST)) 17595 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))] 17596 "reload_completed" 17597 [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)] 17598 UNSPEC_FIST)) 17599 (set (match_dup 0) (match_dup 2))] 17600 "") 17601 17602(define_split 17603 [(set (match_operand:X87MODEI12 0 "memory_operand" "") 17604 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 17605 UNSPEC_FIST)) 17606 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))] 17607 "reload_completed" 17608 [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] 17609 UNSPEC_FIST))] 17610 "") 17611 17612(define_expand "lrint<mode>2" 17613 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "") 17614 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")] 17615 UNSPEC_FIST))] 17616 "TARGET_USE_FANCY_MATH_387 17617 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17618 && flag_unsafe_math_optimizations" 17619 "") 17620 17621;; Rounding mode control word calculation could clobber FLAGS_REG. 17622(define_insn_and_split "frndintxf2_floor" 17623 [(set (match_operand:XF 0 "register_operand" "=f") 17624 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 17625 UNSPEC_FRNDINT_FLOOR)) 17626 (clobber (reg:CC FLAGS_REG))] 17627 "TARGET_USE_FANCY_MATH_387 17628 && flag_unsafe_math_optimizations 17629 && !(reload_completed || reload_in_progress)" 17630 "#" 17631 "&& 1" 17632 [(const_int 0)] 17633{ 17634 ix86_optimize_mode_switching[I387_FLOOR] = 1; 17635 17636 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 17637 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR); 17638 17639 emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1], 17640 operands[2], operands[3])); 17641 DONE; 17642} 17643 [(set_attr "type" "frndint") 17644 (set_attr "i387_cw" "floor") 17645 (set_attr "mode" "XF")]) 17646 17647(define_insn "frndintxf2_floor_i387" 17648 [(set (match_operand:XF 0 "register_operand" "=f") 17649 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 17650 UNSPEC_FRNDINT_FLOOR)) 17651 (use (match_operand:HI 2 "memory_operand" "m")) 17652 (use (match_operand:HI 3 "memory_operand" "m"))] 17653 "TARGET_USE_FANCY_MATH_387 17654 && flag_unsafe_math_optimizations" 17655 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2" 17656 [(set_attr "type" "frndint") 17657 (set_attr "i387_cw" "floor") 17658 (set_attr "mode" "XF")]) 17659 17660(define_expand "floorxf2" 17661 [(use (match_operand:XF 0 "register_operand" "")) 17662 (use (match_operand:XF 1 "register_operand" ""))] 17663 "TARGET_USE_FANCY_MATH_387 17664 && flag_unsafe_math_optimizations" 17665{ 17666 emit_insn (gen_frndintxf2_floor (operands[0], operands[1])); 17667 DONE; 17668}) 17669 17670(define_expand "floordf2" 17671 [(use (match_operand:DF 0 "register_operand" "")) 17672 (use (match_operand:DF 1 "register_operand" ""))] 17673 "TARGET_USE_FANCY_MATH_387 17674 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17675 && flag_unsafe_math_optimizations" 17676{ 17677 rtx op0 = gen_reg_rtx (XFmode); 17678 rtx op1 = gen_reg_rtx (XFmode); 17679 17680 emit_insn (gen_extenddfxf2 (op1, operands[1])); 17681 emit_insn (gen_frndintxf2_floor (op0, op1)); 17682 17683 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 17684 DONE; 17685}) 17686 17687(define_expand "floorsf2" 17688 [(use (match_operand:SF 0 "register_operand" "")) 17689 (use (match_operand:SF 1 "register_operand" ""))] 17690 "TARGET_USE_FANCY_MATH_387 17691 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17692 && flag_unsafe_math_optimizations" 17693{ 17694 rtx op0 = gen_reg_rtx (XFmode); 17695 rtx op1 = gen_reg_rtx (XFmode); 17696 17697 emit_insn (gen_extendsfxf2 (op1, operands[1])); 17698 emit_insn (gen_frndintxf2_floor (op0, op1)); 17699 17700 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 17701 DONE; 17702}) 17703 17704(define_insn_and_split "*fist<mode>2_floor_1" 17705 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r") 17706 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")] 17707 UNSPEC_FIST_FLOOR)) 17708 (clobber (reg:CC FLAGS_REG))] 17709 "TARGET_USE_FANCY_MATH_387 17710 && flag_unsafe_math_optimizations 17711 && !(reload_completed || reload_in_progress)" 17712 "#" 17713 "&& 1" 17714 [(const_int 0)] 17715{ 17716 ix86_optimize_mode_switching[I387_FLOOR] = 1; 17717 17718 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 17719 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR); 17720 if (memory_operand (operands[0], VOIDmode)) 17721 emit_insn (gen_fist<mode>2_floor (operands[0], operands[1], 17722 operands[2], operands[3])); 17723 else 17724 { 17725 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP); 17726 emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1], 17727 operands[2], operands[3], 17728 operands[4])); 17729 } 17730 DONE; 17731} 17732 [(set_attr "type" "fistp") 17733 (set_attr "i387_cw" "floor") 17734 (set_attr "mode" "<MODE>")]) 17735 17736(define_insn "fistdi2_floor" 17737 [(set (match_operand:DI 0 "memory_operand" "=m") 17738 (unspec:DI [(match_operand:XF 1 "register_operand" "f")] 17739 UNSPEC_FIST_FLOOR)) 17740 (use (match_operand:HI 2 "memory_operand" "m")) 17741 (use (match_operand:HI 3 "memory_operand" "m")) 17742 (clobber (match_scratch:XF 4 "=&1f"))] 17743 "TARGET_USE_FANCY_MATH_387 17744 && flag_unsafe_math_optimizations" 17745 "* return output_fix_trunc (insn, operands, 0);" 17746 [(set_attr "type" "fistp") 17747 (set_attr "i387_cw" "floor") 17748 (set_attr "mode" "DI")]) 17749 17750(define_insn "fistdi2_floor_with_temp" 17751 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r") 17752 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")] 17753 UNSPEC_FIST_FLOOR)) 17754 (use (match_operand:HI 2 "memory_operand" "m,m")) 17755 (use (match_operand:HI 3 "memory_operand" "m,m")) 17756 (clobber (match_operand:DI 4 "memory_operand" "=m,m")) 17757 (clobber (match_scratch:XF 5 "=&1f,&1f"))] 17758 "TARGET_USE_FANCY_MATH_387 17759 && flag_unsafe_math_optimizations" 17760 "#" 17761 [(set_attr "type" "fistp") 17762 (set_attr "i387_cw" "floor") 17763 (set_attr "mode" "DI")]) 17764 17765(define_split 17766 [(set (match_operand:DI 0 "register_operand" "") 17767 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 17768 UNSPEC_FIST_FLOOR)) 17769 (use (match_operand:HI 2 "memory_operand" "")) 17770 (use (match_operand:HI 3 "memory_operand" "")) 17771 (clobber (match_operand:DI 4 "memory_operand" "")) 17772 (clobber (match_scratch 5 ""))] 17773 "reload_completed" 17774 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR)) 17775 (use (match_dup 2)) 17776 (use (match_dup 3)) 17777 (clobber (match_dup 5))]) 17778 (set (match_dup 0) (match_dup 4))] 17779 "") 17780 17781(define_split 17782 [(set (match_operand:DI 0 "memory_operand" "") 17783 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 17784 UNSPEC_FIST_FLOOR)) 17785 (use (match_operand:HI 2 "memory_operand" "")) 17786 (use (match_operand:HI 3 "memory_operand" "")) 17787 (clobber (match_operand:DI 4 "memory_operand" "")) 17788 (clobber (match_scratch 5 ""))] 17789 "reload_completed" 17790 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR)) 17791 (use (match_dup 2)) 17792 (use (match_dup 3)) 17793 (clobber (match_dup 5))])] 17794 "") 17795 17796(define_insn "fist<mode>2_floor" 17797 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m") 17798 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")] 17799 UNSPEC_FIST_FLOOR)) 17800 (use (match_operand:HI 2 "memory_operand" "m")) 17801 (use (match_operand:HI 3 "memory_operand" "m"))] 17802 "TARGET_USE_FANCY_MATH_387 17803 && flag_unsafe_math_optimizations" 17804 "* return output_fix_trunc (insn, operands, 0);" 17805 [(set_attr "type" "fistp") 17806 (set_attr "i387_cw" "floor") 17807 (set_attr "mode" "<MODE>")]) 17808 17809(define_insn "fist<mode>2_floor_with_temp" 17810 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r") 17811 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")] 17812 UNSPEC_FIST_FLOOR)) 17813 (use (match_operand:HI 2 "memory_operand" "m,m")) 17814 (use (match_operand:HI 3 "memory_operand" "m,m")) 17815 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))] 17816 "TARGET_USE_FANCY_MATH_387 17817 && flag_unsafe_math_optimizations" 17818 "#" 17819 [(set_attr "type" "fistp") 17820 (set_attr "i387_cw" "floor") 17821 (set_attr "mode" "<MODE>")]) 17822 17823(define_split 17824 [(set (match_operand:X87MODEI12 0 "register_operand" "") 17825 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 17826 UNSPEC_FIST_FLOOR)) 17827 (use (match_operand:HI 2 "memory_operand" "")) 17828 (use (match_operand:HI 3 "memory_operand" "")) 17829 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 17830 "reload_completed" 17831 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)] 17832 UNSPEC_FIST_FLOOR)) 17833 (use (match_dup 2)) 17834 (use (match_dup 3))]) 17835 (set (match_dup 0) (match_dup 4))] 17836 "") 17837 17838(define_split 17839 [(set (match_operand:X87MODEI12 0 "memory_operand" "") 17840 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 17841 UNSPEC_FIST_FLOOR)) 17842 (use (match_operand:HI 2 "memory_operand" "")) 17843 (use (match_operand:HI 3 "memory_operand" "")) 17844 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 17845 "reload_completed" 17846 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] 17847 UNSPEC_FIST_FLOOR)) 17848 (use (match_dup 2)) 17849 (use (match_dup 3))])] 17850 "") 17851 17852(define_expand "lfloor<mode>2" 17853 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "") 17854 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")] 17855 UNSPEC_FIST_FLOOR)) 17856 (clobber (reg:CC FLAGS_REG))])] 17857 "TARGET_USE_FANCY_MATH_387 17858 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17859 && flag_unsafe_math_optimizations" 17860 "") 17861 17862;; Rounding mode control word calculation could clobber FLAGS_REG. 17863(define_insn_and_split "frndintxf2_ceil" 17864 [(set (match_operand:XF 0 "register_operand" "=f") 17865 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 17866 UNSPEC_FRNDINT_CEIL)) 17867 (clobber (reg:CC FLAGS_REG))] 17868 "TARGET_USE_FANCY_MATH_387 17869 && flag_unsafe_math_optimizations 17870 && !(reload_completed || reload_in_progress)" 17871 "#" 17872 "&& 1" 17873 [(const_int 0)] 17874{ 17875 ix86_optimize_mode_switching[I387_CEIL] = 1; 17876 17877 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 17878 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL); 17879 17880 emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1], 17881 operands[2], operands[3])); 17882 DONE; 17883} 17884 [(set_attr "type" "frndint") 17885 (set_attr "i387_cw" "ceil") 17886 (set_attr "mode" "XF")]) 17887 17888(define_insn "frndintxf2_ceil_i387" 17889 [(set (match_operand:XF 0 "register_operand" "=f") 17890 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 17891 UNSPEC_FRNDINT_CEIL)) 17892 (use (match_operand:HI 2 "memory_operand" "m")) 17893 (use (match_operand:HI 3 "memory_operand" "m"))] 17894 "TARGET_USE_FANCY_MATH_387 17895 && flag_unsafe_math_optimizations" 17896 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2" 17897 [(set_attr "type" "frndint") 17898 (set_attr "i387_cw" "ceil") 17899 (set_attr "mode" "XF")]) 17900 17901(define_expand "ceilxf2" 17902 [(use (match_operand:XF 0 "register_operand" "")) 17903 (use (match_operand:XF 1 "register_operand" ""))] 17904 "TARGET_USE_FANCY_MATH_387 17905 && flag_unsafe_math_optimizations" 17906{ 17907 emit_insn (gen_frndintxf2_ceil (operands[0], operands[1])); 17908 DONE; 17909}) 17910 17911(define_expand "ceildf2" 17912 [(use (match_operand:DF 0 "register_operand" "")) 17913 (use (match_operand:DF 1 "register_operand" ""))] 17914 "TARGET_USE_FANCY_MATH_387 17915 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 17916 && flag_unsafe_math_optimizations" 17917{ 17918 rtx op0 = gen_reg_rtx (XFmode); 17919 rtx op1 = gen_reg_rtx (XFmode); 17920 17921 emit_insn (gen_extenddfxf2 (op1, operands[1])); 17922 emit_insn (gen_frndintxf2_ceil (op0, op1)); 17923 17924 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 17925 DONE; 17926}) 17927 17928(define_expand "ceilsf2" 17929 [(use (match_operand:SF 0 "register_operand" "")) 17930 (use (match_operand:SF 1 "register_operand" ""))] 17931 "TARGET_USE_FANCY_MATH_387 17932 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 17933 && flag_unsafe_math_optimizations" 17934{ 17935 rtx op0 = gen_reg_rtx (XFmode); 17936 rtx op1 = gen_reg_rtx (XFmode); 17937 17938 emit_insn (gen_extendsfxf2 (op1, operands[1])); 17939 emit_insn (gen_frndintxf2_ceil (op0, op1)); 17940 17941 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 17942 DONE; 17943}) 17944 17945(define_insn_and_split "*fist<mode>2_ceil_1" 17946 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r") 17947 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")] 17948 UNSPEC_FIST_CEIL)) 17949 (clobber (reg:CC FLAGS_REG))] 17950 "TARGET_USE_FANCY_MATH_387 17951 && flag_unsafe_math_optimizations 17952 && !(reload_completed || reload_in_progress)" 17953 "#" 17954 "&& 1" 17955 [(const_int 0)] 17956{ 17957 ix86_optimize_mode_switching[I387_CEIL] = 1; 17958 17959 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 17960 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL); 17961 if (memory_operand (operands[0], VOIDmode)) 17962 emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1], 17963 operands[2], operands[3])); 17964 else 17965 { 17966 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP); 17967 emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1], 17968 operands[2], operands[3], 17969 operands[4])); 17970 } 17971 DONE; 17972} 17973 [(set_attr "type" "fistp") 17974 (set_attr "i387_cw" "ceil") 17975 (set_attr "mode" "<MODE>")]) 17976 17977(define_insn "fistdi2_ceil" 17978 [(set (match_operand:DI 0 "memory_operand" "=m") 17979 (unspec:DI [(match_operand:XF 1 "register_operand" "f")] 17980 UNSPEC_FIST_CEIL)) 17981 (use (match_operand:HI 2 "memory_operand" "m")) 17982 (use (match_operand:HI 3 "memory_operand" "m")) 17983 (clobber (match_scratch:XF 4 "=&1f"))] 17984 "TARGET_USE_FANCY_MATH_387 17985 && flag_unsafe_math_optimizations" 17986 "* return output_fix_trunc (insn, operands, 0);" 17987 [(set_attr "type" "fistp") 17988 (set_attr "i387_cw" "ceil") 17989 (set_attr "mode" "DI")]) 17990 17991(define_insn "fistdi2_ceil_with_temp" 17992 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r") 17993 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")] 17994 UNSPEC_FIST_CEIL)) 17995 (use (match_operand:HI 2 "memory_operand" "m,m")) 17996 (use (match_operand:HI 3 "memory_operand" "m,m")) 17997 (clobber (match_operand:DI 4 "memory_operand" "=m,m")) 17998 (clobber (match_scratch:XF 5 "=&1f,&1f"))] 17999 "TARGET_USE_FANCY_MATH_387 18000 && flag_unsafe_math_optimizations" 18001 "#" 18002 [(set_attr "type" "fistp") 18003 (set_attr "i387_cw" "ceil") 18004 (set_attr "mode" "DI")]) 18005 18006(define_split 18007 [(set (match_operand:DI 0 "register_operand" "") 18008 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 18009 UNSPEC_FIST_CEIL)) 18010 (use (match_operand:HI 2 "memory_operand" "")) 18011 (use (match_operand:HI 3 "memory_operand" "")) 18012 (clobber (match_operand:DI 4 "memory_operand" "")) 18013 (clobber (match_scratch 5 ""))] 18014 "reload_completed" 18015 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL)) 18016 (use (match_dup 2)) 18017 (use (match_dup 3)) 18018 (clobber (match_dup 5))]) 18019 (set (match_dup 0) (match_dup 4))] 18020 "") 18021 18022(define_split 18023 [(set (match_operand:DI 0 "memory_operand" "") 18024 (unspec:DI [(match_operand:XF 1 "register_operand" "")] 18025 UNSPEC_FIST_CEIL)) 18026 (use (match_operand:HI 2 "memory_operand" "")) 18027 (use (match_operand:HI 3 "memory_operand" "")) 18028 (clobber (match_operand:DI 4 "memory_operand" "")) 18029 (clobber (match_scratch 5 ""))] 18030 "reload_completed" 18031 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL)) 18032 (use (match_dup 2)) 18033 (use (match_dup 3)) 18034 (clobber (match_dup 5))])] 18035 "") 18036 18037(define_insn "fist<mode>2_ceil" 18038 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m") 18039 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")] 18040 UNSPEC_FIST_CEIL)) 18041 (use (match_operand:HI 2 "memory_operand" "m")) 18042 (use (match_operand:HI 3 "memory_operand" "m"))] 18043 "TARGET_USE_FANCY_MATH_387 18044 && flag_unsafe_math_optimizations" 18045 "* return output_fix_trunc (insn, operands, 0);" 18046 [(set_attr "type" "fistp") 18047 (set_attr "i387_cw" "ceil") 18048 (set_attr "mode" "<MODE>")]) 18049 18050(define_insn "fist<mode>2_ceil_with_temp" 18051 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r") 18052 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")] 18053 UNSPEC_FIST_CEIL)) 18054 (use (match_operand:HI 2 "memory_operand" "m,m")) 18055 (use (match_operand:HI 3 "memory_operand" "m,m")) 18056 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))] 18057 "TARGET_USE_FANCY_MATH_387 18058 && flag_unsafe_math_optimizations" 18059 "#" 18060 [(set_attr "type" "fistp") 18061 (set_attr "i387_cw" "ceil") 18062 (set_attr "mode" "<MODE>")]) 18063 18064(define_split 18065 [(set (match_operand:X87MODEI12 0 "register_operand" "") 18066 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 18067 UNSPEC_FIST_CEIL)) 18068 (use (match_operand:HI 2 "memory_operand" "")) 18069 (use (match_operand:HI 3 "memory_operand" "")) 18070 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 18071 "reload_completed" 18072 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)] 18073 UNSPEC_FIST_CEIL)) 18074 (use (match_dup 2)) 18075 (use (match_dup 3))]) 18076 (set (match_dup 0) (match_dup 4))] 18077 "") 18078 18079(define_split 18080 [(set (match_operand:X87MODEI12 0 "memory_operand" "") 18081 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")] 18082 UNSPEC_FIST_CEIL)) 18083 (use (match_operand:HI 2 "memory_operand" "")) 18084 (use (match_operand:HI 3 "memory_operand" "")) 18085 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))] 18086 "reload_completed" 18087 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] 18088 UNSPEC_FIST_CEIL)) 18089 (use (match_dup 2)) 18090 (use (match_dup 3))])] 18091 "") 18092 18093(define_expand "lceil<mode>2" 18094 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "") 18095 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")] 18096 UNSPEC_FIST_CEIL)) 18097 (clobber (reg:CC FLAGS_REG))])] 18098 "TARGET_USE_FANCY_MATH_387 18099 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 18100 && flag_unsafe_math_optimizations" 18101 "") 18102 18103;; Rounding mode control word calculation could clobber FLAGS_REG. 18104(define_insn_and_split "frndintxf2_trunc" 18105 [(set (match_operand:XF 0 "register_operand" "=f") 18106 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 18107 UNSPEC_FRNDINT_TRUNC)) 18108 (clobber (reg:CC FLAGS_REG))] 18109 "TARGET_USE_FANCY_MATH_387 18110 && flag_unsafe_math_optimizations 18111 && !(reload_completed || reload_in_progress)" 18112 "#" 18113 "&& 1" 18114 [(const_int 0)] 18115{ 18116 ix86_optimize_mode_switching[I387_TRUNC] = 1; 18117 18118 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 18119 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC); 18120 18121 emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1], 18122 operands[2], operands[3])); 18123 DONE; 18124} 18125 [(set_attr "type" "frndint") 18126 (set_attr "i387_cw" "trunc") 18127 (set_attr "mode" "XF")]) 18128 18129(define_insn "frndintxf2_trunc_i387" 18130 [(set (match_operand:XF 0 "register_operand" "=f") 18131 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 18132 UNSPEC_FRNDINT_TRUNC)) 18133 (use (match_operand:HI 2 "memory_operand" "m")) 18134 (use (match_operand:HI 3 "memory_operand" "m"))] 18135 "TARGET_USE_FANCY_MATH_387 18136 && flag_unsafe_math_optimizations" 18137 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2" 18138 [(set_attr "type" "frndint") 18139 (set_attr "i387_cw" "trunc") 18140 (set_attr "mode" "XF")]) 18141 18142(define_expand "btruncxf2" 18143 [(use (match_operand:XF 0 "register_operand" "")) 18144 (use (match_operand:XF 1 "register_operand" ""))] 18145 "TARGET_USE_FANCY_MATH_387 18146 && flag_unsafe_math_optimizations" 18147{ 18148 emit_insn (gen_frndintxf2_trunc (operands[0], operands[1])); 18149 DONE; 18150}) 18151 18152(define_expand "btruncdf2" 18153 [(use (match_operand:DF 0 "register_operand" "")) 18154 (use (match_operand:DF 1 "register_operand" ""))] 18155 "TARGET_USE_FANCY_MATH_387 18156 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 18157 && flag_unsafe_math_optimizations" 18158{ 18159 rtx op0 = gen_reg_rtx (XFmode); 18160 rtx op1 = gen_reg_rtx (XFmode); 18161 18162 emit_insn (gen_extenddfxf2 (op1, operands[1])); 18163 emit_insn (gen_frndintxf2_trunc (op0, op1)); 18164 18165 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 18166 DONE; 18167}) 18168 18169(define_expand "btruncsf2" 18170 [(use (match_operand:SF 0 "register_operand" "")) 18171 (use (match_operand:SF 1 "register_operand" ""))] 18172 "TARGET_USE_FANCY_MATH_387 18173 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 18174 && flag_unsafe_math_optimizations" 18175{ 18176 rtx op0 = gen_reg_rtx (XFmode); 18177 rtx op1 = gen_reg_rtx (XFmode); 18178 18179 emit_insn (gen_extendsfxf2 (op1, operands[1])); 18180 emit_insn (gen_frndintxf2_trunc (op0, op1)); 18181 18182 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 18183 DONE; 18184}) 18185 18186;; Rounding mode control word calculation could clobber FLAGS_REG. 18187(define_insn_and_split "frndintxf2_mask_pm" 18188 [(set (match_operand:XF 0 "register_operand" "=f") 18189 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 18190 UNSPEC_FRNDINT_MASK_PM)) 18191 (clobber (reg:CC FLAGS_REG))] 18192 "TARGET_USE_FANCY_MATH_387 18193 && flag_unsafe_math_optimizations 18194 && !(reload_completed || reload_in_progress)" 18195 "#" 18196 "&& 1" 18197 [(const_int 0)] 18198{ 18199 ix86_optimize_mode_switching[I387_MASK_PM] = 1; 18200 18201 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); 18202 operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM); 18203 18204 emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1], 18205 operands[2], operands[3])); 18206 DONE; 18207} 18208 [(set_attr "type" "frndint") 18209 (set_attr "i387_cw" "mask_pm") 18210 (set_attr "mode" "XF")]) 18211 18212(define_insn "frndintxf2_mask_pm_i387" 18213 [(set (match_operand:XF 0 "register_operand" "=f") 18214 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 18215 UNSPEC_FRNDINT_MASK_PM)) 18216 (use (match_operand:HI 2 "memory_operand" "m")) 18217 (use (match_operand:HI 3 "memory_operand" "m"))] 18218 "TARGET_USE_FANCY_MATH_387 18219 && flag_unsafe_math_optimizations" 18220 "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2" 18221 [(set_attr "type" "frndint") 18222 (set_attr "i387_cw" "mask_pm") 18223 (set_attr "mode" "XF")]) 18224 18225(define_expand "nearbyintxf2" 18226 [(use (match_operand:XF 0 "register_operand" "")) 18227 (use (match_operand:XF 1 "register_operand" ""))] 18228 "TARGET_USE_FANCY_MATH_387 18229 && flag_unsafe_math_optimizations" 18230{ 18231 emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1])); 18232 18233 DONE; 18234}) 18235 18236(define_expand "nearbyintdf2" 18237 [(use (match_operand:DF 0 "register_operand" "")) 18238 (use (match_operand:DF 1 "register_operand" ""))] 18239 "TARGET_USE_FANCY_MATH_387 18240 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387) 18241 && flag_unsafe_math_optimizations" 18242{ 18243 rtx op0 = gen_reg_rtx (XFmode); 18244 rtx op1 = gen_reg_rtx (XFmode); 18245 18246 emit_insn (gen_extenddfxf2 (op1, operands[1])); 18247 emit_insn (gen_frndintxf2_mask_pm (op0, op1)); 18248 18249 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0)); 18250 DONE; 18251}) 18252 18253(define_expand "nearbyintsf2" 18254 [(use (match_operand:SF 0 "register_operand" "")) 18255 (use (match_operand:SF 1 "register_operand" ""))] 18256 "TARGET_USE_FANCY_MATH_387 18257 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387) 18258 && flag_unsafe_math_optimizations" 18259{ 18260 rtx op0 = gen_reg_rtx (XFmode); 18261 rtx op1 = gen_reg_rtx (XFmode); 18262 18263 emit_insn (gen_extendsfxf2 (op1, operands[1])); 18264 emit_insn (gen_frndintxf2_mask_pm (op0, op1)); 18265 18266 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0)); 18267 DONE; 18268}) 18269 18270 18271;; Block operation instructions 18272 18273(define_insn "cld" 18274 [(set (reg:SI DIRFLAG_REG) (const_int 0))] 18275 "" 18276 "cld" 18277 [(set_attr "type" "cld")]) 18278 18279(define_expand "movmemsi" 18280 [(use (match_operand:BLK 0 "memory_operand" "")) 18281 (use (match_operand:BLK 1 "memory_operand" "")) 18282 (use (match_operand:SI 2 "nonmemory_operand" "")) 18283 (use (match_operand:SI 3 "const_int_operand" ""))] 18284 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS" 18285{ 18286 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3])) 18287 DONE; 18288 else 18289 FAIL; 18290}) 18291 18292(define_expand "movmemdi" 18293 [(use (match_operand:BLK 0 "memory_operand" "")) 18294 (use (match_operand:BLK 1 "memory_operand" "")) 18295 (use (match_operand:DI 2 "nonmemory_operand" "")) 18296 (use (match_operand:DI 3 "const_int_operand" ""))] 18297 "TARGET_64BIT" 18298{ 18299 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3])) 18300 DONE; 18301 else 18302 FAIL; 18303}) 18304 18305;; Most CPUs don't like single string operations 18306;; Handle this case here to simplify previous expander. 18307 18308(define_expand "strmov" 18309 [(set (match_dup 4) (match_operand 3 "memory_operand" "")) 18310 (set (match_operand 1 "memory_operand" "") (match_dup 4)) 18311 (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5)) 18312 (clobber (reg:CC FLAGS_REG))]) 18313 (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6)) 18314 (clobber (reg:CC FLAGS_REG))])] 18315 "" 18316{ 18317 rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1]))); 18318 18319 /* If .md ever supports :P for Pmode, these can be directly 18320 in the pattern above. */ 18321 operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust); 18322 operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust); 18323 18324 if (TARGET_SINGLE_STRINGOP || optimize_size) 18325 { 18326 emit_insn (gen_strmov_singleop (operands[0], operands[1], 18327 operands[2], operands[3], 18328 operands[5], operands[6])); 18329 DONE; 18330 } 18331 18332 operands[4] = gen_reg_rtx (GET_MODE (operands[1])); 18333}) 18334 18335(define_expand "strmov_singleop" 18336 [(parallel [(set (match_operand 1 "memory_operand" "") 18337 (match_operand 3 "memory_operand" "")) 18338 (set (match_operand 0 "register_operand" "") 18339 (match_operand 4 "" "")) 18340 (set (match_operand 2 "register_operand" "") 18341 (match_operand 5 "" "")) 18342 (use (reg:SI DIRFLAG_REG))])] 18343 "TARGET_SINGLE_STRINGOP || optimize_size" 18344 "") 18345 18346(define_insn "*strmovdi_rex_1" 18347 [(set (mem:DI (match_operand:DI 2 "register_operand" "0")) 18348 (mem:DI (match_operand:DI 3 "register_operand" "1"))) 18349 (set (match_operand:DI 0 "register_operand" "=D") 18350 (plus:DI (match_dup 2) 18351 (const_int 8))) 18352 (set (match_operand:DI 1 "register_operand" "=S") 18353 (plus:DI (match_dup 3) 18354 (const_int 8))) 18355 (use (reg:SI DIRFLAG_REG))] 18356 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18357 "movsq" 18358 [(set_attr "type" "str") 18359 (set_attr "mode" "DI") 18360 (set_attr "memory" "both")]) 18361 18362(define_insn "*strmovsi_1" 18363 [(set (mem:SI (match_operand:SI 2 "register_operand" "0")) 18364 (mem:SI (match_operand:SI 3 "register_operand" "1"))) 18365 (set (match_operand:SI 0 "register_operand" "=D") 18366 (plus:SI (match_dup 2) 18367 (const_int 4))) 18368 (set (match_operand:SI 1 "register_operand" "=S") 18369 (plus:SI (match_dup 3) 18370 (const_int 4))) 18371 (use (reg:SI DIRFLAG_REG))] 18372 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18373 "{movsl|movsd}" 18374 [(set_attr "type" "str") 18375 (set_attr "mode" "SI") 18376 (set_attr "memory" "both")]) 18377 18378(define_insn "*strmovsi_rex_1" 18379 [(set (mem:SI (match_operand:DI 2 "register_operand" "0")) 18380 (mem:SI (match_operand:DI 3 "register_operand" "1"))) 18381 (set (match_operand:DI 0 "register_operand" "=D") 18382 (plus:DI (match_dup 2) 18383 (const_int 4))) 18384 (set (match_operand:DI 1 "register_operand" "=S") 18385 (plus:DI (match_dup 3) 18386 (const_int 4))) 18387 (use (reg:SI DIRFLAG_REG))] 18388 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18389 "{movsl|movsd}" 18390 [(set_attr "type" "str") 18391 (set_attr "mode" "SI") 18392 (set_attr "memory" "both")]) 18393 18394(define_insn "*strmovhi_1" 18395 [(set (mem:HI (match_operand:SI 2 "register_operand" "0")) 18396 (mem:HI (match_operand:SI 3 "register_operand" "1"))) 18397 (set (match_operand:SI 0 "register_operand" "=D") 18398 (plus:SI (match_dup 2) 18399 (const_int 2))) 18400 (set (match_operand:SI 1 "register_operand" "=S") 18401 (plus:SI (match_dup 3) 18402 (const_int 2))) 18403 (use (reg:SI DIRFLAG_REG))] 18404 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18405 "movsw" 18406 [(set_attr "type" "str") 18407 (set_attr "memory" "both") 18408 (set_attr "mode" "HI")]) 18409 18410(define_insn "*strmovhi_rex_1" 18411 [(set (mem:HI (match_operand:DI 2 "register_operand" "0")) 18412 (mem:HI (match_operand:DI 3 "register_operand" "1"))) 18413 (set (match_operand:DI 0 "register_operand" "=D") 18414 (plus:DI (match_dup 2) 18415 (const_int 2))) 18416 (set (match_operand:DI 1 "register_operand" "=S") 18417 (plus:DI (match_dup 3) 18418 (const_int 2))) 18419 (use (reg:SI DIRFLAG_REG))] 18420 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18421 "movsw" 18422 [(set_attr "type" "str") 18423 (set_attr "memory" "both") 18424 (set_attr "mode" "HI")]) 18425 18426(define_insn "*strmovqi_1" 18427 [(set (mem:QI (match_operand:SI 2 "register_operand" "0")) 18428 (mem:QI (match_operand:SI 3 "register_operand" "1"))) 18429 (set (match_operand:SI 0 "register_operand" "=D") 18430 (plus:SI (match_dup 2) 18431 (const_int 1))) 18432 (set (match_operand:SI 1 "register_operand" "=S") 18433 (plus:SI (match_dup 3) 18434 (const_int 1))) 18435 (use (reg:SI DIRFLAG_REG))] 18436 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18437 "movsb" 18438 [(set_attr "type" "str") 18439 (set_attr "memory" "both") 18440 (set_attr "mode" "QI")]) 18441 18442(define_insn "*strmovqi_rex_1" 18443 [(set (mem:QI (match_operand:DI 2 "register_operand" "0")) 18444 (mem:QI (match_operand:DI 3 "register_operand" "1"))) 18445 (set (match_operand:DI 0 "register_operand" "=D") 18446 (plus:DI (match_dup 2) 18447 (const_int 1))) 18448 (set (match_operand:DI 1 "register_operand" "=S") 18449 (plus:DI (match_dup 3) 18450 (const_int 1))) 18451 (use (reg:SI DIRFLAG_REG))] 18452 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18453 "movsb" 18454 [(set_attr "type" "str") 18455 (set_attr "memory" "both") 18456 (set_attr "mode" "QI")]) 18457 18458(define_expand "rep_mov" 18459 [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0)) 18460 (set (match_operand 0 "register_operand" "") 18461 (match_operand 5 "" "")) 18462 (set (match_operand 2 "register_operand" "") 18463 (match_operand 6 "" "")) 18464 (set (match_operand 1 "memory_operand" "") 18465 (match_operand 3 "memory_operand" "")) 18466 (use (match_dup 4)) 18467 (use (reg:SI DIRFLAG_REG))])] 18468 "" 18469 "") 18470 18471(define_insn "*rep_movdi_rex64" 18472 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0)) 18473 (set (match_operand:DI 0 "register_operand" "=D") 18474 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2") 18475 (const_int 3)) 18476 (match_operand:DI 3 "register_operand" "0"))) 18477 (set (match_operand:DI 1 "register_operand" "=S") 18478 (plus:DI (ashift:DI (match_dup 5) (const_int 3)) 18479 (match_operand:DI 4 "register_operand" "1"))) 18480 (set (mem:BLK (match_dup 3)) 18481 (mem:BLK (match_dup 4))) 18482 (use (match_dup 5)) 18483 (use (reg:SI DIRFLAG_REG))] 18484 "TARGET_64BIT" 18485 "{rep\;movsq|rep movsq}" 18486 [(set_attr "type" "str") 18487 (set_attr "prefix_rep" "1") 18488 (set_attr "memory" "both") 18489 (set_attr "mode" "DI")]) 18490 18491(define_insn "*rep_movsi" 18492 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0)) 18493 (set (match_operand:SI 0 "register_operand" "=D") 18494 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2") 18495 (const_int 2)) 18496 (match_operand:SI 3 "register_operand" "0"))) 18497 (set (match_operand:SI 1 "register_operand" "=S") 18498 (plus:SI (ashift:SI (match_dup 5) (const_int 2)) 18499 (match_operand:SI 4 "register_operand" "1"))) 18500 (set (mem:BLK (match_dup 3)) 18501 (mem:BLK (match_dup 4))) 18502 (use (match_dup 5)) 18503 (use (reg:SI DIRFLAG_REG))] 18504 "!TARGET_64BIT" 18505 "{rep\;movsl|rep movsd}" 18506 [(set_attr "type" "str") 18507 (set_attr "prefix_rep" "1") 18508 (set_attr "memory" "both") 18509 (set_attr "mode" "SI")]) 18510 18511(define_insn "*rep_movsi_rex64" 18512 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0)) 18513 (set (match_operand:DI 0 "register_operand" "=D") 18514 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2") 18515 (const_int 2)) 18516 (match_operand:DI 3 "register_operand" "0"))) 18517 (set (match_operand:DI 1 "register_operand" "=S") 18518 (plus:DI (ashift:DI (match_dup 5) (const_int 2)) 18519 (match_operand:DI 4 "register_operand" "1"))) 18520 (set (mem:BLK (match_dup 3)) 18521 (mem:BLK (match_dup 4))) 18522 (use (match_dup 5)) 18523 (use (reg:SI DIRFLAG_REG))] 18524 "TARGET_64BIT" 18525 "{rep\;movsl|rep movsd}" 18526 [(set_attr "type" "str") 18527 (set_attr "prefix_rep" "1") 18528 (set_attr "memory" "both") 18529 (set_attr "mode" "SI")]) 18530 18531(define_insn "*rep_movqi" 18532 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0)) 18533 (set (match_operand:SI 0 "register_operand" "=D") 18534 (plus:SI (match_operand:SI 3 "register_operand" "0") 18535 (match_operand:SI 5 "register_operand" "2"))) 18536 (set (match_operand:SI 1 "register_operand" "=S") 18537 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5))) 18538 (set (mem:BLK (match_dup 3)) 18539 (mem:BLK (match_dup 4))) 18540 (use (match_dup 5)) 18541 (use (reg:SI DIRFLAG_REG))] 18542 "!TARGET_64BIT" 18543 "{rep\;movsb|rep movsb}" 18544 [(set_attr "type" "str") 18545 (set_attr "prefix_rep" "1") 18546 (set_attr "memory" "both") 18547 (set_attr "mode" "SI")]) 18548 18549(define_insn "*rep_movqi_rex64" 18550 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0)) 18551 (set (match_operand:DI 0 "register_operand" "=D") 18552 (plus:DI (match_operand:DI 3 "register_operand" "0") 18553 (match_operand:DI 5 "register_operand" "2"))) 18554 (set (match_operand:DI 1 "register_operand" "=S") 18555 (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5))) 18556 (set (mem:BLK (match_dup 3)) 18557 (mem:BLK (match_dup 4))) 18558 (use (match_dup 5)) 18559 (use (reg:SI DIRFLAG_REG))] 18560 "TARGET_64BIT" 18561 "{rep\;movsb|rep movsb}" 18562 [(set_attr "type" "str") 18563 (set_attr "prefix_rep" "1") 18564 (set_attr "memory" "both") 18565 (set_attr "mode" "SI")]) 18566 18567(define_expand "setmemsi" 18568 [(use (match_operand:BLK 0 "memory_operand" "")) 18569 (use (match_operand:SI 1 "nonmemory_operand" "")) 18570 (use (match_operand 2 "const_int_operand" "")) 18571 (use (match_operand 3 "const_int_operand" ""))] 18572 "" 18573{ 18574 /* If value to set is not zero, use the library routine. */ 18575 if (operands[2] != const0_rtx) 18576 FAIL; 18577 18578 if (ix86_expand_clrmem (operands[0], operands[1], operands[3])) 18579 DONE; 18580 else 18581 FAIL; 18582}) 18583 18584(define_expand "setmemdi" 18585 [(use (match_operand:BLK 0 "memory_operand" "")) 18586 (use (match_operand:DI 1 "nonmemory_operand" "")) 18587 (use (match_operand 2 "const_int_operand" "")) 18588 (use (match_operand 3 "const_int_operand" ""))] 18589 "TARGET_64BIT" 18590{ 18591 /* If value to set is not zero, use the library routine. */ 18592 if (operands[2] != const0_rtx) 18593 FAIL; 18594 18595 if (ix86_expand_clrmem (operands[0], operands[1], operands[3])) 18596 DONE; 18597 else 18598 FAIL; 18599}) 18600 18601;; Most CPUs don't like single string operations 18602;; Handle this case here to simplify previous expander. 18603 18604(define_expand "strset" 18605 [(set (match_operand 1 "memory_operand" "") 18606 (match_operand 2 "register_operand" "")) 18607 (parallel [(set (match_operand 0 "register_operand" "") 18608 (match_dup 3)) 18609 (clobber (reg:CC FLAGS_REG))])] 18610 "" 18611{ 18612 if (GET_MODE (operands[1]) != GET_MODE (operands[2])) 18613 operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0); 18614 18615 /* If .md ever supports :P for Pmode, this can be directly 18616 in the pattern above. */ 18617 operands[3] = gen_rtx_PLUS (Pmode, operands[0], 18618 GEN_INT (GET_MODE_SIZE (GET_MODE 18619 (operands[2])))); 18620 if (TARGET_SINGLE_STRINGOP || optimize_size) 18621 { 18622 emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2], 18623 operands[3])); 18624 DONE; 18625 } 18626}) 18627 18628(define_expand "strset_singleop" 18629 [(parallel [(set (match_operand 1 "memory_operand" "") 18630 (match_operand 2 "register_operand" "")) 18631 (set (match_operand 0 "register_operand" "") 18632 (match_operand 3 "" "")) 18633 (use (reg:SI DIRFLAG_REG))])] 18634 "TARGET_SINGLE_STRINGOP || optimize_size" 18635 "") 18636 18637(define_insn "*strsetdi_rex_1" 18638 [(set (mem:DI (match_operand:DI 1 "register_operand" "0")) 18639 (match_operand:DI 2 "register_operand" "a")) 18640 (set (match_operand:DI 0 "register_operand" "=D") 18641 (plus:DI (match_dup 1) 18642 (const_int 8))) 18643 (use (reg:SI DIRFLAG_REG))] 18644 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18645 "stosq" 18646 [(set_attr "type" "str") 18647 (set_attr "memory" "store") 18648 (set_attr "mode" "DI")]) 18649 18650(define_insn "*strsetsi_1" 18651 [(set (mem:SI (match_operand:SI 1 "register_operand" "0")) 18652 (match_operand:SI 2 "register_operand" "a")) 18653 (set (match_operand:SI 0 "register_operand" "=D") 18654 (plus:SI (match_dup 1) 18655 (const_int 4))) 18656 (use (reg:SI DIRFLAG_REG))] 18657 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18658 "{stosl|stosd}" 18659 [(set_attr "type" "str") 18660 (set_attr "memory" "store") 18661 (set_attr "mode" "SI")]) 18662 18663(define_insn "*strsetsi_rex_1" 18664 [(set (mem:SI (match_operand:DI 1 "register_operand" "0")) 18665 (match_operand:SI 2 "register_operand" "a")) 18666 (set (match_operand:DI 0 "register_operand" "=D") 18667 (plus:DI (match_dup 1) 18668 (const_int 4))) 18669 (use (reg:SI DIRFLAG_REG))] 18670 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18671 "{stosl|stosd}" 18672 [(set_attr "type" "str") 18673 (set_attr "memory" "store") 18674 (set_attr "mode" "SI")]) 18675 18676(define_insn "*strsethi_1" 18677 [(set (mem:HI (match_operand:SI 1 "register_operand" "0")) 18678 (match_operand:HI 2 "register_operand" "a")) 18679 (set (match_operand:SI 0 "register_operand" "=D") 18680 (plus:SI (match_dup 1) 18681 (const_int 2))) 18682 (use (reg:SI DIRFLAG_REG))] 18683 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18684 "stosw" 18685 [(set_attr "type" "str") 18686 (set_attr "memory" "store") 18687 (set_attr "mode" "HI")]) 18688 18689(define_insn "*strsethi_rex_1" 18690 [(set (mem:HI (match_operand:DI 1 "register_operand" "0")) 18691 (match_operand:HI 2 "register_operand" "a")) 18692 (set (match_operand:DI 0 "register_operand" "=D") 18693 (plus:DI (match_dup 1) 18694 (const_int 2))) 18695 (use (reg:SI DIRFLAG_REG))] 18696 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18697 "stosw" 18698 [(set_attr "type" "str") 18699 (set_attr "memory" "store") 18700 (set_attr "mode" "HI")]) 18701 18702(define_insn "*strsetqi_1" 18703 [(set (mem:QI (match_operand:SI 1 "register_operand" "0")) 18704 (match_operand:QI 2 "register_operand" "a")) 18705 (set (match_operand:SI 0 "register_operand" "=D") 18706 (plus:SI (match_dup 1) 18707 (const_int 1))) 18708 (use (reg:SI DIRFLAG_REG))] 18709 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18710 "stosb" 18711 [(set_attr "type" "str") 18712 (set_attr "memory" "store") 18713 (set_attr "mode" "QI")]) 18714 18715(define_insn "*strsetqi_rex_1" 18716 [(set (mem:QI (match_operand:DI 1 "register_operand" "0")) 18717 (match_operand:QI 2 "register_operand" "a")) 18718 (set (match_operand:DI 0 "register_operand" "=D") 18719 (plus:DI (match_dup 1) 18720 (const_int 1))) 18721 (use (reg:SI DIRFLAG_REG))] 18722 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)" 18723 "stosb" 18724 [(set_attr "type" "str") 18725 (set_attr "memory" "store") 18726 (set_attr "mode" "QI")]) 18727 18728(define_expand "rep_stos" 18729 [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0)) 18730 (set (match_operand 0 "register_operand" "") 18731 (match_operand 4 "" "")) 18732 (set (match_operand 2 "memory_operand" "") (const_int 0)) 18733 (use (match_operand 3 "register_operand" "")) 18734 (use (match_dup 1)) 18735 (use (reg:SI DIRFLAG_REG))])] 18736 "" 18737 "") 18738 18739(define_insn "*rep_stosdi_rex64" 18740 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0)) 18741 (set (match_operand:DI 0 "register_operand" "=D") 18742 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1") 18743 (const_int 3)) 18744 (match_operand:DI 3 "register_operand" "0"))) 18745 (set (mem:BLK (match_dup 3)) 18746 (const_int 0)) 18747 (use (match_operand:DI 2 "register_operand" "a")) 18748 (use (match_dup 4)) 18749 (use (reg:SI DIRFLAG_REG))] 18750 "TARGET_64BIT" 18751 "{rep\;stosq|rep stosq}" 18752 [(set_attr "type" "str") 18753 (set_attr "prefix_rep" "1") 18754 (set_attr "memory" "store") 18755 (set_attr "mode" "DI")]) 18756 18757(define_insn "*rep_stossi" 18758 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0)) 18759 (set (match_operand:SI 0 "register_operand" "=D") 18760 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1") 18761 (const_int 2)) 18762 (match_operand:SI 3 "register_operand" "0"))) 18763 (set (mem:BLK (match_dup 3)) 18764 (const_int 0)) 18765 (use (match_operand:SI 2 "register_operand" "a")) 18766 (use (match_dup 4)) 18767 (use (reg:SI DIRFLAG_REG))] 18768 "!TARGET_64BIT" 18769 "{rep\;stosl|rep stosd}" 18770 [(set_attr "type" "str") 18771 (set_attr "prefix_rep" "1") 18772 (set_attr "memory" "store") 18773 (set_attr "mode" "SI")]) 18774 18775(define_insn "*rep_stossi_rex64" 18776 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0)) 18777 (set (match_operand:DI 0 "register_operand" "=D") 18778 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1") 18779 (const_int 2)) 18780 (match_operand:DI 3 "register_operand" "0"))) 18781 (set (mem:BLK (match_dup 3)) 18782 (const_int 0)) 18783 (use (match_operand:SI 2 "register_operand" "a")) 18784 (use (match_dup 4)) 18785 (use (reg:SI DIRFLAG_REG))] 18786 "TARGET_64BIT" 18787 "{rep\;stosl|rep stosd}" 18788 [(set_attr "type" "str") 18789 (set_attr "prefix_rep" "1") 18790 (set_attr "memory" "store") 18791 (set_attr "mode" "SI")]) 18792 18793(define_insn "*rep_stosqi" 18794 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0)) 18795 (set (match_operand:SI 0 "register_operand" "=D") 18796 (plus:SI (match_operand:SI 3 "register_operand" "0") 18797 (match_operand:SI 4 "register_operand" "1"))) 18798 (set (mem:BLK (match_dup 3)) 18799 (const_int 0)) 18800 (use (match_operand:QI 2 "register_operand" "a")) 18801 (use (match_dup 4)) 18802 (use (reg:SI DIRFLAG_REG))] 18803 "!TARGET_64BIT" 18804 "{rep\;stosb|rep stosb}" 18805 [(set_attr "type" "str") 18806 (set_attr "prefix_rep" "1") 18807 (set_attr "memory" "store") 18808 (set_attr "mode" "QI")]) 18809 18810(define_insn "*rep_stosqi_rex64" 18811 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0)) 18812 (set (match_operand:DI 0 "register_operand" "=D") 18813 (plus:DI (match_operand:DI 3 "register_operand" "0") 18814 (match_operand:DI 4 "register_operand" "1"))) 18815 (set (mem:BLK (match_dup 3)) 18816 (const_int 0)) 18817 (use (match_operand:QI 2 "register_operand" "a")) 18818 (use (match_dup 4)) 18819 (use (reg:SI DIRFLAG_REG))] 18820 "TARGET_64BIT" 18821 "{rep\;stosb|rep stosb}" 18822 [(set_attr "type" "str") 18823 (set_attr "prefix_rep" "1") 18824 (set_attr "memory" "store") 18825 (set_attr "mode" "QI")]) 18826 18827(define_expand "cmpstrnsi" 18828 [(set (match_operand:SI 0 "register_operand" "") 18829 (compare:SI (match_operand:BLK 1 "general_operand" "") 18830 (match_operand:BLK 2 "general_operand" ""))) 18831 (use (match_operand 3 "general_operand" "")) 18832 (use (match_operand 4 "immediate_operand" ""))] 18833 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS" 18834{ 18835 rtx addr1, addr2, out, outlow, count, countreg, align; 18836 18837 /* Can't use this if the user has appropriated esi or edi. */ 18838 if (global_regs[4] || global_regs[5]) 18839 FAIL; 18840 18841 out = operands[0]; 18842 if (GET_CODE (out) != REG) 18843 out = gen_reg_rtx (SImode); 18844 18845 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0)); 18846 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0)); 18847 if (addr1 != XEXP (operands[1], 0)) 18848 operands[1] = replace_equiv_address_nv (operands[1], addr1); 18849 if (addr2 != XEXP (operands[2], 0)) 18850 operands[2] = replace_equiv_address_nv (operands[2], addr2); 18851 18852 count = operands[3]; 18853 countreg = ix86_zero_extend_to_Pmode (count); 18854 18855 /* %%% Iff we are testing strict equality, we can use known alignment 18856 to good advantage. This may be possible with combine, particularly 18857 once cc0 is dead. */ 18858 align = operands[4]; 18859 18860 emit_insn (gen_cld ()); 18861 if (GET_CODE (count) == CONST_INT) 18862 { 18863 if (INTVAL (count) == 0) 18864 { 18865 emit_move_insn (operands[0], const0_rtx); 18866 DONE; 18867 } 18868 emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align, 18869 operands[1], operands[2])); 18870 } 18871 else 18872 { 18873 if (TARGET_64BIT) 18874 emit_insn (gen_cmpdi_1_rex64 (countreg, countreg)); 18875 else 18876 emit_insn (gen_cmpsi_1 (countreg, countreg)); 18877 emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align, 18878 operands[1], operands[2])); 18879 } 18880 18881 outlow = gen_lowpart (QImode, out); 18882 emit_insn (gen_cmpintqi (outlow)); 18883 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow)); 18884 18885 if (operands[0] != out) 18886 emit_move_insn (operands[0], out); 18887 18888 DONE; 18889}) 18890 18891;; Produce a tri-state integer (-1, 0, 1) from condition codes. 18892 18893(define_expand "cmpintqi" 18894 [(set (match_dup 1) 18895 (gtu:QI (reg:CC FLAGS_REG) (const_int 0))) 18896 (set (match_dup 2) 18897 (ltu:QI (reg:CC FLAGS_REG) (const_int 0))) 18898 (parallel [(set (match_operand:QI 0 "register_operand" "") 18899 (minus:QI (match_dup 1) 18900 (match_dup 2))) 18901 (clobber (reg:CC FLAGS_REG))])] 18902 "" 18903 "operands[1] = gen_reg_rtx (QImode); 18904 operands[2] = gen_reg_rtx (QImode);") 18905 18906;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is 18907;; zero. Emit extra code to make sure that a zero-length compare is EQ. 18908 18909(define_expand "cmpstrnqi_nz_1" 18910 [(parallel [(set (reg:CC FLAGS_REG) 18911 (compare:CC (match_operand 4 "memory_operand" "") 18912 (match_operand 5 "memory_operand" ""))) 18913 (use (match_operand 2 "register_operand" "")) 18914 (use (match_operand:SI 3 "immediate_operand" "")) 18915 (use (reg:SI DIRFLAG_REG)) 18916 (clobber (match_operand 0 "register_operand" "")) 18917 (clobber (match_operand 1 "register_operand" "")) 18918 (clobber (match_dup 2))])] 18919 "" 18920 "") 18921 18922(define_insn "*cmpstrnqi_nz_1" 18923 [(set (reg:CC FLAGS_REG) 18924 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0")) 18925 (mem:BLK (match_operand:SI 5 "register_operand" "1")))) 18926 (use (match_operand:SI 6 "register_operand" "2")) 18927 (use (match_operand:SI 3 "immediate_operand" "i")) 18928 (use (reg:SI DIRFLAG_REG)) 18929 (clobber (match_operand:SI 0 "register_operand" "=S")) 18930 (clobber (match_operand:SI 1 "register_operand" "=D")) 18931 (clobber (match_operand:SI 2 "register_operand" "=c"))] 18932 "!TARGET_64BIT" 18933 "repz{\;| }cmpsb" 18934 [(set_attr "type" "str") 18935 (set_attr "mode" "QI") 18936 (set_attr "prefix_rep" "1")]) 18937 18938(define_insn "*cmpstrnqi_nz_rex_1" 18939 [(set (reg:CC FLAGS_REG) 18940 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0")) 18941 (mem:BLK (match_operand:DI 5 "register_operand" "1")))) 18942 (use (match_operand:DI 6 "register_operand" "2")) 18943 (use (match_operand:SI 3 "immediate_operand" "i")) 18944 (use (reg:SI DIRFLAG_REG)) 18945 (clobber (match_operand:DI 0 "register_operand" "=S")) 18946 (clobber (match_operand:DI 1 "register_operand" "=D")) 18947 (clobber (match_operand:DI 2 "register_operand" "=c"))] 18948 "TARGET_64BIT" 18949 "repz{\;| }cmpsb" 18950 [(set_attr "type" "str") 18951 (set_attr "mode" "QI") 18952 (set_attr "prefix_rep" "1")]) 18953 18954;; The same, but the count is not known to not be zero. 18955 18956(define_expand "cmpstrnqi_1" 18957 [(parallel [(set (reg:CC FLAGS_REG) 18958 (if_then_else:CC (ne (match_operand 2 "register_operand" "") 18959 (const_int 0)) 18960 (compare:CC (match_operand 4 "memory_operand" "") 18961 (match_operand 5 "memory_operand" "")) 18962 (const_int 0))) 18963 (use (match_operand:SI 3 "immediate_operand" "")) 18964 (use (reg:CC FLAGS_REG)) 18965 (use (reg:SI DIRFLAG_REG)) 18966 (clobber (match_operand 0 "register_operand" "")) 18967 (clobber (match_operand 1 "register_operand" "")) 18968 (clobber (match_dup 2))])] 18969 "" 18970 "") 18971 18972(define_insn "*cmpstrnqi_1" 18973 [(set (reg:CC FLAGS_REG) 18974 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2") 18975 (const_int 0)) 18976 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0")) 18977 (mem:BLK (match_operand:SI 5 "register_operand" "1"))) 18978 (const_int 0))) 18979 (use (match_operand:SI 3 "immediate_operand" "i")) 18980 (use (reg:CC FLAGS_REG)) 18981 (use (reg:SI DIRFLAG_REG)) 18982 (clobber (match_operand:SI 0 "register_operand" "=S")) 18983 (clobber (match_operand:SI 1 "register_operand" "=D")) 18984 (clobber (match_operand:SI 2 "register_operand" "=c"))] 18985 "!TARGET_64BIT" 18986 "repz{\;| }cmpsb" 18987 [(set_attr "type" "str") 18988 (set_attr "mode" "QI") 18989 (set_attr "prefix_rep" "1")]) 18990 18991(define_insn "*cmpstrnqi_rex_1" 18992 [(set (reg:CC FLAGS_REG) 18993 (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2") 18994 (const_int 0)) 18995 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0")) 18996 (mem:BLK (match_operand:DI 5 "register_operand" "1"))) 18997 (const_int 0))) 18998 (use (match_operand:SI 3 "immediate_operand" "i")) 18999 (use (reg:CC FLAGS_REG)) 19000 (use (reg:SI DIRFLAG_REG)) 19001 (clobber (match_operand:DI 0 "register_operand" "=S")) 19002 (clobber (match_operand:DI 1 "register_operand" "=D")) 19003 (clobber (match_operand:DI 2 "register_operand" "=c"))] 19004 "TARGET_64BIT" 19005 "repz{\;| }cmpsb" 19006 [(set_attr "type" "str") 19007 (set_attr "mode" "QI") 19008 (set_attr "prefix_rep" "1")]) 19009 19010(define_expand "strlensi" 19011 [(set (match_operand:SI 0 "register_operand" "") 19012 (unspec:SI [(match_operand:BLK 1 "general_operand" "") 19013 (match_operand:QI 2 "immediate_operand" "") 19014 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))] 19015 "" 19016{ 19017 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3])) 19018 DONE; 19019 else 19020 FAIL; 19021}) 19022 19023(define_expand "strlendi" 19024 [(set (match_operand:DI 0 "register_operand" "") 19025 (unspec:DI [(match_operand:BLK 1 "general_operand" "") 19026 (match_operand:QI 2 "immediate_operand" "") 19027 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))] 19028 "" 19029{ 19030 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3])) 19031 DONE; 19032 else 19033 FAIL; 19034}) 19035 19036(define_expand "strlenqi_1" 19037 [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" "")) 19038 (use (reg:SI DIRFLAG_REG)) 19039 (clobber (match_operand 1 "register_operand" "")) 19040 (clobber (reg:CC FLAGS_REG))])] 19041 "" 19042 "") 19043 19044(define_insn "*strlenqi_1" 19045 [(set (match_operand:SI 0 "register_operand" "=&c") 19046 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1")) 19047 (match_operand:QI 2 "register_operand" "a") 19048 (match_operand:SI 3 "immediate_operand" "i") 19049 (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS)) 19050 (use (reg:SI DIRFLAG_REG)) 19051 (clobber (match_operand:SI 1 "register_operand" "=D")) 19052 (clobber (reg:CC FLAGS_REG))] 19053 "!TARGET_64BIT" 19054 "repnz{\;| }scasb" 19055 [(set_attr "type" "str") 19056 (set_attr "mode" "QI") 19057 (set_attr "prefix_rep" "1")]) 19058 19059(define_insn "*strlenqi_rex_1" 19060 [(set (match_operand:DI 0 "register_operand" "=&c") 19061 (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1")) 19062 (match_operand:QI 2 "register_operand" "a") 19063 (match_operand:DI 3 "immediate_operand" "i") 19064 (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS)) 19065 (use (reg:SI DIRFLAG_REG)) 19066 (clobber (match_operand:DI 1 "register_operand" "=D")) 19067 (clobber (reg:CC FLAGS_REG))] 19068 "TARGET_64BIT" 19069 "repnz{\;| }scasb" 19070 [(set_attr "type" "str") 19071 (set_attr "mode" "QI") 19072 (set_attr "prefix_rep" "1")]) 19073 19074;; Peephole optimizations to clean up after cmpstrn*. This should be 19075;; handled in combine, but it is not currently up to the task. 19076;; When used for their truth value, the cmpstrn* expanders generate 19077;; code like this: 19078;; 19079;; repz cmpsb 19080;; seta %al 19081;; setb %dl 19082;; cmpb %al, %dl 19083;; jcc label 19084;; 19085;; The intermediate three instructions are unnecessary. 19086 19087;; This one handles cmpstrn*_nz_1... 19088(define_peephole2 19089 [(parallel[ 19090 (set (reg:CC FLAGS_REG) 19091 (compare:CC (mem:BLK (match_operand 4 "register_operand" "")) 19092 (mem:BLK (match_operand 5 "register_operand" "")))) 19093 (use (match_operand 6 "register_operand" "")) 19094 (use (match_operand:SI 3 "immediate_operand" "")) 19095 (use (reg:SI DIRFLAG_REG)) 19096 (clobber (match_operand 0 "register_operand" "")) 19097 (clobber (match_operand 1 "register_operand" "")) 19098 (clobber (match_operand 2 "register_operand" ""))]) 19099 (set (match_operand:QI 7 "register_operand" "") 19100 (gtu:QI (reg:CC FLAGS_REG) (const_int 0))) 19101 (set (match_operand:QI 8 "register_operand" "") 19102 (ltu:QI (reg:CC FLAGS_REG) (const_int 0))) 19103 (set (reg FLAGS_REG) 19104 (compare (match_dup 7) (match_dup 8))) 19105 ] 19106 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])" 19107 [(parallel[ 19108 (set (reg:CC FLAGS_REG) 19109 (compare:CC (mem:BLK (match_dup 4)) 19110 (mem:BLK (match_dup 5)))) 19111 (use (match_dup 6)) 19112 (use (match_dup 3)) 19113 (use (reg:SI DIRFLAG_REG)) 19114 (clobber (match_dup 0)) 19115 (clobber (match_dup 1)) 19116 (clobber (match_dup 2))])] 19117 "") 19118 19119;; ...and this one handles cmpstrn*_1. 19120(define_peephole2 19121 [(parallel[ 19122 (set (reg:CC FLAGS_REG) 19123 (if_then_else:CC (ne (match_operand 6 "register_operand" "") 19124 (const_int 0)) 19125 (compare:CC (mem:BLK (match_operand 4 "register_operand" "")) 19126 (mem:BLK (match_operand 5 "register_operand" ""))) 19127 (const_int 0))) 19128 (use (match_operand:SI 3 "immediate_operand" "")) 19129 (use (reg:CC FLAGS_REG)) 19130 (use (reg:SI DIRFLAG_REG)) 19131 (clobber (match_operand 0 "register_operand" "")) 19132 (clobber (match_operand 1 "register_operand" "")) 19133 (clobber (match_operand 2 "register_operand" ""))]) 19134 (set (match_operand:QI 7 "register_operand" "") 19135 (gtu:QI (reg:CC FLAGS_REG) (const_int 0))) 19136 (set (match_operand:QI 8 "register_operand" "") 19137 (ltu:QI (reg:CC FLAGS_REG) (const_int 0))) 19138 (set (reg FLAGS_REG) 19139 (compare (match_dup 7) (match_dup 8))) 19140 ] 19141 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])" 19142 [(parallel[ 19143 (set (reg:CC FLAGS_REG) 19144 (if_then_else:CC (ne (match_dup 6) 19145 (const_int 0)) 19146 (compare:CC (mem:BLK (match_dup 4)) 19147 (mem:BLK (match_dup 5))) 19148 (const_int 0))) 19149 (use (match_dup 3)) 19150 (use (reg:CC FLAGS_REG)) 19151 (use (reg:SI DIRFLAG_REG)) 19152 (clobber (match_dup 0)) 19153 (clobber (match_dup 1)) 19154 (clobber (match_dup 2))])] 19155 "") 19156 19157 19158 19159;; Conditional move instructions. 19160 19161(define_expand "movdicc" 19162 [(set (match_operand:DI 0 "register_operand" "") 19163 (if_then_else:DI (match_operand 1 "comparison_operator" "") 19164 (match_operand:DI 2 "general_operand" "") 19165 (match_operand:DI 3 "general_operand" "")))] 19166 "TARGET_64BIT" 19167 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;") 19168 19169(define_insn "x86_movdicc_0_m1_rex64" 19170 [(set (match_operand:DI 0 "register_operand" "=r") 19171 (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "") 19172 (const_int -1) 19173 (const_int 0))) 19174 (clobber (reg:CC FLAGS_REG))] 19175 "TARGET_64BIT" 19176 "sbb{q}\t%0, %0" 19177 ; Since we don't have the proper number of operands for an alu insn, 19178 ; fill in all the blanks. 19179 [(set_attr "type" "alu") 19180 (set_attr "pent_pair" "pu") 19181 (set_attr "memory" "none") 19182 (set_attr "imm_disp" "false") 19183 (set_attr "mode" "DI") 19184 (set_attr "length_immediate" "0")]) 19185 19186(define_insn "*movdicc_c_rex64" 19187 [(set (match_operand:DI 0 "register_operand" "=r,r") 19188 (if_then_else:DI (match_operator 1 "ix86_comparison_operator" 19189 [(reg FLAGS_REG) (const_int 0)]) 19190 (match_operand:DI 2 "nonimmediate_operand" "rm,0") 19191 (match_operand:DI 3 "nonimmediate_operand" "0,rm")))] 19192 "TARGET_64BIT && TARGET_CMOVE 19193 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19194 "@ 19195 cmov%O2%C1\t{%2, %0|%0, %2} 19196 cmov%O2%c1\t{%3, %0|%0, %3}" 19197 [(set_attr "type" "icmov") 19198 (set_attr "mode" "DI")]) 19199 19200(define_expand "movsicc" 19201 [(set (match_operand:SI 0 "register_operand" "") 19202 (if_then_else:SI (match_operand 1 "comparison_operator" "") 19203 (match_operand:SI 2 "general_operand" "") 19204 (match_operand:SI 3 "general_operand" "")))] 19205 "" 19206 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;") 19207 19208;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing 19209;; the register first winds up with `sbbl $0,reg', which is also weird. 19210;; So just document what we're doing explicitly. 19211 19212(define_insn "x86_movsicc_0_m1" 19213 [(set (match_operand:SI 0 "register_operand" "=r") 19214 (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "") 19215 (const_int -1) 19216 (const_int 0))) 19217 (clobber (reg:CC FLAGS_REG))] 19218 "" 19219 "sbb{l}\t%0, %0" 19220 ; Since we don't have the proper number of operands for an alu insn, 19221 ; fill in all the blanks. 19222 [(set_attr "type" "alu") 19223 (set_attr "pent_pair" "pu") 19224 (set_attr "memory" "none") 19225 (set_attr "imm_disp" "false") 19226 (set_attr "mode" "SI") 19227 (set_attr "length_immediate" "0")]) 19228 19229(define_insn "*movsicc_noc" 19230 [(set (match_operand:SI 0 "register_operand" "=r,r") 19231 (if_then_else:SI (match_operator 1 "ix86_comparison_operator" 19232 [(reg FLAGS_REG) (const_int 0)]) 19233 (match_operand:SI 2 "nonimmediate_operand" "rm,0") 19234 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))] 19235 "TARGET_CMOVE 19236 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19237 "@ 19238 cmov%O2%C1\t{%2, %0|%0, %2} 19239 cmov%O2%c1\t{%3, %0|%0, %3}" 19240 [(set_attr "type" "icmov") 19241 (set_attr "mode" "SI")]) 19242 19243(define_expand "movhicc" 19244 [(set (match_operand:HI 0 "register_operand" "") 19245 (if_then_else:HI (match_operand 1 "comparison_operator" "") 19246 (match_operand:HI 2 "general_operand" "") 19247 (match_operand:HI 3 "general_operand" "")))] 19248 "TARGET_HIMODE_MATH" 19249 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;") 19250 19251(define_insn "*movhicc_noc" 19252 [(set (match_operand:HI 0 "register_operand" "=r,r") 19253 (if_then_else:HI (match_operator 1 "ix86_comparison_operator" 19254 [(reg FLAGS_REG) (const_int 0)]) 19255 (match_operand:HI 2 "nonimmediate_operand" "rm,0") 19256 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))] 19257 "TARGET_CMOVE 19258 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19259 "@ 19260 cmov%O2%C1\t{%2, %0|%0, %2} 19261 cmov%O2%c1\t{%3, %0|%0, %3}" 19262 [(set_attr "type" "icmov") 19263 (set_attr "mode" "HI")]) 19264 19265(define_expand "movqicc" 19266 [(set (match_operand:QI 0 "register_operand" "") 19267 (if_then_else:QI (match_operand 1 "comparison_operator" "") 19268 (match_operand:QI 2 "general_operand" "") 19269 (match_operand:QI 3 "general_operand" "")))] 19270 "TARGET_QIMODE_MATH" 19271 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;") 19272 19273(define_insn_and_split "*movqicc_noc" 19274 [(set (match_operand:QI 0 "register_operand" "=r,r") 19275 (if_then_else:QI (match_operator 1 "ix86_comparison_operator" 19276 [(match_operand 4 "flags_reg_operand" "") 19277 (const_int 0)]) 19278 (match_operand:QI 2 "register_operand" "r,0") 19279 (match_operand:QI 3 "register_operand" "0,r")))] 19280 "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL" 19281 "#" 19282 "&& reload_completed" 19283 [(set (match_dup 0) 19284 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)]) 19285 (match_dup 2) 19286 (match_dup 3)))] 19287 "operands[0] = gen_lowpart (SImode, operands[0]); 19288 operands[2] = gen_lowpart (SImode, operands[2]); 19289 operands[3] = gen_lowpart (SImode, operands[3]);" 19290 [(set_attr "type" "icmov") 19291 (set_attr "mode" "SI")]) 19292 19293(define_expand "movsfcc" 19294 [(set (match_operand:SF 0 "register_operand" "") 19295 (if_then_else:SF (match_operand 1 "comparison_operator" "") 19296 (match_operand:SF 2 "register_operand" "") 19297 (match_operand:SF 3 "register_operand" "")))] 19298 "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH" 19299 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;") 19300 19301(define_insn "*movsfcc_1_387" 19302 [(set (match_operand:SF 0 "register_operand" "=f,f,r,r") 19303 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator" 19304 [(reg FLAGS_REG) (const_int 0)]) 19305 (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0") 19306 (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))] 19307 "TARGET_80387 && TARGET_CMOVE 19308 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19309 "@ 19310 fcmov%F1\t{%2, %0|%0, %2} 19311 fcmov%f1\t{%3, %0|%0, %3} 19312 cmov%O2%C1\t{%2, %0|%0, %2} 19313 cmov%O2%c1\t{%3, %0|%0, %3}" 19314 [(set_attr "type" "fcmov,fcmov,icmov,icmov") 19315 (set_attr "mode" "SF,SF,SI,SI")]) 19316 19317(define_expand "movdfcc" 19318 [(set (match_operand:DF 0 "register_operand" "") 19319 (if_then_else:DF (match_operand 1 "comparison_operator" "") 19320 (match_operand:DF 2 "register_operand" "") 19321 (match_operand:DF 3 "register_operand" "")))] 19322 "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)" 19323 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;") 19324 19325(define_insn "*movdfcc_1" 19326 [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r") 19327 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 19328 [(reg FLAGS_REG) (const_int 0)]) 19329 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0") 19330 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))] 19331 "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE 19332 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19333 "@ 19334 fcmov%F1\t{%2, %0|%0, %2} 19335 fcmov%f1\t{%3, %0|%0, %3} 19336 # 19337 #" 19338 [(set_attr "type" "fcmov,fcmov,multi,multi") 19339 (set_attr "mode" "DF")]) 19340 19341(define_insn "*movdfcc_1_rex64" 19342 [(set (match_operand:DF 0 "register_operand" "=f,f,r,r") 19343 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 19344 [(reg FLAGS_REG) (const_int 0)]) 19345 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0") 19346 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))] 19347 "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE 19348 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)" 19349 "@ 19350 fcmov%F1\t{%2, %0|%0, %2} 19351 fcmov%f1\t{%3, %0|%0, %3} 19352 cmov%O2%C1\t{%2, %0|%0, %2} 19353 cmov%O2%c1\t{%3, %0|%0, %3}" 19354 [(set_attr "type" "fcmov,fcmov,icmov,icmov") 19355 (set_attr "mode" "DF")]) 19356 19357(define_split 19358 [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "") 19359 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 19360 [(match_operand 4 "flags_reg_operand" "") 19361 (const_int 0)]) 19362 (match_operand:DF 2 "nonimmediate_operand" "") 19363 (match_operand:DF 3 "nonimmediate_operand" "")))] 19364 "!TARGET_64BIT && reload_completed" 19365 [(set (match_dup 2) 19366 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)]) 19367 (match_dup 5) 19368 (match_dup 7))) 19369 (set (match_dup 3) 19370 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)]) 19371 (match_dup 6) 19372 (match_dup 8)))] 19373 "split_di (operands+2, 1, operands+5, operands+6); 19374 split_di (operands+3, 1, operands+7, operands+8); 19375 split_di (operands, 1, operands+2, operands+3);") 19376 19377(define_expand "movxfcc" 19378 [(set (match_operand:XF 0 "register_operand" "") 19379 (if_then_else:XF (match_operand 1 "comparison_operator" "") 19380 (match_operand:XF 2 "register_operand" "") 19381 (match_operand:XF 3 "register_operand" "")))] 19382 "TARGET_80387 && TARGET_CMOVE" 19383 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;") 19384 19385(define_insn "*movxfcc_1" 19386 [(set (match_operand:XF 0 "register_operand" "=f,f") 19387 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator" 19388 [(reg FLAGS_REG) (const_int 0)]) 19389 (match_operand:XF 2 "register_operand" "f,0") 19390 (match_operand:XF 3 "register_operand" "0,f")))] 19391 "TARGET_80387 && TARGET_CMOVE" 19392 "@ 19393 fcmov%F1\t{%2, %0|%0, %2} 19394 fcmov%f1\t{%3, %0|%0, %3}" 19395 [(set_attr "type" "fcmov") 19396 (set_attr "mode" "XF")]) 19397 19398;; These versions of the min/max patterns are intentionally ignorant of 19399;; their behavior wrt -0.0 and NaN (via the commutative operand mark). 19400;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator 19401;; are undefined in this condition, we're certain this is correct. 19402 19403(define_insn "sminsf3" 19404 [(set (match_operand:SF 0 "register_operand" "=x") 19405 (smin:SF (match_operand:SF 1 "nonimmediate_operand" "%0") 19406 (match_operand:SF 2 "nonimmediate_operand" "xm")))] 19407 "TARGET_SSE_MATH" 19408 "minss\t{%2, %0|%0, %2}" 19409 [(set_attr "type" "sseadd") 19410 (set_attr "mode" "SF")]) 19411 19412(define_insn "smaxsf3" 19413 [(set (match_operand:SF 0 "register_operand" "=x") 19414 (smax:SF (match_operand:SF 1 "nonimmediate_operand" "%0") 19415 (match_operand:SF 2 "nonimmediate_operand" "xm")))] 19416 "TARGET_SSE_MATH" 19417 "maxss\t{%2, %0|%0, %2}" 19418 [(set_attr "type" "sseadd") 19419 (set_attr "mode" "SF")]) 19420 19421(define_insn "smindf3" 19422 [(set (match_operand:DF 0 "register_operand" "=x") 19423 (smin:DF (match_operand:DF 1 "nonimmediate_operand" "%0") 19424 (match_operand:DF 2 "nonimmediate_operand" "xm")))] 19425 "TARGET_SSE2 && TARGET_SSE_MATH" 19426 "minsd\t{%2, %0|%0, %2}" 19427 [(set_attr "type" "sseadd") 19428 (set_attr "mode" "DF")]) 19429 19430(define_insn "smaxdf3" 19431 [(set (match_operand:DF 0 "register_operand" "=x") 19432 (smax:DF (match_operand:DF 1 "nonimmediate_operand" "%0") 19433 (match_operand:DF 2 "nonimmediate_operand" "xm")))] 19434 "TARGET_SSE2 && TARGET_SSE_MATH" 19435 "maxsd\t{%2, %0|%0, %2}" 19436 [(set_attr "type" "sseadd") 19437 (set_attr "mode" "DF")]) 19438 19439;; These versions of the min/max patterns implement exactly the operations 19440;; min = (op1 < op2 ? op1 : op2) 19441;; max = (!(op1 < op2) ? op1 : op2) 19442;; Their operands are not commutative, and thus they may be used in the 19443;; presence of -0.0 and NaN. 19444 19445(define_insn "*ieee_sminsf3" 19446 [(set (match_operand:SF 0 "register_operand" "=x") 19447 (unspec:SF [(match_operand:SF 1 "register_operand" "0") 19448 (match_operand:SF 2 "nonimmediate_operand" "xm")] 19449 UNSPEC_IEEE_MIN))] 19450 "TARGET_SSE_MATH" 19451 "minss\t{%2, %0|%0, %2}" 19452 [(set_attr "type" "sseadd") 19453 (set_attr "mode" "SF")]) 19454 19455(define_insn "*ieee_smaxsf3" 19456 [(set (match_operand:SF 0 "register_operand" "=x") 19457 (unspec:SF [(match_operand:SF 1 "register_operand" "0") 19458 (match_operand:SF 2 "nonimmediate_operand" "xm")] 19459 UNSPEC_IEEE_MAX))] 19460 "TARGET_SSE_MATH" 19461 "maxss\t{%2, %0|%0, %2}" 19462 [(set_attr "type" "sseadd") 19463 (set_attr "mode" "SF")]) 19464 19465(define_insn "*ieee_smindf3" 19466 [(set (match_operand:DF 0 "register_operand" "=x") 19467 (unspec:DF [(match_operand:DF 1 "register_operand" "0") 19468 (match_operand:DF 2 "nonimmediate_operand" "xm")] 19469 UNSPEC_IEEE_MIN))] 19470 "TARGET_SSE2 && TARGET_SSE_MATH" 19471 "minsd\t{%2, %0|%0, %2}" 19472 [(set_attr "type" "sseadd") 19473 (set_attr "mode" "DF")]) 19474 19475(define_insn "*ieee_smaxdf3" 19476 [(set (match_operand:DF 0 "register_operand" "=x") 19477 (unspec:DF [(match_operand:DF 1 "register_operand" "0") 19478 (match_operand:DF 2 "nonimmediate_operand" "xm")] 19479 UNSPEC_IEEE_MAX))] 19480 "TARGET_SSE2 && TARGET_SSE_MATH" 19481 "maxsd\t{%2, %0|%0, %2}" 19482 [(set_attr "type" "sseadd") 19483 (set_attr "mode" "DF")]) 19484 19485;; Make two stack loads independent: 19486;; fld aa fld aa 19487;; fld %st(0) -> fld bb 19488;; fmul bb fmul %st(1), %st 19489;; 19490;; Actually we only match the last two instructions for simplicity. 19491(define_peephole2 19492 [(set (match_operand 0 "fp_register_operand" "") 19493 (match_operand 1 "fp_register_operand" "")) 19494 (set (match_dup 0) 19495 (match_operator 2 "binary_fp_operator" 19496 [(match_dup 0) 19497 (match_operand 3 "memory_operand" "")]))] 19498 "REGNO (operands[0]) != REGNO (operands[1])" 19499 [(set (match_dup 0) (match_dup 3)) 19500 (set (match_dup 0) (match_dup 4))] 19501 19502 ;; The % modifier is not operational anymore in peephole2's, so we have to 19503 ;; swap the operands manually in the case of addition and multiplication. 19504 "if (COMMUTATIVE_ARITH_P (operands[2])) 19505 operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]), 19506 operands[0], operands[1]); 19507 else 19508 operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]), 19509 operands[1], operands[0]);") 19510 19511;; Conditional addition patterns 19512(define_expand "addqicc" 19513 [(match_operand:QI 0 "register_operand" "") 19514 (match_operand 1 "comparison_operator" "") 19515 (match_operand:QI 2 "register_operand" "") 19516 (match_operand:QI 3 "const_int_operand" "")] 19517 "" 19518 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;") 19519 19520(define_expand "addhicc" 19521 [(match_operand:HI 0 "register_operand" "") 19522 (match_operand 1 "comparison_operator" "") 19523 (match_operand:HI 2 "register_operand" "") 19524 (match_operand:HI 3 "const_int_operand" "")] 19525 "" 19526 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;") 19527 19528(define_expand "addsicc" 19529 [(match_operand:SI 0 "register_operand" "") 19530 (match_operand 1 "comparison_operator" "") 19531 (match_operand:SI 2 "register_operand" "") 19532 (match_operand:SI 3 "const_int_operand" "")] 19533 "" 19534 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;") 19535 19536(define_expand "adddicc" 19537 [(match_operand:DI 0 "register_operand" "") 19538 (match_operand 1 "comparison_operator" "") 19539 (match_operand:DI 2 "register_operand" "") 19540 (match_operand:DI 3 "const_int_operand" "")] 19541 "TARGET_64BIT" 19542 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;") 19543 19544 19545;; Misc patterns (?) 19546 19547;; This pattern exists to put a dependency on all ebp-based memory accesses. 19548;; Otherwise there will be nothing to keep 19549;; 19550;; [(set (reg ebp) (reg esp))] 19551;; [(set (reg esp) (plus (reg esp) (const_int -160000))) 19552;; (clobber (eflags)] 19553;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))] 19554;; 19555;; in proper program order. 19556(define_insn "pro_epilogue_adjust_stack_1" 19557 [(set (match_operand:SI 0 "register_operand" "=r,r") 19558 (plus:SI (match_operand:SI 1 "register_operand" "0,r") 19559 (match_operand:SI 2 "immediate_operand" "i,i"))) 19560 (clobber (reg:CC FLAGS_REG)) 19561 (clobber (mem:BLK (scratch)))] 19562 "!TARGET_64BIT" 19563{ 19564 switch (get_attr_type (insn)) 19565 { 19566 case TYPE_IMOV: 19567 return "mov{l}\t{%1, %0|%0, %1}"; 19568 19569 case TYPE_ALU: 19570 if (GET_CODE (operands[2]) == CONST_INT 19571 && (INTVAL (operands[2]) == 128 19572 || (INTVAL (operands[2]) < 0 19573 && INTVAL (operands[2]) != -128))) 19574 { 19575 operands[2] = GEN_INT (-INTVAL (operands[2])); 19576 return "sub{l}\t{%2, %0|%0, %2}"; 19577 } 19578 return "add{l}\t{%2, %0|%0, %2}"; 19579 19580 case TYPE_LEA: 19581 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0)); 19582 return "lea{l}\t{%a2, %0|%0, %a2}"; 19583 19584 default: 19585 gcc_unreachable (); 19586 } 19587} 19588 [(set (attr "type") 19589 (cond [(eq_attr "alternative" "0") 19590 (const_string "alu") 19591 (match_operand:SI 2 "const0_operand" "") 19592 (const_string "imov") 19593 ] 19594 (const_string "lea"))) 19595 (set_attr "mode" "SI")]) 19596 19597(define_insn "pro_epilogue_adjust_stack_rex64" 19598 [(set (match_operand:DI 0 "register_operand" "=r,r") 19599 (plus:DI (match_operand:DI 1 "register_operand" "0,r") 19600 (match_operand:DI 2 "x86_64_immediate_operand" "e,e"))) 19601 (clobber (reg:CC FLAGS_REG)) 19602 (clobber (mem:BLK (scratch)))] 19603 "TARGET_64BIT" 19604{ 19605 switch (get_attr_type (insn)) 19606 { 19607 case TYPE_IMOV: 19608 return "mov{q}\t{%1, %0|%0, %1}"; 19609 19610 case TYPE_ALU: 19611 if (GET_CODE (operands[2]) == CONST_INT 19612 /* Avoid overflows. */ 19613 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))) 19614 && (INTVAL (operands[2]) == 128 19615 || (INTVAL (operands[2]) < 0 19616 && INTVAL (operands[2]) != -128))) 19617 { 19618 operands[2] = GEN_INT (-INTVAL (operands[2])); 19619 return "sub{q}\t{%2, %0|%0, %2}"; 19620 } 19621 return "add{q}\t{%2, %0|%0, %2}"; 19622 19623 case TYPE_LEA: 19624 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0)); 19625 return "lea{q}\t{%a2, %0|%0, %a2}"; 19626 19627 default: 19628 gcc_unreachable (); 19629 } 19630} 19631 [(set (attr "type") 19632 (cond [(eq_attr "alternative" "0") 19633 (const_string "alu") 19634 (match_operand:DI 2 "const0_operand" "") 19635 (const_string "imov") 19636 ] 19637 (const_string "lea"))) 19638 (set_attr "mode" "DI")]) 19639 19640(define_insn "pro_epilogue_adjust_stack_rex64_2" 19641 [(set (match_operand:DI 0 "register_operand" "=r,r") 19642 (plus:DI (match_operand:DI 1 "register_operand" "0,r") 19643 (match_operand:DI 3 "immediate_operand" "i,i"))) 19644 (use (match_operand:DI 2 "register_operand" "r,r")) 19645 (clobber (reg:CC FLAGS_REG)) 19646 (clobber (mem:BLK (scratch)))] 19647 "TARGET_64BIT" 19648{ 19649 switch (get_attr_type (insn)) 19650 { 19651 case TYPE_ALU: 19652 return "add{q}\t{%2, %0|%0, %2}"; 19653 19654 case TYPE_LEA: 19655 operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]); 19656 return "lea{q}\t{%a2, %0|%0, %a2}"; 19657 19658 default: 19659 gcc_unreachable (); 19660 } 19661} 19662 [(set_attr "type" "alu,lea") 19663 (set_attr "mode" "DI")]) 19664 19665(define_expand "allocate_stack_worker" 19666 [(match_operand:SI 0 "register_operand" "")] 19667 "TARGET_STACK_PROBE" 19668{ 19669 if (reload_completed) 19670 { 19671 if (TARGET_64BIT) 19672 emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0])); 19673 else 19674 emit_insn (gen_allocate_stack_worker_postreload (operands[0])); 19675 } 19676 else 19677 { 19678 if (TARGET_64BIT) 19679 emit_insn (gen_allocate_stack_worker_rex64 (operands[0])); 19680 else 19681 emit_insn (gen_allocate_stack_worker_1 (operands[0])); 19682 } 19683 DONE; 19684}) 19685 19686(define_insn "allocate_stack_worker_1" 19687 [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")] 19688 UNSPECV_STACK_PROBE) 19689 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0))) 19690 (clobber (match_scratch:SI 1 "=0")) 19691 (clobber (reg:CC FLAGS_REG))] 19692 "!TARGET_64BIT && TARGET_STACK_PROBE" 19693 "call\t__alloca" 19694 [(set_attr "type" "multi") 19695 (set_attr "length" "5")]) 19696 19697(define_expand "allocate_stack_worker_postreload" 19698 [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")] 19699 UNSPECV_STACK_PROBE) 19700 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0))) 19701 (clobber (match_dup 0)) 19702 (clobber (reg:CC FLAGS_REG))])] 19703 "" 19704 "") 19705 19706(define_insn "allocate_stack_worker_rex64" 19707 [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")] 19708 UNSPECV_STACK_PROBE) 19709 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0))) 19710 (clobber (match_scratch:DI 1 "=0")) 19711 (clobber (reg:CC FLAGS_REG))] 19712 "TARGET_64BIT && TARGET_STACK_PROBE" 19713 "call\t__alloca" 19714 [(set_attr "type" "multi") 19715 (set_attr "length" "5")]) 19716 19717(define_expand "allocate_stack_worker_rex64_postreload" 19718 [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")] 19719 UNSPECV_STACK_PROBE) 19720 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0))) 19721 (clobber (match_dup 0)) 19722 (clobber (reg:CC FLAGS_REG))])] 19723 "" 19724 "") 19725 19726(define_expand "allocate_stack" 19727 [(parallel [(set (match_operand:SI 0 "register_operand" "=r") 19728 (minus:SI (reg:SI SP_REG) 19729 (match_operand:SI 1 "general_operand" ""))) 19730 (clobber (reg:CC FLAGS_REG))]) 19731 (parallel [(set (reg:SI SP_REG) 19732 (minus:SI (reg:SI SP_REG) (match_dup 1))) 19733 (clobber (reg:CC FLAGS_REG))])] 19734 "TARGET_STACK_PROBE" 19735{ 19736#ifdef CHECK_STACK_LIMIT 19737 if (GET_CODE (operands[1]) == CONST_INT 19738 && INTVAL (operands[1]) < CHECK_STACK_LIMIT) 19739 emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx, 19740 operands[1])); 19741 else 19742#endif 19743 emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode, 19744 operands[1]))); 19745 19746 emit_move_insn (operands[0], virtual_stack_dynamic_rtx); 19747 DONE; 19748}) 19749 19750(define_expand "builtin_setjmp_receiver" 19751 [(label_ref (match_operand 0 "" ""))] 19752 "!TARGET_64BIT && flag_pic" 19753{ 19754 if (TARGET_MACHO) 19755 { 19756 rtx xops[3]; 19757 rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM); 19758 rtx label_rtx = gen_label_rtx (); 19759 emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx)); 19760 xops[0] = xops[1] = picreg; 19761 xops[2] = gen_rtx_CONST (SImode, 19762 gen_rtx_MINUS (SImode, 19763 gen_rtx_LABEL_REF (SImode, label_rtx), 19764 gen_rtx_SYMBOL_REF (SImode, GOT_SYMBOL_NAME))); 19765 ix86_expand_binary_operator (MINUS, SImode, xops); 19766 } 19767 else 19768 emit_insn (gen_set_got (pic_offset_table_rtx)); 19769 DONE; 19770}) 19771 19772;; Avoid redundant prefixes by splitting HImode arithmetic to SImode. 19773 19774(define_split 19775 [(set (match_operand 0 "register_operand" "") 19776 (match_operator 3 "promotable_binary_operator" 19777 [(match_operand 1 "register_operand" "") 19778 (match_operand 2 "aligned_operand" "")])) 19779 (clobber (reg:CC FLAGS_REG))] 19780 "! TARGET_PARTIAL_REG_STALL && reload_completed 19781 && ((GET_MODE (operands[0]) == HImode 19782 && ((!optimize_size && !TARGET_FAST_PREFIX) 19783 /* ??? next two lines just !satisfies_constraint_K (...) */ 19784 || GET_CODE (operands[2]) != CONST_INT 19785 || satisfies_constraint_K (operands[2]))) 19786 || (GET_MODE (operands[0]) == QImode 19787 && (TARGET_PROMOTE_QImode || optimize_size)))" 19788 [(parallel [(set (match_dup 0) 19789 (match_op_dup 3 [(match_dup 1) (match_dup 2)])) 19790 (clobber (reg:CC FLAGS_REG))])] 19791 "operands[0] = gen_lowpart (SImode, operands[0]); 19792 operands[1] = gen_lowpart (SImode, operands[1]); 19793 if (GET_CODE (operands[3]) != ASHIFT) 19794 operands[2] = gen_lowpart (SImode, operands[2]); 19795 PUT_MODE (operands[3], SImode);") 19796 19797; Promote the QImode tests, as i386 has encoding of the AND 19798; instruction with 32-bit sign-extended immediate and thus the 19799; instruction size is unchanged, except in the %eax case for 19800; which it is increased by one byte, hence the ! optimize_size. 19801(define_split 19802 [(set (match_operand 0 "flags_reg_operand" "") 19803 (match_operator 2 "compare_operator" 19804 [(and (match_operand 3 "aligned_operand" "") 19805 (match_operand 4 "const_int_operand" "")) 19806 (const_int 0)])) 19807 (set (match_operand 1 "register_operand" "") 19808 (and (match_dup 3) (match_dup 4)))] 19809 "! TARGET_PARTIAL_REG_STALL && reload_completed 19810 /* Ensure that the operand will remain sign-extended immediate. */ 19811 && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode) 19812 && ! optimize_size 19813 && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX) 19814 || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))" 19815 [(parallel [(set (match_dup 0) 19816 (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4)) 19817 (const_int 0)])) 19818 (set (match_dup 1) 19819 (and:SI (match_dup 3) (match_dup 4)))])] 19820{ 19821 operands[4] 19822 = gen_int_mode (INTVAL (operands[4]) 19823 & GET_MODE_MASK (GET_MODE (operands[1])), SImode); 19824 operands[1] = gen_lowpart (SImode, operands[1]); 19825 operands[3] = gen_lowpart (SImode, operands[3]); 19826}) 19827 19828; Don't promote the QImode tests, as i386 doesn't have encoding of 19829; the TEST instruction with 32-bit sign-extended immediate and thus 19830; the instruction size would at least double, which is not what we 19831; want even with ! optimize_size. 19832(define_split 19833 [(set (match_operand 0 "flags_reg_operand" "") 19834 (match_operator 1 "compare_operator" 19835 [(and (match_operand:HI 2 "aligned_operand" "") 19836 (match_operand:HI 3 "const_int_operand" "")) 19837 (const_int 0)]))] 19838 "! TARGET_PARTIAL_REG_STALL && reload_completed 19839 /* Ensure that the operand will remain sign-extended immediate. */ 19840 && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode) 19841 && ! TARGET_FAST_PREFIX 19842 && ! optimize_size" 19843 [(set (match_dup 0) 19844 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3)) 19845 (const_int 0)]))] 19846{ 19847 operands[3] 19848 = gen_int_mode (INTVAL (operands[3]) 19849 & GET_MODE_MASK (GET_MODE (operands[2])), SImode); 19850 operands[2] = gen_lowpart (SImode, operands[2]); 19851}) 19852 19853(define_split 19854 [(set (match_operand 0 "register_operand" "") 19855 (neg (match_operand 1 "register_operand" ""))) 19856 (clobber (reg:CC FLAGS_REG))] 19857 "! TARGET_PARTIAL_REG_STALL && reload_completed 19858 && (GET_MODE (operands[0]) == HImode 19859 || (GET_MODE (operands[0]) == QImode 19860 && (TARGET_PROMOTE_QImode || optimize_size)))" 19861 [(parallel [(set (match_dup 0) 19862 (neg:SI (match_dup 1))) 19863 (clobber (reg:CC FLAGS_REG))])] 19864 "operands[0] = gen_lowpart (SImode, operands[0]); 19865 operands[1] = gen_lowpart (SImode, operands[1]);") 19866 19867(define_split 19868 [(set (match_operand 0 "register_operand" "") 19869 (not (match_operand 1 "register_operand" "")))] 19870 "! TARGET_PARTIAL_REG_STALL && reload_completed 19871 && (GET_MODE (operands[0]) == HImode 19872 || (GET_MODE (operands[0]) == QImode 19873 && (TARGET_PROMOTE_QImode || optimize_size)))" 19874 [(set (match_dup 0) 19875 (not:SI (match_dup 1)))] 19876 "operands[0] = gen_lowpart (SImode, operands[0]); 19877 operands[1] = gen_lowpart (SImode, operands[1]);") 19878 19879(define_split 19880 [(set (match_operand 0 "register_operand" "") 19881 (if_then_else (match_operator 1 "comparison_operator" 19882 [(reg FLAGS_REG) (const_int 0)]) 19883 (match_operand 2 "register_operand" "") 19884 (match_operand 3 "register_operand" "")))] 19885 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE 19886 && (GET_MODE (operands[0]) == HImode 19887 || (GET_MODE (operands[0]) == QImode 19888 && (TARGET_PROMOTE_QImode || optimize_size)))" 19889 [(set (match_dup 0) 19890 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))] 19891 "operands[0] = gen_lowpart (SImode, operands[0]); 19892 operands[2] = gen_lowpart (SImode, operands[2]); 19893 operands[3] = gen_lowpart (SImode, operands[3]);") 19894 19895 19896;; RTL Peephole optimizations, run before sched2. These primarily look to 19897;; transform a complex memory operation into two memory to register operations. 19898 19899;; Don't push memory operands 19900(define_peephole2 19901 [(set (match_operand:SI 0 "push_operand" "") 19902 (match_operand:SI 1 "memory_operand" "")) 19903 (match_scratch:SI 2 "r")] 19904 "!optimize_size && !TARGET_PUSH_MEMORY 19905 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))" 19906 [(set (match_dup 2) (match_dup 1)) 19907 (set (match_dup 0) (match_dup 2))] 19908 "") 19909 19910(define_peephole2 19911 [(set (match_operand:DI 0 "push_operand" "") 19912 (match_operand:DI 1 "memory_operand" "")) 19913 (match_scratch:DI 2 "r")] 19914 "!optimize_size && !TARGET_PUSH_MEMORY 19915 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))" 19916 [(set (match_dup 2) (match_dup 1)) 19917 (set (match_dup 0) (match_dup 2))] 19918 "") 19919 19920;; We need to handle SFmode only, because DFmode and XFmode is split to 19921;; SImode pushes. 19922(define_peephole2 19923 [(set (match_operand:SF 0 "push_operand" "") 19924 (match_operand:SF 1 "memory_operand" "")) 19925 (match_scratch:SF 2 "r")] 19926 "!optimize_size && !TARGET_PUSH_MEMORY 19927 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))" 19928 [(set (match_dup 2) (match_dup 1)) 19929 (set (match_dup 0) (match_dup 2))] 19930 "") 19931 19932(define_peephole2 19933 [(set (match_operand:HI 0 "push_operand" "") 19934 (match_operand:HI 1 "memory_operand" "")) 19935 (match_scratch:HI 2 "r")] 19936 "!optimize_size && !TARGET_PUSH_MEMORY 19937 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))" 19938 [(set (match_dup 2) (match_dup 1)) 19939 (set (match_dup 0) (match_dup 2))] 19940 "") 19941 19942(define_peephole2 19943 [(set (match_operand:QI 0 "push_operand" "") 19944 (match_operand:QI 1 "memory_operand" "")) 19945 (match_scratch:QI 2 "q")] 19946 "!optimize_size && !TARGET_PUSH_MEMORY 19947 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))" 19948 [(set (match_dup 2) (match_dup 1)) 19949 (set (match_dup 0) (match_dup 2))] 19950 "") 19951 19952;; Don't move an immediate directly to memory when the instruction 19953;; gets too big. 19954(define_peephole2 19955 [(match_scratch:SI 1 "r") 19956 (set (match_operand:SI 0 "memory_operand" "") 19957 (const_int 0))] 19958 "! optimize_size 19959 && ! TARGET_USE_MOV0 19960 && TARGET_SPLIT_LONG_MOVES 19961 && get_attr_length (insn) >= ix86_cost->large_insn 19962 && peep2_regno_dead_p (0, FLAGS_REG)" 19963 [(parallel [(set (match_dup 1) (const_int 0)) 19964 (clobber (reg:CC FLAGS_REG))]) 19965 (set (match_dup 0) (match_dup 1))] 19966 "") 19967 19968(define_peephole2 19969 [(match_scratch:HI 1 "r") 19970 (set (match_operand:HI 0 "memory_operand" "") 19971 (const_int 0))] 19972 "! optimize_size 19973 && ! TARGET_USE_MOV0 19974 && TARGET_SPLIT_LONG_MOVES 19975 && get_attr_length (insn) >= ix86_cost->large_insn 19976 && peep2_regno_dead_p (0, FLAGS_REG)" 19977 [(parallel [(set (match_dup 2) (const_int 0)) 19978 (clobber (reg:CC FLAGS_REG))]) 19979 (set (match_dup 0) (match_dup 1))] 19980 "operands[2] = gen_lowpart (SImode, operands[1]);") 19981 19982(define_peephole2 19983 [(match_scratch:QI 1 "q") 19984 (set (match_operand:QI 0 "memory_operand" "") 19985 (const_int 0))] 19986 "! optimize_size 19987 && ! TARGET_USE_MOV0 19988 && TARGET_SPLIT_LONG_MOVES 19989 && get_attr_length (insn) >= ix86_cost->large_insn 19990 && peep2_regno_dead_p (0, FLAGS_REG)" 19991 [(parallel [(set (match_dup 2) (const_int 0)) 19992 (clobber (reg:CC FLAGS_REG))]) 19993 (set (match_dup 0) (match_dup 1))] 19994 "operands[2] = gen_lowpart (SImode, operands[1]);") 19995 19996(define_peephole2 19997 [(match_scratch:SI 2 "r") 19998 (set (match_operand:SI 0 "memory_operand" "") 19999 (match_operand:SI 1 "immediate_operand" ""))] 20000 "! optimize_size 20001 && get_attr_length (insn) >= ix86_cost->large_insn 20002 && TARGET_SPLIT_LONG_MOVES" 20003 [(set (match_dup 2) (match_dup 1)) 20004 (set (match_dup 0) (match_dup 2))] 20005 "") 20006 20007(define_peephole2 20008 [(match_scratch:HI 2 "r") 20009 (set (match_operand:HI 0 "memory_operand" "") 20010 (match_operand:HI 1 "immediate_operand" ""))] 20011 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn 20012 && TARGET_SPLIT_LONG_MOVES" 20013 [(set (match_dup 2) (match_dup 1)) 20014 (set (match_dup 0) (match_dup 2))] 20015 "") 20016 20017(define_peephole2 20018 [(match_scratch:QI 2 "q") 20019 (set (match_operand:QI 0 "memory_operand" "") 20020 (match_operand:QI 1 "immediate_operand" ""))] 20021 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn 20022 && TARGET_SPLIT_LONG_MOVES" 20023 [(set (match_dup 2) (match_dup 1)) 20024 (set (match_dup 0) (match_dup 2))] 20025 "") 20026 20027;; Don't compare memory with zero, load and use a test instead. 20028(define_peephole2 20029 [(set (match_operand 0 "flags_reg_operand" "") 20030 (match_operator 1 "compare_operator" 20031 [(match_operand:SI 2 "memory_operand" "") 20032 (const_int 0)])) 20033 (match_scratch:SI 3 "r")] 20034 "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size" 20035 [(set (match_dup 3) (match_dup 2)) 20036 (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))] 20037 "") 20038 20039;; NOT is not pairable on Pentium, while XOR is, but one byte longer. 20040;; Don't split NOTs with a displacement operand, because resulting XOR 20041;; will not be pairable anyway. 20042;; 20043;; On AMD K6, NOT is vector decoded with memory operand that cannot be 20044;; represented using a modRM byte. The XOR replacement is long decoded, 20045;; so this split helps here as well. 20046;; 20047;; Note: Can't do this as a regular split because we can't get proper 20048;; lifetime information then. 20049 20050(define_peephole2 20051 [(set (match_operand:SI 0 "nonimmediate_operand" "") 20052 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))] 20053 "!optimize_size 20054 && peep2_regno_dead_p (0, FLAGS_REG) 20055 && ((TARGET_PENTIUM 20056 && (GET_CODE (operands[0]) != MEM 20057 || !memory_displacement_operand (operands[0], SImode))) 20058 || (TARGET_K6 && long_memory_operand (operands[0], SImode)))" 20059 [(parallel [(set (match_dup 0) 20060 (xor:SI (match_dup 1) (const_int -1))) 20061 (clobber (reg:CC FLAGS_REG))])] 20062 "") 20063 20064(define_peephole2 20065 [(set (match_operand:HI 0 "nonimmediate_operand" "") 20066 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))] 20067 "!optimize_size 20068 && peep2_regno_dead_p (0, FLAGS_REG) 20069 && ((TARGET_PENTIUM 20070 && (GET_CODE (operands[0]) != MEM 20071 || !memory_displacement_operand (operands[0], HImode))) 20072 || (TARGET_K6 && long_memory_operand (operands[0], HImode)))" 20073 [(parallel [(set (match_dup 0) 20074 (xor:HI (match_dup 1) (const_int -1))) 20075 (clobber (reg:CC FLAGS_REG))])] 20076 "") 20077 20078(define_peephole2 20079 [(set (match_operand:QI 0 "nonimmediate_operand" "") 20080 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))] 20081 "!optimize_size 20082 && peep2_regno_dead_p (0, FLAGS_REG) 20083 && ((TARGET_PENTIUM 20084 && (GET_CODE (operands[0]) != MEM 20085 || !memory_displacement_operand (operands[0], QImode))) 20086 || (TARGET_K6 && long_memory_operand (operands[0], QImode)))" 20087 [(parallel [(set (match_dup 0) 20088 (xor:QI (match_dup 1) (const_int -1))) 20089 (clobber (reg:CC FLAGS_REG))])] 20090 "") 20091 20092;; Non pairable "test imm, reg" instructions can be translated to 20093;; "and imm, reg" if reg dies. The "and" form is also shorter (one 20094;; byte opcode instead of two, have a short form for byte operands), 20095;; so do it for other CPUs as well. Given that the value was dead, 20096;; this should not create any new dependencies. Pass on the sub-word 20097;; versions if we're concerned about partial register stalls. 20098 20099(define_peephole2 20100 [(set (match_operand 0 "flags_reg_operand" "") 20101 (match_operator 1 "compare_operator" 20102 [(and:SI (match_operand:SI 2 "register_operand" "") 20103 (match_operand:SI 3 "immediate_operand" "")) 20104 (const_int 0)]))] 20105 "ix86_match_ccmode (insn, CCNOmode) 20106 && (true_regnum (operands[2]) != 0 20107 || satisfies_constraint_K (operands[3])) 20108 && peep2_reg_dead_p (1, operands[2])" 20109 [(parallel 20110 [(set (match_dup 0) 20111 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3)) 20112 (const_int 0)])) 20113 (set (match_dup 2) 20114 (and:SI (match_dup 2) (match_dup 3)))])] 20115 "") 20116 20117;; We don't need to handle HImode case, because it will be promoted to SImode 20118;; on ! TARGET_PARTIAL_REG_STALL 20119 20120(define_peephole2 20121 [(set (match_operand 0 "flags_reg_operand" "") 20122 (match_operator 1 "compare_operator" 20123 [(and:QI (match_operand:QI 2 "register_operand" "") 20124 (match_operand:QI 3 "immediate_operand" "")) 20125 (const_int 0)]))] 20126 "! TARGET_PARTIAL_REG_STALL 20127 && ix86_match_ccmode (insn, CCNOmode) 20128 && true_regnum (operands[2]) != 0 20129 && peep2_reg_dead_p (1, operands[2])" 20130 [(parallel 20131 [(set (match_dup 0) 20132 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3)) 20133 (const_int 0)])) 20134 (set (match_dup 2) 20135 (and:QI (match_dup 2) (match_dup 3)))])] 20136 "") 20137 20138(define_peephole2 20139 [(set (match_operand 0 "flags_reg_operand" "") 20140 (match_operator 1 "compare_operator" 20141 [(and:SI 20142 (zero_extract:SI 20143 (match_operand 2 "ext_register_operand" "") 20144 (const_int 8) 20145 (const_int 8)) 20146 (match_operand 3 "const_int_operand" "")) 20147 (const_int 0)]))] 20148 "! TARGET_PARTIAL_REG_STALL 20149 && ix86_match_ccmode (insn, CCNOmode) 20150 && true_regnum (operands[2]) != 0 20151 && peep2_reg_dead_p (1, operands[2])" 20152 [(parallel [(set (match_dup 0) 20153 (match_op_dup 1 20154 [(and:SI 20155 (zero_extract:SI 20156 (match_dup 2) 20157 (const_int 8) 20158 (const_int 8)) 20159 (match_dup 3)) 20160 (const_int 0)])) 20161 (set (zero_extract:SI (match_dup 2) 20162 (const_int 8) 20163 (const_int 8)) 20164 (and:SI 20165 (zero_extract:SI 20166 (match_dup 2) 20167 (const_int 8) 20168 (const_int 8)) 20169 (match_dup 3)))])] 20170 "") 20171 20172;; Don't do logical operations with memory inputs. 20173(define_peephole2 20174 [(match_scratch:SI 2 "r") 20175 (parallel [(set (match_operand:SI 0 "register_operand" "") 20176 (match_operator:SI 3 "arith_or_logical_operator" 20177 [(match_dup 0) 20178 (match_operand:SI 1 "memory_operand" "")])) 20179 (clobber (reg:CC FLAGS_REG))])] 20180 "! optimize_size && ! TARGET_READ_MODIFY" 20181 [(set (match_dup 2) (match_dup 1)) 20182 (parallel [(set (match_dup 0) 20183 (match_op_dup 3 [(match_dup 0) (match_dup 2)])) 20184 (clobber (reg:CC FLAGS_REG))])] 20185 "") 20186 20187(define_peephole2 20188 [(match_scratch:SI 2 "r") 20189 (parallel [(set (match_operand:SI 0 "register_operand" "") 20190 (match_operator:SI 3 "arith_or_logical_operator" 20191 [(match_operand:SI 1 "memory_operand" "") 20192 (match_dup 0)])) 20193 (clobber (reg:CC FLAGS_REG))])] 20194 "! optimize_size && ! TARGET_READ_MODIFY" 20195 [(set (match_dup 2) (match_dup 1)) 20196 (parallel [(set (match_dup 0) 20197 (match_op_dup 3 [(match_dup 2) (match_dup 0)])) 20198 (clobber (reg:CC FLAGS_REG))])] 20199 "") 20200 20201; Don't do logical operations with memory outputs 20202; 20203; These two don't make sense for PPro/PII -- we're expanding a 4-uop 20204; instruction into two 1-uop insns plus a 2-uop insn. That last has 20205; the same decoder scheduling characteristics as the original. 20206 20207(define_peephole2 20208 [(match_scratch:SI 2 "r") 20209 (parallel [(set (match_operand:SI 0 "memory_operand" "") 20210 (match_operator:SI 3 "arith_or_logical_operator" 20211 [(match_dup 0) 20212 (match_operand:SI 1 "nonmemory_operand" "")])) 20213 (clobber (reg:CC FLAGS_REG))])] 20214 "! optimize_size && ! TARGET_READ_MODIFY_WRITE" 20215 [(set (match_dup 2) (match_dup 0)) 20216 (parallel [(set (match_dup 2) 20217 (match_op_dup 3 [(match_dup 2) (match_dup 1)])) 20218 (clobber (reg:CC FLAGS_REG))]) 20219 (set (match_dup 0) (match_dup 2))] 20220 "") 20221 20222(define_peephole2 20223 [(match_scratch:SI 2 "r") 20224 (parallel [(set (match_operand:SI 0 "memory_operand" "") 20225 (match_operator:SI 3 "arith_or_logical_operator" 20226 [(match_operand:SI 1 "nonmemory_operand" "") 20227 (match_dup 0)])) 20228 (clobber (reg:CC FLAGS_REG))])] 20229 "! optimize_size && ! TARGET_READ_MODIFY_WRITE" 20230 [(set (match_dup 2) (match_dup 0)) 20231 (parallel [(set (match_dup 2) 20232 (match_op_dup 3 [(match_dup 1) (match_dup 2)])) 20233 (clobber (reg:CC FLAGS_REG))]) 20234 (set (match_dup 0) (match_dup 2))] 20235 "") 20236 20237;; Attempt to always use XOR for zeroing registers. 20238(define_peephole2 20239 [(set (match_operand 0 "register_operand" "") 20240 (match_operand 1 "const0_operand" ""))] 20241 "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD 20242 && (! TARGET_USE_MOV0 || optimize_size) 20243 && GENERAL_REG_P (operands[0]) 20244 && peep2_regno_dead_p (0, FLAGS_REG)" 20245 [(parallel [(set (match_dup 0) (const_int 0)) 20246 (clobber (reg:CC FLAGS_REG))])] 20247{ 20248 operands[0] = gen_lowpart (word_mode, operands[0]); 20249}) 20250 20251(define_peephole2 20252 [(set (strict_low_part (match_operand 0 "register_operand" "")) 20253 (const_int 0))] 20254 "(GET_MODE (operands[0]) == QImode 20255 || GET_MODE (operands[0]) == HImode) 20256 && (! TARGET_USE_MOV0 || optimize_size) 20257 && peep2_regno_dead_p (0, FLAGS_REG)" 20258 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0)) 20259 (clobber (reg:CC FLAGS_REG))])]) 20260 20261;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg. 20262(define_peephole2 20263 [(set (match_operand 0 "register_operand" "") 20264 (const_int -1))] 20265 "(GET_MODE (operands[0]) == HImode 20266 || GET_MODE (operands[0]) == SImode 20267 || (GET_MODE (operands[0]) == DImode && TARGET_64BIT)) 20268 && (optimize_size || TARGET_PENTIUM) 20269 && peep2_regno_dead_p (0, FLAGS_REG)" 20270 [(parallel [(set (match_dup 0) (const_int -1)) 20271 (clobber (reg:CC FLAGS_REG))])] 20272 "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode, 20273 operands[0]);") 20274 20275;; Attempt to convert simple leas to adds. These can be created by 20276;; move expanders. 20277(define_peephole2 20278 [(set (match_operand:SI 0 "register_operand" "") 20279 (plus:SI (match_dup 0) 20280 (match_operand:SI 1 "nonmemory_operand" "")))] 20281 "peep2_regno_dead_p (0, FLAGS_REG)" 20282 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1))) 20283 (clobber (reg:CC FLAGS_REG))])] 20284 "") 20285 20286(define_peephole2 20287 [(set (match_operand:SI 0 "register_operand" "") 20288 (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "") 20289 (match_operand:DI 2 "nonmemory_operand" "")) 0))] 20290 "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])" 20291 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2))) 20292 (clobber (reg:CC FLAGS_REG))])] 20293 "operands[2] = gen_lowpart (SImode, operands[2]);") 20294 20295(define_peephole2 20296 [(set (match_operand:DI 0 "register_operand" "") 20297 (plus:DI (match_dup 0) 20298 (match_operand:DI 1 "x86_64_general_operand" "")))] 20299 "peep2_regno_dead_p (0, FLAGS_REG)" 20300 [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1))) 20301 (clobber (reg:CC FLAGS_REG))])] 20302 "") 20303 20304(define_peephole2 20305 [(set (match_operand:SI 0 "register_operand" "") 20306 (mult:SI (match_dup 0) 20307 (match_operand:SI 1 "const_int_operand" "")))] 20308 "exact_log2 (INTVAL (operands[1])) >= 0 20309 && peep2_regno_dead_p (0, FLAGS_REG)" 20310 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2))) 20311 (clobber (reg:CC FLAGS_REG))])] 20312 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));") 20313 20314(define_peephole2 20315 [(set (match_operand:DI 0 "register_operand" "") 20316 (mult:DI (match_dup 0) 20317 (match_operand:DI 1 "const_int_operand" "")))] 20318 "exact_log2 (INTVAL (operands[1])) >= 0 20319 && peep2_regno_dead_p (0, FLAGS_REG)" 20320 [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2))) 20321 (clobber (reg:CC FLAGS_REG))])] 20322 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));") 20323 20324(define_peephole2 20325 [(set (match_operand:SI 0 "register_operand" "") 20326 (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "") 20327 (match_operand:DI 2 "const_int_operand" "")) 0))] 20328 "exact_log2 (INTVAL (operands[2])) >= 0 20329 && REGNO (operands[0]) == REGNO (operands[1]) 20330 && peep2_regno_dead_p (0, FLAGS_REG)" 20331 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2))) 20332 (clobber (reg:CC FLAGS_REG))])] 20333 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));") 20334 20335;; The ESP adjustments can be done by the push and pop instructions. Resulting 20336;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On 20337;; many CPUs it is also faster, since special hardware to avoid esp 20338;; dependencies is present. 20339 20340;; While some of these conversions may be done using splitters, we use peepholes 20341;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL. 20342 20343;; Convert prologue esp subtractions to push. 20344;; We need register to push. In order to keep verify_flow_info happy we have 20345;; two choices 20346;; - use scratch and clobber it in order to avoid dependencies 20347;; - use already live register 20348;; We can't use the second way right now, since there is no reliable way how to 20349;; verify that given register is live. First choice will also most likely in 20350;; fewer dependencies. On the place of esp adjustments it is very likely that 20351;; call clobbered registers are dead. We may want to use base pointer as an 20352;; alternative when no register is available later. 20353 20354(define_peephole2 20355 [(match_scratch:SI 0 "r") 20356 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4))) 20357 (clobber (reg:CC FLAGS_REG)) 20358 (clobber (mem:BLK (scratch)))])] 20359 "optimize_size || !TARGET_SUB_ESP_4" 20360 [(clobber (match_dup 0)) 20361 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0)) 20362 (clobber (mem:BLK (scratch)))])]) 20363 20364(define_peephole2 20365 [(match_scratch:SI 0 "r") 20366 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8))) 20367 (clobber (reg:CC FLAGS_REG)) 20368 (clobber (mem:BLK (scratch)))])] 20369 "optimize_size || !TARGET_SUB_ESP_8" 20370 [(clobber (match_dup 0)) 20371 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0)) 20372 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0)) 20373 (clobber (mem:BLK (scratch)))])]) 20374 20375;; Convert esp subtractions to push. 20376(define_peephole2 20377 [(match_scratch:SI 0 "r") 20378 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4))) 20379 (clobber (reg:CC FLAGS_REG))])] 20380 "optimize_size || !TARGET_SUB_ESP_4" 20381 [(clobber (match_dup 0)) 20382 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))]) 20383 20384(define_peephole2 20385 [(match_scratch:SI 0 "r") 20386 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8))) 20387 (clobber (reg:CC FLAGS_REG))])] 20388 "optimize_size || !TARGET_SUB_ESP_8" 20389 [(clobber (match_dup 0)) 20390 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0)) 20391 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))]) 20392 20393;; Convert epilogue deallocator to pop. 20394(define_peephole2 20395 [(match_scratch:SI 0 "r") 20396 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4))) 20397 (clobber (reg:CC FLAGS_REG)) 20398 (clobber (mem:BLK (scratch)))])] 20399 "optimize_size || !TARGET_ADD_ESP_4" 20400 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20401 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4))) 20402 (clobber (mem:BLK (scratch)))])] 20403 "") 20404 20405;; Two pops case is tricky, since pop causes dependency on destination register. 20406;; We use two registers if available. 20407(define_peephole2 20408 [(match_scratch:SI 0 "r") 20409 (match_scratch:SI 1 "r") 20410 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8))) 20411 (clobber (reg:CC FLAGS_REG)) 20412 (clobber (mem:BLK (scratch)))])] 20413 "optimize_size || !TARGET_ADD_ESP_8" 20414 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20415 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4))) 20416 (clobber (mem:BLK (scratch)))]) 20417 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG))) 20418 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])] 20419 "") 20420 20421(define_peephole2 20422 [(match_scratch:SI 0 "r") 20423 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8))) 20424 (clobber (reg:CC FLAGS_REG)) 20425 (clobber (mem:BLK (scratch)))])] 20426 "optimize_size" 20427 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20428 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4))) 20429 (clobber (mem:BLK (scratch)))]) 20430 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20431 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])] 20432 "") 20433 20434;; Convert esp additions to pop. 20435(define_peephole2 20436 [(match_scratch:SI 0 "r") 20437 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4))) 20438 (clobber (reg:CC FLAGS_REG))])] 20439 "" 20440 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20441 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])] 20442 "") 20443 20444;; Two pops case is tricky, since pop causes dependency on destination register. 20445;; We use two registers if available. 20446(define_peephole2 20447 [(match_scratch:SI 0 "r") 20448 (match_scratch:SI 1 "r") 20449 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8))) 20450 (clobber (reg:CC FLAGS_REG))])] 20451 "" 20452 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20453 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))]) 20454 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG))) 20455 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])] 20456 "") 20457 20458(define_peephole2 20459 [(match_scratch:SI 0 "r") 20460 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8))) 20461 (clobber (reg:CC FLAGS_REG))])] 20462 "optimize_size" 20463 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20464 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))]) 20465 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG))) 20466 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])] 20467 "") 20468 20469;; Convert compares with 1 to shorter inc/dec operations when CF is not 20470;; required and register dies. Similarly for 128 to plus -128. 20471(define_peephole2 20472 [(set (match_operand 0 "flags_reg_operand" "") 20473 (match_operator 1 "compare_operator" 20474 [(match_operand 2 "register_operand" "") 20475 (match_operand 3 "const_int_operand" "")]))] 20476 "(INTVAL (operands[3]) == -1 20477 || INTVAL (operands[3]) == 1 20478 || INTVAL (operands[3]) == 128) 20479 && ix86_match_ccmode (insn, CCGCmode) 20480 && peep2_reg_dead_p (1, operands[2])" 20481 [(parallel [(set (match_dup 0) 20482 (match_op_dup 1 [(match_dup 2) (match_dup 3)])) 20483 (clobber (match_dup 2))])] 20484 "") 20485 20486(define_peephole2 20487 [(match_scratch:DI 0 "r") 20488 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8))) 20489 (clobber (reg:CC FLAGS_REG)) 20490 (clobber (mem:BLK (scratch)))])] 20491 "optimize_size || !TARGET_SUB_ESP_4" 20492 [(clobber (match_dup 0)) 20493 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0)) 20494 (clobber (mem:BLK (scratch)))])]) 20495 20496(define_peephole2 20497 [(match_scratch:DI 0 "r") 20498 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16))) 20499 (clobber (reg:CC FLAGS_REG)) 20500 (clobber (mem:BLK (scratch)))])] 20501 "optimize_size || !TARGET_SUB_ESP_8" 20502 [(clobber (match_dup 0)) 20503 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0)) 20504 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0)) 20505 (clobber (mem:BLK (scratch)))])]) 20506 20507;; Convert esp subtractions to push. 20508(define_peephole2 20509 [(match_scratch:DI 0 "r") 20510 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8))) 20511 (clobber (reg:CC FLAGS_REG))])] 20512 "optimize_size || !TARGET_SUB_ESP_4" 20513 [(clobber (match_dup 0)) 20514 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))]) 20515 20516(define_peephole2 20517 [(match_scratch:DI 0 "r") 20518 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16))) 20519 (clobber (reg:CC FLAGS_REG))])] 20520 "optimize_size || !TARGET_SUB_ESP_8" 20521 [(clobber (match_dup 0)) 20522 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0)) 20523 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))]) 20524 20525;; Convert epilogue deallocator to pop. 20526(define_peephole2 20527 [(match_scratch:DI 0 "r") 20528 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8))) 20529 (clobber (reg:CC FLAGS_REG)) 20530 (clobber (mem:BLK (scratch)))])] 20531 "optimize_size || !TARGET_ADD_ESP_4" 20532 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20533 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8))) 20534 (clobber (mem:BLK (scratch)))])] 20535 "") 20536 20537;; Two pops case is tricky, since pop causes dependency on destination register. 20538;; We use two registers if available. 20539(define_peephole2 20540 [(match_scratch:DI 0 "r") 20541 (match_scratch:DI 1 "r") 20542 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16))) 20543 (clobber (reg:CC FLAGS_REG)) 20544 (clobber (mem:BLK (scratch)))])] 20545 "optimize_size || !TARGET_ADD_ESP_8" 20546 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20547 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8))) 20548 (clobber (mem:BLK (scratch)))]) 20549 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG))) 20550 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])] 20551 "") 20552 20553(define_peephole2 20554 [(match_scratch:DI 0 "r") 20555 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16))) 20556 (clobber (reg:CC FLAGS_REG)) 20557 (clobber (mem:BLK (scratch)))])] 20558 "optimize_size" 20559 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20560 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8))) 20561 (clobber (mem:BLK (scratch)))]) 20562 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20563 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])] 20564 "") 20565 20566;; Convert esp additions to pop. 20567(define_peephole2 20568 [(match_scratch:DI 0 "r") 20569 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8))) 20570 (clobber (reg:CC FLAGS_REG))])] 20571 "" 20572 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20573 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])] 20574 "") 20575 20576;; Two pops case is tricky, since pop causes dependency on destination register. 20577;; We use two registers if available. 20578(define_peephole2 20579 [(match_scratch:DI 0 "r") 20580 (match_scratch:DI 1 "r") 20581 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16))) 20582 (clobber (reg:CC FLAGS_REG))])] 20583 "" 20584 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20585 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))]) 20586 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG))) 20587 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])] 20588 "") 20589 20590(define_peephole2 20591 [(match_scratch:DI 0 "r") 20592 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16))) 20593 (clobber (reg:CC FLAGS_REG))])] 20594 "optimize_size" 20595 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20596 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))]) 20597 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG))) 20598 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])] 20599 "") 20600 20601;; Convert imul by three, five and nine into lea 20602(define_peephole2 20603 [(parallel 20604 [(set (match_operand:SI 0 "register_operand" "") 20605 (mult:SI (match_operand:SI 1 "register_operand" "") 20606 (match_operand:SI 2 "const_int_operand" ""))) 20607 (clobber (reg:CC FLAGS_REG))])] 20608 "INTVAL (operands[2]) == 3 20609 || INTVAL (operands[2]) == 5 20610 || INTVAL (operands[2]) == 9" 20611 [(set (match_dup 0) 20612 (plus:SI (mult:SI (match_dup 1) (match_dup 2)) 20613 (match_dup 1)))] 20614 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); }) 20615 20616(define_peephole2 20617 [(parallel 20618 [(set (match_operand:SI 0 "register_operand" "") 20619 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "") 20620 (match_operand:SI 2 "const_int_operand" ""))) 20621 (clobber (reg:CC FLAGS_REG))])] 20622 "!optimize_size 20623 && (INTVAL (operands[2]) == 3 20624 || INTVAL (operands[2]) == 5 20625 || INTVAL (operands[2]) == 9)" 20626 [(set (match_dup 0) (match_dup 1)) 20627 (set (match_dup 0) 20628 (plus:SI (mult:SI (match_dup 0) (match_dup 2)) 20629 (match_dup 0)))] 20630 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); }) 20631 20632(define_peephole2 20633 [(parallel 20634 [(set (match_operand:DI 0 "register_operand" "") 20635 (mult:DI (match_operand:DI 1 "register_operand" "") 20636 (match_operand:DI 2 "const_int_operand" ""))) 20637 (clobber (reg:CC FLAGS_REG))])] 20638 "TARGET_64BIT 20639 && (INTVAL (operands[2]) == 3 20640 || INTVAL (operands[2]) == 5 20641 || INTVAL (operands[2]) == 9)" 20642 [(set (match_dup 0) 20643 (plus:DI (mult:DI (match_dup 1) (match_dup 2)) 20644 (match_dup 1)))] 20645 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); }) 20646 20647(define_peephole2 20648 [(parallel 20649 [(set (match_operand:DI 0 "register_operand" "") 20650 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "") 20651 (match_operand:DI 2 "const_int_operand" ""))) 20652 (clobber (reg:CC FLAGS_REG))])] 20653 "TARGET_64BIT 20654 && !optimize_size 20655 && (INTVAL (operands[2]) == 3 20656 || INTVAL (operands[2]) == 5 20657 || INTVAL (operands[2]) == 9)" 20658 [(set (match_dup 0) (match_dup 1)) 20659 (set (match_dup 0) 20660 (plus:DI (mult:DI (match_dup 0) (match_dup 2)) 20661 (match_dup 0)))] 20662 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); }) 20663 20664;; Imul $32bit_imm, mem, reg is vector decoded, while 20665;; imul $32bit_imm, reg, reg is direct decoded. 20666(define_peephole2 20667 [(match_scratch:DI 3 "r") 20668 (parallel [(set (match_operand:DI 0 "register_operand" "") 20669 (mult:DI (match_operand:DI 1 "memory_operand" "") 20670 (match_operand:DI 2 "immediate_operand" ""))) 20671 (clobber (reg:CC FLAGS_REG))])] 20672 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size 20673 && !satisfies_constraint_K (operands[2])" 20674 [(set (match_dup 3) (match_dup 1)) 20675 (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2))) 20676 (clobber (reg:CC FLAGS_REG))])] 20677"") 20678 20679(define_peephole2 20680 [(match_scratch:SI 3 "r") 20681 (parallel [(set (match_operand:SI 0 "register_operand" "") 20682 (mult:SI (match_operand:SI 1 "memory_operand" "") 20683 (match_operand:SI 2 "immediate_operand" ""))) 20684 (clobber (reg:CC FLAGS_REG))])] 20685 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size 20686 && !satisfies_constraint_K (operands[2])" 20687 [(set (match_dup 3) (match_dup 1)) 20688 (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2))) 20689 (clobber (reg:CC FLAGS_REG))])] 20690"") 20691 20692(define_peephole2 20693 [(match_scratch:SI 3 "r") 20694 (parallel [(set (match_operand:DI 0 "register_operand" "") 20695 (zero_extend:DI 20696 (mult:SI (match_operand:SI 1 "memory_operand" "") 20697 (match_operand:SI 2 "immediate_operand" "")))) 20698 (clobber (reg:CC FLAGS_REG))])] 20699 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size 20700 && !satisfies_constraint_K (operands[2])" 20701 [(set (match_dup 3) (match_dup 1)) 20702 (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2)))) 20703 (clobber (reg:CC FLAGS_REG))])] 20704"") 20705 20706;; imul $8/16bit_imm, regmem, reg is vector decoded. 20707;; Convert it into imul reg, reg 20708;; It would be better to force assembler to encode instruction using long 20709;; immediate, but there is apparently no way to do so. 20710(define_peephole2 20711 [(parallel [(set (match_operand:DI 0 "register_operand" "") 20712 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "") 20713 (match_operand:DI 2 "const_int_operand" ""))) 20714 (clobber (reg:CC FLAGS_REG))]) 20715 (match_scratch:DI 3 "r")] 20716 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size 20717 && satisfies_constraint_K (operands[2])" 20718 [(set (match_dup 3) (match_dup 2)) 20719 (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3))) 20720 (clobber (reg:CC FLAGS_REG))])] 20721{ 20722 if (!rtx_equal_p (operands[0], operands[1])) 20723 emit_move_insn (operands[0], operands[1]); 20724}) 20725 20726(define_peephole2 20727 [(parallel [(set (match_operand:SI 0 "register_operand" "") 20728 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "") 20729 (match_operand:SI 2 "const_int_operand" ""))) 20730 (clobber (reg:CC FLAGS_REG))]) 20731 (match_scratch:SI 3 "r")] 20732 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size 20733 && satisfies_constraint_K (operands[2])" 20734 [(set (match_dup 3) (match_dup 2)) 20735 (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3))) 20736 (clobber (reg:CC FLAGS_REG))])] 20737{ 20738 if (!rtx_equal_p (operands[0], operands[1])) 20739 emit_move_insn (operands[0], operands[1]); 20740}) 20741 20742(define_peephole2 20743 [(parallel [(set (match_operand:HI 0 "register_operand" "") 20744 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "") 20745 (match_operand:HI 2 "immediate_operand" ""))) 20746 (clobber (reg:CC FLAGS_REG))]) 20747 (match_scratch:HI 3 "r")] 20748 "(TARGET_K8 || TARGET_GENERIC64 || TARGET_AMDFAM10) && !optimize_size" 20749 [(set (match_dup 3) (match_dup 2)) 20750 (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3))) 20751 (clobber (reg:CC FLAGS_REG))])] 20752{ 20753 if (!rtx_equal_p (operands[0], operands[1])) 20754 emit_move_insn (operands[0], operands[1]); 20755}) 20756 20757;; After splitting up read-modify operations, array accesses with memory 20758;; operands might end up in form: 20759;; sall $2, %eax 20760;; movl 4(%esp), %edx 20761;; addl %edx, %eax 20762;; instead of pre-splitting: 20763;; sall $2, %eax 20764;; addl 4(%esp), %eax 20765;; Turn it into: 20766;; movl 4(%esp), %edx 20767;; leal (%edx,%eax,4), %eax 20768 20769(define_peephole2 20770 [(parallel [(set (match_operand 0 "register_operand" "") 20771 (ashift (match_operand 1 "register_operand" "") 20772 (match_operand 2 "const_int_operand" ""))) 20773 (clobber (reg:CC FLAGS_REG))]) 20774 (set (match_operand 3 "register_operand") 20775 (match_operand 4 "x86_64_general_operand" "")) 20776 (parallel [(set (match_operand 5 "register_operand" "") 20777 (plus (match_operand 6 "register_operand" "") 20778 (match_operand 7 "register_operand" ""))) 20779 (clobber (reg:CC FLAGS_REG))])] 20780 "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3 20781 /* Validate MODE for lea. */ 20782 && ((!TARGET_PARTIAL_REG_STALL 20783 && (GET_MODE (operands[0]) == QImode 20784 || GET_MODE (operands[0]) == HImode)) 20785 || GET_MODE (operands[0]) == SImode 20786 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)) 20787 /* We reorder load and the shift. */ 20788 && !rtx_equal_p (operands[1], operands[3]) 20789 && !reg_overlap_mentioned_p (operands[0], operands[4]) 20790 /* Last PLUS must consist of operand 0 and 3. */ 20791 && !rtx_equal_p (operands[0], operands[3]) 20792 && (rtx_equal_p (operands[3], operands[6]) 20793 || rtx_equal_p (operands[3], operands[7])) 20794 && (rtx_equal_p (operands[0], operands[6]) 20795 || rtx_equal_p (operands[0], operands[7])) 20796 /* The intermediate operand 0 must die or be same as output. */ 20797 && (rtx_equal_p (operands[0], operands[5]) 20798 || peep2_reg_dead_p (3, operands[0]))" 20799 [(set (match_dup 3) (match_dup 4)) 20800 (set (match_dup 0) (match_dup 1))] 20801{ 20802 enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode; 20803 int scale = 1 << INTVAL (operands[2]); 20804 rtx index = gen_lowpart (Pmode, operands[1]); 20805 rtx base = gen_lowpart (Pmode, operands[3]); 20806 rtx dest = gen_lowpart (mode, operands[5]); 20807 20808 operands[1] = gen_rtx_PLUS (Pmode, base, 20809 gen_rtx_MULT (Pmode, index, GEN_INT (scale))); 20810 if (mode != Pmode) 20811 operands[1] = gen_rtx_SUBREG (mode, operands[1], 0); 20812 operands[0] = dest; 20813}) 20814 20815;; Call-value patterns last so that the wildcard operand does not 20816;; disrupt insn-recog's switch tables. 20817 20818(define_insn "*call_value_pop_0" 20819 [(set (match_operand 0 "" "") 20820 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" "")) 20821 (match_operand:SI 2 "" ""))) 20822 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) 20823 (match_operand:SI 3 "immediate_operand" "")))] 20824 "!TARGET_64BIT" 20825{ 20826 if (SIBLING_CALL_P (insn)) 20827 return "jmp\t%P1"; 20828 else 20829 return "call\t%P1"; 20830} 20831 [(set_attr "type" "callv")]) 20832 20833(define_insn "*call_value_pop_1" 20834 [(set (match_operand 0 "" "") 20835 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm")) 20836 (match_operand:SI 2 "" ""))) 20837 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) 20838 (match_operand:SI 3 "immediate_operand" "i")))] 20839 "!TARGET_64BIT" 20840{ 20841 if (constant_call_address_operand (operands[1], Pmode)) 20842 { 20843 if (SIBLING_CALL_P (insn)) 20844 return "jmp\t%P1"; 20845 else 20846 return "call\t%P1"; 20847 } 20848 if (SIBLING_CALL_P (insn)) 20849 return "jmp\t%A1"; 20850 else 20851 return "call\t%A1"; 20852} 20853 [(set_attr "type" "callv")]) 20854 20855(define_insn "*call_value_0" 20856 [(set (match_operand 0 "" "") 20857 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" "")) 20858 (match_operand:SI 2 "" "")))] 20859 "!TARGET_64BIT" 20860{ 20861 if (SIBLING_CALL_P (insn)) 20862 return "jmp\t%P1"; 20863 else 20864 return "call\t%P1"; 20865} 20866 [(set_attr "type" "callv")]) 20867 20868(define_insn "*call_value_0_rex64" 20869 [(set (match_operand 0 "" "") 20870 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" "")) 20871 (match_operand:DI 2 "const_int_operand" "")))] 20872 "TARGET_64BIT" 20873{ 20874 if (SIBLING_CALL_P (insn)) 20875 return "jmp\t%P1"; 20876 else 20877 return "call\t%P1"; 20878} 20879 [(set_attr "type" "callv")]) 20880 20881(define_insn "*call_value_1" 20882 [(set (match_operand 0 "" "") 20883 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm")) 20884 (match_operand:SI 2 "" "")))] 20885 "!SIBLING_CALL_P (insn) && !TARGET_64BIT" 20886{ 20887 if (constant_call_address_operand (operands[1], Pmode)) 20888 return "call\t%P1"; 20889 return "call\t%A1"; 20890} 20891 [(set_attr "type" "callv")]) 20892 20893(define_insn "*sibcall_value_1" 20894 [(set (match_operand 0 "" "") 20895 (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a")) 20896 (match_operand:SI 2 "" "")))] 20897 "SIBLING_CALL_P (insn) && !TARGET_64BIT" 20898{ 20899 if (constant_call_address_operand (operands[1], Pmode)) 20900 return "jmp\t%P1"; 20901 return "jmp\t%A1"; 20902} 20903 [(set_attr "type" "callv")]) 20904 20905(define_insn "*call_value_1_rex64" 20906 [(set (match_operand 0 "" "") 20907 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm")) 20908 (match_operand:DI 2 "" "")))] 20909 "!SIBLING_CALL_P (insn) && TARGET_64BIT" 20910{ 20911 if (constant_call_address_operand (operands[1], Pmode)) 20912 return "call\t%P1"; 20913 return "call\t%A1"; 20914} 20915 [(set_attr "type" "callv")]) 20916 20917(define_insn "*sibcall_value_1_rex64" 20918 [(set (match_operand 0 "" "") 20919 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" "")) 20920 (match_operand:DI 2 "" "")))] 20921 "SIBLING_CALL_P (insn) && TARGET_64BIT" 20922 "jmp\t%P1" 20923 [(set_attr "type" "callv")]) 20924 20925(define_insn "*sibcall_value_1_rex64_v" 20926 [(set (match_operand 0 "" "") 20927 (call (mem:QI (reg:DI 40)) 20928 (match_operand:DI 1 "" "")))] 20929 "SIBLING_CALL_P (insn) && TARGET_64BIT" 20930 "jmp\t*%%r11" 20931 [(set_attr "type" "callv")]) 20932 20933;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5. 20934;; That, however, is usually mapped by the OS to SIGSEGV, which is often 20935;; caught for use by garbage collectors and the like. Using an insn that 20936;; maps to SIGILL makes it more likely the program will rightfully die. 20937;; Keeping with tradition, "6" is in honor of #UD. 20938(define_insn "trap" 20939 [(trap_if (const_int 1) (const_int 6))] 20940 "" 20941 { return ASM_SHORT "0x0b0f"; } 20942 [(set_attr "length" "2")]) 20943 20944(define_expand "sse_prologue_save" 20945 [(parallel [(set (match_operand:BLK 0 "" "") 20946 (unspec:BLK [(reg:DI 21) 20947 (reg:DI 22) 20948 (reg:DI 23) 20949 (reg:DI 24) 20950 (reg:DI 25) 20951 (reg:DI 26) 20952 (reg:DI 27) 20953 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE)) 20954 (use (match_operand:DI 1 "register_operand" "")) 20955 (use (match_operand:DI 2 "immediate_operand" "")) 20956 (use (label_ref:DI (match_operand 3 "" "")))])] 20957 "TARGET_64BIT" 20958 "") 20959 20960(define_insn "*sse_prologue_save_insn" 20961 [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R") 20962 (match_operand:DI 4 "const_int_operand" "n"))) 20963 (unspec:BLK [(reg:DI 21) 20964 (reg:DI 22) 20965 (reg:DI 23) 20966 (reg:DI 24) 20967 (reg:DI 25) 20968 (reg:DI 26) 20969 (reg:DI 27) 20970 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE)) 20971 (use (match_operand:DI 1 "register_operand" "r")) 20972 (use (match_operand:DI 2 "const_int_operand" "i")) 20973 (use (label_ref:DI (match_operand 3 "" "X")))] 20974 "TARGET_64BIT 20975 && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128 20976 && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128" 20977 "* 20978{ 20979 int i; 20980 operands[0] = gen_rtx_MEM (Pmode, 20981 gen_rtx_PLUS (Pmode, operands[0], operands[4])); 20982 output_asm_insn (\"jmp\\t%A1\", operands); 20983 for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--) 20984 { 20985 operands[4] = adjust_address (operands[0], DImode, i*16); 20986 operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i)); 20987 PUT_MODE (operands[4], TImode); 20988 if (GET_CODE (XEXP (operands[0], 0)) != PLUS) 20989 output_asm_insn (\"rex\", operands); 20990 output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands); 20991 } 20992 (*targetm.asm_out.internal_label) (asm_out_file, \"L\", 20993 CODE_LABEL_NUMBER (operands[3])); 20994 RET; 20995} 20996 " 20997 [(set_attr "type" "other") 20998 (set_attr "length_immediate" "0") 20999 (set_attr "length_address" "0") 21000 (set_attr "length" "135") 21001 (set_attr "memory" "store") 21002 (set_attr "modrm" "0") 21003 (set_attr "mode" "DI")]) 21004 21005(define_expand "prefetch" 21006 [(prefetch (match_operand 0 "address_operand" "") 21007 (match_operand:SI 1 "const_int_operand" "") 21008 (match_operand:SI 2 "const_int_operand" ""))] 21009 "TARGET_PREFETCH_SSE || TARGET_3DNOW" 21010{ 21011 int rw = INTVAL (operands[1]); 21012 int locality = INTVAL (operands[2]); 21013 21014 gcc_assert (rw == 0 || rw == 1); 21015 gcc_assert (locality >= 0 && locality <= 3); 21016 gcc_assert (GET_MODE (operands[0]) == Pmode 21017 || GET_MODE (operands[0]) == VOIDmode); 21018 21019 /* Use 3dNOW prefetch in case we are asking for write prefetch not 21020 supported by SSE counterpart or the SSE prefetch is not available 21021 (K6 machines). Otherwise use SSE prefetch as it allows specifying 21022 of locality. */ 21023 if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw)) 21024 operands[2] = GEN_INT (3); 21025 else 21026 operands[1] = const0_rtx; 21027}) 21028 21029(define_insn "*prefetch_sse" 21030 [(prefetch (match_operand:SI 0 "address_operand" "p") 21031 (const_int 0) 21032 (match_operand:SI 1 "const_int_operand" ""))] 21033 "TARGET_PREFETCH_SSE && !TARGET_64BIT" 21034{ 21035 static const char * const patterns[4] = { 21036 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0" 21037 }; 21038 21039 int locality = INTVAL (operands[1]); 21040 gcc_assert (locality >= 0 && locality <= 3); 21041 21042 return patterns[locality]; 21043} 21044 [(set_attr "type" "sse") 21045 (set_attr "memory" "none")]) 21046 21047(define_insn "*prefetch_sse_rex" 21048 [(prefetch (match_operand:DI 0 "address_operand" "p") 21049 (const_int 0) 21050 (match_operand:SI 1 "const_int_operand" ""))] 21051 "TARGET_PREFETCH_SSE && TARGET_64BIT" 21052{ 21053 static const char * const patterns[4] = { 21054 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0" 21055 }; 21056 21057 int locality = INTVAL (operands[1]); 21058 gcc_assert (locality >= 0 && locality <= 3); 21059 21060 return patterns[locality]; 21061} 21062 [(set_attr "type" "sse") 21063 (set_attr "memory" "none")]) 21064 21065(define_insn "*prefetch_3dnow" 21066 [(prefetch (match_operand:SI 0 "address_operand" "p") 21067 (match_operand:SI 1 "const_int_operand" "n") 21068 (const_int 3))] 21069 "TARGET_3DNOW && !TARGET_64BIT" 21070{ 21071 if (INTVAL (operands[1]) == 0) 21072 return "prefetch\t%a0"; 21073 else 21074 return "prefetchw\t%a0"; 21075} 21076 [(set_attr "type" "mmx") 21077 (set_attr "memory" "none")]) 21078 21079(define_insn "*prefetch_3dnow_rex" 21080 [(prefetch (match_operand:DI 0 "address_operand" "p") 21081 (match_operand:SI 1 "const_int_operand" "n") 21082 (const_int 3))] 21083 "TARGET_3DNOW && TARGET_64BIT" 21084{ 21085 if (INTVAL (operands[1]) == 0) 21086 return "prefetch\t%a0"; 21087 else 21088 return "prefetchw\t%a0"; 21089} 21090 [(set_attr "type" "mmx") 21091 (set_attr "memory" "none")]) 21092 21093(define_expand "stack_protect_set" 21094 [(match_operand 0 "memory_operand" "") 21095 (match_operand 1 "memory_operand" "")] 21096 "" 21097{ 21098#ifdef TARGET_THREAD_SSP_OFFSET 21099 if (TARGET_64BIT) 21100 emit_insn (gen_stack_tls_protect_set_di (operands[0], 21101 GEN_INT (TARGET_THREAD_SSP_OFFSET))); 21102 else 21103 emit_insn (gen_stack_tls_protect_set_si (operands[0], 21104 GEN_INT (TARGET_THREAD_SSP_OFFSET))); 21105#else 21106 if (TARGET_64BIT) 21107 emit_insn (gen_stack_protect_set_di (operands[0], operands[1])); 21108 else 21109 emit_insn (gen_stack_protect_set_si (operands[0], operands[1])); 21110#endif 21111 DONE; 21112}) 21113 21114(define_insn "stack_protect_set_si" 21115 [(set (match_operand:SI 0 "memory_operand" "=m") 21116 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET)) 21117 (set (match_scratch:SI 2 "=&r") (const_int 0)) 21118 (clobber (reg:CC FLAGS_REG))] 21119 "" 21120 "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2" 21121 [(set_attr "type" "multi")]) 21122 21123(define_insn "stack_protect_set_di" 21124 [(set (match_operand:DI 0 "memory_operand" "=m") 21125 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET)) 21126 (set (match_scratch:DI 2 "=&r") (const_int 0)) 21127 (clobber (reg:CC FLAGS_REG))] 21128 "TARGET_64BIT" 21129 "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2" 21130 [(set_attr "type" "multi")]) 21131 21132(define_insn "stack_tls_protect_set_si" 21133 [(set (match_operand:SI 0 "memory_operand" "=m") 21134 (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET)) 21135 (set (match_scratch:SI 2 "=&r") (const_int 0)) 21136 (clobber (reg:CC FLAGS_REG))] 21137 "" 21138 "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR %%gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2" 21139 [(set_attr "type" "multi")]) 21140 21141(define_insn "stack_tls_protect_set_di" 21142 [(set (match_operand:DI 0 "memory_operand" "=m") 21143 (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET)) 21144 (set (match_scratch:DI 2 "=&r") (const_int 0)) 21145 (clobber (reg:CC FLAGS_REG))] 21146 "TARGET_64BIT" 21147 { 21148 /* The kernel uses a different segment register for performance reasons; a 21149 system call would not have to trash the userspace segment register, 21150 which would be expensive */ 21151 if (ix86_cmodel != CM_KERNEL) 21152 return "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR %%fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"; 21153 else 21154 return "mov{q}\t{%%gs:%P1, %2|%2, QWORD PTR %%gs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"; 21155 } 21156 [(set_attr "type" "multi")]) 21157 21158(define_expand "stack_protect_test" 21159 [(match_operand 0 "memory_operand" "") 21160 (match_operand 1 "memory_operand" "") 21161 (match_operand 2 "" "")] 21162 "" 21163{ 21164 rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG); 21165 ix86_compare_op0 = operands[0]; 21166 ix86_compare_op1 = operands[1]; 21167 ix86_compare_emitted = flags; 21168 21169#ifdef TARGET_THREAD_SSP_OFFSET 21170 if (TARGET_64BIT) 21171 emit_insn (gen_stack_tls_protect_test_di (flags, operands[0], 21172 GEN_INT (TARGET_THREAD_SSP_OFFSET))); 21173 else 21174 emit_insn (gen_stack_tls_protect_test_si (flags, operands[0], 21175 GEN_INT (TARGET_THREAD_SSP_OFFSET))); 21176#else 21177 if (TARGET_64BIT) 21178 emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1])); 21179 else 21180 emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1])); 21181#endif 21182 emit_jump_insn (gen_beq (operands[2])); 21183 DONE; 21184}) 21185 21186(define_insn "stack_protect_test_si" 21187 [(set (match_operand:CCZ 0 "flags_reg_operand" "") 21188 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m") 21189 (match_operand:SI 2 "memory_operand" "m")] 21190 UNSPEC_SP_TEST)) 21191 (clobber (match_scratch:SI 3 "=&r"))] 21192 "" 21193 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}" 21194 [(set_attr "type" "multi")]) 21195 21196(define_insn "stack_protect_test_di" 21197 [(set (match_operand:CCZ 0 "flags_reg_operand" "") 21198 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m") 21199 (match_operand:DI 2 "memory_operand" "m")] 21200 UNSPEC_SP_TEST)) 21201 (clobber (match_scratch:DI 3 "=&r"))] 21202 "TARGET_64BIT" 21203 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}" 21204 [(set_attr "type" "multi")]) 21205 21206(define_insn "stack_tls_protect_test_si" 21207 [(set (match_operand:CCZ 0 "flags_reg_operand" "") 21208 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m") 21209 (match_operand:SI 2 "const_int_operand" "i")] 21210 UNSPEC_SP_TLS_TEST)) 21211 (clobber (match_scratch:SI 3 "=r"))] 21212 "" 21213 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR %%gs:%P2}" 21214 [(set_attr "type" "multi")]) 21215 21216(define_insn "stack_tls_protect_test_di" 21217 [(set (match_operand:CCZ 0 "flags_reg_operand" "") 21218 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m") 21219 (match_operand:DI 2 "const_int_operand" "i")] 21220 UNSPEC_SP_TLS_TEST)) 21221 (clobber (match_scratch:DI 3 "=r"))] 21222 "TARGET_64BIT" 21223 { 21224 /* The kernel uses a different segment register for performance reasons; a 21225 system call would not have to trash the userspace segment register, 21226 which would be expensive */ 21227 if (ix86_cmodel != CM_KERNEL) 21228 return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR %%fs:%P2}"; 21229 else 21230 return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%gs:%P2, %3|%3, QWORD PTR %%gs:%P2}"; 21231 } 21232 [(set_attr "type" "multi")]) 21233 21234(include "mmx.md") 21235(include "sse.md") 21236(include "sync.md") 21237