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