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