]> gcc.gnu.org Git - gcc.git/blame - gcc/config/ia64/ia64.md
s390.md ("muldf3", [...]): Do not clobber CC.
[gcc.git] / gcc / config / ia64 / ia64.md
CommitLineData
c65ebc55 1;; IA-64 Machine description template
f9974026 2;; Copyright (C) 1999, 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
c65ebc55
JW
3;; Contributed by James E. Wilson <wilson@cygnus.com> and
4;; David Mosberger <davidm@hpl.hp.com>.
5
3bed2930 6;; This file is part of GCC.
c65ebc55 7
3bed2930 8;; GCC is free software; you can redistribute it and/or modify
c65ebc55
JW
9;; it under the terms of the GNU General Public License as published by
10;; the Free Software Foundation; either version 2, or (at your option)
11;; any later version.
12
3bed2930 13;; GCC is distributed in the hope that it will be useful,
c65ebc55
JW
14;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16;; GNU General Public License for more details.
17
18;; You should have received a copy of the GNU General Public License
3bed2930 19;; along with GCC; see the file COPYING. If not, write to
c65ebc55
JW
20;; the Free Software Foundation, 59 Temple Place - Suite 330,
21;; Boston, MA 02111-1307, USA.
22
23;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
24
c65ebc55
JW
25;; ??? register_operand accepts (subreg:DI (mem:SI X)) which forces later
26;; reload. This will be fixed once scheduling support is turned on.
27
28;; ??? Optimize for post-increment addressing modes.
29
30;; ??? fselect is not supported, because there is no integer register
31;; equivalent.
32
33;; ??? fp abs/min/max instructions may also work for integer values.
34
35;; ??? Would a predicate_reg_operand predicate be useful? The HP one is buggy,
36;; it assumes the operand is a register and takes REGNO of it without checking.
37
38;; ??? Would a branch_reg_operand predicate be useful? The HP one is buggy,
39;; it assumes the operand is a register and takes REGNO of it without checking.
40
41;; ??? Go through list of documented named patterns and look for more to
42;; implement.
43
44;; ??? Go through instruction manual and look for more instructions that
45;; can be emitted.
46
47;; ??? Add function unit scheduling info for Itanium (TM) processor.
48
26102535
RH
49;; ??? Need a better way to describe alternate fp status registers.
50
086c0f96 51(define_constants
7b6e506e
RH
52 [; Relocations
53 (UNSPEC_LTOFF_DTPMOD 0)
54 (UNSPEC_LTOFF_DTPREL 1)
55 (UNSPEC_DTPREL 2)
56 (UNSPEC_LTOFF_TPREL 3)
57 (UNSPEC_TPREL 4)
58
59 (UNSPEC_LD_BASE 9)
60 (UNSPEC_GR_SPILL 10)
61 (UNSPEC_GR_RESTORE 11)
62 (UNSPEC_FR_SPILL 12)
63 (UNSPEC_FR_RESTORE 13)
64 (UNSPEC_FR_RECIP_APPROX 14)
65 (UNSPEC_PRED_REL_MUTEX 15)
c407570a 66 (UNSPEC_GETF_EXP 16)
7b6e506e
RH
67 (UNSPEC_PIC_CALL 17)
68 (UNSPEC_MF 18)
69 (UNSPEC_CMPXCHG_ACQ 19)
70 (UNSPEC_FETCHADD_ACQ 20)
71 (UNSPEC_BSP_VALUE 21)
72 (UNSPEC_FLUSHRS 22)
73 (UNSPEC_BUNDLE_SELECTOR 23)
086c0f96
RH
74 (UNSPEC_ADDP4 24)
75 (UNSPEC_PROLOGUE_USE 25)
af1e5518 76 (UNSPEC_RET_ADDR 26)
086c0f96
RH
77 ])
78
79(define_constants
80 [(UNSPECV_ALLOC 0)
81 (UNSPECV_BLOCKAGE 1)
82 (UNSPECV_INSN_GROUP_BARRIER 2)
83 (UNSPECV_BREAK 3)
7b6e506e
RH
84 (UNSPECV_SET_BSP 4)
85 (UNSPECV_PSAC_ALL 5) ; pred.safe_across_calls
86 (UNSPECV_PSAC_NORMAL 6)
b39eb2f9 87 (UNSPECV_SETJMP_RECEIVER 7)
086c0f96 88 ])
c65ebc55
JW
89\f
90;; ::::::::::::::::::::
91;; ::
92;; :: Attributes
93;; ::
94;; ::::::::::::::::::::
95
30028c85
VM
96;; Processor type. This attribute must exactly match the processor_type
97;; enumeration in ia64.h.
98(define_attr "cpu" "itanium,itanium2" (const (symbol_ref "ia64_tune")))
99
c65ebc55
JW
100;; Instruction type. This primarily determines how instructions can be
101;; packed in bundles, and secondarily affects scheduling to function units.
102
103;; A alu, can go in I or M syllable of a bundle
104;; I integer
105;; M memory
106;; F floating-point
107;; B branch
108;; L long immediate, takes two syllables
109;; S stop bit
110
111;; ??? Should not have any pattern with type unknown. Perhaps add code to
112;; check this in md_reorg? Currently use unknown for patterns which emit
113;; multiple instructions, patterns which emit 0 instructions, and patterns
114;; which emit instruction that can go in any slot (e.g. nop).
115
1d5d7a21
RH
116(define_attr "itanium_class" "unknown,ignore,stop_bit,br,fcmp,fcvtfx,fld,
117 fmac,fmisc,frar_i,frar_m,frbr,frfr,frpr,ialu,icmp,ilog,ishf,ld,
118 chk_s,long_i,mmmul,mmshf,mmshfi,rse_m,scall,sem,stf,st,syst_m0,
30028c85
VM
119 syst_m,tbit,toar_i,toar_m,tobr,tofr,topr,xmpy,xtd,nop,nop_b,nop_f,
120 nop_i,nop_m,nop_x,lfetch,pre_cycle"
1d5d7a21 121 (const_string "unknown"))
52e12ad0 122
2130b7fb
BS
123;; chk_s has an I and an M form; use type A for convenience.
124(define_attr "type" "unknown,A,I,M,F,B,L,X,S"
125 (cond [(eq_attr "itanium_class" "ld,st,fld,stf,sem,nop_m") (const_string "M")
52e12ad0
BS
126 (eq_attr "itanium_class" "rse_m,syst_m,syst_m0") (const_string "M")
127 (eq_attr "itanium_class" "frar_m,toar_m,frfr,tofr") (const_string "M")
44eca121 128 (eq_attr "itanium_class" "lfetch") (const_string "M")
2130b7fb
BS
129 (eq_attr "itanium_class" "chk_s,ialu,icmp,ilog") (const_string "A")
130 (eq_attr "itanium_class" "fmisc,fmac,fcmp,xmpy") (const_string "F")
131 (eq_attr "itanium_class" "fcvtfx,nop_f") (const_string "F")
52e12ad0
BS
132 (eq_attr "itanium_class" "frar_i,toar_i,frbr,tobr") (const_string "I")
133 (eq_attr "itanium_class" "frpr,topr,ishf,xtd,tbit") (const_string "I")
2130b7fb
BS
134 (eq_attr "itanium_class" "mmmul,mmshf,mmshfi,nop_i") (const_string "I")
135 (eq_attr "itanium_class" "br,scall,nop_b") (const_string "B")
52e12ad0 136 (eq_attr "itanium_class" "stop_bit") (const_string "S")
2130b7fb 137 (eq_attr "itanium_class" "nop_x") (const_string "X")
52e12ad0
BS
138 (eq_attr "itanium_class" "long_i") (const_string "L")]
139 (const_string "unknown")))
c65ebc55 140
2130b7fb
BS
141(define_attr "itanium_requires_unit0" "no,yes"
142 (cond [(eq_attr "itanium_class" "syst_m0,sem,frfr,rse_m") (const_string "yes")
143 (eq_attr "itanium_class" "toar_m,frar_m") (const_string "yes")
144 (eq_attr "itanium_class" "frbr,tobr,mmmul") (const_string "yes")
145 (eq_attr "itanium_class" "tbit,ishf,topr,frpr") (const_string "yes")
146 (eq_attr "itanium_class" "toar_i,frar_i") (const_string "yes")
147 (eq_attr "itanium_class" "fmisc,fcmp") (const_string "yes")]
148 (const_string "no")))
149
e5bde68a
RH
150;; Predication. True iff this instruction can be predicated.
151
152(define_attr "predicable" "no,yes" (const_string "yes"))
153
c65ebc55 154\f
c65ebc55 155
30028c85
VM
156;; DFA descriptions of ia64 processors used for insn scheduling and
157;; bundling.
158
159(automata_option "ndfa")
160
161;; Uncomment the following line to output automata for debugging.
162;; (automata_option "v")
163
164(automata_option "w")
165
166;;(automata_option "no-minimization")
167
168
169(include "itanium1.md")
170(include "itanium2.md")
171
c65ebc55
JW
172\f
173;; ::::::::::::::::::::
174;; ::
175;; :: Moves
176;; ::
177;; ::::::::::::::::::::
178
f2f90c63
RH
179;; Set of a single predicate register. This is only used to implement
180;; pr-to-pr move and complement.
181
182(define_insn "*movcci"
183 [(set (match_operand:CCI 0 "register_operand" "=c,c,c")
184 (match_operand:CCI 1 "nonmemory_operand" "O,n,c"))]
185 ""
186 "@
187 cmp.ne %0, p0 = r0, r0
188 cmp.eq %0, p0 = r0, r0
189 (%1) cmp.eq.unc %0, p0 = r0, r0"
52e12ad0 190 [(set_attr "itanium_class" "icmp")
f2f90c63
RH
191 (set_attr "predicable" "no")])
192
193(define_insn "movbi"
cd5c4048
RH
194 [(set (match_operand:BI 0 "nonimmediate_operand" "=c,c,?c,?*r, c,*r,*r,*m,*r")
195 (match_operand:BI 1 "move_operand" " O,n, c, c,*r, n,*m,*r,*r"))]
f2f90c63
RH
196 ""
197 "@
198 cmp.ne %0, %I0 = r0, r0
199 cmp.eq %0, %I0 = r0, r0
200 #
201 #
202 tbit.nz %0, %I0 = %1, 0
203 adds %0 = %1, r0
204 ld1%O1 %0 = %1%P1
cd5c4048
RH
205 st1%Q0 %0 = %1%P0
206 mov %0 = %1"
52e12ad0 207 [(set_attr "itanium_class" "icmp,icmp,unknown,unknown,tbit,ialu,ld,st,ialu")])
f2f90c63
RH
208
209(define_split
210 [(set (match_operand:BI 0 "register_operand" "")
211 (match_operand:BI 1 "register_operand" ""))]
212 "reload_completed
213 && GET_CODE (operands[0]) == REG && GR_REGNO_P (REGNO (operands[0]))
214 && GET_CODE (operands[1]) == REG && PR_REGNO_P (REGNO (operands[1]))"
215 [(cond_exec (ne (match_dup 1) (const_int 0))
216 (set (match_dup 0) (const_int 1)))
217 (cond_exec (eq (match_dup 1) (const_int 0))
218 (set (match_dup 0) (const_int 0)))]
219 "")
220
221(define_split
222 [(set (match_operand:BI 0 "register_operand" "")
223 (match_operand:BI 1 "register_operand" ""))]
224 "reload_completed
225 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
226 && GET_CODE (operands[1]) == REG && PR_REGNO_P (REGNO (operands[1]))"
227 [(set (match_dup 2) (match_dup 4))
228 (set (match_dup 3) (match_dup 5))
086c0f96 229 (set (match_dup 0) (unspec:BI [(match_dup 0)] UNSPEC_PRED_REL_MUTEX))]
f2f90c63
RH
230 "operands[2] = gen_rtx_REG (CCImode, REGNO (operands[0]));
231 operands[3] = gen_rtx_REG (CCImode, REGNO (operands[0]) + 1);
232 operands[4] = gen_rtx_REG (CCImode, REGNO (operands[1]));
233 operands[5] = gen_rtx_REG (CCImode, REGNO (operands[1]) + 1);")
234
c65ebc55
JW
235(define_expand "movqi"
236 [(set (match_operand:QI 0 "general_operand" "")
237 (match_operand:QI 1 "general_operand" ""))]
238 ""
c65ebc55 239{
7b6e506e
RH
240 rtx op1 = ia64_expand_move (operands[0], operands[1]);
241 if (!op1)
242 DONE;
243 operands[1] = op1;
1d5d7a21 244})
c65ebc55
JW
245
246(define_insn "*movqi_internal"
4b983fdc
RH
247 [(set (match_operand:QI 0 "destination_operand" "=r,r,r, m, r,*f,*f")
248 (match_operand:QI 1 "move_operand" "rO,J,m,rO,*f,rO,*f"))]
aebf2462 249 "ia64_move_ok (operands[0], operands[1])"
c65ebc55 250 "@
13da91fd 251 mov %0 = %r1
c65ebc55
JW
252 addl %0 = %1, r0
253 ld1%O1 %0 = %1%P1
13da91fd 254 st1%Q0 %0 = %r1%P0
c65ebc55 255 getf.sig %0 = %1
13da91fd
RH
256 setf.sig %0 = %r1
257 mov %0 = %1"
52e12ad0 258 [(set_attr "itanium_class" "ialu,ialu,ld,st,frfr,tofr,fmisc")])
c65ebc55
JW
259
260(define_expand "movhi"
261 [(set (match_operand:HI 0 "general_operand" "")
262 (match_operand:HI 1 "general_operand" ""))]
263 ""
c65ebc55 264{
7b6e506e
RH
265 rtx op1 = ia64_expand_move (operands[0], operands[1]);
266 if (!op1)
267 DONE;
268 operands[1] = op1;
1d5d7a21 269})
c65ebc55
JW
270
271(define_insn "*movhi_internal"
4b983fdc
RH
272 [(set (match_operand:HI 0 "destination_operand" "=r,r,r, m, r,*f,*f")
273 (match_operand:HI 1 "move_operand" "rO,J,m,rO,*f,rO,*f"))]
aebf2462 274 "ia64_move_ok (operands[0], operands[1])"
c65ebc55 275 "@
13da91fd 276 mov %0 = %r1
c65ebc55
JW
277 addl %0 = %1, r0
278 ld2%O1 %0 = %1%P1
13da91fd 279 st2%Q0 %0 = %r1%P0
c65ebc55 280 getf.sig %0 = %1
13da91fd
RH
281 setf.sig %0 = %r1
282 mov %0 = %1"
52e12ad0 283 [(set_attr "itanium_class" "ialu,ialu,ld,st,frfr,tofr,fmisc")])
c65ebc55
JW
284
285(define_expand "movsi"
286 [(set (match_operand:SI 0 "general_operand" "")
287 (match_operand:SI 1 "general_operand" ""))]
288 ""
c65ebc55 289{
7b6e506e
RH
290 rtx op1 = ia64_expand_move (operands[0], operands[1]);
291 if (!op1)
292 DONE;
293 operands[1] = op1;
1d5d7a21 294})
c65ebc55
JW
295
296(define_insn "*movsi_internal"
97e242b0 297 [(set (match_operand:SI 0 "destination_operand" "=r,r,r,r, m, r,*f,*f, r,*d")
514f96e6 298 (match_operand:SI 1 "move_operand" "rO,J,i,m,rO,*f,rO,*f,*d,rK"))]
aebf2462 299 "ia64_move_ok (operands[0], operands[1])"
c65ebc55 300 "@
13da91fd 301 mov %0 = %r1
c65ebc55
JW
302 addl %0 = %1, r0
303 movl %0 = %1
304 ld4%O1 %0 = %1%P1
13da91fd 305 st4%Q0 %0 = %r1%P0
c65ebc55 306 getf.sig %0 = %1
13da91fd 307 setf.sig %0 = %r1
97e242b0
RH
308 mov %0 = %1
309 mov %0 = %1
310 mov %0 = %r1"
1d5d7a21 311 ;; frar_m, toar_m ??? why not frar_i and toar_i
52e12ad0 312 [(set_attr "itanium_class" "ialu,ialu,long_i,ld,st,frfr,tofr,fmisc,frar_m,toar_m")])
c65ebc55
JW
313
314(define_expand "movdi"
315 [(set (match_operand:DI 0 "general_operand" "")
316 (match_operand:DI 1 "general_operand" ""))]
317 ""
c65ebc55 318{
7b6e506e
RH
319 rtx op1 = ia64_expand_move (operands[0], operands[1]);
320 if (!op1)
321 DONE;
322 operands[1] = op1;
1d5d7a21 323})
c65ebc55 324
c65ebc55 325(define_insn "*movdi_internal"
4b983fdc 326 [(set (match_operand:DI 0 "destination_operand"
52e12ad0 327 "=r,r,r,r, m, r,*f,*f,*f, Q, r,*b, r,*e, r,*d, r,*c")
4b983fdc 328 (match_operand:DI 1 "move_operand"
a32767e4 329 "rO,JT,i,m,rO,*f,rO,*f, Q,*f,*b,rO,*e,rK,*d,rK,*c,rO"))]
aebf2462 330 "ia64_move_ok (operands[0], operands[1])"
9b7bf67d
RH
331{
332 static const char * const alt[] = {
1d5d7a21
RH
333 "%,mov %0 = %r1",
334 "%,addl %0 = %1, r0",
335 "%,movl %0 = %1",
336 "%,ld8%O1 %0 = %1%P1",
337 "%,st8%Q0 %0 = %r1%P0",
338 "%,getf.sig %0 = %1",
339 "%,setf.sig %0 = %r1",
340 "%,mov %0 = %1",
341 "%,ldf8 %0 = %1%P1",
342 "%,stf8 %0 = %1%P0",
343 "%,mov %0 = %1",
344 "%,mov %0 = %r1",
345 "%,mov %0 = %1",
346 "%,mov %0 = %1",
347 "%,mov %0 = %1",
348 "%,mov %0 = %1",
349 "mov %0 = pr",
350 "mov pr = %1, -1"
9b7bf67d
RH
351 };
352
9b7bf67d
RH
353 if (which_alternative == 2 && ! TARGET_NO_PIC
354 && symbolic_operand (operands[1], VOIDmode))
355 abort ();
356
357 return alt[which_alternative];
1d5d7a21 358}
52e12ad0 359 [(set_attr "itanium_class" "ialu,ialu,long_i,ld,st,frfr,tofr,fmisc,fld,stf,frbr,tobr,frar_i,toar_i,frar_m,toar_m,frpr,topr")])
c65ebc55 360
9b7bf67d 361(define_split
21515593
RH
362 [(set (match_operand 0 "register_operand" "")
363 (match_operand 1 "symbolic_operand" ""))]
9b7bf67d
RH
364 "reload_completed && ! TARGET_NO_PIC"
365 [(const_int 0)]
9b7bf67d 366{
21515593 367 ia64_expand_load_address (operands[0], operands[1]);
9b7bf67d 368 DONE;
1d5d7a21 369})
9b7bf67d 370
c65ebc55
JW
371(define_expand "load_fptr"
372 [(set (match_dup 2)
5da4f548 373 (plus:DI (reg:DI 1) (match_operand 1 "function_operand" "")))
ec039e3c 374 (set (match_operand:DI 0 "register_operand" "") (match_dup 3))]
c65ebc55 375 ""
c65ebc55 376{
ec039e3c
RH
377 operands[2] = no_new_pseudos ? operands[0] : gen_reg_rtx (DImode);
378 operands[3] = gen_rtx_MEM (DImode, operands[2]);
379 RTX_UNCHANGING_P (operands[3]) = 1;
1d5d7a21 380})
c65ebc55
JW
381
382(define_insn "*load_fptr_internal1"
383 [(set (match_operand:DI 0 "register_operand" "=r")
5da4f548 384 (plus:DI (reg:DI 1) (match_operand 1 "function_operand" "s")))]
c65ebc55
JW
385 ""
386 "addl %0 = @ltoff(@fptr(%1)), gp"
52e12ad0 387 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
388
389(define_insn "load_gprel"
390 [(set (match_operand:DI 0 "register_operand" "=r")
5da4f548 391 (plus:DI (reg:DI 1) (match_operand 1 "sdata_symbolic_operand" "s")))]
c65ebc55
JW
392 ""
393 "addl %0 = @gprel(%1), gp"
52e12ad0 394 [(set_attr "itanium_class" "ialu")])
c65ebc55 395
59da9a7d
JW
396(define_insn "gprel64_offset"
397 [(set (match_operand:DI 0 "register_operand" "=r")
398 (minus:DI (match_operand:DI 1 "symbolic_operand" "") (reg:DI 1)))]
399 ""
400 "movl %0 = @gprel(%1)"
52e12ad0 401 [(set_attr "itanium_class" "long_i")])
59da9a7d
JW
402
403(define_expand "load_gprel64"
404 [(set (match_dup 2)
b5d37c6f 405 (minus:DI (match_operand:DI 1 "symbolic_operand" "") (match_dup 3)))
59da9a7d 406 (set (match_operand:DI 0 "register_operand" "")
b5d37c6f 407 (plus:DI (match_dup 3) (match_dup 2)))]
59da9a7d 408 ""
ec039e3c
RH
409{
410 operands[2] = no_new_pseudos ? operands[0] : gen_reg_rtx (DImode);
b5d37c6f 411 operands[3] = pic_offset_table_rtx;
1d5d7a21 412})
59da9a7d 413
af1e5518
RH
414;; This is used as a placeholder for the return address during early
415;; compilation. We won't know where we've placed this until during
416;; reload, at which point it can wind up in b0, a general register,
417;; or memory. The only safe destination under these conditions is a
418;; general register.
419
420(define_insn_and_split "*movdi_ret_addr"
421 [(set (match_operand:DI 0 "register_operand" "=r")
422 (unspec:DI [(const_int 0)] UNSPEC_RET_ADDR))]
423 ""
424 "#"
425 "reload_completed"
426 [(const_int 0)]
427{
428 ia64_split_return_addr_rtx (operands[0]);
429 DONE;
430}
431 [(set_attr "itanium_class" "ialu")])
432
ef1ecf87 433(define_insn "*load_symptr_high"
c65ebc55 434 [(set (match_operand:DI 0 "register_operand" "=r")
ef1ecf87
RH
435 (plus:DI (high:DI (match_operand 1 "got_symbolic_operand" "s"))
436 (match_operand:DI 2 "register_operand" "a")))]
c65ebc55 437 ""
ef1ecf87
RH
438{
439 if (HAVE_AS_LTOFFX_LDXMOV_RELOCS)
440 return "%,addl %0 = @ltoffx(%1), %2";
441 else
442 return "%,addl %0 = @ltoff(%1), %2";
443}
52e12ad0 444 [(set_attr "itanium_class" "ialu")])
c65ebc55 445
ef1ecf87
RH
446(define_insn "*load_symptr_low"
447 [(set (match_operand:DI 0 "register_operand" "=r")
448 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
449 (match_operand 2 "got_symbolic_operand" "s")))]
450 ""
451{
452 if (HAVE_AS_LTOFFX_LDXMOV_RELOCS)
453 return "%,ld8.mov %0 = [%1], %2";
454 else
455 return "%,ld8 %0 = [%1]";
456}
457 [(set_attr "itanium_class" "ld")])
458
7b6e506e
RH
459(define_insn "load_ltoff_dtpmod"
460 [(set (match_operand:DI 0 "register_operand" "=r")
461 (plus:DI (reg:DI 1)
462 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
463 UNSPEC_LTOFF_DTPMOD)))]
464 ""
465 "addl %0 = @ltoff(@dtpmod(%1)), gp"
466 [(set_attr "itanium_class" "ialu")])
467
468(define_insn "load_ltoff_dtprel"
469 [(set (match_operand:DI 0 "register_operand" "=r")
470 (plus:DI (reg:DI 1)
471 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
472 UNSPEC_LTOFF_DTPREL)))]
473 ""
474 "addl %0 = @ltoff(@dtprel(%1)), gp"
475 [(set_attr "itanium_class" "ialu")])
476
477(define_expand "load_dtprel"
478 [(set (match_operand:DI 0 "register_operand" "")
479 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
480 UNSPEC_DTPREL))]
481 ""
482 "")
483
484(define_insn "*load_dtprel64"
485 [(set (match_operand:DI 0 "register_operand" "=r")
486 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
487 UNSPEC_DTPREL))]
488 "TARGET_TLS64"
489 "movl %0 = @dtprel(%1)"
490 [(set_attr "itanium_class" "long_i")])
491
492(define_insn "*load_dtprel22"
493 [(set (match_operand:DI 0 "register_operand" "=r")
494 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
495 UNSPEC_DTPREL))]
496 ""
497 "addl %0 = @dtprel(%1), r0"
498 [(set_attr "itanium_class" "ialu")])
499
500(define_expand "add_dtprel"
501 [(set (match_operand:DI 0 "register_operand" "")
502 (plus:DI (match_operand:DI 1 "register_operand" "")
503 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
504 UNSPEC_DTPREL)))]
505 "!TARGET_TLS64"
506 "")
507
508(define_insn "*add_dtprel14"
509 [(set (match_operand:DI 0 "register_operand" "=r")
510 (plus:DI (match_operand:DI 1 "register_operand" "r")
511 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
512 UNSPEC_DTPREL)))]
513 "TARGET_TLS14"
514 "adds %0 = @dtprel(%2), %1"
515 [(set_attr "itanium_class" "ialu")])
516
517(define_insn "*add_dtprel22"
518 [(set (match_operand:DI 0 "register_operand" "=r")
519 (plus:DI (match_operand:DI 1 "register_operand" "a")
520 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
521 UNSPEC_DTPREL)))]
522 "TARGET_TLS22"
523 "addl %0 = @dtprel(%2), %1"
524 [(set_attr "itanium_class" "ialu")])
525
526(define_insn "load_ltoff_tprel"
527 [(set (match_operand:DI 0 "register_operand" "=r")
528 (plus:DI (reg:DI 1)
529 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
530 UNSPEC_LTOFF_TPREL)))]
531 ""
532 "addl %0 = @ltoff(@tprel(%1)), gp"
533 [(set_attr "itanium_class" "ialu")])
534
535(define_expand "load_tprel"
536 [(set (match_operand:DI 0 "register_operand" "")
537 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
538 UNSPEC_TPREL))]
539 ""
540 "")
541
542(define_insn "*load_tprel64"
543 [(set (match_operand:DI 0 "register_operand" "=r")
544 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
545 UNSPEC_TPREL))]
546 "TARGET_TLS64"
547 "movl %0 = @tprel(%1)"
548 [(set_attr "itanium_class" "long_i")])
549
550(define_insn "*load_tprel22"
551 [(set (match_operand:DI 0 "register_operand" "=r")
552 (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
553 UNSPEC_TPREL))]
554 ""
555 "addl %0 = @tprel(%1), r0"
556 [(set_attr "itanium_class" "ialu")])
557
558(define_expand "add_tprel"
559 [(set (match_operand:DI 0 "register_operand" "")
560 (plus:DI (match_operand:DI 1 "register_operand" "")
561 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
562 UNSPEC_TPREL)))]
563 "!TARGET_TLS64"
564 "")
565
566(define_insn "*add_tprel14"
567 [(set (match_operand:DI 0 "register_operand" "=r")
568 (plus:DI (match_operand:DI 1 "register_operand" "r")
569 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
570 UNSPEC_TPREL)))]
571 "TARGET_TLS14"
572 "adds %0 = @tprel(%2), %1"
573 [(set_attr "itanium_class" "ialu")])
574
575(define_insn "*add_tprel22"
576 [(set (match_operand:DI 0 "register_operand" "=r")
577 (plus:DI (match_operand:DI 1 "register_operand" "a")
578 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
579 UNSPEC_TPREL)))]
580 "TARGET_TLS22"
581 "addl %0 = @tprel(%2), %1"
582 [(set_attr "itanium_class" "ialu")])
583
3f622353
RH
584;; With no offsettable memory references, we've got to have a scratch
585;; around to play with the second word.
586(define_expand "movti"
587 [(parallel [(set (match_operand:TI 0 "general_operand" "")
588 (match_operand:TI 1 "general_operand" ""))
589 (clobber (match_scratch:DI 2 ""))])]
590 ""
3f622353 591{
7b6e506e
RH
592 rtx op1 = ia64_expand_move (operands[0], operands[1]);
593 if (!op1)
594 DONE;
595 operands[1] = op1;
1d5d7a21 596})
3f622353
RH
597
598(define_insn_and_split "*movti_internal"
599 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,r,m")
600 (match_operand:TI 1 "general_operand" "ri,m,r"))
601 (clobber (match_scratch:DI 2 "=X,&r,&r"))]
602 "ia64_move_ok (operands[0], operands[1])"
603 "#"
604 "reload_completed"
605 [(const_int 0)]
3f622353 606{
703cf211 607 rtx adj1, adj2, in[2], out[2], insn;
3f622353
RH
608 int first;
609
610 adj1 = ia64_split_timode (in, operands[1], operands[2]);
611 adj2 = ia64_split_timode (out, operands[0], operands[2]);
612
613 first = 0;
614 if (reg_overlap_mentioned_p (out[0], in[1]))
615 {
616 if (reg_overlap_mentioned_p (out[1], in[0]))
617 abort ();
618 first = 1;
619 }
620
621 if (adj1 && adj2)
622 abort ();
623 if (adj1)
624 emit_insn (adj1);
625 if (adj2)
626 emit_insn (adj2);
703cf211
BS
627 insn = emit_insn (gen_rtx_SET (VOIDmode, out[first], in[first]));
628 if (GET_CODE (out[first]) == MEM
629 && GET_CODE (XEXP (out[first], 0)) == POST_MODIFY)
630 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_INC,
631 XEXP (XEXP (out[first], 0), 0),
632 REG_NOTES (insn));
633 insn = emit_insn (gen_rtx_SET (VOIDmode, out[!first], in[!first]));
634 if (GET_CODE (out[!first]) == MEM
635 && GET_CODE (XEXP (out[!first], 0)) == POST_MODIFY)
636 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_INC,
637 XEXP (XEXP (out[!first], 0), 0),
638 REG_NOTES (insn));
3f622353 639 DONE;
1d5d7a21 640}
52e12ad0 641 [(set_attr "itanium_class" "unknown")
3f622353 642 (set_attr "predicable" "no")])
e314e331 643
3f622353
RH
644;; ??? SSA creates these. Can't allow memories since we don't have
645;; the scratch register. Fortunately combine will know how to add
646;; the clobber and scratch.
647(define_insn_and_split "*movti_internal_reg"
648 [(set (match_operand:TI 0 "register_operand" "=r")
649 (match_operand:TI 1 "nonmemory_operand" "ri"))]
650 ""
e314e331 651 "#"
3f622353
RH
652 "reload_completed"
653 [(const_int 0)]
3f622353
RH
654{
655 rtx in[2], out[2];
656 int first;
657
658 ia64_split_timode (in, operands[1], NULL_RTX);
659 ia64_split_timode (out, operands[0], NULL_RTX);
660
661 first = 0;
662 if (reg_overlap_mentioned_p (out[0], in[1]))
663 {
664 if (reg_overlap_mentioned_p (out[1], in[0]))
665 abort ();
666 first = 1;
667 }
668
669 emit_insn (gen_rtx_SET (VOIDmode, out[first], in[first]));
670 emit_insn (gen_rtx_SET (VOIDmode, out[!first], in[!first]));
671 DONE;
1d5d7a21 672}
52e12ad0 673 [(set_attr "itanium_class" "unknown")
e314e331
JW
674 (set_attr "predicable" "no")])
675
3f622353
RH
676(define_expand "reload_inti"
677 [(parallel [(set (match_operand:TI 0 "register_operand" "=r")
678 (match_operand:TI 1 "" "m"))
60a3c181 679 (clobber (match_operand:TI 2 "register_operand" "=&r"))])]
3f622353 680 ""
3f622353 681{
60a3c181
RH
682 unsigned int s_regno = REGNO (operands[2]);
683 if (s_regno == REGNO (operands[0]))
684 s_regno += 1;
685 operands[2] = gen_rtx_REG (DImode, s_regno);
1d5d7a21 686})
3f622353
RH
687
688(define_expand "reload_outti"
689 [(parallel [(set (match_operand:TI 0 "" "=m")
690 (match_operand:TI 1 "register_operand" "r"))
60a3c181 691 (clobber (match_operand:TI 2 "register_operand" "=&r"))])]
3f622353 692 ""
3f622353 693{
60a3c181
RH
694 unsigned int s_regno = REGNO (operands[2]);
695 if (s_regno == REGNO (operands[1]))
696 s_regno += 1;
697 operands[2] = gen_rtx_REG (DImode, s_regno);
1d5d7a21 698})
e314e331 699
c65ebc55
JW
700;; Floating Point Moves
701;;
702;; Note - Patterns for SF mode moves are compulsory, but
05713b80 703;; patterns for DF are optional, as GCC can synthesize them.
c65ebc55
JW
704
705(define_expand "movsf"
706 [(set (match_operand:SF 0 "general_operand" "")
707 (match_operand:SF 1 "general_operand" ""))]
708 ""
c65ebc55 709{
7b6e506e
RH
710 rtx op1 = ia64_expand_move (operands[0], operands[1]);
711 if (!op1)
712 DONE;
713 operands[1] = op1;
1d5d7a21 714})
c65ebc55 715
c65ebc55 716(define_insn "*movsf_internal"
4b983fdc
RH
717 [(set (match_operand:SF 0 "destination_operand" "=f,f, Q,*r, f,*r,*r, m")
718 (match_operand:SF 1 "general_operand" "fG,Q,fG,fG,*r,*r, m,*r"))]
aebf2462 719 "ia64_move_ok (operands[0], operands[1])"
c65ebc55 720 "@
1d5d7a21
RH
721 mov %0 = %F1
722 ldfs %0 = %1%P1
723 stfs %0 = %F1%P0
724 getf.s %0 = %F1
725 setf.s %0 = %1
726 mov %0 = %1
727 ld4%O1 %0 = %1%P1
728 st4%Q0 %0 = %1%P0"
52e12ad0 729 [(set_attr "itanium_class" "fmisc,fld,stf,frfr,tofr,ialu,ld,st")])
c65ebc55
JW
730
731(define_expand "movdf"
732 [(set (match_operand:DF 0 "general_operand" "")
733 (match_operand:DF 1 "general_operand" ""))]
734 ""
c65ebc55 735{
7b6e506e
RH
736 rtx op1 = ia64_expand_move (operands[0], operands[1]);
737 if (!op1)
738 DONE;
739 operands[1] = op1;
1d5d7a21 740})
c65ebc55 741
c65ebc55 742(define_insn "*movdf_internal"
4b983fdc
RH
743 [(set (match_operand:DF 0 "destination_operand" "=f,f, Q,*r, f,*r,*r, m")
744 (match_operand:DF 1 "general_operand" "fG,Q,fG,fG,*r,*r, m,*r"))]
aebf2462 745 "ia64_move_ok (operands[0], operands[1])"
c65ebc55 746 "@
1d5d7a21
RH
747 mov %0 = %F1
748 ldfd %0 = %1%P1
749 stfd %0 = %F1%P0
750 getf.d %0 = %F1
751 setf.d %0 = %1
752 mov %0 = %1
753 ld8%O1 %0 = %1%P1
754 st8%Q0 %0 = %1%P0"
52e12ad0 755 [(set_attr "itanium_class" "fmisc,fld,stf,frfr,tofr,ialu,ld,st")])
c65ebc55 756
3f622353
RH
757;; With no offsettable memory references, we've got to have a scratch
758;; around to play with the second word if the variable winds up in GRs.
759(define_expand "movtf"
760 [(set (match_operand:TF 0 "general_operand" "")
761 (match_operand:TF 1 "general_operand" ""))]
23c108af 762 "INTEL_EXTENDED_IEEE_FORMAT"
e5bde68a 763{
3f622353
RH
764 /* We must support TFmode loads into general registers for stdarg/vararg
765 and unprototyped calls. We split them into DImode loads for convenience.
766 We don't need TFmode stores from general regs, because a stdarg/vararg
767 routine does a block store to memory of unnamed arguments. */
768 if (GET_CODE (operands[0]) == REG
769 && GR_REGNO_P (REGNO (operands[0])))
770 {
771 /* We're hoping to transform everything that deals with TFmode
772 quantities and GR registers early in the compiler. */
773 if (no_new_pseudos)
774 abort ();
775
776 /* Struct to register can just use TImode instead. */
777 if ((GET_CODE (operands[1]) == SUBREG
778 && GET_MODE (SUBREG_REG (operands[1])) == TImode)
779 || (GET_CODE (operands[1]) == REG
780 && GR_REGNO_P (REGNO (operands[1]))))
781 {
782 emit_move_insn (gen_rtx_REG (TImode, REGNO (operands[0])),
783 SUBREG_REG (operands[1]));
784 DONE;
785 }
786
787 if (GET_CODE (operands[1]) == CONST_DOUBLE)
788 {
789 emit_move_insn (gen_rtx_REG (DImode, REGNO (operands[0])),
2bf47a10 790 operand_subword (operands[1], 0, 0, TFmode));
3f622353 791 emit_move_insn (gen_rtx_REG (DImode, REGNO (operands[0]) + 1),
2bf47a10 792 operand_subword (operands[1], 1, 0, TFmode));
3f622353
RH
793 DONE;
794 }
795
796 /* If the quantity is in a register not known to be GR, spill it. */
797 if (register_operand (operands[1], TFmode))
798 operands[1] = spill_tfmode_operand (operands[1], 1);
799
800 if (GET_CODE (operands[1]) == MEM)
801 {
802 rtx out[2];
803
804 out[WORDS_BIG_ENDIAN] = gen_rtx_REG (DImode, REGNO (operands[0]));
805 out[!WORDS_BIG_ENDIAN] = gen_rtx_REG (DImode, REGNO (operands[0])+1);
806
f4ef873c
RK
807 emit_move_insn (out[0], adjust_address (operands[1], DImode, 0));
808 emit_move_insn (out[1], adjust_address (operands[1], DImode, 8));
3f622353
RH
809 DONE;
810 }
811
812 abort ();
813 }
814
815 if (! reload_in_progress && ! reload_completed)
816 {
817 operands[0] = spill_tfmode_operand (operands[0], 0);
818 operands[1] = spill_tfmode_operand (operands[1], 0);
819
820 if (! ia64_move_ok (operands[0], operands[1]))
821 operands[1] = force_reg (TFmode, operands[1]);
822 }
1d5d7a21 823})
e5bde68a 824
3b572406 825;; ??? There's no easy way to mind volatile acquire/release semantics.
75cdbeb8 826
3f622353
RH
827(define_insn "*movtf_internal"
828 [(set (match_operand:TF 0 "destination_tfmode_operand" "=f,f, m")
829 (match_operand:TF 1 "general_tfmode_operand" "fG,m,fG"))]
23c108af 830 "INTEL_EXTENDED_IEEE_FORMAT && ia64_move_ok (operands[0], operands[1])"
e5bde68a 831 "@
1d5d7a21
RH
832 mov %0 = %F1
833 ldfe %0 = %1%P1
834 stfe %0 = %F1%P0"
52e12ad0 835 [(set_attr "itanium_class" "fmisc,fld,stf")])
c65ebc55
JW
836\f
837;; ::::::::::::::::::::
838;; ::
839;; :: Conversions
840;; ::
841;; ::::::::::::::::::::
842
843;; Signed conversions from a smaller integer to a larger integer
844
845(define_insn "extendqidi2"
0551c32d
RH
846 [(set (match_operand:DI 0 "gr_register_operand" "=r")
847 (sign_extend:DI (match_operand:QI 1 "gr_register_operand" "r")))]
c65ebc55
JW
848 ""
849 "sxt1 %0 = %1"
52e12ad0 850 [(set_attr "itanium_class" "xtd")])
c65ebc55
JW
851
852(define_insn "extendhidi2"
0551c32d
RH
853 [(set (match_operand:DI 0 "gr_register_operand" "=r")
854 (sign_extend:DI (match_operand:HI 1 "gr_register_operand" "r")))]
c65ebc55
JW
855 ""
856 "sxt2 %0 = %1"
52e12ad0 857 [(set_attr "itanium_class" "xtd")])
c65ebc55
JW
858
859(define_insn "extendsidi2"
655f2eb9
RH
860 [(set (match_operand:DI 0 "grfr_register_operand" "=r,?f")
861 (sign_extend:DI (match_operand:SI 1 "grfr_register_operand" "r,f")))]
c65ebc55
JW
862 ""
863 "@
864 sxt4 %0 = %1
aebf2462 865 fsxt.r %0 = %1, %1"
52e12ad0 866 [(set_attr "itanium_class" "xtd,fmisc")])
c65ebc55
JW
867
868;; Unsigned conversions from a smaller integer to a larger integer
869
870(define_insn "zero_extendqidi2"
0551c32d
RH
871 [(set (match_operand:DI 0 "gr_register_operand" "=r,r")
872 (zero_extend:DI (match_operand:QI 1 "gr_nonimmediate_operand" "r,m")))]
c65ebc55
JW
873 ""
874 "@
875 zxt1 %0 = %1
876 ld1%O1 %0 = %1%P1"
52e12ad0 877 [(set_attr "itanium_class" "xtd,ld")])
c65ebc55
JW
878
879(define_insn "zero_extendhidi2"
0551c32d
RH
880 [(set (match_operand:DI 0 "gr_register_operand" "=r,r")
881 (zero_extend:DI (match_operand:HI 1 "gr_nonimmediate_operand" "r,m")))]
c65ebc55
JW
882 ""
883 "@
884 zxt2 %0 = %1
885 ld2%O1 %0 = %1%P1"
52e12ad0 886 [(set_attr "itanium_class" "xtd,ld")])
c65ebc55
JW
887
888(define_insn "zero_extendsidi2"
655f2eb9 889 [(set (match_operand:DI 0 "grfr_register_operand" "=r,r,?f")
0551c32d 890 (zero_extend:DI
655f2eb9 891 (match_operand:SI 1 "grfr_nonimmediate_operand" "r,m,f")))]
c65ebc55
JW
892 ""
893 "@
894 zxt4 %0 = %1
895 ld4%O1 %0 = %1%P1
aebf2462 896 fmix.r %0 = f0, %1"
52e12ad0 897 [(set_attr "itanium_class" "xtd,ld,fmisc")])
c65ebc55
JW
898
899;; Convert between floating point types of different sizes.
900
640cea5f
JW
901;; At first glance, it would appear that emitting fnorm for an extending
902;; conversion is unnecessary. However, the stf and getf instructions work
903;; correctly only if the input is properly rounded for its type. In
904;; particular, we get the wrong result for getf.d/stfd if the input is a
905;; denorm single. Since we don't know what the next instruction will be, we
906;; have to emit an fnorm.
907
e8e20f18
RH
908;; ??? Optimization opportunity here. Get rid of the insn altogether
909;; when we can. Should probably use a scheme like has been proposed
910;; for ia32 in dealing with operands that match unary operators. This
640cea5f
JW
911;; would let combine merge the thing into adjacent insns. See also how the
912;; mips port handles SIGN_EXTEND as operands to integer arithmetic insns via
913;; se_register_operand.
c65ebc55 914
640cea5f
JW
915(define_insn "extendsfdf2"
916 [(set (match_operand:DF 0 "fr_register_operand" "=f")
917 (float_extend:DF (match_operand:SF 1 "fr_register_operand" "f")))]
c65ebc55 918 ""
640cea5f
JW
919 "fnorm.d %0 = %1"
920 [(set_attr "itanium_class" "fmac")])
c65ebc55 921
640cea5f
JW
922(define_insn "extendsftf2"
923 [(set (match_operand:TF 0 "fr_register_operand" "=f")
924 (float_extend:TF (match_operand:SF 1 "fr_register_operand" "f")))]
23c108af 925 "INTEL_EXTENDED_IEEE_FORMAT"
640cea5f
JW
926 "fnorm %0 = %1"
927 [(set_attr "itanium_class" "fmac")])
3f622353 928
640cea5f
JW
929(define_insn "extenddftf2"
930 [(set (match_operand:TF 0 "fr_register_operand" "=f")
931 (float_extend:TF (match_operand:DF 1 "fr_register_operand" "f")))]
23c108af 932 "INTEL_EXTENDED_IEEE_FORMAT"
640cea5f
JW
933 "fnorm %0 = %1"
934 [(set_attr "itanium_class" "fmac")])
3f622353 935
c65ebc55 936(define_insn "truncdfsf2"
0551c32d
RH
937 [(set (match_operand:SF 0 "fr_register_operand" "=f")
938 (float_truncate:SF (match_operand:DF 1 "fr_register_operand" "f")))]
c65ebc55 939 ""
aebf2462 940 "fnorm.s %0 = %1"
52e12ad0 941 [(set_attr "itanium_class" "fmac")])
c65ebc55 942
3f622353 943(define_insn "trunctfsf2"
0551c32d
RH
944 [(set (match_operand:SF 0 "fr_register_operand" "=f")
945 (float_truncate:SF (match_operand:TF 1 "fr_register_operand" "f")))]
23c108af 946 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 947 "fnorm.s %0 = %1"
52e12ad0 948 [(set_attr "itanium_class" "fmac")])
c65ebc55 949
3f622353 950(define_insn "trunctfdf2"
0551c32d
RH
951 [(set (match_operand:DF 0 "fr_register_operand" "=f")
952 (float_truncate:DF (match_operand:TF 1 "fr_register_operand" "f")))]
23c108af 953 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 954 "fnorm.d %0 = %1"
52e12ad0 955 [(set_attr "itanium_class" "fmac")])
e5bde68a
RH
956
957;; Convert between signed integer types and floating point.
958
3f622353 959(define_insn "floatditf2"
0551c32d
RH
960 [(set (match_operand:TF 0 "fr_register_operand" "=f")
961 (float:TF (match_operand:DI 1 "fr_register_operand" "f")))]
23c108af 962 "INTEL_EXTENDED_IEEE_FORMAT"
e5bde68a 963 "fcvt.xf %0 = %1"
52e12ad0 964 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55 965
23c108af
SE
966;; ??? Suboptimal. This should be split somehow.
967(define_insn "floatdidf2"
968 [(set (match_operand:DF 0 "register_operand" "=f")
969 (float:DF (match_operand:DI 1 "register_operand" "f")))]
970 "!INTEL_EXTENDED_IEEE_FORMAT"
582d11e6 971 "fcvt.xf %0 = %1\;;;\;%,fnorm.d %0 = %0"
23c108af
SE
972 [(set_attr "itanium_class" "fcvtfx")])
973
974;; ??? Suboptimal. This should be split somehow.
975(define_insn "floatdisf2"
976 [(set (match_operand:SF 0 "register_operand" "=f")
977 (float:SF (match_operand:DI 1 "register_operand" "f")))]
978 "!INTEL_EXTENDED_IEEE_FORMAT"
582d11e6 979 "fcvt.xf %0 = %1\;;;\;%,fnorm.s %0 = %0"
23c108af
SE
980 [(set_attr "itanium_class" "fcvtfx")])
981
c65ebc55 982(define_insn "fix_truncsfdi2"
0551c32d
RH
983 [(set (match_operand:DI 0 "fr_register_operand" "=f")
984 (fix:DI (match_operand:SF 1 "fr_register_operand" "f")))]
c65ebc55 985 ""
aebf2462 986 "fcvt.fx.trunc %0 = %1"
52e12ad0 987 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55
JW
988
989(define_insn "fix_truncdfdi2"
0551c32d
RH
990 [(set (match_operand:DI 0 "fr_register_operand" "=f")
991 (fix:DI (match_operand:DF 1 "fr_register_operand" "f")))]
c65ebc55 992 ""
aebf2462 993 "fcvt.fx.trunc %0 = %1"
52e12ad0 994 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55 995
3f622353 996(define_insn "fix_trunctfdi2"
0551c32d
RH
997 [(set (match_operand:DI 0 "fr_register_operand" "=f")
998 (fix:DI (match_operand:TF 1 "fr_register_operand" "f")))]
23c108af 999 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 1000 "fcvt.fx.trunc %0 = %1"
52e12ad0 1001 [(set_attr "itanium_class" "fcvtfx")])
3f622353 1002
655f2eb9
RH
1003(define_insn "fix_trunctfdi2_alts"
1004 [(set (match_operand:DI 0 "fr_register_operand" "=f")
1005 (fix:DI (match_operand:TF 1 "fr_register_operand" "f")))
1006 (use (match_operand:SI 2 "const_int_operand" ""))]
23c108af 1007 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 1008 "fcvt.fx.trunc.s%2 %0 = %1"
52e12ad0 1009 [(set_attr "itanium_class" "fcvtfx")])
655f2eb9 1010
c65ebc55
JW
1011;; Convert between unsigned integer types and floating point.
1012
1013(define_insn "floatunsdisf2"
0551c32d
RH
1014 [(set (match_operand:SF 0 "fr_register_operand" "=f")
1015 (unsigned_float:SF (match_operand:DI 1 "fr_register_operand" "f")))]
c65ebc55 1016 ""
aebf2462 1017 "fcvt.xuf.s %0 = %1"
52e12ad0 1018 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55
JW
1019
1020(define_insn "floatunsdidf2"
0551c32d
RH
1021 [(set (match_operand:DF 0 "fr_register_operand" "=f")
1022 (unsigned_float:DF (match_operand:DI 1 "fr_register_operand" "f")))]
c65ebc55 1023 ""
aebf2462 1024 "fcvt.xuf.d %0 = %1"
52e12ad0 1025 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55 1026
3f622353 1027(define_insn "floatunsditf2"
0551c32d
RH
1028 [(set (match_operand:TF 0 "fr_register_operand" "=f")
1029 (unsigned_float:TF (match_operand:DI 1 "fr_register_operand" "f")))]
23c108af 1030 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 1031 "fcvt.xuf %0 = %1"
52e12ad0 1032 [(set_attr "itanium_class" "fcvtfx")])
3f622353 1033
c65ebc55 1034(define_insn "fixuns_truncsfdi2"
0551c32d
RH
1035 [(set (match_operand:DI 0 "fr_register_operand" "=f")
1036 (unsigned_fix:DI (match_operand:SF 1 "fr_register_operand" "f")))]
c65ebc55 1037 ""
aebf2462 1038 "fcvt.fxu.trunc %0 = %1"
52e12ad0 1039 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55
JW
1040
1041(define_insn "fixuns_truncdfdi2"
0551c32d
RH
1042 [(set (match_operand:DI 0 "fr_register_operand" "=f")
1043 (unsigned_fix:DI (match_operand:DF 1 "fr_register_operand" "f")))]
c65ebc55 1044 ""
aebf2462 1045 "fcvt.fxu.trunc %0 = %1"
52e12ad0 1046 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55 1047
3f622353 1048(define_insn "fixuns_trunctfdi2"
0551c32d
RH
1049 [(set (match_operand:DI 0 "fr_register_operand" "=f")
1050 (unsigned_fix:DI (match_operand:TF 1 "fr_register_operand" "f")))]
23c108af 1051 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 1052 "fcvt.fxu.trunc %0 = %1"
52e12ad0 1053 [(set_attr "itanium_class" "fcvtfx")])
655f2eb9
RH
1054
1055(define_insn "fixuns_trunctfdi2_alts"
1056 [(set (match_operand:DI 0 "fr_register_operand" "=f")
1057 (unsigned_fix:DI (match_operand:TF 1 "fr_register_operand" "f")))
1058 (use (match_operand:SI 2 "const_int_operand" ""))]
23c108af 1059 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 1060 "fcvt.fxu.trunc.s%2 %0 = %1"
52e12ad0 1061 [(set_attr "itanium_class" "fcvtfx")])
c65ebc55
JW
1062\f
1063;; ::::::::::::::::::::
1064;; ::
1065;; :: Bit field extraction
1066;; ::
1067;; ::::::::::::::::::::
1068
c65ebc55 1069(define_insn "extv"
0551c32d
RH
1070 [(set (match_operand:DI 0 "gr_register_operand" "=r")
1071 (sign_extract:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
1072 (match_operand:DI 2 "const_int_operand" "n")
1073 (match_operand:DI 3 "const_int_operand" "n")))]
1074 ""
1075 "extr %0 = %1, %3, %2"
52e12ad0 1076 [(set_attr "itanium_class" "ishf")])
c65ebc55
JW
1077
1078(define_insn "extzv"
0551c32d
RH
1079 [(set (match_operand:DI 0 "gr_register_operand" "=r")
1080 (zero_extract:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
1081 (match_operand:DI 2 "const_int_operand" "n")
1082 (match_operand:DI 3 "const_int_operand" "n")))]
1083 ""
1084 "extr.u %0 = %1, %3, %2"
52e12ad0 1085 [(set_attr "itanium_class" "ishf")])
c65ebc55
JW
1086
1087;; Insert a bit field.
1088;; Can have 3 operands, source1 (inserter), source2 (insertee), dest.
1089;; Source1 can be 0 or -1.
1090;; Source2 can be 0.
1091
1092;; ??? Actual dep instruction is more powerful than what these insv
1093;; patterns support. Unfortunately, combine is unable to create patterns
1094;; where source2 != dest.
1095
1096(define_expand "insv"
0551c32d 1097 [(set (zero_extract:DI (match_operand:DI 0 "gr_register_operand" "")
c65ebc55
JW
1098 (match_operand:DI 1 "const_int_operand" "")
1099 (match_operand:DI 2 "const_int_operand" ""))
1100 (match_operand:DI 3 "nonmemory_operand" ""))]
1101 ""
c65ebc55
JW
1102{
1103 int width = INTVAL (operands[1]);
1104 int shift = INTVAL (operands[2]);
1105
1106 /* If operand[3] is a constant, and isn't 0 or -1, then load it into a
1107 pseudo. */
1108 if (! register_operand (operands[3], DImode)
1109 && operands[3] != const0_rtx && operands[3] != constm1_rtx)
1110 operands[3] = force_reg (DImode, operands[3]);
1111
1112 /* If this is a single dep instruction, we have nothing to do. */
1113 if (! ((register_operand (operands[3], DImode) && width <= 16)
1114 || operands[3] == const0_rtx || operands[3] == constm1_rtx))
1115 {
1116 /* Check for cases that can be implemented with a mix instruction. */
1117 if (width == 32 && shift == 0)
1118 {
1119 /* Directly generating the mix4left instruction confuses
1120 optimize_bit_field in function.c. Since this is performing
1121 a useful optimization, we defer generation of the complicated
1122 mix4left RTL to the first splitting phase. */
1123 rtx tmp = gen_reg_rtx (DImode);
1124 emit_insn (gen_shift_mix4left (operands[0], operands[3], tmp));
1125 DONE;
1126 }
1127 else if (width == 32 && shift == 32)
1128 {
1129 emit_insn (gen_mix4right (operands[0], operands[3]));
1130 DONE;
1131 }
1132
d2ba6dcf
JW
1133 /* We could handle remaining cases by emitting multiple dep
1134 instructions.
1135
1136 If we need more than two dep instructions then we lose. A 6
1137 insn sequence mov mask1,mov mask2,shl;;and,and;;or is better than
1138 mov;;dep,shr;;dep,shr;;dep. The former can be executed in 3 cycles,
1139 the latter is 6 cycles on an Itanium (TM) processor, because there is
1140 only one function unit that can execute dep and shr immed.
1141
1142 If we only need two dep instruction, then we still lose.
1143 mov;;dep,shr;;dep is still 4 cycles. Even if we optimize away
1144 the unnecessary mov, this is still undesirable because it will be
1145 hard to optimize, and it creates unnecessary pressure on the I0
1146 function unit. */
1147
c65ebc55
JW
1148 FAIL;
1149
1150#if 0
1151 /* This code may be useful for other IA-64 processors, so we leave it in
1152 for now. */
1153 while (width > 16)
1154 {
1155 rtx tmp;
1156
1157 emit_insn (gen_insv (operands[0], GEN_INT (16), GEN_INT (shift),
1158 operands[3]));
1159 shift += 16;
1160 width -= 16;
1161 tmp = gen_reg_rtx (DImode);
1162 emit_insn (gen_lshrdi3 (tmp, operands[3], GEN_INT (16)));
1163 operands[3] = tmp;
1164 }
1165 operands[1] = GEN_INT (width);
1166 operands[2] = GEN_INT (shift);
1167#endif
1168 }
1d5d7a21 1169})
c65ebc55
JW
1170
1171(define_insn "*insv_internal"
0551c32d 1172 [(set (zero_extract:DI (match_operand:DI 0 "gr_register_operand" "+r")
c65ebc55
JW
1173 (match_operand:DI 1 "const_int_operand" "n")
1174 (match_operand:DI 2 "const_int_operand" "n"))
1175 (match_operand:DI 3 "nonmemory_operand" "rP"))]
0551c32d 1176 "(gr_register_operand (operands[3], DImode) && INTVAL (operands[1]) <= 16)
c65ebc55
JW
1177 || operands[3] == const0_rtx || operands[3] == constm1_rtx"
1178 "dep %0 = %3, %0, %2, %1"
52e12ad0 1179 [(set_attr "itanium_class" "ishf")])
c65ebc55 1180
43a88a8c 1181;; Combine doesn't like to create bit-field insertions into zero.
041f25e6 1182(define_insn "*depz_internal"
0551c32d
RH
1183 [(set (match_operand:DI 0 "gr_register_operand" "=r")
1184 (and:DI (ashift:DI (match_operand:DI 1 "gr_register_operand" "r")
041f25e6
RH
1185 (match_operand:DI 2 "const_int_operand" "n"))
1186 (match_operand:DI 3 "const_int_operand" "n")))]
1187 "CONST_OK_FOR_M (INTVAL (operands[2]))
1188 && ia64_depz_field_mask (operands[3], operands[2]) > 0"
041f25e6
RH
1189{
1190 operands[3] = GEN_INT (ia64_depz_field_mask (operands[3], operands[2]));
1d5d7a21
RH
1191 return "%,dep.z %0 = %1, %2, %3";
1192}
52e12ad0 1193 [(set_attr "itanium_class" "ishf")])
041f25e6 1194
c65ebc55 1195(define_insn "shift_mix4left"
0551c32d 1196 [(set (zero_extract:DI (match_operand:DI 0 "gr_register_operand" "+r")
c65ebc55 1197 (const_int 32) (const_int 0))
0551c32d
RH
1198 (match_operand:DI 1 "gr_register_operand" "r"))
1199 (clobber (match_operand:DI 2 "gr_register_operand" "=r"))]
c65ebc55
JW
1200 ""
1201 "#"
52e12ad0 1202 [(set_attr "itanium_class" "unknown")])
c65ebc55 1203
c65ebc55
JW
1204(define_split
1205 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "")
1206 (const_int 32) (const_int 0))
1207 (match_operand:DI 1 "register_operand" ""))
1208 (clobber (match_operand:DI 2 "register_operand" ""))]
1209 "reload_completed"
1210 [(set (match_dup 3) (ashift:DI (match_dup 1) (const_int 32)))
c65ebc55
JW
1211 (set (zero_extract:DI (match_dup 0) (const_int 32) (const_int 0))
1212 (lshiftrt:DI (match_dup 3) (const_int 32)))]
1213 "operands[3] = operands[2];")
1214
1215(define_split
1216 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "")
1217 (const_int 32) (const_int 0))
1218 (match_operand:DI 1 "register_operand" ""))
1219 (clobber (match_operand:DI 2 "register_operand" ""))]
1220 "! reload_completed"
1221 [(set (match_dup 3) (ashift:DI (match_dup 1) (const_int 32)))
1222 (set (zero_extract:DI (match_dup 0) (const_int 32) (const_int 0))
1223 (lshiftrt:DI (match_dup 3) (const_int 32)))]
1224 "operands[3] = operands[2];")
1225
1226(define_insn "*mix4left"
0551c32d 1227 [(set (zero_extract:DI (match_operand:DI 0 "gr_register_operand" "+r")
c65ebc55 1228 (const_int 32) (const_int 0))
0551c32d 1229 (lshiftrt:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
1230 (const_int 32)))]
1231 ""
1232 "mix4.l %0 = %0, %r1"
52e12ad0 1233 [(set_attr "itanium_class" "mmshf")])
c65ebc55
JW
1234
1235(define_insn "mix4right"
0551c32d 1236 [(set (zero_extract:DI (match_operand:DI 0 "gr_register_operand" "+r")
c65ebc55 1237 (const_int 32) (const_int 32))
0551c32d 1238 (match_operand:DI 1 "gr_reg_or_0_operand" "rO"))]
c65ebc55
JW
1239 ""
1240 "mix4.r %0 = %r1, %0"
52e12ad0 1241 [(set_attr "itanium_class" "mmshf")])
c65ebc55
JW
1242
1243;; This is used by the rotrsi3 pattern.
1244
1245(define_insn "*mix4right_3op"
0551c32d
RH
1246 [(set (match_operand:DI 0 "gr_register_operand" "=r")
1247 (ior:DI (zero_extend:DI (match_operand:SI 1 "gr_register_operand" "r"))
1248 (ashift:DI (zero_extend:DI
1249 (match_operand:SI 2 "gr_register_operand" "r"))
c65ebc55
JW
1250 (const_int 32))))]
1251 ""
fa9a44e8 1252 "mix4.r %0 = %2, %1"
52e12ad0 1253 [(set_attr "itanium_class" "mmshf")])
c65ebc55
JW
1254
1255\f
1256;; ::::::::::::::::::::
cf1f6ae3 1257;; ::
f2f90c63
RH
1258;; :: 1 bit Integer arithmetic
1259;; ::
1260;; ::::::::::::::::::::
1261
1262(define_insn_and_split "andbi3"
1263 [(set (match_operand:BI 0 "register_operand" "=c,c,r")
1264 (and:BI (match_operand:BI 1 "register_operand" "%0,0,r")
1265 (match_operand:BI 2 "register_operand" "c,r,r")))]
1266 ""
1267 "@
1268 #
1269 tbit.nz.and.orcm %0, %I0 = %2, 0
1270 and %0 = %2, %1"
1271 "reload_completed
1272 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
1273 && GET_CODE (operands[2]) == REG && PR_REGNO_P (REGNO (operands[2]))"
1274 [(cond_exec (eq (match_dup 2) (const_int 0))
1275 (set (match_dup 0) (and:BI (ne:BI (const_int 0) (const_int 0))
1276 (match_dup 0))))]
1277 ""
52e12ad0 1278 [(set_attr "itanium_class" "unknown,tbit,ilog")])
f2f90c63
RH
1279
1280(define_insn_and_split "*andcmbi3"
1281 [(set (match_operand:BI 0 "register_operand" "=c,c,r")
1282 (and:BI (not:BI (match_operand:BI 1 "register_operand" "c,r,r"))
1283 (match_operand:BI 2 "register_operand" "0,0,r")))]
1284 ""
1285 "@
1286 #
967603ef 1287 tbit.z.and.orcm %0, %I0 = %1, 0
f2f90c63
RH
1288 andcm %0 = %2, %1"
1289 "reload_completed
1290 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
967603ef 1291 && GET_CODE (operands[1]) == REG && PR_REGNO_P (REGNO (operands[1]))"
f2f90c63
RH
1292 [(cond_exec (ne (match_dup 1) (const_int 0))
1293 (set (match_dup 0) (and:BI (ne:BI (const_int 0) (const_int 0))
1294 (match_dup 0))))]
1295 ""
52e12ad0 1296 [(set_attr "itanium_class" "unknown,tbit,ilog")])
f2f90c63
RH
1297
1298(define_insn_and_split "iorbi3"
1299 [(set (match_operand:BI 0 "register_operand" "=c,c,r")
1300 (ior:BI (match_operand:BI 1 "register_operand" "%0,0,r")
1301 (match_operand:BI 2 "register_operand" "c,r,r")))]
1302 ""
1303 "@
1304 #
1305 tbit.nz.or.andcm %0, %I0 = %2, 0
1306 or %0 = %2, %1"
1307 "reload_completed
1308 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
1309 && GET_CODE (operands[2]) == REG && PR_REGNO_P (REGNO (operands[2]))"
1310 [(cond_exec (ne (match_dup 2) (const_int 0))
1311 (set (match_dup 0) (ior:BI (eq:BI (const_int 0) (const_int 0))
1312 (match_dup 0))))]
1313 ""
52e12ad0 1314 [(set_attr "itanium_class" "unknown,tbit,ilog")])
f2f90c63
RH
1315
1316(define_insn_and_split "*iorcmbi3"
1317 [(set (match_operand:BI 0 "register_operand" "=c,c")
1318 (ior:BI (not:BI (match_operand:BI 1 "register_operand" "c,r"))
1319 (match_operand:BI 2 "register_operand" "0,0")))]
1320 ""
1321 "@
1322 #
967603ef 1323 tbit.z.or.andcm %0, %I0 = %1, 0"
f2f90c63
RH
1324 "reload_completed
1325 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
967603ef 1326 && GET_CODE (operands[1]) == REG && PR_REGNO_P (REGNO (operands[1]))"
f2f90c63
RH
1327 [(cond_exec (eq (match_dup 1) (const_int 0))
1328 (set (match_dup 0) (ior:BI (eq:BI (const_int 0) (const_int 0))
1329 (match_dup 0))))]
1330 ""
52e12ad0 1331 [(set_attr "itanium_class" "unknown,tbit")])
f2f90c63
RH
1332
1333(define_insn "one_cmplbi2"
1334 [(set (match_operand:BI 0 "register_operand" "=c,r,c,&c")
1335 (not:BI (match_operand:BI 1 "register_operand" "r,r,0,c")))
1336 (clobber (match_scratch:BI 2 "=X,X,c,X"))]
1337 ""
1338 "@
1339 tbit.z %0, %I0 = %1, 0
1340 xor %0 = 1, %1
1341 #
1342 #"
52e12ad0 1343 [(set_attr "itanium_class" "tbit,ilog,unknown,unknown")])
f2f90c63
RH
1344
1345(define_split
1346 [(set (match_operand:BI 0 "register_operand" "")
1347 (not:BI (match_operand:BI 1 "register_operand" "")))
1348 (clobber (match_scratch:BI 2 ""))]
1349 "reload_completed
1350 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
f2f90c63
RH
1351 && rtx_equal_p (operands[0], operands[1])"
1352 [(set (match_dup 4) (match_dup 3))
1353 (set (match_dup 0) (const_int 1))
1354 (cond_exec (ne (match_dup 2) (const_int 0))
1355 (set (match_dup 0) (const_int 0)))
086c0f96 1356 (set (match_dup 0) (unspec:BI [(match_dup 0)] UNSPEC_PRED_REL_MUTEX))]
f2f90c63
RH
1357 "operands[3] = gen_rtx_REG (CCImode, REGNO (operands[1]));
1358 operands[4] = gen_rtx_REG (CCImode, REGNO (operands[2]));")
1359
1360(define_split
1361 [(set (match_operand:BI 0 "register_operand" "")
1362 (not:BI (match_operand:BI 1 "register_operand" "")))
1363 (clobber (match_scratch:BI 2 ""))]
1364 "reload_completed
1365 && GET_CODE (operands[0]) == REG && PR_REGNO_P (REGNO (operands[0]))
1366 && GET_CODE (operands[1]) == REG && PR_REGNO_P (REGNO (operands[1]))
1367 && ! rtx_equal_p (operands[0], operands[1])"
1368 [(cond_exec (ne (match_dup 1) (const_int 0))
1369 (set (match_dup 0) (const_int 0)))
1370 (cond_exec (eq (match_dup 1) (const_int 0))
1371 (set (match_dup 0) (const_int 1)))
086c0f96 1372 (set (match_dup 0) (unspec:BI [(match_dup 0)] UNSPEC_PRED_REL_MUTEX))]
f2f90c63
RH
1373 "")
1374
1375(define_insn "*cmpsi_and_0"
1376 [(set (match_operand:BI 0 "register_operand" "=c")
1377 (and:BI (match_operator:BI 4 "predicate_operator"
1378 [(match_operand:SI 2 "gr_reg_or_0_operand" "rO")
1379 (match_operand:SI 3 "gr_reg_or_8bit_operand" "rK")])
1380 (match_operand:BI 1 "register_operand" "0")))]
1381 ""
1382 "cmp4.%C4.and.orcm %0, %I0 = %3, %r2"
52e12ad0 1383 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1384
1385(define_insn "*cmpsi_and_1"
1386 [(set (match_operand:BI 0 "register_operand" "=c")
1387 (and:BI (match_operator:BI 3 "signed_inequality_operator"
1388 [(match_operand:SI 2 "gr_register_operand" "r")
1389 (const_int 0)])
1390 (match_operand:BI 1 "register_operand" "0")))]
1391 ""
1392 "cmp4.%C3.and.orcm %0, %I0 = r0, %2"
52e12ad0 1393 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1394
1395(define_insn "*cmpsi_andnot_0"
1396 [(set (match_operand:BI 0 "register_operand" "=c")
1397 (and:BI (not:BI (match_operator:BI 4 "predicate_operator"
1398 [(match_operand:SI 2 "gr_reg_or_0_operand" "rO")
1399 (match_operand:SI 3 "gr_reg_or_8bit_operand" "rK")]))
1400 (match_operand:BI 1 "register_operand" "0")))]
1401 ""
1402 "cmp4.%C4.or.andcm %I0, %0 = %3, %r2"
52e12ad0 1403 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1404
1405(define_insn "*cmpsi_andnot_1"
1406 [(set (match_operand:BI 0 "register_operand" "=c")
1407 (and:BI (not:BI (match_operator:BI 3 "signed_inequality_operator"
1408 [(match_operand:SI 2 "gr_register_operand" "r")
1409 (const_int 0)]))
1410 (match_operand:BI 1 "register_operand" "0")))]
1411 ""
1412 "cmp4.%C3.or.andcm %I0, %0 = r0, %2"
52e12ad0 1413 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1414
1415(define_insn "*cmpdi_and_0"
1416 [(set (match_operand:BI 0 "register_operand" "=c")
1417 (and:BI (match_operator:BI 4 "predicate_operator"
1418 [(match_operand:DI 2 "gr_register_operand" "r")
1419 (match_operand:DI 3 "gr_reg_or_8bit_operand" "rK")])
1420 (match_operand:BI 1 "register_operand" "0")))]
1421 ""
1422 "cmp.%C4.and.orcm %0, %I0 = %3, %2"
52e12ad0 1423 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1424
1425(define_insn "*cmpdi_and_1"
1426 [(set (match_operand:BI 0 "register_operand" "=c")
1427 (and:BI (match_operator:BI 3 "signed_inequality_operator"
1428 [(match_operand:DI 2 "gr_register_operand" "r")
1429 (const_int 0)])
1430 (match_operand:BI 1 "register_operand" "0")))]
1431 ""
1432 "cmp.%C3.and.orcm %0, %I0 = r0, %2"
52e12ad0 1433 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1434
1435(define_insn "*cmpdi_andnot_0"
1436 [(set (match_operand:BI 0 "register_operand" "=c")
1437 (and:BI (not:BI (match_operator:BI 4 "predicate_operator"
1438 [(match_operand:DI 2 "gr_register_operand" "r")
1439 (match_operand:DI 3 "gr_reg_or_8bit_operand" "rK")]))
1440 (match_operand:BI 1 "register_operand" "0")))]
1441 ""
1442 "cmp.%C4.or.andcm %I0, %0 = %3, %2"
52e12ad0 1443 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1444
1445(define_insn "*cmpdi_andnot_1"
1446 [(set (match_operand:BI 0 "register_operand" "=c")
1447 (and:BI (not:BI (match_operator:BI 3 "signed_inequality_operator"
1448 [(match_operand:DI 2 "gr_register_operand" "r")
1449 (const_int 0)]))
1450 (match_operand:BI 1 "register_operand" "0")))]
1451 ""
1452 "cmp.%C3.or.andcm %I0, %0 = r0, %2"
52e12ad0 1453 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1454
1455(define_insn "*tbit_and_0"
1456 [(set (match_operand:BI 0 "register_operand" "=c")
1457 (and:BI (ne:BI (and:DI (match_operand:DI 1 "gr_register_operand" "r")
1458 (const_int 1))
1459 (const_int 0))
c77e04ae 1460 (match_operand:BI 2 "register_operand" "0")))]
f2f90c63
RH
1461 ""
1462 "tbit.nz.and.orcm %0, %I0 = %1, 0"
52e12ad0 1463 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1464
1465(define_insn "*tbit_and_1"
1466 [(set (match_operand:BI 0 "register_operand" "=c")
1467 (and:BI (eq:BI (and:DI (match_operand:DI 1 "gr_register_operand" "r")
1468 (const_int 1))
1469 (const_int 0))
c77e04ae 1470 (match_operand:BI 2 "register_operand" "0")))]
f2f90c63
RH
1471 ""
1472 "tbit.z.and.orcm %0, %I0 = %1, 0"
52e12ad0 1473 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1474
1475(define_insn "*tbit_and_2"
1476 [(set (match_operand:BI 0 "register_operand" "=c")
1477 (and:BI (ne:BI (zero_extract:DI
1478 (match_operand:DI 1 "gr_register_operand" "r")
1479 (const_int 1)
1480 (match_operand:DI 2 "const_int_operand" "n"))
1481 (const_int 0))
1482 (match_operand:BI 3 "register_operand" "0")))]
1483 ""
1484 "tbit.nz.and.orcm %0, %I0 = %1, %2"
52e12ad0 1485 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1486
1487(define_insn "*tbit_and_3"
1488 [(set (match_operand:BI 0 "register_operand" "=c")
1489 (and:BI (eq:BI (zero_extract:DI
1490 (match_operand:DI 1 "gr_register_operand" "r")
1491 (const_int 1)
1492 (match_operand:DI 2 "const_int_operand" "n"))
1493 (const_int 0))
1494 (match_operand:BI 3 "register_operand" "0")))]
1495 ""
1496 "tbit.z.and.orcm %0, %I0 = %1, %2"
52e12ad0 1497 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1498
1499(define_insn "*cmpsi_or_0"
1500 [(set (match_operand:BI 0 "register_operand" "=c")
1501 (ior:BI (match_operator:BI 4 "predicate_operator"
1502 [(match_operand:SI 2 "gr_reg_or_0_operand" "rO")
1503 (match_operand:SI 3 "gr_reg_or_8bit_operand" "rK")])
1504 (match_operand:BI 1 "register_operand" "0")))]
1505 ""
1506 "cmp4.%C4.or.andcm %0, %I0 = %3, %r2"
52e12ad0 1507 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1508
1509(define_insn "*cmpsi_or_1"
1510 [(set (match_operand:BI 0 "register_operand" "=c")
1511 (ior:BI (match_operator:BI 3 "signed_inequality_operator"
1512 [(match_operand:SI 2 "gr_register_operand" "r")
1513 (const_int 0)])
1514 (match_operand:BI 1 "register_operand" "0")))]
1515 ""
1516 "cmp4.%C3.or.andcm %0, %I0 = r0, %2"
52e12ad0 1517 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1518
1519(define_insn "*cmpsi_orcm_0"
1520 [(set (match_operand:BI 0 "register_operand" "=c")
1521 (ior:BI (not:BI (match_operator:BI 4 "predicate_operator"
1522 [(match_operand:SI 2 "gr_reg_or_0_operand" "rO")
1523 (match_operand:SI 3 "gr_reg_or_8bit_operand" "rK")]))
1524 (match_operand:BI 1 "register_operand" "0")))]
1525 ""
1526 "cmp4.%C4.and.orcm %I0, %0 = %3, %r2"
52e12ad0 1527 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1528
1529(define_insn "*cmpsi_orcm_1"
1530 [(set (match_operand:BI 0 "register_operand" "=c")
1531 (ior:BI (not:BI (match_operator:BI 3 "signed_inequality_operator"
1532 [(match_operand:SI 2 "gr_register_operand" "r")
1533 (const_int 0)]))
1534 (match_operand:BI 1 "register_operand" "0")))]
1535 ""
1536 "cmp4.%C3.and.orcm %I0, %0 = r0, %2"
52e12ad0 1537 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1538
1539(define_insn "*cmpdi_or_0"
1540 [(set (match_operand:BI 0 "register_operand" "=c")
1541 (ior:BI (match_operator:BI 4 "predicate_operator"
1542 [(match_operand:DI 2 "gr_register_operand" "r")
1543 (match_operand:DI 3 "gr_reg_or_8bit_operand" "rK")])
1544 (match_operand:BI 1 "register_operand" "0")))]
1545 ""
1546 "cmp.%C4.or.andcm %0, %I0 = %3, %2"
52e12ad0 1547 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1548
1549(define_insn "*cmpdi_or_1"
1550 [(set (match_operand:BI 0 "register_operand" "=c")
1551 (ior:BI (match_operator:BI 3 "signed_inequality_operator"
1552 [(match_operand:DI 2 "gr_register_operand" "r")
1553 (const_int 0)])
1554 (match_operand:BI 1 "register_operand" "0")))]
1555 ""
1556 "cmp.%C3.or.andcm %0, %I0 = r0, %2"
52e12ad0 1557 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1558
1559(define_insn "*cmpdi_orcm_0"
1560 [(set (match_operand:BI 0 "register_operand" "=c")
1561 (ior:BI (not:BI (match_operator:BI 4 "predicate_operator"
1562 [(match_operand:DI 2 "gr_register_operand" "r")
1563 (match_operand:DI 3 "gr_reg_or_8bit_operand" "rK")]))
1564 (match_operand:BI 1 "register_operand" "0")))]
1565 ""
1566 "cmp.%C4.and.orcm %I0, %0 = %3, %2"
52e12ad0 1567 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1568
1569(define_insn "*cmpdi_orcm_1"
1570 [(set (match_operand:BI 0 "register_operand" "=c")
1571 (ior:BI (not:BI (match_operator:BI 3 "signed_inequality_operator"
1572 [(match_operand:DI 2 "gr_register_operand" "r")
1573 (const_int 0)]))
1574 (match_operand:BI 1 "register_operand" "0")))]
1575 ""
1576 "cmp.%C3.and.orcm %I0, %0 = r0, %2"
52e12ad0 1577 [(set_attr "itanium_class" "icmp")])
f2f90c63
RH
1578
1579(define_insn "*tbit_or_0"
1580 [(set (match_operand:BI 0 "register_operand" "=c")
1581 (ior:BI (ne:BI (and:DI (match_operand:DI 1 "gr_register_operand" "r")
1582 (const_int 1))
1583 (const_int 0))
c77e04ae 1584 (match_operand:BI 2 "register_operand" "0")))]
f2f90c63
RH
1585 ""
1586 "tbit.nz.or.andcm %0, %I0 = %1, 0"
52e12ad0 1587 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1588
1589(define_insn "*tbit_or_1"
1590 [(set (match_operand:BI 0 "register_operand" "=c")
1591 (ior:BI (eq:BI (and:DI (match_operand:DI 1 "gr_register_operand" "r")
1592 (const_int 1))
1593 (const_int 0))
c77e04ae 1594 (match_operand:BI 2 "register_operand" "0")))]
f2f90c63
RH
1595 ""
1596 "tbit.z.or.andcm %0, %I0 = %1, 0"
52e12ad0 1597 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1598
1599(define_insn "*tbit_or_2"
1600 [(set (match_operand:BI 0 "register_operand" "=c")
1601 (ior:BI (ne:BI (zero_extract:DI
1602 (match_operand:DI 1 "gr_register_operand" "r")
1603 (const_int 1)
1604 (match_operand:DI 2 "const_int_operand" "n"))
1605 (const_int 0))
1606 (match_operand:BI 3 "register_operand" "0")))]
1607 ""
1608 "tbit.nz.or.andcm %0, %I0 = %1, %2"
52e12ad0 1609 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1610
1611(define_insn "*tbit_or_3"
1612 [(set (match_operand:BI 0 "register_operand" "=c")
1613 (ior:BI (eq:BI (zero_extract:DI
1614 (match_operand:DI 1 "gr_register_operand" "r")
1615 (const_int 1)
1616 (match_operand:DI 2 "const_int_operand" "n"))
1617 (const_int 0))
1618 (match_operand:BI 3 "register_operand" "0")))]
1619 ""
1620 "tbit.z.or.andcm %0, %I0 = %1, %2"
52e12ad0 1621 [(set_attr "itanium_class" "tbit")])
f2f90c63
RH
1622
1623;; Transform test of and/or of setcc into parallel comparisons.
1624
1625(define_split
1626 [(set (match_operand:BI 0 "register_operand" "")
1627 (ne:BI (and:DI (ne:DI (match_operand:BI 2 "register_operand" "")
1628 (const_int 0))
1629 (match_operand:DI 3 "register_operand" ""))
1630 (const_int 0)))]
1631 ""
1632 [(set (match_dup 0)
1633 (and:BI (ne:BI (and:DI (match_dup 3) (const_int 1)) (const_int 0))
1634 (match_dup 2)))]
1635 "")
1636
1637(define_split
1638 [(set (match_operand:BI 0 "register_operand" "")
1639 (eq:BI (and:DI (ne:DI (match_operand:BI 2 "register_operand" "")
1640 (const_int 0))
1641 (match_operand:DI 3 "register_operand" ""))
1642 (const_int 0)))]
1643 ""
1644 [(set (match_dup 0)
1645 (and:BI (ne:BI (and:DI (match_dup 3) (const_int 1)) (const_int 0))
1646 (match_dup 2)))
1647 (parallel [(set (match_dup 0) (not:BI (match_dup 0)))
1648 (clobber (scratch))])]
1649 "")
1650
1651(define_split
1652 [(set (match_operand:BI 0 "register_operand" "")
1653 (ne:BI (ior:DI (ne:DI (match_operand:BI 2 "register_operand" "")
1654 (const_int 0))
1655 (match_operand:DI 3 "register_operand" ""))
1656 (const_int 0)))]
1657 ""
1658 [(set (match_dup 0)
1659 (ior:BI (ne:BI (match_dup 3) (const_int 0))
1660 (match_dup 2)))]
1661 "")
1662
1663(define_split
1664 [(set (match_operand:BI 0 "register_operand" "")
1665 (eq:BI (ior:DI (ne:DI (match_operand:BI 2 "register_operand" "")
1666 (const_int 0))
1667 (match_operand:DI 3 "register_operand" ""))
1668 (const_int 0)))]
1669 ""
1670 [(set (match_dup 0)
1671 (ior:BI (ne:BI (match_dup 3) (const_int 0))
1672 (match_dup 2)))
1673 (parallel [(set (match_dup 0) (not:BI (match_dup 0)))
1674 (clobber (scratch))])]
1675 "")
1676
1677;; ??? Incredibly hackish. Either need four proper patterns with all
1678;; the alternatives, or rely on sched1 to split the insn and hope that
1679;; nothing bad happens to the comparisons in the meantime.
1680;;
1681;; Alternately, adjust combine to allow 2->2 and 3->3 splits, assuming
1682;; that we're doing height reduction.
1683;
1684;(define_insn_and_split ""
1685; [(set (match_operand:BI 0 "register_operand" "=c")
1686; (and:BI (and:BI (match_operator:BI 1 "comparison_operator"
1687; [(match_operand 2 "" "")
1688; (match_operand 3 "" "")])
1689; (match_operator:BI 4 "comparison_operator"
1690; [(match_operand 5 "" "")
1691; (match_operand 6 "" "")]))
1692; (match_dup 0)))]
1693; "flag_schedule_insns"
1694; "#"
1695; ""
1696; [(set (match_dup 0) (and:BI (match_dup 1) (match_dup 0)))
1697; (set (match_dup 0) (and:BI (match_dup 4) (match_dup 0)))]
1698; "")
1699;
1700;(define_insn_and_split ""
1701; [(set (match_operand:BI 0 "register_operand" "=c")
1702; (ior:BI (ior:BI (match_operator:BI 1 "comparison_operator"
1703; [(match_operand 2 "" "")
1704; (match_operand 3 "" "")])
1705; (match_operator:BI 4 "comparison_operator"
1706; [(match_operand 5 "" "")
1707; (match_operand 6 "" "")]))
1708; (match_dup 0)))]
1709; "flag_schedule_insns"
1710; "#"
1711; ""
1712; [(set (match_dup 0) (ior:BI (match_dup 1) (match_dup 0)))
1713; (set (match_dup 0) (ior:BI (match_dup 4) (match_dup 0)))]
1714; "")
1715;
1716;(define_split
1717; [(set (match_operand:BI 0 "register_operand" "")
1718; (and:BI (and:BI (match_operator:BI 1 "comparison_operator"
1719; [(match_operand 2 "" "")
1720; (match_operand 3 "" "")])
1721; (match_operand:BI 7 "register_operand" ""))
1722; (and:BI (match_operator:BI 4 "comparison_operator"
1723; [(match_operand 5 "" "")
1724; (match_operand 6 "" "")])
1725; (match_operand:BI 8 "register_operand" ""))))]
1726; ""
1727; [(set (match_dup 0) (and:BI (match_dup 7) (match_dup 8)))
1728; (set (match_dup 0) (and:BI (and:BI (match_dup 1) (match_dup 4))
1729; (match_dup 0)))]
1730; "")
1731;
1732;(define_split
1733; [(set (match_operand:BI 0 "register_operand" "")
1734; (ior:BI (ior:BI (match_operator:BI 1 "comparison_operator"
1735; [(match_operand 2 "" "")
1736; (match_operand 3 "" "")])
1737; (match_operand:BI 7 "register_operand" ""))
1738; (ior:BI (match_operator:BI 4 "comparison_operator"
1739; [(match_operand 5 "" "")
1740; (match_operand 6 "" "")])
1741; (match_operand:BI 8 "register_operand" ""))))]
1742; ""
1743; [(set (match_dup 0) (ior:BI (match_dup 7) (match_dup 8)))
1744; (set (match_dup 0) (ior:BI (ior:BI (match_dup 1) (match_dup 4))
1745; (match_dup 0)))]
1746; "")
1747
1748;; Try harder to avoid predicate copies by duplicating compares.
1749;; Note that we'll have already split the predicate copy, which
1750;; is kind of a pain, but oh well.
1751
1752(define_peephole2
1753 [(set (match_operand:BI 0 "register_operand" "")
1754 (match_operand:BI 1 "comparison_operator" ""))
1755 (set (match_operand:CCI 2 "register_operand" "")
1756 (match_operand:CCI 3 "register_operand" ""))
1757 (set (match_operand:CCI 4 "register_operand" "")
1758 (match_operand:CCI 5 "register_operand" ""))
1759 (set (match_operand:BI 6 "register_operand" "")
086c0f96 1760 (unspec:BI [(match_dup 6)] UNSPEC_PRED_REL_MUTEX))]
f2f90c63
RH
1761 "REGNO (operands[3]) == REGNO (operands[0])
1762 && REGNO (operands[4]) == REGNO (operands[0]) + 1
1763 && REGNO (operands[4]) == REGNO (operands[2]) + 1
1764 && REGNO (operands[6]) == REGNO (operands[2])"
1765 [(set (match_dup 0) (match_dup 1))
1766 (set (match_dup 6) (match_dup 7))]
1767 "operands[7] = copy_rtx (operands[1]);")
1768\f
1769;; ::::::::::::::::::::
1770;; ::
cf1f6ae3
RH
1771;; :: 16 bit Integer arithmetic
1772;; ::
1773;; ::::::::::::::::::::
1774
1775(define_insn "mulhi3"
1776 [(set (match_operand:HI 0 "gr_register_operand" "=r")
1777 (mult:HI (match_operand:HI 1 "gr_register_operand" "r")
1778 (match_operand:HI 2 "gr_register_operand" "r")))]
1779 ""
2a7ffc85 1780 "pmpy2.r %0 = %1, %2"
52e12ad0 1781 [(set_attr "itanium_class" "mmmul")])
cf1f6ae3
RH
1782
1783\f
1784;; ::::::::::::::::::::
c65ebc55
JW
1785;; ::
1786;; :: 32 bit Integer arithmetic
1787;; ::
1788;; ::::::::::::::::::::
1789
058557c4 1790(define_insn "addsi3"
0551c32d
RH
1791 [(set (match_operand:SI 0 "gr_register_operand" "=r,r,r")
1792 (plus:SI (match_operand:SI 1 "gr_register_operand" "%r,r,a")
1793 (match_operand:SI 2 "gr_reg_or_22bit_operand" "r,I,J")))]
c65ebc55
JW
1794 ""
1795 "@
1d5d7a21
RH
1796 add %0 = %1, %2
1797 adds %0 = %2, %1
1798 addl %0 = %2, %1"
52e12ad0 1799 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
1800
1801(define_insn "*addsi3_plus1"
0551c32d
RH
1802 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1803 (plus:SI (plus:SI (match_operand:SI 1 "gr_register_operand" "r")
1804 (match_operand:SI 2 "gr_register_operand" "r"))
c65ebc55
JW
1805 (const_int 1)))]
1806 ""
1807 "add %0 = %1, %2, 1"
52e12ad0 1808 [(set_attr "itanium_class" "ialu")])
c65ebc55 1809
5527bf14 1810(define_insn "*addsi3_plus1_alt"
0551c32d
RH
1811 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1812 (plus:SI (mult:SI (match_operand:SI 1 "gr_register_operand" "r")
5527bf14
RH
1813 (const_int 2))
1814 (const_int 1)))]
1815 ""
1816 "add %0 = %1, %1, 1"
52e12ad0 1817 [(set_attr "itanium_class" "ialu")])
5527bf14 1818
058557c4 1819(define_insn "*addsi3_shladd"
0551c32d
RH
1820 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1821 (plus:SI (mult:SI (match_operand:SI 1 "gr_register_operand" "r")
058557c4 1822 (match_operand:SI 2 "shladd_operand" "n"))
0551c32d 1823 (match_operand:SI 3 "gr_register_operand" "r")))]
c65ebc55 1824 ""
058557c4 1825 "shladd %0 = %1, %S2, %3"
52e12ad0 1826 [(set_attr "itanium_class" "ialu")])
c65ebc55 1827
058557c4 1828(define_insn "subsi3"
0551c32d
RH
1829 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1830 (minus:SI (match_operand:SI 1 "gr_reg_or_8bit_operand" "rK")
1831 (match_operand:SI 2 "gr_register_operand" "r")))]
c65ebc55
JW
1832 ""
1833 "sub %0 = %1, %2"
52e12ad0 1834 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
1835
1836(define_insn "*subsi3_minus1"
0551c32d
RH
1837 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1838 (plus:SI (not:SI (match_operand:SI 1 "gr_register_operand" "r"))
1839 (match_operand:SI 2 "gr_register_operand" "r")))]
c65ebc55
JW
1840 ""
1841 "sub %0 = %2, %1, 1"
52e12ad0
BS
1842 [(set_attr "itanium_class" "ialu")])
1843
1844;; ??? Could add maddsi3 patterns patterned after the madddi3 patterns.
c65ebc55 1845
058557c4 1846(define_insn "mulsi3"
0551c32d 1847 [(set (match_operand:SI 0 "fr_register_operand" "=f")
11a13704
RH
1848 (mult:SI (match_operand:SI 1 "grfr_register_operand" "f")
1849 (match_operand:SI 2 "grfr_register_operand" "f")))]
c65ebc55 1850 ""
aebf2462 1851 "xmpy.l %0 = %1, %2"
52e12ad0 1852 [(set_attr "itanium_class" "xmpy")])
c65ebc55 1853
655f2eb9 1854(define_insn "maddsi4"
11a13704
RH
1855 [(set (match_operand:SI 0 "fr_register_operand" "=f")
1856 (plus:SI (mult:SI (match_operand:SI 1 "grfr_register_operand" "f")
1857 (match_operand:SI 2 "grfr_register_operand" "f"))
1858 (match_operand:SI 3 "grfr_register_operand" "f")))]
1859 ""
aebf2462 1860 "xma.l %0 = %1, %2, %3"
52e12ad0 1861 [(set_attr "itanium_class" "xmpy")])
11a13704 1862
058557c4 1863(define_insn "negsi2"
0551c32d
RH
1864 [(set (match_operand:SI 0 "gr_register_operand" "=r")
1865 (neg:SI (match_operand:SI 1 "gr_register_operand" "r")))]
c65ebc55
JW
1866 ""
1867 "sub %0 = r0, %1"
52e12ad0 1868 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
1869
1870(define_expand "abssi2"
1871 [(set (match_dup 2)
f2f90c63 1872 (ge:BI (match_operand:SI 1 "gr_register_operand" "") (const_int 0)))
0551c32d 1873 (set (match_operand:SI 0 "gr_register_operand" "")
f2f90c63 1874 (if_then_else:SI (eq (match_dup 2) (const_int 0))
e5bde68a
RH
1875 (neg:SI (match_dup 1))
1876 (match_dup 1)))]
c65ebc55 1877 ""
1d5d7a21 1878 { operands[2] = gen_reg_rtx (BImode); })
c65ebc55
JW
1879
1880(define_expand "sminsi3"
1881 [(set (match_dup 3)
f2f90c63 1882 (ge:BI (match_operand:SI 1 "gr_register_operand" "")
0551c32d
RH
1883 (match_operand:SI 2 "gr_register_operand" "")))
1884 (set (match_operand:SI 0 "gr_register_operand" "")
f2f90c63 1885 (if_then_else:SI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
1886 (match_dup 2) (match_dup 1)))]
1887 ""
1d5d7a21 1888 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
1889
1890(define_expand "smaxsi3"
1891 [(set (match_dup 3)
f2f90c63 1892 (ge:BI (match_operand:SI 1 "gr_register_operand" "")
0551c32d
RH
1893 (match_operand:SI 2 "gr_register_operand" "")))
1894 (set (match_operand:SI 0 "gr_register_operand" "")
f2f90c63 1895 (if_then_else:SI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
1896 (match_dup 1) (match_dup 2)))]
1897 ""
1d5d7a21 1898 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
1899
1900(define_expand "uminsi3"
1901 [(set (match_dup 3)
f2f90c63 1902 (geu:BI (match_operand:SI 1 "gr_register_operand" "")
0551c32d
RH
1903 (match_operand:SI 2 "gr_register_operand" "")))
1904 (set (match_operand:SI 0 "gr_register_operand" "")
f2f90c63 1905 (if_then_else:SI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
1906 (match_dup 2) (match_dup 1)))]
1907 ""
1d5d7a21 1908 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
1909
1910(define_expand "umaxsi3"
1911 [(set (match_dup 3)
f2f90c63 1912 (geu:BI (match_operand:SI 1 "gr_register_operand" "")
0551c32d
RH
1913 (match_operand:SI 2 "gr_register_operand" "")))
1914 (set (match_operand:SI 0 "gr_register_operand" "")
f2f90c63 1915 (if_then_else:SI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
1916 (match_dup 1) (match_dup 2)))]
1917 ""
1d5d7a21 1918 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55 1919
655f2eb9
RH
1920(define_expand "divsi3"
1921 [(set (match_operand:SI 0 "register_operand" "")
1922 (div:SI (match_operand:SI 1 "general_operand" "")
1923 (match_operand:SI 2 "general_operand" "")))]
dcffbade 1924 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
1925{
1926 rtx op1_tf, op2_tf, op0_tf, op0_di, twon34;
efdc7e19 1927 REAL_VALUE_TYPE twon34_r;
655f2eb9
RH
1928
1929 op0_tf = gen_reg_rtx (TFmode);
1930 op0_di = gen_reg_rtx (DImode);
1931
1932 if (CONSTANT_P (operands[1]))
1933 operands[1] = force_reg (SImode, operands[1]);
1934 op1_tf = gen_reg_rtx (TFmode);
1935 expand_float (op1_tf, operands[1], 0);
1936
1937 if (CONSTANT_P (operands[2]))
1938 operands[2] = force_reg (SImode, operands[2]);
1939 op2_tf = gen_reg_rtx (TFmode);
1940 expand_float (op2_tf, operands[2], 0);
1941
1942 /* 2^-34 */
efdc7e19
RH
1943 real_2expN (&twon34_r, -34);
1944 twon34 = CONST_DOUBLE_FROM_REAL_VALUE (twon34_r, TFmode);
655f2eb9 1945 twon34 = force_reg (TFmode, twon34);
655f2eb9
RH
1946
1947 emit_insn (gen_divsi3_internal (op0_tf, op1_tf, op2_tf, twon34));
1948
1949 emit_insn (gen_fix_trunctfdi2_alts (op0_di, op0_tf, const1_rtx));
1950 emit_move_insn (operands[0], gen_lowpart (SImode, op0_di));
1951 DONE;
1d5d7a21 1952})
655f2eb9
RH
1953
1954(define_expand "modsi3"
1955 [(set (match_operand:SI 0 "register_operand" "")
1956 (mod:SI (match_operand:SI 1 "general_operand" "")
1957 (match_operand:SI 2 "general_operand" "")))]
dcffbade 1958 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
1959{
1960 rtx op2_neg, op1_di, div;
1961
1962 div = gen_reg_rtx (SImode);
1963 emit_insn (gen_divsi3 (div, operands[1], operands[2]));
1964
1965 op2_neg = expand_unop (SImode, neg_optab, operands[2], NULL_RTX, 0);
1966
1967 /* This is a trick to get us to reuse the value that we're sure to
1968 have already copied to the FP regs. */
1969 op1_di = gen_reg_rtx (DImode);
1970 convert_move (op1_di, operands[1], 0);
1971
1972 emit_insn (gen_maddsi4 (operands[0], div, op2_neg,
1973 gen_lowpart (SImode, op1_di)));
1974 DONE;
1d5d7a21 1975})
655f2eb9
RH
1976
1977(define_expand "udivsi3"
1978 [(set (match_operand:SI 0 "register_operand" "")
1979 (udiv:SI (match_operand:SI 1 "general_operand" "")
1980 (match_operand:SI 2 "general_operand" "")))]
dcffbade 1981 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
1982{
1983 rtx op1_tf, op2_tf, op0_tf, op0_di, twon34;
efdc7e19 1984 REAL_VALUE_TYPE twon34_r;
655f2eb9
RH
1985
1986 op0_tf = gen_reg_rtx (TFmode);
1987 op0_di = gen_reg_rtx (DImode);
1988
1989 if (CONSTANT_P (operands[1]))
1990 operands[1] = force_reg (SImode, operands[1]);
1991 op1_tf = gen_reg_rtx (TFmode);
1992 expand_float (op1_tf, operands[1], 1);
1993
1994 if (CONSTANT_P (operands[2]))
1995 operands[2] = force_reg (SImode, operands[2]);
1996 op2_tf = gen_reg_rtx (TFmode);
1997 expand_float (op2_tf, operands[2], 1);
1998
1999 /* 2^-34 */
efdc7e19
RH
2000 real_2expN (&twon34_r, -34);
2001 twon34 = CONST_DOUBLE_FROM_REAL_VALUE (twon34_r, TFmode);
655f2eb9 2002 twon34 = force_reg (TFmode, twon34);
655f2eb9
RH
2003
2004 emit_insn (gen_divsi3_internal (op0_tf, op1_tf, op2_tf, twon34));
2005
2006 emit_insn (gen_fixuns_trunctfdi2_alts (op0_di, op0_tf, const1_rtx));
2007 emit_move_insn (operands[0], gen_lowpart (SImode, op0_di));
2008 DONE;
1d5d7a21 2009})
655f2eb9
RH
2010
2011(define_expand "umodsi3"
2012 [(set (match_operand:SI 0 "register_operand" "")
2013 (umod:SI (match_operand:SI 1 "general_operand" "")
2014 (match_operand:SI 2 "general_operand" "")))]
dcffbade 2015 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2016{
2017 rtx op2_neg, op1_di, div;
2018
2019 div = gen_reg_rtx (SImode);
2020 emit_insn (gen_udivsi3 (div, operands[1], operands[2]));
2021
2022 op2_neg = expand_unop (SImode, neg_optab, operands[2], NULL_RTX, 0);
2023
2024 /* This is a trick to get us to reuse the value that we're sure to
2025 have already copied to the FP regs. */
2026 op1_di = gen_reg_rtx (DImode);
2027 convert_move (op1_di, operands[1], 1);
2028
2029 emit_insn (gen_maddsi4 (operands[0], div, op2_neg,
2030 gen_lowpart (SImode, op1_di)));
2031 DONE;
1d5d7a21 2032})
655f2eb9
RH
2033
2034(define_insn_and_split "divsi3_internal"
2035 [(set (match_operand:TF 0 "fr_register_operand" "=&f")
2036 (float:TF (div:SI (match_operand:TF 1 "fr_register_operand" "f")
2037 (match_operand:TF 2 "fr_register_operand" "f"))))
2038 (clobber (match_scratch:TF 4 "=&f"))
2039 (clobber (match_scratch:TF 5 "=&f"))
f2f90c63 2040 (clobber (match_scratch:BI 6 "=c"))
655f2eb9 2041 (use (match_operand:TF 3 "fr_register_operand" "f"))]
dcffbade 2042 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2043 "#"
2044 "&& reload_completed"
2045 [(parallel [(set (match_dup 0) (div:TF (const_int 1) (match_dup 2)))
086c0f96
RH
2046 (set (match_dup 6) (unspec:BI [(match_dup 1) (match_dup 2)]
2047 UNSPEC_FR_RECIP_APPROX))
655f2eb9
RH
2048 (use (const_int 1))])
2049 (cond_exec (ne (match_dup 6) (const_int 0))
2050 (parallel [(set (match_dup 4) (mult:TF (match_dup 1) (match_dup 0)))
2051 (use (const_int 1))]))
2052 (cond_exec (ne (match_dup 6) (const_int 0))
2053 (parallel [(set (match_dup 5)
2054 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
2055 (match_dup 7)))
2056 (use (const_int 1))]))
2057 (cond_exec (ne (match_dup 6) (const_int 0))
2058 (parallel [(set (match_dup 4)
2059 (plus:TF (mult:TF (match_dup 5) (match_dup 4))
2060 (match_dup 4)))
2061 (use (const_int 1))]))
2062 (cond_exec (ne (match_dup 6) (const_int 0))
2063 (parallel [(set (match_dup 5)
2064 (plus:TF (mult:TF (match_dup 5) (match_dup 5))
2065 (match_dup 3)))
2066 (use (const_int 1))]))
2067 (cond_exec (ne (match_dup 6) (const_int 0))
2068 (parallel [(set (match_dup 0)
2069 (plus:TF (mult:TF (match_dup 5) (match_dup 4))
2070 (match_dup 4)))
2071 (use (const_int 1))]))
2072 ]
2073 "operands[7] = CONST1_RTX (TFmode);"
2074 [(set_attr "predicable" "no")])
c65ebc55
JW
2075\f
2076;; ::::::::::::::::::::
2077;; ::
2078;; :: 64 bit Integer arithmetic
2079;; ::
2080;; ::::::::::::::::::::
2081
2082(define_insn "adddi3"
0551c32d
RH
2083 [(set (match_operand:DI 0 "gr_register_operand" "=r,r,r")
2084 (plus:DI (match_operand:DI 1 "gr_register_operand" "%r,r,a")
2085 (match_operand:DI 2 "gr_reg_or_22bit_operand" "r,I,J")))]
c65ebc55
JW
2086 ""
2087 "@
1d5d7a21
RH
2088 add %0 = %1, %2
2089 adds %0 = %2, %1
2090 addl %0 = %2, %1"
52e12ad0 2091 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
2092
2093(define_insn "*adddi3_plus1"
0551c32d
RH
2094 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2095 (plus:DI (plus:DI (match_operand:DI 1 "gr_register_operand" "r")
2096 (match_operand:DI 2 "gr_register_operand" "r"))
c65ebc55
JW
2097 (const_int 1)))]
2098 ""
2099 "add %0 = %1, %2, 1"
52e12ad0 2100 [(set_attr "itanium_class" "ialu")])
c65ebc55 2101
5527bf14
RH
2102;; This has some of the same problems as shladd. We let the shladd
2103;; eliminator hack handle it, which results in the 1 being forced into
2104;; a register, but not more ugliness here.
2105(define_insn "*adddi3_plus1_alt"
0551c32d
RH
2106 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2107 (plus:DI (mult:DI (match_operand:DI 1 "gr_register_operand" "r")
5527bf14
RH
2108 (const_int 2))
2109 (const_int 1)))]
2110 ""
2111 "add %0 = %1, %1, 1"
52e12ad0 2112 [(set_attr "itanium_class" "ialu")])
5527bf14 2113
c65ebc55 2114(define_insn "subdi3"
0551c32d
RH
2115 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2116 (minus:DI (match_operand:DI 1 "gr_reg_or_8bit_operand" "rK")
2117 (match_operand:DI 2 "gr_register_operand" "r")))]
c65ebc55
JW
2118 ""
2119 "sub %0 = %1, %2"
52e12ad0 2120 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
2121
2122(define_insn "*subdi3_minus1"
0551c32d
RH
2123 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2124 (plus:DI (not:DI (match_operand:DI 1 "gr_register_operand" "r"))
2125 (match_operand:DI 2 "gr_register_operand" "r")))]
c65ebc55
JW
2126 ""
2127 "sub %0 = %2, %1, 1"
52e12ad0 2128 [(set_attr "itanium_class" "ialu")])
c65ebc55 2129
cee58bc0
RH
2130;; ??? Use grfr instead of fr because of virtual register elimination
2131;; and silly test cases multiplying by the frame pointer.
c65ebc55 2132(define_insn "muldi3"
0551c32d 2133 [(set (match_operand:DI 0 "fr_register_operand" "=f")
cee58bc0
RH
2134 (mult:DI (match_operand:DI 1 "grfr_register_operand" "f")
2135 (match_operand:DI 2 "grfr_register_operand" "f")))]
c65ebc55 2136 ""
aebf2462 2137 "xmpy.l %0 = %1, %2"
52e12ad0 2138 [(set_attr "itanium_class" "xmpy")])
c65ebc55
JW
2139
2140;; ??? If operand 3 is an eliminable reg, then register elimination causes the
2141;; same problem that we have with shladd below. Unfortunately, this case is
2142;; much harder to fix because the multiply puts the result in an FP register,
2143;; but the add needs inputs from a general register. We add a spurious clobber
2144;; here so that it will be present just in case register elimination gives us
2145;; the funny result.
2146
2147;; ??? Maybe validate_changes should try adding match_scratch clobbers?
2148
2149;; ??? Maybe we should change how adds are canonicalized.
2150
655f2eb9 2151(define_insn "madddi4"
0551c32d 2152 [(set (match_operand:DI 0 "fr_register_operand" "=f")
11a13704
RH
2153 (plus:DI (mult:DI (match_operand:DI 1 "grfr_register_operand" "f")
2154 (match_operand:DI 2 "grfr_register_operand" "f"))
2155 (match_operand:DI 3 "grfr_register_operand" "f")))
c65ebc55
JW
2156 (clobber (match_scratch:DI 4 "=X"))]
2157 ""
aebf2462 2158 "xma.l %0 = %1, %2, %3"
52e12ad0 2159 [(set_attr "itanium_class" "xmpy")])
c65ebc55
JW
2160
2161;; This can be created by register elimination if operand3 of shladd is an
2162;; eliminable register or has reg_equiv_constant set.
2163
2164;; We have to use nonmemory_operand for operand 4, to ensure that the
2165;; validate_changes call inside eliminate_regs will always succeed. If it
655f2eb9 2166;; doesn't succeed, then this remain a madddi4 pattern, and will be reloaded
c65ebc55
JW
2167;; incorrectly.
2168
655f2eb9 2169(define_insn "*madddi4_elim"
c65ebc55 2170 [(set (match_operand:DI 0 "register_operand" "=&r")
13da91fd
RH
2171 (plus:DI (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "f")
2172 (match_operand:DI 2 "register_operand" "f"))
2173 (match_operand:DI 3 "register_operand" "f"))
c65ebc55 2174 (match_operand:DI 4 "nonmemory_operand" "rI")))
13da91fd 2175 (clobber (match_scratch:DI 5 "=f"))]
c65ebc55
JW
2176 "reload_in_progress"
2177 "#"
52e12ad0 2178 [(set_attr "itanium_class" "unknown")])
c65ebc55 2179
c65ebc55
JW
2180(define_split
2181 [(set (match_operand:DI 0 "register_operand" "")
2182 (plus:DI (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
2183 (match_operand:DI 2 "register_operand" ""))
2184 (match_operand:DI 3 "register_operand" ""))
0551c32d 2185 (match_operand:DI 4 "gr_reg_or_14bit_operand" "")))
c65ebc55
JW
2186 (clobber (match_scratch:DI 5 ""))]
2187 "reload_completed"
2188 [(parallel [(set (match_dup 5) (plus:DI (mult:DI (match_dup 1) (match_dup 2))
2189 (match_dup 3)))
2190 (clobber (match_dup 0))])
c65ebc55 2191 (set (match_dup 0) (match_dup 5))
c65ebc55
JW
2192 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
2193 "")
2194
2195;; ??? There are highpart multiply and add instructions, but we have no way
2196;; to generate them.
2197
2198(define_insn "smuldi3_highpart"
0551c32d 2199 [(set (match_operand:DI 0 "fr_register_operand" "=f")
c65ebc55
JW
2200 (truncate:DI
2201 (lshiftrt:TI
0551c32d
RH
2202 (mult:TI (sign_extend:TI
2203 (match_operand:DI 1 "fr_register_operand" "f"))
2204 (sign_extend:TI
2205 (match_operand:DI 2 "fr_register_operand" "f")))
c65ebc55
JW
2206 (const_int 64))))]
2207 ""
aebf2462 2208 "xmpy.h %0 = %1, %2"
52e12ad0 2209 [(set_attr "itanium_class" "xmpy")])
c65ebc55
JW
2210
2211(define_insn "umuldi3_highpart"
0551c32d 2212 [(set (match_operand:DI 0 "fr_register_operand" "=f")
c65ebc55
JW
2213 (truncate:DI
2214 (lshiftrt:TI
0551c32d
RH
2215 (mult:TI (zero_extend:TI
2216 (match_operand:DI 1 "fr_register_operand" "f"))
2217 (zero_extend:TI
2218 (match_operand:DI 2 "fr_register_operand" "f")))
c65ebc55
JW
2219 (const_int 64))))]
2220 ""
aebf2462 2221 "xmpy.hu %0 = %1, %2"
52e12ad0 2222 [(set_attr "itanium_class" "xmpy")])
c65ebc55
JW
2223
2224(define_insn "negdi2"
0551c32d
RH
2225 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2226 (neg:DI (match_operand:DI 1 "gr_register_operand" "r")))]
c65ebc55
JW
2227 ""
2228 "sub %0 = r0, %1"
52e12ad0 2229 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
2230
2231(define_expand "absdi2"
2232 [(set (match_dup 2)
f2f90c63 2233 (ge:BI (match_operand:DI 1 "gr_register_operand" "") (const_int 0)))
0551c32d 2234 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2235 (if_then_else:DI (eq (match_dup 2) (const_int 0))
e5bde68a
RH
2236 (neg:DI (match_dup 1))
2237 (match_dup 1)))]
c65ebc55 2238 ""
1d5d7a21 2239 { operands[2] = gen_reg_rtx (BImode); })
c65ebc55
JW
2240
2241(define_expand "smindi3"
2242 [(set (match_dup 3)
f2f90c63 2243 (ge:BI (match_operand:DI 1 "gr_register_operand" "")
0551c32d
RH
2244 (match_operand:DI 2 "gr_register_operand" "")))
2245 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2246 (if_then_else:DI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
2247 (match_dup 2) (match_dup 1)))]
2248 ""
1d5d7a21 2249 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
2250
2251(define_expand "smaxdi3"
2252 [(set (match_dup 3)
f2f90c63 2253 (ge:BI (match_operand:DI 1 "gr_register_operand" "")
0551c32d
RH
2254 (match_operand:DI 2 "gr_register_operand" "")))
2255 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2256 (if_then_else:DI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
2257 (match_dup 1) (match_dup 2)))]
2258 ""
1d5d7a21 2259 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
2260
2261(define_expand "umindi3"
2262 [(set (match_dup 3)
f2f90c63 2263 (geu:BI (match_operand:DI 1 "gr_register_operand" "")
0551c32d
RH
2264 (match_operand:DI 2 "gr_register_operand" "")))
2265 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2266 (if_then_else:DI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
2267 (match_dup 2) (match_dup 1)))]
2268 ""
1d5d7a21 2269 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
2270
2271(define_expand "umaxdi3"
2272 [(set (match_dup 3)
f2f90c63 2273 (geu:BI (match_operand:DI 1 "gr_register_operand" "")
0551c32d
RH
2274 (match_operand:DI 2 "gr_register_operand" "")))
2275 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2276 (if_then_else:DI (ne (match_dup 3) (const_int 0))
c65ebc55
JW
2277 (match_dup 1) (match_dup 2)))]
2278 ""
1d5d7a21 2279 { operands[3] = gen_reg_rtx (BImode); })
c65ebc55
JW
2280
2281(define_expand "ffsdi2"
2282 [(set (match_dup 6)
f2f90c63 2283 (eq:BI (match_operand:DI 1 "gr_register_operand" "") (const_int 0)))
c65ebc55
JW
2284 (set (match_dup 2) (plus:DI (match_dup 1) (const_int -1)))
2285 (set (match_dup 5) (const_int 0))
2286 (set (match_dup 3) (xor:DI (match_dup 1) (match_dup 2)))
c407570a 2287 (set (match_dup 4) (popcount:DI (match_dup 3)))
0551c32d 2288 (set (match_operand:DI 0 "gr_register_operand" "")
f2f90c63 2289 (if_then_else:DI (ne (match_dup 6) (const_int 0))
c65ebc55
JW
2290 (match_dup 5) (match_dup 4)))]
2291 ""
c65ebc55
JW
2292{
2293 operands[2] = gen_reg_rtx (DImode);
2294 operands[3] = gen_reg_rtx (DImode);
2295 operands[4] = gen_reg_rtx (DImode);
2296 operands[5] = gen_reg_rtx (DImode);
f2f90c63 2297 operands[6] = gen_reg_rtx (BImode);
1d5d7a21 2298})
c65ebc55 2299
c407570a
RH
2300(define_expand "ctzdi2"
2301 [(set (match_dup 2) (plus:DI (match_operand:DI 1 "gr_register_operand" "")
2302 (const_int -1)))
2303 (set (match_dup 3) (not:DI (match_dup 1)))
2304 (set (match_dup 4) (and:DI (match_dup 2) (match_dup 3)))
2305 (set (match_operand:DI 0 "gr_register_operand" "")
2306 (popcount:DI (match_dup 4)))]
2307 ""
2308{
2309 operands[2] = gen_reg_rtx (DImode);
2310 operands[3] = gen_reg_rtx (DImode);
2311 operands[4] = gen_reg_rtx (DImode);
2312})
2313
2314;; ??? Ought to invent some unspecs for !INTEL_EXTENDED_IEEE_FORMAT.
2315;; Note the computation here is op0 = 63 - (exp - 0xffff).
2316(define_expand "clzdi2"
2317 [(set (match_dup 2)
2318 (unsigned_float:TF (match_operand:DI 1 "fr_register_operand" "")))
2319 (set (match_dup 3)
2320 (unspec:DI [(match_dup 2)] UNSPEC_GETF_EXP))
2321 (set (match_dup 4) (const_int 65598))
2322 (set (match_operand:DI 0 "gr_register_operand" "")
2323 (minus:DI (match_dup 4) (match_dup 3)))]
2324 "INTEL_EXTENDED_IEEE_FORMAT"
2325{
2326 operands[2] = gen_reg_rtx (TFmode);
2327 operands[3] = gen_reg_rtx (DImode);
2328 operands[4] = gen_reg_rtx (DImode);
2329})
2330
2331(define_insn "popcountdi2"
0551c32d 2332 [(set (match_operand:DI 0 "gr_register_operand" "=r")
c407570a 2333 (popcount:DI (match_operand:DI 1 "gr_register_operand" "r")))]
c65ebc55
JW
2334 ""
2335 "popcnt %0 = %1"
52e12ad0 2336 [(set_attr "itanium_class" "mmmul")])
c65ebc55 2337
c407570a
RH
2338(define_insn "*getf_exp_tf"
2339 [(set (match_operand:DI 0 "gr_register_operand" "=r")
2340 (unspec:DI [(match_operand:TF 1 "fr_register_operand" "f")]
2341 UNSPEC_GETF_EXP))]
2342 "INTEL_EXTENDED_IEEE_FORMAT"
2343 "getf.exp %0 = %1"
2344 [(set_attr "itanium_class" "frfr")])
2345
655f2eb9
RH
2346(define_expand "divdi3"
2347 [(set (match_operand:DI 0 "register_operand" "")
2348 (div:DI (match_operand:DI 1 "general_operand" "")
2349 (match_operand:DI 2 "general_operand" "")))]
dcffbade 2350 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2351{
2352 rtx op1_tf, op2_tf, op0_tf;
2353
2354 op0_tf = gen_reg_rtx (TFmode);
2355
2356 if (CONSTANT_P (operands[1]))
2357 operands[1] = force_reg (DImode, operands[1]);
2358 op1_tf = gen_reg_rtx (TFmode);
2359 expand_float (op1_tf, operands[1], 0);
2360
2361 if (CONSTANT_P (operands[2]))
2362 operands[2] = force_reg (DImode, operands[2]);
2363 op2_tf = gen_reg_rtx (TFmode);
2364 expand_float (op2_tf, operands[2], 0);
2365
dcffbade 2366 if (TARGET_INLINE_INT_DIV_LAT)
655f2eb9
RH
2367 emit_insn (gen_divdi3_internal_lat (op0_tf, op1_tf, op2_tf));
2368 else
2369 emit_insn (gen_divdi3_internal_thr (op0_tf, op1_tf, op2_tf));
2370
2371 emit_insn (gen_fix_trunctfdi2_alts (operands[0], op0_tf, const1_rtx));
2372 DONE;
1d5d7a21 2373})
655f2eb9
RH
2374
2375(define_expand "moddi3"
2376 [(set (match_operand:DI 0 "register_operand" "")
2377 (mod:SI (match_operand:DI 1 "general_operand" "")
2378 (match_operand:DI 2 "general_operand" "")))]
dcffbade 2379 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2380{
2381 rtx op2_neg, div;
2382
2383 div = gen_reg_rtx (DImode);
2384 emit_insn (gen_divdi3 (div, operands[1], operands[2]));
2385
2386 op2_neg = expand_unop (DImode, neg_optab, operands[2], NULL_RTX, 0);
2387
2388 emit_insn (gen_madddi4 (operands[0], div, op2_neg, operands[1]));
2389 DONE;
1d5d7a21 2390})
655f2eb9
RH
2391
2392(define_expand "udivdi3"
2393 [(set (match_operand:DI 0 "register_operand" "")
2394 (udiv:DI (match_operand:DI 1 "general_operand" "")
2395 (match_operand:DI 2 "general_operand" "")))]
dcffbade 2396 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2397{
2398 rtx op1_tf, op2_tf, op0_tf;
2399
2400 op0_tf = gen_reg_rtx (TFmode);
2401
2402 if (CONSTANT_P (operands[1]))
2403 operands[1] = force_reg (DImode, operands[1]);
2404 op1_tf = gen_reg_rtx (TFmode);
2405 expand_float (op1_tf, operands[1], 1);
2406
2407 if (CONSTANT_P (operands[2]))
2408 operands[2] = force_reg (DImode, operands[2]);
2409 op2_tf = gen_reg_rtx (TFmode);
2410 expand_float (op2_tf, operands[2], 1);
2411
dcffbade 2412 if (TARGET_INLINE_INT_DIV_LAT)
655f2eb9
RH
2413 emit_insn (gen_divdi3_internal_lat (op0_tf, op1_tf, op2_tf));
2414 else
2415 emit_insn (gen_divdi3_internal_thr (op0_tf, op1_tf, op2_tf));
2416
2417 emit_insn (gen_fixuns_trunctfdi2_alts (operands[0], op0_tf, const1_rtx));
2418 DONE;
1d5d7a21 2419})
655f2eb9
RH
2420
2421(define_expand "umoddi3"
2422 [(set (match_operand:DI 0 "register_operand" "")
2423 (umod:DI (match_operand:DI 1 "general_operand" "")
2424 (match_operand:DI 2 "general_operand" "")))]
dcffbade 2425 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV"
655f2eb9
RH
2426{
2427 rtx op2_neg, div;
2428
2429 div = gen_reg_rtx (DImode);
2430 emit_insn (gen_udivdi3 (div, operands[1], operands[2]));
2431
2432 op2_neg = expand_unop (DImode, neg_optab, operands[2], NULL_RTX, 0);
2433
2434 emit_insn (gen_madddi4 (operands[0], div, op2_neg, operands[1]));
2435 DONE;
1d5d7a21 2436})
655f2eb9
RH
2437
2438(define_insn_and_split "divdi3_internal_lat"
2439 [(set (match_operand:TF 0 "fr_register_operand" "=&f")
2440 (float:TF (div:SI (match_operand:TF 1 "fr_register_operand" "f")
2441 (match_operand:TF 2 "fr_register_operand" "f"))))
2442 (clobber (match_scratch:TF 3 "=&f"))
2443 (clobber (match_scratch:TF 4 "=&f"))
2444 (clobber (match_scratch:TF 5 "=&f"))
f2f90c63 2445 (clobber (match_scratch:BI 6 "=c"))]
dcffbade 2446 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV_LAT"
655f2eb9
RH
2447 "#"
2448 "&& reload_completed"
2449 [(parallel [(set (match_dup 0) (div:TF (const_int 1) (match_dup 2)))
086c0f96
RH
2450 (set (match_dup 6) (unspec:BI [(match_dup 1) (match_dup 2)]
2451 UNSPEC_FR_RECIP_APPROX))
655f2eb9
RH
2452 (use (const_int 1))])
2453 (cond_exec (ne (match_dup 6) (const_int 0))
2454 (parallel [(set (match_dup 3)
2455 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
2456 (match_dup 7)))
2457 (use (const_int 1))]))
2458 (cond_exec (ne (match_dup 6) (const_int 0))
2459 (parallel [(set (match_dup 4) (mult:TF (match_dup 1) (match_dup 0)))
2460 (use (const_int 1))]))
2461 (cond_exec (ne (match_dup 6) (const_int 0))
2462 (parallel [(set (match_dup 5) (mult:TF (match_dup 3) (match_dup 3)))
2463 (use (const_int 1))]))
2464 (cond_exec (ne (match_dup 6) (const_int 0))
2465 (parallel [(set (match_dup 4)
2466 (plus:TF (mult:TF (match_dup 3) (match_dup 4))
2467 (match_dup 4)))
2468 (use (const_int 1))]))
2469 (cond_exec (ne (match_dup 6) (const_int 0))
2470 (parallel [(set (match_dup 0)
2471 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
2472 (match_dup 0)))
2473 (use (const_int 1))]))
2474 (cond_exec (ne (match_dup 6) (const_int 0))
2475 (parallel [(set (match_dup 3)
2476 (plus:TF (mult:TF (match_dup 5) (match_dup 4))
2477 (match_dup 4)))
2478 (use (const_int 1))]))
2479 (cond_exec (ne (match_dup 6) (const_int 0))
2480 (parallel [(set (match_dup 0)
2481 (plus:TF (mult:TF (match_dup 5) (match_dup 0))
2482 (match_dup 0)))
2483 (use (const_int 1))]))
2484 (cond_exec (ne (match_dup 6) (const_int 0))
2485 (parallel [(set (match_dup 4)
2486 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 3)))
2487 (match_dup 1)))
2488 (use (const_int 1))]))
2489 (cond_exec (ne (match_dup 6) (const_int 0))
2490 (parallel [(set (match_dup 0)
2491 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
2492 (match_dup 3)))
2493 (use (const_int 1))]))
2494 ]
2495 "operands[7] = CONST1_RTX (TFmode);"
2496 [(set_attr "predicable" "no")])
2497
2498(define_insn_and_split "divdi3_internal_thr"
2499 [(set (match_operand:TF 0 "fr_register_operand" "=&f")
2500 (float:TF (div:SI (match_operand:TF 1 "fr_register_operand" "f")
2501 (match_operand:TF 2 "fr_register_operand" "f"))))
2502 (clobber (match_scratch:TF 3 "=&f"))
2503 (clobber (match_scratch:TF 4 "=f"))
f2f90c63 2504 (clobber (match_scratch:BI 5 "=c"))]
dcffbade 2505 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_INT_DIV_THR"
655f2eb9
RH
2506 "#"
2507 "&& reload_completed"
2508 [(parallel [(set (match_dup 0) (div:TF (const_int 1) (match_dup 2)))
086c0f96
RH
2509 (set (match_dup 5) (unspec:BI [(match_dup 1) (match_dup 2)]
2510 UNSPEC_FR_RECIP_APPROX))
655f2eb9
RH
2511 (use (const_int 1))])
2512 (cond_exec (ne (match_dup 5) (const_int 0))
2513 (parallel [(set (match_dup 3)
2514 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
2515 (match_dup 6)))
2516 (use (const_int 1))]))
2517 (cond_exec (ne (match_dup 5) (const_int 0))
2518 (parallel [(set (match_dup 0)
2519 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
2520 (match_dup 0)))
2521 (use (const_int 1))]))
2522 (cond_exec (ne (match_dup 5) (const_int 0))
2523 (parallel [(set (match_dup 3) (mult:TF (match_dup 3) (match_dup 3)))
2524 (use (const_int 1))]))
2525 (cond_exec (ne (match_dup 5) (const_int 0))
2526 (parallel [(set (match_dup 0)
2527 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
2528 (match_dup 0)))
2529 (use (const_int 1))]))
2530 (cond_exec (ne (match_dup 5) (const_int 0))
2531 (parallel [(set (match_dup 3) (mult:TF (match_dup 0) (match_dup 1)))
2532 (use (const_int 1))]))
2533 (cond_exec (ne (match_dup 5) (const_int 0))
2534 (parallel [(set (match_dup 4)
2535 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 3)))
2536 (match_dup 1)))
2537 (use (const_int 1))]))
2538 (cond_exec (ne (match_dup 5) (const_int 0))
2539 (parallel [(set (match_dup 0)
2540 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
2541 (match_dup 3)))
2542 (use (const_int 1))]))
2543 ]
2544 "operands[6] = CONST1_RTX (TFmode);"
2545 [(set_attr "predicable" "no")])
c65ebc55
JW
2546\f
2547;; ::::::::::::::::::::
2548;; ::
2549;; :: 32 bit floating point arithmetic
2550;; ::
2551;; ::::::::::::::::::::
2552
2553(define_insn "addsf3"
0551c32d
RH
2554 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2555 (plus:SF (match_operand:SF 1 "fr_register_operand" "%f")
2556 (match_operand:SF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2557 ""
aebf2462 2558 "fadd.s %0 = %1, %F2"
52e12ad0 2559 [(set_attr "itanium_class" "fmac")])
c65ebc55
JW
2560
2561(define_insn "subsf3"
0551c32d
RH
2562 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2563 (minus:SF (match_operand:SF 1 "fr_reg_or_fp01_operand" "fG")
2564 (match_operand:SF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2565 ""
aebf2462 2566 "fsub.s %0 = %F1, %F2"
52e12ad0 2567 [(set_attr "itanium_class" "fmac")])
c65ebc55
JW
2568
2569(define_insn "mulsf3"
0551c32d
RH
2570 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2571 (mult:SF (match_operand:SF 1 "fr_register_operand" "%f")
2572 (match_operand:SF 2 "fr_register_operand" "f")))]
c65ebc55 2573 ""
aebf2462 2574 "fmpy.s %0 = %1, %2"
52e12ad0 2575 [(set_attr "itanium_class" "fmac")])
c65ebc55
JW
2576
2577(define_insn "abssf2"
0551c32d
RH
2578 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2579 (abs:SF (match_operand:SF 1 "fr_register_operand" "f")))]
c65ebc55 2580 ""
aebf2462 2581 "fabs %0 = %1"
52e12ad0 2582 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2583
2584(define_insn "negsf2"
0551c32d
RH
2585 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2586 (neg:SF (match_operand:SF 1 "fr_register_operand" "f")))]
c65ebc55 2587 ""
aebf2462 2588 "fneg %0 = %1"
52e12ad0 2589 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2590
2591(define_insn "*nabssf2"
0551c32d
RH
2592 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2593 (neg:SF (abs:SF (match_operand:SF 1 "fr_register_operand" "f"))))]
c65ebc55 2594 ""
aebf2462 2595 "fnegabs %0 = %1"
52e12ad0 2596 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2597
2598(define_insn "minsf3"
0551c32d
RH
2599 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2600 (smin:SF (match_operand:SF 1 "fr_register_operand" "f")
2601 (match_operand:SF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2602 ""
aebf2462 2603 "fmin %0 = %1, %F2"
52e12ad0 2604 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2605
2606(define_insn "maxsf3"
0551c32d
RH
2607 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2608 (smax:SF (match_operand:SF 1 "fr_register_operand" "f")
2609 (match_operand:SF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2610 ""
aebf2462 2611 "fmax %0 = %1, %F2"
52e12ad0 2612 [(set_attr "itanium_class" "fmisc")])
c65ebc55 2613
655f2eb9 2614(define_insn "*maddsf4"
0551c32d
RH
2615 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2616 (plus:SF (mult:SF (match_operand:SF 1 "fr_register_operand" "f")
2617 (match_operand:SF 2 "fr_register_operand" "f"))
2618 (match_operand:SF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2619 ""
aebf2462 2620 "fma.s %0 = %1, %2, %F3"
52e12ad0 2621 [(set_attr "itanium_class" "fmac")])
c65ebc55 2622
655f2eb9 2623(define_insn "*msubsf4"
0551c32d
RH
2624 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2625 (minus:SF (mult:SF (match_operand:SF 1 "fr_register_operand" "f")
2626 (match_operand:SF 2 "fr_register_operand" "f"))
2627 (match_operand:SF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2628 ""
aebf2462 2629 "fms.s %0 = %1, %2, %F3"
52e12ad0 2630 [(set_attr "itanium_class" "fmac")])
c65ebc55
JW
2631
2632(define_insn "*nmulsf3"
0551c32d
RH
2633 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2634 (neg:SF (mult:SF (match_operand:SF 1 "fr_register_operand" "f")
2635 (match_operand:SF 2 "fr_register_operand" "f"))))]
c65ebc55 2636 ""
aebf2462 2637 "fnmpy.s %0 = %1, %2"
52e12ad0 2638 [(set_attr "itanium_class" "fmac")])
c65ebc55
JW
2639
2640;; ??? Is it possible to canonicalize this as (minus (reg) (mult))?
2641
655f2eb9 2642(define_insn "*nmaddsf4"
0551c32d 2643 [(set (match_operand:SF 0 "fr_register_operand" "=f")
26102535
RH
2644 (plus:SF (neg:SF (mult:SF
2645 (match_operand:SF 1 "fr_register_operand" "f")
2646 (match_operand:SF 2 "fr_register_operand" "f")))
0551c32d 2647 (match_operand:SF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2648 ""
aebf2462 2649 "fnma.s %0 = %1, %2, %F3"
52e12ad0 2650 [(set_attr "itanium_class" "fmac")])
c65ebc55 2651
26102535
RH
2652(define_expand "divsf3"
2653 [(set (match_operand:SF 0 "fr_register_operand" "")
2654 (div:SF (match_operand:SF 1 "fr_register_operand" "")
2655 (match_operand:SF 2 "fr_register_operand" "")))]
dcffbade 2656 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV"
26102535
RH
2657{
2658 rtx insn;
dcffbade 2659 if (TARGET_INLINE_FLOAT_DIV_LAT)
26102535
RH
2660 insn = gen_divsf3_internal_lat (operands[0], operands[1], operands[2]);
2661 else
2662 insn = gen_divsf3_internal_thr (operands[0], operands[1], operands[2]);
2663 emit_insn (insn);
2664 DONE;
1d5d7a21 2665})
26102535
RH
2666
2667(define_insn_and_split "divsf3_internal_lat"
2668 [(set (match_operand:SF 0 "fr_register_operand" "=&f")
2669 (div:SF (match_operand:SF 1 "fr_register_operand" "f")
2670 (match_operand:SF 2 "fr_register_operand" "f")))
2671 (clobber (match_scratch:TF 3 "=&f"))
2672 (clobber (match_scratch:TF 4 "=f"))
f2f90c63 2673 (clobber (match_scratch:BI 5 "=c"))]
dcffbade 2674 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_LAT"
26102535
RH
2675 "#"
2676 "&& reload_completed"
2677 [(parallel [(set (match_dup 6) (div:TF (const_int 1) (match_dup 8)))
086c0f96
RH
2678 (set (match_dup 5) (unspec:BI [(match_dup 7) (match_dup 8)]
2679 UNSPEC_FR_RECIP_APPROX))
26102535
RH
2680 (use (const_int 1))])
2681 (cond_exec (ne (match_dup 5) (const_int 0))
2682 (parallel [(set (match_dup 3) (mult:TF (match_dup 7) (match_dup 6)))
2683 (use (const_int 1))]))
2684 (cond_exec (ne (match_dup 5) (const_int 0))
2685 (parallel [(set (match_dup 4)
2686 (plus:TF (neg:TF (mult:TF (match_dup 8) (match_dup 6)))
2687 (match_dup 10)))
2688 (use (const_int 1))]))
2689 (cond_exec (ne (match_dup 5) (const_int 0))
2690 (parallel [(set (match_dup 3)
2691 (plus:TF (mult:TF (match_dup 4) (match_dup 3))
2692 (match_dup 3)))
2693 (use (const_int 1))]))
2694 (cond_exec (ne (match_dup 5) (const_int 0))
2695 (parallel [(set (match_dup 4) (mult:TF (match_dup 4) (match_dup 4)))
2696 (use (const_int 1))]))
2697 (cond_exec (ne (match_dup 5) (const_int 0))
2698 (parallel [(set (match_dup 3)
2699 (plus:TF (mult:TF (match_dup 4) (match_dup 3))
2700 (match_dup 3)))
2701 (use (const_int 1))]))
2702 (cond_exec (ne (match_dup 5) (const_int 0))
2703 (parallel [(set (match_dup 4) (mult:TF (match_dup 4) (match_dup 4)))
2704 (use (const_int 1))]))
2705 (cond_exec (ne (match_dup 5) (const_int 0))
2706 (parallel [(set (match_dup 9)
2707 (float_truncate:DF
2708 (plus:TF (mult:TF (match_dup 4) (match_dup 3))
2709 (match_dup 3))))
2710 (use (const_int 1))]))
2711 (cond_exec (ne (match_dup 5) (const_int 0))
2712 (set (match_dup 0)
2713 (float_truncate:SF (match_dup 6))))
2714 ]
1d5d7a21
RH
2715{
2716 operands[6] = gen_rtx_REG (TFmode, REGNO (operands[0]));
2717 operands[7] = gen_rtx_REG (TFmode, REGNO (operands[1]));
2718 operands[8] = gen_rtx_REG (TFmode, REGNO (operands[2]));
2719 operands[9] = gen_rtx_REG (DFmode, REGNO (operands[0]));
2720 operands[10] = CONST1_RTX (TFmode);
2721}
26102535
RH
2722 [(set_attr "predicable" "no")])
2723
2724(define_insn_and_split "divsf3_internal_thr"
2725 [(set (match_operand:SF 0 "fr_register_operand" "=&f")
2726 (div:SF (match_operand:SF 1 "fr_register_operand" "f")
2727 (match_operand:SF 2 "fr_register_operand" "f")))
2728 (clobber (match_scratch:TF 3 "=&f"))
2729 (clobber (match_scratch:TF 4 "=f"))
f2f90c63 2730 (clobber (match_scratch:BI 5 "=c"))]
dcffbade 2731 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_THR"
26102535
RH
2732 "#"
2733 "&& reload_completed"
2734 [(parallel [(set (match_dup 6) (div:TF (const_int 1) (match_dup 8)))
086c0f96
RH
2735 (set (match_dup 5) (unspec:BI [(match_dup 7) (match_dup 8)]
2736 UNSPEC_FR_RECIP_APPROX))
26102535
RH
2737 (use (const_int 1))])
2738 (cond_exec (ne (match_dup 5) (const_int 0))
2739 (parallel [(set (match_dup 3)
2740 (plus:TF (neg:TF (mult:TF (match_dup 8) (match_dup 6)))
2741 (match_dup 10)))
2742 (use (const_int 1))]))
2743 (cond_exec (ne (match_dup 5) (const_int 0))
2744 (parallel [(set (match_dup 3)
2745 (plus:TF (mult:TF (match_dup 3) (match_dup 3))
2746 (match_dup 3)))
2747 (use (const_int 1))]))
2748 (cond_exec (ne (match_dup 5) (const_int 0))
2749 (parallel [(set (match_dup 6)
2750 (plus:TF (mult:TF (match_dup 3) (match_dup 6))
2751 (match_dup 6)))
2752 (use (const_int 1))]))
2753 (cond_exec (ne (match_dup 5) (const_int 0))
2754 (parallel [(set (match_dup 9)
2755 (float_truncate:SF
2756 (mult:TF (match_dup 7) (match_dup 6))))
2757 (use (const_int 1))]))
2758 (cond_exec (ne (match_dup 5) (const_int 0))
2759 (parallel [(set (match_dup 4)
2760 (plus:TF (neg:TF (mult:TF (match_dup 8) (match_dup 3)))
2761 (match_dup 7)))
2762 (use (const_int 1))]))
2763 (cond_exec (ne (match_dup 5) (const_int 0))
2764 (set (match_dup 0)
2765 (float_truncate:SF
2766 (plus:TF (mult:TF (match_dup 4) (match_dup 6))
2767 (match_dup 3)))))
2768 ]
1d5d7a21
RH
2769{
2770 operands[6] = gen_rtx_REG (TFmode, REGNO (operands[0]));
2771 operands[7] = gen_rtx_REG (TFmode, REGNO (operands[1]));
2772 operands[8] = gen_rtx_REG (TFmode, REGNO (operands[2]));
2773 operands[9] = gen_rtx_REG (SFmode, REGNO (operands[3]));
2774 operands[10] = CONST1_RTX (TFmode);
2775}
26102535 2776 [(set_attr "predicable" "no")])
c65ebc55
JW
2777\f
2778;; ::::::::::::::::::::
2779;; ::
2780;; :: 64 bit floating point arithmetic
2781;; ::
2782;; ::::::::::::::::::::
2783
2784(define_insn "adddf3"
0551c32d
RH
2785 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2786 (plus:DF (match_operand:DF 1 "fr_register_operand" "%f")
2787 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2788 ""
aebf2462 2789 "fadd.d %0 = %1, %F2"
52e12ad0 2790 [(set_attr "itanium_class" "fmac")])
c65ebc55 2791
26102535
RH
2792(define_insn "*adddf3_trunc"
2793 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2794 (float_truncate:SF
2795 (plus:DF (match_operand:DF 1 "fr_register_operand" "%f")
2796 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG"))))]
2797 ""
aebf2462 2798 "fadd.s %0 = %1, %F2"
52e12ad0 2799 [(set_attr "itanium_class" "fmac")])
26102535 2800
c65ebc55 2801(define_insn "subdf3"
0551c32d
RH
2802 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2803 (minus:DF (match_operand:DF 1 "fr_reg_or_fp01_operand" "fG")
2804 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2805 ""
aebf2462 2806 "fsub.d %0 = %F1, %F2"
52e12ad0 2807 [(set_attr "itanium_class" "fmac")])
c65ebc55 2808
26102535
RH
2809(define_insn "*subdf3_trunc"
2810 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2811 (float_truncate:SF
2812 (minus:DF (match_operand:DF 1 "fr_reg_or_fp01_operand" "fG")
2813 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG"))))]
2814 ""
aebf2462 2815 "fsub.s %0 = %F1, %F2"
52e12ad0 2816 [(set_attr "itanium_class" "fmac")])
26102535 2817
c65ebc55 2818(define_insn "muldf3"
0551c32d
RH
2819 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2820 (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2821 (match_operand:DF 2 "fr_register_operand" "f")))]
c65ebc55 2822 ""
aebf2462 2823 "fmpy.d %0 = %1, %2"
52e12ad0 2824 [(set_attr "itanium_class" "fmac")])
c65ebc55 2825
26102535
RH
2826(define_insn "*muldf3_trunc"
2827 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2828 (float_truncate:SF
2829 (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2830 (match_operand:DF 2 "fr_register_operand" "f"))))]
2831 ""
aebf2462 2832 "fmpy.s %0 = %1, %2"
52e12ad0 2833 [(set_attr "itanium_class" "fmac")])
26102535 2834
c65ebc55 2835(define_insn "absdf2"
0551c32d
RH
2836 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2837 (abs:DF (match_operand:DF 1 "fr_register_operand" "f")))]
c65ebc55 2838 ""
aebf2462 2839 "fabs %0 = %1"
52e12ad0 2840 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2841
2842(define_insn "negdf2"
0551c32d
RH
2843 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2844 (neg:DF (match_operand:DF 1 "fr_register_operand" "f")))]
c65ebc55 2845 ""
aebf2462 2846 "fneg %0 = %1"
52e12ad0 2847 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2848
2849(define_insn "*nabsdf2"
0551c32d
RH
2850 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2851 (neg:DF (abs:DF (match_operand:DF 1 "fr_register_operand" "f"))))]
c65ebc55 2852 ""
aebf2462 2853 "fnegabs %0 = %1"
52e12ad0 2854 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2855
2856(define_insn "mindf3"
0551c32d
RH
2857 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2858 (smin:DF (match_operand:DF 1 "fr_register_operand" "f")
2859 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2860 ""
aebf2462 2861 "fmin %0 = %1, %F2"
52e12ad0 2862 [(set_attr "itanium_class" "fmisc")])
c65ebc55
JW
2863
2864(define_insn "maxdf3"
0551c32d
RH
2865 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2866 (smax:DF (match_operand:DF 1 "fr_register_operand" "f")
2867 (match_operand:DF 2 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2868 ""
aebf2462 2869 "fmax %0 = %1, %F2"
52e12ad0 2870 [(set_attr "itanium_class" "fmisc")])
c65ebc55 2871
655f2eb9 2872(define_insn "*madddf4"
0551c32d
RH
2873 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2874 (plus:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2875 (match_operand:DF 2 "fr_register_operand" "f"))
2876 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2877 ""
aebf2462 2878 "fma.d %0 = %1, %2, %F3"
52e12ad0 2879 [(set_attr "itanium_class" "fmac")])
c65ebc55 2880
26102535
RH
2881(define_insn "*madddf4_trunc"
2882 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2883 (float_truncate:SF
2884 (plus:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2885 (match_operand:DF 2 "fr_register_operand" "f"))
2886 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG"))))]
2887 ""
aebf2462 2888 "fma.s %0 = %1, %2, %F3"
52e12ad0 2889 [(set_attr "itanium_class" "fmac")])
26102535 2890
655f2eb9 2891(define_insn "*msubdf4"
0551c32d
RH
2892 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2893 (minus:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2894 (match_operand:DF 2 "fr_register_operand" "f"))
2895 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2896 ""
aebf2462 2897 "fms.d %0 = %1, %2, %F3"
52e12ad0 2898 [(set_attr "itanium_class" "fmac")])
c65ebc55 2899
26102535
RH
2900(define_insn "*msubdf4_trunc"
2901 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2902 (float_truncate:SF
2903 (minus:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2904 (match_operand:DF 2 "fr_register_operand" "f"))
2905 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG"))))]
2906 ""
aebf2462 2907 "fms.s %0 = %1, %2, %F3"
52e12ad0 2908 [(set_attr "itanium_class" "fmac")])
26102535 2909
c65ebc55 2910(define_insn "*nmuldf3"
0551c32d
RH
2911 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2912 (neg:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2913 (match_operand:DF 2 "fr_register_operand" "f"))))]
c65ebc55 2914 ""
aebf2462 2915 "fnmpy.d %0 = %1, %2"
52e12ad0 2916 [(set_attr "itanium_class" "fmac")])
c65ebc55 2917
26102535
RH
2918(define_insn "*nmuldf3_trunc"
2919 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2920 (float_truncate:SF
2921 (neg:DF (mult:DF (match_operand:DF 1 "fr_register_operand" "f")
2922 (match_operand:DF 2 "fr_register_operand" "f")))))]
2923 ""
aebf2462 2924 "fnmpy.s %0 = %1, %2"
52e12ad0 2925 [(set_attr "itanium_class" "fmac")])
26102535 2926
c65ebc55
JW
2927;; ??? Is it possible to canonicalize this as (minus (reg) (mult))?
2928
655f2eb9 2929(define_insn "*nmadddf4"
0551c32d 2930 [(set (match_operand:DF 0 "fr_register_operand" "=f")
26102535
RH
2931 (plus:DF (neg:DF (mult:DF
2932 (match_operand:DF 1 "fr_register_operand" "f")
2933 (match_operand:DF 2 "fr_register_operand" "f")))
0551c32d 2934 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG")))]
c65ebc55 2935 ""
aebf2462 2936 "fnma.d %0 = %1, %2, %F3"
52e12ad0 2937 [(set_attr "itanium_class" "fmac")])
26102535
RH
2938
2939(define_insn "*nmadddf4_alts"
2940 [(set (match_operand:DF 0 "fr_register_operand" "=f")
2941 (plus:DF (neg:DF (mult:DF
2942 (match_operand:DF 1 "fr_register_operand" "f")
2943 (match_operand:DF 2 "fr_register_operand" "f")))
2944 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG")))
2945 (use (match_operand:SI 4 "const_int_operand" ""))]
2946 ""
aebf2462 2947 "fnma.d.s%4 %0 = %1, %2, %F3"
52e12ad0 2948 [(set_attr "itanium_class" "fmac")])
26102535
RH
2949
2950(define_insn "*nmadddf4_trunc"
2951 [(set (match_operand:SF 0 "fr_register_operand" "=f")
2952 (float_truncate:SF
2953 (plus:DF (neg:DF (mult:DF
2954 (match_operand:DF 1 "fr_register_operand" "f")
2955 (match_operand:DF 2 "fr_register_operand" "f")))
2956 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG"))))]
2957 ""
aebf2462 2958 "fnma.s %0 = %1, %2, %F3"
52e12ad0 2959 [(set_attr "itanium_class" "fmac")])
26102535
RH
2960
2961(define_expand "divdf3"
2962 [(set (match_operand:DF 0 "fr_register_operand" "")
2963 (div:DF (match_operand:DF 1 "fr_register_operand" "")
2964 (match_operand:DF 2 "fr_register_operand" "")))]
dcffbade 2965 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV"
26102535
RH
2966{
2967 rtx insn;
dcffbade 2968 if (TARGET_INLINE_FLOAT_DIV_LAT)
26102535
RH
2969 insn = gen_divdf3_internal_lat (operands[0], operands[1], operands[2]);
2970 else
2971 insn = gen_divdf3_internal_thr (operands[0], operands[1], operands[2]);
2972 emit_insn (insn);
2973 DONE;
1d5d7a21 2974})
26102535
RH
2975
2976(define_insn_and_split "divdf3_internal_lat"
2977 [(set (match_operand:DF 0 "fr_register_operand" "=&f")
2978 (div:DF (match_operand:DF 1 "fr_register_operand" "f")
2979 (match_operand:DF 2 "fr_register_operand" "f")))
2980 (clobber (match_scratch:TF 3 "=&f"))
2981 (clobber (match_scratch:TF 4 "=&f"))
2982 (clobber (match_scratch:TF 5 "=&f"))
f2f90c63 2983 (clobber (match_scratch:BI 6 "=c"))]
dcffbade 2984 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_LAT"
26102535
RH
2985 "#"
2986 "&& reload_completed"
2987 [(parallel [(set (match_dup 7) (div:TF (const_int 1) (match_dup 9)))
086c0f96
RH
2988 (set (match_dup 6) (unspec:BI [(match_dup 8) (match_dup 9)]
2989 UNSPEC_FR_RECIP_APPROX))
26102535
RH
2990 (use (const_int 1))])
2991 (cond_exec (ne (match_dup 6) (const_int 0))
2992 (parallel [(set (match_dup 3) (mult:TF (match_dup 8) (match_dup 7)))
2993 (use (const_int 1))]))
2994 (cond_exec (ne (match_dup 6) (const_int 0))
2995 (parallel [(set (match_dup 4)
2996 (plus:TF (neg:TF (mult:TF (match_dup 9) (match_dup 7)))
2997 (match_dup 12)))
2998 (use (const_int 1))]))
2999 (cond_exec (ne (match_dup 6) (const_int 0))
3000 (parallel [(set (match_dup 3)
3001 (plus:TF (mult:TF (match_dup 4) (match_dup 3))
3002 (match_dup 3)))
3003 (use (const_int 1))]))
3004 (cond_exec (ne (match_dup 6) (const_int 0))
3005 (parallel [(set (match_dup 5) (mult:TF (match_dup 4) (match_dup 4)))
3006 (use (const_int 1))]))
3007 (cond_exec (ne (match_dup 6) (const_int 0))
3008 (parallel [(set (match_dup 7)
3009 (plus:TF (mult:TF (match_dup 4) (match_dup 7))
3010 (match_dup 7)))
3011 (use (const_int 1))]))
3012 (cond_exec (ne (match_dup 6) (const_int 0))
3013 (parallel [(set (match_dup 3)
3014 (plus:TF (mult:TF (match_dup 5) (match_dup 3))
3015 (match_dup 3)))
3016 (use (const_int 1))]))
3017 (cond_exec (ne (match_dup 6) (const_int 0))
3018 (parallel [(set (match_dup 4) (mult:TF (match_dup 5) (match_dup 5)))
3019 (use (const_int 1))]))
3020 (cond_exec (ne (match_dup 6) (const_int 0))
3021 (parallel [(set (match_dup 7)
3022 (plus:TF (mult:TF (match_dup 5) (match_dup 7))
3023 (match_dup 7)))
3024 (use (const_int 1))]))
3025 (cond_exec (ne (match_dup 6) (const_int 0))
3026 (parallel [(set (match_dup 10)
3027 (float_truncate:DF
3028 (plus:TF (mult:TF (match_dup 4) (match_dup 3))
3029 (match_dup 3))))
3030 (use (const_int 1))]))
3031 (cond_exec (ne (match_dup 6) (const_int 0))
3032 (parallel [(set (match_dup 7)
3033 (plus:TF (mult:TF (match_dup 4) (match_dup 7))
3034 (match_dup 7)))
3035 (use (const_int 1))]))
3036 (cond_exec (ne (match_dup 6) (const_int 0))
3037 (parallel [(set (match_dup 11)
3038 (float_truncate:DF
3039 (plus:TF (neg:TF (mult:TF (match_dup 9) (match_dup 3)))
3040 (match_dup 8))))
3041 (use (const_int 1))]))
3042 (cond_exec (ne (match_dup 6) (const_int 0))
3043 (set (match_dup 0)
3044 (float_truncate:DF (plus:TF (mult:TF (match_dup 5) (match_dup 7))
3045 (match_dup 3)))))
3046 ]
1d5d7a21
RH
3047{
3048 operands[7] = gen_rtx_REG (TFmode, REGNO (operands[0]));
3049 operands[8] = gen_rtx_REG (TFmode, REGNO (operands[1]));
3050 operands[9] = gen_rtx_REG (TFmode, REGNO (operands[2]));
3051 operands[10] = gen_rtx_REG (DFmode, REGNO (operands[3]));
3052 operands[11] = gen_rtx_REG (DFmode, REGNO (operands[5]));
3053 operands[12] = CONST1_RTX (TFmode);
3054}
26102535
RH
3055 [(set_attr "predicable" "no")])
3056
3057(define_insn_and_split "divdf3_internal_thr"
3058 [(set (match_operand:DF 0 "fr_register_operand" "=&f")
3059 (div:DF (match_operand:DF 1 "fr_register_operand" "f")
3060 (match_operand:DF 2 "fr_register_operand" "f")))
3061 (clobber (match_scratch:TF 3 "=&f"))
3062 (clobber (match_scratch:DF 4 "=f"))
f2f90c63 3063 (clobber (match_scratch:BI 5 "=c"))]
dcffbade 3064 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_THR"
26102535
RH
3065 "#"
3066 "&& reload_completed"
3067 [(parallel [(set (match_dup 6) (div:TF (const_int 1) (match_dup 8)))
086c0f96
RH
3068 (set (match_dup 5) (unspec:BI [(match_dup 7) (match_dup 8)]
3069 UNSPEC_FR_RECIP_APPROX))
26102535
RH
3070 (use (const_int 1))])
3071 (cond_exec (ne (match_dup 5) (const_int 0))
3072 (parallel [(set (match_dup 3)
3073 (plus:TF (neg:TF (mult:TF (match_dup 8) (match_dup 6)))
3074 (match_dup 10)))
3075 (use (const_int 1))]))
3076 (cond_exec (ne (match_dup 5) (const_int 0))
3077 (parallel [(set (match_dup 6)
3078 (plus:TF (mult:TF (match_dup 3) (match_dup 6))
3079 (match_dup 6)))
3080 (use (const_int 1))]))
3081 (cond_exec (ne (match_dup 5) (const_int 0))
3082 (parallel [(set (match_dup 3)
3083 (mult:TF (match_dup 3) (match_dup 3)))
3084 (use (const_int 1))]))
3085 (cond_exec (ne (match_dup 5) (const_int 0))
3086 (parallel [(set (match_dup 6)
3087 (plus:TF (mult:TF (match_dup 3) (match_dup 6))
3088 (match_dup 6)))
3089 (use (const_int 1))]))
3090 (cond_exec (ne (match_dup 5) (const_int 0))
3091 (parallel [(set (match_dup 3)
3092 (mult:TF (match_dup 3) (match_dup 3)))
3093 (use (const_int 1))]))
3094 (cond_exec (ne (match_dup 5) (const_int 0))
3095 (parallel [(set (match_dup 6)
3096 (plus:TF (mult:TF (match_dup 3) (match_dup 6))
3097 (match_dup 6)))
3098 (use (const_int 1))]))
3099 (cond_exec (ne (match_dup 5) (const_int 0))
3100 (parallel [(set (match_dup 9)
3101 (float_truncate:DF
3102 (mult:TF (match_dup 7) (match_dup 3))))
3103 (use (const_int 1))]))
3104 (cond_exec (ne (match_dup 5) (const_int 0))
3105 (parallel [(set (match_dup 4)
3106 (plus:DF (neg:DF (mult:DF (match_dup 2) (match_dup 9)))
3107 (match_dup 1)))
3108 (use (const_int 1))]))
3109 (cond_exec (ne (match_dup 5) (const_int 0))
3110 (set (match_dup 0)
3111 (plus:DF (mult:DF (match_dup 4) (match_dup 0))
3112 (match_dup 9))))
3113 ]
1d5d7a21
RH
3114{
3115 operands[6] = gen_rtx_REG (TFmode, REGNO (operands[0]));
3116 operands[7] = gen_rtx_REG (TFmode, REGNO (operands[1]));
3117 operands[8] = gen_rtx_REG (TFmode, REGNO (operands[2]));
3118 operands[9] = gen_rtx_REG (DFmode, REGNO (operands[3]));
3119 operands[10] = CONST1_RTX (TFmode);
3120}
26102535 3121 [(set_attr "predicable" "no")])
3f622353
RH
3122\f
3123;; ::::::::::::::::::::
3124;; ::
3125;; :: 80 bit floating point arithmetic
3126;; ::
3127;; ::::::::::::::::::::
3128
3129(define_insn "addtf3"
0551c32d 3130 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3131 (plus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3132 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))]
23c108af 3133 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3134 "fadd %0 = %F1, %F2"
52e12ad0 3135 [(set_attr "itanium_class" "fmac")])
3f622353 3136
26102535
RH
3137(define_insn "*addtf3_truncsf"
3138 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3139 (float_truncate:SF
3140 (plus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3141 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3142 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3143 "fadd.s %0 = %F1, %F2"
52e12ad0 3144 [(set_attr "itanium_class" "fmac")])
26102535
RH
3145
3146(define_insn "*addtf3_truncdf"
3147 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3148 (float_truncate:DF
3149 (plus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3150 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3151 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3152 "fadd.d %0 = %F1, %F2"
52e12ad0 3153 [(set_attr "itanium_class" "fmac")])
26102535 3154
3f622353 3155(define_insn "subtf3"
0551c32d 3156 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3157 (minus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3158 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))]
23c108af 3159 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3160 "fsub %0 = %F1, %F2"
52e12ad0 3161 [(set_attr "itanium_class" "fmac")])
3f622353 3162
26102535
RH
3163(define_insn "*subtf3_truncsf"
3164 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3165 (float_truncate:SF
3166 (minus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3167 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3168 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3169 "fsub.s %0 = %F1, %F2"
52e12ad0 3170 [(set_attr "itanium_class" "fmac")])
26102535
RH
3171
3172(define_insn "*subtf3_truncdf"
3173 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3174 (float_truncate:DF
3175 (minus:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3176 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3177 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3178 "fsub.d %0 = %F1, %F2"
52e12ad0 3179 [(set_attr "itanium_class" "fmac")])
26102535 3180
3f622353 3181(define_insn "multf3"
0551c32d 3182 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3183 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3184 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))]
23c108af 3185 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3186 "fmpy %0 = %F1, %F2"
52e12ad0 3187 [(set_attr "itanium_class" "fmac")])
3f622353 3188
26102535
RH
3189(define_insn "*multf3_truncsf"
3190 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3191 (float_truncate:SF
3192 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3193 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3194 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3195 "fmpy.s %0 = %F1, %F2"
52e12ad0 3196 [(set_attr "itanium_class" "fmac")])
26102535
RH
3197
3198(define_insn "*multf3_truncdf"
3199 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3200 (float_truncate:DF
3201 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3202 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3203 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3204 "fmpy.d %0 = %F1, %F2"
52e12ad0 3205 [(set_attr "itanium_class" "fmac")])
26102535 3206
655f2eb9
RH
3207(define_insn "*multf3_alts"
3208 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3209 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3210 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3211 (use (match_operand:SI 3 "const_int_operand" ""))]
23c108af 3212 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3213 "fmpy.s%3 %0 = %F1, %F2"
52e12ad0 3214 [(set_attr "itanium_class" "fmac")])
655f2eb9 3215
26102535
RH
3216(define_insn "*multf3_truncsf_alts"
3217 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3218 (float_truncate:SF
3219 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3220 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))
3221 (use (match_operand:SI 3 "const_int_operand" ""))]
23c108af 3222 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3223 "fmpy.s.s%3 %0 = %F1, %F2"
52e12ad0 3224 [(set_attr "itanium_class" "fmac")])
26102535
RH
3225
3226(define_insn "*multf3_truncdf_alts"
3227 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3228 (float_truncate:DF
3229 (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3230 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))
3231 (use (match_operand:SI 3 "const_int_operand" ""))]
23c108af 3232 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3233 "fmpy.d.s%3 %0 = %F1, %F2"
52e12ad0 3234 [(set_attr "itanium_class" "fmac")])
26102535 3235
3f622353 3236(define_insn "abstf2"
0551c32d 3237 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353 3238 (abs:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")))]
23c108af 3239 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3240 "fabs %0 = %F1"
52e12ad0 3241 [(set_attr "itanium_class" "fmisc")])
3f622353
RH
3242
3243(define_insn "negtf2"
0551c32d 3244 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353 3245 (neg:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")))]
23c108af 3246 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3247 "fneg %0 = %F1"
52e12ad0 3248 [(set_attr "itanium_class" "fmisc")])
3f622353
RH
3249
3250(define_insn "*nabstf2"
0551c32d 3251 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353 3252 (neg:TF (abs:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3253 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3254 "fnegabs %0 = %F1"
52e12ad0 3255 [(set_attr "itanium_class" "fmisc")])
3f622353
RH
3256
3257(define_insn "mintf3"
0551c32d 3258 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3259 (smin:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3260 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))]
23c108af 3261 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3262 "fmin %0 = %F1, %F2"
52e12ad0 3263 [(set_attr "itanium_class" "fmisc")])
3f622353
RH
3264
3265(define_insn "maxtf3"
0551c32d 3266 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3267 (smax:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3268 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))]
23c108af 3269 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3270 "fmax %0 = %F1, %F2"
52e12ad0 3271 [(set_attr "itanium_class" "fmisc")])
3f622353 3272
655f2eb9 3273(define_insn "*maddtf4"
0551c32d 3274 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3275 (plus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3276 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3277 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")))]
23c108af 3278 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3279 "fma %0 = %F1, %F2, %F3"
52e12ad0 3280 [(set_attr "itanium_class" "fmac")])
3f622353 3281
26102535
RH
3282(define_insn "*maddtf4_truncsf"
3283 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3284 (float_truncate:SF
3285 (plus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3286 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3287 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3288 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3289 "fma.s %0 = %F1, %F2, %F3"
52e12ad0 3290 [(set_attr "itanium_class" "fmac")])
26102535
RH
3291
3292(define_insn "*maddtf4_truncdf"
3293 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3294 (float_truncate:DF
3295 (plus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3296 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3297 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3298 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3299 "fma.d %0 = %F1, %F2, %F3"
52e12ad0 3300 [(set_attr "itanium_class" "fmac")])
26102535 3301
655f2eb9
RH
3302(define_insn "*maddtf4_alts"
3303 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3304 (plus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3305 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3306 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")))
3307 (use (match_operand:SI 4 "const_int_operand" ""))]
23c108af 3308 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3309 "fma.s%4 %0 = %F1, %F2, %F3"
52e12ad0 3310 [(set_attr "itanium_class" "fmac")])
655f2eb9 3311
26102535
RH
3312(define_insn "*maddtf4_alts_truncdf"
3313 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3314 (float_truncate:DF
3315 (plus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3316 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3317 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))
3318 (use (match_operand:SI 4 "const_int_operand" ""))]
23c108af 3319 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3320 "fma.d.s%4 %0 = %F1, %F2, %F3"
52e12ad0 3321 [(set_attr "itanium_class" "fmac")])
26102535 3322
655f2eb9 3323(define_insn "*msubtf4"
0551c32d 3324 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3325 (minus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3326 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3327 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")))]
23c108af 3328 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3329 "fms %0 = %F1, %F2, %F3"
52e12ad0 3330 [(set_attr "itanium_class" "fmac")])
3f622353 3331
26102535
RH
3332(define_insn "*msubtf4_truncsf"
3333 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3334 (float_truncate:SF
3335 (minus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3336 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3337 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3338 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3339 "fms.s %0 = %F1, %F2, %F3"
52e12ad0 3340 [(set_attr "itanium_class" "fmac")])
26102535
RH
3341
3342(define_insn "*msubtf4_truncdf"
3343 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3344 (float_truncate:DF
3345 (minus:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3346 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))
3347 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3348 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3349 "fms.d %0 = %F1, %F2, %F3"
52e12ad0 3350 [(set_attr "itanium_class" "fmac")])
26102535 3351
3f622353 3352(define_insn "*nmultf3"
0551c32d 3353 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3354 (neg:TF (mult:TF (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3355 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3356 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3357 "fnmpy %0 = %F1, %F2"
52e12ad0 3358 [(set_attr "itanium_class" "fmac")])
c65ebc55 3359
26102535
RH
3360(define_insn "*nmultf3_truncsf"
3361 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3362 (float_truncate:SF
3363 (neg:TF (mult:TF
3364 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3365 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))))]
23c108af 3366 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3367 "fnmpy.s %0 = %F1, %F2"
52e12ad0 3368 [(set_attr "itanium_class" "fmac")])
26102535
RH
3369
3370(define_insn "*nmultf3_truncdf"
3371 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3372 (float_truncate:DF
3373 (neg:TF (mult:TF
3374 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3375 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))))]
23c108af 3376 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3377 "fnmpy.d %0 = %F1, %F2"
52e12ad0 3378 [(set_attr "itanium_class" "fmac")])
26102535 3379
3f622353
RH
3380;; ??? Is it possible to canonicalize this as (minus (reg) (mult))?
3381
655f2eb9 3382(define_insn "*nmaddtf4"
0551c32d 3383 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3f622353
RH
3384 (plus:TF (neg:TF (mult:TF
3385 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3386 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3387 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")))]
23c108af 3388 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3389 "fnma %0 = %F1, %F2, %F3"
52e12ad0 3390 [(set_attr "itanium_class" "fmac")])
655f2eb9 3391
26102535
RH
3392(define_insn "*nmaddtf4_truncsf"
3393 [(set (match_operand:SF 0 "fr_register_operand" "=f")
3394 (float_truncate:SF
3395 (plus:TF (neg:TF (mult:TF
3396 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3397 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3398 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3399 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3400 "fnma.s %0 = %F1, %F2, %F3"
52e12ad0 3401 [(set_attr "itanium_class" "fmac")])
26102535
RH
3402
3403(define_insn "*nmaddtf4_truncdf"
3404 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3405 (float_truncate:DF
3406 (plus:TF (neg:TF (mult:TF
3407 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3408 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3409 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))]
23c108af 3410 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3411 "fnma.d %0 = %F1, %F2, %F3"
52e12ad0 3412 [(set_attr "itanium_class" "fmac")])
26102535 3413
655f2eb9
RH
3414(define_insn "*nmaddtf4_alts"
3415 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3416 (plus:TF (neg:TF (mult:TF
3417 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3418 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3419 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")))
3420 (use (match_operand:SI 4 "const_int_operand" ""))]
23c108af 3421 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3422 "fnma.s%4 %0 = %F1, %F2, %F3"
52e12ad0 3423 [(set_attr "itanium_class" "fmac")])
655f2eb9 3424
26102535
RH
3425(define_insn "*nmaddtf4_truncdf_alts"
3426 [(set (match_operand:DF 0 "fr_register_operand" "=f")
3427 (float_truncate:DF
3428 (plus:TF (neg:TF
3429 (mult:TF
3430 (match_operand:TF 1 "tfreg_or_fp01_operand" "fG")
3431 (match_operand:TF 2 "tfreg_or_fp01_operand" "fG")))
3432 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG"))))
3433 (use (match_operand:SI 4 "const_int_operand" ""))]
23c108af 3434 "INTEL_EXTENDED_IEEE_FORMAT"
aebf2462 3435 "fnma.d.s%4 %0 = %F1, %F2, %F3"
52e12ad0 3436 [(set_attr "itanium_class" "fmac")])
26102535
RH
3437
3438(define_expand "divtf3"
3439 [(set (match_operand:TF 0 "fr_register_operand" "")
3440 (div:TF (match_operand:TF 1 "fr_register_operand" "")
3441 (match_operand:TF 2 "fr_register_operand" "")))]
dcffbade 3442 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV"
26102535
RH
3443{
3444 rtx insn;
dcffbade 3445 if (TARGET_INLINE_FLOAT_DIV_LAT)
26102535
RH
3446 insn = gen_divtf3_internal_lat (operands[0], operands[1], operands[2]);
3447 else
3448 insn = gen_divtf3_internal_thr (operands[0], operands[1], operands[2]);
3449 emit_insn (insn);
3450 DONE;
1d5d7a21 3451})
26102535
RH
3452
3453(define_insn_and_split "divtf3_internal_lat"
3454 [(set (match_operand:TF 0 "fr_register_operand" "=&f")
3455 (div:TF (match_operand:TF 1 "fr_register_operand" "f")
3456 (match_operand:TF 2 "fr_register_operand" "f")))
3457 (clobber (match_scratch:TF 3 "=&f"))
3458 (clobber (match_scratch:TF 4 "=&f"))
3459 (clobber (match_scratch:TF 5 "=&f"))
3460 (clobber (match_scratch:TF 6 "=&f"))
f2f90c63 3461 (clobber (match_scratch:BI 7 "=c"))]
dcffbade 3462 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_LAT"
26102535
RH
3463 "#"
3464 "&& reload_completed"
3465 [(parallel [(set (match_dup 0) (div:TF (const_int 1) (match_dup 2)))
086c0f96
RH
3466 (set (match_dup 7) (unspec:BI [(match_dup 1) (match_dup 2)]
3467 UNSPEC_FR_RECIP_APPROX))
26102535
RH
3468 (use (const_int 1))])
3469 (cond_exec (ne (match_dup 7) (const_int 0))
3470 (parallel [(set (match_dup 3)
3471 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
3472 (match_dup 8)))
3473 (use (const_int 1))]))
3474 (cond_exec (ne (match_dup 7) (const_int 0))
3475 (parallel [(set (match_dup 4) (mult:TF (match_dup 1) (match_dup 0)))
3476 (use (const_int 1))]))
3477 (cond_exec (ne (match_dup 7) (const_int 0))
3478 (parallel [(set (match_dup 5) (mult:TF (match_dup 3) (match_dup 3)))
3479 (use (const_int 1))]))
3480 (cond_exec (ne (match_dup 7) (const_int 0))
3481 (parallel [(set (match_dup 6)
3482 (plus:TF (mult:TF (match_dup 3) (match_dup 3))
3483 (match_dup 3)))
3484 (use (const_int 1))]))
3485 (cond_exec (ne (match_dup 7) (const_int 0))
3486 (parallel [(set (match_dup 3)
3487 (plus:TF (mult:TF (match_dup 5) (match_dup 5))
3488 (match_dup 3)))
3489 (use (const_int 1))]))
3490 (cond_exec (ne (match_dup 7) (const_int 0))
3491 (parallel [(set (match_dup 5)
3492 (plus:TF (mult:TF (match_dup 6) (match_dup 0))
3493 (match_dup 0)))
3494 (use (const_int 1))]))
3495 (cond_exec (ne (match_dup 7) (const_int 0))
3496 (parallel [(set (match_dup 0)
3497 (plus:TF (mult:TF (match_dup 5) (match_dup 3))
3498 (match_dup 0)))
3499 (use (const_int 1))]))
3500 (cond_exec (ne (match_dup 7) (const_int 0))
3501 (parallel [(set (match_dup 4)
3502 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 4)))
3503 (match_dup 1)))
3504 (use (const_int 1))]))
3505 (cond_exec (ne (match_dup 7) (const_int 0))
3506 (parallel [(set (match_dup 3)
3507 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
3508 (match_dup 4)))
3509 (use (const_int 1))]))
3510 (cond_exec (ne (match_dup 7) (const_int 0))
3511 (parallel [(set (match_dup 5)
3512 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
3513 (match_dup 8)))
3514 (use (const_int 1))]))
3515 (cond_exec (ne (match_dup 7) (const_int 0))
3516 (parallel [(set (match_dup 0)
3517 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
3518 (match_dup 0)))
3519 (use (const_int 1))]))
3520 (cond_exec (ne (match_dup 7) (const_int 0))
3521 (parallel [(set (match_dup 4)
3522 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 3)))
3523 (match_dup 1)))
3524 (use (const_int 1))]))
3525 (cond_exec (ne (match_dup 7) (const_int 0))
3526 (set (match_dup 0)
3527 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
3528 (match_dup 3))))
3529 ]
3530 "operands[8] = CONST1_RTX (TFmode);"
3531 [(set_attr "predicable" "no")])
3532
3533(define_insn_and_split "divtf3_internal_thr"
3534 [(set (match_operand:TF 0 "fr_register_operand" "=&f")
3535 (div:TF (match_operand:TF 1 "fr_register_operand" "f")
3536 (match_operand:TF 2 "fr_register_operand" "f")))
3537 (clobber (match_scratch:TF 3 "=&f"))
3538 (clobber (match_scratch:TF 4 "=&f"))
f2f90c63 3539 (clobber (match_scratch:BI 5 "=c"))]
dcffbade 3540 "INTEL_EXTENDED_IEEE_FORMAT && TARGET_INLINE_FLOAT_DIV_THR"
26102535
RH
3541 "#"
3542 "&& reload_completed"
3543 [(parallel [(set (match_dup 0) (div:TF (const_int 1) (match_dup 2)))
086c0f96
RH
3544 (set (match_dup 5) (unspec:BI [(match_dup 1) (match_dup 2)]
3545 UNSPEC_FR_RECIP_APPROX))
26102535
RH
3546 (use (const_int 1))])
3547 (cond_exec (ne (match_dup 5) (const_int 0))
3548 (parallel [(set (match_dup 3)
3549 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
3550 (match_dup 6)))
3551 (use (const_int 1))]))
3552 (cond_exec (ne (match_dup 5) (const_int 0))
3553 (parallel [(set (match_dup 4)
3554 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
3555 (match_dup 0)))
3556 (use (const_int 1))]))
3557 (cond_exec (ne (match_dup 5) (const_int 0))
3558 (parallel [(set (match_dup 3) (mult:TF (match_dup 3) (match_dup 3)))
3559 (use (const_int 1))]))
3560 (cond_exec (ne (match_dup 5) (const_int 0))
3561 (parallel [(set (match_dup 3)
3562 (plus:TF (mult:TF (match_dup 3) (match_dup 4))
3563 (match_dup 4)))
3564 (use (const_int 1))]))
3565 (cond_exec (ne (match_dup 5) (const_int 0))
3566 (parallel [(set (match_dup 4) (mult:TF (match_dup 1) (match_dup 0)))
3567 (use (const_int 1))]))
3568 (cond_exec (ne (match_dup 5) (const_int 0))
3569 (parallel [(set (match_dup 0)
3570 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 3)))
3571 (match_dup 6)))
3572 (use (const_int 1))]))
3573 (cond_exec (ne (match_dup 5) (const_int 0))
3574 (parallel [(set (match_dup 0)
3575 (plus:TF (mult:TF (match_dup 0) (match_dup 3))
3576 (match_dup 3)))
3577 (use (const_int 1))]))
3578 (cond_exec (ne (match_dup 5) (const_int 0))
3579 (parallel [(set (match_dup 3)
3580 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 4)))
3581 (match_dup 1)))
3582 (use (const_int 1))]))
3583 (cond_exec (ne (match_dup 5) (const_int 0))
3584 (parallel [(set (match_dup 3)
3585 (plus:TF (mult:TF (match_dup 3) (match_dup 0))
3586 (match_dup 4)))
3587 (use (const_int 1))]))
3588 (cond_exec (ne (match_dup 5) (const_int 0))
3589 (parallel [(set (match_dup 4)
3590 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 0)))
3591 (match_dup 6)))
3592 (use (const_int 1))]))
3593 (cond_exec (ne (match_dup 5) (const_int 0))
3594 (parallel [(set (match_dup 0)
3595 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
3596 (match_dup 0)))
3597 (use (const_int 1))]))
3598 (cond_exec (ne (match_dup 5) (const_int 0))
3599 (parallel [(set (match_dup 4)
3600 (plus:TF (neg:TF (mult:TF (match_dup 2) (match_dup 3)))
3601 (match_dup 1)))
3602 (use (const_int 1))]))
3603 (cond_exec (ne (match_dup 5) (const_int 0))
3604 (set (match_dup 0)
3605 (plus:TF (mult:TF (match_dup 4) (match_dup 0))
3606 (match_dup 3))))
3607 ]
3608 "operands[6] = CONST1_RTX (TFmode);"
3609 [(set_attr "predicable" "no")])
3610
3611;; ??? frcpa works like cmp.foo.unc.
3612
655f2eb9
RH
3613(define_insn "*recip_approx"
3614 [(set (match_operand:TF 0 "fr_register_operand" "=f")
3615 (div:TF (const_int 1)
3616 (match_operand:TF 3 "fr_register_operand" "f")))
f2f90c63
RH
3617 (set (match_operand:BI 1 "register_operand" "=c")
3618 (unspec:BI [(match_operand:TF 2 "fr_register_operand" "f")
086c0f96 3619 (match_dup 3)] UNSPEC_FR_RECIP_APPROX))
655f2eb9 3620 (use (match_operand:SI 4 "const_int_operand" ""))]
23c108af 3621 "INTEL_EXTENDED_IEEE_FORMAT"
655f2eb9 3622 "frcpa.s%4 %0, %1 = %2, %3"
52e12ad0 3623 [(set_attr "itanium_class" "fmisc")
26102535 3624 (set_attr "predicable" "no")])
c65ebc55
JW
3625\f
3626;; ::::::::::::::::::::
3627;; ::
3628;; :: 32 bit Integer Shifts and Rotates
3629;; ::
3630;; ::::::::::::::::::::
3631
9c668921 3632(define_expand "ashlsi3"
0551c32d
RH
3633 [(set (match_operand:SI 0 "gr_register_operand" "")
3634 (ashift:SI (match_operand:SI 1 "gr_register_operand" "")
3635 (match_operand:SI 2 "gr_reg_or_5bit_operand" "")))]
9c668921 3636 ""
9c668921
RH
3637{
3638 if (GET_CODE (operands[2]) != CONST_INT)
3639 {
3640 /* Why oh why didn't Intel arrange for SHIFT_COUNT_TRUNCATED? Now
3641 we've got to get rid of stray bits outside the SImode register. */
3642 rtx subshift = gen_reg_rtx (DImode);
3643 emit_insn (gen_zero_extendsidi2 (subshift, operands[2]));
3644 operands[2] = subshift;
3645 }
1d5d7a21 3646})
9c668921
RH
3647
3648(define_insn "*ashlsi3_internal"
0551c32d
RH
3649 [(set (match_operand:SI 0 "gr_register_operand" "=r,r,r")
3650 (ashift:SI (match_operand:SI 1 "gr_register_operand" "r,r,r")
3651 (match_operand:DI 2 "gr_reg_or_5bit_operand" "R,n,r")))]
c65ebc55 3652 ""
041f25e6
RH
3653 "@
3654 shladd %0 = %1, %2, r0
3655 dep.z %0 = %1, %2, %E2
3656 shl %0 = %1, %2"
52e12ad0 3657 [(set_attr "itanium_class" "ialu,ishf,mmshf")])
c65ebc55
JW
3658
3659(define_expand "ashrsi3"
0551c32d
RH
3660 [(set (match_operand:SI 0 "gr_register_operand" "")
3661 (ashiftrt:SI (match_operand:SI 1 "gr_register_operand" "")
3662 (match_operand:SI 2 "gr_reg_or_5bit_operand" "")))]
c65ebc55 3663 ""
c65ebc55 3664{
041f25e6
RH
3665 rtx subtarget = gen_reg_rtx (DImode);
3666 if (GET_CODE (operands[2]) == CONST_INT)
3667 emit_insn (gen_extv (subtarget, gen_lowpart (DImode, operands[1]),
3668 GEN_INT (32 - INTVAL (operands[2])), operands[2]));
3669 else
3670 {
9c668921 3671 rtx subshift = gen_reg_rtx (DImode);
041f25e6 3672 emit_insn (gen_extendsidi2 (subtarget, operands[1]));
9c668921
RH
3673 emit_insn (gen_zero_extendsidi2 (subshift, operands[2]));
3674 emit_insn (gen_ashrdi3 (subtarget, subtarget, subshift));
041f25e6
RH
3675 }
3676 emit_move_insn (gen_lowpart (DImode, operands[0]), subtarget);
3677 DONE;
1d5d7a21 3678})
c65ebc55 3679
c65ebc55 3680(define_expand "lshrsi3"
0551c32d
RH
3681 [(set (match_operand:SI 0 "gr_register_operand" "")
3682 (lshiftrt:SI (match_operand:SI 1 "gr_register_operand" "")
3683 (match_operand:SI 2 "gr_reg_or_5bit_operand" "")))]
c65ebc55 3684 ""
c65ebc55 3685{
041f25e6
RH
3686 rtx subtarget = gen_reg_rtx (DImode);
3687 if (GET_CODE (operands[2]) == CONST_INT)
3688 emit_insn (gen_extzv (subtarget, gen_lowpart (DImode, operands[1]),
3689 GEN_INT (32 - INTVAL (operands[2])), operands[2]));
3690 else
3691 {
9c668921 3692 rtx subshift = gen_reg_rtx (DImode);
041f25e6 3693 emit_insn (gen_zero_extendsidi2 (subtarget, operands[1]));
9c668921
RH
3694 emit_insn (gen_zero_extendsidi2 (subshift, operands[2]));
3695 emit_insn (gen_lshrdi3 (subtarget, subtarget, subshift));
041f25e6
RH
3696 }
3697 emit_move_insn (gen_lowpart (DImode, operands[0]), subtarget);
3698 DONE;
1d5d7a21 3699})
c65ebc55 3700
c65ebc55 3701;; Use mix4.r/shr to implement rotrsi3. We only get 32 bits of valid result
66db6b45
RH
3702;; here, instead of 64 like the patterns above. Keep the pattern together
3703;; until after combine; otherwise it won't get matched often.
c65ebc55
JW
3704
3705(define_expand "rotrsi3"
66db6b45
RH
3706 [(set (match_operand:SI 0 "gr_register_operand" "")
3707 (rotatert:SI (match_operand:SI 1 "gr_register_operand" "")
3708 (match_operand:SI 2 "gr_reg_or_5bit_operand" "")))]
3709 ""
66db6b45
RH
3710{
3711 if (GET_MODE (operands[2]) != VOIDmode)
3712 {
3713 rtx tmp = gen_reg_rtx (DImode);
3714 emit_insn (gen_zero_extendsidi2 (tmp, operands[2]));
3715 operands[2] = tmp;
3716 }
1d5d7a21 3717})
66db6b45
RH
3718
3719(define_insn_and_split "*rotrsi3_internal"
3720 [(set (match_operand:SI 0 "gr_register_operand" "=&r")
3721 (rotatert:SI (match_operand:SI 1 "gr_register_operand" "r")
3722 (match_operand:DI 2 "gr_reg_or_5bit_operand" "rM")))]
3723 ""
3724 "#"
3725 "reload_completed"
c65ebc55 3726 [(set (match_dup 3)
66db6b45 3727 (ior:DI (zero_extend:DI (match_dup 1))
c65ebc55
JW
3728 (ashift:DI (zero_extend:DI (match_dup 1)) (const_int 32))))
3729 (set (match_dup 3)
66db6b45
RH
3730 (lshiftrt:DI (match_dup 3) (match_dup 2)))]
3731 "operands[3] = gen_rtx_REG (DImode, REGNO (operands[0]));")
3732
3733(define_expand "rotlsi3"
3734 [(set (match_operand:SI 0 "gr_register_operand" "")
3735 (rotate:SI (match_operand:SI 1 "gr_register_operand" "")
3736 (match_operand:SI 2 "gr_reg_or_5bit_operand" "")))]
c65ebc55 3737 ""
c65ebc55
JW
3738{
3739 if (! shift_32bit_count_operand (operands[2], SImode))
66db6b45
RH
3740 {
3741 rtx tmp = gen_reg_rtx (SImode);
3742 emit_insn (gen_subsi3 (tmp, GEN_INT (32), operands[2]));
3743 emit_insn (gen_rotrsi3 (operands[0], operands[1], tmp));
3744 DONE;
3745 }
1d5d7a21 3746})
66db6b45
RH
3747
3748(define_insn_and_split "*rotlsi3_internal"
3749 [(set (match_operand:SI 0 "gr_register_operand" "=r")
3750 (rotate:SI (match_operand:SI 1 "gr_register_operand" "r")
3751 (match_operand:SI 2 "shift_32bit_count_operand" "n")))]
3752 ""
3753 "#"
3754 "reload_completed"
3755 [(set (match_dup 3)
3756 (ior:DI (zero_extend:DI (match_dup 1))
3757 (ashift:DI (zero_extend:DI (match_dup 1)) (const_int 32))))
3758 (set (match_dup 3)
3759 (lshiftrt:DI (match_dup 3) (match_dup 2)))]
1d5d7a21
RH
3760{
3761 operands[3] = gen_rtx_REG (DImode, REGNO (operands[0]));
3762 operands[2] = GEN_INT (32 - INTVAL (operands[2]));
3763})
c65ebc55
JW
3764\f
3765;; ::::::::::::::::::::
3766;; ::
3767;; :: 64 bit Integer Shifts and Rotates
3768;; ::
3769;; ::::::::::::::::::::
3770
3771(define_insn "ashldi3"
52e12ad0
BS
3772 [(set (match_operand:DI 0 "gr_register_operand" "=r,r,r")
3773 (ashift:DI (match_operand:DI 1 "gr_register_operand" "r,r,r")
3774 (match_operand:DI 2 "gr_reg_or_6bit_operand" "R,r,rM")))]
c65ebc55 3775 ""
041f25e6
RH
3776 "@
3777 shladd %0 = %1, %2, r0
52e12ad0 3778 shl %0 = %1, %2
041f25e6 3779 shl %0 = %1, %2"
52e12ad0 3780 [(set_attr "itanium_class" "ialu,mmshf,mmshfi")])
c65ebc55
JW
3781
3782;; ??? Maybe combine this with the multiply and add instruction?
3783
3784(define_insn "*shladd"
0551c32d
RH
3785 [(set (match_operand:DI 0 "gr_register_operand" "=r")
3786 (plus:DI (mult:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55 3787 (match_operand:DI 2 "shladd_operand" "n"))
0551c32d 3788 (match_operand:DI 3 "gr_register_operand" "r")))]
c65ebc55
JW
3789 ""
3790 "shladd %0 = %1, %S2, %3"
52e12ad0 3791 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
3792
3793;; This can be created by register elimination if operand3 of shladd is an
3794;; eliminable register or has reg_equiv_constant set.
3795
3796;; We have to use nonmemory_operand for operand 4, to ensure that the
3797;; validate_changes call inside eliminate_regs will always succeed. If it
3798;; doesn't succeed, then this remain a shladd pattern, and will be reloaded
3799;; incorrectly.
3800
5527bf14 3801(define_insn_and_split "*shladd_elim"
0551c32d
RH
3802 [(set (match_operand:DI 0 "gr_register_operand" "=&r")
3803 (plus:DI (plus:DI (mult:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55 3804 (match_operand:DI 2 "shladd_operand" "n"))
5527bf14 3805 (match_operand:DI 3 "nonmemory_operand" "r"))
c65ebc55
JW
3806 (match_operand:DI 4 "nonmemory_operand" "rI")))]
3807 "reload_in_progress"
5527bf14 3808 "* abort ();"
c65ebc55
JW
3809 "reload_completed"
3810 [(set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (match_dup 2))
3811 (match_dup 3)))
c65ebc55 3812 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
5527bf14 3813 ""
52e12ad0 3814 [(set_attr "itanium_class" "unknown")])
c65ebc55
JW
3815
3816(define_insn "ashrdi3"
52e12ad0
BS
3817 [(set (match_operand:DI 0 "gr_register_operand" "=r,r")
3818 (ashiftrt:DI (match_operand:DI 1 "gr_register_operand" "r,r")
3819 (match_operand:DI 2 "gr_reg_or_6bit_operand" "r,rM")))]
c65ebc55 3820 ""
52e12ad0
BS
3821 "@
3822 shr %0 = %1, %2
3823 shr %0 = %1, %2"
3824 [(set_attr "itanium_class" "mmshf,mmshfi")])
c65ebc55
JW
3825
3826(define_insn "lshrdi3"
52e12ad0
BS
3827 [(set (match_operand:DI 0 "gr_register_operand" "=r,r")
3828 (lshiftrt:DI (match_operand:DI 1 "gr_register_operand" "r,r")
3829 (match_operand:DI 2 "gr_reg_or_6bit_operand" "r,rM")))]
c65ebc55 3830 ""
52e12ad0
BS
3831 "@
3832 shr.u %0 = %1, %2
3833 shr.u %0 = %1, %2"
3834 [(set_attr "itanium_class" "mmshf,mmshfi")])
c65ebc55
JW
3835
3836;; Using a predicate that accepts only constants doesn't work, because optabs
3837;; will load the operand into a register and call the pattern if the predicate
3838;; did not accept it on the first try. So we use nonmemory_operand and then
3839;; verify that we have an appropriate constant in the expander.
3840
3841(define_expand "rotrdi3"
0551c32d
RH
3842 [(set (match_operand:DI 0 "gr_register_operand" "")
3843 (rotatert:DI (match_operand:DI 1 "gr_register_operand" "")
c65ebc55
JW
3844 (match_operand:DI 2 "nonmemory_operand" "")))]
3845 ""
c65ebc55
JW
3846{
3847 if (! shift_count_operand (operands[2], DImode))
3848 FAIL;
1d5d7a21 3849})
c65ebc55
JW
3850
3851(define_insn "*rotrdi3_internal"
0551c32d
RH
3852 [(set (match_operand:DI 0 "gr_register_operand" "=r")
3853 (rotatert:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
3854 (match_operand:DI 2 "shift_count_operand" "M")))]
3855 ""
3856 "shrp %0 = %1, %1, %2"
52e12ad0 3857 [(set_attr "itanium_class" "ishf")])
c65ebc55 3858
66db6b45
RH
3859(define_expand "rotldi3"
3860 [(set (match_operand:DI 0 "gr_register_operand" "")
3861 (rotate:DI (match_operand:DI 1 "gr_register_operand" "")
3862 (match_operand:DI 2 "nonmemory_operand" "")))]
3863 ""
66db6b45
RH
3864{
3865 if (! shift_count_operand (operands[2], DImode))
3866 FAIL;
1d5d7a21 3867})
66db6b45
RH
3868
3869(define_insn "*rotldi3_internal"
3870 [(set (match_operand:DI 0 "gr_register_operand" "=r")
3871 (rotate:DI (match_operand:DI 1 "gr_register_operand" "r")
3872 (match_operand:DI 2 "shift_count_operand" "M")))]
3873 ""
3874 "shrp %0 = %1, %1, %e2"
52e12ad0 3875 [(set_attr "itanium_class" "ishf")])
c65ebc55
JW
3876\f
3877;; ::::::::::::::::::::
3878;; ::
058557c4 3879;; :: 32 bit Integer Logical operations
c65ebc55
JW
3880;; ::
3881;; ::::::::::::::::::::
3882
3883;; We don't seem to need any other 32-bit logical operations, because gcc
3884;; generates zero-extend;zero-extend;DImode-op, which combine optimizes to
3885;; DImode-op;zero-extend, and then we can optimize away the zero-extend.
3886;; This doesn't work for unary logical operations, because we don't call
3887;; apply_distributive_law for them.
3888
3889;; ??? Likewise, this doesn't work for andnot, which isn't handled by
3890;; apply_distributive_law. We get inefficient code for
3891;; int sub4 (int i, int j) { return i & ~j; }
3892;; We could convert (and (not (sign_extend A)) (sign_extend B)) to
3893;; (zero_extend (and (not A) B)) in combine.
3894;; Or maybe fix this by adding andsi3/iorsi3/xorsi3 patterns like the
3895;; one_cmplsi2 pattern.
3896
058557c4 3897(define_insn "one_cmplsi2"
0551c32d
RH
3898 [(set (match_operand:SI 0 "gr_register_operand" "=r")
3899 (not:SI (match_operand:SI 1 "gr_register_operand" "r")))]
c65ebc55
JW
3900 ""
3901 "andcm %0 = -1, %1"
52e12ad0 3902 [(set_attr "itanium_class" "ilog")])
c65ebc55
JW
3903\f
3904;; ::::::::::::::::::::
3905;; ::
058557c4 3906;; :: 64 bit Integer Logical operations
c65ebc55
JW
3907;; ::
3908;; ::::::::::::::::::::
3909
3910(define_insn "anddi3"
0551c32d
RH
3911 [(set (match_operand:DI 0 "grfr_register_operand" "=r,*f")
3912 (and:DI (match_operand:DI 1 "grfr_register_operand" "%r,*f")
3913 (match_operand:DI 2 "grfr_reg_or_8bit_operand" "rK,*f")))]
c65ebc55
JW
3914 ""
3915 "@
3916 and %0 = %2, %1
aebf2462 3917 fand %0 = %2, %1"
52e12ad0 3918 [(set_attr "itanium_class" "ilog,fmisc")])
c65ebc55
JW
3919
3920(define_insn "*andnot"
0551c32d
RH
3921 [(set (match_operand:DI 0 "grfr_register_operand" "=r,*f")
3922 (and:DI (not:DI (match_operand:DI 1 "grfr_register_operand" "r,*f"))
3923 (match_operand:DI 2 "grfr_reg_or_8bit_operand" "rK,*f")))]
c65ebc55
JW
3924 ""
3925 "@
3926 andcm %0 = %2, %1
aebf2462 3927 fandcm %0 = %2, %1"
52e12ad0 3928 [(set_attr "itanium_class" "ilog,fmisc")])
c65ebc55
JW
3929
3930(define_insn "iordi3"
0551c32d
RH
3931 [(set (match_operand:DI 0 "grfr_register_operand" "=r,*f")
3932 (ior:DI (match_operand:DI 1 "grfr_register_operand" "%r,*f")
3933 (match_operand:DI 2 "grfr_reg_or_8bit_operand" "rK,*f")))]
c65ebc55
JW
3934 ""
3935 "@
3936 or %0 = %2, %1
aebf2462 3937 for %0 = %2, %1"
52e12ad0 3938 [(set_attr "itanium_class" "ilog,fmisc")])
c65ebc55
JW
3939
3940(define_insn "xordi3"
0551c32d
RH
3941 [(set (match_operand:DI 0 "grfr_register_operand" "=r,*f")
3942 (xor:DI (match_operand:DI 1 "grfr_register_operand" "%r,*f")
3943 (match_operand:DI 2 "grfr_reg_or_8bit_operand" "rK,*f")))]
c65ebc55
JW
3944 ""
3945 "@
3946 xor %0 = %2, %1
aebf2462 3947 fxor %0 = %2, %1"
52e12ad0 3948 [(set_attr "itanium_class" "ilog,fmisc")])
c65ebc55
JW
3949
3950(define_insn "one_cmpldi2"
0551c32d
RH
3951 [(set (match_operand:DI 0 "gr_register_operand" "=r")
3952 (not:DI (match_operand:DI 1 "gr_register_operand" "r")))]
c65ebc55
JW
3953 ""
3954 "andcm %0 = -1, %1"
52e12ad0 3955 [(set_attr "itanium_class" "ilog")])
c65ebc55
JW
3956\f
3957;; ::::::::::::::::::::
3958;; ::
3959;; :: Comparisons
3960;; ::
3961;; ::::::::::::::::::::
3962
f2f90c63
RH
3963(define_expand "cmpbi"
3964 [(set (cc0)
3965 (compare (match_operand:BI 0 "register_operand" "")
3966 (match_operand:BI 1 "const_int_operand" "")))]
3967 ""
f2f90c63
RH
3968{
3969 ia64_compare_op0 = operands[0];
3970 ia64_compare_op1 = operands[1];
3971 DONE;
1d5d7a21 3972})
f2f90c63 3973
c65ebc55
JW
3974(define_expand "cmpsi"
3975 [(set (cc0)
0551c32d
RH
3976 (compare (match_operand:SI 0 "gr_register_operand" "")
3977 (match_operand:SI 1 "gr_reg_or_8bit_and_adjusted_operand" "")))]
c65ebc55 3978 ""
c65ebc55
JW
3979{
3980 ia64_compare_op0 = operands[0];
3981 ia64_compare_op1 = operands[1];
3982 DONE;
1d5d7a21 3983})
c65ebc55
JW
3984
3985(define_expand "cmpdi"
3986 [(set (cc0)
0551c32d
RH
3987 (compare (match_operand:DI 0 "gr_register_operand" "")
3988 (match_operand:DI 1 "gr_reg_or_8bit_and_adjusted_operand" "")))]
c65ebc55 3989 ""
c65ebc55
JW
3990{
3991 ia64_compare_op0 = operands[0];
3992 ia64_compare_op1 = operands[1];
3993 DONE;
1d5d7a21 3994})
c65ebc55
JW
3995
3996(define_expand "cmpsf"
3997 [(set (cc0)
0551c32d
RH
3998 (compare (match_operand:SF 0 "fr_reg_or_fp01_operand" "")
3999 (match_operand:SF 1 "fr_reg_or_fp01_operand" "")))]
c65ebc55 4000 ""
c65ebc55
JW
4001{
4002 ia64_compare_op0 = operands[0];
4003 ia64_compare_op1 = operands[1];
4004 DONE;
1d5d7a21 4005})
c65ebc55
JW
4006
4007(define_expand "cmpdf"
4008 [(set (cc0)
0551c32d
RH
4009 (compare (match_operand:DF 0 "fr_reg_or_fp01_operand" "")
4010 (match_operand:DF 1 "fr_reg_or_fp01_operand" "")))]
c65ebc55 4011 ""
c65ebc55
JW
4012{
4013 ia64_compare_op0 = operands[0];
4014 ia64_compare_op1 = operands[1];
4015 DONE;
1d5d7a21 4016})
c65ebc55 4017
3f622353 4018(define_expand "cmptf"
c65ebc55 4019 [(set (cc0)
3f622353
RH
4020 (compare (match_operand:TF 0 "tfreg_or_fp01_operand" "")
4021 (match_operand:TF 1 "tfreg_or_fp01_operand" "")))]
23c108af 4022 "INTEL_EXTENDED_IEEE_FORMAT"
c65ebc55
JW
4023{
4024 ia64_compare_op0 = operands[0];
4025 ia64_compare_op1 = operands[1];
4026 DONE;
1d5d7a21 4027})
c65ebc55
JW
4028
4029(define_insn "*cmpsi_normal"
f2f90c63
RH
4030 [(set (match_operand:BI 0 "register_operand" "=c")
4031 (match_operator:BI 1 "normal_comparison_operator"
0551c32d
RH
4032 [(match_operand:SI 2 "gr_register_operand" "r")
4033 (match_operand:SI 3 "gr_reg_or_8bit_operand" "rK")]))]
c65ebc55
JW
4034 ""
4035 "cmp4.%C1 %0, %I0 = %3, %2"
52e12ad0 4036 [(set_attr "itanium_class" "icmp")])
c65ebc55 4037
18a3c539
JW
4038;; We use %r3 because it is possible for us to match a 0, and two of the
4039;; unsigned comparisons don't accept immediate operands of zero.
4040
c65ebc55 4041(define_insn "*cmpsi_adjusted"
f2f90c63
RH
4042 [(set (match_operand:BI 0 "register_operand" "=c")
4043 (match_operator:BI 1 "adjusted_comparison_operator"
0551c32d
RH
4044 [(match_operand:SI 2 "gr_register_operand" "r")
4045 (match_operand:SI 3 "gr_reg_or_8bit_adjusted_operand" "rL")]))]
c65ebc55 4046 ""
18a3c539 4047 "cmp4.%C1 %0, %I0 = %r3, %2"
52e12ad0 4048 [(set_attr "itanium_class" "icmp")])
c65ebc55
JW
4049
4050(define_insn "*cmpdi_normal"
f2f90c63
RH
4051 [(set (match_operand:BI 0 "register_operand" "=c")
4052 (match_operator:BI 1 "normal_comparison_operator"
4053 [(match_operand:DI 2 "gr_reg_or_0_operand" "rO")
0551c32d 4054 (match_operand:DI 3 "gr_reg_or_8bit_operand" "rK")]))]
c65ebc55 4055 ""
f2f90c63 4056 "cmp.%C1 %0, %I0 = %3, %r2"
52e12ad0 4057 [(set_attr "itanium_class" "icmp")])
c65ebc55 4058
18a3c539
JW
4059;; We use %r3 because it is possible for us to match a 0, and two of the
4060;; unsigned comparisons don't accept immediate operands of zero.
4061
c65ebc55 4062(define_insn "*cmpdi_adjusted"
f2f90c63
RH
4063 [(set (match_operand:BI 0 "register_operand" "=c")
4064 (match_operator:BI 1 "adjusted_comparison_operator"
0551c32d
RH
4065 [(match_operand:DI 2 "gr_register_operand" "r")
4066 (match_operand:DI 3 "gr_reg_or_8bit_adjusted_operand" "rL")]))]
c65ebc55 4067 ""
18a3c539 4068 "cmp.%C1 %0, %I0 = %r3, %2"
52e12ad0 4069 [(set_attr "itanium_class" "icmp")])
c65ebc55
JW
4070
4071(define_insn "*cmpsf_internal"
f2f90c63
RH
4072 [(set (match_operand:BI 0 "register_operand" "=c")
4073 (match_operator:BI 1 "comparison_operator"
0551c32d
RH
4074 [(match_operand:SF 2 "fr_reg_or_fp01_operand" "fG")
4075 (match_operand:SF 3 "fr_reg_or_fp01_operand" "fG")]))]
c65ebc55
JW
4076 ""
4077 "fcmp.%D1 %0, %I0 = %F2, %F3"
52e12ad0 4078 [(set_attr "itanium_class" "fcmp")])
c65ebc55
JW
4079
4080(define_insn "*cmpdf_internal"
f2f90c63
RH
4081 [(set (match_operand:BI 0 "register_operand" "=c")
4082 (match_operator:BI 1 "comparison_operator"
0551c32d
RH
4083 [(match_operand:DF 2 "fr_reg_or_fp01_operand" "fG")
4084 (match_operand:DF 3 "fr_reg_or_fp01_operand" "fG")]))]
c65ebc55
JW
4085 ""
4086 "fcmp.%D1 %0, %I0 = %F2, %F3"
52e12ad0 4087 [(set_attr "itanium_class" "fcmp")])
c65ebc55 4088
3f622353 4089(define_insn "*cmptf_internal"
f2f90c63
RH
4090 [(set (match_operand:BI 0 "register_operand" "=c")
4091 (match_operator:BI 1 "comparison_operator"
3f622353
RH
4092 [(match_operand:TF 2 "tfreg_or_fp01_operand" "fG")
4093 (match_operand:TF 3 "tfreg_or_fp01_operand" "fG")]))]
23c108af 4094 "INTEL_EXTENDED_IEEE_FORMAT"
3f622353 4095 "fcmp.%D1 %0, %I0 = %F2, %F3"
52e12ad0 4096 [(set_attr "itanium_class" "fcmp")])
3f622353 4097
c65ebc55
JW
4098;; ??? Can this pattern be generated?
4099
4100(define_insn "*bit_zero"
f2f90c63
RH
4101 [(set (match_operand:BI 0 "register_operand" "=c")
4102 (eq:BI (zero_extract:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
4103 (const_int 1)
4104 (match_operand:DI 2 "immediate_operand" "n"))
4105 (const_int 0)))]
4106 ""
4107 "tbit.z %0, %I0 = %1, %2"
52e12ad0 4108 [(set_attr "itanium_class" "tbit")])
c65ebc55
JW
4109
4110(define_insn "*bit_one"
f2f90c63
RH
4111 [(set (match_operand:BI 0 "register_operand" "=c")
4112 (ne:BI (zero_extract:DI (match_operand:DI 1 "gr_register_operand" "r")
c65ebc55
JW
4113 (const_int 1)
4114 (match_operand:DI 2 "immediate_operand" "n"))
4115 (const_int 0)))]
4116 ""
4117 "tbit.nz %0, %I0 = %1, %2"
52e12ad0 4118 [(set_attr "itanium_class" "tbit")])
c65ebc55
JW
4119\f
4120;; ::::::::::::::::::::
4121;; ::
4122;; :: Branches
4123;; ::
4124;; ::::::::::::::::::::
4125
4126(define_expand "beq"
f2f90c63
RH
4127 [(set (pc)
4128 (if_then_else (match_dup 1)
c65ebc55
JW
4129 (label_ref (match_operand 0 "" ""))
4130 (pc)))]
4131 ""
f2f90c63 4132 "operands[1] = ia64_expand_compare (EQ, VOIDmode);")
c65ebc55
JW
4133
4134(define_expand "bne"
f2f90c63
RH
4135 [(set (pc)
4136 (if_then_else (match_dup 1)
c65ebc55
JW
4137 (label_ref (match_operand 0 "" ""))
4138 (pc)))]
4139 ""
f2f90c63 4140 "operands[1] = ia64_expand_compare (NE, VOIDmode);")
c65ebc55
JW
4141
4142(define_expand "blt"
f2f90c63
RH
4143 [(set (pc)
4144 (if_then_else (match_dup 1)
c65ebc55
JW
4145 (label_ref (match_operand 0 "" ""))
4146 (pc)))]
4147 ""
f2f90c63 4148 "operands[1] = ia64_expand_compare (LT, VOIDmode);")
c65ebc55
JW
4149
4150(define_expand "ble"
f2f90c63
RH
4151 [(set (pc)
4152 (if_then_else (match_dup 1)
c65ebc55
JW
4153 (label_ref (match_operand 0 "" ""))
4154 (pc)))]
4155 ""
f2f90c63 4156 "operands[1] = ia64_expand_compare (LE, VOIDmode);")
c65ebc55
JW
4157
4158(define_expand "bgt"
f2f90c63
RH
4159 [(set (pc)
4160 (if_then_else (match_dup 1)
c65ebc55
JW
4161 (label_ref (match_operand 0 "" ""))
4162 (pc)))]
4163 ""
f2f90c63 4164 "operands[1] = ia64_expand_compare (GT, VOIDmode);")
c65ebc55
JW
4165
4166(define_expand "bge"
f2f90c63
RH
4167 [(set (pc)
4168 (if_then_else (match_dup 1)
c65ebc55
JW
4169 (label_ref (match_operand 0 "" ""))
4170 (pc)))]
4171 ""
f2f90c63 4172 "operands[1] = ia64_expand_compare (GE, VOIDmode);")
c65ebc55
JW
4173
4174(define_expand "bltu"
f2f90c63
RH
4175 [(set (pc)
4176 (if_then_else (match_dup 1)
c65ebc55
JW
4177 (label_ref (match_operand 0 "" ""))
4178 (pc)))]
4179 ""
f2f90c63 4180 "operands[1] = ia64_expand_compare (LTU, VOIDmode);")
c65ebc55
JW
4181
4182(define_expand "bleu"
f2f90c63
RH
4183 [(set (pc)
4184 (if_then_else (match_dup 1)
c65ebc55
JW
4185 (label_ref (match_operand 0 "" ""))
4186 (pc)))]
4187 ""
f2f90c63 4188 "operands[1] = ia64_expand_compare (LEU, VOIDmode);")
c65ebc55
JW
4189
4190(define_expand "bgtu"
f2f90c63
RH
4191 [(set (pc)
4192 (if_then_else (match_dup 1)
c65ebc55
JW
4193 (label_ref (match_operand 0 "" ""))
4194 (pc)))]
4195 ""
f2f90c63 4196 "operands[1] = ia64_expand_compare (GTU, VOIDmode);")
c65ebc55
JW
4197
4198(define_expand "bgeu"
f2f90c63
RH
4199 [(set (pc)
4200 (if_then_else (match_dup 1)
c65ebc55
JW
4201 (label_ref (match_operand 0 "" ""))
4202 (pc)))]
4203 ""
f2f90c63 4204 "operands[1] = ia64_expand_compare (GEU, VOIDmode);")
c65ebc55 4205
e57b9d65 4206(define_expand "bunordered"
f2f90c63
RH
4207 [(set (pc)
4208 (if_then_else (match_dup 1)
e57b9d65
RH
4209 (label_ref (match_operand 0 "" ""))
4210 (pc)))]
4211 ""
f2f90c63 4212 "operands[1] = ia64_expand_compare (UNORDERED, VOIDmode);")
e57b9d65
RH
4213
4214(define_expand "bordered"
f2f90c63
RH
4215 [(set (pc)
4216 (if_then_else (match_dup 1)
e57b9d65
RH
4217 (label_ref (match_operand 0 "" ""))
4218 (pc)))]
4219 ""
f2f90c63 4220 "operands[1] = ia64_expand_compare (ORDERED, VOIDmode);")
e57b9d65 4221
6b6c1201 4222(define_insn "*br_true"
c65ebc55 4223 [(set (pc)
6b6c1201 4224 (if_then_else (match_operator 0 "predicate_operator"
f2f90c63 4225 [(match_operand:BI 1 "register_operand" "c")
6b6c1201
RH
4226 (const_int 0)])
4227 (label_ref (match_operand 2 "" ""))
c65ebc55
JW
4228 (pc)))]
4229 ""
85548039 4230 "(%J0) br.cond%+ %l2"
52e12ad0 4231 [(set_attr "itanium_class" "br")
e5bde68a 4232 (set_attr "predicable" "no")])
c65ebc55 4233
6b6c1201 4234(define_insn "*br_false"
c65ebc55 4235 [(set (pc)
6b6c1201 4236 (if_then_else (match_operator 0 "predicate_operator"
f2f90c63 4237 [(match_operand:BI 1 "register_operand" "c")
6b6c1201 4238 (const_int 0)])
c65ebc55 4239 (pc)
6b6c1201 4240 (label_ref (match_operand 2 "" ""))))]
c65ebc55 4241 ""
85548039 4242 "(%j0) br.cond%+ %l2"
52e12ad0 4243 [(set_attr "itanium_class" "br")
e5bde68a 4244 (set_attr "predicable" "no")])
c65ebc55
JW
4245\f
4246;; ::::::::::::::::::::
4247;; ::
5527bf14
RH
4248;; :: Counted loop operations
4249;; ::
4250;; ::::::::::::::::::::
4251
4252(define_expand "doloop_end"
4253 [(use (match_operand 0 "" "")) ; loop pseudo
4254 (use (match_operand 1 "" "")) ; iterations; zero if unknown
4255 (use (match_operand 2 "" "")) ; max iterations
4256 (use (match_operand 3 "" "")) ; loop level
4257 (use (match_operand 4 "" ""))] ; label
4258 ""
5527bf14
RH
4259{
4260 /* Only use cloop on innermost loops. */
4261 if (INTVAL (operands[3]) > 1)
4262 FAIL;
4263 emit_jump_insn (gen_doloop_end_internal (gen_rtx_REG (DImode, AR_LC_REGNUM),
4264 operands[4]));
4265 DONE;
1d5d7a21 4266})
5527bf14
RH
4267
4268(define_insn "doloop_end_internal"
4269 [(set (pc) (if_then_else (ne (match_operand:DI 0 "ar_lc_reg_operand" "")
4270 (const_int 0))
4271 (label_ref (match_operand 1 "" ""))
4272 (pc)))
4273 (set (match_dup 0) (if_then_else:DI (ne (match_dup 0) (const_int 0))
147d5f6f
AM
4274 (plus:DI (match_dup 0) (const_int -1))
4275 (match_dup 0)))]
5527bf14
RH
4276 ""
4277 "br.cloop.sptk.few %l1"
52e12ad0 4278 [(set_attr "itanium_class" "br")
5527bf14
RH
4279 (set_attr "predicable" "no")])
4280\f
4281;; ::::::::::::::::::::
4282;; ::
c65ebc55
JW
4283;; :: Set flag operations
4284;; ::
4285;; ::::::::::::::::::::
4286
4287(define_expand "seq"
f2f90c63 4288 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4289 ""
f2f90c63 4290 "operands[1] = ia64_expand_compare (EQ, DImode);")
c65ebc55
JW
4291
4292(define_expand "sne"
f2f90c63 4293 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4294 ""
f2f90c63 4295 "operands[1] = ia64_expand_compare (NE, DImode);")
c65ebc55
JW
4296
4297(define_expand "slt"
f2f90c63 4298 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4299 ""
f2f90c63 4300 "operands[1] = ia64_expand_compare (LT, DImode);")
c65ebc55
JW
4301
4302(define_expand "sle"
f2f90c63 4303 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4304 ""
f2f90c63 4305 "operands[1] = ia64_expand_compare (LE, DImode);")
c65ebc55
JW
4306
4307(define_expand "sgt"
f2f90c63 4308 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4309 ""
f2f90c63 4310 "operands[1] = ia64_expand_compare (GT, DImode);")
c65ebc55
JW
4311
4312(define_expand "sge"
f2f90c63 4313 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4314 ""
f2f90c63 4315 "operands[1] = ia64_expand_compare (GE, DImode);")
c65ebc55
JW
4316
4317(define_expand "sltu"
f2f90c63 4318 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4319 ""
f2f90c63 4320 "operands[1] = ia64_expand_compare (LTU, DImode);")
c65ebc55
JW
4321
4322(define_expand "sleu"
f2f90c63 4323 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4324 ""
f2f90c63 4325 "operands[1] = ia64_expand_compare (LEU, DImode);")
c65ebc55
JW
4326
4327(define_expand "sgtu"
f2f90c63 4328 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4329 ""
f2f90c63 4330 "operands[1] = ia64_expand_compare (GTU, DImode);")
c65ebc55
JW
4331
4332(define_expand "sgeu"
f2f90c63 4333 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
c65ebc55 4334 ""
f2f90c63 4335 "operands[1] = ia64_expand_compare (GEU, DImode);")
c65ebc55 4336
e57b9d65 4337(define_expand "sunordered"
f2f90c63 4338 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
e57b9d65 4339 ""
f2f90c63 4340 "operands[1] = ia64_expand_compare (UNORDERED, DImode);")
e57b9d65
RH
4341
4342(define_expand "sordered"
f2f90c63 4343 [(set (match_operand:DI 0 "gr_register_operand" "") (match_dup 1))]
e57b9d65 4344 ""
f2f90c63 4345 "operands[1] = ia64_expand_compare (ORDERED, DImode);")
e57b9d65 4346
c65ebc55
JW
4347;; Don't allow memory as destination here, because cmov/cmov/st is more
4348;; efficient than mov/mov/cst/cst.
4349
0551c32d
RH
4350(define_insn_and_split "*sne_internal"
4351 [(set (match_operand:DI 0 "gr_register_operand" "=r")
f2f90c63 4352 (ne:DI (match_operand:BI 1 "register_operand" "c")
c65ebc55
JW
4353 (const_int 0)))]
4354 ""
4355 "#"
c65ebc55 4356 "reload_completed"
f2f90c63
RH
4357 [(cond_exec (ne (match_dup 1) (const_int 0))
4358 (set (match_dup 0) (const_int 1)))
4359 (cond_exec (eq (match_dup 1) (const_int 0))
4360 (set (match_dup 0) (const_int 0)))]
0551c32d 4361 ""
52e12ad0 4362 [(set_attr "itanium_class" "unknown")])
c65ebc55 4363
0551c32d
RH
4364(define_insn_and_split "*seq_internal"
4365 [(set (match_operand:DI 0 "gr_register_operand" "=r")
f2f90c63 4366 (eq:DI (match_operand:BI 1 "register_operand" "c")
c65ebc55
JW
4367 (const_int 0)))]
4368 ""
4369 "#"
c65ebc55 4370 "reload_completed"
f2f90c63
RH
4371 [(cond_exec (ne (match_dup 1) (const_int 0))
4372 (set (match_dup 0) (const_int 0)))
4373 (cond_exec (eq (match_dup 1) (const_int 0))
4374 (set (match_dup 0) (const_int 1)))]
0551c32d 4375 ""
52e12ad0 4376 [(set_attr "itanium_class" "unknown")])
c65ebc55
JW
4377\f
4378;; ::::::::::::::::::::
4379;; ::
4380;; :: Conditional move instructions.
4381;; ::
4382;; ::::::::::::::::::::
4383
4384;; ??? Add movXXcc patterns?
4385
c65ebc55
JW
4386;;
4387;; DImode if_then_else patterns.
4388;;
4389
75cdbeb8 4390(define_insn "*cmovdi_internal"
f2f90c63 4391 [(set (match_operand:DI 0 "destination_operand"
cd5c4048 4392 "= r, r, r, r, r, r, r, r, r, r, m, Q, *f,*b,*d*e")
e5bde68a 4393 (if_then_else:DI
f2f90c63
RH
4394 (match_operator 4 "predicate_operator"
4395 [(match_operand:BI 1 "register_operand"
cd5c4048 4396 "c,c,c,c,c,c,c,c,c,c,c,c,c,c,c")
e5bde68a 4397 (const_int 0)])
f2f90c63 4398 (match_operand:DI 2 "move_operand"
cd5c4048 4399 "rim, *f, *b,*d*e,rim,rim, rim,*f,*b,*d*e,rO,*f,rOQ,rO, rK")
f2f90c63 4400 (match_operand:DI 3 "move_operand"
cd5c4048 4401 "rim,rim,rim, rim, *f, *b,*d*e,*f,*b,*d*e,rO,*f,rOQ,rO, rK")))]
aebf2462 4402 "ia64_move_ok (operands[0], operands[2])
f2f90c63 4403 && ia64_move_ok (operands[0], operands[3])"
1d5d7a21 4404 { abort (); }
75cdbeb8
RH
4405 [(set_attr "predicable" "no")])
4406
4407(define_split
f2f90c63 4408 [(set (match_operand 0 "destination_operand" "")
75cdbeb8 4409 (if_then_else
f2f90c63
RH
4410 (match_operator 4 "predicate_operator"
4411 [(match_operand:BI 1 "register_operand" "")
75cdbeb8 4412 (const_int 0)])
f2f90c63
RH
4413 (match_operand 2 "move_operand" "")
4414 (match_operand 3 "move_operand" "")))]
3b572406
RH
4415 "reload_completed"
4416 [(const_int 0)]
e5bde68a 4417{
21515593
RH
4418 bool emitted_something = false;
4419 rtx dest = operands[0];
4420 rtx srct = operands[2];
4421 rtx srcf = operands[3];
4422 rtx cond = operands[4];
2f937369 4423
21515593 4424 if (! rtx_equal_p (dest, srct))
e5bde68a 4425 {
21515593
RH
4426 ia64_emit_cond_move (dest, srct, cond);
4427 emitted_something = true;
e5bde68a 4428 }
21515593 4429 if (! rtx_equal_p (dest, srcf))
3b572406 4430 {
21515593
RH
4431 cond = gen_rtx_fmt_ee (GET_CODE (cond) == NE ? EQ : NE,
4432 VOIDmode, operands[1], const0_rtx);
4433 ia64_emit_cond_move (dest, srcf, cond);
4434 emitted_something = true;
3b572406 4435 }
2f937369 4436 if (! emitted_something)
f9974026 4437 emit_note (NOTE_INSN_DELETED);
3b572406 4438 DONE;
1d5d7a21 4439})
c65ebc55
JW
4440
4441;; Absolute value pattern.
4442
4443(define_insn "*absdi2_internal"
0551c32d 4444 [(set (match_operand:DI 0 "gr_register_operand" "=r,r")
e5bde68a 4445 (if_then_else:DI
f2f90c63
RH
4446 (match_operator 4 "predicate_operator"
4447 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4448 (const_int 0)])
0551c32d
RH
4449 (neg:DI (match_operand:DI 2 "gr_reg_or_22bit_operand" "rI,rI"))
4450 (match_operand:DI 3 "gr_reg_or_22bit_operand" "0,rI")))]
c65ebc55 4451 ""
e5bde68a 4452 "#"
52e12ad0 4453 [(set_attr "itanium_class" "ialu,unknown")
3b572406 4454 (set_attr "predicable" "no")])
c65ebc55
JW
4455
4456(define_split
4457 [(set (match_operand:DI 0 "register_operand" "")
e5bde68a 4458 (if_then_else:DI
f2f90c63
RH
4459 (match_operator 4 "predicate_operator"
4460 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4461 (const_int 0)])
0551c32d
RH
4462 (neg:DI (match_operand:DI 2 "gr_reg_or_22bit_operand" ""))
4463 (match_operand:DI 3 "gr_reg_or_22bit_operand" "")))]
e5bde68a
RH
4464 "reload_completed && rtx_equal_p (operands[0], operands[3])"
4465 [(cond_exec
4466 (match_dup 4)
4467 (set (match_dup 0)
4468 (neg:DI (match_dup 2))))]
c65ebc55
JW
4469 "")
4470
e5bde68a
RH
4471(define_split
4472 [(set (match_operand:DI 0 "register_operand" "")
4473 (if_then_else:DI
f2f90c63
RH
4474 (match_operator 4 "predicate_operator"
4475 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4476 (const_int 0)])
0551c32d
RH
4477 (neg:DI (match_operand:DI 2 "gr_reg_or_22bit_operand" ""))
4478 (match_operand:DI 3 "gr_reg_or_22bit_operand" "")))]
e5bde68a
RH
4479 "reload_completed"
4480 [(cond_exec
4481 (match_dup 4)
4482 (set (match_dup 0) (neg:DI (match_dup 2))))
4483 (cond_exec
4484 (match_dup 5)
4485 (set (match_dup 0) (match_dup 3)))]
e5bde68a
RH
4486{
4487 operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[4]) == NE ? EQ : NE,
f2f90c63 4488 VOIDmode, operands[1], const0_rtx);
1d5d7a21 4489})
c65ebc55
JW
4490
4491;;
4492;; SImode if_then_else patterns.
4493;;
4494
75cdbeb8 4495(define_insn "*cmovsi_internal"
f2f90c63 4496 [(set (match_operand:SI 0 "destination_operand" "=r,m,*f,r,m,*f,r,m,*f")
e5bde68a 4497 (if_then_else:SI
f2f90c63
RH
4498 (match_operator 4 "predicate_operator"
4499 [(match_operand:BI 1 "register_operand" "c,c,c,c,c,c,c,c,c")
e5bde68a 4500 (const_int 0)])
f2f90c63 4501 (match_operand:SI 2 "move_operand"
3b572406 4502 "0,0,0,rim*f,rO,rO,rim*f,rO,rO")
f2f90c63 4503 (match_operand:SI 3 "move_operand"
3b572406 4504 "rim*f,rO,rO,0,0,0,rim*f,rO,rO")))]
aebf2462 4505 "ia64_move_ok (operands[0], operands[2])
f2f90c63 4506 && ia64_move_ok (operands[0], operands[3])"
1d5d7a21 4507 { abort (); }
3b572406 4508 [(set_attr "predicable" "no")])
c65ebc55
JW
4509
4510(define_insn "*abssi2_internal"
0551c32d 4511 [(set (match_operand:SI 0 "gr_register_operand" "=r,r")
e5bde68a 4512 (if_then_else:SI
f2f90c63
RH
4513 (match_operator 4 "predicate_operator"
4514 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4515 (const_int 0)])
0551c32d
RH
4516 (neg:SI (match_operand:SI 3 "gr_reg_or_22bit_operand" "rI,rI"))
4517 (match_operand:SI 2 "gr_reg_or_22bit_operand" "0,rI")))]
c65ebc55 4518 ""
e5bde68a 4519 "#"
52e12ad0 4520 [(set_attr "itanium_class" "ialu,unknown")
3b572406 4521 (set_attr "predicable" "no")])
c65ebc55
JW
4522
4523(define_split
4524 [(set (match_operand:SI 0 "register_operand" "")
e5bde68a 4525 (if_then_else:SI
f2f90c63
RH
4526 (match_operator 4 "predicate_operator"
4527 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4528 (const_int 0)])
0551c32d
RH
4529 (neg:SI (match_operand:SI 2 "gr_reg_or_22bit_operand" ""))
4530 (match_operand:SI 3 "gr_reg_or_22bit_operand" "")))]
e5bde68a
RH
4531 "reload_completed && rtx_equal_p (operands[0], operands[3])"
4532 [(cond_exec
4533 (match_dup 4)
4534 (set (match_dup 0)
4535 (neg:SI (match_dup 2))))]
c65ebc55
JW
4536 "")
4537
e5bde68a
RH
4538(define_split
4539 [(set (match_operand:SI 0 "register_operand" "")
4540 (if_then_else:SI
f2f90c63
RH
4541 (match_operator 4 "predicate_operator"
4542 [(match_operand:BI 1 "register_operand" "c,c")
e5bde68a 4543 (const_int 0)])
0551c32d
RH
4544 (neg:SI (match_operand:SI 2 "gr_reg_or_22bit_operand" ""))
4545 (match_operand:SI 3 "gr_reg_or_22bit_operand" "")))]
e5bde68a
RH
4546 "reload_completed"
4547 [(cond_exec
4548 (match_dup 4)
4549 (set (match_dup 0) (neg:SI (match_dup 2))))
4550 (cond_exec
4551 (match_dup 5)
4552 (set (match_dup 0) (match_dup 3)))]
e5bde68a
RH
4553{
4554 operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[4]) == NE ? EQ : NE,
f2f90c63 4555 VOIDmode, operands[1], const0_rtx);
1d5d7a21 4556})
e5bde68a 4557
7dcc803e 4558(define_insn_and_split "*cond_opsi2_internal"
acb0638d
BS
4559 [(set (match_operand:SI 0 "gr_register_operand" "=r")
4560 (match_operator:SI 5 "condop_operator"
4561 [(if_then_else:SI
4562 (match_operator 6 "predicate_operator"
4563 [(match_operand:BI 1 "register_operand" "c")
4564 (const_int 0)])
4565 (match_operand:SI 2 "gr_register_operand" "r")
4566 (match_operand:SI 3 "gr_register_operand" "r"))
4567 (match_operand:SI 4 "gr_register_operand" "r")]))]
4568 ""
4569 "#"
acb0638d
BS
4570 "reload_completed"
4571 [(cond_exec
4572 (match_dup 6)
4573 (set (match_dup 0) (match_op_dup:SI 5 [(match_dup 2) (match_dup 4)])))
4574 (cond_exec
4575 (match_dup 7)
4576 (set (match_dup 0) (match_op_dup:SI 5 [(match_dup 3) (match_dup 4)])))]
acb0638d
BS
4577{
4578 operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[6]) == NE ? EQ : NE,
4579 VOIDmode, operands[1], const0_rtx);
1d5d7a21 4580}
7dcc803e
BS
4581 [(set_attr "itanium_class" "ialu")
4582 (set_attr "predicable" "no")])
4583
acb0638d 4584
7dcc803e 4585(define_insn_and_split "*cond_opsi2_internal_b"
acb0638d
BS
4586 [(set (match_operand:SI 0 "gr_register_operand" "=r")
4587 (match_operator:SI 5 "condop_operator"
4588 [(match_operand:SI 4 "gr_register_operand" "r")
4589 (if_then_else:SI
4590 (match_operator 6 "predicate_operator"
4591 [(match_operand:BI 1 "register_operand" "c")
4592 (const_int 0)])
4593 (match_operand:SI 2 "gr_register_operand" "r")
4594 (match_operand:SI 3 "gr_register_operand" "r"))]))]
4595 ""
4596 "#"
acb0638d
BS
4597 "reload_completed"
4598 [(cond_exec
4599 (match_dup 6)
4600 (set (match_dup 0) (match_op_dup:SI 5 [(match_dup 4) (match_dup 2)])))
4601 (cond_exec
4602 (match_dup 7)
4603 (set (match_dup 0) (match_op_dup:SI 5 [(match_dup 4) (match_dup 3)])))]
acb0638d
BS
4604{
4605 operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[6]) == NE ? EQ : NE,
4606 VOIDmode, operands[1], const0_rtx);
1d5d7a21 4607}
7dcc803e
BS
4608 [(set_attr "itanium_class" "ialu")
4609 (set_attr "predicable" "no")])
acb0638d 4610
c65ebc55
JW
4611\f
4612;; ::::::::::::::::::::
4613;; ::
4614;; :: Call and branch instructions
4615;; ::
4616;; ::::::::::::::::::::
4617
4618;; Subroutine call instruction returning no value. Operand 0 is the function
4619;; to call; operand 1 is the number of bytes of arguments pushed (in mode
4620;; `SImode', except it is normally a `const_int'); operand 2 is the number of
4621;; registers used as operands.
4622
4623;; On most machines, operand 2 is not actually stored into the RTL pattern. It
4624;; is supplied for the sake of some RISC machines which need to put this
4625;; information into the assembler code; they can put it in the RTL instead of
4626;; operand 1.
4627
4628(define_expand "call"
4629 [(use (match_operand:DI 0 "" ""))
4630 (use (match_operand 1 "" ""))
4631 (use (match_operand 2 "" ""))
4632 (use (match_operand 3 "" ""))]
4633 ""
c65ebc55 4634{
599aedd9 4635 ia64_expand_call (NULL_RTX, operands[0], operands[2], false);
c65ebc55 4636 DONE;
1d5d7a21 4637})
c65ebc55 4638
2ed4af6f
RH
4639(define_expand "sibcall"
4640 [(use (match_operand:DI 0 "" ""))
4641 (use (match_operand 1 "" ""))
4642 (use (match_operand 2 "" ""))
4643 (use (match_operand 3 "" ""))]
c65ebc55 4644 ""
c65ebc55 4645{
599aedd9 4646 ia64_expand_call (NULL_RTX, operands[0], operands[2], true);
2ed4af6f 4647 DONE;
1d5d7a21 4648})
c65ebc55 4649
c65ebc55 4650;; Subroutine call instruction returning a value. Operand 0 is the hard
2ed4af6f
RH
4651;; register in which the value is returned. There are three more operands,
4652;; the same as the three operands of the `call' instruction (but with numbers
c65ebc55 4653;; increased by one).
2ed4af6f 4654;;
c65ebc55
JW
4655;; Subroutines that return `BLKmode' objects use the `call' insn.
4656
4657(define_expand "call_value"
4658 [(use (match_operand 0 "" ""))
4659 (use (match_operand:DI 1 "" ""))
4660 (use (match_operand 2 "" ""))
4661 (use (match_operand 3 "" ""))
4662 (use (match_operand 4 "" ""))]
4663 ""
c65ebc55 4664{
599aedd9 4665 ia64_expand_call (operands[0], operands[1], operands[3], false);
c65ebc55 4666 DONE;
1d5d7a21 4667})
c65ebc55 4668
2ed4af6f
RH
4669(define_expand "sibcall_value"
4670 [(use (match_operand 0 "" ""))
4671 (use (match_operand:DI 1 "" ""))
4672 (use (match_operand 2 "" ""))
4673 (use (match_operand 3 "" ""))
4674 (use (match_operand 4 "" ""))]
c65ebc55 4675 ""
c65ebc55 4676{
599aedd9 4677 ia64_expand_call (operands[0], operands[1], operands[3], true);
2ed4af6f 4678 DONE;
1d5d7a21 4679})
c65ebc55 4680
c65ebc55
JW
4681;; Call subroutine returning any type.
4682
4683(define_expand "untyped_call"
4684 [(parallel [(call (match_operand 0 "" "")
4685 (const_int 0))
4686 (match_operand 1 "" "")
4687 (match_operand 2 "" "")])]
4688 ""
c65ebc55
JW
4689{
4690 int i;
4691
4692 emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx));
4693
4694 for (i = 0; i < XVECLEN (operands[2], 0); i++)
4695 {
4696 rtx set = XVECEXP (operands[2], 0, i);
4697 emit_move_insn (SET_DEST (set), SET_SRC (set));
4698 }
4699
4700 /* The optimizer does not know that the call sets the function value
4701 registers we stored in the result block. We avoid problems by
4702 claiming that all hard registers are used and clobbered at this
4703 point. */
4704 emit_insn (gen_blockage ());
4705
4706 DONE;
1d5d7a21 4707})
c65ebc55 4708
599aedd9
RH
4709(define_insn "call_nogp"
4710 [(call (mem:DI (match_operand:DI 0 "call_operand" "?b,i"))
4711 (const_int 0))
4712 (clobber (match_operand:DI 1 "register_operand" "=b,b"))]
2ed4af6f 4713 ""
599aedd9 4714 "br.call%+.many %1 = %0"
52e12ad0 4715 [(set_attr "itanium_class" "br,scall")])
2ed4af6f 4716
599aedd9 4717(define_insn "call_value_nogp"
2ed4af6f 4718 [(set (match_operand 0 "" "")
599aedd9
RH
4719 (call (mem:DI (match_operand:DI 1 "call_operand" "?b,i"))
4720 (const_int 0)))
4721 (clobber (match_operand:DI 2 "register_operand" "=b,b"))]
2ed4af6f 4722 ""
599aedd9 4723 "br.call%+.many %2 = %1"
52e12ad0 4724 [(set_attr "itanium_class" "br,scall")])
2ed4af6f 4725
599aedd9
RH
4726(define_insn "sibcall_nogp"
4727 [(call (mem:DI (match_operand:DI 0 "call_operand" "?b,i"))
4728 (const_int 0))]
2ed4af6f
RH
4729 ""
4730 "br%+.many %0"
52e12ad0 4731 [(set_attr "itanium_class" "br,scall")])
2ed4af6f 4732
599aedd9 4733(define_insn "call_gp"
15d11f13 4734 [(call (mem:DI (match_operand 0 "call_operand" "?r,i"))
599aedd9
RH
4735 (const_int 1))
4736 (clobber (match_operand:DI 1 "register_operand" "=b,b"))
4737 (clobber (match_scratch:DI 2 "=&r,X"))
4738 (clobber (match_scratch:DI 3 "=b,X"))]
2ed4af6f 4739 ""
599aedd9 4740 "#"
52e12ad0 4741 [(set_attr "itanium_class" "br,scall")])
2ed4af6f 4742
599aedd9
RH
4743;; Irritatingly, we don't have access to INSN within the split body.
4744;; See commentary in ia64_split_call as to why these aren't peep2.
4745(define_split
4746 [(call (mem (match_operand 0 "call_operand" ""))
4747 (const_int 1))
4748 (clobber (match_operand:DI 1 "register_operand" ""))
4749 (clobber (match_scratch:DI 2 ""))
4750 (clobber (match_scratch:DI 3 ""))]
4751 "reload_completed && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
4752 [(const_int 0)]
4753{
4754 ia64_split_call (NULL_RTX, operands[0], operands[1], operands[2],
4755 operands[3], true, false);
4756 DONE;
4757})
4758
4759(define_split
4760 [(call (mem (match_operand 0 "call_operand" ""))
4761 (const_int 1))
4762 (clobber (match_operand:DI 1 "register_operand" ""))
4763 (clobber (match_scratch:DI 2 ""))
4764 (clobber (match_scratch:DI 3 ""))]
4765 "reload_completed"
4766 [(const_int 0)]
4767{
4768 ia64_split_call (NULL_RTX, operands[0], operands[1], operands[2],
4769 operands[3], false, false);
4770 DONE;
4771})
4772
4773(define_insn "call_value_gp"
2ed4af6f 4774 [(set (match_operand 0 "" "")
599aedd9
RH
4775 (call (mem:DI (match_operand:DI 1 "call_operand" "?r,i"))
4776 (const_int 1)))
4777 (clobber (match_operand:DI 2 "register_operand" "=b,b"))
4778 (clobber (match_scratch:DI 3 "=&r,X"))
4779 (clobber (match_scratch:DI 4 "=b,X"))]
2ed4af6f 4780 ""
599aedd9 4781 "#"
52e12ad0 4782 [(set_attr "itanium_class" "br,scall")])
2ed4af6f 4783
599aedd9
RH
4784(define_split
4785 [(set (match_operand 0 "" "")
4786 (call (mem:DI (match_operand:DI 1 "call_operand" ""))
4787 (const_int 1)))
4788 (clobber (match_operand:DI 2 "register_operand" ""))
4789 (clobber (match_scratch:DI 3 ""))
4790 (clobber (match_scratch:DI 4 ""))]
4791 "reload_completed && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
4792 [(const_int 0)]
4793{
4794 ia64_split_call (operands[0], operands[1], operands[2], operands[3],
4795 operands[4], true, false);
4796 DONE;
4797})
4798
4799(define_split
4800 [(set (match_operand 0 "" "")
4801 (call (mem:DI (match_operand:DI 1 "call_operand" ""))
4802 (const_int 1)))
4803 (clobber (match_operand:DI 2 "register_operand" ""))
4804 (clobber (match_scratch:DI 3 ""))
4805 (clobber (match_scratch:DI 4 ""))]
4806 "reload_completed"
4807 [(const_int 0)]
4808{
4809 ia64_split_call (operands[0], operands[1], operands[2], operands[3],
4810 operands[4], false, false);
4811 DONE;
4812})
4813
4814(define_insn_and_split "sibcall_gp"
4815 [(call (mem:DI (match_operand:DI 0 "call_operand" "?r,i"))
4816 (const_int 1))
4817 (clobber (match_scratch:DI 1 "=&r,X"))
4818 (clobber (match_scratch:DI 2 "=b,X"))]
2ed4af6f 4819 ""
599aedd9
RH
4820 "#"
4821 "reload_completed"
4822 [(const_int 0)]
4823{
4824 ia64_split_call (NULL_RTX, operands[0], NULL_RTX, operands[1],
4825 operands[2], true, true);
4826 DONE;
4827}
52e12ad0 4828 [(set_attr "itanium_class" "br")])
2ed4af6f 4829
c65ebc55
JW
4830(define_insn "return_internal"
4831 [(return)
4832 (use (match_operand:DI 0 "register_operand" "b"))]
4833 ""
4834 "br.ret.sptk.many %0"
52e12ad0 4835 [(set_attr "itanium_class" "br")])
c65ebc55
JW
4836
4837(define_insn "return"
4838 [(return)]
4839 "ia64_direct_return ()"
4840 "br.ret.sptk.many rp"
52e12ad0 4841 [(set_attr "itanium_class" "br")])
c65ebc55 4842
6b6c1201 4843(define_insn "*return_true"
c65ebc55 4844 [(set (pc)
6b6c1201 4845 (if_then_else (match_operator 0 "predicate_operator"
f2f90c63 4846 [(match_operand:BI 1 "register_operand" "c")
6b6c1201 4847 (const_int 0)])
c65ebc55
JW
4848 (return)
4849 (pc)))]
4850 "ia64_direct_return ()"
13da91fd 4851 "(%J0) br.ret%+.many rp"
52e12ad0 4852 [(set_attr "itanium_class" "br")
e5bde68a 4853 (set_attr "predicable" "no")])
c65ebc55 4854
6b6c1201 4855(define_insn "*return_false"
c65ebc55 4856 [(set (pc)
6b6c1201 4857 (if_then_else (match_operator 0 "predicate_operator"
f2f90c63 4858 [(match_operand:BI 1 "register_operand" "c")
6b6c1201 4859 (const_int 0)])
c65ebc55
JW
4860 (pc)
4861 (return)))]
4862 "ia64_direct_return ()"
13da91fd 4863 "(%j0) br.ret%+.many rp"
52e12ad0 4864 [(set_attr "itanium_class" "br")
e5bde68a 4865 (set_attr "predicable" "no")])
c65ebc55
JW
4866
4867(define_insn "jump"
4868 [(set (pc) (label_ref (match_operand 0 "" "")))]
4869 ""
4870 "br %l0"
52e12ad0 4871 [(set_attr "itanium_class" "br")])
c65ebc55
JW
4872
4873(define_insn "indirect_jump"
4874 [(set (pc) (match_operand:DI 0 "register_operand" "b"))]
4875 ""
4876 "br %0"
52e12ad0 4877 [(set_attr "itanium_class" "br")])
c65ebc55
JW
4878
4879(define_expand "tablejump"
340f7e7c
RH
4880 [(parallel [(set (pc) (match_operand:DI 0 "memory_operand" ""))
4881 (use (label_ref (match_operand 1 "" "")))])]
c65ebc55 4882 ""
c65ebc55 4883{
340f7e7c
RH
4884 rtx op0 = operands[0];
4885 rtx addr;
4886
4887 /* ??? Bother -- do_tablejump is "helpful" and pulls the table
4888 element into a register without bothering to see whether that
4889 is necessary given the operand predicate. Check for MEM just
4890 in case someone fixes this. */
4891 if (GET_CODE (op0) == MEM)
4892 addr = XEXP (op0, 0);
4893 else
4894 {
4895 /* Otherwise, cheat and guess that the previous insn in the
4896 stream was the memory load. Grab the address from that.
4897 Note we have to momentarily pop out of the sequence started
4898 by the insn-emit wrapper in order to grab the last insn. */
4899 rtx last, set;
4900
4901 end_sequence ();
4902 last = get_last_insn ();
4903 start_sequence ();
4904 set = single_set (last);
4905
4906 if (! rtx_equal_p (SET_DEST (set), op0)
4907 || GET_CODE (SET_SRC (set)) != MEM)
4908 abort ();
4909 addr = XEXP (SET_SRC (set), 0);
4910 if (rtx_equal_p (addr, op0))
4911 abort ();
4912 }
c65ebc55 4913
340f7e7c
RH
4914 /* Jump table elements are stored pc-relative. That is, a displacement
4915 from the entry to the label. Thus to convert to an absolute address
4916 we add the address of the memory from which the value is loaded. */
4917 operands[0] = expand_simple_binop (DImode, PLUS, op0, addr,
4918 NULL_RTX, 1, OPTAB_DIRECT);
4919})
c65ebc55 4920
340f7e7c 4921(define_insn "*tablejump_internal"
c65ebc55
JW
4922 [(set (pc) (match_operand:DI 0 "register_operand" "b"))
4923 (use (label_ref (match_operand 1 "" "")))]
4924 ""
4925 "br %0"
52e12ad0 4926 [(set_attr "itanium_class" "br")])
c65ebc55
JW
4927
4928\f
4929;; ::::::::::::::::::::
4930;; ::
4931;; :: Prologue and Epilogue instructions
4932;; ::
4933;; ::::::::::::::::::::
4934
4935(define_expand "prologue"
4936 [(const_int 1)]
4937 ""
c65ebc55
JW
4938{
4939 ia64_expand_prologue ();
4940 DONE;
1d5d7a21 4941})
c65ebc55
JW
4942
4943(define_expand "epilogue"
2ed4af6f
RH
4944 [(return)]
4945 ""
2ed4af6f
RH
4946{
4947 ia64_expand_epilogue (0);
4948 DONE;
1d5d7a21 4949})
2ed4af6f
RH
4950
4951(define_expand "sibcall_epilogue"
4952 [(return)]
c65ebc55 4953 ""
c65ebc55 4954{
2ed4af6f 4955 ia64_expand_epilogue (1);
c65ebc55 4956 DONE;
1d5d7a21 4957})
c65ebc55
JW
4958
4959;; This prevents the scheduler from moving the SP decrement past FP-relative
4960;; stack accesses. This is the same as adddi3 plus the extra set.
4961
4962(define_insn "prologue_allocate_stack"
4963 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
4964 (plus:DI (match_operand:DI 1 "register_operand" "%r,r,a")
0551c32d 4965 (match_operand:DI 2 "gr_reg_or_22bit_operand" "r,I,J")))
bdbe5b8d 4966 (set (match_operand:DI 3 "register_operand" "+r,r,r")
c65ebc55
JW
4967 (match_dup 3))]
4968 ""
4969 "@
1d5d7a21
RH
4970 add %0 = %1, %2
4971 adds %0 = %2, %1
4972 addl %0 = %2, %1"
52e12ad0 4973 [(set_attr "itanium_class" "ialu")])
c65ebc55
JW
4974
4975;; This prevents the scheduler from moving the SP restore past FP-relative
4976;; stack accesses. This is similar to movdi plus the extra set.
4977
4978(define_insn "epilogue_deallocate_stack"
4979 [(set (match_operand:DI 0 "register_operand" "=r")
4980 (match_operand:DI 1 "register_operand" "+r"))
4981 (set (match_dup 1) (match_dup 1))]
4982 ""
4983 "mov %0 = %1"
52e12ad0 4984 [(set_attr "itanium_class" "ialu")])
c65ebc55 4985
1d5d7a21
RH
4986;; As USE insns aren't meaningful after reload, this is used instead
4987;; to prevent deleting instructions setting registers for EH handling
4988(define_insn "prologue_use"
4989 [(unspec:DI [(match_operand:DI 0 "register_operand" "")]
4990 UNSPEC_PROLOGUE_USE)]
4991 ""
4992 ""
4993 [(set_attr "itanium_class" "ignore")
4994 (set_attr "predicable" "no")])
4995
c65ebc55
JW
4996;; Allocate a new register frame.
4997
4998(define_insn "alloc"
4999 [(set (match_operand:DI 0 "register_operand" "=r")
086c0f96 5000 (unspec_volatile:DI [(const_int 0)] UNSPECV_ALLOC))
c65ebc55
JW
5001 (use (match_operand:DI 1 "const_int_operand" "i"))
5002 (use (match_operand:DI 2 "const_int_operand" "i"))
5003 (use (match_operand:DI 3 "const_int_operand" "i"))
5004 (use (match_operand:DI 4 "const_int_operand" "i"))]
5005 ""
5006 "alloc %0 = ar.pfs, %1, %2, %3, %4"
52e12ad0 5007 [(set_attr "itanium_class" "syst_m0")
e5bde68a 5008 (set_attr "predicable" "no")])
c65ebc55 5009
97e242b0
RH
5010;; Modifies ar.unat
5011(define_expand "gr_spill"
870f9ec0
RH
5012 [(parallel [(set (match_operand:DI 0 "memory_operand" "=m")
5013 (unspec:DI [(match_operand:DI 1 "register_operand" "r")
086c0f96
RH
5014 (match_operand:DI 2 "const_int_operand" "")]
5015 UNSPEC_GR_SPILL))
870f9ec0 5016 (clobber (match_dup 3))])]
97e242b0 5017 ""
870f9ec0 5018 "operands[3] = gen_rtx_REG (DImode, AR_UNAT_REGNUM);")
97e242b0 5019
870f9ec0 5020(define_insn "gr_spill_internal"
c65ebc55 5021 [(set (match_operand:DI 0 "memory_operand" "=m")
870f9ec0 5022 (unspec:DI [(match_operand:DI 1 "register_operand" "r")
086c0f96
RH
5023 (match_operand:DI 2 "const_int_operand" "")]
5024 UNSPEC_GR_SPILL))
870f9ec0 5025 (clobber (match_operand:DI 3 "register_operand" ""))]
c65ebc55 5026 ""
2130b7fb 5027{
1d5d7a21
RH
5028 /* Note that we use a C output pattern here to avoid the predicate
5029 being automatically added before the .mem.offset directive. */
5030 return ".mem.offset %2, 0\;%,st8.spill %0 = %1%P0";
5031}
52e12ad0 5032 [(set_attr "itanium_class" "st")])
c65ebc55 5033
97e242b0
RH
5034;; Reads ar.unat
5035(define_expand "gr_restore"
870f9ec0
RH
5036 [(parallel [(set (match_operand:DI 0 "register_operand" "=r")
5037 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")
086c0f96
RH
5038 (match_operand:DI 2 "const_int_operand" "")]
5039 UNSPEC_GR_RESTORE))
870f9ec0 5040 (use (match_dup 3))])]
97e242b0 5041 ""
870f9ec0 5042 "operands[3] = gen_rtx_REG (DImode, AR_UNAT_REGNUM);")
97e242b0 5043
870f9ec0 5044(define_insn "gr_restore_internal"
c65ebc55 5045 [(set (match_operand:DI 0 "register_operand" "=r")
870f9ec0 5046 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")
086c0f96
RH
5047 (match_operand:DI 2 "const_int_operand" "")]
5048 UNSPEC_GR_RESTORE))
870f9ec0 5049 (use (match_operand:DI 3 "register_operand" ""))]
c65ebc55 5050 ""
1d5d7a21 5051 { return ".mem.offset %2, 0\;%,ld8.fill %0 = %1%P1"; }
52e12ad0 5052 [(set_attr "itanium_class" "ld")])
c65ebc55
JW
5053
5054(define_insn "fr_spill"
3f622353 5055 [(set (match_operand:TF 0 "memory_operand" "=m")
086c0f96
RH
5056 (unspec:TF [(match_operand:TF 1 "register_operand" "f")]
5057 UNSPEC_FR_SPILL))]
c65ebc55
JW
5058 ""
5059 "stf.spill %0 = %1%P0"
52e12ad0 5060 [(set_attr "itanium_class" "stf")])
c65ebc55
JW
5061
5062(define_insn "fr_restore"
3f622353 5063 [(set (match_operand:TF 0 "register_operand" "=f")
086c0f96
RH
5064 (unspec:TF [(match_operand:TF 1 "memory_operand" "m")]
5065 UNSPEC_FR_RESTORE))]
c65ebc55
JW
5066 ""
5067 "ldf.fill %0 = %1%P1"
52e12ad0 5068 [(set_attr "itanium_class" "fld")])
c65ebc55 5069
0024a804
JW
5070;; ??? The explicit stop is not ideal. It would be better if
5071;; rtx_needs_barrier took care of this, but this is something that can be
5072;; fixed later. This avoids an RSE DV.
5073
0c96007e
AM
5074(define_insn "bsp_value"
5075 [(set (match_operand:DI 0 "register_operand" "=r")
086c0f96 5076 (unspec:DI [(const_int 0)] UNSPEC_BSP_VALUE))]
0c96007e 5077 ""
582d11e6
JW
5078 "*
5079{
5080 return \";;\;%,mov %0 = ar.bsp\";
5081}"
52e12ad0 5082 [(set_attr "itanium_class" "frar_i")])
0c96007e
AM
5083
5084(define_insn "set_bsp"
086c0f96
RH
5085 [(unspec_volatile [(match_operand:DI 0 "register_operand" "r")]
5086 UNSPECV_SET_BSP)]
0c96007e 5087 ""
1d5d7a21
RH
5088 "flushrs
5089 mov r19=ar.rsc
5090 ;;
5091 and r19=0x1c,r19
5092 ;;
5093 mov ar.rsc=r19
5094 ;;
5095 mov ar.bspstore=%0
5096 ;;
5097 or r19=0x3,r19
5098 ;;
5099 loadrs
5100 invala
5101 ;;
5102 mov ar.rsc=r19"
52e12ad0 5103 [(set_attr "itanium_class" "unknown")
e5bde68a 5104 (set_attr "predicable" "no")])
ce152ef8 5105
0024a804
JW
5106;; ??? The explicit stops are not ideal. It would be better if
5107;; rtx_needs_barrier took care of this, but this is something that can be
5108;; fixed later. This avoids an RSE DV.
5109
ce152ef8 5110(define_insn "flushrs"
086c0f96 5111 [(unspec [(const_int 0)] UNSPEC_FLUSHRS)]
ce152ef8 5112 ""
0024a804 5113 ";;\;flushrs\;;;"
582d11e6
JW
5114 [(set_attr "itanium_class" "rse_m")
5115 (set_attr "predicable" "no")])
c65ebc55
JW
5116\f
5117;; ::::::::::::::::::::
5118;; ::
5119;; :: Miscellaneous instructions
5120;; ::
5121;; ::::::::::::::::::::
5122
5123;; ??? Emiting a NOP instruction isn't very useful. This should probably
5124;; be emitting ";;" to force a break in the instruction packing.
5125
5126;; No operation, needed in case the user uses -g but not -O.
5127(define_insn "nop"
5128 [(const_int 0)]
5129 ""
5130 "nop 0"
30028c85 5131 [(set_attr "itanium_class" "nop")])
c65ebc55 5132
2130b7fb
BS
5133(define_insn "nop_m"
5134 [(const_int 1)]
5135 ""
5136 "nop.m 0"
5137 [(set_attr "itanium_class" "nop_m")])
5138
5139(define_insn "nop_i"
5140 [(const_int 2)]
5141 ""
5142 "nop.i 0"
5143 [(set_attr "itanium_class" "nop_i")])
5144
5145(define_insn "nop_f"
5146 [(const_int 3)]
5147 ""
5148 "nop.f 0"
5149 [(set_attr "itanium_class" "nop_f")])
5150
5151(define_insn "nop_b"
5152 [(const_int 4)]
5153 ""
5154 "nop.b 0"
5155 [(set_attr "itanium_class" "nop_b")])
5156
5157(define_insn "nop_x"
5158 [(const_int 5)]
5159 ""
5160 ""
5161 [(set_attr "itanium_class" "nop_x")])
5162
30028c85
VM
5163;; The following insn will be never generated. It is used only by
5164;; insn scheduler to change state before advancing cycle.
5165(define_insn "pre_cycle"
5166 [(const_int 6)]
5167 ""
5168 ""
5169 [(set_attr "itanium_class" "pre_cycle")])
5170
2130b7fb 5171(define_insn "bundle_selector"
086c0f96 5172 [(unspec [(match_operand 0 "const_int_operand" "")] UNSPEC_BUNDLE_SELECTOR)]
2130b7fb 5173 ""
1d5d7a21 5174 { return get_bundle_name (INTVAL (operands[0])); }
2130b7fb
BS
5175 [(set_attr "itanium_class" "ignore")
5176 (set_attr "predicable" "no")])
5177
c65ebc55
JW
5178;; Pseudo instruction that prevents the scheduler from moving code above this
5179;; point.
5180(define_insn "blockage"
086c0f96 5181 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
c65ebc55
JW
5182 ""
5183 ""
52e12ad0 5184 [(set_attr "itanium_class" "ignore")
e5bde68a 5185 (set_attr "predicable" "no")])
c65ebc55
JW
5186
5187(define_insn "insn_group_barrier"
086c0f96
RH
5188 [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
5189 UNSPECV_INSN_GROUP_BARRIER)]
c65ebc55
JW
5190 ""
5191 ";;"
52e12ad0 5192 [(set_attr "itanium_class" "stop_bit")
e5bde68a 5193 (set_attr "predicable" "no")])
c65ebc55 5194
26406018
RH
5195(define_expand "trap"
5196 [(trap_if (const_int 1) (const_int 0))]
5197 ""
5198 "")
5199
5200;; ??? We don't have a match-any slot type. Setting the type to unknown
5201;; produces worse code that setting the slot type to A.
5202
5203(define_insn "*trap"
5204 [(trap_if (const_int 1) (match_operand 0 "const_int_operand" ""))]
5205 ""
5206 "break %0"
5207 [(set_attr "itanium_class" "chk_s")])
5208
5209(define_expand "conditional_trap"
5210 [(trap_if (match_operand 0 "" "") (match_operand 1 "" ""))]
5211 ""
5212{
5213 operands[0] = ia64_expand_compare (GET_CODE (operands[0]), VOIDmode);
5214})
5215
5216(define_insn "*conditional_trap"
5217 [(trap_if (match_operator 0 "predicate_operator"
5218 [(match_operand:BI 1 "register_operand" "c")
5219 (const_int 0)])
5220 (match_operand 2 "const_int_operand" ""))]
5221 ""
5cf63e3f 5222 "(%J0) break %2"
26406018
RH
5223 [(set_attr "itanium_class" "chk_s")
5224 (set_attr "predicable" "no")])
5225
f12f25a7 5226(define_insn "break_f"
086c0f96 5227 [(unspec_volatile [(const_int 0)] UNSPECV_BREAK)]
f12f25a7
RH
5228 ""
5229 "break.f 0"
5230 [(set_attr "itanium_class" "nop_f")])
44eca121
JJ
5231
5232(define_insn "prefetch"
5233 [(prefetch (match_operand:DI 0 "address_operand" "p")
5234 (match_operand:DI 1 "const_int_operand" "n")
5235 (match_operand:DI 2 "const_int_operand" "n"))]
5236 ""
5237{
5238 static const char * const alt[2][4] = {
b3656137 5239 {
92cbea22
L
5240 "%,lfetch.nta [%0]",
5241 "%,lfetch.nt1 [%0]",
5242 "%,lfetch.nt2 [%0]",
5243 "%,lfetch [%0]"
b3656137
KG
5244 },
5245 {
92cbea22
L
5246 "%,lfetch.excl.nta [%0]",
5247 "%,lfetch.excl.nt1 [%0]",
5248 "%,lfetch.excl.nt2 [%0]",
5249 "%,lfetch.excl [%0]"
b3656137 5250 }
44eca121
JJ
5251 };
5252 int i = (INTVAL (operands[1]));
5253 int j = (INTVAL (operands[2]));
5254
5255 if (i != 0 && i != 1)
5256 abort ();
5257 if (j < 0 || j > 3)
5258 abort ();
5259 return alt[i][j];
5260}
5261 [(set_attr "itanium_class" "lfetch")])
c65ebc55
JW
5262\f
5263;; Non-local goto support.
5264
5265(define_expand "save_stack_nonlocal"
5266 [(use (match_operand:OI 0 "memory_operand" ""))
5267 (use (match_operand:DI 1 "register_operand" ""))]
5268 ""
c65ebc55
JW
5269{
5270 emit_library_call (gen_rtx_SYMBOL_REF (Pmode,
5271 \"__ia64_save_stack_nonlocal\"),
5272 0, VOIDmode, 2, XEXP (operands[0], 0), Pmode,
5273 operands[1], Pmode);
5274 DONE;
1d5d7a21 5275})
c65ebc55
JW
5276
5277(define_expand "nonlocal_goto"
5278 [(use (match_operand 0 "general_operand" ""))
5279 (use (match_operand 1 "general_operand" ""))
5280 (use (match_operand 2 "general_operand" ""))
5281 (use (match_operand 3 "general_operand" ""))]
5282 ""
c65ebc55 5283{
c65ebc55 5284 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, \"__ia64_nonlocal_goto\"),
8206fc89 5285 LCT_NORETURN, VOIDmode, 3,
7c2b017c 5286 operands[1], Pmode,
c65ebc55 5287 copy_to_reg (XEXP (operands[2], 0)), Pmode,
7c2b017c 5288 operands[3], Pmode);
c65ebc55
JW
5289 emit_barrier ();
5290 DONE;
1d5d7a21 5291})
c65ebc55 5292
b39eb2f9
RH
5293(define_insn_and_split "builtin_setjmp_receiver"
5294 [(unspec_volatile [(match_operand:DI 0 "" "")] UNSPECV_SETJMP_RECEIVER)]
97e242b0 5295 ""
b39eb2f9
RH
5296 "#"
5297 "reload_completed"
5298 [(const_int 0)]
97e242b0 5299{
599aedd9 5300 ia64_reload_gp ();
c65ebc55 5301 DONE;
1d5d7a21 5302})
c65ebc55 5303
0c96007e
AM
5304(define_expand "eh_epilogue"
5305 [(use (match_operand:DI 0 "register_operand" "r"))
5306 (use (match_operand:DI 1 "register_operand" "r"))
5307 (use (match_operand:DI 2 "register_operand" "r"))]
5308 ""
0c96007e
AM
5309{
5310 rtx bsp = gen_rtx_REG (Pmode, 10);
5311 rtx sp = gen_rtx_REG (Pmode, 9);
5312
5313 if (GET_CODE (operands[0]) != REG || REGNO (operands[0]) != 10)
5314 {
5315 emit_move_insn (bsp, operands[0]);
5316 operands[0] = bsp;
5317 }
5318 if (GET_CODE (operands[2]) != REG || REGNO (operands[2]) != 9)
5319 {
5320 emit_move_insn (sp, operands[2]);
5321 operands[2] = sp;
5322 }
5323 emit_insn (gen_rtx_USE (VOIDmode, sp));
5324 emit_insn (gen_rtx_USE (VOIDmode, bsp));
5325
5326 cfun->machine->ia64_eh_epilogue_sp = sp;
5327 cfun->machine->ia64_eh_epilogue_bsp = bsp;
1d5d7a21 5328})
9525c690
JW
5329\f
5330;; Builtin apply support.
5331
5332(define_expand "restore_stack_nonlocal"
5333 [(use (match_operand:DI 0 "register_operand" ""))
5334 (use (match_operand:OI 1 "memory_operand" ""))]
5335 ""
9525c690
JW
5336{
5337 emit_library_call (gen_rtx_SYMBOL_REF (Pmode,
1d5d7a21 5338 "__ia64_restore_stack_nonlocal"),
9525c690
JW
5339 0, VOIDmode, 1,
5340 copy_to_reg (XEXP (operands[1], 0)), Pmode);
5341 DONE;
1d5d7a21 5342})
9525c690
JW
5343
5344\f
5345;;; Intrinsics support.
c65ebc55 5346
0551c32d
RH
5347(define_expand "mf"
5348 [(set (mem:BLK (match_dup 0))
086c0f96 5349 (unspec:BLK [(mem:BLK (match_dup 0))] UNSPEC_MF))]
0551c32d 5350 ""
0551c32d
RH
5351{
5352 operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (DImode));
5353 MEM_VOLATILE_P (operands[0]) = 1;
1d5d7a21 5354})
0551c32d
RH
5355
5356(define_insn "*mf_internal"
5357 [(set (match_operand:BLK 0 "" "")
086c0f96 5358 (unspec:BLK [(match_operand:BLK 1 "" "")] UNSPEC_MF))]
c65ebc55
JW
5359 ""
5360 "mf"
52e12ad0 5361 [(set_attr "itanium_class" "syst_m")])
c65ebc55
JW
5362
5363(define_insn "fetchadd_acq_si"
0551c32d
RH
5364 [(set (match_operand:SI 0 "gr_register_operand" "=r")
5365 (match_dup 1))
5366 (set (match_operand:SI 1 "not_postinc_memory_operand" "+S")
5367 (unspec:SI [(match_dup 1)
086c0f96
RH
5368 (match_operand:SI 2 "fetchadd_operand" "n")]
5369 UNSPEC_FETCHADD_ACQ))]
c65ebc55
JW
5370 ""
5371 "fetchadd4.acq %0 = %1, %2"
52e12ad0 5372 [(set_attr "itanium_class" "sem")])
c65ebc55
JW
5373
5374(define_insn "fetchadd_acq_di"
0551c32d
RH
5375 [(set (match_operand:DI 0 "gr_register_operand" "=r")
5376 (match_dup 1))
5377 (set (match_operand:DI 1 "not_postinc_memory_operand" "+S")
5378 (unspec:DI [(match_dup 1)
086c0f96
RH
5379 (match_operand:DI 2 "fetchadd_operand" "n")]
5380 UNSPEC_FETCHADD_ACQ))]
c65ebc55
JW
5381 ""
5382 "fetchadd8.acq %0 = %1, %2"
52e12ad0 5383 [(set_attr "itanium_class" "sem")])
c65ebc55
JW
5384
5385(define_insn "cmpxchg_acq_si"
0551c32d
RH
5386 [(set (match_operand:SI 0 "gr_register_operand" "=r")
5387 (match_dup 1))
5388 (set (match_operand:SI 1 "not_postinc_memory_operand" "+S")
5389 (unspec:SI [(match_dup 1)
5390 (match_operand:SI 2 "gr_register_operand" "r")
be565ad7 5391 (match_operand 3 "ar_ccv_reg_operand" "")]
086c0f96 5392 UNSPEC_CMPXCHG_ACQ))]
c65ebc55 5393 ""
97e242b0 5394 "cmpxchg4.acq %0 = %1, %2, %3"
52e12ad0 5395 [(set_attr "itanium_class" "sem")])
c65ebc55
JW
5396
5397(define_insn "cmpxchg_acq_di"
0551c32d
RH
5398 [(set (match_operand:DI 0 "gr_register_operand" "=r")
5399 (match_dup 1))
5400 (set (match_operand:DI 1 "not_postinc_memory_operand" "+S")
5401 (unspec:DI [(match_dup 1)
5402 (match_operand:DI 2 "gr_register_operand" "r")
086c0f96
RH
5403 (match_operand:DI 3 "ar_ccv_reg_operand" "")]
5404 UNSPEC_CMPXCHG_ACQ))]
c65ebc55 5405 ""
97e242b0 5406 "cmpxchg8.acq %0 = %1, %2, %3"
52e12ad0 5407 [(set_attr "itanium_class" "sem")])
c65ebc55 5408
c65ebc55 5409(define_insn "xchgsi"
0551c32d
RH
5410 [(set (match_operand:SI 0 "gr_register_operand" "=r")
5411 (match_operand:SI 1 "not_postinc_memory_operand" "+S"))
c65ebc55 5412 (set (match_dup 1)
0551c32d 5413 (match_operand:SI 2 "gr_register_operand" "r"))]
c65ebc55
JW
5414 ""
5415 "xchg4 %0 = %1, %2"
52e12ad0 5416 [(set_attr "itanium_class" "sem")])
c65ebc55
JW
5417
5418(define_insn "xchgdi"
0551c32d
RH
5419 [(set (match_operand:DI 0 "gr_register_operand" "=r")
5420 (match_operand:DI 1 "not_postinc_memory_operand" "+S"))
c65ebc55 5421 (set (match_dup 1)
0551c32d 5422 (match_operand:DI 2 "gr_register_operand" "r"))]
c65ebc55
JW
5423 ""
5424 "xchg8 %0 = %1, %2"
52e12ad0 5425 [(set_attr "itanium_class" "sem")])
e5bde68a
RH
5426\f
5427;; Predication.
5428
5429(define_cond_exec
5430 [(match_operator 0 "predicate_operator"
f2f90c63 5431 [(match_operand:BI 1 "register_operand" "c")
e5bde68a
RH
5432 (const_int 0)])]
5433 ""
5434 "(%J0)")
3b572406
RH
5435
5436(define_insn "pred_rel_mutex"
f2f90c63 5437 [(set (match_operand:BI 0 "register_operand" "+c")
086c0f96 5438 (unspec:BI [(match_dup 0)] UNSPEC_PRED_REL_MUTEX))]
3b572406 5439 ""
054451ea 5440 ".pred.rel.mutex %0, %I0"
52e12ad0 5441 [(set_attr "itanium_class" "ignore")
3b572406 5442 (set_attr "predicable" "no")])
ca3920ad
JW
5443
5444(define_insn "safe_across_calls_all"
086c0f96 5445 [(unspec_volatile [(const_int 0)] UNSPECV_PSAC_ALL)]
ca3920ad
JW
5446 ""
5447 ".pred.safe_across_calls p1-p63"
52e12ad0 5448 [(set_attr "itanium_class" "ignore")
ca3920ad
JW
5449 (set_attr "predicable" "no")])
5450
5451(define_insn "safe_across_calls_normal"
086c0f96 5452 [(unspec_volatile [(const_int 0)] UNSPECV_PSAC_NORMAL)]
ca3920ad 5453 ""
ca3920ad 5454{
1bc7c5b6 5455 emit_safe_across_calls ();
1d5d7a21
RH
5456 return "";
5457}
52e12ad0 5458 [(set_attr "itanium_class" "ignore")
ca3920ad
JW
5459 (set_attr "predicable" "no")])
5460
6dd12198
SE
5461;; UNSPEC instruction definition to "swizzle" 32 bit pointer into 64 bit
5462;; pointer. This is used by the HP-UX 32 bit mode.
5463
5464(define_insn "ptr_extend"
5465 [(set (match_operand:DI 0 "gr_register_operand" "=r")
086c0f96
RH
5466 (unspec:DI [(match_operand:SI 1 "gr_register_operand" "r")]
5467 UNSPEC_ADDP4))]
6dd12198
SE
5468 ""
5469 "addp4 %0 = 0,%1"
5470 [(set_attr "itanium_class" "ialu")])
5471
e206a74f
SE
5472;;
5473;; Optimizations for ptr_extend
5474
36c216e5 5475(define_insn "ptr_extend_plus_imm"
e206a74f
SE
5476 [(set (match_operand:DI 0 "gr_register_operand" "=r")
5477 (unspec:DI
5478 [(plus:SI (match_operand:SI 1 "basereg_operand" "r")
5479 (match_operand:SI 2 "gr_reg_or_14bit_operand" "rI"))]
086c0f96 5480 UNSPEC_ADDP4))]
08744705 5481 "addp4_optimize_ok (operands[1], operands[2])"
e206a74f
SE
5482 "addp4 %0 = %2, %1"
5483 [(set_attr "itanium_class" "ialu")])
5484
5485(define_insn "*ptr_extend_plus_2"
5486 [(set (match_operand:DI 0 "gr_register_operand" "=r")
5487 (unspec:DI
5488 [(plus:SI (match_operand:SI 1 "gr_register_operand" "r")
5489 (match_operand:SI 2 "basereg_operand" "r"))]
086c0f96 5490 UNSPEC_ADDP4))]
08744705 5491 "addp4_optimize_ok (operands[1], operands[2])"
e206a74f
SE
5492 "addp4 %0 = %1, %2"
5493 [(set_attr "itanium_class" "ialu")])
This page took 1.585538 seconds and 5 git commands to generate.