OSDN Git Service

2002-04-29 Vladimir Makarov <vmakarov@redhat.com>
[pf3gnuchains/gcc-fork.git] / gcc / config / pa / pa.md
1 ;;- Machine description for HP PA-RISC architecture for GNU C compiler
2 ;;   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
3 ;;   2002 Free Software Foundation, Inc.
4 ;;   Contributed by the Center for Software Science at the University
5 ;;   of Utah.
6
7 ;; This file is part of GNU CC.
8
9 ;; GNU CC is free software; you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation; either version 2, or (at your option)
12 ;; any later version.
13
14 ;; GNU CC 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.
18
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GNU CC; see the file COPYING.  If not, write to
21 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
22 ;; Boston, MA 02111-1307, USA.
23
24 ;; This gcc Version 2 machine description is inspired by sparc.md and
25 ;; mips.md.
26
27 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
28
29 ;; Insn type.  Used to default other attribute values.
30
31 ;; type "unary" insns have one input operand (1) and one output operand (0)
32 ;; type "binary" insns have two input operands (1,2) and one output (0)
33
34 (define_attr "type"
35   "move,unary,binary,shift,nullshift,compare,load,store,uncond_branch,branch,cbranch,fbranch,call,dyncall,fpload,fpstore,fpalu,fpcc,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,multi,milli,parallel_branch"
36   (const_string "binary"))
37
38 (define_attr "pa_combine_type"
39   "fmpy,faddsub,uncond_branch,addmove,none"
40   (const_string "none"))
41
42 ;; Processor type (for scheduling, not code generation) -- this attribute
43 ;; must exactly match the processor_type enumeration in pa.h.
44 ;;
45 ;; FIXME: Add 800 scheduling for completeness?
46
47 (define_attr "cpu" "700,7100,7100LC,7200,7300,8000" (const (symbol_ref "pa_cpu_attr")))
48
49 ;; Length (in # of bytes).
50 (define_attr "length" ""
51   (cond [(eq_attr "type" "load,fpload")
52          (if_then_else (match_operand 1 "symbolic_memory_operand" "")
53                        (const_int 8) (const_int 4))
54
55          (eq_attr "type" "store,fpstore")
56          (if_then_else (match_operand 0 "symbolic_memory_operand" "")
57                        (const_int 8) (const_int 4))
58
59          (eq_attr "type" "binary,shift,nullshift")
60          (if_then_else (match_operand 2 "arith_operand" "")
61                        (const_int 4) (const_int 12))
62
63          (eq_attr "type" "move,unary,shift,nullshift")
64          (if_then_else (match_operand 1 "arith_operand" "")
65                        (const_int 4) (const_int 8))]
66
67         (const_int 4)))
68
69 (define_asm_attributes
70   [(set_attr "length" "4")
71    (set_attr "type" "multi")])
72
73 ;; Attributes for instruction and branch scheduling
74
75 ;; For conditional branches.
76 (define_attr "in_branch_delay" "false,true"
77   (if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
78                      (eq_attr "length" "4"))
79                 (const_string "true")
80                 (const_string "false")))
81
82 ;; Disallow instructions which use the FPU since they will tie up the FPU
83 ;; even if the instruction is nullified.
84 (define_attr "in_nullified_branch_delay" "false,true"
85   (if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,parallel_branch")
86                      (eq_attr "length" "4"))
87                 (const_string "true")
88                 (const_string "false")))
89
90 ;; For calls and millicode calls.  Allow unconditional branches in the
91 ;; delay slot.
92 (define_attr "in_call_delay" "false,true"
93   (cond [(and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
94               (eq_attr "length" "4"))
95            (const_string "true")
96          (eq_attr "type" "uncond_branch")
97            (if_then_else (ne (symbol_ref "TARGET_JUMP_IN_DELAY")
98                              (const_int 0))
99                          (const_string "true")
100                          (const_string "false"))]
101         (const_string "false")))
102
103
104 ;; Call delay slot description.
105 (define_delay (eq_attr "type" "call")
106   [(eq_attr "in_call_delay" "true") (nil) (nil)])
107
108 ;; millicode call delay slot description.  Note it disallows delay slot
109 ;; when TARGET_PORTABLE_RUNTIME is true.
110 (define_delay (eq_attr "type" "milli")
111   [(and (eq_attr "in_call_delay" "true")
112         (eq (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0)))
113    (nil) (nil)])
114
115 ;; Return and other similar instructions.
116 (define_delay (eq_attr "type" "branch,parallel_branch")
117   [(eq_attr "in_branch_delay" "true") (nil) (nil)])
118
119 ;; Floating point conditional branch delay slot description and
120 (define_delay (eq_attr "type" "fbranch")
121   [(eq_attr "in_branch_delay" "true")
122    (eq_attr "in_nullified_branch_delay" "true")
123    (nil)])
124
125 ;; Integer conditional branch delay slot description.
126 ;; Nullification of conditional branches on the PA is dependent on the
127 ;; direction of the branch.  Forward branches nullify true and
128 ;; backward branches nullify false.  If the direction is unknown
129 ;; then nullification is not allowed.
130 (define_delay (eq_attr "type" "cbranch")
131   [(eq_attr "in_branch_delay" "true")
132    (and (eq_attr "in_nullified_branch_delay" "true")
133         (attr_flag "forward"))
134    (and (eq_attr "in_nullified_branch_delay" "true")
135         (attr_flag "backward"))])
136
137 (define_delay (and (eq_attr "type" "uncond_branch")
138                    (eq (symbol_ref "following_call (insn)")
139                        (const_int 0)))
140   [(eq_attr "in_branch_delay" "true") (nil) (nil)])
141
142 ;; Memory. Disregarding Cache misses, the Mustang memory times are:
143 ;; load: 2, fpload: 3
144 ;; store, fpstore: 3, no D-cache operations should be scheduled.
145
146 ;; The Timex (aka 700) has two floating-point units: ALU, and MUL/DIV/SQRT.
147 ;; Timings:
148 ;; Instruction  Time    Unit    Minimum Distance (unit contention)
149 ;; fcpy         3       ALU     2
150 ;; fabs         3       ALU     2
151 ;; fadd         3       ALU     2
152 ;; fsub         3       ALU     2
153 ;; fcmp         3       ALU     2
154 ;; fcnv         3       ALU     2
155 ;; fmpyadd      3       ALU,MPY 2
156 ;; fmpysub      3       ALU,MPY 2
157 ;; fmpycfxt     3       ALU,MPY 2
158 ;; fmpy         3       MPY     2
159 ;; fmpyi        3       MPY     2
160 ;; fdiv,sgl     10      MPY     10
161 ;; fdiv,dbl     12      MPY     12
162 ;; fsqrt,sgl    14      MPY     14
163 ;; fsqrt,dbl    18      MPY     18
164 ;;
165 ;; We don't model fmpyadd/fmpysub properly as those instructions
166 ;; keep both the FP ALU and MPY units busy.  Given that these
167 ;; processors are obsolete, I'm not going to spend the time to
168 ;; model those instructions correctly.
169
170 (define_automaton "pa700")
171 (define_cpu_unit "dummy_700,mem_700,fpalu_700,fpmpy_700" "pa700")
172
173 (define_insn_reservation "W0" 4
174   (and (eq_attr "type" "fpcc")
175        (eq_attr "cpu" "700"))
176   "fpalu_700*2")
177
178 (define_insn_reservation "W1" 3
179   (and (eq_attr "type" "fpalu")
180        (eq_attr "cpu" "700"))
181   "fpalu_700*2")
182
183 (define_insn_reservation "W2" 3
184   (and (eq_attr "type" "fpmulsgl,fpmuldbl")
185        (eq_attr "cpu" "700"))
186   "fpmpy_700*2")
187
188 (define_insn_reservation "W3" 10
189   (and (eq_attr "type" "fpdivsgl")
190        (eq_attr "cpu" "700"))
191   "fpmpy_700*10")
192
193 (define_insn_reservation "W4" 12
194   (and (eq_attr "type" "fpdivdbl")
195        (eq_attr "cpu" "700"))
196   "fpmpy_700*12")
197
198 (define_insn_reservation "W5" 14
199   (and (eq_attr "type" "fpsqrtsgl")
200        (eq_attr "cpu" "700"))
201   "fpmpy_700*14")
202
203 (define_insn_reservation "W6" 18
204   (and (eq_attr "type" "fpsqrtdbl")
205        (eq_attr "cpu" "700"))
206   "fpmpy_700*18")
207
208 (define_insn_reservation "W7" 2
209   (and (eq_attr "type" "load,fpload")
210        (eq_attr "cpu" "700"))
211   "mem_700")
212
213 (define_insn_reservation "W8" 3
214   (and (eq_attr "type" "store,fpstore")
215        (eq_attr "cpu" "700"))
216   "mem_700*3")
217
218 (define_insn_reservation "W9" 1
219   (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,load,fpload,store,fpstore")
220        (eq_attr "cpu" "700"))
221   "dummy_700")
222
223 ;; Function units for the 7100 and 7150.  The 7100/7150 can dual-issue
224 ;; floating point computations with non-floating point computations (fp loads
225 ;; and stores are not fp computations).
226 ;;
227 ;; Memory. Disregarding Cache misses, memory loads take two cycles; stores also
228 ;; take two cycles, during which no Dcache operations should be scheduled.
229 ;; Any special cases are handled in pa_adjust_cost.  The 7100, 7150 and 7100LC
230 ;; all have the same memory characteristics if one disregards cache misses.
231
232 ;; The 7100/7150 has three floating-point units: ALU, MUL, and DIV.
233 ;; Timings:
234 ;; Instruction  Time    Unit    Minimum Distance (unit contention)
235 ;; fcpy         2       ALU     1
236 ;; fabs         2       ALU     1
237 ;; fadd         2       ALU     1
238 ;; fsub         2       ALU     1
239 ;; fcmp         2       ALU     1
240 ;; fcnv         2       ALU     1
241 ;; fmpyadd      2       ALU,MPY 1
242 ;; fmpysub      2       ALU,MPY 1
243 ;; fmpycfxt     2       ALU,MPY 1
244 ;; fmpy         2       MPY     1
245 ;; fmpyi        2       MPY     1
246 ;; fdiv,sgl     8       DIV     8
247 ;; fdiv,dbl     15      DIV     15
248 ;; fsqrt,sgl    8       DIV     8
249 ;; fsqrt,dbl    15      DIV     15
250 ;;
251 ;; We don't really model the FP ALU/MPY units properly (they are
252 ;; distinct subunits in the FP unit).  However, there can never be
253 ;; a functional unit; conflict given the latency and issue rates
254 ;; for those units.
255
256 (define_automaton "pa7100")
257 (define_cpu_unit "i_7100, f_7100,fpmac_7100,fpdivsqrt_7100,mem_7100" "pa7100")
258
259 (define_insn_reservation "X0" 2
260   (and (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
261        (eq_attr "cpu" "7100"))
262   "f_7100,fpmac_7100")
263
264 (define_insn_reservation "X1" 8
265   (and (eq_attr "type" "fpdivsgl,fpsqrtsgl")
266        (eq_attr "cpu" "7100"))
267   "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*7")
268
269 (define_insn_reservation "X2" 15
270   (and (eq_attr "type" "fpdivdbl,fpsqrtdbl")
271        (eq_attr "cpu" "7100"))
272   "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*14")
273
274 (define_insn_reservation "X3" 2
275   (and (eq_attr "type" "load,fpload")
276        (eq_attr "cpu" "7100"))
277   "i_7100+mem_7100")
278
279 (define_insn_reservation "X4" 2
280   (and (eq_attr "type" "store,fpstore")
281        (eq_attr "cpu" "7100"))
282   "i_7100+mem_7100,mem_7100")
283
284 (define_insn_reservation "X5" 1
285   (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore")
286        (eq_attr "cpu" "7100"))
287   "i_7100")
288
289 ;; The 7100LC has three floating-point units: ALU, MUL, and DIV.
290 ;; Timings:
291 ;; Instruction  Time    Unit    Minimum Distance (unit contention)
292 ;; fcpy         2       ALU     1
293 ;; fabs         2       ALU     1
294 ;; fadd         2       ALU     1
295 ;; fsub         2       ALU     1
296 ;; fcmp         2       ALU     1
297 ;; fcnv         2       ALU     1
298 ;; fmpyadd,sgl  2       ALU,MPY 1
299 ;; fmpyadd,dbl  3       ALU,MPY 2
300 ;; fmpysub,sgl  2       ALU,MPY 1
301 ;; fmpysub,dbl  3       ALU,MPY 2
302 ;; fmpycfxt,sgl 2       ALU,MPY 1
303 ;; fmpycfxt,dbl 3       ALU,MPY 2
304 ;; fmpy,sgl     2       MPY     1
305 ;; fmpy,dbl     3       MPY     2
306 ;; fmpyi        3       MPY     2
307 ;; fdiv,sgl     8       DIV     8
308 ;; fdiv,dbl     15      DIV     15
309 ;; fsqrt,sgl    8       DIV     8
310 ;; fsqrt,dbl    15      DIV     15
311 ;;
312 ;; The PA7200 is just like the PA7100LC except that there is
313 ;; no store-store penalty.
314 ;;
315 ;; The PA7300 is just like the PA7200 except that there is
316 ;; no store-load penalty.
317 ;;
318 ;; Note there are some aspects of the 7100LC we are not modeling
319 ;; at the moment.  I'll be reviewing the 7100LC scheduling info
320 ;; shortly and updating this description.
321 ;;
322 ;;   load-load pairs
323 ;;   store-store pairs
324 ;;   fmpyadd,dbl
325 ;;   fmpysub,dbl
326 ;;   other issue modeling
327
328 (define_automaton "pa7100lc")
329 (define_cpu_unit "i0_7100lc, i1_7100lc, f_7100lc" "pa7100lc")
330 (define_cpu_unit "fpalu_7100lc,fpdivsqrt_7100lc,fpmul_7100lc" "pa7100lc")
331 (define_cpu_unit "mem_7100lc" "pa7100lc")
332
333 (define_insn_reservation "Y0" 2
334   (and (eq_attr "type" "fpcc,fpalu")
335        (eq_attr "cpu" "7100LC,7200,7300"))
336   "f_7100lc,fpalu_7100lc")
337
338 (define_insn_reservation "Y1" 2
339   (and (eq_attr "type" "fpmulsgl")
340        (eq_attr "cpu" "7100LC,7200,7300"))
341   "f_7100lc,fpmul_7100lc")
342
343 (define_insn_reservation "Y2" 3
344   (and (eq_attr "type" "fpmuldbl")
345        (eq_attr "cpu" "7100LC,7200,7300"))
346   "f_7100lc,fpmul_7100lc,fpmul_7100lc")
347
348 (define_insn_reservation "Y3" 8
349   (and (eq_attr "type" "fpdivsgl,fpsqrtsgl")
350        (eq_attr "cpu" "7100LC,7200,7300"))
351   "f_7100lc+fpdivsqrt_7100lc,fpdivsqrt_7100lc*7")
352
353 (define_insn_reservation "Y4" 15
354   (and (eq_attr "type" "fpdivdbl,fpsqrtdbl")
355        (eq_attr "cpu" "7100LC,7200,7300"))
356   "f_7100lc+fpdivsqrt_7100lc,fpdivsqrt_7100lc*14")
357
358 (define_insn_reservation "Y5" 2
359   (and (eq_attr "type" "load,fpload")
360        (eq_attr "cpu" "7100LC,7200,7300"))
361   "i1_7100lc+mem_7100lc")
362
363 (define_insn_reservation "Y6" 2
364   (and (eq_attr "type" "store,fpstore")
365        (eq_attr "cpu" "7100LC"))
366   "i1_7100lc+mem_7100lc,mem_7100lc")
367
368 (define_insn_reservation "Y7" 1
369   (and (eq_attr "type" "shift,nullshift")
370        (eq_attr "cpu" "7100LC,7200,7300"))
371   "i1_7100lc")
372
373 (define_insn_reservation "Y8" 1
374   (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore,shift,nullshift")
375        (eq_attr "cpu" "7100LC,7200,7300"))
376   "(i0_7100lc|i1_7100lc)")
377
378 ;; The 7200 has a store-load penalty
379 (define_insn_reservation "Y9" 2
380   (and (eq_attr "type" "store,fpstore")
381        (eq_attr "cpu" "7200"))
382   "i0_7100lc,mem_7100lc")
383
384 ;; The 7300 has no penalty for store-store or store-load
385 (define_insn_reservation "YA" 2
386   (and (eq_attr "type" "store,fpstore")
387        (eq_attr "cpu" "7300"))
388   "i0_7100lc")
389
390 ;; Scheduling for the PA8000 is somewhat different than scheduling for a
391 ;; traditional architecture.
392 ;;
393 ;; The PA8000 has a large (56) entry reorder buffer that is split between
394 ;; memory and non-memory operations.
395 ;;
396 ;; The PA8000 can issue two memory and two non-memory operations per cycle to
397 ;; the function units, with the exception of branches and multi-output
398 ;; instructions.  The PA8000 can retire two non-memory operations per cycle
399 ;; and two memory operations per cycle, only one of which may be a store.
400 ;;
401 ;; Given the large reorder buffer, the processor can hide most latencies.
402 ;; According to HP, they've got the best results by scheduling for retirement
403 ;; bandwidth with limited latency scheduling for floating point operations.
404 ;; Latency for integer operations and memory references is ignored.
405 ;;
406 ;;
407 ;; We claim floating point operations have a 2 cycle latency and are
408 ;; fully pipelined, except for div and sqrt which are not pipelined and
409 ;; take from 17 to 31 cycles to complete.
410 ;;
411 ;; It's worth noting that there is no way to saturate all the functional
412 ;; units on the PA8000 as there is not enough issue bandwidth.
413
414 (define_automaton "pa8000")
415 (define_cpu_unit "inm0_8000, inm1_8000, im0_8000, im1_8000" "pa8000")
416 (define_cpu_unit "rnm0_8000, rnm1_8000, rm0_8000, rm1_8000" "pa8000")
417 (define_cpu_unit "store_8000" "pa8000")
418 (define_cpu_unit "f0_8000, f1_8000" "pa8000")
419 (define_cpu_unit "fdivsqrt0_8000, fdivsqrt1_8000" "pa8000")
420 (define_reservation "inm_8000" "inm0_8000 | inm1_8000")
421 (define_reservation "im_8000" "im0_8000 | im1_8000")
422 (define_reservation "rnm_8000" "rnm0_8000 | rnm1_8000")
423 (define_reservation "rm_8000" "rm0_8000 | rm1_8000")
424 (define_reservation "f_8000" "f0_8000 | f1_8000")
425 (define_reservation "fdivsqrt_8000" "fdivsqrt0_8000 | fdivsqrt1_8000")
426
427 ;; We can issue any two memops per cycle, but we can only retire
428 ;; one memory store per cycle.  We assume that the reorder buffer
429 ;; will hide any memory latencies per HP's recommendation.
430 (define_insn_reservation "Z0" 0
431   (and
432     (eq_attr "type" "load,fpload")
433     (eq_attr "cpu" "8000"))
434   "im_8000,rm_8000")
435
436 (define_insn_reservation "Z1" 0
437   (and
438     (eq_attr "type" "store,fpstore")
439     (eq_attr "cpu" "8000"))
440   "im_8000,rm_8000+store_8000")
441
442 ;; We can issue and retire two non-memory operations per cycle with
443 ;; a few exceptions (branches).  This group catches those we want
444 ;; to assume have zero latency.
445 (define_insn_reservation "Z2" 0
446   (and
447     (eq_attr "type" "!load,fpload,store,fpstore,uncond_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch,fpcc,fpalu,fpmulsgl,fpmuldbl,fpsqrtsgl,fpsqrtdbl,fpdivsgl,fpdivdbl")
448     (eq_attr "cpu" "8000"))
449   "inm_8000,rnm_8000")
450
451 ;; Branches use both slots in the non-memory issue and
452 ;; retirement unit.
453 (define_insn_reservation "Z3" 0
454   (and
455     (eq_attr "type" "uncond_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
456     (eq_attr "cpu" "8000"))
457   "inm0_8000+inm1_8000,rnm0_8000+rnm1_8000")
458
459 ;; We partial latency schedule the floating point units.
460 ;; They can issue/retire two at a time in the non-memory
461 ;; units.  We fix their latency at 2 cycles and they
462 ;; are fully pipelined.
463 (define_insn_reservation "Z4" 1
464  (and
465    (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
466    (eq_attr "cpu" "8000"))
467  "inm_8000,f_8000,rnm_8000")
468
469 ;; The fdivsqrt units are not pipelined and have a very long latency.  
470 ;; To keep the DFA from exploding, we do not show all the
471 ;; reservations for the divsqrt unit.
472 (define_insn_reservation "Z5" 17
473  (and
474    (eq_attr "type" "fpdivsgl,fpsqrtsgl")
475    (eq_attr "cpu" "8000"))
476  "inm_8000,fdivsqrt_8000*6,rnm_8000")
477
478 (define_insn_reservation "Z6" 31
479  (and
480    (eq_attr "type" "fpdivdbl,fpsqrtdbl")
481    (eq_attr "cpu" "8000"))
482  "inm_8000,fdivsqrt_8000*6,rnm_8000")
483
484
485 \f
486 ;; Compare instructions.
487 ;; This controls RTL generation and register allocation.
488
489 ;; We generate RTL for comparisons and branches by having the cmpxx
490 ;; patterns store away the operands.  Then, the scc and bcc patterns
491 ;; emit RTL for both the compare and the branch.
492 ;;
493
494 (define_expand "cmpdi"
495   [(set (reg:CC 0)
496         (compare:CC (match_operand:DI 0 "reg_or_0_operand" "")
497                     (match_operand:DI 1 "register_operand" "")))]
498   "TARGET_64BIT"
499
500   "
501 {
502  hppa_compare_op0 = operands[0];
503  hppa_compare_op1 = operands[1];
504  hppa_branch_type = CMP_SI;
505  DONE;
506 }")
507
508 (define_expand "cmpsi"
509   [(set (reg:CC 0)
510         (compare:CC (match_operand:SI 0 "reg_or_0_operand" "")
511                     (match_operand:SI 1 "arith5_operand" "")))]
512   ""
513   "
514 {
515  hppa_compare_op0 = operands[0];
516  hppa_compare_op1 = operands[1];
517  hppa_branch_type = CMP_SI;
518  DONE;
519 }")
520
521 (define_expand "cmpsf"
522   [(set (reg:CCFP 0)
523         (compare:CCFP (match_operand:SF 0 "reg_or_0_operand" "")
524                       (match_operand:SF 1 "reg_or_0_operand" "")))]
525   "! TARGET_SOFT_FLOAT"
526   "
527 {
528   hppa_compare_op0 = operands[0];
529   hppa_compare_op1 = operands[1];
530   hppa_branch_type = CMP_SF;
531   DONE;
532 }")
533
534 (define_expand "cmpdf"
535   [(set (reg:CCFP 0)
536       (compare:CCFP (match_operand:DF 0 "reg_or_0_operand" "")
537                     (match_operand:DF 1 "reg_or_0_operand" "")))]
538   "! TARGET_SOFT_FLOAT"
539   "
540 {
541   hppa_compare_op0 = operands[0];
542   hppa_compare_op1 = operands[1];
543   hppa_branch_type = CMP_DF;
544   DONE;
545 }")
546
547 (define_insn ""
548   [(set (reg:CCFP 0)
549         (match_operator:CCFP 2 "comparison_operator"
550                              [(match_operand:SF 0 "reg_or_0_operand" "fG")
551                               (match_operand:SF 1 "reg_or_0_operand" "fG")]))]
552   "! TARGET_SOFT_FLOAT"
553   "fcmp,sgl,%Y2 %f0,%f1"
554   [(set_attr "length" "4")
555    (set_attr "type" "fpcc")])
556
557 (define_insn ""
558   [(set (reg:CCFP 0)
559         (match_operator:CCFP 2 "comparison_operator"
560                              [(match_operand:DF 0 "reg_or_0_operand" "fG")
561                               (match_operand:DF 1 "reg_or_0_operand" "fG")]))]
562   "! TARGET_SOFT_FLOAT"
563   "fcmp,dbl,%Y2 %f0,%f1"
564   [(set_attr "length" "4")
565    (set_attr "type" "fpcc")])
566
567 ;; scc insns.
568
569 (define_expand "seq"
570   [(set (match_operand:SI 0 "register_operand" "")
571         (eq:SI (match_dup 1)
572                (match_dup 2)))]
573   "!TARGET_64BIT"
574   "
575 {
576   /* fp scc patterns rarely match, and are not a win on the PA.  */
577   if (hppa_branch_type != CMP_SI)
578     FAIL;
579   /* set up operands from compare.  */
580   operands[1] = hppa_compare_op0;
581   operands[2] = hppa_compare_op1;
582   /* fall through and generate default code */
583 }")
584
585 (define_expand "sne"
586   [(set (match_operand:SI 0 "register_operand" "")
587         (ne:SI (match_dup 1)
588                (match_dup 2)))]
589   "!TARGET_64BIT"
590   "
591 {
592   /* fp scc patterns rarely match, and are not a win on the PA.  */
593   if (hppa_branch_type != CMP_SI)
594     FAIL;
595   operands[1] = hppa_compare_op0;
596   operands[2] = hppa_compare_op1;
597 }")
598
599 (define_expand "slt"
600   [(set (match_operand:SI 0 "register_operand" "")
601         (lt:SI (match_dup 1)
602                (match_dup 2)))]
603   "!TARGET_64BIT"
604   "
605 {
606   /* fp scc patterns rarely match, and are not a win on the PA.  */
607   if (hppa_branch_type != CMP_SI)
608     FAIL;
609   operands[1] = hppa_compare_op0;
610   operands[2] = hppa_compare_op1;
611 }")
612
613 (define_expand "sgt"
614   [(set (match_operand:SI 0 "register_operand" "")
615         (gt:SI (match_dup 1)
616                (match_dup 2)))]
617   "!TARGET_64BIT"
618   "
619 {
620   /* fp scc patterns rarely match, and are not a win on the PA.  */
621   if (hppa_branch_type != CMP_SI)
622     FAIL;
623   operands[1] = hppa_compare_op0;
624   operands[2] = hppa_compare_op1;
625 }")
626
627 (define_expand "sle"
628   [(set (match_operand:SI 0 "register_operand" "")
629         (le:SI (match_dup 1)
630                (match_dup 2)))]
631   "!TARGET_64BIT"
632   "
633 {
634   /* fp scc patterns rarely match, and are not a win on the PA.  */
635   if (hppa_branch_type != CMP_SI)
636     FAIL;
637   operands[1] = hppa_compare_op0;
638   operands[2] = hppa_compare_op1;
639 }")
640
641 (define_expand "sge"
642   [(set (match_operand:SI 0 "register_operand" "")
643         (ge:SI (match_dup 1)
644                (match_dup 2)))]
645   "!TARGET_64BIT"
646   "
647 {
648   /* fp scc patterns rarely match, and are not a win on the PA.  */
649   if (hppa_branch_type != CMP_SI)
650     FAIL;
651   operands[1] = hppa_compare_op0;
652   operands[2] = hppa_compare_op1;
653 }")
654
655 (define_expand "sltu"
656   [(set (match_operand:SI 0 "register_operand" "")
657         (ltu:SI (match_dup 1)
658                 (match_dup 2)))]
659   "!TARGET_64BIT"
660   "
661 {
662   if (hppa_branch_type != CMP_SI)
663     FAIL;
664   operands[1] = hppa_compare_op0;
665   operands[2] = hppa_compare_op1;
666 }")
667
668 (define_expand "sgtu"
669   [(set (match_operand:SI 0 "register_operand" "")
670         (gtu:SI (match_dup 1)
671                 (match_dup 2)))]
672   "!TARGET_64BIT"
673   "
674 {
675   if (hppa_branch_type != CMP_SI)
676     FAIL;
677   operands[1] = hppa_compare_op0;
678   operands[2] = hppa_compare_op1;
679 }")
680
681 (define_expand "sleu"
682   [(set (match_operand:SI 0 "register_operand" "")
683         (leu:SI (match_dup 1)
684                 (match_dup 2)))]
685   "!TARGET_64BIT"
686   "
687 {
688   if (hppa_branch_type != CMP_SI)
689     FAIL;
690   operands[1] = hppa_compare_op0;
691   operands[2] = hppa_compare_op1;
692 }")
693
694 (define_expand "sgeu"
695   [(set (match_operand:SI 0 "register_operand" "")
696         (geu:SI (match_dup 1)
697                 (match_dup 2)))]
698   "!TARGET_64BIT"
699   "
700 {
701   if (hppa_branch_type != CMP_SI)
702     FAIL;
703   operands[1] = hppa_compare_op0;
704   operands[2] = hppa_compare_op1;
705 }")
706
707 ;; Instruction canonicalization puts immediate operands second, which
708 ;; is the reverse of what we want.
709
710 (define_insn "scc"
711   [(set (match_operand:SI 0 "register_operand" "=r")
712         (match_operator:SI 3 "comparison_operator"
713                            [(match_operand:SI 1 "register_operand" "r")
714                             (match_operand:SI 2 "arith11_operand" "rI")]))]
715   ""
716   "{com%I2clr|cmp%I2clr},%B3 %2,%1,%0\;ldi 1,%0"
717   [(set_attr "type" "binary")
718    (set_attr "length" "8")])
719
720 (define_insn ""
721   [(set (match_operand:DI 0 "register_operand" "=r")
722         (match_operator:DI 3 "comparison_operator"
723                            [(match_operand:DI 1 "register_operand" "r")
724                             (match_operand:DI 2 "arith11_operand" "rI")]))]
725   "TARGET_64BIT"
726   "cmp%I2clr,*%B3 %2,%1,%0\;ldi 1,%0"
727   [(set_attr "type" "binary")
728    (set_attr "length" "8")])
729
730 (define_insn "iorscc"
731   [(set (match_operand:SI 0 "register_operand" "=r")
732         (ior:SI (match_operator:SI 3 "comparison_operator"
733                                    [(match_operand:SI 1 "register_operand" "r")
734                                     (match_operand:SI 2 "arith11_operand" "rI")])
735                 (match_operator:SI 6 "comparison_operator"
736                                    [(match_operand:SI 4 "register_operand" "r")
737                                     (match_operand:SI 5 "arith11_operand" "rI")])))]
738   ""
739   "{com%I2clr|cmp%I2clr},%S3 %2,%1,%%r0\;{com%I5clr|cmp%I5clr},%B6 %5,%4,%0\;ldi 1,%0"
740   [(set_attr "type" "binary")
741    (set_attr "length" "12")])
742
743 (define_insn ""
744   [(set (match_operand:DI 0 "register_operand" "=r")
745         (ior:DI (match_operator:DI 3 "comparison_operator"
746                                    [(match_operand:DI 1 "register_operand" "r")
747                                     (match_operand:DI 2 "arith11_operand" "rI")])
748                 (match_operator:DI 6 "comparison_operator"
749                                    [(match_operand:DI 4 "register_operand" "r")
750                                     (match_operand:DI 5 "arith11_operand" "rI")])))]
751   "TARGET_64BIT"
752   "cmp%I2clr,*%S3 %2,%1,%%r0\;cmp%I5clr,*%B6 %5,%4,%0\;ldi 1,%0"
753   [(set_attr "type" "binary")
754    (set_attr "length" "12")])
755
756 ;; Combiner patterns for common operations performed with the output
757 ;; from an scc insn (negscc and incscc).
758 (define_insn "negscc"
759   [(set (match_operand:SI 0 "register_operand" "=r")
760         (neg:SI (match_operator:SI 3 "comparison_operator"
761                [(match_operand:SI 1 "register_operand" "r")
762                 (match_operand:SI 2 "arith11_operand" "rI")])))]
763   ""
764   "{com%I2clr|cmp%I2clr},%B3 %2,%1,%0\;ldi -1,%0"
765   [(set_attr "type" "binary")
766    (set_attr "length" "8")])
767
768 (define_insn ""
769   [(set (match_operand:DI 0 "register_operand" "=r")
770         (neg:DI (match_operator:DI 3 "comparison_operator"
771                [(match_operand:DI 1 "register_operand" "r")
772                 (match_operand:DI 2 "arith11_operand" "rI")])))]
773   "TARGET_64BIT"
774   "cmp%I2clr,*%B3 %2,%1,%0\;ldi -1,%0"
775   [(set_attr "type" "binary")
776    (set_attr "length" "8")])
777
778 ;; Patterns for adding/subtracting the result of a boolean expression from
779 ;; a register.  First we have special patterns that make use of the carry
780 ;; bit, and output only two instructions.  For the cases we can't in
781 ;; general do in two instructions, the incscc pattern at the end outputs
782 ;; two or three instructions.
783
784 (define_insn ""
785   [(set (match_operand:SI 0 "register_operand" "=r")
786         (plus:SI (leu:SI (match_operand:SI 2 "register_operand" "r")
787                          (match_operand:SI 3 "arith11_operand" "rI"))
788                  (match_operand:SI 1 "register_operand" "r")))]
789   ""
790   "sub%I3 %3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
791   [(set_attr "type" "binary")
792    (set_attr "length" "8")])
793
794 (define_insn ""
795   [(set (match_operand:DI 0 "register_operand" "=r")
796         (plus:DI (leu:DI (match_operand:DI 2 "register_operand" "r")
797                          (match_operand:DI 3 "arith11_operand" "rI"))
798                  (match_operand:DI 1 "register_operand" "r")))]
799   "TARGET_64BIT"
800   "sub%I3 %3,%2,%%r0\;add,dc %%r0,%1,%0"
801   [(set_attr "type" "binary")
802    (set_attr "length" "8")])
803
804 ; This need only accept registers for op3, since canonicalization
805 ; replaces geu with gtu when op3 is an integer.
806 (define_insn ""
807   [(set (match_operand:SI 0 "register_operand" "=r")
808         (plus:SI (geu:SI (match_operand:SI 2 "register_operand" "r")
809                          (match_operand:SI 3 "register_operand" "r"))
810                  (match_operand:SI 1 "register_operand" "r")))]
811   ""
812   "sub %2,%3,%%r0\;{addc|add,c} %%r0,%1,%0"
813   [(set_attr "type" "binary")
814    (set_attr "length" "8")])
815
816 (define_insn ""
817   [(set (match_operand:DI 0 "register_operand" "=r")
818         (plus:DI (geu:DI (match_operand:DI 2 "register_operand" "r")
819                          (match_operand:DI 3 "register_operand" "r"))
820                  (match_operand:DI 1 "register_operand" "r")))]
821   "TARGET_64BIT"
822   "sub %2,%3,%%r0\;add,dc %%r0,%1,%0"
823   [(set_attr "type" "binary")
824    (set_attr "length" "8")])
825
826 ; Match only integers for op3 here.  This is used as canonical form of the
827 ; geu pattern when op3 is an integer.  Don't match registers since we can't
828 ; make better code than the general incscc pattern.
829 (define_insn ""
830   [(set (match_operand:SI 0 "register_operand" "=r")
831         (plus:SI (gtu:SI (match_operand:SI 2 "register_operand" "r")
832                          (match_operand:SI 3 "int11_operand" "I"))
833                  (match_operand:SI 1 "register_operand" "r")))]
834   ""
835   "addi %k3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
836   [(set_attr "type" "binary")
837    (set_attr "length" "8")])
838
839 (define_insn ""
840   [(set (match_operand:DI 0 "register_operand" "=r")
841         (plus:DI (gtu:DI (match_operand:DI 2 "register_operand" "r")
842                          (match_operand:DI 3 "int11_operand" "I"))
843                  (match_operand:DI 1 "register_operand" "r")))]
844   "TARGET_64BIT"
845   "addi %k3,%2,%%r0\;add,dc %%r0,%1,%0"
846   [(set_attr "type" "binary")
847    (set_attr "length" "8")])
848
849 (define_insn "incscc"
850   [(set (match_operand:SI 0 "register_operand" "=r,r")
851         (plus:SI (match_operator:SI 4 "comparison_operator"
852                     [(match_operand:SI 2 "register_operand" "r,r")
853                      (match_operand:SI 3 "arith11_operand" "rI,rI")])
854                  (match_operand:SI 1 "register_operand" "0,?r")))]
855   ""
856   "@
857    {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi 1,%0,%0
858    {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
859   [(set_attr "type" "binary,binary")
860    (set_attr "length" "8,12")])
861
862 (define_insn ""
863   [(set (match_operand:DI 0 "register_operand" "=r,r")
864         (plus:DI (match_operator:DI 4 "comparison_operator"
865                     [(match_operand:DI 2 "register_operand" "r,r")
866                      (match_operand:DI 3 "arith11_operand" "rI,rI")])
867                  (match_operand:DI 1 "register_operand" "0,?r")))]
868   "TARGET_64BIT"
869   "@
870    cmp%I3clr,*%B4 %3,%2,%%r0\;addi 1,%0,%0
871    cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
872   [(set_attr "type" "binary,binary")
873    (set_attr "length" "8,12")])
874
875 (define_insn ""
876   [(set (match_operand:SI 0 "register_operand" "=r")
877         (minus:SI (match_operand:SI 1 "register_operand" "r")
878                   (gtu:SI (match_operand:SI 2 "register_operand" "r")
879                           (match_operand:SI 3 "arith11_operand" "rI"))))]
880   ""
881   "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
882   [(set_attr "type" "binary")
883    (set_attr "length" "8")])
884
885 (define_insn ""
886   [(set (match_operand:DI 0 "register_operand" "=r")
887         (minus:DI (match_operand:DI 1 "register_operand" "r")
888                   (gtu:DI (match_operand:DI 2 "register_operand" "r")
889                           (match_operand:DI 3 "arith11_operand" "rI"))))]
890   "TARGET_64BIT"
891   "sub%I3 %3,%2,%%r0\;sub,db %1,%%r0,%0"
892   [(set_attr "type" "binary")
893    (set_attr "length" "8")])
894
895 (define_insn ""
896   [(set (match_operand:SI 0 "register_operand" "=r")
897         (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
898                             (gtu:SI (match_operand:SI 2 "register_operand" "r")
899                                     (match_operand:SI 3 "arith11_operand" "rI")))
900                   (match_operand:SI 4 "register_operand" "r")))]
901   ""
902   "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
903   [(set_attr "type" "binary")
904    (set_attr "length" "8")])
905
906 (define_insn ""
907   [(set (match_operand:DI 0 "register_operand" "=r")
908         (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
909                             (gtu:DI (match_operand:DI 2 "register_operand" "r")
910                                     (match_operand:DI 3 "arith11_operand" "rI")))
911                   (match_operand:DI 4 "register_operand" "r")))]
912   "TARGET_64BIT"
913   "sub%I3 %3,%2,%%r0\;sub,db %1,%4,%0"
914   [(set_attr "type" "binary")
915    (set_attr "length" "8")])
916
917 ; This need only accept registers for op3, since canonicalization
918 ; replaces ltu with leu when op3 is an integer.
919 (define_insn ""
920   [(set (match_operand:SI 0 "register_operand" "=r")
921         (minus:SI (match_operand:SI 1 "register_operand" "r")
922                   (ltu:SI (match_operand:SI 2 "register_operand" "r")
923                           (match_operand:SI 3 "register_operand" "r"))))]
924   ""
925   "sub %2,%3,%%r0\;{subb|sub,b} %1,%%r0,%0"
926   [(set_attr "type" "binary")
927    (set_attr "length" "8")])
928
929 (define_insn ""
930   [(set (match_operand:DI 0 "register_operand" "=r")
931         (minus:DI (match_operand:DI 1 "register_operand" "r")
932                   (ltu:DI (match_operand:DI 2 "register_operand" "r")
933                           (match_operand:DI 3 "register_operand" "r"))))]
934   "TARGET_64BIT"
935   "sub %2,%3,%%r0\;sub,db %1,%%r0,%0"
936   [(set_attr "type" "binary")
937    (set_attr "length" "8")])
938
939 (define_insn ""
940   [(set (match_operand:SI 0 "register_operand" "=r")
941         (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
942                             (ltu:SI (match_operand:SI 2 "register_operand" "r")
943                                     (match_operand:SI 3 "register_operand" "r")))
944                   (match_operand:SI 4 "register_operand" "r")))]
945   ""
946   "sub %2,%3,%%r0\;{subb|sub,b} %1,%4,%0"
947   [(set_attr "type" "binary")
948    (set_attr "length" "8")])
949
950 (define_insn ""
951   [(set (match_operand:DI 0 "register_operand" "=r")
952         (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
953                             (ltu:DI (match_operand:DI 2 "register_operand" "r")
954                                     (match_operand:DI 3 "register_operand" "r")))
955                   (match_operand:DI 4 "register_operand" "r")))]
956   "TARGET_64BIT"
957   "sub %2,%3,%%r0\;sub,db %1,%4,%0"
958   [(set_attr "type" "binary")
959    (set_attr "length" "8")])
960
961 ; Match only integers for op3 here.  This is used as canonical form of the
962 ; ltu pattern when op3 is an integer.  Don't match registers since we can't
963 ; make better code than the general incscc pattern.
964 (define_insn ""
965   [(set (match_operand:SI 0 "register_operand" "=r")
966         (minus:SI (match_operand:SI 1 "register_operand" "r")
967                   (leu:SI (match_operand:SI 2 "register_operand" "r")
968                           (match_operand:SI 3 "int11_operand" "I"))))]
969   ""
970   "addi %k3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
971   [(set_attr "type" "binary")
972    (set_attr "length" "8")])
973
974 (define_insn ""
975   [(set (match_operand:DI 0 "register_operand" "=r")
976         (minus:DI (match_operand:DI 1 "register_operand" "r")
977                   (leu:DI (match_operand:DI 2 "register_operand" "r")
978                           (match_operand:DI 3 "int11_operand" "I"))))]
979   "TARGET_64BIT"
980   "addi %k3,%2,%%r0\;sub,db %1,%%r0,%0"
981   [(set_attr "type" "binary")
982    (set_attr "length" "8")])
983
984 (define_insn ""
985   [(set (match_operand:SI 0 "register_operand" "=r")
986         (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
987                             (leu:SI (match_operand:SI 2 "register_operand" "r")
988                                     (match_operand:SI 3 "int11_operand" "I")))
989                   (match_operand:SI 4 "register_operand" "r")))]
990   ""
991   "addi %k3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
992   [(set_attr "type" "binary")
993    (set_attr "length" "8")])
994
995 (define_insn ""
996   [(set (match_operand:DI 0 "register_operand" "=r")
997         (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
998                             (leu:DI (match_operand:DI 2 "register_operand" "r")
999                                     (match_operand:DI 3 "int11_operand" "I")))
1000                   (match_operand:DI 4 "register_operand" "r")))]
1001   "TARGET_64BIT"
1002   "addi %k3,%2,%%r0\;sub,db %1,%4,%0"
1003   [(set_attr "type" "binary")
1004    (set_attr "length" "8")])
1005
1006 (define_insn "decscc"
1007   [(set (match_operand:SI 0 "register_operand" "=r,r")
1008         (minus:SI (match_operand:SI 1 "register_operand" "0,?r")
1009                   (match_operator:SI 4 "comparison_operator"
1010                      [(match_operand:SI 2 "register_operand" "r,r")
1011                       (match_operand:SI 3 "arith11_operand" "rI,rI")])))]
1012   ""
1013   "@
1014    {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi -1,%0,%0
1015    {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1016   [(set_attr "type" "binary,binary")
1017    (set_attr "length" "8,12")])
1018
1019 (define_insn ""
1020   [(set (match_operand:DI 0 "register_operand" "=r,r")
1021         (minus:DI (match_operand:DI 1 "register_operand" "0,?r")
1022                   (match_operator:DI 4 "comparison_operator"
1023                      [(match_operand:DI 2 "register_operand" "r,r")
1024                       (match_operand:DI 3 "arith11_operand" "rI,rI")])))]
1025   "TARGET_64BIT"
1026   "@
1027    cmp%I3clr,*%B4 %3,%2,%%r0\;addi -1,%0,%0
1028    cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1029   [(set_attr "type" "binary,binary")
1030    (set_attr "length" "8,12")])
1031
1032 ; Patterns for max and min.  (There is no need for an earlyclobber in the
1033 ; last alternative since the middle alternative will match if op0 == op1.)
1034
1035 (define_insn "sminsi3"
1036   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1037         (smin:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1038                  (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1039   ""
1040   "@
1041   {comclr|cmpclr},> %2,%0,%%r0\;copy %2,%0
1042   {comiclr|cmpiclr},> %2,%0,%%r0\;ldi %2,%0
1043   {comclr|cmpclr},> %1,%r2,%0\;copy %1,%0"
1044 [(set_attr "type" "multi,multi,multi")
1045  (set_attr "length" "8,8,8")])
1046
1047 (define_insn "smindi3"
1048   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1049         (smin:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1050                  (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1051   "TARGET_64BIT"
1052   "@
1053   cmpclr,*> %2,%0,%%r0\;copy %2,%0
1054   cmpiclr,*> %2,%0,%%r0\;ldi %2,%0
1055   cmpclr,*> %1,%r2,%0\;copy %1,%0"
1056 [(set_attr "type" "multi,multi,multi")
1057  (set_attr "length" "8,8,8")])
1058
1059 (define_insn "uminsi3"
1060   [(set (match_operand:SI 0 "register_operand" "=r,r")
1061         (umin:SI (match_operand:SI 1 "register_operand" "%0,0")
1062                  (match_operand:SI 2 "arith11_operand" "r,I")))]
1063   ""
1064   "@
1065   {comclr|cmpclr},>> %2,%0,%%r0\;copy %2,%0
1066   {comiclr|cmpiclr},>> %2,%0,%%r0\;ldi %2,%0"
1067 [(set_attr "type" "multi,multi")
1068  (set_attr "length" "8,8")])
1069
1070 (define_insn "umindi3"
1071   [(set (match_operand:DI 0 "register_operand" "=r,r")
1072         (umin:DI (match_operand:DI 1 "register_operand" "%0,0")
1073                  (match_operand:DI 2 "arith11_operand" "r,I")))]
1074   "TARGET_64BIT"
1075   "@
1076   cmpclr,*>> %2,%0,%%r0\;copy %2,%0
1077   cmpiclr,*>> %2,%0,%%r0\;ldi %2,%0"
1078 [(set_attr "type" "multi,multi")
1079  (set_attr "length" "8,8")])
1080
1081 (define_insn "smaxsi3"
1082   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1083         (smax:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1084                  (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1085   ""
1086   "@
1087   {comclr|cmpclr},< %2,%0,%%r0\;copy %2,%0
1088   {comiclr|cmpiclr},< %2,%0,%%r0\;ldi %2,%0
1089   {comclr|cmpclr},< %1,%r2,%0\;copy %1,%0"
1090 [(set_attr "type" "multi,multi,multi")
1091  (set_attr "length" "8,8,8")])
1092
1093 (define_insn "smaxdi3"
1094   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1095         (smax:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1096                  (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1097   "TARGET_64BIT"
1098   "@
1099   cmpclr,*< %2,%0,%%r0\;copy %2,%0
1100   cmpiclr,*< %2,%0,%%r0\;ldi %2,%0
1101   cmpclr,*< %1,%r2,%0\;copy %1,%0"
1102 [(set_attr "type" "multi,multi,multi")
1103  (set_attr "length" "8,8,8")])
1104
1105 (define_insn "umaxsi3"
1106   [(set (match_operand:SI 0 "register_operand" "=r,r")
1107         (umax:SI (match_operand:SI 1 "register_operand" "%0,0")
1108                  (match_operand:SI 2 "arith11_operand" "r,I")))]
1109   ""
1110   "@
1111   {comclr|cmpclr},<< %2,%0,%%r0\;copy %2,%0
1112   {comiclr|cmpiclr},<< %2,%0,%%r0\;ldi %2,%0"
1113 [(set_attr "type" "multi,multi")
1114  (set_attr "length" "8,8")])
1115
1116 (define_insn "umaxdi3"
1117   [(set (match_operand:DI 0 "register_operand" "=r,r")
1118         (umax:DI (match_operand:DI 1 "register_operand" "%0,0")
1119                  (match_operand:DI 2 "arith11_operand" "r,I")))]
1120   "TARGET_64BIT"
1121   "@
1122   cmpclr,*<< %2,%0,%%r0\;copy %2,%0
1123   cmpiclr,*<< %2,%0,%%r0\;ldi %2,%0"
1124 [(set_attr "type" "multi,multi")
1125  (set_attr "length" "8,8")])
1126
1127 (define_insn "abssi2"
1128   [(set (match_operand:SI 0 "register_operand" "=r")
1129         (abs:SI (match_operand:SI 1 "register_operand" "r")))]
1130   ""
1131   "or,>= %%r0,%1,%0\;subi 0,%0,%0"
1132   [(set_attr "type" "multi")
1133    (set_attr "length" "8")])
1134
1135 (define_insn "absdi2"
1136   [(set (match_operand:DI 0 "register_operand" "=r")
1137         (abs:DI (match_operand:DI 1 "register_operand" "r")))]
1138   "TARGET_64BIT"
1139   "or,*>= %%r0,%1,%0\;subi 0,%0,%0"
1140   [(set_attr "type" "multi")
1141    (set_attr "length" "8")])
1142
1143 ;;; Experimental conditional move patterns
1144
1145 (define_expand "movsicc"
1146   [(set (match_operand:SI 0 "register_operand" "")
1147         (if_then_else:SI
1148          (match_operator 1 "comparison_operator"
1149             [(match_dup 4)
1150              (match_dup 5)])
1151          (match_operand:SI 2 "reg_or_cint_move_operand" "")
1152          (match_operand:SI 3 "reg_or_cint_move_operand" "")))]
1153   ""
1154   "
1155 {
1156   enum rtx_code code = GET_CODE (operands[1]);
1157
1158   if (hppa_branch_type != CMP_SI)
1159     FAIL;
1160
1161   if (GET_MODE (hppa_compare_op0) != GET_MODE (hppa_compare_op1)
1162       || GET_MODE (hppa_compare_op0) != GET_MODE (operands[0]))
1163     FAIL;
1164
1165   /* operands[1] is currently the result of compare_from_rtx.  We want to
1166      emit a compare of the original operands.  */
1167   operands[1] = gen_rtx_fmt_ee (code, SImode, hppa_compare_op0, hppa_compare_op1);
1168   operands[4] = hppa_compare_op0;
1169   operands[5] = hppa_compare_op1;
1170 }")
1171
1172 ;; We used to accept any register for op1.
1173 ;;
1174 ;; However, it loses sometimes because the compiler will end up using
1175 ;; different registers for op0 and op1 in some critical cases.  local-alloc
1176 ;; will  not tie op0 and op1 because op0 is used in multiple basic blocks.
1177 ;;
1178 ;; If/when global register allocation supports tying we should allow any
1179 ;; register for op1 again.
1180 (define_insn ""
1181   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
1182         (if_then_else:SI
1183          (match_operator 2 "comparison_operator"
1184             [(match_operand:SI 3 "register_operand" "r,r,r,r")
1185              (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI")])
1186          (match_operand:SI 1 "reg_or_cint_move_operand" "0,J,N,K")
1187          (const_int 0)))]
1188   ""
1189   "@
1190    {com%I4clr|cmp%I4clr},%S2 %4,%3,%%r0\;ldi 0,%0
1191    {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldi %1,%0
1192    {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldil L'%1,%0
1193    {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;{zdepi|depwi,z} %Z1,%0"
1194   [(set_attr "type" "multi,multi,multi,nullshift")
1195    (set_attr "length" "8,8,8,8")])
1196
1197 (define_insn ""
1198   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1199         (if_then_else:SI
1200          (match_operator 5 "comparison_operator"
1201             [(match_operand:SI 3 "register_operand" "r,r,r,r,r,r,r,r")
1202              (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1203          (match_operand:SI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1204          (match_operand:SI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1205   ""
1206   "@
1207    {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;copy %2,%0
1208    {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldi %2,%0
1209    {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldil L'%2,%0
1210    {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;{zdepi|depwi,z} %Z2,%0
1211    {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;copy %1,%0
1212    {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldi %1,%0
1213    {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldil L'%1,%0
1214    {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;{zdepi|depwi,z} %Z1,%0"
1215   [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1216    (set_attr "length" "8,8,8,8,8,8,8,8")])
1217
1218 (define_expand "movdicc"
1219   [(set (match_operand:DI 0 "register_operand" "")
1220         (if_then_else:DI
1221          (match_operator 1 "comparison_operator"
1222             [(match_dup 4)
1223              (match_dup 5)])
1224          (match_operand:DI 2 "reg_or_cint_move_operand" "")
1225          (match_operand:DI 3 "reg_or_cint_move_operand" "")))]
1226   "TARGET_64BIT"
1227   "
1228 {
1229   enum rtx_code code = GET_CODE (operands[1]);
1230
1231   if (hppa_branch_type != CMP_SI)
1232     FAIL;
1233
1234   if (GET_MODE (hppa_compare_op0) != GET_MODE (hppa_compare_op1)
1235       || GET_MODE (hppa_compare_op0) != GET_MODE (operands[0]))
1236     FAIL;
1237
1238   /* operands[1] is currently the result of compare_from_rtx.  We want to
1239      emit a compare of the original operands.  */
1240   operands[1] = gen_rtx_fmt_ee (code, DImode, hppa_compare_op0, hppa_compare_op1);
1241   operands[4] = hppa_compare_op0;
1242   operands[5] = hppa_compare_op1;
1243 }")
1244
1245 ; We need the first constraint alternative in order to avoid
1246 ; earlyclobbers on all other alternatives.
1247 (define_insn ""
1248   [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r")
1249         (if_then_else:DI
1250          (match_operator 2 "comparison_operator"
1251             [(match_operand:DI 3 "register_operand" "r,r,r,r,r")
1252              (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI")])
1253          (match_operand:DI 1 "reg_or_cint_move_operand" "0,r,J,N,K")
1254          (const_int 0)))]
1255   "TARGET_64BIT"
1256   "@
1257    cmp%I4clr,*%S2 %4,%3,%%r0\;ldi 0,%0
1258    cmp%I4clr,*%B2 %4,%3,%0\;copy %1,%0
1259    cmp%I4clr,*%B2 %4,%3,%0\;ldi %1,%0
1260    cmp%I4clr,*%B2 %4,%3,%0\;ldil L'%1,%0
1261    cmp%I4clr,*%B2 %4,%3,%0\;depdi,z %z1,%0"
1262   [(set_attr "type" "multi,multi,multi,multi,nullshift")
1263    (set_attr "length" "8,8,8,8,8")])
1264
1265 (define_insn ""
1266   [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1267         (if_then_else:DI
1268          (match_operator 5 "comparison_operator"
1269             [(match_operand:DI 3 "register_operand" "r,r,r,r,r,r,r,r")
1270              (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1271          (match_operand:DI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1272          (match_operand:DI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1273   "TARGET_64BIT"
1274   "@
1275    cmp%I4clr,*%S5 %4,%3,%%r0\;copy %2,%0
1276    cmp%I4clr,*%S5 %4,%3,%%r0\;ldi %2,%0
1277    cmp%I4clr,*%S5 %4,%3,%%r0\;ldil L'%2,%0
1278    cmp%I4clr,*%S5 %4,%3,%%r0\;depdi,z %z2,%0
1279    cmp%I4clr,*%B5 %4,%3,%%r0\;copy %1,%0
1280    cmp%I4clr,*%B5 %4,%3,%%r0\;ldi %1,%0
1281    cmp%I4clr,*%B5 %4,%3,%%r0\;ldil L'%1,%0
1282    cmp%I4clr,*%B5 %4,%3,%%r0\;depdi,z %z1,%0"
1283   [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1284    (set_attr "length" "8,8,8,8,8,8,8,8")])
1285
1286 ;; Conditional Branches
1287
1288 (define_expand "beq"
1289   [(set (pc)
1290         (if_then_else (eq (match_dup 1) (match_dup 2))
1291                       (label_ref (match_operand 0 "" ""))
1292                       (pc)))]
1293   ""
1294   "
1295 {
1296   if (hppa_branch_type != CMP_SI)
1297     {
1298       emit_insn (gen_cmp_fp (EQ, hppa_compare_op0, hppa_compare_op1));
1299       emit_bcond_fp (NE, operands[0]);
1300       DONE;
1301     }
1302   /* set up operands from compare.  */
1303   operands[1] = hppa_compare_op0;
1304   operands[2] = hppa_compare_op1;
1305   /* fall through and generate default code */
1306 }")
1307
1308 (define_expand "bne"
1309   [(set (pc)
1310         (if_then_else (ne (match_dup 1) (match_dup 2))
1311                       (label_ref (match_operand 0 "" ""))
1312                       (pc)))]
1313   ""
1314   "
1315 {
1316   if (hppa_branch_type != CMP_SI)
1317     {
1318       emit_insn (gen_cmp_fp (NE, hppa_compare_op0, hppa_compare_op1));
1319       emit_bcond_fp (NE, operands[0]);
1320       DONE;
1321     }
1322   operands[1] = hppa_compare_op0;
1323   operands[2] = hppa_compare_op1;
1324 }")
1325
1326 (define_expand "bgt"
1327   [(set (pc)
1328         (if_then_else (gt (match_dup 1) (match_dup 2))
1329                       (label_ref (match_operand 0 "" ""))
1330                       (pc)))]
1331   ""
1332   "
1333 {
1334   if (hppa_branch_type != CMP_SI)
1335     {
1336       emit_insn (gen_cmp_fp (GT, hppa_compare_op0, hppa_compare_op1));
1337       emit_bcond_fp (NE, operands[0]);
1338       DONE;
1339     }
1340   operands[1] = hppa_compare_op0;
1341   operands[2] = hppa_compare_op1;
1342 }")
1343
1344 (define_expand "blt"
1345   [(set (pc)
1346         (if_then_else (lt (match_dup 1) (match_dup 2))
1347                       (label_ref (match_operand 0 "" ""))
1348                       (pc)))]
1349   ""
1350   "
1351 {
1352   if (hppa_branch_type != CMP_SI)
1353     {
1354       emit_insn (gen_cmp_fp (LT, hppa_compare_op0, hppa_compare_op1));
1355       emit_bcond_fp (NE, operands[0]);
1356       DONE;
1357     }
1358   operands[1] = hppa_compare_op0;
1359   operands[2] = hppa_compare_op1;
1360 }")
1361
1362 (define_expand "bge"
1363   [(set (pc)
1364         (if_then_else (ge (match_dup 1) (match_dup 2))
1365                       (label_ref (match_operand 0 "" ""))
1366                       (pc)))]
1367   ""
1368   "
1369 {
1370   if (hppa_branch_type != CMP_SI)
1371     {
1372       emit_insn (gen_cmp_fp (GE, hppa_compare_op0, hppa_compare_op1));
1373       emit_bcond_fp (NE, operands[0]);
1374       DONE;
1375     }
1376   operands[1] = hppa_compare_op0;
1377   operands[2] = hppa_compare_op1;
1378 }")
1379
1380 (define_expand "ble"
1381   [(set (pc)
1382         (if_then_else (le (match_dup 1) (match_dup 2))
1383                       (label_ref (match_operand 0 "" ""))
1384                       (pc)))]
1385   ""
1386   "
1387 {
1388   if (hppa_branch_type != CMP_SI)
1389     {
1390       emit_insn (gen_cmp_fp (LE, hppa_compare_op0, hppa_compare_op1));
1391       emit_bcond_fp (NE, operands[0]);
1392       DONE;
1393     }
1394   operands[1] = hppa_compare_op0;
1395   operands[2] = hppa_compare_op1;
1396 }")
1397
1398 (define_expand "bgtu"
1399   [(set (pc)
1400         (if_then_else (gtu (match_dup 1) (match_dup 2))
1401                       (label_ref (match_operand 0 "" ""))
1402                       (pc)))]
1403   ""
1404   "
1405 {
1406   if (hppa_branch_type != CMP_SI)
1407     FAIL;
1408   operands[1] = hppa_compare_op0;
1409   operands[2] = hppa_compare_op1;
1410 }")
1411
1412 (define_expand "bltu"
1413   [(set (pc)
1414         (if_then_else (ltu (match_dup 1) (match_dup 2))
1415                       (label_ref (match_operand 0 "" ""))
1416                       (pc)))]
1417   ""
1418   "
1419 {
1420   if (hppa_branch_type != CMP_SI)
1421     FAIL;
1422   operands[1] = hppa_compare_op0;
1423   operands[2] = hppa_compare_op1;
1424 }")
1425
1426 (define_expand "bgeu"
1427   [(set (pc)
1428         (if_then_else (geu (match_dup 1) (match_dup 2))
1429                       (label_ref (match_operand 0 "" ""))
1430                       (pc)))]
1431   ""
1432   "
1433 {
1434   if (hppa_branch_type != CMP_SI)
1435     FAIL;
1436   operands[1] = hppa_compare_op0;
1437   operands[2] = hppa_compare_op1;
1438 }")
1439
1440 (define_expand "bleu"
1441   [(set (pc)
1442         (if_then_else (leu (match_dup 1) (match_dup 2))
1443                       (label_ref (match_operand 0 "" ""))
1444                       (pc)))]
1445   ""
1446   "
1447 {
1448   if (hppa_branch_type != CMP_SI)
1449     FAIL;
1450   operands[1] = hppa_compare_op0;
1451   operands[2] = hppa_compare_op1;
1452 }")
1453
1454 (define_expand "bltgt"
1455   [(set (pc)
1456         (if_then_else (ltgt (match_dup 1) (match_dup 2))
1457                       (label_ref (match_operand 0 "" ""))
1458                       (pc)))]
1459   ""
1460   "
1461 {
1462   if (hppa_branch_type == CMP_SI)
1463     FAIL;
1464   emit_insn (gen_cmp_fp (LTGT, hppa_compare_op0, hppa_compare_op1));
1465   emit_bcond_fp (NE, operands[0]);
1466   DONE;
1467 }")
1468
1469 (define_expand "bunle"
1470   [(set (pc)
1471         (if_then_else (unle (match_dup 1) (match_dup 2))
1472                       (label_ref (match_operand 0 "" ""))
1473                       (pc)))]
1474   ""
1475   "
1476 {
1477   if (hppa_branch_type == CMP_SI)
1478     FAIL;
1479   emit_insn (gen_cmp_fp (UNLE, hppa_compare_op0, hppa_compare_op1));
1480   emit_bcond_fp (NE, operands[0]);
1481   DONE;
1482 }")
1483
1484 (define_expand "bunlt"
1485   [(set (pc)
1486         (if_then_else (unlt (match_dup 1) (match_dup 2))
1487                       (label_ref (match_operand 0 "" ""))
1488                       (pc)))]
1489   ""
1490   "
1491 {
1492   if (hppa_branch_type == CMP_SI)
1493     FAIL;
1494   emit_insn (gen_cmp_fp (UNLT, hppa_compare_op0, hppa_compare_op1));
1495   emit_bcond_fp (NE, operands[0]);
1496   DONE;
1497 }")
1498
1499 (define_expand "bunge"
1500   [(set (pc)
1501         (if_then_else (unge (match_dup 1) (match_dup 2))
1502                       (label_ref (match_operand 0 "" ""))
1503                       (pc)))]
1504   ""
1505   "
1506 {
1507   if (hppa_branch_type == CMP_SI)
1508     FAIL;
1509   emit_insn (gen_cmp_fp (UNGE, hppa_compare_op0, hppa_compare_op1));
1510   emit_bcond_fp (NE, operands[0]);
1511   DONE;
1512 }")
1513
1514 (define_expand "bungt"
1515   [(set (pc)
1516         (if_then_else (ungt (match_dup 1) (match_dup 2))
1517                       (label_ref (match_operand 0 "" ""))
1518                       (pc)))]
1519   ""
1520   "
1521 {
1522   if (hppa_branch_type == CMP_SI)
1523     FAIL;
1524   emit_insn (gen_cmp_fp (UNGT, hppa_compare_op0, hppa_compare_op1));
1525   emit_bcond_fp (NE, operands[0]);
1526   DONE;
1527 }")
1528
1529 (define_expand "buneq"
1530   [(set (pc)
1531         (if_then_else (uneq (match_dup 1) (match_dup 2))
1532                       (label_ref (match_operand 0 "" ""))
1533                       (pc)))]
1534   ""
1535   "
1536 {
1537   if (hppa_branch_type == CMP_SI)
1538     FAIL;
1539   emit_insn (gen_cmp_fp (UNEQ, hppa_compare_op0, hppa_compare_op1));
1540   emit_bcond_fp (NE, operands[0]);
1541   DONE;
1542 }")
1543
1544 (define_expand "bunordered"
1545   [(set (pc)
1546         (if_then_else (unordered (match_dup 1) (match_dup 2))
1547                       (label_ref (match_operand 0 "" ""))
1548                       (pc)))]
1549   ""
1550   "
1551 {
1552   if (hppa_branch_type == CMP_SI)
1553     FAIL;
1554   emit_insn (gen_cmp_fp (UNORDERED, hppa_compare_op0, hppa_compare_op1));
1555   emit_bcond_fp (NE, operands[0]);
1556   DONE;
1557 }")
1558
1559 (define_expand "bordered"
1560   [(set (pc)
1561         (if_then_else (ordered (match_dup 1) (match_dup 2))
1562                       (label_ref (match_operand 0 "" ""))
1563                       (pc)))]
1564   ""
1565   "
1566 {
1567   if (hppa_branch_type == CMP_SI)
1568     FAIL;
1569   emit_insn (gen_cmp_fp (ORDERED, hppa_compare_op0, hppa_compare_op1));
1570   emit_bcond_fp (NE, operands[0]);
1571   DONE;
1572 }")
1573
1574 ;; Match the branch patterns.
1575
1576
1577 ;; Note a long backward conditional branch with an annulled delay slot
1578 ;; has a length of 12.
1579 (define_insn ""
1580   [(set (pc)
1581         (if_then_else
1582          (match_operator 3 "comparison_operator"
1583                          [(match_operand:SI 1 "reg_or_0_operand" "rM")
1584                           (match_operand:SI 2 "arith5_operand" "rL")])
1585          (label_ref (match_operand 0 "" ""))
1586          (pc)))]
1587   ""
1588   "*
1589 {
1590   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1591                          get_attr_length (insn), 0, insn);
1592 }"
1593 [(set_attr "type" "cbranch")
1594  (set (attr "length")
1595     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1596                (const_int 8184))
1597            (const_int 4)
1598            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1599                (const_int 262100))
1600            (const_int 8)
1601            (eq (symbol_ref "flag_pic") (const_int 0))
1602            (const_int 20)]
1603           (const_int 28)))])
1604
1605 ;; Match the negated branch.
1606
1607 (define_insn ""
1608   [(set (pc)
1609         (if_then_else
1610          (match_operator 3 "comparison_operator"
1611                          [(match_operand:SI 1 "reg_or_0_operand" "rM")
1612                           (match_operand:SI 2 "arith5_operand" "rL")])
1613          (pc)
1614          (label_ref (match_operand 0 "" ""))))]
1615   ""
1616   "*
1617 {
1618   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1619                          get_attr_length (insn), 1, insn);
1620 }"
1621 [(set_attr "type" "cbranch")
1622  (set (attr "length")
1623     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1624                (const_int 8184))
1625            (const_int 4)
1626            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1627                (const_int 262100))
1628            (const_int 8)
1629            (eq (symbol_ref "flag_pic") (const_int 0))
1630            (const_int 20)]
1631           (const_int 28)))])
1632
1633 (define_insn ""
1634   [(set (pc)
1635         (if_then_else
1636          (match_operator 3 "comparison_operator"
1637                          [(match_operand:DI 1 "reg_or_0_operand" "rM")
1638                           (match_operand:DI 2 "reg_or_0_operand" "rM")])
1639          (label_ref (match_operand 0 "" ""))
1640          (pc)))]
1641   "TARGET_64BIT"
1642   "*
1643 {
1644   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1645                          get_attr_length (insn), 0, insn);
1646 }"
1647 [(set_attr "type" "cbranch")
1648  (set (attr "length")
1649     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1650                (const_int 8184))
1651            (const_int 4)
1652            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1653                (const_int 262100))
1654            (const_int 8)
1655            (eq (symbol_ref "flag_pic") (const_int 0))
1656            (const_int 20)]
1657           (const_int 28)))])
1658
1659 ;; Match the negated branch.
1660
1661 (define_insn ""
1662   [(set (pc)
1663         (if_then_else
1664          (match_operator 3 "comparison_operator"
1665                          [(match_operand:DI 1 "reg_or_0_operand" "rM")
1666                           (match_operand:DI 2 "reg_or_0_operand" "rM")])
1667          (pc)
1668          (label_ref (match_operand 0 "" ""))))]
1669   "TARGET_64BIT"
1670   "*
1671 {
1672   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1673                          get_attr_length (insn), 1, insn);
1674 }"
1675 [(set_attr "type" "cbranch")
1676  (set (attr "length")
1677     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1678                (const_int 8184))
1679            (const_int 4)
1680            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1681                (const_int 262100))
1682            (const_int 8)
1683            (eq (symbol_ref "flag_pic") (const_int 0))
1684            (const_int 20)]
1685           (const_int 28)))])
1686 (define_insn ""
1687   [(set (pc)
1688         (if_then_else
1689          (match_operator 3 "cmpib_comparison_operator"
1690                          [(match_operand:DI 1 "reg_or_0_operand" "rM")
1691                           (match_operand:DI 2 "arith5_operand" "rL")])
1692          (label_ref (match_operand 0 "" ""))
1693          (pc)))]
1694   "TARGET_64BIT"
1695   "*
1696 {
1697   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1698                          get_attr_length (insn), 0, insn);
1699 }"
1700 [(set_attr "type" "cbranch")
1701  (set (attr "length")
1702     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1703                (const_int 8184))
1704            (const_int 4)
1705            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1706                (const_int 262100))
1707            (const_int 8)
1708            (eq (symbol_ref "flag_pic") (const_int 0))
1709            (const_int 20)]
1710           (const_int 28)))])
1711
1712 ;; Match the negated branch.
1713
1714 (define_insn ""
1715   [(set (pc)
1716         (if_then_else
1717          (match_operator 3 "cmpib_comparison_operator"
1718                          [(match_operand:DI 1 "reg_or_0_operand" "rM")
1719                           (match_operand:DI 2 "arith5_operand" "rL")])
1720          (pc)
1721          (label_ref (match_operand 0 "" ""))))]
1722   "TARGET_64BIT"
1723   "*
1724 {
1725   return output_cbranch (operands, INSN_ANNULLED_BRANCH_P (insn),
1726                          get_attr_length (insn), 1, insn);
1727 }"
1728 [(set_attr "type" "cbranch")
1729  (set (attr "length")
1730     (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1731                (const_int 8184))
1732            (const_int 4)
1733            (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1734                (const_int 262100))
1735            (const_int 8)
1736            (eq (symbol_ref "flag_pic") (const_int 0))
1737            (const_int 20)]
1738           (const_int 28)))])
1739
1740 ;; Branch on Bit patterns.
1741 (define_insn ""
1742   [(set (pc)
1743         (if_then_else
1744          (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1745                               (const_int 1)
1746                               (match_operand:SI 1 "uint5_operand" ""))
1747              (const_int 0))
1748          (label_ref (match_operand 2 "" ""))
1749          (pc)))]
1750   ""
1751   "*
1752 {
1753   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1754                          get_attr_length (insn), 0, insn, 0);
1755 }"
1756 [(set_attr "type" "cbranch")
1757  (set (attr "length")
1758     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1759                       (const_int 8184))
1760            (const_int 4)
1761            (const_int 8)))])
1762
1763 (define_insn ""
1764   [(set (pc)
1765         (if_then_else
1766          (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1767                               (const_int 1)
1768                               (match_operand:DI 1 "uint32_operand" ""))
1769              (const_int 0))
1770          (label_ref (match_operand 2 "" ""))
1771          (pc)))]
1772   "TARGET_64BIT"
1773   "*
1774 {
1775   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1776                          get_attr_length (insn), 0, insn, 0);
1777 }"
1778 [(set_attr "type" "cbranch")
1779  (set (attr "length")
1780     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1781                       (const_int 8184))
1782            (const_int 4)
1783            (const_int 8)))])
1784
1785 (define_insn ""
1786   [(set (pc)
1787         (if_then_else
1788          (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1789                               (const_int 1)
1790                               (match_operand:SI 1 "uint5_operand" ""))
1791              (const_int 0))
1792          (pc)
1793          (label_ref (match_operand 2 "" ""))))]
1794   ""
1795   "*
1796 {
1797   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1798                          get_attr_length (insn), 1, insn, 0);
1799 }"
1800 [(set_attr "type" "cbranch")
1801  (set (attr "length")
1802     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1803                       (const_int 8184))
1804            (const_int 4)
1805            (const_int 8)))])
1806
1807 (define_insn ""
1808   [(set (pc)
1809         (if_then_else
1810          (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1811                               (const_int 1)
1812                               (match_operand:DI 1 "uint32_operand" ""))
1813              (const_int 0))
1814          (pc)
1815          (label_ref (match_operand 2 "" ""))))]
1816   "TARGET_64BIT"
1817   "*
1818 {
1819   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1820                          get_attr_length (insn), 1, insn, 0);
1821 }"
1822 [(set_attr "type" "cbranch")
1823  (set (attr "length")
1824     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1825                       (const_int 8184))
1826            (const_int 4)
1827            (const_int 8)))])
1828
1829 (define_insn ""
1830   [(set (pc)
1831         (if_then_else
1832          (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1833                               (const_int 1)
1834                               (match_operand:SI 1 "uint5_operand" ""))
1835              (const_int 0))
1836          (label_ref (match_operand 2 "" ""))
1837          (pc)))]
1838   ""
1839   "*
1840 {
1841   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1842                          get_attr_length (insn), 0, insn, 1);
1843 }"
1844 [(set_attr "type" "cbranch")
1845  (set (attr "length")
1846     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1847                       (const_int 8184))
1848            (const_int 4)
1849            (const_int 8)))])
1850
1851 (define_insn ""
1852   [(set (pc)
1853         (if_then_else
1854          (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1855                               (const_int 1)
1856                               (match_operand:DI 1 "uint32_operand" ""))
1857              (const_int 0))
1858          (label_ref (match_operand 2 "" ""))
1859          (pc)))]
1860   "TARGET_64BIT"
1861   "*
1862 {
1863   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1864                          get_attr_length (insn), 0, insn, 1);
1865 }"
1866 [(set_attr "type" "cbranch")
1867  (set (attr "length")
1868     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1869                       (const_int 8184))
1870            (const_int 4)
1871            (const_int 8)))])
1872
1873 (define_insn ""
1874   [(set (pc)
1875         (if_then_else
1876          (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1877                               (const_int 1)
1878                               (match_operand:SI 1 "uint5_operand" ""))
1879              (const_int 0))
1880          (pc)
1881          (label_ref (match_operand 2 "" ""))))]
1882   ""
1883   "*
1884 {
1885   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1886                          get_attr_length (insn), 1, insn, 1);
1887 }"
1888 [(set_attr "type" "cbranch")
1889  (set (attr "length")
1890     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1891                       (const_int 8184))
1892            (const_int 4)
1893            (const_int 8)))])
1894
1895 (define_insn ""
1896   [(set (pc)
1897         (if_then_else
1898          (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1899                               (const_int 1)
1900                               (match_operand:DI 1 "uint32_operand" ""))
1901              (const_int 0))
1902          (pc)
1903          (label_ref (match_operand 2 "" ""))))]
1904   "TARGET_64BIT"
1905   "*
1906 {
1907   return output_bb (operands, INSN_ANNULLED_BRANCH_P (insn),
1908                          get_attr_length (insn), 1, insn, 1);
1909 }"
1910 [(set_attr "type" "cbranch")
1911  (set (attr "length")
1912     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1913                       (const_int 8184))
1914            (const_int 4)
1915            (const_int 8)))])
1916
1917 ;; Branch on Variable Bit patterns.
1918 (define_insn ""
1919   [(set (pc)
1920         (if_then_else
1921          (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1922                               (const_int 1)
1923                               (match_operand:SI 1 "register_operand" "q"))
1924              (const_int 0))
1925          (label_ref (match_operand 2 "" ""))
1926          (pc)))]
1927   ""
1928   "*
1929 {
1930   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
1931                      get_attr_length (insn), 0, insn, 0);
1932 }"
1933 [(set_attr "type" "cbranch")
1934  (set (attr "length")
1935     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1936                       (const_int 8184))
1937            (const_int 4)
1938            (const_int 8)))])
1939
1940 (define_insn ""
1941   [(set (pc)
1942         (if_then_else
1943          (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1944                               (const_int 1)
1945                               (match_operand:DI 1 "register_operand" "q"))
1946              (const_int 0))
1947          (label_ref (match_operand 2 "" ""))
1948          (pc)))]
1949   "TARGET_64BIT"
1950   "*
1951 {
1952   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
1953                      get_attr_length (insn), 0, insn, 0);
1954 }"
1955 [(set_attr "type" "cbranch")
1956  (set (attr "length")
1957     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1958                       (const_int 8184))
1959            (const_int 4)
1960            (const_int 8)))])
1961
1962 (define_insn ""
1963   [(set (pc)
1964         (if_then_else
1965          (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1966                               (const_int 1)
1967                               (match_operand:SI 1 "register_operand" "q"))
1968              (const_int 0))
1969          (pc)
1970          (label_ref (match_operand 2 "" ""))))]
1971   ""
1972   "*
1973 {
1974   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
1975                      get_attr_length (insn), 1, insn, 0);
1976 }"
1977 [(set_attr "type" "cbranch")
1978  (set (attr "length")
1979     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1980                       (const_int 8184))
1981            (const_int 4)
1982            (const_int 8)))])
1983
1984 (define_insn ""
1985   [(set (pc)
1986         (if_then_else
1987          (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1988                               (const_int 1)
1989                               (match_operand:DI 1 "register_operand" "q"))
1990              (const_int 0))
1991          (pc)
1992          (label_ref (match_operand 2 "" ""))))]
1993   "TARGET_64BIT"
1994   "*
1995 {
1996   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
1997                      get_attr_length (insn), 1, insn, 0);
1998 }"
1999 [(set_attr "type" "cbranch")
2000  (set (attr "length")
2001     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2002                       (const_int 8184))
2003            (const_int 4)
2004            (const_int 8)))])
2005
2006 (define_insn ""
2007   [(set (pc)
2008         (if_then_else
2009          (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2010                               (const_int 1)
2011                               (match_operand:SI 1 "register_operand" "q"))
2012              (const_int 0))
2013          (label_ref (match_operand 2 "" ""))
2014          (pc)))]
2015   ""
2016   "*
2017 {
2018   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
2019                      get_attr_length (insn), 0, insn, 1);
2020 }"
2021 [(set_attr "type" "cbranch")
2022  (set (attr "length")
2023     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2024                       (const_int 8184))
2025            (const_int 4)
2026            (const_int 8)))])
2027
2028 (define_insn ""
2029   [(set (pc)
2030         (if_then_else
2031          (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2032                               (const_int 1)
2033                               (match_operand:DI 1 "register_operand" "q"))
2034              (const_int 0))
2035          (label_ref (match_operand 2 "" ""))
2036          (pc)))]
2037   "TARGET_64BIT"
2038   "*
2039 {
2040   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
2041                      get_attr_length (insn), 0, insn, 1);
2042 }"
2043 [(set_attr "type" "cbranch")
2044  (set (attr "length")
2045     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2046                       (const_int 8184))
2047            (const_int 4)
2048            (const_int 8)))])
2049
2050 (define_insn ""
2051   [(set (pc)
2052         (if_then_else
2053          (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2054                               (const_int 1)
2055                               (match_operand:SI 1 "register_operand" "q"))
2056              (const_int 0))
2057          (pc)
2058          (label_ref (match_operand 2 "" ""))))]
2059   ""
2060   "*
2061 {
2062   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
2063                      get_attr_length (insn), 1, insn, 1);
2064 }"
2065 [(set_attr "type" "cbranch")
2066  (set (attr "length")
2067     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2068                       (const_int 8184))
2069            (const_int 4)
2070            (const_int 8)))])
2071
2072 (define_insn ""
2073   [(set (pc)
2074         (if_then_else
2075          (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2076                               (const_int 1)
2077                               (match_operand:DI 1 "register_operand" "q"))
2078              (const_int 0))
2079          (pc)
2080          (label_ref (match_operand 2 "" ""))))]
2081   "TARGET_64BIT"
2082   "*
2083 {
2084   return output_bvb (operands, INSN_ANNULLED_BRANCH_P (insn),
2085                      get_attr_length (insn), 1, insn, 1);
2086 }"
2087 [(set_attr "type" "cbranch")
2088  (set (attr "length")
2089     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2090                       (const_int 8184))
2091            (const_int 4)
2092            (const_int 8)))])
2093
2094 ;; Floating point branches
2095 (define_insn ""
2096   [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2097                            (label_ref (match_operand 0 "" ""))
2098                            (pc)))]
2099   "! TARGET_SOFT_FLOAT"
2100   "*
2101 {
2102   if (INSN_ANNULLED_BRANCH_P (insn))
2103     return \"ftest\;b,n %0\";
2104   else
2105     return \"ftest\;b%* %0\";
2106 }"
2107   [(set_attr "type" "fbranch")
2108    (set_attr "length" "8")])
2109
2110 (define_insn ""
2111   [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2112                            (pc)
2113                            (label_ref (match_operand 0 "" ""))))]
2114   "! TARGET_SOFT_FLOAT"
2115   "*
2116 {
2117   if (INSN_ANNULLED_BRANCH_P (insn))
2118     return \"ftest\;add,tr %%r0,%%r0,%%r0\;b,n %0\";
2119   else
2120     return \"ftest\;add,tr %%r0,%%r0,%%r0\;b%* %0\";
2121 }"
2122   [(set_attr "type" "fbranch")
2123    (set_attr "length" "12")])
2124
2125 ;; Move instructions
2126
2127 (define_expand "movsi"
2128   [(set (match_operand:SI 0 "general_operand" "")
2129         (match_operand:SI 1 "general_operand" ""))]
2130   ""
2131   "
2132 {
2133   if (emit_move_sequence (operands, SImode, 0))
2134     DONE;
2135 }")
2136
2137 ;; Reloading an SImode or DImode value requires a scratch register if
2138 ;; going in to or out of float point registers.
2139
2140 (define_expand "reload_insi"
2141   [(set (match_operand:SI 0 "register_operand" "=Z")
2142         (match_operand:SI 1 "non_hard_reg_operand" ""))
2143    (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2144   ""
2145   "
2146 {
2147   if (emit_move_sequence (operands, SImode, operands[2]))
2148     DONE;
2149
2150   /* We don't want the clobber emitted, so handle this ourselves.  */
2151   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2152   DONE;
2153 }")
2154
2155 (define_expand "reload_outsi"
2156   [(set (match_operand:SI 0 "non_hard_reg_operand" "")
2157         (match_operand:SI 1  "register_operand" "Z"))
2158    (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2159   ""
2160   "
2161 {
2162   if (emit_move_sequence (operands, SImode, operands[2]))
2163     DONE;
2164
2165   /* We don't want the clobber emitted, so handle this ourselves.  */
2166   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2167   DONE;
2168 }")
2169
2170 (define_insn ""
2171   [(set (match_operand:SI 0 "reg_or_nonsymb_mem_operand"
2172                                 "=r,r,r,r,r,r,Q,*q,!f,f,*TR")
2173         (match_operand:SI 1 "move_operand"
2174                                 "A,r,J,N,K,RQ,rM,rM,!fM,*RT,f"))]
2175   "(register_operand (operands[0], SImode)
2176     || reg_or_0_operand (operands[1], SImode))
2177    && ! TARGET_SOFT_FLOAT"
2178   "@
2179    ldw RT'%A1,%0
2180    copy %1,%0
2181    ldi %1,%0
2182    ldil L'%1,%0
2183    {zdepi|depwi,z} %Z1,%0
2184    ldw%M1 %1,%0
2185    stw%M0 %r1,%0
2186    mtsar %r1
2187    fcpy,sgl %f1,%0
2188    fldw%F1 %1,%0
2189    fstw%F0 %1,%0"
2190   [(set_attr "type" "load,move,move,move,shift,load,store,move,fpalu,fpload,fpstore")
2191    (set_attr "pa_combine_type" "addmove")
2192    (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4")])
2193
2194 (define_insn ""
2195   [(set (match_operand:SI 0 "reg_or_nonsymb_mem_operand"
2196                                 "=r,r,r,r,r,r,Q,*q")
2197         (match_operand:SI 1 "move_operand"
2198                                 "A,r,J,N,K,RQ,rM,rM"))]
2199   "(register_operand (operands[0], SImode)
2200     || reg_or_0_operand (operands[1], SImode))
2201    && TARGET_SOFT_FLOAT"
2202   "@
2203    ldw RT'%A1,%0
2204    copy %1,%0
2205    ldi %1,%0
2206    ldil L'%1,%0
2207    {zdepi|depwi,z} %Z1,%0
2208    ldw%M1 %1,%0
2209    stw%M0 %r1,%0
2210    mtsar %r1"
2211   [(set_attr "type" "load,move,move,move,move,load,store,move")
2212    (set_attr "pa_combine_type" "addmove")
2213    (set_attr "length" "4,4,4,4,4,4,4,4")])
2214
2215 (define_insn ""
2216   [(set (match_operand:SI 0 "register_operand" "=r")
2217         (mem:SI (plus:SI (match_operand:SI 1 "basereg_operand" "r")
2218                          (match_operand:SI 2 "register_operand" "r"))))]
2219   "! TARGET_DISABLE_INDEXING"
2220   "{ldwx|ldw} %2(%1),%0"
2221   [(set_attr "type" "load")
2222    (set_attr "length" "4")])
2223
2224 (define_insn ""
2225   [(set (match_operand:SI 0 "register_operand" "=r")
2226         (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "r")
2227                          (match_operand:SI 2 "basereg_operand" "r"))))]
2228   "! TARGET_DISABLE_INDEXING"
2229   "{ldwx|ldw} %1(%2),%0"
2230   [(set_attr "type" "load")
2231    (set_attr "length" "4")])
2232
2233 ;; Load or store with base-register modification.
2234
2235 (define_expand "pre_load"
2236   [(parallel [(set (match_operand:SI 0 "register_operand" "")
2237               (mem (plus (match_operand 1 "register_operand" "")
2238                                (match_operand 2 "pre_cint_operand" ""))))
2239               (set (match_dup 1)
2240                    (plus (match_dup 1) (match_dup 2)))])]
2241   ""
2242   "
2243 {
2244   if (TARGET_64BIT)
2245     {
2246       emit_insn (gen_pre_ldd (operands[0], operands[1], operands[2]));
2247       DONE;
2248     }
2249   emit_insn (gen_pre_ldw (operands[0], operands[1], operands[2]));
2250   DONE;
2251 }")
2252
2253 (define_insn "pre_ldw"
2254   [(set (match_operand:SI 0 "register_operand" "=r")
2255         (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2256                          (match_operand:SI 2 "pre_cint_operand" ""))))
2257    (set (match_dup 1)
2258         (plus:SI (match_dup 1) (match_dup 2)))]
2259   ""
2260   "*
2261 {
2262   if (INTVAL (operands[2]) < 0)
2263     return \"{ldwm|ldw,mb} %2(%1),%0\";
2264   return \"{ldws|ldw},mb %2(%1),%0\";
2265 }"
2266   [(set_attr "type" "load")
2267    (set_attr "length" "4")])
2268
2269 (define_insn "pre_ldd"
2270   [(set (match_operand:DI 0 "register_operand" "=r")
2271         (mem:DI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2272                          (match_operand:DI 2 "pre_cint_operand" ""))))
2273    (set (match_dup 1)
2274         (plus:DI (match_dup 1) (match_dup 2)))]
2275   "TARGET_64BIT"
2276   "ldd,mb %2(%1),%0"
2277   [(set_attr "type" "load")
2278    (set_attr "length" "4")])
2279
2280 (define_insn ""
2281   [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2282                          (match_operand:SI 1 "pre_cint_operand" "")))
2283         (match_operand:SI 2 "reg_or_0_operand" "rM"))
2284    (set (match_dup 0)
2285         (plus:SI (match_dup 0) (match_dup 1)))]
2286   ""
2287   "*
2288 {
2289   if (INTVAL (operands[1]) < 0)
2290     return \"{stwm|stw,mb} %r2,%1(%0)\";
2291   return \"{stws|stw},mb %r2,%1(%0)\";
2292 }"
2293   [(set_attr "type" "store")
2294    (set_attr "length" "4")])
2295
2296 (define_insn ""
2297   [(set (match_operand:SI 0 "register_operand" "=r")
2298         (mem:SI (match_operand:SI 1 "register_operand" "+r")))
2299    (set (match_dup 1)
2300         (plus:SI (match_dup 1)
2301                  (match_operand:SI 2 "post_cint_operand" "")))]
2302   ""
2303   "*
2304 {
2305   if (INTVAL (operands[2]) > 0)
2306     return \"{ldwm|ldw,ma} %2(%1),%0\";
2307   return \"{ldws|ldw},ma %2(%1),%0\";
2308 }"
2309   [(set_attr "type" "load")
2310    (set_attr "length" "4")])
2311
2312 (define_expand "post_store"
2313   [(parallel [(set (mem (match_operand 0 "register_operand" ""))
2314                    (match_operand 1 "reg_or_0_operand" ""))
2315               (set (match_dup 0)
2316                    (plus (match_dup 0)
2317                          (match_operand 2 "post_cint_operand" "")))])]
2318   ""
2319   "
2320 {
2321   if (TARGET_64BIT)
2322     {
2323       emit_insn (gen_post_std (operands[0], operands[1], operands[2]));
2324       DONE;
2325     }
2326   emit_insn (gen_post_stw (operands[0], operands[1], operands[2]));
2327   DONE;
2328 }")
2329
2330 (define_insn "post_stw"
2331   [(set (mem:SI (match_operand:SI 0 "register_operand" "+r"))
2332         (match_operand:SI 1 "reg_or_0_operand" "rM"))
2333    (set (match_dup 0)
2334         (plus:SI (match_dup 0)
2335                  (match_operand:SI 2 "post_cint_operand" "")))]
2336   ""
2337   "*
2338 {
2339   if (INTVAL (operands[2]) > 0)
2340     return \"{stwm|stw,ma} %r1,%2(%0)\";
2341   return \"{stws|stw},ma %r1,%2(%0)\";
2342 }"
2343   [(set_attr "type" "store")
2344    (set_attr "length" "4")])
2345
2346 (define_insn "post_std"
2347   [(set (mem:DI (match_operand:DI 0 "register_operand" "+r"))
2348         (match_operand:DI 1 "reg_or_0_operand" "rM"))
2349    (set (match_dup 0)
2350         (plus:DI (match_dup 0)
2351                  (match_operand:DI 2 "post_cint_operand" "")))]
2352   "TARGET_64BIT"
2353   "std,ma %r1,%2(%0)"
2354   [(set_attr "type" "store")
2355    (set_attr "length" "4")])
2356
2357 ;; For loading the address of a label while generating PIC code.
2358 ;; Note since this pattern can be created at reload time (via movsi), all
2359 ;; the same rules for movsi apply here.  (no new pseudos, no temporaries).
2360 (define_insn ""
2361   [(set (match_operand 0 "pmode_register_operand" "=a")
2362         (match_operand 1 "pic_label_operand" ""))]
2363   ""
2364   "*
2365 {
2366   rtx xoperands[3];
2367   extern FILE *asm_out_file;
2368
2369   xoperands[0] = operands[0];
2370   xoperands[1] = operands[1];
2371   if (TARGET_SOM || ! TARGET_GAS)
2372     xoperands[2] = gen_label_rtx ();
2373
2374   output_asm_insn (\"{bl|b,l} .+8,%0\", xoperands);
2375   output_asm_insn (\"{depi|depwi} 0,31,2,%0\", xoperands);
2376   if (TARGET_SOM || ! TARGET_GAS)
2377     ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
2378                                CODE_LABEL_NUMBER (xoperands[2]));
2379
2380   /* If we're trying to load the address of a label that happens to be
2381      close, then we can use a shorter sequence.  */
2382   if (GET_CODE (operands[1]) == LABEL_REF
2383       && INSN_ADDRESSES_SET_P ()
2384       && abs (INSN_ADDRESSES (INSN_UID (XEXP (operands[1], 0)))
2385                 - INSN_ADDRESSES (INSN_UID (insn))) < 8100)
2386     {
2387       /* Prefixing with R% here is wrong, it extracts just 11 bits and is
2388          always non-negative.  */
2389       if (TARGET_SOM || ! TARGET_GAS)
2390         output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands);
2391       else
2392         output_asm_insn (\"ldo %1-$PIC_pcrel$0+8(%0),%0\", xoperands);
2393     }
2394   else
2395     {
2396       if (TARGET_SOM || ! TARGET_GAS)
2397         {
2398           output_asm_insn (\"addil L%%%1-%2,%0\", xoperands);
2399           output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands);
2400         }
2401       else
2402         {
2403           output_asm_insn (\"addil L%%%1-$PIC_pcrel$0+8,%0\", xoperands);
2404           output_asm_insn (\"ldo R%%%1-$PIC_pcrel$0+12(%0),%0\",
2405                            xoperands);
2406         }
2407     }
2408   return \"\";
2409 }"
2410   [(set_attr "type" "multi")
2411    (set_attr "length" "16")])           ; 12 or 16
2412
2413 (define_insn ""
2414   [(set (match_operand:SI 0 "register_operand" "=a")
2415         (plus:SI (match_operand:SI 1 "register_operand" "r")
2416                  (high:SI (match_operand 2 "" ""))))]
2417   "symbolic_operand (operands[2], Pmode)
2418    && ! function_label_operand (operands[2], Pmode)
2419    && flag_pic"
2420   "addil LT'%G2,%1"
2421   [(set_attr "type" "binary")
2422    (set_attr "length" "4")])
2423
2424 (define_insn ""
2425   [(set (match_operand:DI 0 "register_operand" "=a")
2426         (plus:DI (match_operand:DI 1 "register_operand" "r")
2427                  (high:DI (match_operand 2 "" ""))))]
2428   "symbolic_operand (operands[2], Pmode)
2429    && ! function_label_operand (operands[2], Pmode)
2430    && TARGET_64BIT
2431    && flag_pic"
2432   "addil LT'%G2,%1"
2433   [(set_attr "type" "binary")
2434    (set_attr "length" "4")])
2435
2436 ;; Always use addil rather than ldil;add sequences.  This allows the
2437 ;; HP linker to eliminate the dp relocation if the symbolic operand
2438 ;; lives in the TEXT space.
2439 (define_insn ""
2440   [(set (match_operand:SI 0 "register_operand" "=a")
2441         (high:SI (match_operand 1 "" "")))]
2442   "symbolic_operand (operands[1], Pmode)
2443    && ! function_label_operand (operands[1], Pmode)
2444    && ! read_only_operand (operands[1], Pmode)
2445    && ! flag_pic"
2446   "*
2447 {
2448   if (TARGET_LONG_LOAD_STORE)
2449     return \"addil NLR'%H1,%%r27\;ldo N'%H1(%%r1),%%r1\";
2450   else
2451     return \"addil LR'%H1,%%r27\";
2452 }"
2453   [(set_attr "type" "binary")
2454    (set (attr "length")
2455       (if_then_else (eq (symbol_ref "TARGET_LONG_LOAD_STORE") (const_int 0))
2456                     (const_int 4)
2457                     (const_int 8)))])
2458
2459
2460 ;; This is for use in the prologue/epilogue code.  We need it
2461 ;; to add large constants to a stack pointer or frame pointer.
2462 ;; Because of the additional %r1 pressure, we probably do not
2463 ;; want to use this in general code, so make it available
2464 ;; only after reload.
2465 (define_insn ""
2466   [(set (match_operand:SI 0 "register_operand" "=!a,*r")
2467         (plus:SI (match_operand:SI 1 "register_operand" "r,r")
2468                  (high:SI (match_operand 2 "const_int_operand" ""))))]
2469   "reload_completed"
2470   "@
2471    addil L'%G2,%1
2472    ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
2473   [(set_attr "type" "binary,binary")
2474    (set_attr "length" "4,8")])
2475
2476 (define_insn ""
2477   [(set (match_operand:DI 0 "register_operand" "=!a,*r")
2478         (plus:DI (match_operand:DI 1 "register_operand" "r,r")
2479                  (high:DI (match_operand 2 "const_int_operand" ""))))]
2480   "reload_completed && TARGET_64BIT"
2481   "@
2482    addil L'%G2,%1
2483    ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
2484   [(set_attr "type" "binary,binary")
2485    (set_attr "length" "4,8")])
2486
2487 (define_insn ""
2488   [(set (match_operand:SI 0 "register_operand" "=r")
2489         (high:SI (match_operand 1 "" "")))]
2490   "(!flag_pic || !symbolic_operand (operands[1], Pmode))
2491     && !is_function_label_plus_const (operands[1])"
2492   "*
2493 {
2494   if (symbolic_operand (operands[1], Pmode))
2495     return \"ldil LR'%H1,%0\";
2496   else
2497     return \"ldil L'%G1,%0\";
2498 }"
2499   [(set_attr "type" "move")
2500    (set_attr "length" "4")])
2501
2502 (define_insn ""
2503   [(set (match_operand:DI 0 "register_operand" "=r")
2504         (high:DI (match_operand 1 "const_int_operand" "")))]
2505   "TARGET_64BIT"
2506   "ldil L'%G1,%0";
2507   [(set_attr "type" "move")
2508    (set_attr "length" "4")])
2509
2510 (define_insn ""
2511   [(set (match_operand:DI 0 "register_operand" "=r")
2512         (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2513                    (match_operand:DI 2 "const_int_operand" "i")))]
2514   "TARGET_64BIT"
2515   "ldo R'%G2(%1),%0";
2516   [(set_attr "type" "move")
2517    (set_attr "length" "4")])
2518
2519 (define_insn ""
2520   [(set (match_operand:SI 0 "register_operand" "=r")
2521         (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
2522                    (match_operand:SI 2 "immediate_operand" "i")))]
2523   "!is_function_label_plus_const (operands[2])"
2524   "*
2525 {
2526   if (flag_pic && symbolic_operand (operands[2], Pmode))
2527     abort ();
2528   else if (symbolic_operand (operands[2], Pmode))
2529     return \"ldo RR'%G2(%1),%0\";
2530   else
2531     return \"ldo R'%G2(%1),%0\";
2532 }"
2533   [(set_attr "type" "move")
2534    (set_attr "length" "4")])
2535
2536 ;; Now that a symbolic_address plus a constant is broken up early
2537 ;; in the compilation phase (for better CSE) we need a special
2538 ;; combiner pattern to load the symbolic address plus the constant
2539 ;; in only 2 instructions. (For cases where the symbolic address
2540 ;; was not a common subexpression.)
2541 (define_split
2542   [(set (match_operand:SI 0 "register_operand" "")
2543         (match_operand:SI 1 "symbolic_operand" ""))
2544    (clobber (match_operand:SI 2 "register_operand" ""))]
2545   "! (flag_pic && pic_label_operand (operands[1], SImode))"
2546   [(set (match_dup 2) (high:SI (match_dup 1)))
2547    (set (match_dup 0) (lo_sum:SI (match_dup 2) (match_dup 1)))]
2548   "")
2549
2550 ;; hppa_legitimize_address goes to a great deal of trouble to
2551 ;; create addresses which use indexing.  In some cases, this
2552 ;; is a lose because there isn't any store instructions which
2553 ;; allow indexed addresses (with integer register source).
2554 ;;
2555 ;; These define_splits try to turn a 3 insn store into
2556 ;; a 2 insn store with some creative RTL rewriting.
2557 (define_split
2558   [(set (mem:SI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2559                                (match_operand:SI 1 "shadd_operand" ""))
2560                    (plus:SI (match_operand:SI 2 "register_operand" "")
2561                             (match_operand:SI 3 "const_int_operand" ""))))
2562         (match_operand:SI 4 "register_operand" ""))
2563    (clobber (match_operand:SI 5 "register_operand" ""))]
2564   ""
2565   [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
2566                                (match_dup 2)))
2567    (set (mem:SI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2568   "")
2569
2570 (define_split
2571   [(set (mem:HI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2572                                (match_operand:SI 1 "shadd_operand" ""))
2573                    (plus:SI (match_operand:SI 2 "register_operand" "")
2574                             (match_operand:SI 3 "const_int_operand" ""))))
2575         (match_operand:HI 4 "register_operand" ""))
2576    (clobber (match_operand:SI 5 "register_operand" ""))]
2577   ""
2578   [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
2579                                (match_dup 2)))
2580    (set (mem:HI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2581   "")
2582
2583 (define_split
2584   [(set (mem:QI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2585                                (match_operand:SI 1 "shadd_operand" ""))
2586                    (plus:SI (match_operand:SI 2 "register_operand" "")
2587                             (match_operand:SI 3 "const_int_operand" ""))))
2588         (match_operand:QI 4 "register_operand" ""))
2589    (clobber (match_operand:SI 5 "register_operand" ""))]
2590   ""
2591   [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
2592                                (match_dup 2)))
2593    (set (mem:QI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2594   "")
2595
2596 (define_expand "movhi"
2597   [(set (match_operand:HI 0 "general_operand" "")
2598         (match_operand:HI 1 "general_operand" ""))]
2599   ""
2600   "
2601 {
2602   if (emit_move_sequence (operands, HImode, 0))
2603     DONE;
2604 }")
2605
2606 (define_insn ""
2607   [(set (match_operand:HI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,Q,*q,!*f")
2608         (match_operand:HI 1 "move_operand" "r,J,N,K,RQ,rM,rM,!*fM"))]
2609   "register_operand (operands[0], HImode)
2610    || reg_or_0_operand (operands[1], HImode)"
2611   "@
2612    copy %1,%0
2613    ldi %1,%0
2614    ldil L'%1,%0
2615    {zdepi|depwi,z} %Z1,%0
2616    ldh%M1 %1,%0
2617    sth%M0 %r1,%0
2618    mtsar %r1
2619    fcpy,sgl %f1,%0"
2620   [(set_attr "type" "move,move,move,shift,load,store,move,fpalu")
2621    (set_attr "pa_combine_type" "addmove")
2622    (set_attr "length" "4,4,4,4,4,4,4,4")])
2623
2624 (define_insn ""
2625   [(set (match_operand:HI 0 "register_operand" "=r")
2626         (mem:HI (plus:SI (match_operand:SI 1 "basereg_operand" "r")
2627                          (match_operand:SI 2 "register_operand" "r"))))]
2628   "! TARGET_DISABLE_INDEXING"
2629   "{ldhx|ldh} %2(%1),%0"
2630   [(set_attr "type" "load")
2631    (set_attr "length" "4")])
2632
2633 (define_insn ""
2634   [(set (match_operand:HI 0 "register_operand" "=r")
2635         (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "r")
2636                          (match_operand:SI 2 "basereg_operand" "r"))))]
2637   "! TARGET_DISABLE_INDEXING"
2638   "{ldhx|ldh} %1(%2),%0"
2639   [(set_attr "type" "load")
2640    (set_attr "length" "4")])
2641
2642 ; Now zero extended variants.
2643 (define_insn ""
2644   [(set (match_operand:SI 0 "register_operand" "=r")
2645         (zero_extend:SI (mem:HI
2646                           (plus:SI
2647                             (match_operand:SI 1 "basereg_operand" "r")
2648                             (match_operand:SI 2 "register_operand" "r")))))]
2649   "! TARGET_DISABLE_INDEXING"
2650   "{ldhx|ldh} %2(%1),%0"
2651   [(set_attr "type" "load")
2652    (set_attr "length" "4")])
2653
2654 (define_insn ""
2655   [(set (match_operand:SI 0 "register_operand" "=r")
2656         (zero_extend:SI (mem:HI
2657                           (plus:SI
2658                              (match_operand:SI 1 "register_operand" "r")
2659                              (match_operand:SI 2 "basereg_operand" "r")))))]
2660   "! TARGET_DISABLE_INDEXING"
2661   "{ldhx|ldh} %1(%2),%0"
2662   [(set_attr "type" "load")
2663    (set_attr "length" "4")])
2664
2665 (define_insn ""
2666   [(set (match_operand:HI 0 "register_operand" "=r")
2667         (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2668                          (match_operand:SI 2 "int5_operand" "L"))))
2669    (set (match_dup 1)
2670         (plus:SI (match_dup 1) (match_dup 2)))]
2671   ""
2672   "{ldhs|ldh},mb %2(%1),%0"
2673   [(set_attr "type" "load")
2674    (set_attr "length" "4")])
2675
2676 ; And a zero extended variant.
2677 (define_insn ""
2678   [(set (match_operand:SI 0 "register_operand" "=r")
2679         (zero_extend:SI (mem:HI
2680                           (plus:SI
2681                             (match_operand:SI 1 "register_operand" "+r")
2682                             (match_operand:SI 2 "int5_operand" "L")))))
2683    (set (match_dup 1)
2684         (plus:SI (match_dup 1) (match_dup 2)))]
2685   ""
2686   "{ldhs|ldh},mb %2(%1),%0"
2687   [(set_attr "type" "load")
2688    (set_attr "length" "4")])
2689
2690 (define_insn ""
2691   [(set (mem:HI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2692                          (match_operand:SI 1 "int5_operand" "L")))
2693         (match_operand:HI 2 "reg_or_0_operand" "rM"))
2694    (set (match_dup 0)
2695         (plus:SI (match_dup 0) (match_dup 1)))]
2696   ""
2697   "{sths|sth},mb %r2,%1(%0)"
2698   [(set_attr "type" "store")
2699    (set_attr "length" "4")])
2700
2701 (define_insn ""
2702   [(set (match_operand:HI 0 "register_operand" "=r")
2703         (plus:HI (match_operand:HI 1 "register_operand" "r")
2704                  (match_operand 2 "const_int_operand" "J")))]
2705   ""
2706   "ldo %2(%1),%0"
2707   [(set_attr "type" "binary")
2708    (set_attr "pa_combine_type" "addmove")
2709    (set_attr "length" "4")])
2710
2711 (define_expand "movqi"
2712   [(set (match_operand:QI 0 "general_operand" "")
2713         (match_operand:QI 1 "general_operand" ""))]
2714   ""
2715   "
2716 {
2717   if (emit_move_sequence (operands, QImode, 0))
2718     DONE;
2719 }")
2720
2721 (define_insn ""
2722   [(set (match_operand:QI 0 "reg_or_nonsymb_mem_operand" "=r,r,r,r,r,Q,*q,!*f")
2723         (match_operand:QI 1 "move_operand" "r,J,N,K,RQ,rM,rM,!*fM"))]
2724   "register_operand (operands[0], QImode)
2725    || reg_or_0_operand (operands[1], QImode)"
2726   "@
2727    copy %1,%0
2728    ldi %1,%0
2729    ldil L'%1,%0
2730    {zdepi|depwi,z} %Z1,%0
2731    ldb%M1 %1,%0
2732    stb%M0 %r1,%0
2733    mtsar %r1
2734    fcpy,sgl %f1,%0"
2735   [(set_attr "type" "move,move,move,shift,load,store,move,fpalu")
2736    (set_attr "pa_combine_type" "addmove")
2737    (set_attr "length" "4,4,4,4,4,4,4,4")])
2738
2739 (define_insn ""
2740   [(set (match_operand:QI 0 "register_operand" "=r")
2741         (mem:QI (plus:SI (match_operand:SI 1 "basereg_operand" "r")
2742                          (match_operand:SI 2 "register_operand" "r"))))]
2743   "! TARGET_DISABLE_INDEXING"
2744   "{ldbx|ldb} %2(%1),%0"
2745   [(set_attr "type" "load")
2746    (set_attr "length" "4")])
2747
2748 (define_insn ""
2749   [(set (match_operand:QI 0 "register_operand" "=r")
2750         (mem:QI (plus:SI (match_operand:SI 1 "register_operand" "r")
2751                          (match_operand:SI 2 "basereg_operand" "r"))))]
2752   "! TARGET_DISABLE_INDEXING"
2753   "{ldbx|ldb} %1(%2),%0"
2754   [(set_attr "type" "load")
2755    (set_attr "length" "4")])
2756
2757 ; Indexed byte load with zero extension to SImode or HImode.
2758 (define_insn ""
2759   [(set (match_operand:SI 0 "register_operand" "=r")
2760         (zero_extend:SI (mem:QI
2761                           (plus:SI
2762                             (match_operand:SI 1 "basereg_operand" "r")
2763                             (match_operand:SI 2 "register_operand" "r")))))]
2764   "! TARGET_DISABLE_INDEXING"
2765   "{ldbx|ldb} %2(%1),%0"
2766   [(set_attr "type" "load")
2767    (set_attr "length" "4")])
2768
2769 (define_insn ""
2770   [(set (match_operand:SI 0 "register_operand" "=r")
2771         (zero_extend:SI (mem:QI
2772                           (plus:SI
2773                             (match_operand:SI 1 "register_operand" "r")
2774                             (match_operand:SI 2 "basereg_operand" "r")))))]
2775   "! TARGET_DISABLE_INDEXING"
2776   "{ldbx|ldb} %1(%2),%0"
2777   [(set_attr "type" "load")
2778    (set_attr "length" "4")])
2779
2780 (define_insn ""
2781   [(set (match_operand:HI 0 "register_operand" "=r")
2782         (zero_extend:HI (mem:QI
2783                           (plus:SI
2784                             (match_operand:SI 1 "basereg_operand" "r")
2785                             (match_operand:SI 2 "register_operand" "r")))))]
2786   "! TARGET_DISABLE_INDEXING"
2787   "{ldbx|ldb} %2(%1),%0"
2788   [(set_attr "type" "load")
2789    (set_attr "length" "4")])
2790
2791 (define_insn ""
2792   [(set (match_operand:HI 0 "register_operand" "=r")
2793         (zero_extend:HI (mem:QI
2794                           (plus:SI
2795                             (match_operand:SI 1 "register_operand" "r")
2796                             (match_operand:SI 2 "basereg_operand" "r")))))]
2797   "! TARGET_DISABLE_INDEXING"
2798   "{ldbx|ldb} %1(%2),%0"
2799   [(set_attr "type" "load")
2800    (set_attr "length" "4")])
2801
2802 (define_insn ""
2803   [(set (match_operand:QI 0 "register_operand" "=r")
2804         (mem:QI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2805                          (match_operand:SI 2 "int5_operand" "L"))))
2806    (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
2807   ""
2808   "{ldbs|ldb},mb %2(%1),%0"
2809   [(set_attr "type" "load")
2810    (set_attr "length" "4")])
2811
2812 ; Now the same thing with zero extensions.
2813 (define_insn ""
2814   [(set (match_operand:SI 0 "register_operand" "=r")
2815         (zero_extend:SI (mem:QI (plus:SI
2816                                   (match_operand:SI 1 "register_operand" "+r")
2817                                   (match_operand:SI 2 "int5_operand" "L")))))
2818    (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
2819   ""
2820   "{ldbs|ldb},mb %2(%1),%0"
2821   [(set_attr "type" "load")
2822    (set_attr "length" "4")])
2823
2824 (define_insn ""
2825   [(set (match_operand:HI 0 "register_operand" "=r")
2826         (zero_extend:HI (mem:QI (plus:SI
2827                                   (match_operand:SI 1 "register_operand" "+r")
2828                                   (match_operand:SI 2 "int5_operand" "L")))))
2829    (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
2830   ""
2831   "{ldbs|ldb},mb %2(%1),%0"
2832   [(set_attr "type" "load")
2833    (set_attr "length" "4")])
2834
2835 (define_insn ""
2836   [(set (mem:QI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2837                          (match_operand:SI 1 "int5_operand" "L")))
2838         (match_operand:QI 2 "reg_or_0_operand" "rM"))
2839    (set (match_dup 0)
2840         (plus:SI (match_dup 0) (match_dup 1)))]
2841   ""
2842   "{stbs|stb},mb %r2,%1(%0)"
2843   [(set_attr "type" "store")
2844    (set_attr "length" "4")])
2845
2846 ;; The definition of this insn does not really explain what it does,
2847 ;; but it should suffice
2848 ;; that anything generated as this insn will be recognized as one
2849 ;; and that it will not successfully combine with anything.
2850 (define_expand "movstrsi"
2851   [(parallel [(set (match_operand:BLK 0 "" "")
2852                    (match_operand:BLK 1 "" ""))
2853               (clobber (match_dup 7))
2854               (clobber (match_dup 8))
2855               (clobber (match_dup 4))
2856               (clobber (match_dup 5))
2857               (clobber (match_dup 6))
2858               (use (match_operand:SI 2 "arith_operand" ""))
2859               (use (match_operand:SI 3 "const_int_operand" ""))])]
2860   "!TARGET_64BIT"
2861   "
2862 {
2863   int size, align;
2864
2865   /* HP provides very fast block move library routine for the PA;
2866      this routine includes:
2867
2868         4x4 byte at a time block moves,
2869         1x4 byte at a time with alignment checked at runtime with
2870             attempts to align the source and destination as needed
2871         1x1 byte loop
2872
2873      With that in mind, here's the heuristics to try and guess when
2874      the inlined block move will be better than the library block
2875      move:
2876
2877         If the size isn't constant, then always use the library routines.
2878
2879         If the size is large in respect to the known alignment, then use
2880         the library routines.
2881
2882         If the size is small in repsect to the known alignment, then open
2883         code the copy (since that will lead to better scheduling).
2884
2885         Else use the block move pattern.   */
2886
2887   /* Undetermined size, use the library routine.  */
2888   if (GET_CODE (operands[2]) != CONST_INT)
2889     FAIL;
2890
2891   size = INTVAL (operands[2]);
2892   align = INTVAL (operands[3]);
2893   align = align > 4 ? 4 : align;
2894
2895   /* If size/alignment > 8 (eg size is large in respect to alignment),
2896      then use the library routines.  */
2897   if (size / align > 16)
2898     FAIL;
2899
2900   /* This does happen, but not often enough to worry much about.  */
2901   if (size / align < MOVE_RATIO)
2902     FAIL;
2903   
2904   /* Fall through means we're going to use our block move pattern.  */
2905   operands[0]
2906     = replace_equiv_address (operands[0],
2907                              copy_to_mode_reg (SImode, XEXP (operands[0], 0)));
2908   operands[1]
2909     = replace_equiv_address (operands[1],
2910                              copy_to_mode_reg (SImode, XEXP (operands[1], 0)));
2911   operands[4] = gen_reg_rtx (SImode);
2912   operands[5] = gen_reg_rtx (SImode);
2913   operands[6] = gen_reg_rtx (SImode);
2914   operands[7] = XEXP (operands[0], 0);
2915   operands[8] = XEXP (operands[1], 0);
2916 }")
2917
2918 ;; The operand constraints are written like this to support both compile-time
2919 ;; and run-time determined byte count.  If the count is run-time determined,
2920 ;; the register with the byte count is clobbered by the copying code, and
2921 ;; therefore it is forced to operand 2.  If the count is compile-time
2922 ;; determined, we need two scratch registers for the unrolled code.
2923 (define_insn "movstrsi_internal"
2924   [(set (mem:BLK (match_operand:SI 0 "register_operand" "+r,r"))
2925         (mem:BLK (match_operand:SI 1 "register_operand" "+r,r")))
2926    (clobber (match_dup 0))
2927    (clobber (match_dup 1))
2928    (clobber (match_operand:SI 2 "register_operand" "=r,r"))     ;loop cnt/tmp
2929    (clobber (match_operand:SI 3 "register_operand" "=&r,&r"))   ;item tmp
2930    (clobber (match_operand:SI 6 "register_operand" "=&r,&r"))   ;item tmp2
2931    (use (match_operand:SI 4 "arith_operand" "J,2"))      ;byte count
2932    (use (match_operand:SI 5 "const_int_operand" "n,n"))] ;alignment
2933   "!TARGET_64BIT"
2934   "* return output_block_move (operands, !which_alternative);"
2935   [(set_attr "type" "multi,multi")])
2936 \f
2937 ;; Floating point move insns
2938
2939 ;; This pattern forces (set (reg:DF ...) (const_double ...))
2940 ;; to be reloaded by putting the constant into memory when
2941 ;; reg is a floating point register.
2942 ;;
2943 ;; For integer registers we use ldil;ldo to set the appropriate
2944 ;; value.
2945 ;;
2946 ;; This must come before the movdf pattern, and it must be present
2947 ;; to handle obscure reloading cases.
2948 (define_insn ""
2949   [(set (match_operand:DF 0 "register_operand" "=?r,f")
2950         (match_operand:DF 1 "" "?F,m"))]
2951   "GET_CODE (operands[1]) == CONST_DOUBLE
2952    && operands[1] != CONST0_RTX (DFmode)
2953    && !TARGET_64BIT
2954    && ! TARGET_SOFT_FLOAT"
2955   "* return (which_alternative == 0 ? output_move_double (operands)
2956                                     : \"fldd%F1 %1,%0\");"
2957   [(set_attr "type" "move,fpload")
2958    (set_attr "length" "16,4")])
2959
2960 (define_expand "movdf"
2961   [(set (match_operand:DF 0 "general_operand" "")
2962         (match_operand:DF 1 "general_operand" ""))]
2963   ""
2964   "
2965 {
2966   if (GET_CODE (operands[1]) == CONST_DOUBLE && TARGET_64BIT)
2967       operands[1] = force_const_mem (DFmode, operands[1]);
2968
2969   if (emit_move_sequence (operands, DFmode, 0))
2970     DONE;
2971 }")
2972
2973 ;; Reloading an SImode or DImode value requires a scratch register if
2974 ;; going in to or out of float point registers.
2975
2976 (define_expand "reload_indf"
2977   [(set (match_operand:DF 0 "register_operand" "=Z")
2978         (match_operand:DF 1 "non_hard_reg_operand" ""))
2979    (clobber (match_operand:DF 2 "register_operand" "=&r"))]
2980   ""
2981   "
2982 {
2983   if (emit_move_sequence (operands, DFmode, operands[2]))
2984     DONE;
2985
2986   /* We don't want the clobber emitted, so handle this ourselves.  */
2987   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2988   DONE;
2989 }")
2990
2991 (define_expand "reload_outdf" 
2992  [(set (match_operand:DF 0 "non_hard_reg_operand" "")
2993         (match_operand:DF 1  "register_operand" "Z"))
2994    (clobber (match_operand:DF 2 "register_operand" "=&r"))]
2995   ""
2996   "
2997 {
2998   if (emit_move_sequence (operands, DFmode, operands[2]))
2999     DONE;
3000
3001   /* We don't want the clobber emitted, so handle this ourselves.  */
3002   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
3003   DONE;
3004 }")
3005
3006 (define_insn ""
3007   [(set (match_operand:DF 0 "reg_or_nonsymb_mem_operand"
3008                           "=f,*r,RQ,?o,?Q,f,*r,*r")
3009         (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
3010                           "fG,*rG,f,*r,*r,RQ,o,RQ"))]
3011   "(register_operand (operands[0], DFmode)
3012     || reg_or_0_operand (operands[1], DFmode))
3013    && ! (GET_CODE (operands[1]) == CONST_DOUBLE
3014          && GET_CODE (operands[0]) == MEM)
3015    && ! TARGET_64BIT
3016    && ! TARGET_SOFT_FLOAT"
3017   "*
3018 {
3019   if (FP_REG_P (operands[0]) || FP_REG_P (operands[1])
3020       || operands[1] == CONST0_RTX (DFmode))
3021     return output_fp_move_double (operands);
3022   return output_move_double (operands);
3023 }"
3024   [(set_attr "type" "fpalu,move,fpstore,store,store,fpload,load,load")
3025    (set_attr "length" "4,8,4,8,16,4,8,16")])
3026
3027 (define_insn ""
3028   [(set (match_operand:DF 0 "reg_or_nonsymb_mem_operand"
3029                           "=r,?o,?Q,r,r")
3030         (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
3031                           "rG,r,r,o,Q"))]
3032   "(register_operand (operands[0], DFmode)
3033     || reg_or_0_operand (operands[1], DFmode))
3034    && ! TARGET_64BIT
3035    && TARGET_SOFT_FLOAT"
3036   "*
3037 {
3038   return output_move_double (operands);
3039 }"
3040   [(set_attr "type" "move,store,store,load,load")
3041    (set_attr "length" "8,8,16,8,16")])
3042
3043 (define_insn ""
3044   [(set (match_operand:DF 0 "reg_or_nonsymb_mem_operand"
3045                                 "=r,r,r,r,r,Q,*q,!f,f,*TR")
3046         (match_operand:DF 1 "move_operand"
3047                                 "r,J,N,K,RQ,rM,rM,!fM,*RT,f"))]
3048   "(register_operand (operands[0], DFmode)
3049     || reg_or_0_operand (operands[1], DFmode))
3050    && ! TARGET_SOFT_FLOAT && TARGET_64BIT"
3051   "@
3052    copy %1,%0
3053    ldi %1,%0
3054    ldil L'%1,%0
3055    depdi,z %z1,%0
3056    ldd%M1 %1,%0
3057    std%M0 %r1,%0
3058    mtsar %r1
3059    fcpy,dbl %f1,%0
3060    fldd%F1 %1,%0
3061    fstd%F0 %1,%0"
3062   [(set_attr "type" "move,move,move,shift,load,store,move,fpalu,fpload,fpstore")
3063    (set_attr "pa_combine_type" "addmove")
3064    (set_attr "length" "4,4,4,4,4,4,4,4,4,4")])
3065
3066 (define_insn ""
3067   [(set (match_operand:DF 0 "register_operand" "=fx")
3068         (mem:DF (plus:SI (match_operand:SI 1 "basereg_operand" "r")
3069                          (match_operand:SI 2 "register_operand" "r"))))]
3070   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3071   "{flddx|fldd} %2(%1),%0"
3072   [(set_attr "type" "fpload")
3073    (set_attr "length" "4")])
3074
3075 (define_insn ""
3076   [(set (match_operand:DF 0 "register_operand" "=fx")
3077         (mem:DF (plus:SI (match_operand:SI 1 "register_operand" "r")
3078                          (match_operand:SI 2 "basereg_operand" "r"))))]
3079   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3080   "{flddx|fldd} %1(%2),%0"
3081   [(set_attr "type" "fpload")
3082    (set_attr "length" "4")])
3083
3084 (define_insn ""
3085   [(set (mem:DF (plus:SI (match_operand:SI 1 "basereg_operand" "r")
3086                          (match_operand:SI 2 "register_operand" "r")))
3087         (match_operand:DF 0 "register_operand" "fx"))]
3088   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3089   "{fstdx|fstd} %0,%2(%1)"
3090   [(set_attr "type" "fpstore")
3091    (set_attr "length" "4")])
3092
3093 (define_insn ""
3094   [(set (mem:DF (plus:SI (match_operand:SI 1 "register_operand" "r")
3095                          (match_operand:SI 2 "basereg_operand" "r")))
3096         (match_operand:DF 0 "register_operand" "fx"))]
3097   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3098   "{fstdx|fstd} %0,%1(%2)"
3099   [(set_attr "type" "fpstore")
3100    (set_attr "length" "4")])
3101
3102 (define_expand "movdi"
3103   [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand" "")
3104         (match_operand:DI 1 "general_operand" ""))]
3105   ""
3106   "
3107 {
3108   if (GET_CODE (operands[1]) == CONST_DOUBLE && TARGET_64BIT)
3109       operands[1] = force_const_mem (DImode, operands[1]);
3110
3111   if (emit_move_sequence (operands, DImode, 0))
3112     DONE;
3113 }")
3114
3115 (define_expand "reload_indi"
3116   [(set (match_operand:DI 0 "register_operand" "=Z")
3117         (match_operand:DI 1 "non_hard_reg_operand" ""))
3118    (clobber (match_operand:SI 2 "register_operand" "=&r"))]
3119   ""
3120   "
3121 {
3122   if (emit_move_sequence (operands, DImode, operands[2]))
3123     DONE;
3124
3125   /* We don't want the clobber emitted, so handle this ourselves.  */
3126   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
3127   DONE;
3128 }")
3129
3130 (define_expand "reload_outdi"
3131   [(set (match_operand:DI 0 "non_hard_reg_operand" "")
3132         (match_operand:DI 1 "register_operand" "Z"))
3133    (clobber (match_operand:SI 2 "register_operand" "=&r"))]
3134   ""
3135   "
3136 {
3137   if (emit_move_sequence (operands, DImode, operands[2]))
3138     DONE;
3139
3140   /* We don't want the clobber emitted, so handle this ourselves.  */
3141   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
3142   DONE;
3143 }")
3144
3145 (define_insn ""
3146   [(set (match_operand:DI 0 "register_operand" "=r")
3147         (high:DI (match_operand 1 "" "")))]
3148   "!TARGET_64BIT"
3149   "*
3150 {
3151   rtx op0 = operands[0];
3152   rtx op1 = operands[1];
3153
3154   if (GET_CODE (op1) == CONST_INT)
3155     {
3156       operands[0] = operand_subword (op0, 1, 0, DImode);
3157       output_asm_insn (\"ldil L'%1,%0\", operands);
3158
3159       operands[0] = operand_subword (op0, 0, 0, DImode);
3160       if (INTVAL (op1) < 0)
3161         output_asm_insn (\"ldi -1,%0\", operands);
3162       else
3163         output_asm_insn (\"ldi 0,%0\", operands);
3164       return \"\";
3165     }
3166   else if (GET_CODE (op1) == CONST_DOUBLE)
3167     {
3168       operands[0] = operand_subword (op0, 1, 0, DImode);
3169       operands[1] = GEN_INT (CONST_DOUBLE_LOW (op1));
3170       output_asm_insn (\"ldil L'%1,%0\", operands);
3171
3172       operands[0] = operand_subword (op0, 0, 0, DImode);
3173       operands[1] = GEN_INT (CONST_DOUBLE_HIGH (op1));
3174       output_asm_insn (singlemove_string (operands), operands);
3175       return \"\";
3176     }
3177   else
3178     abort ();
3179 }"
3180   [(set_attr "type" "move")
3181    (set_attr "length" "8")])
3182
3183 (define_insn ""
3184   [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand"
3185                           "=r,o,Q,r,r,r,f,f,*TR")
3186         (match_operand:DI 1 "general_operand"
3187                           "rM,r,r,o*R,Q,i,fM,*TR,f"))]
3188   "(register_operand (operands[0], DImode)
3189     || reg_or_0_operand (operands[1], DImode))
3190    && ! TARGET_64BIT
3191    && ! TARGET_SOFT_FLOAT"
3192   "*
3193 {
3194   if (FP_REG_P (operands[0]) || FP_REG_P (operands[1])
3195       || (operands[1] == CONST0_RTX (DImode)))
3196     return output_fp_move_double (operands);
3197   return output_move_double (operands);
3198 }"
3199   [(set_attr "type" "move,store,store,load,load,multi,fpalu,fpload,fpstore")
3200    (set_attr "length" "8,8,16,8,16,16,4,4,4")])
3201
3202 (define_insn ""
3203   [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand"
3204                                 "=r,r,r,r,r,r,Q,*q,!f,f,*TR")
3205         (match_operand:DI 1 "move_operand"
3206                                 "A,r,J,N,K,RQ,rM,rM,!fM,*RT,f"))]
3207   "(register_operand (operands[0], DImode)
3208     || reg_or_0_operand (operands[1], DImode))
3209    && ! TARGET_SOFT_FLOAT && TARGET_64BIT"
3210   "@
3211    ldd RT'%A1,%0
3212    copy %1,%0
3213    ldi %1,%0
3214    ldil L'%1,%0
3215    depdi,z %z1,%0
3216    ldd%M1 %1,%0
3217    std%M0 %r1,%0
3218    mtsar %r1
3219    fcpy,dbl %f1,%0
3220    fldd%F1 %1,%0
3221    fstd%F0 %1,%0"
3222   [(set_attr "type" "load,move,move,move,shift,load,store,move,fpalu,fpload,fpstore")
3223    (set_attr "pa_combine_type" "addmove")
3224    (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4")])
3225
3226 (define_insn ""
3227   [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand"
3228                           "=r,o,Q,r,r,r")
3229         (match_operand:DI 1 "general_operand"
3230                           "rM,r,r,o,Q,i"))]
3231   "(register_operand (operands[0], DImode)
3232     || reg_or_0_operand (operands[1], DImode))
3233    && ! TARGET_64BIT
3234    && TARGET_SOFT_FLOAT"
3235   "*
3236 {
3237   return output_move_double (operands);
3238 }"
3239   [(set_attr "type" "move,store,store,load,load,multi")
3240    (set_attr "length" "8,8,16,8,16,16")])
3241
3242 (define_insn ""
3243   [(set (match_operand:DI 0 "register_operand" "=r,&r")
3244         (lo_sum:DI (match_operand:DI 1 "register_operand" "0,r")
3245                    (match_operand:DI 2 "immediate_operand" "i,i")))]
3246   "!TARGET_64BIT"
3247   "*
3248 {
3249   /* Don't output a 64 bit constant, since we can't trust the assembler to
3250      handle it correctly.  */
3251   if (GET_CODE (operands[2]) == CONST_DOUBLE)
3252     operands[2] = GEN_INT (CONST_DOUBLE_LOW (operands[2]));
3253   if (which_alternative == 1)
3254     output_asm_insn (\"copy %1,%0\", operands);
3255   return \"ldo R'%G2(%R1),%R0\";
3256 }"
3257   [(set_attr "type" "move,move")
3258    (set_attr "length" "4,8")])
3259
3260 ;; This pattern forces (set (reg:SF ...) (const_double ...))
3261 ;; to be reloaded by putting the constant into memory when
3262 ;; reg is a floating point register.
3263 ;;
3264 ;; For integer registers we use ldil;ldo to set the appropriate
3265 ;; value.
3266 ;;
3267 ;; This must come before the movsf pattern, and it must be present
3268 ;; to handle obscure reloading cases.
3269 (define_insn ""
3270   [(set (match_operand:SF 0 "register_operand" "=?r,f")
3271         (match_operand:SF 1 "" "?F,m"))]
3272   "GET_CODE (operands[1]) == CONST_DOUBLE
3273    && operands[1] != CONST0_RTX (SFmode)
3274    && ! TARGET_SOFT_FLOAT"
3275   "* return (which_alternative == 0 ? singlemove_string (operands)
3276                                     : \" fldw%F1 %1,%0\");"
3277   [(set_attr "type" "move,fpload")
3278    (set_attr "length" "8,4")])
3279
3280 (define_expand "movsf"
3281   [(set (match_operand:SF 0 "general_operand" "")
3282         (match_operand:SF 1 "general_operand" ""))]
3283   ""
3284   "
3285 {
3286   if (emit_move_sequence (operands, SFmode, 0))
3287     DONE;
3288 }")
3289
3290 ;; Reloading an SImode or DImode value requires a scratch register if
3291 ;; going in to or out of float point registers.
3292
3293 (define_expand "reload_insf"
3294   [(set (match_operand:SF 0 "register_operand" "=Z")
3295         (match_operand:SF 1 "non_hard_reg_operand" ""))
3296    (clobber (match_operand:SF 2 "register_operand" "=&r"))]
3297   ""
3298   "
3299 {
3300   if (emit_move_sequence (operands, SFmode, operands[2]))
3301     DONE;
3302
3303   /* We don't want the clobber emitted, so handle this ourselves.  */
3304   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
3305   DONE;
3306 }")
3307
3308 (define_expand "reload_outsf"
3309   [(set (match_operand:SF 0 "non_hard_reg_operand" "")
3310         (match_operand:SF 1  "register_operand" "Z"))
3311    (clobber (match_operand:SF 2 "register_operand" "=&r"))]
3312   ""
3313   "
3314 {
3315   if (emit_move_sequence (operands, SFmode, operands[2]))
3316     DONE;
3317
3318   /* We don't want the clobber emitted, so handle this ourselves.  */
3319   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
3320   DONE;
3321 }")
3322
3323 (define_insn ""
3324   [(set (match_operand:SF 0 "reg_or_nonsymb_mem_operand"
3325                           "=f,r,f,r,RQ,Q")
3326         (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
3327                           "fG,rG,RQ,RQ,f,rG"))]
3328   "(register_operand (operands[0], SFmode)
3329     || reg_or_0_operand (operands[1], SFmode))
3330    && ! TARGET_SOFT_FLOAT"
3331   "@
3332    fcpy,sgl %f1,%0
3333    copy %r1,%0
3334    fldw%F1 %1,%0
3335    ldw%M1 %1,%0
3336    fstw%F0 %r1,%0
3337    stw%M0 %r1,%0"
3338   [(set_attr "type" "fpalu,move,fpload,load,fpstore,store")
3339    (set_attr "pa_combine_type" "addmove")
3340    (set_attr "length" "4,4,4,4,4,4")])
3341
3342 (define_insn ""
3343   [(set (match_operand:SF 0 "reg_or_nonsymb_mem_operand"
3344                           "=r,r,Q")
3345         (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
3346                           "rG,RQ,rG"))]
3347   "(register_operand (operands[0], SFmode)
3348     || reg_or_0_operand (operands[1], SFmode))
3349    && TARGET_SOFT_FLOAT"
3350   "@
3351    copy %r1,%0
3352    ldw%M1 %1,%0
3353    stw%M0 %r1,%0"
3354   [(set_attr "type" "move,load,store")
3355    (set_attr "pa_combine_type" "addmove")
3356    (set_attr "length" "4,4,4")])
3357
3358 (define_insn ""
3359   [(set (match_operand:SF 0 "register_operand" "=fx")
3360         (mem:SF (plus:SI (match_operand:SI 1 "basereg_operand" "r")
3361                          (match_operand:SI 2 "register_operand" "r"))))]
3362   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3363   "{fldwx|fldw} %2(%1),%0"
3364   [(set_attr "type" "fpload")
3365    (set_attr "length" "4")])
3366
3367 (define_insn ""
3368   [(set (match_operand:SF 0 "register_operand" "=fx")
3369         (mem:SF (plus:SI (match_operand:SI 1 "register_operand" "r")
3370                          (match_operand:SI 2 "basereg_operand" "r"))))]
3371   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3372   "{fldwx|fldw} %1(%2),%0"
3373   [(set_attr "type" "fpload")
3374    (set_attr "length" "4")])
3375
3376 (define_insn ""
3377   [(set (mem:SF (plus:SI (match_operand:SI 1 "basereg_operand" "r")
3378                          (match_operand:SI 2 "register_operand" "r")))
3379       (match_operand:SF 0 "register_operand" "fx"))]
3380   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3381   "{fstwx|fstw} %0,%2(%1)"
3382   [(set_attr "type" "fpstore")
3383    (set_attr "length" "4")])
3384 \f
3385 (define_insn ""
3386   [(set (mem:SF (plus:SI (match_operand:SI 1 "register_operand" "r")
3387                          (match_operand:SI 2 "basereg_operand" "r")))
3388       (match_operand:SF 0 "register_operand" "fx"))]
3389   "! TARGET_DISABLE_INDEXING && ! TARGET_SOFT_FLOAT"
3390   "{fstwx|fstw} %0,%1(%2)"
3391   [(set_attr "type" "fpstore")
3392    (set_attr "length" "4")])
3393 \f
3394
3395 ;;- zero extension instructions
3396 ;; We have define_expand for zero extension patterns to make sure the
3397 ;; operands get loaded into registers.  The define_insns accept
3398 ;; memory operands.  This gives us better overall code than just
3399 ;; having a pattern that does or does not accept memory operands.
3400
3401 (define_expand "zero_extendhisi2"
3402   [(set (match_operand:SI 0 "register_operand" "")
3403         (zero_extend:SI
3404          (match_operand:HI 1 "register_operand" "")))]
3405   ""
3406   "")
3407
3408 (define_insn ""
3409   [(set (match_operand:SI 0 "register_operand" "=r,r")
3410         (zero_extend:SI
3411          (match_operand:HI 1 "move_operand" "r,RQ")))]
3412   "GET_CODE (operands[1]) != CONST_INT"
3413   "@
3414    {extru|extrw,u} %1,31,16,%0
3415    ldh%M1 %1,%0"
3416   [(set_attr "type" "shift,load")
3417    (set_attr "length" "4,4")])
3418
3419 (define_expand "zero_extendqihi2"
3420   [(set (match_operand:HI 0 "register_operand" "")
3421         (zero_extend:HI
3422          (match_operand:QI 1 "register_operand" "")))]
3423   ""
3424   "")
3425
3426 (define_insn ""
3427   [(set (match_operand:HI 0 "register_operand" "=r,r")
3428         (zero_extend:HI
3429          (match_operand:QI 1 "move_operand" "r,RQ")))]
3430   "GET_CODE (operands[1]) != CONST_INT"
3431   "@
3432    {extru|extrw,u} %1,31,8,%0
3433    ldb%M1 %1,%0"
3434   [(set_attr "type" "shift,load")
3435    (set_attr "length" "4,4")])
3436
3437 (define_expand "zero_extendqisi2"
3438   [(set (match_operand:SI 0 "register_operand" "")
3439         (zero_extend:SI
3440          (match_operand:QI 1 "register_operand" "")))]
3441   ""
3442   "")
3443
3444 (define_insn ""
3445   [(set (match_operand:SI 0 "register_operand" "=r,r")
3446         (zero_extend:SI
3447          (match_operand:QI 1 "move_operand" "r,RQ")))]
3448   "GET_CODE (operands[1]) != CONST_INT"
3449   "@
3450    {extru|extrw,u} %1,31,8,%0
3451    ldb%M1 %1,%0"
3452   [(set_attr "type" "shift,load")
3453    (set_attr "length" "4,4")])
3454
3455 (define_insn "zero_extendqidi2"
3456   [(set (match_operand:DI 0 "register_operand" "=r")
3457         (zero_extend:DI (match_operand:QI 1 "register_operand" "r")))]
3458   "TARGET_64BIT"
3459   "extrd,u %1,63,8,%0"
3460   [(set_attr "type" "shift") 
3461   (set_attr "length" "4")])
3462
3463 (define_insn "zero_extendhidi2"
3464   [(set (match_operand:DI 0 "register_operand" "=r")
3465         (zero_extend:DI (match_operand:HI 1 "register_operand" "r")))]
3466   "TARGET_64BIT"
3467   "extrd,u %1,63,16,%0"
3468   [(set_attr "type" "shift") 
3469   (set_attr "length" "4")])
3470
3471 (define_insn "zero_extendsidi2"
3472   [(set (match_operand:DI 0 "register_operand" "=r")
3473         (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
3474   "TARGET_64BIT"
3475   "extrd,u %1,63,32,%0"
3476   [(set_attr "type" "shift") 
3477   (set_attr "length" "4")])
3478
3479 ;;- sign extension instructions
3480
3481 (define_insn "extendhisi2"
3482   [(set (match_operand:SI 0 "register_operand" "=r")
3483         (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
3484   ""
3485   "{extrs|extrw,s} %1,31,16,%0"
3486   [(set_attr "type" "shift")
3487    (set_attr "length" "4")])
3488
3489 (define_insn "extendqihi2"
3490   [(set (match_operand:HI 0 "register_operand" "=r")
3491         (sign_extend:HI (match_operand:QI 1 "register_operand" "r")))]
3492   ""
3493   "{extrs|extrw,s} %1,31,8,%0"
3494   [(set_attr "type" "shift") 
3495   (set_attr "length" "4")])
3496
3497 (define_insn "extendqisi2"
3498   [(set (match_operand:SI 0 "register_operand" "=r")
3499         (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
3500   ""
3501   "{extrs|extrw,s} %1,31,8,%0"
3502   [(set_attr "type" "shift")
3503    (set_attr "length" "4")])
3504
3505 (define_insn "extendqidi2"
3506   [(set (match_operand:DI 0 "register_operand" "=r")
3507         (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))]
3508   "TARGET_64BIT"
3509   "extrd,s %1,63,8,%0"
3510   [(set_attr "type" "shift") 
3511   (set_attr "length" "4")])
3512
3513 (define_insn "extendhidi2"
3514   [(set (match_operand:DI 0 "register_operand" "=r")
3515         (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))]
3516   "TARGET_64BIT"
3517   "extrd,s %1,63,16,%0"
3518   [(set_attr "type" "shift") 
3519   (set_attr "length" "4")])
3520
3521 (define_insn "extendsidi2"
3522   [(set (match_operand:DI 0 "register_operand" "=r")
3523         (sign_extend:DI (match_operand:SI 1 "register_operand" "r")))]
3524   "TARGET_64BIT"
3525   "extrd,s %1,63,32,%0"
3526   [(set_attr "type" "shift") 
3527   (set_attr "length" "4")])
3528
3529 \f
3530 ;; Conversions between float and double.
3531
3532 (define_insn "extendsfdf2"
3533   [(set (match_operand:DF 0 "register_operand" "=f")
3534         (float_extend:DF
3535          (match_operand:SF 1 "register_operand" "f")))]
3536   "! TARGET_SOFT_FLOAT"
3537   "{fcnvff|fcnv},sgl,dbl %1,%0"
3538   [(set_attr "type" "fpalu")
3539    (set_attr "length" "4")])
3540
3541 (define_insn "truncdfsf2"
3542   [(set (match_operand:SF 0 "register_operand" "=f")
3543         (float_truncate:SF
3544          (match_operand:DF 1 "register_operand" "f")))]
3545   "! TARGET_SOFT_FLOAT"
3546   "{fcnvff|fcnv},dbl,sgl %1,%0"
3547   [(set_attr "type" "fpalu")
3548    (set_attr "length" "4")])
3549
3550 ;; Conversion between fixed point and floating point.
3551 ;; Note that among the fix-to-float insns
3552 ;; the ones that start with SImode come first.
3553 ;; That is so that an operand that is a CONST_INT
3554 ;; (and therefore lacks a specific machine mode).
3555 ;; will be recognized as SImode (which is always valid)
3556 ;; rather than as QImode or HImode.
3557
3558 ;; This pattern forces (set (reg:SF ...) (float:SF (const_int ...)))
3559 ;; to be reloaded by putting the constant into memory.
3560 ;; It must come before the more general floatsisf2 pattern.
3561 (define_insn ""
3562   [(set (match_operand:SF 0 "register_operand" "=f")
3563         (float:SF (match_operand:SI 1 "const_int_operand" "m")))]
3564   "! TARGET_SOFT_FLOAT"
3565   "fldw%F1 %1,%0\;{fcnvxf,sgl,sgl|fcnv,w,sgl} %0,%0"
3566   [(set_attr "type" "fpalu")
3567    (set_attr "length" "8")])
3568
3569 (define_insn "floatsisf2"
3570   [(set (match_operand:SF 0 "register_operand" "=f")
3571         (float:SF (match_operand:SI 1 "register_operand" "f")))]
3572   "! TARGET_SOFT_FLOAT"
3573   "{fcnvxf,sgl,sgl|fcnv,w,sgl} %1,%0"
3574   [(set_attr "type" "fpalu")
3575    (set_attr "length" "4")])
3576
3577 ;; This pattern forces (set (reg:DF ...) (float:DF (const_int ...)))
3578 ;; to be reloaded by putting the constant into memory.
3579 ;; It must come before the more general floatsidf2 pattern.
3580 (define_insn ""
3581   [(set (match_operand:DF 0 "register_operand" "=f")
3582         (float:DF (match_operand:SI 1 "const_int_operand" "m")))]
3583   "! TARGET_SOFT_FLOAT"
3584   "fldw%F1 %1,%0\;{fcnvxf,sgl,dbl|fcnv,w,dbl} %0,%0"
3585   [(set_attr "type" "fpalu")
3586    (set_attr "length" "8")])
3587
3588 (define_insn "floatsidf2"
3589   [(set (match_operand:DF 0 "register_operand" "=f")
3590         (float:DF (match_operand:SI 1 "register_operand" "f")))]
3591   "! TARGET_SOFT_FLOAT"
3592   "{fcnvxf,sgl,dbl|fcnv,w,dbl} %1,%0"
3593   [(set_attr "type" "fpalu")
3594    (set_attr "length" "4")])
3595
3596 (define_expand "floatunssisf2"
3597   [(set (subreg:SI (match_dup 2) 4)
3598         (match_operand:SI 1 "register_operand" ""))
3599    (set (subreg:SI (match_dup 2) 0)
3600         (const_int 0))
3601    (set (match_operand:SF 0 "register_operand" "")
3602         (float:SF (match_dup 2)))]
3603   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3604   "
3605 {
3606   if (TARGET_PA_20)
3607     {
3608       emit_insn (gen_floatunssisf2_pa20 (operands[0], operands[1]));
3609       DONE;
3610     }
3611   operands[2] = gen_reg_rtx (DImode);
3612 }")
3613
3614 (define_expand "floatunssidf2"
3615   [(set (subreg:SI (match_dup 2) 4)
3616         (match_operand:SI 1 "register_operand" ""))
3617    (set (subreg:SI (match_dup 2) 0)
3618         (const_int 0))
3619    (set (match_operand:DF 0 "register_operand" "")
3620         (float:DF (match_dup 2)))]
3621   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3622   "
3623 {
3624   if (TARGET_PA_20)
3625     {
3626       emit_insn (gen_floatunssidf2_pa20 (operands[0], operands[1]));
3627       DONE;
3628     }
3629   operands[2] = gen_reg_rtx (DImode);
3630 }")
3631
3632 (define_insn "floatdisf2"
3633   [(set (match_operand:SF 0 "register_operand" "=f")
3634         (float:SF (match_operand:DI 1 "register_operand" "f")))]
3635   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3636   "{fcnvxf,dbl,sgl|fcnv,dw,sgl} %1,%0"
3637   [(set_attr "type" "fpalu")
3638    (set_attr "length" "4")])
3639
3640 (define_insn "floatdidf2"
3641   [(set (match_operand:DF 0 "register_operand" "=f")
3642         (float:DF (match_operand:DI 1 "register_operand" "f")))]
3643   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3644   "{fcnvxf,dbl,dbl|fcnv,dw,dbl} %1,%0"
3645   [(set_attr "type" "fpalu")
3646    (set_attr "length" "4")])
3647
3648 ;; Convert a float to an actual integer.
3649 ;; Truncation is performed as part of the conversion.
3650
3651 (define_insn "fix_truncsfsi2"
3652   [(set (match_operand:SI 0 "register_operand" "=f")
3653         (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
3654   "! TARGET_SOFT_FLOAT"
3655   "{fcnvfxt,sgl,sgl|fcnv,t,sgl,w} %1,%0"
3656   [(set_attr "type" "fpalu")
3657    (set_attr "length" "4")])
3658
3659 (define_insn "fix_truncdfsi2"
3660   [(set (match_operand:SI 0 "register_operand" "=f")
3661         (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
3662   "! TARGET_SOFT_FLOAT"
3663   "{fcnvfxt,dbl,sgl|fcnv,t,dbl,w} %1,%0"
3664   [(set_attr "type" "fpalu")
3665    (set_attr "length" "4")])
3666
3667 (define_insn "fix_truncsfdi2"
3668   [(set (match_operand:DI 0 "register_operand" "=f")
3669         (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
3670   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3671   "{fcnvfxt,sgl,dbl|fcnv,t,sgl,dw} %1,%0"
3672   [(set_attr "type" "fpalu")
3673    (set_attr "length" "4")])
3674
3675 (define_insn "fix_truncdfdi2"
3676   [(set (match_operand:DI 0 "register_operand" "=f")
3677         (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
3678   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
3679   "{fcnvfxt,dbl,dbl|fcnv,t,dbl,dw} %1,%0"
3680   [(set_attr "type" "fpalu")
3681    (set_attr "length" "4")])
3682
3683 (define_insn "floatunssidf2_pa20"
3684   [(set (match_operand:DF 0 "register_operand" "=f")
3685         (unsigned_float:DF (match_operand:SI 1 "register_operand" "f")))]
3686   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3687   "fcnv,uw,dbl %1,%0"
3688   [(set_attr "type" "fpalu")
3689    (set_attr "length" "4")])
3690
3691 (define_insn "floatunssisf2_pa20"
3692   [(set (match_operand:SF 0 "register_operand" "=f")
3693         (unsigned_float:SF (match_operand:SI 1 "register_operand" "f")))]
3694   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3695   "fcnv,uw,sgl %1,%0"
3696   [(set_attr "type" "fpalu")
3697    (set_attr "length" "4")])
3698
3699 (define_insn "floatunsdisf2"
3700   [(set (match_operand:SF 0 "register_operand" "=f")
3701         (unsigned_float:SF (match_operand:DI 1 "register_operand" "f")))]
3702   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3703   "fcnv,udw,sgl %1,%0"
3704   [(set_attr "type" "fpalu")
3705    (set_attr "length" "4")])
3706
3707 (define_insn "floatunsdidf2"
3708   [(set (match_operand:DF 0 "register_operand" "=f")
3709         (unsigned_float:DF (match_operand:DI 1 "register_operand" "f")))]
3710   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3711   "fcnv,udw,dbl %1,%0"
3712   [(set_attr "type" "fpalu")
3713    (set_attr "length" "4")])
3714
3715 (define_insn "fixuns_truncsfsi2"
3716   [(set (match_operand:SI 0 "register_operand" "=f")
3717         (unsigned_fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
3718   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3719   "fcnv,t,sgl,uw %1,%0"
3720   [(set_attr "type" "fpalu")
3721    (set_attr "length" "4")])
3722
3723 (define_insn "fixuns_truncdfsi2"
3724   [(set (match_operand:SI 0 "register_operand" "=f")
3725         (unsigned_fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
3726   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3727   "fcnv,t,dbl,uw %1,%0"
3728   [(set_attr "type" "fpalu")
3729    (set_attr "length" "4")])
3730
3731 (define_insn "fixuns_truncsfdi2"
3732   [(set (match_operand:DI 0 "register_operand" "=f")
3733         (unsigned_fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
3734   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3735   "fcnv,t,sgl,udw %1,%0"
3736   [(set_attr "type" "fpalu")
3737    (set_attr "length" "4")])
3738
3739 (define_insn "fixuns_truncdfdi2"
3740   [(set (match_operand:DI 0 "register_operand" "=f")
3741         (unsigned_fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
3742   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
3743   "fcnv,t,dbl,udw %1,%0"
3744   [(set_attr "type" "fpalu")
3745    (set_attr "length" "4")])
3746 \f
3747 ;;- arithmetic instructions
3748
3749 (define_expand "adddi3"
3750   [(set (match_operand:DI 0 "register_operand" "")
3751         (plus:DI (match_operand:DI 1 "register_operand" "")
3752                  (match_operand:DI 2 "arith_operand" "")))]
3753   ""
3754   "")
3755
3756 ;; We allow arith_operand for operands2, even though strictly speaking it
3757 ;; we would prefer to us arith11_operand since that's what the hardware
3758 ;; can actually support.
3759 ;;
3760 ;; But the price of the extra reload in that case is worth the simplicity
3761 ;; we get by allowing a trivial adddi3 expander to be used for both
3762 ;; PA64 and PA32.
3763
3764 (define_insn ""
3765   [(set (match_operand:DI 0 "register_operand" "=r")
3766         (plus:DI (match_operand:DI 1 "register_operand" "%r")
3767                  (match_operand:DI 2 "arith_operand" "rI")))]
3768   "!TARGET_64BIT"
3769   "*
3770 {
3771   if (GET_CODE (operands[2]) == CONST_INT)
3772     {
3773       if (INTVAL (operands[2]) >= 0)
3774         return \"addi %2,%R1,%R0\;{addc|add,c} %1,%%r0,%0\";
3775       else
3776         return \"addi %2,%R1,%R0\;{subb|sub,b} %1,%%r0,%0\";
3777     }
3778   else
3779     return \"add %R2,%R1,%R0\;{addc|add,c} %2,%1,%0\";
3780 }"
3781   [(set_attr "type" "binary")
3782    (set_attr "length" "8")])
3783
3784 (define_insn ""
3785   [(set (match_operand:DI 0 "register_operand" "=r,r")
3786         (plus:DI (match_operand:DI 1 "register_operand" "%r,r")
3787                  (match_operand:DI 2 "arith_operand" "r,J")))]
3788   "TARGET_64BIT"
3789   "@
3790    {addl|add,l} %1,%2,%0
3791    ldo %2(%1),%0"
3792   [(set_attr "type" "binary,binary")
3793    (set_attr "pa_combine_type" "addmove")
3794    (set_attr "length" "4,4")])
3795
3796 (define_insn ""
3797   [(set (match_operand:DI 0 "register_operand" "=r")
3798         (plus:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
3799                  (match_operand:DI 2 "register_operand" "r")))]
3800   "TARGET_64BIT"
3801   "uaddcm %2,%1,%0"
3802   [(set_attr "type" "binary")
3803    (set_attr "length" "4")])
3804
3805 (define_insn ""
3806   [(set (match_operand:SI 0 "register_operand" "=r")
3807         (plus:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
3808                  (match_operand:SI 2 "register_operand" "r")))]
3809   ""
3810   "uaddcm %2,%1,%0"
3811   [(set_attr "type" "binary")
3812    (set_attr "length" "4")])
3813
3814 ;; define_splits to optimize cases of adding a constant integer
3815 ;; to a register when the constant does not fit in 14 bits.  */
3816 (define_split
3817   [(set (match_operand:SI 0 "register_operand" "")
3818         (plus:SI (match_operand:SI 1 "register_operand" "")
3819                  (match_operand:SI 2 "const_int_operand" "")))
3820    (clobber (match_operand:SI 4 "register_operand" ""))]
3821   "! cint_ok_for_move (INTVAL (operands[2]))
3822    && VAL_14_BITS_P (INTVAL (operands[2]) >> 1)"
3823   [(set (match_dup 4) (plus:SI (match_dup 1) (match_dup 2)))
3824    (set (match_dup 0) (plus:SI (match_dup 4) (match_dup 3)))]
3825   "
3826 {
3827   int val = INTVAL (operands[2]);
3828   int low = (val < 0) ? -0x2000 : 0x1fff;
3829   int rest = val - low;
3830
3831   operands[2] = GEN_INT (rest);
3832   operands[3] = GEN_INT (low);
3833 }")
3834
3835 (define_split
3836   [(set (match_operand:SI 0 "register_operand" "")
3837         (plus:SI (match_operand:SI 1 "register_operand" "")
3838                  (match_operand:SI 2 "const_int_operand" "")))
3839    (clobber (match_operand:SI 4 "register_operand" ""))]
3840   "! cint_ok_for_move (INTVAL (operands[2]))"
3841   [(set (match_dup 4) (match_dup 2))
3842    (set (match_dup 0) (plus:SI (mult:SI (match_dup 4) (match_dup 3))
3843                                (match_dup 1)))]
3844   "
3845 {
3846   HOST_WIDE_INT intval = INTVAL (operands[2]);
3847
3848   /* Try dividing the constant by 2, then 4, and finally 8 to see
3849      if we can get a constant which can be loaded into a register
3850      in a single instruction (cint_ok_for_move). 
3851
3852      If that fails, try to negate the constant and subtract it
3853      from our input operand.  */
3854   if (intval % 2 == 0 && cint_ok_for_move (intval / 2))
3855     {
3856       operands[2] = GEN_INT (intval / 2);
3857       operands[3] = GEN_INT (2);
3858     }
3859   else if (intval % 4 == 0 && cint_ok_for_move (intval / 4))
3860     {
3861       operands[2] = GEN_INT (intval / 4);
3862       operands[3] = GEN_INT (4);
3863     }
3864   else if (intval % 8 == 0 && cint_ok_for_move (intval / 8))
3865     {
3866       operands[2] = GEN_INT (intval / 8);
3867       operands[3] = GEN_INT (8);
3868     }
3869   else if (cint_ok_for_move (-intval))
3870     {
3871       emit_insn (gen_rtx_SET (VOIDmode, operands[4], GEN_INT (-intval)));
3872       emit_insn (gen_subsi3 (operands[0], operands[1], operands[4]));
3873       DONE;
3874     }
3875   else
3876     FAIL;
3877 }")
3878
3879 (define_insn "addsi3"
3880   [(set (match_operand:SI 0 "register_operand" "=r,r")
3881         (plus:SI (match_operand:SI 1 "register_operand" "%r,r")
3882                  (match_operand:SI 2 "arith_operand" "r,J")))]
3883   ""
3884   "@
3885    {addl|add,l} %1,%2,%0
3886    ldo %2(%1),%0"
3887   [(set_attr "type" "binary,binary")
3888    (set_attr "pa_combine_type" "addmove")
3889    (set_attr "length" "4,4")])
3890
3891 (define_expand "subdi3"
3892   [(set (match_operand:DI 0 "register_operand" "")
3893         (minus:DI (match_operand:DI 1 "register_operand" "")
3894                   (match_operand:DI 2 "register_operand" "")))]
3895   ""
3896   "")
3897
3898 (define_insn ""
3899   [(set (match_operand:DI 0 "register_operand" "=r")
3900         (minus:DI (match_operand:DI 1 "register_operand" "r")
3901                   (match_operand:DI 2 "register_operand" "r")))]
3902   "!TARGET_64BIT"
3903   "sub %R1,%R2,%R0\;{subb|sub,b} %1,%2,%0"
3904   [(set_attr "type" "binary")
3905   (set_attr "length" "8")])
3906
3907 (define_insn ""
3908   [(set (match_operand:DI 0 "register_operand" "=r,r,q")
3909         (minus:DI (match_operand:DI 1 "arith11_operand" "r,I,U")
3910                   (match_operand:DI 2 "register_operand" "r,r,r")))]
3911   "TARGET_64BIT"
3912   "@
3913    sub %1,%2,%0
3914    subi %1,%2,%0
3915    mtsarcm %2"
3916   [(set_attr "type" "binary,binary,move")
3917   (set_attr "length" "4,4,4")])
3918
3919 (define_expand "subsi3"
3920   [(set (match_operand:SI 0 "register_operand" "")
3921         (minus:SI (match_operand:SI 1 "arith11_operand" "")
3922                   (match_operand:SI 2 "register_operand" "")))]
3923   ""
3924   "")
3925
3926 (define_insn ""
3927   [(set (match_operand:SI 0 "register_operand" "=r,r")
3928         (minus:SI (match_operand:SI 1 "arith11_operand" "r,I")
3929                   (match_operand:SI 2 "register_operand" "r,r")))]
3930   "!TARGET_PA_20"
3931   "@
3932    sub %1,%2,%0
3933    subi %1,%2,%0"
3934   [(set_attr "type" "binary,binary")
3935    (set_attr "length" "4,4")])
3936
3937 (define_insn ""
3938   [(set (match_operand:SI 0 "register_operand" "=r,r,q")
3939         (minus:SI (match_operand:SI 1 "arith11_operand" "r,I,S")
3940                   (match_operand:SI 2 "register_operand" "r,r,r")))]
3941   "TARGET_PA_20"
3942   "@
3943    sub %1,%2,%0
3944    subi %1,%2,%0
3945    mtsarcm %2"
3946   [(set_attr "type" "binary,binary,move")
3947    (set_attr "length" "4,4,4")])
3948
3949 ;; Clobbering a "register_operand" instead of a match_scratch
3950 ;; in operand3 of millicode calls avoids spilling %r1 and
3951 ;; produces better code.
3952
3953 ;; The mulsi3 insns set up registers for the millicode call.
3954 (define_expand "mulsi3"
3955   [(set (reg:SI 26) (match_operand:SI 1 "move_operand" ""))
3956    (set (reg:SI 25) (match_operand:SI 2 "move_operand" ""))
3957    (parallel [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
3958               (clobber (match_dup 3))
3959               (clobber (reg:SI 26))
3960               (clobber (reg:SI 25))
3961               (clobber (match_dup 4))])
3962    (set (match_operand:SI 0 "general_operand" "") (reg:SI 29))]
3963   ""
3964   "
3965 {
3966   operands[4] = gen_rtx_REG (SImode, TARGET_64BIT ? 2 : 31);
3967   if (TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT)
3968     {
3969       rtx scratch = gen_reg_rtx (DImode);
3970       operands[1] = force_reg (SImode, operands[1]);
3971       operands[2] = force_reg (SImode, operands[2]);
3972       emit_insn (gen_umulsidi3 (scratch, operands[1], operands[2]));
3973       emit_insn (gen_rtx_SET (VOIDmode, operands[0],
3974                               gen_rtx_SUBREG (SImode, scratch, GET_MODE_SIZE (SImode))));
3975       DONE;
3976     }
3977   operands[3] = gen_reg_rtx (SImode);
3978 }")
3979
3980 (define_insn "umulsidi3"
3981   [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
3982         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
3983                  (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "f"))))]
3984   "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
3985   "xmpyu %1,%2,%0"
3986   [(set_attr "type" "fpmuldbl")
3987    (set_attr "length" "4")])
3988
3989 (define_insn ""
3990   [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
3991         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
3992                  (match_operand:DI 2 "uint32_operand" "f")))]
3993   "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && !TARGET_64BIT"
3994   "xmpyu %1,%R2,%0"
3995   [(set_attr "type" "fpmuldbl")
3996    (set_attr "length" "4")])
3997
3998 (define_insn ""
3999   [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
4000         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
4001                  (match_operand:DI 2 "uint32_operand" "f")))]
4002   "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && TARGET_64BIT"
4003   "xmpyu %1,%2R,%0"
4004   [(set_attr "type" "fpmuldbl")
4005    (set_attr "length" "4")])
4006
4007 (define_insn ""
4008   [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
4009    (clobber (match_operand:SI 0 "register_operand" "=a"))
4010    (clobber (reg:SI 26))
4011    (clobber (reg:SI 25))
4012    (clobber (reg:SI 31))]
4013   "!TARGET_64BIT"
4014   "* return output_mul_insn (0, insn);"
4015   [(set_attr "type" "milli")
4016    (set (attr "length")
4017      (cond [
4018 ;; Target (or stub) within reach
4019             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
4020                      (const_int 240000))
4021                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
4022                      (const_int 0)))
4023             (const_int 4)
4024
4025 ;; Out of reach PIC
4026             (ne (symbol_ref "flag_pic")
4027                 (const_int 0))
4028             (const_int 24)
4029
4030 ;; Out of reach PORTABLE_RUNTIME
4031             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
4032                 (const_int 0))
4033             (const_int 20)]
4034
4035 ;; Out of reach, can use ble
4036           (const_int 12)))])
4037
4038 (define_insn ""
4039   [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
4040    (clobber (match_operand:SI 0 "register_operand" "=a"))
4041    (clobber (reg:SI 26))
4042    (clobber (reg:SI 25))
4043    (clobber (reg:SI 2))]
4044   "TARGET_64BIT"
4045   "* return output_mul_insn (0, insn);"
4046   [(set_attr "type" "milli")
4047    (set (attr "length") (const_int 4))])
4048
4049 (define_expand "muldi3"
4050   [(set (match_operand:DI 0 "register_operand" "")
4051         (mult:DI (match_operand:DI 1 "register_operand" "")
4052                  (match_operand:DI 2 "register_operand" "")))]
4053   "TARGET_64BIT && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
4054   "
4055 {
4056   rtx low_product = gen_reg_rtx (DImode);
4057   rtx cross_product1 = gen_reg_rtx (DImode);
4058   rtx cross_product2 = gen_reg_rtx (DImode);
4059   rtx cross_scratch = gen_reg_rtx (DImode);
4060   rtx cross_product = gen_reg_rtx (DImode);
4061   rtx op1l, op1r, op2l, op2r;
4062   rtx op1shifted, op2shifted;
4063
4064   op1shifted = gen_reg_rtx (DImode);
4065   op2shifted = gen_reg_rtx (DImode);
4066   op1l = gen_reg_rtx (SImode);
4067   op1r = gen_reg_rtx (SImode);
4068   op2l = gen_reg_rtx (SImode);
4069   op2r = gen_reg_rtx (SImode);
4070
4071   emit_move_insn (op1shifted, gen_rtx_LSHIFTRT (DImode, operands[1],
4072                                                 GEN_INT (32)));
4073   emit_move_insn (op2shifted, gen_rtx_LSHIFTRT (DImode, operands[2],
4074                                                 GEN_INT (32)));
4075   op1r = gen_rtx_SUBREG (SImode, operands[1], 4);
4076   op2r = gen_rtx_SUBREG (SImode, operands[2], 4);
4077   op1l = gen_rtx_SUBREG (SImode, op1shifted, 4);
4078   op2l = gen_rtx_SUBREG (SImode, op2shifted, 4);
4079
4080   /* Emit multiplies for the cross products.  */
4081   emit_insn (gen_umulsidi3 (cross_product1, op2r, op1l));
4082   emit_insn (gen_umulsidi3 (cross_product2, op2l, op1r));
4083
4084   /* Emit a multiply for the low sub-word.  */
4085   emit_insn (gen_umulsidi3 (low_product, op2r, op1r));
4086
4087   /* Sum the cross products and shift them into proper position.  */
4088   emit_insn (gen_adddi3 (cross_scratch, cross_product1, cross_product2));
4089   emit_insn (gen_ashldi3 (cross_product, cross_scratch, GEN_INT (32)));
4090
4091   /* Add the cross product to the low product and store the result
4092      into the output operand .  */
4093   emit_insn (gen_adddi3 (operands[0], cross_product, low_product));
4094   DONE;
4095 }")
4096
4097 ;;; Division and mod.
4098 (define_expand "divsi3"
4099   [(set (reg:SI 26) (match_operand:SI 1 "move_operand" ""))
4100    (set (reg:SI 25) (match_operand:SI 2 "move_operand" ""))
4101    (parallel [(set (reg:SI 29) (div:SI (reg:SI 26) (reg:SI 25)))
4102               (clobber (match_dup 3))
4103               (clobber (match_dup 4))
4104               (clobber (reg:SI 26))
4105               (clobber (reg:SI 25))
4106               (clobber (match_dup 5))])
4107    (set (match_operand:SI 0 "general_operand" "") (reg:SI 29))]
4108   ""
4109   "
4110 {
4111   operands[3] = gen_reg_rtx (SImode);
4112   if (TARGET_64BIT)
4113     {
4114       operands[5] = gen_rtx_REG (SImode, 2);
4115       operands[4] = operands[5];
4116     }
4117   else
4118     {
4119       operands[5] = gen_rtx_REG (SImode, 31);
4120       operands[4] = gen_reg_rtx (SImode);
4121     }
4122   if (GET_CODE (operands[2]) == CONST_INT && emit_hpdiv_const (operands, 0))
4123     DONE;
4124 }")
4125
4126 (define_insn ""
4127   [(set (reg:SI 29)
4128         (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
4129    (clobber (match_operand:SI 1 "register_operand" "=a"))
4130    (clobber (match_operand:SI 2 "register_operand" "=&r"))
4131    (clobber (reg:SI 26))
4132    (clobber (reg:SI 25))
4133    (clobber (reg:SI 31))]
4134   "!TARGET_64BIT"
4135   "*
4136    return output_div_insn (operands, 0, insn);"
4137   [(set_attr "type" "milli")
4138    (set (attr "length")
4139      (cond [
4140 ;; Target (or stub) within reach
4141             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
4142                      (const_int 240000))
4143                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
4144                      (const_int 0)))
4145             (const_int 4)
4146
4147 ;; Out of reach PIC
4148             (ne (symbol_ref "flag_pic")
4149                 (const_int 0))
4150             (const_int 24)
4151
4152 ;; Out of reach PORTABLE_RUNTIME
4153             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
4154                 (const_int 0))
4155             (const_int 20)]
4156
4157 ;; Out of reach, can use ble
4158           (const_int 12)))])
4159
4160 (define_insn ""
4161   [(set (reg:SI 29)
4162         (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
4163    (clobber (match_operand:SI 1 "register_operand" "=a"))
4164    (clobber (match_operand:SI 2 "register_operand" "=&r"))
4165    (clobber (reg:SI 26))
4166    (clobber (reg:SI 25))
4167    (clobber (reg:SI 2))]
4168   "TARGET_64BIT"
4169   "*
4170    return output_div_insn (operands, 0, insn);"
4171   [(set_attr "type" "milli")
4172    (set (attr "length") (const_int 4))])
4173
4174 (define_expand "udivsi3"
4175   [(set (reg:SI 26) (match_operand:SI 1 "move_operand" ""))
4176    (set (reg:SI 25) (match_operand:SI 2 "move_operand" ""))
4177    (parallel [(set (reg:SI 29) (udiv:SI (reg:SI 26) (reg:SI 25)))
4178               (clobber (match_dup 3))
4179               (clobber (match_dup 4))
4180               (clobber (reg:SI 26))
4181               (clobber (reg:SI 25))
4182               (clobber (match_dup 5))])
4183    (set (match_operand:SI 0 "general_operand" "") (reg:SI 29))]
4184   ""
4185   "
4186 {
4187   operands[3] = gen_reg_rtx (SImode);
4188   if (TARGET_64BIT)
4189     {
4190       operands[5] = gen_rtx_REG (SImode, 2);
4191       operands[4] = operands[5];
4192     }
4193   else
4194     {
4195       operands[5] = gen_rtx_REG (SImode, 31);
4196       operands[4] = gen_reg_rtx (SImode);
4197     }
4198   if (GET_CODE (operands[2]) == CONST_INT && emit_hpdiv_const (operands, 1))
4199     DONE;
4200 }")
4201
4202 (define_insn ""
4203   [(set (reg:SI 29)
4204         (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
4205    (clobber (match_operand:SI 1 "register_operand" "=a"))
4206    (clobber (match_operand:SI 2 "register_operand" "=&r"))
4207    (clobber (reg:SI 26))
4208    (clobber (reg:SI 25))
4209    (clobber (reg:SI 31))]
4210   "!TARGET_64BIT"
4211   "*
4212    return output_div_insn (operands, 1, insn);"
4213   [(set_attr "type" "milli")
4214    (set (attr "length")
4215      (cond [
4216 ;; Target (or stub) within reach
4217             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
4218                      (const_int 240000))
4219                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
4220                      (const_int 0)))
4221             (const_int 4)
4222
4223 ;; Out of reach PIC
4224             (ne (symbol_ref "flag_pic")
4225                 (const_int 0))
4226             (const_int 24)
4227
4228 ;; Out of reach PORTABLE_RUNTIME
4229             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
4230                 (const_int 0))
4231             (const_int 20)]
4232
4233 ;; Out of reach, can use ble
4234           (const_int 12)))])
4235
4236 (define_insn ""
4237   [(set (reg:SI 29)
4238         (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
4239    (clobber (match_operand:SI 1 "register_operand" "=a"))
4240    (clobber (match_operand:SI 2 "register_operand" "=&r"))
4241    (clobber (reg:SI 26))
4242    (clobber (reg:SI 25))
4243    (clobber (reg:SI 2))]
4244   "TARGET_64BIT"
4245   "*
4246    return output_div_insn (operands, 1, insn);"
4247   [(set_attr "type" "milli")
4248    (set (attr "length") (const_int 4))])
4249
4250 (define_expand "modsi3"
4251   [(set (reg:SI 26) (match_operand:SI 1 "move_operand" ""))
4252    (set (reg:SI 25) (match_operand:SI 2 "move_operand" ""))
4253    (parallel [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
4254               (clobber (match_dup 3))
4255               (clobber (match_dup 4))
4256               (clobber (reg:SI 26))
4257               (clobber (reg:SI 25))
4258               (clobber (match_dup 5))])
4259    (set (match_operand:SI 0 "general_operand" "") (reg:SI 29))]
4260   ""
4261   "
4262 {
4263   if (TARGET_64BIT)
4264     {
4265       operands[5] = gen_rtx_REG (SImode, 2);
4266       operands[4] = operands[5];
4267     }
4268   else
4269     {
4270       operands[5] = gen_rtx_REG (SImode, 31);
4271       operands[4] = gen_reg_rtx (SImode);
4272     }
4273   operands[3] = gen_reg_rtx (SImode);
4274 }")
4275
4276 (define_insn ""
4277   [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
4278    (clobber (match_operand:SI 0 "register_operand" "=a"))
4279    (clobber (match_operand:SI 1 "register_operand" "=&r"))
4280    (clobber (reg:SI 26))
4281    (clobber (reg:SI 25))
4282    (clobber (reg:SI 31))]
4283   "!TARGET_64BIT"
4284   "*
4285   return output_mod_insn (0, insn);"
4286   [(set_attr "type" "milli")
4287    (set (attr "length")
4288      (cond [
4289 ;; Target (or stub) within reach
4290             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
4291                      (const_int 240000))
4292                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
4293                      (const_int 0)))
4294             (const_int 4)
4295
4296 ;; Out of reach PIC
4297             (ne (symbol_ref "flag_pic")
4298                 (const_int 0))
4299             (const_int 24)
4300
4301 ;; Out of reach PORTABLE_RUNTIME
4302             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
4303                 (const_int 0))
4304             (const_int 20)]
4305
4306 ;; Out of reach, can use ble
4307           (const_int 12)))])
4308
4309 (define_insn ""
4310   [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
4311    (clobber (match_operand:SI 0 "register_operand" "=a"))
4312    (clobber (match_operand:SI 1 "register_operand" "=&r"))
4313    (clobber (reg:SI 26))
4314    (clobber (reg:SI 25))
4315    (clobber (reg:SI 2))]
4316   "TARGET_64BIT"
4317   "*
4318   return output_mod_insn (0, insn);"
4319   [(set_attr "type" "milli")
4320    (set (attr "length") (const_int 4))])
4321
4322 (define_expand "umodsi3"
4323   [(set (reg:SI 26) (match_operand:SI 1 "move_operand" ""))
4324    (set (reg:SI 25) (match_operand:SI 2 "move_operand" ""))
4325    (parallel [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
4326               (clobber (match_dup 3))
4327               (clobber (match_dup 4))
4328               (clobber (reg:SI 26))
4329               (clobber (reg:SI 25))
4330               (clobber (match_dup 5))])
4331    (set (match_operand:SI 0 "general_operand" "") (reg:SI 29))]
4332   ""
4333   "
4334 {
4335   if (TARGET_64BIT)
4336     {
4337       operands[5] = gen_rtx_REG (SImode, 2);
4338       operands[4] = operands[5];
4339     }
4340   else
4341     {
4342       operands[5] = gen_rtx_REG (SImode, 31);
4343       operands[4] = gen_reg_rtx (SImode);
4344     }
4345   operands[3] = gen_reg_rtx (SImode);
4346 }")
4347
4348 (define_insn ""
4349   [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
4350    (clobber (match_operand:SI 0 "register_operand" "=a"))
4351    (clobber (match_operand:SI 1 "register_operand" "=&r"))
4352    (clobber (reg:SI 26))
4353    (clobber (reg:SI 25))
4354    (clobber (reg:SI 31))]
4355   "!TARGET_64BIT"
4356   "*
4357   return output_mod_insn (1, insn);"
4358   [(set_attr "type" "milli")
4359    (set (attr "length")
4360      (cond [
4361 ;; Target (or stub) within reach
4362             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
4363                      (const_int 240000))
4364                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
4365                      (const_int 0)))
4366             (const_int 4)
4367
4368 ;; Out of reach PIC
4369             (ne (symbol_ref "flag_pic")
4370                 (const_int 0))
4371             (const_int 24)
4372
4373 ;; Out of reach PORTABLE_RUNTIME
4374             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
4375                 (const_int 0))
4376             (const_int 20)]
4377
4378 ;; Out of reach, can use ble
4379           (const_int 12)))])
4380
4381 (define_insn ""
4382   [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
4383    (clobber (match_operand:SI 0 "register_operand" "=a"))
4384    (clobber (match_operand:SI 1 "register_operand" "=&r"))
4385    (clobber (reg:SI 26))
4386    (clobber (reg:SI 25))
4387    (clobber (reg:SI 2))]
4388   "TARGET_64BIT"
4389   "*
4390   return output_mod_insn (1, insn);"
4391   [(set_attr "type" "milli")
4392    (set (attr "length") (const_int 4))])
4393
4394 ;;- and instructions
4395 ;; We define DImode `and` so with DImode `not` we can get
4396 ;; DImode `andn`.  Other combinations are possible.
4397
4398 (define_expand "anddi3"
4399   [(set (match_operand:DI 0 "register_operand" "")
4400         (and:DI (match_operand:DI 1 "arith_double_operand" "")
4401                 (match_operand:DI 2 "arith_double_operand" "")))]
4402   ""
4403   "
4404 {
4405   if (! register_operand (operands[1], DImode)
4406       || ! register_operand (operands[2], DImode))
4407     /* Let GCC break this into word-at-a-time operations.  */
4408     FAIL;
4409 }")
4410
4411 (define_insn ""
4412   [(set (match_operand:DI 0 "register_operand" "=r")
4413         (and:DI (match_operand:DI 1 "register_operand" "%r")
4414                 (match_operand:DI 2 "register_operand" "r")))]
4415   "!TARGET_64BIT"
4416   "and %1,%2,%0\;and %R1,%R2,%R0"
4417   [(set_attr "type" "binary")
4418    (set_attr "length" "8")])
4419
4420 (define_insn ""
4421   [(set (match_operand:DI 0 "register_operand" "=r,r")
4422         (and:DI (match_operand:DI 1 "register_operand" "%?r,0")
4423                 (match_operand:DI 2 "and_operand" "rO,P")))]
4424   "TARGET_64BIT"
4425   "* return output_64bit_and (operands); "
4426   [(set_attr "type" "binary")
4427    (set_attr "length" "4")])
4428
4429 ; The ? for op1 makes reload prefer zdepi instead of loading a huge
4430 ; constant with ldil;ldo.
4431 (define_insn "andsi3"
4432   [(set (match_operand:SI 0 "register_operand" "=r,r")
4433         (and:SI (match_operand:SI 1 "register_operand" "%?r,0")
4434                 (match_operand:SI 2 "and_operand" "rO,P")))]
4435   ""
4436   "* return output_and (operands); "
4437   [(set_attr "type" "binary,shift")
4438    (set_attr "length" "4,4")])
4439
4440 (define_insn ""
4441   [(set (match_operand:DI 0 "register_operand" "=r")
4442         (and:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
4443                 (match_operand:DI 2 "register_operand" "r")))]
4444   "!TARGET_64BIT"
4445   "andcm %2,%1,%0\;andcm %R2,%R1,%R0"
4446   [(set_attr "type" "binary")
4447    (set_attr "length" "8")])
4448
4449 (define_insn ""
4450   [(set (match_operand:DI 0 "register_operand" "=r")
4451         (and:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
4452                 (match_operand:DI 2 "register_operand" "r")))]
4453   "TARGET_64BIT"
4454   "andcm %2,%1,%0"
4455   [(set_attr "type" "binary")
4456    (set_attr "length" "4")])
4457
4458 (define_insn ""
4459   [(set (match_operand:SI 0 "register_operand" "=r")
4460         (and:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
4461                 (match_operand:SI 2 "register_operand" "r")))]
4462   ""
4463   "andcm %2,%1,%0"
4464   [(set_attr "type" "binary")
4465   (set_attr "length" "4")])
4466
4467 (define_expand "iordi3"
4468   [(set (match_operand:DI 0 "register_operand" "")
4469         (ior:DI (match_operand:DI 1 "arith_double_operand" "")
4470                 (match_operand:DI 2 "arith_double_operand" "")))]
4471   ""
4472   "
4473 {
4474   if (! register_operand (operands[1], DImode)
4475       || ! register_operand (operands[2], DImode))
4476     /* Let GCC break this into word-at-a-time operations.  */
4477     FAIL;
4478 }")
4479
4480 (define_insn ""
4481   [(set (match_operand:DI 0 "register_operand" "=r")
4482         (ior:DI (match_operand:DI 1 "register_operand" "%r")
4483                 (match_operand:DI 2 "register_operand" "r")))]
4484   "!TARGET_64BIT"
4485   "or %1,%2,%0\;or %R1,%R2,%R0"
4486   [(set_attr "type" "binary")
4487    (set_attr "length" "8")])
4488
4489 (define_insn ""
4490   [(set (match_operand:DI 0 "register_operand" "=r,r")
4491         (ior:DI (match_operand:DI 1 "register_operand" "0,0")
4492                 (match_operand:DI 2 "ior_operand" "M,i")))]
4493   "TARGET_64BIT"
4494   "* return output_64bit_ior (operands); "
4495   [(set_attr "type" "binary,shift")
4496    (set_attr "length" "4,4")])
4497
4498 (define_insn ""
4499   [(set (match_operand:DI 0 "register_operand" "=r")
4500         (ior:DI (match_operand:DI 1 "register_operand" "%r")
4501                 (match_operand:DI 2 "register_operand" "r")))]
4502   "TARGET_64BIT"
4503   "or %1,%2,%0"
4504   [(set_attr "type" "binary")
4505    (set_attr "length" "4")])
4506
4507 ;; Need a define_expand because we've run out of CONST_OK... characters.
4508 (define_expand "iorsi3"
4509   [(set (match_operand:SI 0 "register_operand" "")
4510         (ior:SI (match_operand:SI 1 "register_operand" "")
4511                 (match_operand:SI 2 "arith32_operand" "")))]
4512   ""
4513   "
4514 {
4515   if (! (ior_operand (operands[2], SImode)
4516          || register_operand (operands[2], SImode)))
4517     operands[2] = force_reg (SImode, operands[2]);
4518 }")
4519
4520 (define_insn ""
4521   [(set (match_operand:SI 0 "register_operand" "=r,r")
4522         (ior:SI (match_operand:SI 1 "register_operand" "0,0")
4523                 (match_operand:SI 2 "ior_operand" "M,i")))]
4524   ""
4525   "* return output_ior (operands); "
4526   [(set_attr "type" "binary,shift")
4527    (set_attr "length" "4,4")])
4528
4529 (define_insn ""
4530   [(set (match_operand:SI 0 "register_operand" "=r")
4531         (ior:SI (match_operand:SI 1 "register_operand" "%r")
4532                 (match_operand:SI 2 "register_operand" "r")))]
4533   ""
4534   "or %1,%2,%0"
4535   [(set_attr "type" "binary")
4536    (set_attr "length" "4")])
4537
4538 (define_expand "xordi3"
4539   [(set (match_operand:DI 0 "register_operand" "")
4540         (xor:DI (match_operand:DI 1 "arith_double_operand" "")
4541                 (match_operand:DI 2 "arith_double_operand" "")))]
4542   ""
4543   "
4544 {
4545   if (! register_operand (operands[1], DImode)
4546       || ! register_operand (operands[2], DImode))
4547     /* Let GCC break this into word-at-a-time operations.  */
4548     FAIL;
4549 }")
4550
4551 (define_insn ""
4552   [(set (match_operand:DI 0 "register_operand" "=r")
4553         (xor:DI (match_operand:DI 1 "register_operand" "%r")
4554                 (match_operand:DI 2 "register_operand" "r")))]
4555   "!TARGET_64BIT"
4556   "xor %1,%2,%0\;xor %R1,%R2,%R0"
4557   [(set_attr "type" "binary")
4558    (set_attr "length" "8")])
4559
4560 (define_insn ""
4561   [(set (match_operand:DI 0 "register_operand" "=r")
4562         (xor:DI (match_operand:DI 1 "register_operand" "%r")
4563                 (match_operand:DI 2 "register_operand" "r")))]
4564   "TARGET_64BIT"
4565   "xor %1,%2,%0"
4566   [(set_attr "type" "binary")
4567    (set_attr "length" "4")])
4568
4569 (define_insn "xorsi3"
4570   [(set (match_operand:SI 0 "register_operand" "=r")
4571         (xor:SI (match_operand:SI 1 "register_operand" "%r")
4572                 (match_operand:SI 2 "register_operand" "r")))]
4573   ""
4574   "xor %1,%2,%0"
4575   [(set_attr "type" "binary")
4576    (set_attr "length" "4")])
4577
4578 (define_expand "negdi2"
4579   [(set (match_operand:DI 0 "register_operand" "")
4580         (neg:DI (match_operand:DI 1 "register_operand" "")))]
4581   ""
4582   "")
4583
4584 (define_insn ""
4585   [(set (match_operand:DI 0 "register_operand" "=r")
4586         (neg:DI (match_operand:DI 1 "register_operand" "r")))]
4587   "!TARGET_64BIT"
4588   "sub %%r0,%R1,%R0\;{subb|sub,b} %%r0,%1,%0"
4589   [(set_attr "type" "unary")
4590    (set_attr "length" "8")])
4591
4592 (define_insn ""
4593   [(set (match_operand:DI 0 "register_operand" "=r")
4594         (neg:DI (match_operand:DI 1 "register_operand" "r")))]
4595   "TARGET_64BIT"
4596   "sub %%r0,%1,%0"
4597   [(set_attr "type" "unary")
4598    (set_attr "length" "4")])
4599
4600 (define_insn "negsi2"
4601   [(set (match_operand:SI 0 "register_operand" "=r")
4602         (neg:SI (match_operand:SI 1 "register_operand" "r")))]
4603   ""
4604   "sub %%r0,%1,%0"
4605   [(set_attr "type" "unary")
4606    (set_attr "length" "4")])
4607
4608 (define_expand "one_cmpldi2"
4609   [(set (match_operand:DI 0 "register_operand" "")
4610         (not:DI (match_operand:DI 1 "arith_double_operand" "")))]
4611   ""
4612   "
4613 {
4614   if (! register_operand (operands[1], DImode))
4615     FAIL;
4616 }")
4617
4618 (define_insn ""
4619   [(set (match_operand:DI 0 "register_operand" "=r")
4620         (not:DI (match_operand:DI 1 "register_operand" "r")))]
4621   "!TARGET_64BIT"
4622   "uaddcm %%r0,%1,%0\;uaddcm %%r0,%R1,%R0"
4623   [(set_attr "type" "unary")
4624    (set_attr "length" "8")])
4625
4626 (define_insn ""
4627   [(set (match_operand:DI 0 "register_operand" "=r")
4628         (not:DI (match_operand:DI 1 "register_operand" "r")))]
4629   "TARGET_64BIT"
4630   "uaddcm %%r0,%1,%0"
4631   [(set_attr "type" "unary")
4632    (set_attr "length" "4")])
4633
4634 (define_insn "one_cmplsi2"
4635   [(set (match_operand:SI 0 "register_operand" "=r")
4636         (not:SI (match_operand:SI 1 "register_operand" "r")))]
4637   ""
4638   "uaddcm %%r0,%1,%0"
4639   [(set_attr "type" "unary")
4640    (set_attr "length" "4")])
4641 \f
4642 ;; Floating point arithmetic instructions.
4643
4644 (define_insn "adddf3"
4645   [(set (match_operand:DF 0 "register_operand" "=f")
4646         (plus:DF (match_operand:DF 1 "register_operand" "f")
4647                  (match_operand:DF 2 "register_operand" "f")))]
4648   "! TARGET_SOFT_FLOAT"
4649   "fadd,dbl %1,%2,%0"
4650   [(set_attr "type" "fpalu")
4651    (set_attr "pa_combine_type" "faddsub")
4652    (set_attr "length" "4")])
4653
4654 (define_insn "addsf3"
4655   [(set (match_operand:SF 0 "register_operand" "=f")
4656         (plus:SF (match_operand:SF 1 "register_operand" "f")
4657                  (match_operand:SF 2 "register_operand" "f")))]
4658   "! TARGET_SOFT_FLOAT"
4659   "fadd,sgl %1,%2,%0"
4660   [(set_attr "type" "fpalu")
4661    (set_attr "pa_combine_type" "faddsub")
4662    (set_attr "length" "4")])
4663
4664 (define_insn "subdf3"
4665   [(set (match_operand:DF 0 "register_operand" "=f")
4666         (minus:DF (match_operand:DF 1 "register_operand" "f")
4667                   (match_operand:DF 2 "register_operand" "f")))]
4668   "! TARGET_SOFT_FLOAT"
4669   "fsub,dbl %1,%2,%0"
4670   [(set_attr "type" "fpalu")
4671    (set_attr "pa_combine_type" "faddsub")
4672    (set_attr "length" "4")])
4673
4674 (define_insn "subsf3"
4675   [(set (match_operand:SF 0 "register_operand" "=f")
4676         (minus:SF (match_operand:SF 1 "register_operand" "f")
4677                   (match_operand:SF 2 "register_operand" "f")))]
4678   "! TARGET_SOFT_FLOAT"
4679   "fsub,sgl %1,%2,%0"
4680   [(set_attr "type" "fpalu")
4681    (set_attr "pa_combine_type" "faddsub")
4682    (set_attr "length" "4")])
4683
4684 (define_insn "muldf3"
4685   [(set (match_operand:DF 0 "register_operand" "=f")
4686         (mult:DF (match_operand:DF 1 "register_operand" "f")
4687                  (match_operand:DF 2 "register_operand" "f")))]
4688   "! TARGET_SOFT_FLOAT"
4689   "fmpy,dbl %1,%2,%0"
4690   [(set_attr "type" "fpmuldbl")
4691    (set_attr "pa_combine_type" "fmpy")
4692    (set_attr "length" "4")])
4693
4694 (define_insn "mulsf3"
4695   [(set (match_operand:SF 0 "register_operand" "=f")
4696         (mult:SF (match_operand:SF 1 "register_operand" "f")
4697                  (match_operand:SF 2 "register_operand" "f")))]
4698   "! TARGET_SOFT_FLOAT"
4699   "fmpy,sgl %1,%2,%0"
4700   [(set_attr "type" "fpmulsgl")
4701    (set_attr "pa_combine_type" "fmpy")
4702    (set_attr "length" "4")])
4703
4704 (define_insn "divdf3"
4705   [(set (match_operand:DF 0 "register_operand" "=f")
4706         (div:DF (match_operand:DF 1 "register_operand" "f")
4707                 (match_operand:DF 2 "register_operand" "f")))]
4708   "! TARGET_SOFT_FLOAT"
4709   "fdiv,dbl %1,%2,%0"
4710   [(set_attr "type" "fpdivdbl")
4711    (set_attr "length" "4")])
4712
4713 (define_insn "divsf3"
4714   [(set (match_operand:SF 0 "register_operand" "=f")
4715         (div:SF (match_operand:SF 1 "register_operand" "f")
4716                 (match_operand:SF 2 "register_operand" "f")))]
4717   "! TARGET_SOFT_FLOAT"
4718   "fdiv,sgl %1,%2,%0"
4719   [(set_attr "type" "fpdivsgl")
4720    (set_attr "length" "4")])
4721
4722 ;; Processors prior to PA 2.0 don't have a fneg instruction.  Fast
4723 ;; negation can be done by subtracting from plus zero.  However, this
4724 ;; violates the IEEE standard when negating plus and minus zero.
4725 (define_expand "negdf2"
4726   [(parallel [(set (match_operand:DF 0 "register_operand" "")
4727                    (neg:DF (match_operand:DF 1 "register_operand" "")))
4728               (use (match_dup 2))])]
4729   "! TARGET_SOFT_FLOAT"
4730 {
4731   if (TARGET_PA_20 || flag_unsafe_math_optimizations)
4732     emit_insn (gen_negdf2_fast (operands[0], operands[1]));
4733   else
4734     {
4735       operands[2] = force_reg (DFmode, immed_real_const_1 (dconstm1, DFmode));
4736       emit_insn (gen_muldf3 (operands[0], operands[1], operands[2]));
4737     }
4738   DONE;
4739 })
4740
4741 (define_insn "negdf2_fast"
4742   [(set (match_operand:DF 0 "register_operand" "=f")
4743         (neg:DF (match_operand:DF 1 "register_operand" "f")))]
4744   "! TARGET_SOFT_FLOAT && (TARGET_PA_20 || flag_unsafe_math_optimizations)"
4745   "*
4746 {
4747   if (TARGET_PA_20)
4748     return \"fneg,dbl %1,%0\";
4749   else
4750     return \"fsub,dbl %%fr0,%1,%0\";
4751 }"
4752   [(set_attr "type" "fpalu")
4753    (set_attr "length" "4")])
4754
4755 (define_expand "negsf2"
4756   [(parallel [(set (match_operand:SF 0 "register_operand" "")
4757                    (neg:SF (match_operand:SF 1 "register_operand" "")))
4758               (use (match_dup 2))])]
4759   "! TARGET_SOFT_FLOAT"
4760 {
4761   if (TARGET_PA_20 || flag_unsafe_math_optimizations)
4762     emit_insn (gen_negsf2_fast (operands[0], operands[1]));
4763   else
4764     {
4765       operands[2] = force_reg (SFmode, immed_real_const_1 (dconstm1, SFmode));
4766       emit_insn (gen_mulsf3 (operands[0], operands[1], operands[2]));
4767     }
4768   DONE;
4769 })
4770
4771 (define_insn "negsf2_fast"
4772   [(set (match_operand:SF 0 "register_operand" "=f")
4773         (neg:SF (match_operand:SF 1 "register_operand" "f")))]
4774   "! TARGET_SOFT_FLOAT && (TARGET_PA_20 || flag_unsafe_math_optimizations)"
4775   "*
4776 {
4777   if (TARGET_PA_20)
4778     return \"fneg,sgl %1,%0\";
4779   else
4780     return \"fsub,sgl %%fr0,%1,%0\";
4781 }"
4782   [(set_attr "type" "fpalu")
4783    (set_attr "length" "4")])
4784
4785 (define_insn "absdf2"
4786   [(set (match_operand:DF 0 "register_operand" "=f")
4787         (abs:DF (match_operand:DF 1 "register_operand" "f")))]
4788   "! TARGET_SOFT_FLOAT"
4789   "fabs,dbl %1,%0"
4790   [(set_attr "type" "fpalu")
4791    (set_attr "length" "4")])
4792
4793 (define_insn "abssf2"
4794   [(set (match_operand:SF 0 "register_operand" "=f")
4795         (abs:SF (match_operand:SF 1 "register_operand" "f")))]
4796   "! TARGET_SOFT_FLOAT"
4797   "fabs,sgl %1,%0"
4798   [(set_attr "type" "fpalu")
4799    (set_attr "length" "4")])
4800
4801 (define_insn "sqrtdf2"
4802   [(set (match_operand:DF 0 "register_operand" "=f")
4803         (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
4804   "! TARGET_SOFT_FLOAT"
4805   "fsqrt,dbl %1,%0"
4806   [(set_attr "type" "fpsqrtdbl")
4807    (set_attr "length" "4")])
4808
4809 (define_insn "sqrtsf2"
4810   [(set (match_operand:SF 0 "register_operand" "=f")
4811         (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
4812   "! TARGET_SOFT_FLOAT"
4813   "fsqrt,sgl %1,%0"
4814   [(set_attr "type" "fpsqrtsgl")
4815    (set_attr "length" "4")])
4816
4817 ;; PA 2.0 floating point instructions
4818
4819 ; fmpyfadd patterns
4820 (define_insn ""
4821   [(set (match_operand:DF 0 "register_operand" "=f")
4822         (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
4823                           (match_operand:DF 2 "register_operand" "f"))
4824                  (match_operand:DF 3 "register_operand" "f")))]
4825   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4826   "fmpyfadd,dbl %1,%2,%3,%0"
4827   [(set_attr "type" "fpmuldbl")
4828    (set_attr "length" "4")])
4829
4830 (define_insn ""
4831   [(set (match_operand:DF 0 "register_operand" "=f")
4832         (plus:DF (match_operand:DF 1 "register_operand" "f")
4833                  (mult:DF (match_operand:DF 2 "register_operand" "f")
4834                           (match_operand:DF 3 "register_operand" "f"))))]
4835   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4836   "fmpyfadd,dbl %2,%3,%1,%0"
4837   [(set_attr "type" "fpmuldbl")
4838    (set_attr "length" "4")])
4839
4840 (define_insn ""
4841   [(set (match_operand:SF 0 "register_operand" "=f")
4842         (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
4843                           (match_operand:SF 2 "register_operand" "f"))
4844                  (match_operand:SF 3 "register_operand" "f")))]
4845   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4846   "fmpyfadd,sgl %1,%2,%3,%0"
4847   [(set_attr "type" "fpmulsgl")
4848    (set_attr "length" "4")])
4849
4850 (define_insn ""
4851   [(set (match_operand:SF 0 "register_operand" "=f")
4852         (plus:SF (match_operand:SF 1 "register_operand" "f")
4853                  (mult:SF (match_operand:SF 2 "register_operand" "f")
4854                           (match_operand:SF 3 "register_operand" "f"))))]
4855   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4856   "fmpyfadd,sgl %2,%3,%1,%0"
4857   [(set_attr "type" "fpmulsgl")
4858    (set_attr "length" "4")])
4859
4860 ; fmpynfadd patterns
4861 (define_insn ""
4862   [(set (match_operand:DF 0 "register_operand" "=f")
4863         (minus:DF (match_operand:DF 1 "register_operand" "f")
4864                   (mult:DF (match_operand:DF 2 "register_operand" "f")
4865                            (match_operand:DF 3 "register_operand" "f"))))]
4866   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4867   "fmpynfadd,dbl %2,%3,%1,%0"
4868   [(set_attr "type" "fpmuldbl")
4869    (set_attr "length" "4")])
4870
4871 (define_insn ""
4872   [(set (match_operand:SF 0 "register_operand" "=f")
4873         (minus:SF (match_operand:SF 1 "register_operand" "f")
4874                   (mult:SF (match_operand:SF 2 "register_operand" "f")
4875                            (match_operand:SF 3 "register_operand" "f"))))]
4876   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4877   "fmpynfadd,sgl %2,%3,%1,%0"
4878   [(set_attr "type" "fpmulsgl")
4879    (set_attr "length" "4")])
4880
4881 ; fnegabs patterns
4882 (define_insn ""
4883   [(set (match_operand:DF 0 "register_operand" "=f")
4884         (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))]
4885   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4886   "fnegabs,dbl %1,%0"
4887   [(set_attr "type" "fpalu")
4888    (set_attr "length" "4")])
4889
4890 (define_insn ""
4891   [(set (match_operand:SF 0 "register_operand" "=f")
4892         (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))]
4893   "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
4894   "fnegabs,sgl %1,%0"
4895   [(set_attr "type" "fpalu")
4896    (set_attr "length" "4")])
4897
4898 ;; Generating a fused multiply sequence is a win for this case as it will
4899 ;; reduce the latency for the fused case without impacting the plain
4900 ;; multiply case.
4901 ;;
4902 ;; Similar possibilities exist for fnegabs, shadd and other insns which
4903 ;; perform two operations with the result of the first feeding the second.
4904 (define_insn ""
4905   [(set (match_operand:DF 0 "register_operand" "=f")
4906         (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
4907                           (match_operand:DF 2 "register_operand" "f"))
4908                  (match_operand:DF 3 "register_operand" "f")))
4909    (set (match_operand:DF 4 "register_operand" "=&f")
4910         (mult:DF (match_dup 1) (match_dup 2)))]
4911   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
4912     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
4913           || reg_overlap_mentioned_p (operands[4], operands[2])))"
4914   "#"
4915   [(set_attr "type" "fpmuldbl")
4916    (set_attr "length" "8")])
4917
4918 ;; We want to split this up during scheduling since we want both insns
4919 ;; to schedule independently.
4920 (define_split
4921   [(set (match_operand:DF 0 "register_operand" "")
4922         (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "")
4923                           (match_operand:DF 2 "register_operand" ""))
4924                  (match_operand:DF 3 "register_operand" "")))
4925    (set (match_operand:DF 4 "register_operand" "")
4926         (mult:DF (match_dup 1) (match_dup 2)))]
4927   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4928   [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
4929    (set (match_dup 0) (plus:DF (mult:DF (match_dup 1) (match_dup 2))
4930                                (match_dup 3)))]
4931   "")
4932
4933 (define_insn ""
4934   [(set (match_operand:SF 0 "register_operand" "=f")
4935         (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
4936                           (match_operand:SF 2 "register_operand" "f"))
4937                  (match_operand:SF 3 "register_operand" "f")))
4938    (set (match_operand:SF 4 "register_operand" "=&f")
4939         (mult:SF (match_dup 1) (match_dup 2)))]
4940   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
4941     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
4942           || reg_overlap_mentioned_p (operands[4], operands[2])))"
4943   "#"
4944   [(set_attr "type" "fpmuldbl")
4945    (set_attr "length" "8")])
4946
4947 ;; We want to split this up during scheduling since we want both insns
4948 ;; to schedule independently.
4949 (define_split
4950   [(set (match_operand:SF 0 "register_operand" "")
4951         (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "")
4952                           (match_operand:SF 2 "register_operand" ""))
4953                  (match_operand:SF 3 "register_operand" "")))
4954    (set (match_operand:SF 4 "register_operand" "")
4955         (mult:SF (match_dup 1) (match_dup 2)))]
4956   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4957   [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
4958    (set (match_dup 0) (plus:SF (mult:SF (match_dup 1) (match_dup 2))
4959                                (match_dup 3)))]
4960   "")
4961
4962 ;; Negating a multiply can be faked by adding zero in a fused multiply-add
4963 ;; instruction.
4964 (define_insn ""
4965   [(set (match_operand:DF 0 "register_operand" "=f")
4966         (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
4967                          (match_operand:DF 2 "register_operand" "f"))))]
4968   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4969   "fmpynfadd,dbl %1,%2,%%fr0,%0"
4970   [(set_attr "type" "fpmuldbl")
4971    (set_attr "length" "4")])
4972
4973 (define_insn ""
4974   [(set (match_operand:SF 0 "register_operand" "=f")
4975         (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
4976                          (match_operand:SF 2 "register_operand" "f"))))]
4977   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4978   "fmpynfadd,sgl %1,%2,%%fr0,%0"
4979   [(set_attr "type" "fpmuldbl")
4980    (set_attr "length" "4")])
4981
4982 (define_insn ""
4983   [(set (match_operand:DF 0 "register_operand" "=f")
4984         (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
4985                          (match_operand:DF 2 "register_operand" "f"))))
4986    (set (match_operand:DF 3 "register_operand" "=&f")
4987         (mult:DF (match_dup 1) (match_dup 2)))]
4988   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
4989     && ! (reg_overlap_mentioned_p (operands[3], operands[1])
4990           || reg_overlap_mentioned_p (operands[3], operands[2])))"
4991   "#"
4992   [(set_attr "type" "fpmuldbl")
4993    (set_attr "length" "8")])
4994
4995 (define_split
4996   [(set (match_operand:DF 0 "register_operand" "")
4997         (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "")
4998                          (match_operand:DF 2 "register_operand" ""))))
4999    (set (match_operand:DF 3 "register_operand" "")
5000         (mult:DF (match_dup 1) (match_dup 2)))]
5001   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5002   [(set (match_dup 3) (mult:DF (match_dup 1) (match_dup 2)))
5003    (set (match_dup 0) (neg:DF (mult:DF (match_dup 1) (match_dup 2))))]
5004   "")
5005
5006 (define_insn ""
5007   [(set (match_operand:SF 0 "register_operand" "=f")
5008         (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
5009                          (match_operand:SF 2 "register_operand" "f"))))
5010    (set (match_operand:SF 3 "register_operand" "=&f")
5011         (mult:SF (match_dup 1) (match_dup 2)))]
5012   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5013     && ! (reg_overlap_mentioned_p (operands[3], operands[1])
5014           || reg_overlap_mentioned_p (operands[3], operands[2])))"
5015   "#"
5016   [(set_attr "type" "fpmuldbl")
5017    (set_attr "length" "8")])
5018
5019 (define_split
5020   [(set (match_operand:SF 0 "register_operand" "")
5021         (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "")
5022                          (match_operand:SF 2 "register_operand" ""))))
5023    (set (match_operand:SF 3 "register_operand" "")
5024         (mult:SF (match_dup 1) (match_dup 2)))]
5025   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5026   [(set (match_dup 3) (mult:SF (match_dup 1) (match_dup 2)))
5027    (set (match_dup 0) (neg:SF (mult:SF (match_dup 1) (match_dup 2))))]
5028   "")
5029
5030 ;; Now fused multiplies with the result of the multiply negated.
5031 (define_insn ""
5032   [(set (match_operand:DF 0 "register_operand" "=f")
5033         (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
5034                                   (match_operand:DF 2 "register_operand" "f")))
5035                  (match_operand:DF 3 "register_operand" "f")))]
5036   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5037   "fmpynfadd,dbl %1,%2,%3,%0"
5038   [(set_attr "type" "fpmuldbl")
5039    (set_attr "length" "4")])
5040
5041 (define_insn ""
5042   [(set (match_operand:SF 0 "register_operand" "=f")
5043         (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
5044                          (match_operand:SF 2 "register_operand" "f")))
5045                  (match_operand:SF 3 "register_operand" "f")))]
5046   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5047   "fmpynfadd,sgl %1,%2,%3,%0"
5048   [(set_attr "type" "fpmuldbl")
5049    (set_attr "length" "4")])
5050
5051 (define_insn ""
5052   [(set (match_operand:DF 0 "register_operand" "=f")
5053         (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
5054                                   (match_operand:DF 2 "register_operand" "f")))
5055                  (match_operand:DF 3 "register_operand" "f")))
5056    (set (match_operand:DF 4 "register_operand" "=&f")
5057         (mult:DF (match_dup 1) (match_dup 2)))]
5058   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5059     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
5060           || reg_overlap_mentioned_p (operands[4], operands[2])))"
5061   "#"
5062   [(set_attr "type" "fpmuldbl")
5063    (set_attr "length" "8")])
5064
5065 (define_split
5066   [(set (match_operand:DF 0 "register_operand" "")
5067         (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "")
5068                                   (match_operand:DF 2 "register_operand" "")))
5069                  (match_operand:DF 3 "register_operand" "")))
5070    (set (match_operand:DF 4 "register_operand" "")
5071         (mult:DF (match_dup 1) (match_dup 2)))]
5072   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5073   [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
5074    (set (match_dup 0) (plus:DF (neg:DF (mult:DF (match_dup 1) (match_dup 2)))
5075                                (match_dup 3)))]
5076   "")
5077
5078 (define_insn ""
5079   [(set (match_operand:SF 0 "register_operand" "=f")
5080         (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
5081                                   (match_operand:SF 2 "register_operand" "f")))
5082                  (match_operand:SF 3 "register_operand" "f")))
5083    (set (match_operand:SF 4 "register_operand" "=&f")
5084         (mult:SF (match_dup 1) (match_dup 2)))]
5085   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5086     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
5087           || reg_overlap_mentioned_p (operands[4], operands[2])))"
5088   "#"
5089   [(set_attr "type" "fpmuldbl")
5090    (set_attr "length" "8")])
5091
5092 (define_split
5093   [(set (match_operand:SF 0 "register_operand" "")
5094         (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "")
5095                                   (match_operand:SF 2 "register_operand" "")))
5096                  (match_operand:SF 3 "register_operand" "")))
5097    (set (match_operand:SF 4 "register_operand" "")
5098         (mult:SF (match_dup 1) (match_dup 2)))]
5099   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5100   [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
5101    (set (match_dup 0) (plus:SF (neg:SF (mult:SF (match_dup 1) (match_dup 2)))
5102                                (match_dup 3)))]
5103   "")
5104
5105 (define_insn ""
5106   [(set (match_operand:DF 0 "register_operand" "=f")
5107         (minus:DF (match_operand:DF 3 "register_operand" "f")
5108                   (mult:DF (match_operand:DF 1 "register_operand" "f")
5109                            (match_operand:DF 2 "register_operand" "f"))))
5110    (set (match_operand:DF 4 "register_operand" "=&f")
5111         (mult:DF (match_dup 1) (match_dup 2)))]
5112   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5113     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
5114           || reg_overlap_mentioned_p (operands[4], operands[2])))"
5115   "#"
5116   [(set_attr "type" "fpmuldbl")
5117    (set_attr "length" "8")])
5118
5119 (define_split
5120   [(set (match_operand:DF 0 "register_operand" "")
5121         (minus:DF (match_operand:DF 3 "register_operand" "")
5122                   (mult:DF (match_operand:DF 1 "register_operand" "")
5123                            (match_operand:DF 2 "register_operand" ""))))
5124    (set (match_operand:DF 4 "register_operand" "")
5125         (mult:DF (match_dup 1) (match_dup 2)))]
5126   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5127   [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
5128    (set (match_dup 0) (minus:DF (match_dup 3)
5129                                 (mult:DF (match_dup 1) (match_dup 2))))]
5130   "")
5131
5132 (define_insn ""
5133   [(set (match_operand:SF 0 "register_operand" "=f")
5134         (minus:SF (match_operand:SF 3 "register_operand" "f")
5135                   (mult:SF (match_operand:SF 1 "register_operand" "f")
5136                            (match_operand:SF 2 "register_operand" "f"))))
5137    (set (match_operand:SF 4 "register_operand" "=&f")
5138         (mult:SF (match_dup 1) (match_dup 2)))]
5139   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5140     && ! (reg_overlap_mentioned_p (operands[4], operands[1])
5141           || reg_overlap_mentioned_p (operands[4], operands[2])))"
5142   "#"
5143   [(set_attr "type" "fpmuldbl")
5144    (set_attr "length" "8")])
5145
5146 (define_split
5147   [(set (match_operand:SF 0 "register_operand" "")
5148         (minus:SF (match_operand:SF 3 "register_operand" "")
5149                   (mult:SF (match_operand:SF 1 "register_operand" "")
5150                            (match_operand:SF 2 "register_operand" ""))))
5151    (set (match_operand:SF 4 "register_operand" "")
5152         (mult:SF (match_dup 1) (match_dup 2)))]
5153   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5154   [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
5155    (set (match_dup 0) (minus:SF (match_dup 3)
5156                                 (mult:SF (match_dup 1) (match_dup 2))))]
5157   "")
5158
5159 (define_insn ""
5160   [(set (match_operand:DF 0 "register_operand" "=f")
5161         (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))
5162    (set (match_operand:DF 2 "register_operand" "=&f") (abs:DF (match_dup 1)))]
5163   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5164     && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
5165   "#"
5166   [(set_attr "type" "fpalu")
5167    (set_attr "length" "8")])
5168
5169 (define_split
5170   [(set (match_operand:DF 0 "register_operand" "")
5171         (neg:DF (abs:DF (match_operand:DF 1 "register_operand" ""))))
5172    (set (match_operand:DF 2 "register_operand" "") (abs:DF (match_dup 1)))]
5173   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5174   [(set (match_dup 2) (abs:DF (match_dup 1)))
5175    (set (match_dup 0) (neg:DF (abs:DF (match_dup 1))))]
5176   "")
5177
5178 (define_insn ""
5179   [(set (match_operand:SF 0 "register_operand" "=f")
5180         (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))
5181    (set (match_operand:SF 2 "register_operand" "=&f") (abs:SF (match_dup 1)))]
5182   "(! TARGET_SOFT_FLOAT && TARGET_PA_20
5183     && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
5184   "#"
5185   [(set_attr "type" "fpalu")
5186    (set_attr "length" "8")])
5187
5188 (define_split
5189   [(set (match_operand:SF 0 "register_operand" "")
5190         (neg:SF (abs:SF (match_operand:SF 1 "register_operand" ""))))
5191    (set (match_operand:SF 2 "register_operand" "") (abs:SF (match_dup 1)))]
5192   "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5193   [(set (match_dup 2) (abs:SF (match_dup 1)))
5194    (set (match_dup 0) (neg:SF (abs:SF (match_dup 1))))]
5195   "")
5196 \f
5197 ;;- Shift instructions
5198
5199 ;; Optimized special case of shifting.
5200
5201 (define_insn ""
5202   [(set (match_operand:SI 0 "register_operand" "=r")
5203         (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
5204                      (const_int 24)))]
5205   ""
5206   "ldb%M1 %1,%0"
5207   [(set_attr "type" "load")
5208    (set_attr "length" "4")])
5209
5210 (define_insn ""
5211   [(set (match_operand:SI 0 "register_operand" "=r")
5212         (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
5213                      (const_int 16)))]
5214   ""
5215   "ldh%M1 %1,%0"
5216   [(set_attr "type" "load")
5217    (set_attr "length" "4")])
5218
5219 (define_insn ""
5220   [(set (match_operand:SI 0 "register_operand" "=r")
5221         (plus:SI (mult:SI (match_operand:SI 2 "register_operand" "r")
5222                           (match_operand:SI 3 "shadd_operand" ""))
5223                  (match_operand:SI 1 "register_operand" "r")))]
5224   ""
5225   "{sh%O3addl %2,%1,%0|shladd,l %2,%O3,%1,%0} "
5226   [(set_attr "type" "binary")
5227    (set_attr "length" "4")])
5228
5229 (define_insn ""
5230   [(set (match_operand:DI 0 "register_operand" "=r")
5231         (plus:DI (mult:DI (match_operand:DI 2 "register_operand" "r")
5232                           (match_operand:DI 3 "shadd_operand" ""))
5233                  (match_operand:DI 1 "register_operand" "r")))]
5234   "TARGET_64BIT"
5235   "shladd,l %2,%O3,%1,%0"
5236   [(set_attr "type" "binary")
5237    (set_attr "length" "4")])
5238
5239 (define_expand "ashlsi3"
5240   [(set (match_operand:SI 0 "register_operand" "")
5241         (ashift:SI (match_operand:SI 1 "lhs_lshift_operand" "")
5242                    (match_operand:SI 2 "arith32_operand" "")))]
5243   ""
5244   "
5245 {
5246   if (GET_CODE (operands[2]) != CONST_INT)
5247     {
5248       rtx temp = gen_reg_rtx (SImode);
5249       emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
5250       if (GET_CODE (operands[1]) == CONST_INT)
5251         emit_insn (gen_zvdep_imm32 (operands[0], operands[1], temp));
5252       else
5253         emit_insn (gen_zvdep32 (operands[0], operands[1], temp));
5254       DONE;
5255     }
5256   /* Make sure both inputs are not constants,
5257      there are no patterns for that.  */
5258   operands[1] = force_reg (SImode, operands[1]);
5259 }")
5260
5261 (define_insn ""
5262   [(set (match_operand:SI 0 "register_operand" "=r")
5263         (ashift:SI (match_operand:SI 1 "register_operand" "r")
5264                    (match_operand:SI 2 "const_int_operand" "n")))]
5265   ""
5266   "{zdep|depw,z} %1,%P2,%L2,%0"
5267   [(set_attr "type" "shift")
5268    (set_attr "length" "4")])
5269
5270 ; Match cases of op1 a CONST_INT here that zvdep_imm32 doesn't handle.
5271 ; Doing it like this makes slightly better code since reload can
5272 ; replace a register with a known value in range -16..15 with a
5273 ; constant.  Ideally, we would like to merge zvdep32 and zvdep_imm32,
5274 ; but since we have no more CONST_OK... characters, that is not
5275 ; possible.
5276 (define_insn "zvdep32"
5277   [(set (match_operand:SI 0 "register_operand" "=r,r")
5278         (ashift:SI (match_operand:SI 1 "arith5_operand" "r,L")
5279                    (minus:SI (const_int 31)
5280                              (match_operand:SI 2 "register_operand" "q,q"))))]
5281   ""
5282   "@
5283    {zvdep %1,32,%0|depw,z %1,%%sar,32,%0}
5284    {zvdepi %1,32,%0|depwi,z %1,%%sar,32,%0}"
5285   [(set_attr "type" "shift,shift")
5286    (set_attr "length" "4,4")])
5287
5288 (define_insn "zvdep_imm32"
5289   [(set (match_operand:SI 0 "register_operand" "=r")
5290         (ashift:SI (match_operand:SI 1 "lhs_lshift_cint_operand" "")
5291                    (minus:SI (const_int 31)
5292                              (match_operand:SI 2 "register_operand" "q"))))]
5293   ""
5294   "*
5295 {
5296   int x = INTVAL (operands[1]);
5297   operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
5298   operands[1] = GEN_INT ((x & 0xf) - 0x10);
5299   return \"{zvdepi %1,%2,%0|depwi,z %1,%%sar,%2,%0}\";
5300 }"
5301   [(set_attr "type" "shift")
5302    (set_attr "length" "4")])
5303
5304 (define_insn "vdepi_ior"
5305   [(set (match_operand:SI 0 "register_operand" "=r")
5306         (ior:SI (ashift:SI (match_operand:SI 1 "const_int_operand" "")
5307                            (minus:SI (const_int 31)
5308                                      (match_operand:SI 2 "register_operand" "q")))
5309                 (match_operand:SI 3 "register_operand" "0")))]
5310   ; accept ...0001...1, can this be generalized?
5311   "exact_log2 (INTVAL (operands[1]) + 1) >= 0"
5312   "*
5313 {
5314   int x = INTVAL (operands[1]);
5315   operands[2] = GEN_INT (exact_log2 (x + 1));
5316   return \"{vdepi -1,%2,%0|depwi -1,%%sar,%2,%0}\";
5317 }"
5318   [(set_attr "type" "shift")
5319    (set_attr "length" "4")])
5320
5321 (define_insn "vdepi_and"
5322   [(set (match_operand:SI 0 "register_operand" "=r")
5323         (and:SI (rotate:SI (match_operand:SI 1 "const_int_operand" "")
5324                            (minus:SI (const_int 31)
5325                                      (match_operand:SI 2 "register_operand" "q")))
5326                 (match_operand:SI 3 "register_operand" "0")))]
5327   ; this can be generalized...!
5328   "INTVAL (operands[1]) == -2"
5329   "*
5330 {
5331   int x = INTVAL (operands[1]);
5332   operands[2] = GEN_INT (exact_log2 ((~x) + 1));
5333   return \"{vdepi 0,%2,%0|depwi 0,%%sar,%2,%0}\";
5334 }"
5335   [(set_attr "type" "shift")
5336    (set_attr "length" "4")])
5337
5338 (define_expand "ashldi3"
5339   [(set (match_operand:DI 0 "register_operand" "")
5340         (ashift:DI (match_operand:DI 1 "lhs_lshift_operand" "")
5341                    (match_operand:DI 2 "arith32_operand" "")))]
5342   "TARGET_64BIT"
5343   "
5344 {
5345   if (GET_CODE (operands[2]) != CONST_INT)
5346     {
5347       rtx temp = gen_reg_rtx (DImode);
5348       emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
5349       if (GET_CODE (operands[1]) == CONST_INT)
5350         emit_insn (gen_zvdep_imm64 (operands[0], operands[1], temp));
5351       else
5352         emit_insn (gen_zvdep64 (operands[0], operands[1], temp));
5353       DONE;
5354     }
5355   /* Make sure both inputs are not constants,
5356      there are no patterns for that.  */
5357   operands[1] = force_reg (DImode, operands[1]);
5358 }")
5359
5360 (define_insn ""
5361   [(set (match_operand:DI 0 "register_operand" "=r")
5362         (ashift:DI (match_operand:DI 1 "register_operand" "r")
5363                    (match_operand:DI 2 "const_int_operand" "n")))]
5364   "TARGET_64BIT"
5365   "depd,z %1,%p2,%Q2,%0"
5366   [(set_attr "type" "shift")
5367    (set_attr "length" "4")])
5368
5369 ; Match cases of op1 a CONST_INT here that zvdep_imm64 doesn't handle.
5370 ; Doing it like this makes slightly better code since reload can
5371 ; replace a register with a known value in range -16..15 with a
5372 ; constant.  Ideally, we would like to merge zvdep64 and zvdep_imm64,
5373 ; but since we have no more CONST_OK... characters, that is not
5374 ; possible.
5375 (define_insn "zvdep64"
5376   [(set (match_operand:DI 0 "register_operand" "=r,r")
5377         (ashift:DI (match_operand:DI 1 "arith5_operand" "r,L")
5378                    (minus:DI (const_int 63)
5379                              (match_operand:DI 2 "register_operand" "q,q"))))]
5380   "TARGET_64BIT"
5381   "@
5382    depd,z %1,%%sar,64,%0
5383    depdi,z %1,%%sar,64,%0"
5384   [(set_attr "type" "shift,shift")
5385    (set_attr "length" "4,4")])
5386
5387 (define_insn "zvdep_imm64"
5388   [(set (match_operand:DI 0 "register_operand" "=r")
5389         (ashift:DI (match_operand:DI 1 "lhs_lshift_cint_operand" "")
5390                    (minus:DI (const_int 63)
5391                              (match_operand:DI 2 "register_operand" "q"))))]
5392   "TARGET_64BIT"
5393   "*
5394 {
5395   int x = INTVAL (operands[1]);
5396   operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
5397   operands[1] = GEN_INT ((x & 0x1f) - 0x20);
5398   return \"depdi,z %1,%%sar,%2,%0\";
5399 }"
5400   [(set_attr "type" "shift")
5401    (set_attr "length" "4")])
5402
5403 (define_insn ""
5404   [(set (match_operand:DI 0 "register_operand" "=r")
5405         (ior:DI (ashift:DI (match_operand:DI 1 "const_int_operand" "")
5406                            (minus:DI (const_int 63)
5407                                      (match_operand:DI 2 "register_operand" "q")))
5408                 (match_operand:DI 3 "register_operand" "0")))]
5409   ; accept ...0001...1, can this be generalized?
5410   "TARGET_64BIT && exact_log2 (INTVAL (operands[1]) + 1) >= 0"
5411   "*
5412 {
5413   int x = INTVAL (operands[1]);
5414   operands[2] = GEN_INT (exact_log2 (x + 1));
5415   return \"depdi -1,%%sar,%2,%0\";
5416 }"
5417   [(set_attr "type" "shift")
5418    (set_attr "length" "4")])
5419
5420 (define_insn ""
5421   [(set (match_operand:DI 0 "register_operand" "=r")
5422         (and:DI (rotate:DI (match_operand:DI 1 "const_int_operand" "")
5423                            (minus:DI (const_int 63)
5424                                      (match_operand:DI 2 "register_operand" "q")))
5425                 (match_operand:DI 3 "register_operand" "0")))]
5426   ; this can be generalized...!
5427   "TARGET_64BIT && INTVAL (operands[1]) == -2"
5428   "*
5429 {
5430   int x = INTVAL (operands[1]);
5431   operands[2] = GEN_INT (exact_log2 ((~x) + 1));
5432   return \"depdi 0,%%sar,%2,%0\";
5433 }"
5434   [(set_attr "type" "shift")
5435    (set_attr "length" "4")])
5436
5437 (define_expand "ashrsi3"
5438   [(set (match_operand:SI 0 "register_operand" "")
5439         (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
5440                      (match_operand:SI 2 "arith32_operand" "")))]
5441   ""
5442   "
5443 {
5444   if (GET_CODE (operands[2]) != CONST_INT)
5445     {
5446       rtx temp = gen_reg_rtx (SImode);
5447       emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
5448       emit_insn (gen_vextrs32 (operands[0], operands[1], temp));
5449       DONE;
5450     }
5451 }")
5452
5453 (define_insn ""
5454   [(set (match_operand:SI 0 "register_operand" "=r")
5455         (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
5456                      (match_operand:SI 2 "const_int_operand" "n")))]
5457   ""
5458   "{extrs|extrw,s} %1,%P2,%L2,%0"
5459   [(set_attr "type" "shift")
5460    (set_attr "length" "4")])
5461
5462 (define_insn "vextrs32"
5463   [(set (match_operand:SI 0 "register_operand" "=r")
5464         (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
5465                      (minus:SI (const_int 31)
5466                                (match_operand:SI 2 "register_operand" "q"))))]
5467   ""
5468   "{vextrs %1,32,%0|extrw,s %1,%%sar,32,%0}"
5469   [(set_attr "type" "shift")
5470    (set_attr "length" "4")])
5471
5472 (define_expand "ashrdi3"
5473   [(set (match_operand:DI 0 "register_operand" "")
5474         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
5475                      (match_operand:DI 2 "arith32_operand" "")))]
5476   "TARGET_64BIT"
5477   "
5478 {
5479   if (GET_CODE (operands[2]) != CONST_INT)
5480     {
5481       rtx temp = gen_reg_rtx (DImode);
5482       emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
5483       emit_insn (gen_vextrs64 (operands[0], operands[1], temp));
5484       DONE;
5485     }
5486 }")
5487
5488 (define_insn ""
5489   [(set (match_operand:DI 0 "register_operand" "=r")
5490         (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
5491                      (match_operand:DI 2 "const_int_operand" "n")))]
5492   "TARGET_64BIT"
5493   "extrd,s %1,%p2,%Q2,%0"
5494   [(set_attr "type" "shift")
5495    (set_attr "length" "4")])
5496
5497 (define_insn "vextrs64"
5498   [(set (match_operand:DI 0 "register_operand" "=r")
5499         (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
5500                      (minus:DI (const_int 63)
5501                                (match_operand:DI 2 "register_operand" "q"))))]
5502   "TARGET_64BIT"
5503   "extrd,s %1,%%sar,64,%0"
5504   [(set_attr "type" "shift")
5505    (set_attr "length" "4")])
5506
5507 (define_insn "lshrsi3"
5508   [(set (match_operand:SI 0 "register_operand" "=r,r")
5509         (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
5510                      (match_operand:SI 2 "arith32_operand" "q,n")))]
5511   ""
5512   "@
5513    {vshd %%r0,%1,%0|shrpw %%r0,%1,%%sar,%0}
5514    {extru|extrw,u} %1,%P2,%L2,%0"
5515   [(set_attr "type" "shift")
5516    (set_attr "length" "4")])
5517
5518 (define_insn "lshrdi3"
5519   [(set (match_operand:DI 0 "register_operand" "=r,r")
5520         (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
5521                      (match_operand:DI 2 "arith32_operand" "q,n")))]
5522   "TARGET_64BIT"
5523   "@
5524    shrpd %%r0,%1,%%sar,%0
5525    extrd,u %1,%p2,%Q2,%0"
5526   [(set_attr "type" "shift")
5527    (set_attr "length" "4")])
5528
5529 (define_insn "rotrsi3"
5530   [(set (match_operand:SI 0 "register_operand" "=r,r")
5531         (rotatert:SI (match_operand:SI 1 "register_operand" "r,r")
5532                      (match_operand:SI 2 "arith32_operand" "q,n")))]
5533   ""
5534   "*
5535 {
5536   if (GET_CODE (operands[2]) == CONST_INT)
5537     {
5538       operands[2] = GEN_INT (INTVAL (operands[2]) & 31);
5539       return \"{shd|shrpw} %1,%1,%2,%0\";
5540     }
5541   else
5542     return \"{vshd %1,%1,%0|shrpw %1,%1,%%sar,%0}\";
5543 }"
5544   [(set_attr "type" "shift")
5545    (set_attr "length" "4")])
5546
5547 (define_expand "rotlsi3"
5548   [(set (match_operand:SI 0 "register_operand" "")
5549         (rotate:SI (match_operand:SI 1 "register_operand" "")
5550                    (match_operand:SI 2 "arith32_operand" "")))]
5551   ""
5552   "
5553 {
5554   if (GET_CODE (operands[2]) != CONST_INT)
5555     {
5556       rtx temp = gen_reg_rtx (SImode);
5557       emit_insn (gen_subsi3 (temp, GEN_INT (32), operands[2]));
5558       emit_insn (gen_rotrsi3 (operands[0], operands[1], temp));
5559       DONE;
5560     }
5561   /* Else expand normally.  */
5562 }")
5563
5564 (define_insn ""
5565   [(set (match_operand:SI 0 "register_operand" "=r")
5566         (rotate:SI (match_operand:SI 1 "register_operand" "r")
5567                    (match_operand:SI 2 "const_int_operand" "n")))]
5568   ""
5569   "*
5570 {
5571   operands[2] = GEN_INT ((32 - INTVAL (operands[2])) & 31);
5572   return \"{shd|shrpw} %1,%1,%2,%0\";
5573 }"
5574   [(set_attr "type" "shift")
5575    (set_attr "length" "4")])
5576
5577 (define_insn ""
5578   [(set (match_operand:SI 0 "register_operand" "=r")
5579         (match_operator:SI 5 "plus_xor_ior_operator"
5580           [(ashift:SI (match_operand:SI 1 "register_operand" "r")
5581                       (match_operand:SI 3 "const_int_operand" "n"))
5582            (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
5583                         (match_operand:SI 4 "const_int_operand" "n"))]))]
5584   "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
5585   "{shd|shrpw} %1,%2,%4,%0"
5586   [(set_attr "type" "shift")
5587    (set_attr "length" "4")])
5588
5589 (define_insn ""
5590   [(set (match_operand:SI 0 "register_operand" "=r")
5591         (match_operator:SI 5 "plus_xor_ior_operator"
5592           [(lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
5593                         (match_operand:SI 4 "const_int_operand" "n"))
5594            (ashift:SI (match_operand:SI 1 "register_operand" "r")
5595                       (match_operand:SI 3 "const_int_operand" "n"))]))]
5596   "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
5597   "{shd|shrpw} %1,%2,%4,%0"
5598   [(set_attr "type" "shift")
5599    (set_attr "length" "4")])
5600
5601 (define_insn ""
5602   [(set (match_operand:SI 0 "register_operand" "=r")
5603         (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
5604                            (match_operand:SI 2 "const_int_operand" ""))
5605                 (match_operand:SI 3 "const_int_operand" "")))]
5606   "exact_log2 (1 + (INTVAL (operands[3]) >> (INTVAL (operands[2]) & 31))) >= 0"
5607   "*
5608 {
5609   int cnt = INTVAL (operands[2]) & 31;
5610   operands[3] = GEN_INT (exact_log2 (1 + (INTVAL (operands[3]) >> cnt)));
5611   operands[2] = GEN_INT (31 - cnt);
5612   return \"{zdep|depw,z} %1,%2,%3,%0\";
5613 }"
5614   [(set_attr "type" "shift")
5615    (set_attr "length" "4")])
5616 \f
5617 ;; Unconditional and other jump instructions.
5618
5619 ;; This can only be used in a leaf function, so we do
5620 ;; not need to use the PIC register when generating PIC code.
5621 (define_insn "return"
5622   [(return)
5623    (use (reg:SI 2))
5624    (const_int 0)]
5625   "hppa_can_use_return_insn_p ()"
5626   "*
5627 {
5628   if (TARGET_PA_20)
5629     return \"bve%* (%%r2)\";
5630   return \"bv%* %%r0(%%r2)\";
5631 }"
5632   [(set_attr "type" "branch")
5633    (set_attr "length" "4")])
5634
5635 ;; Emit a different pattern for functions which have non-trivial
5636 ;; epilogues so as not to confuse jump and reorg.
5637 (define_insn "return_internal"
5638   [(return)
5639    (use (reg:SI 2))
5640    (const_int 1)]
5641   "! flag_pic"
5642   "*
5643 {
5644   if (TARGET_PA_20)
5645     return \"bve%* (%%r2)\";
5646   return \"bv%* %%r0(%%r2)\";
5647 }"
5648   [(set_attr "type" "branch")
5649    (set_attr "length" "4")])
5650
5651 ;; Use the PIC register to ensure it's restored after a
5652 ;; call in PIC mode.
5653 (define_insn "return_internal_pic"
5654   [(return)
5655    (use (match_operand 0 "register_operand" "r"))
5656    (use (reg:SI 2))]
5657   "flag_pic && true_regnum (operands[0]) == PIC_OFFSET_TABLE_REGNUM"
5658   "*
5659 {
5660   if (TARGET_PA_20)
5661     return \"bve%* (%%r2)\";
5662   return \"bv%* %%r0(%%r2)\";
5663 }"
5664   [(set_attr "type" "branch")
5665    (set_attr "length" "4")])
5666
5667 ;; Use the PIC register to ensure it's restored after a
5668 ;; call in PIC mode.  This is used for eh returns which
5669 ;; bypass the return stub.
5670 (define_insn "return_external_pic"
5671   [(return)
5672    (use (match_operand 0 "register_operand" "r"))
5673    (use (reg:SI 2))
5674    (clobber (reg:SI 1))]
5675   "flag_pic
5676    && current_function_calls_eh_return
5677    && true_regnum (operands[0]) == PIC_OFFSET_TABLE_REGNUM"
5678   "ldsid (%%sr0,%%r2),%%r1\;mtsp %%r1,%%sr0\;be%* 0(%%sr0,%%r2)"
5679   [(set_attr "type" "branch")
5680    (set_attr "length" "12")])
5681
5682 (define_expand "prologue"
5683   [(const_int 0)]
5684   ""
5685   "hppa_expand_prologue ();DONE;")
5686
5687 (define_expand "sibcall_epilogue"
5688   [(return)]
5689   ""
5690   "
5691 {
5692   hppa_expand_epilogue ();
5693   DONE;
5694 }")
5695
5696 (define_expand "epilogue"
5697   [(return)]
5698   ""
5699   "
5700 {
5701   /* Try to use the trivial return first.  Else use the full
5702      epilogue.  */
5703   if (hppa_can_use_return_insn_p ())
5704     emit_jump_insn (gen_return ());
5705   else
5706     {
5707       rtx x;
5708
5709       hppa_expand_epilogue ();
5710       if (flag_pic)
5711         {
5712           rtx pic = gen_rtx_REG (word_mode, PIC_OFFSET_TABLE_REGNUM);
5713
5714           /* EH returns bypass the normal return stub.  Thus, we must do an
5715              interspace branch to return from functions that call eh_return.
5716              This is only a problem for returns from shared code.  */
5717           if (current_function_calls_eh_return)
5718             x = gen_return_external_pic (pic);
5719           else
5720             x = gen_return_internal_pic (pic);
5721         }
5722       else
5723         x = gen_return_internal ();
5724       emit_jump_insn (x);
5725     }
5726   DONE;
5727 }")
5728
5729 ;; Special because we use the value placed in %r2 by the bl instruction
5730 ;; from within its delay slot to set the value for the 2nd parameter to
5731 ;; the call.
5732 (define_insn "call_profiler"
5733   [(call (mem:SI (match_operand 0 "call_operand_address" ""))
5734          (match_operand 1 "" ""))
5735    (use (match_operand 2 "" ""))
5736    (use (reg:SI 25))
5737    (use (reg:SI 26))
5738    (clobber (reg:SI 2))]
5739   ""
5740   "*
5741 {
5742   rtx xoperands[3];
5743
5744   output_arg_descriptor (insn);
5745
5746   xoperands[0] = operands[0];
5747   xoperands[1] = operands[2];
5748   xoperands[2] = gen_label_rtx ();
5749   output_asm_insn (\"{bl|b,l} %0,%%r2\;ldo %1-%2(%%r2),%%r25\", xoperands);
5750
5751   ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
5752                              CODE_LABEL_NUMBER (xoperands[2]));
5753   return \"\";
5754 }"
5755   [(set_attr "type" "multi")
5756    (set_attr "length" "8")])
5757
5758 (define_insn "blockage"
5759   [(unspec_volatile [(const_int 2)] 0)]
5760   ""
5761   ""
5762   [(set_attr "length" "0")])
5763
5764 (define_insn "jump"
5765   [(set (pc) (label_ref (match_operand 0 "" "")))]
5766   ""
5767   "*
5768 {
5769   extern int optimize;
5770
5771   if (GET_MODE (insn) == SImode)
5772     return \"b %l0%#\";
5773
5774   /* An unconditional branch which can reach its target.  */
5775   if (get_attr_length (insn) != 24
5776       && get_attr_length (insn) != 16)
5777     return \"b%* %l0\";
5778
5779   /* An unconditional branch which can not reach its target.
5780
5781      We need to be able to use %r1 as a scratch register; however,
5782      we can never be sure whether or not it's got a live value in
5783      it.  Therefore, we must restore its original value after the
5784      jump.
5785
5786      To make matters worse, we don't have a stack slot which we
5787      can always clobber.  sp-12/sp-16 shouldn't ever have a live
5788      value during a non-optimizing compilation, so we use those
5789      slots for now.  We don't support very long branches when
5790      optimizing -- they should be quite rare when optimizing.
5791
5792      Really the way to go long term is a register scavenger; goto
5793      the target of the jump and find a register which we can use
5794      as a scratch to hold the value in %r1.  */
5795
5796   /* We don't know how to register scavenge yet.  */
5797   if (optimize)
5798     abort ();
5799
5800   /* First store %r1 into the stack.  */
5801   output_asm_insn (\"stw %%r1,-16(%%r30)\", operands);
5802
5803   /* Now load the target address into %r1 and do an indirect jump
5804      to the value specified in %r1.  Be careful to generate PIC
5805      code as needed.  */
5806   if (flag_pic)
5807     {
5808       rtx xoperands[2];
5809       xoperands[0] = operands[0];
5810       if (TARGET_SOM || ! TARGET_GAS)
5811         {
5812           xoperands[1] = gen_label_rtx ();
5813
5814           output_asm_insn (\"{bl|b,l} .+8,%%r1\\n\\taddil L'%l0-%l1,%%r1\",
5815                            xoperands);
5816           ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
5817                                      CODE_LABEL_NUMBER (xoperands[1]));
5818           output_asm_insn (\"ldo R'%l0-%l1(%%r1),%%r1\", xoperands);
5819         }
5820       else
5821         {
5822           output_asm_insn (\"{bl|b,l} .+8,%%r1\", xoperands);
5823           output_asm_insn (\"addil L'%l0-$PIC_pcrel$0+4,%%r1\", xoperands);
5824           output_asm_insn (\"ldo R'%l0-$PIC_pcrel$0+8(%%r1),%%r1\", xoperands);
5825         }
5826       output_asm_insn (\"bv %%r0(%%r1)\", xoperands);
5827     }
5828   else
5829     output_asm_insn (\"ldil L'%l0,%%r1\\n\\tbe R'%l0(%%sr4,%%r1)\", operands);;
5830
5831   /* And restore the value of %r1 in the delay slot.  We're not optimizing,
5832      so we know nothing else can be in the delay slot.  */
5833   return \"ldw -16(%%r30),%%r1\";
5834 }"
5835   [(set_attr "type" "uncond_branch")
5836    (set_attr "pa_combine_type" "uncond_branch")
5837    (set (attr "length")
5838     (cond [(eq (symbol_ref "jump_in_call_delay (insn)") (const_int 1))
5839            (if_then_else (lt (abs (minus (match_dup 0)
5840                                          (plus (pc) (const_int 8))))
5841                              (const_int 8184))
5842                          (const_int 4)
5843                          (const_int 8))
5844            (ge (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
5845                (const_int 262100))
5846            (if_then_else (eq (symbol_ref "flag_pic") (const_int 0))
5847                          (const_int 16)
5848                          (const_int 24))]
5849           (const_int 4)))])
5850
5851 ;; Subroutines of "casesi".
5852 ;; operand 0 is index
5853 ;; operand 1 is the minimum bound
5854 ;; operand 2 is the maximum bound - minimum bound + 1
5855 ;; operand 3 is CODE_LABEL for the table;
5856 ;; operand 4 is the CODE_LABEL to go to if index out of range.
5857
5858 (define_expand "casesi"
5859   [(match_operand:SI 0 "general_operand" "")
5860    (match_operand:SI 1 "const_int_operand" "")
5861    (match_operand:SI 2 "const_int_operand" "")
5862    (match_operand 3 "" "")
5863    (match_operand 4 "" "")]
5864   ""
5865   "
5866 {
5867   if (GET_CODE (operands[0]) != REG)
5868     operands[0] = force_reg (SImode, operands[0]);
5869
5870   if (operands[1] != const0_rtx)
5871     {
5872       rtx reg = gen_reg_rtx (SImode);
5873
5874       operands[1] = GEN_INT (-INTVAL (operands[1]));
5875       if (!INT_14_BITS (operands[1]))
5876         operands[1] = force_reg (SImode, operands[1]);
5877       emit_insn (gen_addsi3 (reg, operands[0], operands[1]));
5878
5879       operands[0] = reg;
5880     }
5881
5882   /* In 64bit mode we must make sure to wipe the upper bits of the register
5883      just in case the addition overflowed or we had random bits in the
5884      high part of the register.  */
5885   if (TARGET_64BIT)
5886     {
5887       rtx reg = gen_reg_rtx (DImode);
5888       emit_insn (gen_extendsidi2 (reg, operands[0]));
5889       operands[0] = gen_rtx_SUBREG (SImode, reg, 4);
5890     }
5891
5892   if (!INT_5_BITS (operands[2]))
5893     operands[2] = force_reg (SImode, operands[2]);
5894
5895   emit_insn (gen_cmpsi (operands[0], operands[2]));
5896   emit_jump_insn (gen_bgtu (operands[4]));
5897   if (TARGET_BIG_SWITCH)
5898     {
5899       rtx temp = gen_reg_rtx (SImode);
5900       emit_move_insn (temp, gen_rtx_PLUS (SImode, operands[0], operands[0]));
5901       operands[0] = temp;
5902     }
5903   emit_jump_insn (gen_casesi0 (operands[0], operands[3]));
5904   DONE;
5905 }")
5906
5907 (define_insn "casesi0"
5908   [(set (pc) (plus:SI
5909                (mem:SI (plus:SI (pc)
5910                                 (match_operand:SI 0 "register_operand" "r")))
5911                (label_ref (match_operand 1 "" ""))))]
5912   ""
5913   "blr %0,%%r0\;nop"
5914   [(set_attr "type" "multi")
5915    (set_attr "length" "8")])
5916
5917 ;; Need nops for the calls because execution is supposed to continue
5918 ;; past; we don't want to nullify an instruction that we need.
5919 ;;- jump to subroutine
5920
5921 (define_expand "call"
5922   [(parallel [(call (match_operand:SI 0 "" "")
5923                     (match_operand 1 "" ""))
5924               (clobber (reg:SI 2))])]
5925   ""
5926   "
5927 {
5928   rtx op;
5929   rtx call_insn;
5930
5931   if (TARGET_PORTABLE_RUNTIME)
5932     op = force_reg (SImode, XEXP (operands[0], 0));
5933   else
5934     op = XEXP (operands[0], 0);
5935
5936   if (TARGET_64BIT)
5937     emit_move_insn (arg_pointer_rtx,
5938                     gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
5939                                   GEN_INT (64)));
5940
5941   /* Use two different patterns for calls to explicitly named functions
5942      and calls through function pointers.  This is necessary as these two
5943      types of calls use different calling conventions, and CSE might try
5944      to change the named call into an indirect call in some cases (using
5945      two patterns keeps CSE from performing this optimization).  */
5946   if (GET_CODE (op) == SYMBOL_REF)
5947     call_insn = emit_call_insn (gen_call_internal_symref (op, operands[1]));
5948   else if (TARGET_64BIT)
5949     {
5950       rtx tmpreg = force_reg (word_mode, op);
5951       call_insn = emit_call_insn (gen_call_internal_reg_64bit (tmpreg,
5952                                                                operands[1]));
5953     }
5954   else
5955     {
5956       rtx tmpreg = gen_rtx_REG (word_mode, 22);
5957       emit_move_insn (tmpreg, force_reg (word_mode, op));
5958       call_insn = emit_call_insn (gen_call_internal_reg (operands[1]));
5959     }
5960
5961   if (flag_pic)
5962     {
5963       use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
5964       if (TARGET_64BIT)
5965         use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
5966
5967       /* After each call we must restore the PIC register, even if it
5968          doesn't appear to be used.  */
5969       emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
5970     }
5971   DONE;
5972 }")
5973
5974 (define_insn "call_internal_symref"
5975   [(call (mem:SI (match_operand 0 "call_operand_address" ""))
5976          (match_operand 1 "" "i"))
5977    (clobber (reg:SI 2))
5978    (use (const_int 0))]
5979   "! TARGET_PORTABLE_RUNTIME"
5980   "*
5981 {
5982   output_arg_descriptor (insn);
5983   return output_call (insn, operands[0], 0);
5984 }"
5985   [(set_attr "type" "call")
5986    (set (attr "length")
5987 ;;       If we're sure that we can either reach the target or that the
5988 ;;       linker can use a long-branch stub, then the length is at most
5989 ;;       8 bytes.
5990 ;;
5991 ;;       For long-calls the length will be at most 68 bytes (non-pic)
5992 ;;       or 84 bytes (pic).  */
5993 ;;       Else we have to use a long-call;
5994       (if_then_else (lt (plus (symbol_ref "total_code_bytes") (pc))
5995                         (const_int 240000))
5996                     (const_int 8)
5997                     (if_then_else (eq (symbol_ref "flag_pic")
5998                                       (const_int 0))
5999                                   (const_int 68)
6000                                   (const_int 84))))])
6001
6002 (define_insn "call_internal_reg_64bit"
6003   [(call (mem:SI (match_operand:DI 0 "register_operand" "r"))
6004          (match_operand 1 "" "i"))
6005    (clobber (reg:SI 2))
6006    (use (const_int 1))]
6007   "TARGET_64BIT"
6008   "*
6009 {
6010   /* ??? Needs more work.  Length computation, split into multiple insns,
6011      do not use %r22 directly, expose delay slot.  */
6012   return \"ldd 16(%0),%%r2\;ldd 24(%0),%%r27\;bve,l (%%r2),%%r2\;nop\";
6013 }"
6014   [(set_attr "type" "dyncall")
6015    (set (attr "length") (const_int 16))])
6016
6017 (define_insn "call_internal_reg"
6018   [(call (mem:SI (reg:SI 22))
6019          (match_operand 0 "" "i"))
6020    (clobber (reg:SI 2))
6021    (use (const_int 1))]
6022   ""
6023   "*
6024 {
6025   rtx xoperands[2];
6026
6027   /* First the special case for kernels, level 0 systems, etc.  */
6028   if (TARGET_FAST_INDIRECT_CALLS)
6029     return \"ble 0(%%sr4,%%r22)\;copy %%r31,%%r2\";
6030
6031   /* Now the normal case -- we can reach $$dyncall directly or
6032      we're sure that we can get there via a long-branch stub. 
6033
6034      No need to check target flags as the length uniquely identifies
6035      the remaining cases.  */
6036   if (get_attr_length (insn) == 8)
6037     return \".CALL\\tARGW0=GR\;{bl|b,l} $$dyncall,%%r31\;copy %%r31,%%r2\";
6038
6039   /* Long millicode call, but we are not generating PIC or portable runtime
6040      code.  */
6041   if (get_attr_length (insn) == 12)
6042     return \".CALL\\tARGW0=GR\;ldil L%%$$dyncall,%%r2\;ble R%%$$dyncall(%%sr4,%%r2)\;copy %%r31,%%r2\";
6043
6044   /* Long millicode call for portable runtime.  */
6045   if (get_attr_length (insn) == 20)
6046     return \"ldil L%%$$dyncall,%%r31\;ldo R%%$$dyncall(%%r31),%%r31\;blr %%r0,%%r2\;bv,n %%r0(%%r31)\;nop\";
6047
6048   /* If we're generating PIC code.  */
6049   xoperands[0] = operands[0];
6050   if (TARGET_SOM || ! TARGET_GAS)
6051     xoperands[1] = gen_label_rtx ();
6052   output_asm_insn (\"{bl|b,l} .+8,%%r1\", xoperands);
6053   if (TARGET_SOM || ! TARGET_GAS)
6054     {
6055       output_asm_insn (\"addil L%%$$dyncall-%1,%%r1\", xoperands);
6056       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
6057                                  CODE_LABEL_NUMBER (xoperands[1]));
6058       output_asm_insn (\"ldo R%%$$dyncall-%1(%%r1),%%r1\", xoperands);
6059     }
6060   else
6061     {
6062       output_asm_insn (\"addil L%%$$dyncall-$PIC_pcrel$0+4,%%r1\", xoperands);
6063       output_asm_insn (\"ldo R%%$$dyncall-$PIC_pcrel$0+8(%%r1),%%r1\",
6064                        xoperands);
6065     }
6066   output_asm_insn (\"blr %%r0,%%r2\", xoperands);
6067   output_asm_insn (\"bv,n %%r0(%%r1)\\n\\tnop\", xoperands);
6068   return \"\";
6069 }"
6070   [(set_attr "type" "dyncall")
6071    (set (attr "length")
6072      (cond [
6073 ;; First FAST_INDIRECT_CALLS
6074             (ne (symbol_ref "TARGET_FAST_INDIRECT_CALLS")
6075                 (const_int 0))
6076             (const_int 8)
6077
6078 ;; Target (or stub) within reach
6079             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
6080                      (const_int 240000))
6081                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
6082                      (const_int 0)))
6083             (const_int 8)
6084
6085 ;; Out of reach PIC
6086             (ne (symbol_ref "flag_pic")
6087                 (const_int 0))
6088             (const_int 24)
6089
6090 ;; Out of reach PORTABLE_RUNTIME
6091             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
6092                 (const_int 0))
6093             (const_int 20)]
6094
6095 ;; Out of reach, can use ble
6096           (const_int 12)))])
6097
6098 (define_expand "call_value"
6099   [(parallel [(set (match_operand 0 "" "")
6100                    (call (match_operand:SI 1 "" "")
6101                          (match_operand 2 "" "")))
6102               (clobber (reg:SI 2))])]
6103   ""
6104   "
6105 {
6106   rtx op;
6107   rtx call_insn;
6108
6109   if (TARGET_PORTABLE_RUNTIME)
6110     op = force_reg (word_mode, XEXP (operands[1], 0));
6111   else
6112     op = XEXP (operands[1], 0);
6113
6114   if (TARGET_64BIT)
6115     emit_move_insn (arg_pointer_rtx,
6116                     gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
6117                                   GEN_INT (64)));
6118
6119   /* Use two different patterns for calls to explicitly named functions
6120      and calls through function pointers.  This is necessary as these two
6121      types of calls use different calling conventions, and CSE might try
6122      to change the named call into an indirect call in some cases (using
6123      two patterns keeps CSE from performing this optimization).  */
6124   if (GET_CODE (op) == SYMBOL_REF)
6125     call_insn = emit_call_insn (gen_call_value_internal_symref (operands[0],
6126                                                                 op,
6127                                                                 operands[2]));
6128   else if (TARGET_64BIT)
6129     {
6130       rtx tmpreg = force_reg (word_mode, op);
6131       call_insn
6132         = emit_call_insn (gen_call_value_internal_reg_64bit (operands[0],
6133                                                              tmpreg,
6134                                                              operands[2]));
6135     }
6136   else
6137     {
6138       rtx tmpreg = gen_rtx_REG (word_mode, 22);
6139       emit_move_insn (tmpreg, force_reg (word_mode, op));
6140       call_insn = emit_call_insn (gen_call_value_internal_reg (operands[0],
6141                                                                operands[2]));
6142     }
6143   if (flag_pic)
6144     {
6145       use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
6146       if (TARGET_64BIT)
6147         use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
6148
6149       /* After each call we must restore the PIC register, even if it
6150          doesn't appear to be used.  */
6151       emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
6152     }
6153   DONE;
6154 }")
6155
6156 (define_insn "call_value_internal_symref"
6157   [(set (match_operand 0 "" "=rf")
6158         (call (mem:SI (match_operand 1 "call_operand_address" ""))
6159               (match_operand 2 "" "i")))
6160    (clobber (reg:SI 2))
6161    (use (const_int 0))]
6162   ;;- Don't use operand 1 for most machines.
6163   "! TARGET_PORTABLE_RUNTIME"
6164   "*
6165 {
6166   output_arg_descriptor (insn);
6167   return output_call (insn, operands[1], 0);
6168 }"
6169   [(set_attr "type" "call")
6170    (set (attr "length")
6171 ;;       If we're sure that we can either reach the target or that the
6172 ;;       linker can use a long-branch stub, then the length is at most
6173 ;;       8 bytes.
6174 ;;
6175 ;;       For long-calls the length will be at most 68 bytes (non-pic)
6176 ;;       or 84 bytes (pic).  */
6177 ;;       Else we have to use a long-call;
6178       (if_then_else (lt (plus (symbol_ref "total_code_bytes") (pc))
6179                         (const_int 240000))
6180                     (const_int 8)
6181                     (if_then_else (eq (symbol_ref "flag_pic")
6182                                       (const_int 0))
6183                                   (const_int 68)
6184                                   (const_int 84))))])
6185
6186 (define_insn "call_value_internal_reg_64bit"
6187   [(set (match_operand 0 "" "=rf")
6188          (call (mem:SI (match_operand:DI 1 "register_operand" "r"))
6189                (match_operand 2 "" "i")))
6190    (clobber (reg:SI 2))
6191    (use (const_int 1))]
6192   "TARGET_64BIT"
6193   "*
6194 {
6195   /* ??? Needs more work.  Length computation, split into multiple insns,
6196      do not use %r22 directly, expose delay slot.  */
6197   return \"ldd 16(%1),%%r2\;ldd 24(%1),%%r27\;bve,l (%%r2),%%r2\;nop\";
6198 }"
6199   [(set_attr "type" "dyncall")
6200    (set (attr "length") (const_int 16))])
6201
6202 (define_insn "call_value_internal_reg"
6203   [(set (match_operand 0 "" "=rf")
6204         (call (mem:SI (reg:SI 22))
6205               (match_operand 1 "" "i")))
6206    (clobber (reg:SI 2))
6207    (use (const_int 1))]
6208   ""
6209   "*
6210 {
6211   rtx xoperands[2];
6212
6213   /* First the special case for kernels, level 0 systems, etc.  */
6214   if (TARGET_FAST_INDIRECT_CALLS)
6215     return \"ble 0(%%sr4,%%r22)\;copy %%r31,%%r2\";
6216
6217   /* Now the normal case -- we can reach $$dyncall directly or
6218      we're sure that we can get there via a long-branch stub. 
6219
6220      No need to check target flags as the length uniquely identifies
6221      the remaining cases.  */
6222   if (get_attr_length (insn) == 8)
6223     return \".CALL\\tARGW0=GR\;{bl|b,l} $$dyncall,%%r31\;copy %%r31,%%r2\";
6224
6225   /* Long millicode call, but we are not generating PIC or portable runtime
6226      code.  */
6227   if (get_attr_length (insn) == 12)
6228     return \".CALL\\tARGW0=GR\;ldil L%%$$dyncall,%%r2\;ble R%%$$dyncall(%%sr4,%%r2)\;copy %%r31,%%r2\";
6229
6230   /* Long millicode call for portable runtime.  */
6231   if (get_attr_length (insn) == 20)
6232     return \"ldil L%%$$dyncall,%%r31\;ldo R%%$$dyncall(%%r31),%%r31\;blr %%r0,%%r2\;bv,n %%r0(%%r31)\;nop\";
6233
6234   /* If we're generating PIC code.  */
6235   xoperands[0] = operands[1];
6236   if (TARGET_SOM || ! TARGET_GAS)
6237     xoperands[1] = gen_label_rtx ();
6238   output_asm_insn (\"{bl|b,l} .+8,%%r1\", xoperands);
6239   if (TARGET_SOM || ! TARGET_GAS)
6240     {
6241       output_asm_insn (\"addil L%%$$dyncall-%1,%%r1\", xoperands);
6242       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
6243                                  CODE_LABEL_NUMBER (xoperands[1]));
6244       output_asm_insn (\"ldo R%%$$dyncall-%1(%%r1),%%r1\", xoperands);
6245     }
6246   else
6247     {
6248       output_asm_insn (\"addil L%%$$dyncall-$PIC_pcrel$0+4,%%r1\", xoperands);
6249       output_asm_insn (\"ldo R%%$$dyncall-$PIC_pcrel$0+8(%%r1),%%r1\",
6250                        xoperands);
6251     }
6252   output_asm_insn (\"blr %%r0,%%r2\", xoperands);
6253   output_asm_insn (\"bv,n %%r0(%%r1)\\n\\tnop\", xoperands);
6254   return \"\";
6255 }"
6256   [(set_attr "type" "dyncall")
6257    (set (attr "length")
6258      (cond [
6259 ;; First FAST_INDIRECT_CALLS
6260             (ne (symbol_ref "TARGET_FAST_INDIRECT_CALLS")
6261                 (const_int 0))
6262             (const_int 8)
6263
6264 ;; Target (or stub) within reach
6265             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
6266                      (const_int 240000))
6267                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
6268                      (const_int 0)))
6269             (const_int 8)
6270
6271 ;; Out of reach PIC
6272             (ne (symbol_ref "flag_pic")
6273                 (const_int 0))
6274             (const_int 24)
6275
6276 ;; Out of reach PORTABLE_RUNTIME
6277             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
6278                 (const_int 0))
6279             (const_int 20)]
6280
6281 ;; Out of reach, can use ble
6282           (const_int 12)))])
6283
6284 ;; Call subroutine returning any type.
6285
6286 (define_expand "untyped_call"
6287   [(parallel [(call (match_operand 0 "" "")
6288                     (const_int 0))
6289               (match_operand 1 "" "")
6290               (match_operand 2 "" "")])]
6291   ""
6292   "
6293 {
6294   int i;
6295
6296   emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
6297
6298   for (i = 0; i < XVECLEN (operands[2], 0); i++)
6299     {
6300       rtx set = XVECEXP (operands[2], 0, i);
6301       emit_move_insn (SET_DEST (set), SET_SRC (set));
6302     }
6303
6304   /* The optimizer does not know that the call sets the function value
6305      registers we stored in the result block.  We avoid problems by
6306      claiming that all hard registers are used and clobbered at this
6307      point.  */
6308   emit_insn (gen_blockage ());
6309
6310   DONE;
6311 }")
6312
6313 (define_expand "sibcall"
6314   [(parallel [(call (match_operand:SI 0 "" "")
6315                     (match_operand 1 "" ""))
6316               (clobber (reg:SI 0))])]
6317   "! TARGET_PORTABLE_RUNTIME"
6318   "
6319 {
6320   rtx op;
6321   rtx call_insn;
6322
6323   op = XEXP (operands[0], 0);
6324
6325   /* We do not allow indirect sibling calls.  */
6326   call_insn = emit_call_insn (gen_sibcall_internal_symref (op, operands[1]));
6327
6328   if (flag_pic)
6329     {
6330       use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
6331
6332       /* After each call we must restore the PIC register, even if it
6333          doesn't appear to be used.  */
6334       emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
6335     }
6336   DONE;
6337 }")
6338
6339 (define_insn "sibcall_internal_symref"
6340   [(call (mem:SI (match_operand 0 "call_operand_address" ""))
6341          (match_operand 1 "" "i"))
6342    (clobber (reg:SI 0))
6343    (use (reg:SI 2))
6344    (use (const_int 0))]
6345   "! TARGET_PORTABLE_RUNTIME"
6346   "*
6347 {
6348   output_arg_descriptor (insn);
6349   return output_call (insn, operands[0], 1);
6350 }"
6351   [(set_attr "type" "call")
6352    (set (attr "length")
6353 ;;       If we're sure that we can either reach the target or that the
6354 ;;       linker can use a long-branch stub, then the length is at most
6355 ;;       8 bytes.
6356 ;;
6357 ;;       For long-calls the length will be at most 68 bytes (non-pic)
6358 ;;       or 84 bytes (pic).  */
6359 ;;       Else we have to use a long-call;
6360       (if_then_else (lt (plus (symbol_ref "total_code_bytes") (pc))
6361                         (const_int 240000))
6362                     (const_int 8)
6363                     (if_then_else (eq (symbol_ref "flag_pic")
6364                                       (const_int 0))
6365                                   (const_int 68)
6366                                   (const_int 84))))])
6367
6368 (define_expand "sibcall_value"
6369   [(parallel [(set (match_operand 0 "" "")
6370                    (call (match_operand:SI 1 "" "")
6371                          (match_operand 2 "" "")))
6372               (clobber (reg:SI 0))])]
6373   "! TARGET_PORTABLE_RUNTIME"
6374   "
6375 {
6376   rtx op;
6377   rtx call_insn;
6378
6379   op = XEXP (operands[1], 0);
6380
6381   /* We do not allow indirect sibling calls.  */
6382   call_insn = emit_call_insn (gen_sibcall_value_internal_symref (operands[0],
6383                                                                  op,
6384                                                                  operands[2]));
6385   if (flag_pic)
6386     {
6387       use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
6388
6389       /* After each call we must restore the PIC register, even if it
6390          doesn't appear to be used.  */
6391       emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
6392     }
6393   DONE;
6394 }")
6395
6396 (define_insn "sibcall_value_internal_symref"
6397   [(set (match_operand 0 "" "=rf")
6398         (call (mem:SI (match_operand 1 "call_operand_address" ""))
6399               (match_operand 2 "" "i")))
6400    (clobber (reg:SI 0))
6401    (use (reg:SI 2))
6402    (use (const_int 0))]
6403   ;;- Don't use operand 1 for most machines.
6404   "! TARGET_PORTABLE_RUNTIME"
6405   "*
6406 {
6407   output_arg_descriptor (insn);
6408   return output_call (insn, operands[1], 1);
6409 }"
6410   [(set_attr "type" "call")
6411    (set (attr "length")
6412 ;;       If we're sure that we can either reach the target or that the
6413 ;;       linker can use a long-branch stub, then the length is at most
6414 ;;       8 bytes.
6415 ;;
6416 ;;       For long-calls the length will be at most 68 bytes (non-pic)
6417 ;;       or 84 bytes (pic).  */
6418 ;;       Else we have to use a long-call;
6419       (if_then_else (lt (plus (symbol_ref "total_code_bytes") (pc))
6420                         (const_int 240000))
6421                     (const_int 8)
6422                     (if_then_else (eq (symbol_ref "flag_pic")
6423                                       (const_int 0))
6424                                   (const_int 68)
6425                                   (const_int 84))))])
6426
6427 (define_insn "nop"
6428   [(const_int 0)]
6429   ""
6430   "nop"
6431   [(set_attr "type" "move")
6432    (set_attr "length" "4")])
6433
6434 ;; These are just placeholders so we know where branch tables
6435 ;; begin and end.
6436 (define_insn "begin_brtab"
6437   [(const_int 1)]
6438   ""
6439   "*
6440 {
6441   /* Only GAS actually supports this pseudo-op.  */
6442   if (TARGET_GAS)
6443     return \".begin_brtab\";
6444   else
6445     return \"\";
6446 }"
6447   [(set_attr "type" "move")
6448    (set_attr "length" "0")])
6449
6450 (define_insn "end_brtab"
6451   [(const_int 2)]
6452   ""
6453   "*
6454 {
6455   /* Only GAS actually supports this pseudo-op.  */
6456   if (TARGET_GAS)
6457     return \".end_brtab\";
6458   else
6459     return \"\";
6460 }"
6461   [(set_attr "type" "move")
6462    (set_attr "length" "0")])
6463
6464 ;;; EH does longjmp's from and within the data section.  Thus,
6465 ;;; an interspace branch is required for the longjmp implementation.
6466 ;;; Registers r1 and r2 are used as scratch registers for the jump.
6467 (define_expand "interspace_jump"
6468   [(parallel
6469      [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
6470       (clobber (match_dup 1))])]
6471   ""
6472   "
6473 {
6474   operands[1] = gen_rtx_REG (word_mode, 2);
6475 }")
6476
6477 (define_insn ""
6478   [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
6479   (clobber (reg:SI 2))]
6480   "!TARGET_64BIT"
6481   "ldsid (%%sr0,%0),%%r2\; mtsp %%r2,%%sr0\; be%* 0(%%sr0,%0)"
6482    [(set_attr "type" "branch")
6483     (set_attr "length" "12")])
6484
6485 (define_insn ""
6486   [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
6487   (clobber (reg:DI 2))]
6488   "TARGET_64BIT"
6489   "ldsid (%%sr0,%0),%%r2\; mtsp %%r2,%%sr0\; be%* 0(%%sr0,%0)"
6490    [(set_attr "type" "branch")
6491     (set_attr "length" "12")])
6492
6493 (define_expand "builtin_longjmp"
6494   [(unspec_volatile [(match_operand 0 "register_operand" "r")] 3)]
6495   ""
6496   "
6497 {
6498   /* The elements of the buffer are, in order:  */
6499   rtx fp = gen_rtx_MEM (Pmode, operands[0]);
6500   rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0],
6501                          POINTER_SIZE / BITS_PER_UNIT));
6502   rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0],
6503                            (POINTER_SIZE * 2) / BITS_PER_UNIT));
6504   rtx pv = gen_rtx_REG (Pmode, 1);
6505
6506   /* This bit is the same as expand_builtin_longjmp.  */
6507   emit_move_insn (hard_frame_pointer_rtx, fp);
6508   emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
6509   emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
6510   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
6511
6512   /* Load the label we are jumping through into r1 so that we know
6513      where to look for it when we get back to setjmp's function for
6514      restoring the gp.  */
6515   emit_move_insn (pv, lab);
6516
6517   /* Prevent the insns above from being scheduled into the delay slot
6518      of the interspace jump because the space register could change.  */
6519   emit_insn (gen_blockage ());
6520
6521   emit_jump_insn (gen_interspace_jump (pv));
6522   emit_barrier ();
6523   DONE;
6524 }")
6525
6526 ;;; Hope this is only within a function...
6527 (define_insn "indirect_jump"
6528   [(set (pc) (match_operand 0 "register_operand" "r"))]
6529   "GET_MODE (operands[0]) == word_mode"
6530   "bv%* %%r0(%0)"
6531   [(set_attr "type" "branch")
6532    (set_attr "length" "4")])
6533
6534 (define_expand "extzv"
6535   [(set (match_operand 0 "register_operand" "")
6536         (zero_extract (match_operand 1 "register_operand" "")
6537                       (match_operand 2 "uint32_operand" "")
6538                       (match_operand 3 "uint32_operand" "")))]
6539   ""
6540   "
6541 {
6542   if (TARGET_64BIT)
6543     emit_insn (gen_extzv_64 (operands[0], operands[1],
6544                              operands[2], operands[3]));
6545   else
6546     emit_insn (gen_extzv_32 (operands[0], operands[1],
6547                              operands[2], operands[3]));
6548   DONE;
6549 }")
6550
6551 (define_insn "extzv_32"
6552   [(set (match_operand:SI 0 "register_operand" "=r")
6553         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
6554                          (match_operand:SI 2 "uint5_operand" "")
6555                          (match_operand:SI 3 "uint5_operand" "")))]
6556   ""
6557   "{extru|extrw,u} %1,%3+%2-1,%2,%0"
6558   [(set_attr "type" "shift")
6559    (set_attr "length" "4")])
6560
6561 (define_insn ""
6562   [(set (match_operand:SI 0 "register_operand" "=r")
6563         (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
6564                          (const_int 1)
6565                          (match_operand:SI 2 "register_operand" "q")))]
6566   ""
6567   "{vextru %1,1,%0|extrw,u %1,%%sar,1,%0}"
6568   [(set_attr "type" "shift")
6569    (set_attr "length" "4")])
6570
6571 (define_insn "extzv_64"
6572   [(set (match_operand:DI 0 "register_operand" "=r")
6573         (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
6574                          (match_operand:DI 2 "uint32_operand" "")
6575                          (match_operand:DI 3 "uint32_operand" "")))]
6576   "TARGET_64BIT"
6577   "extrd,u %1,%3+%2-1,%2,%0"
6578   [(set_attr "type" "shift")
6579    (set_attr "length" "4")])
6580
6581 (define_insn ""
6582   [(set (match_operand:DI 0 "register_operand" "=r")
6583         (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
6584                          (const_int 1)
6585                          (match_operand:DI 2 "register_operand" "q")))]
6586   "TARGET_64BIT"
6587   "extrd,u %1,%%sar,1,%0"
6588   [(set_attr "type" "shift")
6589    (set_attr "length" "4")])
6590
6591 (define_expand "extv"
6592   [(set (match_operand 0 "register_operand" "")
6593         (sign_extract (match_operand 1 "register_operand" "")
6594                       (match_operand 2 "uint32_operand" "")
6595                       (match_operand 3 "uint32_operand" "")))]
6596   ""
6597   "
6598 {
6599   if (TARGET_64BIT)
6600     emit_insn (gen_extv_64 (operands[0], operands[1],
6601                             operands[2], operands[3]));
6602   else
6603     emit_insn (gen_extv_32 (operands[0], operands[1],
6604                             operands[2], operands[3]));
6605   DONE;
6606 }")
6607
6608 (define_insn "extv_32"
6609   [(set (match_operand:SI 0 "register_operand" "=r")
6610         (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
6611                          (match_operand:SI 2 "uint5_operand" "")
6612                          (match_operand:SI 3 "uint5_operand" "")))]
6613   ""
6614   "{extrs|extrw,s} %1,%3+%2-1,%2,%0"
6615   [(set_attr "type" "shift")
6616    (set_attr "length" "4")])
6617
6618 (define_insn ""
6619   [(set (match_operand:SI 0 "register_operand" "=r")
6620         (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
6621                          (const_int 1)
6622                          (match_operand:SI 2 "register_operand" "q")))]
6623   "!TARGET_64BIT"
6624   "{vextrs %1,1,%0|extrw,s %1,%%sar,1,%0}"
6625   [(set_attr "type" "shift")
6626    (set_attr "length" "4")])
6627
6628 (define_insn "extv_64"
6629   [(set (match_operand:DI 0 "register_operand" "=r")
6630         (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
6631                          (match_operand:DI 2 "uint32_operand" "")
6632                          (match_operand:DI 3 "uint32_operand" "")))]
6633   "TARGET_64BIT"
6634   "extrd,s %1,%3+%2-1,%2,%0"
6635   [(set_attr "type" "shift")
6636    (set_attr "length" "4")])
6637
6638 (define_insn ""
6639   [(set (match_operand:DI 0 "register_operand" "=r")
6640         (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
6641                          (const_int 1)
6642                          (match_operand:DI 2 "register_operand" "q")))]
6643   "TARGET_64BIT"
6644   "extrd,s %1,%%sar,1,%0"
6645   [(set_attr "type" "shift")
6646    (set_attr "length" "4")])
6647
6648 ;; Only specify the mode operands 0, the rest are assumed to be word_mode.
6649 (define_expand "insv"
6650   [(set (zero_extract (match_operand 0 "register_operand" "")
6651                       (match_operand 1 "uint32_operand" "")
6652                       (match_operand 2 "uint32_operand" ""))
6653         (match_operand 3 "arith5_operand" ""))]
6654   ""
6655   "
6656 {
6657   if (TARGET_64BIT)
6658     emit_insn (gen_insv_64 (operands[0], operands[1],
6659                             operands[2], operands[3]));
6660   else
6661     emit_insn (gen_insv_32 (operands[0], operands[1],
6662                             operands[2], operands[3]));
6663   DONE;
6664 }")
6665
6666 (define_insn "insv_32"
6667   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r,r")
6668                          (match_operand:SI 1 "uint5_operand" "")
6669                          (match_operand:SI 2 "uint5_operand" ""))
6670         (match_operand:SI 3 "arith5_operand" "r,L"))]
6671   ""
6672   "@
6673    {dep|depw} %3,%2+%1-1,%1,%0
6674    {depi|depwi} %3,%2+%1-1,%1,%0"
6675   [(set_attr "type" "shift,shift")
6676    (set_attr "length" "4,4")])
6677
6678 ;; Optimize insertion of const_int values of type 1...1xxxx.
6679 (define_insn ""
6680   [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
6681                          (match_operand:SI 1 "uint5_operand" "")
6682                          (match_operand:SI 2 "uint5_operand" ""))
6683         (match_operand:SI 3 "const_int_operand" ""))]
6684   "(INTVAL (operands[3]) & 0x10) != 0 &&
6685    (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
6686   "*
6687 {
6688   operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
6689   return \"{depi|depwi} %3,%2+%1-1,%1,%0\";
6690 }"
6691   [(set_attr "type" "shift")
6692    (set_attr "length" "4")])
6693
6694 (define_insn "insv_64"
6695   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r,r")
6696                          (match_operand:DI 1 "uint32_operand" "")
6697                          (match_operand:DI 2 "uint32_operand" ""))
6698         (match_operand:DI 3 "arith32_operand" "r,L"))]
6699   "TARGET_64BIT"
6700   "@
6701    depd %3,%2+%1-1,%1,%0
6702    depdi %3,%2+%1-1,%1,%0"
6703   [(set_attr "type" "shift,shift")
6704    (set_attr "length" "4,4")])
6705
6706 ;; Optimize insertion of const_int values of type 1...1xxxx.
6707 (define_insn ""
6708   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
6709                          (match_operand:DI 1 "uint32_operand" "")
6710                          (match_operand:DI 2 "uint32_operand" ""))
6711         (match_operand:DI 3 "const_int_operand" ""))]
6712   "(INTVAL (operands[3]) & 0x10) != 0
6713    && TARGET_64BIT
6714    && (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
6715   "*
6716 {
6717   operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
6718   return \"depdi %3,%2+%1-1,%1,%0\";
6719 }"
6720   [(set_attr "type" "shift")
6721    (set_attr "length" "4")])
6722
6723 (define_insn ""
6724   [(set (match_operand:DI 0 "register_operand" "=r")
6725         (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
6726                    (const_int 32)))]
6727   "TARGET_64BIT"
6728   "depd,z %1,31,32,%0"
6729   [(set_attr "type" "shift")
6730    (set_attr "length" "4")])
6731
6732 ;; This insn is used for some loop tests, typically loops reversed when
6733 ;; strength reduction is used.  It is actually created when the instruction
6734 ;; combination phase combines the special loop test.  Since this insn
6735 ;; is both a jump insn and has an output, it must deal with its own
6736 ;; reloads, hence the `m' constraints.  The `!' constraints direct reload
6737 ;; to not choose the register alternatives in the event a reload is needed.
6738 (define_insn "decrement_and_branch_until_zero"
6739   [(set (pc)
6740         (if_then_else
6741           (match_operator 2 "comparison_operator"
6742            [(plus:SI
6743               (match_operand:SI 0 "reg_before_reload_operand" "+!r,!*f,*m")
6744               (match_operand:SI 1 "int5_operand" "L,L,L"))
6745             (const_int 0)])
6746           (label_ref (match_operand 3 "" ""))
6747           (pc)))
6748    (set (match_dup 0)
6749         (plus:SI (match_dup 0) (match_dup 1)))
6750    (clobber (match_scratch:SI 4 "=X,r,r"))]
6751   ""
6752   "* return output_dbra (operands, insn, which_alternative); "
6753 ;; Do not expect to understand this the first time through.
6754 [(set_attr "type" "cbranch,multi,multi")
6755  (set (attr "length")
6756       (if_then_else (eq_attr "alternative" "0")
6757 ;; Loop counter in register case
6758 ;; Short branch has length of 4
6759 ;; Long branch has length of 8
6760         (if_then_else (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6761                       (const_int 8184))
6762            (const_int 4)
6763            (const_int 8))
6764
6765 ;; Loop counter in FP reg case.
6766 ;; Extra goo to deal with additional reload insns.
6767         (if_then_else (eq_attr "alternative" "1")
6768           (if_then_else (lt (match_dup 3) (pc))
6769             (if_then_else
6770               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 24))))
6771                   (const_int 8184))
6772               (const_int 24)
6773               (const_int 28))
6774             (if_then_else
6775               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6776                   (const_int 8184))
6777               (const_int 24)
6778               (const_int 28)))
6779 ;; Loop counter in memory case.
6780 ;; Extra goo to deal with additional reload insns.
6781         (if_then_else (lt (match_dup 3) (pc))
6782           (if_then_else
6783             (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
6784                 (const_int 8184))
6785             (const_int 12)
6786             (const_int 16))
6787           (if_then_else
6788             (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6789                 (const_int 8184))
6790             (const_int 12)
6791             (const_int 16))))))])
6792
6793 (define_insn ""
6794   [(set (pc)
6795         (if_then_else
6796           (match_operator 2 "movb_comparison_operator"
6797            [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
6798           (label_ref (match_operand 3 "" ""))
6799           (pc)))
6800    (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*m,!*q")
6801         (match_dup 1))]
6802   ""
6803 "* return output_movb (operands, insn, which_alternative, 0); "
6804 ;; Do not expect to understand this the first time through.
6805 [(set_attr "type" "cbranch,multi,multi,multi")
6806  (set (attr "length")
6807       (if_then_else (eq_attr "alternative" "0")
6808 ;; Loop counter in register case
6809 ;; Short branch has length of 4
6810 ;; Long branch has length of 8
6811         (if_then_else (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6812                       (const_int 8184))
6813            (const_int 4)
6814            (const_int 8))
6815
6816 ;; Loop counter in FP reg case.
6817 ;; Extra goo to deal with additional reload insns.
6818         (if_then_else (eq_attr "alternative" "1")
6819           (if_then_else (lt (match_dup 3) (pc))
6820             (if_then_else
6821               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
6822                   (const_int 8184))
6823               (const_int 12)
6824               (const_int 16))
6825             (if_then_else
6826               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6827                   (const_int 8184))
6828               (const_int 12)
6829               (const_int 16)))
6830 ;; Loop counter in memory or sar case.
6831 ;; Extra goo to deal with additional reload insns.
6832         (if_then_else
6833           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6834               (const_int 8184))
6835           (const_int 8)
6836           (const_int 12)))))])
6837
6838 ;; Handle negated branch.
6839 (define_insn ""
6840   [(set (pc)
6841         (if_then_else
6842           (match_operator 2 "movb_comparison_operator"
6843            [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
6844           (pc)
6845           (label_ref (match_operand 3 "" ""))))
6846    (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*m,!*q")
6847         (match_dup 1))]
6848   ""
6849 "* return output_movb (operands, insn, which_alternative, 1); "
6850 ;; Do not expect to understand this the first time through.
6851 [(set_attr "type" "cbranch,multi,multi,multi")
6852  (set (attr "length")
6853       (if_then_else (eq_attr "alternative" "0")
6854 ;; Loop counter in register case
6855 ;; Short branch has length of 4
6856 ;; Long branch has length of 8
6857         (if_then_else (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6858                       (const_int 8184))
6859            (const_int 4)
6860            (const_int 8))
6861
6862 ;; Loop counter in FP reg case.
6863 ;; Extra goo to deal with additional reload insns.
6864         (if_then_else (eq_attr "alternative" "1")
6865           (if_then_else (lt (match_dup 3) (pc))
6866             (if_then_else
6867               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
6868                   (const_int 8184))
6869               (const_int 12)
6870               (const_int 16))
6871             (if_then_else
6872               (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6873                   (const_int 8184))
6874               (const_int 12)
6875               (const_int 16)))
6876 ;; Loop counter in memory or SAR case.
6877 ;; Extra goo to deal with additional reload insns.
6878         (if_then_else
6879           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6880               (const_int 8184))
6881           (const_int 8)
6882           (const_int 12)))))])
6883
6884 (define_insn ""
6885   [(set (pc) (label_ref (match_operand 3 "" "" )))
6886    (set (match_operand:SI 0 "ireg_operand" "=r")
6887         (plus:SI (match_operand:SI 1 "ireg_operand" "r")
6888                  (match_operand:SI 2 "ireg_or_int5_operand" "rL")))]
6889   "(reload_completed && operands[0] == operands[1]) || operands[0] == operands[2]"
6890   "*
6891 {
6892   return output_parallel_addb (operands, get_attr_length (insn));
6893 }"
6894   [(set_attr "type" "parallel_branch")
6895    (set (attr "length")
6896     (if_then_else (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
6897                       (const_int 8184))
6898            (const_int 4)
6899            (const_int 8)))])
6900
6901 (define_insn ""
6902   [(set (pc) (label_ref (match_operand 2 "" "" )))
6903    (set (match_operand:SF 0 "ireg_operand" "=r")
6904         (match_operand:SF 1 "ireg_or_int5_operand" "rL"))]
6905   "reload_completed"
6906   "*
6907 {
6908   return output_parallel_movb (operands, get_attr_length (insn));
6909 }"
6910   [(set_attr "type" "parallel_branch")
6911    (set (attr "length")
6912     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
6913                       (const_int 8184))
6914            (const_int 4)
6915            (const_int 8)))])
6916
6917 (define_insn ""
6918   [(set (pc) (label_ref (match_operand 2 "" "" )))
6919    (set (match_operand:SI 0 "ireg_operand" "=r")
6920         (match_operand:SI 1 "ireg_or_int5_operand" "rL"))]
6921   "reload_completed"
6922   "*
6923 {
6924   return output_parallel_movb (operands, get_attr_length (insn));
6925 }"
6926   [(set_attr "type" "parallel_branch")
6927    (set (attr "length")
6928     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
6929                       (const_int 8184))
6930            (const_int 4)
6931            (const_int 8)))])
6932
6933 (define_insn ""
6934   [(set (pc) (label_ref (match_operand 2 "" "" )))
6935    (set (match_operand:HI 0 "ireg_operand" "=r")
6936         (match_operand:HI 1 "ireg_or_int5_operand" "rL"))]
6937   "reload_completed"
6938   "*
6939 {
6940   return output_parallel_movb (operands, get_attr_length (insn));
6941 }"
6942   [(set_attr "type" "parallel_branch")
6943    (set (attr "length")
6944     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
6945                       (const_int 8184))
6946            (const_int 4)
6947            (const_int 8)))])
6948
6949 (define_insn ""
6950   [(set (pc) (label_ref (match_operand 2 "" "" )))
6951    (set (match_operand:QI 0 "ireg_operand" "=r")
6952         (match_operand:QI 1 "ireg_or_int5_operand" "rL"))]
6953   "reload_completed"
6954   "*
6955 {
6956   return output_parallel_movb (operands, get_attr_length (insn));
6957 }"
6958   [(set_attr "type" "parallel_branch")
6959    (set (attr "length")
6960     (if_then_else (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
6961                       (const_int 8184))
6962            (const_int 4)
6963            (const_int 8)))])
6964
6965 (define_insn ""
6966   [(set (match_operand 0 "register_operand" "=f")
6967         (mult (match_operand 1 "register_operand" "f")
6968               (match_operand 2 "register_operand" "f")))
6969    (set (match_operand 3 "register_operand" "+f")
6970         (plus (match_operand 4 "register_operand" "f")
6971               (match_operand 5 "register_operand" "f")))]
6972   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
6973    && reload_completed && fmpyaddoperands (operands)"
6974   "*
6975 {
6976   if (GET_MODE (operands[0]) == DFmode)
6977     {
6978       if (rtx_equal_p (operands[3], operands[5]))
6979         return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
6980       else
6981         return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
6982     }
6983   else
6984     {
6985       if (rtx_equal_p (operands[3], operands[5]))
6986         return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
6987       else
6988         return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
6989     }
6990 }"
6991   [(set_attr "type" "fpalu")
6992    (set_attr "length" "4")])
6993
6994 (define_insn ""
6995   [(set (match_operand 3 "register_operand" "+f")
6996         (plus (match_operand 4 "register_operand" "f")
6997               (match_operand 5 "register_operand" "f")))
6998    (set (match_operand 0 "register_operand" "=f")
6999         (mult (match_operand 1 "register_operand" "f")
7000               (match_operand 2 "register_operand" "f")))]
7001   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
7002    && reload_completed && fmpyaddoperands (operands)"
7003   "*
7004 {
7005   if (GET_MODE (operands[0]) == DFmode)
7006     {
7007       if (rtx_equal_p (operands[3], operands[5]))
7008         return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
7009       else
7010         return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
7011     }
7012   else
7013     {
7014       if (rtx_equal_p (operands[3], operands[5]))
7015         return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
7016       else
7017         return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
7018     }
7019 }"
7020   [(set_attr "type" "fpalu")
7021    (set_attr "length" "4")])
7022
7023 (define_insn ""
7024   [(set (match_operand 0 "register_operand" "=f")
7025         (mult (match_operand 1 "register_operand" "f")
7026               (match_operand 2 "register_operand" "f")))
7027    (set (match_operand 3 "register_operand" "+f")
7028         (minus (match_operand 4 "register_operand" "f")
7029                (match_operand 5 "register_operand" "f")))]
7030   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
7031    && reload_completed && fmpysuboperands (operands)"
7032   "*
7033 {
7034   if (GET_MODE (operands[0]) == DFmode)
7035     return \"fmpysub,dbl %1,%2,%0,%5,%3\";
7036   else
7037     return \"fmpysub,sgl %1,%2,%0,%5,%3\";
7038 }"
7039   [(set_attr "type" "fpalu")
7040    (set_attr "length" "4")])
7041
7042 (define_insn ""
7043   [(set (match_operand 3 "register_operand" "+f")
7044         (minus (match_operand 4 "register_operand" "f")
7045                (match_operand 5 "register_operand" "f")))
7046    (set (match_operand 0 "register_operand" "=f")
7047         (mult (match_operand 1 "register_operand" "f")
7048               (match_operand 2 "register_operand" "f")))]
7049   "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
7050    && reload_completed && fmpysuboperands (operands)"
7051   "*
7052 {
7053   if (GET_MODE (operands[0]) == DFmode)
7054     return \"fmpysub,dbl %1,%2,%0,%5,%3\";
7055   else
7056     return \"fmpysub,sgl %1,%2,%0,%5,%3\";
7057 }"
7058   [(set_attr "type" "fpalu")
7059    (set_attr "length" "4")])
7060
7061 ;; Clean up turds left by reload.
7062 (define_peephole
7063   [(set (match_operand 0 "reg_or_nonsymb_mem_operand" "")
7064         (match_operand 1 "register_operand" "fr"))
7065    (set (match_operand 2 "register_operand" "fr")
7066         (match_dup 0))]
7067   "! TARGET_SOFT_FLOAT
7068    && GET_CODE (operands[0]) == MEM
7069    && ! MEM_VOLATILE_P (operands[0])
7070    && GET_MODE (operands[0]) == GET_MODE (operands[1])
7071    && GET_MODE (operands[0]) == GET_MODE (operands[2])
7072    && GET_MODE (operands[0]) == DFmode
7073    && GET_CODE (operands[1]) == REG
7074    && GET_CODE (operands[2]) == REG
7075    && ! side_effects_p (XEXP (operands[0], 0))
7076    && REGNO_REG_CLASS (REGNO (operands[1]))
7077       == REGNO_REG_CLASS (REGNO (operands[2]))"
7078   "*
7079 {
7080   rtx xoperands[2];
7081
7082   if (FP_REG_P (operands[1]))
7083     output_asm_insn (output_fp_move_double (operands), operands);
7084   else
7085     output_asm_insn (output_move_double (operands), operands);
7086
7087   if (rtx_equal_p (operands[1], operands[2]))
7088     return \"\";
7089
7090   xoperands[0] = operands[2];
7091   xoperands[1] = operands[1];
7092       
7093   if (FP_REG_P (xoperands[1]))
7094     output_asm_insn (output_fp_move_double (xoperands), xoperands);
7095   else
7096     output_asm_insn (output_move_double (xoperands), xoperands);
7097
7098   return \"\";
7099 }")
7100
7101 (define_peephole
7102   [(set (match_operand 0 "register_operand" "fr")
7103         (match_operand 1 "reg_or_nonsymb_mem_operand" ""))
7104    (set (match_operand 2 "register_operand" "fr")
7105         (match_dup 1))]
7106   "! TARGET_SOFT_FLOAT
7107    && GET_CODE (operands[1]) == MEM
7108    && ! MEM_VOLATILE_P (operands[1])
7109    && GET_MODE (operands[0]) == GET_MODE (operands[1])
7110    && GET_MODE (operands[0]) == GET_MODE (operands[2])
7111    && GET_MODE (operands[0]) == DFmode
7112    && GET_CODE (operands[0]) == REG
7113    && GET_CODE (operands[2]) == REG
7114    && ! side_effects_p (XEXP (operands[1], 0))
7115    && REGNO_REG_CLASS (REGNO (operands[0]))
7116       == REGNO_REG_CLASS (REGNO (operands[2]))"
7117   "*
7118 {
7119   rtx xoperands[2];
7120
7121   if (FP_REG_P (operands[0]))
7122     output_asm_insn (output_fp_move_double (operands), operands);
7123   else
7124     output_asm_insn (output_move_double (operands), operands);
7125
7126   xoperands[0] = operands[2];
7127   xoperands[1] = operands[0];
7128       
7129   if (FP_REG_P (xoperands[1]))
7130     output_asm_insn (output_fp_move_double (xoperands), xoperands);
7131   else
7132     output_asm_insn (output_move_double (xoperands), xoperands);
7133
7134   return \"\";
7135 }")
7136
7137 ;; Flush the I and D cache line found at the address in operand 0.
7138 ;; This is used by the trampoline code for nested functions.
7139 ;; So long as the trampoline itself is less than 32 bytes this
7140 ;; is sufficient.
7141
7142 (define_insn "dcacheflush"
7143   [(unspec_volatile [(const_int 1)] 0)
7144    (use (mem:SI (match_operand 0 "pmode_register_operand" "r")))
7145    (use (mem:SI (match_operand 1 "pmode_register_operand" "r")))]
7146   ""
7147   "fdc 0(%0)\;fdc 0(%1)\;sync"
7148   [(set_attr "type" "multi")
7149    (set_attr "length" "12")])
7150
7151 (define_insn "icacheflush"
7152   [(unspec_volatile [(const_int 2)] 0)
7153    (use (mem:SI (match_operand 0 "pmode_register_operand" "r")))
7154    (use (mem:SI (match_operand 1 "pmode_register_operand" "r")))
7155    (use (match_operand 2 "pmode_register_operand" "r"))
7156    (clobber (match_operand 3 "pmode_register_operand" "=&r"))
7157    (clobber (match_operand 4 "pmode_register_operand" "=&r"))]
7158   ""
7159   "mfsp %%sr0,%4\;ldsid (%2),%3\;mtsp %3,%%sr0\;fic 0(%%sr0,%0)\;fic 0(%%sr0,%1)\;sync\;mtsp %4,%%sr0\;nop\;nop\;nop\;nop\;nop\;nop"
7160   [(set_attr "type" "multi")
7161    (set_attr "length" "52")])
7162
7163 ;; An out-of-line prologue.
7164 (define_insn "outline_prologue_call"
7165   [(unspec_volatile [(const_int 0)] 0)
7166    (clobber (reg:SI 31))
7167    (clobber (reg:SI 22))
7168    (clobber (reg:SI 21))
7169    (clobber (reg:SI 20))
7170    (clobber (reg:SI 19))
7171    (clobber (reg:SI 1))]
7172   ""
7173   "*
7174 {
7175   extern int frame_pointer_needed;
7176
7177   /* We need two different versions depending on whether or not we
7178      need a frame pointer.   Also note that we return to the instruction
7179      immediately after the branch rather than two instructions after the
7180      break as normally is the case.  */
7181   if (frame_pointer_needed)
7182     {
7183       /* Must import the magic millicode routine(s).  */
7184       output_asm_insn (\".IMPORT __outline_prologue_fp,MILLICODE\", NULL);
7185
7186       if (TARGET_PORTABLE_RUNTIME)
7187         {
7188           output_asm_insn (\"ldil L'__outline_prologue_fp,%%r31\", NULL);
7189           output_asm_insn (\"ble,n R'__outline_prologue_fp(%%sr0,%%r31)\",
7190                            NULL);
7191         }
7192       else
7193         output_asm_insn (\"{bl|b,l},n __outline_prologue_fp,%%r31\", NULL);
7194     }
7195   else
7196     {
7197       /* Must import the magic millicode routine(s).  */
7198       output_asm_insn (\".IMPORT __outline_prologue,MILLICODE\", NULL);
7199
7200       if (TARGET_PORTABLE_RUNTIME)
7201         {
7202           output_asm_insn (\"ldil L'__outline_prologue,%%r31\", NULL);
7203           output_asm_insn (\"ble,n R'__outline_prologue(%%sr0,%%r31)\", NULL);
7204         }
7205       else
7206         output_asm_insn (\"{bl|b,l},n __outline_prologue,%%r31\", NULL);
7207     }
7208   return \"\";
7209 }"
7210   [(set_attr "type" "multi")
7211    (set_attr "length" "8")])
7212
7213 ;; An out-of-line epilogue.
7214 (define_insn "outline_epilogue_call"
7215   [(unspec_volatile [(const_int 1)] 0)
7216    (use (reg:SI 29))
7217    (use (reg:SI 28))
7218    (clobber (reg:SI 31))
7219    (clobber (reg:SI 22))
7220    (clobber (reg:SI 21))
7221    (clobber (reg:SI 20))
7222    (clobber (reg:SI 19))
7223    (clobber (reg:SI 2))
7224    (clobber (reg:SI 1))]
7225   ""
7226   "*
7227 {
7228   extern int frame_pointer_needed;
7229
7230   /* We need two different versions depending on whether or not we
7231      need a frame pointer.   Also note that we return to the instruction
7232      immediately after the branch rather than two instructions after the
7233      break as normally is the case.  */
7234   if (frame_pointer_needed)
7235     {
7236       /* Must import the magic millicode routine.  */
7237       output_asm_insn (\".IMPORT __outline_epilogue_fp,MILLICODE\", NULL);
7238
7239       /* The out-of-line prologue will make sure we return to the right
7240          instruction.  */
7241       if (TARGET_PORTABLE_RUNTIME)
7242         {
7243           output_asm_insn (\"ldil L'__outline_epilogue_fp,%%r31\", NULL);
7244           output_asm_insn (\"ble,n R'__outline_epilogue_fp(%%sr0,%%r31)\",
7245                            NULL);
7246         }
7247       else
7248         output_asm_insn (\"{bl|b,l},n __outline_epilogue_fp,%%r31\", NULL);
7249     }
7250   else
7251     {
7252       /* Must import the magic millicode routine.  */
7253       output_asm_insn (\".IMPORT __outline_epilogue,MILLICODE\", NULL);
7254
7255       /* The out-of-line prologue will make sure we return to the right
7256          instruction.  */
7257       if (TARGET_PORTABLE_RUNTIME)
7258         {
7259           output_asm_insn (\"ldil L'__outline_epilogue,%%r31\", NULL);
7260           output_asm_insn (\"ble,n R'__outline_epilogue(%%sr0,%%r31)\", NULL);
7261         }
7262       else
7263         output_asm_insn (\"{bl|b,l},n __outline_epilogue,%%r31\", NULL);
7264     }
7265   return \"\";
7266 }"
7267   [(set_attr "type" "multi")
7268    (set_attr "length" "8")])
7269
7270 ;; Given a function pointer, canonicalize it so it can be 
7271 ;; reliably compared to another function pointer.  */
7272 (define_expand "canonicalize_funcptr_for_compare"
7273   [(set (reg:SI 26) (match_operand:SI 1 "register_operand" ""))
7274    (parallel [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] 0))
7275               (clobber (match_dup 2))
7276               (clobber (reg:SI 26))
7277               (clobber (reg:SI 22))
7278               (clobber (reg:SI 31))])
7279    (set (match_operand:SI 0 "register_operand" "")
7280         (reg:SI 29))]
7281   "! TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && !TARGET_ELF32"
7282   "
7283 {
7284   operands[2] = gen_reg_rtx (SImode);
7285   if (GET_CODE (operands[1]) != REG)
7286     {
7287       rtx tmp = gen_reg_rtx (Pmode);
7288       emit_move_insn (tmp, operands[1]);
7289       operands[1] = tmp;
7290     }
7291 }")
7292
7293 (define_insn ""
7294   [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] 0))
7295    (clobber (match_operand:SI 0 "register_operand" "=a"))
7296    (clobber (reg:SI 26))
7297    (clobber (reg:SI 22))
7298    (clobber (reg:SI 31))]
7299   "!TARGET_64BIT"
7300   "*
7301 {
7302   /* Must import the magic millicode routine.  */
7303   output_asm_insn (\".IMPORT $$sh_func_adrs,MILLICODE\", NULL);
7304
7305   /* This is absolutely amazing.
7306
7307      First, copy our input parameter into %r29 just in case we don't
7308      need to call $$sh_func_adrs.  */
7309   output_asm_insn (\"copy %%r26,%%r29\", NULL);
7310
7311   /* Next, examine the low two bits in %r26, if they aren't 0x2, then
7312      we use %r26 unchanged.  */
7313   if (get_attr_length (insn) == 32)
7314     output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\;{comib|cmpib},<>,n 2,%%r31,.+24\", NULL);
7315   else if (get_attr_length (insn) == 40)
7316     output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\;{comib|cmpib},<>,n 2,%%r31,.+32\", NULL);
7317   else if (get_attr_length (insn) == 44)
7318     output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\;{comib|cmpib},<>,n 2,%%r31,.+36\", NULL);
7319   else
7320     output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\;{comib|cmpib},<>,n 2,%%r31,.+20\", NULL);
7321
7322   /* Next, compare %r26 with 4096, if %r26 is less than or equal to
7323      4096, then we use %r26 unchanged.  */
7324   if (get_attr_length (insn) == 32)
7325     output_asm_insn (\"ldi 4096,%%r31\;{comb|cmpb},<<,n %%r26,%%r31,.+16\",
7326                      NULL);
7327   else if (get_attr_length (insn) == 40)
7328     output_asm_insn (\"ldi 4096,%%r31\;{comb|cmpb},<<,n %%r26,%%r31,.+24\",
7329                      NULL);
7330   else if (get_attr_length (insn) == 44)
7331     output_asm_insn (\"ldi 4096,%%r31\;{comb|cmpb},<<,n %%r26,%%r31,.+28\",
7332                      NULL);
7333   else
7334     output_asm_insn (\"ldi 4096,%%r31\;{comb|cmpb},<<,n %%r26,%%r31,.+12\",
7335                      NULL);
7336
7337   /* Else call $$sh_func_adrs to extract the function's real add24.  */
7338   return output_millicode_call (insn,
7339                                 gen_rtx_SYMBOL_REF (SImode,
7340                                          \"$$sh_func_adrs\"));
7341 }"
7342   [(set_attr "type" "multi")
7343    (set (attr "length")
7344      (cond [
7345 ;; Target (or stub) within reach
7346             (and (lt (plus (symbol_ref "total_code_bytes") (pc))
7347                      (const_int 240000))
7348                  (eq (symbol_ref "TARGET_PORTABLE_RUNTIME")
7349                      (const_int 0)))
7350             (const_int 28)
7351
7352 ;; Out of reach PIC
7353             (ne (symbol_ref "flag_pic")
7354                 (const_int 0))
7355             (const_int 44)
7356
7357 ;; Out of reach PORTABLE_RUNTIME
7358             (ne (symbol_ref "TARGET_PORTABLE_RUNTIME")
7359                 (const_int 0))
7360             (const_int 40)]
7361
7362 ;; Out of reach, can use ble
7363           (const_int 32)))])
7364
7365 ;; On the PA, the PIC register is call clobbered, so it must
7366 ;; be saved & restored around calls by the caller.  If the call
7367 ;; doesn't return normally (nonlocal goto, or an exception is
7368 ;; thrown), then the code at the exception handler label must
7369 ;; restore the PIC register.
7370 (define_expand "exception_receiver"
7371   [(const_int 4)]
7372   "flag_pic"
7373   "
7374 {
7375   /* Restore the PIC register using hppa_pic_save_rtx ().  The
7376      PIC register is not saved in the frame in 64-bit ABI.  */
7377   emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
7378   DONE;
7379 }")
7380
7381 (define_expand "builtin_setjmp_receiver"
7382   [(label_ref (match_operand 0 "" ""))]
7383   "flag_pic"
7384   "
7385 {
7386   /* Restore the PIC register.  Hopefully, this will always be from
7387      a stack slot.  The only registers that are valid after a
7388      builtin_longjmp are the stack and frame pointers.  */
7389   emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
7390   DONE;
7391 }")