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