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