1 ;;- Machine description for HP PA-RISC architecture for GCC compiler
2 ;; Copyright (C) 1992-2015 Free Software Foundation, Inc.
3 ;; Contributed by the Center for Software Science at the University
6 ;; This file is part of GCC.
8 ;; GCC is free software; you can redistribute it and/or modify
9 ;; it under the terms of the GNU General Public License as published by
10 ;; the Free Software Foundation; either version 3, or (at your option)
13 ;; GCC is distributed in the hope that it will be useful,
14 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 ;; GNU General Public License for more details.
18 ;; You should have received a copy of the GNU General Public License
19 ;; along with GCC; see the file COPYING3. If not see
20 ;; <http://www.gnu.org/licenses/>.
22 ;; This machine description is inspired by sparc.md and to a lesser
25 ;; Possible improvements:
27 ;; * With PA1.1, most computational instructions can conditionally nullify
28 ;; the execution of the following instruction. A nullified instruction
29 ;; does not cause the instruction pipeline to stall, making it a very
30 ;; efficient alternative to e.g. branching or conditional moves.
32 ;; Nullification is performed conditionally based on the outcome of a
33 ;; test specified in the opcode. The test result is stored in PSW[N]
34 ;; and can only be used to nullify the instruction following immediately
35 ;; after the test. For example:
39 ;; sub,< %r26,%r25,%r28
40 ;; sub %r28,%r25,%r28 ; %r28 == 0
41 ;; sub,> %r26,%r25,%r29
42 ;; sub %r29,%r25,%r29 ; %r29 == 5
44 ;; This could be tricky to implement because the result of the test has
45 ;; to be propagated one instruction forward, which, in the worst case,
46 ;; would involve (1) adding a fake register for PSW[N]; (2) adding the
47 ;; variants of the computational instructions that set or consume this
48 ;; fake register. The cond_exec infrastructure is probably not helpful
51 ;; * PA-RISC includes a set of conventions for branch instruction usage
52 ;; to indicate whether a particular branch is more likely to be taken
53 ;; or not taken. For example, the prediction for CMPB instructions
54 ;; (CMPB,cond,n r1,r2,target) depends on the direction of the branch
55 ;; (forward or backward) and on the order of the operands:
57 ;; | branch | operand | branch |
58 ;; | direction | compare | prediction |
59 ;; +-----------+----------+------------+
60 ;; | backward | r1 < r2 | taken |
61 ;; | backward | r1 >= r2 | not taken |
62 ;; | forward | r1 < r2 | not taken |
63 ;; | forward | r1 >= r2 | taken |
65 ;; By choosing instructions and operand order carefully, the compiler
66 ;; could give the CPU branch predictor some help.
69 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
71 ;; Uses of UNSPEC in this file:
73 (define_c_enum "unspec"
74 [UNSPEC_CFFC ; canonicalize_funcptr_for_compare
75 UNSPEC_GOTO ; indirect_goto
91 (define_c_enum "unspecv"
92 [UNSPECV_BLOCKAGE ; blockage
93 UNSPECV_DCACHE ; dcacheflush
94 UNSPECV_ICACHE ; icacheflush
95 UNSPECV_OPC ; outline_prologue_call
96 UNSPECV_OEC ; outline_epilogue_call
97 UNSPECV_LONGJMP ; builtin_longjmp
100 ;; Maximum pc-relative branch offsets.
102 ;; These numbers are a bit smaller than the maximum allowable offsets
103 ;; so that a few instructions may be inserted before the actual branch.
106 [(MAX_12BIT_OFFSET 8184) ; 12-bit branch
107 (MAX_17BIT_OFFSET 262100) ; 17-bit branch
110 ;; Mode and code iterators
112 ;; This mode iterator allows :P to be used for patterns that operate on
113 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
114 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
116 ;; This attribute defines the condition prefix for word and double word
117 ;; add, compare, subtract and logical instructions.
118 (define_mode_attr dwc [(SI "") (DI "*")])
120 ;; Insn type. Used to default other attribute values.
122 ;; type "unary" insns have one input operand (1) and one output operand (0)
123 ;; type "binary" insns have two input operands (1,2) and one output (0)
126 "move,unary,binary,shift,nullshift,compare,load,store,uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,fpload,fpstore,fpalu,fpcc,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,multi,milli,sh_func_adrs,parallel_branch,fpstore_load,store_fpload,trap"
127 (const_string "binary"))
129 (define_attr "pa_combine_type"
130 "fmpy,faddsub,uncond_branch,addmove,none"
131 (const_string "none"))
133 ;; Processor type (for scheduling, not code generation) -- this attribute
134 ;; must exactly match the processor_type enumeration in pa.h.
136 ;; FIXME: Add 800 scheduling for completeness?
138 (define_attr "cpu" "700,7100,7100LC,7200,7300,8000" (const (symbol_ref "pa_cpu_attr")))
140 ;; Length (in # of bytes).
141 (define_attr "length" ""
142 (cond [(eq_attr "type" "load,fpload")
143 (if_then_else (match_operand 1 "symbolic_memory_operand" "")
144 (const_int 8) (const_int 4))
146 (eq_attr "type" "store,fpstore")
147 (if_then_else (match_operand 0 "symbolic_memory_operand" "")
148 (const_int 8) (const_int 4))
150 (eq_attr "type" "binary,shift,nullshift")
151 (if_then_else (match_operand 2 "arith14_operand" "")
152 (const_int 4) (const_int 12))
154 (eq_attr "type" "move,unary,shift,nullshift")
155 (if_then_else (match_operand 1 "arith14_operand" "")
156 (const_int 4) (const_int 8))]
160 (define_asm_attributes
161 [(set_attr "length" "4")
162 (set_attr "type" "multi")])
164 ;; Attributes for instruction and branch scheduling
166 ;; For conditional branches. Frame related instructions are not allowed
167 ;; because they confuse the unwind support.
168 (define_attr "in_branch_delay" "false,true"
169 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch,trap")
170 (eq_attr "length" "4")
171 (not (match_test "RTX_FRAME_RELATED_P (insn)")))
172 (const_string "true")
173 (const_string "false")))
175 ;; Disallow instructions which use the FPU since they will tie up the FPU
176 ;; even if the instruction is nullified.
177 (define_attr "in_nullified_branch_delay" "false,true"
178 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,parallel_branch,trap")
179 (eq_attr "length" "4")
180 (not (match_test "RTX_FRAME_RELATED_P (insn)")))
181 (const_string "true")
182 (const_string "false")))
184 ;; For calls and millicode calls.
185 (define_attr "in_call_delay" "false,true"
186 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch,trap")
187 (eq_attr "length" "4")
188 (not (match_test "RTX_FRAME_RELATED_P (insn)")))
189 (const_string "true")
190 (const_string "false")))
192 ;; Call delay slot description.
193 (define_delay (eq_attr "type" "call")
194 [(eq_attr "in_call_delay" "true") (nil) (nil)])
196 ;; Sibcall delay slot description.
197 (define_delay (eq_attr "type" "sibcall")
198 [(eq_attr "in_call_delay" "true") (nil) (nil)])
200 ;; Millicode call delay slot description.
201 (define_delay (eq_attr "type" "milli")
202 [(eq_attr "in_call_delay" "true") (nil) (nil)])
204 ;; Return and other similar instructions.
205 (define_delay (eq_attr "type" "branch,parallel_branch")
206 [(eq_attr "in_branch_delay" "true") (nil) (nil)])
208 ;; Floating point conditional branch delay slot description.
209 (define_delay (eq_attr "type" "fbranch")
210 [(eq_attr "in_branch_delay" "true")
211 (eq_attr "in_nullified_branch_delay" "true")
214 ;; Integer conditional branch delay slot description.
215 ;; Nullification of conditional branches on the PA is dependent on the
216 ;; direction of the branch. Forward branches nullify true and
217 ;; backward branches nullify false. If the direction is unknown
218 ;; then nullification is not allowed.
219 (define_delay (eq_attr "type" "cbranch")
220 [(eq_attr "in_branch_delay" "true")
221 (and (eq_attr "in_nullified_branch_delay" "true")
222 (attr_flag "forward"))
223 (and (eq_attr "in_nullified_branch_delay" "true")
224 (attr_flag "backward"))])
226 (define_delay (eq_attr "type" "uncond_branch")
227 [(eq_attr "in_branch_delay" "true") (nil) (nil)])
229 ;; Memory. Disregarding Cache misses, the Mustang memory times are:
230 ;; load: 2, fpload: 3
231 ;; store, fpstore: 3, no D-cache operations should be scheduled.
233 ;; The Timex (aka 700) has two floating-point units: ALU, and MUL/DIV/SQRT.
235 ;; Instruction Time Unit Minimum Distance (unit contention)
242 ;; fmpyadd 3 ALU,MPY 2
243 ;; fmpysub 3 ALU,MPY 2
244 ;; fmpycfxt 3 ALU,MPY 2
247 ;; fdiv,sgl 10 MPY 10
248 ;; fdiv,dbl 12 MPY 12
249 ;; fsqrt,sgl 14 MPY 14
250 ;; fsqrt,dbl 18 MPY 18
252 ;; We don't model fmpyadd/fmpysub properly as those instructions
253 ;; keep both the FP ALU and MPY units busy. Given that these
254 ;; processors are obsolete, I'm not going to spend the time to
255 ;; model those instructions correctly.
257 (define_automaton "pa700")
258 (define_cpu_unit "dummy_700,mem_700,fpalu_700,fpmpy_700" "pa700")
260 (define_insn_reservation "W0" 4
261 (and (eq_attr "type" "fpcc")
262 (eq_attr "cpu" "700"))
265 (define_insn_reservation "W1" 3
266 (and (eq_attr "type" "fpalu")
267 (eq_attr "cpu" "700"))
270 (define_insn_reservation "W2" 3
271 (and (eq_attr "type" "fpmulsgl,fpmuldbl")
272 (eq_attr "cpu" "700"))
275 (define_insn_reservation "W3" 10
276 (and (eq_attr "type" "fpdivsgl")
277 (eq_attr "cpu" "700"))
280 (define_insn_reservation "W4" 12
281 (and (eq_attr "type" "fpdivdbl")
282 (eq_attr "cpu" "700"))
285 (define_insn_reservation "W5" 14
286 (and (eq_attr "type" "fpsqrtsgl")
287 (eq_attr "cpu" "700"))
290 (define_insn_reservation "W6" 18
291 (and (eq_attr "type" "fpsqrtdbl")
292 (eq_attr "cpu" "700"))
295 (define_insn_reservation "W7" 2
296 (and (eq_attr "type" "load")
297 (eq_attr "cpu" "700"))
300 (define_insn_reservation "W8" 2
301 (and (eq_attr "type" "fpload")
302 (eq_attr "cpu" "700"))
305 (define_insn_reservation "W9" 3
306 (and (eq_attr "type" "store")
307 (eq_attr "cpu" "700"))
310 (define_insn_reservation "W10" 3
311 (and (eq_attr "type" "fpstore")
312 (eq_attr "cpu" "700"))
315 (define_insn_reservation "W11" 5
316 (and (eq_attr "type" "fpstore_load")
317 (eq_attr "cpu" "700"))
320 (define_insn_reservation "W12" 6
321 (and (eq_attr "type" "store_fpload")
322 (eq_attr "cpu" "700"))
325 (define_insn_reservation "W13" 1
326 (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,load,fpload,store,fpstore,fpstore_load,store_fpload")
327 (eq_attr "cpu" "700"))
330 ;; We have a bypass for all computations in the FP unit which feed an
331 ;; FP store as long as the sizes are the same.
332 (define_bypass 2 "W1,W2" "W10,W11" "pa_fpstore_bypass_p")
333 (define_bypass 9 "W3" "W10,W11" "pa_fpstore_bypass_p")
334 (define_bypass 11 "W4" "W10,W11" "pa_fpstore_bypass_p")
335 (define_bypass 13 "W5" "W10,W11" "pa_fpstore_bypass_p")
336 (define_bypass 17 "W6" "W10,W11" "pa_fpstore_bypass_p")
338 ;; We have an "anti-bypass" for FP loads which feed an FP store.
339 (define_bypass 4 "W8,W12" "W10,W11" "pa_fpstore_bypass_p")
341 ;; Function units for the 7100 and 7150. The 7100/7150 can dual-issue
342 ;; floating point computations with non-floating point computations (fp loads
343 ;; and stores are not fp computations).
345 ;; Memory. Disregarding Cache misses, memory loads take two cycles; stores also
346 ;; take two cycles, during which no Dcache operations should be scheduled.
347 ;; Any special cases are handled in pa_adjust_cost. The 7100, 7150 and 7100LC
348 ;; all have the same memory characteristics if one disregards cache misses.
350 ;; The 7100/7150 has three floating-point units: ALU, MUL, and DIV.
351 ;; There's no value in modeling the ALU and MUL separately though
352 ;; since there can never be a functional unit conflict given the
353 ;; latency and issue rates for those units.
356 ;; Instruction Time Unit Minimum Distance (unit contention)
363 ;; fmpyadd 2 ALU,MPY 1
364 ;; fmpysub 2 ALU,MPY 1
365 ;; fmpycfxt 2 ALU,MPY 1
369 ;; fdiv,dbl 15 DIV 15
371 ;; fsqrt,dbl 15 DIV 15
373 (define_automaton "pa7100")
374 (define_cpu_unit "i_7100, f_7100,fpmac_7100,fpdivsqrt_7100,mem_7100" "pa7100")
376 (define_insn_reservation "X0" 2
377 (and (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
378 (eq_attr "cpu" "7100"))
381 (define_insn_reservation "X1" 8
382 (and (eq_attr "type" "fpdivsgl,fpsqrtsgl")
383 (eq_attr "cpu" "7100"))
384 "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*7")
386 (define_insn_reservation "X2" 15
387 (and (eq_attr "type" "fpdivdbl,fpsqrtdbl")
388 (eq_attr "cpu" "7100"))
389 "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*14")
391 (define_insn_reservation "X3" 2
392 (and (eq_attr "type" "load")
393 (eq_attr "cpu" "7100"))
396 (define_insn_reservation "X4" 2
397 (and (eq_attr "type" "fpload")
398 (eq_attr "cpu" "7100"))
401 (define_insn_reservation "X5" 2
402 (and (eq_attr "type" "store")
403 (eq_attr "cpu" "7100"))
404 "i_7100+mem_7100,mem_7100")
406 (define_insn_reservation "X6" 2
407 (and (eq_attr "type" "fpstore")
408 (eq_attr "cpu" "7100"))
409 "i_7100+mem_7100,mem_7100")
411 (define_insn_reservation "X7" 4
412 (and (eq_attr "type" "fpstore_load")
413 (eq_attr "cpu" "7100"))
414 "i_7100+mem_7100,mem_7100*3")
416 (define_insn_reservation "X8" 4
417 (and (eq_attr "type" "store_fpload")
418 (eq_attr "cpu" "7100"))
419 "i_7100+mem_7100,mem_7100*3")
421 (define_insn_reservation "X9" 1
422 (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore,fpstore_load,store_fpload")
423 (eq_attr "cpu" "7100"))
426 ;; We have a bypass for all computations in the FP unit which feed an
427 ;; FP store as long as the sizes are the same.
428 (define_bypass 1 "X0" "X6,X7" "pa_fpstore_bypass_p")
429 (define_bypass 7 "X1" "X6,X7" "pa_fpstore_bypass_p")
430 (define_bypass 14 "X2" "X6,X7" "pa_fpstore_bypass_p")
432 ;; We have an "anti-bypass" for FP loads which feed an FP store.
433 (define_bypass 3 "X4,X8" "X6,X7" "pa_fpstore_bypass_p")
435 ;; The 7100LC has three floating-point units: ALU, MUL, and DIV.
436 ;; There's no value in modeling the ALU and MUL separately though
437 ;; since there can never be a functional unit conflict that
438 ;; can be avoided given the latency, issue rates and mandatory
439 ;; one cycle cpu-wide lock for a double precision fp multiply.
442 ;; Instruction Time Unit Minimum Distance (unit contention)
449 ;; fmpyadd,sgl 2 ALU,MPY 1
450 ;; fmpyadd,dbl 3 ALU,MPY 2
451 ;; fmpysub,sgl 2 ALU,MPY 1
452 ;; fmpysub,dbl 3 ALU,MPY 2
453 ;; fmpycfxt,sgl 2 ALU,MPY 1
454 ;; fmpycfxt,dbl 3 ALU,MPY 2
459 ;; fdiv,dbl 15 DIV 15
461 ;; fsqrt,dbl 15 DIV 15
463 ;; The PA7200 is just like the PA7100LC except that there is
464 ;; no store-store penalty.
466 ;; The PA7300 is just like the PA7200 except that there is
467 ;; no store-load penalty.
469 ;; Note there are some aspects of the 7100LC we are not modeling
470 ;; at the moment. I'll be reviewing the 7100LC scheduling info
471 ;; shortly and updating this description.
475 ;; other issue modeling
477 (define_automaton "pa7100lc")
478 (define_cpu_unit "i0_7100lc, i1_7100lc, f_7100lc" "pa7100lc")
479 (define_cpu_unit "fpmac_7100lc" "pa7100lc")
480 (define_cpu_unit "mem_7100lc" "pa7100lc")
482 ;; Double precision multiplies lock the entire CPU for one
483 ;; cycle. There is no way to avoid this lock and trying to
484 ;; schedule around the lock is pointless and thus there is no
485 ;; value in trying to model this lock.
487 ;; Not modeling the lock allows us to treat fp multiplies just
488 ;; like any other FP alu instruction. It allows for a smaller
489 ;; DFA and may reduce register pressure.
490 (define_insn_reservation "Y0" 2
491 (and (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
492 (eq_attr "cpu" "7100LC,7200,7300"))
493 "f_7100lc,fpmac_7100lc")
495 ;; fp division and sqrt instructions lock the entire CPU for
496 ;; 7 cycles (single precision) or 14 cycles (double precision).
497 ;; There is no way to avoid this lock and trying to schedule
498 ;; around the lock is pointless and thus there is no value in
499 ;; trying to model this lock. Not modeling the lock allows
500 ;; for a smaller DFA and may reduce register pressure.
501 (define_insn_reservation "Y1" 1
502 (and (eq_attr "type" "fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl")
503 (eq_attr "cpu" "7100LC,7200,7300"))
506 (define_insn_reservation "Y2" 2
507 (and (eq_attr "type" "load")
508 (eq_attr "cpu" "7100LC,7200,7300"))
509 "i1_7100lc+mem_7100lc")
511 (define_insn_reservation "Y3" 2
512 (and (eq_attr "type" "fpload")
513 (eq_attr "cpu" "7100LC,7200,7300"))
514 "i1_7100lc+mem_7100lc")
516 (define_insn_reservation "Y4" 2
517 (and (eq_attr "type" "store")
518 (eq_attr "cpu" "7100LC"))
519 "i1_7100lc+mem_7100lc,mem_7100lc")
521 (define_insn_reservation "Y5" 2
522 (and (eq_attr "type" "fpstore")
523 (eq_attr "cpu" "7100LC"))
524 "i1_7100lc+mem_7100lc,mem_7100lc")
526 (define_insn_reservation "Y6" 4
527 (and (eq_attr "type" "fpstore_load")
528 (eq_attr "cpu" "7100LC"))
529 "i1_7100lc+mem_7100lc,mem_7100lc*3")
531 (define_insn_reservation "Y7" 4
532 (and (eq_attr "type" "store_fpload")
533 (eq_attr "cpu" "7100LC"))
534 "i1_7100lc+mem_7100lc,mem_7100lc*3")
536 (define_insn_reservation "Y8" 1
537 (and (eq_attr "type" "shift,nullshift")
538 (eq_attr "cpu" "7100LC,7200,7300"))
541 (define_insn_reservation "Y9" 1
542 (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore,shift,nullshift")
543 (eq_attr "cpu" "7100LC,7200,7300"))
544 "(i0_7100lc|i1_7100lc)")
546 ;; The 7200 has a store-load penalty
547 (define_insn_reservation "Y10" 2
548 (and (eq_attr "type" "store")
549 (eq_attr "cpu" "7200"))
550 "i1_7100lc,mem_7100lc")
552 (define_insn_reservation "Y11" 2
553 (and (eq_attr "type" "fpstore")
554 (eq_attr "cpu" "7200"))
555 "i1_7100lc,mem_7100lc")
557 (define_insn_reservation "Y12" 4
558 (and (eq_attr "type" "fpstore_load")
559 (eq_attr "cpu" "7200"))
560 "i1_7100lc,mem_7100lc,i1_7100lc+mem_7100lc")
562 (define_insn_reservation "Y13" 4
563 (and (eq_attr "type" "store_fpload")
564 (eq_attr "cpu" "7200"))
565 "i1_7100lc,mem_7100lc,i1_7100lc+mem_7100lc")
567 ;; The 7300 has no penalty for store-store or store-load
568 (define_insn_reservation "Y14" 2
569 (and (eq_attr "type" "store")
570 (eq_attr "cpu" "7300"))
573 (define_insn_reservation "Y15" 2
574 (and (eq_attr "type" "fpstore")
575 (eq_attr "cpu" "7300"))
578 (define_insn_reservation "Y16" 4
579 (and (eq_attr "type" "fpstore_load")
580 (eq_attr "cpu" "7300"))
581 "i1_7100lc,i1_7100lc+mem_7100lc")
583 (define_insn_reservation "Y17" 4
584 (and (eq_attr "type" "store_fpload")
585 (eq_attr "cpu" "7300"))
586 "i1_7100lc,i1_7100lc+mem_7100lc")
588 ;; We have an "anti-bypass" for FP loads which feed an FP store.
589 (define_bypass 3 "Y3,Y7,Y13,Y17" "Y5,Y6,Y11,Y12,Y15,Y16" "pa_fpstore_bypass_p")
591 ;; Scheduling for the PA8000 is somewhat different than scheduling for a
592 ;; traditional architecture.
594 ;; The PA8000 has a large (56) entry reorder buffer that is split between
595 ;; memory and non-memory operations.
597 ;; The PA8000 can issue two memory and two non-memory operations per cycle to
598 ;; the function units, with the exception of branches and multi-output
599 ;; instructions. The PA8000 can retire two non-memory operations per cycle
600 ;; and two memory operations per cycle, only one of which may be a store.
602 ;; Given the large reorder buffer, the processor can hide most latencies.
603 ;; According to HP, they've got the best results by scheduling for retirement
604 ;; bandwidth with limited latency scheduling for floating point operations.
605 ;; Latency for integer operations and memory references is ignored.
608 ;; We claim floating point operations have a 2 cycle latency and are
609 ;; fully pipelined, except for div and sqrt which are not pipelined and
610 ;; take from 17 to 31 cycles to complete.
612 ;; It's worth noting that there is no way to saturate all the functional
613 ;; units on the PA8000 as there is not enough issue bandwidth.
615 (define_automaton "pa8000")
616 (define_cpu_unit "inm0_8000, inm1_8000, im0_8000, im1_8000" "pa8000")
617 (define_cpu_unit "rnm0_8000, rnm1_8000, rm0_8000, rm1_8000" "pa8000")
618 (define_cpu_unit "store_8000" "pa8000")
619 (define_cpu_unit "f0_8000, f1_8000" "pa8000")
620 (define_cpu_unit "fdivsqrt0_8000, fdivsqrt1_8000" "pa8000")
621 (define_reservation "inm_8000" "inm0_8000 | inm1_8000")
622 (define_reservation "im_8000" "im0_8000 | im1_8000")
623 (define_reservation "rnm_8000" "rnm0_8000 | rnm1_8000")
624 (define_reservation "rm_8000" "rm0_8000 | rm1_8000")
625 (define_reservation "f_8000" "f0_8000 | f1_8000")
626 (define_reservation "fdivsqrt_8000" "fdivsqrt0_8000 | fdivsqrt1_8000")
628 ;; We can issue any two memops per cycle, but we can only retire
629 ;; one memory store per cycle. We assume that the reorder buffer
630 ;; will hide any memory latencies per HP's recommendation.
631 (define_insn_reservation "Z0" 0
633 (eq_attr "type" "load,fpload")
634 (eq_attr "cpu" "8000"))
637 (define_insn_reservation "Z1" 0
639 (eq_attr "type" "store,fpstore")
640 (eq_attr "cpu" "8000"))
641 "im_8000,rm_8000+store_8000")
643 (define_insn_reservation "Z2" 0
644 (and (eq_attr "type" "fpstore_load,store_fpload")
645 (eq_attr "cpu" "8000"))
646 "im_8000,rm_8000+store_8000,im_8000,rm_8000")
648 ;; We can issue and retire two non-memory operations per cycle with
649 ;; a few exceptions (branches). This group catches those we want
650 ;; to assume have zero latency.
651 (define_insn_reservation "Z3" 0
653 (eq_attr "type" "!load,fpload,store,fpstore,uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch,fpcc,fpalu,fpmulsgl,fpmuldbl,fpsqrtsgl,fpsqrtdbl,fpdivsgl,fpdivdbl,fpstore_load,store_fpload")
654 (eq_attr "cpu" "8000"))
657 ;; Branches use both slots in the non-memory issue and
659 (define_insn_reservation "Z4" 0
661 (eq_attr "type" "uncond_branch,branch,cbranch,fbranch,call,sibcall,dyncall,multi,milli,sh_func_adrs,parallel_branch")
662 (eq_attr "cpu" "8000"))
663 "inm0_8000+inm1_8000,rnm0_8000+rnm1_8000")
665 ;; We partial latency schedule the floating point units.
666 ;; They can issue/retire two at a time in the non-memory
667 ;; units. We fix their latency at 2 cycles and they
668 ;; are fully pipelined.
669 (define_insn_reservation "Z5" 1
671 (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
672 (eq_attr "cpu" "8000"))
673 "inm_8000,f_8000,rnm_8000")
675 ;; The fdivsqrt units are not pipelined and have a very long latency.
676 ;; To keep the DFA from exploding, we do not show all the
677 ;; reservations for the divsqrt unit.
678 (define_insn_reservation "Z6" 17
680 (eq_attr "type" "fpdivsgl,fpsqrtsgl")
681 (eq_attr "cpu" "8000"))
682 "inm_8000,fdivsqrt_8000*6,rnm_8000")
684 (define_insn_reservation "Z7" 31
686 (eq_attr "type" "fpdivdbl,fpsqrtdbl")
687 (eq_attr "cpu" "8000"))
688 "inm_8000,fdivsqrt_8000*6,rnm_8000")
690 ;; Operand and operator predicates and constraints
692 (include "predicates.md")
693 (include "constraints.md")
695 ;; Atomic instructions
697 ;; All memory loads and stores access storage atomically except
698 ;; for one exception. The STORE BYTES, STORE DOUBLE BYTES, and
699 ;; doubleword loads and stores are not guaranteed to be atomic
700 ;; when referencing the I/O address space.
702 ;; Implement atomic DImode load using 64-bit floating point load and copy.
704 (define_expand "atomic_loaddi"
705 [(match_operand:DI 0 "register_operand") ;; val out
706 (match_operand:DI 1 "memory_operand") ;; memory
707 (match_operand:SI 2 "const_int_operand")] ;; model
708 "!TARGET_64BIT && !TARGET_SOFT_FLOAT"
710 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
711 operands[1] = force_reg (SImode, XEXP (operands[1], 0));
712 operands[2] = gen_reg_rtx (DImode);
713 expand_mem_thread_fence (model);
714 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1], operands[2]));
715 if (is_mm_seq_cst (model))
716 expand_mem_thread_fence (model);
720 (define_insn "atomic_loaddi_1"
721 [(set (match_operand:DI 0 "register_operand" "=r")
722 (mem:DI (match_operand:SI 1 "register_operand" "r")))
723 (clobber (match_operand:DI 2 "register_operand" "=&f"))]
724 "!TARGET_64BIT && !TARGET_SOFT_FLOAT"
725 "{fldds|fldd} 0(%1),%2\;{fstds|fstd} %2,-16(%%sp)\;{ldws|ldw} -16(%%sp),%0\;{ldws|ldw} -12(%%sp),%R0"
726 [(set_attr "type" "move")
727 (set_attr "length" "16")])
729 ;; Implement atomic DImode store using copy and 64-bit floating point store.
731 (define_expand "atomic_storedi"
732 [(match_operand:DI 0 "memory_operand") ;; memory
733 (match_operand:DI 1 "register_operand") ;; val out
734 (match_operand:SI 2 "const_int_operand")] ;; model
735 "!TARGET_64BIT && !TARGET_SOFT_FLOAT"
737 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
738 operands[0] = force_reg (SImode, XEXP (operands[0], 0));
739 operands[2] = gen_reg_rtx (DImode);
740 expand_mem_thread_fence (model);
741 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1], operands[2]));
742 if (is_mm_seq_cst (model))
743 expand_mem_thread_fence (model);
747 (define_insn "atomic_storedi_1"
748 [(set (mem:DI (match_operand:SI 0 "register_operand" "r"))
749 (match_operand:DI 1 "register_operand" "r"))
750 (clobber (match_operand:DI 2 "register_operand" "=&f"))]
751 "!TARGET_64BIT && !TARGET_SOFT_FLOAT"
752 "{stws|stw} %1,-16(%%sp)\;{stws|stw} %R1,-12(%%sp)\;{fldds|fldd} -16(%%sp),%2\;{fstds|fstd} %2,0(%0)"
753 [(set_attr "type" "move")
754 (set_attr "length" "16")])
756 ;; Compare instructions.
757 ;; This controls RTL generation and register allocation.
761 (match_operator:CCFP 2 "comparison_operator"
762 [(match_operand:SF 0 "reg_or_0_operand" "fG")
763 (match_operand:SF 1 "reg_or_0_operand" "fG")]))]
764 "! TARGET_SOFT_FLOAT"
765 "fcmp,sgl,%Y2 %f0,%f1"
766 [(set_attr "length" "4")
767 (set_attr "type" "fpcc")])
771 (match_operator:CCFP 2 "comparison_operator"
772 [(match_operand:DF 0 "reg_or_0_operand" "fG")
773 (match_operand:DF 1 "reg_or_0_operand" "fG")]))]
774 "! TARGET_SOFT_FLOAT"
775 "fcmp,dbl,%Y2 %f0,%f1"
776 [(set_attr "length" "4")
777 (set_attr "type" "fpcc")])
779 ;; Provide a means to emit the movccfp0 and movccfp1 optimization
780 ;; placeholders. This is necessary in rare situations when a
781 ;; placeholder is re-emitted (see PR 8705).
783 (define_expand "movccfp"
785 (match_operand 0 "const_int_operand" ""))]
786 "! TARGET_SOFT_FLOAT"
789 if ((unsigned HOST_WIDE_INT) INTVAL (operands[0]) > 1)
793 ;; The following patterns are optimization placeholders. In almost
794 ;; all cases, the user of the condition code will be simplified and the
795 ;; original condition code setting insn should be eliminated.
797 (define_insn "*movccfp0"
800 "! TARGET_SOFT_FLOAT"
801 "fcmp,dbl,= %%fr0,%%fr0"
802 [(set_attr "length" "4")
803 (set_attr "type" "fpcc")])
805 (define_insn "*movccfp1"
808 "! TARGET_SOFT_FLOAT"
809 "fcmp,dbl,!= %%fr0,%%fr0"
810 [(set_attr "length" "4")
811 (set_attr "type" "fpcc")])
815 (define_expand "cstoresi4"
816 [(set (match_operand:SI 0 "register_operand")
817 (match_operator:SI 1 "ordered_comparison_operator"
818 [(match_operand:SI 2 "reg_or_0_operand" "")
819 (match_operand:SI 3 "arith5_operand" "")]))]
823 ;; Instruction canonicalization puts immediate operands second, which
824 ;; is the reverse of what we want.
827 [(set (match_operand:SI 0 "register_operand" "=r")
828 (match_operator:SI 3 "comparison_operator"
829 [(match_operand:SI 1 "reg_or_0_operand" "rM")
830 (match_operand:SI 2 "arith11_operand" "rI")]))]
832 "{com%I2clr|cmp%I2clr},%B3 %2,%r1,%0\;ldi 1,%0"
833 [(set_attr "type" "binary")
834 (set_attr "length" "8")])
837 [(set (match_operand:DI 0 "register_operand" "=r")
838 (match_operator:DI 3 "comparison_operator"
839 [(match_operand:DI 1 "reg_or_0_operand" "rM")
840 (match_operand:DI 2 "arith11_operand" "rI")]))]
842 "cmp%I2clr,*%B3 %2,%r1,%0\;ldi 1,%0"
843 [(set_attr "type" "binary")
844 (set_attr "length" "8")])
846 (define_insn "iorscc"
847 [(set (match_operand:SI 0 "register_operand" "=r")
848 (ior:SI (match_operator:SI 3 "comparison_operator"
849 [(match_operand:SI 1 "reg_or_0_operand" "rM")
850 (match_operand:SI 2 "arith11_operand" "rI")])
851 (match_operator:SI 6 "comparison_operator"
852 [(match_operand:SI 4 "reg_or_0_operand" "rM")
853 (match_operand:SI 5 "arith11_operand" "rI")])))]
855 "{com%I2clr|cmp%I2clr},%S3 %2,%r1,%%r0\;{com%I5clr|cmp%I5clr},%B6 %5,%r4,%0\;ldi 1,%0"
856 [(set_attr "type" "binary")
857 (set_attr "length" "12")])
860 [(set (match_operand:DI 0 "register_operand" "=r")
861 (ior:DI (match_operator:DI 3 "comparison_operator"
862 [(match_operand:DI 1 "reg_or_0_operand" "rM")
863 (match_operand:DI 2 "arith11_operand" "rI")])
864 (match_operator:DI 6 "comparison_operator"
865 [(match_operand:DI 4 "reg_or_0_operand" "rM")
866 (match_operand:DI 5 "arith11_operand" "rI")])))]
868 "cmp%I2clr,*%S3 %2,%r1,%%r0\;cmp%I5clr,*%B6 %5,%r4,%0\;ldi 1,%0"
869 [(set_attr "type" "binary")
870 (set_attr "length" "12")])
872 ;; Combiner patterns for common operations performed with the output
873 ;; from an scc insn (negscc and incscc).
874 (define_insn "negscc"
875 [(set (match_operand:SI 0 "register_operand" "=r")
876 (neg:SI (match_operator:SI 3 "comparison_operator"
877 [(match_operand:SI 1 "reg_or_0_operand" "rM")
878 (match_operand:SI 2 "arith11_operand" "rI")])))]
880 "{com%I2clr|cmp%I2clr},%B3 %2,%r1,%0\;ldi -1,%0"
881 [(set_attr "type" "binary")
882 (set_attr "length" "8")])
885 [(set (match_operand:DI 0 "register_operand" "=r")
886 (neg:DI (match_operator:DI 3 "comparison_operator"
887 [(match_operand:DI 1 "reg_or_0_operand" "rM")
888 (match_operand:DI 2 "arith11_operand" "rI")])))]
890 "cmp%I2clr,*%B3 %2,%r1,%0\;ldi -1,%0"
891 [(set_attr "type" "binary")
892 (set_attr "length" "8")])
894 ;; Patterns for adding/subtracting the result of a boolean expression from
895 ;; a register. First we have special patterns that make use of the carry
896 ;; bit, and output only two instructions. For the cases we can't in
897 ;; general do in two instructions, the incscc pattern at the end outputs
898 ;; two or three instructions.
901 [(set (match_operand:SI 0 "register_operand" "=r")
902 (plus:SI (leu:SI (match_operand:SI 2 "register_operand" "r")
903 (match_operand:SI 3 "arith11_operand" "rI"))
904 (match_operand:SI 1 "register_operand" "r")))]
906 "sub%I3 %3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
907 [(set_attr "type" "binary")
908 (set_attr "length" "8")])
911 [(set (match_operand:DI 0 "register_operand" "=r")
912 (plus:DI (leu:DI (match_operand:DI 2 "register_operand" "r")
913 (match_operand:DI 3 "arith11_operand" "rI"))
914 (match_operand:DI 1 "register_operand" "r")))]
916 "sub%I3 %3,%2,%%r0\;add,dc %%r0,%1,%0"
917 [(set_attr "type" "binary")
918 (set_attr "length" "8")])
920 ; This need only accept registers for op3, since canonicalization
921 ; replaces geu with gtu when op3 is an integer.
923 [(set (match_operand:SI 0 "register_operand" "=r")
924 (plus:SI (geu:SI (match_operand:SI 2 "register_operand" "r")
925 (match_operand:SI 3 "register_operand" "r"))
926 (match_operand:SI 1 "register_operand" "r")))]
928 "sub %2,%3,%%r0\;{addc|add,c} %%r0,%1,%0"
929 [(set_attr "type" "binary")
930 (set_attr "length" "8")])
933 [(set (match_operand:DI 0 "register_operand" "=r")
934 (plus:DI (geu:DI (match_operand:DI 2 "register_operand" "r")
935 (match_operand:DI 3 "register_operand" "r"))
936 (match_operand:DI 1 "register_operand" "r")))]
938 "sub %2,%3,%%r0\;add,dc %%r0,%1,%0"
939 [(set_attr "type" "binary")
940 (set_attr "length" "8")])
942 ; Match only integers for op3 here. This is used as canonical form of the
943 ; geu pattern when op3 is an integer. Don't match registers since we can't
944 ; make better code than the general incscc pattern.
946 [(set (match_operand:SI 0 "register_operand" "=r")
947 (plus:SI (gtu:SI (match_operand:SI 2 "register_operand" "r")
948 (match_operand:SI 3 "int11_operand" "I"))
949 (match_operand:SI 1 "register_operand" "r")))]
951 "addi %k3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
952 [(set_attr "type" "binary")
953 (set_attr "length" "8")])
956 [(set (match_operand:DI 0 "register_operand" "=r")
957 (plus:DI (gtu:DI (match_operand:DI 2 "register_operand" "r")
958 (match_operand:DI 3 "int11_operand" "I"))
959 (match_operand:DI 1 "register_operand" "r")))]
961 "addi %k3,%2,%%r0\;add,dc %%r0,%1,%0"
962 [(set_attr "type" "binary")
963 (set_attr "length" "8")])
965 (define_insn "incscc"
966 [(set (match_operand:SI 0 "register_operand" "=r,r")
967 (plus:SI (match_operator:SI 4 "comparison_operator"
968 [(match_operand:SI 2 "register_operand" "r,r")
969 (match_operand:SI 3 "arith11_operand" "rI,rI")])
970 (match_operand:SI 1 "register_operand" "0,?r")))]
973 {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi 1,%0,%0
974 {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
975 [(set_attr "type" "binary,binary")
976 (set_attr "length" "8,12")])
979 [(set (match_operand:DI 0 "register_operand" "=r,r")
980 (plus:DI (match_operator:DI 4 "comparison_operator"
981 [(match_operand:DI 2 "register_operand" "r,r")
982 (match_operand:DI 3 "arith11_operand" "rI,rI")])
983 (match_operand:DI 1 "register_operand" "0,?r")))]
986 cmp%I3clr,*%B4 %3,%2,%%r0\;addi 1,%0,%0
987 cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
988 [(set_attr "type" "binary,binary")
989 (set_attr "length" "8,12")])
992 [(set (match_operand:SI 0 "register_operand" "=r")
993 (minus:SI (match_operand:SI 1 "register_operand" "r")
994 (gtu:SI (match_operand:SI 2 "register_operand" "r")
995 (match_operand:SI 3 "arith11_operand" "rI"))))]
997 "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
998 [(set_attr "type" "binary")
999 (set_attr "length" "8")])
1002 [(set (match_operand:DI 0 "register_operand" "=r")
1003 (minus:DI (match_operand:DI 1 "register_operand" "r")
1004 (gtu:DI (match_operand:DI 2 "register_operand" "r")
1005 (match_operand:DI 3 "arith11_operand" "rI"))))]
1007 "sub%I3 %3,%2,%%r0\;sub,db %1,%%r0,%0"
1008 [(set_attr "type" "binary")
1009 (set_attr "length" "8")])
1012 [(set (match_operand:SI 0 "register_operand" "=r")
1013 (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1014 (gtu:SI (match_operand:SI 2 "register_operand" "r")
1015 (match_operand:SI 3 "arith11_operand" "rI")))
1016 (match_operand:SI 4 "register_operand" "r")))]
1018 "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
1019 [(set_attr "type" "binary")
1020 (set_attr "length" "8")])
1023 [(set (match_operand:DI 0 "register_operand" "=r")
1024 (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1025 (gtu:DI (match_operand:DI 2 "register_operand" "r")
1026 (match_operand:DI 3 "arith11_operand" "rI")))
1027 (match_operand:DI 4 "register_operand" "r")))]
1029 "sub%I3 %3,%2,%%r0\;sub,db %1,%4,%0"
1030 [(set_attr "type" "binary")
1031 (set_attr "length" "8")])
1033 ; This need only accept registers for op3, since canonicalization
1034 ; replaces ltu with leu when op3 is an integer.
1036 [(set (match_operand:SI 0 "register_operand" "=r")
1037 (minus:SI (match_operand:SI 1 "register_operand" "r")
1038 (ltu:SI (match_operand:SI 2 "register_operand" "r")
1039 (match_operand:SI 3 "register_operand" "r"))))]
1041 "sub %2,%3,%%r0\;{subb|sub,b} %1,%%r0,%0"
1042 [(set_attr "type" "binary")
1043 (set_attr "length" "8")])
1046 [(set (match_operand:DI 0 "register_operand" "=r")
1047 (minus:DI (match_operand:DI 1 "register_operand" "r")
1048 (ltu:DI (match_operand:DI 2 "register_operand" "r")
1049 (match_operand:DI 3 "register_operand" "r"))))]
1051 "sub %2,%3,%%r0\;sub,db %1,%%r0,%0"
1052 [(set_attr "type" "binary")
1053 (set_attr "length" "8")])
1056 [(set (match_operand:SI 0 "register_operand" "=r")
1057 (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1058 (ltu:SI (match_operand:SI 2 "register_operand" "r")
1059 (match_operand:SI 3 "register_operand" "r")))
1060 (match_operand:SI 4 "register_operand" "r")))]
1062 "sub %2,%3,%%r0\;{subb|sub,b} %1,%4,%0"
1063 [(set_attr "type" "binary")
1064 (set_attr "length" "8")])
1067 [(set (match_operand:DI 0 "register_operand" "=r")
1068 (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1069 (ltu:DI (match_operand:DI 2 "register_operand" "r")
1070 (match_operand:DI 3 "register_operand" "r")))
1071 (match_operand:DI 4 "register_operand" "r")))]
1073 "sub %2,%3,%%r0\;sub,db %1,%4,%0"
1074 [(set_attr "type" "binary")
1075 (set_attr "length" "8")])
1077 ; Match only integers for op3 here. This is used as canonical form of the
1078 ; ltu pattern when op3 is an integer. Don't match registers since we can't
1079 ; make better code than the general incscc pattern.
1081 [(set (match_operand:SI 0 "register_operand" "=r")
1082 (minus:SI (match_operand:SI 1 "register_operand" "r")
1083 (leu:SI (match_operand:SI 2 "register_operand" "r")
1084 (match_operand:SI 3 "int11_operand" "I"))))]
1086 "addi %k3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
1087 [(set_attr "type" "binary")
1088 (set_attr "length" "8")])
1091 [(set (match_operand:DI 0 "register_operand" "=r")
1092 (minus:DI (match_operand:DI 1 "register_operand" "r")
1093 (leu:DI (match_operand:DI 2 "register_operand" "r")
1094 (match_operand:DI 3 "int11_operand" "I"))))]
1096 "addi %k3,%2,%%r0\;sub,db %1,%%r0,%0"
1097 [(set_attr "type" "binary")
1098 (set_attr "length" "8")])
1101 [(set (match_operand:SI 0 "register_operand" "=r")
1102 (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1103 (leu:SI (match_operand:SI 2 "register_operand" "r")
1104 (match_operand:SI 3 "int11_operand" "I")))
1105 (match_operand:SI 4 "register_operand" "r")))]
1107 "addi %k3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
1108 [(set_attr "type" "binary")
1109 (set_attr "length" "8")])
1112 [(set (match_operand:DI 0 "register_operand" "=r")
1113 (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1114 (leu:DI (match_operand:DI 2 "register_operand" "r")
1115 (match_operand:DI 3 "int11_operand" "I")))
1116 (match_operand:DI 4 "register_operand" "r")))]
1118 "addi %k3,%2,%%r0\;sub,db %1,%4,%0"
1119 [(set_attr "type" "binary")
1120 (set_attr "length" "8")])
1122 (define_insn "decscc"
1123 [(set (match_operand:SI 0 "register_operand" "=r,r")
1124 (minus:SI (match_operand:SI 1 "register_operand" "0,?r")
1125 (match_operator:SI 4 "comparison_operator"
1126 [(match_operand:SI 2 "register_operand" "r,r")
1127 (match_operand:SI 3 "arith11_operand" "rI,rI")])))]
1130 {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi -1,%0,%0
1131 {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1132 [(set_attr "type" "binary,binary")
1133 (set_attr "length" "8,12")])
1136 [(set (match_operand:DI 0 "register_operand" "=r,r")
1137 (minus:DI (match_operand:DI 1 "register_operand" "0,?r")
1138 (match_operator:DI 4 "comparison_operator"
1139 [(match_operand:DI 2 "register_operand" "r,r")
1140 (match_operand:DI 3 "arith11_operand" "rI,rI")])))]
1143 cmp%I3clr,*%B4 %3,%2,%%r0\;addi -1,%0,%0
1144 cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1145 [(set_attr "type" "binary,binary")
1146 (set_attr "length" "8,12")])
1148 ; Patterns for max and min. (There is no need for an earlyclobber in the
1149 ; last alternative since the middle alternative will match if op0 == op1.)
1151 (define_insn "sminsi3"
1152 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1153 (smin:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1154 (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1157 {comclr|cmpclr},> %2,%0,%%r0\;copy %2,%0
1158 {comiclr|cmpiclr},> %2,%0,%%r0\;ldi %2,%0
1159 {comclr|cmpclr},> %1,%r2,%0\;copy %1,%0"
1160 [(set_attr "type" "multi,multi,multi")
1161 (set_attr "length" "8,8,8")])
1163 (define_insn "smindi3"
1164 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1165 (smin:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1166 (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1169 cmpclr,*> %2,%0,%%r0\;copy %2,%0
1170 cmpiclr,*> %2,%0,%%r0\;ldi %2,%0
1171 cmpclr,*> %1,%r2,%0\;copy %1,%0"
1172 [(set_attr "type" "multi,multi,multi")
1173 (set_attr "length" "8,8,8")])
1175 (define_insn "uminsi3"
1176 [(set (match_operand:SI 0 "register_operand" "=r,r")
1177 (umin:SI (match_operand:SI 1 "register_operand" "%0,0")
1178 (match_operand:SI 2 "arith11_operand" "r,I")))]
1181 {comclr|cmpclr},>> %2,%0,%%r0\;copy %2,%0
1182 {comiclr|cmpiclr},>> %2,%0,%%r0\;ldi %2,%0"
1183 [(set_attr "type" "multi,multi")
1184 (set_attr "length" "8,8")])
1186 (define_insn "umindi3"
1187 [(set (match_operand:DI 0 "register_operand" "=r,r")
1188 (umin:DI (match_operand:DI 1 "register_operand" "%0,0")
1189 (match_operand:DI 2 "arith11_operand" "r,I")))]
1192 cmpclr,*>> %2,%0,%%r0\;copy %2,%0
1193 cmpiclr,*>> %2,%0,%%r0\;ldi %2,%0"
1194 [(set_attr "type" "multi,multi")
1195 (set_attr "length" "8,8")])
1197 (define_insn "smaxsi3"
1198 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1199 (smax:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1200 (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1203 {comclr|cmpclr},< %2,%0,%%r0\;copy %2,%0
1204 {comiclr|cmpiclr},< %2,%0,%%r0\;ldi %2,%0
1205 {comclr|cmpclr},< %1,%r2,%0\;copy %1,%0"
1206 [(set_attr "type" "multi,multi,multi")
1207 (set_attr "length" "8,8,8")])
1209 (define_insn "smaxdi3"
1210 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1211 (smax:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1212 (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1215 cmpclr,*< %2,%0,%%r0\;copy %2,%0
1216 cmpiclr,*< %2,%0,%%r0\;ldi %2,%0
1217 cmpclr,*< %1,%r2,%0\;copy %1,%0"
1218 [(set_attr "type" "multi,multi,multi")
1219 (set_attr "length" "8,8,8")])
1221 (define_insn "umaxsi3"
1222 [(set (match_operand:SI 0 "register_operand" "=r,r")
1223 (umax:SI (match_operand:SI 1 "register_operand" "%0,0")
1224 (match_operand:SI 2 "arith11_operand" "r,I")))]
1227 {comclr|cmpclr},<< %2,%0,%%r0\;copy %2,%0
1228 {comiclr|cmpiclr},<< %2,%0,%%r0\;ldi %2,%0"
1229 [(set_attr "type" "multi,multi")
1230 (set_attr "length" "8,8")])
1232 (define_insn "umaxdi3"
1233 [(set (match_operand:DI 0 "register_operand" "=r,r")
1234 (umax:DI (match_operand:DI 1 "register_operand" "%0,0")
1235 (match_operand:DI 2 "arith11_operand" "r,I")))]
1238 cmpclr,*<< %2,%0,%%r0\;copy %2,%0
1239 cmpiclr,*<< %2,%0,%%r0\;ldi %2,%0"
1240 [(set_attr "type" "multi,multi")
1241 (set_attr "length" "8,8")])
1243 (define_insn "abssi2"
1244 [(set (match_operand:SI 0 "register_operand" "=r")
1245 (abs:SI (match_operand:SI 1 "register_operand" "r")))]
1247 "or,>= %%r0,%1,%0\;subi 0,%0,%0"
1248 [(set_attr "type" "multi")
1249 (set_attr "length" "8")])
1251 (define_insn "absdi2"
1252 [(set (match_operand:DI 0 "register_operand" "=r")
1253 (abs:DI (match_operand:DI 1 "register_operand" "r")))]
1255 "or,*>= %%r0,%1,%0\;subi 0,%0,%0"
1256 [(set_attr "type" "multi")
1257 (set_attr "length" "8")])
1259 ;;; Experimental conditional move patterns
1261 (define_expand "movsicc"
1262 [(set (match_operand:SI 0 "register_operand" "")
1264 (match_operand 1 "comparison_operator" "")
1265 (match_operand:SI 2 "reg_or_cint_move_operand" "")
1266 (match_operand:SI 3 "reg_or_cint_move_operand" "")))]
1270 if (GET_MODE (XEXP (operands[1], 0)) != SImode
1271 || GET_MODE (XEXP (operands[1], 0)) != GET_MODE (XEXP (operands[1], 1)))
1275 ;; We used to accept any register for op1.
1277 ;; However, it loses sometimes because the compiler will end up using
1278 ;; different registers for op0 and op1 in some critical cases. local-alloc
1279 ;; will not tie op0 and op1 because op0 is used in multiple basic blocks.
1281 ;; If/when global register allocation supports tying we should allow any
1282 ;; register for op1 again.
1284 [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
1286 (match_operator 2 "comparison_operator"
1287 [(match_operand:SI 3 "register_operand" "r,r,r,r")
1288 (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI")])
1289 (match_operand:SI 1 "reg_or_cint_move_operand" "0,J,N,K")
1293 {com%I4clr|cmp%I4clr},%S2 %4,%3,%%r0\;ldi 0,%0
1294 {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldi %1,%0
1295 {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldil L'%1,%0
1296 {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;{zdepi|depwi,z} %Z1,%0"
1297 [(set_attr "type" "multi,multi,multi,nullshift")
1298 (set_attr "length" "8,8,8,8")])
1301 [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1303 (match_operator 5 "comparison_operator"
1304 [(match_operand:SI 3 "register_operand" "r,r,r,r,r,r,r,r")
1305 (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1306 (match_operand:SI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1307 (match_operand:SI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1310 {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;copy %2,%0
1311 {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldi %2,%0
1312 {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldil L'%2,%0
1313 {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;{zdepi|depwi,z} %Z2,%0
1314 {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;copy %1,%0
1315 {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldi %1,%0
1316 {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldil L'%1,%0
1317 {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;{zdepi|depwi,z} %Z1,%0"
1318 [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1319 (set_attr "length" "8,8,8,8,8,8,8,8")])
1321 (define_expand "movdicc"
1322 [(set (match_operand:DI 0 "register_operand" "")
1324 (match_operand 1 "comparison_operator" "")
1325 (match_operand:DI 2 "reg_or_cint_move_operand" "")
1326 (match_operand:DI 3 "reg_or_cint_move_operand" "")))]
1330 if (GET_MODE (XEXP (operands[1], 0)) != DImode
1331 || GET_MODE (XEXP (operands[1], 0)) != GET_MODE (XEXP (operands[1], 1)))
1335 ; We need the first constraint alternative in order to avoid
1336 ; earlyclobbers on all other alternatives.
1338 [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r")
1340 (match_operator 2 "comparison_operator"
1341 [(match_operand:DI 3 "register_operand" "r,r,r,r,r")
1342 (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI")])
1343 (match_operand:DI 1 "reg_or_cint_move_operand" "0,r,J,N,K")
1347 cmp%I4clr,*%S2 %4,%3,%%r0\;ldi 0,%0
1348 cmp%I4clr,*%B2 %4,%3,%0\;copy %1,%0
1349 cmp%I4clr,*%B2 %4,%3,%0\;ldi %1,%0
1350 cmp%I4clr,*%B2 %4,%3,%0\;ldil L'%1,%0
1351 cmp%I4clr,*%B2 %4,%3,%0\;depdi,z %z1,%0"
1352 [(set_attr "type" "multi,multi,multi,multi,nullshift")
1353 (set_attr "length" "8,8,8,8,8")])
1356 [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1358 (match_operator 5 "comparison_operator"
1359 [(match_operand:DI 3 "register_operand" "r,r,r,r,r,r,r,r")
1360 (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1361 (match_operand:DI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1362 (match_operand:DI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1365 cmp%I4clr,*%S5 %4,%3,%%r0\;copy %2,%0
1366 cmp%I4clr,*%S5 %4,%3,%%r0\;ldi %2,%0
1367 cmp%I4clr,*%S5 %4,%3,%%r0\;ldil L'%2,%0
1368 cmp%I4clr,*%S5 %4,%3,%%r0\;depdi,z %z2,%0
1369 cmp%I4clr,*%B5 %4,%3,%%r0\;copy %1,%0
1370 cmp%I4clr,*%B5 %4,%3,%%r0\;ldi %1,%0
1371 cmp%I4clr,*%B5 %4,%3,%%r0\;ldil L'%1,%0
1372 cmp%I4clr,*%B5 %4,%3,%%r0\;depdi,z %z1,%0"
1373 [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1374 (set_attr "length" "8,8,8,8,8,8,8,8")])
1376 ;; Conditional Branches
1378 (define_expand "cbranchdi4"
1380 (if_then_else (match_operator 0 "ordered_comparison_operator"
1381 [(match_operand:DI 1 "reg_or_0_operand" "")
1382 (match_operand:DI 2 "register_operand" "")])
1383 (label_ref (match_operand 3 "" ""))
1388 (define_expand "cbranchsi4"
1390 (if_then_else (match_operator 0 "ordered_comparison_operator"
1391 [(match_operand:SI 1 "reg_or_0_operand" "")
1392 (match_operand:SI 2 "arith5_operand" "")])
1393 (label_ref (match_operand 3 "" ""))
1398 (define_expand "cbranchsf4"
1400 (if_then_else (match_operator 0 "comparison_operator"
1401 [(match_operand:SF 1 "reg_or_0_operand" "")
1402 (match_operand:SF 2 "reg_or_0_operand" "")])
1403 (label_ref (match_operand 3 "" ""))
1408 pa_emit_bcond_fp (operands);
1413 (define_expand "cbranchdf4"
1415 (if_then_else (match_operator 0 "comparison_operator"
1416 [(match_operand:DF 1 "reg_or_0_operand" "")
1417 (match_operand:DF 2 "reg_or_0_operand" "")])
1418 (label_ref (match_operand 3 "" ""))
1423 pa_emit_bcond_fp (operands);
1427 ;; Match the branch patterns.
1430 ;; Note a long backward conditional branch with an annulled delay slot
1431 ;; has a length of 12.
1435 (match_operator 3 "comparison_operator"
1436 [(match_operand:SI 1 "reg_or_0_operand" "rM")
1437 (match_operand:SI 2 "arith5_operand" "rL")])
1438 (label_ref (match_operand 0 "" ""))
1443 return pa_output_cbranch (operands, 0, insn);
1445 [(set_attr "type" "cbranch")
1446 (set (attr "length")
1447 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1448 (const_int MAX_12BIT_OFFSET))
1450 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1451 (const_int MAX_17BIT_OFFSET))
1453 (match_test "TARGET_PORTABLE_RUNTIME")
1455 (not (match_test "flag_pic"))
1459 ;; Match the negated branch.
1464 (match_operator 3 "comparison_operator"
1465 [(match_operand:SI 1 "reg_or_0_operand" "rM")
1466 (match_operand:SI 2 "arith5_operand" "rL")])
1468 (label_ref (match_operand 0 "" ""))))]
1472 return pa_output_cbranch (operands, 1, insn);
1474 [(set_attr "type" "cbranch")
1475 (set (attr "length")
1476 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1477 (const_int MAX_12BIT_OFFSET))
1479 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1480 (const_int MAX_17BIT_OFFSET))
1482 (match_test "TARGET_PORTABLE_RUNTIME")
1484 (not (match_test "flag_pic"))
1491 (match_operator 3 "comparison_operator"
1492 [(match_operand:DI 1 "reg_or_0_operand" "rM")
1493 (match_operand:DI 2 "reg_or_0_operand" "rM")])
1494 (label_ref (match_operand 0 "" ""))
1499 return pa_output_cbranch (operands, 0, insn);
1501 [(set_attr "type" "cbranch")
1502 (set (attr "length")
1503 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1504 (const_int MAX_12BIT_OFFSET))
1506 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1507 (const_int MAX_17BIT_OFFSET))
1509 (match_test "TARGET_PORTABLE_RUNTIME")
1511 (not (match_test "flag_pic"))
1515 ;; Match the negated branch.
1520 (match_operator 3 "comparison_operator"
1521 [(match_operand:DI 1 "reg_or_0_operand" "rM")
1522 (match_operand:DI 2 "reg_or_0_operand" "rM")])
1524 (label_ref (match_operand 0 "" ""))))]
1528 return pa_output_cbranch (operands, 1, insn);
1530 [(set_attr "type" "cbranch")
1531 (set (attr "length")
1532 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1533 (const_int MAX_12BIT_OFFSET))
1535 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1536 (const_int MAX_17BIT_OFFSET))
1538 (match_test "TARGET_PORTABLE_RUNTIME")
1540 (not (match_test "flag_pic"))
1546 (match_operator 3 "cmpib_comparison_operator"
1547 [(match_operand:DI 1 "reg_or_0_operand" "rM")
1548 (match_operand:DI 2 "arith5_operand" "rL")])
1549 (label_ref (match_operand 0 "" ""))
1554 return pa_output_cbranch (operands, 0, insn);
1556 [(set_attr "type" "cbranch")
1557 (set (attr "length")
1558 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1559 (const_int MAX_12BIT_OFFSET))
1561 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1562 (const_int MAX_17BIT_OFFSET))
1564 (match_test "TARGET_PORTABLE_RUNTIME")
1566 (not (match_test "flag_pic"))
1570 ;; Match the negated branch.
1575 (match_operator 3 "cmpib_comparison_operator"
1576 [(match_operand:DI 1 "reg_or_0_operand" "rM")
1577 (match_operand:DI 2 "arith5_operand" "rL")])
1579 (label_ref (match_operand 0 "" ""))))]
1583 return pa_output_cbranch (operands, 1, insn);
1585 [(set_attr "type" "cbranch")
1586 (set (attr "length")
1587 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1588 (const_int MAX_12BIT_OFFSET))
1590 (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1591 (const_int MAX_17BIT_OFFSET))
1593 (match_test "TARGET_PORTABLE_RUNTIME")
1595 (not (match_test "flag_pic"))
1599 ;; Branch on Bit patterns.
1603 (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1605 (match_operand:SI 1 "uint5_operand" ""))
1607 (label_ref (match_operand 2 "" ""))
1612 return pa_output_bb (operands, 0, insn, 0);
1614 [(set_attr "type" "cbranch")
1615 (set (attr "length")
1616 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1617 (const_int MAX_12BIT_OFFSET))
1619 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1620 (const_int MAX_17BIT_OFFSET))
1622 (match_test "TARGET_PORTABLE_RUNTIME")
1624 (not (match_test "flag_pic"))
1631 (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1633 (match_operand:DI 1 "uint32_operand" ""))
1635 (label_ref (match_operand 2 "" ""))
1640 return pa_output_bb (operands, 0, insn, 0);
1642 [(set_attr "type" "cbranch")
1643 (set (attr "length")
1644 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1645 (const_int MAX_12BIT_OFFSET))
1647 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1648 (const_int MAX_17BIT_OFFSET))
1650 (match_test "TARGET_PORTABLE_RUNTIME")
1652 (not (match_test "flag_pic"))
1659 (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1661 (match_operand:SI 1 "uint5_operand" ""))
1664 (label_ref (match_operand 2 "" ""))))]
1668 return pa_output_bb (operands, 1, insn, 0);
1670 [(set_attr "type" "cbranch")
1671 (set (attr "length")
1672 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1673 (const_int MAX_12BIT_OFFSET))
1675 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1676 (const_int MAX_17BIT_OFFSET))
1678 (match_test "TARGET_PORTABLE_RUNTIME")
1680 (not (match_test "flag_pic"))
1687 (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1689 (match_operand:DI 1 "uint32_operand" ""))
1692 (label_ref (match_operand 2 "" ""))))]
1696 return pa_output_bb (operands, 1, insn, 0);
1698 [(set_attr "type" "cbranch")
1699 (set (attr "length")
1700 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1701 (const_int MAX_12BIT_OFFSET))
1703 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1704 (const_int MAX_17BIT_OFFSET))
1706 (match_test "TARGET_PORTABLE_RUNTIME")
1708 (not (match_test "flag_pic"))
1715 (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1717 (match_operand:SI 1 "uint5_operand" ""))
1719 (label_ref (match_operand 2 "" ""))
1724 return pa_output_bb (operands, 0, insn, 1);
1726 [(set_attr "type" "cbranch")
1727 (set (attr "length")
1728 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1729 (const_int MAX_12BIT_OFFSET))
1731 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1732 (const_int MAX_17BIT_OFFSET))
1734 (match_test "TARGET_PORTABLE_RUNTIME")
1736 (not (match_test "flag_pic"))
1743 (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1745 (match_operand:DI 1 "uint32_operand" ""))
1747 (label_ref (match_operand 2 "" ""))
1752 return pa_output_bb (operands, 0, insn, 1);
1754 [(set_attr "type" "cbranch")
1755 (set (attr "length")
1756 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1757 (const_int MAX_12BIT_OFFSET))
1759 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1760 (const_int MAX_17BIT_OFFSET))
1762 (match_test "TARGET_PORTABLE_RUNTIME")
1764 (not (match_test "flag_pic"))
1771 (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1773 (match_operand:SI 1 "uint5_operand" ""))
1776 (label_ref (match_operand 2 "" ""))))]
1780 return pa_output_bb (operands, 1, insn, 1);
1782 [(set_attr "type" "cbranch")
1783 (set (attr "length")
1784 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1785 (const_int MAX_12BIT_OFFSET))
1787 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1788 (const_int MAX_17BIT_OFFSET))
1790 (match_test "TARGET_PORTABLE_RUNTIME")
1792 (not (match_test "flag_pic"))
1799 (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1801 (match_operand:DI 1 "uint32_operand" ""))
1804 (label_ref (match_operand 2 "" ""))))]
1808 return pa_output_bb (operands, 1, insn, 1);
1810 [(set_attr "type" "cbranch")
1811 (set (attr "length")
1812 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1813 (const_int MAX_12BIT_OFFSET))
1815 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1816 (const_int MAX_17BIT_OFFSET))
1818 (match_test "TARGET_PORTABLE_RUNTIME")
1820 (not (match_test "flag_pic"))
1824 ;; Branch on Variable Bit patterns.
1828 (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1830 (match_operand:SI 1 "register_operand" "q"))
1832 (label_ref (match_operand 2 "" ""))
1837 return pa_output_bvb (operands, 0, insn, 0);
1839 [(set_attr "type" "cbranch")
1840 (set (attr "length")
1841 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1842 (const_int MAX_12BIT_OFFSET))
1844 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1845 (const_int MAX_17BIT_OFFSET))
1847 (match_test "TARGET_PORTABLE_RUNTIME")
1849 (not (match_test "flag_pic"))
1856 (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1858 (match_operand:DI 1 "register_operand" "q"))
1860 (label_ref (match_operand 2 "" ""))
1865 return pa_output_bvb (operands, 0, insn, 0);
1867 [(set_attr "type" "cbranch")
1868 (set (attr "length")
1869 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1870 (const_int MAX_12BIT_OFFSET))
1872 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1873 (const_int MAX_17BIT_OFFSET))
1875 (match_test "TARGET_PORTABLE_RUNTIME")
1877 (not (match_test "flag_pic"))
1884 (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1886 (match_operand:SI 1 "register_operand" "q"))
1889 (label_ref (match_operand 2 "" ""))))]
1893 return pa_output_bvb (operands, 1, insn, 0);
1895 [(set_attr "type" "cbranch")
1896 (set (attr "length")
1897 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1898 (const_int MAX_12BIT_OFFSET))
1900 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1901 (const_int MAX_17BIT_OFFSET))
1903 (match_test "TARGET_PORTABLE_RUNTIME")
1905 (not (match_test "flag_pic"))
1912 (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1914 (match_operand:DI 1 "register_operand" "q"))
1917 (label_ref (match_operand 2 "" ""))))]
1921 return pa_output_bvb (operands, 1, insn, 0);
1923 [(set_attr "type" "cbranch")
1924 (set (attr "length")
1925 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1926 (const_int MAX_12BIT_OFFSET))
1928 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1929 (const_int MAX_17BIT_OFFSET))
1931 (match_test "TARGET_PORTABLE_RUNTIME")
1933 (not (match_test "flag_pic"))
1940 (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1942 (match_operand:SI 1 "register_operand" "q"))
1944 (label_ref (match_operand 2 "" ""))
1949 return pa_output_bvb (operands, 0, insn, 1);
1951 [(set_attr "type" "cbranch")
1952 (set (attr "length")
1953 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1954 (const_int MAX_12BIT_OFFSET))
1956 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1957 (const_int MAX_17BIT_OFFSET))
1959 (match_test "TARGET_PORTABLE_RUNTIME")
1961 (not (match_test "flag_pic"))
1968 (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1970 (match_operand:DI 1 "register_operand" "q"))
1972 (label_ref (match_operand 2 "" ""))
1977 return pa_output_bvb (operands, 0, insn, 1);
1979 [(set_attr "type" "cbranch")
1980 (set (attr "length")
1981 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1982 (const_int MAX_12BIT_OFFSET))
1984 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1985 (const_int MAX_17BIT_OFFSET))
1987 (match_test "TARGET_PORTABLE_RUNTIME")
1989 (not (match_test "flag_pic"))
1996 (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1998 (match_operand:SI 1 "register_operand" "q"))
2001 (label_ref (match_operand 2 "" ""))))]
2005 return pa_output_bvb (operands, 1, insn, 1);
2007 [(set_attr "type" "cbranch")
2008 (set (attr "length")
2009 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2010 (const_int MAX_12BIT_OFFSET))
2012 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2013 (const_int MAX_17BIT_OFFSET))
2015 (match_test "TARGET_PORTABLE_RUNTIME")
2017 (not (match_test "flag_pic"))
2024 (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2026 (match_operand:DI 1 "register_operand" "q"))
2029 (label_ref (match_operand 2 "" ""))))]
2033 return pa_output_bvb (operands, 1, insn, 1);
2035 [(set_attr "type" "cbranch")
2036 (set (attr "length")
2037 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2038 (const_int MAX_12BIT_OFFSET))
2040 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2041 (const_int MAX_17BIT_OFFSET))
2043 (match_test "TARGET_PORTABLE_RUNTIME")
2045 (not (match_test "flag_pic"))
2049 ;; Floating point branches
2051 ;; ??? Nullification is handled differently from other branches.
2052 ;; If nullification is specified, the delay slot is nullified on any
2053 ;; taken branch regardless of branch direction.
2055 [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2056 (label_ref (match_operand 0 "" ""))
2058 "!TARGET_SOFT_FLOAT"
2061 int length = get_attr_length (insn);
2063 int nullify, xdelay;
2066 return \"ftest\;b%* %l0\";
2068 if (dbr_sequence_length () == 0 || INSN_ANNULLED_BRANCH_P (insn))
2072 xoperands[0] = GEN_INT (length - 8);
2078 xoperands[0] = GEN_INT (length - 4);
2082 output_asm_insn (\"ftest\;add,tr %%r0,%%r0,%%r0\;b,n .+%0\", xoperands);
2084 output_asm_insn (\"ftest\;add,tr %%r0,%%r0,%%r0\;b .+%0\", xoperands);
2085 return pa_output_lbranch (operands[0], insn, xdelay);
2087 [(set_attr "type" "fbranch")
2088 (set (attr "length")
2089 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
2090 (const_int MAX_17BIT_OFFSET))
2092 (match_test "TARGET_PORTABLE_RUNTIME")
2094 (not (match_test "flag_pic"))
2099 [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2101 (label_ref (match_operand 0 "" ""))))]
2102 "!TARGET_SOFT_FLOAT"
2105 int length = get_attr_length (insn);
2107 int nullify, xdelay;
2110 return \"ftest\;add,tr %%r0,%%r0,%%r0\;b%* %0\";
2112 if (dbr_sequence_length () == 0 || INSN_ANNULLED_BRANCH_P (insn))
2116 xoperands[0] = GEN_INT (length - 4);
2122 xoperands[0] = GEN_INT (length);
2126 output_asm_insn (\"ftest\;b,n .+%0\", xoperands);
2128 output_asm_insn (\"ftest\;b .+%0\", xoperands);
2129 return pa_output_lbranch (operands[0], insn, xdelay);
2131 [(set_attr "type" "fbranch")
2132 (set (attr "length")
2133 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
2134 (const_int MAX_17BIT_OFFSET))
2136 (match_test "TARGET_PORTABLE_RUNTIME")
2138 (not (match_test "flag_pic"))
2142 ;; Move instructions
2144 (define_expand "movsi"
2145 [(set (match_operand:SI 0 "general_operand" "")
2146 (match_operand:SI 1 "general_operand" ""))]
2150 if (pa_emit_move_sequence (operands, SImode, 0))
2154 ;; Handle SImode input reloads requiring %r1 as a scratch register.
2155 (define_expand "reload_insi_r1"
2156 [(set (match_operand:SI 0 "register_operand" "=Z")
2157 (match_operand:SI 1 "non_hard_reg_operand" ""))
2158 (clobber (match_operand:SI 2 "register_operand" "=&a"))]
2162 if (pa_emit_move_sequence (operands, SImode, operands[2]))
2165 /* We don't want the clobber emitted, so handle this ourselves. */
2166 emit_insn (gen_rtx_SET (operands[0], operands[1]));
2170 ;; Handle SImode input reloads requiring a general register as a
2171 ;; scratch register.
2172 (define_expand "reload_insi"
2173 [(set (match_operand:SI 0 "register_operand" "=Z")
2174 (match_operand:SI 1 "non_hard_reg_operand" ""))
2175 (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2179 if (pa_emit_move_sequence (operands, SImode, operands[2]))
2182 /* We don't want the clobber emitted, so handle this ourselves. */
2183 emit_insn (gen_rtx_SET (operands[0], operands[1]));
2187 ;; Handle SImode output reloads requiring a general register as a
2188 ;; scratch register.
2189 (define_expand "reload_outsi"
2190 [(set (match_operand:SI 0 "non_hard_reg_operand" "")
2191 (match_operand:SI 1 "register_operand" "Z"))
2192 (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2196 if (pa_emit_move_sequence (operands, SImode, operands[2]))
2199 /* We don't want the clobber emitted, so handle this ourselves. */
2200 emit_insn (gen_rtx_SET (operands[0], operands[1]));
2205 [(set (match_operand:SI 0 "move_dest_operand"
2206 "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T,?r,?*f")
2207 (match_operand:SI 1 "move_src_operand"
2208 "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f,*f,r"))]
2209 "(register_operand (operands[0], SImode)
2210 || reg_or_0_operand (operands[1], SImode))
2211 && !TARGET_SOFT_FLOAT
2218 {zdepi|depwi,z} %Z1,%0
2222 {mfctl|mfctl,w} %%sar,%0
2226 {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
2227 {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
2228 [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore,fpstore_load,store_fpload")
2229 (set_attr "pa_combine_type" "addmove")
2230 (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4,8,8")])
2233 [(set (match_operand:SI 0 "move_dest_operand"
2234 "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T")
2235 (match_operand:SI 1 "move_src_operand"
2236 "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f"))]
2237 "(register_operand (operands[0], SImode)
2238 || reg_or_0_operand (operands[1], SImode))
2239 && !TARGET_SOFT_FLOAT
2246 {zdepi|depwi,z} %Z1,%0
2250 {mfctl|mfctl,w} %%sar,%0
2254 [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore")
2255 (set_attr "pa_combine_type" "addmove")
2256 (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4")])
2259 [(set (match_operand:SI 0 "indexed_memory_operand" "=R")
2260 (match_operand:SI 1 "register_operand" "f"))]
2262 && !TARGET_DISABLE_INDEXING
2263 && reload_completed"
2265 [(set_attr "type" "fpstore")
2266 (set_attr "pa_combine_type" "addmove")
2267 (set_attr "length" "4")])
2269 ; Rewrite RTL using an indexed store. This will allow the insn that
2270 ; computes the address to be deleted if the register it sets is dead.
2272 [(set (match_operand:SI 0 "register_operand" "")
2273 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
2275 (match_operand:SI 2 "register_operand" "")))
2276 (set (mem:SI (match_dup 0))
2277 (match_operand:SI 3 "register_operand" ""))]
2279 && !TARGET_DISABLE_INDEXING
2280 && REG_OK_FOR_BASE_P (operands[2])
2281 && FP_REGNO_P (REGNO (operands[3]))"
2282 [(set (mem:SI (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
2284 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
2289 [(set (match_operand:SI 0 "register_operand" "")
2290 (plus:SI (match_operand:SI 2 "register_operand" "")
2291 (mult:SI (match_operand:SI 1 "register_operand" "")
2293 (set (mem:SI (match_dup 0))
2294 (match_operand:SI 3 "register_operand" ""))]
2296 && !TARGET_DISABLE_INDEXING
2297 && REG_OK_FOR_BASE_P (operands[2])
2298 && FP_REGNO_P (REGNO (operands[3]))"
2299 [(set (mem:SI (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
2301 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
2306 [(set (match_operand:DI 0 "register_operand" "")
2307 (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
2309 (match_operand:DI 2 "register_operand" "")))
2310 (set (mem:SI (match_dup 0))
2311 (match_operand:SI 3 "register_operand" ""))]
2313 && !TARGET_DISABLE_INDEXING
2315 && REG_OK_FOR_BASE_P (operands[2])
2316 && FP_REGNO_P (REGNO (operands[3]))"
2317 [(set (mem:SI (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
2319 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
2324 [(set (match_operand:DI 0 "register_operand" "")
2325 (plus:DI (match_operand:DI 2 "register_operand" "")
2326 (mult:DI (match_operand:DI 1 "register_operand" "")
2328 (set (mem:SI (match_dup 0))
2329 (match_operand:SI 3 "register_operand" ""))]
2331 && !TARGET_DISABLE_INDEXING
2333 && REG_OK_FOR_BASE_P (operands[2])
2334 && FP_REGNO_P (REGNO (operands[3]))"
2335 [(set (mem:SI (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
2337 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
2342 [(set (match_operand:SI 0 "register_operand" "")
2343 (plus:SI (match_operand:SI 1 "register_operand" "")
2344 (match_operand:SI 2 "register_operand" "")))
2345 (set (mem:SI (match_dup 0))
2346 (match_operand:SI 3 "register_operand" ""))]
2348 && !TARGET_DISABLE_INDEXING
2349 && TARGET_NO_SPACE_REGS
2350 && REG_OK_FOR_INDEX_P (operands[1])
2351 && REG_OK_FOR_BASE_P (operands[2])
2352 && FP_REGNO_P (REGNO (operands[3]))"
2353 [(set (mem:SI (plus:SI (match_dup 1) (match_dup 2)))
2355 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2359 [(set (match_operand:SI 0 "register_operand" "")
2360 (plus:SI (match_operand:SI 1 "register_operand" "")
2361 (match_operand:SI 2 "register_operand" "")))
2362 (set (mem:SI (match_dup 0))
2363 (match_operand:SI 3 "register_operand" ""))]
2365 && !TARGET_DISABLE_INDEXING
2366 && TARGET_NO_SPACE_REGS
2367 && REG_OK_FOR_BASE_P (operands[1])
2368 && REG_OK_FOR_INDEX_P (operands[2])
2369 && FP_REGNO_P (REGNO (operands[3]))"
2370 [(set (mem:SI (plus:SI (match_dup 2) (match_dup 1)))
2372 (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
2376 [(set (match_operand:DI 0 "register_operand" "")
2377 (plus:DI (match_operand:DI 1 "register_operand" "")
2378 (match_operand:DI 2 "register_operand" "")))
2379 (set (mem:SI (match_dup 0))
2380 (match_operand:SI 3 "register_operand" ""))]
2382 && !TARGET_DISABLE_INDEXING
2384 && TARGET_NO_SPACE_REGS
2385 && REG_OK_FOR_INDEX_P (operands[1])
2386 && REG_OK_FOR_BASE_P (operands[2])
2387 && FP_REGNO_P (REGNO (operands[3]))"
2388 [(set (mem:SI (plus:DI (match_dup 1) (match_dup 2)))
2390 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
2394 [(set (match_operand:DI 0 "register_operand" "")
2395 (plus:DI (match_operand:DI 1 "register_operand" "")
2396 (match_operand:DI 2 "register_operand" "")))
2397 (set (mem:SI (match_dup 0))
2398 (match_operand:SI 3 "register_operand" ""))]
2400 && !TARGET_DISABLE_INDEXING
2402 && TARGET_NO_SPACE_REGS
2403 && REG_OK_FOR_BASE_P (operands[1])
2404 && REG_OK_FOR_INDEX_P (operands[2])
2405 && FP_REGNO_P (REGNO (operands[3]))"
2406 [(set (mem:SI (plus:DI (match_dup 2) (match_dup 1)))
2408 (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
2412 [(set (match_operand:SI 0 "move_dest_operand"
2413 "=r,r,r,r,r,r,Q,!*q,!r")
2414 (match_operand:SI 1 "move_src_operand"
2415 "A,r,J,N,K,RQ,rM,!rM,!*q"))]
2416 "(register_operand (operands[0], SImode)
2417 || reg_or_0_operand (operands[1], SImode))
2418 && TARGET_SOFT_FLOAT"
2424 {zdepi|depwi,z} %Z1,%0
2428 {mfctl|mfctl,w} %%sar,%0"
2429 [(set_attr "type" "load,move,move,move,move,load,store,move,move")
2430 (set_attr "pa_combine_type" "addmove")
2431 (set_attr "length" "4,4,4,4,4,4,4,4,4")])
2433 ;; Load or store with base-register modification.
2435 [(set (match_operand:SI 0 "register_operand" "=r")
2436 (mem:SI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2437 (match_operand:DI 2 "int5_operand" "L"))))
2439 (plus:DI (match_dup 1) (match_dup 2)))]
2442 [(set_attr "type" "load")
2443 (set_attr "length" "4")])
2445 ; And a zero extended variant.
2447 [(set (match_operand:DI 0 "register_operand" "=r")
2448 (zero_extend:DI (mem:SI
2450 (match_operand:DI 1 "register_operand" "+r")
2451 (match_operand:DI 2 "int5_operand" "L")))))
2453 (plus:DI (match_dup 1) (match_dup 2)))]
2456 [(set_attr "type" "load")
2457 (set_attr "length" "4")])
2459 (define_expand "pre_load"
2460 [(parallel [(set (match_operand:SI 0 "register_operand" "")
2461 (mem (plus (match_operand 1 "register_operand" "")
2462 (match_operand 2 "pre_cint_operand" ""))))
2464 (plus (match_dup 1) (match_dup 2)))])]
2470 emit_insn (gen_pre_ldd (operands[0], operands[1], operands[2]));
2473 emit_insn (gen_pre_ldw (operands[0], operands[1], operands[2]));
2477 (define_insn "pre_ldw"
2478 [(set (match_operand:SI 0 "register_operand" "=r")
2479 (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2480 (match_operand:SI 2 "pre_cint_operand" ""))))
2482 (plus:SI (match_dup 1) (match_dup 2)))]
2486 if (INTVAL (operands[2]) < 0)
2487 return \"{ldwm|ldw,mb} %2(%1),%0\";
2488 return \"{ldws|ldw},mb %2(%1),%0\";
2490 [(set_attr "type" "load")
2491 (set_attr "length" "4")])
2493 (define_insn "pre_ldd"
2494 [(set (match_operand:DI 0 "register_operand" "=r")
2495 (mem:DI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2496 (match_operand:DI 2 "pre_cint_operand" ""))))
2498 (plus:DI (match_dup 1) (match_dup 2)))]
2501 [(set_attr "type" "load")
2502 (set_attr "length" "4")])
2505 [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2506 (match_operand:SI 1 "pre_cint_operand" "")))
2507 (match_operand:SI 2 "reg_or_0_operand" "rM"))
2509 (plus:SI (match_dup 0) (match_dup 1)))]
2513 if (INTVAL (operands[1]) < 0)
2514 return \"{stwm|stw,mb} %r2,%1(%0)\";
2515 return \"{stws|stw},mb %r2,%1(%0)\";
2517 [(set_attr "type" "store")
2518 (set_attr "length" "4")])
2521 [(set (match_operand:SI 0 "register_operand" "=r")
2522 (mem:SI (match_operand:SI 1 "register_operand" "+r")))
2524 (plus:SI (match_dup 1)
2525 (match_operand:SI 2 "post_cint_operand" "")))]
2529 if (INTVAL (operands[2]) > 0)
2530 return \"{ldwm|ldw,ma} %2(%1),%0\";
2531 return \"{ldws|ldw},ma %2(%1),%0\";
2533 [(set_attr "type" "load")
2534 (set_attr "length" "4")])
2536 (define_expand "post_store"
2537 [(parallel [(set (mem (match_operand 0 "register_operand" ""))
2538 (match_operand 1 "reg_or_0_operand" ""))
2541 (match_operand 2 "post_cint_operand" "")))])]
2547 emit_insn (gen_post_std (operands[0], operands[1], operands[2]));
2550 emit_insn (gen_post_stw (operands[0], operands[1], operands[2]));
2554 (define_insn "post_stw"
2555 [(set (mem:SI (match_operand:SI 0 "register_operand" "+r"))
2556 (match_operand:SI 1 "reg_or_0_operand" "rM"))
2558 (plus:SI (match_dup 0)
2559 (match_operand:SI 2 "post_cint_operand" "")))]
2563 if (INTVAL (operands[2]) > 0)
2564 return \"{stwm|stw,ma} %r1,%2(%0)\";
2565 return \"{stws|stw},ma %r1,%2(%0)\";
2567 [(set_attr "type" "store")
2568 (set_attr "length" "4")])
2570 (define_insn "post_std"
2571 [(set (mem:DI (match_operand:DI 0 "register_operand" "+r"))
2572 (match_operand:DI 1 "reg_or_0_operand" "rM"))
2574 (plus:DI (match_dup 0)
2575 (match_operand:DI 2 "post_cint_operand" "")))]
2578 [(set_attr "type" "store")
2579 (set_attr "length" "4")])
2581 ;; For loading the address of a label while generating PIC code.
2582 ;; Note since this pattern can be created at reload time (via movsi), all
2583 ;; the same rules for movsi apply here. (no new pseudos, no temporaries).
2585 [(set (match_operand 0 "pmode_register_operand" "=a")
2586 (match_operand 1 "pic_label_operand" ""))]
2592 xoperands[0] = operands[0];
2593 xoperands[1] = operands[1];
2594 xoperands[2] = gen_label_rtx ();
2596 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
2597 CODE_LABEL_NUMBER (xoperands[2]));
2598 output_asm_insn (\"mfia %0\", xoperands);
2600 /* If we're trying to load the address of a label that happens to be
2601 close, then we can use a shorter sequence. */
2602 if (GET_CODE (operands[1]) == LABEL_REF
2603 && !LABEL_REF_NONLOCAL_P (operands[1])
2604 && INSN_ADDRESSES_SET_P ()
2605 && abs (INSN_ADDRESSES (INSN_UID (XEXP (operands[1], 0)))
2606 - INSN_ADDRESSES (INSN_UID (insn))) < 8100)
2607 output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands);
2610 output_asm_insn (\"addil L%%%1-%2,%0\", xoperands);
2611 output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands);
2615 [(set_attr "type" "multi")
2616 (set_attr "length" "12")]) ; 8 or 12
2619 [(set (match_operand 0 "pmode_register_operand" "=a")
2620 (match_operand 1 "pic_label_operand" ""))]
2626 xoperands[0] = operands[0];
2627 xoperands[1] = operands[1];
2628 xoperands[2] = gen_label_rtx ();
2630 output_asm_insn (\"bl .+8,%0\", xoperands);
2631 output_asm_insn (\"depi 0,31,2,%0\", xoperands);
2632 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
2633 CODE_LABEL_NUMBER (xoperands[2]));
2635 /* If we're trying to load the address of a label that happens to be
2636 close, then we can use a shorter sequence. */
2637 if (GET_CODE (operands[1]) == LABEL_REF
2638 && !LABEL_REF_NONLOCAL_P (operands[1])
2639 && INSN_ADDRESSES_SET_P ()
2640 && abs (INSN_ADDRESSES (INSN_UID (XEXP (operands[1], 0)))
2641 - INSN_ADDRESSES (INSN_UID (insn))) < 8100)
2642 output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands);
2645 output_asm_insn (\"addil L%%%1-%2,%0\", xoperands);
2646 output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands);
2650 [(set_attr "type" "multi")
2651 (set_attr "length" "16")]) ; 12 or 16
2654 [(set (match_operand:SI 0 "register_operand" "=a")
2655 (plus:SI (match_operand:SI 1 "register_operand" "r")
2656 (high:SI (match_operand 2 "" ""))))]
2657 "symbolic_operand (operands[2], Pmode)
2658 && ! function_label_operand (operands[2], Pmode)
2661 [(set_attr "type" "binary")
2662 (set_attr "length" "4")])
2665 [(set (match_operand:DI 0 "register_operand" "=a")
2666 (plus:DI (match_operand:DI 1 "register_operand" "r")
2667 (high:DI (match_operand 2 "" ""))))]
2668 "symbolic_operand (operands[2], Pmode)
2669 && ! function_label_operand (operands[2], Pmode)
2673 [(set_attr "type" "binary")
2674 (set_attr "length" "4")])
2677 [(set (match_operand:SI 0 "register_operand" "=r")
2678 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
2679 (unspec:SI [(match_operand 2 "" "")] UNSPEC_DLTIND14R)))]
2680 "symbolic_operand (operands[2], Pmode)
2681 && ! function_label_operand (operands[2], Pmode)
2684 [(set_attr "type" "binary")
2685 (set_attr "length" "4")])
2688 [(set (match_operand:DI 0 "register_operand" "=r")
2689 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2690 (unspec:DI [(match_operand 2 "" "")] UNSPEC_DLTIND14R)))]
2691 "symbolic_operand (operands[2], Pmode)
2692 && ! function_label_operand (operands[2], Pmode)
2696 [(set_attr "type" "binary")
2697 (set_attr "length" "4")])
2699 ;; Always use addil rather than ldil;add sequences. This allows the
2700 ;; HP linker to eliminate the dp relocation if the symbolic operand
2701 ;; lives in the TEXT space.
2703 [(set (match_operand:SI 0 "register_operand" "=a")
2704 (high:SI (match_operand 1 "" "")))]
2705 "symbolic_operand (operands[1], Pmode)
2706 && ! function_label_operand (operands[1], Pmode)
2707 && ! read_only_operand (operands[1], Pmode)
2711 if (TARGET_LONG_LOAD_STORE)
2712 return \"addil NLR'%H1,%%r27\;ldo N'%H1(%%r1),%%r1\";
2714 return \"addil LR'%H1,%%r27\";
2716 [(set_attr "type" "binary")
2717 (set (attr "length")
2718 (if_then_else (not (match_test "TARGET_LONG_LOAD_STORE"))
2723 ;; This is for use in the prologue/epilogue code. We need it
2724 ;; to add large constants to a stack pointer or frame pointer.
2725 ;; Because of the additional %r1 pressure, we probably do not
2726 ;; want to use this in general code, so make it available
2727 ;; only after reload.
2729 [(set (match_operand:SI 0 "register_operand" "=!a,*r")
2730 (plus:SI (match_operand:SI 1 "register_operand" "r,r")
2731 (high:SI (match_operand 2 "const_int_operand" ""))))]
2735 ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
2736 [(set_attr "type" "binary,binary")
2737 (set_attr "length" "4,8")])
2740 [(set (match_operand:DI 0 "register_operand" "=!a,*r")
2741 (plus:DI (match_operand:DI 1 "register_operand" "r,r")
2742 (high:DI (match_operand 2 "const_int_operand" ""))))]
2743 "reload_completed && TARGET_64BIT"
2746 ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
2747 [(set_attr "type" "binary,binary")
2748 (set_attr "length" "4,8")])
2751 [(set (match_operand:SI 0 "register_operand" "=r")
2752 (high:SI (match_operand 1 "" "")))]
2753 "(!flag_pic || !symbolic_operand (operands[1], Pmode))
2754 && !pa_is_function_label_plus_const (operands[1])"
2757 if (symbolic_operand (operands[1], Pmode))
2758 return \"ldil LR'%H1,%0\";
2760 return \"ldil L'%G1,%0\";
2762 [(set_attr "type" "move")
2763 (set_attr "length" "4")])
2766 [(set (match_operand:DI 0 "register_operand" "=r")
2767 (high:DI (match_operand 1 "const_int_operand" "")))]
2770 [(set_attr "type" "move")
2771 (set_attr "length" "4")])
2774 [(set (match_operand:DI 0 "register_operand" "=r")
2775 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2776 (match_operand:DI 2 "const_int_operand" "i")))]
2779 [(set_attr "type" "move")
2780 (set_attr "length" "4")])
2783 [(set (match_operand:SI 0 "register_operand" "=r")
2784 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
2785 (match_operand:SI 2 "immediate_operand" "i")))]
2786 "!pa_is_function_label_plus_const (operands[2])"
2789 gcc_assert (!flag_pic || !symbolic_operand (operands[2], Pmode));
2791 if (symbolic_operand (operands[2], Pmode))
2792 return \"ldo RR'%G2(%1),%0\";
2794 return \"ldo R'%G2(%1),%0\";
2796 [(set_attr "type" "move")
2797 (set_attr "length" "4")])
2799 ;; Now that a symbolic_address plus a constant is broken up early
2800 ;; in the compilation phase (for better CSE) we need a special
2801 ;; combiner pattern to load the symbolic address plus the constant
2802 ;; in only 2 instructions. (For cases where the symbolic address
2803 ;; was not a common subexpression.)
2805 [(set (match_operand:SI 0 "register_operand" "")
2806 (match_operand:SI 1 "symbolic_operand" ""))
2807 (clobber (match_operand:SI 2 "register_operand" ""))]
2808 "! (flag_pic && pic_label_operand (operands[1], SImode))"
2809 [(set (match_dup 2) (high:SI (match_dup 1)))
2810 (set (match_dup 0) (lo_sum:SI (match_dup 2) (match_dup 1)))]
2813 ;; hppa_legitimize_address goes to a great deal of trouble to
2814 ;; create addresses which use indexing. In some cases, this
2815 ;; is a lose because there isn't any store instructions which
2816 ;; allow indexed addresses (with integer register source).
2818 ;; These define_splits try to turn a 3 insn store into
2819 ;; a 2 insn store with some creative RTL rewriting.
2821 [(set (mem:SI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2822 (match_operand:SI 1 "mem_shadd_operand" ""))
2823 (plus:SI (match_operand:SI 2 "register_operand" "")
2824 (match_operand:SI 3 "const_int_operand" ""))))
2825 (match_operand:SI 4 "register_operand" ""))
2826 (clobber (match_operand:SI 5 "register_operand" ""))]
2828 [(set (match_dup 5) (plus:SI (ashift:SI (match_dup 0) (match_dup 1))
2830 (set (mem:SI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2833 operands[1] = GEN_INT (exact_log2 (INTVAL (operands[1])));
2838 [(set (mem:HI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2839 (match_operand:SI 1 "mem_shadd_operand" ""))
2840 (plus:SI (match_operand:SI 2 "register_operand" "")
2841 (match_operand:SI 3 "const_int_operand" ""))))
2842 (match_operand:HI 4 "register_operand" ""))
2843 (clobber (match_operand:SI 5 "register_operand" ""))]
2845 [(set (match_dup 5) (plus:SI (ashift:SI (match_dup 0) (match_dup 1))
2847 (set (mem:HI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2850 operands[1] = GEN_INT (exact_log2 (INTVAL (operands[1])));
2855 [(set (mem:QI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
2856 (match_operand:SI 1 "mem_shadd_operand" ""))
2857 (plus:SI (match_operand:SI 2 "register_operand" "")
2858 (match_operand:SI 3 "const_int_operand" ""))))
2859 (match_operand:QI 4 "register_operand" ""))
2860 (clobber (match_operand:SI 5 "register_operand" ""))]
2862 [(set (match_dup 5) (plus:SI (ashift:SI (match_dup 0) (match_dup 1))
2864 (set (mem:QI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
2867 operands[1] = GEN_INT (exact_log2 (INTVAL (operands[1])));
2871 (define_expand "movhi"
2872 [(set (match_operand:HI 0 "general_operand" "")
2873 (match_operand:HI 1 "general_operand" ""))]
2877 if (pa_emit_move_sequence (operands, HImode, 0))
2881 ;; Handle HImode input reloads requiring a general register as a
2882 ;; scratch register.
2883 (define_expand "reload_inhi"
2884 [(set (match_operand:HI 0 "register_operand" "=Z")
2885 (match_operand:HI 1 "non_hard_reg_operand" ""))
2886 (clobber (match_operand:HI 2 "register_operand" "=&r"))]
2890 if (pa_emit_move_sequence (operands, HImode, operands[2]))
2893 /* We don't want the clobber emitted, so handle this ourselves. */
2894 emit_insn (gen_rtx_SET (operands[0], operands[1]));
2898 ;; Handle HImode output reloads requiring a general register as a
2899 ;; scratch register.
2900 (define_expand "reload_outhi"
2901 [(set (match_operand:HI 0 "non_hard_reg_operand" "")
2902 (match_operand:HI 1 "register_operand" "Z"))
2903 (clobber (match_operand:HI 2 "register_operand" "=&r"))]
2907 if (pa_emit_move_sequence (operands, HImode, operands[2]))
2910 /* We don't want the clobber emitted, so handle this ourselves. */
2911 emit_insn (gen_rtx_SET (operands[0], operands[1]));
2916 [(set (match_operand:HI 0 "move_dest_operand"
2917 "=r,r,r,r,r,Q,!*q,!r")
2918 (match_operand:HI 1 "move_src_operand"
2919 "r,J,N,K,RQ,rM,!rM,!*q"))]
2920 "(register_operand (operands[0], HImode)
2921 || reg_or_0_operand (operands[1], HImode))"
2926 {zdepi|depwi,z} %Z1,%0
2930 {mfctl|mfctl,w} %sar,%0"
2931 [(set_attr "type" "move,move,move,shift,load,store,move,move")
2932 (set_attr "pa_combine_type" "addmove")
2933 (set_attr "length" "4,4,4,4,4,4,4,4")])
2936 [(set (match_operand:HI 0 "register_operand" "=r")
2937 (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2938 (match_operand:SI 2 "int5_operand" "L"))))
2940 (plus:SI (match_dup 1) (match_dup 2)))]
2942 "{ldhs|ldh},mb %2(%1),%0"
2943 [(set_attr "type" "load")
2944 (set_attr "length" "4")])
2947 [(set (match_operand:HI 0 "register_operand" "=r")
2948 (mem:HI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2949 (match_operand:DI 2 "int5_operand" "L"))))
2951 (plus:DI (match_dup 1) (match_dup 2)))]
2954 [(set_attr "type" "load")
2955 (set_attr "length" "4")])
2957 ; And a zero extended variant.
2959 [(set (match_operand:DI 0 "register_operand" "=r")
2960 (zero_extend:DI (mem:HI
2962 (match_operand:DI 1 "register_operand" "+r")
2963 (match_operand:DI 2 "int5_operand" "L")))))
2965 (plus:DI (match_dup 1) (match_dup 2)))]
2968 [(set_attr "type" "load")
2969 (set_attr "length" "4")])
2972 [(set (match_operand:SI 0 "register_operand" "=r")
2973 (zero_extend:SI (mem:HI
2975 (match_operand:SI 1 "register_operand" "+r")
2976 (match_operand:SI 2 "int5_operand" "L")))))
2978 (plus:SI (match_dup 1) (match_dup 2)))]
2980 "{ldhs|ldh},mb %2(%1),%0"
2981 [(set_attr "type" "load")
2982 (set_attr "length" "4")])
2985 [(set (match_operand:SI 0 "register_operand" "=r")
2986 (zero_extend:SI (mem:HI
2988 (match_operand:DI 1 "register_operand" "+r")
2989 (match_operand:DI 2 "int5_operand" "L")))))
2991 (plus:DI (match_dup 1) (match_dup 2)))]
2994 [(set_attr "type" "load")
2995 (set_attr "length" "4")])
2998 [(set (mem:HI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2999 (match_operand:SI 1 "int5_operand" "L")))
3000 (match_operand:HI 2 "reg_or_0_operand" "rM"))
3002 (plus:SI (match_dup 0) (match_dup 1)))]
3004 "{sths|sth},mb %r2,%1(%0)"
3005 [(set_attr "type" "store")
3006 (set_attr "length" "4")])
3009 [(set (mem:HI (plus:DI (match_operand:DI 0 "register_operand" "+r")
3010 (match_operand:DI 1 "int5_operand" "L")))
3011 (match_operand:HI 2 "reg_or_0_operand" "rM"))
3013 (plus:DI (match_dup 0) (match_dup 1)))]
3016 [(set_attr "type" "store")
3017 (set_attr "length" "4")])
3019 (define_insn "addhi3"
3020 [(set (match_operand:HI 0 "register_operand" "=r,r")
3021 (plus:HI (match_operand:HI 1 "register_operand" "%r,r")
3022 (match_operand:HI 2 "arith14_operand" "r,J")))]
3025 {addl|add,l} %1,%2,%0
3027 [(set_attr "type" "binary,binary")
3028 (set_attr "pa_combine_type" "addmove")
3029 (set_attr "length" "4,4")])
3031 (define_expand "movqi"
3032 [(set (match_operand:QI 0 "general_operand" "")
3033 (match_operand:QI 1 "general_operand" ""))]
3037 if (pa_emit_move_sequence (operands, QImode, 0))
3041 ;; Handle QImode input reloads requiring a general register as a
3042 ;; scratch register.
3043 (define_expand "reload_inqi"
3044 [(set (match_operand:QI 0 "register_operand" "=Z")
3045 (match_operand:QI 1 "non_hard_reg_operand" ""))
3046 (clobber (match_operand:QI 2 "register_operand" "=&r"))]
3050 if (pa_emit_move_sequence (operands, QImode, operands[2]))
3053 /* We don't want the clobber emitted, so handle this ourselves. */
3054 emit_insn (gen_rtx_SET (operands[0], operands[1]));
3058 ;; Handle QImode output reloads requiring a general register as a
3059 ;; scratch register.
3060 (define_expand "reload_outqi"
3061 [(set (match_operand:QI 0 "non_hard_reg_operand" "")
3062 (match_operand:QI 1 "register_operand" "Z"))
3063 (clobber (match_operand:QI 2 "register_operand" "=&r"))]
3067 if (pa_emit_move_sequence (operands, QImode, operands[2]))
3070 /* We don't want the clobber emitted, so handle this ourselves. */
3071 emit_insn (gen_rtx_SET (operands[0], operands[1]));
3076 [(set (match_operand:QI 0 "move_dest_operand"
3077 "=r,r,r,r,r,Q,!*q,!r")
3078 (match_operand:QI 1 "move_src_operand"
3079 "r,J,N,K,RQ,rM,!rM,!*q"))]
3080 "(register_operand (operands[0], QImode)
3081 || reg_or_0_operand (operands[1], QImode))"
3086 {zdepi|depwi,z} %Z1,%0
3090 {mfctl|mfctl,w} %%sar,%0"
3091 [(set_attr "type" "move,move,move,shift,load,store,move,move")
3092 (set_attr "pa_combine_type" "addmove")
3093 (set_attr "length" "4,4,4,4,4,4,4,4")])
3096 [(set (match_operand:QI 0 "register_operand" "=r")
3097 (mem:QI (plus:SI (match_operand:SI 1 "register_operand" "+r")
3098 (match_operand:SI 2 "int5_operand" "L"))))
3099 (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3101 "{ldbs|ldb},mb %2(%1),%0"
3102 [(set_attr "type" "load")
3103 (set_attr "length" "4")])
3106 [(set (match_operand:QI 0 "register_operand" "=r")
3107 (mem:QI (plus:DI (match_operand:DI 1 "register_operand" "+r")
3108 (match_operand:DI 2 "int5_operand" "L"))))
3109 (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3112 [(set_attr "type" "load")
3113 (set_attr "length" "4")])
3115 ; Now the same thing with zero extensions.
3117 [(set (match_operand:DI 0 "register_operand" "=r")
3118 (zero_extend:DI (mem:QI (plus:DI
3119 (match_operand:DI 1 "register_operand" "+r")
3120 (match_operand:DI 2 "int5_operand" "L")))))
3121 (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3124 [(set_attr "type" "load")
3125 (set_attr "length" "4")])
3128 [(set (match_operand:SI 0 "register_operand" "=r")
3129 (zero_extend:SI (mem:QI (plus:SI
3130 (match_operand:SI 1 "register_operand" "+r")
3131 (match_operand:SI 2 "int5_operand" "L")))))
3132 (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3134 "{ldbs|ldb},mb %2(%1),%0"
3135 [(set_attr "type" "load")
3136 (set_attr "length" "4")])
3139 [(set (match_operand:SI 0 "register_operand" "=r")
3140 (zero_extend:SI (mem:QI (plus:DI
3141 (match_operand:DI 1 "register_operand" "+r")
3142 (match_operand:DI 2 "int5_operand" "L")))))
3143 (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3146 [(set_attr "type" "load")
3147 (set_attr "length" "4")])
3150 [(set (match_operand:HI 0 "register_operand" "=r")
3151 (zero_extend:HI (mem:QI (plus:SI
3152 (match_operand:SI 1 "register_operand" "+r")
3153 (match_operand:SI 2 "int5_operand" "L")))))
3154 (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3156 "{ldbs|ldb},mb %2(%1),%0"
3157 [(set_attr "type" "load")
3158 (set_attr "length" "4")])
3161 [(set (match_operand:HI 0 "register_operand" "=r")
3162 (zero_extend:HI (mem:QI (plus:DI
3163 (match_operand:DI 1 "register_operand" "+r")
3164 (match_operand:DI 2 "int5_operand" "L")))))
3165 (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3168 [(set_attr "type" "load")
3169 (set_attr "length" "4")])
3172 [(set (mem:QI (plus:SI (match_operand:SI 0 "register_operand" "+r")
3173 (match_operand:SI 1 "int5_operand" "L")))
3174 (match_operand:QI 2 "reg_or_0_operand" "rM"))
3176 (plus:SI (match_dup 0) (match_dup 1)))]
3178 "{stbs|stb},mb %r2,%1(%0)"
3179 [(set_attr "type" "store")
3180 (set_attr "length" "4")])
3183 [(set (mem:QI (plus:DI (match_operand:DI 0 "register_operand" "+r")
3184 (match_operand:DI 1 "int5_operand" "L")))
3185 (match_operand:QI 2 "reg_or_0_operand" "rM"))
3187 (plus:DI (match_dup 0) (match_dup 1)))]
3190 [(set_attr "type" "store")
3191 (set_attr "length" "4")])
3193 ;; The definition of this insn does not really explain what it does,
3194 ;; but it should suffice that anything generated as this insn will be
3195 ;; recognized as a movmemsi operation, and that it will not successfully
3196 ;; combine with anything.
3197 (define_expand "movmemsi"
3198 [(parallel [(set (match_operand:BLK 0 "" "")
3199 (match_operand:BLK 1 "" ""))
3200 (clobber (match_dup 4))
3201 (clobber (match_dup 5))
3202 (clobber (match_dup 6))
3203 (clobber (match_dup 7))
3204 (clobber (match_dup 8))
3205 (use (match_operand:SI 2 "arith14_operand" ""))
3206 (use (match_operand:SI 3 "const_int_operand" ""))])]
3207 "!TARGET_64BIT && optimize > 0"
3212 /* HP provides very fast block move library routine for the PA;
3213 this routine includes:
3215 4x4 byte at a time block moves,
3216 1x4 byte at a time with alignment checked at runtime with
3217 attempts to align the source and destination as needed
3220 With that in mind, here's the heuristics to try and guess when
3221 the inlined block move will be better than the library block
3224 If the size isn't constant, then always use the library routines.
3226 If the size is large in respect to the known alignment, then use
3227 the library routines.
3229 If the size is small in respect to the known alignment, then open
3230 code the copy (since that will lead to better scheduling).
3232 Else use the block move pattern. */
3234 /* Undetermined size, use the library routine. */
3235 if (GET_CODE (operands[2]) != CONST_INT)
3238 size = INTVAL (operands[2]);
3239 align = INTVAL (operands[3]);
3240 align = align > 4 ? 4 : (align ? align : 1);
3242 /* If size/alignment is large, then use the library routines. */
3243 if (size / align > 16)
3246 /* This does happen, but not often enough to worry much about. */
3247 if (size / align < MOVE_RATIO (optimize_insn_for_speed_p ()))
3250 /* Fall through means we're going to use our block move pattern. */
3252 = replace_equiv_address (operands[0],
3253 copy_to_mode_reg (SImode, XEXP (operands[0], 0)));
3255 = replace_equiv_address (operands[1],
3256 copy_to_mode_reg (SImode, XEXP (operands[1], 0)));
3257 operands[4] = gen_reg_rtx (SImode);
3258 operands[5] = gen_reg_rtx (SImode);
3259 operands[6] = gen_reg_rtx (SImode);
3260 operands[7] = gen_reg_rtx (SImode);
3261 operands[8] = gen_reg_rtx (SImode);
3264 ;; The operand constraints are written like this to support both compile-time
3265 ;; and run-time determined byte counts. The expander and pa_output_block_move
3266 ;; only support compile-time determined counts at this time.
3268 ;; If the count is run-time determined, the register with the byte count
3269 ;; is clobbered by the copying code, and therefore it is forced to operand 2.
3271 ;; We used to clobber operands 0 and 1. However, a change to regrename.c
3272 ;; broke this semantic for pseudo registers. We can't use match_scratch
3273 ;; as this requires two registers in the class R1_REGS when the MEMs for
3274 ;; operands 0 and 1 are both equivalent to symbolic MEMs. Thus, we are
3275 ;; forced to internally copy operands 0 and 1 to operands 7 and 8,
3276 ;; respectively. We then split or peephole optimize after reload.
3277 (define_insn "movmemsi_prereload"
3278 [(set (mem:BLK (match_operand:SI 0 "register_operand" "r,r"))
3279 (mem:BLK (match_operand:SI 1 "register_operand" "r,r")))
3280 (clobber (match_operand:SI 2 "register_operand" "=&r,&r")) ;loop cnt/tmp
3281 (clobber (match_operand:SI 3 "register_operand" "=&r,&r")) ;item tmp1
3282 (clobber (match_operand:SI 6 "register_operand" "=&r,&r")) ;item tmp2
3283 (clobber (match_operand:SI 7 "register_operand" "=&r,&r")) ;item tmp3
3284 (clobber (match_operand:SI 8 "register_operand" "=&r,&r")) ;item tmp4
3285 (use (match_operand:SI 4 "arith14_operand" "J,2")) ;byte count
3286 (use (match_operand:SI 5 "const_int_operand" "n,n"))] ;alignment
3289 [(set_attr "type" "multi,multi")])
3292 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3293 (match_operand:BLK 1 "memory_operand" ""))
3294 (clobber (match_operand:SI 2 "register_operand" ""))
3295 (clobber (match_operand:SI 3 "register_operand" ""))
3296 (clobber (match_operand:SI 6 "register_operand" ""))
3297 (clobber (match_operand:SI 7 "register_operand" ""))
3298 (clobber (match_operand:SI 8 "register_operand" ""))
3299 (use (match_operand:SI 4 "arith14_operand" ""))
3300 (use (match_operand:SI 5 "const_int_operand" ""))])]
3301 "!TARGET_64BIT && reload_completed && !flag_peephole2
3302 && GET_CODE (operands[0]) == MEM
3303 && register_operand (XEXP (operands[0], 0), SImode)
3304 && GET_CODE (operands[1]) == MEM
3305 && register_operand (XEXP (operands[1], 0), SImode)"
3306 [(set (match_dup 7) (match_dup 9))
3307 (set (match_dup 8) (match_dup 10))
3308 (parallel [(set (match_dup 0) (match_dup 1))
3309 (clobber (match_dup 2))
3310 (clobber (match_dup 3))
3311 (clobber (match_dup 6))
3312 (clobber (match_dup 7))
3313 (clobber (match_dup 8))
3319 operands[9] = XEXP (operands[0], 0);
3320 operands[10] = XEXP (operands[1], 0);
3321 operands[0] = replace_equiv_address (operands[0], operands[7]);
3322 operands[1] = replace_equiv_address (operands[1], operands[8]);
3326 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3327 (match_operand:BLK 1 "memory_operand" ""))
3328 (clobber (match_operand:SI 2 "register_operand" ""))
3329 (clobber (match_operand:SI 3 "register_operand" ""))
3330 (clobber (match_operand:SI 6 "register_operand" ""))
3331 (clobber (match_operand:SI 7 "register_operand" ""))
3332 (clobber (match_operand:SI 8 "register_operand" ""))
3333 (use (match_operand:SI 4 "arith14_operand" ""))
3334 (use (match_operand:SI 5 "const_int_operand" ""))])]
3336 && GET_CODE (operands[0]) == MEM
3337 && register_operand (XEXP (operands[0], 0), SImode)
3338 && GET_CODE (operands[1]) == MEM
3339 && register_operand (XEXP (operands[1], 0), SImode)"
3340 [(parallel [(set (match_dup 0) (match_dup 1))
3341 (clobber (match_dup 2))
3342 (clobber (match_dup 3))
3343 (clobber (match_dup 6))
3344 (clobber (match_dup 7))
3345 (clobber (match_dup 8))
3351 rtx addr = XEXP (operands[0], 0);
3352 if (dead_or_set_p (curr_insn, addr))
3356 emit_insn (gen_rtx_SET (operands[7], addr));
3357 operands[0] = replace_equiv_address (operands[0], operands[7]);
3360 addr = XEXP (operands[1], 0);
3361 if (dead_or_set_p (curr_insn, addr))
3365 emit_insn (gen_rtx_SET (operands[8], addr));
3366 operands[1] = replace_equiv_address (operands[1], operands[8]);
3370 (define_insn "movmemsi_postreload"
3371 [(set (mem:BLK (match_operand:SI 0 "register_operand" "+r,r"))
3372 (mem:BLK (match_operand:SI 1 "register_operand" "+r,r")))
3373 (clobber (match_operand:SI 2 "register_operand" "=&r,&r")) ;loop cnt/tmp
3374 (clobber (match_operand:SI 3 "register_operand" "=&r,&r")) ;item tmp1
3375 (clobber (match_operand:SI 6 "register_operand" "=&r,&r")) ;item tmp2
3376 (clobber (match_dup 0))
3377 (clobber (match_dup 1))
3378 (use (match_operand:SI 4 "arith14_operand" "J,2")) ;byte count
3379 (use (match_operand:SI 5 "const_int_operand" "n,n")) ;alignment
3381 "!TARGET_64BIT && reload_completed"
3382 "* return pa_output_block_move (operands, !which_alternative);"
3383 [(set_attr "type" "multi,multi")])
3385 (define_expand "movmemdi"
3386 [(parallel [(set (match_operand:BLK 0 "" "")
3387 (match_operand:BLK 1 "" ""))
3388 (clobber (match_dup 4))
3389 (clobber (match_dup 5))
3390 (clobber (match_dup 6))
3391 (clobber (match_dup 7))
3392 (clobber (match_dup 8))
3393 (use (match_operand:DI 2 "arith14_operand" ""))
3394 (use (match_operand:DI 3 "const_int_operand" ""))])]
3395 "TARGET_64BIT && optimize > 0"
3400 /* HP provides very fast block move library routine for the PA;
3401 this routine includes:
3403 4x4 byte at a time block moves,
3404 1x4 byte at a time with alignment checked at runtime with
3405 attempts to align the source and destination as needed
3408 With that in mind, here's the heuristics to try and guess when
3409 the inlined block move will be better than the library block
3412 If the size isn't constant, then always use the library routines.
3414 If the size is large in respect to the known alignment, then use
3415 the library routines.
3417 If the size is small in respect to the known alignment, then open
3418 code the copy (since that will lead to better scheduling).
3420 Else use the block move pattern. */
3422 /* Undetermined size, use the library routine. */
3423 if (GET_CODE (operands[2]) != CONST_INT)
3426 size = INTVAL (operands[2]);
3427 align = INTVAL (operands[3]);
3428 align = align > 8 ? 8 : (align ? align : 1);
3430 /* If size/alignment is large, then use the library routines. */
3431 if (size / align > 16)
3434 /* This does happen, but not often enough to worry much about. */
3435 if (size / align < MOVE_RATIO (optimize_insn_for_speed_p ()))
3438 /* Fall through means we're going to use our block move pattern. */
3440 = replace_equiv_address (operands[0],
3441 copy_to_mode_reg (DImode, XEXP (operands[0], 0)));
3443 = replace_equiv_address (operands[1],
3444 copy_to_mode_reg (DImode, XEXP (operands[1], 0)));
3445 operands[4] = gen_reg_rtx (DImode);
3446 operands[5] = gen_reg_rtx (DImode);
3447 operands[6] = gen_reg_rtx (DImode);
3448 operands[7] = gen_reg_rtx (DImode);
3449 operands[8] = gen_reg_rtx (DImode);
3452 ;; The operand constraints are written like this to support both compile-time
3453 ;; and run-time determined byte counts. The expander and pa_output_block_move
3454 ;; only support compile-time determined counts at this time.
3456 ;; If the count is run-time determined, the register with the byte count
3457 ;; is clobbered by the copying code, and therefore it is forced to operand 2.
3459 ;; We used to clobber operands 0 and 1. However, a change to regrename.c
3460 ;; broke this semantic for pseudo registers. We can't use match_scratch
3461 ;; as this requires two registers in the class R1_REGS when the MEMs for
3462 ;; operands 0 and 1 are both equivalent to symbolic MEMs. Thus, we are
3463 ;; forced to internally copy operands 0 and 1 to operands 7 and 8,
3464 ;; respectively. We then split or peephole optimize after reload.
3465 (define_insn "movmemdi_prereload"
3466 [(set (mem:BLK (match_operand:DI 0 "register_operand" "r,r"))
3467 (mem:BLK (match_operand:DI 1 "register_operand" "r,r")))
3468 (clobber (match_operand:DI 2 "register_operand" "=&r,&r")) ;loop cnt/tmp
3469 (clobber (match_operand:DI 3 "register_operand" "=&r,&r")) ;item tmp1
3470 (clobber (match_operand:DI 6 "register_operand" "=&r,&r")) ;item tmp2
3471 (clobber (match_operand:DI 7 "register_operand" "=&r,&r")) ;item tmp3
3472 (clobber (match_operand:DI 8 "register_operand" "=&r,&r")) ;item tmp4
3473 (use (match_operand:DI 4 "arith14_operand" "J,2")) ;byte count
3474 (use (match_operand:DI 5 "const_int_operand" "n,n"))] ;alignment
3477 [(set_attr "type" "multi,multi")])
3480 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3481 (match_operand:BLK 1 "memory_operand" ""))
3482 (clobber (match_operand:DI 2 "register_operand" ""))
3483 (clobber (match_operand:DI 3 "register_operand" ""))
3484 (clobber (match_operand:DI 6 "register_operand" ""))
3485 (clobber (match_operand:DI 7 "register_operand" ""))
3486 (clobber (match_operand:DI 8 "register_operand" ""))
3487 (use (match_operand:DI 4 "arith14_operand" ""))
3488 (use (match_operand:DI 5 "const_int_operand" ""))])]
3489 "TARGET_64BIT && reload_completed && !flag_peephole2
3490 && GET_CODE (operands[0]) == MEM
3491 && register_operand (XEXP (operands[0], 0), DImode)
3492 && GET_CODE (operands[1]) == MEM
3493 && register_operand (XEXP (operands[1], 0), DImode)"
3494 [(set (match_dup 7) (match_dup 9))
3495 (set (match_dup 8) (match_dup 10))
3496 (parallel [(set (match_dup 0) (match_dup 1))
3497 (clobber (match_dup 2))
3498 (clobber (match_dup 3))
3499 (clobber (match_dup 6))
3500 (clobber (match_dup 7))
3501 (clobber (match_dup 8))
3507 operands[9] = XEXP (operands[0], 0);
3508 operands[10] = XEXP (operands[1], 0);
3509 operands[0] = replace_equiv_address (operands[0], operands[7]);
3510 operands[1] = replace_equiv_address (operands[1], operands[8]);
3514 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3515 (match_operand:BLK 1 "memory_operand" ""))
3516 (clobber (match_operand:DI 2 "register_operand" ""))
3517 (clobber (match_operand:DI 3 "register_operand" ""))
3518 (clobber (match_operand:DI 6 "register_operand" ""))
3519 (clobber (match_operand:DI 7 "register_operand" ""))
3520 (clobber (match_operand:DI 8 "register_operand" ""))
3521 (use (match_operand:DI 4 "arith14_operand" ""))
3522 (use (match_operand:DI 5 "const_int_operand" ""))])]
3524 && GET_CODE (operands[0]) == MEM
3525 && register_operand (XEXP (operands[0], 0), DImode)
3526 && GET_CODE (operands[1]) == MEM
3527 && register_operand (XEXP (operands[1], 0), DImode)"
3528 [(parallel [(set (match_dup 0) (match_dup 1))
3529 (clobber (match_dup 2))
3530 (clobber (match_dup 3))
3531 (clobber (match_dup 6))
3532 (clobber (match_dup 7))
3533 (clobber (match_dup 8))
3539 rtx addr = XEXP (operands[0], 0);
3540 if (dead_or_set_p (curr_insn, addr))
3544 emit_insn (gen_rtx_SET (operands[7], addr));
3545 operands[0] = replace_equiv_address (operands[0], operands[7]);
3548 addr = XEXP (operands[1], 0);
3549 if (dead_or_set_p (curr_insn, addr))
3553 emit_insn (gen_rtx_SET (operands[8], addr));
3554 operands[1] = replace_equiv_address (operands[1], operands[8]);
3558 (define_insn "movmemdi_postreload"
3559 [(set (mem:BLK (match_operand:DI 0 "register_operand" "+r,r"))
3560 (mem:BLK (match_operand:DI 1 "register_operand" "+r,r")))
3561 (clobber (match_operand:DI 2 "register_operand" "=&r,&r")) ;loop cnt/tmp
3562 (clobber (match_operand:DI 3 "register_operand" "=&r,&r")) ;item tmp1
3563 (clobber (match_operand:DI 6 "register_operand" "=&r,&r")) ;item tmp2
3564 (clobber (match_dup 0))
3565 (clobber (match_dup 1))
3566 (use (match_operand:DI 4 "arith14_operand" "J,2")) ;byte count
3567 (use (match_operand:DI 5 "const_int_operand" "n,n")) ;alignment
3569 "TARGET_64BIT && reload_completed"
3570 "* return pa_output_block_move (operands, !which_alternative);"
3571 [(set_attr "type" "multi,multi")])
3573 (define_expand "setmemsi"
3574 [(parallel [(set (match_operand:BLK 0 "" "")
3575 (match_operand 2 "const_int_operand" ""))
3576 (clobber (match_dup 4))
3577 (clobber (match_dup 5))
3578 (use (match_operand:SI 1 "arith14_operand" ""))
3579 (use (match_operand:SI 3 "const_int_operand" ""))])]
3580 "!TARGET_64BIT && optimize > 0"
3585 /* If value to set is not zero, use the library routine. */
3586 if (operands[2] != const0_rtx)
3589 /* Undetermined size, use the library routine. */
3590 if (GET_CODE (operands[1]) != CONST_INT)
3593 size = INTVAL (operands[1]);
3594 align = INTVAL (operands[3]);
3595 align = align > 4 ? 4 : align;
3597 /* If size/alignment is large, then use the library routines. */
3598 if (size / align > 16)
3601 /* This does happen, but not often enough to worry much about. */
3602 if (size / align < MOVE_RATIO (optimize_insn_for_speed_p ()))
3605 /* Fall through means we're going to use our block clear pattern. */
3607 = replace_equiv_address (operands[0],
3608 copy_to_mode_reg (SImode, XEXP (operands[0], 0)));
3609 operands[4] = gen_reg_rtx (SImode);
3610 operands[5] = gen_reg_rtx (SImode);
3613 (define_insn "clrmemsi_prereload"
3614 [(set (mem:BLK (match_operand:SI 0 "register_operand" "r,r"))
3616 (clobber (match_operand:SI 1 "register_operand" "=&r,&r")) ;loop cnt/tmp
3617 (clobber (match_operand:SI 4 "register_operand" "=&r,&r")) ;tmp1
3618 (use (match_operand:SI 2 "arith14_operand" "J,1")) ;byte count
3619 (use (match_operand:SI 3 "const_int_operand" "n,n"))] ;alignment
3622 [(set_attr "type" "multi,multi")])
3625 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3627 (clobber (match_operand:SI 1 "register_operand" ""))
3628 (clobber (match_operand:SI 4 "register_operand" ""))
3629 (use (match_operand:SI 2 "arith14_operand" ""))
3630 (use (match_operand:SI 3 "const_int_operand" ""))])]
3631 "!TARGET_64BIT && reload_completed && !flag_peephole2
3632 && GET_CODE (operands[0]) == MEM
3633 && register_operand (XEXP (operands[0], 0), SImode)"
3634 [(set (match_dup 4) (match_dup 5))
3635 (parallel [(set (match_dup 0) (const_int 0))
3636 (clobber (match_dup 1))
3637 (clobber (match_dup 4))
3643 operands[5] = XEXP (operands[0], 0);
3644 operands[0] = replace_equiv_address (operands[0], operands[4]);
3648 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3650 (clobber (match_operand:SI 1 "register_operand" ""))
3651 (clobber (match_operand:SI 4 "register_operand" ""))
3652 (use (match_operand:SI 2 "arith14_operand" ""))
3653 (use (match_operand:SI 3 "const_int_operand" ""))])]
3655 && GET_CODE (operands[0]) == MEM
3656 && register_operand (XEXP (operands[0], 0), SImode)"
3657 [(parallel [(set (match_dup 0) (const_int 0))
3658 (clobber (match_dup 1))
3659 (clobber (match_dup 4))
3665 rtx addr = XEXP (operands[0], 0);
3666 if (dead_or_set_p (curr_insn, addr))
3670 emit_insn (gen_rtx_SET (operands[4], addr));
3671 operands[0] = replace_equiv_address (operands[0], operands[4]);
3675 (define_insn "clrmemsi_postreload"
3676 [(set (mem:BLK (match_operand:SI 0 "register_operand" "+r,r"))
3678 (clobber (match_operand:SI 1 "register_operand" "=&r,&r")) ;loop cnt/tmp
3679 (clobber (match_dup 0))
3680 (use (match_operand:SI 2 "arith14_operand" "J,1")) ;byte count
3681 (use (match_operand:SI 3 "const_int_operand" "n,n")) ;alignment
3683 "!TARGET_64BIT && reload_completed"
3684 "* return pa_output_block_clear (operands, !which_alternative);"
3685 [(set_attr "type" "multi,multi")])
3687 (define_expand "setmemdi"
3688 [(parallel [(set (match_operand:BLK 0 "" "")
3689 (match_operand 2 "const_int_operand" ""))
3690 (clobber (match_dup 4))
3691 (clobber (match_dup 5))
3692 (use (match_operand:DI 1 "arith14_operand" ""))
3693 (use (match_operand:DI 3 "const_int_operand" ""))])]
3694 "TARGET_64BIT && optimize > 0"
3699 /* If value to set is not zero, use the library routine. */
3700 if (operands[2] != const0_rtx)
3703 /* Undetermined size, use the library routine. */
3704 if (GET_CODE (operands[1]) != CONST_INT)
3707 size = INTVAL (operands[1]);
3708 align = INTVAL (operands[3]);
3709 align = align > 8 ? 8 : align;
3711 /* If size/alignment is large, then use the library routines. */
3712 if (size / align > 16)
3715 /* This does happen, but not often enough to worry much about. */
3716 if (size / align < MOVE_RATIO (optimize_insn_for_speed_p ()))
3719 /* Fall through means we're going to use our block clear pattern. */
3721 = replace_equiv_address (operands[0],
3722 copy_to_mode_reg (DImode, XEXP (operands[0], 0)));
3723 operands[4] = gen_reg_rtx (DImode);
3724 operands[5] = gen_reg_rtx (DImode);
3727 (define_insn "clrmemdi_prereload"
3728 [(set (mem:BLK (match_operand:DI 0 "register_operand" "r,r"))
3730 (clobber (match_operand:DI 1 "register_operand" "=&r,&r")) ;loop cnt/tmp
3731 (clobber (match_operand:DI 4 "register_operand" "=&r,&r")) ;item tmp1
3732 (use (match_operand:DI 2 "arith14_operand" "J,1")) ;byte count
3733 (use (match_operand:DI 3 "const_int_operand" "n,n"))] ;alignment
3736 [(set_attr "type" "multi,multi")])
3739 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3741 (clobber (match_operand:DI 1 "register_operand" ""))
3742 (clobber (match_operand:DI 4 "register_operand" ""))
3743 (use (match_operand:DI 2 "arith14_operand" ""))
3744 (use (match_operand:DI 3 "const_int_operand" ""))])]
3745 "TARGET_64BIT && reload_completed && !flag_peephole2
3746 && GET_CODE (operands[0]) == MEM
3747 && register_operand (XEXP (operands[0], 0), DImode)"
3748 [(set (match_dup 4) (match_dup 5))
3749 (parallel [(set (match_dup 0) (const_int 0))
3750 (clobber (match_dup 1))
3751 (clobber (match_dup 4))
3757 operands[5] = XEXP (operands[0], 0);
3758 operands[0] = replace_equiv_address (operands[0], operands[4]);
3762 [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3764 (clobber (match_operand:DI 1 "register_operand" ""))
3765 (clobber (match_operand:DI 4 "register_operand" ""))
3766 (use (match_operand:DI 2 "arith14_operand" ""))
3767 (use (match_operand:DI 3 "const_int_operand" ""))])]
3769 && GET_CODE (operands[0]) == MEM
3770 && register_operand (XEXP (operands[0], 0), DImode)"
3771 [(parallel [(set (match_dup 0) (const_int 0))
3772 (clobber (match_dup 1))
3773 (clobber (match_dup 4))
3779 rtx addr = XEXP (operands[0], 0);
3780 if (dead_or_set_p (curr_insn, addr))
3784 emit_insn (gen_rtx_SET (operands[4], addr));
3785 operands[0] = replace_equiv_address (operands[0], operands[4]);
3789 (define_insn "clrmemdi_postreload"
3790 [(set (mem:BLK (match_operand:DI 0 "register_operand" "+r,r"))
3792 (clobber (match_operand:DI 1 "register_operand" "=&r,&r")) ;loop cnt/tmp
3793 (clobber (match_dup 0))
3794 (use (match_operand:DI 2 "arith14_operand" "J,1")) ;byte count
3795 (use (match_operand:DI 3 "const_int_operand" "n,n")) ;alignment
3797 "TARGET_64BIT && reload_completed"
3798 "* return pa_output_block_clear (operands, !which_alternative);"
3799 [(set_attr "type" "multi,multi")])
3801 ;; Floating point move insns
3803 (define_expand "movdf"
3804 [(set (match_operand:DF 0 "general_operand" "")
3805 (match_operand:DF 1 "general_operand" ""))]
3809 if (pa_emit_move_sequence (operands, DFmode, 0))
3813 ;; Handle DFmode input reloads requiring %r1 as a scratch register.
3814 (define_expand "reload_indf_r1"
3815 [(set (match_operand:DF 0 "register_operand" "=Z")
3816 (match_operand:DF 1 "non_hard_reg_operand" ""))
3817 (clobber (match_operand:SI 2 "register_operand" "=&a"))]
3821 if (pa_emit_move_sequence (operands, DFmode, operands[2]))
3824 /* We don't want the clobber emitted, so handle this ourselves. */
3825 emit_insn (gen_rtx_SET (operands[0], operands[1]));
3829 ;; Handle DFmode input reloads requiring a general register as a
3830 ;; scratch register.
3831 (define_expand "reload_indf"
3832 [(set (match_operand:DF 0 "register_operand" "=Z")
3833 (match_operand:DF 1 "non_hard_reg_operand" ""))
3834 (clobber (match_operand:DF 2 "register_operand" "=&r"))]
3838 if (pa_emit_move_sequence (operands, DFmode, operands[2]))
3841 /* We don't want the clobber emitted, so handle this ourselves. */
3842 emit_insn (gen_rtx_SET (operands[0], operands[1]));
3846 ;; Handle DFmode output reloads requiring a general register as a
3847 ;; scratch register.
3848 (define_expand "reload_outdf"
3849 [(set (match_operand:DF 0 "non_hard_reg_operand" "")
3850 (match_operand:DF 1 "register_operand" "Z"))
3851 (clobber (match_operand:DF 2 "register_operand" "=&r"))]
3855 if (pa_emit_move_sequence (operands, DFmode, operands[2]))
3858 /* We don't want the clobber emitted, so handle this ourselves. */
3859 emit_insn (gen_rtx_SET (operands[0], operands[1]));
3864 [(set (match_operand:DF 0 "move_dest_operand"
3865 "=f,*r,T,?o,?Q,f,*r,*r,?*r,?f")
3866 (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
3867 "fG,*rG,f,*r,*r,RT,o,RQ,f,*r"))]
3868 "(register_operand (operands[0], DFmode)
3869 || reg_or_0_operand (operands[1], DFmode))
3870 && !(GET_CODE (operands[1]) == CONST_DOUBLE
3871 && GET_CODE (operands[0]) == MEM)
3873 && !TARGET_SOFT_FLOAT"
3876 if ((FP_REG_P (operands[0]) || FP_REG_P (operands[1])
3877 || operands[1] == CONST0_RTX (DFmode))
3878 && !(REG_P (operands[0]) && REG_P (operands[1])
3879 && FP_REG_P (operands[0]) ^ FP_REG_P (operands[1])))
3880 return pa_output_fp_move_double (operands);
3881 return pa_output_move_double (operands);
3883 [(set_attr "type" "fpalu,move,fpstore,store,store,fpload,load,load,fpstore_load,store_fpload")
3884 (set_attr "length" "4,8,4,8,16,4,8,16,12,12")])
3887 [(set (match_operand:DF 0 "indexed_memory_operand" "=R")
3888 (match_operand:DF 1 "reg_or_0_operand" "f"))]
3890 && !TARGET_DISABLE_INDEXING
3891 && reload_completed"
3893 [(set_attr "type" "fpstore")
3894 (set_attr "pa_combine_type" "addmove")
3895 (set_attr "length" "4")])
3898 [(set (match_operand:SI 0 "register_operand" "")
3899 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
3901 (match_operand:SI 2 "register_operand" "")))
3902 (set (mem:DF (match_dup 0))
3903 (match_operand:DF 3 "register_operand" ""))]
3905 && !TARGET_DISABLE_INDEXING
3906 && REG_OK_FOR_BASE_P (operands[2])
3907 && FP_REGNO_P (REGNO (operands[3]))"
3908 [(set (mem:DF (plus:SI (mult:SI (match_dup 1) (const_int 8)) (match_dup 2)))
3910 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 8))
3915 [(set (match_operand:SI 0 "register_operand" "")
3916 (plus:SI (match_operand:SI 2 "register_operand" "")
3917 (mult:SI (match_operand:SI 1 "register_operand" "")
3919 (set (mem:DF (match_dup 0))
3920 (match_operand:DF 3 "register_operand" ""))]
3922 && !TARGET_DISABLE_INDEXING
3923 && REG_OK_FOR_BASE_P (operands[2])
3924 && FP_REGNO_P (REGNO (operands[3]))"
3925 [(set (mem:DF (plus:SI (mult:SI (match_dup 1) (const_int 8)) (match_dup 2)))
3927 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 8))
3932 [(set (match_operand:DI 0 "register_operand" "")
3933 (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
3935 (match_operand:DI 2 "register_operand" "")))
3936 (set (mem:DF (match_dup 0))
3937 (match_operand:DF 3 "register_operand" ""))]
3939 && !TARGET_DISABLE_INDEXING
3941 && REG_OK_FOR_BASE_P (operands[2])
3942 && FP_REGNO_P (REGNO (operands[3]))"
3943 [(set (mem:DF (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
3945 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
3950 [(set (match_operand:DI 0 "register_operand" "")
3951 (plus:DI (match_operand:DI 2 "register_operand" "")
3952 (mult:DI (match_operand:DI 1 "register_operand" "")
3954 (set (mem:DF (match_dup 0))
3955 (match_operand:DF 3 "register_operand" ""))]
3957 && !TARGET_DISABLE_INDEXING
3959 && REG_OK_FOR_BASE_P (operands[2])
3960 && FP_REGNO_P (REGNO (operands[3]))"
3961 [(set (mem:DF (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
3963 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
3968 [(set (match_operand:SI 0 "register_operand" "")
3969 (plus:SI (match_operand:SI 1 "register_operand" "")
3970 (match_operand:SI 2 "register_operand" "")))
3971 (set (mem:DF (match_dup 0))
3972 (match_operand:DF 3 "register_operand" ""))]
3974 && !TARGET_DISABLE_INDEXING
3975 && TARGET_NO_SPACE_REGS
3976 && REG_OK_FOR_INDEX_P (operands[1])
3977 && REG_OK_FOR_BASE_P (operands[2])
3978 && FP_REGNO_P (REGNO (operands[3]))"
3979 [(set (mem:DF (plus:SI (match_dup 1) (match_dup 2)))
3981 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
3985 [(set (match_operand:SI 0 "register_operand" "")
3986 (plus:SI (match_operand:SI 1 "register_operand" "")
3987 (match_operand:SI 2 "register_operand" "")))
3988 (set (mem:DF (match_dup 0))
3989 (match_operand:DF 3 "register_operand" ""))]
3991 && !TARGET_DISABLE_INDEXING
3992 && TARGET_NO_SPACE_REGS
3993 && REG_OK_FOR_BASE_P (operands[1])
3994 && REG_OK_FOR_INDEX_P (operands[2])
3995 && FP_REGNO_P (REGNO (operands[3]))"
3996 [(set (mem:DF (plus:SI (match_dup 2) (match_dup 1)))
3998 (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
4002 [(set (match_operand:DI 0 "register_operand" "")
4003 (plus:DI (match_operand:DI 1 "register_operand" "")
4004 (match_operand:DI 2 "register_operand" "")))
4005 (set (mem:DF (match_dup 0))
4006 (match_operand:DF 3 "register_operand" ""))]
4008 && !TARGET_DISABLE_INDEXING
4010 && TARGET_NO_SPACE_REGS
4011 && REG_OK_FOR_INDEX_P (operands[1])
4012 && REG_OK_FOR_BASE_P (operands[2])
4013 && FP_REGNO_P (REGNO (operands[3]))"
4014 [(set (mem:DF (plus:DI (match_dup 1) (match_dup 2)))
4016 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4020 [(set (match_operand:DI 0 "register_operand" "")
4021 (plus:DI (match_operand:DI 1 "register_operand" "")
4022 (match_operand:DI 2 "register_operand" "")))
4023 (set (mem:DF (match_dup 0))
4024 (match_operand:DF 3 "register_operand" ""))]
4026 && !TARGET_DISABLE_INDEXING
4028 && TARGET_NO_SPACE_REGS
4029 && REG_OK_FOR_BASE_P (operands[1])
4030 && REG_OK_FOR_INDEX_P (operands[2])
4031 && FP_REGNO_P (REGNO (operands[3]))"
4032 [(set (mem:DF (plus:DI (match_dup 2) (match_dup 1)))
4034 (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4038 [(set (match_operand:DF 0 "move_dest_operand"
4040 (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
4042 "(register_operand (operands[0], DFmode)
4043 || reg_or_0_operand (operands[1], DFmode))
4045 && TARGET_SOFT_FLOAT"
4048 return pa_output_move_double (operands);
4050 [(set_attr "type" "move,store,store,load,load")
4051 (set_attr "length" "8,8,16,8,16")])
4054 [(set (match_operand:DF 0 "move_dest_operand"
4055 "=!*r,*r,*r,*r,*r,Q,f,f,T")
4056 (match_operand:DF 1 "move_src_operand"
4057 "!*r,J,N,K,RQ,*rG,fG,RT,f"))]
4058 "(register_operand (operands[0], DFmode)
4059 || reg_or_0_operand (operands[1], DFmode))
4060 && !TARGET_SOFT_FLOAT && TARGET_64BIT"
4071 [(set_attr "type" "move,move,move,shift,load,store,fpalu,fpload,fpstore")
4072 (set_attr "pa_combine_type" "addmove")
4073 (set_attr "length" "4,4,4,4,4,4,4,4,4")])
4076 (define_expand "movdi"
4077 [(set (match_operand:DI 0 "general_operand" "")
4078 (match_operand:DI 1 "general_operand" ""))]
4082 if (pa_emit_move_sequence (operands, DImode, 0))
4086 ;; Handle DImode input reloads requiring %r1 as a scratch register.
4087 (define_expand "reload_indi_r1"
4088 [(set (match_operand:DI 0 "register_operand" "=Z")
4089 (match_operand:DI 1 "non_hard_reg_operand" ""))
4090 (clobber (match_operand:SI 2 "register_operand" "=&a"))]
4094 if (pa_emit_move_sequence (operands, DImode, operands[2]))
4097 /* We don't want the clobber emitted, so handle this ourselves. */
4098 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4102 ;; Handle DImode input reloads requiring a general register as a
4103 ;; scratch register.
4104 (define_expand "reload_indi"
4105 [(set (match_operand:DI 0 "register_operand" "=Z")
4106 (match_operand:DI 1 "non_hard_reg_operand" ""))
4107 (clobber (match_operand:SI 2 "register_operand" "=&r"))]
4111 if (pa_emit_move_sequence (operands, DImode, operands[2]))
4114 /* We don't want the clobber emitted, so handle this ourselves. */
4115 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4119 ;; Handle DImode output reloads requiring a general register as a
4120 ;; scratch register.
4121 (define_expand "reload_outdi"
4122 [(set (match_operand:DI 0 "non_hard_reg_operand" "")
4123 (match_operand:DI 1 "register_operand" "Z"))
4124 (clobber (match_operand:SI 2 "register_operand" "=&r"))]
4128 if (pa_emit_move_sequence (operands, DImode, operands[2]))
4131 /* We don't want the clobber emitted, so handle this ourselves. */
4132 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4137 [(set (match_operand:DI 0 "register_operand" "=r")
4138 (high:DI (match_operand 1 "" "")))]
4142 rtx op0 = operands[0];
4143 rtx op1 = operands[1];
4145 switch (GET_CODE (op1))
4148 #if HOST_BITS_PER_WIDE_INT <= 32
4149 operands[0] = operand_subword (op0, 1, 0, DImode);
4150 output_asm_insn (\"ldil L'%1,%0\", operands);
4152 operands[0] = operand_subword (op0, 0, 0, DImode);
4153 if (INTVAL (op1) < 0)
4154 output_asm_insn (\"ldi -1,%0\", operands);
4156 output_asm_insn (\"ldi 0,%0\", operands);
4158 operands[0] = operand_subword (op0, 1, 0, DImode);
4159 operands[1] = GEN_INT (INTVAL (op1) & 0xffffffff);
4160 output_asm_insn (\"ldil L'%1,%0\", operands);
4162 operands[0] = operand_subword (op0, 0, 0, DImode);
4163 operands[1] = GEN_INT (INTVAL (op1) >> 32);
4164 output_asm_insn (pa_singlemove_string (operands), operands);
4169 operands[0] = operand_subword (op0, 1, 0, DImode);
4170 operands[1] = GEN_INT (CONST_DOUBLE_LOW (op1));
4171 output_asm_insn (\"ldil L'%1,%0\", operands);
4173 operands[0] = operand_subword (op0, 0, 0, DImode);
4174 operands[1] = GEN_INT (CONST_DOUBLE_HIGH (op1));
4175 output_asm_insn (pa_singlemove_string (operands), operands);
4183 [(set_attr "type" "move")
4184 (set_attr "length" "12")])
4187 [(set (match_operand:DI 0 "move_dest_operand"
4188 "=r,o,Q,r,r,r,*f,*f,T,?r,?*f")
4189 (match_operand:DI 1 "move_src_operand"
4190 "rM,r,r,o*R,Q,i,*fM,RT,*f,*f,r"))]
4191 "(register_operand (operands[0], DImode)
4192 || reg_or_0_operand (operands[1], DImode))
4194 && !TARGET_SOFT_FLOAT"
4197 if ((FP_REG_P (operands[0]) || FP_REG_P (operands[1])
4198 || operands[1] == CONST0_RTX (DFmode))
4199 && !(REG_P (operands[0]) && REG_P (operands[1])
4200 && FP_REG_P (operands[0]) ^ FP_REG_P (operands[1])))
4201 return pa_output_fp_move_double (operands);
4202 return pa_output_move_double (operands);
4205 "move,store,store,load,load,multi,fpalu,fpload,fpstore,fpstore_load,store_fpload")
4206 (set_attr "length" "8,8,16,8,16,16,4,4,4,12,12")])
4209 [(set (match_operand:DI 0 "move_dest_operand"
4210 "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T")
4211 (match_operand:DI 1 "move_src_operand"
4212 "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f"))]
4213 "(register_operand (operands[0], DImode)
4214 || reg_or_0_operand (operands[1], DImode))
4215 && !TARGET_SOFT_FLOAT && TARGET_64BIT"
4225 {mfctl|mfctl,w} %%sar,%0
4229 [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore")
4230 (set_attr "pa_combine_type" "addmove")
4231 (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4")])
4234 [(set (match_operand:DI 0 "indexed_memory_operand" "=R")
4235 (match_operand:DI 1 "register_operand" "f"))]
4238 && !TARGET_DISABLE_INDEXING
4239 && reload_completed"
4241 [(set_attr "type" "fpstore")
4242 (set_attr "pa_combine_type" "addmove")
4243 (set_attr "length" "4")])
4246 [(set (match_operand:DI 0 "register_operand" "")
4247 (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
4249 (match_operand:DI 2 "register_operand" "")))
4250 (set (mem:DI (match_dup 0))
4251 (match_operand:DI 3 "register_operand" ""))]
4253 && !TARGET_DISABLE_INDEXING
4255 && REG_OK_FOR_BASE_P (operands[2])
4256 && FP_REGNO_P (REGNO (operands[3]))"
4257 [(set (mem:DI (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4259 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4264 [(set (match_operand:DI 0 "register_operand" "")
4265 (plus:DI (match_operand:DI 2 "register_operand" "")
4266 (mult:DI (match_operand:DI 1 "register_operand" "")
4268 (set (mem:DI (match_dup 0))
4269 (match_operand:DI 3 "register_operand" ""))]
4271 && !TARGET_DISABLE_INDEXING
4273 && REG_OK_FOR_BASE_P (operands[2])
4274 && FP_REGNO_P (REGNO (operands[3]))"
4275 [(set (mem:DI (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4277 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4282 [(set (match_operand:DI 0 "register_operand" "")
4283 (plus:DI (match_operand:DI 1 "register_operand" "")
4284 (match_operand:DI 2 "register_operand" "")))
4285 (set (mem:DI (match_dup 0))
4286 (match_operand:DI 3 "register_operand" ""))]
4288 && !TARGET_DISABLE_INDEXING
4290 && TARGET_NO_SPACE_REGS
4291 && REG_OK_FOR_INDEX_P (operands[1])
4292 && REG_OK_FOR_BASE_P (operands[2])
4293 && FP_REGNO_P (REGNO (operands[3]))"
4294 [(set (mem:DI (plus:DI (match_dup 1) (match_dup 2)))
4296 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4300 [(set (match_operand:DI 0 "register_operand" "")
4301 (plus:DI (match_operand:DI 1 "register_operand" "")
4302 (match_operand:DI 2 "register_operand" "")))
4303 (set (mem:DI (match_dup 0))
4304 (match_operand:DI 3 "register_operand" ""))]
4306 && !TARGET_DISABLE_INDEXING
4308 && TARGET_NO_SPACE_REGS
4309 && REG_OK_FOR_BASE_P (operands[1])
4310 && REG_OK_FOR_INDEX_P (operands[2])
4311 && FP_REGNO_P (REGNO (operands[3]))"
4312 [(set (mem:DI (plus:DI (match_dup 2) (match_dup 1)))
4314 (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4318 [(set (match_operand:DI 0 "move_dest_operand"
4320 (match_operand:DI 1 "general_operand"
4322 "(register_operand (operands[0], DImode)
4323 || reg_or_0_operand (operands[1], DImode))
4325 && TARGET_SOFT_FLOAT"
4328 return pa_output_move_double (operands);
4330 [(set_attr "type" "move,store,store,load,load,multi")
4331 (set_attr "length" "8,8,16,8,16,16")])
4334 [(set (match_operand:DI 0 "register_operand" "=r,&r")
4335 (lo_sum:DI (match_operand:DI 1 "register_operand" "0,r")
4336 (match_operand:DI 2 "immediate_operand" "i,i")))]
4340 /* Don't output a 64-bit constant, since we can't trust the assembler to
4341 handle it correctly. */
4342 if (GET_CODE (operands[2]) == CONST_DOUBLE)
4343 operands[2] = GEN_INT (CONST_DOUBLE_LOW (operands[2]));
4344 else if (HOST_BITS_PER_WIDE_INT > 32
4345 && GET_CODE (operands[2]) == CONST_INT)
4346 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xffffffff);
4347 if (which_alternative == 1)
4348 output_asm_insn (\"copy %1,%0\", operands);
4349 return \"ldo R'%G2(%R1),%R0\";
4351 [(set_attr "type" "move,move")
4352 (set_attr "length" "4,8")])
4354 (define_expand "movsf"
4355 [(set (match_operand:SF 0 "general_operand" "")
4356 (match_operand:SF 1 "general_operand" ""))]
4360 if (pa_emit_move_sequence (operands, SFmode, 0))
4364 ;; Handle SFmode input reloads requiring %r1 as a scratch register.
4365 (define_expand "reload_insf_r1"
4366 [(set (match_operand:SF 0 "register_operand" "=Z")
4367 (match_operand:SF 1 "non_hard_reg_operand" ""))
4368 (clobber (match_operand:SI 2 "register_operand" "=&a"))]
4372 if (pa_emit_move_sequence (operands, SFmode, operands[2]))
4375 /* We don't want the clobber emitted, so handle this ourselves. */
4376 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4380 ;; Handle SFmode input reloads requiring a general register as a
4381 ;; scratch register.
4382 (define_expand "reload_insf"
4383 [(set (match_operand:SF 0 "register_operand" "=Z")
4384 (match_operand:SF 1 "non_hard_reg_operand" ""))
4385 (clobber (match_operand:SF 2 "register_operand" "=&r"))]
4389 if (pa_emit_move_sequence (operands, SFmode, operands[2]))
4392 /* We don't want the clobber emitted, so handle this ourselves. */
4393 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4397 ;; Handle SFmode output reloads requiring a general register as a
4398 ;; scratch register.
4399 (define_expand "reload_outsf"
4400 [(set (match_operand:SF 0 "non_hard_reg_operand" "")
4401 (match_operand:SF 1 "register_operand" "Z"))
4402 (clobber (match_operand:SF 2 "register_operand" "=&r"))]
4406 if (pa_emit_move_sequence (operands, SFmode, operands[2]))
4409 /* We don't want the clobber emitted, so handle this ourselves. */
4410 emit_insn (gen_rtx_SET (operands[0], operands[1]));
4415 [(set (match_operand:SF 0 "move_dest_operand"
4416 "=f,!*r,f,*r,T,Q,?*r,?f")
4417 (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4418 "fG,!*rG,RT,RQ,f,*rG,f,*r"))]
4419 "(register_operand (operands[0], SFmode)
4420 || reg_or_0_operand (operands[1], SFmode))
4421 && !TARGET_SOFT_FLOAT
4430 {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
4431 {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
4432 [(set_attr "type" "fpalu,move,fpload,load,fpstore,store,fpstore_load,store_fpload")
4433 (set_attr "pa_combine_type" "addmove")
4434 (set_attr "length" "4,4,4,4,4,4,8,8")])
4437 [(set (match_operand:SF 0 "move_dest_operand"
4439 (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4440 "fG,!*rG,RT,RQ,f,*rG"))]
4441 "(register_operand (operands[0], SFmode)
4442 || reg_or_0_operand (operands[1], SFmode))
4443 && !TARGET_SOFT_FLOAT
4452 [(set_attr "type" "fpalu,move,fpload,load,fpstore,store")
4453 (set_attr "pa_combine_type" "addmove")
4454 (set_attr "length" "4,4,4,4,4,4")])
4457 [(set (match_operand:SF 0 "indexed_memory_operand" "=R")
4458 (match_operand:SF 1 "register_operand" "f"))]
4460 && !TARGET_DISABLE_INDEXING
4461 && reload_completed"
4463 [(set_attr "type" "fpstore")
4464 (set_attr "pa_combine_type" "addmove")
4465 (set_attr "length" "4")])
4468 [(set (match_operand:SI 0 "register_operand" "")
4469 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
4471 (match_operand:SI 2 "register_operand" "")))
4472 (set (mem:SF (match_dup 0))
4473 (match_operand:SF 3 "register_operand" ""))]
4475 && !TARGET_DISABLE_INDEXING
4476 && REG_OK_FOR_BASE_P (operands[2])
4477 && FP_REGNO_P (REGNO (operands[3]))"
4478 [(set (mem:SF (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
4480 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
4485 [(set (match_operand:SI 0 "register_operand" "")
4486 (plus:SI (match_operand:SI 2 "register_operand" "")
4487 (mult:SI (match_operand:SI 1 "register_operand" "")
4489 (set (mem:SF (match_dup 0))
4490 (match_operand:SF 3 "register_operand" ""))]
4492 && !TARGET_DISABLE_INDEXING
4493 && REG_OK_FOR_BASE_P (operands[2])
4494 && FP_REGNO_P (REGNO (operands[3]))"
4495 [(set (mem:SF (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
4497 (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
4502 [(set (match_operand:DI 0 "register_operand" "")
4503 (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
4505 (match_operand:DI 2 "register_operand" "")))
4506 (set (mem:SF (match_dup 0))
4507 (match_operand:SF 3 "register_operand" ""))]
4509 && !TARGET_DISABLE_INDEXING
4511 && REG_OK_FOR_BASE_P (operands[2])
4512 && FP_REGNO_P (REGNO (operands[3]))"
4513 [(set (mem:SF (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
4515 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
4520 [(set (match_operand:DI 0 "register_operand" "")
4521 (plus:DI (match_operand:DI 2 "register_operand" "")
4522 (mult:DI (match_operand:DI 1 "register_operand" "")
4524 (set (mem:SF (match_dup 0))
4525 (match_operand:SF 3 "register_operand" ""))]
4527 && !TARGET_DISABLE_INDEXING
4529 && REG_OK_FOR_BASE_P (operands[2])
4530 && FP_REGNO_P (REGNO (operands[3]))"
4531 [(set (mem:SF (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
4533 (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
4538 [(set (match_operand:SI 0 "register_operand" "")
4539 (plus:SI (match_operand:SI 1 "register_operand" "")
4540 (match_operand:SI 2 "register_operand" "")))
4541 (set (mem:SF (match_dup 0))
4542 (match_operand:SF 3 "register_operand" ""))]
4544 && !TARGET_DISABLE_INDEXING
4545 && TARGET_NO_SPACE_REGS
4546 && REG_OK_FOR_INDEX_P (operands[1])
4547 && REG_OK_FOR_BASE_P (operands[2])
4548 && FP_REGNO_P (REGNO (operands[3]))"
4549 [(set (mem:SF (plus:SI (match_dup 1) (match_dup 2)))
4551 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
4555 [(set (match_operand:SI 0 "register_operand" "")
4556 (plus:SI (match_operand:SI 1 "register_operand" "")
4557 (match_operand:SI 2 "register_operand" "")))
4558 (set (mem:SF (match_dup 0))
4559 (match_operand:SF 3 "register_operand" ""))]
4561 && !TARGET_DISABLE_INDEXING
4562 && TARGET_NO_SPACE_REGS
4563 && REG_OK_FOR_BASE_P (operands[1])
4564 && REG_OK_FOR_INDEX_P (operands[2])
4565 && FP_REGNO_P (REGNO (operands[3]))"
4566 [(set (mem:SF (plus:SI (match_dup 2) (match_dup 1)))
4568 (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
4572 [(set (match_operand:DI 0 "register_operand" "")
4573 (plus:DI (match_operand:DI 1 "register_operand" "")
4574 (match_operand:DI 2 "register_operand" "")))
4575 (set (mem:SF (match_dup 0))
4576 (match_operand:SF 3 "register_operand" ""))]
4578 && !TARGET_DISABLE_INDEXING
4580 && TARGET_NO_SPACE_REGS
4581 && REG_OK_FOR_INDEX_P (operands[1])
4582 && REG_OK_FOR_BASE_P (operands[2])
4583 && FP_REGNO_P (REGNO (operands[3]))"
4584 [(set (mem:SF (plus:DI (match_dup 1) (match_dup 2)))
4586 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4590 [(set (match_operand:DI 0 "register_operand" "")
4591 (plus:DI (match_operand:DI 1 "register_operand" "")
4592 (match_operand:DI 2 "register_operand" "")))
4593 (set (mem:SF (match_dup 0))
4594 (match_operand:SF 3 "register_operand" ""))]
4596 && !TARGET_DISABLE_INDEXING
4598 && TARGET_NO_SPACE_REGS
4599 && REG_OK_FOR_BASE_P (operands[1])
4600 && REG_OK_FOR_INDEX_P (operands[2])
4601 && FP_REGNO_P (REGNO (operands[3]))"
4602 [(set (mem:SF (plus:DI (match_dup 2) (match_dup 1)))
4604 (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4608 [(set (match_operand:SF 0 "move_dest_operand"
4610 (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4612 "(register_operand (operands[0], SFmode)
4613 || reg_or_0_operand (operands[1], SFmode))
4614 && TARGET_SOFT_FLOAT"
4619 [(set_attr "type" "move,load,store")
4620 (set_attr "pa_combine_type" "addmove")
4621 (set_attr "length" "4,4,4")])
4625 ;;- zero extension instructions
4626 ;; We have define_expand for zero extension patterns to make sure the
4627 ;; operands get loaded into registers. The define_insns accept
4628 ;; memory operands. This gives us better overall code than just
4629 ;; having a pattern that does or does not accept memory operands.
4631 (define_expand "zero_extendqihi2"
4632 [(set (match_operand:HI 0 "register_operand" "")
4634 (match_operand:QI 1 "register_operand" "")))]
4639 [(set (match_operand:HI 0 "register_operand" "=r,r")
4641 (match_operand:QI 1 "move_src_operand" "r,RQ")))]
4642 "GET_CODE (operands[1]) != CONST_INT"
4644 {extru|extrw,u} %1,31,8,%0
4646 [(set_attr "type" "shift,load")
4647 (set_attr "length" "4,4")])
4649 (define_expand "zero_extendqisi2"
4650 [(set (match_operand:SI 0 "register_operand" "")
4652 (match_operand:QI 1 "register_operand" "")))]
4657 [(set (match_operand:SI 0 "register_operand" "=r,r")
4659 (match_operand:QI 1 "move_src_operand" "r,RQ")))]
4660 "GET_CODE (operands[1]) != CONST_INT"
4662 {extru|extrw,u} %1,31,8,%0
4664 [(set_attr "type" "shift,load")
4665 (set_attr "length" "4,4")])
4667 (define_expand "zero_extendhisi2"
4668 [(set (match_operand:SI 0 "register_operand" "")
4670 (match_operand:HI 1 "register_operand" "")))]
4675 [(set (match_operand:SI 0 "register_operand" "=r,r")
4677 (match_operand:HI 1 "move_src_operand" "r,RQ")))]
4678 "GET_CODE (operands[1]) != CONST_INT"
4680 {extru|extrw,u} %1,31,16,%0
4682 [(set_attr "type" "shift,load")
4683 (set_attr "length" "4,4")])
4685 (define_expand "zero_extendqidi2"
4686 [(set (match_operand:DI 0 "register_operand" "")
4688 (match_operand:QI 1 "register_operand" "")))]
4693 [(set (match_operand:DI 0 "register_operand" "=r,r")
4695 (match_operand:QI 1 "move_src_operand" "r,RQ")))]
4696 "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
4700 [(set_attr "type" "shift,load")
4701 (set_attr "length" "4,4")])
4703 (define_expand "zero_extendhidi2"
4704 [(set (match_operand:DI 0 "register_operand" "")
4706 (match_operand:HI 1 "register_operand" "")))]
4711 [(set (match_operand:DI 0 "register_operand" "=r,r")
4713 (match_operand:HI 1 "move_src_operand" "r,RQ")))]
4714 "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
4718 [(set_attr "type" "shift,load")
4719 (set_attr "length" "4,4")])
4721 (define_expand "zero_extendsidi2"
4722 [(set (match_operand:DI 0 "register_operand" "")
4724 (match_operand:SI 1 "register_operand" "")))]
4729 [(set (match_operand:DI 0 "register_operand" "=r,r")
4731 (match_operand:SI 1 "move_src_operand" "r,RQ")))]
4732 "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
4736 [(set_attr "type" "shift,load")
4737 (set_attr "length" "4,4")])
4739 ;;- sign extension instructions
4741 (define_insn "extendhisi2"
4742 [(set (match_operand:SI 0 "register_operand" "=r")
4743 (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
4745 "{extrs|extrw,s} %1,31,16,%0"
4746 [(set_attr "type" "shift")
4747 (set_attr "length" "4")])
4749 (define_insn "extendqihi2"
4750 [(set (match_operand:HI 0 "register_operand" "=r")
4751 (sign_extend:HI (match_operand:QI 1 "register_operand" "r")))]
4753 "{extrs|extrw,s} %1,31,8,%0"
4754 [(set_attr "type" "shift")
4755 (set_attr "length" "4")])
4757 (define_insn "extendqisi2"
4758 [(set (match_operand:SI 0 "register_operand" "=r")
4759 (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
4761 "{extrs|extrw,s} %1,31,8,%0"
4762 [(set_attr "type" "shift")
4763 (set_attr "length" "4")])
4765 (define_insn "extendqidi2"
4766 [(set (match_operand:DI 0 "register_operand" "=r")
4767 (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))]
4769 "extrd,s %1,63,8,%0"
4770 [(set_attr "type" "shift")
4771 (set_attr "length" "4")])
4773 (define_insn "extendhidi2"
4774 [(set (match_operand:DI 0 "register_operand" "=r")
4775 (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))]
4777 "extrd,s %1,63,16,%0"
4778 [(set_attr "type" "shift")
4779 (set_attr "length" "4")])
4781 (define_insn "extendsidi2"
4782 [(set (match_operand:DI 0 "register_operand" "=r")
4783 (sign_extend:DI (match_operand:SI 1 "register_operand" "r")))]
4785 "extrd,s %1,63,32,%0"
4786 [(set_attr "type" "shift")
4787 (set_attr "length" "4")])
4790 ;; Conversions between float and double.
4792 (define_insn "extendsfdf2"
4793 [(set (match_operand:DF 0 "register_operand" "=f")
4795 (match_operand:SF 1 "register_operand" "f")))]
4796 "! TARGET_SOFT_FLOAT"
4797 "{fcnvff|fcnv},sgl,dbl %1,%0"
4798 [(set_attr "type" "fpalu")
4799 (set_attr "length" "4")])
4801 (define_insn "truncdfsf2"
4802 [(set (match_operand:SF 0 "register_operand" "=f")
4804 (match_operand:DF 1 "register_operand" "f")))]
4805 "! TARGET_SOFT_FLOAT"
4806 "{fcnvff|fcnv},dbl,sgl %1,%0"
4807 [(set_attr "type" "fpalu")
4808 (set_attr "length" "4")])
4810 ;; Conversion between fixed point and floating point.
4811 ;; Note that among the fix-to-float insns
4812 ;; the ones that start with SImode come first.
4813 ;; That is so that an operand that is a CONST_INT
4814 ;; (and therefore lacks a specific machine mode).
4815 ;; will be recognized as SImode (which is always valid)
4816 ;; rather than as QImode or HImode.
4818 ;; This pattern forces (set (reg:SF ...) (float:SF (const_int ...)))
4819 ;; to be reloaded by putting the constant into memory.
4820 ;; It must come before the more general floatsisf2 pattern.
4822 [(set (match_operand:SF 0 "register_operand" "=f")
4823 (float:SF (match_operand:SI 1 "const_int_operand" "m")))]
4824 "! TARGET_SOFT_FLOAT"
4825 "fldw%F1 %1,%0\;{fcnvxf,sgl,sgl|fcnv,w,sgl} %0,%0"
4826 [(set_attr "type" "fpalu")
4827 (set_attr "length" "8")])
4829 (define_insn "floatsisf2"
4830 [(set (match_operand:SF 0 "register_operand" "=f")
4831 (float:SF (match_operand:SI 1 "register_operand" "f")))]
4832 "! TARGET_SOFT_FLOAT"
4833 "{fcnvxf,sgl,sgl|fcnv,w,sgl} %1,%0"
4834 [(set_attr "type" "fpalu")
4835 (set_attr "length" "4")])
4837 ;; This pattern forces (set (reg:DF ...) (float:DF (const_int ...)))
4838 ;; to be reloaded by putting the constant into memory.
4839 ;; It must come before the more general floatsidf2 pattern.
4841 [(set (match_operand:DF 0 "register_operand" "=f")
4842 (float:DF (match_operand:SI 1 "const_int_operand" "m")))]
4843 "! TARGET_SOFT_FLOAT"
4844 "fldw%F1 %1,%0\;{fcnvxf,sgl,dbl|fcnv,w,dbl} %0,%0"
4845 [(set_attr "type" "fpalu")
4846 (set_attr "length" "8")])
4848 (define_insn "floatsidf2"
4849 [(set (match_operand:DF 0 "register_operand" "=f")
4850 (float:DF (match_operand:SI 1 "register_operand" "f")))]
4851 "! TARGET_SOFT_FLOAT"
4852 "{fcnvxf,sgl,dbl|fcnv,w,dbl} %1,%0"
4853 [(set_attr "type" "fpalu")
4854 (set_attr "length" "4")])
4856 (define_expand "floatunssisf2"
4857 [(set (subreg:SI (match_dup 2) 4)
4858 (match_operand:SI 1 "register_operand" ""))
4859 (set (subreg:SI (match_dup 2) 0)
4861 (set (match_operand:SF 0 "register_operand" "")
4862 (float:SF (match_dup 2)))]
4863 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4868 emit_insn (gen_floatunssisf2_pa20 (operands[0], operands[1]));
4871 operands[2] = gen_reg_rtx (DImode);
4874 (define_expand "floatunssidf2"
4875 [(set (subreg:SI (match_dup 2) 4)
4876 (match_operand:SI 1 "register_operand" ""))
4877 (set (subreg:SI (match_dup 2) 0)
4879 (set (match_operand:DF 0 "register_operand" "")
4880 (float:DF (match_dup 2)))]
4881 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4886 emit_insn (gen_floatunssidf2_pa20 (operands[0], operands[1]));
4889 operands[2] = gen_reg_rtx (DImode);
4892 (define_insn "floatdisf2"
4893 [(set (match_operand:SF 0 "register_operand" "=f")
4894 (float:SF (match_operand:DI 1 "register_operand" "f")))]
4895 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4896 "{fcnvxf,dbl,sgl|fcnv,dw,sgl} %1,%0"
4897 [(set_attr "type" "fpalu")
4898 (set_attr "length" "4")])
4900 (define_insn "floatdidf2"
4901 [(set (match_operand:DF 0 "register_operand" "=f")
4902 (float:DF (match_operand:DI 1 "register_operand" "f")))]
4903 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4904 "{fcnvxf,dbl,dbl|fcnv,dw,dbl} %1,%0"
4905 [(set_attr "type" "fpalu")
4906 (set_attr "length" "4")])
4908 ;; Convert a float to an actual integer.
4909 ;; Truncation is performed as part of the conversion.
4911 (define_insn "fix_truncsfsi2"
4912 [(set (match_operand:SI 0 "register_operand" "=f")
4913 (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4914 "! TARGET_SOFT_FLOAT"
4915 "{fcnvfxt,sgl,sgl|fcnv,t,sgl,w} %1,%0"
4916 [(set_attr "type" "fpalu")
4917 (set_attr "length" "4")])
4919 (define_insn "fix_truncdfsi2"
4920 [(set (match_operand:SI 0 "register_operand" "=f")
4921 (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
4922 "! TARGET_SOFT_FLOAT"
4923 "{fcnvfxt,dbl,sgl|fcnv,t,dbl,w} %1,%0"
4924 [(set_attr "type" "fpalu")
4925 (set_attr "length" "4")])
4927 (define_insn "fix_truncsfdi2"
4928 [(set (match_operand:DI 0 "register_operand" "=f")
4929 (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4930 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4931 "{fcnvfxt,sgl,dbl|fcnv,t,sgl,dw} %1,%0"
4932 [(set_attr "type" "fpalu")
4933 (set_attr "length" "4")])
4935 (define_insn "fix_truncdfdi2"
4936 [(set (match_operand:DI 0 "register_operand" "=f")
4937 (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
4938 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
4939 "{fcnvfxt,dbl,dbl|fcnv,t,dbl,dw} %1,%0"
4940 [(set_attr "type" "fpalu")
4941 (set_attr "length" "4")])
4943 (define_insn "floatunssidf2_pa20"
4944 [(set (match_operand:DF 0 "register_operand" "=f")
4945 (unsigned_float:DF (match_operand:SI 1 "register_operand" "f")))]
4946 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4948 [(set_attr "type" "fpalu")
4949 (set_attr "length" "4")])
4951 (define_insn "floatunssisf2_pa20"
4952 [(set (match_operand:SF 0 "register_operand" "=f")
4953 (unsigned_float:SF (match_operand:SI 1 "register_operand" "f")))]
4954 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4956 [(set_attr "type" "fpalu")
4957 (set_attr "length" "4")])
4959 (define_insn "floatunsdisf2"
4960 [(set (match_operand:SF 0 "register_operand" "=f")
4961 (unsigned_float:SF (match_operand:DI 1 "register_operand" "f")))]
4962 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4963 "fcnv,udw,sgl %1,%0"
4964 [(set_attr "type" "fpalu")
4965 (set_attr "length" "4")])
4967 (define_insn "floatunsdidf2"
4968 [(set (match_operand:DF 0 "register_operand" "=f")
4969 (unsigned_float:DF (match_operand:DI 1 "register_operand" "f")))]
4970 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4971 "fcnv,udw,dbl %1,%0"
4972 [(set_attr "type" "fpalu")
4973 (set_attr "length" "4")])
4975 (define_insn "fixuns_truncsfsi2"
4976 [(set (match_operand:SI 0 "register_operand" "=f")
4977 (unsigned_fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4978 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4979 "fcnv,t,sgl,uw %1,%0"
4980 [(set_attr "type" "fpalu")
4981 (set_attr "length" "4")])
4983 (define_insn "fixuns_truncdfsi2"
4984 [(set (match_operand:SI 0 "register_operand" "=f")
4985 (unsigned_fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
4986 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4987 "fcnv,t,dbl,uw %1,%0"
4988 [(set_attr "type" "fpalu")
4989 (set_attr "length" "4")])
4991 (define_insn "fixuns_truncsfdi2"
4992 [(set (match_operand:DI 0 "register_operand" "=f")
4993 (unsigned_fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4994 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
4995 "fcnv,t,sgl,udw %1,%0"
4996 [(set_attr "type" "fpalu")
4997 (set_attr "length" "4")])
4999 (define_insn "fixuns_truncdfdi2"
5000 [(set (match_operand:DI 0 "register_operand" "=f")
5001 (unsigned_fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
5002 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5003 "fcnv,t,dbl,udw %1,%0"
5004 [(set_attr "type" "fpalu")
5005 (set_attr "length" "4")])
5007 ;;- arithmetic instructions
5009 (define_expand "adddi3"
5010 [(set (match_operand:DI 0 "register_operand" "")
5011 (plus:DI (match_operand:DI 1 "register_operand" "")
5012 (match_operand:DI 2 "adddi3_operand" "")))]
5017 [(set (match_operand:DI 0 "register_operand" "=r")
5018 (plus:DI (match_operand:DI 1 "register_operand" "%r")
5019 (match_operand:DI 2 "arith11_operand" "rI")))]
5023 if (GET_CODE (operands[2]) == CONST_INT)
5025 if (INTVAL (operands[2]) >= 0)
5026 return \"addi %2,%R1,%R0\;{addc|add,c} %1,%%r0,%0\";
5028 return \"addi %2,%R1,%R0\;{subb|sub,b} %1,%%r0,%0\";
5031 return \"add %R2,%R1,%R0\;{addc|add,c} %2,%1,%0\";
5033 [(set_attr "type" "binary")
5034 (set_attr "length" "8")])
5037 [(set (match_operand:DI 0 "register_operand" "=r,r")
5038 (plus:DI (match_operand:DI 1 "register_operand" "%r,r")
5039 (match_operand:DI 2 "arith14_operand" "r,J")))]
5044 [(set_attr "type" "binary,binary")
5045 (set_attr "pa_combine_type" "addmove")
5046 (set_attr "length" "4,4")])
5049 [(set (match_operand:DI 0 "register_operand" "=r")
5050 (plus:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
5051 (match_operand:DI 2 "register_operand" "r")))]
5054 [(set_attr "type" "binary")
5055 (set_attr "length" "4")])
5058 [(set (match_operand:SI 0 "register_operand" "=r")
5059 (plus:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
5060 (match_operand:SI 2 "register_operand" "r")))]
5063 [(set_attr "type" "binary")
5064 (set_attr "length" "4")])
5066 (define_expand "addvdi3"
5067 [(parallel [(set (match_operand:DI 0 "register_operand" "")
5068 (plus:DI (match_operand:DI 1 "reg_or_0_operand" "")
5069 (match_operand:DI 2 "arith11_operand" "")))
5070 (trap_if (ne (plus:TI (sign_extend:TI (match_dup 1))
5071 (sign_extend:TI (match_dup 2)))
5072 (sign_extend:TI (plus:DI (match_dup 1)
5079 [(set (match_operand:DI 0 "register_operand" "=r,r")
5080 (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rM,rM")
5081 (match_operand:DI 2 "arith11_operand" "r,I")))
5082 (trap_if (ne (plus:TI (sign_extend:TI (match_dup 1))
5083 (sign_extend:TI (match_dup 2)))
5084 (sign_extend:TI (plus:DI (match_dup 1)
5090 addi,tsv,* %2,%1,%0"
5091 [(set_attr "type" "binary,binary")
5092 (set_attr "length" "4,4")])
5095 [(set (match_operand:DI 0 "register_operand" "=r")
5096 (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rM")
5097 (match_operand:DI 2 "arith11_operand" "rI")))
5098 (trap_if (ne (plus:TI (sign_extend:TI (match_dup 1))
5099 (sign_extend:TI (match_dup 2)))
5100 (sign_extend:TI (plus:DI (match_dup 1)
5106 if (GET_CODE (operands[2]) == CONST_INT)
5108 if (INTVAL (operands[2]) >= 0)
5109 return \"addi %2,%R1,%R0\;{addco|add,c,tsv} %1,%%r0,%0\";
5111 return \"addi %2,%R1,%R0\;{subbo|sub,b,tsv} %1,%%r0,%0\";
5114 return \"add %R2,%R1,%R0\;{addco|add,c,tsv} %2,%1,%0\";
5116 [(set_attr "type" "binary")
5117 (set_attr "length" "8")])
5119 ;; define_splits to optimize cases of adding a constant integer
5120 ;; to a register when the constant does not fit in 14 bits. */
5122 [(set (match_operand:SI 0 "register_operand" "")
5123 (plus:SI (match_operand:SI 1 "register_operand" "")
5124 (match_operand:SI 2 "const_int_operand" "")))
5125 (clobber (match_operand:SI 4 "register_operand" ""))]
5126 "! pa_cint_ok_for_move (INTVAL (operands[2]))
5127 && VAL_14_BITS_P (INTVAL (operands[2]) >> 1)"
5128 [(set (match_dup 4) (plus:SI (match_dup 1) (match_dup 2)))
5129 (set (match_dup 0) (plus:SI (match_dup 4) (match_dup 3)))]
5132 int val = INTVAL (operands[2]);
5133 int low = (val < 0) ? -0x2000 : 0x1fff;
5134 int rest = val - low;
5136 operands[2] = GEN_INT (rest);
5137 operands[3] = GEN_INT (low);
5141 [(set (match_operand:SI 0 "register_operand" "")
5142 (plus:SI (match_operand:SI 1 "register_operand" "")
5143 (match_operand:SI 2 "const_int_operand" "")))
5144 (clobber (match_operand:SI 4 "register_operand" ""))]
5145 "! pa_cint_ok_for_move (INTVAL (operands[2]))"
5146 [(set (match_dup 4) (match_dup 2))
5147 (set (match_dup 0) (plus:SI (ashift:SI (match_dup 4) (match_dup 3))
5151 HOST_WIDE_INT intval = INTVAL (operands[2]);
5153 /* Try dividing the constant by 2, then 4, and finally 8 to see
5154 if we can get a constant which can be loaded into a register
5155 in a single instruction (pa_cint_ok_for_move).
5157 If that fails, try to negate the constant and subtract it
5158 from our input operand. */
5159 if (intval % 2 == 0 && pa_cint_ok_for_move (intval / 2))
5161 operands[2] = GEN_INT (intval / 2);
5162 operands[3] = const1_rtx;
5164 else if (intval % 4 == 0 && pa_cint_ok_for_move (intval / 4))
5166 operands[2] = GEN_INT (intval / 4);
5167 operands[3] = const2_rtx;
5169 else if (intval % 8 == 0 && pa_cint_ok_for_move (intval / 8))
5171 operands[2] = GEN_INT (intval / 8);
5172 operands[3] = GEN_INT (3);
5174 else if (pa_cint_ok_for_move (-intval))
5176 emit_insn (gen_rtx_SET (operands[4], GEN_INT (-intval)));
5177 emit_insn (gen_subsi3 (operands[0], operands[1], operands[4]));
5184 (define_insn "addsi3"
5185 [(set (match_operand:SI 0 "register_operand" "=r,r")
5186 (plus:SI (match_operand:SI 1 "register_operand" "%r,r")
5187 (match_operand:SI 2 "arith14_operand" "r,J")))]
5190 {addl|add,l} %1,%2,%0
5192 [(set_attr "type" "binary,binary")
5193 (set_attr "pa_combine_type" "addmove")
5194 (set_attr "length" "4,4")])
5196 (define_insn "addvsi3"
5197 [(set (match_operand:SI 0 "register_operand" "=r,r")
5198 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rM,rM")
5199 (match_operand:SI 2 "arith11_operand" "r,I")))
5200 (trap_if (ne (plus:DI (sign_extend:DI (match_dup 1))
5201 (sign_extend:DI (match_dup 2)))
5202 (sign_extend:DI (plus:SI (match_dup 1)
5207 {addo|add,tsv} %2,%1,%0
5208 {addio|addi,tsv} %2,%1,%0"
5209 [(set_attr "type" "binary,binary")
5210 (set_attr "length" "4,4")])
5212 (define_expand "subdi3"
5213 [(set (match_operand:DI 0 "register_operand" "")
5214 (minus:DI (match_operand:DI 1 "arith11_operand" "")
5215 (match_operand:DI 2 "reg_or_0_operand" "")))]
5220 [(set (match_operand:DI 0 "register_operand" "=r,r,!q")
5221 (minus:DI (match_operand:DI 1 "arith11_operand" "r,I,!U")
5222 (match_operand:DI 2 "reg_or_0_operand" "rM,rM,!rM")))]
5228 [(set_attr "type" "binary,binary,move")
5229 (set_attr "length" "4,4,4")])
5232 [(set (match_operand:DI 0 "register_operand" "=r,&r")
5233 (minus:DI (match_operand:DI 1 "arith11_operand" "r,I")
5234 (match_operand:DI 2 "reg_or_0_operand" "rM,rM")))]
5238 if (GET_CODE (operands[1]) == CONST_INT)
5240 if (INTVAL (operands[1]) >= 0)
5241 return \"subi %1,%R2,%R0\;{subb|sub,b} %%r0,%2,%0\";
5243 return \"ldi -1,%0\;subi %1,%R2,%R0\;{subb|sub,b} %0,%2,%0\";
5246 return \"sub %R1,%R2,%R0\;{subb|sub,b} %1,%2,%0\";
5248 [(set_attr "type" "binary")
5249 (set (attr "length")
5250 (if_then_else (eq_attr "alternative" "0")
5252 (if_then_else (ge (symbol_ref "INTVAL (operands[1])")
5257 (define_expand "subvdi3"
5258 [(parallel [(set (match_operand:DI 0 "register_operand" "")
5259 (minus:DI (match_operand:DI 1 "arith11_operand" "")
5260 (match_operand:DI 2 "reg_or_0_operand" "")))
5261 (trap_if (ne (minus:TI (sign_extend:TI (match_dup 1))
5262 (sign_extend:TI (match_dup 2)))
5263 (sign_extend:TI (minus:DI (match_dup 1)
5270 [(set (match_operand:DI 0 "register_operand" "=r,r")
5271 (minus:DI (match_operand:DI 1 "arith11_operand" "r,I")
5272 (match_operand:DI 2 "reg_or_0_operand" "rM,rM")))
5273 (trap_if (ne (minus:TI (sign_extend:TI (match_dup 1))
5274 (sign_extend:TI (match_dup 2)))
5275 (sign_extend:TI (minus:DI (match_dup 1)
5280 {subo|sub,tsv} %1,%2,%0
5281 {subio|subi,tsv} %1,%2,%0"
5282 [(set_attr "type" "binary,binary")
5283 (set_attr "length" "4,4")])
5286 [(set (match_operand:DI 0 "register_operand" "=r,&r")
5287 (minus:DI (match_operand:DI 1 "arith11_operand" "r,I")
5288 (match_operand:DI 2 "reg_or_0_operand" "rM,rM")))
5289 (trap_if (ne (minus:TI (sign_extend:TI (match_dup 1))
5290 (sign_extend:TI (match_dup 2)))
5291 (sign_extend:TI (minus:DI (match_dup 1)
5297 if (GET_CODE (operands[1]) == CONST_INT)
5299 if (INTVAL (operands[1]) >= 0)
5300 return \"subi %1,%R2,%R0\;{subbo|sub,b,tsv} %%r0,%2,%0\";
5302 return \"ldi -1,%0\;subi %1,%R2,%R0\;{subbo|sub,b,tsv} %0,%2,%0\";
5305 return \"sub %R1,%R2,%R0\;{subbo|sub,b,tsv} %1,%2,%0\";
5307 [(set_attr "type" "binary,binary")
5308 (set (attr "length")
5309 (if_then_else (eq_attr "alternative" "0")
5311 (if_then_else (ge (symbol_ref "INTVAL (operands[1])")
5316 (define_expand "subsi3"
5317 [(set (match_operand:SI 0 "register_operand" "")
5318 (minus:SI (match_operand:SI 1 "arith11_operand" "")
5319 (match_operand:SI 2 "register_operand" "")))]
5324 [(set (match_operand:SI 0 "register_operand" "=r,r")
5325 (minus:SI (match_operand:SI 1 "arith11_operand" "r,I")
5326 (match_operand:SI 2 "register_operand" "r,r")))]
5331 [(set_attr "type" "binary,binary")
5332 (set_attr "length" "4,4")])
5335 [(set (match_operand:SI 0 "register_operand" "=r,r,!q")
5336 (minus:SI (match_operand:SI 1 "arith11_operand" "r,I,!S")
5337 (match_operand:SI 2 "register_operand" "r,r,!r")))]
5343 [(set_attr "type" "binary,binary,move")
5344 (set_attr "length" "4,4,4")])
5346 (define_insn "subvsi3"
5347 [(set (match_operand:SI 0 "register_operand" "=r,r")
5348 (minus:SI (match_operand:SI 1 "arith11_operand" "rM,I")
5349 (match_operand:SI 2 "reg_or_0_operand" "rM,rM")))
5350 (trap_if (ne (minus:DI (sign_extend:DI (match_dup 1))
5351 (sign_extend:DI (match_dup 2)))
5352 (sign_extend:DI (minus:SI (match_dup 1)
5357 {subo|sub,tsv} %1,%2,%0
5358 {subio|subi,tsv} %1,%2,%0"
5359 [(set_attr "type" "binary,binary")
5360 (set_attr "length" "4,4")])
5362 ;; Trap instructions.
5365 [(trap_if (const_int 1) (const_int 0))]
5367 "{addit|addi,tc},<> 1,%%r0,%%r0"
5368 [(set_attr "type" "trap")
5369 (set_attr "length" "4")])
5371 ;; Clobbering a "register_operand" instead of a match_scratch
5372 ;; in operand3 of millicode calls avoids spilling %r1 and
5373 ;; produces better code.
5375 ;; The mulsi3 insns set up registers for the millicode call.
5376 (define_expand "mulsi3"
5377 [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5378 (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5379 (parallel [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5380 (clobber (match_dup 3))
5381 (clobber (reg:SI 26))
5382 (clobber (reg:SI 25))
5383 (clobber (match_dup 4))])
5384 (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5388 operands[4] = gen_rtx_REG (SImode, TARGET_64BIT ? 2 : 31);
5389 if (TARGET_PA_11 && !TARGET_DISABLE_FPREGS && !TARGET_SOFT_FLOAT)
5391 rtx scratch = gen_reg_rtx (DImode);
5392 operands[1] = force_reg (SImode, operands[1]);
5393 operands[2] = force_reg (SImode, operands[2]);
5394 emit_insn (gen_umulsidi3 (scratch, operands[1], operands[2]));
5395 emit_insn (gen_movsi (operands[0],
5396 gen_rtx_SUBREG (SImode, scratch,
5397 GET_MODE_SIZE (SImode))));
5400 operands[3] = gen_reg_rtx (SImode);
5403 (define_insn "umulsidi3"
5404 [(set (match_operand:DI 0 "register_operand" "=f")
5405 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5406 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "f"))))]
5407 "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
5409 [(set_attr "type" "fpmuldbl")
5410 (set_attr "length" "4")])
5413 [(set (match_operand:DI 0 "register_operand" "=f")
5414 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5415 (match_operand:DI 2 "uint32_operand" "f")))]
5416 "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && !TARGET_64BIT"
5418 [(set_attr "type" "fpmuldbl")
5419 (set_attr "length" "4")])
5422 [(set (match_operand:DI 0 "register_operand" "=f")
5423 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5424 (match_operand:DI 2 "uint32_operand" "f")))]
5425 "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && TARGET_64BIT"
5427 [(set_attr "type" "fpmuldbl")
5428 (set_attr "length" "4")])
5431 [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5432 (clobber (match_operand:SI 0 "register_operand" "=a"))
5433 (clobber (reg:SI 26))
5434 (clobber (reg:SI 25))
5435 (clobber (reg:SI 31))]
5437 "* return pa_output_mul_insn (0, insn);"
5438 [(set_attr "type" "milli")
5439 (set (attr "length")
5440 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5441 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5444 [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5445 (clobber (match_operand:SI 0 "register_operand" "=a"))
5446 (clobber (reg:SI 26))
5447 (clobber (reg:SI 25))
5448 (clobber (reg:SI 2))]
5450 "* return pa_output_mul_insn (0, insn);"
5451 [(set_attr "type" "milli")
5452 (set (attr "length")
5453 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5454 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5456 (define_expand "muldi3"
5457 [(set (match_operand:DI 0 "register_operand" "")
5458 (mult:DI (match_operand:DI 1 "register_operand" "")
5459 (match_operand:DI 2 "register_operand" "")))]
5460 "TARGET_64BIT && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
5463 rtx low_product = gen_reg_rtx (DImode);
5464 rtx cross_product1 = gen_reg_rtx (DImode);
5465 rtx cross_product2 = gen_reg_rtx (DImode);
5466 rtx cross_scratch = gen_reg_rtx (DImode);
5467 rtx cross_product = gen_reg_rtx (DImode);
5468 rtx op1l, op1r, op2l, op2r;
5469 rtx op1shifted, op2shifted;
5471 op1shifted = gen_reg_rtx (DImode);
5472 op2shifted = gen_reg_rtx (DImode);
5473 op1l = gen_reg_rtx (SImode);
5474 op1r = gen_reg_rtx (SImode);
5475 op2l = gen_reg_rtx (SImode);
5476 op2r = gen_reg_rtx (SImode);
5478 emit_move_insn (op1shifted, gen_rtx_LSHIFTRT (DImode, operands[1],
5480 emit_move_insn (op2shifted, gen_rtx_LSHIFTRT (DImode, operands[2],
5482 op1r = force_reg (SImode, gen_rtx_SUBREG (SImode, operands[1], 4));
5483 op2r = force_reg (SImode, gen_rtx_SUBREG (SImode, operands[2], 4));
5484 op1l = force_reg (SImode, gen_rtx_SUBREG (SImode, op1shifted, 4));
5485 op2l = force_reg (SImode, gen_rtx_SUBREG (SImode, op2shifted, 4));
5487 /* Emit multiplies for the cross products. */
5488 emit_insn (gen_umulsidi3 (cross_product1, op2r, op1l));
5489 emit_insn (gen_umulsidi3 (cross_product2, op2l, op1r));
5491 /* Emit a multiply for the low sub-word. */
5492 emit_insn (gen_umulsidi3 (low_product, copy_rtx (op2r), copy_rtx (op1r)));
5494 /* Sum the cross products and shift them into proper position. */
5495 emit_insn (gen_adddi3 (cross_scratch, cross_product1, cross_product2));
5496 emit_insn (gen_ashldi3 (cross_product, cross_scratch, GEN_INT (32)));
5498 /* Add the cross product to the low product and store the result
5499 into the output operand . */
5500 emit_insn (gen_adddi3 (operands[0], cross_product, low_product));
5504 ;;; Division and mod.
5505 (define_expand "divsi3"
5506 [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5507 (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5508 (parallel [(set (reg:SI 29) (div:SI (reg:SI 26) (reg:SI 25)))
5509 (clobber (match_dup 3))
5510 (clobber (match_dup 4))
5511 (clobber (reg:SI 26))
5512 (clobber (reg:SI 25))
5513 (clobber (match_dup 5))])
5514 (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5518 operands[3] = gen_reg_rtx (SImode);
5521 operands[5] = gen_rtx_REG (SImode, 2);
5522 operands[4] = operands[5];
5526 operands[5] = gen_rtx_REG (SImode, 31);
5527 operands[4] = gen_reg_rtx (SImode);
5529 if (GET_CODE (operands[2]) == CONST_INT && pa_emit_hpdiv_const (operands, 0))
5535 (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5536 (clobber (match_operand:SI 1 "register_operand" "=a"))
5537 (clobber (match_operand:SI 2 "register_operand" "=&r"))
5538 (clobber (reg:SI 26))
5539 (clobber (reg:SI 25))
5540 (clobber (reg:SI 31))]
5543 return pa_output_div_insn (operands, 0, insn);"
5544 [(set_attr "type" "milli")
5545 (set (attr "length")
5546 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5547 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5551 (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5552 (clobber (match_operand:SI 1 "register_operand" "=a"))
5553 (clobber (match_operand:SI 2 "register_operand" "=&r"))
5554 (clobber (reg:SI 26))
5555 (clobber (reg:SI 25))
5556 (clobber (reg:SI 2))]
5559 return pa_output_div_insn (operands, 0, insn);"
5560 [(set_attr "type" "milli")
5561 (set (attr "length")
5562 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5563 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5565 (define_expand "udivsi3"
5566 [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5567 (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5568 (parallel [(set (reg:SI 29) (udiv:SI (reg:SI 26) (reg:SI 25)))
5569 (clobber (match_dup 3))
5570 (clobber (match_dup 4))
5571 (clobber (reg:SI 26))
5572 (clobber (reg:SI 25))
5573 (clobber (match_dup 5))])
5574 (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5578 operands[3] = gen_reg_rtx (SImode);
5582 operands[5] = gen_rtx_REG (SImode, 2);
5583 operands[4] = operands[5];
5587 operands[5] = gen_rtx_REG (SImode, 31);
5588 operands[4] = gen_reg_rtx (SImode);
5590 if (GET_CODE (operands[2]) == CONST_INT && pa_emit_hpdiv_const (operands, 1))
5596 (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5597 (clobber (match_operand:SI 1 "register_operand" "=a"))
5598 (clobber (match_operand:SI 2 "register_operand" "=&r"))
5599 (clobber (reg:SI 26))
5600 (clobber (reg:SI 25))
5601 (clobber (reg:SI 31))]
5604 return pa_output_div_insn (operands, 1, insn);"
5605 [(set_attr "type" "milli")
5606 (set (attr "length")
5607 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5608 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5612 (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5613 (clobber (match_operand:SI 1 "register_operand" "=a"))
5614 (clobber (match_operand:SI 2 "register_operand" "=&r"))
5615 (clobber (reg:SI 26))
5616 (clobber (reg:SI 25))
5617 (clobber (reg:SI 2))]
5620 return pa_output_div_insn (operands, 1, insn);"
5621 [(set_attr "type" "milli")
5622 (set (attr "length")
5623 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5624 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5626 (define_expand "modsi3"
5627 [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5628 (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5629 (parallel [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5630 (clobber (match_dup 3))
5631 (clobber (match_dup 4))
5632 (clobber (reg:SI 26))
5633 (clobber (reg:SI 25))
5634 (clobber (match_dup 5))])
5635 (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5641 operands[5] = gen_rtx_REG (SImode, 2);
5642 operands[4] = operands[5];
5646 operands[5] = gen_rtx_REG (SImode, 31);
5647 operands[4] = gen_reg_rtx (SImode);
5649 operands[3] = gen_reg_rtx (SImode);
5653 [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5654 (clobber (match_operand:SI 0 "register_operand" "=a"))
5655 (clobber (match_operand:SI 1 "register_operand" "=&r"))
5656 (clobber (reg:SI 26))
5657 (clobber (reg:SI 25))
5658 (clobber (reg:SI 31))]
5661 return pa_output_mod_insn (0, insn);"
5662 [(set_attr "type" "milli")
5663 (set (attr "length")
5664 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5665 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5668 [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5669 (clobber (match_operand:SI 0 "register_operand" "=a"))
5670 (clobber (match_operand:SI 1 "register_operand" "=&r"))
5671 (clobber (reg:SI 26))
5672 (clobber (reg:SI 25))
5673 (clobber (reg:SI 2))]
5676 return pa_output_mod_insn (0, insn);"
5677 [(set_attr "type" "milli")
5678 (set (attr "length")
5679 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5680 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5682 (define_expand "umodsi3"
5683 [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5684 (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5685 (parallel [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5686 (clobber (match_dup 3))
5687 (clobber (match_dup 4))
5688 (clobber (reg:SI 26))
5689 (clobber (reg:SI 25))
5690 (clobber (match_dup 5))])
5691 (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5697 operands[5] = gen_rtx_REG (SImode, 2);
5698 operands[4] = operands[5];
5702 operands[5] = gen_rtx_REG (SImode, 31);
5703 operands[4] = gen_reg_rtx (SImode);
5705 operands[3] = gen_reg_rtx (SImode);
5709 [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5710 (clobber (match_operand:SI 0 "register_operand" "=a"))
5711 (clobber (match_operand:SI 1 "register_operand" "=&r"))
5712 (clobber (reg:SI 26))
5713 (clobber (reg:SI 25))
5714 (clobber (reg:SI 31))]
5717 return pa_output_mod_insn (1, insn);"
5718 [(set_attr "type" "milli")
5719 (set (attr "length")
5720 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5721 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5724 [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5725 (clobber (match_operand:SI 0 "register_operand" "=a"))
5726 (clobber (match_operand:SI 1 "register_operand" "=&r"))
5727 (clobber (reg:SI 26))
5728 (clobber (reg:SI 25))
5729 (clobber (reg:SI 2))]
5732 return pa_output_mod_insn (1, insn);"
5733 [(set_attr "type" "milli")
5734 (set (attr "length")
5735 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
5736 (symbol_ref "pa_attr_length_millicode_call (insn)")))])
5738 ;;- and instructions
5739 ;; We define DImode `and` so with DImode `not` we can get
5740 ;; DImode `andn`. Other combinations are possible.
5742 (define_expand "anddi3"
5743 [(set (match_operand:DI 0 "register_operand" "")
5744 (and:DI (match_operand:DI 1 "register_operand" "")
5745 (match_operand:DI 2 "and_operand" "")))]
5750 [(set (match_operand:DI 0 "register_operand" "=r,r")
5751 (and:DI (match_operand:DI 1 "register_operand" "%?r,0")
5752 (match_operand:DI 2 "and_operand" "rO,P")))]
5754 "* return pa_output_64bit_and (operands); "
5755 [(set_attr "type" "binary")
5756 (set_attr "length" "4")])
5758 ; The ? for op1 makes reload prefer zdepi instead of loading a huge
5759 ; constant with ldil;ldo.
5760 (define_insn "andsi3"
5761 [(set (match_operand:SI 0 "register_operand" "=r,r")
5762 (and:SI (match_operand:SI 1 "register_operand" "%?r,0")
5763 (match_operand:SI 2 "and_operand" "rO,P")))]
5765 "* return pa_output_and (operands); "
5766 [(set_attr "type" "binary,shift")
5767 (set_attr "length" "4,4")])
5770 [(set (match_operand:DI 0 "register_operand" "=r")
5771 (and:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
5772 (match_operand:DI 2 "register_operand" "r")))]
5775 [(set_attr "type" "binary")
5776 (set_attr "length" "4")])
5779 [(set (match_operand:SI 0 "register_operand" "=r")
5780 (and:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
5781 (match_operand:SI 2 "register_operand" "r")))]
5784 [(set_attr "type" "binary")
5785 (set_attr "length" "4")])
5787 (define_expand "iordi3"
5788 [(set (match_operand:DI 0 "register_operand" "")
5789 (ior:DI (match_operand:DI 1 "register_operand" "")
5790 (match_operand:DI 2 "reg_or_cint_ior_operand" "")))]
5795 [(set (match_operand:DI 0 "register_operand" "=r,r")
5796 (ior:DI (match_operand:DI 1 "register_operand" "0,0")
5797 (match_operand:DI 2 "cint_ior_operand" "M,i")))]
5799 "* return pa_output_64bit_ior (operands); "
5800 [(set_attr "type" "binary,shift")
5801 (set_attr "length" "4,4")])
5804 [(set (match_operand:DI 0 "register_operand" "=r")
5805 (ior:DI (match_operand:DI 1 "register_operand" "%r")
5806 (match_operand:DI 2 "register_operand" "r")))]
5809 [(set_attr "type" "binary")
5810 (set_attr "length" "4")])
5812 ;; Need a define_expand because we've run out of CONST_OK... characters.
5813 (define_expand "iorsi3"
5814 [(set (match_operand:SI 0 "register_operand" "")
5815 (ior:SI (match_operand:SI 1 "register_operand" "")
5816 (match_operand:SI 2 "reg_or_cint_ior_operand" "")))]
5821 [(set (match_operand:SI 0 "register_operand" "=r,r")
5822 (ior:SI (match_operand:SI 1 "register_operand" "0,0")
5823 (match_operand:SI 2 "cint_ior_operand" "M,i")))]
5825 "* return pa_output_ior (operands); "
5826 [(set_attr "type" "binary,shift")
5827 (set_attr "length" "4,4")])
5830 [(set (match_operand:SI 0 "register_operand" "=r")
5831 (ior:SI (match_operand:SI 1 "register_operand" "%r")
5832 (match_operand:SI 2 "register_operand" "r")))]
5835 [(set_attr "type" "binary")
5836 (set_attr "length" "4")])
5838 (define_expand "xordi3"
5839 [(set (match_operand:DI 0 "register_operand" "")
5840 (xor:DI (match_operand:DI 1 "register_operand" "")
5841 (match_operand:DI 2 "register_operand" "")))]
5846 [(set (match_operand:DI 0 "register_operand" "=r")
5847 (xor:DI (match_operand:DI 1 "register_operand" "%r")
5848 (match_operand:DI 2 "register_operand" "r")))]
5851 [(set_attr "type" "binary")
5852 (set_attr "length" "4")])
5854 (define_insn "xorsi3"
5855 [(set (match_operand:SI 0 "register_operand" "=r")
5856 (xor:SI (match_operand:SI 1 "register_operand" "%r")
5857 (match_operand:SI 2 "register_operand" "r")))]
5860 [(set_attr "type" "binary")
5861 (set_attr "length" "4")])
5863 (define_expand "negdi2"
5864 [(set (match_operand:DI 0 "register_operand" "")
5865 (neg:DI (match_operand:DI 1 "register_operand" "")))]
5870 [(set (match_operand:DI 0 "register_operand" "=r")
5871 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
5873 "sub %%r0,%R1,%R0\;{subb|sub,b} %%r0,%1,%0"
5874 [(set_attr "type" "unary")
5875 (set_attr "length" "8")])
5878 [(set (match_operand:DI 0 "register_operand" "=r")
5879 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
5882 [(set_attr "type" "unary")
5883 (set_attr "length" "4")])
5885 (define_expand "negvdi2"
5886 [(parallel [(set (match_operand:DI 0 "register_operand" "")
5887 (neg:DI (match_operand:DI 1 "register_operand" "")))
5888 (trap_if (ne (neg:TI (sign_extend:TI (match_dup 1)))
5889 (sign_extend:TI (neg:DI (match_dup 1))))
5895 [(set (match_operand:DI 0 "register_operand" "=r")
5896 (neg:DI (match_operand:DI 1 "register_operand" "r")))
5897 (trap_if (ne (neg:TI (sign_extend:TI (match_dup 1)))
5898 (sign_extend:TI (neg:DI (match_dup 1))))
5901 "sub %%r0,%R1,%R0\;{subbo|sub,b,tsv} %%r0,%1,%0"
5902 [(set_attr "type" "unary")
5903 (set_attr "length" "8")])
5906 [(set (match_operand:DI 0 "register_operand" "=r")
5907 (neg:DI (match_operand:DI 1 "register_operand" "r")))
5908 (trap_if (ne (neg:TI (sign_extend:TI (match_dup 1)))
5909 (sign_extend:TI (neg:DI (match_dup 1))))
5912 "sub,tsv %%r0,%1,%0"
5913 [(set_attr "type" "unary")
5914 (set_attr "length" "4")])
5916 (define_insn "negsi2"
5917 [(set (match_operand:SI 0 "register_operand" "=r")
5918 (neg:SI (match_operand:SI 1 "register_operand" "r")))]
5921 [(set_attr "type" "unary")
5922 (set_attr "length" "4")])
5924 (define_insn "negvsi2"
5925 [(set (match_operand:SI 0 "register_operand" "=r")
5926 (neg:SI (match_operand:SI 1 "register_operand" "r")))
5927 (trap_if (ne (neg:DI (sign_extend:DI (match_dup 1)))
5928 (sign_extend:DI (neg:SI (match_dup 1))))
5931 "{subo|sub,tsv} %%r0,%1,%0"
5932 [(set_attr "type" "unary")
5933 (set_attr "length" "4")])
5935 (define_expand "one_cmpldi2"
5936 [(set (match_operand:DI 0 "register_operand" "")
5937 (not:DI (match_operand:DI 1 "register_operand" "")))]
5944 [(set (match_operand:DI 0 "register_operand" "=r")
5945 (not:DI (match_operand:DI 1 "register_operand" "r")))]
5947 "uaddcm %%r0,%1,%0\;uaddcm %%r0,%R1,%R0"
5948 [(set_attr "type" "unary")
5949 (set_attr "length" "8")])
5952 [(set (match_operand:DI 0 "register_operand" "=r")
5953 (not:DI (match_operand:DI 1 "register_operand" "r")))]
5956 [(set_attr "type" "unary")
5957 (set_attr "length" "4")])
5959 (define_insn "one_cmplsi2"
5960 [(set (match_operand:SI 0 "register_operand" "=r")
5961 (not:SI (match_operand:SI 1 "register_operand" "r")))]
5964 [(set_attr "type" "unary")
5965 (set_attr "length" "4")])
5967 ;; Floating point arithmetic instructions.
5969 (define_insn "adddf3"
5970 [(set (match_operand:DF 0 "register_operand" "=f")
5971 (plus:DF (match_operand:DF 1 "register_operand" "f")
5972 (match_operand:DF 2 "register_operand" "f")))]
5973 "! TARGET_SOFT_FLOAT"
5975 [(set_attr "type" "fpalu")
5976 (set_attr "pa_combine_type" "faddsub")
5977 (set_attr "length" "4")])
5979 (define_insn "addsf3"
5980 [(set (match_operand:SF 0 "register_operand" "=f")
5981 (plus:SF (match_operand:SF 1 "register_operand" "f")
5982 (match_operand:SF 2 "register_operand" "f")))]
5983 "! TARGET_SOFT_FLOAT"
5985 [(set_attr "type" "fpalu")
5986 (set_attr "pa_combine_type" "faddsub")
5987 (set_attr "length" "4")])
5989 (define_insn "subdf3"
5990 [(set (match_operand:DF 0 "register_operand" "=f")
5991 (minus:DF (match_operand:DF 1 "register_operand" "f")
5992 (match_operand:DF 2 "register_operand" "f")))]
5993 "! TARGET_SOFT_FLOAT"
5995 [(set_attr "type" "fpalu")
5996 (set_attr "pa_combine_type" "faddsub")
5997 (set_attr "length" "4")])
5999 (define_insn "subsf3"
6000 [(set (match_operand:SF 0 "register_operand" "=f")
6001 (minus:SF (match_operand:SF 1 "register_operand" "f")
6002 (match_operand:SF 2 "register_operand" "f")))]
6003 "! TARGET_SOFT_FLOAT"
6005 [(set_attr "type" "fpalu")
6006 (set_attr "pa_combine_type" "faddsub")
6007 (set_attr "length" "4")])
6009 (define_insn "muldf3"
6010 [(set (match_operand:DF 0 "register_operand" "=f")
6011 (mult:DF (match_operand:DF 1 "register_operand" "f")
6012 (match_operand:DF 2 "register_operand" "f")))]
6013 "! TARGET_SOFT_FLOAT"
6015 [(set_attr "type" "fpmuldbl")
6016 (set_attr "pa_combine_type" "fmpy")
6017 (set_attr "length" "4")])
6019 (define_insn "mulsf3"
6020 [(set (match_operand:SF 0 "register_operand" "=f")
6021 (mult:SF (match_operand:SF 1 "register_operand" "f")
6022 (match_operand:SF 2 "register_operand" "f")))]
6023 "! TARGET_SOFT_FLOAT"
6025 [(set_attr "type" "fpmulsgl")
6026 (set_attr "pa_combine_type" "fmpy")
6027 (set_attr "length" "4")])
6029 (define_insn "divdf3"
6030 [(set (match_operand:DF 0 "register_operand" "=f")
6031 (div:DF (match_operand:DF 1 "register_operand" "f")
6032 (match_operand:DF 2 "register_operand" "f")))]
6033 "! TARGET_SOFT_FLOAT"
6035 [(set_attr "type" "fpdivdbl")
6036 (set_attr "length" "4")])
6038 (define_insn "divsf3"
6039 [(set (match_operand:SF 0 "register_operand" "=f")
6040 (div:SF (match_operand:SF 1 "register_operand" "f")
6041 (match_operand:SF 2 "register_operand" "f")))]
6042 "! TARGET_SOFT_FLOAT"
6044 [(set_attr "type" "fpdivsgl")
6045 (set_attr "length" "4")])
6047 ;; Processors prior to PA 2.0 don't have a fneg instruction. Fast
6048 ;; negation can be done by subtracting from plus zero. However, this
6049 ;; violates the IEEE standard when negating plus and minus zero.
6050 ;; The slow path toggles the sign bit in the general registers.
6051 (define_expand "negdf2"
6052 [(set (match_operand:DF 0 "register_operand" "")
6053 (neg:DF (match_operand:DF 1 "register_operand" "")))]
6054 "!TARGET_SOFT_FLOAT"
6056 if (TARGET_PA_20 || !flag_signed_zeros)
6057 emit_insn (gen_negdf2_fast (operands[0], operands[1]));
6059 emit_insn (gen_negdf2_slow (operands[0], operands[1]));
6063 (define_insn "negdf2_slow"
6064 [(set (match_operand:DF 0 "register_operand" "=r")
6065 (neg:DF (match_operand:DF 1 "register_operand" "r")))]
6066 "!TARGET_SOFT_FLOAT && !TARGET_PA_20"
6069 if (rtx_equal_p (operands[0], operands[1]))
6070 return \"and,< %1,%1,%0\;depi,tr 1,0,1,%0\;depi 0,0,1,%0\";
6072 return \"and,< %1,%1,%0\;depi,tr 1,0,1,%0\;depi 0,0,1,%0\;copy %R1,%R0\";
6074 [(set_attr "type" "multi")
6075 (set (attr "length")
6076 (if_then_else (match_test "rtx_equal_p (operands[0], operands[1])")
6080 (define_insn "negdf2_fast"
6081 [(set (match_operand:DF 0 "register_operand" "=f")
6082 (neg:DF (match_operand:DF 1 "register_operand" "f")))]
6083 "!TARGET_SOFT_FLOAT"
6087 return \"fneg,dbl %1,%0\";
6089 return \"fsub,dbl %%fr0,%1,%0\";
6091 [(set_attr "type" "fpalu")
6092 (set_attr "length" "4")])
6094 (define_expand "negsf2"
6095 [(set (match_operand:SF 0 "register_operand" "")
6096 (neg:SF (match_operand:SF 1 "register_operand" "")))]
6097 "!TARGET_SOFT_FLOAT"
6099 if (TARGET_PA_20 || !flag_signed_zeros)
6100 emit_insn (gen_negsf2_fast (operands[0], operands[1]));
6102 emit_insn (gen_negsf2_slow (operands[0], operands[1]));
6106 (define_insn "negsf2_slow"
6107 [(set (match_operand:SF 0 "register_operand" "=r")
6108 (neg:SF (match_operand:SF 1 "register_operand" "r")))]
6109 "!TARGET_SOFT_FLOAT && !TARGET_PA_20"
6110 "and,< %1,%1,%0\;depi,tr 1,0,1,%0\;depi 0,0,1,%0"
6111 [(set_attr "type" "multi")
6112 (set_attr "length" "12")])
6114 (define_insn "negsf2_fast"
6115 [(set (match_operand:SF 0 "register_operand" "=f")
6116 (neg:SF (match_operand:SF 1 "register_operand" "f")))]
6117 "!TARGET_SOFT_FLOAT"
6121 return \"fneg,sgl %1,%0\";
6123 return \"fsub,sgl %%fr0,%1,%0\";
6125 [(set_attr "type" "fpalu")
6126 (set_attr "length" "4")])
6128 (define_insn "absdf2"
6129 [(set (match_operand:DF 0 "register_operand" "=f")
6130 (abs:DF (match_operand:DF 1 "register_operand" "f")))]
6131 "! TARGET_SOFT_FLOAT"
6133 [(set_attr "type" "fpalu")
6134 (set_attr "length" "4")])
6136 (define_insn "abssf2"
6137 [(set (match_operand:SF 0 "register_operand" "=f")
6138 (abs:SF (match_operand:SF 1 "register_operand" "f")))]
6139 "! TARGET_SOFT_FLOAT"
6141 [(set_attr "type" "fpalu")
6142 (set_attr "length" "4")])
6144 (define_insn "sqrtdf2"
6145 [(set (match_operand:DF 0 "register_operand" "=f")
6146 (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
6147 "! TARGET_SOFT_FLOAT"
6149 [(set_attr "type" "fpsqrtdbl")
6150 (set_attr "length" "4")])
6152 (define_insn "sqrtsf2"
6153 [(set (match_operand:SF 0 "register_operand" "=f")
6154 (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
6155 "! TARGET_SOFT_FLOAT"
6157 [(set_attr "type" "fpsqrtsgl")
6158 (set_attr "length" "4")])
6160 ;; PA 2.0 floating point instructions
6163 (define_insn "fmadf4"
6164 [(set (match_operand:DF 0 "register_operand" "=f")
6165 (fma:DF (match_operand:DF 1 "register_operand" "f")
6166 (match_operand:DF 2 "register_operand" "f")
6167 (match_operand:DF 3 "register_operand" "f")))]
6168 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6169 "fmpyfadd,dbl %1,%2,%3,%0"
6170 [(set_attr "type" "fpmuldbl")
6171 (set_attr "length" "4")])
6173 (define_insn "fmasf4"
6174 [(set (match_operand:SF 0 "register_operand" "=f")
6175 (fma:SF (match_operand:SF 1 "register_operand" "f")
6176 (match_operand:SF 2 "register_operand" "f")
6177 (match_operand:SF 3 "register_operand" "f")))]
6178 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6179 "fmpyfadd,sgl %1,%2,%3,%0"
6180 [(set_attr "type" "fpmulsgl")
6181 (set_attr "length" "4")])
6183 ; fmpynfadd patterns
6184 (define_insn "fnmadf4"
6185 [(set (match_operand:DF 0 "register_operand" "=f")
6186 (fma:DF (neg:DF (match_operand:DF 1 "register_operand" "f"))
6187 (match_operand:DF 2 "register_operand" "f")
6188 (match_operand:DF 3 "register_operand" "f")))]
6189 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6190 "fmpynfadd,dbl %1,%2,%3,%0"
6191 [(set_attr "type" "fpmuldbl")
6192 (set_attr "length" "4")])
6194 (define_insn "fnmasf4"
6195 [(set (match_operand:SF 0 "register_operand" "=f")
6196 (fma:SF (neg:SF (match_operand:SF 1 "register_operand" "f"))
6197 (match_operand:SF 2 "register_operand" "f")
6198 (match_operand:SF 3 "register_operand" "f")))]
6199 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6200 "fmpynfadd,sgl %1,%2,%3,%0"
6201 [(set_attr "type" "fpmulsgl")
6202 (set_attr "length" "4")])
6206 [(set (match_operand:DF 0 "register_operand" "=f")
6207 (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))]
6208 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6210 [(set_attr "type" "fpalu")
6211 (set_attr "length" "4")])
6214 [(set (match_operand:SF 0 "register_operand" "=f")
6215 (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))]
6216 "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6218 [(set_attr "type" "fpalu")
6219 (set_attr "length" "4")])
6222 [(set (match_operand:DF 0 "register_operand" "=f")
6223 (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))
6224 (set (match_operand:DF 2 "register_operand" "=&f") (abs:DF (match_dup 1)))]
6225 "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6226 && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
6228 [(set_attr "type" "fpalu")
6229 (set_attr "length" "8")])
6232 [(set (match_operand:DF 0 "register_operand" "")
6233 (neg:DF (abs:DF (match_operand:DF 1 "register_operand" ""))))
6234 (set (match_operand:DF 2 "register_operand" "") (abs:DF (match_dup 1)))]
6235 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6236 [(set (match_dup 2) (abs:DF (match_dup 1)))
6237 (set (match_dup 0) (neg:DF (abs:DF (match_dup 1))))]
6241 [(set (match_operand:SF 0 "register_operand" "=f")
6242 (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))
6243 (set (match_operand:SF 2 "register_operand" "=&f") (abs:SF (match_dup 1)))]
6244 "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6245 && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
6247 [(set_attr "type" "fpalu")
6248 (set_attr "length" "8")])
6251 [(set (match_operand:SF 0 "register_operand" "")
6252 (neg:SF (abs:SF (match_operand:SF 1 "register_operand" ""))))
6253 (set (match_operand:SF 2 "register_operand" "") (abs:SF (match_dup 1)))]
6254 "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6255 [(set (match_dup 2) (abs:SF (match_dup 1)))
6256 (set (match_dup 0) (neg:SF (abs:SF (match_dup 1))))]
6259 ;; Negating a multiply can be faked by adding zero in a fused multiply-add
6260 ;; instruction if we can ignore the sign of zero.
6262 [(set (match_operand:DF 0 "register_operand" "=f")
6263 (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6264 (match_operand:DF 2 "register_operand" "f"))))]
6265 "!TARGET_SOFT_FLOAT && TARGET_PA_20 && !flag_signed_zeros"
6266 "fmpynfadd,dbl %1,%2,%%fr0,%0"
6267 [(set_attr "type" "fpmuldbl")
6268 (set_attr "length" "4")])
6271 [(set (match_operand:SF 0 "register_operand" "=f")
6272 (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6273 (match_operand:SF 2 "register_operand" "f"))))]
6274 "!TARGET_SOFT_FLOAT && TARGET_PA_20 && !flag_signed_zeros"
6275 "fmpynfadd,sgl %1,%2,%%fr0,%0"
6276 [(set_attr "type" "fpmuldbl")
6277 (set_attr "length" "4")])
6280 [(set (match_operand:DF 0 "register_operand" "=f")
6281 (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6282 (match_operand:DF 2 "register_operand" "f"))))
6283 (set (match_operand:DF 3 "register_operand" "=&f")
6284 (mult:DF (match_dup 1) (match_dup 2)))]
6285 "(!TARGET_SOFT_FLOAT && TARGET_PA_20 && !flag_signed_zeros
6286 && ! (reg_overlap_mentioned_p (operands[3], operands[1])
6287 || reg_overlap_mentioned_p (operands[3], operands[2])))"
6289 [(set_attr "type" "fpmuldbl")
6290 (set_attr "length" "8")])
6293 [(set (match_operand:DF 0 "register_operand" "")
6294 (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "")
6295 (match_operand:DF 2 "register_operand" ""))))
6296 (set (match_operand:DF 3 "register_operand" "")
6297 (mult:DF (match_dup 1) (match_dup 2)))]
6298 "!TARGET_SOFT_FLOAT && TARGET_PA_20 && !flag_signed_zeros"
6299 [(set (match_dup 3) (mult:DF (match_dup 1) (match_dup 2)))
6300 (set (match_dup 0) (neg:DF (mult:DF (match_dup 1) (match_dup 2))))]
6304 [(set (match_operand:SF 0 "register_operand" "=f")
6305 (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6306 (match_operand:SF 2 "register_operand" "f"))))
6307 (set (match_operand:SF 3 "register_operand" "=&f")
6308 (mult:SF (match_dup 1) (match_dup 2)))]
6309 "(!TARGET_SOFT_FLOAT && TARGET_PA_20 && !flag_signed_zeros
6310 && ! (reg_overlap_mentioned_p (operands[3], operands[1])
6311 || reg_overlap_mentioned_p (operands[3], operands[2])))"
6313 [(set_attr "type" "fpmuldbl")
6314 (set_attr "length" "8")])
6317 [(set (match_operand:SF 0 "register_operand" "")
6318 (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "")
6319 (match_operand:SF 2 "register_operand" ""))))
6320 (set (match_operand:SF 3 "register_operand" "")
6321 (mult:SF (match_dup 1) (match_dup 2)))]
6322 "!TARGET_SOFT_FLOAT && TARGET_PA_20&& !flag_signed_zeros"
6323 [(set (match_dup 3) (mult:SF (match_dup 1) (match_dup 2)))
6324 (set (match_dup 0) (neg:SF (mult:SF (match_dup 1) (match_dup 2))))]
6327 ;;- Shift instructions
6329 ;; Optimized special case of shifting.
6332 [(set (match_operand:SI 0 "register_operand" "=r")
6333 (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
6337 [(set_attr "type" "load")
6338 (set_attr "length" "4")])
6341 [(set (match_operand:SI 0 "register_operand" "=r")
6342 (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
6346 [(set_attr "type" "load")
6347 (set_attr "length" "4")])
6350 [(set (match_operand:SI 0 "register_operand" "=r")
6351 (plus:SI (mult:SI (match_operand:SI 2 "register_operand" "r")
6352 (match_operand:SI 3 "mem_shadd_operand" ""))
6353 (match_operand:SI 1 "register_operand" "r")))]
6355 "{sh%O3addl %2,%1,%0|shladd,l %2,%O3,%1,%0} "
6356 [(set_attr "type" "binary")
6357 (set_attr "length" "4")])
6360 [(set (match_operand:DI 0 "register_operand" "=r")
6361 (plus:DI (mult:DI (match_operand:DI 2 "register_operand" "r")
6362 (match_operand:DI 3 "mem_shadd_operand" ""))
6363 (match_operand:DI 1 "register_operand" "r")))]
6365 "shladd,l %2,%O3,%1,%0"
6366 [(set_attr "type" "binary")
6367 (set_attr "length" "4")])
6370 [(set (match_operand:SI 0 "register_operand" "=r")
6371 (plus:SI (ashift:SI (match_operand:SI 2 "register_operand" "r")
6372 (match_operand:SI 3 "shadd_operand" ""))
6373 (match_operand:SI 1 "register_operand" "r")))]
6375 "{sh%o3addl %2,%1,%0|shladd,l %2,%o3,%1,%0} "
6376 [(set_attr "type" "binary")
6377 (set_attr "length" "4")])
6380 [(set (match_operand:DI 0 "register_operand" "=r")
6381 (plus:DI (ashift:DI (match_operand:DI 2 "register_operand" "r")
6382 (match_operand:DI 3 "shadd_operand" ""))
6383 (match_operand:DI 1 "register_operand" "r")))]
6385 "shladd,l %2,%o3,%1,%0"
6386 [(set_attr "type" "binary")
6387 (set_attr "length" "4")])
6389 (define_expand "ashlsi3"
6390 [(set (match_operand:SI 0 "register_operand" "")
6391 (ashift:SI (match_operand:SI 1 "lhs_lshift_operand" "")
6392 (match_operand:SI 2 "arith32_operand" "")))]
6396 if (GET_CODE (operands[2]) != CONST_INT)
6398 rtx temp = gen_reg_rtx (SImode);
6399 emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
6400 if (GET_CODE (operands[1]) == CONST_INT)
6401 emit_insn (gen_zvdep_imm32 (operands[0], operands[1], temp));
6403 emit_insn (gen_zvdep32 (operands[0], operands[1], temp));
6406 /* Make sure both inputs are not constants,
6407 there are no patterns for that. */
6408 operands[1] = force_reg (SImode, operands[1]);
6412 [(set (match_operand:SI 0 "register_operand" "=r")
6413 (ashift:SI (match_operand:SI 1 "register_operand" "r")
6414 (match_operand:SI 2 "const_int_operand" "n")))]
6416 "{zdep|depw,z} %1,%P2,%L2,%0"
6417 [(set_attr "type" "shift")
6418 (set_attr "length" "4")])
6420 ; Match cases of op1 a CONST_INT here that zvdep_imm32 doesn't handle.
6421 ; Doing it like this makes slightly better code since reload can
6422 ; replace a register with a known value in range -16..15 with a
6423 ; constant. Ideally, we would like to merge zvdep32 and zvdep_imm32,
6424 ; but since we have no more CONST_OK... characters, that is not
6426 (define_insn "zvdep32"
6427 [(set (match_operand:SI 0 "register_operand" "=r,r")
6428 (ashift:SI (match_operand:SI 1 "arith5_operand" "r,L")
6429 (minus:SI (const_int 31)
6430 (match_operand:SI 2 "register_operand" "q,q"))))]
6433 {zvdep %1,32,%0|depw,z %1,%%sar,32,%0}
6434 {zvdepi %1,32,%0|depwi,z %1,%%sar,32,%0}"
6435 [(set_attr "type" "shift,shift")
6436 (set_attr "length" "4,4")])
6438 (define_insn "zvdep_imm32"
6439 [(set (match_operand:SI 0 "register_operand" "=r")
6440 (ashift:SI (match_operand:SI 1 "lhs_lshift_cint_operand" "")
6441 (minus:SI (const_int 31)
6442 (match_operand:SI 2 "register_operand" "q"))))]
6446 unsigned HOST_WIDE_INT x = UINTVAL (operands[1]);
6447 operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
6448 operands[1] = GEN_INT ((x & 0xf) - 0x10);
6449 return \"{zvdepi %1,%2,%0|depwi,z %1,%%sar,%2,%0}\";
6451 [(set_attr "type" "shift")
6452 (set_attr "length" "4")])
6454 (define_insn "vdepi_ior"
6455 [(set (match_operand:SI 0 "register_operand" "=r")
6456 (ior:SI (ashift:SI (match_operand:SI 1 "const_int_operand" "")
6457 (minus:SI (const_int 31)
6458 (match_operand:SI 2 "register_operand" "q")))
6459 (match_operand:SI 3 "register_operand" "0")))]
6460 ; accept ...0001...1, can this be generalized?
6461 "exact_log2 (INTVAL (operands[1]) + 1) > 0"
6464 HOST_WIDE_INT x = INTVAL (operands[1]);
6465 operands[2] = GEN_INT (exact_log2 (x + 1));
6466 return \"{vdepi -1,%2,%0|depwi -1,%%sar,%2,%0}\";
6468 [(set_attr "type" "shift")
6469 (set_attr "length" "4")])
6471 (define_insn "vdepi_and"
6472 [(set (match_operand:SI 0 "register_operand" "=r")
6473 (and:SI (rotate:SI (match_operand:SI 1 "const_int_operand" "")
6474 (minus:SI (const_int 31)
6475 (match_operand:SI 2 "register_operand" "q")))
6476 (match_operand:SI 3 "register_operand" "0")))]
6477 ; this can be generalized...!
6478 "INTVAL (operands[1]) == -2"
6481 HOST_WIDE_INT x = INTVAL (operands[1]);
6482 operands[2] = GEN_INT (exact_log2 ((~x) + 1));
6483 return \"{vdepi 0,%2,%0|depwi 0,%%sar,%2,%0}\";
6485 [(set_attr "type" "shift")
6486 (set_attr "length" "4")])
6488 (define_expand "ashldi3"
6489 [(set (match_operand:DI 0 "register_operand" "")
6490 (ashift:DI (match_operand:DI 1 "lhs_lshift_operand" "")
6491 (match_operand:DI 2 "arith32_operand" "")))]
6495 if (GET_CODE (operands[2]) != CONST_INT)
6497 rtx temp = gen_reg_rtx (DImode);
6498 emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
6499 if (GET_CODE (operands[1]) == CONST_INT)
6500 emit_insn (gen_zvdep_imm64 (operands[0], operands[1], temp));
6502 emit_insn (gen_zvdep64 (operands[0], operands[1], temp));
6505 /* Make sure both inputs are not constants,
6506 there are no patterns for that. */
6507 operands[1] = force_reg (DImode, operands[1]);
6511 [(set (match_operand:DI 0 "register_operand" "=r")
6512 (ashift:DI (match_operand:DI 1 "register_operand" "r")
6513 (match_operand:DI 2 "const_int_operand" "n")))]
6515 "depd,z %1,%p2,%Q2,%0"
6516 [(set_attr "type" "shift")
6517 (set_attr "length" "4")])
6519 ; Match cases of op1 a CONST_INT here that zvdep_imm64 doesn't handle.
6520 ; Doing it like this makes slightly better code since reload can
6521 ; replace a register with a known value in range -16..15 with a
6522 ; constant. Ideally, we would like to merge zvdep64 and zvdep_imm64,
6523 ; but since we have no more CONST_OK... characters, that is not
6525 (define_insn "zvdep64"
6526 [(set (match_operand:DI 0 "register_operand" "=r,r")
6527 (ashift:DI (match_operand:DI 1 "arith5_operand" "r,L")
6528 (minus:DI (const_int 63)
6529 (match_operand:DI 2 "register_operand" "q,q"))))]
6532 depd,z %1,%%sar,64,%0
6533 depdi,z %1,%%sar,64,%0"
6534 [(set_attr "type" "shift,shift")
6535 (set_attr "length" "4,4")])
6537 (define_insn "zvdep_imm64"
6538 [(set (match_operand:DI 0 "register_operand" "=r")
6539 (ashift:DI (match_operand:DI 1 "lhs_lshift_cint_operand" "")
6540 (minus:DI (const_int 63)
6541 (match_operand:DI 2 "register_operand" "q"))))]
6545 unsigned HOST_WIDE_INT x = UINTVAL (operands[1]);
6546 operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
6547 operands[1] = GEN_INT ((x & 0x1f) - 0x20);
6548 return \"depdi,z %1,%%sar,%2,%0\";
6550 [(set_attr "type" "shift")
6551 (set_attr "length" "4")])
6554 [(set (match_operand:DI 0 "register_operand" "=r")
6555 (ior:DI (ashift:DI (match_operand:DI 1 "const_int_operand" "")
6556 (minus:DI (const_int 63)
6557 (match_operand:DI 2 "register_operand" "q")))
6558 (match_operand:DI 3 "register_operand" "0")))]
6559 ; accept ...0001...1, can this be generalized?
6560 "TARGET_64BIT && exact_log2 (INTVAL (operands[1]) + 1) > 0"
6563 HOST_WIDE_INT x = INTVAL (operands[1]);
6564 operands[2] = GEN_INT (exact_log2 (x + 1));
6565 return \"depdi -1,%%sar,%2,%0\";
6567 [(set_attr "type" "shift")
6568 (set_attr "length" "4")])
6571 [(set (match_operand:DI 0 "register_operand" "=r")
6572 (and:DI (rotate:DI (match_operand:DI 1 "const_int_operand" "")
6573 (minus:DI (const_int 63)
6574 (match_operand:DI 2 "register_operand" "q")))
6575 (match_operand:DI 3 "register_operand" "0")))]
6576 ; this can be generalized...!
6577 "TARGET_64BIT && INTVAL (operands[1]) == -2"
6580 HOST_WIDE_INT x = INTVAL (operands[1]);
6581 operands[2] = GEN_INT (exact_log2 ((~x) + 1));
6582 return \"depdi 0,%%sar,%2,%0\";
6584 [(set_attr "type" "shift")
6585 (set_attr "length" "4")])
6587 (define_expand "ashrsi3"
6588 [(set (match_operand:SI 0 "register_operand" "")
6589 (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
6590 (match_operand:SI 2 "arith32_operand" "")))]
6594 if (GET_CODE (operands[2]) != CONST_INT)
6596 rtx temp = gen_reg_rtx (SImode);
6597 emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
6598 emit_insn (gen_vextrs32 (operands[0], operands[1], temp));
6604 [(set (match_operand:SI 0 "register_operand" "=r")
6605 (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6606 (match_operand:SI 2 "const_int_operand" "n")))]
6608 "{extrs|extrw,s} %1,%P2,%L2,%0"
6609 [(set_attr "type" "shift")
6610 (set_attr "length" "4")])
6612 (define_insn "vextrs32"
6613 [(set (match_operand:SI 0 "register_operand" "=r")
6614 (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6615 (minus:SI (const_int 31)
6616 (match_operand:SI 2 "register_operand" "q"))))]
6618 "{vextrs %1,32,%0|extrw,s %1,%%sar,32,%0}"
6619 [(set_attr "type" "shift")
6620 (set_attr "length" "4")])
6622 (define_expand "ashrdi3"
6623 [(set (match_operand:DI 0 "register_operand" "")
6624 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
6625 (match_operand:DI 2 "arith32_operand" "")))]
6629 if (GET_CODE (operands[2]) != CONST_INT)
6631 rtx temp = gen_reg_rtx (DImode);
6632 emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
6633 emit_insn (gen_vextrs64 (operands[0], operands[1], temp));
6639 [(set (match_operand:DI 0 "register_operand" "=r")
6640 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6641 (match_operand:DI 2 "const_int_operand" "n")))]
6643 "extrd,s %1,%p2,%Q2,%0"
6644 [(set_attr "type" "shift")
6645 (set_attr "length" "4")])
6647 (define_insn "vextrs64"
6648 [(set (match_operand:DI 0 "register_operand" "=r")
6649 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6650 (minus:DI (const_int 63)
6651 (match_operand:DI 2 "register_operand" "q"))))]
6653 "extrd,s %1,%%sar,64,%0"
6654 [(set_attr "type" "shift")
6655 (set_attr "length" "4")])
6657 (define_insn "lshrsi3"
6658 [(set (match_operand:SI 0 "register_operand" "=r,r")
6659 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
6660 (match_operand:SI 2 "shift5_operand" "q,n")))]
6663 {vshd %%r0,%1,%0|shrpw %%r0,%1,%%sar,%0}
6664 {extru|extrw,u} %1,%P2,%L2,%0"
6665 [(set_attr "type" "shift")
6666 (set_attr "length" "4")])
6668 (define_insn "lshrdi3"
6669 [(set (match_operand:DI 0 "register_operand" "=r,r")
6670 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
6671 (match_operand:DI 2 "shift6_operand" "q,n")))]
6674 shrpd %%r0,%1,%%sar,%0
6675 extrd,u %1,%p2,%Q2,%0"
6676 [(set_attr "type" "shift")
6677 (set_attr "length" "4")])
6679 ; Shift right pair word 0 to 31 bits.
6680 (define_insn "shrpsi4"
6681 [(set (match_operand:SI 0 "register_operand" "=r,r")
6682 (ior:SI (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
6683 (minus:SI (const_int 32)
6684 (match_operand:SI 3 "shift5_operand" "q,n")))
6685 (lshiftrt:SI (match_operand:SI 2 "register_operand" "r,r")
6689 {vshd %1,%2,%0|shrpw %1,%2,%%sar,%0}
6690 {shd|shrpw} %1,%2,%3,%0"
6691 [(set_attr "type" "shift")
6692 (set_attr "length" "4")])
6694 ; Shift right pair doubleword 0 to 63 bits.
6695 (define_insn "shrpdi4"
6696 [(set (match_operand:DI 0 "register_operand" "=r,r")
6697 (ior:DI (ashift:DI (match_operand:SI 1 "register_operand" "r,r")
6698 (minus:DI (const_int 64)
6699 (match_operand:DI 3 "shift6_operand" "q,n")))
6700 (lshiftrt:DI (match_operand:DI 2 "register_operand" "r,r")
6704 shrpd %1,%2,%%sar,%0
6706 [(set_attr "type" "shift")
6707 (set_attr "length" "4")])
6709 (define_insn "rotrsi3"
6710 [(set (match_operand:SI 0 "register_operand" "=r,r")
6711 (rotatert:SI (match_operand:SI 1 "register_operand" "r,r")
6712 (match_operand:SI 2 "shift5_operand" "q,n")))]
6716 if (GET_CODE (operands[2]) == CONST_INT)
6718 operands[2] = GEN_INT (INTVAL (operands[2]) & 31);
6719 return \"{shd|shrpw} %1,%1,%2,%0\";
6722 return \"{vshd %1,%1,%0|shrpw %1,%1,%%sar,%0}\";
6724 [(set_attr "type" "shift")
6725 (set_attr "length" "4")])
6727 (define_expand "rotlsi3"
6728 [(set (match_operand:SI 0 "register_operand" "")
6729 (rotate:SI (match_operand:SI 1 "register_operand" "")
6730 (match_operand:SI 2 "arith32_operand" "")))]
6734 if (GET_CODE (operands[2]) != CONST_INT)
6736 rtx temp = gen_reg_rtx (SImode);
6737 emit_insn (gen_subsi3 (temp, GEN_INT (32), operands[2]));
6738 emit_insn (gen_rotrsi3 (operands[0], operands[1], temp));
6741 /* Else expand normally. */
6745 [(set (match_operand:SI 0 "register_operand" "=r")
6746 (rotate:SI (match_operand:SI 1 "register_operand" "r")
6747 (match_operand:SI 2 "const_int_operand" "n")))]
6751 operands[2] = GEN_INT ((32 - INTVAL (operands[2])) & 31);
6752 return \"{shd|shrpw} %1,%1,%2,%0\";
6754 [(set_attr "type" "shift")
6755 (set_attr "length" "4")])
6758 [(set (match_operand:SI 0 "register_operand" "=r")
6759 (match_operator:SI 5 "plus_xor_ior_operator"
6760 [(ashift:SI (match_operand:SI 1 "register_operand" "r")
6761 (match_operand:SI 3 "const_int_operand" "n"))
6762 (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
6763 (match_operand:SI 4 "const_int_operand" "n"))]))]
6764 "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
6765 "{shd|shrpw} %1,%2,%4,%0"
6766 [(set_attr "type" "shift")
6767 (set_attr "length" "4")])
6770 [(set (match_operand:SI 0 "register_operand" "=r")
6771 (match_operator:SI 5 "plus_xor_ior_operator"
6772 [(lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
6773 (match_operand:SI 4 "const_int_operand" "n"))
6774 (ashift:SI (match_operand:SI 1 "register_operand" "r")
6775 (match_operand:SI 3 "const_int_operand" "n"))]))]
6776 "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
6777 "{shd|shrpw} %1,%2,%4,%0"
6778 [(set_attr "type" "shift")
6779 (set_attr "length" "4")])
6782 [(set (match_operand:SI 0 "register_operand" "=r")
6783 (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
6784 (match_operand:SI 2 "const_int_operand" ""))
6785 (match_operand:SI 3 "const_int_operand" "")))]
6786 "exact_log2 (1 + (INTVAL (operands[3]) >> (INTVAL (operands[2]) & 31))) > 0"
6789 int cnt = INTVAL (operands[2]) & 31;
6790 operands[3] = GEN_INT (exact_log2 (1 + (INTVAL (operands[3]) >> cnt)));
6791 operands[2] = GEN_INT (31 - cnt);
6792 return \"{zdep|depw,z} %1,%2,%3,%0\";
6794 [(set_attr "type" "shift")
6795 (set_attr "length" "4")])
6797 ;; Unconditional and other jump instructions.
6799 ;; Trivial return used when no epilogue is needed.
6800 (define_insn "return"
6803 "pa_can_use_return_insn ()"
6807 return \"bve%* (%%r2)\";
6808 return \"bv%* %%r0(%%r2)\";
6810 [(set_attr "type" "branch")
6811 (set_attr "length" "4")])
6813 ;; This is used for most returns.
6814 (define_insn "return_internal"
6821 return \"bve%* (%%r2)\";
6822 return \"bv%* %%r0(%%r2)\";
6824 [(set_attr "type" "branch")
6825 (set_attr "length" "4")])
6827 ;; This is used for eh returns which bypass the return stub.
6828 (define_insn "return_external_pic"
6830 (clobber (reg:SI 1))
6832 "!TARGET_NO_SPACE_REGS
6834 && flag_pic && crtl->calls_eh_return"
6835 "ldsid (%%sr0,%%r2),%%r1\;mtsp %%r1,%%sr0\;be%* 0(%%sr0,%%r2)"
6836 [(set_attr "type" "branch")
6837 (set_attr "length" "12")])
6839 (define_expand "prologue"
6842 "pa_expand_prologue ();DONE;")
6844 (define_expand "sibcall_epilogue"
6849 pa_expand_epilogue ();
6853 (define_expand "epilogue"
6860 /* Try to use the trivial return first. Else use the full epilogue. */
6861 if (pa_can_use_return_insn ())
6865 pa_expand_epilogue ();
6867 /* EH returns bypass the normal return stub. Thus, we must do an
6868 interspace branch to return from functions that call eh_return.
6869 This is only a problem for returns from shared code on ports
6870 using space registers. */
6871 if (!TARGET_NO_SPACE_REGS
6873 && flag_pic && crtl->calls_eh_return)
6874 x = gen_return_external_pic ();
6876 x = gen_return_internal ();
6882 ; Used by hppa_profile_hook to load the starting address of the current
6883 ; function; operand 1 contains the address of the label in operand 3
6884 (define_insn "load_offset_label_address"
6885 [(set (match_operand:SI 0 "register_operand" "=r")
6886 (plus:SI (match_operand:SI 1 "register_operand" "r")
6887 (minus:SI (match_operand:SI 2 "" "")
6888 (label_ref:SI (match_operand 3 "" "")))))]
6891 [(set_attr "type" "multi")
6892 (set_attr "length" "4")])
6894 ; Output a code label and load its address.
6895 (define_insn "lcla1"
6896 [(set (match_operand:SI 0 "register_operand" "=r")
6897 (label_ref:SI (match_operand 1 "" "")))
6902 output_asm_insn (\"bl .+8,%0\;depi 0,31,2,%0\", operands);
6903 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
6904 CODE_LABEL_NUMBER (operands[1]));
6907 [(set_attr "type" "multi")
6908 (set_attr "length" "8")])
6910 (define_insn "lcla2"
6911 [(set (match_operand:SI 0 "register_operand" "=r")
6912 (label_ref:SI (match_operand 1 "" "")))
6917 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
6918 CODE_LABEL_NUMBER (operands[1]));
6921 [(set_attr "type" "move")
6922 (set_attr "length" "4")])
6924 (define_insn "blockage"
6925 [(unspec_volatile [(const_int 2)] UNSPECV_BLOCKAGE)]
6928 [(set_attr "length" "0")])
6931 [(set (pc) (label_ref (match_operand 0 "" "")))]
6935 /* An unconditional branch which can reach its target. */
6936 if (get_attr_length (insn) < 16)
6939 return pa_output_lbranch (operands[0], insn, 1);
6941 [(set_attr "type" "uncond_branch")
6942 (set_attr "pa_combine_type" "uncond_branch")
6943 (set (attr "length")
6944 (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
6945 (const_int MAX_17BIT_OFFSET))
6947 (match_test "TARGET_PORTABLE_RUNTIME")
6949 (not (match_test "flag_pic"))
6953 ;;; Hope this is only within a function...
6954 (define_insn "indirect_jump"
6955 [(set (pc) (match_operand 0 "register_operand" "r"))]
6956 "GET_MODE (operands[0]) == word_mode"
6958 [(set_attr "type" "branch")
6959 (set_attr "length" "4")])
6961 ;;; An indirect jump can be optimized to a direct jump. GAS for the
6962 ;;; SOM target doesn't allow branching to a label inside a function.
6963 ;;; We also don't correctly compute branch distances for labels
6964 ;;; outside the current function. Thus, we use an indirect jump can't
6965 ;;; be optimized to a direct jump for all targets. We assume that
6966 ;;; the branch target is in the same space (i.e., nested function
6967 ;;; jumping to a label in an outer function in the same translation
6969 (define_expand "nonlocal_goto"
6970 [(use (match_operand 0 "general_operand" ""))
6971 (use (match_operand 1 "general_operand" ""))
6972 (use (match_operand 2 "general_operand" ""))
6973 (use (match_operand 3 "general_operand" ""))]
6976 rtx lab = operands[1];
6977 rtx stack = operands[2];
6978 rtx fp = operands[3];
6980 lab = copy_to_reg (lab);
6982 emit_clobber (gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode)));
6983 emit_clobber (gen_rtx_MEM (BLKmode, hard_frame_pointer_rtx));
6985 /* Restore the frame pointer. The virtual_stack_vars_rtx is saved
6986 instead of the hard_frame_pointer_rtx in the save area. As a
6987 result, an extra instruction is needed to adjust for the offset
6988 of the virtual stack variables and the hard frame pointer. */
6989 if (GET_CODE (fp) != REG)
6990 fp = force_reg (Pmode, fp);
6991 emit_move_insn (hard_frame_pointer_rtx, plus_constant (Pmode, fp, -8));
6993 emit_stack_restore (SAVE_NONLOCAL, stack);
6995 emit_use (hard_frame_pointer_rtx);
6996 emit_use (stack_pointer_rtx);
6998 /* Nonlocal goto jumps are only used between functions in the same
6999 translation unit. Thus, we can avoid the extra overhead of an
7001 emit_jump_insn (gen_indirect_goto (lab));
7006 (define_insn "indirect_goto"
7007 [(unspec [(match_operand 0 "register_operand" "=r")] UNSPEC_GOTO)]
7008 "GET_MODE (operands[0]) == word_mode"
7010 [(set_attr "type" "branch")
7011 (set_attr "length" "4")])
7013 ;; Subroutines of "casesi".
7014 ;; operand 0 is index
7015 ;; operand 1 is the minimum bound
7016 ;; operand 2 is the maximum bound - minimum bound + 1
7017 ;; operand 3 is CODE_LABEL for the table;
7018 ;; operand 4 is the CODE_LABEL to go to if index out of range.
7020 (define_expand "casesi"
7021 [(match_operand:SI 0 "general_operand" "")
7022 (match_operand:SI 1 "const_int_operand" "")
7023 (match_operand:SI 2 "const_int_operand" "")
7024 (match_operand 3 "" "")
7025 (match_operand 4 "" "")]
7029 if (GET_CODE (operands[0]) != REG)
7030 operands[0] = force_reg (SImode, operands[0]);
7032 if (operands[1] != const0_rtx)
7034 rtx index = gen_reg_rtx (SImode);
7036 operands[1] = gen_int_mode (-INTVAL (operands[1]), SImode);
7037 if (!INT_14_BITS (operands[1]))
7038 operands[1] = force_reg (SImode, operands[1]);
7039 emit_insn (gen_addsi3 (index, operands[0], operands[1]));
7040 operands[0] = index;
7043 if (!INT_5_BITS (operands[2]))
7044 operands[2] = force_reg (SImode, operands[2]);
7046 /* This branch prevents us finding an insn for the delay slot of the
7047 following vectored branch. It might be possible to use the delay
7048 slot if an index value of -1 was used to transfer to the out-of-range
7049 label. In order to do this, we would have to output the -1 vector
7050 element after the delay insn. The casesi output code would have to
7051 check if the casesi insn is in a delay branch sequence and output
7052 the delay insn if one is found. If this was done, then it might
7053 then be worthwhile to split the casesi patterns to improve scheduling.
7054 However, it's not clear that all this extra complexity is worth
7057 rtx test = gen_rtx_GTU (VOIDmode, operands[0], operands[2]);
7058 emit_jump_insn (gen_cbranchsi4 (test, operands[0], operands[2], operands[4]));
7061 /* In 64bit mode we must make sure to wipe the upper bits of the register
7062 just in case the addition overflowed or we had random bits in the
7063 high part of the register. */
7066 rtx index = gen_reg_rtx (DImode);
7068 emit_insn (gen_extendsidi2 (index, operands[0]));
7069 operands[0] = index;
7073 emit_jump_insn (gen_casesi64p (operands[0], operands[3]));
7075 emit_jump_insn (gen_casesi32p (operands[0], operands[3]));
7077 emit_jump_insn (gen_casesi32 (operands[0], operands[3]));
7081 ;;; 32-bit code, absolute branch table.
7082 (define_insn "casesi32"
7083 [(set (pc) (mem:SI (plus:SI
7084 (mult:SI (match_operand:SI 0 "register_operand" "r")
7086 (label_ref (match_operand 1 "" "")))))
7087 (clobber (match_scratch:SI 2 "=&r"))]
7089 "ldil L'%l1,%2\;ldo R'%l1(%2),%2\;{ldwx|ldw},s %0(%2),%2\;bv,n %%r0(%2)"
7090 [(set_attr "type" "multi")
7091 (set_attr "length" "16")])
7093 ;;; 32-bit code, relative branch table.
7094 (define_insn "casesi32p"
7095 [(set (pc) (mem:SI (plus:SI
7096 (mult:SI (match_operand:SI 0 "register_operand" "r")
7098 (label_ref (match_operand 1 "" "")))))
7099 (clobber (match_scratch:SI 2 "=&r"))
7100 (clobber (match_scratch:SI 3 "=&r"))]
7102 "{bl .+8,%2\;depi 0,31,2,%2|mfia %2}\;ldo {%l1-.|%l1+4-.}(%2),%2\;\
7103 {ldwx|ldw},s %0(%2),%3\;{addl|add,l} %2,%3,%3\;bv,n %%r0(%3)"
7104 [(set_attr "type" "multi")
7105 (set (attr "length")
7106 (if_then_else (match_test "TARGET_PA_20")
7110 ;;; 64-bit code, 32-bit relative branch table.
7111 (define_insn "casesi64p"
7112 [(set (pc) (mem:DI (plus:DI
7113 (mult:DI (match_operand:DI 0 "register_operand" "r")
7115 (label_ref (match_operand 1 "" "")))))
7116 (clobber (match_scratch:DI 2 "=&r"))
7117 (clobber (match_scratch:DI 3 "=&r"))]
7119 "mfia %2\;ldo %l1+4-.(%2),%2\;ldw,s %0(%2),%3\;extrd,s %3,63,32,%3\;\
7120 add,l %2,%3,%3\;bv,n %%r0(%3)"
7121 [(set_attr "type" "multi")
7122 (set_attr "length" "24")])
7126 ;;- jump to subroutine
7128 (define_expand "call"
7129 [(parallel [(call (match_operand:SI 0 "" "")
7130 (match_operand 1 "" ""))
7131 (clobber (reg:SI 2))])]
7136 rtx nb = operands[1];
7138 if (TARGET_PORTABLE_RUNTIME)
7139 op = force_reg (SImode, XEXP (operands[0], 0));
7142 op = XEXP (operands[0], 0);
7144 /* Generate indirect long calls to non-local functions. */
7145 if (!TARGET_64BIT && TARGET_LONG_CALLS && GET_CODE (op) == SYMBOL_REF)
7147 tree call_decl = SYMBOL_REF_DECL (op);
7148 if (!(call_decl && targetm.binds_local_p (call_decl)))
7149 op = force_reg (word_mode, op);
7155 if (!virtuals_instantiated)
7156 emit_move_insn (arg_pointer_rtx,
7157 gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
7161 /* The loop pass can generate new libcalls after the virtual
7162 registers are instantiated when fpregs are disabled because
7163 the only method that we have for doing DImode multiplication
7164 is with a libcall. This could be trouble if we haven't
7165 allocated enough space for the outgoing arguments. */
7166 gcc_assert (INTVAL (nb) <= crtl->outgoing_args_size);
7168 emit_move_insn (arg_pointer_rtx,
7169 gen_rtx_PLUS (word_mode, stack_pointer_rtx,
7170 GEN_INT (STACK_POINTER_OFFSET + 64)));
7174 /* Use two different patterns for calls to explicitly named functions
7175 and calls through function pointers. This is necessary as these two
7176 types of calls use different calling conventions, and CSE might try
7177 to change the named call into an indirect call in some cases (using
7178 two patterns keeps CSE from performing this optimization).
7180 We now use even more call patterns as there was a subtle bug in
7181 attempting to restore the pic register after a call using a simple
7182 move insn. During reload, a instruction involving a pseudo register
7183 with no explicit dependence on the PIC register can be converted
7184 to an equivalent load from memory using the PIC register. If we
7185 emit a simple move to restore the PIC register in the initial rtl
7186 generation, then it can potentially be repositioned during scheduling.
7187 and an instruction that eventually uses the PIC register may end up
7188 between the call and the PIC register restore.
7190 This only worked because there is a post call group of instructions
7191 that are scheduled with the call. These instructions are included
7192 in the same basic block as the call. However, calls can throw in
7193 C++ code and a basic block has to terminate at the call if the call
7194 can throw. This results in the PIC register restore being scheduled
7195 independently from the call. So, we now hide the save and restore
7196 of the PIC register in the call pattern until after reload. Then,
7197 we split the moves out. A small side benefit is that we now don't
7198 need to have a use of the PIC register in the return pattern and
7199 the final save/restore operation is not needed.
7201 I elected to just use register %r4 in the PIC patterns instead
7202 of trying to force hppa_pic_save_rtx () to a callee saved register.
7203 This might have required a new register class and constraint. It
7204 was also simpler to just handle the restore from a register than a
7208 rtx r4 = gen_rtx_REG (word_mode, 4);
7209 if (GET_CODE (op) == SYMBOL_REF)
7210 emit_call_insn (gen_call_symref_64bit (op, nb, r4));
7213 op = force_reg (word_mode, op);
7214 emit_call_insn (gen_call_reg_64bit (op, nb, r4));
7219 if (GET_CODE (op) == SYMBOL_REF)
7223 rtx r4 = gen_rtx_REG (word_mode, 4);
7224 emit_call_insn (gen_call_symref_pic (op, nb, r4));
7227 emit_call_insn (gen_call_symref (op, nb));
7231 rtx tmpreg = gen_rtx_REG (word_mode, 22);
7232 emit_move_insn (tmpreg, force_reg (word_mode, op));
7235 rtx r4 = gen_rtx_REG (word_mode, 4);
7236 emit_call_insn (gen_call_reg_pic (nb, r4));
7239 emit_call_insn (gen_call_reg (nb));
7246 ;; We use function calls to set the attribute length of calls and millicode
7247 ;; calls. This is necessary because of the large variety of call sequences.
7248 ;; Implementing the calculation in rtl is difficult as well as ugly. As
7249 ;; we need the same calculation in several places, maintenance becomes a
7252 ;; However, this has a subtle impact on branch shortening. When the
7253 ;; expression used to set the length attribute of an instruction depends
7254 ;; on a relative address (e.g., pc or a branch address), genattrtab
7255 ;; notes that the insn's length is variable, and attempts to determine a
7256 ;; worst-case default length and code to compute an insn's current length.
7258 ;; The use of a function call hides the variable dependence of our calls
7259 ;; and millicode calls. The result is genattrtab doesn't treat the operation
7260 ;; as variable and it only generates code for the default case using our
7261 ;; function call. Because of this, calls and millicode calls have a fixed
7262 ;; length in the branch shortening pass, and some branches will use a longer
7263 ;; code sequence than necessary. However, the length of any given call
7264 ;; will still reflect its final code location and it may be shorter than
7265 ;; the initial length estimate.
7267 ;; It's possible to trick genattrtab by adding an expression involving `pc'
7268 ;; in the set. However, when genattrtab hits a function call in its attempt
7269 ;; to compute the default length, it marks the result as unknown and sets
7270 ;; the default result to MAX_INT ;-( One possible fix that would allow
7271 ;; calls to participate in branch shortening would be to make the call to
7272 ;; insn_default_length a target option. Then, we could massage unknown
7273 ;; results. Another fix might be to change genattrtab so that it just does
7274 ;; the call in the variable case as it already does for the fixed case.
7276 (define_insn "call_symref"
7277 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7278 (match_operand 1 "" "i"))
7279 (clobber (reg:SI 1))
7280 (clobber (reg:SI 2))
7281 (use (const_int 0))]
7282 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7285 pa_output_arg_descriptor (insn);
7286 return pa_output_call (insn, operands[0], 0);
7288 [(set_attr "type" "call")
7289 (set (attr "length")
7290 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7291 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7293 (define_insn "call_symref_pic"
7294 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7295 (match_operand 1 "" "i"))
7296 (clobber (reg:SI 1))
7297 (clobber (reg:SI 2))
7298 (clobber (match_operand 2))
7300 (use (const_int 0))]
7301 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7304 ;; Split out the PIC register save and restore after reload. As the
7305 ;; split is done after reload, there are some situations in which we
7306 ;; unnecessarily save and restore %r4. This happens when there is a
7307 ;; single call and the PIC register is not used after the call.
7309 ;; The split has to be done since call_from_call_insn () can't handle
7310 ;; the pattern as is. Noreturn calls are special because they have to
7311 ;; terminate the basic block. The split has to contain more than one
7314 [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7315 (match_operand 1 "" ""))
7316 (clobber (reg:SI 1))
7317 (clobber (reg:SI 2))
7318 (clobber (match_operand 2))
7320 (use (const_int 0))])]
7321 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed
7322 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7323 [(set (match_dup 2) (reg:SI 19))
7324 (parallel [(call (mem:SI (match_dup 0))
7326 (clobber (reg:SI 1))
7327 (clobber (reg:SI 2))
7329 (use (const_int 0))])]
7333 [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7334 (match_operand 1 "" ""))
7335 (clobber (reg:SI 1))
7336 (clobber (reg:SI 2))
7337 (clobber (match_operand 2))
7339 (use (const_int 0))])]
7340 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed"
7341 [(set (match_dup 2) (reg:SI 19))
7342 (parallel [(call (mem:SI (match_dup 0))
7344 (clobber (reg:SI 1))
7345 (clobber (reg:SI 2))
7347 (use (const_int 0))])
7348 (set (reg:SI 19) (match_dup 2))]
7351 (define_insn "*call_symref_pic_post_reload"
7352 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7353 (match_operand 1 "" "i"))
7354 (clobber (reg:SI 1))
7355 (clobber (reg:SI 2))
7357 (use (const_int 0))]
7358 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7361 pa_output_arg_descriptor (insn);
7362 return pa_output_call (insn, operands[0], 0);
7364 [(set_attr "type" "call")
7365 (set (attr "length")
7366 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7367 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7369 ;; This pattern is split if it is necessary to save and restore the
7371 (define_insn "call_symref_64bit"
7372 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7373 (match_operand 1 "" "i"))
7374 (clobber (reg:DI 1))
7375 (clobber (reg:DI 2))
7376 (clobber (match_operand 2))
7379 (use (const_int 0))]
7383 ;; Split out the PIC register save and restore after reload. As the
7384 ;; split is done after reload, there are some situations in which we
7385 ;; unnecessarily save and restore %r4. This happens when there is a
7386 ;; single call and the PIC register is not used after the call.
7388 ;; The split has to be done since call_from_call_insn () can't handle
7389 ;; the pattern as is. Noreturn calls are special because they have to
7390 ;; terminate the basic block. The split has to contain more than one
7393 [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7394 (match_operand 1 "" ""))
7395 (clobber (reg:DI 1))
7396 (clobber (reg:DI 2))
7397 (clobber (match_operand 2))
7400 (use (const_int 0))])]
7401 "TARGET_64BIT && reload_completed
7402 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7403 [(set (match_dup 2) (reg:DI 27))
7404 (parallel [(call (mem:SI (match_dup 0))
7406 (clobber (reg:DI 1))
7407 (clobber (reg:DI 2))
7410 (use (const_int 0))])]
7414 [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7415 (match_operand 1 "" ""))
7416 (clobber (reg:DI 1))
7417 (clobber (reg:DI 2))
7418 (clobber (match_operand 2))
7421 (use (const_int 0))])]
7422 "TARGET_64BIT && reload_completed"
7423 [(set (match_dup 2) (reg:DI 27))
7424 (parallel [(call (mem:SI (match_dup 0))
7426 (clobber (reg:DI 1))
7427 (clobber (reg:DI 2))
7430 (use (const_int 0))])
7431 (set (reg:DI 27) (match_dup 2))]
7434 (define_insn "*call_symref_64bit_post_reload"
7435 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7436 (match_operand 1 "" "i"))
7437 (clobber (reg:DI 1))
7438 (clobber (reg:DI 2))
7441 (use (const_int 0))]
7445 pa_output_arg_descriptor (insn);
7446 return pa_output_call (insn, operands[0], 0);
7448 [(set_attr "type" "call")
7449 (set (attr "length")
7450 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7451 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7453 (define_insn "call_reg"
7454 [(call (mem:SI (reg:SI 22))
7455 (match_operand 0 "" "i"))
7456 (clobber (reg:SI 1))
7457 (clobber (reg:SI 2))
7458 (use (const_int 1))]
7462 return pa_output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
7464 [(set_attr "type" "dyncall")
7465 (set (attr "length")
7466 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7467 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
7469 ;; This pattern is split if it is necessary to save and restore the
7471 (define_insn "call_reg_pic"
7472 [(call (mem:SI (reg:SI 22))
7473 (match_operand 0 "" "i"))
7474 (clobber (reg:SI 1))
7475 (clobber (reg:SI 2))
7476 (clobber (match_operand 1))
7478 (use (const_int 1))]
7482 ;; Split out the PIC register save and restore after reload. As the
7483 ;; split is done after reload, there are some situations in which we
7484 ;; unnecessarily save and restore %r4. This happens when there is a
7485 ;; single call and the PIC register is not used after the call.
7487 ;; The split has to be done since call_from_call_insn () can't handle
7488 ;; the pattern as is. Noreturn calls are special because they have to
7489 ;; terminate the basic block. The split has to contain more than one
7492 [(parallel [(call (mem:SI (reg:SI 22))
7493 (match_operand 0 "" ""))
7494 (clobber (reg:SI 1))
7495 (clobber (reg:SI 2))
7496 (clobber (match_operand 1))
7498 (use (const_int 1))])]
7499 "!TARGET_64BIT && reload_completed
7500 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7501 [(set (match_dup 1) (reg:SI 19))
7502 (parallel [(call (mem:SI (reg:SI 22))
7504 (clobber (reg:SI 1))
7505 (clobber (reg:SI 2))
7507 (use (const_int 1))])]
7511 [(parallel [(call (mem:SI (reg:SI 22))
7512 (match_operand 0 "" ""))
7513 (clobber (reg:SI 1))
7514 (clobber (reg:SI 2))
7515 (clobber (match_operand 1))
7517 (use (const_int 1))])]
7518 "!TARGET_64BIT && reload_completed"
7519 [(set (match_dup 1) (reg:SI 19))
7520 (parallel [(call (mem:SI (reg:SI 22))
7522 (clobber (reg:SI 1))
7523 (clobber (reg:SI 2))
7525 (use (const_int 1))])
7526 (set (reg:SI 19) (match_dup 1))]
7529 (define_insn "*call_reg_pic_post_reload"
7530 [(call (mem:SI (reg:SI 22))
7531 (match_operand 0 "" "i"))
7532 (clobber (reg:SI 1))
7533 (clobber (reg:SI 2))
7535 (use (const_int 1))]
7539 return pa_output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
7541 [(set_attr "type" "dyncall")
7542 (set (attr "length")
7543 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7544 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
7546 ;; This pattern is split if it is necessary to save and restore the
7548 (define_insn "call_reg_64bit"
7549 [(call (mem:SI (match_operand:DI 0 "register_operand" "r"))
7550 (match_operand 1 "" "i"))
7551 (clobber (reg:DI 1))
7552 (clobber (reg:DI 2))
7553 (clobber (match_operand 2))
7556 (use (const_int 1))]
7560 ;; Split out the PIC register save and restore after reload. As the
7561 ;; split is done after reload, there are some situations in which we
7562 ;; unnecessarily save and restore %r4. This happens when there is a
7563 ;; single call and the PIC register is not used after the call.
7565 ;; The split has to be done since call_from_call_insn () can't handle
7566 ;; the pattern as is. Noreturn calls are special because they have to
7567 ;; terminate the basic block. The split has to contain more than one
7570 [(parallel [(call (mem:SI (match_operand 0 "register_operand" ""))
7571 (match_operand 1 "" ""))
7572 (clobber (reg:DI 1))
7573 (clobber (reg:DI 2))
7574 (clobber (match_operand 2))
7577 (use (const_int 1))])]
7578 "TARGET_64BIT && reload_completed
7579 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7580 [(set (match_dup 2) (reg:DI 27))
7581 (parallel [(call (mem:SI (match_dup 0))
7583 (clobber (reg:DI 1))
7584 (clobber (reg:DI 2))
7587 (use (const_int 1))])]
7591 [(parallel [(call (mem:SI (match_operand 0 "register_operand" ""))
7592 (match_operand 1 "" ""))
7593 (clobber (reg:DI 1))
7594 (clobber (reg:DI 2))
7595 (clobber (match_operand 2))
7598 (use (const_int 1))])]
7599 "TARGET_64BIT && reload_completed"
7600 [(set (match_dup 2) (reg:DI 27))
7601 (parallel [(call (mem:SI (match_dup 0))
7603 (clobber (reg:DI 1))
7604 (clobber (reg:DI 2))
7607 (use (const_int 1))])
7608 (set (reg:DI 27) (match_dup 2))]
7611 (define_insn "*call_reg_64bit_post_reload"
7612 [(call (mem:SI (match_operand:DI 0 "register_operand" "r"))
7613 (match_operand 1 "" "i"))
7614 (clobber (reg:DI 1))
7615 (clobber (reg:DI 2))
7618 (use (const_int 1))]
7622 return pa_output_indirect_call (insn, operands[0]);
7624 [(set_attr "type" "dyncall")
7625 (set (attr "length")
7626 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 12)]
7627 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
7629 (define_expand "call_value"
7630 [(parallel [(set (match_operand 0 "" "")
7631 (call (match_operand:SI 1 "" "")
7632 (match_operand 2 "" "")))
7633 (clobber (reg:SI 2))])]
7637 rtx dst = operands[0];
7638 rtx nb = operands[2];
7639 bool call_powf = false;
7641 if (TARGET_PORTABLE_RUNTIME)
7642 op = force_reg (SImode, XEXP (operands[1], 0));
7645 op = XEXP (operands[1], 0);
7646 if (GET_CODE (op) == SYMBOL_REF)
7648 /* Handle special call to buggy powf function. */
7649 if (TARGET_HPUX && !TARGET_DISABLE_FPREGS && !TARGET_SOFT_FLOAT
7650 && !strcmp (targetm.strip_name_encoding (XSTR (op, 0)), "powf"))
7653 /* Generate indirect long calls to non-local functions. */
7654 else if (!TARGET_64BIT && TARGET_LONG_CALLS)
7656 tree call_decl = SYMBOL_REF_DECL (op);
7657 if (!(call_decl && targetm.binds_local_p (call_decl)))
7658 op = force_reg (word_mode, op);
7665 if (!virtuals_instantiated)
7666 emit_move_insn (arg_pointer_rtx,
7667 gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
7671 /* The loop pass can generate new libcalls after the virtual
7672 registers are instantiated when fpregs are disabled because
7673 the only method that we have for doing DImode multiplication
7674 is with a libcall. This could be trouble if we haven't
7675 allocated enough space for the outgoing arguments. */
7676 gcc_assert (INTVAL (nb) <= crtl->outgoing_args_size);
7678 emit_move_insn (arg_pointer_rtx,
7679 gen_rtx_PLUS (word_mode, stack_pointer_rtx,
7680 GEN_INT (STACK_POINTER_OFFSET + 64)));
7684 /* Use two different patterns for calls to explicitly named functions
7685 and calls through function pointers. This is necessary as these two
7686 types of calls use different calling conventions, and CSE might try
7687 to change the named call into an indirect call in some cases (using
7688 two patterns keeps CSE from performing this optimization).
7690 We now use even more call patterns as there was a subtle bug in
7691 attempting to restore the pic register after a call using a simple
7692 move insn. During reload, a instruction involving a pseudo register
7693 with no explicit dependence on the PIC register can be converted
7694 to an equivalent load from memory using the PIC register. If we
7695 emit a simple move to restore the PIC register in the initial rtl
7696 generation, then it can potentially be repositioned during scheduling.
7697 and an instruction that eventually uses the PIC register may end up
7698 between the call and the PIC register restore.
7700 This only worked because there is a post call group of instructions
7701 that are scheduled with the call. These instructions are included
7702 in the same basic block as the call. However, calls can throw in
7703 C++ code and a basic block has to terminate at the call if the call
7704 can throw. This results in the PIC register restore being scheduled
7705 independently from the call. So, we now hide the save and restore
7706 of the PIC register in the call pattern until after reload. Then,
7707 we split the moves out. A small side benefit is that we now don't
7708 need to have a use of the PIC register in the return pattern and
7709 the final save/restore operation is not needed.
7711 I elected to just use register %r4 in the PIC patterns instead
7712 of trying to force hppa_pic_save_rtx () to a callee saved register.
7713 This might have required a new register class and constraint. It
7714 was also simpler to just handle the restore from a register than a
7718 rtx r4 = gen_rtx_REG (word_mode, 4);
7719 if (GET_CODE (op) == SYMBOL_REF)
7722 emit_call_insn (gen_call_val_powf_64bit (dst, op, nb, r4));
7724 emit_call_insn (gen_call_val_symref_64bit (dst, op, nb, r4));
7728 op = force_reg (word_mode, op);
7729 emit_call_insn (gen_call_val_reg_64bit (dst, op, nb, r4));
7734 if (GET_CODE (op) == SYMBOL_REF)
7738 rtx r4 = gen_rtx_REG (word_mode, 4);
7741 emit_call_insn (gen_call_val_powf_pic (dst, op, nb, r4));
7743 emit_call_insn (gen_call_val_symref_pic (dst, op, nb, r4));
7748 emit_call_insn (gen_call_val_powf (dst, op, nb));
7750 emit_call_insn (gen_call_val_symref (dst, op, nb));
7755 rtx tmpreg = gen_rtx_REG (word_mode, 22);
7756 emit_move_insn (tmpreg, force_reg (word_mode, op));
7759 rtx r4 = gen_rtx_REG (word_mode, 4);
7760 emit_call_insn (gen_call_val_reg_pic (dst, nb, r4));
7763 emit_call_insn (gen_call_val_reg (dst, nb));
7770 (define_insn "call_val_symref"
7771 [(set (match_operand 0 "" "")
7772 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7773 (match_operand 2 "" "i")))
7774 (clobber (reg:SI 1))
7775 (clobber (reg:SI 2))
7776 (use (const_int 0))]
7777 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7780 pa_output_arg_descriptor (insn);
7781 return pa_output_call (insn, operands[1], 0);
7783 [(set_attr "type" "call")
7784 (set (attr "length")
7785 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7786 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7788 ;; powf function clobbers %fr12
7789 (define_insn "call_val_powf"
7790 [(set (match_operand 0 "" "")
7791 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7792 (match_operand 2 "" "i")))
7793 (clobber (reg:SI 1))
7794 (clobber (reg:SI 2))
7795 (clobber (reg:DF 48))
7796 (use (const_int 1))]
7797 "TARGET_HPUX && !TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7800 pa_output_arg_descriptor (insn);
7801 return pa_output_call (insn, operands[1], 0);
7803 [(set_attr "type" "call")
7804 (set (attr "length")
7805 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7806 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7808 (define_insn "call_val_symref_pic"
7809 [(set (match_operand 0 "" "")
7810 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7811 (match_operand 2 "" "i")))
7812 (clobber (reg:SI 1))
7813 (clobber (reg:SI 2))
7814 (clobber (match_operand 3))
7816 (use (const_int 0))]
7817 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7820 ;; Split out the PIC register save and restore after reload. As the
7821 ;; split is done after reload, there are some situations in which we
7822 ;; unnecessarily save and restore %r4. This happens when there is a
7823 ;; single call and the PIC register is not used after the call.
7825 ;; The split has to be done since call_from_call_insn () can't handle
7826 ;; the pattern as is. Noreturn calls are special because they have to
7827 ;; terminate the basic block. The split has to contain more than one
7830 [(parallel [(set (match_operand 0 "" "")
7831 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7832 (match_operand 2 "" "")))
7833 (clobber (reg:SI 1))
7834 (clobber (reg:SI 2))
7835 (clobber (match_operand 3))
7837 (use (const_int 0))])]
7838 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed
7839 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7840 [(set (match_dup 3) (reg:SI 19))
7841 (parallel [(set (match_dup 0)
7842 (call (mem:SI (match_dup 1))
7844 (clobber (reg:SI 1))
7845 (clobber (reg:SI 2))
7847 (use (const_int 0))])]
7851 [(parallel [(set (match_operand 0 "" "")
7852 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7853 (match_operand 2 "" "")))
7854 (clobber (reg:SI 1))
7855 (clobber (reg:SI 2))
7856 (clobber (match_operand 3))
7858 (use (const_int 0))])]
7859 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed"
7860 [(set (match_dup 3) (reg:SI 19))
7861 (parallel [(set (match_dup 0)
7862 (call (mem:SI (match_dup 1))
7864 (clobber (reg:SI 1))
7865 (clobber (reg:SI 2))
7867 (use (const_int 0))])
7868 (set (reg:SI 19) (match_dup 3))]
7871 (define_insn "*call_val_symref_pic_post_reload"
7872 [(set (match_operand 0 "" "")
7873 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7874 (match_operand 2 "" "i")))
7875 (clobber (reg:SI 1))
7876 (clobber (reg:SI 2))
7878 (use (const_int 0))]
7879 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7882 pa_output_arg_descriptor (insn);
7883 return pa_output_call (insn, operands[1], 0);
7885 [(set_attr "type" "call")
7886 (set (attr "length")
7887 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7888 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7890 ;; powf function clobbers %fr12
7891 (define_insn "call_val_powf_pic"
7892 [(set (match_operand 0 "" "")
7893 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7894 (match_operand 2 "" "i")))
7895 (clobber (reg:SI 1))
7896 (clobber (reg:SI 2))
7897 (clobber (reg:DF 48))
7898 (clobber (match_operand 3))
7900 (use (const_int 1))]
7901 "TARGET_HPUX && !TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7904 ;; Split out the PIC register save and restore after reload. As the
7905 ;; split is done after reload, there are some situations in which we
7906 ;; unnecessarily save and restore %r4. This happens when there is a
7907 ;; single call and the PIC register is not used after the call.
7909 ;; The split has to be done since call_from_call_insn () can't handle
7910 ;; the pattern as is. Noreturn calls are special because they have to
7911 ;; terminate the basic block. The split has to contain more than one
7914 [(parallel [(set (match_operand 0 "" "")
7915 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7916 (match_operand 2 "" "")))
7917 (clobber (reg:SI 1))
7918 (clobber (reg:SI 2))
7919 (clobber (reg:DF 48))
7920 (clobber (match_operand 3))
7922 (use (const_int 1))])]
7923 "TARGET_HPUX && !TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed
7924 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7925 [(set (match_dup 3) (reg:SI 19))
7926 (parallel [(set (match_dup 0)
7927 (call (mem:SI (match_dup 1))
7929 (clobber (reg:SI 1))
7930 (clobber (reg:SI 2))
7931 (clobber (reg:DF 48))
7933 (use (const_int 1))])]
7937 [(parallel [(set (match_operand 0 "" "")
7938 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7939 (match_operand 2 "" "")))
7940 (clobber (reg:SI 1))
7941 (clobber (reg:SI 2))
7942 (clobber (reg:DF 48))
7943 (clobber (match_operand 3))
7945 (use (const_int 1))])]
7946 "TARGET_HPUX && !TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed"
7947 [(set (match_dup 3) (reg:SI 19))
7948 (parallel [(set (match_dup 0)
7949 (call (mem:SI (match_dup 1))
7951 (clobber (reg:SI 1))
7952 (clobber (reg:SI 2))
7953 (clobber (reg:DF 48))
7955 (use (const_int 1))])
7956 (set (reg:SI 19) (match_dup 3))]
7959 (define_insn "*call_val_powf_pic_post_reload"
7960 [(set (match_operand 0 "" "")
7961 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7962 (match_operand 2 "" "i")))
7963 (clobber (reg:SI 1))
7964 (clobber (reg:SI 2))
7965 (clobber (reg:DF 48))
7967 (use (const_int 1))]
7968 "TARGET_HPUX && !TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7971 pa_output_arg_descriptor (insn);
7972 return pa_output_call (insn, operands[1], 0);
7974 [(set_attr "type" "call")
7975 (set (attr "length")
7976 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
7977 (symbol_ref "pa_attr_length_call (insn, 0)")))])
7979 ;; This pattern is split if it is necessary to save and restore the
7981 (define_insn "call_val_symref_64bit"
7982 [(set (match_operand 0 "" "")
7983 (call (mem:SI (match_operand 1 "call_operand_address" ""))
7984 (match_operand 2 "" "i")))
7985 (clobber (reg:DI 1))
7986 (clobber (reg:DI 2))
7987 (clobber (match_operand 3))
7990 (use (const_int 0))]
7994 ;; Split out the PIC register save and restore after reload. As the
7995 ;; split is done after reload, there are some situations in which we
7996 ;; unnecessarily save and restore %r4. This happens when there is a
7997 ;; single call and the PIC register is not used after the call.
7999 ;; The split has to be done since call_from_call_insn () can't handle
8000 ;; the pattern as is. Noreturn calls are special because they have to
8001 ;; terminate the basic block. The split has to contain more than one
8004 [(parallel [(set (match_operand 0 "" "")
8005 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8006 (match_operand 2 "" "")))
8007 (clobber (reg:DI 1))
8008 (clobber (reg:DI 2))
8009 (clobber (match_operand 3))
8012 (use (const_int 0))])]
8013 "TARGET_64BIT && reload_completed
8014 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8015 [(set (match_dup 3) (reg:DI 27))
8016 (parallel [(set (match_dup 0)
8017 (call (mem:SI (match_dup 1))
8019 (clobber (reg:DI 1))
8020 (clobber (reg:DI 2))
8023 (use (const_int 0))])]
8027 [(parallel [(set (match_operand 0 "" "")
8028 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8029 (match_operand 2 "" "")))
8030 (clobber (reg:DI 1))
8031 (clobber (reg:DI 2))
8032 (clobber (match_operand 3))
8035 (use (const_int 0))])]
8036 "TARGET_64BIT && reload_completed"
8037 [(set (match_dup 3) (reg:DI 27))
8038 (parallel [(set (match_dup 0)
8039 (call (mem:SI (match_dup 1))
8041 (clobber (reg:DI 1))
8042 (clobber (reg:DI 2))
8045 (use (const_int 0))])
8046 (set (reg:DI 27) (match_dup 3))]
8049 (define_insn "*call_val_symref_64bit_post_reload"
8050 [(set (match_operand 0 "" "")
8051 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8052 (match_operand 2 "" "i")))
8053 (clobber (reg:DI 1))
8054 (clobber (reg:DI 2))
8057 (use (const_int 0))]
8061 pa_output_arg_descriptor (insn);
8062 return pa_output_call (insn, operands[1], 0);
8064 [(set_attr "type" "call")
8065 (set (attr "length")
8066 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8067 (symbol_ref "pa_attr_length_call (insn, 0)")))])
8069 ;; powf function clobbers %fr12
8070 (define_insn "call_val_powf_64bit"
8071 [(set (match_operand 0 "" "")
8072 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8073 (match_operand 2 "" "i")))
8074 (clobber (reg:DI 1))
8075 (clobber (reg:DI 2))
8076 (clobber (reg:DF 40))
8077 (clobber (match_operand 3))
8080 (use (const_int 1))]
8081 "TARGET_64BIT && TARGET_HPUX"
8084 ;; Split out the PIC register save and restore after reload. As the
8085 ;; split is done after reload, there are some situations in which we
8086 ;; unnecessarily save and restore %r4. This happens when there is a
8087 ;; single call and the PIC register is not used after the call.
8089 ;; The split has to be done since call_from_call_insn () can't handle
8090 ;; the pattern as is. Noreturn calls are special because they have to
8091 ;; terminate the basic block. The split has to contain more than one
8094 [(parallel [(set (match_operand 0 "" "")
8095 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8096 (match_operand 2 "" "")))
8097 (clobber (reg:DI 1))
8098 (clobber (reg:DI 2))
8099 (clobber (reg:DF 40))
8100 (clobber (match_operand 3))
8103 (use (const_int 1))])]
8104 "TARGET_64BIT && TARGET_HPUX && reload_completed
8105 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8106 [(set (match_dup 3) (reg:DI 27))
8107 (parallel [(set (match_dup 0)
8108 (call (mem:SI (match_dup 1))
8110 (clobber (reg:DI 1))
8111 (clobber (reg:DI 2))
8112 (clobber (reg:DF 40))
8115 (use (const_int 1))])]
8119 [(parallel [(set (match_operand 0 "" "")
8120 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8121 (match_operand 2 "" "")))
8122 (clobber (reg:DI 1))
8123 (clobber (reg:DI 2))
8124 (clobber (reg:DF 40))
8125 (clobber (match_operand 3))
8128 (use (const_int 1))])]
8129 "TARGET_64BIT && TARGET_HPUX && reload_completed"
8130 [(set (match_dup 3) (reg:DI 27))
8131 (parallel [(set (match_dup 0)
8132 (call (mem:SI (match_dup 1))
8134 (clobber (reg:DI 1))
8135 (clobber (reg:DI 2))
8136 (clobber (reg:DF 40))
8139 (use (const_int 1))])
8140 (set (reg:DI 27) (match_dup 3))]
8143 (define_insn "*call_val_powf_64bit_post_reload"
8144 [(set (match_operand 0 "" "")
8145 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8146 (match_operand 2 "" "i")))
8147 (clobber (reg:DI 1))
8148 (clobber (reg:DI 2))
8149 (clobber (reg:DF 40))
8152 (use (const_int 1))]
8153 "TARGET_64BIT && TARGET_HPUX"
8156 pa_output_arg_descriptor (insn);
8157 return pa_output_call (insn, operands[1], 0);
8159 [(set_attr "type" "call")
8160 (set (attr "length")
8161 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8162 (symbol_ref "pa_attr_length_call (insn, 0)")))])
8164 (define_insn "call_val_reg"
8165 [(set (match_operand 0 "" "")
8166 (call (mem:SI (reg:SI 22))
8167 (match_operand 1 "" "i")))
8168 (clobber (reg:SI 1))
8169 (clobber (reg:SI 2))
8170 (use (const_int 1))]
8174 return pa_output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
8176 [(set_attr "type" "dyncall")
8177 (set (attr "length")
8178 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8179 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
8181 ;; This pattern is split if it is necessary to save and restore the
8183 (define_insn "call_val_reg_pic"
8184 [(set (match_operand 0 "" "")
8185 (call (mem:SI (reg:SI 22))
8186 (match_operand 1 "" "i")))
8187 (clobber (reg:SI 1))
8188 (clobber (reg:SI 2))
8189 (clobber (match_operand 2))
8191 (use (const_int 1))]
8195 ;; Split out the PIC register save and restore after reload. As the
8196 ;; split is done after reload, there are some situations in which we
8197 ;; unnecessarily save and restore %r4. This happens when there is a
8198 ;; single call and the PIC register is not used after the call.
8200 ;; The split has to be done since call_from_call_insn () can't handle
8201 ;; the pattern as is. Noreturn calls are special because they have to
8202 ;; terminate the basic block. The split has to contain more than one
8205 [(parallel [(set (match_operand 0 "" "")
8206 (call (mem:SI (reg:SI 22))
8207 (match_operand 1 "" "")))
8208 (clobber (reg:SI 1))
8209 (clobber (reg:SI 2))
8210 (clobber (match_operand 2))
8212 (use (const_int 1))])]
8213 "!TARGET_64BIT && reload_completed
8214 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8215 [(set (match_dup 2) (reg:SI 19))
8216 (parallel [(set (match_dup 0)
8217 (call (mem:SI (reg:SI 22))
8219 (clobber (reg:SI 1))
8220 (clobber (reg:SI 2))
8222 (use (const_int 1))])]
8226 [(parallel [(set (match_operand 0 "" "")
8227 (call (mem:SI (reg:SI 22))
8228 (match_operand 1 "" "")))
8229 (clobber (reg:SI 1))
8230 (clobber (reg:SI 2))
8231 (clobber (match_operand 2))
8233 (use (const_int 1))])]
8234 "!TARGET_64BIT && reload_completed"
8235 [(set (match_dup 2) (reg:SI 19))
8236 (parallel [(set (match_dup 0)
8237 (call (mem:SI (reg:SI 22))
8239 (clobber (reg:SI 1))
8240 (clobber (reg:SI 2))
8242 (use (const_int 1))])
8243 (set (reg:SI 19) (match_dup 2))]
8246 (define_insn "*call_val_reg_pic_post_reload"
8247 [(set (match_operand 0 "" "")
8248 (call (mem:SI (reg:SI 22))
8249 (match_operand 1 "" "i")))
8250 (clobber (reg:SI 1))
8251 (clobber (reg:SI 2))
8253 (use (const_int 1))]
8257 return pa_output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
8259 [(set_attr "type" "dyncall")
8260 (set (attr "length")
8261 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8262 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
8264 ;; This pattern is split if it is necessary to save and restore the
8266 (define_insn "call_val_reg_64bit"
8267 [(set (match_operand 0 "" "")
8268 (call (mem:SI (match_operand:DI 1 "register_operand" "r"))
8269 (match_operand 2 "" "i")))
8270 (clobber (reg:DI 1))
8271 (clobber (reg:DI 2))
8272 (clobber (match_operand 3))
8275 (use (const_int 1))]
8279 ;; Split out the PIC register save and restore after reload. As the
8280 ;; split is done after reload, there are some situations in which we
8281 ;; unnecessarily save and restore %r4. This happens when there is a
8282 ;; single call and the PIC register is not used after the call.
8284 ;; The split has to be done since call_from_call_insn () can't handle
8285 ;; the pattern as is. Noreturn calls are special because they have to
8286 ;; terminate the basic block. The split has to contain more than one
8289 [(parallel [(set (match_operand 0 "" "")
8290 (call (mem:SI (match_operand:DI 1 "register_operand" ""))
8291 (match_operand 2 "" "")))
8292 (clobber (reg:DI 1))
8293 (clobber (reg:DI 2))
8294 (clobber (match_operand 3))
8297 (use (const_int 1))])]
8298 "TARGET_64BIT && reload_completed
8299 && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8300 [(set (match_dup 3) (reg:DI 27))
8301 (parallel [(set (match_dup 0)
8302 (call (mem:SI (match_dup 1))
8304 (clobber (reg:DI 1))
8305 (clobber (reg:DI 2))
8308 (use (const_int 1))])]
8312 [(parallel [(set (match_operand 0 "" "")
8313 (call (mem:SI (match_operand:DI 1 "register_operand" ""))
8314 (match_operand 2 "" "")))
8315 (clobber (reg:DI 1))
8316 (clobber (reg:DI 2))
8317 (clobber (match_operand 3))
8320 (use (const_int 1))])]
8321 "TARGET_64BIT && reload_completed"
8322 [(set (match_dup 3) (reg:DI 27))
8323 (parallel [(set (match_dup 0)
8324 (call (mem:SI (match_dup 1))
8326 (clobber (reg:DI 1))
8327 (clobber (reg:DI 2))
8330 (use (const_int 1))])
8331 (set (reg:DI 27) (match_dup 3))]
8334 (define_insn "*call_val_reg_64bit_post_reload"
8335 [(set (match_operand 0 "" "")
8336 (call (mem:SI (match_operand:DI 1 "register_operand" "r"))
8337 (match_operand 2 "" "i")))
8338 (clobber (reg:DI 1))
8339 (clobber (reg:DI 2))
8342 (use (const_int 1))]
8346 return pa_output_indirect_call (insn, operands[1]);
8348 [(set_attr "type" "dyncall")
8349 (set (attr "length")
8350 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 12)]
8351 (symbol_ref "pa_attr_length_indirect_call (insn)")))])
8353 ;; Call subroutine returning any type.
8355 (define_expand "untyped_call"
8356 [(parallel [(call (match_operand 0 "" "")
8358 (match_operand 1 "" "")
8359 (match_operand 2 "" "")])]
8365 emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
8367 for (i = 0; i < XVECLEN (operands[2], 0); i++)
8369 rtx set = XVECEXP (operands[2], 0, i);
8370 emit_move_insn (SET_DEST (set), SET_SRC (set));
8373 /* The optimizer does not know that the call sets the function value
8374 registers we stored in the result block. We avoid problems by
8375 claiming that all hard registers are used and clobbered at this
8377 emit_insn (gen_blockage ());
8382 (define_expand "sibcall"
8383 [(call (match_operand:SI 0 "" "")
8384 (match_operand 1 "" ""))]
8385 "!TARGET_PORTABLE_RUNTIME"
8389 rtx nb = operands[1];
8391 op = XEXP (operands[0], 0);
8395 if (!virtuals_instantiated)
8396 emit_move_insn (arg_pointer_rtx,
8397 gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
8401 /* The loop pass can generate new libcalls after the virtual
8402 registers are instantiated when fpregs are disabled because
8403 the only method that we have for doing DImode multiplication
8404 is with a libcall. This could be trouble if we haven't
8405 allocated enough space for the outgoing arguments. */
8406 gcc_assert (INTVAL (nb) <= crtl->outgoing_args_size);
8408 emit_move_insn (arg_pointer_rtx,
8409 gen_rtx_PLUS (word_mode, stack_pointer_rtx,
8410 GEN_INT (STACK_POINTER_OFFSET + 64)));
8414 /* Indirect sibling calls are not allowed. */
8416 call_insn = gen_sibcall_internal_symref_64bit (op, operands[1]);
8418 call_insn = gen_sibcall_internal_symref (op, operands[1]);
8420 call_insn = emit_call_insn (call_insn);
8423 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
8425 /* We don't have to restore the PIC register. */
8427 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
8432 (define_insn "sibcall_internal_symref"
8433 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
8434 (match_operand 1 "" "i"))
8435 (clobber (reg:SI 1))
8437 (use (const_int 0))]
8438 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8441 pa_output_arg_descriptor (insn);
8442 return pa_output_call (insn, operands[0], 1);
8444 [(set_attr "type" "sibcall")
8445 (set (attr "length")
8446 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8447 (symbol_ref "pa_attr_length_call (insn, 1)")))])
8449 (define_insn "sibcall_internal_symref_64bit"
8450 [(call (mem:SI (match_operand 0 "call_operand_address" ""))
8451 (match_operand 1 "" "i"))
8452 (clobber (reg:DI 1))
8454 (use (const_int 0))]
8458 pa_output_arg_descriptor (insn);
8459 return pa_output_call (insn, operands[0], 1);
8461 [(set_attr "type" "sibcall")
8462 (set (attr "length")
8463 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8464 (symbol_ref "pa_attr_length_call (insn, 1)")))])
8466 (define_expand "sibcall_value"
8467 [(set (match_operand 0 "" "")
8468 (call (match_operand:SI 1 "" "")
8469 (match_operand 2 "" "")))]
8470 "!TARGET_PORTABLE_RUNTIME"
8474 rtx nb = operands[1];
8476 op = XEXP (operands[1], 0);
8480 if (!virtuals_instantiated)
8481 emit_move_insn (arg_pointer_rtx,
8482 gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
8486 /* The loop pass can generate new libcalls after the virtual
8487 registers are instantiated when fpregs are disabled because
8488 the only method that we have for doing DImode multiplication
8489 is with a libcall. This could be trouble if we haven't
8490 allocated enough space for the outgoing arguments. */
8491 gcc_assert (INTVAL (nb) <= crtl->outgoing_args_size);
8493 emit_move_insn (arg_pointer_rtx,
8494 gen_rtx_PLUS (word_mode, stack_pointer_rtx,
8495 GEN_INT (STACK_POINTER_OFFSET + 64)));
8499 /* Indirect sibling calls are not allowed. */
8502 = gen_sibcall_value_internal_symref_64bit (operands[0], op, operands[2]);
8505 = gen_sibcall_value_internal_symref (operands[0], op, operands[2]);
8507 call_insn = emit_call_insn (call_insn);
8510 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
8512 /* We don't have to restore the PIC register. */
8514 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
8519 (define_insn "sibcall_value_internal_symref"
8520 [(set (match_operand 0 "" "")
8521 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8522 (match_operand 2 "" "i")))
8523 (clobber (reg:SI 1))
8525 (use (const_int 0))]
8526 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8529 pa_output_arg_descriptor (insn);
8530 return pa_output_call (insn, operands[1], 1);
8532 [(set_attr "type" "sibcall")
8533 (set (attr "length")
8534 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8535 (symbol_ref "pa_attr_length_call (insn, 1)")))])
8537 (define_insn "sibcall_value_internal_symref_64bit"
8538 [(set (match_operand 0 "" "")
8539 (call (mem:SI (match_operand 1 "call_operand_address" ""))
8540 (match_operand 2 "" "i")))
8541 (clobber (reg:DI 1))
8543 (use (const_int 0))]
8547 pa_output_arg_descriptor (insn);
8548 return pa_output_call (insn, operands[1], 1);
8550 [(set_attr "type" "sibcall")
8551 (set (attr "length")
8552 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 8)]
8553 (symbol_ref "pa_attr_length_call (insn, 1)")))])
8559 [(set_attr "type" "move")
8560 (set_attr "length" "4")])
8562 ;;; EH does longjmp's from and within the data section. Thus,
8563 ;;; an interspace branch is required for the longjmp implementation.
8564 ;;; Registers r1 and r2 are used as scratch registers for the jump
8566 (define_expand "interspace_jump"
8568 [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8569 (clobber (match_dup 1))])]
8573 operands[1] = gen_rtx_REG (word_mode, 2);
8577 [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8578 (clobber (reg:SI 2))]
8579 "TARGET_PA_20 && !TARGET_64BIT"
8581 [(set_attr "type" "branch")
8582 (set_attr "length" "4")])
8585 [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8586 (clobber (reg:SI 2))]
8587 "TARGET_NO_SPACE_REGS && !TARGET_64BIT"
8589 [(set_attr "type" "branch")
8590 (set_attr "length" "4")])
8593 [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8594 (clobber (reg:SI 2))]
8596 "ldsid (%%sr0,%0),%%r2\;mtsp %%r2,%%sr0\;be%* 0(%%sr0,%0)"
8597 [(set_attr "type" "branch")
8598 (set_attr "length" "12")])
8601 [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8602 (clobber (reg:DI 2))]
8605 [(set_attr "type" "branch")
8606 (set_attr "length" "4")])
8608 (define_expand "builtin_longjmp"
8609 [(unspec_volatile [(match_operand 0 "register_operand" "r")] UNSPECV_LONGJMP)]
8613 /* The elements of the buffer are, in order: */
8614 rtx fp = gen_rtx_MEM (Pmode, operands[0]);
8615 rtx lab = gen_rtx_MEM (Pmode, plus_constant (Pmode, operands[0],
8616 POINTER_SIZE / BITS_PER_UNIT));
8617 rtx stack = gen_rtx_MEM (Pmode, plus_constant (Pmode, operands[0],
8618 (POINTER_SIZE * 2) / BITS_PER_UNIT));
8619 rtx pv = gen_rtx_REG (Pmode, 1);
8621 emit_clobber (gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode)));
8622 emit_clobber (gen_rtx_MEM (BLKmode, hard_frame_pointer_rtx));
8624 /* Restore the frame pointer. The virtual_stack_vars_rtx is saved
8625 instead of the hard_frame_pointer_rtx in the save area. We need
8626 to adjust for the offset between these two values. */
8627 if (GET_CODE (fp) != REG)
8628 fp = force_reg (Pmode, fp);
8629 emit_move_insn (hard_frame_pointer_rtx, plus_constant (Pmode, fp, -8));
8631 /* This bit is the same as expand_builtin_longjmp. */
8632 emit_stack_restore (SAVE_NONLOCAL, stack);
8633 emit_use (hard_frame_pointer_rtx);
8634 emit_use (stack_pointer_rtx);
8636 /* Load the label we are jumping through into r1 so that we know
8637 where to look for it when we get back to setjmp's function for
8638 restoring the gp. */
8639 emit_move_insn (pv, lab);
8641 /* Prevent the insns above from being scheduled into the delay slot
8642 of the interspace jump because the space register could change. */
8643 emit_insn (gen_blockage ());
8645 emit_jump_insn (gen_interspace_jump (pv));
8650 ;;; Operands 2 and 3 are assumed to be CONST_INTs.
8651 (define_expand "extzvsi"
8652 [(set (match_operand:SI 0 "register_operand" "")
8653 (zero_extract:SI (match_operand:SI 1 "register_operand" "")
8654 (match_operand:SI 2 "uint5_operand" "")
8655 (match_operand:SI 3 "uint5_operand" "")))]
8659 unsigned HOST_WIDE_INT len = UINTVAL (operands[2]);
8660 unsigned HOST_WIDE_INT pos = UINTVAL (operands[3]);
8662 /* PA extraction insns don't support zero length bitfields or fields
8663 extending beyond the left or right-most bits. Also, the predicate
8664 rejects lengths equal to a word as they are better handled by
8665 the move patterns. */
8666 if (len == 0 || pos + len > 32)
8669 /* From mips.md: extract_bit_field doesn't verify that our source
8670 matches the predicate, so check it again here. */
8671 if (!register_operand (operands[1], VOIDmode))
8674 emit_insn (gen_extzv_32 (operands[0], operands[1],
8675 operands[2], operands[3]));
8679 (define_insn "extzv_32"
8680 [(set (match_operand:SI 0 "register_operand" "=r")
8681 (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
8682 (match_operand:SI 2 "uint5_operand" "")
8683 (match_operand:SI 3 "uint5_operand" "")))]
8684 "UINTVAL (operands[2]) > 0
8685 && UINTVAL (operands[2]) + UINTVAL (operands[3]) <= 32"
8686 "{extru|extrw,u} %1,%3+%2-1,%2,%0"
8687 [(set_attr "type" "shift")
8688 (set_attr "length" "4")])
8691 [(set (match_operand:SI 0 "register_operand" "=r")
8692 (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
8694 (match_operand:SI 2 "register_operand" "q")))]
8696 "{vextru %1,1,%0|extrw,u %1,%%sar,1,%0}"
8697 [(set_attr "type" "shift")
8698 (set_attr "length" "4")])
8700 (define_expand "extzvdi"
8701 [(set (match_operand:DI 0 "register_operand" "")
8702 (zero_extract:DI (match_operand:DI 1 "register_operand" "")
8703 (match_operand:DI 2 "uint6_operand" "")
8704 (match_operand:DI 3 "uint6_operand" "")))]
8708 unsigned HOST_WIDE_INT len = UINTVAL (operands[2]);
8709 unsigned HOST_WIDE_INT pos = UINTVAL (operands[3]);
8711 /* PA extraction insns don't support zero length bitfields or fields
8712 extending beyond the left or right-most bits. Also, the predicate
8713 rejects lengths equal to a doubleword as they are better handled by
8714 the move patterns. */
8715 if (len == 0 || pos + len > 64)
8718 /* From mips.md: extract_bit_field doesn't verify that our source
8719 matches the predicate, so check it again here. */
8720 if (!register_operand (operands[1], VOIDmode))
8723 emit_insn (gen_extzv_64 (operands[0], operands[1],
8724 operands[2], operands[3]));
8728 (define_insn "extzv_64"
8729 [(set (match_operand:DI 0 "register_operand" "=r")
8730 (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
8731 (match_operand:DI 2 "uint6_operand" "")
8732 (match_operand:DI 3 "uint6_operand" "")))]
8734 && UINTVAL (operands[2]) > 0
8735 && UINTVAL (operands[2]) + UINTVAL (operands[3]) <= 64"
8736 "extrd,u %1,%3+%2-1,%2,%0"
8737 [(set_attr "type" "shift")
8738 (set_attr "length" "4")])
8741 [(set (match_operand:DI 0 "register_operand" "=r")
8742 (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
8744 (match_operand:DI 2 "register_operand" "q")))]
8746 "extrd,u %1,%%sar,1,%0"
8747 [(set_attr "type" "shift")
8748 (set_attr "length" "4")])
8750 ;;; Operands 2 and 3 are assumed to be CONST_INTs.
8751 (define_expand "extvsi"
8752 [(set (match_operand:SI 0 "register_operand" "")
8753 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
8754 (match_operand:SI 2 "uint5_operand" "")
8755 (match_operand:SI 3 "uint5_operand" "")))]
8759 unsigned HOST_WIDE_INT len = UINTVAL (operands[2]);
8760 unsigned HOST_WIDE_INT pos = UINTVAL (operands[3]);
8762 /* PA extraction insns don't support zero length bitfields or fields
8763 extending beyond the left or right-most bits. Also, the predicate
8764 rejects lengths equal to a word as they are better handled by
8765 the move patterns. */
8766 if (len == 0 || pos + len > 32)
8769 /* From mips.md: extract_bit_field doesn't verify that our source
8770 matches the predicate, so check it again here. */
8771 if (!register_operand (operands[1], VOIDmode))
8774 emit_insn (gen_extv_32 (operands[0], operands[1],
8775 operands[2], operands[3]));
8779 (define_insn "extv_32"
8780 [(set (match_operand:SI 0 "register_operand" "=r")
8781 (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
8782 (match_operand:SI 2 "uint5_operand" "")
8783 (match_operand:SI 3 "uint5_operand" "")))]
8784 "UINTVAL (operands[2]) > 0
8785 && UINTVAL (operands[2]) + UINTVAL (operands[3]) <= 32"
8786 "{extrs|extrw,s} %1,%3+%2-1,%2,%0"
8787 [(set_attr "type" "shift")
8788 (set_attr "length" "4")])
8791 [(set (match_operand:SI 0 "register_operand" "=r")
8792 (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
8794 (match_operand:SI 2 "register_operand" "q")))]
8796 "{vextrs %1,1,%0|extrw,s %1,%%sar,1,%0}"
8797 [(set_attr "type" "shift")
8798 (set_attr "length" "4")])
8800 (define_expand "extvdi"
8801 [(set (match_operand:DI 0 "register_operand" "")
8802 (sign_extract:DI (match_operand:DI 1 "register_operand" "")
8803 (match_operand:DI 2 "uint6_operand" "")
8804 (match_operand:DI 3 "uint6_operand" "")))]
8808 unsigned HOST_WIDE_INT len = UINTVAL (operands[2]);
8809 unsigned HOST_WIDE_INT pos = UINTVAL (operands[3]);
8811 /* PA extraction insns don't support zero length bitfields or fields
8812 extending beyond the left or right-most bits. Also, the predicate
8813 rejects lengths equal to a doubleword as they are better handled by
8814 the move patterns. */
8815 if (len == 0 || pos + len > 64)
8818 /* From mips.md: extract_bit_field doesn't verify that our source
8819 matches the predicate, so check it again here. */
8820 if (!register_operand (operands[1], VOIDmode))
8823 emit_insn (gen_extv_64 (operands[0], operands[1],
8824 operands[2], operands[3]));
8828 (define_insn "extv_64"
8829 [(set (match_operand:DI 0 "register_operand" "=r")
8830 (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
8831 (match_operand:DI 2 "uint6_operand" "")
8832 (match_operand:DI 3 "uint6_operand" "")))]
8834 && UINTVAL (operands[2]) > 0
8835 && UINTVAL (operands[2]) + UINTVAL (operands[3]) <= 64"
8836 "extrd,s %1,%3+%2-1,%2,%0"
8837 [(set_attr "type" "shift")
8838 (set_attr "length" "4")])
8841 [(set (match_operand:DI 0 "register_operand" "=r")
8842 (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
8844 (match_operand:DI 2 "register_operand" "q")))]
8846 "extrd,s %1,%%sar,1,%0"
8847 [(set_attr "type" "shift")
8848 (set_attr "length" "4")])
8850 ;;; Operands 1 and 2 are assumed to be CONST_INTs.
8851 (define_expand "insvsi"
8852 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "")
8853 (match_operand:SI 1 "uint5_operand" "")
8854 (match_operand:SI 2 "uint5_operand" ""))
8855 (match_operand:SI 3 "arith5_operand" ""))]
8859 unsigned HOST_WIDE_INT len = UINTVAL (operands[1]);
8860 unsigned HOST_WIDE_INT pos = UINTVAL (operands[2]);
8862 /* PA insertion insns don't support zero length bitfields or fields
8863 extending beyond the left or right-most bits. Also, the predicate
8864 rejects lengths equal to a word as they are better handled by
8865 the move patterns. */
8866 if (len <= 0 || pos + len > 32)
8869 /* From mips.md: insert_bit_field doesn't verify that our destination
8870 matches the predicate, so check it again here. */
8871 if (!register_operand (operands[0], VOIDmode))
8874 emit_insn (gen_insv_32 (operands[0], operands[1],
8875 operands[2], operands[3]));
8879 (define_insn "insv_32"
8880 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r,r")
8881 (match_operand:SI 1 "uint5_operand" "")
8882 (match_operand:SI 2 "uint5_operand" ""))
8883 (match_operand:SI 3 "arith5_operand" "r,L"))]
8884 "UINTVAL (operands[1]) > 0
8885 && UINTVAL (operands[1]) + UINTVAL (operands[2]) <= 32"
8887 {dep|depw} %3,%2+%1-1,%1,%0
8888 {depi|depwi} %3,%2+%1-1,%1,%0"
8889 [(set_attr "type" "shift,shift")
8890 (set_attr "length" "4,4")])
8892 ;; Optimize insertion of const_int values of type 1...1xxxx.
8894 [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
8895 (match_operand:SI 1 "uint5_operand" "")
8896 (match_operand:SI 2 "uint5_operand" ""))
8897 (match_operand:SI 3 "const_int_operand" ""))]
8898 "(INTVAL (operands[3]) & 0x10) != 0 &&
8899 (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
8902 operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
8903 return \"{depi|depwi} %3,%2+%1-1,%1,%0\";
8905 [(set_attr "type" "shift")
8906 (set_attr "length" "4")])
8908 (define_expand "insvdi"
8909 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "")
8910 (match_operand:DI 1 "uint6_operand" "")
8911 (match_operand:DI 2 "uint6_operand" ""))
8912 (match_operand:DI 3 "arith5_operand" ""))]
8916 unsigned HOST_WIDE_INT len = UINTVAL (operands[1]);
8917 unsigned HOST_WIDE_INT pos = UINTVAL (operands[2]);
8919 /* PA insertion insns don't support zero length bitfields or fields
8920 extending beyond the left or right-most bits. Also, the predicate
8921 rejects lengths equal to a doubleword as they are better handled by
8922 the move patterns. */
8923 if (len <= 0 || pos + len > 64)
8926 /* From mips.md: insert_bit_field doesn't verify that our destination
8927 matches the predicate, so check it again here. */
8928 if (!register_operand (operands[0], VOIDmode))
8931 emit_insn (gen_insv_64 (operands[0], operands[1],
8932 operands[2], operands[3]));
8936 (define_insn "insv_64"
8937 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r,r")
8938 (match_operand:DI 1 "uint6_operand" "")
8939 (match_operand:DI 2 "uint6_operand" ""))
8940 (match_operand:DI 3 "arith5_operand" "r,L"))]
8942 && UINTVAL (operands[1]) > 0
8943 && UINTVAL (operands[1]) + UINTVAL (operands[2]) <= 64"
8945 depd %3,%2+%1-1,%1,%0
8946 depdi %3,%2+%1-1,%1,%0"
8947 [(set_attr "type" "shift,shift")
8948 (set_attr "length" "4,4")])
8950 ;; Optimize insertion of const_int values of type 1...1xxxx.
8952 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
8953 (match_operand:DI 1 "uint6_operand" "")
8954 (match_operand:DI 2 "uint6_operand" ""))
8955 (match_operand:DI 3 "const_int_operand" ""))]
8956 "(INTVAL (operands[3]) & 0x10) != 0
8958 && (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
8961 operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
8962 return \"depdi %3,%2+%1-1,%1,%0\";
8964 [(set_attr "type" "shift")
8965 (set_attr "length" "4")])
8968 [(set (match_operand:DI 0 "register_operand" "=r")
8969 (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
8972 "depd,z %1,31,32,%0"
8973 [(set_attr "type" "shift")
8974 (set_attr "length" "4")])
8976 ;; This insn is used for some loop tests, typically loops reversed when
8977 ;; strength reduction is used. It is actually created when the instruction
8978 ;; combination phase combines the special loop test. Since this insn
8979 ;; is both a jump insn and has an output, it must deal with its own
8980 ;; reloads, hence the `Q' constraints. The `!' constraints direct reload
8981 ;; to not choose the register alternatives in the event a reload is needed.
8982 (define_insn "decrement_and_branch_until_zero"
8985 (match_operator 2 "comparison_operator"
8987 (match_operand:SI 0 "reg_before_reload_operand" "+!r,!*f,*Q")
8988 (match_operand:SI 1 "int5_operand" "L,L,L"))
8990 (label_ref (match_operand 3 "" ""))
8993 (plus:SI (match_dup 0) (match_dup 1)))
8994 (clobber (match_scratch:SI 4 "=X,r,r"))]
8996 "* return pa_output_dbra (operands, insn, which_alternative); "
8997 ;; Do not expect to understand this the first time through.
8998 [(set_attr "type" "cbranch,multi,multi")
8999 (set (attr "length")
9000 (if_then_else (eq_attr "alternative" "0")
9001 ;; Loop counter in register case
9002 ;; Short branch has length of 4
9003 ;; Long branch has length of 8, 20, 24 or 28
9004 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9005 (const_int MAX_12BIT_OFFSET))
9007 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9008 (const_int MAX_17BIT_OFFSET))
9010 (match_test "TARGET_PORTABLE_RUNTIME")
9012 (not (match_test "flag_pic"))
9016 ;; Loop counter in FP reg case.
9017 ;; Extra goo to deal with additional reload insns.
9018 (if_then_else (eq_attr "alternative" "1")
9019 (if_then_else (lt (match_dup 3) (pc))
9020 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 24))))
9021 (const_int MAX_12BIT_OFFSET))
9023 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 24))))
9024 (const_int MAX_17BIT_OFFSET))
9026 (match_test "TARGET_PORTABLE_RUNTIME")
9028 (not (match_test "flag_pic"))
9031 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9032 (const_int MAX_12BIT_OFFSET))
9034 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9035 (const_int MAX_17BIT_OFFSET))
9037 (match_test "TARGET_PORTABLE_RUNTIME")
9039 (not (match_test "flag_pic"))
9043 ;; Loop counter in memory case.
9044 ;; Extra goo to deal with additional reload insns.
9045 (if_then_else (lt (match_dup 3) (pc))
9046 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9047 (const_int MAX_12BIT_OFFSET))
9049 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9050 (const_int MAX_17BIT_OFFSET))
9052 (match_test "TARGET_PORTABLE_RUNTIME")
9054 (not (match_test "flag_pic"))
9057 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9058 (const_int MAX_12BIT_OFFSET))
9060 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9061 (const_int MAX_17BIT_OFFSET))
9063 (match_test "TARGET_PORTABLE_RUNTIME")
9065 (not (match_test "flag_pic"))
9067 (const_int 36))))))])
9072 (match_operator 2 "movb_comparison_operator"
9073 [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
9074 (label_ref (match_operand 3 "" ""))
9076 (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*Q,!*q")
9079 "* return pa_output_movb (operands, insn, which_alternative, 0); "
9080 ;; Do not expect to understand this the first time through.
9081 [(set_attr "type" "cbranch,multi,multi,multi")
9082 (set (attr "length")
9083 (if_then_else (eq_attr "alternative" "0")
9084 ;; Loop counter in register case
9085 ;; Short branch has length of 4
9086 ;; Long branch has length of 8, 20, 24 or 28
9087 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9088 (const_int MAX_12BIT_OFFSET))
9090 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9091 (const_int MAX_17BIT_OFFSET))
9093 (match_test "TARGET_PORTABLE_RUNTIME")
9095 (not (match_test "flag_pic"))
9099 ;; Loop counter in FP reg case.
9100 ;; Extra goo to deal with additional reload insns.
9101 (if_then_else (eq_attr "alternative" "1")
9102 (if_then_else (lt (match_dup 3) (pc))
9103 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9104 (const_int MAX_12BIT_OFFSET))
9106 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9107 (const_int MAX_17BIT_OFFSET))
9109 (match_test "TARGET_PORTABLE_RUNTIME")
9111 (not (match_test "flag_pic"))
9114 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9115 (const_int MAX_12BIT_OFFSET))
9117 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9118 (const_int MAX_17BIT_OFFSET))
9120 (match_test "TARGET_PORTABLE_RUNTIME")
9122 (not (match_test "flag_pic"))
9126 ;; Loop counter in memory or sar case.
9127 ;; Extra goo to deal with additional reload insns.
9128 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9129 (const_int MAX_12BIT_OFFSET))
9131 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9132 (const_int MAX_17BIT_OFFSET))
9134 (match_test "TARGET_PORTABLE_RUNTIME")
9136 (not (match_test "flag_pic"))
9138 (const_int 32)))))])
9140 ;; Handle negated branch.
9144 (match_operator 2 "movb_comparison_operator"
9145 [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
9147 (label_ref (match_operand 3 "" ""))))
9148 (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*Q,!*q")
9151 "* return pa_output_movb (operands, insn, which_alternative, 1); "
9152 ;; Do not expect to understand this the first time through.
9153 [(set_attr "type" "cbranch,multi,multi,multi")
9154 (set (attr "length")
9155 (if_then_else (eq_attr "alternative" "0")
9156 ;; Loop counter in register case
9157 ;; Short branch has length of 4
9158 ;; Long branch has length of 8
9159 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9160 (const_int MAX_12BIT_OFFSET))
9162 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9163 (const_int MAX_17BIT_OFFSET))
9165 (match_test "TARGET_PORTABLE_RUNTIME")
9167 (not (match_test "flag_pic"))
9171 ;; Loop counter in FP reg case.
9172 ;; Extra goo to deal with additional reload insns.
9173 (if_then_else (eq_attr "alternative" "1")
9174 (if_then_else (lt (match_dup 3) (pc))
9175 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9176 (const_int MAX_12BIT_OFFSET))
9178 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9179 (const_int MAX_17BIT_OFFSET))
9181 (match_test "TARGET_PORTABLE_RUNTIME")
9183 (not (match_test "flag_pic"))
9186 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9187 (const_int MAX_12BIT_OFFSET))
9189 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9190 (const_int MAX_17BIT_OFFSET))
9192 (match_test "TARGET_PORTABLE_RUNTIME")
9194 (not (match_test "flag_pic"))
9198 ;; Loop counter in memory or SAR case.
9199 ;; Extra goo to deal with additional reload insns.
9200 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9201 (const_int MAX_12BIT_OFFSET))
9203 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9204 (const_int MAX_17BIT_OFFSET))
9206 (match_test "TARGET_PORTABLE_RUNTIME")
9208 (not (match_test "flag_pic"))
9210 (const_int 32)))))])
9213 [(set (pc) (label_ref (match_operand 3 "" "" )))
9214 (set (match_operand:SI 0 "ireg_operand" "=r")
9215 (plus:SI (match_operand:SI 1 "ireg_operand" "r")
9216 (match_operand:SI 2 "ireg_or_int5_operand" "rL")))]
9217 "(reload_completed && operands[0] == operands[1]) || operands[0] == operands[2]"
9220 return pa_output_parallel_addb (operands, insn);
9222 [(set_attr "type" "parallel_branch")
9223 (set (attr "length")
9224 (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9225 (const_int MAX_12BIT_OFFSET))
9227 (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9228 (const_int MAX_17BIT_OFFSET))
9230 (match_test "TARGET_PORTABLE_RUNTIME")
9232 (not (match_test "flag_pic"))
9237 [(set (pc) (label_ref (match_operand 2 "" "" )))
9238 (set (match_operand:SF 0 "ireg_operand" "=r")
9239 (match_operand:SF 1 "ireg_or_int5_operand" "rL"))]
9243 return pa_output_parallel_movb (operands, insn);
9245 [(set_attr "type" "parallel_branch")
9246 (set (attr "length")
9247 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9248 (const_int MAX_12BIT_OFFSET))
9250 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9251 (const_int MAX_17BIT_OFFSET))
9253 (match_test "TARGET_PORTABLE_RUNTIME")
9255 (not (match_test "flag_pic"))
9260 [(set (pc) (label_ref (match_operand 2 "" "" )))
9261 (set (match_operand:SI 0 "ireg_operand" "=r")
9262 (match_operand:SI 1 "ireg_or_int5_operand" "rL"))]
9266 return pa_output_parallel_movb (operands, insn);
9268 [(set_attr "type" "parallel_branch")
9269 (set (attr "length")
9270 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9271 (const_int MAX_12BIT_OFFSET))
9273 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9274 (const_int MAX_17BIT_OFFSET))
9276 (match_test "TARGET_PORTABLE_RUNTIME")
9278 (not (match_test "flag_pic"))
9283 [(set (pc) (label_ref (match_operand 2 "" "" )))
9284 (set (match_operand:HI 0 "ireg_operand" "=r")
9285 (match_operand:HI 1 "ireg_or_int5_operand" "rL"))]
9289 return pa_output_parallel_movb (operands, insn);
9291 [(set_attr "type" "parallel_branch")
9292 (set (attr "length")
9293 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9294 (const_int MAX_12BIT_OFFSET))
9296 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9297 (const_int MAX_17BIT_OFFSET))
9299 (match_test "TARGET_PORTABLE_RUNTIME")
9301 (not (match_test "flag_pic"))
9306 [(set (pc) (label_ref (match_operand 2 "" "" )))
9307 (set (match_operand:QI 0 "ireg_operand" "=r")
9308 (match_operand:QI 1 "ireg_or_int5_operand" "rL"))]
9312 return pa_output_parallel_movb (operands, insn);
9314 [(set_attr "type" "parallel_branch")
9315 (set (attr "length")
9316 (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9317 (const_int MAX_12BIT_OFFSET))
9319 (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9320 (const_int MAX_17BIT_OFFSET))
9322 (match_test "TARGET_PORTABLE_RUNTIME")
9324 (not (match_test "flag_pic"))
9329 [(set (match_operand 0 "register_operand" "=f")
9330 (mult (match_operand 1 "register_operand" "f")
9331 (match_operand 2 "register_operand" "f")))
9332 (set (match_operand 3 "register_operand" "+f")
9333 (plus (match_operand 4 "register_operand" "f")
9334 (match_operand 5 "register_operand" "f")))]
9335 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9336 && reload_completed && pa_fmpyaddoperands (operands)"
9339 if (GET_MODE (operands[0]) == DFmode)
9341 if (rtx_equal_p (operands[3], operands[5]))
9342 return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
9344 return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
9348 if (rtx_equal_p (operands[3], operands[5]))
9349 return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
9351 return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
9354 [(set_attr "type" "fpalu")
9355 (set_attr "length" "4")])
9358 [(set (match_operand 3 "register_operand" "+f")
9359 (plus (match_operand 4 "register_operand" "f")
9360 (match_operand 5 "register_operand" "f")))
9361 (set (match_operand 0 "register_operand" "=f")
9362 (mult (match_operand 1 "register_operand" "f")
9363 (match_operand 2 "register_operand" "f")))]
9364 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9365 && reload_completed && pa_fmpyaddoperands (operands)"
9368 if (GET_MODE (operands[0]) == DFmode)
9370 if (rtx_equal_p (operands[3], operands[5]))
9371 return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
9373 return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
9377 if (rtx_equal_p (operands[3], operands[5]))
9378 return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
9380 return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
9383 [(set_attr "type" "fpalu")
9384 (set_attr "length" "4")])
9387 [(set (match_operand 0 "register_operand" "=f")
9388 (mult (match_operand 1 "register_operand" "f")
9389 (match_operand 2 "register_operand" "f")))
9390 (set (match_operand 3 "register_operand" "+f")
9391 (minus (match_operand 4 "register_operand" "f")
9392 (match_operand 5 "register_operand" "f")))]
9393 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9394 && reload_completed && pa_fmpysuboperands (operands)"
9397 if (GET_MODE (operands[0]) == DFmode)
9398 return \"fmpysub,dbl %1,%2,%0,%5,%3\";
9400 return \"fmpysub,sgl %1,%2,%0,%5,%3\";
9402 [(set_attr "type" "fpalu")
9403 (set_attr "length" "4")])
9406 [(set (match_operand 3 "register_operand" "+f")
9407 (minus (match_operand 4 "register_operand" "f")
9408 (match_operand 5 "register_operand" "f")))
9409 (set (match_operand 0 "register_operand" "=f")
9410 (mult (match_operand 1 "register_operand" "f")
9411 (match_operand 2 "register_operand" "f")))]
9412 "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9413 && reload_completed && pa_fmpysuboperands (operands)"
9416 if (GET_MODE (operands[0]) == DFmode)
9417 return \"fmpysub,dbl %1,%2,%0,%5,%3\";
9419 return \"fmpysub,sgl %1,%2,%0,%5,%3\";
9421 [(set_attr "type" "fpalu")
9422 (set_attr "length" "4")])
9424 ;; The following two patterns are used by the trampoline code for nested
9425 ;; functions. They flush the I and D cache lines from the start address
9426 ;; (operand0) to the end address (operand1). No lines are flushed if the
9427 ;; end address is less than the start address (unsigned).
9429 ;; Because the range of memory flushed is variable and the size of a MEM
9430 ;; can only be a CONST_INT, the patterns specify that they perform an
9431 ;; unspecified volatile operation on all memory.
9433 ;; The address range for an icache flush must lie within a single
9434 ;; space on targets with non-equivalent space registers.
9436 ;; Operand 0 contains the start address.
9437 ;; Operand 1 contains the end address.
9438 ;; Operand 2 contains the line length to use.
9439 (define_insn "dcacheflush<P:mode>"
9441 (unspec_volatile [(mem:BLK (scratch))] UNSPECV_DCACHE)
9442 (use (match_operand 0 "pmode_register_operand" "r"))
9443 (use (match_operand 1 "pmode_register_operand" "r"))
9444 (use (match_operand 2 "pmode_register_operand" "r"))
9445 (clobber (match_scratch:P 3 "=&0"))]
9447 "cmpb,<dwc><<=,n %3,%1,.\;fdc,m %2(%3)\;sync"
9448 [(set_attr "type" "multi")
9449 (set_attr "length" "12")])
9451 (define_insn "icacheflush<P:mode>"
9453 (unspec_volatile [(mem:BLK (scratch))] UNSPECV_ICACHE)
9454 (use (match_operand 0 "pmode_register_operand" "r"))
9455 (use (match_operand 1 "pmode_register_operand" "r"))
9456 (use (match_operand 2 "pmode_register_operand" "r"))
9457 (clobber (match_operand 3 "pmode_register_operand" "=&r"))
9458 (clobber (match_operand 4 "pmode_register_operand" "=&r"))
9459 (clobber (match_scratch:P 5 "=&0"))]
9461 "mfsp %%sr0,%4\;ldsid (%5),%3\;mtsp %3,%%sr0\;cmpb,<dwc><<=,n %5,%1,.\;fic,m %2(%%sr0,%5)\;sync\;mtsp %4,%%sr0\;nop\;nop\;nop\;nop\;nop\;nop"
9462 [(set_attr "type" "multi")
9463 (set_attr "length" "52")])
9465 ;; An out-of-line prologue.
9466 (define_insn "outline_prologue_call"
9467 [(unspec_volatile [(const_int 0)] UNSPECV_OPC)
9468 (clobber (reg:SI 31))
9469 (clobber (reg:SI 22))
9470 (clobber (reg:SI 21))
9471 (clobber (reg:SI 20))
9472 (clobber (reg:SI 19))
9473 (clobber (reg:SI 1))]
9478 /* We need two different versions depending on whether or not we
9479 need a frame pointer. Also note that we return to the instruction
9480 immediately after the branch rather than two instructions after the
9481 break as normally is the case. */
9482 if (frame_pointer_needed)
9484 /* Must import the magic millicode routine(s). */
9485 output_asm_insn (\".IMPORT __outline_prologue_fp,MILLICODE\", NULL);
9487 if (TARGET_PORTABLE_RUNTIME)
9489 output_asm_insn (\"ldil L'__outline_prologue_fp,%%r31\", NULL);
9490 output_asm_insn (\"ble,n R'__outline_prologue_fp(%%sr0,%%r31)\",
9494 output_asm_insn (\"{bl|b,l},n __outline_prologue_fp,%%r31\", NULL);
9498 /* Must import the magic millicode routine(s). */
9499 output_asm_insn (\".IMPORT __outline_prologue,MILLICODE\", NULL);
9501 if (TARGET_PORTABLE_RUNTIME)
9503 output_asm_insn (\"ldil L'__outline_prologue,%%r31\", NULL);
9504 output_asm_insn (\"ble,n R'__outline_prologue(%%sr0,%%r31)\", NULL);
9507 output_asm_insn (\"{bl|b,l},n __outline_prologue,%%r31\", NULL);
9511 [(set_attr "type" "multi")
9512 (set_attr "length" "8")])
9514 ;; An out-of-line epilogue.
9515 (define_insn "outline_epilogue_call"
9516 [(unspec_volatile [(const_int 1)] UNSPECV_OEC)
9519 (clobber (reg:SI 31))
9520 (clobber (reg:SI 22))
9521 (clobber (reg:SI 21))
9522 (clobber (reg:SI 20))
9523 (clobber (reg:SI 19))
9524 (clobber (reg:SI 2))
9525 (clobber (reg:SI 1))]
9530 /* We need two different versions depending on whether or not we
9531 need a frame pointer. Also note that we return to the instruction
9532 immediately after the branch rather than two instructions after the
9533 break as normally is the case. */
9534 if (frame_pointer_needed)
9536 /* Must import the magic millicode routine. */
9537 output_asm_insn (\".IMPORT __outline_epilogue_fp,MILLICODE\", NULL);
9539 /* The out-of-line prologue will make sure we return to the right
9541 if (TARGET_PORTABLE_RUNTIME)
9543 output_asm_insn (\"ldil L'__outline_epilogue_fp,%%r31\", NULL);
9544 output_asm_insn (\"ble,n R'__outline_epilogue_fp(%%sr0,%%r31)\",
9548 output_asm_insn (\"{bl|b,l},n __outline_epilogue_fp,%%r31\", NULL);
9552 /* Must import the magic millicode routine. */
9553 output_asm_insn (\".IMPORT __outline_epilogue,MILLICODE\", NULL);
9555 /* The out-of-line prologue will make sure we return to the right
9557 if (TARGET_PORTABLE_RUNTIME)
9559 output_asm_insn (\"ldil L'__outline_epilogue,%%r31\", NULL);
9560 output_asm_insn (\"ble,n R'__outline_epilogue(%%sr0,%%r31)\", NULL);
9563 output_asm_insn (\"{bl|b,l},n __outline_epilogue,%%r31\", NULL);
9567 [(set_attr "type" "multi")
9568 (set_attr "length" "8")])
9570 ;; Given a function pointer, canonicalize it so it can be
9571 ;; reliably compared to another function pointer. */
9572 (define_expand "canonicalize_funcptr_for_compare"
9573 [(set (reg:SI 26) (match_operand:SI 1 "register_operand" ""))
9574 (parallel [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] UNSPEC_CFFC))
9575 (clobber (match_dup 2))
9576 (clobber (reg:SI 26))
9577 (clobber (reg:SI 22))
9578 (clobber (reg:SI 31))])
9579 (set (match_operand:SI 0 "register_operand" "")
9581 "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
9586 rtx canonicalize_funcptr_for_compare_libfunc
9587 = init_one_libfunc (CANONICALIZE_FUNCPTR_FOR_COMPARE_LIBCALL);
9589 emit_library_call_value (canonicalize_funcptr_for_compare_libfunc,
9590 operands[0], LCT_NORMAL, Pmode,
9591 1, operands[1], Pmode);
9595 operands[2] = gen_reg_rtx (SImode);
9596 if (GET_CODE (operands[1]) != REG)
9598 rtx tmp = gen_reg_rtx (Pmode);
9599 emit_move_insn (tmp, operands[1]);
9604 (define_insn "*$$sh_func_adrs"
9605 [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] UNSPEC_CFFC))
9606 (clobber (match_operand:SI 0 "register_operand" "=a"))
9607 (clobber (reg:SI 26))
9608 (clobber (reg:SI 22))
9609 (clobber (reg:SI 31))]
9613 int length = get_attr_length (insn);
9616 xoperands[0] = GEN_INT (length - 8);
9617 xoperands[1] = GEN_INT (length - 16);
9619 /* Must import the magic millicode routine. */
9620 output_asm_insn (\".IMPORT $$sh_func_adrs,MILLICODE\", NULL);
9622 /* This is absolutely amazing.
9624 First, copy our input parameter into %r29 just in case we don't
9625 need to call $$sh_func_adrs. */
9626 output_asm_insn (\"copy %%r26,%%r29\", NULL);
9627 output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\", NULL);
9629 /* Next, examine the low two bits in %r26, if they aren't 0x2, then
9630 we use %r26 unchanged. */
9631 output_asm_insn (\"{comib|cmpib},<>,n 2,%%r31,.+%0\", xoperands);
9632 output_asm_insn (\"ldi 4096,%%r31\", NULL);
9634 /* Next, compare %r26 with 4096, if %r26 is less than or equal to
9635 4096, then again we use %r26 unchanged. */
9636 output_asm_insn (\"{comb|cmpb},<<,n %%r26,%%r31,.+%1\", xoperands);
9638 /* Finally, call $$sh_func_adrs to extract the function's real add24. */
9639 return pa_output_millicode_call (insn,
9640 gen_rtx_SYMBOL_REF (SImode,
9641 \"$$sh_func_adrs\"));
9643 [(set_attr "type" "sh_func_adrs")
9644 (set (attr "length")
9645 (cond [(and (const_int 0) (eq (const_int 0) (pc))) (const_int 28)]
9646 (plus (symbol_ref "pa_attr_length_millicode_call (insn)")
9649 ;; On the PA, the PIC register is call clobbered, so it must
9650 ;; be saved & restored around calls by the caller. If the call
9651 ;; doesn't return normally (nonlocal goto, or an exception is
9652 ;; thrown), then the code at the exception handler label must
9653 ;; restore the PIC register.
9654 (define_expand "exception_receiver"
9659 /* On the 64-bit port, we need a blockage because there is
9660 confusion regarding the dependence of the restore on the
9661 frame pointer. As a result, the frame pointer and pic
9662 register restores sometimes are interchanged erroneously. */
9664 emit_insn (gen_blockage ());
9665 /* Restore the PIC register using hppa_pic_save_rtx (). The
9666 PIC register is not saved in the frame in 64-bit ABI. */
9667 emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
9668 emit_insn (gen_blockage ());
9672 (define_expand "builtin_setjmp_receiver"
9673 [(label_ref (match_operand 0 "" ""))]
9678 emit_insn (gen_blockage ());
9679 /* Restore the PIC register. Hopefully, this will always be from
9680 a stack slot. The only registers that are valid after a
9681 builtin_longjmp are the stack and frame pointers. */
9682 emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
9683 emit_insn (gen_blockage ());
9687 ;; Allocate new stack space and update the saved stack pointer in the
9688 ;; frame marker. The HP C compilers also copy additional words in the
9689 ;; frame marker. The 64-bit compiler copies words at -48, -32 and -24.
9690 ;; The 32-bit compiler copies the word at -16 (Static Link). We
9691 ;; currently don't copy these values.
9693 ;; Since the copy of the frame marker can't be done atomically, I
9694 ;; suspect that using it for unwind purposes may be somewhat unreliable.
9695 ;; The HP compilers appear to raise the stack and copy the frame
9696 ;; marker in a strict instruction sequence. This suggests that the
9697 ;; unwind library may check for an alloca sequence when ALLOCA_FRAME
9698 ;; is set in the callinfo data. We currently don't set ALLOCA_FRAME
9699 ;; as GAS doesn't support it, or try to keep the instructions emitted
9700 ;; here in strict sequence.
9701 (define_expand "allocate_stack"
9702 [(match_operand 0 "" "")
9703 (match_operand 1 "" "")]
9709 /* Since the stack grows upward, we need to store virtual_stack_dynamic_rtx
9710 in operand 0 before adjusting the stack. */
9711 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
9712 anti_adjust_stack (operands[1]);
9713 if (TARGET_HPUX_UNWIND_LIBRARY)
9715 addr = gen_rtx_PLUS (word_mode, stack_pointer_rtx,
9716 GEN_INT (TARGET_64BIT ? -8 : -4));
9717 emit_move_insn (gen_rtx_MEM (word_mode, addr), hard_frame_pointer_rtx);
9719 if (!TARGET_64BIT && flag_pic)
9721 rtx addr = gen_rtx_PLUS (word_mode, stack_pointer_rtx, GEN_INT (-32));
9722 emit_move_insn (gen_rtx_MEM (word_mode, addr), pic_offset_table_rtx);
9727 (define_expand "prefetch"
9728 [(match_operand 0 "address_operand" "")
9729 (match_operand 1 "const_int_operand" "")
9730 (match_operand 2 "const_int_operand" "")]
9733 operands[0] = copy_addr_to_reg (operands[0]);
9734 emit_insn (gen_prefetch_20 (operands[0], operands[1], operands[2]));
9738 (define_insn "prefetch_20"
9739 [(prefetch (match_operand 0 "pmode_register_operand" "r")
9740 (match_operand:SI 1 "const_int_operand" "n")
9741 (match_operand:SI 2 "const_int_operand" "n"))]
9744 /* The SL cache-control completer indicates good spatial locality but
9745 poor temporal locality. The ldw instruction with a target of general
9746 register 0 prefetches a cache line for a read. The ldd instruction
9747 prefetches a cache line for a write. */
9748 static const char * const instr[2][2] = {
9750 "ldw,sl 0(%0),%%r0",
9758 int read_or_write = INTVAL (operands[1]) == 0 ? 0 : 1;
9759 int locality = INTVAL (operands[2]) == 0 ? 0 : 1;
9761 return instr [locality][read_or_write];
9763 [(set_attr "type" "load")
9764 (set_attr "length" "4")])
9767 (define_insn "tgd_load"
9768 [(set (match_operand:SI 0 "register_operand" "=r")
9769 (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")] UNSPEC_TLSGD))
9770 (clobber (reg:SI 1))
9775 return \"addil LR'%1-$tls_gdidx$,%%r27\;ldo RR'%1-$tls_gdidx$(%%r1),%0\";
9777 [(set_attr "type" "multi")
9778 (set_attr "length" "8")])
9780 (define_insn "tgd_load_pic"
9781 [(set (match_operand:SI 0 "register_operand" "=r")
9782 (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")] UNSPEC_TLSGD_PIC))
9783 (clobber (reg:SI 1))
9788 return \"addil LT'%1-$tls_gdidx$,%%r19\;ldo RT'%1-$tls_gdidx$(%%r1),%0\";
9790 [(set_attr "type" "multi")
9791 (set_attr "length" "8")])
9793 (define_insn "tld_load"
9794 [(set (match_operand:SI 0 "register_operand" "=r")
9795 (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")] UNSPEC_TLSLDM))
9796 (clobber (reg:SI 1))
9801 return \"addil LR'%1-$tls_ldidx$,%%r27\;ldo RR'%1-$tls_ldidx$(%%r1),%0\";
9803 [(set_attr "type" "multi")
9804 (set_attr "length" "8")])
9806 (define_insn "tld_load_pic"
9807 [(set (match_operand:SI 0 "register_operand" "=r")
9808 (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")] UNSPEC_TLSLDM_PIC))
9809 (clobber (reg:SI 1))
9814 return \"addil LT'%1-$tls_ldidx$,%%r19\;ldo RT'%1-$tls_ldidx$(%%r1),%0\";
9816 [(set_attr "type" "multi")
9817 (set_attr "length" "8")])
9819 (define_insn "tld_offset_load"
9820 [(set (match_operand:SI 0 "register_operand" "=r")
9821 (plus:SI (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")]
9823 (match_operand:SI 2 "register_operand" "r")))
9824 (clobber (reg:SI 1))]
9828 return \"addil LR'%1-$tls_dtpoff$,%2\;ldo RR'%1-$tls_dtpoff$(%%r1),%0\";
9830 [(set_attr "type" "multi")
9831 (set_attr "length" "8")])
9833 (define_insn "tp_load"
9834 [(set (match_operand:SI 0 "register_operand" "=r")
9835 (unspec:SI [(const_int 0)] UNSPEC_TP))]
9838 [(set_attr "type" "multi")
9839 (set_attr "length" "4")])
9841 (define_insn "tie_load"
9842 [(set (match_operand:SI 0 "register_operand" "=r")
9843 (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")] UNSPEC_TLSIE))
9844 (clobber (reg:SI 1))
9849 return \"addil LR'%1-$tls_ieoff$,%%r27\;ldw RR'%1-$tls_ieoff$(%%r1),%0\";
9851 [(set_attr "type" "multi")
9852 (set_attr "length" "8")])
9854 (define_insn "tie_load_pic"
9855 [(set (match_operand:SI 0 "register_operand" "=r")
9856 (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")] UNSPEC_TLSIE_PIC))
9857 (clobber (reg:SI 1))
9862 return \"addil LT'%1-$tls_ieoff$,%%r19\;ldw RT'%1-$tls_ieoff$(%%r1),%0\";
9864 [(set_attr "type" "multi")
9865 (set_attr "length" "8")])
9867 (define_insn "tle_load"
9868 [(set (match_operand:SI 0 "register_operand" "=r")
9869 (plus:SI (unspec:SI [(match_operand 1 "tle_symbolic_operand" "")]
9871 (match_operand:SI 2 "register_operand" "r")))
9872 (clobber (reg:SI 1))]
9874 "addil LR'%1-$tls_leoff$,%2\;ldo RR'%1-$tls_leoff$(%%r1),%0"
9875 [(set_attr "type" "multi")
9876 (set_attr "length" "8")])