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