* config/xtensa/lib1funcs.asm (__mulsi3): Use symbolic name for ACCLO.
[official-gcc.git] / gcc / config / xtensa / xtensa.md
blob507465124105f280f4ca06708f9e1b2ca7c4f414
1 ;; GCC machine description for Tensilica's Xtensa architecture.
2 ;; Copyright (C) 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
3 ;; Contributed by Bob Wilson (bwilson@tensilica.com) at Tensilica.
5 ;; This file is part of GCC.
7 ;; GCC is free software; you can redistribute it and/or modify it
8 ;; under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 2, or (at your option)
10 ;; any later version.
12 ;; GCC is distributed in the hope that it will be useful, but WITHOUT
13 ;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 ;; or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
15 ;; License for more details.
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GCC; see the file COPYING.  If not, write to the Free
19 ;; Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20 ;; 02111-1307, USA.
23 (define_constants [
24   (A0_REG               0)
25   (A1_REG               1)
26   (A7_REG               7)
27   (A8_REG               8)
29   (UNSPEC_NSAU          1)
30   (UNSPEC_NOP           2)
31   (UNSPEC_PLT           3)
32   (UNSPEC_RET_ADDR      4)
33   (UNSPECV_SET_FP       1)
34   (UNSPECV_ENTRY        2)
38 ;; Attributes.
40 (define_attr "type"
41   "unknown,jump,call,load,store,move,arith,multi,nop,farith,fmadd,fdiv,fsqrt,fconv,fload,fstore,mul16,mul32,div32,mac16,rsr,wsr"
42   (const_string "unknown"))
44 (define_attr "mode"
45   "unknown,none,QI,HI,SI,DI,SF,DF,BL"
46   (const_string "unknown"))
48 (define_attr "length" "" (const_int 1))
50 ;; Describe a user's asm statement.
51 (define_asm_attributes
52   [(set_attr "type" "multi")])
55 ;; Pipeline model.
57 ;; The Xtensa basically has simple 5-stage RISC pipeline.
58 ;; Most instructions complete in 1 cycle, and it is OK to assume that
59 ;; everything is fully pipelined.  The exceptions have special insn
60 ;; reservations in the pipeline description below.  The Xtensa can
61 ;; issue one instruction per cycle, so defining CPU units is unnecessary.
63 (define_insn_reservation "xtensa_any_insn" 1
64                          (eq_attr "type" "!load,fload,rsr,mul16,mul32,fmadd,fconv")
65                          "nothing")
67 (define_insn_reservation "xtensa_memory" 2
68                          (eq_attr "type" "load,fload")
69                          "nothing")
71 (define_insn_reservation "xtensa_sreg" 2
72                          (eq_attr "type" "rsr")
73                          "nothing")
75 (define_insn_reservation "xtensa_mul16" 2
76                          (eq_attr "type" "mul16")
77                          "nothing")
79 (define_insn_reservation "xtensa_mul32" 2
80                          (eq_attr "type" "mul32")
81                          "nothing")
83 (define_insn_reservation "xtensa_fmadd" 4
84                          (eq_attr "type" "fmadd")
85                          "nothing")
87 (define_insn_reservation "xtensa_fconv" 2
88                          (eq_attr "type" "fconv")
89                          "nothing")
91 ;; Include predicate definitions
93 (include "predicates.md")
96 ;; Addition.
98 (define_expand "adddi3"
99   [(set (match_operand:DI 0 "register_operand" "")
100         (plus:DI (match_operand:DI 1 "register_operand" "")
101                  (match_operand:DI 2 "register_operand" "")))]
102   ""
104   rtx srclo;
105   rtx dstlo = gen_lowpart (SImode, operands[0]);
106   rtx src1lo = gen_lowpart (SImode, operands[1]);
107   rtx src2lo = gen_lowpart (SImode, operands[2]);
109   rtx dsthi = gen_highpart (SImode, operands[0]);
110   rtx src1hi = gen_highpart (SImode, operands[1]);
111   rtx src2hi = gen_highpart (SImode, operands[2]);
113   /* Either source can be used for overflow checking, as long as it's
114      not clobbered by the first addition.  */
115   if (!rtx_equal_p (dstlo, src1lo))
116     srclo = src1lo;
117   else if (!rtx_equal_p (dstlo, src2lo))
118     srclo = src2lo;
119   else
120     {
121       srclo = gen_reg_rtx (SImode);
122       emit_move_insn (srclo, src1lo);
123     }
125   emit_insn (gen_addsi3 (dstlo, src1lo, src2lo));
126   emit_insn (gen_addsi3 (dsthi, src1hi, src2hi));
127   emit_insn (gen_adddi_carry (dsthi, dstlo, srclo));
128   DONE;
131 ;; Represent the add-carry operation as an atomic operation instead of
132 ;; expanding it to a conditional branch.  Otherwise, the edge
133 ;; profiling code breaks because inserting the count increment code
134 ;; causes a new jump insn to be added.
136 (define_insn "adddi_carry"
137   [(set (match_operand:SI 0 "register_operand" "+a")
138         (plus:SI (ltu:SI (match_operand:SI 1 "register_operand" "r")
139                          (match_operand:SI 2 "register_operand" "r"))
140                  (match_dup 0)))]
141   ""
142   "bgeu\t%1, %2, 0f\;addi\t%0, %0, 1\;0:"
143   [(set_attr "type"     "multi")
144    (set_attr "mode"     "SI")
145    (set_attr "length"   "6")])
147 (define_insn "addsi3"
148   [(set (match_operand:SI 0 "register_operand" "=D,D,a,a,a")
149         (plus:SI (match_operand:SI 1 "register_operand" "%d,d,r,r,r")
150                  (match_operand:SI 2 "add_operand" "d,O,r,J,N")))]
151   ""
152   "@
153    add.n\t%0, %1, %2
154    addi.n\t%0, %1, %d2
155    add\t%0, %1, %2
156    addi\t%0, %1, %d2
157    addmi\t%0, %1, %x2"
158   [(set_attr "type"     "arith,arith,arith,arith,arith")
159    (set_attr "mode"     "SI")
160    (set_attr "length"   "2,2,3,3,3")])
162 (define_insn "*addx2"
163   [(set (match_operand:SI 0 "register_operand" "=a")
164         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
165                           (const_int 2))
166                  (match_operand:SI 2 "register_operand" "r")))]
167   "TARGET_ADDX"
168   "addx2\t%0, %1, %2"
169   [(set_attr "type"     "arith")
170    (set_attr "mode"     "SI")
171    (set_attr "length"   "3")])
173 (define_insn "*addx4"
174   [(set (match_operand:SI 0 "register_operand" "=a")
175         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
176                           (const_int 4))
177                  (match_operand:SI 2 "register_operand" "r")))]
178   "TARGET_ADDX"
179   "addx4\t%0, %1, %2"
180   [(set_attr "type"     "arith")
181    (set_attr "mode"     "SI")
182    (set_attr "length"   "3")])
184 (define_insn "*addx8"
185   [(set (match_operand:SI 0 "register_operand" "=a")
186         (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
187                           (const_int 8))
188                  (match_operand:SI 2 "register_operand" "r")))]
189   "TARGET_ADDX"
190   "addx8\t%0, %1, %2"
191   [(set_attr "type"     "arith")
192    (set_attr "mode"     "SI")
193    (set_attr "length"   "3")])
195 (define_insn "addsf3"
196   [(set (match_operand:SF 0 "register_operand" "=f")
197         (plus:SF (match_operand:SF 1 "register_operand" "%f")
198                  (match_operand:SF 2 "register_operand" "f")))]
199   "TARGET_HARD_FLOAT"
200   "add.s\t%0, %1, %2"
201   [(set_attr "type"     "fmadd")
202    (set_attr "mode"     "SF")
203    (set_attr "length"   "3")])
206 ;; Subtraction.
208 (define_expand "subdi3"
209   [(set (match_operand:DI 0 "register_operand" "")
210         (minus:DI (match_operand:DI 1 "register_operand" "")
211                   (match_operand:DI 2 "register_operand" "")))]
212   ""
214   rtx dstlo = gen_lowpart (SImode, operands[0]);
215   rtx src1lo = gen_lowpart (SImode, operands[1]);
216   rtx src2lo = gen_lowpart (SImode, operands[2]);
218   rtx dsthi = gen_highpart (SImode, operands[0]);
219   rtx src1hi = gen_highpart (SImode, operands[1]);
220   rtx src2hi = gen_highpart (SImode, operands[2]);
222   emit_insn (gen_subsi3 (dsthi, src1hi, src2hi));
223   emit_insn (gen_subdi_carry (dsthi, src1lo, src2lo));
224   emit_insn (gen_subsi3 (dstlo, src1lo, src2lo));
225   DONE;
228 (define_insn "subdi_carry"
229   [(set (match_operand:SI 0 "register_operand" "+a")
230         (minus:SI (match_dup 0)
231                   (ltu:SI (match_operand:SI 1 "register_operand" "r")
232                           (match_operand:SI 2 "register_operand" "r"))))]
233   ""
234   "bgeu\t%1, %2, 0f\;addi\t%0, %0, -1\;0:"
235   [(set_attr "type"     "multi")
236    (set_attr "mode"     "SI")
237    (set_attr "length"   "6")])
239 (define_insn "subsi3"
240   [(set (match_operand:SI 0 "register_operand" "=a")
241         (minus:SI (match_operand:SI 1 "register_operand" "r")
242                   (match_operand:SI 2 "register_operand" "r")))]
243   ""
244   "sub\t%0, %1, %2"
245   [(set_attr "type"     "arith")
246    (set_attr "mode"     "SI")
247    (set_attr "length"   "3")])
249 (define_insn "*subx2"
250   [(set (match_operand:SI 0 "register_operand" "=a")
251         (minus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
252                            (const_int 2))
253                   (match_operand:SI 2 "register_operand" "r")))]
254   "TARGET_ADDX"
255   "subx2\t%0, %1, %2"
256   [(set_attr "type"     "arith")
257    (set_attr "mode"     "SI")
258    (set_attr "length"   "3")])
260 (define_insn "*subx4"
261   [(set (match_operand:SI 0 "register_operand" "=a")
262         (minus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
263                            (const_int 4))
264                   (match_operand:SI 2 "register_operand" "r")))]
265   "TARGET_ADDX"
266   "subx4\t%0, %1, %2"
267   [(set_attr "type"     "arith")
268    (set_attr "mode"     "SI")
269    (set_attr "length"   "3")])
271 (define_insn "*subx8"
272   [(set (match_operand:SI 0 "register_operand" "=a")
273         (minus:SI (mult:SI (match_operand:SI 1 "register_operand" "r")
274                            (const_int 8))
275                   (match_operand:SI 2 "register_operand" "r")))]
276   "TARGET_ADDX"
277   "subx8\t%0, %1, %2"
278   [(set_attr "type"     "arith")
279    (set_attr "mode"     "SI")
280    (set_attr "length"   "3")])
282 (define_insn "subsf3"
283   [(set (match_operand:SF 0 "register_operand" "=f")
284         (minus:SF (match_operand:SF 1 "register_operand" "f")
285                   (match_operand:SF 2 "register_operand" "f")))]
286   "TARGET_HARD_FLOAT"
287   "sub.s\t%0, %1, %2"
288   [(set_attr "type"     "fmadd")
289    (set_attr "mode"     "SF")
290    (set_attr "length"   "3")])
293 ;; Multiplication.
295 (define_insn "mulsi3"
296   [(set (match_operand:SI 0 "register_operand" "=a")
297         (mult:SI (match_operand:SI 1 "register_operand" "%r")
298                  (match_operand:SI 2 "register_operand" "r")))]
299   "TARGET_MUL32"
300   "mull\t%0, %1, %2"
301   [(set_attr "type"     "mul32")
302    (set_attr "mode"     "SI")
303    (set_attr "length"   "3")])
305 (define_insn "mulhisi3"
306   [(set (match_operand:SI 0 "register_operand" "=C,A")
307         (mult:SI (sign_extend:SI
308                   (match_operand:HI 1 "register_operand" "%r,r"))
309                  (sign_extend:SI
310                   (match_operand:HI 2 "register_operand" "r,r"))))]
311   "TARGET_MUL16 || TARGET_MAC16"
312   "@
313    mul16s\t%0, %1, %2
314    mul.aa.ll\t%1, %2"
315   [(set_attr "type"     "mul16,mac16")
316    (set_attr "mode"     "SI")
317    (set_attr "length"   "3,3")])
319 (define_insn "umulhisi3"
320   [(set (match_operand:SI 0 "register_operand" "=C,A")
321         (mult:SI (zero_extend:SI
322                   (match_operand:HI 1 "register_operand" "%r,r"))
323                  (zero_extend:SI
324                   (match_operand:HI 2 "register_operand" "r,r"))))]
325   "TARGET_MUL16 || TARGET_MAC16"
326   "@
327    mul16u\t%0, %1, %2
328    umul.aa.ll\t%1, %2"
329   [(set_attr "type"     "mul16,mac16")
330    (set_attr "mode"     "SI")
331    (set_attr "length"   "3,3")])
333 (define_insn "muladdhisi"
334   [(set (match_operand:SI 0 "register_operand" "=A")
335         (plus:SI (mult:SI (sign_extend:SI
336                            (match_operand:HI 1 "register_operand" "%r"))
337                           (sign_extend:SI
338                            (match_operand:HI 2 "register_operand" "r")))
339                  (match_operand:SI 3 "register_operand" "0")))]
340   "TARGET_MAC16"
341   "mula.aa.ll\t%1, %2"
342   [(set_attr "type"     "mac16")
343    (set_attr "mode"     "SI")
344    (set_attr "length"   "3")])
346 (define_insn "mulsubhisi"
347   [(set (match_operand:SI 0 "register_operand" "=A")
348         (minus:SI (match_operand:SI 1 "register_operand" "0")
349                   (mult:SI (sign_extend:SI
350                             (match_operand:HI 2 "register_operand" "%r"))
351                            (sign_extend:SI
352                             (match_operand:HI 3 "register_operand" "r")))))]
353   "TARGET_MAC16"
354   "muls.aa.ll\t%2, %3"
355   [(set_attr "type"     "mac16")
356    (set_attr "mode"     "SI")
357    (set_attr "length"   "3")])
359 (define_insn "mulsf3"
360   [(set (match_operand:SF 0 "register_operand" "=f")
361         (mult:SF (match_operand:SF 1 "register_operand" "%f")
362                  (match_operand:SF 2 "register_operand" "f")))]
363   "TARGET_HARD_FLOAT"
364   "mul.s\t%0, %1, %2"
365   [(set_attr "type"     "fmadd")
366    (set_attr "mode"     "SF")
367    (set_attr "length"   "3")])
369 (define_insn "muladdsf3"
370   [(set (match_operand:SF 0 "register_operand" "=f")
371         (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "%f")
372                           (match_operand:SF 2 "register_operand" "f"))
373                  (match_operand:SF 3 "register_operand" "0")))]
374   "TARGET_HARD_FLOAT && !TARGET_NO_FUSED_MADD"
375   "madd.s\t%0, %1, %2"
376   [(set_attr "type"     "fmadd")
377    (set_attr "mode"     "SF")
378    (set_attr "length"   "3")])
380 (define_insn "mulsubsf3"
381   [(set (match_operand:SF 0 "register_operand" "=f")
382         (minus:SF (match_operand:SF 1 "register_operand" "0")
383                   (mult:SF (match_operand:SF 2 "register_operand" "%f")
384                            (match_operand:SF 3 "register_operand" "f"))))]
385   "TARGET_HARD_FLOAT && !TARGET_NO_FUSED_MADD"
386   "msub.s\t%0, %2, %3"
387   [(set_attr "type"     "fmadd")
388    (set_attr "mode"     "SF")
389    (set_attr "length"   "3")])
392 ;; Division.
394 (define_insn "divsi3"
395   [(set (match_operand:SI 0 "register_operand" "=a")
396         (div:SI (match_operand:SI 1 "register_operand" "r")
397                 (match_operand:SI 2 "register_operand" "r")))]
398   "TARGET_DIV32"
399   "quos\t%0, %1, %2"
400   [(set_attr "type"     "div32")
401    (set_attr "mode"     "SI")
402    (set_attr "length"   "3")])
404 (define_insn "udivsi3"
405   [(set (match_operand:SI 0 "register_operand" "=a")
406         (udiv:SI (match_operand:SI 1 "register_operand" "r")
407                  (match_operand:SI 2 "register_operand" "r")))]
408   "TARGET_DIV32"
409   "quou\t%0, %1, %2"
410   [(set_attr "type"     "div32")
411    (set_attr "mode"     "SI")
412    (set_attr "length"   "3")])
414 (define_insn "divsf3"
415   [(set (match_operand:SF 0 "register_operand" "=f")
416         (div:SF (match_operand:SF 1 "register_operand" "f")
417                 (match_operand:SF 2 "register_operand" "f")))]
418   "TARGET_HARD_FLOAT_DIV"
419   "div.s\t%0, %1, %2"
420   [(set_attr "type"     "fdiv")
421    (set_attr "mode"     "SF")
422    (set_attr "length"   "3")])
424 (define_insn "*recipsf2"
425   [(set (match_operand:SF 0 "register_operand" "=f")
426         (div:SF (match_operand:SF 1 "const_float_1_operand" "")
427                 (match_operand:SF 2 "register_operand" "f")))]
428   "TARGET_HARD_FLOAT_RECIP && flag_unsafe_math_optimizations"
429   "recip.s\t%0, %2"
430   [(set_attr "type"     "fdiv")
431    (set_attr "mode"     "SF")
432    (set_attr "length"   "3")])
435 ;; Remainders.
437 (define_insn "modsi3"
438   [(set (match_operand:SI 0 "register_operand" "=a")
439         (mod:SI (match_operand:SI 1 "register_operand" "r")
440                 (match_operand:SI 2 "register_operand" "r")))]
441   "TARGET_DIV32"
442   "rems\t%0, %1, %2"
443   [(set_attr "type"     "div32")
444    (set_attr "mode"     "SI")
445    (set_attr "length"   "3")])
447 (define_insn "umodsi3"
448   [(set (match_operand:SI 0 "register_operand" "=a")
449         (umod:SI (match_operand:SI 1 "register_operand" "r")
450                  (match_operand:SI 2 "register_operand" "r")))]
451   "TARGET_DIV32"
452   "remu\t%0, %1, %2"
453   [(set_attr "type"     "div32")
454    (set_attr "mode"     "SI")
455    (set_attr "length"   "3")])
458 ;; Square roots.
460 (define_insn "sqrtsf2"
461   [(set (match_operand:SF 0 "register_operand" "=f")
462         (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
463   "TARGET_HARD_FLOAT_SQRT"
464   "sqrt.s\t%0, %1"
465   [(set_attr "type"     "fsqrt")
466    (set_attr "mode"     "SF")
467    (set_attr "length"   "3")])
469 (define_insn "*rsqrtsf2"
470   [(set (match_operand:SF 0 "register_operand" "=f")
471         (div:SF (match_operand:SF 1 "const_float_1_operand" "")
472                 (sqrt:SF (match_operand:SF 2 "register_operand" "f"))))]
473   "TARGET_HARD_FLOAT_RSQRT && flag_unsafe_math_optimizations"
474   "rsqrt.s\t%0, %2"
475   [(set_attr "type"     "fsqrt")
476    (set_attr "mode"     "SF")
477    (set_attr "length"   "3")])
480 ;; Absolute value.
482 (define_insn "abssi2"
483   [(set (match_operand:SI 0 "register_operand" "=a")
484         (abs:SI (match_operand:SI 1 "register_operand" "r")))]
485   "TARGET_ABS"
486   "abs\t%0, %1"
487   [(set_attr "type"     "arith")
488    (set_attr "mode"     "SI")
489    (set_attr "length"   "3")])
491 (define_insn "abssf2"
492   [(set (match_operand:SF 0 "register_operand" "=f")
493         (abs:SF (match_operand:SF 1 "register_operand" "f")))]
494   "TARGET_HARD_FLOAT"
495   "abs.s\t%0, %1"
496   [(set_attr "type"     "farith")
497    (set_attr "mode"     "SF")
498    (set_attr "length"   "3")])
501 ;; Min and max.
503 (define_insn "sminsi3"
504   [(set (match_operand:SI 0 "register_operand" "=a")
505         (smin:SI (match_operand:SI 1 "register_operand" "%r")
506                  (match_operand:SI 2 "register_operand" "r")))]
507   "TARGET_MINMAX"
508   "min\t%0, %1, %2"
509   [(set_attr "type"     "arith")
510    (set_attr "mode"     "SI")
511    (set_attr "length"   "3")])
513 (define_insn "uminsi3"
514   [(set (match_operand:SI 0 "register_operand" "=a")
515         (umin:SI (match_operand:SI 1 "register_operand" "%r")
516                  (match_operand:SI 2 "register_operand" "r")))]
517   "TARGET_MINMAX"
518   "minu\t%0, %1, %2"
519   [(set_attr "type"     "arith")
520    (set_attr "mode"     "SI")
521    (set_attr "length"   "3")])
523 (define_insn "smaxsi3"
524   [(set (match_operand:SI 0 "register_operand" "=a")
525         (smax:SI (match_operand:SI 1 "register_operand" "%r")
526                  (match_operand:SI 2 "register_operand" "r")))]
527   "TARGET_MINMAX"
528   "max\t%0, %1, %2"
529   [(set_attr "type"     "arith")
530    (set_attr "mode"     "SI")
531    (set_attr "length"   "3")])
533 (define_insn "umaxsi3"
534   [(set (match_operand:SI 0 "register_operand" "=a")
535         (umax:SI (match_operand:SI 1 "register_operand" "%r")
536                  (match_operand:SI 2 "register_operand" "r")))]
537   "TARGET_MINMAX"
538   "maxu\t%0, %1, %2"
539   [(set_attr "type"     "arith")
540    (set_attr "mode"     "SI")
541    (set_attr "length"   "3")])
544 ;; Find first bit.
546 (define_expand "ffssi2"
547   [(set (match_operand:SI 0 "register_operand" "")
548         (ffs:SI (match_operand:SI 1 "register_operand" "")))]
549   "TARGET_NSA"
551   rtx temp = gen_reg_rtx (SImode);
552   emit_insn (gen_negsi2 (temp, operands[1]));
553   emit_insn (gen_andsi3 (temp, temp, operands[1]));
554   emit_insn (gen_nsau (temp, temp));
555   emit_insn (gen_negsi2 (temp, temp));
556   emit_insn (gen_addsi3 (operands[0], temp, GEN_INT (32)));
557   DONE;
560 ;; There is no RTL operator corresponding to NSAU.
561 (define_insn "nsau"
562   [(set (match_operand:SI 0 "register_operand" "=a")
563         (unspec:SI [(match_operand:SI 1 "register_operand" "r")] UNSPEC_NSAU))]
564   "TARGET_NSA"
565   "nsau\t%0, %1"
566   [(set_attr "type"     "arith")
567    (set_attr "mode"     "SI")
568    (set_attr "length"   "3")])
571 ;; Negation and one's complement.
573 (define_insn "negsi2"
574   [(set (match_operand:SI 0 "register_operand" "=a")
575         (neg:SI (match_operand:SI 1 "register_operand" "r")))]
576   ""
577   "neg\t%0, %1"
578   [(set_attr "type"     "arith")
579    (set_attr "mode"     "SI")
580    (set_attr "length"   "3")])
582 (define_expand "one_cmplsi2"
583   [(set (match_operand:SI 0 "register_operand" "")
584         (not:SI (match_operand:SI 1 "register_operand" "")))]
585   ""
587   rtx temp = gen_reg_rtx (SImode);
588   emit_insn (gen_movsi (temp, constm1_rtx));
589   emit_insn (gen_xorsi3 (operands[0], temp, operands[1]));
590   DONE;
593 (define_insn "negsf2"
594   [(set (match_operand:SF 0 "register_operand" "=f")
595         (neg:SF (match_operand:SF 1 "register_operand" "f")))]
596   "TARGET_HARD_FLOAT"
597   "neg.s\t%0, %1"
598   [(set_attr "type"     "farith")
599    (set_attr "mode"     "SF")
600    (set_attr "length"   "3")])
603 ;; Logical instructions.
605 (define_insn "andsi3"
606   [(set (match_operand:SI 0 "register_operand" "=a,a")
607         (and:SI (match_operand:SI 1 "register_operand" "%r,r")
608                 (match_operand:SI 2 "mask_operand" "P,r")))]
609   ""
610   "@
611    extui\t%0, %1, 0, %K2
612    and\t%0, %1, %2"
613   [(set_attr "type"     "arith,arith")
614    (set_attr "mode"     "SI")
615    (set_attr "length"   "3,3")])
617 (define_insn "iorsi3"
618   [(set (match_operand:SI 0 "register_operand" "=a")
619         (ior:SI (match_operand:SI 1 "register_operand" "%r")
620                 (match_operand:SI 2 "register_operand" "r")))]
621   ""
622   "or\t%0, %1, %2"
623   [(set_attr "type"     "arith")
624    (set_attr "mode"     "SI")
625    (set_attr "length"   "3")])
627 (define_insn "xorsi3"
628   [(set (match_operand:SI 0 "register_operand" "=a")
629         (xor:SI (match_operand:SI 1 "register_operand" "%r")
630                 (match_operand:SI 2 "register_operand" "r")))]
631   ""
632   "xor\t%0, %1, %2"
633   [(set_attr "type"     "arith")
634    (set_attr "mode"     "SI")
635    (set_attr "length"   "3")])
638 ;; Zero-extend instructions.
640 (define_insn "zero_extendhisi2"
641   [(set (match_operand:SI 0 "register_operand" "=a,a")
642         (zero_extend:SI (match_operand:HI 1 "nonimmed_operand" "r,U")))]
643   ""
644   "@
645    extui\t%0, %1, 0, 16
646    l16ui\t%0, %1"
647   [(set_attr "type"     "arith,load")
648    (set_attr "mode"     "SI")
649    (set_attr "length"   "3,3")])
651 (define_insn "zero_extendqisi2"
652   [(set (match_operand:SI 0 "register_operand" "=a,a")
653         (zero_extend:SI (match_operand:QI 1 "nonimmed_operand" "r,U")))]
654   ""
655   "@
656    extui\t%0, %1, 0, 8
657    l8ui\t%0, %1"
658   [(set_attr "type"     "arith,load")
659    (set_attr "mode"     "SI")
660    (set_attr "length"   "3,3")])
663 ;; Sign-extend instructions.
665 (define_expand "extendhisi2"
666   [(set (match_operand:SI 0 "register_operand" "")
667         (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
668   ""
670   if (sext_operand (operands[1], HImode))
671     emit_insn (gen_extendhisi2_internal (operands[0], operands[1]));
672   else
673     xtensa_extend_reg (operands[0], operands[1]);
674   DONE;
677 (define_insn "extendhisi2_internal"
678   [(set (match_operand:SI 0 "register_operand" "=B,a")
679         (sign_extend:SI (match_operand:HI 1 "sext_operand" "r,U")))]
680   ""
681   "@
682    sext\t%0, %1, 15
683    l16si\t%0, %1"
684   [(set_attr "type"     "arith,load")
685    (set_attr "mode"     "SI")
686    (set_attr "length"   "3,3")])
688 (define_expand "extendqisi2"
689   [(set (match_operand:SI 0 "register_operand" "")
690         (sign_extend:SI (match_operand:QI 1 "register_operand" "")))]
691   ""
693   if (TARGET_SEXT)
694     emit_insn (gen_extendqisi2_internal (operands[0], operands[1]));
695   else
696     xtensa_extend_reg (operands[0], operands[1]);
697   DONE;
700 (define_insn "extendqisi2_internal"
701   [(set (match_operand:SI 0 "register_operand" "=B")
702         (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
703   "TARGET_SEXT"
704   "sext\t%0, %1, 7"
705   [(set_attr "type"     "arith")
706    (set_attr "mode"     "SI")
707    (set_attr "length"   "3")])
710 ;; Field extract instructions.
712 (define_expand "extv"
713   [(set (match_operand:SI 0 "register_operand" "")
714         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
715                          (match_operand:SI 2 "const_int_operand" "")
716                          (match_operand:SI 3 "const_int_operand" "")))]
717   "TARGET_SEXT"
719   if (!sext_fldsz_operand (operands[2], SImode))
720     FAIL;
722   /* We could expand to a right shift followed by SEXT but that's
723      no better than the standard left and right shift sequence.  */
724   if (!lsbitnum_operand (operands[3], SImode))
725     FAIL;
727   emit_insn (gen_extv_internal (operands[0], operands[1],
728                                 operands[2], operands[3]));
729   DONE;
732 (define_insn "extv_internal"
733   [(set (match_operand:SI 0 "register_operand" "=a")
734         (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
735                          (match_operand:SI 2 "sext_fldsz_operand" "i")
736                          (match_operand:SI 3 "lsbitnum_operand" "i")))]
737   "TARGET_SEXT"
739   int fldsz = INTVAL (operands[2]);
740   operands[2] = GEN_INT (fldsz - 1);
741   return "sext\t%0, %1, %2";
743   [(set_attr "type"     "arith")
744    (set_attr "mode"     "SI")
745    (set_attr "length"   "3")])
747 (define_expand "extzv"
748   [(set (match_operand:SI 0 "register_operand" "")
749         (zero_extract:SI (match_operand:SI 1 "register_operand" "")
750                          (match_operand:SI 2 "const_int_operand" "")
751                          (match_operand:SI 3 "const_int_operand" "")))]
752   ""
754   if (!extui_fldsz_operand (operands[2], SImode))
755     FAIL;
756   emit_insn (gen_extzv_internal (operands[0], operands[1],
757                                  operands[2], operands[3]));
758   DONE;
761 (define_insn "extzv_internal"
762   [(set (match_operand:SI 0 "register_operand" "=a")
763         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
764                          (match_operand:SI 2 "extui_fldsz_operand" "i")
765                          (match_operand:SI 3 "const_int_operand" "i")))]
766   ""
768   int shift;
769   if (BITS_BIG_ENDIAN)
770     shift = (32 - (INTVAL (operands[2]) + INTVAL (operands[3]))) & 0x1f;
771   else
772     shift = INTVAL (operands[3]) & 0x1f;
773   operands[3] = GEN_INT (shift);
774   return "extui\t%0, %1, %3, %2";
776   [(set_attr "type"     "arith")
777    (set_attr "mode"     "SI")
778    (set_attr "length"   "3")])
781 ;; Conversions.
783 (define_insn "fix_truncsfsi2"
784   [(set (match_operand:SI 0 "register_operand" "=a")
785         (fix:SI (match_operand:SF 1 "register_operand" "f")))]
786   "TARGET_HARD_FLOAT"
787   "trunc.s\t%0, %1, 0"
788   [(set_attr "type"     "fconv")
789    (set_attr "mode"     "SF")
790    (set_attr "length"   "3")])
792 (define_insn "fixuns_truncsfsi2"
793   [(set (match_operand:SI 0 "register_operand" "=a")
794         (unsigned_fix:SI (match_operand:SF 1 "register_operand" "f")))]
795   "TARGET_HARD_FLOAT"
796   "utrunc.s\t%0, %1, 0"
797   [(set_attr "type"     "fconv")
798    (set_attr "mode"     "SF")
799    (set_attr "length"   "3")])
801 (define_insn "floatsisf2"
802   [(set (match_operand:SF 0 "register_operand" "=f")
803         (float:SF (match_operand:SI 1 "register_operand" "a")))]
804   "TARGET_HARD_FLOAT"
805   "float.s\t%0, %1, 0"
806   [(set_attr "type"     "fconv")
807    (set_attr "mode"     "SF")
808    (set_attr "length"   "3")])
810 (define_insn "floatunssisf2"
811   [(set (match_operand:SF 0 "register_operand" "=f")
812         (unsigned_float:SF (match_operand:SI 1 "register_operand" "a")))]
813   "TARGET_HARD_FLOAT"
814   "ufloat.s\t%0, %1, 0"
815   [(set_attr "type"     "fconv")
816    (set_attr "mode"     "SF")
817    (set_attr "length"   "3")])
820 ;; Data movement instructions.
822 ;; 64-bit Integer moves
824 (define_expand "movdi"
825   [(set (match_operand:DI 0 "nonimmed_operand" "")
826         (match_operand:DI 1 "general_operand" ""))]
827   ""
829   if (CONSTANT_P (operands[1]) && !TARGET_CONST16)
830     operands[1] = force_const_mem (DImode, operands[1]);
832   if (!register_operand (operands[0], DImode)
833       && !register_operand (operands[1], DImode))
834     operands[1] = force_reg (DImode, operands[1]);
836   operands[1] = xtensa_copy_incoming_a7 (operands[1]);
839 (define_insn_and_split "movdi_internal"
840   [(set (match_operand:DI 0 "nonimmed_operand" "=a,W,a,a,U")
841         (match_operand:DI 1 "move_operand" "r,i,T,U,r"))]
842   "register_operand (operands[0], DImode)
843    || register_operand (operands[1], DImode)"
844   "#"
845   "reload_completed"
846   [(set (match_dup 0) (match_dup 2))
847    (set (match_dup 1) (match_dup 3))]
849   xtensa_split_operand_pair (operands, SImode);
850   if (reg_overlap_mentioned_p (operands[0], operands[3]))
851     {
852       rtx tmp;
853       tmp = operands[0], operands[0] = operands[1], operands[1] = tmp;
854       tmp = operands[2], operands[2] = operands[3], operands[3] = tmp;
855     }
858 ;; 32-bit Integer moves
860 (define_expand "movsi"
861   [(set (match_operand:SI 0 "nonimmed_operand" "")
862         (match_operand:SI 1 "general_operand" ""))]
863   ""
865   if (xtensa_emit_move_sequence (operands, SImode))
866     DONE;
869 (define_insn "movsi_internal"
870   [(set (match_operand:SI 0 "nonimmed_operand" "=D,D,D,D,R,R,a,q,a,W,a,a,U,*a,*A")
871         (match_operand:SI 1 "move_operand" "M,D,d,R,D,d,r,r,I,i,T,U,r,*A,*r"))]
872   "xtensa_valid_move (SImode, operands)"
873   "@
874    movi.n\t%0, %x1
875    mov.n\t%0, %1
876    mov.n\t%0, %1
877    %v1l32i.n\t%0, %1
878    %v0s32i.n\t%1, %0
879    %v0s32i.n\t%1, %0
880    mov\t%0, %1
881    movsp\t%0, %1
882    movi\t%0, %x1
883    const16\t%0, %t1\;const16\t%0, %b1
884    %v1l32r\t%0, %1
885    %v1l32i\t%0, %1
886    %v0s32i\t%1, %0
887    rsr\t%0, ACCLO
888    wsr\t%1, ACCLO"
889   [(set_attr "type" "move,move,move,load,store,store,move,move,move,move,load,load,store,rsr,wsr")
890    (set_attr "mode"     "SI")
891    (set_attr "length"   "2,2,2,2,2,2,3,3,3,6,3,3,3,3,3")])
893 ;; 16-bit Integer moves
895 (define_expand "movhi"
896   [(set (match_operand:HI 0 "nonimmed_operand" "")
897         (match_operand:HI 1 "general_operand" ""))]
898   ""
900   if (xtensa_emit_move_sequence (operands, HImode))
901     DONE;
904 (define_insn "movhi_internal"
905   [(set (match_operand:HI 0 "nonimmed_operand" "=D,D,a,a,a,U,*a,*A")
906         (match_operand:HI 1 "move_operand" "M,d,r,I,U,r,*A,*r"))]
907   "xtensa_valid_move (HImode, operands)"
908   "@
909    movi.n\t%0, %x1
910    mov.n\t%0, %1
911    mov\t%0, %1
912    movi\t%0, %x1
913    %v1l16ui\t%0, %1
914    %v0s16i\t%1, %0
915    rsr\t%0, ACCLO
916    wsr\t%1, ACCLO"
917   [(set_attr "type"     "move,move,move,move,load,store,rsr,wsr")
918    (set_attr "mode"     "HI")
919    (set_attr "length"   "2,2,3,3,3,3,3,3")])
921 ;; 8-bit Integer moves
923 (define_expand "movqi"
924   [(set (match_operand:QI 0 "nonimmed_operand" "")
925         (match_operand:QI 1 "general_operand" ""))]
926   ""
928   if (xtensa_emit_move_sequence (operands, QImode))
929     DONE;
932 (define_insn "movqi_internal"
933   [(set (match_operand:QI 0 "nonimmed_operand" "=D,D,a,a,a,U,*a,*A")
934         (match_operand:QI 1 "move_operand" "M,d,r,I,U,r,*A,*r"))]
935   "xtensa_valid_move (QImode, operands)"
936   "@
937    movi.n\t%0, %x1
938    mov.n\t%0, %1
939    mov\t%0, %1
940    movi\t%0, %x1
941    %v1l8ui\t%0, %1
942    %v0s8i\t%1, %0
943    rsr\t%0, ACCLO
944    wsr\t%1, ACCLO"
945   [(set_attr "type"     "move,move,move,move,load,store,rsr,wsr")
946    (set_attr "mode"     "QI")
947    (set_attr "length"   "2,2,3,3,3,3,3,3")])
949 ;; 32-bit floating point moves
951 (define_expand "movsf"
952   [(set (match_operand:SF 0 "nonimmed_operand" "")
953         (match_operand:SF 1 "general_operand" ""))]
954   ""
956   if (!TARGET_CONST16 && CONSTANT_P (operands[1]))
957     operands[1] = force_const_mem (SFmode, operands[1]);
959   if ((!register_operand (operands[0], SFmode)
960        && !register_operand (operands[1], SFmode))
961       || (FP_REG_P (xt_true_regnum (operands[0]))
962           && !(reload_in_progress | reload_completed)
963           && (constantpool_mem_p (operands[1])
964               || CONSTANT_P (operands[1]))))
965     operands[1] = force_reg (SFmode, operands[1]);
967   operands[1] = xtensa_copy_incoming_a7 (operands[1]);
970 (define_insn "movsf_internal"
971   [(set (match_operand:SF 0 "nonimmed_operand" "=f,f,U,D,D,R,a,f,a,W,a,a,U")
972         (match_operand:SF 1 "move_operand" "f,U,f,d,R,d,r,r,f,iF,T,U,r"))]
973   "((register_operand (operands[0], SFmode)
974      || register_operand (operands[1], SFmode))
975     && !(FP_REG_P (xt_true_regnum (operands[0]))
976          && (constantpool_mem_p (operands[1]) || CONSTANT_P (operands[1]))))"
977   "@
978    mov.s\t%0, %1
979    %v1lsi\t%0, %1
980    %v0ssi\t%1, %0
981    mov.n\t%0, %1
982    %v1l32i.n\t%0, %1
983    %v0s32i.n\t%1, %0
984    mov\t%0, %1
985    wfr\t%0, %1
986    rfr\t%0, %1
987    const16\t%0, %t1\;const16\t%0, %b1
988    %v1l32r\t%0, %1
989    %v1l32i\t%0, %1
990    %v0s32i\t%1, %0"
991   [(set_attr "type"     "farith,fload,fstore,move,load,store,move,farith,farith,move,load,load,store")
992    (set_attr "mode"     "SF")
993    (set_attr "length"   "3,3,3,2,2,2,3,3,3,6,3,3,3")])
995 (define_insn "*lsiu"
996   [(set (match_operand:SF 0 "register_operand" "=f")
997         (mem:SF (plus:SI (match_operand:SI 1 "register_operand" "+a")
998                          (match_operand:SI 2 "fpmem_offset_operand" "i"))))
999    (set (match_dup 1)
1000         (plus:SI (match_dup 1) (match_dup 2)))]
1001   "TARGET_HARD_FLOAT"
1003   if (volatile_refs_p (PATTERN (insn)))
1004     output_asm_insn ("memw", operands);
1005   return "lsiu\t%0, %1, %2";
1007   [(set_attr "type"     "fload")
1008    (set_attr "mode"     "SF")
1009    (set_attr "length"   "3")])
1011 (define_insn "*ssiu"
1012   [(set (mem:SF (plus:SI (match_operand:SI 0 "register_operand" "+a")
1013                          (match_operand:SI 1 "fpmem_offset_operand" "i")))
1014         (match_operand:SF 2 "register_operand" "f"))
1015    (set (match_dup 0)
1016         (plus:SI (match_dup 0) (match_dup 1)))]
1017   "TARGET_HARD_FLOAT"
1019   if (volatile_refs_p (PATTERN (insn)))
1020     output_asm_insn ("memw", operands);
1021   return "ssiu\t%2, %0, %1";
1023   [(set_attr "type"     "fstore")
1024    (set_attr "mode"     "SF")
1025    (set_attr "length"   "3")])
1027 ;; 64-bit floating point moves
1029 (define_expand "movdf"
1030   [(set (match_operand:DF 0 "nonimmed_operand" "")
1031         (match_operand:DF 1 "general_operand" ""))]
1032   ""
1034   if (CONSTANT_P (operands[1]) && !TARGET_CONST16)
1035     operands[1] = force_const_mem (DFmode, operands[1]);
1037   if (!register_operand (operands[0], DFmode)
1038       && !register_operand (operands[1], DFmode))
1039     operands[1] = force_reg (DFmode, operands[1]);
1041   operands[1] = xtensa_copy_incoming_a7 (operands[1]);
1044 (define_insn_and_split "movdf_internal"
1045   [(set (match_operand:DF 0 "nonimmed_operand" "=a,W,a,a,U")
1046         (match_operand:DF 1 "move_operand" "r,iF,T,U,r"))]
1047   "register_operand (operands[0], DFmode)
1048    || register_operand (operands[1], DFmode)"
1049   "#"
1050   "reload_completed"
1051   [(set (match_dup 0) (match_dup 2))
1052    (set (match_dup 1) (match_dup 3))]
1054   xtensa_split_operand_pair (operands, SFmode);
1055   if (reg_overlap_mentioned_p (operands[0], operands[3]))
1056     {
1057       rtx tmp;
1058       tmp = operands[0], operands[0] = operands[1], operands[1] = tmp;
1059       tmp = operands[2], operands[2] = operands[3], operands[3] = tmp;
1060     }
1063 ;; Block moves
1065 (define_expand "movmemsi"
1066   [(parallel [(set (match_operand:BLK 0 "" "")
1067                    (match_operand:BLK 1 "" ""))
1068               (use (match_operand:SI 2 "arith_operand" ""))
1069               (use (match_operand:SI 3 "const_int_operand" ""))])]
1070   ""
1072   if (!xtensa_expand_block_move (operands))
1073     FAIL;
1074   DONE;
1078 ;; Shift instructions.
1080 (define_expand "ashlsi3"
1081   [(set (match_operand:SI 0 "register_operand" "")
1082         (ashift:SI (match_operand:SI 1 "register_operand" "")
1083                    (match_operand:SI 2 "arith_operand" "")))]
1084   ""
1086   operands[1] = xtensa_copy_incoming_a7 (operands[1]);
1089 (define_insn "ashlsi3_internal"
1090   [(set (match_operand:SI 0 "register_operand" "=a,a")
1091         (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
1092                    (match_operand:SI 2 "arith_operand" "J,r")))]
1093   ""      
1094   "@
1095    slli\t%0, %1, %R2
1096    ssl\t%2\;sll\t%0, %1"
1097   [(set_attr "type"     "arith,arith")
1098    (set_attr "mode"     "SI")
1099    (set_attr "length"   "3,6")])
1101 (define_insn "ashrsi3"
1102   [(set (match_operand:SI 0 "register_operand" "=a,a")
1103         (ashiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
1104                      (match_operand:SI 2 "arith_operand" "J,r")))]
1105   ""
1106   "@
1107    srai\t%0, %1, %R2
1108    ssr\t%2\;sra\t%0, %1"
1109   [(set_attr "type"     "arith,arith")
1110    (set_attr "mode"     "SI")
1111    (set_attr "length"   "3,6")])
1113 (define_insn "lshrsi3"
1114   [(set (match_operand:SI 0 "register_operand" "=a,a")
1115         (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
1116                      (match_operand:SI 2 "arith_operand" "J,r")))]
1117   ""
1119   if (which_alternative == 0)
1120     {
1121       if ((INTVAL (operands[2]) & 0x1f) < 16)
1122         return "srli\t%0, %1, %R2";
1123       else
1124         return "extui\t%0, %1, %R2, %L2";
1125     }
1126   return "ssr\t%2\;srl\t%0, %1";
1128   [(set_attr "type"     "arith,arith")
1129    (set_attr "mode"     "SI")
1130    (set_attr "length"   "3,6")])
1132 (define_insn "rotlsi3"
1133   [(set (match_operand:SI 0 "register_operand" "=a,a")
1134         (rotate:SI (match_operand:SI 1 "register_operand" "r,r")
1135                      (match_operand:SI 2 "arith_operand" "J,r")))]
1136   ""
1137   "@
1138    ssai\t%L2\;src\t%0, %1, %1
1139    ssl\t%2\;src\t%0, %1, %1"
1140   [(set_attr "type"     "multi,multi")
1141    (set_attr "mode"     "SI")
1142    (set_attr "length"   "6,6")])
1144 (define_insn "rotrsi3"
1145   [(set (match_operand:SI 0 "register_operand" "=a,a")
1146         (rotatert:SI (match_operand:SI 1 "register_operand" "r,r")
1147                      (match_operand:SI 2 "arith_operand" "J,r")))]
1148   ""
1149   "@
1150    ssai\t%R2\;src\t%0, %1, %1
1151    ssr\t%2\;src\t%0, %1, %1"
1152   [(set_attr "type"     "multi,multi")
1153    (set_attr "mode"     "SI")
1154    (set_attr "length"   "6,6")])
1157 ;; Comparisons.
1159 ;; Handle comparisons by stashing away the operands and then using that
1160 ;; information in the subsequent conditional branch.
1162 (define_expand "cmpsi"
1163   [(set (cc0)
1164         (compare:CC (match_operand:SI 0 "register_operand" "")
1165                     (match_operand:SI 1 "nonmemory_operand" "")))]
1166   ""
1168   branch_cmp[0] = operands[0];
1169   branch_cmp[1] = operands[1];
1170   branch_type = CMP_SI;
1171   DONE;
1174 (define_expand "tstsi"
1175   [(set (cc0)
1176         (match_operand:SI 0 "register_operand" ""))]
1177   ""
1179   branch_cmp[0] = operands[0];
1180   branch_cmp[1] = const0_rtx;
1181   branch_type = CMP_SI;
1182   DONE;
1185 (define_expand "cmpsf"
1186   [(set (cc0)
1187         (compare:CC (match_operand:SF 0 "register_operand" "")
1188                     (match_operand:SF 1 "register_operand" "")))]
1189   "TARGET_HARD_FLOAT"
1191   branch_cmp[0] = operands[0];
1192   branch_cmp[1] = operands[1];
1193   branch_type = CMP_SF;
1194   DONE;
1198 ;; Conditional branches.
1200 (define_expand "beq"
1201   [(set (pc)
1202         (if_then_else (eq (cc0) (const_int 0))
1203                       (label_ref (match_operand 0 "" ""))
1204                       (pc)))]
1205   ""
1207   xtensa_expand_conditional_branch (operands, EQ);
1208   DONE;
1211 (define_expand "bne"
1212   [(set (pc)
1213         (if_then_else (ne (cc0) (const_int 0))
1214                       (label_ref (match_operand 0 "" ""))
1215                       (pc)))]
1216   ""
1218   xtensa_expand_conditional_branch (operands, NE);
1219   DONE;
1222 (define_expand "bgt"
1223   [(set (pc)
1224         (if_then_else (gt (cc0) (const_int 0))
1225                       (label_ref (match_operand 0 "" ""))
1226                       (pc)))]
1227   ""
1229   xtensa_expand_conditional_branch (operands, GT);
1230   DONE;
1233 (define_expand "bge"
1234   [(set (pc)
1235         (if_then_else (ge (cc0) (const_int 0))
1236                       (label_ref (match_operand 0 "" ""))
1237                       (pc)))]
1238   ""
1240   xtensa_expand_conditional_branch (operands, GE);
1241   DONE;
1244 (define_expand "blt"
1245   [(set (pc)
1246         (if_then_else (lt (cc0) (const_int 0))
1247                       (label_ref (match_operand 0 "" ""))
1248                       (pc)))]
1249   ""
1251   xtensa_expand_conditional_branch (operands, LT);
1252   DONE;
1255 (define_expand "ble"
1256   [(set (pc)
1257         (if_then_else (le (cc0) (const_int 0))
1258                       (label_ref (match_operand 0 "" ""))
1259                       (pc)))]
1260   ""
1262   xtensa_expand_conditional_branch (operands, LE);
1263   DONE;
1266 (define_expand "bgtu"
1267   [(set (pc)
1268         (if_then_else (gtu (cc0) (const_int 0))
1269                       (label_ref (match_operand 0 "" ""))
1270                       (pc)))]
1271   ""
1273   xtensa_expand_conditional_branch (operands, GTU);
1274   DONE;
1277 (define_expand "bgeu"
1278   [(set (pc)
1279         (if_then_else (geu (cc0) (const_int 0))
1280                       (label_ref (match_operand 0 "" ""))
1281                       (pc)))]
1282   ""
1284   xtensa_expand_conditional_branch (operands, GEU);
1285   DONE;
1288 (define_expand "bltu"
1289   [(set (pc)
1290         (if_then_else (ltu (cc0) (const_int 0))
1291                       (label_ref (match_operand 0 "" ""))
1292                       (pc)))]
1293   ""
1295   xtensa_expand_conditional_branch (operands, LTU);
1296   DONE;
1299 (define_expand "bleu"
1300   [(set (pc)
1301         (if_then_else (leu (cc0) (const_int 0))
1302                       (label_ref (match_operand 0 "" ""))
1303                       (pc)))]
1304   ""
1306   xtensa_expand_conditional_branch (operands, LEU);
1307   DONE;
1310 ;; Branch patterns for standard integer comparisons
1312 (define_insn "*btrue"
1313   [(set (pc)
1314         (if_then_else (match_operator 3 "branch_operator"
1315                          [(match_operand:SI 0 "register_operand" "r,r")
1316                           (match_operand:SI 1 "branch_operand" "K,r")])
1317                       (label_ref (match_operand 2 "" ""))
1318                       (pc)))]
1319   ""
1321   if (which_alternative == 1)
1322     {
1323       switch (GET_CODE (operands[3]))
1324         {
1325         case EQ:        return "beq\t%0, %1, %2";
1326         case NE:        return "bne\t%0, %1, %2";
1327         case LT:        return "blt\t%0, %1, %2";
1328         case GE:        return "bge\t%0, %1, %2";
1329         default:        break;
1330         }
1331     }
1332   else if (INTVAL (operands[1]) == 0)
1333     {
1334       switch (GET_CODE (operands[3]))
1335         {
1336         case EQ:        return (TARGET_DENSITY
1337                                 ? "beqz.n\t%0, %2"
1338                                 : "beqz\t%0, %2");
1339         case NE:        return (TARGET_DENSITY
1340                                 ? "bnez.n\t%0, %2"
1341                                 : "bnez\t%0, %2");
1342         case LT:        return "bltz\t%0, %2";
1343         case GE:        return "bgez\t%0, %2";
1344         default:        break;
1345         }
1346     }
1347   else
1348     {
1349       switch (GET_CODE (operands[3]))
1350         {
1351         case EQ:        return "beqi\t%0, %d1, %2";
1352         case NE:        return "bnei\t%0, %d1, %2";
1353         case LT:        return "blti\t%0, %d1, %2";
1354         case GE:        return "bgei\t%0, %d1, %2";
1355         default:        break;
1356         }
1357     }
1358   abort ();
1359   return "";
1361   [(set_attr "type"     "jump,jump")
1362    (set_attr "mode"     "none")
1363    (set_attr "length"   "3,3")])
1365 (define_insn "*bfalse"
1366   [(set (pc)
1367         (if_then_else (match_operator 3 "branch_operator"
1368                          [(match_operand:SI 0 "register_operand" "r,r")
1369                           (match_operand:SI 1 "branch_operand" "K,r")])
1370                       (pc)
1371                       (label_ref (match_operand 2 "" ""))))]
1372   ""
1374   if (which_alternative == 1)
1375     {
1376       switch (GET_CODE (operands[3]))
1377         {
1378         case EQ:        return "bne\t%0, %1, %2";
1379         case NE:        return "beq\t%0, %1, %2";
1380         case LT:        return "bge\t%0, %1, %2";
1381         case GE:        return "blt\t%0, %1, %2";
1382         default:        break;
1383         }
1384     }
1385   else if (INTVAL (operands[1]) == 0)
1386     {
1387       switch (GET_CODE (operands[3]))
1388         {
1389         case EQ:        return (TARGET_DENSITY
1390                                 ? "bnez.n\t%0, %2"
1391                                 : "bnez\t%0, %2");
1392         case NE:        return (TARGET_DENSITY
1393                                 ? "beqz.n\t%0, %2"
1394                                 : "beqz\t%0, %2");
1395         case LT:        return "bgez\t%0, %2";
1396         case GE:        return "bltz\t%0, %2";
1397         default:        break;
1398         }
1399     }
1400   else
1401     {
1402       switch (GET_CODE (operands[3]))
1403         {
1404         case EQ:        return "bnei\t%0, %d1, %2";
1405         case NE:        return "beqi\t%0, %d1, %2";
1406         case LT:        return "bgei\t%0, %d1, %2";
1407         case GE:        return "blti\t%0, %d1, %2";
1408         default:        break;
1409         }
1410     }
1411   abort ();
1412   return "";
1414   [(set_attr "type"     "jump,jump")
1415    (set_attr "mode"     "none")
1416    (set_attr "length"   "3,3")])
1418 (define_insn "*ubtrue"
1419   [(set (pc)
1420         (if_then_else (match_operator 3 "ubranch_operator"
1421                          [(match_operand:SI 0 "register_operand" "r,r")
1422                           (match_operand:SI 1 "ubranch_operand" "L,r")])
1423                       (label_ref (match_operand 2 "" ""))
1424                       (pc)))]
1425   ""
1427   if (which_alternative == 1)
1428     {
1429       switch (GET_CODE (operands[3]))
1430         {
1431         case LTU:       return "bltu\t%0, %1, %2";
1432         case GEU:       return "bgeu\t%0, %1, %2";
1433         default:        break;
1434         }
1435     }
1436   else
1437     {
1438       switch (GET_CODE (operands[3]))
1439         {
1440         case LTU:       return "bltui\t%0, %d1, %2";
1441         case GEU:       return "bgeui\t%0, %d1, %2";
1442         default:        break;
1443         }
1444     }
1445   abort ();
1446   return "";
1448   [(set_attr "type"     "jump,jump")
1449    (set_attr "mode"     "none")
1450    (set_attr "length"   "3,3")])
1452 (define_insn "*ubfalse"
1453   [(set (pc)
1454         (if_then_else (match_operator 3 "ubranch_operator"
1455                          [(match_operand:SI 0 "register_operand" "r,r")
1456                           (match_operand:SI 1 "ubranch_operand" "L,r")])
1457                       (pc)
1458                       (label_ref (match_operand 2 "" ""))))]
1459   ""
1461   if (which_alternative == 1)
1462     {
1463       switch (GET_CODE (operands[3]))
1464         {
1465         case LTU:       return "bgeu\t%0, %1, %2";
1466         case GEU:       return "bltu\t%0, %1, %2";
1467         default:        break;
1468         }
1469     }
1470   else
1471     {
1472       switch (GET_CODE (operands[3]))
1473         {
1474         case LTU:       return "bgeui\t%0, %d1, %2";
1475         case GEU:       return "bltui\t%0, %d1, %2";
1476         default:        break;
1477         }
1478     }
1479   abort ();
1480   return "";
1482   [(set_attr "type"     "jump,jump")
1483    (set_attr "mode"     "none")
1484    (set_attr "length"   "3,3")])
1486 ;; Branch patterns for bit testing
1488 (define_insn "*bittrue"
1489   [(set (pc)
1490         (if_then_else (match_operator 3 "boolean_operator"
1491                         [(zero_extract:SI
1492                             (match_operand:SI 0 "register_operand" "r,r")
1493                             (const_int 1)
1494                             (match_operand:SI 1 "arith_operand" "J,r"))
1495                          (const_int 0)])
1496                       (label_ref (match_operand 2 "" ""))
1497                       (pc)))]
1498   ""
1500   if (which_alternative == 0)
1501     {
1502       unsigned bitnum = INTVAL(operands[1]) & 0x1f;
1503       operands[1] = GEN_INT(bitnum);
1504       switch (GET_CODE (operands[3]))
1505         {
1506         case EQ:        return "bbci\t%0, %d1, %2";
1507         case NE:        return "bbsi\t%0, %d1, %2";
1508         default:        break;
1509         }
1510     }
1511   else
1512     {
1513       switch (GET_CODE (operands[3]))
1514         {
1515         case EQ:        return "bbc\t%0, %1, %2";
1516         case NE:        return "bbs\t%0, %1, %2";
1517         default:        break;
1518         }
1519     }
1520   abort ();
1521   return "";
1523   [(set_attr "type"     "jump")
1524    (set_attr "mode"     "none")
1525    (set_attr "length"   "3")])
1527 (define_insn "*bitfalse"
1528   [(set (pc)
1529         (if_then_else (match_operator 3 "boolean_operator"
1530                         [(zero_extract:SI
1531                             (match_operand:SI 0 "register_operand" "r,r")
1532                             (const_int 1)
1533                             (match_operand:SI 1 "arith_operand" "J,r"))
1534                          (const_int 0)])
1535                       (pc)
1536                       (label_ref (match_operand 2 "" ""))))]
1537   ""
1539   if (which_alternative == 0)
1540     {
1541       unsigned bitnum = INTVAL (operands[1]) & 0x1f;
1542       operands[1] = GEN_INT (bitnum);
1543       switch (GET_CODE (operands[3]))
1544         {
1545         case EQ:        return "bbsi\t%0, %d1, %2";
1546         case NE:        return "bbci\t%0, %d1, %2";
1547         default:        break;
1548         }
1549     }
1550   else
1551     {
1552       switch (GET_CODE (operands[3]))
1553         {
1554         case EQ:        return "bbs\t%0, %1, %2";
1555         case NE:        return "bbc\t%0, %1, %2";
1556         default:        break;
1557         }
1558     }
1559   abort ();
1560   return "";
1562   [(set_attr "type"     "jump")
1563    (set_attr "mode"     "none")
1564    (set_attr "length"   "3")])
1566 (define_insn "*masktrue"
1567   [(set (pc)
1568         (if_then_else (match_operator 3 "boolean_operator"
1569                  [(and:SI (match_operand:SI 0 "register_operand" "r")
1570                           (match_operand:SI 1 "register_operand" "r"))
1571                   (const_int 0)])
1572                       (label_ref (match_operand 2 "" ""))
1573                       (pc)))]
1574   ""
1576   switch (GET_CODE (operands[3]))
1577     {
1578     case EQ:            return "bnone\t%0, %1, %2";
1579     case NE:            return "bany\t%0, %1, %2";
1580     default:            break;
1581     }
1582   abort ();
1583   return "";
1585   [(set_attr "type"     "jump")
1586    (set_attr "mode"     "none")
1587    (set_attr "length"   "3")])
1589 (define_insn "*maskfalse"
1590   [(set (pc)
1591         (if_then_else (match_operator 3 "boolean_operator"
1592                  [(and:SI (match_operand:SI 0 "register_operand" "r")
1593                           (match_operand:SI 1 "register_operand" "r"))
1594                   (const_int 0)])
1595                       (pc)
1596                       (label_ref (match_operand 2 "" ""))))]
1597   ""
1599   switch (GET_CODE (operands[3]))
1600     {
1601     case EQ:            return "bany\t%0, %1, %2";
1602     case NE:            return "bnone\t%0, %1, %2";
1603     default:            break;
1604     }
1605   abort ();
1606   return "";
1608   [(set_attr "type"     "jump")
1609    (set_attr "mode"     "none")
1610    (set_attr "length"   "3")])
1613 ;; Define the loop insns used by bct optimization to represent the
1614 ;; start and end of a zero-overhead loop (in loop.c).  This start
1615 ;; template generates the loop insn; the end template doesn't generate
1616 ;; any instructions since loop end is handled in hardware.
1618 (define_insn "zero_cost_loop_start"
1619   [(set (pc)
1620         (if_then_else (eq (match_operand:SI 0 "register_operand" "a")
1621                           (const_int 0))
1622                       (label_ref (match_operand 1 "" ""))
1623                       (pc)))
1624    (set (reg:SI 19)
1625         (plus:SI (match_dup 0) (const_int -1)))]
1626   ""
1627   "loopnez\t%0, %l1"
1628   [(set_attr "type"     "jump")
1629    (set_attr "mode"     "none")
1630    (set_attr "length"   "3")])
1632 (define_insn "zero_cost_loop_end"
1633   [(set (pc)
1634         (if_then_else (ne (reg:SI 19) (const_int 0))
1635                       (label_ref (match_operand 0 "" ""))
1636                       (pc)))
1637    (set (reg:SI 19)
1638         (plus:SI (reg:SI 19) (const_int -1)))]
1639   ""
1641     xtensa_emit_loop_end (insn, operands);
1642     return "";
1644   [(set_attr "type"     "jump")
1645    (set_attr "mode"     "none")
1646    (set_attr "length"   "0")])
1649 ;; Setting a register from a comparison.
1651 (define_expand "seq"
1652   [(set (match_operand:SI 0 "register_operand" "")
1653         (match_dup 1))]
1654   ""
1656   operands[1] = gen_rtx_EQ (SImode, branch_cmp[0], branch_cmp[1]);
1657   if (!xtensa_expand_scc (operands))
1658     FAIL;
1659   DONE;
1662 (define_expand "sne"
1663   [(set (match_operand:SI 0 "register_operand" "")
1664         (match_dup 1))]
1665   ""
1667   operands[1] = gen_rtx_NE (SImode, branch_cmp[0], branch_cmp[1]);
1668   if (!xtensa_expand_scc (operands))
1669     FAIL;
1670   DONE;
1673 (define_expand "sgt"
1674   [(set (match_operand:SI 0 "register_operand" "")
1675         (match_dup 1))]
1676   ""
1678   operands[1] = gen_rtx_GT (SImode, branch_cmp[0], branch_cmp[1]);
1679   if (!xtensa_expand_scc (operands))
1680     FAIL;
1681   DONE;
1684 (define_expand "sge"
1685   [(set (match_operand:SI 0 "register_operand" "")
1686         (match_dup 1))]
1687   ""
1689   operands[1] = gen_rtx_GE (SImode, branch_cmp[0], branch_cmp[1]);
1690   if (!xtensa_expand_scc (operands))
1691     FAIL;
1692   DONE;
1695 (define_expand "slt"
1696   [(set (match_operand:SI 0 "register_operand" "")
1697         (match_dup 1))]
1698   ""
1700   operands[1] = gen_rtx_LT (SImode, branch_cmp[0], branch_cmp[1]);
1701   if (!xtensa_expand_scc (operands))
1702     FAIL;
1703   DONE;
1706 (define_expand "sle"
1707   [(set (match_operand:SI 0 "register_operand" "")
1708         (match_dup 1))]
1709   ""
1711   operands[1] = gen_rtx_LE (SImode, branch_cmp[0], branch_cmp[1]);
1712   if (!xtensa_expand_scc (operands))
1713     FAIL;
1714   DONE;
1718 ;; Conditional moves.
1720 (define_expand "movsicc"
1721   [(set (match_operand:SI 0 "register_operand" "")
1722         (if_then_else:SI (match_operand 1 "comparison_operator" "")
1723                          (match_operand:SI 2 "register_operand" "")
1724                          (match_operand:SI 3 "register_operand" "")))]
1725   ""
1727   if (!xtensa_expand_conditional_move (operands, 0))
1728     FAIL;
1729   DONE;
1732 (define_expand "movsfcc"
1733   [(set (match_operand:SF 0 "register_operand" "")
1734         (if_then_else:SF (match_operand 1 "comparison_operator" "")
1735                          (match_operand:SF 2 "register_operand" "")
1736                          (match_operand:SF 3 "register_operand" "")))]
1737   ""
1739   if (!xtensa_expand_conditional_move (operands, 1))
1740     FAIL;
1741   DONE;
1744 (define_insn "movsicc_internal0"
1745   [(set (match_operand:SI 0 "register_operand" "=a,a")
1746         (if_then_else:SI (match_operator 4 "branch_operator"
1747                            [(match_operand:SI 1 "register_operand" "r,r")
1748                             (const_int 0)])
1749                          (match_operand:SI 2 "register_operand" "r,0")
1750                          (match_operand:SI 3 "register_operand" "0,r")))]
1751   ""
1753   if (which_alternative == 0)
1754     {
1755       switch (GET_CODE (operands[4]))
1756         {
1757         case EQ:        return "moveqz\t%0, %2, %1";
1758         case NE:        return "movnez\t%0, %2, %1";
1759         case LT:        return "movltz\t%0, %2, %1";
1760         case GE:        return "movgez\t%0, %2, %1";
1761         default:        break;
1762         }
1763     }
1764   else
1765     {
1766       switch (GET_CODE (operands[4]))
1767         {
1768         case EQ:        return "movnez\t%0, %3, %1";
1769         case NE:        return "moveqz\t%0, %3, %1";
1770         case LT:        return "movgez\t%0, %3, %1";
1771         case GE:        return "movltz\t%0, %3, %1";
1772         default:        break;
1773         }
1774     }
1775   abort ();
1776   return "";
1778   [(set_attr "type"     "move,move")
1779    (set_attr "mode"     "SI")
1780    (set_attr "length"   "3,3")])
1782 (define_insn "movsicc_internal1"
1783   [(set (match_operand:SI 0 "register_operand" "=a,a")
1784         (if_then_else:SI (match_operator 4 "boolean_operator"
1785                            [(match_operand:CC 1 "register_operand" "b,b")
1786                             (const_int 0)])
1787                          (match_operand:SI 2 "register_operand" "r,0")
1788                          (match_operand:SI 3 "register_operand" "0,r")))]
1789   "TARGET_BOOLEANS"
1791   int isEq = (GET_CODE (operands[4]) == EQ);
1792   switch (which_alternative)
1793     {
1794     case 0:
1795       if (isEq) return "movf\t%0, %2, %1";
1796       return "movt\t%0, %2, %1";
1797     case 1:
1798       if (isEq) return "movt\t%0, %3, %1";
1799       return "movf\t%0, %3, %1";
1800     }
1801   abort ();
1802   return "";
1804   [(set_attr "type"     "move,move")
1805    (set_attr "mode"     "SI")
1806    (set_attr "length"   "3,3")])
1808 (define_insn "movsfcc_internal0"
1809   [(set (match_operand:SF 0 "register_operand" "=a,a,f,f")
1810         (if_then_else:SF (match_operator 4 "branch_operator"
1811                            [(match_operand:SI 1 "register_operand" "r,r,r,r")
1812                             (const_int 0)])
1813                          (match_operand:SF 2 "register_operand" "r,0,f,0")
1814                          (match_operand:SF 3 "register_operand" "0,r,0,f")))]
1815   ""
1817   if (which_alternative == 0)
1818     {
1819       switch (GET_CODE (operands[4]))
1820         {
1821         case EQ:        return "moveqz\t%0, %2, %1";
1822         case NE:        return "movnez\t%0, %2, %1";
1823         case LT:        return "movltz\t%0, %2, %1";
1824         case GE:        return "movgez\t%0, %2, %1";
1825         default:        break;
1826         }
1827     }
1828   else if (which_alternative == 1)
1829     {
1830       switch (GET_CODE (operands[4]))
1831         {
1832         case EQ:        return "movnez\t%0, %3, %1";
1833         case NE:        return "moveqz\t%0, %3, %1";
1834         case LT:        return "movgez\t%0, %3, %1";
1835         case GE:        return "movltz\t%0, %3, %1";
1836         default:        break;
1837         }
1838     }
1839   else if (which_alternative == 2)
1840     {
1841       switch (GET_CODE (operands[4]))
1842         {
1843         case EQ:        return "moveqz.s %0, %2, %1";
1844         case NE:        return "movnez.s %0, %2, %1";
1845         case LT:        return "movltz.s %0, %2, %1";
1846         case GE:        return "movgez.s %0, %2, %1";
1847         default:        break;
1848         }
1849     }
1850   else if (which_alternative == 3)
1851     {
1852       switch (GET_CODE (operands[4]))
1853         {
1854         case EQ:        return "movnez.s %0, %3, %1";
1855         case NE:        return "moveqz.s %0, %3, %1";
1856         case LT:        return "movgez.s %0, %3, %1";
1857         case GE:        return "movltz.s %0, %3, %1";
1858         default:        break;
1859         }
1860     }
1861   abort ();
1862   return "";
1864   [(set_attr "type"     "move,move,move,move")
1865    (set_attr "mode"     "SF")
1866    (set_attr "length"   "3,3,3,3")])
1868 (define_insn "movsfcc_internal1"
1869   [(set (match_operand:SF 0 "register_operand" "=a,a,f,f")
1870         (if_then_else:SF (match_operator 4 "boolean_operator"
1871                            [(match_operand:CC 1 "register_operand" "b,b,b,b")
1872                             (const_int 0)])
1873                          (match_operand:SF 2 "register_operand" "r,0,f,0")
1874                          (match_operand:SF 3 "register_operand" "0,r,0,f")))]
1875   "TARGET_BOOLEANS"
1877   int isEq = (GET_CODE (operands[4]) == EQ);
1878   switch (which_alternative)
1879     {
1880     case 0:
1881       if (isEq) return "movf\t%0, %2, %1";
1882       return "movt\t%0, %2, %1";
1883     case 1:
1884       if (isEq) return "movt\t%0, %3, %1";
1885       return "movf\t%0, %3, %1";
1886     case 2:
1887       if (isEq) return "movf.s\t%0, %2, %1";
1888       return "movt.s\t%0, %2, %1";
1889     case 3:
1890       if (isEq) return "movt.s\t%0, %3, %1";
1891       return "movf.s\t%0, %3, %1";
1892     }
1893   abort ();
1894   return "";
1896   [(set_attr "type"     "move,move,move,move")
1897    (set_attr "mode"     "SF")
1898    (set_attr "length"   "3,3,3,3")])
1901 ;; Floating-point comparisons.
1903 (define_insn "seq_sf"
1904   [(set (match_operand:CC 0 "register_operand" "=b")
1905         (eq:CC (match_operand:SF 1 "register_operand" "f")
1906                (match_operand:SF 2 "register_operand" "f")))]
1907   "TARGET_HARD_FLOAT"
1908   "oeq.s\t%0, %1, %2"
1909   [(set_attr "type"     "farith")
1910    (set_attr "mode"     "BL")
1911    (set_attr "length"   "3")])
1913 (define_insn "slt_sf"
1914   [(set (match_operand:CC 0 "register_operand" "=b")
1915         (lt:CC (match_operand:SF 1 "register_operand" "f")
1916                (match_operand:SF 2 "register_operand" "f")))]
1917   "TARGET_HARD_FLOAT"
1918   "olt.s\t%0, %1, %2"
1919   [(set_attr "type"     "farith")
1920    (set_attr "mode"     "BL")
1921    (set_attr "length"   "3")])
1923 (define_insn "sle_sf"
1924   [(set (match_operand:CC 0 "register_operand" "=b")
1925         (le:CC (match_operand:SF 1 "register_operand" "f")
1926                (match_operand:SF 2 "register_operand" "f")))]
1927   "TARGET_HARD_FLOAT"
1928   "ole.s\t%0, %1, %2"
1929   [(set_attr "type"     "farith")
1930    (set_attr "mode"     "BL")
1931    (set_attr "length"   "3")])
1934 ;; Unconditional branches.
1936 (define_insn "jump"
1937   [(set (pc)
1938         (label_ref (match_operand 0 "" "")))]
1939   ""
1940   "j\t%l0"
1941   [(set_attr "type"     "jump")
1942    (set_attr "mode"     "none")
1943    (set_attr "length"   "3")])
1945 (define_expand "indirect_jump"
1946   [(set (pc)
1947         (match_operand 0 "register_operand" ""))]
1948   ""
1950   rtx dest = operands[0];
1951   if (GET_CODE (dest) != REG || GET_MODE (dest) != Pmode)
1952     operands[0] = copy_to_mode_reg (Pmode, dest);
1954   emit_jump_insn (gen_indirect_jump_internal (dest));
1955   DONE;
1958 (define_insn "indirect_jump_internal"
1959   [(set (pc) (match_operand:SI 0 "register_operand" "r"))]
1960   ""
1961   "jx\t%0"
1962   [(set_attr "type"     "jump")
1963    (set_attr "mode"     "none")
1964    (set_attr "length"   "3")])
1967 (define_expand "tablejump"
1968   [(use (match_operand:SI 0 "register_operand" ""))
1969    (use (label_ref (match_operand 1 "" "")))]
1970    ""
1972   rtx target = operands[0];
1973   if (flag_pic)
1974     {
1975       /* For PIC, the table entry is relative to the start of the table.  */
1976       rtx label = gen_reg_rtx (SImode);
1977       target = gen_reg_rtx (SImode);
1978       emit_move_insn (label, gen_rtx_LABEL_REF (SImode, operands[1]));
1979       emit_insn (gen_addsi3 (target, operands[0], label));
1980     }
1981   emit_jump_insn (gen_tablejump_internal (target, operands[1]));
1982   DONE;
1985 (define_insn "tablejump_internal"
1986   [(set (pc)
1987         (match_operand:SI 0 "register_operand" "r"))
1988    (use (label_ref (match_operand 1 "" "")))]
1989   ""
1990   "jx\t%0"
1991   [(set_attr "type"     "jump")
1992    (set_attr "mode"     "none")
1993    (set_attr "length"   "3")])
1996 ;; Function calls.
1998 (define_expand "sym_PLT"
1999   [(const (unspec [(match_operand:SI 0 "" "")] UNSPEC_PLT))]
2000   ""
2001   "")
2003 (define_expand "call"
2004   [(call (match_operand 0 "memory_operand" "")
2005          (match_operand 1 "" ""))]
2006   ""
2008   rtx addr = XEXP (operands[0], 0);
2009   if (flag_pic && GET_CODE (addr) == SYMBOL_REF
2010       && (!SYMBOL_REF_LOCAL_P (addr) || SYMBOL_REF_EXTERNAL_P (addr)))
2011     addr = gen_sym_PLT (addr);
2012   if (!call_insn_operand (addr, VOIDmode))
2013     XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, addr);
2016 (define_insn "call_internal"
2017   [(call (mem (match_operand:SI 0 "call_insn_operand" "n,i,r"))
2018          (match_operand 1 "" "i,i,i"))]
2019   ""
2021   return xtensa_emit_call (0, operands);
2023   [(set_attr "type"     "call")
2024    (set_attr "mode"     "none")
2025    (set_attr "length"   "3")])
2027 (define_expand "call_value"
2028   [(set (match_operand 0 "register_operand" "")
2029         (call (match_operand 1 "memory_operand" "")
2030               (match_operand 2 "" "")))]
2031   ""
2033   rtx addr = XEXP (operands[1], 0);
2034   if (flag_pic && GET_CODE (addr) == SYMBOL_REF
2035       && (!SYMBOL_REF_LOCAL_P (addr) || SYMBOL_REF_EXTERNAL_P (addr)))
2036     addr = gen_sym_PLT (addr);
2037   if (!call_insn_operand (addr, VOIDmode))
2038     XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, addr);
2041 ;; Cannot combine constraints for operand 0 into "afvb":
2042 ;; reload.c:find_reloads seems to assume that grouped constraints somehow
2043 ;; specify related register classes, and when they don't the constraints
2044 ;; fail to match.  By not grouping the constraints, we get the correct
2045 ;; behavior.
2046 (define_insn "call_value_internal"
2047    [(set (match_operand 0 "register_operand" "=af,af,af,v,v,v,b,b,b")
2048          (call (mem (match_operand:SI 1 "call_insn_operand"
2049                                         "n,i,r,n,i,r,n,i,r"))
2050                (match_operand 2 "" "i,i,i,i,i,i,i,i,i")))]
2051   ""
2053   return xtensa_emit_call (1, operands);
2055   [(set_attr "type"     "call")
2056    (set_attr "mode"     "none")
2057    (set_attr "length"   "3")])
2059 (define_insn "entry"
2060   [(set (reg:SI A1_REG)
2061         (unspec_volatile:SI [(match_operand:SI 0 "const_int_operand" "i")
2062                              (match_operand:SI 1 "const_int_operand" "i")]
2063                             UNSPECV_ENTRY))]
2064   ""
2066   if (frame_pointer_needed)
2067     output_asm_insn (".frame\ta7, %0", operands);
2068   else
2069     output_asm_insn (".frame\tsp, %0", operands);
2070   return "entry\tsp, %1";
2072   [(set_attr "type"     "move")
2073    (set_attr "mode"     "SI")
2074    (set_attr "length"   "3")])
2076 (define_insn "return"
2077   [(return)
2078    (use (reg:SI A0_REG))]
2079   "reload_completed"
2081   return (TARGET_DENSITY ? "retw.n" : "retw");
2083   [(set_attr "type"     "jump")
2084    (set_attr "mode"     "none")
2085    (set_attr "length"   "2")])
2088 ;; Miscellaneous instructions.
2090 (define_expand "prologue"
2091   [(const_int 0)]
2092   ""
2094   xtensa_expand_prologue ();
2095   DONE;
2098 (define_expand "epilogue"
2099   [(return)]
2100   ""
2102   emit_jump_insn (gen_return ());
2103   DONE;
2106 (define_insn "nop"
2107   [(const_int 0)]
2108   ""
2110   return (TARGET_DENSITY ? "nop.n" : "nop");
2112   [(set_attr "type"     "nop")
2113    (set_attr "mode"     "none")
2114    (set_attr "length"   "3")])
2116 (define_expand "nonlocal_goto"
2117   [(match_operand:SI 0 "general_operand" "")
2118    (match_operand:SI 1 "general_operand" "")
2119    (match_operand:SI 2 "general_operand" "")
2120    (match_operand:SI 3 "" "")]
2121   ""
2123   xtensa_expand_nonlocal_goto (operands);
2124   DONE;
2127 ;; Setting up a frame pointer is tricky for Xtensa because GCC doesn't
2128 ;; know if a frame pointer is required until the reload pass, and
2129 ;; because there may be an incoming argument value in the hard frame
2130 ;; pointer register (a7).  If there is an incoming argument in that
2131 ;; register, the "set_frame_ptr" insn gets inserted immediately after
2132 ;; the insn that copies the incoming argument to a pseudo or to the
2133 ;; stack.  This serves several purposes here: (1) it keeps the
2134 ;; optimizer from copy-propagating or scheduling the use of a7 as an
2135 ;; incoming argument away from the beginning of the function; (2) we
2136 ;; can use a post-reload splitter to expand away the insn if a frame
2137 ;; pointer is not required, so that the post-reload scheduler can do
2138 ;; the right thing; and (3) it makes it easy for the prologue expander
2139 ;; to search for this insn to determine whether it should add a new insn
2140 ;; to set up the frame pointer.
2142 (define_insn "set_frame_ptr"
2143   [(set (reg:SI A7_REG) (unspec_volatile:SI [(const_int 0)] UNSPECV_SET_FP))]
2144   ""
2146   if (frame_pointer_needed)
2147     return "mov\ta7, sp";
2148   return "";
2150   [(set_attr "type"     "move")
2151    (set_attr "mode"     "SI")
2152    (set_attr "length"   "3")])
2154 ;; Post-reload splitter to remove fp assignment when it's not needed.
2155 (define_split
2156   [(set (reg:SI A7_REG) (unspec_volatile:SI [(const_int 0)] UNSPECV_SET_FP))]
2157   "reload_completed && !frame_pointer_needed"
2158   [(unspec [(const_int 0)] UNSPEC_NOP)]
2159   "")
2161 ;; The preceding splitter needs something to split the insn into;
2162 ;; things start breaking if the result is just a "use" so instead we
2163 ;; generate the following insn.
2164 (define_insn "*unspec_nop"
2165   [(unspec [(const_int 0)] UNSPEC_NOP)]
2166   ""
2167   ""
2168   [(set_attr "type"     "nop")
2169    (set_attr "mode"     "none")
2170    (set_attr "length"   "0")])
2172 ;; The fix_return_addr pattern sets the high 2 bits of an address in a
2173 ;; register to match the high bits of the current PC.
2174 (define_insn "fix_return_addr"
2175   [(set (match_operand:SI 0 "register_operand" "=a")
2176         (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
2177                    UNSPEC_RET_ADDR))
2178    (clobber (match_scratch:SI 2 "=r"))
2179    (clobber (match_scratch:SI 3 "=r"))]
2180   ""
2181   "mov\t%2, a0\;call0\t0f\;.align\t4\;0:\;mov\t%3, a0\;mov\ta0, %2\;\
2182 srli\t%3, %3, 30\;slli\t%0, %1, 2\;ssai\t2\;src\t%0, %3, %0"
2183   [(set_attr "type"     "multi")
2184    (set_attr "mode"     "SI")
2185    (set_attr "length"   "24")])
2188 ;; Instructions for the Xtensa "boolean" option.
2190 (define_insn "*booltrue"
2191   [(set (pc)
2192         (if_then_else (match_operator 2 "boolean_operator"
2193                          [(match_operand:CC 0 "register_operand" "b")
2194                           (const_int 0)])
2195                       (label_ref (match_operand 1 "" ""))
2196                       (pc)))]
2197   "TARGET_BOOLEANS"
2199   if (GET_CODE (operands[2]) == EQ)
2200     return "bf\t%0, %1";
2201   else
2202     return "bt\t%0, %1";
2204   [(set_attr "type"     "jump")
2205    (set_attr "mode"     "none")
2206    (set_attr "length"   "3")])
2208 (define_insn "*boolfalse"
2209   [(set (pc)
2210         (if_then_else (match_operator 2 "boolean_operator"
2211                          [(match_operand:CC 0 "register_operand" "b")
2212                           (const_int 0)])
2213                       (pc)
2214                       (label_ref (match_operand 1 "" ""))))]
2215   "TARGET_BOOLEANS"
2217   if (GET_CODE (operands[2]) == EQ)
2218     return "bt\t%0, %1";
2219   else
2220     return "bf\t%0, %1";
2222   [(set_attr "type"     "jump")
2223    (set_attr "mode"     "none")
2224    (set_attr "length"   "3")])