OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-old/] [gcc-4.2.2/] [gcc/] [config/] [pa/] [pa.md] - Blame information for rev 816

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 38 julius
;;- Machine description for HP PA-RISC architecture for GCC compiler
2
;;   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
3
;;   2002, 2003, 2004, 2005, 2006, 2007 Free Software Foundation, Inc.
4
;;   Contributed by the Center for Software Science at the University
5
;;   of Utah.
6
 
7
;; This file is part of GCC.
8
 
9
;; GCC is free software; you can redistribute it and/or modify
10
;; it under the terms of the GNU General Public License as published by
11
;; the Free Software Foundation; either version 3, or (at your option)
12
;; any later version.
13
 
14
;; GCC is distributed in the hope that it will be useful,
15
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
;; GNU General Public License for more details.
18
 
19
;; You should have received a copy of the GNU General Public License
20
;; along with GCC; see the file COPYING3.  If not see
21
;; .
22
 
23
;; This gcc Version 2 machine description is inspired by sparc.md and
24
;; mips.md.
25
 
26
;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
27
 
28
;; Uses of UNSPEC in this file:
29
 
30
(define_constants
31
  [(UNSPEC_CFFC         0)      ; canonicalize_funcptr_for_compare
32
   (UNSPEC_GOTO         1)      ; indirect_goto
33
   (UNSPEC_DLTIND14R    2)      ;
34
   (UNSPEC_TP           3)
35
   (UNSPEC_TLSGD        4)
36
   (UNSPEC_TLSLDM       5)
37
   (UNSPEC_TLSLDO       6)
38
   (UNSPEC_TLSLDBASE    7)
39
   (UNSPEC_TLSIE        8)
40
   (UNSPEC_TLSLE        9)
41
   (UNSPEC_TLSGD_PIC   10)
42
   (UNSPEC_TLSLDM_PIC  11)
43
   (UNSPEC_TLSIE_PIC   12)
44
  ])
45
 
46
;; UNSPEC_VOLATILE:
47
 
48
(define_constants
49
  [(UNSPECV_BLOCKAGE    0)      ; blockage
50
   (UNSPECV_DCACHE      1)      ; dcacheflush
51
   (UNSPECV_ICACHE      2)      ; icacheflush
52
   (UNSPECV_OPC         3)      ; outline_prologue_call
53
   (UNSPECV_OEC         4)      ; outline_epilogue_call
54
   (UNSPECV_LONGJMP     5)      ; builtin_longjmp
55
  ])
56
 
57
;; Maximum pc-relative branch offsets.
58
 
59
;; These numbers are a bit smaller than the maximum allowable offsets
60
;; so that a few instructions may be inserted before the actual branch.
61
 
62
(define_constants
63
  [(MAX_12BIT_OFFSET     8184)  ; 12-bit branch
64
   (MAX_17BIT_OFFSET   262100)  ; 17-bit branch
65
  ])
66
 
67
;; Insn type.  Used to default other attribute values.
68
 
69
;; type "unary" insns have one input operand (1) and one output operand (0)
70
;; type "binary" insns have two input operands (1,2) and one output (0)
71
 
72
(define_attr "type"
73
  "move,unary,binary,shift,nullshift,compare,load,store,uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,fpload,fpstore,fpalu,fpcc,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,multi,milli,parallel_branch"
74
  (const_string "binary"))
75
 
76
(define_attr "pa_combine_type"
77
  "fmpy,faddsub,uncond_branch,addmove,none"
78
  (const_string "none"))
79
 
80
;; Processor type (for scheduling, not code generation) -- this attribute
81
;; must exactly match the processor_type enumeration in pa.h.
82
;;
83
;; FIXME: Add 800 scheduling for completeness?
84
 
85
(define_attr "cpu" "700,7100,7100LC,7200,7300,8000" (const (symbol_ref "pa_cpu_attr")))
86
 
87
;; Length (in # of bytes).
88
(define_attr "length" ""
89
  (cond [(eq_attr "type" "load,fpload")
90
         (if_then_else (match_operand 1 "symbolic_memory_operand" "")
91
                       (const_int 8) (const_int 4))
92
 
93
         (eq_attr "type" "store,fpstore")
94
         (if_then_else (match_operand 0 "symbolic_memory_operand" "")
95
                       (const_int 8) (const_int 4))
96
 
97
         (eq_attr "type" "binary,shift,nullshift")
98
         (if_then_else (match_operand 2 "arith_operand" "")
99
                       (const_int 4) (const_int 12))
100
 
101
         (eq_attr "type" "move,unary,shift,nullshift")
102
         (if_then_else (match_operand 1 "arith_operand" "")
103
                       (const_int 4) (const_int 8))]
104
 
105
        (const_int 4)))
106
 
107
(define_asm_attributes
108
  [(set_attr "length" "4")
109
   (set_attr "type" "multi")])
110
 
111
;; Attributes for instruction and branch scheduling
112
 
113
;; For conditional branches.
114
(define_attr "in_branch_delay" "false,true"
115
  (if_then_else (and (eq_attr "type" "!uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
116
                     (eq_attr "length" "4"))
117
                (const_string "true")
118
                (const_string "false")))
119
 
120
;; Disallow instructions which use the FPU since they will tie up the FPU
121
;; even if the instruction is nullified.
122
(define_attr "in_nullified_branch_delay" "false,true"
123
  (if_then_else (and (eq_attr "type" "!uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,parallel_branch")
124
                     (eq_attr "length" "4"))
125
                (const_string "true")
126
                (const_string "false")))
127
 
128
;; For calls and millicode calls.  Allow unconditional branches in the
129
;; delay slot.
130
(define_attr "in_call_delay" "false,true"
131
  (cond [(and (eq_attr "type" "!uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
132
              (eq_attr "length" "4"))
133
           (const_string "true")
134
         (eq_attr "type" "uncond_branch")
135
           (if_then_else (ne (symbol_ref "TARGET_JUMP_IN_DELAY")
136
                             (const_int 0))
137
                         (const_string "true")
138
                         (const_string "false"))]
139
        (const_string "false")))
140
 
141
 
142
;; Call delay slot description.
143
(define_delay (eq_attr "type" "call")
144
  [(eq_attr "in_call_delay" "true") (nil) (nil)])
145
 
146
;; Millicode call delay slot description.
147
(define_delay (eq_attr "type" "milli")
148
  [(eq_attr "in_call_delay" "true") (nil) (nil)])
149
 
150
;; Return and other similar instructions.
151
(define_delay (eq_attr "type" "btable_branch,branch,parallel_branch")
152
  [(eq_attr "in_branch_delay" "true") (nil) (nil)])
153
 
154
;; Floating point conditional branch delay slot description.
155
(define_delay (eq_attr "type" "fbranch")
156
  [(eq_attr "in_branch_delay" "true")
157
   (eq_attr "in_nullified_branch_delay" "true")
158
   (nil)])
159
 
160
;; Integer conditional branch delay slot description.
161
;; Nullification of conditional branches on the PA is dependent on the
162
;; direction of the branch.  Forward branches nullify true and
163
;; backward branches nullify false.  If the direction is unknown
164
;; then nullification is not allowed.
165
(define_delay (eq_attr "type" "cbranch")
166
  [(eq_attr "in_branch_delay" "true")
167
   (and (eq_attr "in_nullified_branch_delay" "true")
168
        (attr_flag "forward"))
169
   (and (eq_attr "in_nullified_branch_delay" "true")
170
        (attr_flag "backward"))])
171
 
172
(define_delay (and (eq_attr "type" "uncond_branch")
173
                   (eq (symbol_ref "following_call (insn)")
174
                       (const_int 0)))
175
  [(eq_attr "in_branch_delay" "true") (nil) (nil)])
176
 
177
;; Memory. Disregarding Cache misses, the Mustang memory times are:
178
;; load: 2, fpload: 3
179
;; store, fpstore: 3, no D-cache operations should be scheduled.
180
 
181
;; The Timex (aka 700) has two floating-point units: ALU, and MUL/DIV/SQRT.
182
;; Timings:
183
;; Instruction  Time    Unit    Minimum Distance (unit contention)
184
;; fcpy         3       ALU     2
185
;; fabs         3       ALU     2
186
;; fadd         3       ALU     2
187
;; fsub         3       ALU     2
188
;; fcmp         3       ALU     2
189
;; fcnv         3       ALU     2
190
;; fmpyadd      3       ALU,MPY 2
191
;; fmpysub      3       ALU,MPY 2
192
;; fmpycfxt     3       ALU,MPY 2
193
;; fmpy         3       MPY     2
194
;; fmpyi        3       MPY     2
195
;; fdiv,sgl     10      MPY     10
196
;; fdiv,dbl     12      MPY     12
197
;; fsqrt,sgl    14      MPY     14
198
;; fsqrt,dbl    18      MPY     18
199
;;
200
;; We don't model fmpyadd/fmpysub properly as those instructions
201
;; keep both the FP ALU and MPY units busy.  Given that these
202
;; processors are obsolete, I'm not going to spend the time to
203
;; model those instructions correctly.
204
 
205
(define_automaton "pa700")
206
(define_cpu_unit "dummy_700,mem_700,fpalu_700,fpmpy_700" "pa700")
207
 
208
(define_insn_reservation "W0" 4
209
  (and (eq_attr "type" "fpcc")
210
       (eq_attr "cpu" "700"))
211
  "fpalu_700*2")
212
 
213
(define_insn_reservation "W1" 3
214
  (and (eq_attr "type" "fpalu")
215
       (eq_attr "cpu" "700"))
216
  "fpalu_700*2")
217
 
218
(define_insn_reservation "W2" 3
219
  (and (eq_attr "type" "fpmulsgl,fpmuldbl")
220
       (eq_attr "cpu" "700"))
221
  "fpmpy_700*2")
222
 
223
(define_insn_reservation "W3" 10
224
  (and (eq_attr "type" "fpdivsgl")
225
       (eq_attr "cpu" "700"))
226
  "fpmpy_700*10")
227
 
228
(define_insn_reservation "W4" 12
229
  (and (eq_attr "type" "fpdivdbl")
230
       (eq_attr "cpu" "700"))
231
  "fpmpy_700*12")
232
 
233
(define_insn_reservation "W5" 14
234
  (and (eq_attr "type" "fpsqrtsgl")
235
       (eq_attr "cpu" "700"))
236
  "fpmpy_700*14")
237
 
238
(define_insn_reservation "W6" 18
239
  (and (eq_attr "type" "fpsqrtdbl")
240
       (eq_attr "cpu" "700"))
241
  "fpmpy_700*18")
242
 
243
(define_insn_reservation "W7" 2
244
  (and (eq_attr "type" "load")
245
       (eq_attr "cpu" "700"))
246
  "mem_700")
247
 
248
(define_insn_reservation "W8" 2
249
  (and (eq_attr "type" "fpload")
250
       (eq_attr "cpu" "700"))
251
  "mem_700")
252
 
253
(define_insn_reservation "W9" 3
254
  (and (eq_attr "type" "store")
255
       (eq_attr "cpu" "700"))
256
  "mem_700*3")
257
 
258
(define_insn_reservation "W10" 3
259
  (and (eq_attr "type" "fpstore")
260
       (eq_attr "cpu" "700"))
261
  "mem_700*3")
262
 
263
(define_insn_reservation "W11" 1
264
  (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpdivdbl,fpsqrtsgl,fpsqrtdbl,load,fpload,store,fpstore")
265
       (eq_attr "cpu" "700"))
266
  "dummy_700")
267
 
268
;; We have a bypass for all computations in the FP unit which feed an
269
;; FP store as long as the sizes are the same.
270
(define_bypass 2 "W1,W2" "W10" "hppa_fpstore_bypass_p")
271
(define_bypass 9 "W3" "W10" "hppa_fpstore_bypass_p")
272
(define_bypass 11 "W4" "W10" "hppa_fpstore_bypass_p")
273
(define_bypass 13 "W5" "W10" "hppa_fpstore_bypass_p")
274
(define_bypass 17 "W6" "W10" "hppa_fpstore_bypass_p")
275
 
276
;; We have an "anti-bypass" for FP loads which feed an FP store.
277
(define_bypass 4 "W8" "W10" "hppa_fpstore_bypass_p")
278
 
279
;; Function units for the 7100 and 7150.  The 7100/7150 can dual-issue
280
;; floating point computations with non-floating point computations (fp loads
281
;; and stores are not fp computations).
282
;;
283
;; Memory. Disregarding Cache misses, memory loads take two cycles; stores also
284
;; take two cycles, during which no Dcache operations should be scheduled.
285
;; Any special cases are handled in pa_adjust_cost.  The 7100, 7150 and 7100LC
286
;; all have the same memory characteristics if one disregards cache misses.
287
;;
288
;; The 7100/7150 has three floating-point units: ALU, MUL, and DIV.
289
;; There's no value in modeling the ALU and MUL separately though
290
;; since there can never be a functional unit conflict given the
291
;; latency and issue rates for those units.
292
;;
293
;; Timings:
294
;; Instruction  Time    Unit    Minimum Distance (unit contention)
295
;; fcpy         2       ALU     1
296
;; fabs         2       ALU     1
297
;; fadd         2       ALU     1
298
;; fsub         2       ALU     1
299
;; fcmp         2       ALU     1
300
;; fcnv         2       ALU     1
301
;; fmpyadd      2       ALU,MPY 1
302
;; fmpysub      2       ALU,MPY 1
303
;; fmpycfxt     2       ALU,MPY 1
304
;; fmpy         2       MPY     1
305
;; fmpyi        2       MPY     1
306
;; fdiv,sgl     8       DIV     8
307
;; fdiv,dbl     15      DIV     15
308
;; fsqrt,sgl    8       DIV     8
309
;; fsqrt,dbl    15      DIV     15
310
 
311
(define_automaton "pa7100")
312
(define_cpu_unit "i_7100, f_7100,fpmac_7100,fpdivsqrt_7100,mem_7100" "pa7100")
313
 
314
(define_insn_reservation "X0" 2
315
  (and (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
316
       (eq_attr "cpu" "7100"))
317
  "f_7100,fpmac_7100")
318
 
319
(define_insn_reservation "X1" 8
320
  (and (eq_attr "type" "fpdivsgl,fpsqrtsgl")
321
       (eq_attr "cpu" "7100"))
322
  "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*7")
323
 
324
(define_insn_reservation "X2" 15
325
  (and (eq_attr "type" "fpdivdbl,fpsqrtdbl")
326
       (eq_attr "cpu" "7100"))
327
  "f_7100+fpdivsqrt_7100,fpdivsqrt_7100*14")
328
 
329
(define_insn_reservation "X3" 2
330
  (and (eq_attr "type" "load")
331
       (eq_attr "cpu" "7100"))
332
  "i_7100+mem_7100")
333
 
334
(define_insn_reservation "X4" 2
335
  (and (eq_attr "type" "fpload")
336
       (eq_attr "cpu" "7100"))
337
  "i_7100+mem_7100")
338
 
339
(define_insn_reservation "X5" 2
340
  (and (eq_attr "type" "store")
341
       (eq_attr "cpu" "7100"))
342
  "i_7100+mem_7100,mem_7100")
343
 
344
(define_insn_reservation "X6" 2
345
  (and (eq_attr "type" "fpstore")
346
       (eq_attr "cpu" "7100"))
347
  "i_7100+mem_7100,mem_7100")
348
 
349
(define_insn_reservation "X7" 1
350
  (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore")
351
       (eq_attr "cpu" "7100"))
352
  "i_7100")
353
 
354
;; We have a bypass for all computations in the FP unit which feed an
355
;; FP store as long as the sizes are the same.
356
(define_bypass 1 "X0" "X6" "hppa_fpstore_bypass_p")
357
(define_bypass 7 "X1" "X6" "hppa_fpstore_bypass_p")
358
(define_bypass 14 "X2" "X6" "hppa_fpstore_bypass_p")
359
 
360
;; We have an "anti-bypass" for FP loads which feed an FP store.
361
(define_bypass 3 "X4" "X6" "hppa_fpstore_bypass_p")
362
 
363
;; The 7100LC has three floating-point units: ALU, MUL, and DIV.
364
;; There's no value in modeling the ALU and MUL separately though
365
;; since there can never be a functional unit conflict that
366
;; can be avoided given the latency, issue rates and mandatory
367
;; one cycle cpu-wide lock for a double precision fp multiply.
368
;;
369
;; Timings:
370
;; Instruction  Time    Unit    Minimum Distance (unit contention)
371
;; fcpy         2       ALU     1
372
;; fabs         2       ALU     1
373
;; fadd         2       ALU     1
374
;; fsub         2       ALU     1
375
;; fcmp         2       ALU     1
376
;; fcnv         2       ALU     1
377
;; fmpyadd,sgl  2       ALU,MPY 1
378
;; fmpyadd,dbl  3       ALU,MPY 2
379
;; fmpysub,sgl  2       ALU,MPY 1
380
;; fmpysub,dbl  3       ALU,MPY 2
381
;; fmpycfxt,sgl 2       ALU,MPY 1
382
;; fmpycfxt,dbl 3       ALU,MPY 2
383
;; fmpy,sgl     2       MPY     1
384
;; fmpy,dbl     3       MPY     2
385
;; fmpyi        3       MPY     2
386
;; fdiv,sgl     8       DIV     8
387
;; fdiv,dbl     15      DIV     15
388
;; fsqrt,sgl    8       DIV     8
389
;; fsqrt,dbl    15      DIV     15
390
;;
391
;; The PA7200 is just like the PA7100LC except that there is
392
;; no store-store penalty.
393
;;
394
;; The PA7300 is just like the PA7200 except that there is
395
;; no store-load penalty.
396
;;
397
;; Note there are some aspects of the 7100LC we are not modeling
398
;; at the moment.  I'll be reviewing the 7100LC scheduling info
399
;; shortly and updating this description.
400
;;
401
;;   load-load pairs
402
;;   store-store pairs
403
;;   other issue modeling
404
 
405
(define_automaton "pa7100lc")
406
(define_cpu_unit "i0_7100lc, i1_7100lc, f_7100lc" "pa7100lc")
407
(define_cpu_unit "fpmac_7100lc" "pa7100lc")
408
(define_cpu_unit "mem_7100lc" "pa7100lc")
409
 
410
;; Double precision multiplies lock the entire CPU for one
411
;; cycle.  There is no way to avoid this lock and trying to
412
;; schedule around the lock is pointless and thus there is no
413
;; value in trying to model this lock.
414
;;
415
;; Not modeling the lock allows us to treat fp multiplies just
416
;; like any other FP alu instruction.  It allows for a smaller
417
;; DFA and may reduce register pressure.
418
(define_insn_reservation "Y0" 2
419
  (and (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
420
       (eq_attr "cpu" "7100LC,7200,7300"))
421
  "f_7100lc,fpmac_7100lc")
422
 
423
;; fp division and sqrt instructions lock the entire CPU for
424
;; 7 cycles (single precision) or 14 cycles (double precision).
425
;; There is no way to avoid this lock and trying to schedule
426
;; around the lock is pointless and thus there is no value in
427
;; trying to model this lock.  Not modeling the lock allows
428
;; for a smaller DFA and may reduce register pressure.
429
(define_insn_reservation "Y1" 1
430
  (and (eq_attr "type" "fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl")
431
       (eq_attr "cpu" "7100LC,7200,7300"))
432
  "f_7100lc")
433
 
434
(define_insn_reservation "Y2" 2
435
  (and (eq_attr "type" "load")
436
       (eq_attr "cpu" "7100LC,7200,7300"))
437
  "i1_7100lc+mem_7100lc")
438
 
439
(define_insn_reservation "Y3" 2
440
  (and (eq_attr "type" "fpload")
441
       (eq_attr "cpu" "7100LC,7200,7300"))
442
  "i1_7100lc+mem_7100lc")
443
 
444
(define_insn_reservation "Y4" 2
445
  (and (eq_attr "type" "store")
446
       (eq_attr "cpu" "7100LC"))
447
  "i1_7100lc+mem_7100lc,mem_7100lc")
448
 
449
(define_insn_reservation "Y5" 2
450
  (and (eq_attr "type" "fpstore")
451
       (eq_attr "cpu" "7100LC"))
452
  "i1_7100lc+mem_7100lc,mem_7100lc")
453
 
454
(define_insn_reservation "Y6" 1
455
  (and (eq_attr "type" "shift,nullshift")
456
       (eq_attr "cpu" "7100LC,7200,7300"))
457
  "i1_7100lc")
458
 
459
(define_insn_reservation "Y7" 1
460
  (and (eq_attr "type" "!fpcc,fpalu,fpmulsgl,fpmuldbl,fpdivsgl,fpsqrtsgl,fpdivdbl,fpsqrtdbl,load,fpload,store,fpstore,shift,nullshift")
461
       (eq_attr "cpu" "7100LC,7200,7300"))
462
  "(i0_7100lc|i1_7100lc)")
463
 
464
;; The 7200 has a store-load penalty
465
(define_insn_reservation "Y8" 2
466
  (and (eq_attr "type" "store")
467
       (eq_attr "cpu" "7200"))
468
  "i1_7100lc,mem_7100lc")
469
 
470
(define_insn_reservation "Y9" 2
471
  (and (eq_attr "type" "fpstore")
472
       (eq_attr "cpu" "7200"))
473
  "i1_7100lc,mem_7100lc")
474
 
475
;; The 7300 has no penalty for store-store or store-load
476
(define_insn_reservation "Y10" 2
477
  (and (eq_attr "type" "store")
478
       (eq_attr "cpu" "7300"))
479
  "i1_7100lc")
480
 
481
(define_insn_reservation "Y11" 2
482
  (and (eq_attr "type" "fpstore")
483
       (eq_attr "cpu" "7300"))
484
  "i1_7100lc")
485
 
486
;; We have an "anti-bypass" for FP loads which feed an FP store.
487
(define_bypass 3 "Y3" "Y5,Y9,Y11" "hppa_fpstore_bypass_p")
488
 
489
;; Scheduling for the PA8000 is somewhat different than scheduling for a
490
;; traditional architecture.
491
;;
492
;; The PA8000 has a large (56) entry reorder buffer that is split between
493
;; memory and non-memory operations.
494
;;
495
;; The PA8000 can issue two memory and two non-memory operations per cycle to
496
;; the function units, with the exception of branches and multi-output
497
;; instructions.  The PA8000 can retire two non-memory operations per cycle
498
;; and two memory operations per cycle, only one of which may be a store.
499
;;
500
;; Given the large reorder buffer, the processor can hide most latencies.
501
;; According to HP, they've got the best results by scheduling for retirement
502
;; bandwidth with limited latency scheduling for floating point operations.
503
;; Latency for integer operations and memory references is ignored.
504
;;
505
;;
506
;; We claim floating point operations have a 2 cycle latency and are
507
;; fully pipelined, except for div and sqrt which are not pipelined and
508
;; take from 17 to 31 cycles to complete.
509
;;
510
;; It's worth noting that there is no way to saturate all the functional
511
;; units on the PA8000 as there is not enough issue bandwidth.
512
 
513
(define_automaton "pa8000")
514
(define_cpu_unit "inm0_8000, inm1_8000, im0_8000, im1_8000" "pa8000")
515
(define_cpu_unit "rnm0_8000, rnm1_8000, rm0_8000, rm1_8000" "pa8000")
516
(define_cpu_unit "store_8000" "pa8000")
517
(define_cpu_unit "f0_8000, f1_8000" "pa8000")
518
(define_cpu_unit "fdivsqrt0_8000, fdivsqrt1_8000" "pa8000")
519
(define_reservation "inm_8000" "inm0_8000 | inm1_8000")
520
(define_reservation "im_8000" "im0_8000 | im1_8000")
521
(define_reservation "rnm_8000" "rnm0_8000 | rnm1_8000")
522
(define_reservation "rm_8000" "rm0_8000 | rm1_8000")
523
(define_reservation "f_8000" "f0_8000 | f1_8000")
524
(define_reservation "fdivsqrt_8000" "fdivsqrt0_8000 | fdivsqrt1_8000")
525
 
526
;; We can issue any two memops per cycle, but we can only retire
527
;; one memory store per cycle.  We assume that the reorder buffer
528
;; will hide any memory latencies per HP's recommendation.
529
(define_insn_reservation "Z0" 0
530
  (and
531
    (eq_attr "type" "load,fpload")
532
    (eq_attr "cpu" "8000"))
533
  "im_8000,rm_8000")
534
 
535
(define_insn_reservation "Z1" 0
536
  (and
537
    (eq_attr "type" "store,fpstore")
538
    (eq_attr "cpu" "8000"))
539
  "im_8000,rm_8000+store_8000")
540
 
541
;; We can issue and retire two non-memory operations per cycle with
542
;; a few exceptions (branches).  This group catches those we want
543
;; to assume have zero latency.
544
(define_insn_reservation "Z2" 0
545
  (and
546
    (eq_attr "type" "!load,fpload,store,fpstore,uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch,fpcc,fpalu,fpmulsgl,fpmuldbl,fpsqrtsgl,fpsqrtdbl,fpdivsgl,fpdivdbl")
547
    (eq_attr "cpu" "8000"))
548
  "inm_8000,rnm_8000")
549
 
550
;; Branches use both slots in the non-memory issue and
551
;; retirement unit.
552
(define_insn_reservation "Z3" 0
553
  (and
554
    (eq_attr "type" "uncond_branch,btable_branch,branch,cbranch,fbranch,call,dyncall,multi,milli,parallel_branch")
555
    (eq_attr "cpu" "8000"))
556
  "inm0_8000+inm1_8000,rnm0_8000+rnm1_8000")
557
 
558
;; We partial latency schedule the floating point units.
559
;; They can issue/retire two at a time in the non-memory
560
;; units.  We fix their latency at 2 cycles and they
561
;; are fully pipelined.
562
(define_insn_reservation "Z4" 1
563
 (and
564
   (eq_attr "type" "fpcc,fpalu,fpmulsgl,fpmuldbl")
565
   (eq_attr "cpu" "8000"))
566
 "inm_8000,f_8000,rnm_8000")
567
 
568
;; The fdivsqrt units are not pipelined and have a very long latency.
569
;; To keep the DFA from exploding, we do not show all the
570
;; reservations for the divsqrt unit.
571
(define_insn_reservation "Z5" 17
572
 (and
573
   (eq_attr "type" "fpdivsgl,fpsqrtsgl")
574
   (eq_attr "cpu" "8000"))
575
 "inm_8000,fdivsqrt_8000*6,rnm_8000")
576
 
577
(define_insn_reservation "Z6" 31
578
 (and
579
   (eq_attr "type" "fpdivdbl,fpsqrtdbl")
580
   (eq_attr "cpu" "8000"))
581
 "inm_8000,fdivsqrt_8000*6,rnm_8000")
582
 
583
(include "predicates.md")
584
 
585
;; Compare instructions.
586
;; This controls RTL generation and register allocation.
587
 
588
;; We generate RTL for comparisons and branches by having the cmpxx
589
;; patterns store away the operands.  Then, the scc and bcc patterns
590
;; emit RTL for both the compare and the branch.
591
;;
592
 
593
(define_expand "cmpdi"
594
  [(set (reg:CC 0)
595
        (compare:CC (match_operand:DI 0 "reg_or_0_operand" "")
596
                    (match_operand:DI 1 "register_operand" "")))]
597
  "TARGET_64BIT"
598
 
599
  "
600
{
601
 hppa_compare_op0 = operands[0];
602
 hppa_compare_op1 = operands[1];
603
 hppa_branch_type = CMP_SI;
604
 DONE;
605
}")
606
 
607
(define_expand "cmpsi"
608
  [(set (reg:CC 0)
609
        (compare:CC (match_operand:SI 0 "reg_or_0_operand" "")
610
                    (match_operand:SI 1 "arith5_operand" "")))]
611
  ""
612
  "
613
{
614
 hppa_compare_op0 = operands[0];
615
 hppa_compare_op1 = operands[1];
616
 hppa_branch_type = CMP_SI;
617
 DONE;
618
}")
619
 
620
(define_expand "cmpsf"
621
  [(set (reg:CCFP 0)
622
        (compare:CCFP (match_operand:SF 0 "reg_or_0_operand" "")
623
                      (match_operand:SF 1 "reg_or_0_operand" "")))]
624
  "! TARGET_SOFT_FLOAT"
625
  "
626
{
627
  hppa_compare_op0 = operands[0];
628
  hppa_compare_op1 = operands[1];
629
  hppa_branch_type = CMP_SF;
630
  DONE;
631
}")
632
 
633
(define_expand "cmpdf"
634
  [(set (reg:CCFP 0)
635
      (compare:CCFP (match_operand:DF 0 "reg_or_0_operand" "")
636
                    (match_operand:DF 1 "reg_or_0_operand" "")))]
637
  "! TARGET_SOFT_FLOAT"
638
  "
639
{
640
  hppa_compare_op0 = operands[0];
641
  hppa_compare_op1 = operands[1];
642
  hppa_branch_type = CMP_DF;
643
  DONE;
644
}")
645
 
646
(define_insn ""
647
  [(set (reg:CCFP 0)
648
        (match_operator:CCFP 2 "comparison_operator"
649
                             [(match_operand:SF 0 "reg_or_0_operand" "fG")
650
                              (match_operand:SF 1 "reg_or_0_operand" "fG")]))]
651
  "! TARGET_SOFT_FLOAT"
652
  "fcmp,sgl,%Y2 %f0,%f1"
653
  [(set_attr "length" "4")
654
   (set_attr "type" "fpcc")])
655
 
656
(define_insn ""
657
  [(set (reg:CCFP 0)
658
        (match_operator:CCFP 2 "comparison_operator"
659
                             [(match_operand:DF 0 "reg_or_0_operand" "fG")
660
                              (match_operand:DF 1 "reg_or_0_operand" "fG")]))]
661
  "! TARGET_SOFT_FLOAT"
662
  "fcmp,dbl,%Y2 %f0,%f1"
663
  [(set_attr "length" "4")
664
   (set_attr "type" "fpcc")])
665
 
666
;; Provide a means to emit the movccfp0 and movccfp1 optimization
667
;; placeholders.  This is necessary in rare situations when a
668
;; placeholder is re-emitted (see PR 8705).
669
 
670
(define_expand "movccfp"
671
  [(set (reg:CCFP 0)
672
        (match_operand 0 "const_int_operand" ""))]
673
  "! TARGET_SOFT_FLOAT"
674
  "
675
{
676
  if ((unsigned HOST_WIDE_INT) INTVAL (operands[0]) > 1)
677
    FAIL;
678
}")
679
 
680
;; The following patterns are optimization placeholders.  In almost
681
;; all cases, the user of the condition code will be simplified and the
682
;; original condition code setting insn should be eliminated.
683
 
684
(define_insn "*movccfp0"
685
  [(set (reg:CCFP 0)
686
        (const_int 0))]
687
  "! TARGET_SOFT_FLOAT"
688
  "fcmp,dbl,= %%fr0,%%fr0"
689
  [(set_attr "length" "4")
690
   (set_attr "type" "fpcc")])
691
 
692
(define_insn "*movccfp1"
693
  [(set (reg:CCFP 0)
694
        (const_int 1))]
695
  "! TARGET_SOFT_FLOAT"
696
  "fcmp,dbl,!= %%fr0,%%fr0"
697
  [(set_attr "length" "4")
698
   (set_attr "type" "fpcc")])
699
 
700
;; scc insns.
701
 
702
(define_expand "seq"
703
  [(set (match_operand:SI 0 "register_operand" "")
704
        (eq:SI (match_dup 1)
705
               (match_dup 2)))]
706
  "!TARGET_64BIT"
707
  "
708
{
709
  /* fp scc patterns rarely match, and are not a win on the PA.  */
710
  if (hppa_branch_type != CMP_SI)
711
    FAIL;
712
  /* set up operands from compare.  */
713
  operands[1] = hppa_compare_op0;
714
  operands[2] = hppa_compare_op1;
715
  /* fall through and generate default code */
716
}")
717
 
718
(define_expand "sne"
719
  [(set (match_operand:SI 0 "register_operand" "")
720
        (ne:SI (match_dup 1)
721
               (match_dup 2)))]
722
  "!TARGET_64BIT"
723
  "
724
{
725
  /* fp scc patterns rarely match, and are not a win on the PA.  */
726
  if (hppa_branch_type != CMP_SI)
727
    FAIL;
728
  operands[1] = hppa_compare_op0;
729
  operands[2] = hppa_compare_op1;
730
}")
731
 
732
(define_expand "slt"
733
  [(set (match_operand:SI 0 "register_operand" "")
734
        (lt:SI (match_dup 1)
735
               (match_dup 2)))]
736
  "!TARGET_64BIT"
737
  "
738
{
739
  /* fp scc patterns rarely match, and are not a win on the PA.  */
740
  if (hppa_branch_type != CMP_SI)
741
    FAIL;
742
  operands[1] = hppa_compare_op0;
743
  operands[2] = hppa_compare_op1;
744
}")
745
 
746
(define_expand "sgt"
747
  [(set (match_operand:SI 0 "register_operand" "")
748
        (gt:SI (match_dup 1)
749
               (match_dup 2)))]
750
  "!TARGET_64BIT"
751
  "
752
{
753
  /* fp scc patterns rarely match, and are not a win on the PA.  */
754
  if (hppa_branch_type != CMP_SI)
755
    FAIL;
756
  operands[1] = hppa_compare_op0;
757
  operands[2] = hppa_compare_op1;
758
}")
759
 
760
(define_expand "sle"
761
  [(set (match_operand:SI 0 "register_operand" "")
762
        (le:SI (match_dup 1)
763
               (match_dup 2)))]
764
  "!TARGET_64BIT"
765
  "
766
{
767
  /* fp scc patterns rarely match, and are not a win on the PA.  */
768
  if (hppa_branch_type != CMP_SI)
769
    FAIL;
770
  operands[1] = hppa_compare_op0;
771
  operands[2] = hppa_compare_op1;
772
}")
773
 
774
(define_expand "sge"
775
  [(set (match_operand:SI 0 "register_operand" "")
776
        (ge:SI (match_dup 1)
777
               (match_dup 2)))]
778
  "!TARGET_64BIT"
779
  "
780
{
781
  /* fp scc patterns rarely match, and are not a win on the PA.  */
782
  if (hppa_branch_type != CMP_SI)
783
    FAIL;
784
  operands[1] = hppa_compare_op0;
785
  operands[2] = hppa_compare_op1;
786
}")
787
 
788
(define_expand "sltu"
789
  [(set (match_operand:SI 0 "register_operand" "")
790
        (ltu:SI (match_dup 1)
791
                (match_dup 2)))]
792
  "!TARGET_64BIT"
793
  "
794
{
795
  if (hppa_branch_type != CMP_SI)
796
    FAIL;
797
  operands[1] = hppa_compare_op0;
798
  operands[2] = hppa_compare_op1;
799
}")
800
 
801
(define_expand "sgtu"
802
  [(set (match_operand:SI 0 "register_operand" "")
803
        (gtu:SI (match_dup 1)
804
                (match_dup 2)))]
805
  "!TARGET_64BIT"
806
  "
807
{
808
  if (hppa_branch_type != CMP_SI)
809
    FAIL;
810
  operands[1] = hppa_compare_op0;
811
  operands[2] = hppa_compare_op1;
812
}")
813
 
814
(define_expand "sleu"
815
  [(set (match_operand:SI 0 "register_operand" "")
816
        (leu:SI (match_dup 1)
817
                (match_dup 2)))]
818
  "!TARGET_64BIT"
819
  "
820
{
821
  if (hppa_branch_type != CMP_SI)
822
    FAIL;
823
  operands[1] = hppa_compare_op0;
824
  operands[2] = hppa_compare_op1;
825
}")
826
 
827
(define_expand "sgeu"
828
  [(set (match_operand:SI 0 "register_operand" "")
829
        (geu:SI (match_dup 1)
830
                (match_dup 2)))]
831
  "!TARGET_64BIT"
832
  "
833
{
834
  if (hppa_branch_type != CMP_SI)
835
    FAIL;
836
  operands[1] = hppa_compare_op0;
837
  operands[2] = hppa_compare_op1;
838
}")
839
 
840
;; Instruction canonicalization puts immediate operands second, which
841
;; is the reverse of what we want.
842
 
843
(define_insn "scc"
844
  [(set (match_operand:SI 0 "register_operand" "=r")
845
        (match_operator:SI 3 "comparison_operator"
846
                           [(match_operand:SI 1 "register_operand" "r")
847
                            (match_operand:SI 2 "arith11_operand" "rI")]))]
848
  ""
849
  "{com%I2clr|cmp%I2clr},%B3 %2,%1,%0\;ldi 1,%0"
850
  [(set_attr "type" "binary")
851
   (set_attr "length" "8")])
852
 
853
(define_insn ""
854
  [(set (match_operand:DI 0 "register_operand" "=r")
855
        (match_operator:DI 3 "comparison_operator"
856
                           [(match_operand:DI 1 "register_operand" "r")
857
                            (match_operand:DI 2 "arith11_operand" "rI")]))]
858
  "TARGET_64BIT"
859
  "cmp%I2clr,*%B3 %2,%1,%0\;ldi 1,%0"
860
  [(set_attr "type" "binary")
861
   (set_attr "length" "8")])
862
 
863
(define_insn "iorscc"
864
  [(set (match_operand:SI 0 "register_operand" "=r")
865
        (ior:SI (match_operator:SI 3 "comparison_operator"
866
                                   [(match_operand:SI 1 "register_operand" "r")
867
                                    (match_operand:SI 2 "arith11_operand" "rI")])
868
                (match_operator:SI 6 "comparison_operator"
869
                                   [(match_operand:SI 4 "register_operand" "r")
870
                                    (match_operand:SI 5 "arith11_operand" "rI")])))]
871
  ""
872
  "{com%I2clr|cmp%I2clr},%S3 %2,%1,%%r0\;{com%I5clr|cmp%I5clr},%B6 %5,%4,%0\;ldi 1,%0"
873
  [(set_attr "type" "binary")
874
   (set_attr "length" "12")])
875
 
876
(define_insn ""
877
  [(set (match_operand:DI 0 "register_operand" "=r")
878
        (ior:DI (match_operator:DI 3 "comparison_operator"
879
                                   [(match_operand:DI 1 "register_operand" "r")
880
                                    (match_operand:DI 2 "arith11_operand" "rI")])
881
                (match_operator:DI 6 "comparison_operator"
882
                                   [(match_operand:DI 4 "register_operand" "r")
883
                                    (match_operand:DI 5 "arith11_operand" "rI")])))]
884
  "TARGET_64BIT"
885
  "cmp%I2clr,*%S3 %2,%1,%%r0\;cmp%I5clr,*%B6 %5,%4,%0\;ldi 1,%0"
886
  [(set_attr "type" "binary")
887
   (set_attr "length" "12")])
888
 
889
;; Combiner patterns for common operations performed with the output
890
;; from an scc insn (negscc and incscc).
891
(define_insn "negscc"
892
  [(set (match_operand:SI 0 "register_operand" "=r")
893
        (neg:SI (match_operator:SI 3 "comparison_operator"
894
               [(match_operand:SI 1 "register_operand" "r")
895
                (match_operand:SI 2 "arith11_operand" "rI")])))]
896
  ""
897
  "{com%I2clr|cmp%I2clr},%B3 %2,%1,%0\;ldi -1,%0"
898
  [(set_attr "type" "binary")
899
   (set_attr "length" "8")])
900
 
901
(define_insn ""
902
  [(set (match_operand:DI 0 "register_operand" "=r")
903
        (neg:DI (match_operator:DI 3 "comparison_operator"
904
               [(match_operand:DI 1 "register_operand" "r")
905
                (match_operand:DI 2 "arith11_operand" "rI")])))]
906
  "TARGET_64BIT"
907
  "cmp%I2clr,*%B3 %2,%1,%0\;ldi -1,%0"
908
  [(set_attr "type" "binary")
909
   (set_attr "length" "8")])
910
 
911
;; Patterns for adding/subtracting the result of a boolean expression from
912
;; a register.  First we have special patterns that make use of the carry
913
;; bit, and output only two instructions.  For the cases we can't in
914
;; general do in two instructions, the incscc pattern at the end outputs
915
;; two or three instructions.
916
 
917
(define_insn ""
918
  [(set (match_operand:SI 0 "register_operand" "=r")
919
        (plus:SI (leu:SI (match_operand:SI 2 "register_operand" "r")
920
                         (match_operand:SI 3 "arith11_operand" "rI"))
921
                 (match_operand:SI 1 "register_operand" "r")))]
922
  ""
923
  "sub%I3 %3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
924
  [(set_attr "type" "binary")
925
   (set_attr "length" "8")])
926
 
927
(define_insn ""
928
  [(set (match_operand:DI 0 "register_operand" "=r")
929
        (plus:DI (leu:DI (match_operand:DI 2 "register_operand" "r")
930
                         (match_operand:DI 3 "arith11_operand" "rI"))
931
                 (match_operand:DI 1 "register_operand" "r")))]
932
  "TARGET_64BIT"
933
  "sub%I3 %3,%2,%%r0\;add,dc %%r0,%1,%0"
934
  [(set_attr "type" "binary")
935
   (set_attr "length" "8")])
936
 
937
; This need only accept registers for op3, since canonicalization
938
; replaces geu with gtu when op3 is an integer.
939
(define_insn ""
940
  [(set (match_operand:SI 0 "register_operand" "=r")
941
        (plus:SI (geu:SI (match_operand:SI 2 "register_operand" "r")
942
                         (match_operand:SI 3 "register_operand" "r"))
943
                 (match_operand:SI 1 "register_operand" "r")))]
944
  ""
945
  "sub %2,%3,%%r0\;{addc|add,c} %%r0,%1,%0"
946
  [(set_attr "type" "binary")
947
   (set_attr "length" "8")])
948
 
949
(define_insn ""
950
  [(set (match_operand:DI 0 "register_operand" "=r")
951
        (plus:DI (geu:DI (match_operand:DI 2 "register_operand" "r")
952
                         (match_operand:DI 3 "register_operand" "r"))
953
                 (match_operand:DI 1 "register_operand" "r")))]
954
  "TARGET_64BIT"
955
  "sub %2,%3,%%r0\;add,dc %%r0,%1,%0"
956
  [(set_attr "type" "binary")
957
   (set_attr "length" "8")])
958
 
959
; Match only integers for op3 here.  This is used as canonical form of the
960
; geu pattern when op3 is an integer.  Don't match registers since we can't
961
; make better code than the general incscc pattern.
962
(define_insn ""
963
  [(set (match_operand:SI 0 "register_operand" "=r")
964
        (plus:SI (gtu:SI (match_operand:SI 2 "register_operand" "r")
965
                         (match_operand:SI 3 "int11_operand" "I"))
966
                 (match_operand:SI 1 "register_operand" "r")))]
967
  ""
968
  "addi %k3,%2,%%r0\;{addc|add,c} %%r0,%1,%0"
969
  [(set_attr "type" "binary")
970
   (set_attr "length" "8")])
971
 
972
(define_insn ""
973
  [(set (match_operand:DI 0 "register_operand" "=r")
974
        (plus:DI (gtu:DI (match_operand:DI 2 "register_operand" "r")
975
                         (match_operand:DI 3 "int11_operand" "I"))
976
                 (match_operand:DI 1 "register_operand" "r")))]
977
  "TARGET_64BIT"
978
  "addi %k3,%2,%%r0\;add,dc %%r0,%1,%0"
979
  [(set_attr "type" "binary")
980
   (set_attr "length" "8")])
981
 
982
(define_insn "incscc"
983
  [(set (match_operand:SI 0 "register_operand" "=r,r")
984
        (plus:SI (match_operator:SI 4 "comparison_operator"
985
                    [(match_operand:SI 2 "register_operand" "r,r")
986
                     (match_operand:SI 3 "arith11_operand" "rI,rI")])
987
                 (match_operand:SI 1 "register_operand" "0,?r")))]
988
  ""
989
  "@
990
   {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi 1,%0,%0
991
   {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
992
  [(set_attr "type" "binary,binary")
993
   (set_attr "length" "8,12")])
994
 
995
(define_insn ""
996
  [(set (match_operand:DI 0 "register_operand" "=r,r")
997
        (plus:DI (match_operator:DI 4 "comparison_operator"
998
                    [(match_operand:DI 2 "register_operand" "r,r")
999
                     (match_operand:DI 3 "arith11_operand" "rI,rI")])
1000
                 (match_operand:DI 1 "register_operand" "0,?r")))]
1001
  "TARGET_64BIT"
1002
  "@
1003
   cmp%I3clr,*%B4 %3,%2,%%r0\;addi 1,%0,%0
1004
   cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr 1,%1,%0\;copy %1,%0"
1005
  [(set_attr "type" "binary,binary")
1006
   (set_attr "length" "8,12")])
1007
 
1008
(define_insn ""
1009
  [(set (match_operand:SI 0 "register_operand" "=r")
1010
        (minus:SI (match_operand:SI 1 "register_operand" "r")
1011
                  (gtu:SI (match_operand:SI 2 "register_operand" "r")
1012
                          (match_operand:SI 3 "arith11_operand" "rI"))))]
1013
  ""
1014
  "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
1015
  [(set_attr "type" "binary")
1016
   (set_attr "length" "8")])
1017
 
1018
(define_insn ""
1019
  [(set (match_operand:DI 0 "register_operand" "=r")
1020
        (minus:DI (match_operand:DI 1 "register_operand" "r")
1021
                  (gtu:DI (match_operand:DI 2 "register_operand" "r")
1022
                          (match_operand:DI 3 "arith11_operand" "rI"))))]
1023
  "TARGET_64BIT"
1024
  "sub%I3 %3,%2,%%r0\;sub,db %1,%%r0,%0"
1025
  [(set_attr "type" "binary")
1026
   (set_attr "length" "8")])
1027
 
1028
(define_insn ""
1029
  [(set (match_operand:SI 0 "register_operand" "=r")
1030
        (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1031
                            (gtu:SI (match_operand:SI 2 "register_operand" "r")
1032
                                    (match_operand:SI 3 "arith11_operand" "rI")))
1033
                  (match_operand:SI 4 "register_operand" "r")))]
1034
  ""
1035
  "sub%I3 %3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
1036
  [(set_attr "type" "binary")
1037
   (set_attr "length" "8")])
1038
 
1039
(define_insn ""
1040
  [(set (match_operand:DI 0 "register_operand" "=r")
1041
        (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1042
                            (gtu:DI (match_operand:DI 2 "register_operand" "r")
1043
                                    (match_operand:DI 3 "arith11_operand" "rI")))
1044
                  (match_operand:DI 4 "register_operand" "r")))]
1045
  "TARGET_64BIT"
1046
  "sub%I3 %3,%2,%%r0\;sub,db %1,%4,%0"
1047
  [(set_attr "type" "binary")
1048
   (set_attr "length" "8")])
1049
 
1050
; This need only accept registers for op3, since canonicalization
1051
; replaces ltu with leu when op3 is an integer.
1052
(define_insn ""
1053
  [(set (match_operand:SI 0 "register_operand" "=r")
1054
        (minus:SI (match_operand:SI 1 "register_operand" "r")
1055
                  (ltu:SI (match_operand:SI 2 "register_operand" "r")
1056
                          (match_operand:SI 3 "register_operand" "r"))))]
1057
  ""
1058
  "sub %2,%3,%%r0\;{subb|sub,b} %1,%%r0,%0"
1059
  [(set_attr "type" "binary")
1060
   (set_attr "length" "8")])
1061
 
1062
(define_insn ""
1063
  [(set (match_operand:DI 0 "register_operand" "=r")
1064
        (minus:DI (match_operand:DI 1 "register_operand" "r")
1065
                  (ltu:DI (match_operand:DI 2 "register_operand" "r")
1066
                          (match_operand:DI 3 "register_operand" "r"))))]
1067
  "TARGET_64BIT"
1068
  "sub %2,%3,%%r0\;sub,db %1,%%r0,%0"
1069
  [(set_attr "type" "binary")
1070
   (set_attr "length" "8")])
1071
 
1072
(define_insn ""
1073
  [(set (match_operand:SI 0 "register_operand" "=r")
1074
        (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1075
                            (ltu:SI (match_operand:SI 2 "register_operand" "r")
1076
                                    (match_operand:SI 3 "register_operand" "r")))
1077
                  (match_operand:SI 4 "register_operand" "r")))]
1078
  ""
1079
  "sub %2,%3,%%r0\;{subb|sub,b} %1,%4,%0"
1080
  [(set_attr "type" "binary")
1081
   (set_attr "length" "8")])
1082
 
1083
(define_insn ""
1084
  [(set (match_operand:DI 0 "register_operand" "=r")
1085
        (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1086
                            (ltu:DI (match_operand:DI 2 "register_operand" "r")
1087
                                    (match_operand:DI 3 "register_operand" "r")))
1088
                  (match_operand:DI 4 "register_operand" "r")))]
1089
  "TARGET_64BIT"
1090
  "sub %2,%3,%%r0\;sub,db %1,%4,%0"
1091
  [(set_attr "type" "binary")
1092
   (set_attr "length" "8")])
1093
 
1094
; Match only integers for op3 here.  This is used as canonical form of the
1095
; ltu pattern when op3 is an integer.  Don't match registers since we can't
1096
; make better code than the general incscc pattern.
1097
(define_insn ""
1098
  [(set (match_operand:SI 0 "register_operand" "=r")
1099
        (minus:SI (match_operand:SI 1 "register_operand" "r")
1100
                  (leu:SI (match_operand:SI 2 "register_operand" "r")
1101
                          (match_operand:SI 3 "int11_operand" "I"))))]
1102
  ""
1103
  "addi %k3,%2,%%r0\;{subb|sub,b} %1,%%r0,%0"
1104
  [(set_attr "type" "binary")
1105
   (set_attr "length" "8")])
1106
 
1107
(define_insn ""
1108
  [(set (match_operand:DI 0 "register_operand" "=r")
1109
        (minus:DI (match_operand:DI 1 "register_operand" "r")
1110
                  (leu:DI (match_operand:DI 2 "register_operand" "r")
1111
                          (match_operand:DI 3 "int11_operand" "I"))))]
1112
  "TARGET_64BIT"
1113
  "addi %k3,%2,%%r0\;sub,db %1,%%r0,%0"
1114
  [(set_attr "type" "binary")
1115
   (set_attr "length" "8")])
1116
 
1117
(define_insn ""
1118
  [(set (match_operand:SI 0 "register_operand" "=r")
1119
        (minus:SI (minus:SI (match_operand:SI 1 "register_operand" "r")
1120
                            (leu:SI (match_operand:SI 2 "register_operand" "r")
1121
                                    (match_operand:SI 3 "int11_operand" "I")))
1122
                  (match_operand:SI 4 "register_operand" "r")))]
1123
  ""
1124
  "addi %k3,%2,%%r0\;{subb|sub,b} %1,%4,%0"
1125
  [(set_attr "type" "binary")
1126
   (set_attr "length" "8")])
1127
 
1128
(define_insn ""
1129
  [(set (match_operand:DI 0 "register_operand" "=r")
1130
        (minus:DI (minus:DI (match_operand:DI 1 "register_operand" "r")
1131
                            (leu:DI (match_operand:DI 2 "register_operand" "r")
1132
                                    (match_operand:DI 3 "int11_operand" "I")))
1133
                  (match_operand:DI 4 "register_operand" "r")))]
1134
  "TARGET_64BIT"
1135
  "addi %k3,%2,%%r0\;sub,db %1,%4,%0"
1136
  [(set_attr "type" "binary")
1137
   (set_attr "length" "8")])
1138
 
1139
(define_insn "decscc"
1140
  [(set (match_operand:SI 0 "register_operand" "=r,r")
1141
        (minus:SI (match_operand:SI 1 "register_operand" "0,?r")
1142
                  (match_operator:SI 4 "comparison_operator"
1143
                     [(match_operand:SI 2 "register_operand" "r,r")
1144
                      (match_operand:SI 3 "arith11_operand" "rI,rI")])))]
1145
  ""
1146
  "@
1147
   {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi -1,%0,%0
1148
   {com%I3clr|cmp%I3clr},%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1149
  [(set_attr "type" "binary,binary")
1150
   (set_attr "length" "8,12")])
1151
 
1152
(define_insn ""
1153
  [(set (match_operand:DI 0 "register_operand" "=r,r")
1154
        (minus:DI (match_operand:DI 1 "register_operand" "0,?r")
1155
                  (match_operator:DI 4 "comparison_operator"
1156
                     [(match_operand:DI 2 "register_operand" "r,r")
1157
                      (match_operand:DI 3 "arith11_operand" "rI,rI")])))]
1158
  "TARGET_64BIT"
1159
  "@
1160
   cmp%I3clr,*%B4 %3,%2,%%r0\;addi -1,%0,%0
1161
   cmp%I3clr,*%B4 %3,%2,%%r0\;addi,tr -1,%1,%0\;copy %1,%0"
1162
  [(set_attr "type" "binary,binary")
1163
   (set_attr "length" "8,12")])
1164
 
1165
; Patterns for max and min.  (There is no need for an earlyclobber in the
1166
; last alternative since the middle alternative will match if op0 == op1.)
1167
 
1168
(define_insn "sminsi3"
1169
  [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1170
        (smin:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1171
                 (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1172
  ""
1173
  "@
1174
  {comclr|cmpclr},> %2,%0,%%r0\;copy %2,%0
1175
  {comiclr|cmpiclr},> %2,%0,%%r0\;ldi %2,%0
1176
  {comclr|cmpclr},> %1,%r2,%0\;copy %1,%0"
1177
[(set_attr "type" "multi,multi,multi")
1178
 (set_attr "length" "8,8,8")])
1179
 
1180
(define_insn "smindi3"
1181
  [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1182
        (smin:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1183
                 (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1184
  "TARGET_64BIT"
1185
  "@
1186
  cmpclr,*> %2,%0,%%r0\;copy %2,%0
1187
  cmpiclr,*> %2,%0,%%r0\;ldi %2,%0
1188
  cmpclr,*> %1,%r2,%0\;copy %1,%0"
1189
[(set_attr "type" "multi,multi,multi")
1190
 (set_attr "length" "8,8,8")])
1191
 
1192
(define_insn "uminsi3"
1193
  [(set (match_operand:SI 0 "register_operand" "=r,r")
1194
        (umin:SI (match_operand:SI 1 "register_operand" "%0,0")
1195
                 (match_operand:SI 2 "arith11_operand" "r,I")))]
1196
  ""
1197
  "@
1198
  {comclr|cmpclr},>> %2,%0,%%r0\;copy %2,%0
1199
  {comiclr|cmpiclr},>> %2,%0,%%r0\;ldi %2,%0"
1200
[(set_attr "type" "multi,multi")
1201
 (set_attr "length" "8,8")])
1202
 
1203
(define_insn "umindi3"
1204
  [(set (match_operand:DI 0 "register_operand" "=r,r")
1205
        (umin:DI (match_operand:DI 1 "register_operand" "%0,0")
1206
                 (match_operand:DI 2 "arith11_operand" "r,I")))]
1207
  "TARGET_64BIT"
1208
  "@
1209
  cmpclr,*>> %2,%0,%%r0\;copy %2,%0
1210
  cmpiclr,*>> %2,%0,%%r0\;ldi %2,%0"
1211
[(set_attr "type" "multi,multi")
1212
 (set_attr "length" "8,8")])
1213
 
1214
(define_insn "smaxsi3"
1215
  [(set (match_operand:SI 0 "register_operand" "=r,r,r")
1216
        (smax:SI (match_operand:SI 1 "register_operand" "%0,0,r")
1217
                 (match_operand:SI 2 "arith11_operand" "r,I,M")))]
1218
  ""
1219
  "@
1220
  {comclr|cmpclr},< %2,%0,%%r0\;copy %2,%0
1221
  {comiclr|cmpiclr},< %2,%0,%%r0\;ldi %2,%0
1222
  {comclr|cmpclr},< %1,%r2,%0\;copy %1,%0"
1223
[(set_attr "type" "multi,multi,multi")
1224
 (set_attr "length" "8,8,8")])
1225
 
1226
(define_insn "smaxdi3"
1227
  [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1228
        (smax:DI (match_operand:DI 1 "register_operand" "%0,0,r")
1229
                 (match_operand:DI 2 "arith11_operand" "r,I,M")))]
1230
  "TARGET_64BIT"
1231
  "@
1232
  cmpclr,*< %2,%0,%%r0\;copy %2,%0
1233
  cmpiclr,*< %2,%0,%%r0\;ldi %2,%0
1234
  cmpclr,*< %1,%r2,%0\;copy %1,%0"
1235
[(set_attr "type" "multi,multi,multi")
1236
 (set_attr "length" "8,8,8")])
1237
 
1238
(define_insn "umaxsi3"
1239
  [(set (match_operand:SI 0 "register_operand" "=r,r")
1240
        (umax:SI (match_operand:SI 1 "register_operand" "%0,0")
1241
                 (match_operand:SI 2 "arith11_operand" "r,I")))]
1242
  ""
1243
  "@
1244
  {comclr|cmpclr},<< %2,%0,%%r0\;copy %2,%0
1245
  {comiclr|cmpiclr},<< %2,%0,%%r0\;ldi %2,%0"
1246
[(set_attr "type" "multi,multi")
1247
 (set_attr "length" "8,8")])
1248
 
1249
(define_insn "umaxdi3"
1250
  [(set (match_operand:DI 0 "register_operand" "=r,r")
1251
        (umax:DI (match_operand:DI 1 "register_operand" "%0,0")
1252
                 (match_operand:DI 2 "arith11_operand" "r,I")))]
1253
  "TARGET_64BIT"
1254
  "@
1255
  cmpclr,*<< %2,%0,%%r0\;copy %2,%0
1256
  cmpiclr,*<< %2,%0,%%r0\;ldi %2,%0"
1257
[(set_attr "type" "multi,multi")
1258
 (set_attr "length" "8,8")])
1259
 
1260
(define_insn "abssi2"
1261
  [(set (match_operand:SI 0 "register_operand" "=r")
1262
        (abs:SI (match_operand:SI 1 "register_operand" "r")))]
1263
  ""
1264
  "or,>= %%r0,%1,%0\;subi 0,%0,%0"
1265
  [(set_attr "type" "multi")
1266
   (set_attr "length" "8")])
1267
 
1268
(define_insn "absdi2"
1269
  [(set (match_operand:DI 0 "register_operand" "=r")
1270
        (abs:DI (match_operand:DI 1 "register_operand" "r")))]
1271
  "TARGET_64BIT"
1272
  "or,*>= %%r0,%1,%0\;subi 0,%0,%0"
1273
  [(set_attr "type" "multi")
1274
   (set_attr "length" "8")])
1275
 
1276
;;; Experimental conditional move patterns
1277
 
1278
(define_expand "movsicc"
1279
  [(set (match_operand:SI 0 "register_operand" "")
1280
        (if_then_else:SI
1281
         (match_operator 1 "comparison_operator"
1282
            [(match_dup 4)
1283
             (match_dup 5)])
1284
         (match_operand:SI 2 "reg_or_cint_move_operand" "")
1285
         (match_operand:SI 3 "reg_or_cint_move_operand" "")))]
1286
  ""
1287
  "
1288
{
1289
  enum rtx_code code = GET_CODE (operands[1]);
1290
 
1291
  if (hppa_branch_type != CMP_SI)
1292
    FAIL;
1293
 
1294
  if (GET_MODE (hppa_compare_op0) != GET_MODE (hppa_compare_op1)
1295
      || GET_MODE (hppa_compare_op0) != GET_MODE (operands[0]))
1296
    FAIL;
1297
 
1298
  /* operands[1] is currently the result of compare_from_rtx.  We want to
1299
     emit a compare of the original operands.  */
1300
  operands[1] = gen_rtx_fmt_ee (code, SImode, hppa_compare_op0, hppa_compare_op1);
1301
  operands[4] = hppa_compare_op0;
1302
  operands[5] = hppa_compare_op1;
1303
}")
1304
 
1305
;; We used to accept any register for op1.
1306
;;
1307
;; However, it loses sometimes because the compiler will end up using
1308
;; different registers for op0 and op1 in some critical cases.  local-alloc
1309
;; will  not tie op0 and op1 because op0 is used in multiple basic blocks.
1310
;;
1311
;; If/when global register allocation supports tying we should allow any
1312
;; register for op1 again.
1313
(define_insn ""
1314
  [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
1315
        (if_then_else:SI
1316
         (match_operator 2 "comparison_operator"
1317
            [(match_operand:SI 3 "register_operand" "r,r,r,r")
1318
             (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI")])
1319
         (match_operand:SI 1 "reg_or_cint_move_operand" "0,J,N,K")
1320
         (const_int 0)))]
1321
  ""
1322
  "@
1323
   {com%I4clr|cmp%I4clr},%S2 %4,%3,%%r0\;ldi 0,%0
1324
   {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldi %1,%0
1325
   {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;ldil L'%1,%0
1326
   {com%I4clr|cmp%I4clr},%B2 %4,%3,%0\;{zdepi|depwi,z} %Z1,%0"
1327
  [(set_attr "type" "multi,multi,multi,nullshift")
1328
   (set_attr "length" "8,8,8,8")])
1329
 
1330
(define_insn ""
1331
  [(set (match_operand:SI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1332
        (if_then_else:SI
1333
         (match_operator 5 "comparison_operator"
1334
            [(match_operand:SI 3 "register_operand" "r,r,r,r,r,r,r,r")
1335
             (match_operand:SI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1336
         (match_operand:SI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1337
         (match_operand:SI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1338
  ""
1339
  "@
1340
   {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;copy %2,%0
1341
   {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldi %2,%0
1342
   {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;ldil L'%2,%0
1343
   {com%I4clr|cmp%I4clr},%S5 %4,%3,%%r0\;{zdepi|depwi,z} %Z2,%0
1344
   {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;copy %1,%0
1345
   {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldi %1,%0
1346
   {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;ldil L'%1,%0
1347
   {com%I4clr|cmp%I4clr},%B5 %4,%3,%%r0\;{zdepi|depwi,z} %Z1,%0"
1348
  [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1349
   (set_attr "length" "8,8,8,8,8,8,8,8")])
1350
 
1351
(define_expand "movdicc"
1352
  [(set (match_operand:DI 0 "register_operand" "")
1353
        (if_then_else:DI
1354
         (match_operator 1 "comparison_operator"
1355
            [(match_dup 4)
1356
             (match_dup 5)])
1357
         (match_operand:DI 2 "reg_or_cint_move_operand" "")
1358
         (match_operand:DI 3 "reg_or_cint_move_operand" "")))]
1359
  "TARGET_64BIT"
1360
  "
1361
{
1362
  enum rtx_code code = GET_CODE (operands[1]);
1363
 
1364
  if (hppa_branch_type != CMP_SI)
1365
    FAIL;
1366
 
1367
  if (GET_MODE (hppa_compare_op0) != GET_MODE (hppa_compare_op1)
1368
      || GET_MODE (hppa_compare_op0) != GET_MODE (operands[0]))
1369
    FAIL;
1370
 
1371
  /* operands[1] is currently the result of compare_from_rtx.  We want to
1372
     emit a compare of the original operands.  */
1373
  operands[1] = gen_rtx_fmt_ee (code, DImode, hppa_compare_op0, hppa_compare_op1);
1374
  operands[4] = hppa_compare_op0;
1375
  operands[5] = hppa_compare_op1;
1376
}")
1377
 
1378
; We need the first constraint alternative in order to avoid
1379
; earlyclobbers on all other alternatives.
1380
(define_insn ""
1381
  [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r")
1382
        (if_then_else:DI
1383
         (match_operator 2 "comparison_operator"
1384
            [(match_operand:DI 3 "register_operand" "r,r,r,r,r")
1385
             (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI")])
1386
         (match_operand:DI 1 "reg_or_cint_move_operand" "0,r,J,N,K")
1387
         (const_int 0)))]
1388
  "TARGET_64BIT"
1389
  "@
1390
   cmp%I4clr,*%S2 %4,%3,%%r0\;ldi 0,%0
1391
   cmp%I4clr,*%B2 %4,%3,%0\;copy %1,%0
1392
   cmp%I4clr,*%B2 %4,%3,%0\;ldi %1,%0
1393
   cmp%I4clr,*%B2 %4,%3,%0\;ldil L'%1,%0
1394
   cmp%I4clr,*%B2 %4,%3,%0\;depdi,z %z1,%0"
1395
  [(set_attr "type" "multi,multi,multi,multi,nullshift")
1396
   (set_attr "length" "8,8,8,8,8")])
1397
 
1398
(define_insn ""
1399
  [(set (match_operand:DI 0 "register_operand" "=r,r,r,r,r,r,r,r")
1400
        (if_then_else:DI
1401
         (match_operator 5 "comparison_operator"
1402
            [(match_operand:DI 3 "register_operand" "r,r,r,r,r,r,r,r")
1403
             (match_operand:DI 4 "arith11_operand" "rI,rI,rI,rI,rI,rI,rI,rI")])
1404
         (match_operand:DI 1 "reg_or_cint_move_operand" "0,0,0,0,r,J,N,K")
1405
         (match_operand:DI 2 "reg_or_cint_move_operand" "r,J,N,K,0,0,0,0")))]
1406
  "TARGET_64BIT"
1407
  "@
1408
   cmp%I4clr,*%S5 %4,%3,%%r0\;copy %2,%0
1409
   cmp%I4clr,*%S5 %4,%3,%%r0\;ldi %2,%0
1410
   cmp%I4clr,*%S5 %4,%3,%%r0\;ldil L'%2,%0
1411
   cmp%I4clr,*%S5 %4,%3,%%r0\;depdi,z %z2,%0
1412
   cmp%I4clr,*%B5 %4,%3,%%r0\;copy %1,%0
1413
   cmp%I4clr,*%B5 %4,%3,%%r0\;ldi %1,%0
1414
   cmp%I4clr,*%B5 %4,%3,%%r0\;ldil L'%1,%0
1415
   cmp%I4clr,*%B5 %4,%3,%%r0\;depdi,z %z1,%0"
1416
  [(set_attr "type" "multi,multi,multi,nullshift,multi,multi,multi,nullshift")
1417
   (set_attr "length" "8,8,8,8,8,8,8,8")])
1418
 
1419
;; Conditional Branches
1420
 
1421
(define_expand "beq"
1422
  [(set (pc)
1423
        (if_then_else (eq (match_dup 1) (match_dup 2))
1424
                      (label_ref (match_operand 0 "" ""))
1425
                      (pc)))]
1426
  ""
1427
  "
1428
{
1429
  if (hppa_branch_type != CMP_SI)
1430
    {
1431
      emit_insn (gen_cmp_fp (EQ, hppa_compare_op0, hppa_compare_op1));
1432
      emit_bcond_fp (NE, operands[0]);
1433
      DONE;
1434
    }
1435
  /* set up operands from compare.  */
1436
  operands[1] = hppa_compare_op0;
1437
  operands[2] = hppa_compare_op1;
1438
  /* fall through and generate default code */
1439
}")
1440
 
1441
(define_expand "bne"
1442
  [(set (pc)
1443
        (if_then_else (ne (match_dup 1) (match_dup 2))
1444
                      (label_ref (match_operand 0 "" ""))
1445
                      (pc)))]
1446
  ""
1447
  "
1448
{
1449
  if (hppa_branch_type != CMP_SI)
1450
    {
1451
      emit_insn (gen_cmp_fp (NE, hppa_compare_op0, hppa_compare_op1));
1452
      emit_bcond_fp (NE, operands[0]);
1453
      DONE;
1454
    }
1455
  operands[1] = hppa_compare_op0;
1456
  operands[2] = hppa_compare_op1;
1457
}")
1458
 
1459
(define_expand "bgt"
1460
  [(set (pc)
1461
        (if_then_else (gt (match_dup 1) (match_dup 2))
1462
                      (label_ref (match_operand 0 "" ""))
1463
                      (pc)))]
1464
  ""
1465
  "
1466
{
1467
  if (hppa_branch_type != CMP_SI)
1468
    {
1469
      emit_insn (gen_cmp_fp (GT, hppa_compare_op0, hppa_compare_op1));
1470
      emit_bcond_fp (NE, operands[0]);
1471
      DONE;
1472
    }
1473
  operands[1] = hppa_compare_op0;
1474
  operands[2] = hppa_compare_op1;
1475
}")
1476
 
1477
(define_expand "blt"
1478
  [(set (pc)
1479
        (if_then_else (lt (match_dup 1) (match_dup 2))
1480
                      (label_ref (match_operand 0 "" ""))
1481
                      (pc)))]
1482
  ""
1483
  "
1484
{
1485
  if (hppa_branch_type != CMP_SI)
1486
    {
1487
      emit_insn (gen_cmp_fp (LT, hppa_compare_op0, hppa_compare_op1));
1488
      emit_bcond_fp (NE, operands[0]);
1489
      DONE;
1490
    }
1491
  operands[1] = hppa_compare_op0;
1492
  operands[2] = hppa_compare_op1;
1493
}")
1494
 
1495
(define_expand "bge"
1496
  [(set (pc)
1497
        (if_then_else (ge (match_dup 1) (match_dup 2))
1498
                      (label_ref (match_operand 0 "" ""))
1499
                      (pc)))]
1500
  ""
1501
  "
1502
{
1503
  if (hppa_branch_type != CMP_SI)
1504
    {
1505
      emit_insn (gen_cmp_fp (GE, hppa_compare_op0, hppa_compare_op1));
1506
      emit_bcond_fp (NE, operands[0]);
1507
      DONE;
1508
    }
1509
  operands[1] = hppa_compare_op0;
1510
  operands[2] = hppa_compare_op1;
1511
}")
1512
 
1513
(define_expand "ble"
1514
  [(set (pc)
1515
        (if_then_else (le (match_dup 1) (match_dup 2))
1516
                      (label_ref (match_operand 0 "" ""))
1517
                      (pc)))]
1518
  ""
1519
  "
1520
{
1521
  if (hppa_branch_type != CMP_SI)
1522
    {
1523
      emit_insn (gen_cmp_fp (LE, hppa_compare_op0, hppa_compare_op1));
1524
      emit_bcond_fp (NE, operands[0]);
1525
      DONE;
1526
    }
1527
  operands[1] = hppa_compare_op0;
1528
  operands[2] = hppa_compare_op1;
1529
}")
1530
 
1531
(define_expand "bgtu"
1532
  [(set (pc)
1533
        (if_then_else (gtu (match_dup 1) (match_dup 2))
1534
                      (label_ref (match_operand 0 "" ""))
1535
                      (pc)))]
1536
  ""
1537
  "
1538
{
1539
  if (hppa_branch_type != CMP_SI)
1540
    FAIL;
1541
  operands[1] = hppa_compare_op0;
1542
  operands[2] = hppa_compare_op1;
1543
}")
1544
 
1545
(define_expand "bltu"
1546
  [(set (pc)
1547
        (if_then_else (ltu (match_dup 1) (match_dup 2))
1548
                      (label_ref (match_operand 0 "" ""))
1549
                      (pc)))]
1550
  ""
1551
  "
1552
{
1553
  if (hppa_branch_type != CMP_SI)
1554
    FAIL;
1555
  operands[1] = hppa_compare_op0;
1556
  operands[2] = hppa_compare_op1;
1557
}")
1558
 
1559
(define_expand "bgeu"
1560
  [(set (pc)
1561
        (if_then_else (geu (match_dup 1) (match_dup 2))
1562
                      (label_ref (match_operand 0 "" ""))
1563
                      (pc)))]
1564
  ""
1565
  "
1566
{
1567
  if (hppa_branch_type != CMP_SI)
1568
    FAIL;
1569
  operands[1] = hppa_compare_op0;
1570
  operands[2] = hppa_compare_op1;
1571
}")
1572
 
1573
(define_expand "bleu"
1574
  [(set (pc)
1575
        (if_then_else (leu (match_dup 1) (match_dup 2))
1576
                      (label_ref (match_operand 0 "" ""))
1577
                      (pc)))]
1578
  ""
1579
  "
1580
{
1581
  if (hppa_branch_type != CMP_SI)
1582
    FAIL;
1583
  operands[1] = hppa_compare_op0;
1584
  operands[2] = hppa_compare_op1;
1585
}")
1586
 
1587
(define_expand "bltgt"
1588
  [(set (pc)
1589
        (if_then_else (ltgt (match_dup 1) (match_dup 2))
1590
                      (label_ref (match_operand 0 "" ""))
1591
                      (pc)))]
1592
  ""
1593
  "
1594
{
1595
  if (hppa_branch_type == CMP_SI)
1596
    FAIL;
1597
  emit_insn (gen_cmp_fp (LTGT, hppa_compare_op0, hppa_compare_op1));
1598
  emit_bcond_fp (NE, operands[0]);
1599
  DONE;
1600
}")
1601
 
1602
(define_expand "bunle"
1603
  [(set (pc)
1604
        (if_then_else (unle (match_dup 1) (match_dup 2))
1605
                      (label_ref (match_operand 0 "" ""))
1606
                      (pc)))]
1607
  ""
1608
  "
1609
{
1610
  if (hppa_branch_type == CMP_SI)
1611
    FAIL;
1612
  emit_insn (gen_cmp_fp (UNLE, hppa_compare_op0, hppa_compare_op1));
1613
  emit_bcond_fp (NE, operands[0]);
1614
  DONE;
1615
}")
1616
 
1617
(define_expand "bunlt"
1618
  [(set (pc)
1619
        (if_then_else (unlt (match_dup 1) (match_dup 2))
1620
                      (label_ref (match_operand 0 "" ""))
1621
                      (pc)))]
1622
  ""
1623
  "
1624
{
1625
  if (hppa_branch_type == CMP_SI)
1626
    FAIL;
1627
  emit_insn (gen_cmp_fp (UNLT, hppa_compare_op0, hppa_compare_op1));
1628
  emit_bcond_fp (NE, operands[0]);
1629
  DONE;
1630
}")
1631
 
1632
(define_expand "bunge"
1633
  [(set (pc)
1634
        (if_then_else (unge (match_dup 1) (match_dup 2))
1635
                      (label_ref (match_operand 0 "" ""))
1636
                      (pc)))]
1637
  ""
1638
  "
1639
{
1640
  if (hppa_branch_type == CMP_SI)
1641
    FAIL;
1642
  emit_insn (gen_cmp_fp (UNGE, hppa_compare_op0, hppa_compare_op1));
1643
  emit_bcond_fp (NE, operands[0]);
1644
  DONE;
1645
}")
1646
 
1647
(define_expand "bungt"
1648
  [(set (pc)
1649
        (if_then_else (ungt (match_dup 1) (match_dup 2))
1650
                      (label_ref (match_operand 0 "" ""))
1651
                      (pc)))]
1652
  ""
1653
  "
1654
{
1655
  if (hppa_branch_type == CMP_SI)
1656
    FAIL;
1657
  emit_insn (gen_cmp_fp (UNGT, hppa_compare_op0, hppa_compare_op1));
1658
  emit_bcond_fp (NE, operands[0]);
1659
  DONE;
1660
}")
1661
 
1662
(define_expand "buneq"
1663
  [(set (pc)
1664
        (if_then_else (uneq (match_dup 1) (match_dup 2))
1665
                      (label_ref (match_operand 0 "" ""))
1666
                      (pc)))]
1667
  ""
1668
  "
1669
{
1670
  if (hppa_branch_type == CMP_SI)
1671
    FAIL;
1672
  emit_insn (gen_cmp_fp (UNEQ, hppa_compare_op0, hppa_compare_op1));
1673
  emit_bcond_fp (NE, operands[0]);
1674
  DONE;
1675
}")
1676
 
1677
(define_expand "bunordered"
1678
  [(set (pc)
1679
        (if_then_else (unordered (match_dup 1) (match_dup 2))
1680
                      (label_ref (match_operand 0 "" ""))
1681
                      (pc)))]
1682
  ""
1683
  "
1684
{
1685
  if (hppa_branch_type == CMP_SI)
1686
    FAIL;
1687
  emit_insn (gen_cmp_fp (UNORDERED, hppa_compare_op0, hppa_compare_op1));
1688
  emit_bcond_fp (NE, operands[0]);
1689
  DONE;
1690
}")
1691
 
1692
(define_expand "bordered"
1693
  [(set (pc)
1694
        (if_then_else (ordered (match_dup 1) (match_dup 2))
1695
                      (label_ref (match_operand 0 "" ""))
1696
                      (pc)))]
1697
  ""
1698
  "
1699
{
1700
  if (hppa_branch_type == CMP_SI)
1701
    FAIL;
1702
  emit_insn (gen_cmp_fp (ORDERED, hppa_compare_op0, hppa_compare_op1));
1703
  emit_bcond_fp (NE, operands[0]);
1704
  DONE;
1705
}")
1706
 
1707
;; Match the branch patterns.
1708
 
1709
 
1710
;; Note a long backward conditional branch with an annulled delay slot
1711
;; has a length of 12.
1712
(define_insn ""
1713
  [(set (pc)
1714
        (if_then_else
1715
         (match_operator 3 "comparison_operator"
1716
                         [(match_operand:SI 1 "reg_or_0_operand" "rM")
1717
                          (match_operand:SI 2 "arith5_operand" "rL")])
1718
         (label_ref (match_operand 0 "" ""))
1719
         (pc)))]
1720
  ""
1721
  "*
1722
{
1723
  return output_cbranch (operands, 0, insn);
1724
}"
1725
[(set_attr "type" "cbranch")
1726
 (set (attr "length")
1727
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1728
               (const_int MAX_12BIT_OFFSET))
1729
           (const_int 4)
1730
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1731
               (const_int MAX_17BIT_OFFSET))
1732
           (const_int 8)
1733
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1734
           (const_int 24)
1735
           (eq (symbol_ref "flag_pic") (const_int 0))
1736
           (const_int 20)]
1737
          (const_int 28)))])
1738
 
1739
;; Match the negated branch.
1740
 
1741
(define_insn ""
1742
  [(set (pc)
1743
        (if_then_else
1744
         (match_operator 3 "comparison_operator"
1745
                         [(match_operand:SI 1 "reg_or_0_operand" "rM")
1746
                          (match_operand:SI 2 "arith5_operand" "rL")])
1747
         (pc)
1748
         (label_ref (match_operand 0 "" ""))))]
1749
  ""
1750
  "*
1751
{
1752
  return output_cbranch (operands, 1, insn);
1753
}"
1754
[(set_attr "type" "cbranch")
1755
 (set (attr "length")
1756
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1757
               (const_int MAX_12BIT_OFFSET))
1758
           (const_int 4)
1759
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1760
               (const_int MAX_17BIT_OFFSET))
1761
           (const_int 8)
1762
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1763
           (const_int 24)
1764
           (eq (symbol_ref "flag_pic") (const_int 0))
1765
           (const_int 20)]
1766
          (const_int 28)))])
1767
 
1768
(define_insn ""
1769
  [(set (pc)
1770
        (if_then_else
1771
         (match_operator 3 "comparison_operator"
1772
                         [(match_operand:DI 1 "reg_or_0_operand" "rM")
1773
                          (match_operand:DI 2 "reg_or_0_operand" "rM")])
1774
         (label_ref (match_operand 0 "" ""))
1775
         (pc)))]
1776
  "TARGET_64BIT"
1777
  "*
1778
{
1779
  return output_cbranch (operands, 0, insn);
1780
}"
1781
[(set_attr "type" "cbranch")
1782
 (set (attr "length")
1783
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1784
               (const_int MAX_12BIT_OFFSET))
1785
           (const_int 4)
1786
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1787
               (const_int MAX_17BIT_OFFSET))
1788
           (const_int 8)
1789
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1790
           (const_int 24)
1791
           (eq (symbol_ref "flag_pic") (const_int 0))
1792
           (const_int 20)]
1793
          (const_int 28)))])
1794
 
1795
;; Match the negated branch.
1796
 
1797
(define_insn ""
1798
  [(set (pc)
1799
        (if_then_else
1800
         (match_operator 3 "comparison_operator"
1801
                         [(match_operand:DI 1 "reg_or_0_operand" "rM")
1802
                          (match_operand:DI 2 "reg_or_0_operand" "rM")])
1803
         (pc)
1804
         (label_ref (match_operand 0 "" ""))))]
1805
  "TARGET_64BIT"
1806
  "*
1807
{
1808
  return output_cbranch (operands, 1, insn);
1809
}"
1810
[(set_attr "type" "cbranch")
1811
 (set (attr "length")
1812
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1813
               (const_int MAX_12BIT_OFFSET))
1814
           (const_int 4)
1815
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1816
               (const_int MAX_17BIT_OFFSET))
1817
           (const_int 8)
1818
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1819
           (const_int 24)
1820
           (eq (symbol_ref "flag_pic") (const_int 0))
1821
           (const_int 20)]
1822
          (const_int 28)))])
1823
(define_insn ""
1824
  [(set (pc)
1825
        (if_then_else
1826
         (match_operator 3 "cmpib_comparison_operator"
1827
                         [(match_operand:DI 1 "reg_or_0_operand" "rM")
1828
                          (match_operand:DI 2 "arith5_operand" "rL")])
1829
         (label_ref (match_operand 0 "" ""))
1830
         (pc)))]
1831
  "TARGET_64BIT"
1832
  "*
1833
{
1834
  return output_cbranch (operands, 0, insn);
1835
}"
1836
[(set_attr "type" "cbranch")
1837
 (set (attr "length")
1838
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1839
               (const_int MAX_12BIT_OFFSET))
1840
           (const_int 4)
1841
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1842
               (const_int MAX_17BIT_OFFSET))
1843
           (const_int 8)
1844
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1845
           (const_int 24)
1846
           (eq (symbol_ref "flag_pic") (const_int 0))
1847
           (const_int 20)]
1848
          (const_int 28)))])
1849
 
1850
;; Match the negated branch.
1851
 
1852
(define_insn ""
1853
  [(set (pc)
1854
        (if_then_else
1855
         (match_operator 3 "cmpib_comparison_operator"
1856
                         [(match_operand:DI 1 "reg_or_0_operand" "rM")
1857
                          (match_operand:DI 2 "arith5_operand" "rL")])
1858
         (pc)
1859
         (label_ref (match_operand 0 "" ""))))]
1860
  "TARGET_64BIT"
1861
  "*
1862
{
1863
  return output_cbranch (operands, 1, insn);
1864
}"
1865
[(set_attr "type" "cbranch")
1866
 (set (attr "length")
1867
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1868
               (const_int MAX_12BIT_OFFSET))
1869
           (const_int 4)
1870
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
1871
               (const_int MAX_17BIT_OFFSET))
1872
           (const_int 8)
1873
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1874
           (const_int 24)
1875
           (eq (symbol_ref "flag_pic") (const_int 0))
1876
           (const_int 20)]
1877
          (const_int 28)))])
1878
 
1879
;; Branch on Bit patterns.
1880
(define_insn ""
1881
  [(set (pc)
1882
        (if_then_else
1883
         (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1884
                              (const_int 1)
1885
                              (match_operand:SI 1 "uint5_operand" ""))
1886
             (const_int 0))
1887
         (label_ref (match_operand 2 "" ""))
1888
         (pc)))]
1889
  ""
1890
  "*
1891
{
1892
  return output_bb (operands, 0, insn, 0);
1893
}"
1894
[(set_attr "type" "cbranch")
1895
 (set (attr "length")
1896
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1897
               (const_int MAX_12BIT_OFFSET))
1898
           (const_int 4)
1899
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1900
               (const_int MAX_17BIT_OFFSET))
1901
           (const_int 8)
1902
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1903
           (const_int 24)
1904
           (eq (symbol_ref "flag_pic") (const_int 0))
1905
           (const_int 20)]
1906
          (const_int 28)))])
1907
 
1908
(define_insn ""
1909
  [(set (pc)
1910
        (if_then_else
1911
         (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1912
                              (const_int 1)
1913
                              (match_operand:DI 1 "uint32_operand" ""))
1914
             (const_int 0))
1915
         (label_ref (match_operand 2 "" ""))
1916
         (pc)))]
1917
  "TARGET_64BIT"
1918
  "*
1919
{
1920
  return output_bb (operands, 0, insn, 0);
1921
}"
1922
[(set_attr "type" "cbranch")
1923
 (set (attr "length")
1924
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1925
               (const_int MAX_12BIT_OFFSET))
1926
           (const_int 4)
1927
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1928
               (const_int MAX_17BIT_OFFSET))
1929
           (const_int 8)
1930
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1931
           (const_int 24)
1932
           (eq (symbol_ref "flag_pic") (const_int 0))
1933
           (const_int 20)]
1934
          (const_int 28)))])
1935
 
1936
(define_insn ""
1937
  [(set (pc)
1938
        (if_then_else
1939
         (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1940
                              (const_int 1)
1941
                              (match_operand:SI 1 "uint5_operand" ""))
1942
             (const_int 0))
1943
         (pc)
1944
         (label_ref (match_operand 2 "" ""))))]
1945
  ""
1946
  "*
1947
{
1948
  return output_bb (operands, 1, insn, 0);
1949
}"
1950
[(set_attr "type" "cbranch")
1951
 (set (attr "length")
1952
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1953
               (const_int MAX_12BIT_OFFSET))
1954
           (const_int 4)
1955
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1956
               (const_int MAX_17BIT_OFFSET))
1957
           (const_int 8)
1958
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1959
           (const_int 24)
1960
           (eq (symbol_ref "flag_pic") (const_int 0))
1961
           (const_int 20)]
1962
          (const_int 28)))])
1963
 
1964
(define_insn ""
1965
  [(set (pc)
1966
        (if_then_else
1967
         (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
1968
                              (const_int 1)
1969
                              (match_operand:DI 1 "uint32_operand" ""))
1970
             (const_int 0))
1971
         (pc)
1972
         (label_ref (match_operand 2 "" ""))))]
1973
  "TARGET_64BIT"
1974
  "*
1975
{
1976
  return output_bb (operands, 1, insn, 0);
1977
}"
1978
[(set_attr "type" "cbranch")
1979
 (set (attr "length")
1980
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1981
               (const_int MAX_12BIT_OFFSET))
1982
           (const_int 4)
1983
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
1984
               (const_int MAX_17BIT_OFFSET))
1985
           (const_int 8)
1986
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
1987
           (const_int 24)
1988
           (eq (symbol_ref "flag_pic") (const_int 0))
1989
           (const_int 20)]
1990
          (const_int 28)))])
1991
 
1992
(define_insn ""
1993
  [(set (pc)
1994
        (if_then_else
1995
         (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
1996
                              (const_int 1)
1997
                              (match_operand:SI 1 "uint5_operand" ""))
1998
             (const_int 0))
1999
         (label_ref (match_operand 2 "" ""))
2000
         (pc)))]
2001
  ""
2002
  "*
2003
{
2004
  return output_bb (operands, 0, insn, 1);
2005
}"
2006
[(set_attr "type" "cbranch")
2007
 (set (attr "length")
2008
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2009
               (const_int MAX_12BIT_OFFSET))
2010
           (const_int 4)
2011
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2012
               (const_int MAX_17BIT_OFFSET))
2013
           (const_int 8)
2014
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2015
           (const_int 24)
2016
           (eq (symbol_ref "flag_pic") (const_int 0))
2017
           (const_int 20)]
2018
          (const_int 28)))])
2019
 
2020
(define_insn ""
2021
  [(set (pc)
2022
        (if_then_else
2023
         (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2024
                              (const_int 1)
2025
                              (match_operand:DI 1 "uint32_operand" ""))
2026
             (const_int 0))
2027
         (label_ref (match_operand 2 "" ""))
2028
         (pc)))]
2029
  "TARGET_64BIT"
2030
  "*
2031
{
2032
  return output_bb (operands, 0, insn, 1);
2033
}"
2034
[(set_attr "type" "cbranch")
2035
 (set (attr "length")
2036
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2037
               (const_int MAX_12BIT_OFFSET))
2038
           (const_int 4)
2039
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2040
               (const_int MAX_17BIT_OFFSET))
2041
           (const_int 8)
2042
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2043
           (const_int 24)
2044
           (eq (symbol_ref "flag_pic") (const_int 0))
2045
           (const_int 20)]
2046
          (const_int 28)))])
2047
 
2048
(define_insn ""
2049
  [(set (pc)
2050
        (if_then_else
2051
         (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2052
                              (const_int 1)
2053
                              (match_operand:SI 1 "uint5_operand" ""))
2054
             (const_int 0))
2055
         (pc)
2056
         (label_ref (match_operand 2 "" ""))))]
2057
  ""
2058
  "*
2059
{
2060
  return output_bb (operands, 1, insn, 1);
2061
}"
2062
[(set_attr "type" "cbranch")
2063
 (set (attr "length")
2064
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2065
               (const_int MAX_12BIT_OFFSET))
2066
           (const_int 4)
2067
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2068
               (const_int MAX_17BIT_OFFSET))
2069
           (const_int 8)
2070
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2071
           (const_int 24)
2072
           (eq (symbol_ref "flag_pic") (const_int 0))
2073
           (const_int 20)]
2074
          (const_int 28)))])
2075
 
2076
(define_insn ""
2077
  [(set (pc)
2078
        (if_then_else
2079
         (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2080
                              (const_int 1)
2081
                              (match_operand:DI 1 "uint32_operand" ""))
2082
             (const_int 0))
2083
         (pc)
2084
         (label_ref (match_operand 2 "" ""))))]
2085
  "TARGET_64BIT"
2086
  "*
2087
{
2088
  return output_bb (operands, 1, insn, 1);
2089
}"
2090
[(set_attr "type" "cbranch")
2091
 (set (attr "length")
2092
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2093
               (const_int MAX_12BIT_OFFSET))
2094
           (const_int 4)
2095
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2096
               (const_int MAX_17BIT_OFFSET))
2097
           (const_int 8)
2098
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2099
           (const_int 24)
2100
           (eq (symbol_ref "flag_pic") (const_int 0))
2101
           (const_int 20)]
2102
          (const_int 28)))])
2103
 
2104
;; Branch on Variable Bit patterns.
2105
(define_insn ""
2106
  [(set (pc)
2107
        (if_then_else
2108
         (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2109
                              (const_int 1)
2110
                              (match_operand:SI 1 "register_operand" "q"))
2111
             (const_int 0))
2112
         (label_ref (match_operand 2 "" ""))
2113
         (pc)))]
2114
  ""
2115
  "*
2116
{
2117
  return output_bvb (operands, 0, insn, 0);
2118
}"
2119
[(set_attr "type" "cbranch")
2120
 (set (attr "length")
2121
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2122
               (const_int MAX_12BIT_OFFSET))
2123
           (const_int 4)
2124
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2125
               (const_int MAX_17BIT_OFFSET))
2126
           (const_int 8)
2127
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2128
           (const_int 24)
2129
           (eq (symbol_ref "flag_pic") (const_int 0))
2130
           (const_int 20)]
2131
          (const_int 28)))])
2132
 
2133
(define_insn ""
2134
  [(set (pc)
2135
        (if_then_else
2136
         (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2137
                              (const_int 1)
2138
                              (match_operand:DI 1 "register_operand" "q"))
2139
             (const_int 0))
2140
         (label_ref (match_operand 2 "" ""))
2141
         (pc)))]
2142
  "TARGET_64BIT"
2143
  "*
2144
{
2145
  return output_bvb (operands, 0, insn, 0);
2146
}"
2147
[(set_attr "type" "cbranch")
2148
 (set (attr "length")
2149
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2150
               (const_int MAX_12BIT_OFFSET))
2151
           (const_int 4)
2152
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2153
               (const_int MAX_17BIT_OFFSET))
2154
           (const_int 8)
2155
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2156
           (const_int 24)
2157
           (eq (symbol_ref "flag_pic") (const_int 0))
2158
           (const_int 20)]
2159
          (const_int 28)))])
2160
 
2161
(define_insn ""
2162
  [(set (pc)
2163
        (if_then_else
2164
         (ne (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2165
                              (const_int 1)
2166
                              (match_operand:SI 1 "register_operand" "q"))
2167
             (const_int 0))
2168
         (pc)
2169
         (label_ref (match_operand 2 "" ""))))]
2170
  ""
2171
  "*
2172
{
2173
  return output_bvb (operands, 1, insn, 0);
2174
}"
2175
[(set_attr "type" "cbranch")
2176
 (set (attr "length")
2177
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2178
               (const_int MAX_12BIT_OFFSET))
2179
           (const_int 4)
2180
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2181
               (const_int MAX_17BIT_OFFSET))
2182
           (const_int 8)
2183
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2184
           (const_int 24)
2185
           (eq (symbol_ref "flag_pic") (const_int 0))
2186
           (const_int 20)]
2187
          (const_int 28)))])
2188
 
2189
(define_insn ""
2190
  [(set (pc)
2191
        (if_then_else
2192
         (ne (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2193
                              (const_int 1)
2194
                              (match_operand:DI 1 "register_operand" "q"))
2195
             (const_int 0))
2196
         (pc)
2197
         (label_ref (match_operand 2 "" ""))))]
2198
  "TARGET_64BIT"
2199
  "*
2200
{
2201
  return output_bvb (operands, 1, insn, 0);
2202
}"
2203
[(set_attr "type" "cbranch")
2204
 (set (attr "length")
2205
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2206
               (const_int MAX_12BIT_OFFSET))
2207
           (const_int 4)
2208
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2209
               (const_int MAX_17BIT_OFFSET))
2210
           (const_int 8)
2211
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2212
           (const_int 24)
2213
           (eq (symbol_ref "flag_pic") (const_int 0))
2214
           (const_int 20)]
2215
          (const_int 28)))])
2216
 
2217
(define_insn ""
2218
  [(set (pc)
2219
        (if_then_else
2220
         (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2221
                              (const_int 1)
2222
                              (match_operand:SI 1 "register_operand" "q"))
2223
             (const_int 0))
2224
         (label_ref (match_operand 2 "" ""))
2225
         (pc)))]
2226
  ""
2227
  "*
2228
{
2229
  return output_bvb (operands, 0, insn, 1);
2230
}"
2231
[(set_attr "type" "cbranch")
2232
 (set (attr "length")
2233
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2234
               (const_int MAX_12BIT_OFFSET))
2235
           (const_int 4)
2236
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2237
               (const_int MAX_17BIT_OFFSET))
2238
           (const_int 8)
2239
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2240
           (const_int 24)
2241
           (eq (symbol_ref "flag_pic") (const_int 0))
2242
           (const_int 20)]
2243
          (const_int 28)))])
2244
 
2245
(define_insn ""
2246
  [(set (pc)
2247
        (if_then_else
2248
         (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2249
                              (const_int 1)
2250
                              (match_operand:DI 1 "register_operand" "q"))
2251
             (const_int 0))
2252
         (label_ref (match_operand 2 "" ""))
2253
         (pc)))]
2254
  "TARGET_64BIT"
2255
  "*
2256
{
2257
  return output_bvb (operands, 0, insn, 1);
2258
}"
2259
[(set_attr "type" "cbranch")
2260
 (set (attr "length")
2261
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2262
               (const_int MAX_12BIT_OFFSET))
2263
           (const_int 4)
2264
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2265
               (const_int MAX_17BIT_OFFSET))
2266
           (const_int 8)
2267
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2268
           (const_int 24)
2269
           (eq (symbol_ref "flag_pic") (const_int 0))
2270
           (const_int 20)]
2271
          (const_int 28)))])
2272
 
2273
(define_insn ""
2274
  [(set (pc)
2275
        (if_then_else
2276
         (eq (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
2277
                              (const_int 1)
2278
                              (match_operand:SI 1 "register_operand" "q"))
2279
             (const_int 0))
2280
         (pc)
2281
         (label_ref (match_operand 2 "" ""))))]
2282
  ""
2283
  "*
2284
{
2285
  return output_bvb (operands, 1, insn, 1);
2286
}"
2287
[(set_attr "type" "cbranch")
2288
 (set (attr "length")
2289
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2290
               (const_int MAX_12BIT_OFFSET))
2291
           (const_int 4)
2292
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2293
               (const_int MAX_17BIT_OFFSET))
2294
           (const_int 8)
2295
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2296
           (const_int 24)
2297
           (eq (symbol_ref "flag_pic") (const_int 0))
2298
           (const_int 20)]
2299
          (const_int 28)))])
2300
 
2301
(define_insn ""
2302
  [(set (pc)
2303
        (if_then_else
2304
         (eq (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
2305
                              (const_int 1)
2306
                              (match_operand:DI 1 "register_operand" "q"))
2307
             (const_int 0))
2308
         (pc)
2309
         (label_ref (match_operand 2 "" ""))))]
2310
  "TARGET_64BIT"
2311
  "*
2312
{
2313
  return output_bvb (operands, 1, insn, 1);
2314
}"
2315
[(set_attr "type" "cbranch")
2316
 (set (attr "length")
2317
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2318
               (const_int MAX_12BIT_OFFSET))
2319
           (const_int 4)
2320
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
2321
               (const_int MAX_17BIT_OFFSET))
2322
           (const_int 8)
2323
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2324
           (const_int 24)
2325
           (eq (symbol_ref "flag_pic") (const_int 0))
2326
           (const_int 20)]
2327
          (const_int 28)))])
2328
 
2329
;; Floating point branches
2330
 
2331
;; ??? Nullification is handled differently from other branches.
2332
;; If nullification is specified, the delay slot is nullified on any
2333
;; taken branch regardless of branch direction.
2334
(define_insn ""
2335
  [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2336
                           (label_ref (match_operand 0 "" ""))
2337
                           (pc)))]
2338
  "!TARGET_SOFT_FLOAT"
2339
  "*
2340
{
2341
  int length = get_attr_length (insn);
2342
  rtx xoperands[1];
2343
  int nullify, xdelay;
2344
 
2345
  if (length < 16)
2346
    return \"ftest\;b%* %l0\";
2347
 
2348
  if (dbr_sequence_length () == 0 || INSN_ANNULLED_BRANCH_P (insn))
2349
    {
2350
      nullify = 1;
2351
      xdelay = 0;
2352
      xoperands[0] = GEN_INT (length - 8);
2353
    }
2354
  else
2355
    {
2356
      nullify = 0;
2357
      xdelay = 1;
2358
      xoperands[0] = GEN_INT (length - 4);
2359
    }
2360
 
2361
  if (nullify)
2362
    output_asm_insn (\"ftest\;add,tr %%r0,%%r0,%%r0\;b,n .+%0\", xoperands);
2363
  else
2364
    output_asm_insn (\"ftest\;add,tr %%r0,%%r0,%%r0\;b .+%0\", xoperands);
2365
  return output_lbranch (operands[0], insn, xdelay);
2366
}"
2367
[(set_attr "type" "fbranch")
2368
 (set (attr "length")
2369
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
2370
               (const_int MAX_17BIT_OFFSET))
2371
           (const_int 8)
2372
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2373
           (const_int 32)
2374
           (eq (symbol_ref "flag_pic") (const_int 0))
2375
           (const_int 28)]
2376
          (const_int 36)))])
2377
 
2378
(define_insn ""
2379
  [(set (pc) (if_then_else (ne (reg:CCFP 0) (const_int 0))
2380
                           (pc)
2381
                           (label_ref (match_operand 0 "" ""))))]
2382
  "!TARGET_SOFT_FLOAT"
2383
  "*
2384
{
2385
  int length = get_attr_length (insn);
2386
  rtx xoperands[1];
2387
  int nullify, xdelay;
2388
 
2389
  if (length < 16)
2390
    return \"ftest\;add,tr %%r0,%%r0,%%r0\;b%* %0\";
2391
 
2392
  if (dbr_sequence_length () == 0 || INSN_ANNULLED_BRANCH_P (insn))
2393
    {
2394
      nullify = 1;
2395
      xdelay = 0;
2396
      xoperands[0] = GEN_INT (length - 4);
2397
    }
2398
  else
2399
    {
2400
      nullify = 0;
2401
      xdelay = 1;
2402
      xoperands[0] = GEN_INT (length);
2403
    }
2404
 
2405
  if (nullify)
2406
    output_asm_insn (\"ftest\;b,n .+%0\", xoperands);
2407
  else
2408
    output_asm_insn (\"ftest\;b .+%0\", xoperands);
2409
  return output_lbranch (operands[0], insn, xdelay);
2410
}"
2411
[(set_attr "type" "fbranch")
2412
 (set (attr "length")
2413
    (cond [(lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
2414
               (const_int MAX_17BIT_OFFSET))
2415
           (const_int 12)
2416
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
2417
           (const_int 28)
2418
           (eq (symbol_ref "flag_pic") (const_int 0))
2419
           (const_int 24)]
2420
          (const_int 32)))])
2421
 
2422
;; Move instructions
2423
 
2424
(define_expand "movsi"
2425
  [(set (match_operand:SI 0 "general_operand" "")
2426
        (match_operand:SI 1 "general_operand" ""))]
2427
  ""
2428
  "
2429
{
2430
  if (emit_move_sequence (operands, SImode, 0))
2431
    DONE;
2432
}")
2433
 
2434
;; Handle SImode input reloads requiring %r1 as a scratch register.
2435
(define_expand "reload_insi_r1"
2436
  [(set (match_operand:SI 0 "register_operand" "=Z")
2437
        (match_operand:SI 1 "non_hard_reg_operand" ""))
2438
   (clobber (match_operand:SI 2 "register_operand" "=&a"))]
2439
  ""
2440
  "
2441
{
2442
  if (emit_move_sequence (operands, SImode, operands[2]))
2443
    DONE;
2444
 
2445
  /* We don't want the clobber emitted, so handle this ourselves.  */
2446
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2447
  DONE;
2448
}")
2449
 
2450
;; Handle SImode input reloads requiring a general register as a
2451
;; scratch register.
2452
(define_expand "reload_insi"
2453
  [(set (match_operand:SI 0 "register_operand" "=Z")
2454
        (match_operand:SI 1 "non_hard_reg_operand" ""))
2455
   (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2456
  ""
2457
  "
2458
{
2459
  if (emit_move_sequence (operands, SImode, operands[2]))
2460
    DONE;
2461
 
2462
  /* We don't want the clobber emitted, so handle this ourselves.  */
2463
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2464
  DONE;
2465
}")
2466
 
2467
;; Handle SImode output reloads requiring a general register as a
2468
;; scratch register.
2469
(define_expand "reload_outsi"
2470
  [(set (match_operand:SI 0 "non_hard_reg_operand" "")
2471
        (match_operand:SI 1  "register_operand" "Z"))
2472
   (clobber (match_operand:SI 2 "register_operand" "=&r"))]
2473
  ""
2474
  "
2475
{
2476
  if (emit_move_sequence (operands, SImode, operands[2]))
2477
    DONE;
2478
 
2479
  /* We don't want the clobber emitted, so handle this ourselves.  */
2480
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
2481
  DONE;
2482
}")
2483
 
2484
(define_insn ""
2485
  [(set (match_operand:SI 0 "move_dest_operand"
2486
                          "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T,?r,?*f")
2487
        (match_operand:SI 1 "move_src_operand"
2488
                          "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f,*f,r"))]
2489
  "(register_operand (operands[0], SImode)
2490
    || reg_or_0_operand (operands[1], SImode))
2491
   && !TARGET_SOFT_FLOAT
2492
   && !TARGET_64BIT"
2493
  "@
2494
   ldw RT'%A1,%0
2495
   copy %1,%0
2496
   ldi %1,%0
2497
   ldil L'%1,%0
2498
   {zdepi|depwi,z} %Z1,%0
2499
   ldw%M1 %1,%0
2500
   stw%M0 %r1,%0
2501
   mtsar %r1
2502
   {mfctl|mfctl,w} %%sar,%0
2503
   fcpy,sgl %f1,%0
2504
   fldw%F1 %1,%0
2505
   fstw%F0 %1,%0
2506
   {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
2507
   {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
2508
  [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore,move,move")
2509
   (set_attr "pa_combine_type" "addmove")
2510
   (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4,8,8")])
2511
 
2512
(define_insn ""
2513
  [(set (match_operand:SI 0 "move_dest_operand"
2514
                          "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T")
2515
        (match_operand:SI 1 "move_src_operand"
2516
                          "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f"))]
2517
  "(register_operand (operands[0], SImode)
2518
    || reg_or_0_operand (operands[1], SImode))
2519
   && !TARGET_SOFT_FLOAT
2520
   && TARGET_64BIT"
2521
  "@
2522
   ldw RT'%A1,%0
2523
   copy %1,%0
2524
   ldi %1,%0
2525
   ldil L'%1,%0
2526
   {zdepi|depwi,z} %Z1,%0
2527
   ldw%M1 %1,%0
2528
   stw%M0 %r1,%0
2529
   mtsar %r1
2530
   {mfctl|mfctl,w} %%sar,%0
2531
   fcpy,sgl %f1,%0
2532
   fldw%F1 %1,%0
2533
   fstw%F0 %1,%0"
2534
  [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore")
2535
   (set_attr "pa_combine_type" "addmove")
2536
   (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4")])
2537
 
2538
(define_insn ""
2539
  [(set (match_operand:SI 0 "indexed_memory_operand" "=R")
2540
        (match_operand:SI 1 "register_operand" "f"))]
2541
  "!TARGET_SOFT_FLOAT
2542
   && !TARGET_DISABLE_INDEXING
2543
   && reload_completed"
2544
  "fstw%F0 %1,%0"
2545
  [(set_attr "type" "fpstore")
2546
   (set_attr "pa_combine_type" "addmove")
2547
   (set_attr "length" "4")])
2548
 
2549
; Rewrite RTL using an indexed store.  This will allow the insn that
2550
; computes the address to be deleted if the register it sets is dead.
2551
(define_peephole2
2552
  [(set (match_operand:SI 0 "register_operand" "")
2553
        (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
2554
                          (const_int 4))
2555
                 (match_operand:SI 2 "register_operand" "")))
2556
   (set (mem:SI (match_dup 0))
2557
        (match_operand:SI 3 "register_operand" ""))]
2558
  "!TARGET_SOFT_FLOAT
2559
   && !TARGET_DISABLE_INDEXING
2560
   && REG_OK_FOR_BASE_P (operands[2])
2561
   && FP_REGNO_P (REGNO (operands[3]))"
2562
  [(set (mem:SI (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
2563
        (match_dup 3))
2564
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
2565
                               (match_dup 2)))]
2566
  "")
2567
 
2568
(define_peephole2
2569
  [(set (match_operand:SI 0 "register_operand" "")
2570
        (plus:SI (match_operand:SI 2 "register_operand" "")
2571
                 (mult:SI (match_operand:SI 1 "register_operand" "")
2572
                          (const_int 4))))
2573
   (set (mem:SI (match_dup 0))
2574
        (match_operand:SI 3 "register_operand" ""))]
2575
  "!TARGET_SOFT_FLOAT
2576
   && !TARGET_DISABLE_INDEXING
2577
   && REG_OK_FOR_BASE_P (operands[2])
2578
   && FP_REGNO_P (REGNO (operands[3]))"
2579
  [(set (mem:SI (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
2580
        (match_dup 3))
2581
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
2582
                               (match_dup 2)))]
2583
  "")
2584
 
2585
(define_peephole2
2586
  [(set (match_operand:DI 0 "register_operand" "")
2587
        (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
2588
                          (const_int 4))
2589
                 (match_operand:DI 2 "register_operand" "")))
2590
   (set (mem:SI (match_dup 0))
2591
        (match_operand:SI 3 "register_operand" ""))]
2592
  "!TARGET_SOFT_FLOAT
2593
   && !TARGET_DISABLE_INDEXING
2594
   && TARGET_64BIT
2595
   && REG_OK_FOR_BASE_P (operands[2])
2596
   && FP_REGNO_P (REGNO (operands[3]))"
2597
  [(set (mem:SI (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
2598
        (match_dup 3))
2599
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
2600
                               (match_dup 2)))]
2601
  "")
2602
 
2603
(define_peephole2
2604
  [(set (match_operand:DI 0 "register_operand" "")
2605
        (plus:DI (match_operand:DI 2 "register_operand" "")
2606
                 (mult:DI (match_operand:DI 1 "register_operand" "")
2607
                          (const_int 4))))
2608
   (set (mem:SI (match_dup 0))
2609
        (match_operand:SI 3 "register_operand" ""))]
2610
  "!TARGET_SOFT_FLOAT
2611
   && !TARGET_DISABLE_INDEXING
2612
   && TARGET_64BIT
2613
   && REG_OK_FOR_BASE_P (operands[2])
2614
   && FP_REGNO_P (REGNO (operands[3]))"
2615
  [(set (mem:SI (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
2616
        (match_dup 3))
2617
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
2618
                               (match_dup 2)))]
2619
  "")
2620
 
2621
(define_peephole2
2622
  [(set (match_operand:SI 0 "register_operand" "")
2623
        (plus:SI (match_operand:SI 1 "register_operand" "")
2624
                 (match_operand:SI 2 "register_operand" "")))
2625
   (set (mem:SI (match_dup 0))
2626
        (match_operand:SI 3 "register_operand" ""))]
2627
  "!TARGET_SOFT_FLOAT
2628
   && !TARGET_DISABLE_INDEXING
2629
   && TARGET_NO_SPACE_REGS
2630
   && REG_OK_FOR_INDEX_P (operands[1])
2631
   && REG_OK_FOR_BASE_P (operands[2])
2632
   && FP_REGNO_P (REGNO (operands[3]))"
2633
  [(set (mem:SI (plus:SI (match_dup 1) (match_dup 2)))
2634
        (match_dup 3))
2635
   (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2636
  "")
2637
 
2638
(define_peephole2
2639
  [(set (match_operand:SI 0 "register_operand" "")
2640
        (plus:SI (match_operand:SI 1 "register_operand" "")
2641
                 (match_operand:SI 2 "register_operand" "")))
2642
   (set (mem:SI (match_dup 0))
2643
        (match_operand:SI 3 "register_operand" ""))]
2644
  "!TARGET_SOFT_FLOAT
2645
   && !TARGET_DISABLE_INDEXING
2646
   && TARGET_NO_SPACE_REGS
2647
   && REG_OK_FOR_BASE_P (operands[1])
2648
   && REG_OK_FOR_INDEX_P (operands[2])
2649
   && FP_REGNO_P (REGNO (operands[3]))"
2650
  [(set (mem:SI (plus:SI (match_dup 2) (match_dup 1)))
2651
        (match_dup 3))
2652
   (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
2653
  "")
2654
 
2655
(define_peephole2
2656
  [(set (match_operand:DI 0 "register_operand" "")
2657
        (plus:DI (match_operand:DI 1 "register_operand" "")
2658
                 (match_operand:DI 2 "register_operand" "")))
2659
   (set (mem:SI (match_dup 0))
2660
        (match_operand:SI 3 "register_operand" ""))]
2661
  "!TARGET_SOFT_FLOAT
2662
   && !TARGET_DISABLE_INDEXING
2663
   && TARGET_64BIT
2664
   && TARGET_NO_SPACE_REGS
2665
   && REG_OK_FOR_INDEX_P (operands[1])
2666
   && REG_OK_FOR_BASE_P (operands[2])
2667
   && FP_REGNO_P (REGNO (operands[3]))"
2668
  [(set (mem:SI (plus:DI (match_dup 1) (match_dup 2)))
2669
        (match_dup 3))
2670
   (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
2671
  "")
2672
 
2673
(define_peephole2
2674
  [(set (match_operand:DI 0 "register_operand" "")
2675
        (plus:DI (match_operand:DI 1 "register_operand" "")
2676
                 (match_operand:DI 2 "register_operand" "")))
2677
   (set (mem:SI (match_dup 0))
2678
        (match_operand:SI 3 "register_operand" ""))]
2679
  "!TARGET_SOFT_FLOAT
2680
   && !TARGET_DISABLE_INDEXING
2681
   && TARGET_64BIT
2682
   && TARGET_NO_SPACE_REGS
2683
   && REG_OK_FOR_BASE_P (operands[1])
2684
   && REG_OK_FOR_INDEX_P (operands[2])
2685
   && FP_REGNO_P (REGNO (operands[3]))"
2686
  [(set (mem:SI (plus:DI (match_dup 2) (match_dup 1)))
2687
        (match_dup 3))
2688
   (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
2689
  "")
2690
 
2691
(define_insn ""
2692
  [(set (match_operand:SI 0 "move_dest_operand"
2693
                          "=r,r,r,r,r,r,Q,!*q,!r")
2694
        (match_operand:SI 1 "move_src_operand"
2695
                          "A,r,J,N,K,RQ,rM,!rM,!*q"))]
2696
  "(register_operand (operands[0], SImode)
2697
    || reg_or_0_operand (operands[1], SImode))
2698
   && TARGET_SOFT_FLOAT"
2699
  "@
2700
   ldw RT'%A1,%0
2701
   copy %1,%0
2702
   ldi %1,%0
2703
   ldil L'%1,%0
2704
   {zdepi|depwi,z} %Z1,%0
2705
   ldw%M1 %1,%0
2706
   stw%M0 %r1,%0
2707
   mtsar %r1
2708
   {mfctl|mfctl,w} %%sar,%0"
2709
  [(set_attr "type" "load,move,move,move,move,load,store,move,move")
2710
   (set_attr "pa_combine_type" "addmove")
2711
   (set_attr "length" "4,4,4,4,4,4,4,4,4")])
2712
 
2713
;; Load or store with base-register modification.
2714
(define_insn ""
2715
  [(set (match_operand:SI 0 "register_operand" "=r")
2716
        (mem:SI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2717
                         (match_operand:DI 2 "int5_operand" "L"))))
2718
   (set (match_dup 1)
2719
        (plus:DI (match_dup 1) (match_dup 2)))]
2720
  "TARGET_64BIT"
2721
  "ldw,mb %2(%1),%0"
2722
  [(set_attr "type" "load")
2723
   (set_attr "length" "4")])
2724
 
2725
; And a zero extended variant.
2726
(define_insn ""
2727
  [(set (match_operand:DI 0 "register_operand" "=r")
2728
        (zero_extend:DI (mem:SI
2729
                          (plus:DI
2730
                            (match_operand:DI 1 "register_operand" "+r")
2731
                            (match_operand:DI 2 "int5_operand" "L")))))
2732
   (set (match_dup 1)
2733
        (plus:DI (match_dup 1) (match_dup 2)))]
2734
  "TARGET_64BIT"
2735
  "ldw,mb %2(%1),%0"
2736
  [(set_attr "type" "load")
2737
   (set_attr "length" "4")])
2738
 
2739
(define_expand "pre_load"
2740
  [(parallel [(set (match_operand:SI 0 "register_operand" "")
2741
              (mem (plus (match_operand 1 "register_operand" "")
2742
                               (match_operand 2 "pre_cint_operand" ""))))
2743
              (set (match_dup 1)
2744
                   (plus (match_dup 1) (match_dup 2)))])]
2745
  ""
2746
  "
2747
{
2748
  if (TARGET_64BIT)
2749
    {
2750
      emit_insn (gen_pre_ldd (operands[0], operands[1], operands[2]));
2751
      DONE;
2752
    }
2753
  emit_insn (gen_pre_ldw (operands[0], operands[1], operands[2]));
2754
  DONE;
2755
}")
2756
 
2757
(define_insn "pre_ldw"
2758
  [(set (match_operand:SI 0 "register_operand" "=r")
2759
        (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "+r")
2760
                         (match_operand:SI 2 "pre_cint_operand" ""))))
2761
   (set (match_dup 1)
2762
        (plus:SI (match_dup 1) (match_dup 2)))]
2763
  ""
2764
  "*
2765
{
2766
  if (INTVAL (operands[2]) < 0)
2767
    return \"{ldwm|ldw,mb} %2(%1),%0\";
2768
  return \"{ldws|ldw},mb %2(%1),%0\";
2769
}"
2770
  [(set_attr "type" "load")
2771
   (set_attr "length" "4")])
2772
 
2773
(define_insn "pre_ldd"
2774
  [(set (match_operand:DI 0 "register_operand" "=r")
2775
        (mem:DI (plus:DI (match_operand:DI 1 "register_operand" "+r")
2776
                         (match_operand:DI 2 "pre_cint_operand" ""))))
2777
   (set (match_dup 1)
2778
        (plus:DI (match_dup 1) (match_dup 2)))]
2779
  "TARGET_64BIT"
2780
  "ldd,mb %2(%1),%0"
2781
  [(set_attr "type" "load")
2782
   (set_attr "length" "4")])
2783
 
2784
(define_insn ""
2785
  [(set (mem:SI (plus:SI (match_operand:SI 0 "register_operand" "+r")
2786
                         (match_operand:SI 1 "pre_cint_operand" "")))
2787
        (match_operand:SI 2 "reg_or_0_operand" "rM"))
2788
   (set (match_dup 0)
2789
        (plus:SI (match_dup 0) (match_dup 1)))]
2790
  ""
2791
  "*
2792
{
2793
  if (INTVAL (operands[1]) < 0)
2794
    return \"{stwm|stw,mb} %r2,%1(%0)\";
2795
  return \"{stws|stw},mb %r2,%1(%0)\";
2796
}"
2797
  [(set_attr "type" "store")
2798
   (set_attr "length" "4")])
2799
 
2800
(define_insn ""
2801
  [(set (match_operand:SI 0 "register_operand" "=r")
2802
        (mem:SI (match_operand:SI 1 "register_operand" "+r")))
2803
   (set (match_dup 1)
2804
        (plus:SI (match_dup 1)
2805
                 (match_operand:SI 2 "post_cint_operand" "")))]
2806
  ""
2807
  "*
2808
{
2809
  if (INTVAL (operands[2]) > 0)
2810
    return \"{ldwm|ldw,ma} %2(%1),%0\";
2811
  return \"{ldws|ldw},ma %2(%1),%0\";
2812
}"
2813
  [(set_attr "type" "load")
2814
   (set_attr "length" "4")])
2815
 
2816
(define_expand "post_store"
2817
  [(parallel [(set (mem (match_operand 0 "register_operand" ""))
2818
                   (match_operand 1 "reg_or_0_operand" ""))
2819
              (set (match_dup 0)
2820
                   (plus (match_dup 0)
2821
                         (match_operand 2 "post_cint_operand" "")))])]
2822
  ""
2823
  "
2824
{
2825
  if (TARGET_64BIT)
2826
    {
2827
      emit_insn (gen_post_std (operands[0], operands[1], operands[2]));
2828
      DONE;
2829
    }
2830
  emit_insn (gen_post_stw (operands[0], operands[1], operands[2]));
2831
  DONE;
2832
}")
2833
 
2834
(define_insn "post_stw"
2835
  [(set (mem:SI (match_operand:SI 0 "register_operand" "+r"))
2836
        (match_operand:SI 1 "reg_or_0_operand" "rM"))
2837
   (set (match_dup 0)
2838
        (plus:SI (match_dup 0)
2839
                 (match_operand:SI 2 "post_cint_operand" "")))]
2840
  ""
2841
  "*
2842
{
2843
  if (INTVAL (operands[2]) > 0)
2844
    return \"{stwm|stw,ma} %r1,%2(%0)\";
2845
  return \"{stws|stw},ma %r1,%2(%0)\";
2846
}"
2847
  [(set_attr "type" "store")
2848
   (set_attr "length" "4")])
2849
 
2850
(define_insn "post_std"
2851
  [(set (mem:DI (match_operand:DI 0 "register_operand" "+r"))
2852
        (match_operand:DI 1 "reg_or_0_operand" "rM"))
2853
   (set (match_dup 0)
2854
        (plus:DI (match_dup 0)
2855
                 (match_operand:DI 2 "post_cint_operand" "")))]
2856
  "TARGET_64BIT"
2857
  "std,ma %r1,%2(%0)"
2858
  [(set_attr "type" "store")
2859
   (set_attr "length" "4")])
2860
 
2861
;; For loading the address of a label while generating PIC code.
2862
;; Note since this pattern can be created at reload time (via movsi), all
2863
;; the same rules for movsi apply here.  (no new pseudos, no temporaries).
2864
(define_insn ""
2865
  [(set (match_operand 0 "pmode_register_operand" "=a")
2866
        (match_operand 1 "pic_label_operand" ""))]
2867
  "TARGET_PA_20"
2868
  "*
2869
{
2870
  rtx xoperands[3];
2871
 
2872
  xoperands[0] = operands[0];
2873
  xoperands[1] = operands[1];
2874
  xoperands[2] = gen_label_rtx ();
2875
 
2876
  (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
2877
                                     CODE_LABEL_NUMBER (xoperands[2]));
2878
  output_asm_insn (\"mfia %0\", xoperands);
2879
 
2880
  /* If we're trying to load the address of a label that happens to be
2881
     close, then we can use a shorter sequence.  */
2882
  if (GET_CODE (operands[1]) == LABEL_REF
2883
      && !LABEL_REF_NONLOCAL_P (operands[1])
2884
      && INSN_ADDRESSES_SET_P ()
2885
      && abs (INSN_ADDRESSES (INSN_UID (XEXP (operands[1], 0)))
2886
                - INSN_ADDRESSES (INSN_UID (insn))) < 8100)
2887
    output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands);
2888
  else
2889
    {
2890
      output_asm_insn (\"addil L%%%1-%2,%0\", xoperands);
2891
      output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands);
2892
    }
2893
  return \"\";
2894
}"
2895
  [(set_attr "type" "multi")
2896
   (set_attr "length" "12")])           ; 8 or 12
2897
 
2898
(define_insn ""
2899
  [(set (match_operand 0 "pmode_register_operand" "=a")
2900
        (match_operand 1 "pic_label_operand" ""))]
2901
  "!TARGET_PA_20"
2902
  "*
2903
{
2904
  rtx xoperands[3];
2905
 
2906
  xoperands[0] = operands[0];
2907
  xoperands[1] = operands[1];
2908
  xoperands[2] = gen_label_rtx ();
2909
 
2910
  output_asm_insn (\"bl .+8,%0\", xoperands);
2911
  output_asm_insn (\"depi 0,31,2,%0\", xoperands);
2912
  (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
2913
                                     CODE_LABEL_NUMBER (xoperands[2]));
2914
 
2915
  /* If we're trying to load the address of a label that happens to be
2916
     close, then we can use a shorter sequence.  */
2917
  if (GET_CODE (operands[1]) == LABEL_REF
2918
      && !LABEL_REF_NONLOCAL_P (operands[1])
2919
      && INSN_ADDRESSES_SET_P ()
2920
      && abs (INSN_ADDRESSES (INSN_UID (XEXP (operands[1], 0)))
2921
                - INSN_ADDRESSES (INSN_UID (insn))) < 8100)
2922
    output_asm_insn (\"ldo %1-%2(%0),%0\", xoperands);
2923
  else
2924
    {
2925
      output_asm_insn (\"addil L%%%1-%2,%0\", xoperands);
2926
      output_asm_insn (\"ldo R%%%1-%2(%0),%0\", xoperands);
2927
    }
2928
  return \"\";
2929
}"
2930
  [(set_attr "type" "multi")
2931
   (set_attr "length" "16")])           ; 12 or 16
2932
 
2933
(define_insn ""
2934
  [(set (match_operand:SI 0 "register_operand" "=a")
2935
        (plus:SI (match_operand:SI 1 "register_operand" "r")
2936
                 (high:SI (match_operand 2 "" ""))))]
2937
  "symbolic_operand (operands[2], Pmode)
2938
   && ! function_label_operand (operands[2], Pmode)
2939
   && flag_pic"
2940
  "addil LT'%G2,%1"
2941
  [(set_attr "type" "binary")
2942
   (set_attr "length" "4")])
2943
 
2944
(define_insn ""
2945
  [(set (match_operand:DI 0 "register_operand" "=a")
2946
        (plus:DI (match_operand:DI 1 "register_operand" "r")
2947
                 (high:DI (match_operand 2 "" ""))))]
2948
  "symbolic_operand (operands[2], Pmode)
2949
   && ! function_label_operand (operands[2], Pmode)
2950
   && TARGET_64BIT
2951
   && flag_pic"
2952
  "addil LT'%G2,%1"
2953
  [(set_attr "type" "binary")
2954
   (set_attr "length" "4")])
2955
 
2956
;; Always use addil rather than ldil;add sequences.  This allows the
2957
;; HP linker to eliminate the dp relocation if the symbolic operand
2958
;; lives in the TEXT space.
2959
(define_insn ""
2960
  [(set (match_operand:SI 0 "register_operand" "=a")
2961
        (high:SI (match_operand 1 "" "")))]
2962
  "symbolic_operand (operands[1], Pmode)
2963
   && ! function_label_operand (operands[1], Pmode)
2964
   && ! read_only_operand (operands[1], Pmode)
2965
   && ! flag_pic"
2966
  "*
2967
{
2968
  if (TARGET_LONG_LOAD_STORE)
2969
    return \"addil NLR'%H1,%%r27\;ldo N'%H1(%%r1),%%r1\";
2970
  else
2971
    return \"addil LR'%H1,%%r27\";
2972
}"
2973
  [(set_attr "type" "binary")
2974
   (set (attr "length")
2975
      (if_then_else (eq (symbol_ref "TARGET_LONG_LOAD_STORE") (const_int 0))
2976
                    (const_int 4)
2977
                    (const_int 8)))])
2978
 
2979
 
2980
;; This is for use in the prologue/epilogue code.  We need it
2981
;; to add large constants to a stack pointer or frame pointer.
2982
;; Because of the additional %r1 pressure, we probably do not
2983
;; want to use this in general code, so make it available
2984
;; only after reload.
2985
(define_insn ""
2986
  [(set (match_operand:SI 0 "register_operand" "=!a,*r")
2987
        (plus:SI (match_operand:SI 1 "register_operand" "r,r")
2988
                 (high:SI (match_operand 2 "const_int_operand" ""))))]
2989
  "reload_completed"
2990
  "@
2991
   addil L'%G2,%1
2992
   ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
2993
  [(set_attr "type" "binary,binary")
2994
   (set_attr "length" "4,8")])
2995
 
2996
(define_insn ""
2997
  [(set (match_operand:DI 0 "register_operand" "=!a,*r")
2998
        (plus:DI (match_operand:DI 1 "register_operand" "r,r")
2999
                 (high:DI (match_operand 2 "const_int_operand" ""))))]
3000
  "reload_completed && TARGET_64BIT"
3001
  "@
3002
   addil L'%G2,%1
3003
   ldil L'%G2,%0\;{addl|add,l} %0,%1,%0"
3004
  [(set_attr "type" "binary,binary")
3005
   (set_attr "length" "4,8")])
3006
 
3007
(define_insn ""
3008
  [(set (match_operand:SI 0 "register_operand" "=r")
3009
        (high:SI (match_operand 1 "" "")))]
3010
  "(!flag_pic || !symbolic_operand (operands[1], Pmode))
3011
    && !is_function_label_plus_const (operands[1])"
3012
  "*
3013
{
3014
  if (symbolic_operand (operands[1], Pmode))
3015
    return \"ldil LR'%H1,%0\";
3016
  else
3017
    return \"ldil L'%G1,%0\";
3018
}"
3019
  [(set_attr "type" "move")
3020
   (set_attr "length" "4")])
3021
 
3022
(define_insn ""
3023
  [(set (match_operand:DI 0 "register_operand" "=r")
3024
        (high:DI (match_operand 1 "const_int_operand" "")))]
3025
  "TARGET_64BIT"
3026
  "ldil L'%G1,%0";
3027
  [(set_attr "type" "move")
3028
   (set_attr "length" "4")])
3029
 
3030
(define_insn ""
3031
  [(set (match_operand:DI 0 "register_operand" "=r")
3032
        (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
3033
                   (match_operand:DI 2 "const_int_operand" "i")))]
3034
  "TARGET_64BIT"
3035
  "ldo R'%G2(%1),%0";
3036
  [(set_attr "type" "move")
3037
   (set_attr "length" "4")])
3038
 
3039
(define_insn ""
3040
  [(set (match_operand:SI 0 "register_operand" "=r")
3041
        (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
3042
                   (match_operand:SI 2 "immediate_operand" "i")))]
3043
  "!is_function_label_plus_const (operands[2])"
3044
  "*
3045
{
3046
  gcc_assert (!flag_pic || !symbolic_operand (operands[2], Pmode));
3047
 
3048
  if (symbolic_operand (operands[2], Pmode))
3049
    return \"ldo RR'%G2(%1),%0\";
3050
  else
3051
    return \"ldo R'%G2(%1),%0\";
3052
}"
3053
  [(set_attr "type" "move")
3054
   (set_attr "length" "4")])
3055
 
3056
;; Now that a symbolic_address plus a constant is broken up early
3057
;; in the compilation phase (for better CSE) we need a special
3058
;; combiner pattern to load the symbolic address plus the constant
3059
;; in only 2 instructions. (For cases where the symbolic address
3060
;; was not a common subexpression.)
3061
(define_split
3062
  [(set (match_operand:SI 0 "register_operand" "")
3063
        (match_operand:SI 1 "symbolic_operand" ""))
3064
   (clobber (match_operand:SI 2 "register_operand" ""))]
3065
  "! (flag_pic && pic_label_operand (operands[1], SImode))"
3066
  [(set (match_dup 2) (high:SI (match_dup 1)))
3067
   (set (match_dup 0) (lo_sum:SI (match_dup 2) (match_dup 1)))]
3068
  "")
3069
 
3070
;; hppa_legitimize_address goes to a great deal of trouble to
3071
;; create addresses which use indexing.  In some cases, this
3072
;; is a lose because there isn't any store instructions which
3073
;; allow indexed addresses (with integer register source).
3074
;;
3075
;; These define_splits try to turn a 3 insn store into
3076
;; a 2 insn store with some creative RTL rewriting.
3077
(define_split
3078
  [(set (mem:SI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
3079
                               (match_operand:SI 1 "shadd_operand" ""))
3080
                   (plus:SI (match_operand:SI 2 "register_operand" "")
3081
                            (match_operand:SI 3 "const_int_operand" ""))))
3082
        (match_operand:SI 4 "register_operand" ""))
3083
   (clobber (match_operand:SI 5 "register_operand" ""))]
3084
  ""
3085
  [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
3086
                               (match_dup 2)))
3087
   (set (mem:SI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
3088
  "")
3089
 
3090
(define_split
3091
  [(set (mem:HI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
3092
                               (match_operand:SI 1 "shadd_operand" ""))
3093
                   (plus:SI (match_operand:SI 2 "register_operand" "")
3094
                            (match_operand:SI 3 "const_int_operand" ""))))
3095
        (match_operand:HI 4 "register_operand" ""))
3096
   (clobber (match_operand:SI 5 "register_operand" ""))]
3097
  ""
3098
  [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
3099
                               (match_dup 2)))
3100
   (set (mem:HI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
3101
  "")
3102
 
3103
(define_split
3104
  [(set (mem:QI (plus:SI (mult:SI (match_operand:SI 0 "register_operand" "")
3105
                               (match_operand:SI 1 "shadd_operand" ""))
3106
                   (plus:SI (match_operand:SI 2 "register_operand" "")
3107
                            (match_operand:SI 3 "const_int_operand" ""))))
3108
        (match_operand:QI 4 "register_operand" ""))
3109
   (clobber (match_operand:SI 5 "register_operand" ""))]
3110
  ""
3111
  [(set (match_dup 5) (plus:SI (mult:SI (match_dup 0) (match_dup 1))
3112
                               (match_dup 2)))
3113
   (set (mem:QI (plus:SI (match_dup 5) (match_dup 3))) (match_dup 4))]
3114
  "")
3115
 
3116
(define_expand "movhi"
3117
  [(set (match_operand:HI 0 "general_operand" "")
3118
        (match_operand:HI 1 "general_operand" ""))]
3119
  ""
3120
  "
3121
{
3122
  if (emit_move_sequence (operands, HImode, 0))
3123
    DONE;
3124
}")
3125
 
3126
(define_insn ""
3127
  [(set (match_operand:HI 0 "move_dest_operand"
3128
                          "=r,r,r,r,r,Q,!*q,!r,!*f,?r,?*f")
3129
        (match_operand:HI 1 "move_src_operand"
3130
                          "r,J,N,K,RQ,rM,!rM,!*q,!*fM,*f,r"))]
3131
  "(register_operand (operands[0], HImode)
3132
    || reg_or_0_operand (operands[1], HImode))
3133
   && !TARGET_SOFT_FLOAT
3134
   && !TARGET_64BIT"
3135
  "@
3136
   copy %1,%0
3137
   ldi %1,%0
3138
   ldil L'%1,%0
3139
   {zdepi|depwi,z} %Z1,%0
3140
   ldh%M1 %1,%0
3141
   sth%M0 %r1,%0
3142
   mtsar %r1
3143
   {mfctl|mfctl,w} %sar,%0
3144
   fcpy,sgl %f1,%0
3145
   {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
3146
   {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
3147
  [(set_attr "type" "move,move,move,shift,load,store,move,move,move,move,move")
3148
   (set_attr "pa_combine_type" "addmove")
3149
   (set_attr "length" "4,4,4,4,4,4,4,4,4,8,8")])
3150
 
3151
(define_insn ""
3152
  [(set (match_operand:HI 0 "move_dest_operand"
3153
                          "=r,r,r,r,r,Q,!*q,!r,!*f")
3154
        (match_operand:HI 1 "move_src_operand"
3155
                          "r,J,N,K,RQ,rM,!rM,!*q,!*fM"))]
3156
  "(register_operand (operands[0], HImode)
3157
    || reg_or_0_operand (operands[1], HImode))
3158
   && !TARGET_SOFT_FLOAT
3159
   && TARGET_64BIT"
3160
  "@
3161
   copy %1,%0
3162
   ldi %1,%0
3163
   ldil L'%1,%0
3164
   {zdepi|depwi,z} %Z1,%0
3165
   ldh%M1 %1,%0
3166
   sth%M0 %r1,%0
3167
   mtsar %r1
3168
   {mfctl|mfctl,w} %sar,%0
3169
   fcpy,sgl %f1,%0"
3170
  [(set_attr "type" "move,move,move,shift,load,store,move,move,move")
3171
   (set_attr "pa_combine_type" "addmove")
3172
   (set_attr "length" "4,4,4,4,4,4,4,4,4")])
3173
 
3174
(define_insn ""
3175
  [(set (match_operand:HI 0 "move_dest_operand"
3176
                          "=r,r,r,r,r,Q,!*q,!r")
3177
        (match_operand:HI 1 "move_src_operand"
3178
                          "r,J,N,K,RQ,rM,!rM,!*q"))]
3179
  "(register_operand (operands[0], HImode)
3180
    || reg_or_0_operand (operands[1], HImode))
3181
   && TARGET_SOFT_FLOAT"
3182
  "@
3183
   copy %1,%0
3184
   ldi %1,%0
3185
   ldil L'%1,%0
3186
   {zdepi|depwi,z} %Z1,%0
3187
   ldh%M1 %1,%0
3188
   sth%M0 %r1,%0
3189
   mtsar %r1
3190
   {mfctl|mfctl,w} %sar,%0"
3191
  [(set_attr "type" "move,move,move,shift,load,store,move,move")
3192
   (set_attr "pa_combine_type" "addmove")
3193
   (set_attr "length" "4,4,4,4,4,4,4,4")])
3194
 
3195
(define_insn ""
3196
  [(set (match_operand:HI 0 "register_operand" "=r")
3197
        (mem:HI (plus:SI (match_operand:SI 1 "register_operand" "+r")
3198
                         (match_operand:SI 2 "int5_operand" "L"))))
3199
   (set (match_dup 1)
3200
        (plus:SI (match_dup 1) (match_dup 2)))]
3201
  ""
3202
  "{ldhs|ldh},mb %2(%1),%0"
3203
  [(set_attr "type" "load")
3204
   (set_attr "length" "4")])
3205
 
3206
(define_insn ""
3207
  [(set (match_operand:HI 0 "register_operand" "=r")
3208
        (mem:HI (plus:DI (match_operand:DI 1 "register_operand" "+r")
3209
                         (match_operand:DI 2 "int5_operand" "L"))))
3210
   (set (match_dup 1)
3211
        (plus:DI (match_dup 1) (match_dup 2)))]
3212
  "TARGET_64BIT"
3213
  "ldh,mb %2(%1),%0"
3214
  [(set_attr "type" "load")
3215
   (set_attr "length" "4")])
3216
 
3217
; And a zero extended variant.
3218
(define_insn ""
3219
  [(set (match_operand:DI 0 "register_operand" "=r")
3220
        (zero_extend:DI (mem:HI
3221
                          (plus:DI
3222
                            (match_operand:DI 1 "register_operand" "+r")
3223
                            (match_operand:DI 2 "int5_operand" "L")))))
3224
   (set (match_dup 1)
3225
        (plus:DI (match_dup 1) (match_dup 2)))]
3226
  "TARGET_64BIT"
3227
  "ldh,mb %2(%1),%0"
3228
  [(set_attr "type" "load")
3229
   (set_attr "length" "4")])
3230
 
3231
(define_insn ""
3232
  [(set (match_operand:SI 0 "register_operand" "=r")
3233
        (zero_extend:SI (mem:HI
3234
                          (plus:SI
3235
                            (match_operand:SI 1 "register_operand" "+r")
3236
                            (match_operand:SI 2 "int5_operand" "L")))))
3237
   (set (match_dup 1)
3238
        (plus:SI (match_dup 1) (match_dup 2)))]
3239
  ""
3240
  "{ldhs|ldh},mb %2(%1),%0"
3241
  [(set_attr "type" "load")
3242
   (set_attr "length" "4")])
3243
 
3244
(define_insn ""
3245
  [(set (match_operand:SI 0 "register_operand" "=r")
3246
        (zero_extend:SI (mem:HI
3247
                          (plus:DI
3248
                            (match_operand:DI 1 "register_operand" "+r")
3249
                            (match_operand:DI 2 "int5_operand" "L")))))
3250
   (set (match_dup 1)
3251
        (plus:DI (match_dup 1) (match_dup 2)))]
3252
  "TARGET_64BIT"
3253
  "ldh,mb %2(%1),%0"
3254
  [(set_attr "type" "load")
3255
   (set_attr "length" "4")])
3256
 
3257
(define_insn ""
3258
  [(set (mem:HI (plus:SI (match_operand:SI 0 "register_operand" "+r")
3259
                         (match_operand:SI 1 "int5_operand" "L")))
3260
        (match_operand:HI 2 "reg_or_0_operand" "rM"))
3261
   (set (match_dup 0)
3262
        (plus:SI (match_dup 0) (match_dup 1)))]
3263
  ""
3264
  "{sths|sth},mb %r2,%1(%0)"
3265
  [(set_attr "type" "store")
3266
   (set_attr "length" "4")])
3267
 
3268
(define_insn ""
3269
  [(set (mem:HI (plus:DI (match_operand:DI 0 "register_operand" "+r")
3270
                         (match_operand:DI 1 "int5_operand" "L")))
3271
        (match_operand:HI 2 "reg_or_0_operand" "rM"))
3272
   (set (match_dup 0)
3273
        (plus:DI (match_dup 0) (match_dup 1)))]
3274
  "TARGET_64BIT"
3275
  "sth,mb %r2,%1(%0)"
3276
  [(set_attr "type" "store")
3277
   (set_attr "length" "4")])
3278
 
3279
(define_insn ""
3280
  [(set (match_operand:HI 0 "register_operand" "=r")
3281
        (plus:HI (match_operand:HI 1 "register_operand" "r")
3282
                 (match_operand 2 "const_int_operand" "J")))]
3283
  ""
3284
  "ldo %2(%1),%0"
3285
  [(set_attr "type" "binary")
3286
   (set_attr "pa_combine_type" "addmove")
3287
   (set_attr "length" "4")])
3288
 
3289
(define_expand "movqi"
3290
  [(set (match_operand:QI 0 "general_operand" "")
3291
        (match_operand:QI 1 "general_operand" ""))]
3292
  ""
3293
  "
3294
{
3295
  if (emit_move_sequence (operands, QImode, 0))
3296
    DONE;
3297
}")
3298
 
3299
(define_insn ""
3300
  [(set (match_operand:QI 0 "move_dest_operand"
3301
                          "=r,r,r,r,r,Q,!*q,!r,!*f,?r,?*f")
3302
        (match_operand:QI 1 "move_src_operand"
3303
                          "r,J,N,K,RQ,rM,!rM,!*q,!*fM,*f,r"))]
3304
  "(register_operand (operands[0], QImode)
3305
    || reg_or_0_operand (operands[1], QImode))
3306
   && !TARGET_SOFT_FLOAT
3307
   && !TARGET_64BIT"
3308
  "@
3309
   copy %1,%0
3310
   ldi %1,%0
3311
   ldil L'%1,%0
3312
   {zdepi|depwi,z} %Z1,%0
3313
   ldb%M1 %1,%0
3314
   stb%M0 %r1,%0
3315
   mtsar %r1
3316
   {mfctl|mfctl,w} %%sar,%0
3317
   fcpy,sgl %f1,%0
3318
   {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
3319
   {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
3320
  [(set_attr "type" "move,move,move,shift,load,store,move,move,move,move,move")
3321
   (set_attr "pa_combine_type" "addmove")
3322
   (set_attr "length" "4,4,4,4,4,4,4,4,4,8,8")])
3323
 
3324
(define_insn ""
3325
  [(set (match_operand:QI 0 "move_dest_operand"
3326
                          "=r,r,r,r,r,Q,!*q,!r,!*f")
3327
        (match_operand:QI 1 "move_src_operand"
3328
                          "r,J,N,K,RQ,rM,!rM,!*q,!*fM"))]
3329
  "(register_operand (operands[0], QImode)
3330
    || reg_or_0_operand (operands[1], QImode))
3331
   && !TARGET_SOFT_FLOAT
3332
   && TARGET_64BIT"
3333
  "@
3334
   copy %1,%0
3335
   ldi %1,%0
3336
   ldil L'%1,%0
3337
   {zdepi|depwi,z} %Z1,%0
3338
   ldb%M1 %1,%0
3339
   stb%M0 %r1,%0
3340
   mtsar %r1
3341
   {mfctl|mfctl,w} %%sar,%0
3342
   fcpy,sgl %f1,%0"
3343
  [(set_attr "type" "move,move,move,shift,load,store,move,move,move")
3344
   (set_attr "pa_combine_type" "addmove")
3345
   (set_attr "length" "4,4,4,4,4,4,4,4,4")])
3346
 
3347
(define_insn ""
3348
  [(set (match_operand:QI 0 "move_dest_operand"
3349
                          "=r,r,r,r,r,Q,!*q,!r")
3350
        (match_operand:QI 1 "move_src_operand"
3351
                          "r,J,N,K,RQ,rM,!rM,!*q"))]
3352
  "(register_operand (operands[0], QImode)
3353
    || reg_or_0_operand (operands[1], QImode))
3354
   && TARGET_SOFT_FLOAT"
3355
  "@
3356
   copy %1,%0
3357
   ldi %1,%0
3358
   ldil L'%1,%0
3359
   {zdepi|depwi,z} %Z1,%0
3360
   ldb%M1 %1,%0
3361
   stb%M0 %r1,%0
3362
   mtsar %r1
3363
   {mfctl|mfctl,w} %%sar,%0"
3364
  [(set_attr "type" "move,move,move,shift,load,store,move,move")
3365
   (set_attr "pa_combine_type" "addmove")
3366
   (set_attr "length" "4,4,4,4,4,4,4,4")])
3367
 
3368
(define_insn ""
3369
  [(set (match_operand:QI 0 "register_operand" "=r")
3370
        (mem:QI (plus:SI (match_operand:SI 1 "register_operand" "+r")
3371
                         (match_operand:SI 2 "int5_operand" "L"))))
3372
   (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3373
  ""
3374
  "{ldbs|ldb},mb %2(%1),%0"
3375
  [(set_attr "type" "load")
3376
   (set_attr "length" "4")])
3377
 
3378
(define_insn ""
3379
  [(set (match_operand:QI 0 "register_operand" "=r")
3380
        (mem:QI (plus:DI (match_operand:DI 1 "register_operand" "+r")
3381
                         (match_operand:DI 2 "int5_operand" "L"))))
3382
   (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3383
  "TARGET_64BIT"
3384
  "ldb,mb %2(%1),%0"
3385
  [(set_attr "type" "load")
3386
   (set_attr "length" "4")])
3387
 
3388
; Now the same thing with zero extensions.
3389
(define_insn ""
3390
  [(set (match_operand:DI 0 "register_operand" "=r")
3391
        (zero_extend:DI (mem:QI (plus:DI
3392
                                  (match_operand:DI 1 "register_operand" "+r")
3393
                                  (match_operand:DI 2 "int5_operand" "L")))))
3394
   (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3395
  "TARGET_64BIT"
3396
  "ldb,mb %2(%1),%0"
3397
  [(set_attr "type" "load")
3398
   (set_attr "length" "4")])
3399
 
3400
(define_insn ""
3401
  [(set (match_operand:SI 0 "register_operand" "=r")
3402
        (zero_extend:SI (mem:QI (plus:SI
3403
                                  (match_operand:SI 1 "register_operand" "+r")
3404
                                  (match_operand:SI 2 "int5_operand" "L")))))
3405
   (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3406
  ""
3407
  "{ldbs|ldb},mb %2(%1),%0"
3408
  [(set_attr "type" "load")
3409
   (set_attr "length" "4")])
3410
 
3411
(define_insn ""
3412
  [(set (match_operand:SI 0 "register_operand" "=r")
3413
        (zero_extend:SI (mem:QI (plus:DI
3414
                                  (match_operand:DI 1 "register_operand" "+r")
3415
                                  (match_operand:DI 2 "int5_operand" "L")))))
3416
   (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3417
  "TARGET_64BIT"
3418
  "ldb,mb %2(%1),%0"
3419
  [(set_attr "type" "load")
3420
   (set_attr "length" "4")])
3421
 
3422
(define_insn ""
3423
  [(set (match_operand:HI 0 "register_operand" "=r")
3424
        (zero_extend:HI (mem:QI (plus:SI
3425
                                  (match_operand:SI 1 "register_operand" "+r")
3426
                                  (match_operand:SI 2 "int5_operand" "L")))))
3427
   (set (match_dup 1) (plus:SI (match_dup 1) (match_dup 2)))]
3428
  ""
3429
  "{ldbs|ldb},mb %2(%1),%0"
3430
  [(set_attr "type" "load")
3431
   (set_attr "length" "4")])
3432
 
3433
(define_insn ""
3434
  [(set (match_operand:HI 0 "register_operand" "=r")
3435
        (zero_extend:HI (mem:QI (plus:DI
3436
                                  (match_operand:DI 1 "register_operand" "+r")
3437
                                  (match_operand:DI 2 "int5_operand" "L")))))
3438
   (set (match_dup 1) (plus:DI (match_dup 1) (match_dup 2)))]
3439
  "TARGET_64BIT"
3440
  "ldb,mb %2(%1),%0"
3441
  [(set_attr "type" "load")
3442
   (set_attr "length" "4")])
3443
 
3444
(define_insn ""
3445
  [(set (mem:QI (plus:SI (match_operand:SI 0 "register_operand" "+r")
3446
                         (match_operand:SI 1 "int5_operand" "L")))
3447
        (match_operand:QI 2 "reg_or_0_operand" "rM"))
3448
   (set (match_dup 0)
3449
        (plus:SI (match_dup 0) (match_dup 1)))]
3450
  ""
3451
  "{stbs|stb},mb %r2,%1(%0)"
3452
  [(set_attr "type" "store")
3453
   (set_attr "length" "4")])
3454
 
3455
(define_insn ""
3456
  [(set (mem:QI (plus:DI (match_operand:DI 0 "register_operand" "+r")
3457
                         (match_operand:DI 1 "int5_operand" "L")))
3458
        (match_operand:QI 2 "reg_or_0_operand" "rM"))
3459
   (set (match_dup 0)
3460
        (plus:DI (match_dup 0) (match_dup 1)))]
3461
  "TARGET_64BIT"
3462
  "stb,mb %r2,%1(%0)"
3463
  [(set_attr "type" "store")
3464
   (set_attr "length" "4")])
3465
 
3466
;; The definition of this insn does not really explain what it does,
3467
;; but it should suffice that anything generated as this insn will be
3468
;; recognized as a movmemsi operation, and that it will not successfully
3469
;; combine with anything.
3470
(define_expand "movmemsi"
3471
  [(parallel [(set (match_operand:BLK 0 "" "")
3472
                   (match_operand:BLK 1 "" ""))
3473
              (clobber (match_dup 4))
3474
              (clobber (match_dup 5))
3475
              (clobber (match_dup 6))
3476
              (clobber (match_dup 7))
3477
              (clobber (match_dup 8))
3478
              (use (match_operand:SI 2 "arith_operand" ""))
3479
              (use (match_operand:SI 3 "const_int_operand" ""))])]
3480
  "!TARGET_64BIT && optimize > 0"
3481
  "
3482
{
3483
  int size, align;
3484
 
3485
  /* HP provides very fast block move library routine for the PA;
3486
     this routine includes:
3487
 
3488
        4x4 byte at a time block moves,
3489
        1x4 byte at a time with alignment checked at runtime with
3490
            attempts to align the source and destination as needed
3491
        1x1 byte loop
3492
 
3493
     With that in mind, here's the heuristics to try and guess when
3494
     the inlined block move will be better than the library block
3495
     move:
3496
 
3497
        If the size isn't constant, then always use the library routines.
3498
 
3499
        If the size is large in respect to the known alignment, then use
3500
        the library routines.
3501
 
3502
        If the size is small in respect to the known alignment, then open
3503
        code the copy (since that will lead to better scheduling).
3504
 
3505
        Else use the block move pattern.   */
3506
 
3507
  /* Undetermined size, use the library routine.  */
3508
  if (GET_CODE (operands[2]) != CONST_INT)
3509
    FAIL;
3510
 
3511
  size = INTVAL (operands[2]);
3512
  align = INTVAL (operands[3]);
3513
  align = align > 4 ? 4 : align;
3514
 
3515
  /* If size/alignment is large, then use the library routines.  */
3516
  if (size / align > 16)
3517
    FAIL;
3518
 
3519
  /* This does happen, but not often enough to worry much about.  */
3520
  if (size / align < MOVE_RATIO)
3521
    FAIL;
3522
 
3523
  /* Fall through means we're going to use our block move pattern.  */
3524
  operands[0]
3525
    = replace_equiv_address (operands[0],
3526
                             copy_to_mode_reg (SImode, XEXP (operands[0], 0)));
3527
  operands[1]
3528
    = replace_equiv_address (operands[1],
3529
                             copy_to_mode_reg (SImode, XEXP (operands[1], 0)));
3530
  operands[4] = gen_reg_rtx (SImode);
3531
  operands[5] = gen_reg_rtx (SImode);
3532
  operands[6] = gen_reg_rtx (SImode);
3533
  operands[7] = gen_reg_rtx (SImode);
3534
  operands[8] = gen_reg_rtx (SImode);
3535
}")
3536
 
3537
;; The operand constraints are written like this to support both compile-time
3538
;; and run-time determined byte counts.  The expander and output_block_move
3539
;; only support compile-time determined counts at this time.
3540
;;
3541
;; If the count is run-time determined, the register with the byte count
3542
;; is clobbered by the copying code, and therefore it is forced to operand 2.
3543
;;
3544
;; We used to clobber operands 0 and 1.  However, a change to regrename.c
3545
;; broke this semantic for pseudo registers.  We can't use match_scratch
3546
;; as this requires two registers in the class R1_REGS when the MEMs for
3547
;; operands 0 and 1 are both equivalent to symbolic MEMs.  Thus, we are
3548
;; forced to internally copy operands 0 and 1 to operands 7 and 8,
3549
;; respectively.  We then split or peephole optimize after reload.
3550
(define_insn "movmemsi_prereload"
3551
  [(set (mem:BLK (match_operand:SI 0 "register_operand" "r,r"))
3552
        (mem:BLK (match_operand:SI 1 "register_operand" "r,r")))
3553
   (clobber (match_operand:SI 2 "register_operand" "=&r,&r"))	;loop cnt/tmp
3554
   (clobber (match_operand:SI 3 "register_operand" "=&r,&r"))	;item tmp1
3555
   (clobber (match_operand:SI 6 "register_operand" "=&r,&r"))	;item tmp2
3556
   (clobber (match_operand:SI 7 "register_operand" "=&r,&r"))	;item tmp3
3557
   (clobber (match_operand:SI 8 "register_operand" "=&r,&r"))	;item tmp4
3558
   (use (match_operand:SI 4 "arith_operand" "J,2"))      ;byte count
3559
   (use (match_operand:SI 5 "const_int_operand" "n,n"))] ;alignment
3560
  "!TARGET_64BIT"
3561
  "#"
3562
  [(set_attr "type" "multi,multi")])
3563
 
3564
(define_split
3565
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3566
                   (match_operand:BLK 1 "memory_operand" ""))
3567
              (clobber (match_operand:SI 2 "register_operand" ""))
3568
              (clobber (match_operand:SI 3 "register_operand" ""))
3569
              (clobber (match_operand:SI 6 "register_operand" ""))
3570
              (clobber (match_operand:SI 7 "register_operand" ""))
3571
              (clobber (match_operand:SI 8 "register_operand" ""))
3572
              (use (match_operand:SI 4 "arith_operand" ""))
3573
              (use (match_operand:SI 5 "const_int_operand" ""))])]
3574
  "!TARGET_64BIT && reload_completed && !flag_peephole2
3575
   && GET_CODE (operands[0]) == MEM
3576
   && register_operand (XEXP (operands[0], 0), SImode)
3577
   && GET_CODE (operands[1]) == MEM
3578
   && register_operand (XEXP (operands[1], 0), SImode)"
3579
  [(set (match_dup 7) (match_dup 9))
3580
   (set (match_dup 8) (match_dup 10))
3581
   (parallel [(set (match_dup 0) (match_dup 1))
3582
              (clobber (match_dup 2))
3583
              (clobber (match_dup 3))
3584
              (clobber (match_dup 6))
3585
              (clobber (match_dup 7))
3586
              (clobber (match_dup 8))
3587
              (use (match_dup 4))
3588
              (use (match_dup 5))
3589
              (const_int 0)])]
3590
  "
3591
{
3592
  operands[9] = XEXP (operands[0], 0);
3593
  operands[10] = XEXP (operands[1], 0);
3594
  operands[0] = replace_equiv_address (operands[0], operands[7]);
3595
  operands[1] = replace_equiv_address (operands[1], operands[8]);
3596
}")
3597
 
3598
(define_peephole2
3599
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3600
                   (match_operand:BLK 1 "memory_operand" ""))
3601
              (clobber (match_operand:SI 2 "register_operand" ""))
3602
              (clobber (match_operand:SI 3 "register_operand" ""))
3603
              (clobber (match_operand:SI 6 "register_operand" ""))
3604
              (clobber (match_operand:SI 7 "register_operand" ""))
3605
              (clobber (match_operand:SI 8 "register_operand" ""))
3606
              (use (match_operand:SI 4 "arith_operand" ""))
3607
              (use (match_operand:SI 5 "const_int_operand" ""))])]
3608
  "!TARGET_64BIT
3609
   && GET_CODE (operands[0]) == MEM
3610
   && register_operand (XEXP (operands[0], 0), SImode)
3611
   && GET_CODE (operands[1]) == MEM
3612
   && register_operand (XEXP (operands[1], 0), SImode)"
3613
  [(parallel [(set (match_dup 0) (match_dup 1))
3614
              (clobber (match_dup 2))
3615
              (clobber (match_dup 3))
3616
              (clobber (match_dup 6))
3617
              (clobber (match_dup 7))
3618
              (clobber (match_dup 8))
3619
              (use (match_dup 4))
3620
              (use (match_dup 5))
3621
              (const_int 0)])]
3622
  "
3623
{
3624
  rtx addr = XEXP (operands[0], 0);
3625
  if (dead_or_set_p (curr_insn, addr))
3626
    operands[7] = addr;
3627
  else
3628
    {
3629
      emit_insn (gen_rtx_SET (VOIDmode, operands[7], addr));
3630
      operands[0] = replace_equiv_address (operands[0], operands[7]);
3631
    }
3632
 
3633
  addr = XEXP (operands[1], 0);
3634
  if (dead_or_set_p (curr_insn, addr))
3635
    operands[8] = addr;
3636
  else
3637
    {
3638
      emit_insn (gen_rtx_SET (VOIDmode, operands[8], addr));
3639
      operands[1] = replace_equiv_address (operands[1], operands[8]);
3640
    }
3641
}")
3642
 
3643
(define_insn "movmemsi_postreload"
3644
  [(set (mem:BLK (match_operand:SI 0 "register_operand" "+r,r"))
3645
        (mem:BLK (match_operand:SI 1 "register_operand" "+r,r")))
3646
   (clobber (match_operand:SI 2 "register_operand" "=&r,&r"))	;loop cnt/tmp
3647
   (clobber (match_operand:SI 3 "register_operand" "=&r,&r"))	;item tmp1
3648
   (clobber (match_operand:SI 6 "register_operand" "=&r,&r"))	;item tmp2
3649
   (clobber (match_dup 0))
3650
   (clobber (match_dup 1))
3651
   (use (match_operand:SI 4 "arith_operand" "J,2"))      ;byte count
3652
   (use (match_operand:SI 5 "const_int_operand" "n,n"))  ;alignment
3653
   (const_int 0)]
3654
  "!TARGET_64BIT && reload_completed"
3655
  "* return output_block_move (operands, !which_alternative);"
3656
  [(set_attr "type" "multi,multi")])
3657
 
3658
(define_expand "movmemdi"
3659
  [(parallel [(set (match_operand:BLK 0 "" "")
3660
                   (match_operand:BLK 1 "" ""))
3661
              (clobber (match_dup 4))
3662
              (clobber (match_dup 5))
3663
              (clobber (match_dup 6))
3664
              (clobber (match_dup 7))
3665
              (clobber (match_dup 8))
3666
              (use (match_operand:DI 2 "arith_operand" ""))
3667
              (use (match_operand:DI 3 "const_int_operand" ""))])]
3668
  "TARGET_64BIT && optimize > 0"
3669
  "
3670
{
3671
  int size, align;
3672
 
3673
  /* HP provides very fast block move library routine for the PA;
3674
     this routine includes:
3675
 
3676
        4x4 byte at a time block moves,
3677
        1x4 byte at a time with alignment checked at runtime with
3678
            attempts to align the source and destination as needed
3679
        1x1 byte loop
3680
 
3681
     With that in mind, here's the heuristics to try and guess when
3682
     the inlined block move will be better than the library block
3683
     move:
3684
 
3685
        If the size isn't constant, then always use the library routines.
3686
 
3687
        If the size is large in respect to the known alignment, then use
3688
        the library routines.
3689
 
3690
        If the size is small in respect to the known alignment, then open
3691
        code the copy (since that will lead to better scheduling).
3692
 
3693
        Else use the block move pattern.   */
3694
 
3695
  /* Undetermined size, use the library routine.  */
3696
  if (GET_CODE (operands[2]) != CONST_INT)
3697
    FAIL;
3698
 
3699
  size = INTVAL (operands[2]);
3700
  align = INTVAL (operands[3]);
3701
  align = align > 8 ? 8 : align;
3702
 
3703
  /* If size/alignment is large, then use the library routines.  */
3704
  if (size / align > 16)
3705
    FAIL;
3706
 
3707
  /* This does happen, but not often enough to worry much about.  */
3708
  if (size / align < MOVE_RATIO)
3709
    FAIL;
3710
 
3711
  /* Fall through means we're going to use our block move pattern.  */
3712
  operands[0]
3713
    = replace_equiv_address (operands[0],
3714
                             copy_to_mode_reg (DImode, XEXP (operands[0], 0)));
3715
  operands[1]
3716
    = replace_equiv_address (operands[1],
3717
                             copy_to_mode_reg (DImode, XEXP (operands[1], 0)));
3718
  operands[4] = gen_reg_rtx (DImode);
3719
  operands[5] = gen_reg_rtx (DImode);
3720
  operands[6] = gen_reg_rtx (DImode);
3721
  operands[7] = gen_reg_rtx (DImode);
3722
  operands[8] = gen_reg_rtx (DImode);
3723
}")
3724
 
3725
;; The operand constraints are written like this to support both compile-time
3726
;; and run-time determined byte counts.  The expander and output_block_move
3727
;; only support compile-time determined counts at this time.
3728
;;
3729
;; If the count is run-time determined, the register with the byte count
3730
;; is clobbered by the copying code, and therefore it is forced to operand 2.
3731
;;
3732
;; We used to clobber operands 0 and 1.  However, a change to regrename.c
3733
;; broke this semantic for pseudo registers.  We can't use match_scratch
3734
;; as this requires two registers in the class R1_REGS when the MEMs for
3735
;; operands 0 and 1 are both equivalent to symbolic MEMs.  Thus, we are
3736
;; forced to internally copy operands 0 and 1 to operands 7 and 8,
3737
;; respectively.  We then split or peephole optimize after reload.
3738
(define_insn "movmemdi_prereload"
3739
  [(set (mem:BLK (match_operand:DI 0 "register_operand" "r,r"))
3740
        (mem:BLK (match_operand:DI 1 "register_operand" "r,r")))
3741
   (clobber (match_operand:DI 2 "register_operand" "=&r,&r"))	;loop cnt/tmp
3742
   (clobber (match_operand:DI 3 "register_operand" "=&r,&r"))	;item tmp1
3743
   (clobber (match_operand:DI 6 "register_operand" "=&r,&r"))	;item tmp2
3744
   (clobber (match_operand:DI 7 "register_operand" "=&r,&r"))	;item tmp3
3745
   (clobber (match_operand:DI 8 "register_operand" "=&r,&r"))	;item tmp4
3746
   (use (match_operand:DI 4 "arith_operand" "J,2"))      ;byte count
3747
   (use (match_operand:DI 5 "const_int_operand" "n,n"))] ;alignment
3748
  "TARGET_64BIT"
3749
  "#"
3750
  [(set_attr "type" "multi,multi")])
3751
 
3752
(define_split
3753
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3754
                   (match_operand:BLK 1 "memory_operand" ""))
3755
              (clobber (match_operand:DI 2 "register_operand" ""))
3756
              (clobber (match_operand:DI 3 "register_operand" ""))
3757
              (clobber (match_operand:DI 6 "register_operand" ""))
3758
              (clobber (match_operand:DI 7 "register_operand" ""))
3759
              (clobber (match_operand:DI 8 "register_operand" ""))
3760
              (use (match_operand:DI 4 "arith_operand" ""))
3761
              (use (match_operand:DI 5 "const_int_operand" ""))])]
3762
  "TARGET_64BIT && reload_completed && !flag_peephole2
3763
   && GET_CODE (operands[0]) == MEM
3764
   && register_operand (XEXP (operands[0], 0), DImode)
3765
   && GET_CODE (operands[1]) == MEM
3766
   && register_operand (XEXP (operands[1], 0), DImode)"
3767
  [(set (match_dup 7) (match_dup 9))
3768
   (set (match_dup 8) (match_dup 10))
3769
   (parallel [(set (match_dup 0) (match_dup 1))
3770
              (clobber (match_dup 2))
3771
              (clobber (match_dup 3))
3772
              (clobber (match_dup 6))
3773
              (clobber (match_dup 7))
3774
              (clobber (match_dup 8))
3775
              (use (match_dup 4))
3776
              (use (match_dup 5))
3777
              (const_int 0)])]
3778
  "
3779
{
3780
  operands[9] = XEXP (operands[0], 0);
3781
  operands[10] = XEXP (operands[1], 0);
3782
  operands[0] = replace_equiv_address (operands[0], operands[7]);
3783
  operands[1] = replace_equiv_address (operands[1], operands[8]);
3784
}")
3785
 
3786
(define_peephole2
3787
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3788
                   (match_operand:BLK 1 "memory_operand" ""))
3789
              (clobber (match_operand:DI 2 "register_operand" ""))
3790
              (clobber (match_operand:DI 3 "register_operand" ""))
3791
              (clobber (match_operand:DI 6 "register_operand" ""))
3792
              (clobber (match_operand:DI 7 "register_operand" ""))
3793
              (clobber (match_operand:DI 8 "register_operand" ""))
3794
              (use (match_operand:DI 4 "arith_operand" ""))
3795
              (use (match_operand:DI 5 "const_int_operand" ""))])]
3796
  "TARGET_64BIT
3797
   && GET_CODE (operands[0]) == MEM
3798
   && register_operand (XEXP (operands[0], 0), DImode)
3799
   && GET_CODE (operands[1]) == MEM
3800
   && register_operand (XEXP (operands[1], 0), DImode)"
3801
  [(parallel [(set (match_dup 0) (match_dup 1))
3802
              (clobber (match_dup 2))
3803
              (clobber (match_dup 3))
3804
              (clobber (match_dup 6))
3805
              (clobber (match_dup 7))
3806
              (clobber (match_dup 8))
3807
              (use (match_dup 4))
3808
              (use (match_dup 5))
3809
              (const_int 0)])]
3810
  "
3811
{
3812
  rtx addr = XEXP (operands[0], 0);
3813
  if (dead_or_set_p (curr_insn, addr))
3814
    operands[7] = addr;
3815
  else
3816
    {
3817
      emit_insn (gen_rtx_SET (VOIDmode, operands[7], addr));
3818
      operands[0] = replace_equiv_address (operands[0], operands[7]);
3819
    }
3820
 
3821
  addr = XEXP (operands[1], 0);
3822
  if (dead_or_set_p (curr_insn, addr))
3823
    operands[8] = addr;
3824
  else
3825
    {
3826
      emit_insn (gen_rtx_SET (VOIDmode, operands[8], addr));
3827
      operands[1] = replace_equiv_address (operands[1], operands[8]);
3828
    }
3829
}")
3830
 
3831
(define_insn "movmemdi_postreload"
3832
  [(set (mem:BLK (match_operand:DI 0 "register_operand" "+r,r"))
3833
        (mem:BLK (match_operand:DI 1 "register_operand" "+r,r")))
3834
   (clobber (match_operand:DI 2 "register_operand" "=&r,&r"))	;loop cnt/tmp
3835
   (clobber (match_operand:DI 3 "register_operand" "=&r,&r"))	;item tmp1
3836
   (clobber (match_operand:DI 6 "register_operand" "=&r,&r"))	;item tmp2
3837
   (clobber (match_dup 0))
3838
   (clobber (match_dup 1))
3839
   (use (match_operand:DI 4 "arith_operand" "J,2"))      ;byte count
3840
   (use (match_operand:DI 5 "const_int_operand" "n,n"))  ;alignment
3841
   (const_int 0)]
3842
  "TARGET_64BIT && reload_completed"
3843
  "* return output_block_move (operands, !which_alternative);"
3844
  [(set_attr "type" "multi,multi")])
3845
 
3846
(define_expand "setmemsi"
3847
  [(parallel [(set (match_operand:BLK 0 "" "")
3848
                   (match_operand 2 "const_int_operand" ""))
3849
              (clobber (match_dup 4))
3850
              (clobber (match_dup 5))
3851
              (use (match_operand:SI 1 "arith_operand" ""))
3852
              (use (match_operand:SI 3 "const_int_operand" ""))])]
3853
  "!TARGET_64BIT && optimize > 0"
3854
  "
3855
{
3856
  int size, align;
3857
 
3858
  /* If value to set is not zero, use the library routine.  */
3859
  if (operands[2] != const0_rtx)
3860
    FAIL;
3861
 
3862
  /* Undetermined size, use the library routine.  */
3863
  if (GET_CODE (operands[1]) != CONST_INT)
3864
    FAIL;
3865
 
3866
  size = INTVAL (operands[1]);
3867
  align = INTVAL (operands[3]);
3868
  align = align > 4 ? 4 : align;
3869
 
3870
  /* If size/alignment is large, then use the library routines.  */
3871
  if (size / align > 16)
3872
    FAIL;
3873
 
3874
  /* This does happen, but not often enough to worry much about.  */
3875
  if (size / align < MOVE_RATIO)
3876
    FAIL;
3877
 
3878
  /* Fall through means we're going to use our block clear pattern.  */
3879
  operands[0]
3880
    = replace_equiv_address (operands[0],
3881
                             copy_to_mode_reg (SImode, XEXP (operands[0], 0)));
3882
  operands[4] = gen_reg_rtx (SImode);
3883
  operands[5] = gen_reg_rtx (SImode);
3884
}")
3885
 
3886
(define_insn "clrmemsi_prereload"
3887
  [(set (mem:BLK (match_operand:SI 0 "register_operand" "r,r"))
3888
        (const_int 0))
3889
   (clobber (match_operand:SI 1 "register_operand" "=&r,&r"))	;loop cnt/tmp
3890
   (clobber (match_operand:SI 4 "register_operand" "=&r,&r"))	;tmp1
3891
   (use (match_operand:SI 2 "arith_operand" "J,1"))      ;byte count
3892
   (use (match_operand:SI 3 "const_int_operand" "n,n"))] ;alignment
3893
  "!TARGET_64BIT"
3894
  "#"
3895
  [(set_attr "type" "multi,multi")])
3896
 
3897
(define_split
3898
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3899
                   (const_int 0))
3900
              (clobber (match_operand:SI 1 "register_operand" ""))
3901
              (clobber (match_operand:SI 4 "register_operand" ""))
3902
              (use (match_operand:SI 2 "arith_operand" ""))
3903
              (use (match_operand:SI 3 "const_int_operand" ""))])]
3904
  "!TARGET_64BIT && reload_completed && !flag_peephole2
3905
   && GET_CODE (operands[0]) == MEM
3906
   && register_operand (XEXP (operands[0], 0), SImode)"
3907
  [(set (match_dup 4) (match_dup 5))
3908
   (parallel [(set (match_dup 0) (const_int 0))
3909
              (clobber (match_dup 1))
3910
              (clobber (match_dup 4))
3911
              (use (match_dup 2))
3912
              (use (match_dup 3))
3913
              (const_int 0)])]
3914
  "
3915
{
3916
  operands[5] = XEXP (operands[0], 0);
3917
  operands[0] = replace_equiv_address (operands[0], operands[4]);
3918
}")
3919
 
3920
(define_peephole2
3921
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
3922
                   (const_int 0))
3923
              (clobber (match_operand:SI 1 "register_operand" ""))
3924
              (clobber (match_operand:SI 4 "register_operand" ""))
3925
              (use (match_operand:SI 2 "arith_operand" ""))
3926
              (use (match_operand:SI 3 "const_int_operand" ""))])]
3927
  "!TARGET_64BIT
3928
   && GET_CODE (operands[0]) == MEM
3929
   && register_operand (XEXP (operands[0], 0), SImode)"
3930
  [(parallel [(set (match_dup 0) (const_int 0))
3931
              (clobber (match_dup 1))
3932
              (clobber (match_dup 4))
3933
              (use (match_dup 2))
3934
              (use (match_dup 3))
3935
              (const_int 0)])]
3936
  "
3937
{
3938
  rtx addr = XEXP (operands[0], 0);
3939
  if (dead_or_set_p (curr_insn, addr))
3940
    operands[4] = addr;
3941
  else
3942
    {
3943
      emit_insn (gen_rtx_SET (VOIDmode, operands[4], addr));
3944
      operands[0] = replace_equiv_address (operands[0], operands[4]);
3945
    }
3946
}")
3947
 
3948
(define_insn "clrmemsi_postreload"
3949
  [(set (mem:BLK (match_operand:SI 0 "register_operand" "+r,r"))
3950
        (const_int 0))
3951
   (clobber (match_operand:SI 1 "register_operand" "=&r,&r"))	;loop cnt/tmp
3952
   (clobber (match_dup 0))
3953
   (use (match_operand:SI 2 "arith_operand" "J,1"))      ;byte count
3954
   (use (match_operand:SI 3 "const_int_operand" "n,n"))  ;alignment
3955
   (const_int 0)]
3956
  "!TARGET_64BIT && reload_completed"
3957
  "* return output_block_clear (operands, !which_alternative);"
3958
  [(set_attr "type" "multi,multi")])
3959
 
3960
(define_expand "setmemdi"
3961
  [(parallel [(set (match_operand:BLK 0 "" "")
3962
                   (match_operand 2 "const_int_operand" ""))
3963
              (clobber (match_dup 4))
3964
              (clobber (match_dup 5))
3965
              (use (match_operand:DI 1 "arith_operand" ""))
3966
              (use (match_operand:DI 3 "const_int_operand" ""))])]
3967
  "TARGET_64BIT && optimize > 0"
3968
  "
3969
{
3970
  int size, align;
3971
 
3972
  /* If value to set is not zero, use the library routine.  */
3973
  if (operands[2] != const0_rtx)
3974
    FAIL;
3975
 
3976
  /* Undetermined size, use the library routine.  */
3977
  if (GET_CODE (operands[1]) != CONST_INT)
3978
    FAIL;
3979
 
3980
  size = INTVAL (operands[1]);
3981
  align = INTVAL (operands[3]);
3982
  align = align > 8 ? 8 : align;
3983
 
3984
  /* If size/alignment is large, then use the library routines.  */
3985
  if (size / align > 16)
3986
    FAIL;
3987
 
3988
  /* This does happen, but not often enough to worry much about.  */
3989
  if (size / align < MOVE_RATIO)
3990
    FAIL;
3991
 
3992
  /* Fall through means we're going to use our block clear pattern.  */
3993
  operands[0]
3994
    = replace_equiv_address (operands[0],
3995
                             copy_to_mode_reg (DImode, XEXP (operands[0], 0)));
3996
  operands[4] = gen_reg_rtx (DImode);
3997
  operands[5] = gen_reg_rtx (DImode);
3998
}")
3999
 
4000
(define_insn "clrmemdi_prereload"
4001
  [(set (mem:BLK (match_operand:DI 0 "register_operand" "r,r"))
4002
        (const_int 0))
4003
   (clobber (match_operand:DI 1 "register_operand" "=&r,&r"))	;loop cnt/tmp
4004
   (clobber (match_operand:DI 4 "register_operand" "=&r,&r"))	;item tmp1
4005
   (use (match_operand:DI 2 "arith_operand" "J,1"))      ;byte count
4006
   (use (match_operand:DI 3 "const_int_operand" "n,n"))] ;alignment
4007
  "TARGET_64BIT"
4008
  "#"
4009
  [(set_attr "type" "multi,multi")])
4010
 
4011
(define_split
4012
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
4013
                   (const_int 0))
4014
              (clobber (match_operand:DI 1 "register_operand" ""))
4015
              (clobber (match_operand:DI 4 "register_operand" ""))
4016
              (use (match_operand:DI 2 "arith_operand" ""))
4017
              (use (match_operand:DI 3 "const_int_operand" ""))])]
4018
  "TARGET_64BIT && reload_completed && !flag_peephole2
4019
   && GET_CODE (operands[0]) == MEM
4020
   && register_operand (XEXP (operands[0], 0), DImode)"
4021
  [(set (match_dup 4) (match_dup 5))
4022
   (parallel [(set (match_dup 0) (const_int 0))
4023
              (clobber (match_dup 1))
4024
              (clobber (match_dup 4))
4025
              (use (match_dup 2))
4026
              (use (match_dup 3))
4027
              (const_int 0)])]
4028
  "
4029
{
4030
  operands[5] = XEXP (operands[0], 0);
4031
  operands[0] = replace_equiv_address (operands[0], operands[4]);
4032
}")
4033
 
4034
(define_peephole2
4035
  [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
4036
                   (const_int 0))
4037
              (clobber (match_operand:DI 1 "register_operand" ""))
4038
              (clobber (match_operand:DI 4 "register_operand" ""))
4039
              (use (match_operand:DI 2 "arith_operand" ""))
4040
              (use (match_operand:DI 3 "const_int_operand" ""))])]
4041
  "TARGET_64BIT
4042
   && GET_CODE (operands[0]) == MEM
4043
   && register_operand (XEXP (operands[0], 0), DImode)"
4044
  [(parallel [(set (match_dup 0) (const_int 0))
4045
              (clobber (match_dup 1))
4046
              (clobber (match_dup 4))
4047
              (use (match_dup 2))
4048
              (use (match_dup 3))
4049
              (const_int 0)])]
4050
  "
4051
{
4052
  rtx addr = XEXP (operands[0], 0);
4053
  if (dead_or_set_p (curr_insn, addr))
4054
    operands[4] = addr;
4055
  else
4056
    {
4057
      emit_insn (gen_rtx_SET (VOIDmode, operands[4], addr));
4058
      operands[0] = replace_equiv_address (operands[0], operands[4]);
4059
    }
4060
}")
4061
 
4062
(define_insn "clrmemdi_postreload"
4063
  [(set (mem:BLK (match_operand:DI 0 "register_operand" "+r,r"))
4064
        (const_int 0))
4065
   (clobber (match_operand:DI 1 "register_operand" "=&r,&r"))	;loop cnt/tmp
4066
   (clobber (match_dup 0))
4067
   (use (match_operand:DI 2 "arith_operand" "J,1"))      ;byte count
4068
   (use (match_operand:DI 3 "const_int_operand" "n,n"))  ;alignment
4069
   (const_int 0)]
4070
  "TARGET_64BIT && reload_completed"
4071
  "* return output_block_clear (operands, !which_alternative);"
4072
  [(set_attr "type" "multi,multi")])
4073
 
4074
;; Floating point move insns
4075
 
4076
;; This pattern forces (set (reg:DF ...) (const_double ...))
4077
;; to be reloaded by putting the constant into memory when
4078
;; reg is a floating point register.
4079
;;
4080
;; For integer registers we use ldil;ldo to set the appropriate
4081
;; value.
4082
;;
4083
;; This must come before the movdf pattern, and it must be present
4084
;; to handle obscure reloading cases.
4085
(define_insn ""
4086
  [(set (match_operand:DF 0 "register_operand" "=?r,f")
4087
        (match_operand:DF 1 "" "?F,m"))]
4088
  "GET_CODE (operands[1]) == CONST_DOUBLE
4089
   && operands[1] != CONST0_RTX (DFmode)
4090
   && !TARGET_64BIT
4091
   && !TARGET_SOFT_FLOAT"
4092
  "* return (which_alternative == 0 ? output_move_double (operands)
4093
                                    : \"fldd%F1 %1,%0\");"
4094
  [(set_attr "type" "move,fpload")
4095
   (set_attr "length" "16,4")])
4096
 
4097
(define_expand "movdf"
4098
  [(set (match_operand:DF 0 "general_operand" "")
4099
        (match_operand:DF 1 "general_operand" ""))]
4100
  ""
4101
  "
4102
{
4103
  if (GET_CODE (operands[1]) == CONST_DOUBLE
4104
      && operands[1] != CONST0_RTX (DFmode))
4105
    {
4106
      /* Reject CONST_DOUBLE loads to all hard registers when
4107
         generating 64-bit code and to floating point registers
4108
         when generating 32-bit code.  */
4109
      if (REG_P (operands[0])
4110
          && HARD_REGISTER_P (operands[0])
4111
          && (TARGET_64BIT || REGNO (operands[0]) >= 32))
4112
        FAIL;
4113
 
4114
      if (TARGET_64BIT)
4115
        operands[1] = force_const_mem (DFmode, operands[1]);
4116
    }
4117
 
4118
  if (emit_move_sequence (operands, DFmode, 0))
4119
    DONE;
4120
}")
4121
 
4122
;; Handle DFmode input reloads requiring a general register as a
4123
;; scratch register.
4124
(define_expand "reload_indf"
4125
  [(set (match_operand:DF 0 "register_operand" "=Z")
4126
        (match_operand:DF 1 "non_hard_reg_operand" ""))
4127
   (clobber (match_operand:DF 2 "register_operand" "=&r"))]
4128
  ""
4129
  "
4130
{
4131
  if (emit_move_sequence (operands, DFmode, operands[2]))
4132
    DONE;
4133
 
4134
  /* We don't want the clobber emitted, so handle this ourselves.  */
4135
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4136
  DONE;
4137
}")
4138
 
4139
;; Handle DFmode output reloads requiring a general register as a
4140
;; scratch register.
4141
(define_expand "reload_outdf"
4142
 [(set (match_operand:DF 0 "non_hard_reg_operand" "")
4143
        (match_operand:DF 1  "register_operand" "Z"))
4144
   (clobber (match_operand:DF 2 "register_operand" "=&r"))]
4145
  ""
4146
  "
4147
{
4148
  if (emit_move_sequence (operands, DFmode, operands[2]))
4149
    DONE;
4150
 
4151
  /* We don't want the clobber emitted, so handle this ourselves.  */
4152
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4153
  DONE;
4154
}")
4155
 
4156
(define_insn ""
4157
  [(set (match_operand:DF 0 "move_dest_operand"
4158
                          "=f,*r,Q,?o,?Q,f,*r,*r,?*r,?f")
4159
        (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
4160
                          "fG,*rG,f,*r,*r,RQ,o,RQ,f,*r"))]
4161
  "(register_operand (operands[0], DFmode)
4162
    || reg_or_0_operand (operands[1], DFmode))
4163
   && !(GET_CODE (operands[1]) == CONST_DOUBLE
4164
        && GET_CODE (operands[0]) == MEM)
4165
   && !TARGET_64BIT
4166
   && !TARGET_SOFT_FLOAT"
4167
  "*
4168
{
4169
  if ((FP_REG_P (operands[0]) || FP_REG_P (operands[1])
4170
       || operands[1] == CONST0_RTX (DFmode))
4171
      && !(REG_P (operands[0]) && REG_P (operands[1])
4172
           && FP_REG_P (operands[0]) ^ FP_REG_P (operands[1])))
4173
    return output_fp_move_double (operands);
4174
  return output_move_double (operands);
4175
}"
4176
  [(set_attr "type" "fpalu,move,fpstore,store,store,fpload,load,load,move,move")
4177
   (set_attr "length" "4,8,4,8,16,4,8,16,12,12")])
4178
 
4179
(define_insn ""
4180
  [(set (match_operand:DF 0 "indexed_memory_operand" "=R")
4181
        (match_operand:DF 1 "reg_or_0_operand" "f"))]
4182
  "!TARGET_SOFT_FLOAT
4183
   && !TARGET_DISABLE_INDEXING
4184
   && reload_completed"
4185
  "fstd%F0 %1,%0"
4186
  [(set_attr "type" "fpstore")
4187
   (set_attr "pa_combine_type" "addmove")
4188
   (set_attr "length" "4")])
4189
 
4190
(define_peephole2
4191
  [(set (match_operand:SI 0 "register_operand" "")
4192
        (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
4193
                          (const_int 8))
4194
                 (match_operand:SI 2 "register_operand" "")))
4195
   (set (mem:DF (match_dup 0))
4196
        (match_operand:DF 3 "register_operand" ""))]
4197
  "!TARGET_SOFT_FLOAT
4198
   && !TARGET_DISABLE_INDEXING
4199
   && REG_OK_FOR_BASE_P (operands[2])
4200
   && FP_REGNO_P (REGNO (operands[3]))"
4201
  [(set (mem:DF (plus:SI (mult:SI (match_dup 1) (const_int 8)) (match_dup 2)))
4202
        (match_dup 3))
4203
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 8))
4204
                               (match_dup 2)))]
4205
  "")
4206
 
4207
(define_peephole2
4208
  [(set (match_operand:SI 0 "register_operand" "")
4209
        (plus:SI (match_operand:SI 2 "register_operand" "")
4210
                 (mult:SI (match_operand:SI 1 "register_operand" "")
4211
                          (const_int 8))))
4212
   (set (mem:DF (match_dup 0))
4213
        (match_operand:DF 3 "register_operand" ""))]
4214
  "!TARGET_SOFT_FLOAT
4215
   && !TARGET_DISABLE_INDEXING
4216
   && REG_OK_FOR_BASE_P (operands[2])
4217
   && FP_REGNO_P (REGNO (operands[3]))"
4218
  [(set (mem:DF (plus:SI (mult:SI (match_dup 1) (const_int 8)) (match_dup 2)))
4219
        (match_dup 3))
4220
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 8))
4221
                               (match_dup 2)))]
4222
  "")
4223
 
4224
(define_peephole2
4225
  [(set (match_operand:DI 0 "register_operand" "")
4226
        (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
4227
                          (const_int 8))
4228
                 (match_operand:DI 2 "register_operand" "")))
4229
   (set (mem:DF (match_dup 0))
4230
        (match_operand:DF 3 "register_operand" ""))]
4231
  "!TARGET_SOFT_FLOAT
4232
   && !TARGET_DISABLE_INDEXING
4233
   && TARGET_64BIT
4234
   && REG_OK_FOR_BASE_P (operands[2])
4235
   && FP_REGNO_P (REGNO (operands[3]))"
4236
  [(set (mem:DF (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4237
        (match_dup 3))
4238
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4239
                               (match_dup 2)))]
4240
  "")
4241
 
4242
(define_peephole2
4243
  [(set (match_operand:DI 0 "register_operand" "")
4244
        (plus:DI (match_operand:DI 2 "register_operand" "")
4245
                 (mult:DI (match_operand:DI 1 "register_operand" "")
4246
                          (const_int 8))))
4247
   (set (mem:DF (match_dup 0))
4248
        (match_operand:DF 3 "register_operand" ""))]
4249
  "!TARGET_SOFT_FLOAT
4250
   && !TARGET_DISABLE_INDEXING
4251
   && TARGET_64BIT
4252
   && REG_OK_FOR_BASE_P (operands[2])
4253
   && FP_REGNO_P (REGNO (operands[3]))"
4254
  [(set (mem:DF (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4255
        (match_dup 3))
4256
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4257
                               (match_dup 2)))]
4258
  "")
4259
 
4260
(define_peephole2
4261
  [(set (match_operand:SI 0 "register_operand" "")
4262
        (plus:SI (match_operand:SI 1 "register_operand" "")
4263
                 (match_operand:SI 2 "register_operand" "")))
4264
   (set (mem:DF (match_dup 0))
4265
        (match_operand:DF 3 "register_operand" ""))]
4266
  "!TARGET_SOFT_FLOAT
4267
   && !TARGET_DISABLE_INDEXING
4268
   && TARGET_NO_SPACE_REGS
4269
   && REG_OK_FOR_INDEX_P (operands[1])
4270
   && REG_OK_FOR_BASE_P (operands[2])
4271
   && FP_REGNO_P (REGNO (operands[3]))"
4272
  [(set (mem:DF (plus:SI (match_dup 1) (match_dup 2)))
4273
        (match_dup 3))
4274
   (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
4275
  "")
4276
 
4277
(define_peephole2
4278
  [(set (match_operand:SI 0 "register_operand" "")
4279
        (plus:SI (match_operand:SI 1 "register_operand" "")
4280
                 (match_operand:SI 2 "register_operand" "")))
4281
   (set (mem:DF (match_dup 0))
4282
        (match_operand:DF 3 "register_operand" ""))]
4283
  "!TARGET_SOFT_FLOAT
4284
   && !TARGET_DISABLE_INDEXING
4285
   && TARGET_NO_SPACE_REGS
4286
   && REG_OK_FOR_BASE_P (operands[1])
4287
   && REG_OK_FOR_INDEX_P (operands[2])
4288
   && FP_REGNO_P (REGNO (operands[3]))"
4289
  [(set (mem:DF (plus:SI (match_dup 2) (match_dup 1)))
4290
        (match_dup 3))
4291
   (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
4292
  "")
4293
 
4294
(define_peephole2
4295
  [(set (match_operand:DI 0 "register_operand" "")
4296
        (plus:DI (match_operand:DI 1 "register_operand" "")
4297
                 (match_operand:DI 2 "register_operand" "")))
4298
   (set (mem:DF (match_dup 0))
4299
        (match_operand:DF 3 "register_operand" ""))]
4300
  "!TARGET_SOFT_FLOAT
4301
   && !TARGET_DISABLE_INDEXING
4302
   && TARGET_64BIT
4303
   && TARGET_NO_SPACE_REGS
4304
   && REG_OK_FOR_INDEX_P (operands[1])
4305
   && REG_OK_FOR_BASE_P (operands[2])
4306
   && FP_REGNO_P (REGNO (operands[3]))"
4307
  [(set (mem:DF (plus:DI (match_dup 1) (match_dup 2)))
4308
        (match_dup 3))
4309
   (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4310
  "")
4311
 
4312
(define_peephole2
4313
  [(set (match_operand:DI 0 "register_operand" "")
4314
        (plus:DI (match_operand:DI 1 "register_operand" "")
4315
                 (match_operand:DI 2 "register_operand" "")))
4316
   (set (mem:DF (match_dup 0))
4317
        (match_operand:DF 3 "register_operand" ""))]
4318
  "!TARGET_SOFT_FLOAT
4319
   && !TARGET_DISABLE_INDEXING
4320
   && TARGET_64BIT
4321
   && TARGET_NO_SPACE_REGS
4322
   && REG_OK_FOR_BASE_P (operands[1])
4323
   && REG_OK_FOR_INDEX_P (operands[2])
4324
   && FP_REGNO_P (REGNO (operands[3]))"
4325
  [(set (mem:DF (plus:DI (match_dup 2) (match_dup 1)))
4326
        (match_dup 3))
4327
   (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4328
  "")
4329
 
4330
(define_insn ""
4331
  [(set (match_operand:DF 0 "move_dest_operand"
4332
                          "=r,?o,?Q,r,r")
4333
        (match_operand:DF 1 "reg_or_0_or_nonsymb_mem_operand"
4334
                          "rG,r,r,o,RQ"))]
4335
  "(register_operand (operands[0], DFmode)
4336
    || reg_or_0_operand (operands[1], DFmode))
4337
   && !TARGET_64BIT
4338
   && TARGET_SOFT_FLOAT"
4339
  "*
4340
{
4341
  return output_move_double (operands);
4342
}"
4343
  [(set_attr "type" "move,store,store,load,load")
4344
   (set_attr "length" "8,8,16,8,16")])
4345
 
4346
(define_insn ""
4347
  [(set (match_operand:DF 0 "move_dest_operand"
4348
                          "=!*r,*r,*r,*r,*r,Q,f,f,T")
4349
        (match_operand:DF 1 "move_src_operand"
4350
                          "!*r,J,N,K,RQ,*rG,fG,RT,f"))]
4351
  "(register_operand (operands[0], DFmode)
4352
    || reg_or_0_operand (operands[1], DFmode))
4353
   && !TARGET_SOFT_FLOAT && TARGET_64BIT"
4354
  "@
4355
   copy %1,%0
4356
   ldi %1,%0
4357
   ldil L'%1,%0
4358
   depdi,z %z1,%0
4359
   ldd%M1 %1,%0
4360
   std%M0 %r1,%0
4361
   fcpy,dbl %f1,%0
4362
   fldd%F1 %1,%0
4363
   fstd%F0 %1,%0"
4364
  [(set_attr "type" "move,move,move,shift,load,store,fpalu,fpload,fpstore")
4365
   (set_attr "pa_combine_type" "addmove")
4366
   (set_attr "length" "4,4,4,4,4,4,4,4,4")])
4367
 
4368
 
4369
(define_expand "movdi"
4370
  [(set (match_operand:DI 0 "general_operand" "")
4371
        (match_operand:DI 1 "general_operand" ""))]
4372
  ""
4373
  "
4374
{
4375
  /* Except for zero, we don't support loading a CONST_INT directly
4376
     to a hard floating-point register since a scratch register is
4377
     needed for the operation.  While the operation could be handled
4378
     before no_new_pseudos is true, the simplest solution is to fail.  */
4379
  if (TARGET_64BIT
4380
      && GET_CODE (operands[1]) == CONST_INT
4381
      && operands[1] != CONST0_RTX (DImode)
4382
      && REG_P (operands[0])
4383
      && HARD_REGISTER_P (operands[0])
4384
      && REGNO (operands[0]) >= 32)
4385
    FAIL;
4386
 
4387
  if (emit_move_sequence (operands, DImode, 0))
4388
    DONE;
4389
}")
4390
 
4391
;; Handle DImode input reloads requiring %r1 as a scratch register.
4392
(define_expand "reload_indi_r1"
4393
  [(set (match_operand:DI 0 "register_operand" "=Z")
4394
        (match_operand:DI 1 "non_hard_reg_operand" ""))
4395
   (clobber (match_operand:SI 2 "register_operand" "=&a"))]
4396
  ""
4397
  "
4398
{
4399
  if (emit_move_sequence (operands, DImode, operands[2]))
4400
    DONE;
4401
 
4402
  /* We don't want the clobber emitted, so handle this ourselves.  */
4403
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4404
  DONE;
4405
}")
4406
 
4407
;; Handle DImode input reloads requiring a general register as a
4408
;; scratch register.
4409
(define_expand "reload_indi"
4410
  [(set (match_operand:DI 0 "register_operand" "=Z")
4411
        (match_operand:DI 1 "non_hard_reg_operand" ""))
4412
   (clobber (match_operand:SI 2 "register_operand" "=&r"))]
4413
  ""
4414
  "
4415
{
4416
  if (emit_move_sequence (operands, DImode, operands[2]))
4417
    DONE;
4418
 
4419
  /* We don't want the clobber emitted, so handle this ourselves.  */
4420
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4421
  DONE;
4422
}")
4423
 
4424
;; Handle DImode output reloads requiring a general register as a
4425
;; scratch register.
4426
(define_expand "reload_outdi"
4427
  [(set (match_operand:DI 0 "non_hard_reg_operand" "")
4428
        (match_operand:DI 1 "register_operand" "Z"))
4429
   (clobber (match_operand:SI 2 "register_operand" "=&r"))]
4430
  ""
4431
  "
4432
{
4433
  if (emit_move_sequence (operands, DImode, operands[2]))
4434
    DONE;
4435
 
4436
  /* We don't want the clobber emitted, so handle this ourselves.  */
4437
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4438
  DONE;
4439
}")
4440
 
4441
(define_insn ""
4442
  [(set (match_operand:DI 0 "register_operand" "=r")
4443
        (high:DI (match_operand 1 "" "")))]
4444
  "!TARGET_64BIT"
4445
  "*
4446
{
4447
  rtx op0 = operands[0];
4448
  rtx op1 = operands[1];
4449
 
4450
  switch (GET_CODE (op1))
4451
    {
4452
    case CONST_INT:
4453
#if HOST_BITS_PER_WIDE_INT <= 32
4454
      operands[0] = operand_subword (op0, 1, 0, DImode);
4455
      output_asm_insn (\"ldil L'%1,%0\", operands);
4456
 
4457
      operands[0] = operand_subword (op0, 0, 0, DImode);
4458
      if (INTVAL (op1) < 0)
4459
        output_asm_insn (\"ldi -1,%0\", operands);
4460
      else
4461
        output_asm_insn (\"ldi 0,%0\", operands);
4462
#else
4463
      operands[0] = operand_subword (op0, 1, 0, DImode);
4464
      operands[1] = GEN_INT (INTVAL (op1) & 0xffffffff);
4465
      output_asm_insn (\"ldil L'%1,%0\", operands);
4466
 
4467
      operands[0] = operand_subword (op0, 0, 0, DImode);
4468
      operands[1] = GEN_INT (INTVAL (op1) >> 32);
4469
      output_asm_insn (singlemove_string (operands), operands);
4470
#endif
4471
      break;
4472
 
4473
    case CONST_DOUBLE:
4474
      operands[0] = operand_subword (op0, 1, 0, DImode);
4475
      operands[1] = GEN_INT (CONST_DOUBLE_LOW (op1));
4476
      output_asm_insn (\"ldil L'%1,%0\", operands);
4477
 
4478
      operands[0] = operand_subword (op0, 0, 0, DImode);
4479
      operands[1] = GEN_INT (CONST_DOUBLE_HIGH (op1));
4480
      output_asm_insn (singlemove_string (operands), operands);
4481
      break;
4482
 
4483
    default:
4484
      gcc_unreachable ();
4485
    }
4486
  return \"\";
4487
}"
4488
  [(set_attr "type" "move")
4489
   (set_attr "length" "12")])
4490
 
4491
(define_insn ""
4492
  [(set (match_operand:DI 0 "move_dest_operand"
4493
                          "=r,o,Q,r,r,r,*f,*f,T,?r,?*f")
4494
        (match_operand:DI 1 "general_operand"
4495
                          "rM,r,r,o*R,Q,i,*fM,RT,*f,*f,r"))]
4496
  "(register_operand (operands[0], DImode)
4497
    || reg_or_0_operand (operands[1], DImode))
4498
   && !TARGET_64BIT
4499
   && !TARGET_SOFT_FLOAT"
4500
  "*
4501
{
4502
  if ((FP_REG_P (operands[0]) || FP_REG_P (operands[1])
4503
       || operands[1] == CONST0_RTX (DFmode))
4504
      && !(REG_P (operands[0]) && REG_P (operands[1])
4505
           && FP_REG_P (operands[0]) ^ FP_REG_P (operands[1])))
4506
    return output_fp_move_double (operands);
4507
  return output_move_double (operands);
4508
}"
4509
  [(set_attr "type"
4510
    "move,store,store,load,load,multi,fpalu,fpload,fpstore,move,move")
4511
   (set_attr "length" "8,8,16,8,16,16,4,4,4,12,12")])
4512
 
4513
(define_insn ""
4514
  [(set (match_operand:DI 0 "move_dest_operand"
4515
                          "=r,r,r,r,r,r,Q,!*q,!r,!*f,*f,T")
4516
        (match_operand:DI 1 "move_src_operand"
4517
                          "A,r,J,N,K,RQ,rM,!rM,!*q,!*fM,RT,*f"))]
4518
  "(register_operand (operands[0], DImode)
4519
    || reg_or_0_operand (operands[1], DImode))
4520
   && !TARGET_SOFT_FLOAT && TARGET_64BIT"
4521
  "@
4522
   ldd RT'%A1,%0
4523
   copy %1,%0
4524
   ldi %1,%0
4525
   ldil L'%1,%0
4526
   depdi,z %z1,%0
4527
   ldd%M1 %1,%0
4528
   std%M0 %r1,%0
4529
   mtsar %r1
4530
   {mfctl|mfctl,w} %%sar,%0
4531
   fcpy,dbl %f1,%0
4532
   fldd%F1 %1,%0
4533
   fstd%F0 %1,%0"
4534
  [(set_attr "type" "load,move,move,move,shift,load,store,move,move,fpalu,fpload,fpstore")
4535
   (set_attr "pa_combine_type" "addmove")
4536
   (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,4")])
4537
 
4538
(define_insn ""
4539
  [(set (match_operand:DI 0 "indexed_memory_operand" "=R")
4540
        (match_operand:DI 1 "register_operand" "f"))]
4541
  "!TARGET_SOFT_FLOAT
4542
   && TARGET_64BIT
4543
   && !TARGET_DISABLE_INDEXING
4544
   && reload_completed"
4545
  "fstd%F0 %1,%0"
4546
  [(set_attr "type" "fpstore")
4547
   (set_attr "pa_combine_type" "addmove")
4548
   (set_attr "length" "4")])
4549
 
4550
(define_peephole2
4551
  [(set (match_operand:DI 0 "register_operand" "")
4552
        (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
4553
                          (const_int 8))
4554
                 (match_operand:DI 2 "register_operand" "")))
4555
   (set (mem:DI (match_dup 0))
4556
        (match_operand:DI 3 "register_operand" ""))]
4557
  "!TARGET_SOFT_FLOAT
4558
   && !TARGET_DISABLE_INDEXING
4559
   && TARGET_64BIT
4560
   && REG_OK_FOR_BASE_P (operands[2])
4561
   && FP_REGNO_P (REGNO (operands[3]))"
4562
  [(set (mem:DI (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4563
        (match_dup 3))
4564
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4565
                               (match_dup 2)))]
4566
  "")
4567
 
4568
(define_peephole2
4569
  [(set (match_operand:DI 0 "register_operand" "")
4570
        (plus:DI (match_operand:DI 2 "register_operand" "")
4571
                 (mult:DI (match_operand:DI 1 "register_operand" "")
4572
                          (const_int 8))))
4573
   (set (mem:DI (match_dup 0))
4574
        (match_operand:DI 3 "register_operand" ""))]
4575
  "!TARGET_SOFT_FLOAT
4576
   && !TARGET_DISABLE_INDEXING
4577
   && TARGET_64BIT
4578
   && REG_OK_FOR_BASE_P (operands[2])
4579
   && FP_REGNO_P (REGNO (operands[3]))"
4580
  [(set (mem:DI (plus:DI (mult:DI (match_dup 1) (const_int 8)) (match_dup 2)))
4581
        (match_dup 3))
4582
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 8))
4583
                               (match_dup 2)))]
4584
  "")
4585
 
4586
(define_peephole2
4587
  [(set (match_operand:DI 0 "register_operand" "")
4588
        (plus:DI (match_operand:DI 1 "register_operand" "")
4589
                 (match_operand:DI 2 "register_operand" "")))
4590
   (set (mem:DI (match_dup 0))
4591
        (match_operand:DI 3 "register_operand" ""))]
4592
  "!TARGET_SOFT_FLOAT
4593
   && !TARGET_DISABLE_INDEXING
4594
   && TARGET_64BIT
4595
   && TARGET_NO_SPACE_REGS
4596
   && REG_OK_FOR_INDEX_P (operands[1])
4597
   && REG_OK_FOR_BASE_P (operands[2])
4598
   && FP_REGNO_P (REGNO (operands[3]))"
4599
  [(set (mem:DI (plus:DI (match_dup 1) (match_dup 2)))
4600
        (match_dup 3))
4601
   (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4602
  "")
4603
 
4604
(define_peephole2
4605
  [(set (match_operand:DI 0 "register_operand" "")
4606
        (plus:DI (match_operand:DI 1 "register_operand" "")
4607
                 (match_operand:DI 2 "register_operand" "")))
4608
   (set (mem:DI (match_dup 0))
4609
        (match_operand:DI 3 "register_operand" ""))]
4610
  "!TARGET_SOFT_FLOAT
4611
   && !TARGET_DISABLE_INDEXING
4612
   && TARGET_64BIT
4613
   && TARGET_NO_SPACE_REGS
4614
   && REG_OK_FOR_BASE_P (operands[1])
4615
   && REG_OK_FOR_INDEX_P (operands[2])
4616
   && FP_REGNO_P (REGNO (operands[3]))"
4617
  [(set (mem:DI (plus:DI (match_dup 2) (match_dup 1)))
4618
        (match_dup 3))
4619
   (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4620
  "")
4621
 
4622
(define_insn ""
4623
  [(set (match_operand:DI 0 "move_dest_operand"
4624
                          "=r,o,Q,r,r,r")
4625
        (match_operand:DI 1 "general_operand"
4626
                          "rM,r,r,o,Q,i"))]
4627
  "(register_operand (operands[0], DImode)
4628
    || reg_or_0_operand (operands[1], DImode))
4629
   && !TARGET_64BIT
4630
   && TARGET_SOFT_FLOAT"
4631
  "*
4632
{
4633
  return output_move_double (operands);
4634
}"
4635
  [(set_attr "type" "move,store,store,load,load,multi")
4636
   (set_attr "length" "8,8,16,8,16,16")])
4637
 
4638
(define_insn ""
4639
  [(set (match_operand:DI 0 "register_operand" "=r,&r")
4640
        (lo_sum:DI (match_operand:DI 1 "register_operand" "0,r")
4641
                   (match_operand:DI 2 "immediate_operand" "i,i")))]
4642
  "!TARGET_64BIT"
4643
  "*
4644
{
4645
  /* Don't output a 64 bit constant, since we can't trust the assembler to
4646
     handle it correctly.  */
4647
  if (GET_CODE (operands[2]) == CONST_DOUBLE)
4648
    operands[2] = GEN_INT (CONST_DOUBLE_LOW (operands[2]));
4649
  else if (HOST_BITS_PER_WIDE_INT > 32
4650
           && GET_CODE (operands[2]) == CONST_INT)
4651
    operands[2] = GEN_INT (INTVAL (operands[2]) & 0xffffffff);
4652
  if (which_alternative == 1)
4653
    output_asm_insn (\"copy %1,%0\", operands);
4654
  return \"ldo R'%G2(%R1),%R0\";
4655
}"
4656
  [(set_attr "type" "move,move")
4657
   (set_attr "length" "4,8")])
4658
 
4659
;; This pattern forces (set (reg:SF ...) (const_double ...))
4660
;; to be reloaded by putting the constant into memory when
4661
;; reg is a floating point register.
4662
;;
4663
;; For integer registers we use ldil;ldo to set the appropriate
4664
;; value.
4665
;;
4666
;; This must come before the movsf pattern, and it must be present
4667
;; to handle obscure reloading cases.
4668
(define_insn ""
4669
  [(set (match_operand:SF 0 "register_operand" "=?r,f")
4670
        (match_operand:SF 1 "" "?F,m"))]
4671
  "GET_CODE (operands[1]) == CONST_DOUBLE
4672
   && operands[1] != CONST0_RTX (SFmode)
4673
   && ! TARGET_SOFT_FLOAT"
4674
  "* return (which_alternative == 0 ? singlemove_string (operands)
4675
                                    : \" fldw%F1 %1,%0\");"
4676
  [(set_attr "type" "move,fpload")
4677
   (set_attr "length" "8,4")])
4678
 
4679
(define_expand "movsf"
4680
  [(set (match_operand:SF 0 "general_operand" "")
4681
        (match_operand:SF 1 "general_operand" ""))]
4682
  ""
4683
  "
4684
{
4685
  /* Reject CONST_DOUBLE loads to floating point registers.  */
4686
  if (GET_CODE (operands[1]) == CONST_DOUBLE
4687
      && operands[1] != CONST0_RTX (SFmode)
4688
      && REG_P (operands[0])
4689
      && HARD_REGISTER_P (operands[0])
4690
      && REGNO (operands[0]) >= 32)
4691
    FAIL;
4692
 
4693
  if (emit_move_sequence (operands, SFmode, 0))
4694
    DONE;
4695
}")
4696
 
4697
;; Handle SFmode input reloads requiring a general register as a
4698
;; scratch register.
4699
(define_expand "reload_insf"
4700
  [(set (match_operand:SF 0 "register_operand" "=Z")
4701
        (match_operand:SF 1 "non_hard_reg_operand" ""))
4702
   (clobber (match_operand:SF 2 "register_operand" "=&r"))]
4703
  ""
4704
  "
4705
{
4706
  if (emit_move_sequence (operands, SFmode, operands[2]))
4707
    DONE;
4708
 
4709
  /* We don't want the clobber emitted, so handle this ourselves.  */
4710
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4711
  DONE;
4712
}")
4713
 
4714
;; Handle SFmode output reloads requiring a general register as a
4715
;; scratch register.
4716
(define_expand "reload_outsf"
4717
  [(set (match_operand:SF 0 "non_hard_reg_operand" "")
4718
        (match_operand:SF 1  "register_operand" "Z"))
4719
   (clobber (match_operand:SF 2 "register_operand" "=&r"))]
4720
  ""
4721
  "
4722
{
4723
  if (emit_move_sequence (operands, SFmode, operands[2]))
4724
    DONE;
4725
 
4726
  /* We don't want the clobber emitted, so handle this ourselves.  */
4727
  emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4728
  DONE;
4729
}")
4730
 
4731
(define_insn ""
4732
  [(set (match_operand:SF 0 "move_dest_operand"
4733
                          "=f,!*r,f,*r,Q,Q,?*r,?f")
4734
        (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4735
                          "fG,!*rG,RQ,RQ,f,*rG,f,*r"))]
4736
  "(register_operand (operands[0], SFmode)
4737
    || reg_or_0_operand (operands[1], SFmode))
4738
   && !TARGET_SOFT_FLOAT
4739
   && !TARGET_64BIT"
4740
  "@
4741
   fcpy,sgl %f1,%0
4742
   copy %r1,%0
4743
   fldw%F1 %1,%0
4744
   ldw%M1 %1,%0
4745
   fstw%F0 %1,%0
4746
   stw%M0 %r1,%0
4747
   {fstws|fstw} %1,-16(%%sp)\n\t{ldws|ldw} -16(%%sp),%0
4748
   {stws|stw} %1,-16(%%sp)\n\t{fldws|fldw} -16(%%sp),%0"
4749
  [(set_attr "type" "fpalu,move,fpload,load,fpstore,store,move,move")
4750
   (set_attr "pa_combine_type" "addmove")
4751
   (set_attr "length" "4,4,4,4,4,4,8,8")])
4752
 
4753
(define_insn ""
4754
  [(set (match_operand:SF 0 "move_dest_operand"
4755
                          "=f,!*r,f,*r,Q,Q")
4756
        (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4757
                          "fG,!*rG,RQ,RQ,f,*rG"))]
4758
  "(register_operand (operands[0], SFmode)
4759
    || reg_or_0_operand (operands[1], SFmode))
4760
   && !TARGET_SOFT_FLOAT
4761
   && TARGET_64BIT"
4762
  "@
4763
   fcpy,sgl %f1,%0
4764
   copy %r1,%0
4765
   fldw%F1 %1,%0
4766
   ldw%M1 %1,%0
4767
   fstw%F0 %1,%0
4768
   stw%M0 %r1,%0"
4769
  [(set_attr "type" "fpalu,move,fpload,load,fpstore,store")
4770
   (set_attr "pa_combine_type" "addmove")
4771
   (set_attr "length" "4,4,4,4,4,4")])
4772
 
4773
(define_insn ""
4774
  [(set (match_operand:SF 0 "indexed_memory_operand" "=R")
4775
        (match_operand:SF 1 "register_operand" "f"))]
4776
  "!TARGET_SOFT_FLOAT
4777
   && !TARGET_DISABLE_INDEXING
4778
   && reload_completed"
4779
  "fstw%F0 %1,%0"
4780
  [(set_attr "type" "fpstore")
4781
   (set_attr "pa_combine_type" "addmove")
4782
   (set_attr "length" "4")])
4783
 
4784
(define_peephole2
4785
  [(set (match_operand:SI 0 "register_operand" "")
4786
        (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "")
4787
                          (const_int 4))
4788
                 (match_operand:SI 2 "register_operand" "")))
4789
   (set (mem:SF (match_dup 0))
4790
        (match_operand:SF 3 "register_operand" ""))]
4791
  "!TARGET_SOFT_FLOAT
4792
   && !TARGET_DISABLE_INDEXING
4793
   && REG_OK_FOR_BASE_P (operands[2])
4794
   && FP_REGNO_P (REGNO (operands[3]))"
4795
  [(set (mem:SF (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
4796
        (match_dup 3))
4797
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
4798
                               (match_dup 2)))]
4799
  "")
4800
 
4801
(define_peephole2
4802
  [(set (match_operand:SI 0 "register_operand" "")
4803
        (plus:SI (match_operand:SI 2 "register_operand" "")
4804
                 (mult:SI (match_operand:SI 1 "register_operand" "")
4805
                          (const_int 4))))
4806
   (set (mem:SF (match_dup 0))
4807
        (match_operand:SF 3 "register_operand" ""))]
4808
  "!TARGET_SOFT_FLOAT
4809
   && !TARGET_DISABLE_INDEXING
4810
   && REG_OK_FOR_BASE_P (operands[2])
4811
   && FP_REGNO_P (REGNO (operands[3]))"
4812
  [(set (mem:SF (plus:SI (mult:SI (match_dup 1) (const_int 4)) (match_dup 2)))
4813
        (match_dup 3))
4814
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 1) (const_int 4))
4815
                               (match_dup 2)))]
4816
  "")
4817
 
4818
(define_peephole2
4819
  [(set (match_operand:DI 0 "register_operand" "")
4820
        (plus:DI (mult:DI (match_operand:DI 1 "register_operand" "")
4821
                          (const_int 4))
4822
                 (match_operand:DI 2 "register_operand" "")))
4823
   (set (mem:SF (match_dup 0))
4824
        (match_operand:SF 3 "register_operand" ""))]
4825
  "!TARGET_SOFT_FLOAT
4826
   && !TARGET_DISABLE_INDEXING
4827
   && TARGET_64BIT
4828
   && REG_OK_FOR_BASE_P (operands[2])
4829
   && FP_REGNO_P (REGNO (operands[3]))"
4830
  [(set (mem:SF (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
4831
        (match_dup 3))
4832
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
4833
                               (match_dup 2)))]
4834
  "")
4835
 
4836
(define_peephole2
4837
  [(set (match_operand:DI 0 "register_operand" "")
4838
        (plus:DI (match_operand:DI 2 "register_operand" "")
4839
                 (mult:DI (match_operand:DI 1 "register_operand" "")
4840
                          (const_int 4))))
4841
   (set (mem:SF (match_dup 0))
4842
        (match_operand:SF 3 "register_operand" ""))]
4843
  "!TARGET_SOFT_FLOAT
4844
   && !TARGET_DISABLE_INDEXING
4845
   && TARGET_64BIT
4846
   && REG_OK_FOR_BASE_P (operands[2])
4847
   && FP_REGNO_P (REGNO (operands[3]))"
4848
  [(set (mem:SF (plus:DI (mult:DI (match_dup 1) (const_int 4)) (match_dup 2)))
4849
        (match_dup 3))
4850
   (set (match_dup 0) (plus:DI (mult:DI (match_dup 1) (const_int 4))
4851
                               (match_dup 2)))]
4852
  "")
4853
 
4854
(define_peephole2
4855
  [(set (match_operand:SI 0 "register_operand" "")
4856
        (plus:SI (match_operand:SI 1 "register_operand" "")
4857
                 (match_operand:SI 2 "register_operand" "")))
4858
   (set (mem:SF (match_dup 0))
4859
        (match_operand:SF 3 "register_operand" ""))]
4860
  "!TARGET_SOFT_FLOAT
4861
   && !TARGET_DISABLE_INDEXING
4862
   && TARGET_NO_SPACE_REGS
4863
   && REG_OK_FOR_INDEX_P (operands[1])
4864
   && REG_OK_FOR_BASE_P (operands[2])
4865
   && FP_REGNO_P (REGNO (operands[3]))"
4866
  [(set (mem:SF (plus:SI (match_dup 1) (match_dup 2)))
4867
        (match_dup 3))
4868
   (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
4869
  "")
4870
 
4871
(define_peephole2
4872
  [(set (match_operand:SI 0 "register_operand" "")
4873
        (plus:SI (match_operand:SI 1 "register_operand" "")
4874
                 (match_operand:SI 2 "register_operand" "")))
4875
   (set (mem:SF (match_dup 0))
4876
        (match_operand:SF 3 "register_operand" ""))]
4877
  "!TARGET_SOFT_FLOAT
4878
   && !TARGET_DISABLE_INDEXING
4879
   && TARGET_NO_SPACE_REGS
4880
   && REG_OK_FOR_BASE_P (operands[1])
4881
   && REG_OK_FOR_INDEX_P (operands[2])
4882
   && FP_REGNO_P (REGNO (operands[3]))"
4883
  [(set (mem:SF (plus:SI (match_dup 2) (match_dup 1)))
4884
        (match_dup 3))
4885
   (set (match_dup 0) (plus:SI (match_dup 2) (match_dup 1)))]
4886
  "")
4887
 
4888
(define_peephole2
4889
  [(set (match_operand:DI 0 "register_operand" "")
4890
        (plus:DI (match_operand:DI 1 "register_operand" "")
4891
                 (match_operand:DI 2 "register_operand" "")))
4892
   (set (mem:SF (match_dup 0))
4893
        (match_operand:SF 3 "register_operand" ""))]
4894
  "!TARGET_SOFT_FLOAT
4895
   && !TARGET_DISABLE_INDEXING
4896
   && TARGET_64BIT
4897
   && TARGET_NO_SPACE_REGS
4898
   && REG_OK_FOR_INDEX_P (operands[1])
4899
   && REG_OK_FOR_BASE_P (operands[2])
4900
   && FP_REGNO_P (REGNO (operands[3]))"
4901
  [(set (mem:SF (plus:DI (match_dup 1) (match_dup 2)))
4902
        (match_dup 3))
4903
   (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
4904
  "")
4905
 
4906
(define_peephole2
4907
  [(set (match_operand:DI 0 "register_operand" "")
4908
        (plus:DI (match_operand:DI 1 "register_operand" "")
4909
                 (match_operand:DI 2 "register_operand" "")))
4910
   (set (mem:SF (match_dup 0))
4911
        (match_operand:SF 3 "register_operand" ""))]
4912
  "!TARGET_SOFT_FLOAT
4913
   && !TARGET_DISABLE_INDEXING
4914
   && TARGET_64BIT
4915
   && TARGET_NO_SPACE_REGS
4916
   && REG_OK_FOR_BASE_P (operands[1])
4917
   && REG_OK_FOR_INDEX_P (operands[2])
4918
   && FP_REGNO_P (REGNO (operands[3]))"
4919
  [(set (mem:SF (plus:DI (match_dup 2) (match_dup 1)))
4920
        (match_dup 3))
4921
   (set (match_dup 0) (plus:DI (match_dup 2) (match_dup 1)))]
4922
  "")
4923
 
4924
(define_insn ""
4925
  [(set (match_operand:SF 0 "move_dest_operand"
4926
                          "=r,r,Q")
4927
        (match_operand:SF 1 "reg_or_0_or_nonsymb_mem_operand"
4928
                          "rG,RQ,rG"))]
4929
  "(register_operand (operands[0], SFmode)
4930
    || reg_or_0_operand (operands[1], SFmode))
4931
   && TARGET_SOFT_FLOAT"
4932
  "@
4933
   copy %r1,%0
4934
   ldw%M1 %1,%0
4935
   stw%M0 %r1,%0"
4936
  [(set_attr "type" "move,load,store")
4937
   (set_attr "pa_combine_type" "addmove")
4938
   (set_attr "length" "4,4,4")])
4939
 
4940
 
4941
 
4942
;;- zero extension instructions
4943
;; We have define_expand for zero extension patterns to make sure the
4944
;; operands get loaded into registers.  The define_insns accept
4945
;; memory operands.  This gives us better overall code than just
4946
;; having a pattern that does or does not accept memory operands.
4947
 
4948
(define_expand "zero_extendqihi2"
4949
  [(set (match_operand:HI 0 "register_operand" "")
4950
        (zero_extend:HI
4951
         (match_operand:QI 1 "register_operand" "")))]
4952
  ""
4953
  "")
4954
 
4955
(define_insn ""
4956
  [(set (match_operand:HI 0 "register_operand" "=r,r")
4957
        (zero_extend:HI
4958
         (match_operand:QI 1 "move_src_operand" "r,RQ")))]
4959
  "GET_CODE (operands[1]) != CONST_INT"
4960
  "@
4961
   {extru|extrw,u} %1,31,8,%0
4962
   ldb%M1 %1,%0"
4963
  [(set_attr "type" "shift,load")
4964
   (set_attr "length" "4,4")])
4965
 
4966
(define_expand "zero_extendqisi2"
4967
  [(set (match_operand:SI 0 "register_operand" "")
4968
        (zero_extend:SI
4969
         (match_operand:QI 1 "register_operand" "")))]
4970
  ""
4971
  "")
4972
 
4973
(define_insn ""
4974
  [(set (match_operand:SI 0 "register_operand" "=r,r")
4975
        (zero_extend:SI
4976
         (match_operand:QI 1 "move_src_operand" "r,RQ")))]
4977
  "GET_CODE (operands[1]) != CONST_INT"
4978
  "@
4979
   {extru|extrw,u} %1,31,8,%0
4980
   ldb%M1 %1,%0"
4981
  [(set_attr "type" "shift,load")
4982
   (set_attr "length" "4,4")])
4983
 
4984
(define_expand "zero_extendhisi2"
4985
  [(set (match_operand:SI 0 "register_operand" "")
4986
        (zero_extend:SI
4987
         (match_operand:HI 1 "register_operand" "")))]
4988
  ""
4989
  "")
4990
 
4991
(define_insn ""
4992
  [(set (match_operand:SI 0 "register_operand" "=r,r")
4993
        (zero_extend:SI
4994
         (match_operand:HI 1 "move_src_operand" "r,RQ")))]
4995
  "GET_CODE (operands[1]) != CONST_INT"
4996
  "@
4997
   {extru|extrw,u} %1,31,16,%0
4998
   ldh%M1 %1,%0"
4999
  [(set_attr "type" "shift,load")
5000
   (set_attr "length" "4,4")])
5001
 
5002
(define_expand "zero_extendqidi2"
5003
  [(set (match_operand:DI 0 "register_operand" "")
5004
        (zero_extend:DI
5005
         (match_operand:QI 1 "register_operand" "")))]
5006
  "TARGET_64BIT"
5007
  "")
5008
 
5009
(define_insn ""
5010
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5011
        (zero_extend:DI
5012
         (match_operand:QI 1 "move_src_operand" "r,RQ")))]
5013
  "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
5014
  "@
5015
   extrd,u %1,63,8,%0
5016
   ldb%M1 %1,%0"
5017
  [(set_attr "type" "shift,load")
5018
   (set_attr "length" "4,4")])
5019
 
5020
(define_expand "zero_extendhidi2"
5021
  [(set (match_operand:DI 0 "register_operand" "")
5022
        (zero_extend:DI
5023
         (match_operand:HI 1 "register_operand" "")))]
5024
  "TARGET_64BIT"
5025
  "")
5026
 
5027
(define_insn ""
5028
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5029
        (zero_extend:DI
5030
         (match_operand:HI 1 "move_src_operand" "r,RQ")))]
5031
  "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
5032
  "@
5033
   extrd,u %1,63,16,%0
5034
   ldh%M1 %1,%0"
5035
  [(set_attr "type" "shift,load")
5036
   (set_attr "length" "4,4")])
5037
 
5038
(define_expand "zero_extendsidi2"
5039
  [(set (match_operand:DI 0 "register_operand" "")
5040
        (zero_extend:DI
5041
         (match_operand:SI 1 "register_operand" "")))]
5042
  "TARGET_64BIT"
5043
  "")
5044
 
5045
(define_insn ""
5046
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5047
        (zero_extend:DI
5048
         (match_operand:SI 1 "move_src_operand" "r,RQ")))]
5049
  "TARGET_64BIT && GET_CODE (operands[1]) != CONST_INT"
5050
  "@
5051
   extrd,u %1,63,32,%0
5052
   ldw%M1 %1,%0"
5053
  [(set_attr "type" "shift,load")
5054
   (set_attr "length" "4,4")])
5055
 
5056
;;- sign extension instructions
5057
 
5058
(define_insn "extendhisi2"
5059
  [(set (match_operand:SI 0 "register_operand" "=r")
5060
        (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
5061
  ""
5062
  "{extrs|extrw,s} %1,31,16,%0"
5063
  [(set_attr "type" "shift")
5064
   (set_attr "length" "4")])
5065
 
5066
(define_insn "extendqihi2"
5067
  [(set (match_operand:HI 0 "register_operand" "=r")
5068
        (sign_extend:HI (match_operand:QI 1 "register_operand" "r")))]
5069
  ""
5070
  "{extrs|extrw,s} %1,31,8,%0"
5071
  [(set_attr "type" "shift")
5072
  (set_attr "length" "4")])
5073
 
5074
(define_insn "extendqisi2"
5075
  [(set (match_operand:SI 0 "register_operand" "=r")
5076
        (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
5077
  ""
5078
  "{extrs|extrw,s} %1,31,8,%0"
5079
  [(set_attr "type" "shift")
5080
   (set_attr "length" "4")])
5081
 
5082
(define_insn "extendqidi2"
5083
  [(set (match_operand:DI 0 "register_operand" "=r")
5084
        (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))]
5085
  "TARGET_64BIT"
5086
  "extrd,s %1,63,8,%0"
5087
  [(set_attr "type" "shift")
5088
  (set_attr "length" "4")])
5089
 
5090
(define_insn "extendhidi2"
5091
  [(set (match_operand:DI 0 "register_operand" "=r")
5092
        (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))]
5093
  "TARGET_64BIT"
5094
  "extrd,s %1,63,16,%0"
5095
  [(set_attr "type" "shift")
5096
  (set_attr "length" "4")])
5097
 
5098
(define_insn "extendsidi2"
5099
  [(set (match_operand:DI 0 "register_operand" "=r")
5100
        (sign_extend:DI (match_operand:SI 1 "register_operand" "r")))]
5101
  "TARGET_64BIT"
5102
  "extrd,s %1,63,32,%0"
5103
  [(set_attr "type" "shift")
5104
  (set_attr "length" "4")])
5105
 
5106
 
5107
;; Conversions between float and double.
5108
 
5109
(define_insn "extendsfdf2"
5110
  [(set (match_operand:DF 0 "register_operand" "=f")
5111
        (float_extend:DF
5112
         (match_operand:SF 1 "register_operand" "f")))]
5113
  "! TARGET_SOFT_FLOAT"
5114
  "{fcnvff|fcnv},sgl,dbl %1,%0"
5115
  [(set_attr "type" "fpalu")
5116
   (set_attr "length" "4")])
5117
 
5118
(define_insn "truncdfsf2"
5119
  [(set (match_operand:SF 0 "register_operand" "=f")
5120
        (float_truncate:SF
5121
         (match_operand:DF 1 "register_operand" "f")))]
5122
  "! TARGET_SOFT_FLOAT"
5123
  "{fcnvff|fcnv},dbl,sgl %1,%0"
5124
  [(set_attr "type" "fpalu")
5125
   (set_attr "length" "4")])
5126
 
5127
;; Conversion between fixed point and floating point.
5128
;; Note that among the fix-to-float insns
5129
;; the ones that start with SImode come first.
5130
;; That is so that an operand that is a CONST_INT
5131
;; (and therefore lacks a specific machine mode).
5132
;; will be recognized as SImode (which is always valid)
5133
;; rather than as QImode or HImode.
5134
 
5135
;; This pattern forces (set (reg:SF ...) (float:SF (const_int ...)))
5136
;; to be reloaded by putting the constant into memory.
5137
;; It must come before the more general floatsisf2 pattern.
5138
(define_insn ""
5139
  [(set (match_operand:SF 0 "register_operand" "=f")
5140
        (float:SF (match_operand:SI 1 "const_int_operand" "m")))]
5141
  "! TARGET_SOFT_FLOAT"
5142
  "fldw%F1 %1,%0\;{fcnvxf,sgl,sgl|fcnv,w,sgl} %0,%0"
5143
  [(set_attr "type" "fpalu")
5144
   (set_attr "length" "8")])
5145
 
5146
(define_insn "floatsisf2"
5147
  [(set (match_operand:SF 0 "register_operand" "=f")
5148
        (float:SF (match_operand:SI 1 "register_operand" "f")))]
5149
  "! TARGET_SOFT_FLOAT"
5150
  "{fcnvxf,sgl,sgl|fcnv,w,sgl} %1,%0"
5151
  [(set_attr "type" "fpalu")
5152
   (set_attr "length" "4")])
5153
 
5154
;; This pattern forces (set (reg:DF ...) (float:DF (const_int ...)))
5155
;; to be reloaded by putting the constant into memory.
5156
;; It must come before the more general floatsidf2 pattern.
5157
(define_insn ""
5158
  [(set (match_operand:DF 0 "register_operand" "=f")
5159
        (float:DF (match_operand:SI 1 "const_int_operand" "m")))]
5160
  "! TARGET_SOFT_FLOAT"
5161
  "fldw%F1 %1,%0\;{fcnvxf,sgl,dbl|fcnv,w,dbl} %0,%0"
5162
  [(set_attr "type" "fpalu")
5163
   (set_attr "length" "8")])
5164
 
5165
(define_insn "floatsidf2"
5166
  [(set (match_operand:DF 0 "register_operand" "=f")
5167
        (float:DF (match_operand:SI 1 "register_operand" "f")))]
5168
  "! TARGET_SOFT_FLOAT"
5169
  "{fcnvxf,sgl,dbl|fcnv,w,dbl} %1,%0"
5170
  [(set_attr "type" "fpalu")
5171
   (set_attr "length" "4")])
5172
 
5173
(define_expand "floatunssisf2"
5174
  [(set (subreg:SI (match_dup 2) 4)
5175
        (match_operand:SI 1 "register_operand" ""))
5176
   (set (subreg:SI (match_dup 2) 0)
5177
        (const_int 0))
5178
   (set (match_operand:SF 0 "register_operand" "")
5179
        (float:SF (match_dup 2)))]
5180
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5181
  "
5182
{
5183
  if (TARGET_PA_20)
5184
    {
5185
      emit_insn (gen_floatunssisf2_pa20 (operands[0], operands[1]));
5186
      DONE;
5187
    }
5188
  operands[2] = gen_reg_rtx (DImode);
5189
}")
5190
 
5191
(define_expand "floatunssidf2"
5192
  [(set (subreg:SI (match_dup 2) 4)
5193
        (match_operand:SI 1 "register_operand" ""))
5194
   (set (subreg:SI (match_dup 2) 0)
5195
        (const_int 0))
5196
   (set (match_operand:DF 0 "register_operand" "")
5197
        (float:DF (match_dup 2)))]
5198
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5199
  "
5200
{
5201
  if (TARGET_PA_20)
5202
    {
5203
      emit_insn (gen_floatunssidf2_pa20 (operands[0], operands[1]));
5204
      DONE;
5205
    }
5206
  operands[2] = gen_reg_rtx (DImode);
5207
}")
5208
 
5209
(define_insn "floatdisf2"
5210
  [(set (match_operand:SF 0 "register_operand" "=f")
5211
        (float:SF (match_operand:DI 1 "register_operand" "f")))]
5212
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5213
  "{fcnvxf,dbl,sgl|fcnv,dw,sgl} %1,%0"
5214
  [(set_attr "type" "fpalu")
5215
   (set_attr "length" "4")])
5216
 
5217
(define_insn "floatdidf2"
5218
  [(set (match_operand:DF 0 "register_operand" "=f")
5219
        (float:DF (match_operand:DI 1 "register_operand" "f")))]
5220
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5221
  "{fcnvxf,dbl,dbl|fcnv,dw,dbl} %1,%0"
5222
  [(set_attr "type" "fpalu")
5223
   (set_attr "length" "4")])
5224
 
5225
;; Convert a float to an actual integer.
5226
;; Truncation is performed as part of the conversion.
5227
 
5228
(define_insn "fix_truncsfsi2"
5229
  [(set (match_operand:SI 0 "register_operand" "=f")
5230
        (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
5231
  "! TARGET_SOFT_FLOAT"
5232
  "{fcnvfxt,sgl,sgl|fcnv,t,sgl,w} %1,%0"
5233
  [(set_attr "type" "fpalu")
5234
   (set_attr "length" "4")])
5235
 
5236
(define_insn "fix_truncdfsi2"
5237
  [(set (match_operand:SI 0 "register_operand" "=f")
5238
        (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
5239
  "! TARGET_SOFT_FLOAT"
5240
  "{fcnvfxt,dbl,sgl|fcnv,t,dbl,w} %1,%0"
5241
  [(set_attr "type" "fpalu")
5242
   (set_attr "length" "4")])
5243
 
5244
(define_insn "fix_truncsfdi2"
5245
  [(set (match_operand:DI 0 "register_operand" "=f")
5246
        (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
5247
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5248
  "{fcnvfxt,sgl,dbl|fcnv,t,sgl,dw} %1,%0"
5249
  [(set_attr "type" "fpalu")
5250
   (set_attr "length" "4")])
5251
 
5252
(define_insn "fix_truncdfdi2"
5253
  [(set (match_operand:DI 0 "register_operand" "=f")
5254
        (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
5255
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT"
5256
  "{fcnvfxt,dbl,dbl|fcnv,t,dbl,dw} %1,%0"
5257
  [(set_attr "type" "fpalu")
5258
   (set_attr "length" "4")])
5259
 
5260
(define_insn "floatunssidf2_pa20"
5261
  [(set (match_operand:DF 0 "register_operand" "=f")
5262
        (unsigned_float:DF (match_operand:SI 1 "register_operand" "f")))]
5263
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5264
  "fcnv,uw,dbl %1,%0"
5265
  [(set_attr "type" "fpalu")
5266
   (set_attr "length" "4")])
5267
 
5268
(define_insn "floatunssisf2_pa20"
5269
  [(set (match_operand:SF 0 "register_operand" "=f")
5270
        (unsigned_float:SF (match_operand:SI 1 "register_operand" "f")))]
5271
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5272
  "fcnv,uw,sgl %1,%0"
5273
  [(set_attr "type" "fpalu")
5274
   (set_attr "length" "4")])
5275
 
5276
(define_insn "floatunsdisf2"
5277
  [(set (match_operand:SF 0 "register_operand" "=f")
5278
        (unsigned_float:SF (match_operand:DI 1 "register_operand" "f")))]
5279
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5280
  "fcnv,udw,sgl %1,%0"
5281
  [(set_attr "type" "fpalu")
5282
   (set_attr "length" "4")])
5283
 
5284
(define_insn "floatunsdidf2"
5285
  [(set (match_operand:DF 0 "register_operand" "=f")
5286
        (unsigned_float:DF (match_operand:DI 1 "register_operand" "f")))]
5287
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5288
  "fcnv,udw,dbl %1,%0"
5289
  [(set_attr "type" "fpalu")
5290
   (set_attr "length" "4")])
5291
 
5292
(define_insn "fixuns_truncsfsi2"
5293
  [(set (match_operand:SI 0 "register_operand" "=f")
5294
        (unsigned_fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
5295
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5296
  "fcnv,t,sgl,uw %1,%0"
5297
  [(set_attr "type" "fpalu")
5298
   (set_attr "length" "4")])
5299
 
5300
(define_insn "fixuns_truncdfsi2"
5301
  [(set (match_operand:SI 0 "register_operand" "=f")
5302
        (unsigned_fix:SI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
5303
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5304
  "fcnv,t,dbl,uw %1,%0"
5305
  [(set_attr "type" "fpalu")
5306
   (set_attr "length" "4")])
5307
 
5308
(define_insn "fixuns_truncsfdi2"
5309
  [(set (match_operand:DI 0 "register_operand" "=f")
5310
        (unsigned_fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
5311
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5312
  "fcnv,t,sgl,udw %1,%0"
5313
  [(set_attr "type" "fpalu")
5314
   (set_attr "length" "4")])
5315
 
5316
(define_insn "fixuns_truncdfdi2"
5317
  [(set (match_operand:DI 0 "register_operand" "=f")
5318
        (unsigned_fix:DI (fix:DF (match_operand:DF 1 "register_operand" "f"))))]
5319
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
5320
  "fcnv,t,dbl,udw %1,%0"
5321
  [(set_attr "type" "fpalu")
5322
   (set_attr "length" "4")])
5323
 
5324
;;- arithmetic instructions
5325
 
5326
(define_expand "adddi3"
5327
  [(set (match_operand:DI 0 "register_operand" "")
5328
        (plus:DI (match_operand:DI 1 "register_operand" "")
5329
                 (match_operand:DI 2 "adddi3_operand" "")))]
5330
  ""
5331
  "")
5332
 
5333
(define_insn ""
5334
  [(set (match_operand:DI 0 "register_operand" "=r")
5335
        (plus:DI (match_operand:DI 1 "register_operand" "%r")
5336
                 (match_operand:DI 2 "arith11_operand" "rI")))]
5337
  "!TARGET_64BIT"
5338
  "*
5339
{
5340
  if (GET_CODE (operands[2]) == CONST_INT)
5341
    {
5342
      if (INTVAL (operands[2]) >= 0)
5343
        return \"addi %2,%R1,%R0\;{addc|add,c} %1,%%r0,%0\";
5344
      else
5345
        return \"addi %2,%R1,%R0\;{subb|sub,b} %1,%%r0,%0\";
5346
    }
5347
  else
5348
    return \"add %R2,%R1,%R0\;{addc|add,c} %2,%1,%0\";
5349
}"
5350
  [(set_attr "type" "binary")
5351
   (set_attr "length" "8")])
5352
 
5353
(define_insn ""
5354
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5355
        (plus:DI (match_operand:DI 1 "register_operand" "%r,r")
5356
                 (match_operand:DI 2 "arith_operand" "r,J")))]
5357
  "TARGET_64BIT"
5358
  "@
5359
   add,l %1,%2,%0
5360
   ldo %2(%1),%0"
5361
  [(set_attr "type" "binary,binary")
5362
   (set_attr "pa_combine_type" "addmove")
5363
   (set_attr "length" "4,4")])
5364
 
5365
(define_insn ""
5366
  [(set (match_operand:DI 0 "register_operand" "=r")
5367
        (plus:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
5368
                 (match_operand:DI 2 "register_operand" "r")))]
5369
  "TARGET_64BIT"
5370
  "uaddcm %2,%1,%0"
5371
  [(set_attr "type" "binary")
5372
   (set_attr "length" "4")])
5373
 
5374
(define_insn ""
5375
  [(set (match_operand:SI 0 "register_operand" "=r")
5376
        (plus:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
5377
                 (match_operand:SI 2 "register_operand" "r")))]
5378
  ""
5379
  "uaddcm %2,%1,%0"
5380
  [(set_attr "type" "binary")
5381
   (set_attr "length" "4")])
5382
 
5383
;; define_splits to optimize cases of adding a constant integer
5384
;; to a register when the constant does not fit in 14 bits.  */
5385
(define_split
5386
  [(set (match_operand:SI 0 "register_operand" "")
5387
        (plus:SI (match_operand:SI 1 "register_operand" "")
5388
                 (match_operand:SI 2 "const_int_operand" "")))
5389
   (clobber (match_operand:SI 4 "register_operand" ""))]
5390
  "! cint_ok_for_move (INTVAL (operands[2]))
5391
   && VAL_14_BITS_P (INTVAL (operands[2]) >> 1)"
5392
  [(set (match_dup 4) (plus:SI (match_dup 1) (match_dup 2)))
5393
   (set (match_dup 0) (plus:SI (match_dup 4) (match_dup 3)))]
5394
  "
5395
{
5396
  int val = INTVAL (operands[2]);
5397
  int low = (val < 0) ? -0x2000 : 0x1fff;
5398
  int rest = val - low;
5399
 
5400
  operands[2] = GEN_INT (rest);
5401
  operands[3] = GEN_INT (low);
5402
}")
5403
 
5404
(define_split
5405
  [(set (match_operand:SI 0 "register_operand" "")
5406
        (plus:SI (match_operand:SI 1 "register_operand" "")
5407
                 (match_operand:SI 2 "const_int_operand" "")))
5408
   (clobber (match_operand:SI 4 "register_operand" ""))]
5409
  "! cint_ok_for_move (INTVAL (operands[2]))"
5410
  [(set (match_dup 4) (match_dup 2))
5411
   (set (match_dup 0) (plus:SI (mult:SI (match_dup 4) (match_dup 3))
5412
                               (match_dup 1)))]
5413
  "
5414
{
5415
  HOST_WIDE_INT intval = INTVAL (operands[2]);
5416
 
5417
  /* Try dividing the constant by 2, then 4, and finally 8 to see
5418
     if we can get a constant which can be loaded into a register
5419
     in a single instruction (cint_ok_for_move).
5420
 
5421
     If that fails, try to negate the constant and subtract it
5422
     from our input operand.  */
5423
  if (intval % 2 == 0 && cint_ok_for_move (intval / 2))
5424
    {
5425
      operands[2] = GEN_INT (intval / 2);
5426
      operands[3] = const2_rtx;
5427
    }
5428
  else if (intval % 4 == 0 && cint_ok_for_move (intval / 4))
5429
    {
5430
      operands[2] = GEN_INT (intval / 4);
5431
      operands[3] = GEN_INT (4);
5432
    }
5433
  else if (intval % 8 == 0 && cint_ok_for_move (intval / 8))
5434
    {
5435
      operands[2] = GEN_INT (intval / 8);
5436
      operands[3] = GEN_INT (8);
5437
    }
5438
  else if (cint_ok_for_move (-intval))
5439
    {
5440
      emit_insn (gen_rtx_SET (VOIDmode, operands[4], GEN_INT (-intval)));
5441
      emit_insn (gen_subsi3 (operands[0], operands[1], operands[4]));
5442
      DONE;
5443
    }
5444
  else
5445
    FAIL;
5446
}")
5447
 
5448
(define_insn "addsi3"
5449
  [(set (match_operand:SI 0 "register_operand" "=r,r")
5450
        (plus:SI (match_operand:SI 1 "register_operand" "%r,r")
5451
                 (match_operand:SI 2 "arith_operand" "r,J")))]
5452
  ""
5453
  "@
5454
   {addl|add,l} %1,%2,%0
5455
   ldo %2(%1),%0"
5456
  [(set_attr "type" "binary,binary")
5457
   (set_attr "pa_combine_type" "addmove")
5458
   (set_attr "length" "4,4")])
5459
 
5460
(define_expand "subdi3"
5461
  [(set (match_operand:DI 0 "register_operand" "")
5462
        (minus:DI (match_operand:DI 1 "register_operand" "")
5463
                  (match_operand:DI 2 "register_operand" "")))]
5464
  ""
5465
  "")
5466
 
5467
(define_insn ""
5468
  [(set (match_operand:DI 0 "register_operand" "=r")
5469
        (minus:DI (match_operand:DI 1 "register_operand" "r")
5470
                  (match_operand:DI 2 "register_operand" "r")))]
5471
  "!TARGET_64BIT"
5472
  "sub %R1,%R2,%R0\;{subb|sub,b} %1,%2,%0"
5473
  [(set_attr "type" "binary")
5474
  (set_attr "length" "8")])
5475
 
5476
(define_insn ""
5477
  [(set (match_operand:DI 0 "register_operand" "=r,r,!q")
5478
        (minus:DI (match_operand:DI 1 "arith11_operand" "r,I,!U")
5479
                  (match_operand:DI 2 "register_operand" "r,r,!r")))]
5480
  "TARGET_64BIT"
5481
  "@
5482
   sub %1,%2,%0
5483
   subi %1,%2,%0
5484
   mtsarcm %2"
5485
  [(set_attr "type" "binary,binary,move")
5486
  (set_attr "length" "4,4,4")])
5487
 
5488
(define_expand "subsi3"
5489
  [(set (match_operand:SI 0 "register_operand" "")
5490
        (minus:SI (match_operand:SI 1 "arith11_operand" "")
5491
                  (match_operand:SI 2 "register_operand" "")))]
5492
  ""
5493
  "")
5494
 
5495
(define_insn ""
5496
  [(set (match_operand:SI 0 "register_operand" "=r,r")
5497
        (minus:SI (match_operand:SI 1 "arith11_operand" "r,I")
5498
                  (match_operand:SI 2 "register_operand" "r,r")))]
5499
  "!TARGET_PA_20"
5500
  "@
5501
   sub %1,%2,%0
5502
   subi %1,%2,%0"
5503
  [(set_attr "type" "binary,binary")
5504
   (set_attr "length" "4,4")])
5505
 
5506
(define_insn ""
5507
  [(set (match_operand:SI 0 "register_operand" "=r,r,!q")
5508
        (minus:SI (match_operand:SI 1 "arith11_operand" "r,I,!S")
5509
                  (match_operand:SI 2 "register_operand" "r,r,!r")))]
5510
  "TARGET_PA_20"
5511
  "@
5512
   sub %1,%2,%0
5513
   subi %1,%2,%0
5514
   mtsarcm %2"
5515
  [(set_attr "type" "binary,binary,move")
5516
   (set_attr "length" "4,4,4")])
5517
 
5518
;; Clobbering a "register_operand" instead of a match_scratch
5519
;; in operand3 of millicode calls avoids spilling %r1 and
5520
;; produces better code.
5521
 
5522
;; The mulsi3 insns set up registers for the millicode call.
5523
(define_expand "mulsi3"
5524
  [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5525
   (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5526
   (parallel [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5527
              (clobber (match_dup 3))
5528
              (clobber (reg:SI 26))
5529
              (clobber (reg:SI 25))
5530
              (clobber (match_dup 4))])
5531
   (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5532
  ""
5533
  "
5534
{
5535
  operands[4] = gen_rtx_REG (SImode, TARGET_64BIT ? 2 : 31);
5536
  if (TARGET_PA_11 && !TARGET_DISABLE_FPREGS && !TARGET_SOFT_FLOAT)
5537
    {
5538
      rtx scratch = gen_reg_rtx (DImode);
5539
      operands[1] = force_reg (SImode, operands[1]);
5540
      operands[2] = force_reg (SImode, operands[2]);
5541
      emit_insn (gen_umulsidi3 (scratch, operands[1], operands[2]));
5542
      emit_insn (gen_movsi (operands[0],
5543
                            gen_rtx_SUBREG (SImode, scratch,
5544
                                            GET_MODE_SIZE (SImode))));
5545
      DONE;
5546
    }
5547
  operands[3] = gen_reg_rtx (SImode);
5548
}")
5549
 
5550
(define_insn "umulsidi3"
5551
  [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
5552
        (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5553
                 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "f"))))]
5554
  "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
5555
  "xmpyu %1,%2,%0"
5556
  [(set_attr "type" "fpmuldbl")
5557
   (set_attr "length" "4")])
5558
 
5559
(define_insn ""
5560
  [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
5561
        (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5562
                 (match_operand:DI 2 "uint32_operand" "f")))]
5563
  "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && !TARGET_64BIT"
5564
  "xmpyu %1,%R2,%0"
5565
  [(set_attr "type" "fpmuldbl")
5566
   (set_attr "length" "4")])
5567
 
5568
(define_insn ""
5569
  [(set (match_operand:DI 0 "nonimmediate_operand" "=f")
5570
        (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "f"))
5571
                 (match_operand:DI 2 "uint32_operand" "f")))]
5572
  "TARGET_PA_11 && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT && TARGET_64BIT"
5573
  "xmpyu %1,%2R,%0"
5574
  [(set_attr "type" "fpmuldbl")
5575
   (set_attr "length" "4")])
5576
 
5577
(define_insn ""
5578
  [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5579
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5580
   (clobber (reg:SI 26))
5581
   (clobber (reg:SI 25))
5582
   (clobber (reg:SI 31))]
5583
  "!TARGET_64BIT"
5584
  "* return output_mul_insn (0, insn);"
5585
  [(set_attr "type" "milli")
5586
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5587
 
5588
(define_insn ""
5589
  [(set (reg:SI 29) (mult:SI (reg:SI 26) (reg:SI 25)))
5590
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5591
   (clobber (reg:SI 26))
5592
   (clobber (reg:SI 25))
5593
   (clobber (reg:SI 2))]
5594
  "TARGET_64BIT"
5595
  "* return output_mul_insn (0, insn);"
5596
  [(set_attr "type" "milli")
5597
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5598
 
5599
(define_expand "muldi3"
5600
  [(set (match_operand:DI 0 "register_operand" "")
5601
        (mult:DI (match_operand:DI 1 "register_operand" "")
5602
                 (match_operand:DI 2 "register_operand" "")))]
5603
  "TARGET_64BIT && ! TARGET_DISABLE_FPREGS && ! TARGET_SOFT_FLOAT"
5604
  "
5605
{
5606
  rtx low_product = gen_reg_rtx (DImode);
5607
  rtx cross_product1 = gen_reg_rtx (DImode);
5608
  rtx cross_product2 = gen_reg_rtx (DImode);
5609
  rtx cross_scratch = gen_reg_rtx (DImode);
5610
  rtx cross_product = gen_reg_rtx (DImode);
5611
  rtx op1l, op1r, op2l, op2r;
5612
  rtx op1shifted, op2shifted;
5613
 
5614
  op1shifted = gen_reg_rtx (DImode);
5615
  op2shifted = gen_reg_rtx (DImode);
5616
  op1l = gen_reg_rtx (SImode);
5617
  op1r = gen_reg_rtx (SImode);
5618
  op2l = gen_reg_rtx (SImode);
5619
  op2r = gen_reg_rtx (SImode);
5620
 
5621
  emit_move_insn (op1shifted, gen_rtx_LSHIFTRT (DImode, operands[1],
5622
                                                GEN_INT (32)));
5623
  emit_move_insn (op2shifted, gen_rtx_LSHIFTRT (DImode, operands[2],
5624
                                                GEN_INT (32)));
5625
  op1r = force_reg (SImode, gen_rtx_SUBREG (SImode, operands[1], 4));
5626
  op2r = force_reg (SImode, gen_rtx_SUBREG (SImode, operands[2], 4));
5627
  op1l = force_reg (SImode, gen_rtx_SUBREG (SImode, op1shifted, 4));
5628
  op2l = force_reg (SImode, gen_rtx_SUBREG (SImode, op2shifted, 4));
5629
 
5630
  /* Emit multiplies for the cross products.  */
5631
  emit_insn (gen_umulsidi3 (cross_product1, op2r, op1l));
5632
  emit_insn (gen_umulsidi3 (cross_product2, op2l, op1r));
5633
 
5634
  /* Emit a multiply for the low sub-word.  */
5635
  emit_insn (gen_umulsidi3 (low_product, copy_rtx (op2r), copy_rtx (op1r)));
5636
 
5637
  /* Sum the cross products and shift them into proper position.  */
5638
  emit_insn (gen_adddi3 (cross_scratch, cross_product1, cross_product2));
5639
  emit_insn (gen_ashldi3 (cross_product, cross_scratch, GEN_INT (32)));
5640
 
5641
  /* Add the cross product to the low product and store the result
5642
     into the output operand .  */
5643
  emit_insn (gen_adddi3 (operands[0], cross_product, low_product));
5644
  DONE;
5645
}")
5646
 
5647
;;; Division and mod.
5648
(define_expand "divsi3"
5649
  [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5650
   (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5651
   (parallel [(set (reg:SI 29) (div:SI (reg:SI 26) (reg:SI 25)))
5652
              (clobber (match_dup 3))
5653
              (clobber (match_dup 4))
5654
              (clobber (reg:SI 26))
5655
              (clobber (reg:SI 25))
5656
              (clobber (match_dup 5))])
5657
   (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5658
  ""
5659
  "
5660
{
5661
  operands[3] = gen_reg_rtx (SImode);
5662
  if (TARGET_64BIT)
5663
    {
5664
      operands[5] = gen_rtx_REG (SImode, 2);
5665
      operands[4] = operands[5];
5666
    }
5667
  else
5668
    {
5669
      operands[5] = gen_rtx_REG (SImode, 31);
5670
      operands[4] = gen_reg_rtx (SImode);
5671
    }
5672
  if (GET_CODE (operands[2]) == CONST_INT && emit_hpdiv_const (operands, 0))
5673
    DONE;
5674
}")
5675
 
5676
(define_insn ""
5677
  [(set (reg:SI 29)
5678
        (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5679
   (clobber (match_operand:SI 1 "register_operand" "=a"))
5680
   (clobber (match_operand:SI 2 "register_operand" "=&r"))
5681
   (clobber (reg:SI 26))
5682
   (clobber (reg:SI 25))
5683
   (clobber (reg:SI 31))]
5684
  "!TARGET_64BIT"
5685
  "*
5686
   return output_div_insn (operands, 0, insn);"
5687
  [(set_attr "type" "milli")
5688
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5689
 
5690
(define_insn ""
5691
  [(set (reg:SI 29)
5692
        (div:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5693
   (clobber (match_operand:SI 1 "register_operand" "=a"))
5694
   (clobber (match_operand:SI 2 "register_operand" "=&r"))
5695
   (clobber (reg:SI 26))
5696
   (clobber (reg:SI 25))
5697
   (clobber (reg:SI 2))]
5698
  "TARGET_64BIT"
5699
  "*
5700
   return output_div_insn (operands, 0, insn);"
5701
  [(set_attr "type" "milli")
5702
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5703
 
5704
(define_expand "udivsi3"
5705
  [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5706
   (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5707
   (parallel [(set (reg:SI 29) (udiv:SI (reg:SI 26) (reg:SI 25)))
5708
              (clobber (match_dup 3))
5709
              (clobber (match_dup 4))
5710
              (clobber (reg:SI 26))
5711
              (clobber (reg:SI 25))
5712
              (clobber (match_dup 5))])
5713
   (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5714
  ""
5715
  "
5716
{
5717
  operands[3] = gen_reg_rtx (SImode);
5718
 
5719
  if (TARGET_64BIT)
5720
    {
5721
      operands[5] = gen_rtx_REG (SImode, 2);
5722
      operands[4] = operands[5];
5723
    }
5724
  else
5725
    {
5726
      operands[5] = gen_rtx_REG (SImode, 31);
5727
      operands[4] = gen_reg_rtx (SImode);
5728
    }
5729
  if (GET_CODE (operands[2]) == CONST_INT && emit_hpdiv_const (operands, 1))
5730
    DONE;
5731
}")
5732
 
5733
(define_insn ""
5734
  [(set (reg:SI 29)
5735
        (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5736
   (clobber (match_operand:SI 1 "register_operand" "=a"))
5737
   (clobber (match_operand:SI 2 "register_operand" "=&r"))
5738
   (clobber (reg:SI 26))
5739
   (clobber (reg:SI 25))
5740
   (clobber (reg:SI 31))]
5741
  "!TARGET_64BIT"
5742
  "*
5743
   return output_div_insn (operands, 1, insn);"
5744
  [(set_attr "type" "milli")
5745
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5746
 
5747
(define_insn ""
5748
  [(set (reg:SI 29)
5749
        (udiv:SI (reg:SI 26) (match_operand:SI 0 "div_operand" "")))
5750
   (clobber (match_operand:SI 1 "register_operand" "=a"))
5751
   (clobber (match_operand:SI 2 "register_operand" "=&r"))
5752
   (clobber (reg:SI 26))
5753
   (clobber (reg:SI 25))
5754
   (clobber (reg:SI 2))]
5755
  "TARGET_64BIT"
5756
  "*
5757
   return output_div_insn (operands, 1, insn);"
5758
  [(set_attr "type" "milli")
5759
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5760
 
5761
(define_expand "modsi3"
5762
  [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5763
   (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5764
   (parallel [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5765
              (clobber (match_dup 3))
5766
              (clobber (match_dup 4))
5767
              (clobber (reg:SI 26))
5768
              (clobber (reg:SI 25))
5769
              (clobber (match_dup 5))])
5770
   (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5771
  ""
5772
  "
5773
{
5774
  if (TARGET_64BIT)
5775
    {
5776
      operands[5] = gen_rtx_REG (SImode, 2);
5777
      operands[4] = operands[5];
5778
    }
5779
  else
5780
    {
5781
      operands[5] = gen_rtx_REG (SImode, 31);
5782
      operands[4] = gen_reg_rtx (SImode);
5783
    }
5784
  operands[3] = gen_reg_rtx (SImode);
5785
}")
5786
 
5787
(define_insn ""
5788
  [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5789
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5790
   (clobber (match_operand:SI 1 "register_operand" "=&r"))
5791
   (clobber (reg:SI 26))
5792
   (clobber (reg:SI 25))
5793
   (clobber (reg:SI 31))]
5794
  "!TARGET_64BIT"
5795
  "*
5796
  return output_mod_insn (0, insn);"
5797
  [(set_attr "type" "milli")
5798
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5799
 
5800
(define_insn ""
5801
  [(set (reg:SI 29) (mod:SI (reg:SI 26) (reg:SI 25)))
5802
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5803
   (clobber (match_operand:SI 1 "register_operand" "=&r"))
5804
   (clobber (reg:SI 26))
5805
   (clobber (reg:SI 25))
5806
   (clobber (reg:SI 2))]
5807
  "TARGET_64BIT"
5808
  "*
5809
  return output_mod_insn (0, insn);"
5810
  [(set_attr "type" "milli")
5811
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5812
 
5813
(define_expand "umodsi3"
5814
  [(set (reg:SI 26) (match_operand:SI 1 "move_src_operand" ""))
5815
   (set (reg:SI 25) (match_operand:SI 2 "move_src_operand" ""))
5816
   (parallel [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5817
              (clobber (match_dup 3))
5818
              (clobber (match_dup 4))
5819
              (clobber (reg:SI 26))
5820
              (clobber (reg:SI 25))
5821
              (clobber (match_dup 5))])
5822
   (set (match_operand:SI 0 "move_dest_operand" "") (reg:SI 29))]
5823
  ""
5824
  "
5825
{
5826
  if (TARGET_64BIT)
5827
    {
5828
      operands[5] = gen_rtx_REG (SImode, 2);
5829
      operands[4] = operands[5];
5830
    }
5831
  else
5832
    {
5833
      operands[5] = gen_rtx_REG (SImode, 31);
5834
      operands[4] = gen_reg_rtx (SImode);
5835
    }
5836
  operands[3] = gen_reg_rtx (SImode);
5837
}")
5838
 
5839
(define_insn ""
5840
  [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5841
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5842
   (clobber (match_operand:SI 1 "register_operand" "=&r"))
5843
   (clobber (reg:SI 26))
5844
   (clobber (reg:SI 25))
5845
   (clobber (reg:SI 31))]
5846
  "!TARGET_64BIT"
5847
  "*
5848
  return output_mod_insn (1, insn);"
5849
  [(set_attr "type" "milli")
5850
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5851
 
5852
(define_insn ""
5853
  [(set (reg:SI 29) (umod:SI (reg:SI 26) (reg:SI 25)))
5854
   (clobber (match_operand:SI 0 "register_operand" "=a"))
5855
   (clobber (match_operand:SI 1 "register_operand" "=&r"))
5856
   (clobber (reg:SI 26))
5857
   (clobber (reg:SI 25))
5858
   (clobber (reg:SI 2))]
5859
  "TARGET_64BIT"
5860
  "*
5861
  return output_mod_insn (1, insn);"
5862
  [(set_attr "type" "milli")
5863
   (set (attr "length") (symbol_ref "attr_length_millicode_call (insn)"))])
5864
 
5865
;;- and instructions
5866
;; We define DImode `and` so with DImode `not` we can get
5867
;; DImode `andn`.  Other combinations are possible.
5868
 
5869
(define_expand "anddi3"
5870
  [(set (match_operand:DI 0 "register_operand" "")
5871
        (and:DI (match_operand:DI 1 "register_operand" "")
5872
                (match_operand:DI 2 "and_operand" "")))]
5873
  ""
5874
  "
5875
{
5876
  /* Both operands must be register operands.  */
5877
  if (!TARGET_64BIT && !register_operand (operands[2], DImode))
5878
    FAIL;
5879
}")
5880
 
5881
(define_insn ""
5882
  [(set (match_operand:DI 0 "register_operand" "=r")
5883
        (and:DI (match_operand:DI 1 "register_operand" "%r")
5884
                (match_operand:DI 2 "register_operand" "r")))]
5885
  "!TARGET_64BIT"
5886
  "and %1,%2,%0\;and %R1,%R2,%R0"
5887
  [(set_attr "type" "binary")
5888
   (set_attr "length" "8")])
5889
 
5890
(define_insn ""
5891
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5892
        (and:DI (match_operand:DI 1 "register_operand" "%?r,0")
5893
                (match_operand:DI 2 "and_operand" "rO,P")))]
5894
  "TARGET_64BIT"
5895
  "* return output_64bit_and (operands); "
5896
  [(set_attr "type" "binary")
5897
   (set_attr "length" "4")])
5898
 
5899
; The ? for op1 makes reload prefer zdepi instead of loading a huge
5900
; constant with ldil;ldo.
5901
(define_insn "andsi3"
5902
  [(set (match_operand:SI 0 "register_operand" "=r,r")
5903
        (and:SI (match_operand:SI 1 "register_operand" "%?r,0")
5904
                (match_operand:SI 2 "and_operand" "rO,P")))]
5905
  ""
5906
  "* return output_and (operands); "
5907
  [(set_attr "type" "binary,shift")
5908
   (set_attr "length" "4,4")])
5909
 
5910
(define_insn ""
5911
  [(set (match_operand:DI 0 "register_operand" "=r")
5912
        (and:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
5913
                (match_operand:DI 2 "register_operand" "r")))]
5914
  "!TARGET_64BIT"
5915
  "andcm %2,%1,%0\;andcm %R2,%R1,%R0"
5916
  [(set_attr "type" "binary")
5917
   (set_attr "length" "8")])
5918
 
5919
(define_insn ""
5920
  [(set (match_operand:DI 0 "register_operand" "=r")
5921
        (and:DI (not:DI (match_operand:DI 1 "register_operand" "r"))
5922
                (match_operand:DI 2 "register_operand" "r")))]
5923
  "TARGET_64BIT"
5924
  "andcm %2,%1,%0"
5925
  [(set_attr "type" "binary")
5926
   (set_attr "length" "4")])
5927
 
5928
(define_insn ""
5929
  [(set (match_operand:SI 0 "register_operand" "=r")
5930
        (and:SI (not:SI (match_operand:SI 1 "register_operand" "r"))
5931
                (match_operand:SI 2 "register_operand" "r")))]
5932
  ""
5933
  "andcm %2,%1,%0"
5934
  [(set_attr "type" "binary")
5935
  (set_attr "length" "4")])
5936
 
5937
(define_expand "iordi3"
5938
  [(set (match_operand:DI 0 "register_operand" "")
5939
        (ior:DI (match_operand:DI 1 "register_operand" "")
5940
                (match_operand:DI 2 "ior_operand" "")))]
5941
  ""
5942
  "
5943
{
5944
  /* Both operands must be register operands.  */
5945
  if (!TARGET_64BIT && !register_operand (operands[2], DImode))
5946
    FAIL;
5947
}")
5948
 
5949
(define_insn ""
5950
  [(set (match_operand:DI 0 "register_operand" "=r")
5951
        (ior:DI (match_operand:DI 1 "register_operand" "%r")
5952
                (match_operand:DI 2 "register_operand" "r")))]
5953
  "!TARGET_64BIT"
5954
  "or %1,%2,%0\;or %R1,%R2,%R0"
5955
  [(set_attr "type" "binary")
5956
   (set_attr "length" "8")])
5957
 
5958
(define_insn ""
5959
  [(set (match_operand:DI 0 "register_operand" "=r,r")
5960
        (ior:DI (match_operand:DI 1 "register_operand" "0,0")
5961
                (match_operand:DI 2 "ior_operand" "M,i")))]
5962
  "TARGET_64BIT"
5963
  "* return output_64bit_ior (operands); "
5964
  [(set_attr "type" "binary,shift")
5965
   (set_attr "length" "4,4")])
5966
 
5967
(define_insn ""
5968
  [(set (match_operand:DI 0 "register_operand" "=r")
5969
        (ior:DI (match_operand:DI 1 "register_operand" "%r")
5970
                (match_operand:DI 2 "register_operand" "r")))]
5971
  "TARGET_64BIT"
5972
  "or %1,%2,%0"
5973
  [(set_attr "type" "binary")
5974
   (set_attr "length" "4")])
5975
 
5976
;; Need a define_expand because we've run out of CONST_OK... characters.
5977
(define_expand "iorsi3"
5978
  [(set (match_operand:SI 0 "register_operand" "")
5979
        (ior:SI (match_operand:SI 1 "register_operand" "")
5980
                (match_operand:SI 2 "arith32_operand" "")))]
5981
  ""
5982
  "
5983
{
5984
  if (! (ior_operand (operands[2], SImode)
5985
         || register_operand (operands[2], SImode)))
5986
    operands[2] = force_reg (SImode, operands[2]);
5987
}")
5988
 
5989
(define_insn ""
5990
  [(set (match_operand:SI 0 "register_operand" "=r,r")
5991
        (ior:SI (match_operand:SI 1 "register_operand" "0,0")
5992
                (match_operand:SI 2 "ior_operand" "M,i")))]
5993
  ""
5994
  "* return output_ior (operands); "
5995
  [(set_attr "type" "binary,shift")
5996
   (set_attr "length" "4,4")])
5997
 
5998
(define_insn ""
5999
  [(set (match_operand:SI 0 "register_operand" "=r")
6000
        (ior:SI (match_operand:SI 1 "register_operand" "%r")
6001
                (match_operand:SI 2 "register_operand" "r")))]
6002
  ""
6003
  "or %1,%2,%0"
6004
  [(set_attr "type" "binary")
6005
   (set_attr "length" "4")])
6006
 
6007
(define_expand "xordi3"
6008
  [(set (match_operand:DI 0 "register_operand" "")
6009
        (xor:DI (match_operand:DI 1 "register_operand" "")
6010
                (match_operand:DI 2 "register_operand" "")))]
6011
  ""
6012
  "
6013
{
6014
}")
6015
 
6016
(define_insn ""
6017
  [(set (match_operand:DI 0 "register_operand" "=r")
6018
        (xor:DI (match_operand:DI 1 "register_operand" "%r")
6019
                (match_operand:DI 2 "register_operand" "r")))]
6020
  "!TARGET_64BIT"
6021
  "xor %1,%2,%0\;xor %R1,%R2,%R0"
6022
  [(set_attr "type" "binary")
6023
   (set_attr "length" "8")])
6024
 
6025
(define_insn ""
6026
  [(set (match_operand:DI 0 "register_operand" "=r")
6027
        (xor:DI (match_operand:DI 1 "register_operand" "%r")
6028
                (match_operand:DI 2 "register_operand" "r")))]
6029
  "TARGET_64BIT"
6030
  "xor %1,%2,%0"
6031
  [(set_attr "type" "binary")
6032
   (set_attr "length" "4")])
6033
 
6034
(define_insn "xorsi3"
6035
  [(set (match_operand:SI 0 "register_operand" "=r")
6036
        (xor:SI (match_operand:SI 1 "register_operand" "%r")
6037
                (match_operand:SI 2 "register_operand" "r")))]
6038
  ""
6039
  "xor %1,%2,%0"
6040
  [(set_attr "type" "binary")
6041
   (set_attr "length" "4")])
6042
 
6043
(define_expand "negdi2"
6044
  [(set (match_operand:DI 0 "register_operand" "")
6045
        (neg:DI (match_operand:DI 1 "register_operand" "")))]
6046
  ""
6047
  "")
6048
 
6049
(define_insn ""
6050
  [(set (match_operand:DI 0 "register_operand" "=r")
6051
        (neg:DI (match_operand:DI 1 "register_operand" "r")))]
6052
  "!TARGET_64BIT"
6053
  "sub %%r0,%R1,%R0\;{subb|sub,b} %%r0,%1,%0"
6054
  [(set_attr "type" "unary")
6055
   (set_attr "length" "8")])
6056
 
6057
(define_insn ""
6058
  [(set (match_operand:DI 0 "register_operand" "=r")
6059
        (neg:DI (match_operand:DI 1 "register_operand" "r")))]
6060
  "TARGET_64BIT"
6061
  "sub %%r0,%1,%0"
6062
  [(set_attr "type" "unary")
6063
   (set_attr "length" "4")])
6064
 
6065
(define_insn "negsi2"
6066
  [(set (match_operand:SI 0 "register_operand" "=r")
6067
        (neg:SI (match_operand:SI 1 "register_operand" "r")))]
6068
  ""
6069
  "sub %%r0,%1,%0"
6070
  [(set_attr "type" "unary")
6071
   (set_attr "length" "4")])
6072
 
6073
(define_expand "one_cmpldi2"
6074
  [(set (match_operand:DI 0 "register_operand" "")
6075
        (not:DI (match_operand:DI 1 "register_operand" "")))]
6076
  ""
6077
  "
6078
{
6079
}")
6080
 
6081
(define_insn ""
6082
  [(set (match_operand:DI 0 "register_operand" "=r")
6083
        (not:DI (match_operand:DI 1 "register_operand" "r")))]
6084
  "!TARGET_64BIT"
6085
  "uaddcm %%r0,%1,%0\;uaddcm %%r0,%R1,%R0"
6086
  [(set_attr "type" "unary")
6087
   (set_attr "length" "8")])
6088
 
6089
(define_insn ""
6090
  [(set (match_operand:DI 0 "register_operand" "=r")
6091
        (not:DI (match_operand:DI 1 "register_operand" "r")))]
6092
  "TARGET_64BIT"
6093
  "uaddcm %%r0,%1,%0"
6094
  [(set_attr "type" "unary")
6095
   (set_attr "length" "4")])
6096
 
6097
(define_insn "one_cmplsi2"
6098
  [(set (match_operand:SI 0 "register_operand" "=r")
6099
        (not:SI (match_operand:SI 1 "register_operand" "r")))]
6100
  ""
6101
  "uaddcm %%r0,%1,%0"
6102
  [(set_attr "type" "unary")
6103
   (set_attr "length" "4")])
6104
 
6105
;; Floating point arithmetic instructions.
6106
 
6107
(define_insn "adddf3"
6108
  [(set (match_operand:DF 0 "register_operand" "=f")
6109
        (plus:DF (match_operand:DF 1 "register_operand" "f")
6110
                 (match_operand:DF 2 "register_operand" "f")))]
6111
  "! TARGET_SOFT_FLOAT"
6112
  "fadd,dbl %1,%2,%0"
6113
  [(set_attr "type" "fpalu")
6114
   (set_attr "pa_combine_type" "faddsub")
6115
   (set_attr "length" "4")])
6116
 
6117
(define_insn "addsf3"
6118
  [(set (match_operand:SF 0 "register_operand" "=f")
6119
        (plus:SF (match_operand:SF 1 "register_operand" "f")
6120
                 (match_operand:SF 2 "register_operand" "f")))]
6121
  "! TARGET_SOFT_FLOAT"
6122
  "fadd,sgl %1,%2,%0"
6123
  [(set_attr "type" "fpalu")
6124
   (set_attr "pa_combine_type" "faddsub")
6125
   (set_attr "length" "4")])
6126
 
6127
(define_insn "subdf3"
6128
  [(set (match_operand:DF 0 "register_operand" "=f")
6129
        (minus:DF (match_operand:DF 1 "register_operand" "f")
6130
                  (match_operand:DF 2 "register_operand" "f")))]
6131
  "! TARGET_SOFT_FLOAT"
6132
  "fsub,dbl %1,%2,%0"
6133
  [(set_attr "type" "fpalu")
6134
   (set_attr "pa_combine_type" "faddsub")
6135
   (set_attr "length" "4")])
6136
 
6137
(define_insn "subsf3"
6138
  [(set (match_operand:SF 0 "register_operand" "=f")
6139
        (minus:SF (match_operand:SF 1 "register_operand" "f")
6140
                  (match_operand:SF 2 "register_operand" "f")))]
6141
  "! TARGET_SOFT_FLOAT"
6142
  "fsub,sgl %1,%2,%0"
6143
  [(set_attr "type" "fpalu")
6144
   (set_attr "pa_combine_type" "faddsub")
6145
   (set_attr "length" "4")])
6146
 
6147
(define_insn "muldf3"
6148
  [(set (match_operand:DF 0 "register_operand" "=f")
6149
        (mult:DF (match_operand:DF 1 "register_operand" "f")
6150
                 (match_operand:DF 2 "register_operand" "f")))]
6151
  "! TARGET_SOFT_FLOAT"
6152
  "fmpy,dbl %1,%2,%0"
6153
  [(set_attr "type" "fpmuldbl")
6154
   (set_attr "pa_combine_type" "fmpy")
6155
   (set_attr "length" "4")])
6156
 
6157
(define_insn "mulsf3"
6158
  [(set (match_operand:SF 0 "register_operand" "=f")
6159
        (mult:SF (match_operand:SF 1 "register_operand" "f")
6160
                 (match_operand:SF 2 "register_operand" "f")))]
6161
  "! TARGET_SOFT_FLOAT"
6162
  "fmpy,sgl %1,%2,%0"
6163
  [(set_attr "type" "fpmulsgl")
6164
   (set_attr "pa_combine_type" "fmpy")
6165
   (set_attr "length" "4")])
6166
 
6167
(define_insn "divdf3"
6168
  [(set (match_operand:DF 0 "register_operand" "=f")
6169
        (div:DF (match_operand:DF 1 "register_operand" "f")
6170
                (match_operand:DF 2 "register_operand" "f")))]
6171
  "! TARGET_SOFT_FLOAT"
6172
  "fdiv,dbl %1,%2,%0"
6173
  [(set_attr "type" "fpdivdbl")
6174
   (set_attr "length" "4")])
6175
 
6176
(define_insn "divsf3"
6177
  [(set (match_operand:SF 0 "register_operand" "=f")
6178
        (div:SF (match_operand:SF 1 "register_operand" "f")
6179
                (match_operand:SF 2 "register_operand" "f")))]
6180
  "! TARGET_SOFT_FLOAT"
6181
  "fdiv,sgl %1,%2,%0"
6182
  [(set_attr "type" "fpdivsgl")
6183
   (set_attr "length" "4")])
6184
 
6185
;; Processors prior to PA 2.0 don't have a fneg instruction.  Fast
6186
;; negation can be done by subtracting from plus zero.  However, this
6187
;; violates the IEEE standard when negating plus and minus zero.
6188
(define_expand "negdf2"
6189
  [(parallel [(set (match_operand:DF 0 "register_operand" "")
6190
                   (neg:DF (match_operand:DF 1 "register_operand" "")))
6191
              (use (match_dup 2))])]
6192
  "! TARGET_SOFT_FLOAT"
6193
{
6194
  if (TARGET_PA_20 || flag_unsafe_math_optimizations)
6195
    emit_insn (gen_negdf2_fast (operands[0], operands[1]));
6196
  else
6197
    {
6198
      operands[2] = force_reg (DFmode,
6199
        CONST_DOUBLE_FROM_REAL_VALUE (dconstm1, DFmode));
6200
      emit_insn (gen_muldf3 (operands[0], operands[1], operands[2]));
6201
    }
6202
  DONE;
6203
})
6204
 
6205
(define_insn "negdf2_fast"
6206
  [(set (match_operand:DF 0 "register_operand" "=f")
6207
        (neg:DF (match_operand:DF 1 "register_operand" "f")))]
6208
  "! TARGET_SOFT_FLOAT && (TARGET_PA_20 || flag_unsafe_math_optimizations)"
6209
  "*
6210
{
6211
  if (TARGET_PA_20)
6212
    return \"fneg,dbl %1,%0\";
6213
  else
6214
    return \"fsub,dbl %%fr0,%1,%0\";
6215
}"
6216
  [(set_attr "type" "fpalu")
6217
   (set_attr "length" "4")])
6218
 
6219
(define_expand "negsf2"
6220
  [(parallel [(set (match_operand:SF 0 "register_operand" "")
6221
                   (neg:SF (match_operand:SF 1 "register_operand" "")))
6222
              (use (match_dup 2))])]
6223
  "! TARGET_SOFT_FLOAT"
6224
{
6225
  if (TARGET_PA_20 || flag_unsafe_math_optimizations)
6226
    emit_insn (gen_negsf2_fast (operands[0], operands[1]));
6227
  else
6228
    {
6229
      operands[2] = force_reg (SFmode,
6230
        CONST_DOUBLE_FROM_REAL_VALUE (dconstm1, SFmode));
6231
      emit_insn (gen_mulsf3 (operands[0], operands[1], operands[2]));
6232
    }
6233
  DONE;
6234
})
6235
 
6236
(define_insn "negsf2_fast"
6237
  [(set (match_operand:SF 0 "register_operand" "=f")
6238
        (neg:SF (match_operand:SF 1 "register_operand" "f")))]
6239
  "! TARGET_SOFT_FLOAT && (TARGET_PA_20 || flag_unsafe_math_optimizations)"
6240
  "*
6241
{
6242
  if (TARGET_PA_20)
6243
    return \"fneg,sgl %1,%0\";
6244
  else
6245
    return \"fsub,sgl %%fr0,%1,%0\";
6246
}"
6247
  [(set_attr "type" "fpalu")
6248
   (set_attr "length" "4")])
6249
 
6250
(define_insn "absdf2"
6251
  [(set (match_operand:DF 0 "register_operand" "=f")
6252
        (abs:DF (match_operand:DF 1 "register_operand" "f")))]
6253
  "! TARGET_SOFT_FLOAT"
6254
  "fabs,dbl %1,%0"
6255
  [(set_attr "type" "fpalu")
6256
   (set_attr "length" "4")])
6257
 
6258
(define_insn "abssf2"
6259
  [(set (match_operand:SF 0 "register_operand" "=f")
6260
        (abs:SF (match_operand:SF 1 "register_operand" "f")))]
6261
  "! TARGET_SOFT_FLOAT"
6262
  "fabs,sgl %1,%0"
6263
  [(set_attr "type" "fpalu")
6264
   (set_attr "length" "4")])
6265
 
6266
(define_insn "sqrtdf2"
6267
  [(set (match_operand:DF 0 "register_operand" "=f")
6268
        (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
6269
  "! TARGET_SOFT_FLOAT"
6270
  "fsqrt,dbl %1,%0"
6271
  [(set_attr "type" "fpsqrtdbl")
6272
   (set_attr "length" "4")])
6273
 
6274
(define_insn "sqrtsf2"
6275
  [(set (match_operand:SF 0 "register_operand" "=f")
6276
        (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
6277
  "! TARGET_SOFT_FLOAT"
6278
  "fsqrt,sgl %1,%0"
6279
  [(set_attr "type" "fpsqrtsgl")
6280
   (set_attr "length" "4")])
6281
 
6282
;; PA 2.0 floating point instructions
6283
 
6284
; fmpyfadd patterns
6285
(define_insn ""
6286
  [(set (match_operand:DF 0 "register_operand" "=f")
6287
        (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6288
                          (match_operand:DF 2 "register_operand" "f"))
6289
                 (match_operand:DF 3 "register_operand" "f")))]
6290
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6291
  "fmpyfadd,dbl %1,%2,%3,%0"
6292
  [(set_attr "type" "fpmuldbl")
6293
   (set_attr "length" "4")])
6294
 
6295
(define_insn ""
6296
  [(set (match_operand:DF 0 "register_operand" "=f")
6297
        (plus:DF (match_operand:DF 1 "register_operand" "f")
6298
                 (mult:DF (match_operand:DF 2 "register_operand" "f")
6299
                          (match_operand:DF 3 "register_operand" "f"))))]
6300
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6301
  "fmpyfadd,dbl %2,%3,%1,%0"
6302
  [(set_attr "type" "fpmuldbl")
6303
   (set_attr "length" "4")])
6304
 
6305
(define_insn ""
6306
  [(set (match_operand:SF 0 "register_operand" "=f")
6307
        (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6308
                          (match_operand:SF 2 "register_operand" "f"))
6309
                 (match_operand:SF 3 "register_operand" "f")))]
6310
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6311
  "fmpyfadd,sgl %1,%2,%3,%0"
6312
  [(set_attr "type" "fpmulsgl")
6313
   (set_attr "length" "4")])
6314
 
6315
(define_insn ""
6316
  [(set (match_operand:SF 0 "register_operand" "=f")
6317
        (plus:SF (match_operand:SF 1 "register_operand" "f")
6318
                 (mult:SF (match_operand:SF 2 "register_operand" "f")
6319
                          (match_operand:SF 3 "register_operand" "f"))))]
6320
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6321
  "fmpyfadd,sgl %2,%3,%1,%0"
6322
  [(set_attr "type" "fpmulsgl")
6323
   (set_attr "length" "4")])
6324
 
6325
; fmpynfadd patterns
6326
(define_insn ""
6327
  [(set (match_operand:DF 0 "register_operand" "=f")
6328
        (minus:DF (match_operand:DF 1 "register_operand" "f")
6329
                  (mult:DF (match_operand:DF 2 "register_operand" "f")
6330
                           (match_operand:DF 3 "register_operand" "f"))))]
6331
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6332
  "fmpynfadd,dbl %2,%3,%1,%0"
6333
  [(set_attr "type" "fpmuldbl")
6334
   (set_attr "length" "4")])
6335
 
6336
(define_insn ""
6337
  [(set (match_operand:SF 0 "register_operand" "=f")
6338
        (minus:SF (match_operand:SF 1 "register_operand" "f")
6339
                  (mult:SF (match_operand:SF 2 "register_operand" "f")
6340
                           (match_operand:SF 3 "register_operand" "f"))))]
6341
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6342
  "fmpynfadd,sgl %2,%3,%1,%0"
6343
  [(set_attr "type" "fpmulsgl")
6344
   (set_attr "length" "4")])
6345
 
6346
; fnegabs patterns
6347
(define_insn ""
6348
  [(set (match_operand:DF 0 "register_operand" "=f")
6349
        (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))]
6350
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6351
  "fnegabs,dbl %1,%0"
6352
  [(set_attr "type" "fpalu")
6353
   (set_attr "length" "4")])
6354
 
6355
(define_insn ""
6356
  [(set (match_operand:SF 0 "register_operand" "=f")
6357
        (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))]
6358
  "TARGET_PA_20 && ! TARGET_SOFT_FLOAT"
6359
  "fnegabs,sgl %1,%0"
6360
  [(set_attr "type" "fpalu")
6361
   (set_attr "length" "4")])
6362
 
6363
;; Generating a fused multiply sequence is a win for this case as it will
6364
;; reduce the latency for the fused case without impacting the plain
6365
;; multiply case.
6366
;;
6367
;; Similar possibilities exist for fnegabs, shadd and other insns which
6368
;; perform two operations with the result of the first feeding the second.
6369
(define_insn ""
6370
  [(set (match_operand:DF 0 "register_operand" "=f")
6371
        (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6372
                          (match_operand:DF 2 "register_operand" "f"))
6373
                 (match_operand:DF 3 "register_operand" "f")))
6374
   (set (match_operand:DF 4 "register_operand" "=&f")
6375
        (mult:DF (match_dup 1) (match_dup 2)))]
6376
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6377
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6378
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6379
  "#"
6380
  [(set_attr "type" "fpmuldbl")
6381
   (set_attr "length" "8")])
6382
 
6383
;; We want to split this up during scheduling since we want both insns
6384
;; to schedule independently.
6385
(define_split
6386
  [(set (match_operand:DF 0 "register_operand" "")
6387
        (plus:DF (mult:DF (match_operand:DF 1 "register_operand" "")
6388
                          (match_operand:DF 2 "register_operand" ""))
6389
                 (match_operand:DF 3 "register_operand" "")))
6390
   (set (match_operand:DF 4 "register_operand" "")
6391
        (mult:DF (match_dup 1) (match_dup 2)))]
6392
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6393
  [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
6394
   (set (match_dup 0) (plus:DF (mult:DF (match_dup 1) (match_dup 2))
6395
                               (match_dup 3)))]
6396
  "")
6397
 
6398
(define_insn ""
6399
  [(set (match_operand:SF 0 "register_operand" "=f")
6400
        (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6401
                          (match_operand:SF 2 "register_operand" "f"))
6402
                 (match_operand:SF 3 "register_operand" "f")))
6403
   (set (match_operand:SF 4 "register_operand" "=&f")
6404
        (mult:SF (match_dup 1) (match_dup 2)))]
6405
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6406
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6407
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6408
  "#"
6409
  [(set_attr "type" "fpmuldbl")
6410
   (set_attr "length" "8")])
6411
 
6412
;; We want to split this up during scheduling since we want both insns
6413
;; to schedule independently.
6414
(define_split
6415
  [(set (match_operand:SF 0 "register_operand" "")
6416
        (plus:SF (mult:SF (match_operand:SF 1 "register_operand" "")
6417
                          (match_operand:SF 2 "register_operand" ""))
6418
                 (match_operand:SF 3 "register_operand" "")))
6419
   (set (match_operand:SF 4 "register_operand" "")
6420
        (mult:SF (match_dup 1) (match_dup 2)))]
6421
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6422
  [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
6423
   (set (match_dup 0) (plus:SF (mult:SF (match_dup 1) (match_dup 2))
6424
                               (match_dup 3)))]
6425
  "")
6426
 
6427
;; Negating a multiply can be faked by adding zero in a fused multiply-add
6428
;; instruction.
6429
(define_insn ""
6430
  [(set (match_operand:DF 0 "register_operand" "=f")
6431
        (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6432
                         (match_operand:DF 2 "register_operand" "f"))))]
6433
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6434
  "fmpynfadd,dbl %1,%2,%%fr0,%0"
6435
  [(set_attr "type" "fpmuldbl")
6436
   (set_attr "length" "4")])
6437
 
6438
(define_insn ""
6439
  [(set (match_operand:SF 0 "register_operand" "=f")
6440
        (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6441
                         (match_operand:SF 2 "register_operand" "f"))))]
6442
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6443
  "fmpynfadd,sgl %1,%2,%%fr0,%0"
6444
  [(set_attr "type" "fpmuldbl")
6445
   (set_attr "length" "4")])
6446
 
6447
(define_insn ""
6448
  [(set (match_operand:DF 0 "register_operand" "=f")
6449
        (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6450
                         (match_operand:DF 2 "register_operand" "f"))))
6451
   (set (match_operand:DF 3 "register_operand" "=&f")
6452
        (mult:DF (match_dup 1) (match_dup 2)))]
6453
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6454
    && ! (reg_overlap_mentioned_p (operands[3], operands[1])
6455
          || reg_overlap_mentioned_p (operands[3], operands[2])))"
6456
  "#"
6457
  [(set_attr "type" "fpmuldbl")
6458
   (set_attr "length" "8")])
6459
 
6460
(define_split
6461
  [(set (match_operand:DF 0 "register_operand" "")
6462
        (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "")
6463
                         (match_operand:DF 2 "register_operand" ""))))
6464
   (set (match_operand:DF 3 "register_operand" "")
6465
        (mult:DF (match_dup 1) (match_dup 2)))]
6466
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6467
  [(set (match_dup 3) (mult:DF (match_dup 1) (match_dup 2)))
6468
   (set (match_dup 0) (neg:DF (mult:DF (match_dup 1) (match_dup 2))))]
6469
  "")
6470
 
6471
(define_insn ""
6472
  [(set (match_operand:SF 0 "register_operand" "=f")
6473
        (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6474
                         (match_operand:SF 2 "register_operand" "f"))))
6475
   (set (match_operand:SF 3 "register_operand" "=&f")
6476
        (mult:SF (match_dup 1) (match_dup 2)))]
6477
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6478
    && ! (reg_overlap_mentioned_p (operands[3], operands[1])
6479
          || reg_overlap_mentioned_p (operands[3], operands[2])))"
6480
  "#"
6481
  [(set_attr "type" "fpmuldbl")
6482
   (set_attr "length" "8")])
6483
 
6484
(define_split
6485
  [(set (match_operand:SF 0 "register_operand" "")
6486
        (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "")
6487
                         (match_operand:SF 2 "register_operand" ""))))
6488
   (set (match_operand:SF 3 "register_operand" "")
6489
        (mult:SF (match_dup 1) (match_dup 2)))]
6490
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6491
  [(set (match_dup 3) (mult:SF (match_dup 1) (match_dup 2)))
6492
   (set (match_dup 0) (neg:SF (mult:SF (match_dup 1) (match_dup 2))))]
6493
  "")
6494
 
6495
;; Now fused multiplies with the result of the multiply negated.
6496
(define_insn ""
6497
  [(set (match_operand:DF 0 "register_operand" "=f")
6498
        (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6499
                                  (match_operand:DF 2 "register_operand" "f")))
6500
                 (match_operand:DF 3 "register_operand" "f")))]
6501
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6502
  "fmpynfadd,dbl %1,%2,%3,%0"
6503
  [(set_attr "type" "fpmuldbl")
6504
   (set_attr "length" "4")])
6505
 
6506
(define_insn ""
6507
  [(set (match_operand:SF 0 "register_operand" "=f")
6508
        (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6509
                         (match_operand:SF 2 "register_operand" "f")))
6510
                 (match_operand:SF 3 "register_operand" "f")))]
6511
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6512
  "fmpynfadd,sgl %1,%2,%3,%0"
6513
  [(set_attr "type" "fpmuldbl")
6514
   (set_attr "length" "4")])
6515
 
6516
(define_insn ""
6517
  [(set (match_operand:DF 0 "register_operand" "=f")
6518
        (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "f")
6519
                                  (match_operand:DF 2 "register_operand" "f")))
6520
                 (match_operand:DF 3 "register_operand" "f")))
6521
   (set (match_operand:DF 4 "register_operand" "=&f")
6522
        (mult:DF (match_dup 1) (match_dup 2)))]
6523
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6524
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6525
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6526
  "#"
6527
  [(set_attr "type" "fpmuldbl")
6528
   (set_attr "length" "8")])
6529
 
6530
(define_split
6531
  [(set (match_operand:DF 0 "register_operand" "")
6532
        (plus:DF (neg:DF (mult:DF (match_operand:DF 1 "register_operand" "")
6533
                                  (match_operand:DF 2 "register_operand" "")))
6534
                 (match_operand:DF 3 "register_operand" "")))
6535
   (set (match_operand:DF 4 "register_operand" "")
6536
        (mult:DF (match_dup 1) (match_dup 2)))]
6537
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6538
  [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
6539
   (set (match_dup 0) (plus:DF (neg:DF (mult:DF (match_dup 1) (match_dup 2)))
6540
                               (match_dup 3)))]
6541
  "")
6542
 
6543
(define_insn ""
6544
  [(set (match_operand:SF 0 "register_operand" "=f")
6545
        (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "f")
6546
                                  (match_operand:SF 2 "register_operand" "f")))
6547
                 (match_operand:SF 3 "register_operand" "f")))
6548
   (set (match_operand:SF 4 "register_operand" "=&f")
6549
        (mult:SF (match_dup 1) (match_dup 2)))]
6550
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6551
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6552
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6553
  "#"
6554
  [(set_attr "type" "fpmuldbl")
6555
   (set_attr "length" "8")])
6556
 
6557
(define_split
6558
  [(set (match_operand:SF 0 "register_operand" "")
6559
        (plus:SF (neg:SF (mult:SF (match_operand:SF 1 "register_operand" "")
6560
                                  (match_operand:SF 2 "register_operand" "")))
6561
                 (match_operand:SF 3 "register_operand" "")))
6562
   (set (match_operand:SF 4 "register_operand" "")
6563
        (mult:SF (match_dup 1) (match_dup 2)))]
6564
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6565
  [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
6566
   (set (match_dup 0) (plus:SF (neg:SF (mult:SF (match_dup 1) (match_dup 2)))
6567
                               (match_dup 3)))]
6568
  "")
6569
 
6570
(define_insn ""
6571
  [(set (match_operand:DF 0 "register_operand" "=f")
6572
        (minus:DF (match_operand:DF 3 "register_operand" "f")
6573
                  (mult:DF (match_operand:DF 1 "register_operand" "f")
6574
                           (match_operand:DF 2 "register_operand" "f"))))
6575
   (set (match_operand:DF 4 "register_operand" "=&f")
6576
        (mult:DF (match_dup 1) (match_dup 2)))]
6577
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6578
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6579
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6580
  "#"
6581
  [(set_attr "type" "fpmuldbl")
6582
   (set_attr "length" "8")])
6583
 
6584
(define_split
6585
  [(set (match_operand:DF 0 "register_operand" "")
6586
        (minus:DF (match_operand:DF 3 "register_operand" "")
6587
                  (mult:DF (match_operand:DF 1 "register_operand" "")
6588
                           (match_operand:DF 2 "register_operand" ""))))
6589
   (set (match_operand:DF 4 "register_operand" "")
6590
        (mult:DF (match_dup 1) (match_dup 2)))]
6591
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6592
  [(set (match_dup 4) (mult:DF (match_dup 1) (match_dup 2)))
6593
   (set (match_dup 0) (minus:DF (match_dup 3)
6594
                                (mult:DF (match_dup 1) (match_dup 2))))]
6595
  "")
6596
 
6597
(define_insn ""
6598
  [(set (match_operand:SF 0 "register_operand" "=f")
6599
        (minus:SF (match_operand:SF 3 "register_operand" "f")
6600
                  (mult:SF (match_operand:SF 1 "register_operand" "f")
6601
                           (match_operand:SF 2 "register_operand" "f"))))
6602
   (set (match_operand:SF 4 "register_operand" "=&f")
6603
        (mult:SF (match_dup 1) (match_dup 2)))]
6604
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6605
    && ! (reg_overlap_mentioned_p (operands[4], operands[1])
6606
          || reg_overlap_mentioned_p (operands[4], operands[2])))"
6607
  "#"
6608
  [(set_attr "type" "fpmuldbl")
6609
   (set_attr "length" "8")])
6610
 
6611
(define_split
6612
  [(set (match_operand:SF 0 "register_operand" "")
6613
        (minus:SF (match_operand:SF 3 "register_operand" "")
6614
                  (mult:SF (match_operand:SF 1 "register_operand" "")
6615
                           (match_operand:SF 2 "register_operand" ""))))
6616
   (set (match_operand:SF 4 "register_operand" "")
6617
        (mult:SF (match_dup 1) (match_dup 2)))]
6618
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6619
  [(set (match_dup 4) (mult:SF (match_dup 1) (match_dup 2)))
6620
   (set (match_dup 0) (minus:SF (match_dup 3)
6621
                                (mult:SF (match_dup 1) (match_dup 2))))]
6622
  "")
6623
 
6624
(define_insn ""
6625
  [(set (match_operand:DF 0 "register_operand" "=f")
6626
        (neg:DF (abs:DF (match_operand:DF 1 "register_operand" "f"))))
6627
   (set (match_operand:DF 2 "register_operand" "=&f") (abs:DF (match_dup 1)))]
6628
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6629
    && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
6630
  "#"
6631
  [(set_attr "type" "fpalu")
6632
   (set_attr "length" "8")])
6633
 
6634
(define_split
6635
  [(set (match_operand:DF 0 "register_operand" "")
6636
        (neg:DF (abs:DF (match_operand:DF 1 "register_operand" ""))))
6637
   (set (match_operand:DF 2 "register_operand" "") (abs:DF (match_dup 1)))]
6638
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6639
  [(set (match_dup 2) (abs:DF (match_dup 1)))
6640
   (set (match_dup 0) (neg:DF (abs:DF (match_dup 1))))]
6641
  "")
6642
 
6643
(define_insn ""
6644
  [(set (match_operand:SF 0 "register_operand" "=f")
6645
        (neg:SF (abs:SF (match_operand:SF 1 "register_operand" "f"))))
6646
   (set (match_operand:SF 2 "register_operand" "=&f") (abs:SF (match_dup 1)))]
6647
  "(! TARGET_SOFT_FLOAT && TARGET_PA_20
6648
    && ! reg_overlap_mentioned_p (operands[2], operands[1]))"
6649
  "#"
6650
  [(set_attr "type" "fpalu")
6651
   (set_attr "length" "8")])
6652
 
6653
(define_split
6654
  [(set (match_operand:SF 0 "register_operand" "")
6655
        (neg:SF (abs:SF (match_operand:SF 1 "register_operand" ""))))
6656
   (set (match_operand:SF 2 "register_operand" "") (abs:SF (match_dup 1)))]
6657
  "! TARGET_SOFT_FLOAT && TARGET_PA_20"
6658
  [(set (match_dup 2) (abs:SF (match_dup 1)))
6659
   (set (match_dup 0) (neg:SF (abs:SF (match_dup 1))))]
6660
  "")
6661
 
6662
;;- Shift instructions
6663
 
6664
;; Optimized special case of shifting.
6665
 
6666
(define_insn ""
6667
  [(set (match_operand:SI 0 "register_operand" "=r")
6668
        (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
6669
                     (const_int 24)))]
6670
  ""
6671
  "ldb%M1 %1,%0"
6672
  [(set_attr "type" "load")
6673
   (set_attr "length" "4")])
6674
 
6675
(define_insn ""
6676
  [(set (match_operand:SI 0 "register_operand" "=r")
6677
        (lshiftrt:SI (match_operand:SI 1 "memory_operand" "m")
6678
                     (const_int 16)))]
6679
  ""
6680
  "ldh%M1 %1,%0"
6681
  [(set_attr "type" "load")
6682
   (set_attr "length" "4")])
6683
 
6684
(define_insn ""
6685
  [(set (match_operand:SI 0 "register_operand" "=r")
6686
        (plus:SI (mult:SI (match_operand:SI 2 "register_operand" "r")
6687
                          (match_operand:SI 3 "shadd_operand" ""))
6688
                 (match_operand:SI 1 "register_operand" "r")))]
6689
  ""
6690
  "{sh%O3addl %2,%1,%0|shladd,l %2,%O3,%1,%0} "
6691
  [(set_attr "type" "binary")
6692
   (set_attr "length" "4")])
6693
 
6694
(define_insn ""
6695
  [(set (match_operand:DI 0 "register_operand" "=r")
6696
        (plus:DI (mult:DI (match_operand:DI 2 "register_operand" "r")
6697
                          (match_operand:DI 3 "shadd_operand" ""))
6698
                 (match_operand:DI 1 "register_operand" "r")))]
6699
  "TARGET_64BIT"
6700
  "shladd,l %2,%O3,%1,%0"
6701
  [(set_attr "type" "binary")
6702
   (set_attr "length" "4")])
6703
 
6704
(define_expand "ashlsi3"
6705
  [(set (match_operand:SI 0 "register_operand" "")
6706
        (ashift:SI (match_operand:SI 1 "lhs_lshift_operand" "")
6707
                   (match_operand:SI 2 "arith32_operand" "")))]
6708
  ""
6709
  "
6710
{
6711
  if (GET_CODE (operands[2]) != CONST_INT)
6712
    {
6713
      rtx temp = gen_reg_rtx (SImode);
6714
      emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
6715
      if (GET_CODE (operands[1]) == CONST_INT)
6716
        emit_insn (gen_zvdep_imm32 (operands[0], operands[1], temp));
6717
      else
6718
        emit_insn (gen_zvdep32 (operands[0], operands[1], temp));
6719
      DONE;
6720
    }
6721
  /* Make sure both inputs are not constants,
6722
     there are no patterns for that.  */
6723
  operands[1] = force_reg (SImode, operands[1]);
6724
}")
6725
 
6726
(define_insn ""
6727
  [(set (match_operand:SI 0 "register_operand" "=r")
6728
        (ashift:SI (match_operand:SI 1 "register_operand" "r")
6729
                   (match_operand:SI 2 "const_int_operand" "n")))]
6730
  ""
6731
  "{zdep|depw,z} %1,%P2,%L2,%0"
6732
  [(set_attr "type" "shift")
6733
   (set_attr "length" "4")])
6734
 
6735
; Match cases of op1 a CONST_INT here that zvdep_imm32 doesn't handle.
6736
; Doing it like this makes slightly better code since reload can
6737
; replace a register with a known value in range -16..15 with a
6738
; constant.  Ideally, we would like to merge zvdep32 and zvdep_imm32,
6739
; but since we have no more CONST_OK... characters, that is not
6740
; possible.
6741
(define_insn "zvdep32"
6742
  [(set (match_operand:SI 0 "register_operand" "=r,r")
6743
        (ashift:SI (match_operand:SI 1 "arith5_operand" "r,L")
6744
                   (minus:SI (const_int 31)
6745
                             (match_operand:SI 2 "register_operand" "q,q"))))]
6746
  ""
6747
  "@
6748
   {zvdep %1,32,%0|depw,z %1,%%sar,32,%0}
6749
   {zvdepi %1,32,%0|depwi,z %1,%%sar,32,%0}"
6750
  [(set_attr "type" "shift,shift")
6751
   (set_attr "length" "4,4")])
6752
 
6753
(define_insn "zvdep_imm32"
6754
  [(set (match_operand:SI 0 "register_operand" "=r")
6755
        (ashift:SI (match_operand:SI 1 "lhs_lshift_cint_operand" "")
6756
                   (minus:SI (const_int 31)
6757
                             (match_operand:SI 2 "register_operand" "q"))))]
6758
  ""
6759
  "*
6760
{
6761
  int x = INTVAL (operands[1]);
6762
  operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
6763
  operands[1] = GEN_INT ((x & 0xf) - 0x10);
6764
  return \"{zvdepi %1,%2,%0|depwi,z %1,%%sar,%2,%0}\";
6765
}"
6766
  [(set_attr "type" "shift")
6767
   (set_attr "length" "4")])
6768
 
6769
(define_insn "vdepi_ior"
6770
  [(set (match_operand:SI 0 "register_operand" "=r")
6771
        (ior:SI (ashift:SI (match_operand:SI 1 "const_int_operand" "")
6772
                           (minus:SI (const_int 31)
6773
                                     (match_operand:SI 2 "register_operand" "q")))
6774
                (match_operand:SI 3 "register_operand" "0")))]
6775
  ; accept ...0001...1, can this be generalized?
6776
  "exact_log2 (INTVAL (operands[1]) + 1) > 0"
6777
  "*
6778
{
6779
  int x = INTVAL (operands[1]);
6780
  operands[2] = GEN_INT (exact_log2 (x + 1));
6781
  return \"{vdepi -1,%2,%0|depwi -1,%%sar,%2,%0}\";
6782
}"
6783
  [(set_attr "type" "shift")
6784
   (set_attr "length" "4")])
6785
 
6786
(define_insn "vdepi_and"
6787
  [(set (match_operand:SI 0 "register_operand" "=r")
6788
        (and:SI (rotate:SI (match_operand:SI 1 "const_int_operand" "")
6789
                           (minus:SI (const_int 31)
6790
                                     (match_operand:SI 2 "register_operand" "q")))
6791
                (match_operand:SI 3 "register_operand" "0")))]
6792
  ; this can be generalized...!
6793
  "INTVAL (operands[1]) == -2"
6794
  "*
6795
{
6796
  int x = INTVAL (operands[1]);
6797
  operands[2] = GEN_INT (exact_log2 ((~x) + 1));
6798
  return \"{vdepi 0,%2,%0|depwi 0,%%sar,%2,%0}\";
6799
}"
6800
  [(set_attr "type" "shift")
6801
   (set_attr "length" "4")])
6802
 
6803
(define_expand "ashldi3"
6804
  [(set (match_operand:DI 0 "register_operand" "")
6805
        (ashift:DI (match_operand:DI 1 "lhs_lshift_operand" "")
6806
                   (match_operand:DI 2 "arith32_operand" "")))]
6807
  "TARGET_64BIT"
6808
  "
6809
{
6810
  if (GET_CODE (operands[2]) != CONST_INT)
6811
    {
6812
      rtx temp = gen_reg_rtx (DImode);
6813
      emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
6814
      if (GET_CODE (operands[1]) == CONST_INT)
6815
        emit_insn (gen_zvdep_imm64 (operands[0], operands[1], temp));
6816
      else
6817
        emit_insn (gen_zvdep64 (operands[0], operands[1], temp));
6818
      DONE;
6819
    }
6820
  /* Make sure both inputs are not constants,
6821
     there are no patterns for that.  */
6822
  operands[1] = force_reg (DImode, operands[1]);
6823
}")
6824
 
6825
(define_insn ""
6826
  [(set (match_operand:DI 0 "register_operand" "=r")
6827
        (ashift:DI (match_operand:DI 1 "register_operand" "r")
6828
                   (match_operand:DI 2 "const_int_operand" "n")))]
6829
  "TARGET_64BIT"
6830
  "depd,z %1,%p2,%Q2,%0"
6831
  [(set_attr "type" "shift")
6832
   (set_attr "length" "4")])
6833
 
6834
; Match cases of op1 a CONST_INT here that zvdep_imm64 doesn't handle.
6835
; Doing it like this makes slightly better code since reload can
6836
; replace a register with a known value in range -16..15 with a
6837
; constant.  Ideally, we would like to merge zvdep64 and zvdep_imm64,
6838
; but since we have no more CONST_OK... characters, that is not
6839
; possible.
6840
(define_insn "zvdep64"
6841
  [(set (match_operand:DI 0 "register_operand" "=r,r")
6842
        (ashift:DI (match_operand:DI 1 "arith5_operand" "r,L")
6843
                   (minus:DI (const_int 63)
6844
                             (match_operand:DI 2 "register_operand" "q,q"))))]
6845
  "TARGET_64BIT"
6846
  "@
6847
   depd,z %1,%%sar,64,%0
6848
   depdi,z %1,%%sar,64,%0"
6849
  [(set_attr "type" "shift,shift")
6850
   (set_attr "length" "4,4")])
6851
 
6852
(define_insn "zvdep_imm64"
6853
  [(set (match_operand:DI 0 "register_operand" "=r")
6854
        (ashift:DI (match_operand:DI 1 "lhs_lshift_cint_operand" "")
6855
                   (minus:DI (const_int 63)
6856
                             (match_operand:DI 2 "register_operand" "q"))))]
6857
  "TARGET_64BIT"
6858
  "*
6859
{
6860
  int x = INTVAL (operands[1]);
6861
  operands[2] = GEN_INT (4 + exact_log2 ((x >> 4) + 1));
6862
  operands[1] = GEN_INT ((x & 0x1f) - 0x20);
6863
  return \"depdi,z %1,%%sar,%2,%0\";
6864
}"
6865
  [(set_attr "type" "shift")
6866
   (set_attr "length" "4")])
6867
 
6868
(define_insn ""
6869
  [(set (match_operand:DI 0 "register_operand" "=r")
6870
        (ior:DI (ashift:DI (match_operand:DI 1 "const_int_operand" "")
6871
                           (minus:DI (const_int 63)
6872
                                     (match_operand:DI 2 "register_operand" "q")))
6873
                (match_operand:DI 3 "register_operand" "0")))]
6874
  ; accept ...0001...1, can this be generalized?
6875
  "TARGET_64BIT && exact_log2 (INTVAL (operands[1]) + 1) > 0"
6876
  "*
6877
{
6878
  int x = INTVAL (operands[1]);
6879
  operands[2] = GEN_INT (exact_log2 (x + 1));
6880
  return \"depdi -1,%%sar,%2,%0\";
6881
}"
6882
  [(set_attr "type" "shift")
6883
   (set_attr "length" "4")])
6884
 
6885
(define_insn ""
6886
  [(set (match_operand:DI 0 "register_operand" "=r")
6887
        (and:DI (rotate:DI (match_operand:DI 1 "const_int_operand" "")
6888
                           (minus:DI (const_int 63)
6889
                                     (match_operand:DI 2 "register_operand" "q")))
6890
                (match_operand:DI 3 "register_operand" "0")))]
6891
  ; this can be generalized...!
6892
  "TARGET_64BIT && INTVAL (operands[1]) == -2"
6893
  "*
6894
{
6895
  int x = INTVAL (operands[1]);
6896
  operands[2] = GEN_INT (exact_log2 ((~x) + 1));
6897
  return \"depdi 0,%%sar,%2,%0\";
6898
}"
6899
  [(set_attr "type" "shift")
6900
   (set_attr "length" "4")])
6901
 
6902
(define_expand "ashrsi3"
6903
  [(set (match_operand:SI 0 "register_operand" "")
6904
        (ashiftrt:SI (match_operand:SI 1 "register_operand" "")
6905
                     (match_operand:SI 2 "arith32_operand" "")))]
6906
  ""
6907
  "
6908
{
6909
  if (GET_CODE (operands[2]) != CONST_INT)
6910
    {
6911
      rtx temp = gen_reg_rtx (SImode);
6912
      emit_insn (gen_subsi3 (temp, GEN_INT (31), operands[2]));
6913
      emit_insn (gen_vextrs32 (operands[0], operands[1], temp));
6914
      DONE;
6915
    }
6916
}")
6917
 
6918
(define_insn ""
6919
  [(set (match_operand:SI 0 "register_operand" "=r")
6920
        (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6921
                     (match_operand:SI 2 "const_int_operand" "n")))]
6922
  ""
6923
  "{extrs|extrw,s} %1,%P2,%L2,%0"
6924
  [(set_attr "type" "shift")
6925
   (set_attr "length" "4")])
6926
 
6927
(define_insn "vextrs32"
6928
  [(set (match_operand:SI 0 "register_operand" "=r")
6929
        (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6930
                     (minus:SI (const_int 31)
6931
                               (match_operand:SI 2 "register_operand" "q"))))]
6932
  ""
6933
  "{vextrs %1,32,%0|extrw,s %1,%%sar,32,%0}"
6934
  [(set_attr "type" "shift")
6935
   (set_attr "length" "4")])
6936
 
6937
(define_expand "ashrdi3"
6938
  [(set (match_operand:DI 0 "register_operand" "")
6939
        (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
6940
                     (match_operand:DI 2 "arith32_operand" "")))]
6941
  "TARGET_64BIT"
6942
  "
6943
{
6944
  if (GET_CODE (operands[2]) != CONST_INT)
6945
    {
6946
      rtx temp = gen_reg_rtx (DImode);
6947
      emit_insn (gen_subdi3 (temp, GEN_INT (63), operands[2]));
6948
      emit_insn (gen_vextrs64 (operands[0], operands[1], temp));
6949
      DONE;
6950
    }
6951
}")
6952
 
6953
(define_insn ""
6954
  [(set (match_operand:DI 0 "register_operand" "=r")
6955
        (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6956
                     (match_operand:DI 2 "const_int_operand" "n")))]
6957
  "TARGET_64BIT"
6958
  "extrd,s %1,%p2,%Q2,%0"
6959
  [(set_attr "type" "shift")
6960
   (set_attr "length" "4")])
6961
 
6962
(define_insn "vextrs64"
6963
  [(set (match_operand:DI 0 "register_operand" "=r")
6964
        (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6965
                     (minus:DI (const_int 63)
6966
                               (match_operand:DI 2 "register_operand" "q"))))]
6967
  "TARGET_64BIT"
6968
  "extrd,s %1,%%sar,64,%0"
6969
  [(set_attr "type" "shift")
6970
   (set_attr "length" "4")])
6971
 
6972
(define_insn "lshrsi3"
6973
  [(set (match_operand:SI 0 "register_operand" "=r,r")
6974
        (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
6975
                     (match_operand:SI 2 "arith32_operand" "q,n")))]
6976
  ""
6977
  "@
6978
   {vshd %%r0,%1,%0|shrpw %%r0,%1,%%sar,%0}
6979
   {extru|extrw,u} %1,%P2,%L2,%0"
6980
  [(set_attr "type" "shift")
6981
   (set_attr "length" "4")])
6982
 
6983
(define_insn "lshrdi3"
6984
  [(set (match_operand:DI 0 "register_operand" "=r,r")
6985
        (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
6986
                     (match_operand:DI 2 "arith32_operand" "q,n")))]
6987
  "TARGET_64BIT"
6988
  "@
6989
   shrpd %%r0,%1,%%sar,%0
6990
   extrd,u %1,%p2,%Q2,%0"
6991
  [(set_attr "type" "shift")
6992
   (set_attr "length" "4")])
6993
 
6994
(define_insn "rotrsi3"
6995
  [(set (match_operand:SI 0 "register_operand" "=r,r")
6996
        (rotatert:SI (match_operand:SI 1 "register_operand" "r,r")
6997
                     (match_operand:SI 2 "arith32_operand" "q,n")))]
6998
  ""
6999
  "*
7000
{
7001
  if (GET_CODE (operands[2]) == CONST_INT)
7002
    {
7003
      operands[2] = GEN_INT (INTVAL (operands[2]) & 31);
7004
      return \"{shd|shrpw} %1,%1,%2,%0\";
7005
    }
7006
  else
7007
    return \"{vshd %1,%1,%0|shrpw %1,%1,%%sar,%0}\";
7008
}"
7009
  [(set_attr "type" "shift")
7010
   (set_attr "length" "4")])
7011
 
7012
(define_expand "rotlsi3"
7013
  [(set (match_operand:SI 0 "register_operand" "")
7014
        (rotate:SI (match_operand:SI 1 "register_operand" "")
7015
                   (match_operand:SI 2 "arith32_operand" "")))]
7016
  ""
7017
  "
7018
{
7019
  if (GET_CODE (operands[2]) != CONST_INT)
7020
    {
7021
      rtx temp = gen_reg_rtx (SImode);
7022
      emit_insn (gen_subsi3 (temp, GEN_INT (32), operands[2]));
7023
      emit_insn (gen_rotrsi3 (operands[0], operands[1], temp));
7024
      DONE;
7025
    }
7026
  /* Else expand normally.  */
7027
}")
7028
 
7029
(define_insn ""
7030
  [(set (match_operand:SI 0 "register_operand" "=r")
7031
        (rotate:SI (match_operand:SI 1 "register_operand" "r")
7032
                   (match_operand:SI 2 "const_int_operand" "n")))]
7033
  ""
7034
  "*
7035
{
7036
  operands[2] = GEN_INT ((32 - INTVAL (operands[2])) & 31);
7037
  return \"{shd|shrpw} %1,%1,%2,%0\";
7038
}"
7039
  [(set_attr "type" "shift")
7040
   (set_attr "length" "4")])
7041
 
7042
(define_insn ""
7043
  [(set (match_operand:SI 0 "register_operand" "=r")
7044
        (match_operator:SI 5 "plus_xor_ior_operator"
7045
          [(ashift:SI (match_operand:SI 1 "register_operand" "r")
7046
                      (match_operand:SI 3 "const_int_operand" "n"))
7047
           (lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
7048
                        (match_operand:SI 4 "const_int_operand" "n"))]))]
7049
  "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
7050
  "{shd|shrpw} %1,%2,%4,%0"
7051
  [(set_attr "type" "shift")
7052
   (set_attr "length" "4")])
7053
 
7054
(define_insn ""
7055
  [(set (match_operand:SI 0 "register_operand" "=r")
7056
        (match_operator:SI 5 "plus_xor_ior_operator"
7057
          [(lshiftrt:SI (match_operand:SI 2 "register_operand" "r")
7058
                        (match_operand:SI 4 "const_int_operand" "n"))
7059
           (ashift:SI (match_operand:SI 1 "register_operand" "r")
7060
                      (match_operand:SI 3 "const_int_operand" "n"))]))]
7061
  "INTVAL (operands[3]) + INTVAL (operands[4]) == 32"
7062
  "{shd|shrpw} %1,%2,%4,%0"
7063
  [(set_attr "type" "shift")
7064
   (set_attr "length" "4")])
7065
 
7066
(define_insn ""
7067
  [(set (match_operand:SI 0 "register_operand" "=r")
7068
        (and:SI (ashift:SI (match_operand:SI 1 "register_operand" "r")
7069
                           (match_operand:SI 2 "const_int_operand" ""))
7070
                (match_operand:SI 3 "const_int_operand" "")))]
7071
  "exact_log2 (1 + (INTVAL (operands[3]) >> (INTVAL (operands[2]) & 31))) > 0"
7072
  "*
7073
{
7074
  int cnt = INTVAL (operands[2]) & 31;
7075
  operands[3] = GEN_INT (exact_log2 (1 + (INTVAL (operands[3]) >> cnt)));
7076
  operands[2] = GEN_INT (31 - cnt);
7077
  return \"{zdep|depw,z} %1,%2,%3,%0\";
7078
}"
7079
  [(set_attr "type" "shift")
7080
   (set_attr "length" "4")])
7081
 
7082
;; Unconditional and other jump instructions.
7083
 
7084
;; This can only be used in a leaf function, so we do
7085
;; not need to use the PIC register when generating PIC code.
7086
(define_insn "return"
7087
  [(return)
7088
   (use (reg:SI 2))
7089
   (const_int 0)]
7090
  "hppa_can_use_return_insn_p ()"
7091
  "*
7092
{
7093
  if (TARGET_PA_20)
7094
    return \"bve%* (%%r2)\";
7095
  return \"bv%* %%r0(%%r2)\";
7096
}"
7097
  [(set_attr "type" "branch")
7098
   (set_attr "length" "4")])
7099
 
7100
;; Emit a different pattern for functions which have non-trivial
7101
;; epilogues so as not to confuse jump and reorg.
7102
(define_insn "return_internal"
7103
  [(return)
7104
   (use (reg:SI 2))
7105
   (const_int 1)]
7106
  ""
7107
  "*
7108
{
7109
  if (TARGET_PA_20)
7110
    return \"bve%* (%%r2)\";
7111
  return \"bv%* %%r0(%%r2)\";
7112
}"
7113
  [(set_attr "type" "branch")
7114
   (set_attr "length" "4")])
7115
 
7116
;; This is used for eh returns which bypass the return stub.
7117
(define_insn "return_external_pic"
7118
  [(return)
7119
   (clobber (reg:SI 1))
7120
   (use (reg:SI 2))]
7121
  "!TARGET_NO_SPACE_REGS
7122
   && !TARGET_PA_20
7123
   && flag_pic && current_function_calls_eh_return"
7124
  "ldsid (%%sr0,%%r2),%%r1\;mtsp %%r1,%%sr0\;be%* 0(%%sr0,%%r2)"
7125
  [(set_attr "type" "branch")
7126
   (set_attr "length" "12")])
7127
 
7128
(define_expand "prologue"
7129
  [(const_int 0)]
7130
  ""
7131
  "hppa_expand_prologue ();DONE;")
7132
 
7133
(define_expand "sibcall_epilogue"
7134
  [(return)]
7135
  ""
7136
  "
7137
{
7138
  hppa_expand_epilogue ();
7139
  DONE;
7140
}")
7141
 
7142
(define_expand "epilogue"
7143
  [(return)]
7144
  ""
7145
  "
7146
{
7147
  /* Try to use the trivial return first.  Else use the full
7148
     epilogue.  */
7149
  if (hppa_can_use_return_insn_p ())
7150
    emit_jump_insn (gen_return ());
7151
  else
7152
    {
7153
      rtx x;
7154
 
7155
      hppa_expand_epilogue ();
7156
 
7157
      /* EH returns bypass the normal return stub.  Thus, we must do an
7158
         interspace branch to return from functions that call eh_return.
7159
         This is only a problem for returns from shared code on ports
7160
         using space registers.  */
7161
      if (!TARGET_NO_SPACE_REGS
7162
          && !TARGET_PA_20
7163
          && flag_pic && current_function_calls_eh_return)
7164
        x = gen_return_external_pic ();
7165
      else
7166
        x = gen_return_internal ();
7167
 
7168
      emit_jump_insn (x);
7169
    }
7170
  DONE;
7171
}")
7172
 
7173
; Used by hppa_profile_hook to load the starting address of the current
7174
; function; operand 1 contains the address of the label in operand 3
7175
(define_insn "load_offset_label_address"
7176
  [(set (match_operand:SI 0 "register_operand" "=r")
7177
        (plus:SI (match_operand:SI 1 "register_operand" "r")
7178
                 (minus:SI (match_operand:SI 2 "" "")
7179
                           (label_ref:SI (match_operand 3 "" "")))))]
7180
  ""
7181
  "ldo %2-%l3(%1),%0"
7182
  [(set_attr "type" "multi")
7183
   (set_attr "length" "4")])
7184
 
7185
; Output a code label and load its address.
7186
(define_insn "lcla1"
7187
  [(set (match_operand:SI 0 "register_operand" "=r")
7188
        (label_ref:SI (match_operand 1 "" "")))
7189
   (const_int 0)]
7190
  "!TARGET_PA_20"
7191
  "*
7192
{
7193
  output_asm_insn (\"bl .+8,%0\;depi 0,31,2,%0\", operands);
7194
  (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
7195
                                     CODE_LABEL_NUMBER (operands[1]));
7196
  return \"\";
7197
}"
7198
  [(set_attr "type" "multi")
7199
   (set_attr "length" "8")])
7200
 
7201
(define_insn "lcla2"
7202
  [(set (match_operand:SI 0 "register_operand" "=r")
7203
        (label_ref:SI (match_operand 1 "" "")))
7204
   (const_int 0)]
7205
  "TARGET_PA_20"
7206
  "*
7207
{
7208
  (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
7209
                                     CODE_LABEL_NUMBER (operands[1]));
7210
  return \"mfia %0\";
7211
}"
7212
  [(set_attr "type" "move")
7213
   (set_attr "length" "4")])
7214
 
7215
(define_insn "blockage"
7216
  [(unspec_volatile [(const_int 2)] UNSPECV_BLOCKAGE)]
7217
  ""
7218
  ""
7219
  [(set_attr "length" "0")])
7220
 
7221
(define_insn "jump"
7222
  [(set (pc) (label_ref (match_operand 0 "" "")))]
7223
  ""
7224
  "*
7225
{
7226
  /* An unconditional branch which can reach its target.  */
7227
  if (get_attr_length (insn) < 16)
7228
    return \"b%* %l0\";
7229
 
7230
  return output_lbranch (operands[0], insn, 1);
7231
}"
7232
  [(set_attr "type" "uncond_branch")
7233
   (set_attr "pa_combine_type" "uncond_branch")
7234
   (set (attr "length")
7235
    (cond [(eq (symbol_ref "jump_in_call_delay (insn)") (const_int 1))
7236
           (if_then_else (lt (abs (minus (match_dup 0)
7237
                                         (plus (pc) (const_int 8))))
7238
                             (const_int MAX_12BIT_OFFSET))
7239
           (const_int 4)
7240
           (const_int 8))
7241
           (lt (abs (minus (match_dup 0) (plus (pc) (const_int 8))))
7242
               (const_int MAX_17BIT_OFFSET))
7243
           (const_int 4)
7244
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
7245
           (const_int 20)
7246
           (eq (symbol_ref "flag_pic") (const_int 0))
7247
           (const_int 16)]
7248
          (const_int 24)))])
7249
 
7250
;;; Hope this is only within a function...
7251
(define_insn "indirect_jump"
7252
  [(set (pc) (match_operand 0 "register_operand" "r"))]
7253
  "GET_MODE (operands[0]) == word_mode"
7254
  "bv%* %%r0(%0)"
7255
  [(set_attr "type" "branch")
7256
   (set_attr "length" "4")])
7257
 
7258
;;; An indirect jump can be optimized to a direct jump.  GAS for the
7259
;;; SOM target doesn't allow branching to a label inside a function.
7260
;;; We also don't correctly compute branch distances for labels
7261
;;; outside the current function.  Thus, we use an indirect jump can't
7262
;;; be optimized to a direct jump for all targets.  We assume that
7263
;;; the branch target is in the same space (i.e., nested function
7264
;;; jumping to a label in an outer function in the same translation
7265
;;; unit).
7266
(define_expand "nonlocal_goto"
7267
  [(use (match_operand 0 "general_operand" ""))
7268
   (use (match_operand 1 "general_operand" ""))
7269
   (use (match_operand 2 "general_operand" ""))
7270
   (use (match_operand 3 "general_operand" ""))]
7271
  ""
7272
{
7273
  rtx lab = operands[1];
7274
  rtx stack = operands[2];
7275
  rtx fp = operands[3];
7276
 
7277
  lab = copy_to_reg (lab);
7278
 
7279
  emit_insn (gen_rtx_CLOBBER (VOIDmode,
7280
                              gen_rtx_MEM (BLKmode,
7281
                                           gen_rtx_SCRATCH (VOIDmode))));
7282
  emit_insn (gen_rtx_CLOBBER (VOIDmode,
7283
                              gen_rtx_MEM (BLKmode,
7284
                                           hard_frame_pointer_rtx)));
7285
 
7286
  /* Restore the frame pointer.  The virtual_stack_vars_rtx is saved
7287
     instead of the hard_frame_pointer_rtx in the save area.  As a
7288
     result, an extra instruction is needed to adjust for the offset
7289
     of the virtual stack variables and the frame pointer.  */
7290
  if (GET_CODE (fp) != REG)
7291
    fp = force_reg (Pmode, fp);
7292
  emit_move_insn (virtual_stack_vars_rtx, fp);
7293
 
7294
  emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
7295
 
7296
  emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
7297
  emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
7298
 
7299
  /* Nonlocal goto jumps are only used between functions in the same
7300
     translation unit.  Thus, we can avoid the extra overhead of an
7301
     interspace jump.  */
7302
  emit_jump_insn (gen_indirect_goto (lab));
7303
  emit_barrier ();
7304
  DONE;
7305
})
7306
 
7307
(define_insn "indirect_goto"
7308
  [(unspec [(match_operand 0 "register_operand" "=r")] UNSPEC_GOTO)]
7309
  "GET_MODE (operands[0]) == word_mode"
7310
  "bv%* %%r0(%0)"
7311
  [(set_attr "type" "branch")
7312
   (set_attr "length" "4")])
7313
 
7314
;;; This jump is used in branch tables where the insn length is fixed.
7315
;;; The length of this insn is adjusted if the delay slot is not filled.
7316
(define_insn "short_jump"
7317
  [(set (pc) (label_ref (match_operand 0 "" "")))
7318
   (const_int 0)]
7319
  ""
7320
  "b%* %l0%#"
7321
  [(set_attr "type" "btable_branch")
7322
   (set_attr "length" "4")])
7323
 
7324
;; Subroutines of "casesi".
7325
;; operand 0 is index
7326
;; operand 1 is the minimum bound
7327
;; operand 2 is the maximum bound - minimum bound + 1
7328
;; operand 3 is CODE_LABEL for the table;
7329
;; operand 4 is the CODE_LABEL to go to if index out of range.
7330
 
7331
(define_expand "casesi"
7332
  [(match_operand:SI 0 "general_operand" "")
7333
   (match_operand:SI 1 "const_int_operand" "")
7334
   (match_operand:SI 2 "const_int_operand" "")
7335
   (match_operand 3 "" "")
7336
   (match_operand 4 "" "")]
7337
  ""
7338
  "
7339
{
7340
  if (GET_CODE (operands[0]) != REG)
7341
    operands[0] = force_reg (SImode, operands[0]);
7342
 
7343
  if (operands[1] != const0_rtx)
7344
    {
7345
      rtx index = gen_reg_rtx (SImode);
7346
 
7347
      operands[1] = GEN_INT (-INTVAL (operands[1]));
7348
      if (!INT_14_BITS (operands[1]))
7349
        operands[1] = force_reg (SImode, operands[1]);
7350
      emit_insn (gen_addsi3 (index, operands[0], operands[1]));
7351
      operands[0] = index;
7352
    }
7353
 
7354
  /* In 64bit mode we must make sure to wipe the upper bits of the register
7355
     just in case the addition overflowed or we had random bits in the
7356
     high part of the register.  */
7357
  if (TARGET_64BIT)
7358
    {
7359
      rtx index = gen_reg_rtx (DImode);
7360
 
7361
      emit_insn (gen_extendsidi2 (index, operands[0]));
7362
      operands[0] = gen_rtx_SUBREG (SImode, index, 4);
7363
    }
7364
 
7365
  if (!INT_5_BITS (operands[2]))
7366
    operands[2] = force_reg (SImode, operands[2]);
7367
 
7368
  /* This branch prevents us finding an insn for the delay slot of the
7369
     following vectored branch.  It might be possible to use the delay
7370
     slot if an index value of -1 was used to transfer to the out-of-range
7371
     label.  In order to do this, we would have to output the -1 vector
7372
     element after the delay insn.  The casesi output code would have to
7373
     check if the casesi insn is in a delay branch sequence and output
7374
     the delay insn if one is found.  If this was done, then it might
7375
     then be worthwhile to split the casesi patterns to improve scheduling.
7376
     However, it's not clear that all this extra complexity is worth
7377
     the effort.  */
7378
  emit_insn (gen_cmpsi (operands[0], operands[2]));
7379
  emit_jump_insn (gen_bgtu (operands[4]));
7380
 
7381
  if (TARGET_BIG_SWITCH)
7382
    {
7383
      if (TARGET_64BIT)
7384
        {
7385
          rtx tmp1 = gen_reg_rtx (DImode);
7386
          rtx tmp2 = gen_reg_rtx (DImode);
7387
 
7388
          emit_jump_insn (gen_casesi64p (operands[0], operands[3],
7389
                                         tmp1, tmp2));
7390
        }
7391
      else
7392
        {
7393
          rtx tmp1 = gen_reg_rtx (SImode);
7394
 
7395
          if (flag_pic)
7396
            {
7397
              rtx tmp2 = gen_reg_rtx (SImode);
7398
 
7399
              emit_jump_insn (gen_casesi32p (operands[0], operands[3],
7400
                                             tmp1, tmp2));
7401
            }
7402
          else
7403
            emit_jump_insn (gen_casesi32 (operands[0], operands[3], tmp1));
7404
        }
7405
    }
7406
  else
7407
    emit_jump_insn (gen_casesi0 (operands[0], operands[3]));
7408
  DONE;
7409
}")
7410
 
7411
;;; The rtl for this pattern doesn't accurately describe what the insn
7412
;;; actually does, particularly when case-vector elements are exploded
7413
;;; in pa_reorg.  However, the initial SET in these patterns must show
7414
;;; the connection of the insn to the following jump table.
7415
(define_insn "casesi0"
7416
  [(set (pc) (mem:SI (plus:SI
7417
                       (mult:SI (match_operand:SI 0 "register_operand" "r")
7418
                                (const_int 4))
7419
                       (label_ref (match_operand 1 "" "")))))]
7420
  ""
7421
  "blr,n %0,%%r0\;nop"
7422
  [(set_attr "type" "multi")
7423
   (set_attr "length" "8")])
7424
 
7425
;;; 32-bit code, absolute branch table.
7426
(define_insn "casesi32"
7427
  [(set (pc) (mem:SI (plus:SI
7428
                       (mult:SI (match_operand:SI 0 "register_operand" "r")
7429
                                (const_int 4))
7430
                       (label_ref (match_operand 1 "" "")))))
7431
   (clobber (match_operand:SI 2 "register_operand" "=&r"))]
7432
  "!TARGET_64BIT && TARGET_BIG_SWITCH"
7433
  "ldil L'%l1,%2\;ldo R'%l1(%2),%2\;{ldwx|ldw},s %0(%2),%2\;bv,n %%r0(%2)"
7434
  [(set_attr "type" "multi")
7435
   (set_attr "length" "16")])
7436
 
7437
;;; 32-bit code, relative branch table.
7438
(define_insn "casesi32p"
7439
  [(set (pc) (mem:SI (plus:SI
7440
                       (mult:SI (match_operand:SI 0 "register_operand" "r")
7441
                                (const_int 4))
7442
                       (label_ref (match_operand 1 "" "")))))
7443
   (clobber (match_operand:SI 2 "register_operand" "=&a"))
7444
   (clobber (match_operand:SI 3 "register_operand" "=&r"))]
7445
  "!TARGET_64BIT && TARGET_BIG_SWITCH"
7446
  "{bl .+8,%2\;depi 0,31,2,%2|mfia %2}\;ldo {16|20}(%2),%2\;\
7447
{ldwx|ldw},s %0(%2),%3\;{addl|add,l} %2,%3,%3\;bv,n %%r0(%3)"
7448
  [(set_attr "type" "multi")
7449
   (set (attr "length")
7450
     (if_then_else (ne (symbol_ref "TARGET_PA_20") (const_int 0))
7451
        (const_int 20)
7452
        (const_int 24)))])
7453
 
7454
;;; 64-bit code, 32-bit relative branch table.
7455
(define_insn "casesi64p"
7456
  [(set (pc) (mem:DI (plus:DI
7457
                       (mult:DI (sign_extend:DI
7458
                                  (match_operand:SI 0 "register_operand" "r"))
7459
                                (const_int 8))
7460
                       (label_ref (match_operand 1 "" "")))))
7461
   (clobber (match_operand:DI 2 "register_operand" "=&r"))
7462
   (clobber (match_operand:DI 3 "register_operand" "=&r"))]
7463
  "TARGET_64BIT && TARGET_BIG_SWITCH"
7464
  "mfia %2\;ldo 24(%2),%2\;ldw,s %0(%2),%3\;extrd,s %3,63,32,%3\;\
7465
add,l %2,%3,%3\;bv,n %%r0(%3)"
7466
  [(set_attr "type" "multi")
7467
   (set_attr "length" "24")])
7468
 
7469
 
7470
;; Call patterns.
7471
;;- jump to subroutine
7472
 
7473
(define_expand "call"
7474
  [(parallel [(call (match_operand:SI 0 "" "")
7475
                    (match_operand 1 "" ""))
7476
              (clobber (reg:SI 2))])]
7477
  ""
7478
  "
7479
{
7480
  rtx op, call_insn;
7481
  rtx nb = operands[1];
7482
 
7483
  if (TARGET_PORTABLE_RUNTIME)
7484
    op = force_reg (SImode, XEXP (operands[0], 0));
7485
  else
7486
    op = XEXP (operands[0], 0);
7487
 
7488
  if (TARGET_64BIT)
7489
    {
7490
      if (!virtuals_instantiated)
7491
        emit_move_insn (arg_pointer_rtx,
7492
                        gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
7493
                                      GEN_INT (64)));
7494
      else
7495
        {
7496
          /* The loop pass can generate new libcalls after the virtual
7497
             registers are instantiated when fpregs are disabled because
7498
             the only method that we have for doing DImode multiplication
7499
             is with a libcall.  This could be trouble if we haven't
7500
             allocated enough space for the outgoing arguments.  */
7501
          gcc_assert (INTVAL (nb) <= current_function_outgoing_args_size);
7502
 
7503
          emit_move_insn (arg_pointer_rtx,
7504
                          gen_rtx_PLUS (word_mode, stack_pointer_rtx,
7505
                                        GEN_INT (STACK_POINTER_OFFSET + 64)));
7506
        }
7507
    }
7508
 
7509
  /* Use two different patterns for calls to explicitly named functions
7510
     and calls through function pointers.  This is necessary as these two
7511
     types of calls use different calling conventions, and CSE might try
7512
     to change the named call into an indirect call in some cases (using
7513
     two patterns keeps CSE from performing this optimization).
7514
 
7515
     We now use even more call patterns as there was a subtle bug in
7516
     attempting to restore the pic register after a call using a simple
7517
     move insn.  During reload, a instruction involving a pseudo register
7518
     with no explicit dependence on the PIC register can be converted
7519
     to an equivalent load from memory using the PIC register.  If we
7520
     emit a simple move to restore the PIC register in the initial rtl
7521
     generation, then it can potentially be repositioned during scheduling.
7522
     and an instruction that eventually uses the PIC register may end up
7523
     between the call and the PIC register restore.
7524
 
7525
     This only worked because there is a post call group of instructions
7526
     that are scheduled with the call.  These instructions are included
7527
     in the same basic block as the call.  However, calls can throw in
7528
     C++ code and a basic block has to terminate at the call if the call
7529
     can throw.  This results in the PIC register restore being scheduled
7530
     independently from the call.  So, we now hide the save and restore
7531
     of the PIC register in the call pattern until after reload.  Then,
7532
     we split the moves out.  A small side benefit is that we now don't
7533
     need to have a use of the PIC register in the return pattern and
7534
     the final save/restore operation is not needed.
7535
 
7536
     I elected to just clobber %r4 in the PIC patterns and use it instead
7537
     of trying to force hppa_pic_save_rtx () to a callee saved register.
7538
     This might have required a new register class and constraint.  It
7539
     was also simpler to just handle the restore from a register than a
7540
     generic pseudo.  */
7541
  if (TARGET_64BIT)
7542
    {
7543
      if (GET_CODE (op) == SYMBOL_REF)
7544
        call_insn = emit_call_insn (gen_call_symref_64bit (op, nb));
7545
      else
7546
        {
7547
          op = force_reg (word_mode, op);
7548
          call_insn = emit_call_insn (gen_call_reg_64bit (op, nb));
7549
        }
7550
    }
7551
  else
7552
    {
7553
      if (GET_CODE (op) == SYMBOL_REF)
7554
        {
7555
          if (flag_pic)
7556
            call_insn = emit_call_insn (gen_call_symref_pic (op, nb));
7557
          else
7558
            call_insn = emit_call_insn (gen_call_symref (op, nb));
7559
        }
7560
      else
7561
        {
7562
          rtx tmpreg = gen_rtx_REG (word_mode, 22);
7563
 
7564
          emit_move_insn (tmpreg, force_reg (word_mode, op));
7565
          if (flag_pic)
7566
            call_insn = emit_call_insn (gen_call_reg_pic (nb));
7567
          else
7568
            call_insn = emit_call_insn (gen_call_reg (nb));
7569
        }
7570
    }
7571
 
7572
  DONE;
7573
}")
7574
 
7575
;; We use function calls to set the attribute length of calls and millicode
7576
;; calls.  This is necessary because of the large variety of call sequences.
7577
;; Implementing the calculation in rtl is difficult as well as ugly.  As
7578
;; we need the same calculation in several places, maintenance becomes a
7579
;; nightmare.
7580
;;
7581
;; However, this has a subtle impact on branch shortening.  When the
7582
;; expression used to set the length attribute of an instruction depends
7583
;; on a relative address (e.g., pc or a branch address), genattrtab
7584
;; notes that the insn's length is variable, and attempts to determine a
7585
;; worst-case default length and code to compute an insn's current length.
7586
 
7587
;; The use of a function call hides the variable dependence of our calls
7588
;; and millicode calls.  The result is genattrtab doesn't treat the operation
7589
;; as variable and it only generates code for the default case using our
7590
;; function call.  Because of this, calls and millicode calls have a fixed
7591
;; length in the branch shortening pass, and some branches will use a longer
7592
;; code sequence than necessary.  However, the length of any given call
7593
;; will still reflect its final code location and it may be shorter than
7594
;; the initial length estimate.
7595
 
7596
;; It's possible to trick genattrtab by adding an expression involving `pc'
7597
;; in the set.  However, when genattrtab hits a function call in its attempt
7598
;; to compute the default length, it marks the result as unknown and sets
7599
;; the default result to MAX_INT ;-(  One possible fix that would allow
7600
;; calls to participate in branch shortening would be to make the call to
7601
;; insn_default_length a target option.  Then, we could massage unknown
7602
;; results.  Another fix might be to change genattrtab so that it just does
7603
;; the call in the variable case as it already does for the fixed case.
7604
 
7605
(define_insn "call_symref"
7606
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7607
         (match_operand 1 "" "i"))
7608
   (clobber (reg:SI 1))
7609
   (clobber (reg:SI 2))
7610
   (use (const_int 0))]
7611
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7612
  "*
7613
{
7614
  output_arg_descriptor (insn);
7615
  return output_call (insn, operands[0], 0);
7616
}"
7617
  [(set_attr "type" "call")
7618
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
7619
 
7620
(define_insn "call_symref_pic"
7621
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7622
         (match_operand 1 "" "i"))
7623
   (clobber (reg:SI 1))
7624
   (clobber (reg:SI 2))
7625
   (clobber (reg:SI 4))
7626
   (use (reg:SI 19))
7627
   (use (const_int 0))]
7628
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7629
  "*
7630
{
7631
  output_arg_descriptor (insn);
7632
  return output_call (insn, operands[0], 0);
7633
}"
7634
  [(set_attr "type" "call")
7635
   (set (attr "length")
7636
        (plus (symbol_ref "attr_length_call (insn, 0)")
7637
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
7638
 
7639
;; Split out the PIC register save and restore after reload.  This is
7640
;; done only if the function returns.  As the split is done after reload,
7641
;; there are some situations in which we unnecessarily save and restore
7642
;; %r4.  This happens when there is a single call and the PIC register
7643
;; is "dead" after the call.  This isn't easy to fix as the usage of
7644
;; the PIC register isn't completely determined until the reload pass.
7645
(define_split
7646
  [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7647
                    (match_operand 1 "" ""))
7648
              (clobber (reg:SI 1))
7649
              (clobber (reg:SI 2))
7650
              (clobber (reg:SI 4))
7651
              (use (reg:SI 19))
7652
              (use (const_int 0))])]
7653
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT
7654
   && reload_completed
7655
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7656
  [(set (reg:SI 4) (reg:SI 19))
7657
   (parallel [(call (mem:SI (match_dup 0))
7658
                    (match_dup 1))
7659
              (clobber (reg:SI 1))
7660
              (clobber (reg:SI 2))
7661
              (use (reg:SI 19))
7662
              (use (const_int 0))])
7663
   (set (reg:SI 19) (reg:SI 4))]
7664
  "")
7665
 
7666
;; Remove the clobber of register 4 when optimizing.  This has to be
7667
;; done with a peephole optimization rather than a split because the
7668
;; split sequence for a call must be longer than one instruction.
7669
(define_peephole2
7670
  [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7671
                    (match_operand 1 "" ""))
7672
              (clobber (reg:SI 1))
7673
              (clobber (reg:SI 2))
7674
              (clobber (reg:SI 4))
7675
              (use (reg:SI 19))
7676
              (use (const_int 0))])]
7677
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed"
7678
  [(parallel [(call (mem:SI (match_dup 0))
7679
                    (match_dup 1))
7680
              (clobber (reg:SI 1))
7681
              (clobber (reg:SI 2))
7682
              (use (reg:SI 19))
7683
              (use (const_int 0))])]
7684
  "")
7685
 
7686
(define_insn "*call_symref_pic_post_reload"
7687
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7688
         (match_operand 1 "" "i"))
7689
   (clobber (reg:SI 1))
7690
   (clobber (reg:SI 2))
7691
   (use (reg:SI 19))
7692
   (use (const_int 0))]
7693
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
7694
  "*
7695
{
7696
  output_arg_descriptor (insn);
7697
  return output_call (insn, operands[0], 0);
7698
}"
7699
  [(set_attr "type" "call")
7700
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
7701
 
7702
;; This pattern is split if it is necessary to save and restore the
7703
;; PIC register.
7704
(define_insn "call_symref_64bit"
7705
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7706
         (match_operand 1 "" "i"))
7707
   (clobber (reg:DI 1))
7708
   (clobber (reg:DI 2))
7709
   (clobber (reg:DI 4))
7710
   (use (reg:DI 27))
7711
   (use (reg:DI 29))
7712
   (use (const_int 0))]
7713
  "TARGET_64BIT"
7714
  "*
7715
{
7716
  output_arg_descriptor (insn);
7717
  return output_call (insn, operands[0], 0);
7718
}"
7719
  [(set_attr "type" "call")
7720
   (set (attr "length")
7721
        (plus (symbol_ref "attr_length_call (insn, 0)")
7722
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
7723
 
7724
;; Split out the PIC register save and restore after reload.  This is
7725
;; done only if the function returns.  As the split is done after reload,
7726
;; there are some situations in which we unnecessarily save and restore
7727
;; %r4.  This happens when there is a single call and the PIC register
7728
;; is "dead" after the call.  This isn't easy to fix as the usage of
7729
;; the PIC register isn't completely determined until the reload pass.
7730
(define_split
7731
  [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7732
                    (match_operand 1 "" ""))
7733
              (clobber (reg:DI 1))
7734
              (clobber (reg:DI 2))
7735
              (clobber (reg:DI 4))
7736
              (use (reg:DI 27))
7737
              (use (reg:DI 29))
7738
              (use (const_int 0))])]
7739
  "TARGET_64BIT
7740
   && reload_completed
7741
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7742
  [(set (reg:DI 4) (reg:DI 27))
7743
   (parallel [(call (mem:SI (match_dup 0))
7744
                    (match_dup 1))
7745
              (clobber (reg:DI 1))
7746
              (clobber (reg:DI 2))
7747
              (use (reg:DI 27))
7748
              (use (reg:DI 29))
7749
              (use (const_int 0))])
7750
   (set (reg:DI 27) (reg:DI 4))]
7751
  "")
7752
 
7753
;; Remove the clobber of register 4 when optimizing.  This has to be
7754
;; done with a peephole optimization rather than a split because the
7755
;; split sequence for a call must be longer than one instruction.
7756
(define_peephole2
7757
  [(parallel [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7758
                    (match_operand 1 "" ""))
7759
              (clobber (reg:DI 1))
7760
              (clobber (reg:DI 2))
7761
              (clobber (reg:DI 4))
7762
              (use (reg:DI 27))
7763
              (use (reg:DI 29))
7764
              (use (const_int 0))])]
7765
  "TARGET_64BIT && reload_completed"
7766
  [(parallel [(call (mem:SI (match_dup 0))
7767
                    (match_dup 1))
7768
              (clobber (reg:DI 1))
7769
              (clobber (reg:DI 2))
7770
              (use (reg:DI 27))
7771
              (use (reg:DI 29))
7772
              (use (const_int 0))])]
7773
  "")
7774
 
7775
(define_insn "*call_symref_64bit_post_reload"
7776
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
7777
         (match_operand 1 "" "i"))
7778
   (clobber (reg:DI 1))
7779
   (clobber (reg:DI 2))
7780
   (use (reg:DI 27))
7781
   (use (reg:DI 29))
7782
   (use (const_int 0))]
7783
  "TARGET_64BIT"
7784
  "*
7785
{
7786
  output_arg_descriptor (insn);
7787
  return output_call (insn, operands[0], 0);
7788
}"
7789
  [(set_attr "type" "call")
7790
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
7791
 
7792
(define_insn "call_reg"
7793
  [(call (mem:SI (reg:SI 22))
7794
         (match_operand 0 "" "i"))
7795
   (clobber (reg:SI 1))
7796
   (clobber (reg:SI 2))
7797
   (use (const_int 1))]
7798
  "!TARGET_64BIT"
7799
  "*
7800
{
7801
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
7802
}"
7803
  [(set_attr "type" "dyncall")
7804
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
7805
 
7806
;; This pattern is split if it is necessary to save and restore the
7807
;; PIC register.
7808
(define_insn "call_reg_pic"
7809
  [(call (mem:SI (reg:SI 22))
7810
         (match_operand 0 "" "i"))
7811
   (clobber (reg:SI 1))
7812
   (clobber (reg:SI 2))
7813
   (clobber (reg:SI 4))
7814
   (use (reg:SI 19))
7815
   (use (const_int 1))]
7816
  "!TARGET_64BIT"
7817
  "*
7818
{
7819
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
7820
}"
7821
  [(set_attr "type" "dyncall")
7822
   (set (attr "length")
7823
        (plus (symbol_ref "attr_length_indirect_call (insn)")
7824
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
7825
 
7826
;; Split out the PIC register save and restore after reload.  This is
7827
;; done only if the function returns.  As the split is done after reload,
7828
;; there are some situations in which we unnecessarily save and restore
7829
;; %r4.  This happens when there is a single call and the PIC register
7830
;; is "dead" after the call.  This isn't easy to fix as the usage of
7831
;; the PIC register isn't completely determined until the reload pass.
7832
(define_split
7833
  [(parallel [(call (mem:SI (reg:SI 22))
7834
                    (match_operand 0 "" ""))
7835
              (clobber (reg:SI 1))
7836
              (clobber (reg:SI 2))
7837
              (clobber (reg:SI 4))
7838
              (use (reg:SI 19))
7839
              (use (const_int 1))])]
7840
  "!TARGET_64BIT
7841
   && reload_completed
7842
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7843
  [(set (reg:SI 4) (reg:SI 19))
7844
   (parallel [(call (mem:SI (reg:SI 22))
7845
                    (match_dup 0))
7846
              (clobber (reg:SI 1))
7847
              (clobber (reg:SI 2))
7848
              (use (reg:SI 19))
7849
              (use (const_int 1))])
7850
   (set (reg:SI 19) (reg:SI 4))]
7851
  "")
7852
 
7853
;; Remove the clobber of register 4 when optimizing.  This has to be
7854
;; done with a peephole optimization rather than a split because the
7855
;; split sequence for a call must be longer than one instruction.
7856
(define_peephole2
7857
  [(parallel [(call (mem:SI (reg:SI 22))
7858
                    (match_operand 0 "" ""))
7859
              (clobber (reg:SI 1))
7860
              (clobber (reg:SI 2))
7861
              (clobber (reg:SI 4))
7862
              (use (reg:SI 19))
7863
              (use (const_int 1))])]
7864
  "!TARGET_64BIT && reload_completed"
7865
  [(parallel [(call (mem:SI (reg:SI 22))
7866
                    (match_dup 0))
7867
              (clobber (reg:SI 1))
7868
              (clobber (reg:SI 2))
7869
              (use (reg:SI 19))
7870
              (use (const_int 1))])]
7871
  "")
7872
 
7873
(define_insn "*call_reg_pic_post_reload"
7874
  [(call (mem:SI (reg:SI 22))
7875
         (match_operand 0 "" "i"))
7876
   (clobber (reg:SI 1))
7877
   (clobber (reg:SI 2))
7878
   (use (reg:SI 19))
7879
   (use (const_int 1))]
7880
  "!TARGET_64BIT"
7881
  "*
7882
{
7883
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
7884
}"
7885
  [(set_attr "type" "dyncall")
7886
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
7887
 
7888
;; This pattern is split if it is necessary to save and restore the
7889
;; PIC register.
7890
(define_insn "call_reg_64bit"
7891
  [(call (mem:SI (match_operand:DI 0 "register_operand" "r"))
7892
         (match_operand 1 "" "i"))
7893
   (clobber (reg:DI 2))
7894
   (clobber (reg:DI 4))
7895
   (use (reg:DI 27))
7896
   (use (reg:DI 29))
7897
   (use (const_int 1))]
7898
  "TARGET_64BIT"
7899
  "*
7900
{
7901
  return output_indirect_call (insn, operands[0]);
7902
}"
7903
  [(set_attr "type" "dyncall")
7904
   (set (attr "length")
7905
        (plus (symbol_ref "attr_length_indirect_call (insn)")
7906
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
7907
 
7908
;; Split out the PIC register save and restore after reload.  This is
7909
;; done only if the function returns.  As the split is done after reload,
7910
;; there are some situations in which we unnecessarily save and restore
7911
;; %r4.  This happens when there is a single call and the PIC register
7912
;; is "dead" after the call.  This isn't easy to fix as the usage of
7913
;; the PIC register isn't completely determined until the reload pass.
7914
(define_split
7915
  [(parallel [(call (mem:SI (match_operand 0 "register_operand" ""))
7916
                    (match_operand 1 "" ""))
7917
              (clobber (reg:DI 2))
7918
              (clobber (reg:DI 4))
7919
              (use (reg:DI 27))
7920
              (use (reg:DI 29))
7921
              (use (const_int 1))])]
7922
  "TARGET_64BIT
7923
   && reload_completed
7924
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7925
  [(set (reg:DI 4) (reg:DI 27))
7926
   (parallel [(call (mem:SI (match_dup 0))
7927
                    (match_dup 1))
7928
              (clobber (reg:DI 2))
7929
              (use (reg:DI 27))
7930
              (use (reg:DI 29))
7931
              (use (const_int 1))])
7932
   (set (reg:DI 27) (reg:DI 4))]
7933
  "")
7934
 
7935
;; Remove the clobber of register 4 when optimizing.  This has to be
7936
;; done with a peephole optimization rather than a split because the
7937
;; split sequence for a call must be longer than one instruction.
7938
(define_peephole2
7939
  [(parallel [(call (mem:SI (match_operand 0 "register_operand" ""))
7940
                    (match_operand 1 "" ""))
7941
              (clobber (reg:DI 2))
7942
              (clobber (reg:DI 4))
7943
              (use (reg:DI 27))
7944
              (use (reg:DI 29))
7945
              (use (const_int 1))])]
7946
  "TARGET_64BIT && reload_completed"
7947
  [(parallel [(call (mem:SI (match_dup 0))
7948
                    (match_dup 1))
7949
              (clobber (reg:DI 2))
7950
              (use (reg:DI 27))
7951
              (use (reg:DI 29))
7952
              (use (const_int 1))])]
7953
  "")
7954
 
7955
(define_insn "*call_reg_64bit_post_reload"
7956
  [(call (mem:SI (match_operand:DI 0 "register_operand" "r"))
7957
         (match_operand 1 "" "i"))
7958
   (clobber (reg:DI 2))
7959
   (use (reg:DI 27))
7960
   (use (reg:DI 29))
7961
   (use (const_int 1))]
7962
  "TARGET_64BIT"
7963
  "*
7964
{
7965
  return output_indirect_call (insn, operands[0]);
7966
}"
7967
  [(set_attr "type" "dyncall")
7968
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
7969
 
7970
(define_expand "call_value"
7971
  [(parallel [(set (match_operand 0 "" "")
7972
                   (call (match_operand:SI 1 "" "")
7973
                         (match_operand 2 "" "")))
7974
              (clobber (reg:SI 2))])]
7975
  ""
7976
  "
7977
{
7978
  rtx op, call_insn;
7979
  rtx dst = operands[0];
7980
  rtx nb = operands[2];
7981
 
7982
  if (TARGET_PORTABLE_RUNTIME)
7983
    op = force_reg (SImode, XEXP (operands[1], 0));
7984
  else
7985
    op = XEXP (operands[1], 0);
7986
 
7987
  if (TARGET_64BIT)
7988
    {
7989
      if (!virtuals_instantiated)
7990
        emit_move_insn (arg_pointer_rtx,
7991
                        gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
7992
                                      GEN_INT (64)));
7993
      else
7994
        {
7995
          /* The loop pass can generate new libcalls after the virtual
7996
             registers are instantiated when fpregs are disabled because
7997
             the only method that we have for doing DImode multiplication
7998
             is with a libcall.  This could be trouble if we haven't
7999
             allocated enough space for the outgoing arguments.  */
8000
          gcc_assert (INTVAL (nb) <= current_function_outgoing_args_size);
8001
 
8002
          emit_move_insn (arg_pointer_rtx,
8003
                          gen_rtx_PLUS (word_mode, stack_pointer_rtx,
8004
                                        GEN_INT (STACK_POINTER_OFFSET + 64)));
8005
        }
8006
    }
8007
 
8008
  /* Use two different patterns for calls to explicitly named functions
8009
     and calls through function pointers.  This is necessary as these two
8010
     types of calls use different calling conventions, and CSE might try
8011
     to change the named call into an indirect call in some cases (using
8012
     two patterns keeps CSE from performing this optimization).
8013
 
8014
     We now use even more call patterns as there was a subtle bug in
8015
     attempting to restore the pic register after a call using a simple
8016
     move insn.  During reload, a instruction involving a pseudo register
8017
     with no explicit dependence on the PIC register can be converted
8018
     to an equivalent load from memory using the PIC register.  If we
8019
     emit a simple move to restore the PIC register in the initial rtl
8020
     generation, then it can potentially be repositioned during scheduling.
8021
     and an instruction that eventually uses the PIC register may end up
8022
     between the call and the PIC register restore.
8023
 
8024
     This only worked because there is a post call group of instructions
8025
     that are scheduled with the call.  These instructions are included
8026
     in the same basic block as the call.  However, calls can throw in
8027
     C++ code and a basic block has to terminate at the call if the call
8028
     can throw.  This results in the PIC register restore being scheduled
8029
     independently from the call.  So, we now hide the save and restore
8030
     of the PIC register in the call pattern until after reload.  Then,
8031
     we split the moves out.  A small side benefit is that we now don't
8032
     need to have a use of the PIC register in the return pattern and
8033
     the final save/restore operation is not needed.
8034
 
8035
     I elected to just clobber %r4 in the PIC patterns and use it instead
8036
     of trying to force hppa_pic_save_rtx () to a callee saved register.
8037
     This might have required a new register class and constraint.  It
8038
     was also simpler to just handle the restore from a register than a
8039
     generic pseudo.  */
8040
  if (TARGET_64BIT)
8041
    {
8042
      if (GET_CODE (op) == SYMBOL_REF)
8043
        call_insn = emit_call_insn (gen_call_val_symref_64bit (dst, op, nb));
8044
      else
8045
        {
8046
          op = force_reg (word_mode, op);
8047
          call_insn = emit_call_insn (gen_call_val_reg_64bit (dst, op, nb));
8048
        }
8049
    }
8050
  else
8051
    {
8052
      if (GET_CODE (op) == SYMBOL_REF)
8053
        {
8054
          if (flag_pic)
8055
            call_insn = emit_call_insn (gen_call_val_symref_pic (dst, op, nb));
8056
          else
8057
            call_insn = emit_call_insn (gen_call_val_symref (dst, op, nb));
8058
        }
8059
      else
8060
        {
8061
          rtx tmpreg = gen_rtx_REG (word_mode, 22);
8062
 
8063
          emit_move_insn (tmpreg, force_reg (word_mode, op));
8064
          if (flag_pic)
8065
            call_insn = emit_call_insn (gen_call_val_reg_pic (dst, nb));
8066
          else
8067
            call_insn = emit_call_insn (gen_call_val_reg (dst, nb));
8068
        }
8069
    }
8070
 
8071
  DONE;
8072
}")
8073
 
8074
(define_insn "call_val_symref"
8075
  [(set (match_operand 0 "" "")
8076
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8077
              (match_operand 2 "" "i")))
8078
   (clobber (reg:SI 1))
8079
   (clobber (reg:SI 2))
8080
   (use (const_int 0))]
8081
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8082
  "*
8083
{
8084
  output_arg_descriptor (insn);
8085
  return output_call (insn, operands[1], 0);
8086
}"
8087
  [(set_attr "type" "call")
8088
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
8089
 
8090
(define_insn "call_val_symref_pic"
8091
  [(set (match_operand 0 "" "")
8092
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8093
              (match_operand 2 "" "i")))
8094
   (clobber (reg:SI 1))
8095
   (clobber (reg:SI 2))
8096
   (clobber (reg:SI 4))
8097
   (use (reg:SI 19))
8098
   (use (const_int 0))]
8099
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8100
  "*
8101
{
8102
  output_arg_descriptor (insn);
8103
  return output_call (insn, operands[1], 0);
8104
}"
8105
  [(set_attr "type" "call")
8106
   (set (attr "length")
8107
        (plus (symbol_ref "attr_length_call (insn, 0)")
8108
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
8109
 
8110
;; Split out the PIC register save and restore after reload.  This is
8111
;; done only if the function returns.  As the split is done after reload,
8112
;; there are some situations in which we unnecessarily save and restore
8113
;; %r4.  This happens when there is a single call and the PIC register
8114
;; is "dead" after the call.  This isn't easy to fix as the usage of
8115
;; the PIC register isn't completely determined until the reload pass.
8116
(define_split
8117
  [(parallel [(set (match_operand 0 "" "")
8118
              (call (mem:SI (match_operand 1 "call_operand_address" ""))
8119
                    (match_operand 2 "" "")))
8120
              (clobber (reg:SI 1))
8121
              (clobber (reg:SI 2))
8122
              (clobber (reg:SI 4))
8123
              (use (reg:SI 19))
8124
              (use (const_int 0))])]
8125
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT
8126
   && reload_completed
8127
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8128
  [(set (reg:SI 4) (reg:SI 19))
8129
   (parallel [(set (match_dup 0)
8130
              (call (mem:SI (match_dup 1))
8131
                    (match_dup 2)))
8132
              (clobber (reg:SI 1))
8133
              (clobber (reg:SI 2))
8134
              (use (reg:SI 19))
8135
              (use (const_int 0))])
8136
   (set (reg:SI 19) (reg:SI 4))]
8137
  "")
8138
 
8139
;; Remove the clobber of register 4 when optimizing.  This has to be
8140
;; done with a peephole optimization rather than a split because the
8141
;; split sequence for a call must be longer than one instruction.
8142
(define_peephole2
8143
  [(parallel [(set (match_operand 0 "" "")
8144
              (call (mem:SI (match_operand 1 "call_operand_address" ""))
8145
                    (match_operand 2 "" "")))
8146
              (clobber (reg:SI 1))
8147
              (clobber (reg:SI 2))
8148
              (clobber (reg:SI 4))
8149
              (use (reg:SI 19))
8150
              (use (const_int 0))])]
8151
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT && reload_completed"
8152
  [(parallel [(set (match_dup 0)
8153
              (call (mem:SI (match_dup 1))
8154
                    (match_dup 2)))
8155
              (clobber (reg:SI 1))
8156
              (clobber (reg:SI 2))
8157
              (use (reg:SI 19))
8158
              (use (const_int 0))])]
8159
  "")
8160
 
8161
(define_insn "*call_val_symref_pic_post_reload"
8162
  [(set (match_operand 0 "" "")
8163
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8164
              (match_operand 2 "" "i")))
8165
   (clobber (reg:SI 1))
8166
   (clobber (reg:SI 2))
8167
   (use (reg:SI 19))
8168
   (use (const_int 0))]
8169
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8170
  "*
8171
{
8172
  output_arg_descriptor (insn);
8173
  return output_call (insn, operands[1], 0);
8174
}"
8175
  [(set_attr "type" "call")
8176
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
8177
 
8178
;; This pattern is split if it is necessary to save and restore the
8179
;; PIC register.
8180
(define_insn "call_val_symref_64bit"
8181
  [(set (match_operand 0 "" "")
8182
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8183
              (match_operand 2 "" "i")))
8184
   (clobber (reg:DI 1))
8185
   (clobber (reg:DI 2))
8186
   (clobber (reg:DI 4))
8187
   (use (reg:DI 27))
8188
   (use (reg:DI 29))
8189
   (use (const_int 0))]
8190
  "TARGET_64BIT"
8191
  "*
8192
{
8193
  output_arg_descriptor (insn);
8194
  return output_call (insn, operands[1], 0);
8195
}"
8196
  [(set_attr "type" "call")
8197
   (set (attr "length")
8198
        (plus (symbol_ref "attr_length_call (insn, 0)")
8199
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
8200
 
8201
;; Split out the PIC register save and restore after reload.  This is
8202
;; done only if the function returns.  As the split is done after reload,
8203
;; there are some situations in which we unnecessarily save and restore
8204
;; %r4.  This happens when there is a single call and the PIC register
8205
;; is "dead" after the call.  This isn't easy to fix as the usage of
8206
;; the PIC register isn't completely determined until the reload pass.
8207
(define_split
8208
  [(parallel [(set (match_operand 0 "" "")
8209
              (call (mem:SI (match_operand 1 "call_operand_address" ""))
8210
                    (match_operand 2 "" "")))
8211
              (clobber (reg:DI 1))
8212
              (clobber (reg:DI 2))
8213
              (clobber (reg:DI 4))
8214
              (use (reg:DI 27))
8215
              (use (reg:DI 29))
8216
              (use (const_int 0))])]
8217
  "TARGET_64BIT
8218
   && reload_completed
8219
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8220
  [(set (reg:DI 4) (reg:DI 27))
8221
   (parallel [(set (match_dup 0)
8222
              (call (mem:SI (match_dup 1))
8223
                    (match_dup 2)))
8224
              (clobber (reg:DI 1))
8225
              (clobber (reg:DI 2))
8226
              (use (reg:DI 27))
8227
              (use (reg:DI 29))
8228
              (use (const_int 0))])
8229
   (set (reg:DI 27) (reg:DI 4))]
8230
  "")
8231
 
8232
;; Remove the clobber of register 4 when optimizing.  This has to be
8233
;; done with a peephole optimization rather than a split because the
8234
;; split sequence for a call must be longer than one instruction.
8235
(define_peephole2
8236
  [(parallel [(set (match_operand 0 "" "")
8237
              (call (mem:SI (match_operand 1 "call_operand_address" ""))
8238
                    (match_operand 2 "" "")))
8239
              (clobber (reg:DI 1))
8240
              (clobber (reg:DI 2))
8241
              (clobber (reg:DI 4))
8242
              (use (reg:DI 27))
8243
              (use (reg:DI 29))
8244
              (use (const_int 0))])]
8245
  "TARGET_64BIT && reload_completed"
8246
  [(parallel [(set (match_dup 0)
8247
              (call (mem:SI (match_dup 1))
8248
                    (match_dup 2)))
8249
              (clobber (reg:DI 1))
8250
              (clobber (reg:DI 2))
8251
              (use (reg:DI 27))
8252
              (use (reg:DI 29))
8253
              (use (const_int 0))])]
8254
  "")
8255
 
8256
(define_insn "*call_val_symref_64bit_post_reload"
8257
  [(set (match_operand 0 "" "")
8258
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8259
              (match_operand 2 "" "i")))
8260
   (clobber (reg:DI 1))
8261
   (clobber (reg:DI 2))
8262
   (use (reg:DI 27))
8263
   (use (reg:DI 29))
8264
   (use (const_int 0))]
8265
  "TARGET_64BIT"
8266
  "*
8267
{
8268
  output_arg_descriptor (insn);
8269
  return output_call (insn, operands[1], 0);
8270
}"
8271
  [(set_attr "type" "call")
8272
   (set (attr "length") (symbol_ref "attr_length_call (insn, 0)"))])
8273
 
8274
(define_insn "call_val_reg"
8275
  [(set (match_operand 0 "" "")
8276
        (call (mem:SI (reg:SI 22))
8277
              (match_operand 1 "" "i")))
8278
   (clobber (reg:SI 1))
8279
   (clobber (reg:SI 2))
8280
   (use (const_int 1))]
8281
  "!TARGET_64BIT"
8282
  "*
8283
{
8284
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
8285
}"
8286
  [(set_attr "type" "dyncall")
8287
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
8288
 
8289
;; This pattern is split if it is necessary to save and restore the
8290
;; PIC register.
8291
(define_insn "call_val_reg_pic"
8292
  [(set (match_operand 0 "" "")
8293
        (call (mem:SI (reg:SI 22))
8294
              (match_operand 1 "" "i")))
8295
   (clobber (reg:SI 1))
8296
   (clobber (reg:SI 2))
8297
   (clobber (reg:SI 4))
8298
   (use (reg:SI 19))
8299
   (use (const_int 1))]
8300
  "!TARGET_64BIT"
8301
  "*
8302
{
8303
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
8304
}"
8305
  [(set_attr "type" "dyncall")
8306
   (set (attr "length")
8307
        (plus (symbol_ref "attr_length_indirect_call (insn)")
8308
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
8309
 
8310
;; Split out the PIC register save and restore after reload.  This is
8311
;; done only if the function returns.  As the split is done after reload,
8312
;; there are some situations in which we unnecessarily save and restore
8313
;; %r4.  This happens when there is a single call and the PIC register
8314
;; is "dead" after the call.  This isn't easy to fix as the usage of
8315
;; the PIC register isn't completely determined until the reload pass.
8316
(define_split
8317
  [(parallel [(set (match_operand 0 "" "")
8318
                   (call (mem:SI (reg:SI 22))
8319
                         (match_operand 1 "" "")))
8320
              (clobber (reg:SI 1))
8321
              (clobber (reg:SI 2))
8322
              (clobber (reg:SI 4))
8323
              (use (reg:SI 19))
8324
              (use (const_int 1))])]
8325
  "!TARGET_64BIT
8326
   && reload_completed
8327
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8328
  [(set (reg:SI 4) (reg:SI 19))
8329
   (parallel [(set (match_dup 0)
8330
                   (call (mem:SI (reg:SI 22))
8331
                         (match_dup 1)))
8332
              (clobber (reg:SI 1))
8333
              (clobber (reg:SI 2))
8334
              (use (reg:SI 19))
8335
              (use (const_int 1))])
8336
   (set (reg:SI 19) (reg:SI 4))]
8337
  "")
8338
 
8339
;; Remove the clobber of register 4 when optimizing.  This has to be
8340
;; done with a peephole optimization rather than a split because the
8341
;; split sequence for a call must be longer than one instruction.
8342
(define_peephole2
8343
  [(parallel [(set (match_operand 0 "" "")
8344
                   (call (mem:SI (reg:SI 22))
8345
                         (match_operand 1 "" "")))
8346
              (clobber (reg:SI 1))
8347
              (clobber (reg:SI 2))
8348
              (clobber (reg:SI 4))
8349
              (use (reg:SI 19))
8350
              (use (const_int 1))])]
8351
  "!TARGET_64BIT && reload_completed"
8352
  [(parallel [(set (match_dup 0)
8353
                   (call (mem:SI (reg:SI 22))
8354
                         (match_dup 1)))
8355
              (clobber (reg:SI 1))
8356
              (clobber (reg:SI 2))
8357
              (use (reg:SI 19))
8358
              (use (const_int 1))])]
8359
  "")
8360
 
8361
(define_insn "*call_val_reg_pic_post_reload"
8362
  [(set (match_operand 0 "" "")
8363
        (call (mem:SI (reg:SI 22))
8364
              (match_operand 1 "" "i")))
8365
   (clobber (reg:SI 1))
8366
   (clobber (reg:SI 2))
8367
   (use (reg:SI 19))
8368
   (use (const_int 1))]
8369
  "!TARGET_64BIT"
8370
  "*
8371
{
8372
  return output_indirect_call (insn, gen_rtx_REG (word_mode, 22));
8373
}"
8374
  [(set_attr "type" "dyncall")
8375
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
8376
 
8377
;; This pattern is split if it is necessary to save and restore the
8378
;; PIC register.
8379
(define_insn "call_val_reg_64bit"
8380
  [(set (match_operand 0 "" "")
8381
        (call (mem:SI (match_operand:DI 1 "register_operand" "r"))
8382
              (match_operand 2 "" "i")))
8383
   (clobber (reg:DI 2))
8384
   (clobber (reg:DI 4))
8385
   (use (reg:DI 27))
8386
   (use (reg:DI 29))
8387
   (use (const_int 1))]
8388
  "TARGET_64BIT"
8389
  "*
8390
{
8391
  return output_indirect_call (insn, operands[1]);
8392
}"
8393
  [(set_attr "type" "dyncall")
8394
   (set (attr "length")
8395
        (plus (symbol_ref "attr_length_indirect_call (insn)")
8396
              (symbol_ref "attr_length_save_restore_dltp (insn)")))])
8397
 
8398
;; Split out the PIC register save and restore after reload.  This is
8399
;; done only if the function returns.  As the split is done after reload,
8400
;; there are some situations in which we unnecessarily save and restore
8401
;; %r4.  This happens when there is a single call and the PIC register
8402
;; is "dead" after the call.  This isn't easy to fix as the usage of
8403
;; the PIC register isn't completely determined until the reload pass.
8404
(define_split
8405
  [(parallel [(set (match_operand 0 "" "")
8406
                   (call (mem:SI (match_operand:DI 1 "register_operand" ""))
8407
                         (match_operand 2 "" "")))
8408
              (clobber (reg:DI 2))
8409
              (clobber (reg:DI 4))
8410
              (use (reg:DI 27))
8411
              (use (reg:DI 29))
8412
              (use (const_int 1))])]
8413
  "TARGET_64BIT
8414
   && reload_completed
8415
   && !find_reg_note (insn, REG_NORETURN, NULL_RTX)"
8416
  [(set (reg:DI 4) (reg:DI 27))
8417
   (parallel [(set (match_dup 0)
8418
                   (call (mem:SI (match_dup 1))
8419
                         (match_dup 2)))
8420
              (clobber (reg:DI 2))
8421
              (use (reg:DI 27))
8422
              (use (reg:DI 29))
8423
              (use (const_int 1))])
8424
   (set (reg:DI 27) (reg:DI 4))]
8425
  "")
8426
 
8427
;; Remove the clobber of register 4 when optimizing.  This has to be
8428
;; done with a peephole optimization rather than a split because the
8429
;; split sequence for a call must be longer than one instruction.
8430
(define_peephole2
8431
  [(parallel [(set (match_operand 0 "" "")
8432
                   (call (mem:SI (match_operand:DI 1 "register_operand" ""))
8433
                         (match_operand 2 "" "")))
8434
              (clobber (reg:DI 2))
8435
              (clobber (reg:DI 4))
8436
              (use (reg:DI 27))
8437
              (use (reg:DI 29))
8438
              (use (const_int 1))])]
8439
  "TARGET_64BIT && reload_completed"
8440
  [(parallel [(set (match_dup 0)
8441
                   (call (mem:SI (match_dup 1))
8442
                         (match_dup 2)))
8443
              (clobber (reg:DI 2))
8444
              (use (reg:DI 27))
8445
              (use (reg:DI 29))
8446
              (use (const_int 1))])]
8447
  "")
8448
 
8449
(define_insn "*call_val_reg_64bit_post_reload"
8450
  [(set (match_operand 0 "" "")
8451
        (call (mem:SI (match_operand:DI 1 "register_operand" "r"))
8452
              (match_operand 2 "" "i")))
8453
   (clobber (reg:DI 2))
8454
   (use (reg:DI 27))
8455
   (use (reg:DI 29))
8456
   (use (const_int 1))]
8457
  "TARGET_64BIT"
8458
  "*
8459
{
8460
  return output_indirect_call (insn, operands[1]);
8461
}"
8462
  [(set_attr "type" "dyncall")
8463
   (set (attr "length") (symbol_ref "attr_length_indirect_call (insn)"))])
8464
 
8465
;; Call subroutine returning any type.
8466
 
8467
(define_expand "untyped_call"
8468
  [(parallel [(call (match_operand 0 "" "")
8469
                    (const_int 0))
8470
              (match_operand 1 "" "")
8471
              (match_operand 2 "" "")])]
8472
  ""
8473
  "
8474
{
8475
  int i;
8476
 
8477
  emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
8478
 
8479
  for (i = 0; i < XVECLEN (operands[2], 0); i++)
8480
    {
8481
      rtx set = XVECEXP (operands[2], 0, i);
8482
      emit_move_insn (SET_DEST (set), SET_SRC (set));
8483
    }
8484
 
8485
  /* The optimizer does not know that the call sets the function value
8486
     registers we stored in the result block.  We avoid problems by
8487
     claiming that all hard registers are used and clobbered at this
8488
     point.  */
8489
  emit_insn (gen_blockage ());
8490
 
8491
  DONE;
8492
}")
8493
 
8494
(define_expand "sibcall"
8495
  [(call (match_operand:SI 0 "" "")
8496
         (match_operand 1 "" ""))]
8497
  "!TARGET_PORTABLE_RUNTIME"
8498
  "
8499
{
8500
  rtx op, call_insn;
8501
  rtx nb = operands[1];
8502
 
8503
  op = XEXP (operands[0], 0);
8504
 
8505
  if (TARGET_64BIT)
8506
    {
8507
      if (!virtuals_instantiated)
8508
        emit_move_insn (arg_pointer_rtx,
8509
                        gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
8510
                                      GEN_INT (64)));
8511
      else
8512
        {
8513
          /* The loop pass can generate new libcalls after the virtual
8514
             registers are instantiated when fpregs are disabled because
8515
             the only method that we have for doing DImode multiplication
8516
             is with a libcall.  This could be trouble if we haven't
8517
             allocated enough space for the outgoing arguments.  */
8518
          gcc_assert (INTVAL (nb) <= current_function_outgoing_args_size);
8519
 
8520
          emit_move_insn (arg_pointer_rtx,
8521
                          gen_rtx_PLUS (word_mode, stack_pointer_rtx,
8522
                                        GEN_INT (STACK_POINTER_OFFSET + 64)));
8523
        }
8524
    }
8525
 
8526
  /* Indirect sibling calls are not allowed.  */
8527
  if (TARGET_64BIT)
8528
    call_insn = gen_sibcall_internal_symref_64bit (op, operands[1]);
8529
  else
8530
    call_insn = gen_sibcall_internal_symref (op, operands[1]);
8531
 
8532
  call_insn = emit_call_insn (call_insn);
8533
 
8534
  if (TARGET_64BIT)
8535
    use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
8536
 
8537
  /* We don't have to restore the PIC register.  */
8538
  if (flag_pic)
8539
    use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
8540
 
8541
  DONE;
8542
}")
8543
 
8544
(define_insn "sibcall_internal_symref"
8545
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
8546
         (match_operand 1 "" "i"))
8547
   (clobber (reg:SI 1))
8548
   (use (reg:SI 2))
8549
   (use (const_int 0))]
8550
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8551
  "*
8552
{
8553
  output_arg_descriptor (insn);
8554
  return output_call (insn, operands[0], 1);
8555
}"
8556
  [(set_attr "type" "call")
8557
   (set (attr "length") (symbol_ref "attr_length_call (insn, 1)"))])
8558
 
8559
(define_insn "sibcall_internal_symref_64bit"
8560
  [(call (mem:SI (match_operand 0 "call_operand_address" ""))
8561
         (match_operand 1 "" "i"))
8562
   (clobber (reg:DI 1))
8563
   (use (reg:DI 2))
8564
   (use (const_int 0))]
8565
  "TARGET_64BIT"
8566
  "*
8567
{
8568
  output_arg_descriptor (insn);
8569
  return output_call (insn, operands[0], 1);
8570
}"
8571
  [(set_attr "type" "call")
8572
   (set (attr "length") (symbol_ref "attr_length_call (insn, 1)"))])
8573
 
8574
(define_expand "sibcall_value"
8575
  [(set (match_operand 0 "" "")
8576
                   (call (match_operand:SI 1 "" "")
8577
                         (match_operand 2 "" "")))]
8578
  "!TARGET_PORTABLE_RUNTIME"
8579
  "
8580
{
8581
  rtx op, call_insn;
8582
  rtx nb = operands[1];
8583
 
8584
  op = XEXP (operands[1], 0);
8585
 
8586
  if (TARGET_64BIT)
8587
    {
8588
      if (!virtuals_instantiated)
8589
        emit_move_insn (arg_pointer_rtx,
8590
                        gen_rtx_PLUS (word_mode, virtual_outgoing_args_rtx,
8591
                                      GEN_INT (64)));
8592
      else
8593
        {
8594
          /* The loop pass can generate new libcalls after the virtual
8595
             registers are instantiated when fpregs are disabled because
8596
             the only method that we have for doing DImode multiplication
8597
             is with a libcall.  This could be trouble if we haven't
8598
             allocated enough space for the outgoing arguments.  */
8599
          gcc_assert (INTVAL (nb) <= current_function_outgoing_args_size);
8600
 
8601
          emit_move_insn (arg_pointer_rtx,
8602
                          gen_rtx_PLUS (word_mode, stack_pointer_rtx,
8603
                                        GEN_INT (STACK_POINTER_OFFSET + 64)));
8604
        }
8605
    }
8606
 
8607
  /* Indirect sibling calls are not allowed.  */
8608
  if (TARGET_64BIT)
8609
    call_insn
8610
      = gen_sibcall_value_internal_symref_64bit (operands[0], op, operands[2]);
8611
  else
8612
    call_insn
8613
      = gen_sibcall_value_internal_symref (operands[0], op, operands[2]);
8614
 
8615
  call_insn = emit_call_insn (call_insn);
8616
 
8617
  if (TARGET_64BIT)
8618
    use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), arg_pointer_rtx);
8619
 
8620
  /* We don't have to restore the PIC register.  */
8621
  if (flag_pic)
8622
    use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn), pic_offset_table_rtx);
8623
 
8624
  DONE;
8625
}")
8626
 
8627
(define_insn "sibcall_value_internal_symref"
8628
  [(set (match_operand 0 "" "")
8629
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8630
              (match_operand 2 "" "i")))
8631
   (clobber (reg:SI 1))
8632
   (use (reg:SI 2))
8633
   (use (const_int 0))]
8634
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
8635
  "*
8636
{
8637
  output_arg_descriptor (insn);
8638
  return output_call (insn, operands[1], 1);
8639
}"
8640
  [(set_attr "type" "call")
8641
   (set (attr "length") (symbol_ref "attr_length_call (insn, 1)"))])
8642
 
8643
(define_insn "sibcall_value_internal_symref_64bit"
8644
  [(set (match_operand 0 "" "")
8645
        (call (mem:SI (match_operand 1 "call_operand_address" ""))
8646
              (match_operand 2 "" "i")))
8647
   (clobber (reg:DI 1))
8648
   (use (reg:DI 2))
8649
   (use (const_int 0))]
8650
  "TARGET_64BIT"
8651
  "*
8652
{
8653
  output_arg_descriptor (insn);
8654
  return output_call (insn, operands[1], 1);
8655
}"
8656
  [(set_attr "type" "call")
8657
   (set (attr "length") (symbol_ref "attr_length_call (insn, 1)"))])
8658
 
8659
(define_insn "nop"
8660
  [(const_int 0)]
8661
  ""
8662
  "nop"
8663
  [(set_attr "type" "move")
8664
   (set_attr "length" "4")])
8665
 
8666
;; These are just placeholders so we know where branch tables
8667
;; begin and end.
8668
(define_insn "begin_brtab"
8669
  [(const_int 1)]
8670
  ""
8671
  "*
8672
{
8673
  /* Only GAS actually supports this pseudo-op.  */
8674
  if (TARGET_GAS)
8675
    return \".begin_brtab\";
8676
  else
8677
    return \"\";
8678
}"
8679
  [(set_attr "type" "move")
8680
   (set_attr "length" "0")])
8681
 
8682
(define_insn "end_brtab"
8683
  [(const_int 2)]
8684
  ""
8685
  "*
8686
{
8687
  /* Only GAS actually supports this pseudo-op.  */
8688
  if (TARGET_GAS)
8689
    return \".end_brtab\";
8690
  else
8691
    return \"\";
8692
}"
8693
  [(set_attr "type" "move")
8694
   (set_attr "length" "0")])
8695
 
8696
;;; EH does longjmp's from and within the data section.  Thus,
8697
;;; an interspace branch is required for the longjmp implementation.
8698
;;; Registers r1 and r2 are used as scratch registers for the jump
8699
;;; when necessary.
8700
(define_expand "interspace_jump"
8701
  [(parallel
8702
     [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8703
      (clobber (match_dup 1))])]
8704
  ""
8705
  "
8706
{
8707
  operands[1] = gen_rtx_REG (word_mode, 2);
8708
}")
8709
 
8710
(define_insn ""
8711
  [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8712
  (clobber (reg:SI 2))]
8713
  "TARGET_PA_20 && !TARGET_64BIT"
8714
  "bve%* (%0)"
8715
   [(set_attr "type" "branch")
8716
    (set_attr "length" "4")])
8717
 
8718
(define_insn ""
8719
  [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8720
  (clobber (reg:SI 2))]
8721
  "TARGET_NO_SPACE_REGS && !TARGET_64BIT"
8722
  "be%* 0(%%sr4,%0)"
8723
   [(set_attr "type" "branch")
8724
    (set_attr "length" "4")])
8725
 
8726
(define_insn ""
8727
  [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8728
  (clobber (reg:SI 2))]
8729
  "!TARGET_64BIT"
8730
  "ldsid (%%sr0,%0),%%r2\;mtsp %%r2,%%sr0\;be%* 0(%%sr0,%0)"
8731
   [(set_attr "type" "branch")
8732
    (set_attr "length" "12")])
8733
 
8734
(define_insn ""
8735
  [(set (pc) (match_operand 0 "pmode_register_operand" "a"))
8736
  (clobber (reg:DI 2))]
8737
  "TARGET_64BIT"
8738
  "bve%* (%0)"
8739
   [(set_attr "type" "branch")
8740
    (set_attr "length" "4")])
8741
 
8742
(define_expand "builtin_longjmp"
8743
  [(unspec_volatile [(match_operand 0 "register_operand" "r")] UNSPECV_LONGJMP)]
8744
  ""
8745
  "
8746
{
8747
  /* The elements of the buffer are, in order:  */
8748
  rtx fp = gen_rtx_MEM (Pmode, operands[0]);
8749
  rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0],
8750
                         POINTER_SIZE / BITS_PER_UNIT));
8751
  rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0],
8752
                           (POINTER_SIZE * 2) / BITS_PER_UNIT));
8753
  rtx pv = gen_rtx_REG (Pmode, 1);
8754
 
8755
  emit_insn (gen_rtx_CLOBBER (VOIDmode,
8756
                              gen_rtx_MEM (BLKmode,
8757
                                           gen_rtx_SCRATCH (VOIDmode))));
8758
  emit_insn (gen_rtx_CLOBBER (VOIDmode,
8759
                              gen_rtx_MEM (BLKmode,
8760
                                           hard_frame_pointer_rtx)));
8761
 
8762
  /* Restore the frame pointer.  The virtual_stack_vars_rtx is saved
8763
     instead of the hard_frame_pointer_rtx in the save area.  We need
8764
     to adjust for the offset between these two values when we have
8765
     a nonlocal_goto pattern.  When we don't have a nonlocal_goto
8766
     pattern, the receiver performs the adjustment.  */
8767
#ifdef HAVE_nonlocal_goto
8768
  if (HAVE_nonlocal_goto)
8769
    emit_move_insn (virtual_stack_vars_rtx, force_reg (Pmode, fp));
8770
  else
8771
#endif
8772
    emit_move_insn (hard_frame_pointer_rtx, fp);
8773
 
8774
  /* This bit is the same as expand_builtin_longjmp.  */
8775
  emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
8776
  emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
8777
  emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
8778
 
8779
  /* Load the label we are jumping through into r1 so that we know
8780
     where to look for it when we get back to setjmp's function for
8781
     restoring the gp.  */
8782
  emit_move_insn (pv, lab);
8783
 
8784
  /* Prevent the insns above from being scheduled into the delay slot
8785
     of the interspace jump because the space register could change.  */
8786
  emit_insn (gen_blockage ());
8787
 
8788
  emit_jump_insn (gen_interspace_jump (pv));
8789
  emit_barrier ();
8790
  DONE;
8791
}")
8792
 
8793
;;; Operands 2 and 3 are assumed to be CONST_INTs.
8794
(define_expand "extzv"
8795
  [(set (match_operand 0 "register_operand" "")
8796
        (zero_extract (match_operand 1 "register_operand" "")
8797
                      (match_operand 2 "uint32_operand" "")
8798
                      (match_operand 3 "uint32_operand" "")))]
8799
  ""
8800
  "
8801
{
8802
  HOST_WIDE_INT len = INTVAL (operands[2]);
8803
  HOST_WIDE_INT pos = INTVAL (operands[3]);
8804
 
8805
  /* PA extraction insns don't support zero length bitfields or fields
8806
     extending beyond the left or right-most bits.  Also, we reject lengths
8807
     equal to a word as they are better handled by the move patterns.  */
8808
  if (len <= 0 || len >= BITS_PER_WORD || pos < 0 || pos + len > BITS_PER_WORD)
8809
    FAIL;
8810
 
8811
  /* From mips.md: extract_bit_field doesn't verify that our source
8812
     matches the predicate, so check it again here.  */
8813
  if (!register_operand (operands[1], VOIDmode))
8814
    FAIL;
8815
 
8816
  if (TARGET_64BIT)
8817
    emit_insn (gen_extzv_64 (operands[0], operands[1],
8818
                             operands[2], operands[3]));
8819
  else
8820
    emit_insn (gen_extzv_32 (operands[0], operands[1],
8821
                             operands[2], operands[3]));
8822
  DONE;
8823
}")
8824
 
8825
(define_insn "extzv_32"
8826
  [(set (match_operand:SI 0 "register_operand" "=r")
8827
        (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
8828
                         (match_operand:SI 2 "uint5_operand" "")
8829
                         (match_operand:SI 3 "uint5_operand" "")))]
8830
  ""
8831
  "{extru|extrw,u} %1,%3+%2-1,%2,%0"
8832
  [(set_attr "type" "shift")
8833
   (set_attr "length" "4")])
8834
 
8835
(define_insn ""
8836
  [(set (match_operand:SI 0 "register_operand" "=r")
8837
        (zero_extract:SI (match_operand:SI 1 "register_operand" "r")
8838
                         (const_int 1)
8839
                         (match_operand:SI 2 "register_operand" "q")))]
8840
  ""
8841
  "{vextru %1,1,%0|extrw,u %1,%%sar,1,%0}"
8842
  [(set_attr "type" "shift")
8843
   (set_attr "length" "4")])
8844
 
8845
(define_insn "extzv_64"
8846
  [(set (match_operand:DI 0 "register_operand" "=r")
8847
        (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
8848
                         (match_operand:DI 2 "uint32_operand" "")
8849
                         (match_operand:DI 3 "uint32_operand" "")))]
8850
  "TARGET_64BIT"
8851
  "extrd,u %1,%3+%2-1,%2,%0"
8852
  [(set_attr "type" "shift")
8853
   (set_attr "length" "4")])
8854
 
8855
(define_insn ""
8856
  [(set (match_operand:DI 0 "register_operand" "=r")
8857
        (zero_extract:DI (match_operand:DI 1 "register_operand" "r")
8858
                         (const_int 1)
8859
                         (match_operand:DI 2 "register_operand" "q")))]
8860
  "TARGET_64BIT"
8861
  "extrd,u %1,%%sar,1,%0"
8862
  [(set_attr "type" "shift")
8863
   (set_attr "length" "4")])
8864
 
8865
;;; Operands 2 and 3 are assumed to be CONST_INTs.
8866
(define_expand "extv"
8867
  [(set (match_operand 0 "register_operand" "")
8868
        (sign_extract (match_operand 1 "register_operand" "")
8869
                      (match_operand 2 "uint32_operand" "")
8870
                      (match_operand 3 "uint32_operand" "")))]
8871
  ""
8872
  "
8873
{
8874
  HOST_WIDE_INT len = INTVAL (operands[2]);
8875
  HOST_WIDE_INT pos = INTVAL (operands[3]);
8876
 
8877
  /* PA extraction insns don't support zero length bitfields or fields
8878
     extending beyond the left or right-most bits.  Also, we reject lengths
8879
     equal to a word as they are better handled by the move patterns.  */
8880
  if (len <= 0 || len >= BITS_PER_WORD || pos < 0 || pos + len > BITS_PER_WORD)
8881
    FAIL;
8882
 
8883
  /* From mips.md: extract_bit_field doesn't verify that our source
8884
     matches the predicate, so check it again here.  */
8885
  if (!register_operand (operands[1], VOIDmode))
8886
    FAIL;
8887
 
8888
  if (TARGET_64BIT)
8889
    emit_insn (gen_extv_64 (operands[0], operands[1],
8890
                            operands[2], operands[3]));
8891
  else
8892
    emit_insn (gen_extv_32 (operands[0], operands[1],
8893
                            operands[2], operands[3]));
8894
  DONE;
8895
}")
8896
 
8897
(define_insn "extv_32"
8898
  [(set (match_operand:SI 0 "register_operand" "=r")
8899
        (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
8900
                         (match_operand:SI 2 "uint5_operand" "")
8901
                         (match_operand:SI 3 "uint5_operand" "")))]
8902
  ""
8903
  "{extrs|extrw,s} %1,%3+%2-1,%2,%0"
8904
  [(set_attr "type" "shift")
8905
   (set_attr "length" "4")])
8906
 
8907
(define_insn ""
8908
  [(set (match_operand:SI 0 "register_operand" "=r")
8909
        (sign_extract:SI (match_operand:SI 1 "register_operand" "r")
8910
                         (const_int 1)
8911
                         (match_operand:SI 2 "register_operand" "q")))]
8912
  "!TARGET_64BIT"
8913
  "{vextrs %1,1,%0|extrw,s %1,%%sar,1,%0}"
8914
  [(set_attr "type" "shift")
8915
   (set_attr "length" "4")])
8916
 
8917
(define_insn "extv_64"
8918
  [(set (match_operand:DI 0 "register_operand" "=r")
8919
        (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
8920
                         (match_operand:DI 2 "uint32_operand" "")
8921
                         (match_operand:DI 3 "uint32_operand" "")))]
8922
  "TARGET_64BIT"
8923
  "extrd,s %1,%3+%2-1,%2,%0"
8924
  [(set_attr "type" "shift")
8925
   (set_attr "length" "4")])
8926
 
8927
(define_insn ""
8928
  [(set (match_operand:DI 0 "register_operand" "=r")
8929
        (sign_extract:DI (match_operand:DI 1 "register_operand" "r")
8930
                         (const_int 1)
8931
                         (match_operand:DI 2 "register_operand" "q")))]
8932
  "TARGET_64BIT"
8933
  "extrd,s %1,%%sar,1,%0"
8934
  [(set_attr "type" "shift")
8935
   (set_attr "length" "4")])
8936
 
8937
;;; Operands 1 and 2 are assumed to be CONST_INTs.
8938
(define_expand "insv"
8939
  [(set (zero_extract (match_operand 0 "register_operand" "")
8940
                      (match_operand 1 "uint32_operand" "")
8941
                      (match_operand 2 "uint32_operand" ""))
8942
        (match_operand 3 "arith5_operand" ""))]
8943
  ""
8944
  "
8945
{
8946
  HOST_WIDE_INT len = INTVAL (operands[1]);
8947
  HOST_WIDE_INT pos = INTVAL (operands[2]);
8948
 
8949
  /* PA insertion insns don't support zero length bitfields or fields
8950
     extending beyond the left or right-most bits.  Also, we reject lengths
8951
     equal to a word as they are better handled by the move patterns.  */
8952
  if (len <= 0 || len >= BITS_PER_WORD || pos < 0 || pos + len > BITS_PER_WORD)
8953
    FAIL;
8954
 
8955
  /* From mips.md: insert_bit_field doesn't verify that our destination
8956
     matches the predicate, so check it again here.  */
8957
  if (!register_operand (operands[0], VOIDmode))
8958
    FAIL;
8959
 
8960
  if (TARGET_64BIT)
8961
    emit_insn (gen_insv_64 (operands[0], operands[1],
8962
                            operands[2], operands[3]));
8963
  else
8964
    emit_insn (gen_insv_32 (operands[0], operands[1],
8965
                            operands[2], operands[3]));
8966
  DONE;
8967
}")
8968
 
8969
(define_insn "insv_32"
8970
  [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r,r")
8971
                         (match_operand:SI 1 "uint5_operand" "")
8972
                         (match_operand:SI 2 "uint5_operand" ""))
8973
        (match_operand:SI 3 "arith5_operand" "r,L"))]
8974
  ""
8975
  "@
8976
   {dep|depw} %3,%2+%1-1,%1,%0
8977
   {depi|depwi} %3,%2+%1-1,%1,%0"
8978
  [(set_attr "type" "shift,shift")
8979
   (set_attr "length" "4,4")])
8980
 
8981
;; Optimize insertion of const_int values of type 1...1xxxx.
8982
(define_insn ""
8983
  [(set (zero_extract:SI (match_operand:SI 0 "register_operand" "+r")
8984
                         (match_operand:SI 1 "uint5_operand" "")
8985
                         (match_operand:SI 2 "uint5_operand" ""))
8986
        (match_operand:SI 3 "const_int_operand" ""))]
8987
  "(INTVAL (operands[3]) & 0x10) != 0 &&
8988
   (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
8989
  "*
8990
{
8991
  operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
8992
  return \"{depi|depwi} %3,%2+%1-1,%1,%0\";
8993
}"
8994
  [(set_attr "type" "shift")
8995
   (set_attr "length" "4")])
8996
 
8997
(define_insn "insv_64"
8998
  [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r,r")
8999
                         (match_operand:DI 1 "uint32_operand" "")
9000
                         (match_operand:DI 2 "uint32_operand" ""))
9001
        (match_operand:DI 3 "arith32_operand" "r,L"))]
9002
  "TARGET_64BIT"
9003
  "@
9004
   depd %3,%2+%1-1,%1,%0
9005
   depdi %3,%2+%1-1,%1,%0"
9006
  [(set_attr "type" "shift,shift")
9007
   (set_attr "length" "4,4")])
9008
 
9009
;; Optimize insertion of const_int values of type 1...1xxxx.
9010
(define_insn ""
9011
  [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
9012
                         (match_operand:DI 1 "uint32_operand" "")
9013
                         (match_operand:DI 2 "uint32_operand" ""))
9014
        (match_operand:DI 3 "const_int_operand" ""))]
9015
  "(INTVAL (operands[3]) & 0x10) != 0
9016
   && TARGET_64BIT
9017
   && (~INTVAL (operands[3]) & ((1L << INTVAL (operands[1])) - 1) & ~0xf) == 0"
9018
  "*
9019
{
9020
  operands[3] = GEN_INT ((INTVAL (operands[3]) & 0xf) - 0x10);
9021
  return \"depdi %3,%2+%1-1,%1,%0\";
9022
}"
9023
  [(set_attr "type" "shift")
9024
   (set_attr "length" "4")])
9025
 
9026
(define_insn ""
9027
  [(set (match_operand:DI 0 "register_operand" "=r")
9028
        (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
9029
                   (const_int 32)))]
9030
  "TARGET_64BIT"
9031
  "depd,z %1,31,32,%0"
9032
  [(set_attr "type" "shift")
9033
   (set_attr "length" "4")])
9034
 
9035
;; This insn is used for some loop tests, typically loops reversed when
9036
;; strength reduction is used.  It is actually created when the instruction
9037
;; combination phase combines the special loop test.  Since this insn
9038
;; is both a jump insn and has an output, it must deal with its own
9039
;; reloads, hence the `m' constraints.  The `!' constraints direct reload
9040
;; to not choose the register alternatives in the event a reload is needed.
9041
(define_insn "decrement_and_branch_until_zero"
9042
  [(set (pc)
9043
        (if_then_else
9044
          (match_operator 2 "comparison_operator"
9045
           [(plus:SI
9046
              (match_operand:SI 0 "reg_before_reload_operand" "+!r,!*f,*m")
9047
              (match_operand:SI 1 "int5_operand" "L,L,L"))
9048
            (const_int 0)])
9049
          (label_ref (match_operand 3 "" ""))
9050
          (pc)))
9051
   (set (match_dup 0)
9052
        (plus:SI (match_dup 0) (match_dup 1)))
9053
   (clobber (match_scratch:SI 4 "=X,r,r"))]
9054
  ""
9055
  "* return output_dbra (operands, insn, which_alternative); "
9056
;; Do not expect to understand this the first time through.
9057
[(set_attr "type" "cbranch,multi,multi")
9058
 (set (attr "length")
9059
      (if_then_else (eq_attr "alternative" "0")
9060
;; Loop counter in register case
9061
;; Short branch has length of 4
9062
;; Long branch has length of 8, 20, 24 or 28
9063
        (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9064
               (const_int MAX_12BIT_OFFSET))
9065
           (const_int 4)
9066
           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9067
               (const_int MAX_17BIT_OFFSET))
9068
           (const_int 8)
9069
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9070
           (const_int 24)
9071
           (eq (symbol_ref "flag_pic") (const_int 0))
9072
           (const_int 20)]
9073
          (const_int 28))
9074
 
9075
;; Loop counter in FP reg case.
9076
;; Extra goo to deal with additional reload insns.
9077
        (if_then_else (eq_attr "alternative" "1")
9078
          (if_then_else (lt (match_dup 3) (pc))
9079
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 24))))
9080
                      (const_int MAX_12BIT_OFFSET))
9081
                    (const_int 24)
9082
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 24))))
9083
                      (const_int MAX_17BIT_OFFSET))
9084
                    (const_int 28)
9085
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9086
                    (const_int 44)
9087
                    (eq (symbol_ref "flag_pic") (const_int 0))
9088
                    (const_int 40)]
9089
                  (const_int 48))
9090
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9091
                      (const_int MAX_12BIT_OFFSET))
9092
                    (const_int 24)
9093
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9094
                      (const_int MAX_17BIT_OFFSET))
9095
                    (const_int 28)
9096
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9097
                    (const_int 44)
9098
                    (eq (symbol_ref "flag_pic") (const_int 0))
9099
                    (const_int 40)]
9100
                  (const_int 48)))
9101
 
9102
;; Loop counter in memory case.
9103
;; Extra goo to deal with additional reload insns.
9104
        (if_then_else (lt (match_dup 3) (pc))
9105
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9106
                      (const_int MAX_12BIT_OFFSET))
9107
                    (const_int 12)
9108
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9109
                      (const_int MAX_17BIT_OFFSET))
9110
                    (const_int 16)
9111
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9112
                    (const_int 32)
9113
                    (eq (symbol_ref "flag_pic") (const_int 0))
9114
                    (const_int 28)]
9115
                  (const_int 36))
9116
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9117
                      (const_int MAX_12BIT_OFFSET))
9118
                    (const_int 12)
9119
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9120
                      (const_int MAX_17BIT_OFFSET))
9121
                    (const_int 16)
9122
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9123
                    (const_int 32)
9124
                    (eq (symbol_ref "flag_pic") (const_int 0))
9125
                    (const_int 28)]
9126
                  (const_int 36))))))])
9127
 
9128
(define_insn ""
9129
  [(set (pc)
9130
        (if_then_else
9131
          (match_operator 2 "movb_comparison_operator"
9132
           [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
9133
          (label_ref (match_operand 3 "" ""))
9134
          (pc)))
9135
   (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*m,!*q")
9136
        (match_dup 1))]
9137
  ""
9138
"* return output_movb (operands, insn, which_alternative, 0); "
9139
;; Do not expect to understand this the first time through.
9140
[(set_attr "type" "cbranch,multi,multi,multi")
9141
 (set (attr "length")
9142
      (if_then_else (eq_attr "alternative" "0")
9143
;; Loop counter in register case
9144
;; Short branch has length of 4
9145
;; Long branch has length of 8, 20, 24 or 28
9146
        (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9147
               (const_int MAX_12BIT_OFFSET))
9148
           (const_int 4)
9149
           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9150
               (const_int MAX_17BIT_OFFSET))
9151
           (const_int 8)
9152
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9153
           (const_int 24)
9154
           (eq (symbol_ref "flag_pic") (const_int 0))
9155
           (const_int 20)]
9156
          (const_int 28))
9157
 
9158
;; Loop counter in FP reg case.
9159
;; Extra goo to deal with additional reload insns.
9160
        (if_then_else (eq_attr "alternative" "1")
9161
          (if_then_else (lt (match_dup 3) (pc))
9162
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9163
                      (const_int MAX_12BIT_OFFSET))
9164
                    (const_int 12)
9165
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9166
                      (const_int MAX_17BIT_OFFSET))
9167
                    (const_int 16)
9168
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9169
                    (const_int 32)
9170
                    (eq (symbol_ref "flag_pic") (const_int 0))
9171
                    (const_int 28)]
9172
                  (const_int 36))
9173
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9174
                      (const_int MAX_12BIT_OFFSET))
9175
                    (const_int 12)
9176
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9177
                      (const_int MAX_17BIT_OFFSET))
9178
                    (const_int 16)
9179
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9180
                    (const_int 32)
9181
                    (eq (symbol_ref "flag_pic") (const_int 0))
9182
                    (const_int 28)]
9183
                  (const_int 36)))
9184
 
9185
;; Loop counter in memory or sar case.
9186
;; Extra goo to deal with additional reload insns.
9187
        (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9188
                   (const_int MAX_12BIT_OFFSET))
9189
                (const_int 8)
9190
                (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9191
                  (const_int MAX_17BIT_OFFSET))
9192
                (const_int 12)
9193
                (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9194
                (const_int 28)
9195
                (eq (symbol_ref "flag_pic") (const_int 0))
9196
                (const_int 24)]
9197
              (const_int 32)))))])
9198
 
9199
;; Handle negated branch.
9200
(define_insn ""
9201
  [(set (pc)
9202
        (if_then_else
9203
          (match_operator 2 "movb_comparison_operator"
9204
           [(match_operand:SI 1 "register_operand" "r,r,r,r") (const_int 0)])
9205
          (pc)
9206
          (label_ref (match_operand 3 "" ""))))
9207
   (set (match_operand:SI 0 "reg_before_reload_operand" "=!r,!*f,*m,!*q")
9208
        (match_dup 1))]
9209
  ""
9210
"* return output_movb (operands, insn, which_alternative, 1); "
9211
;; Do not expect to understand this the first time through.
9212
[(set_attr "type" "cbranch,multi,multi,multi")
9213
 (set (attr "length")
9214
      (if_then_else (eq_attr "alternative" "0")
9215
;; Loop counter in register case
9216
;; Short branch has length of 4
9217
;; Long branch has length of 8
9218
        (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9219
               (const_int MAX_12BIT_OFFSET))
9220
           (const_int 4)
9221
           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9222
               (const_int MAX_17BIT_OFFSET))
9223
           (const_int 8)
9224
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9225
           (const_int 24)
9226
           (eq (symbol_ref "flag_pic") (const_int 0))
9227
           (const_int 20)]
9228
          (const_int 28))
9229
 
9230
;; Loop counter in FP reg case.
9231
;; Extra goo to deal with additional reload insns.
9232
        (if_then_else (eq_attr "alternative" "1")
9233
          (if_then_else (lt (match_dup 3) (pc))
9234
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9235
                      (const_int MAX_12BIT_OFFSET))
9236
                    (const_int 12)
9237
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 12))))
9238
                      (const_int MAX_17BIT_OFFSET))
9239
                    (const_int 16)
9240
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9241
                    (const_int 32)
9242
                    (eq (symbol_ref "flag_pic") (const_int 0))
9243
                    (const_int 28)]
9244
                  (const_int 36))
9245
             (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9246
                      (const_int MAX_12BIT_OFFSET))
9247
                    (const_int 12)
9248
                    (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9249
                      (const_int MAX_17BIT_OFFSET))
9250
                    (const_int 16)
9251
                    (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9252
                    (const_int 32)
9253
                    (eq (symbol_ref "flag_pic") (const_int 0))
9254
                    (const_int 28)]
9255
                  (const_int 36)))
9256
 
9257
;; Loop counter in memory or SAR case.
9258
;; Extra goo to deal with additional reload insns.
9259
        (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9260
                   (const_int MAX_12BIT_OFFSET))
9261
                (const_int 8)
9262
                (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9263
                  (const_int MAX_17BIT_OFFSET))
9264
                (const_int 12)
9265
                (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9266
                (const_int 28)
9267
                (eq (symbol_ref "flag_pic") (const_int 0))
9268
                (const_int 24)]
9269
              (const_int 32)))))])
9270
 
9271
(define_insn ""
9272
  [(set (pc) (label_ref (match_operand 3 "" "" )))
9273
   (set (match_operand:SI 0 "ireg_operand" "=r")
9274
        (plus:SI (match_operand:SI 1 "ireg_operand" "r")
9275
                 (match_operand:SI 2 "ireg_or_int5_operand" "rL")))]
9276
  "(reload_completed && operands[0] == operands[1]) || operands[0] == operands[2]"
9277
  "*
9278
{
9279
  return output_parallel_addb (operands, insn);
9280
}"
9281
[(set_attr "type" "parallel_branch")
9282
 (set (attr "length")
9283
    (cond [(lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9284
               (const_int MAX_12BIT_OFFSET))
9285
           (const_int 4)
9286
           (lt (abs (minus (match_dup 3) (plus (pc) (const_int 8))))
9287
               (const_int MAX_17BIT_OFFSET))
9288
           (const_int 8)
9289
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9290
           (const_int 24)
9291
           (eq (symbol_ref "flag_pic") (const_int 0))
9292
           (const_int 20)]
9293
          (const_int 28)))])
9294
 
9295
(define_insn ""
9296
  [(set (pc) (label_ref (match_operand 2 "" "" )))
9297
   (set (match_operand:SF 0 "ireg_operand" "=r")
9298
        (match_operand:SF 1 "ireg_or_int5_operand" "rL"))]
9299
  "reload_completed"
9300
  "*
9301
{
9302
  return output_parallel_movb (operands, insn);
9303
}"
9304
[(set_attr "type" "parallel_branch")
9305
 (set (attr "length")
9306
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9307
               (const_int MAX_12BIT_OFFSET))
9308
           (const_int 4)
9309
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9310
               (const_int MAX_17BIT_OFFSET))
9311
           (const_int 8)
9312
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9313
           (const_int 24)
9314
           (eq (symbol_ref "flag_pic") (const_int 0))
9315
           (const_int 20)]
9316
          (const_int 28)))])
9317
 
9318
(define_insn ""
9319
  [(set (pc) (label_ref (match_operand 2 "" "" )))
9320
   (set (match_operand:SI 0 "ireg_operand" "=r")
9321
        (match_operand:SI 1 "ireg_or_int5_operand" "rL"))]
9322
  "reload_completed"
9323
  "*
9324
{
9325
  return output_parallel_movb (operands, insn);
9326
}"
9327
[(set_attr "type" "parallel_branch")
9328
 (set (attr "length")
9329
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9330
               (const_int MAX_12BIT_OFFSET))
9331
           (const_int 4)
9332
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9333
               (const_int MAX_17BIT_OFFSET))
9334
           (const_int 8)
9335
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9336
           (const_int 24)
9337
           (eq (symbol_ref "flag_pic") (const_int 0))
9338
           (const_int 20)]
9339
          (const_int 28)))])
9340
 
9341
(define_insn ""
9342
  [(set (pc) (label_ref (match_operand 2 "" "" )))
9343
   (set (match_operand:HI 0 "ireg_operand" "=r")
9344
        (match_operand:HI 1 "ireg_or_int5_operand" "rL"))]
9345
  "reload_completed"
9346
  "*
9347
{
9348
  return output_parallel_movb (operands, insn);
9349
}"
9350
[(set_attr "type" "parallel_branch")
9351
 (set (attr "length")
9352
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9353
               (const_int MAX_12BIT_OFFSET))
9354
           (const_int 4)
9355
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9356
               (const_int MAX_17BIT_OFFSET))
9357
           (const_int 8)
9358
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9359
           (const_int 24)
9360
           (eq (symbol_ref "flag_pic") (const_int 0))
9361
           (const_int 20)]
9362
          (const_int 28)))])
9363
 
9364
(define_insn ""
9365
  [(set (pc) (label_ref (match_operand 2 "" "" )))
9366
   (set (match_operand:QI 0 "ireg_operand" "=r")
9367
        (match_operand:QI 1 "ireg_or_int5_operand" "rL"))]
9368
  "reload_completed"
9369
  "*
9370
{
9371
  return output_parallel_movb (operands, insn);
9372
}"
9373
[(set_attr "type" "parallel_branch")
9374
 (set (attr "length")
9375
    (cond [(lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9376
               (const_int MAX_12BIT_OFFSET))
9377
           (const_int 4)
9378
           (lt (abs (minus (match_dup 2) (plus (pc) (const_int 8))))
9379
               (const_int MAX_17BIT_OFFSET))
9380
           (const_int 8)
9381
           (ne (symbol_ref "TARGET_PORTABLE_RUNTIME") (const_int 0))
9382
           (const_int 24)
9383
           (eq (symbol_ref "flag_pic") (const_int 0))
9384
           (const_int 20)]
9385
          (const_int 28)))])
9386
 
9387
(define_insn ""
9388
  [(set (match_operand 0 "register_operand" "=f")
9389
        (mult (match_operand 1 "register_operand" "f")
9390
              (match_operand 2 "register_operand" "f")))
9391
   (set (match_operand 3 "register_operand" "+f")
9392
        (plus (match_operand 4 "register_operand" "f")
9393
              (match_operand 5 "register_operand" "f")))]
9394
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9395
   && reload_completed && fmpyaddoperands (operands)"
9396
  "*
9397
{
9398
  if (GET_MODE (operands[0]) == DFmode)
9399
    {
9400
      if (rtx_equal_p (operands[3], operands[5]))
9401
        return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
9402
      else
9403
        return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
9404
    }
9405
  else
9406
    {
9407
      if (rtx_equal_p (operands[3], operands[5]))
9408
        return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
9409
      else
9410
        return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
9411
    }
9412
}"
9413
  [(set_attr "type" "fpalu")
9414
   (set_attr "length" "4")])
9415
 
9416
(define_insn ""
9417
  [(set (match_operand 3 "register_operand" "+f")
9418
        (plus (match_operand 4 "register_operand" "f")
9419
              (match_operand 5 "register_operand" "f")))
9420
   (set (match_operand 0 "register_operand" "=f")
9421
        (mult (match_operand 1 "register_operand" "f")
9422
              (match_operand 2 "register_operand" "f")))]
9423
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9424
   && reload_completed && fmpyaddoperands (operands)"
9425
  "*
9426
{
9427
  if (GET_MODE (operands[0]) == DFmode)
9428
    {
9429
      if (rtx_equal_p (operands[3], operands[5]))
9430
        return \"fmpyadd,dbl %1,%2,%0,%4,%3\";
9431
      else
9432
        return \"fmpyadd,dbl %1,%2,%0,%5,%3\";
9433
    }
9434
  else
9435
    {
9436
      if (rtx_equal_p (operands[3], operands[5]))
9437
        return \"fmpyadd,sgl %1,%2,%0,%4,%3\";
9438
      else
9439
        return \"fmpyadd,sgl %1,%2,%0,%5,%3\";
9440
    }
9441
}"
9442
  [(set_attr "type" "fpalu")
9443
   (set_attr "length" "4")])
9444
 
9445
(define_insn ""
9446
  [(set (match_operand 0 "register_operand" "=f")
9447
        (mult (match_operand 1 "register_operand" "f")
9448
              (match_operand 2 "register_operand" "f")))
9449
   (set (match_operand 3 "register_operand" "+f")
9450
        (minus (match_operand 4 "register_operand" "f")
9451
               (match_operand 5 "register_operand" "f")))]
9452
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9453
   && reload_completed && fmpysuboperands (operands)"
9454
  "*
9455
{
9456
  if (GET_MODE (operands[0]) == DFmode)
9457
    return \"fmpysub,dbl %1,%2,%0,%5,%3\";
9458
  else
9459
    return \"fmpysub,sgl %1,%2,%0,%5,%3\";
9460
}"
9461
  [(set_attr "type" "fpalu")
9462
   (set_attr "length" "4")])
9463
 
9464
(define_insn ""
9465
  [(set (match_operand 3 "register_operand" "+f")
9466
        (minus (match_operand 4 "register_operand" "f")
9467
               (match_operand 5 "register_operand" "f")))
9468
   (set (match_operand 0 "register_operand" "=f")
9469
        (mult (match_operand 1 "register_operand" "f")
9470
              (match_operand 2 "register_operand" "f")))]
9471
  "TARGET_PA_11 && ! TARGET_SOFT_FLOAT
9472
   && reload_completed && fmpysuboperands (operands)"
9473
  "*
9474
{
9475
  if (GET_MODE (operands[0]) == DFmode)
9476
    return \"fmpysub,dbl %1,%2,%0,%5,%3\";
9477
  else
9478
    return \"fmpysub,sgl %1,%2,%0,%5,%3\";
9479
}"
9480
  [(set_attr "type" "fpalu")
9481
   (set_attr "length" "4")])
9482
 
9483
;; Flush the I and D cache lines from the start address (operand0)
9484
;; to the end address (operand1).  No lines are flushed if the end
9485
;; address is less than the start address (unsigned).
9486
;;
9487
;; Because the range of memory flushed is variable and the size of
9488
;; a MEM can only be a CONST_INT, the patterns specify that they
9489
;; perform an unspecified volatile operation on all memory.
9490
;;
9491
;; The address range for an icache flush must lie within a single
9492
;; space on targets with non-equivalent space registers.
9493
;;
9494
;; This is used by the trampoline code for nested functions.
9495
;;
9496
;; Operand 0 contains the start address.
9497
;; Operand 1 contains the end address.
9498
;; Operand 2 contains the line length to use.
9499
;; Operands 3 and 4 (icacheflush) are clobbered scratch registers.
9500
(define_insn "dcacheflush"
9501
  [(const_int 1)
9502
   (unspec_volatile [(mem:BLK (scratch))] UNSPECV_DCACHE)
9503
   (use (match_operand 0 "pmode_register_operand" "r"))
9504
   (use (match_operand 1 "pmode_register_operand" "r"))
9505
   (use (match_operand 2 "pmode_register_operand" "r"))
9506
   (clobber (match_scratch 3 "=&0"))]
9507
  ""
9508
  "*
9509
{
9510
  if (TARGET_64BIT)
9511
    return \"cmpb,*<<=,n %3,%1,.\;fdc,m %2(%3)\;sync\";
9512
  else
9513
    return \"cmpb,<<=,n %3,%1,.\;fdc,m %2(%3)\;sync\";
9514
}"
9515
  [(set_attr "type" "multi")
9516
   (set_attr "length" "12")])
9517
 
9518
(define_insn "icacheflush"
9519
  [(const_int 2)
9520
   (unspec_volatile [(mem:BLK (scratch))] UNSPECV_ICACHE)
9521
   (use (match_operand 0 "pmode_register_operand" "r"))
9522
   (use (match_operand 1 "pmode_register_operand" "r"))
9523
   (use (match_operand 2 "pmode_register_operand" "r"))
9524
   (clobber (match_operand 3 "pmode_register_operand" "=&r"))
9525
   (clobber (match_operand 4 "pmode_register_operand" "=&r"))
9526
   (clobber (match_scratch 5 "=&0"))]
9527
  ""
9528
  "*
9529
{
9530
  if (TARGET_64BIT)
9531
    return \"mfsp %%sr0,%4\;ldsid (%5),%3\;mtsp %3,%%sr0\;cmpb,*<<=,n %5,%1,.\;fic,m %2(%%sr0,%5)\;sync\;mtsp %4,%%sr0\;nop\;nop\;nop\;nop\;nop\;nop\";
9532
  else
9533
    return \"mfsp %%sr0,%4\;ldsid (%5),%3\;mtsp %3,%%sr0\;cmpb,<<=,n %5,%1,.\;fic,m %2(%%sr0,%5)\;sync\;mtsp %4,%%sr0\;nop\;nop\;nop\;nop\;nop\;nop\";
9534
}"
9535
  [(set_attr "type" "multi")
9536
   (set_attr "length" "52")])
9537
 
9538
;; An out-of-line prologue.
9539
(define_insn "outline_prologue_call"
9540
  [(unspec_volatile [(const_int 0)] UNSPECV_OPC)
9541
   (clobber (reg:SI 31))
9542
   (clobber (reg:SI 22))
9543
   (clobber (reg:SI 21))
9544
   (clobber (reg:SI 20))
9545
   (clobber (reg:SI 19))
9546
   (clobber (reg:SI 1))]
9547
  ""
9548
  "*
9549
{
9550
  extern int frame_pointer_needed;
9551
 
9552
  /* We need two different versions depending on whether or not we
9553
     need a frame pointer.   Also note that we return to the instruction
9554
     immediately after the branch rather than two instructions after the
9555
     break as normally is the case.  */
9556
  if (frame_pointer_needed)
9557
    {
9558
      /* Must import the magic millicode routine(s).  */
9559
      output_asm_insn (\".IMPORT __outline_prologue_fp,MILLICODE\", NULL);
9560
 
9561
      if (TARGET_PORTABLE_RUNTIME)
9562
        {
9563
          output_asm_insn (\"ldil L'__outline_prologue_fp,%%r31\", NULL);
9564
          output_asm_insn (\"ble,n R'__outline_prologue_fp(%%sr0,%%r31)\",
9565
                           NULL);
9566
        }
9567
      else
9568
        output_asm_insn (\"{bl|b,l},n __outline_prologue_fp,%%r31\", NULL);
9569
    }
9570
  else
9571
    {
9572
      /* Must import the magic millicode routine(s).  */
9573
      output_asm_insn (\".IMPORT __outline_prologue,MILLICODE\", NULL);
9574
 
9575
      if (TARGET_PORTABLE_RUNTIME)
9576
        {
9577
          output_asm_insn (\"ldil L'__outline_prologue,%%r31\", NULL);
9578
          output_asm_insn (\"ble,n R'__outline_prologue(%%sr0,%%r31)\", NULL);
9579
        }
9580
      else
9581
        output_asm_insn (\"{bl|b,l},n __outline_prologue,%%r31\", NULL);
9582
    }
9583
  return \"\";
9584
}"
9585
  [(set_attr "type" "multi")
9586
   (set_attr "length" "8")])
9587
 
9588
;; An out-of-line epilogue.
9589
(define_insn "outline_epilogue_call"
9590
  [(unspec_volatile [(const_int 1)] UNSPECV_OEC)
9591
   (use (reg:SI 29))
9592
   (use (reg:SI 28))
9593
   (clobber (reg:SI 31))
9594
   (clobber (reg:SI 22))
9595
   (clobber (reg:SI 21))
9596
   (clobber (reg:SI 20))
9597
   (clobber (reg:SI 19))
9598
   (clobber (reg:SI 2))
9599
   (clobber (reg:SI 1))]
9600
  ""
9601
  "*
9602
{
9603
  extern int frame_pointer_needed;
9604
 
9605
  /* We need two different versions depending on whether or not we
9606
     need a frame pointer.   Also note that we return to the instruction
9607
     immediately after the branch rather than two instructions after the
9608
     break as normally is the case.  */
9609
  if (frame_pointer_needed)
9610
    {
9611
      /* Must import the magic millicode routine.  */
9612
      output_asm_insn (\".IMPORT __outline_epilogue_fp,MILLICODE\", NULL);
9613
 
9614
      /* The out-of-line prologue will make sure we return to the right
9615
         instruction.  */
9616
      if (TARGET_PORTABLE_RUNTIME)
9617
        {
9618
          output_asm_insn (\"ldil L'__outline_epilogue_fp,%%r31\", NULL);
9619
          output_asm_insn (\"ble,n R'__outline_epilogue_fp(%%sr0,%%r31)\",
9620
                           NULL);
9621
        }
9622
      else
9623
        output_asm_insn (\"{bl|b,l},n __outline_epilogue_fp,%%r31\", NULL);
9624
    }
9625
  else
9626
    {
9627
      /* Must import the magic millicode routine.  */
9628
      output_asm_insn (\".IMPORT __outline_epilogue,MILLICODE\", NULL);
9629
 
9630
      /* The out-of-line prologue will make sure we return to the right
9631
         instruction.  */
9632
      if (TARGET_PORTABLE_RUNTIME)
9633
        {
9634
          output_asm_insn (\"ldil L'__outline_epilogue,%%r31\", NULL);
9635
          output_asm_insn (\"ble,n R'__outline_epilogue(%%sr0,%%r31)\", NULL);
9636
        }
9637
      else
9638
        output_asm_insn (\"{bl|b,l},n __outline_epilogue,%%r31\", NULL);
9639
    }
9640
  return \"\";
9641
}"
9642
  [(set_attr "type" "multi")
9643
   (set_attr "length" "8")])
9644
 
9645
;; Given a function pointer, canonicalize it so it can be
9646
;; reliably compared to another function pointer.  */
9647
(define_expand "canonicalize_funcptr_for_compare"
9648
  [(set (reg:SI 26) (match_operand:SI 1 "register_operand" ""))
9649
   (parallel [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] UNSPEC_CFFC))
9650
              (clobber (match_dup 2))
9651
              (clobber (reg:SI 26))
9652
              (clobber (reg:SI 22))
9653
              (clobber (reg:SI 31))])
9654
   (set (match_operand:SI 0 "register_operand" "")
9655
        (reg:SI 29))]
9656
  "!TARGET_PORTABLE_RUNTIME && !TARGET_64BIT"
9657
  "
9658
{
9659
  if (TARGET_ELF32)
9660
    {
9661
      rtx canonicalize_funcptr_for_compare_libfunc
9662
        = init_one_libfunc (CANONICALIZE_FUNCPTR_FOR_COMPARE_LIBCALL);
9663
 
9664
      emit_library_call_value (canonicalize_funcptr_for_compare_libfunc,
9665
                               operands[0], LCT_NORMAL, Pmode,
9666
                               1, operands[1], Pmode);
9667
      DONE;
9668
    }
9669
 
9670
  operands[2] = gen_reg_rtx (SImode);
9671
  if (GET_CODE (operands[1]) != REG)
9672
    {
9673
      rtx tmp = gen_reg_rtx (Pmode);
9674
      emit_move_insn (tmp, operands[1]);
9675
      operands[1] = tmp;
9676
    }
9677
}")
9678
 
9679
(define_insn "*$$sh_func_adrs"
9680
  [(set (reg:SI 29) (unspec:SI [(reg:SI 26)] UNSPEC_CFFC))
9681
   (clobber (match_operand:SI 0 "register_operand" "=a"))
9682
   (clobber (reg:SI 26))
9683
   (clobber (reg:SI 22))
9684
   (clobber (reg:SI 31))]
9685
  "!TARGET_64BIT"
9686
  "*
9687
{
9688
  int length = get_attr_length (insn);
9689
  rtx xoperands[2];
9690
 
9691
  xoperands[0] = GEN_INT (length - 8);
9692
  xoperands[1] = GEN_INT (length - 16);
9693
 
9694
  /* Must import the magic millicode routine.  */
9695
  output_asm_insn (\".IMPORT $$sh_func_adrs,MILLICODE\", NULL);
9696
 
9697
  /* This is absolutely amazing.
9698
 
9699
     First, copy our input parameter into %r29 just in case we don't
9700
     need to call $$sh_func_adrs.  */
9701
  output_asm_insn (\"copy %%r26,%%r29\", NULL);
9702
  output_asm_insn (\"{extru|extrw,u} %%r26,31,2,%%r31\", NULL);
9703
 
9704
  /* Next, examine the low two bits in %r26, if they aren't 0x2, then
9705
     we use %r26 unchanged.  */
9706
  output_asm_insn (\"{comib|cmpib},<>,n 2,%%r31,.+%0\", xoperands);
9707
  output_asm_insn (\"ldi 4096,%%r31\", NULL);
9708
 
9709
  /* Next, compare %r26 with 4096, if %r26 is less than or equal to
9710
     4096, then again we use %r26 unchanged.  */
9711
  output_asm_insn (\"{comb|cmpb},<<,n %%r26,%%r31,.+%1\", xoperands);
9712
 
9713
  /* Finally, call $$sh_func_adrs to extract the function's real add24.  */
9714
  return output_millicode_call (insn,
9715
                                gen_rtx_SYMBOL_REF (SImode,
9716
                                                    \"$$sh_func_adrs\"));
9717
}"
9718
  [(set_attr "type" "multi")
9719
   (set (attr "length")
9720
        (plus (symbol_ref "attr_length_millicode_call (insn)")
9721
              (const_int 20)))])
9722
 
9723
;; On the PA, the PIC register is call clobbered, so it must
9724
;; be saved & restored around calls by the caller.  If the call
9725
;; doesn't return normally (nonlocal goto, or an exception is
9726
;; thrown), then the code at the exception handler label must
9727
;; restore the PIC register.
9728
(define_expand "exception_receiver"
9729
  [(const_int 4)]
9730
  "flag_pic"
9731
  "
9732
{
9733
  /* On the 64-bit port, we need a blockage because there is
9734
     confusion regarding the dependence of the restore on the
9735
     frame pointer.  As a result, the frame pointer and pic
9736
     register restores sometimes are interchanged erroneously.  */
9737
  if (TARGET_64BIT)
9738
    emit_insn (gen_blockage ());
9739
  /* Restore the PIC register using hppa_pic_save_rtx ().  The
9740
     PIC register is not saved in the frame in 64-bit ABI.  */
9741
  emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
9742
  emit_insn (gen_blockage ());
9743
  DONE;
9744
}")
9745
 
9746
(define_expand "builtin_setjmp_receiver"
9747
  [(label_ref (match_operand 0 "" ""))]
9748
  "flag_pic"
9749
  "
9750
{
9751
  if (TARGET_64BIT)
9752
    emit_insn (gen_blockage ());
9753
  /* Restore the PIC register.  Hopefully, this will always be from
9754
     a stack slot.  The only registers that are valid after a
9755
     builtin_longjmp are the stack and frame pointers.  */
9756
  emit_move_insn (pic_offset_table_rtx, hppa_pic_save_rtx ());
9757
  emit_insn (gen_blockage ());
9758
  DONE;
9759
}")
9760
 
9761
;; Allocate new stack space and update the saved stack pointer in the
9762
;; frame marker.  The HP C compilers also copy additional words in the
9763
;; frame marker.  The 64-bit compiler copies words at -48, -32 and -24.
9764
;; The 32-bit compiler copies the word at -16 (Static Link).  We
9765
;; currently don't copy these values.
9766
;;
9767
;; Since the copy of the frame marker can't be done atomically, I
9768
;; suspect that using it for unwind purposes may be somewhat unreliable.
9769
;; The HP compilers appear to raise the stack and copy the frame
9770
;; marker in a strict instruction sequence.  This suggests that the
9771
;; unwind library may check for an alloca sequence when ALLOCA_FRAME
9772
;; is set in the callinfo data.  We currently don't set ALLOCA_FRAME
9773
;; as GAS doesn't support it, or try to keep the instructions emitted
9774
;; here in strict sequence.
9775
(define_expand "allocate_stack"
9776
  [(match_operand 0 "" "")
9777
   (match_operand 1 "" "")]
9778
  ""
9779
  "
9780
{
9781
  rtx addr;
9782
 
9783
  /* Since the stack grows upward, we need to store virtual_stack_dynamic_rtx
9784
     in operand 0 before adjusting the stack.  */
9785
  emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
9786
  anti_adjust_stack (operands[1]);
9787
  if (TARGET_HPUX_UNWIND_LIBRARY)
9788
    {
9789
      addr = gen_rtx_PLUS (word_mode, stack_pointer_rtx,
9790
                           GEN_INT (TARGET_64BIT ? -8 : -4));
9791
      emit_move_insn (gen_rtx_MEM (word_mode, addr), frame_pointer_rtx);
9792
    }
9793
  if (!TARGET_64BIT && flag_pic)
9794
    {
9795
      rtx addr = gen_rtx_PLUS (word_mode, stack_pointer_rtx, GEN_INT (-32));
9796
      emit_move_insn (gen_rtx_MEM (word_mode, addr), pic_offset_table_rtx);
9797
    }
9798
  DONE;
9799
}")
9800
 
9801
(define_expand "prefetch"
9802
  [(match_operand 0 "address_operand" "")
9803
   (match_operand 1 "const_int_operand" "")
9804
   (match_operand 2 "const_int_operand" "")]
9805
  "TARGET_PA_20"
9806
{
9807
  int locality = INTVAL (operands[2]);
9808
 
9809
  gcc_assert (locality >= 0 && locality <= 3);
9810
 
9811
  /* Change operand[0] to a MEM as we don't have the infrastructure
9812
     to output all the supported address modes for ldw/ldd when we use
9813
     the address directly.  However, we do have it for MEMs.  */
9814
  operands[0] = gen_rtx_MEM (QImode, operands[0]);
9815
 
9816
  /* If the address isn't valid for the prefetch, replace it.  */
9817
  if (locality)
9818
    {
9819
      if (!prefetch_nocc_operand (operands[0], QImode))
9820
        operands[0]
9821
          = replace_equiv_address (operands[0],
9822
                                   copy_to_mode_reg (Pmode,
9823
                                                     XEXP (operands[0], 0)));
9824
      emit_insn (gen_prefetch_nocc (operands[0], operands[1], operands[2]));
9825
    }
9826
  else
9827
    {
9828
      if (!prefetch_cc_operand (operands[0], QImode))
9829
        operands[0]
9830
          = replace_equiv_address (operands[0],
9831
                                   copy_to_mode_reg (Pmode,
9832
                                                     XEXP (operands[0], 0)));
9833
      emit_insn (gen_prefetch_cc (operands[0], operands[1], operands[2]));
9834
    }
9835
  DONE;
9836
})
9837
 
9838
(define_insn "prefetch_cc"
9839
  [(prefetch (match_operand:QI 0 "prefetch_cc_operand" "RW")
9840
             (match_operand:SI 1 "const_int_operand" "n")
9841
             (match_operand:SI 2 "const_int_operand" "n"))]
9842
  "TARGET_PA_20 && operands[2] == const0_rtx"
9843
{
9844
  /* The SL cache-control completor indicates good spatial locality but
9845
     poor temporal locality.  The ldw instruction with a target of general
9846
     register 0 prefetches a cache line for a read.  The ldd instruction
9847
     prefetches a cache line for a write.  */
9848
  static const char * const instr[2] = {
9849
    "ldw%M0,sl %0,%%r0",
9850
    "ldd%M0,sl %0,%%r0"
9851
  };
9852
  int read_or_write = INTVAL (operands[1]);
9853
 
9854
  gcc_assert (read_or_write >= 0 && read_or_write <= 1);
9855
 
9856
  return instr [read_or_write];
9857
}
9858
  [(set_attr "type" "load")
9859
   (set_attr "length" "4")])
9860
 
9861
(define_insn "prefetch_nocc"
9862
  [(prefetch (match_operand:QI 0 "prefetch_nocc_operand" "A,RQ")
9863
             (match_operand:SI 1 "const_int_operand" "n,n")
9864
             (match_operand:SI 2 "const_int_operand" "n,n"))]
9865
  "TARGET_PA_20 && operands[2] != const0_rtx"
9866
{
9867
  /* The ldw instruction with a target of general register 0 prefetches
9868
     a cache line for a read.  The ldd instruction prefetches a cache line
9869
     for a write.  */
9870
  static const char * const instr[2][2] = {
9871
    {
9872
      "ldw RT'%A0,%%r0",
9873
      "ldd RT'%A0,%%r0",
9874
    },
9875
    {
9876
      "ldw%M0 %0,%%r0",
9877
      "ldd%M0 %0,%%r0",
9878
    }
9879
  };
9880
  int read_or_write = INTVAL (operands[1]);
9881
 
9882
  gcc_assert (which_alternative == 0 || which_alternative == 1);
9883
  gcc_assert (read_or_write >= 0 && read_or_write <= 1);
9884
 
9885
  return instr [which_alternative][read_or_write];
9886
}
9887
  [(set_attr "type" "load")
9888
   (set_attr "length" "4")])
9889
 
9890
 
9891
;; TLS Support
9892
(define_insn "tgd_load"
9893
 [(set (match_operand:SI 0 "register_operand" "=r")
9894
       (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")] UNSPEC_TLSGD))
9895
  (clobber (reg:SI 1))
9896
  (use (reg:SI 27))]
9897
  ""
9898
  "*
9899
{
9900
  return \"addil LR'%1-$tls_gdidx$,%%r27\;ldo RR'%1-$tls_gdidx$(%%r1),%0\";
9901
}"
9902
  [(set_attr "type" "multi")
9903
   (set_attr "length" "8")])
9904
 
9905
(define_insn "tgd_load_pic"
9906
 [(set (match_operand:SI 0 "register_operand" "=r")
9907
       (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")] UNSPEC_TLSGD_PIC))
9908
  (clobber (reg:SI 1))
9909
  (use (reg:SI 19))]
9910
  ""
9911
  "*
9912
{
9913
  return \"addil LT'%1-$tls_gdidx$,%%r19\;ldo RT'%1-$tls_gdidx$(%%r1),%0\";
9914
}"
9915
  [(set_attr "type" "multi")
9916
   (set_attr "length" "8")])
9917
 
9918
(define_insn "tld_load"
9919
 [(set (match_operand:SI 0 "register_operand" "=r")
9920
       (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")] UNSPEC_TLSLDM))
9921
  (clobber (reg:SI 1))
9922
  (use (reg:SI 27))]
9923
  ""
9924
  "*
9925
{
9926
  return \"addil LR'%1-$tls_ldidx$,%%r27\;ldo RR'%1-$tls_ldidx$(%%r1),%0\";
9927
}"
9928
  [(set_attr "type" "multi")
9929
   (set_attr "length" "8")])
9930
 
9931
(define_insn "tld_load_pic"
9932
 [(set (match_operand:SI 0 "register_operand" "=r")
9933
       (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")] UNSPEC_TLSLDM_PIC))
9934
  (clobber (reg:SI 1))
9935
  (use (reg:SI 19))]
9936
  ""
9937
  "*
9938
{
9939
  return \"addil LT'%1-$tls_ldidx$,%%r19\;ldo RT'%1-$tls_ldidx$(%%r1),%0\";
9940
}"
9941
  [(set_attr "type" "multi")
9942
   (set_attr "length" "8")])
9943
 
9944
(define_insn "tld_offset_load"
9945
  [(set (match_operand:SI 0 "register_operand" "=r")
9946
        (plus:SI (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")]
9947
                            UNSPEC_TLSLDO)
9948
                 (match_operand:SI 2 "register_operand" "r")))
9949
   (clobber (reg:SI 1))]
9950
  ""
9951
  "*
9952
{
9953
  return \"addil LR'%1-$tls_dtpoff$,%2\;ldo RR'%1-$tls_dtpoff$(%%r1),%0\";
9954
}"
9955
  [(set_attr "type" "multi")
9956
   (set_attr "length" "8")])
9957
 
9958
(define_insn "tp_load"
9959
  [(set (match_operand:SI 0 "register_operand" "=r")
9960
        (unspec:SI [(const_int 0)] UNSPEC_TP))]
9961
  ""
9962
  "mfctl %%cr27,%0"
9963
  [(set_attr "type" "multi")
9964
   (set_attr "length" "4")])
9965
 
9966
(define_insn "tie_load"
9967
  [(set (match_operand:SI 0 "register_operand" "=r")
9968
        (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")] UNSPEC_TLSIE))
9969
   (clobber (reg:SI 1))
9970
   (use (reg:SI 27))]
9971
  ""
9972
  "*
9973
{
9974
  return \"addil LR'%1-$tls_ieoff$,%%r27\;ldw RR'%1-$tls_ieoff$(%%r1),%0\";
9975
}"
9976
  [(set_attr "type" "multi")
9977
   (set_attr "length" "8")])
9978
 
9979
(define_insn "tie_load_pic"
9980
  [(set (match_operand:SI 0 "register_operand" "=r")
9981
        (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")] UNSPEC_TLSIE_PIC))
9982
   (clobber (reg:SI 1))
9983
   (use (reg:SI 19))]
9984
  ""
9985
  "*
9986
{
9987
  return \"addil LT'%1-$tls_ieoff$,%%r19\;ldw RT'%1-$tls_ieoff$(%%r1),%0\";
9988
}"
9989
  [(set_attr "type" "multi")
9990
   (set_attr "length" "8")])
9991
 
9992
(define_insn "tle_load"
9993
  [(set (match_operand:SI 0 "register_operand" "=r")
9994
        (plus:SI (unspec:SI [(match_operand 1 "tle_symbolic_operand" "")]
9995
                            UNSPEC_TLSLE)
9996
                 (match_operand:SI 2 "register_operand" "r")))
9997
   (clobber (reg:SI 1))]
9998
  ""
9999
  "addil LR'%1-$tls_leoff$,%2\;ldo RR'%1-$tls_leoff$(%%r1),%0"
10000
  [(set_attr "type" "multi")
10001
   (set_attr "length" "8")])

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.