]> gcc.gnu.org Git - gcc.git/blob - gcc/config/rs6000/rs6000.md
Add attribute((longcall)) support
[gcc.git] / gcc / config / rs6000 / rs6000.md
1 ;; Machine description for IBM RISC System 6000 (POWER) for GNU C compiler
2 ;; Copyright (C) 1990, 91, 92, 93, 94, 95, 1996 Free Software Foundation, Inc.
3 ;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
4
5 ;; This file is part of GNU CC.
6
7 ;; GNU CC is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 2, or (at your option)
10 ;; any later version.
11
12 ;; GNU CC is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 ;; GNU General Public License for more details.
16
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GNU CC; see the file COPYING. If not, write to
19 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
20 ;; Boston, MA 02111-1307, USA.
21
22 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
23 \f
24 ;; Define an insn type attribute. This is used in function unit delay
25 ;; computations.
26 (define_attr "type" "integer,load,fpload,imul,idiv,branch,compare,delayed_compare,fpcompare,mtjmpr,fp,dmul,sdiv,ddiv,ssqrt,dsqrt,jmpreg"
27 (const_string "integer"))
28
29 ;; Length (in bytes).
30 (define_attr "length" ""
31 (if_then_else (eq_attr "type" "branch")
32 (if_then_else (and (ge (minus (pc) (match_dup 0))
33 (const_int -32768))
34 (lt (minus (pc) (match_dup 0))
35 (const_int 32767)))
36 (const_int 8)
37 (const_int 12))
38 (const_int 4)))
39
40 ;; Processor type -- this attribute must exactly match the processor_type
41 ;; enumeration in rs6000.h.
42
43 (define_attr "cpu" "rios1,rios2,mpccore,ppc403,ppc601,ppc602,ppc603,ppc604,ppc620"
44 (const (symbol_ref "rs6000_cpu_attr")))
45
46 ; (define_function_unit NAME MULTIPLICITY SIMULTANEITY
47 ; TEST READY-DELAY ISSUE-DELAY [CONFLICT-LIST])
48
49 ; Load/Store Unit -- POWER/2 and pure PowerPC only
50 ; (POWER and 601 use Integer Unit)
51 (define_function_unit "lsu" 1 0
52 (and (eq_attr "type" "load")
53 (eq_attr "cpu" "mpccore,ppc602,ppc603,ppc604,ppc620"))
54 2 1)
55
56 (define_function_unit "lsu" 1 0
57 (and (eq_attr "type" "fpload")
58 (eq_attr "cpu" "ppc604,ppc620"))
59 3 1)
60
61 (define_function_unit "lsu" 1 0
62 (and (eq_attr "type" "fpload")
63 (eq_attr "cpu" "mpccore,ppc602,ppc603"))
64 2 1)
65
66 (define_function_unit "iu" 1 0
67 (and (eq_attr "type" "load")
68 (eq_attr "cpu" "rios1,ppc601,ppc403"))
69 2 1)
70
71 (define_function_unit "iu" 1 0
72 (and (eq_attr "type" "fpload")
73 (eq_attr "cpu" "rios1,ppc601"))
74 2 0)
75
76 ; Integer Unit (RIOS1, PPC601, PPC603)
77 ; Trivial operations take one cycle which need not be listed here.
78 (define_function_unit "iu" 1 0
79 (and (eq_attr "type" "imul")
80 (eq_attr "cpu" "rios1"))
81 3 3)
82
83 (define_function_unit "iu" 1 0
84 (and (eq_attr "type" "imul")
85 (eq_attr "cpu" "ppc403"))
86 4 4)
87
88 (define_function_unit "iu" 1 0
89 (and (eq_attr "type" "imul")
90 (eq_attr "cpu" "ppc601,ppc602,ppc603"))
91 5 5)
92
93 (define_function_unit "iu" 1 0
94 (and (eq_attr "type" "idiv")
95 (eq_attr "cpu" "rios1"))
96 19 19)
97
98 (define_function_unit "iu" 1 0
99 (and (eq_attr "type" "idiv")
100 (eq_attr "cpu" "ppc601"))
101 36 36)
102
103 (define_function_unit "iu" 1 0
104 (and (eq_attr "type" "idiv")
105 (eq_attr "cpu" "ppc403"))
106 33 33)
107
108 (define_function_unit "iu" 1 0
109 (and (eq_attr "type" "idiv")
110 (eq_attr "cpu" "ppc602,ppc603"))
111 37 36)
112
113 ; RIOS2 has two integer units: a primary one which can perform all
114 ; operations and a secondary one which is fed in lock step with the first
115 ; and can perform "simple" integer operations.
116 ; To catch this we define a 'dummy' imuldiv-unit that is also needed
117 ; for the complex insns.
118 (define_function_unit "iu2" 2 0
119 (and (eq_attr "type" "integer")
120 (eq_attr "cpu" "rios2"))
121 1 0)
122
123 (define_function_unit "iu2" 2 0
124 (and (eq_attr "type" "imul")
125 (eq_attr "cpu" "rios2"))
126 2 2)
127
128 (define_function_unit "iu2" 2 0
129 (and (eq_attr "type" "idiv")
130 (eq_attr "cpu" "rios2"))
131 13 13)
132
133 (define_function_unit "imuldiv" 1 0
134 (and (eq_attr "type" "imul")
135 (eq_attr "cpu" "rios2"))
136 2 2)
137
138
139 (define_function_unit "imuldiv" 1 0
140 (and (eq_attr "type" "idiv")
141 (eq_attr "cpu" "rios2"))
142 13 13)
143
144 ; MPCCORE has separate IMUL/IDIV unit for multicycle instructions
145 ; Divide latency varies greatly from 2-11, use 6 as average
146 (define_function_unit "imuldiv" 1 0
147 (and (eq_attr "type" "imul")
148 (eq_attr "cpu" "mpccore"))
149 2 1)
150
151 (define_function_unit "imuldiv" 1 0
152 (and (eq_attr "type" "idiv")
153 (eq_attr "cpu" "mpccore"))
154 6 6)
155
156 ; PPC604 has two units that perform integer operations
157 ; and one unit for divide/multiply operations (and move
158 ; from/to spr).
159 (define_function_unit "iu2" 2 0
160 (and (eq_attr "type" "integer")
161 (eq_attr "cpu" "ppc604,ppc620"))
162 1 1
163 [(eq_attr "type" "imul,idiv")])
164
165 (define_function_unit "imuldiv" 1 0
166 (and (eq_attr "type" "imul")
167 (eq_attr "cpu" "ppc604,ppc620"))
168 4 2
169 [(eq_attr "type" "integer")])
170
171 (define_function_unit "imuldiv" 1 0
172 (and (eq_attr "type" "idiv")
173 (eq_attr "cpu" "ppc604,ppc620"))
174 20 19
175 [(eq_attr "type" "integer")])
176
177 ; compare is done on integer unit, but feeds insns which
178 ; execute on the branch unit. Ready-delay of the compare
179 ; on the branch unit is large (3-5 cycles). On the iu/fpu
180 ; it is 1. One drawback is that the compare will also be
181 ; assigned to the bpu, but this inaccuracy is worth for being
182 ; able to fill the compare-branch delay, with insns on iu/fpu.
183 (define_function_unit "iu" 1 0
184 (and (eq_attr "type" "compare")
185 (eq_attr "cpu" "rios1,mpccore,ppc601"))
186 1 1)
187
188 (define_function_unit "iu2" 2 0
189 (and (eq_attr "type" "compare")
190 (eq_attr "cpu" "rios2"))
191 1 1)
192
193 (define_function_unit "bpu" 1 0
194 (and (eq_attr "type" "compare")
195 (eq_attr "cpu" "rios1,rios2,ppc403,mpccore,ppc601,ppc603,ppc604,ppc620"))
196 4 1)
197
198 ; different machines have different compare timings
199 ; in ppc604, compare is done on the one of the two
200 ; main integer units.
201 (define_function_unit "iu2" 2 0
202 (and (eq_attr "type" "compare")
203 (eq_attr "cpu" "ppc604,ppc620"))
204 1 1)
205
206 (define_function_unit "bpu" 1 0
207 (eq_attr "type" "delayed_compare")
208 5 0)
209
210 ; fp compare uses fp unit
211 (define_function_unit "fpu" 1 0
212 (and (eq_attr "type" "fpcompare")
213 (eq_attr "cpu" "rios1"))
214 8 1)
215
216 ; rios1 and rios2 have different fpcompare delays
217 (define_function_unit "fpu2" 2 0
218 (and (eq_attr "type" "fpcompare")
219 (eq_attr "cpu" "rios2"))
220 5 1)
221
222 ; on ppc601 and ppc603, fpcompare takes also 2 cycles from
223 ; the integer unit
224 ; here we do not define delays, just occupy the unit. The dependencies
225 ; will be signed by the fpcompare definition in the fpu.
226 (define_function_unit "iu" 1 0
227 (and (eq_attr "type" "fpcompare")
228 (eq_attr "cpu" "ppc601,ppc602,ppc603"))
229 0 2)
230
231 ; fp compare uses fp unit
232 (define_function_unit "fpu" 1 0
233 (and (eq_attr "type" "fpcompare")
234 (eq_attr "cpu" "ppc601,ppc602,ppc603,ppc604,ppc620"))
235 5 1)
236
237 (define_function_unit "fpu" 1 0
238 (and (eq_attr "type" "fpcompare")
239 (eq_attr "cpu" "mpccore"))
240 1 1)
241
242 (define_function_unit "bpu" 1 0
243 (and (eq_attr "type" "mtjmpr")
244 (eq_attr "cpu" "rios1,rios2"))
245 5 0)
246
247 (define_function_unit "bpu" 1 0
248 (and (eq_attr "type" "mtjmpr")
249 (eq_attr "cpu" "ppc403,mpccore,ppc601,ppc602,ppc603,ppc604,ppc620"))
250 4 0)
251
252 ; all jumps/branches are executing on the bpu, in 1 cycle, for all machines.
253 (define_function_unit "bpu" 1 0
254 (eq_attr "type" "jmpreg")
255 1 0)
256
257 (define_function_unit "bpu" 1 0
258 (eq_attr "type" "branch")
259 1 0)
260
261 ; Floating Point Unit
262 (define_function_unit "fpu" 1 0
263 (and (eq_attr "type" "fp,dmul")
264 (eq_attr "cpu" "rios1"))
265 2 0)
266
267 (define_function_unit "fpu" 1 0
268 (and (eq_attr "type" "fp")
269 (eq_attr "cpu" "mpccore"))
270 4 4)
271
272 (define_function_unit "fpu" 1 0
273 (and (eq_attr "type" "fp")
274 (eq_attr "cpu" "ppc601"))
275 4 0)
276
277 (define_function_unit "fpu" 1 0
278 (and (eq_attr "type" "fp")
279 (eq_attr "cpu" "ppc602,ppc603,ppc604,ppc620"))
280 3 1)
281
282 (define_function_unit "fpu" 1 0
283 (and (eq_attr "type" "dmul")
284 (eq_attr "cpu" "mpccore"))
285 5 5)
286
287 (define_function_unit "fpu" 1 0
288 (and (eq_attr "type" "dmul")
289 (eq_attr "cpu" "ppc601"))
290 5 2)
291
292 ; is this true?
293 (define_function_unit "fpu" 1 0
294 (and (eq_attr "type" "dmul")
295 (eq_attr "cpu" "ppc602,ppc603"))
296 4 2)
297
298 (define_function_unit "fpu" 1 0
299 (and (eq_attr "type" "dmul")
300 (eq_attr "cpu" "ppc604,ppc620"))
301 3 1)
302
303 (define_function_unit "fpu" 1 0
304 (and (eq_attr "type" "sdiv,ddiv")
305 (eq_attr "cpu" "rios1"))
306 19 19)
307
308 (define_function_unit "fpu" 1 0
309 (and (eq_attr "type" "sdiv")
310 (eq_attr "cpu" "ppc601"))
311 17 17)
312
313 (define_function_unit "fpu" 1 0
314 (and (eq_attr "type" "sdiv")
315 (eq_attr "cpu" "mpccore"))
316 10 10)
317
318 (define_function_unit "fpu" 1 0
319 (and (eq_attr "type" "sdiv")
320 (eq_attr "cpu" "ppc602,ppc603,ppc604,ppc620"))
321 18 18)
322
323 (define_function_unit "fpu" 1 0
324 (and (eq_attr "type" "ddiv")
325 (eq_attr "cpu" "mpccore"))
326 17 17)
327
328 (define_function_unit "fpu" 1 0
329 (and (eq_attr "type" "ddiv")
330 (eq_attr "cpu" "ppc601,ppc604,ppc620"))
331 31 31)
332
333 (define_function_unit "fpu" 1 0
334 (and (eq_attr "type" "ddiv")
335 (eq_attr "cpu" "ppc602,ppc603"))
336 33 33)
337
338 (define_function_unit "fpu" 1 0
339 (and (eq_attr "type" "ssqrt")
340 (eq_attr "cpu" "ppc620"))
341 31 31)
342
343 (define_function_unit "fpu" 1 0
344 (and (eq_attr "type" "dsqrt")
345 (eq_attr "cpu" "ppc620"))
346 31 31)
347
348 ; RIOS2 has two symmetric FPUs.
349 (define_function_unit "fpu2" 2 0
350 (and (eq_attr "type" "fp")
351 (eq_attr "cpu" "rios2"))
352 2 0)
353
354 (define_function_unit "fpu2" 2 0
355 (and (eq_attr "type" "dmul")
356 (eq_attr "cpu" "rios2"))
357 2 0)
358
359 (define_function_unit "fpu2" 2 0
360 (and (eq_attr "type" "sdiv,ddiv")
361 (eq_attr "cpu" "rios2"))
362 17 17)
363
364 (define_function_unit "fpu2" 2 0
365 (and (eq_attr "type" "ssqrt,dsqrt")
366 (eq_attr "cpu" "rios2"))
367 26 26)
368
369 \f
370 ;; Start with fixed-point load and store insns. Here we put only the more
371 ;; complex forms. Basic data transfer is done later.
372
373 (define_expand "zero_extendqidi2"
374 [(set (match_operand:DI 0 "gpc_reg_operand" "")
375 (zero_extend:DI (match_operand:QI 1 "gpc_reg_operand" "")))]
376 "TARGET_POWERPC64"
377 "")
378
379 (define_insn ""
380 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
381 (zero_extend:DI (match_operand:QI 1 "reg_or_mem_operand" "m,r")))]
382 "TARGET_POWERPC64"
383 "@
384 lbz%U1%X1 %0,%1
385 rldicl %0,%1,0,56"
386 [(set_attr "type" "load,*")])
387
388 (define_insn ""
389 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
390 (compare:CC (zero_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r"))
391 (const_int 0)))
392 (clobber (match_scratch:DI 2 "=r"))]
393 "TARGET_POWERPC64"
394 "rldicl. %2,%1,0,56"
395 [(set_attr "type" "compare")])
396
397 (define_insn ""
398 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
399 (compare:CC (zero_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r"))
400 (const_int 0)))
401 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
402 (zero_extend:DI (match_dup 1)))]
403 "TARGET_POWERPC64"
404 "rldicl. %0,%1,0,56"
405 [(set_attr "type" "compare")])
406
407 (define_insn "extendqidi2"
408 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
409 (sign_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r")))]
410 "TARGET_POWERPC64"
411 "extsb %0,%1")
412
413 (define_insn ""
414 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
415 (compare:CC (sign_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r"))
416 (const_int 0)))
417 (clobber (match_scratch:DI 2 "=r"))]
418 "TARGET_POWERPC64"
419 "extsb. %2,%1"
420 [(set_attr "type" "compare")])
421
422 (define_insn ""
423 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
424 (compare:CC (sign_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r"))
425 (const_int 0)))
426 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
427 (sign_extend:DI (match_dup 1)))]
428 "TARGET_POWERPC64"
429 "extsb. %0,%1"
430 [(set_attr "type" "compare")])
431
432 (define_expand "zero_extendhidi2"
433 [(set (match_operand:DI 0 "gpc_reg_operand" "")
434 (zero_extend:DI (match_operand:HI 1 "gpc_reg_operand" "")))]
435 "TARGET_POWERPC64"
436 "")
437
438 (define_insn ""
439 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
440 (zero_extend:DI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
441 "TARGET_POWERPC64"
442 "@
443 lhz%U1%X1 %0,%1
444 rldicl %0,%1,0,48"
445 [(set_attr "type" "load,*")])
446
447 (define_insn ""
448 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
449 (compare:CC (zero_extend:DI (match_operand:HI 1 "gpc_reg_operand" "r"))
450 (const_int 0)))
451 (clobber (match_scratch:DI 2 "=r"))]
452 "TARGET_POWERPC64"
453 "rldicl. %2,%1,0,48"
454 [(set_attr "type" "compare")])
455
456 (define_insn ""
457 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
458 (compare:CC (zero_extend:DI (match_operand:HI 1 "gpc_reg_operand" "r"))
459 (const_int 0)))
460 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
461 (zero_extend:DI (match_dup 1)))]
462 "TARGET_POWERPC64"
463 "rldicl. %0,%1,0,48"
464 [(set_attr "type" "compare")])
465
466 (define_expand "extendhidi2"
467 [(set (match_operand:DI 0 "gpc_reg_operand" "")
468 (sign_extend:DI (match_operand:HI 1 "gpc_reg_operand" "")))]
469 "TARGET_POWERPC64"
470 "")
471
472 (define_insn ""
473 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
474 (sign_extend:DI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
475 "TARGET_POWERPC64"
476 "@
477 lha%U1%X1 %0,%1
478 extsh %0,%1"
479 [(set_attr "type" "load,*")])
480
481 (define_insn ""
482 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
483 (compare:CC (sign_extend:DI (match_operand:HI 1 "gpc_reg_operand" "r"))
484 (const_int 0)))
485 (clobber (match_scratch:DI 2 "=r"))]
486 "TARGET_POWERPC64"
487 "extsh. %2,%1"
488 [(set_attr "type" "compare")])
489
490 (define_insn ""
491 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
492 (compare:CC (sign_extend:DI (match_operand:HI 1 "gpc_reg_operand" "r"))
493 (const_int 0)))
494 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
495 (sign_extend:DI (match_dup 1)))]
496 "TARGET_POWERPC64"
497 "extsh. %0,%1"
498 [(set_attr "type" "compare")])
499
500 (define_expand "zero_extendsidi2"
501 [(set (match_operand:DI 0 "gpc_reg_operand" "")
502 (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" "")))]
503 "TARGET_POWERPC64"
504 "")
505
506 (define_insn ""
507 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
508 (zero_extend:DI (match_operand:SI 1 "reg_or_mem_operand" "m,r")))]
509 "TARGET_POWERPC64"
510 "@
511 lwz%U1%X1 %0,%1
512 rldicl %0,%1,0,32"
513 [(set_attr "type" "load,*")])
514
515 (define_insn ""
516 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
517 (compare:CC (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" "r"))
518 (const_int 0)))
519 (clobber (match_scratch:DI 2 "=r"))]
520 "TARGET_POWERPC64"
521 "rldicl. %2,%1,0,32"
522 [(set_attr "type" "compare")])
523
524 (define_insn ""
525 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
526 (compare:CC (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" "r"))
527 (const_int 0)))
528 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
529 (zero_extend:DI (match_dup 1)))]
530 "TARGET_POWERPC64"
531 "rldicl. %0,%1,0,32"
532 [(set_attr "type" "compare")])
533
534 (define_expand "extendsidi2"
535 [(set (match_operand:DI 0 "gpc_reg_operand" "")
536 (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" "")))]
537 "TARGET_POWERPC64"
538 "")
539
540 (define_insn ""
541 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
542 (sign_extend:DI (match_operand:SI 1 "lwa_operand" "m,r")))]
543 "TARGET_POWERPC64"
544 "@
545 lwa%U1%X1 %0,%1
546 extsw %0,%1"
547 [(set_attr "type" "load,*")])
548
549 (define_insn ""
550 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
551 (compare:CC (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" "r"))
552 (const_int 0)))
553 (clobber (match_scratch:DI 2 "=r"))]
554 "TARGET_POWERPC64"
555 "extsw. %2,%1"
556 [(set_attr "type" "compare")])
557
558 (define_insn ""
559 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
560 (compare:CC (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" "r"))
561 (const_int 0)))
562 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
563 (sign_extend:DI (match_dup 1)))]
564 "TARGET_POWERPC64"
565 "extsw. %0,%1"
566 [(set_attr "type" "compare")])
567
568 (define_expand "zero_extendqisi2"
569 [(set (match_operand:SI 0 "gpc_reg_operand" "")
570 (zero_extend:SI (match_operand:QI 1 "gpc_reg_operand" "")))]
571 ""
572 "")
573
574 (define_insn ""
575 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
576 (zero_extend:SI (match_operand:QI 1 "reg_or_mem_operand" "m,r")))]
577 ""
578 "@
579 lbz%U1%X1 %0,%1
580 {rlinm|rlwinm} %0,%1,0,0xff"
581 [(set_attr "type" "load,*")])
582
583 (define_insn ""
584 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
585 (compare:CC (zero_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r"))
586 (const_int 0)))
587 (clobber (match_scratch:SI 2 "=r"))]
588 ""
589 "{andil.|andi.} %2,%1,0xff"
590 [(set_attr "type" "compare")])
591
592 (define_insn ""
593 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
594 (compare:CC (zero_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r"))
595 (const_int 0)))
596 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
597 (zero_extend:SI (match_dup 1)))]
598 ""
599 "{andil.|andi.} %0,%1,0xff"
600 [(set_attr "type" "compare")])
601
602 (define_expand "extendqisi2"
603 [(use (match_operand:SI 0 "gpc_reg_operand" ""))
604 (use (match_operand:QI 1 "gpc_reg_operand" ""))]
605 ""
606 "
607 {
608 if (TARGET_POWERPC)
609 emit_insn (gen_extendqisi2_ppc (operands[0], operands[1]));
610 else if (TARGET_POWER)
611 emit_insn (gen_extendqisi2_power (operands[0], operands[1]));
612 else
613 emit_insn (gen_extendqisi2_no_power (operands[0], operands[1]));
614 DONE;
615 }")
616
617 (define_insn "extendqisi2_ppc"
618 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
619 (sign_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r")))]
620 "TARGET_POWERPC"
621 "extsb %0,%1")
622
623 (define_insn ""
624 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
625 (compare:CC (sign_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r"))
626 (const_int 0)))
627 (clobber (match_scratch:SI 2 "=r"))]
628 "TARGET_POWERPC"
629 "extsb. %2,%1"
630 [(set_attr "type" "compare")])
631
632 (define_insn ""
633 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
634 (compare:CC (sign_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r"))
635 (const_int 0)))
636 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
637 (sign_extend:SI (match_dup 1)))]
638 "TARGET_POWERPC"
639 "extsb. %0,%1"
640 [(set_attr "type" "compare")])
641
642 (define_expand "extendqisi2_power"
643 [(parallel [(set (match_dup 2)
644 (ashift:SI (match_operand:QI 1 "gpc_reg_operand" "")
645 (const_int 24)))
646 (clobber (scratch:SI))])
647 (parallel [(set (match_operand:SI 0 "gpc_reg_operand" "")
648 (ashiftrt:SI (match_dup 2)
649 (const_int 24)))
650 (clobber (scratch:SI))])]
651 "TARGET_POWER"
652 "
653 { operands[1] = gen_lowpart (SImode, operands[1]);
654 operands[2] = gen_reg_rtx (SImode); }")
655
656 (define_expand "extendqisi2_no_power"
657 [(set (match_dup 2)
658 (ashift:SI (match_operand:QI 1 "gpc_reg_operand" "")
659 (const_int 24)))
660 (set (match_operand:SI 0 "gpc_reg_operand" "")
661 (ashiftrt:SI (match_dup 2)
662 (const_int 24)))]
663 "! TARGET_POWER && ! TARGET_POWERPC"
664 "
665 { operands[1] = gen_lowpart (SImode, operands[1]);
666 operands[2] = gen_reg_rtx (SImode); }")
667
668 (define_expand "zero_extendqihi2"
669 [(set (match_operand:HI 0 "gpc_reg_operand" "")
670 (zero_extend:HI (match_operand:QI 1 "gpc_reg_operand" "")))]
671 ""
672 "")
673
674 (define_insn ""
675 [(set (match_operand:HI 0 "gpc_reg_operand" "=r,r")
676 (zero_extend:HI (match_operand:QI 1 "reg_or_mem_operand" "m,r")))]
677 ""
678 "@
679 lbz%U1%X1 %0,%1
680 {rlinm|rlwinm} %0,%1,0,0xff"
681 [(set_attr "type" "load,*")])
682
683 (define_insn ""
684 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
685 (compare:CC (zero_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r"))
686 (const_int 0)))
687 (clobber (match_scratch:HI 2 "=r"))]
688 ""
689 "{andil.|andi.} %2,%1,0xff"
690 [(set_attr "type" "compare")])
691
692 (define_insn ""
693 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
694 (compare:CC (zero_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r"))
695 (const_int 0)))
696 (set (match_operand:HI 0 "gpc_reg_operand" "=r")
697 (zero_extend:HI (match_dup 1)))]
698 ""
699 "{andil.|andi.} %0,%1,0xff"
700 [(set_attr "type" "compare")])
701
702 (define_expand "extendqihi2"
703 [(use (match_operand:HI 0 "gpc_reg_operand" ""))
704 (use (match_operand:QI 1 "gpc_reg_operand" ""))]
705 ""
706 "
707 {
708 if (TARGET_POWERPC)
709 emit_insn (gen_extendqihi2_ppc (operands[0], operands[1]));
710 else if (TARGET_POWER)
711 emit_insn (gen_extendqihi2_power (operands[0], operands[1]));
712 else
713 emit_insn (gen_extendqihi2_no_power (operands[0], operands[1]));
714 DONE;
715 }")
716
717 (define_insn "extendqihi2_ppc"
718 [(set (match_operand:HI 0 "gpc_reg_operand" "=r")
719 (sign_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r")))]
720 "TARGET_POWERPC"
721 "extsb %0,%1")
722
723 (define_insn ""
724 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
725 (compare:CC (sign_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r"))
726 (const_int 0)))
727 (clobber (match_scratch:HI 2 "=r"))]
728 "TARGET_POWERPC"
729 "extsb. %2,%1"
730 [(set_attr "type" "compare")])
731
732 (define_insn ""
733 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
734 (compare:CC (sign_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r"))
735 (const_int 0)))
736 (set (match_operand:HI 0 "gpc_reg_operand" "=r")
737 (sign_extend:HI (match_dup 1)))]
738 "TARGET_POWERPC"
739 "extsb. %0,%1"
740 [(set_attr "type" "compare")])
741
742 (define_expand "extendqihi2_power"
743 [(parallel [(set (match_dup 2)
744 (ashift:SI (match_operand:QI 1 "gpc_reg_operand" "")
745 (const_int 24)))
746 (clobber (scratch:SI))])
747 (parallel [(set (match_operand:HI 0 "gpc_reg_operand" "")
748 (ashiftrt:SI (match_dup 2)
749 (const_int 24)))
750 (clobber (scratch:SI))])]
751 "TARGET_POWER"
752 "
753 { operands[0] = gen_lowpart (SImode, operands[0]);
754 operands[1] = gen_lowpart (SImode, operands[1]);
755 operands[2] = gen_reg_rtx (SImode); }")
756
757 (define_expand "extendqihi2_no_power"
758 [(set (match_dup 2)
759 (ashift:SI (match_operand:QI 1 "gpc_reg_operand" "")
760 (const_int 24)))
761 (set (match_operand:HI 0 "gpc_reg_operand" "")
762 (ashiftrt:SI (match_dup 2)
763 (const_int 24)))]
764 "! TARGET_POWER && ! TARGET_POWERPC"
765 "
766 { operands[0] = gen_lowpart (SImode, operands[0]);
767 operands[1] = gen_lowpart (SImode, operands[1]);
768 operands[2] = gen_reg_rtx (SImode); }")
769
770 (define_expand "zero_extendhisi2"
771 [(set (match_operand:SI 0 "gpc_reg_operand" "")
772 (zero_extend:SI (match_operand:HI 1 "gpc_reg_operand" "")))]
773 ""
774 "")
775
776 (define_insn ""
777 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
778 (zero_extend:SI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
779 ""
780 "@
781 lhz%U1%X1 %0,%1
782 {rlinm|rlwinm} %0,%1,0,0xffff"
783 [(set_attr "type" "load,*")])
784
785 (define_insn ""
786 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
787 (compare:CC (zero_extend:SI (match_operand:HI 1 "gpc_reg_operand" "r"))
788 (const_int 0)))
789 (clobber (match_scratch:SI 2 "=r"))]
790 ""
791 "{andil.|andi.} %2,%1,0xffff"
792 [(set_attr "type" "compare")])
793
794 (define_insn ""
795 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
796 (compare:CC (zero_extend:SI (match_operand:HI 1 "gpc_reg_operand" "r"))
797 (const_int 0)))
798 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
799 (zero_extend:SI (match_dup 1)))]
800 ""
801 "{andil.|andi.} %0,%1,0xffff"
802 [(set_attr "type" "compare")])
803
804 (define_expand "extendhisi2"
805 [(set (match_operand:SI 0 "gpc_reg_operand" "")
806 (sign_extend:SI (match_operand:HI 1 "gpc_reg_operand" "")))]
807 ""
808 "")
809
810 (define_insn ""
811 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
812 (sign_extend:SI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
813 ""
814 "@
815 lha%U1%X1 %0,%1
816 {exts|extsh} %0,%1"
817 [(set_attr "type" "load,*")])
818
819 (define_insn ""
820 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
821 (compare:CC (sign_extend:SI (match_operand:HI 1 "gpc_reg_operand" "r"))
822 (const_int 0)))
823 (clobber (match_scratch:SI 2 "=r"))]
824 ""
825 "{exts.|extsh.} %2,%1"
826 [(set_attr "type" "compare")])
827
828 (define_insn ""
829 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
830 (compare:CC (sign_extend:SI (match_operand:HI 1 "gpc_reg_operand" "r"))
831 (const_int 0)))
832 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
833 (sign_extend:SI (match_dup 1)))]
834 ""
835 "{exts.|extsh.} %0,%1"
836 [(set_attr "type" "compare")])
837 \f
838 ;; Fixed-point arithmetic insns.
839
840 ;; Discourage ai/addic because of carry but provide it in an alternative
841 ;; allowing register zero as source.
842 (define_insn "addsi3"
843 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,?r,r")
844 (plus:SI (match_operand:SI 1 "gpc_reg_operand" "%r,b,r,b")
845 (match_operand:SI 2 "add_operand" "r,I,I,J")))]
846 ""
847 "@
848 {cax|add} %0,%1,%2
849 {cal %0,%2(%1)|addi %0,%1,%2}
850 {ai|addic} %0,%1,%2
851 {cau|addis} %0,%1,%u2")
852
853 (define_insn ""
854 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
855 (compare:CC (plus:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r")
856 (match_operand:SI 2 "reg_or_short_operand" "r,I"))
857 (const_int 0)))
858 (clobber (match_scratch:SI 3 "=r,r"))]
859 ""
860 "@
861 {cax.|add.} %3,%1,%2
862 {ai.|addic.} %3,%1,%2"
863 [(set_attr "type" "compare")])
864
865 (define_insn ""
866 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
867 (compare:CC (plus:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r")
868 (match_operand:SI 2 "reg_or_short_operand" "r,I"))
869 (const_int 0)))
870 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
871 (plus:SI (match_dup 1) (match_dup 2)))]
872 ""
873 "@
874 {cax.|add.} %0,%1,%2
875 {ai.|addic.} %0,%1,%2"
876 [(set_attr "type" "compare")])
877
878 ;; Split an add that we can't do in one insn into two insns, each of which
879 ;; does one 16-bit part. This is used by combine. Note that the low-order
880 ;; add should be last in case the result gets used in an address.
881
882 (define_split
883 [(set (match_operand:SI 0 "gpc_reg_operand" "")
884 (plus:SI (match_operand:SI 1 "gpc_reg_operand" "")
885 (match_operand:SI 2 "non_add_cint_operand" "")))]
886 ""
887 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 3)))
888 (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 4)))]
889 "
890 {
891 HOST_WIDE_INT low = INTVAL (operands[2]) & 0xffff;
892 HOST_WIDE_INT high = INTVAL (operands[2]) & (~ (HOST_WIDE_INT) 0xffff);
893
894 if (low & 0x8000)
895 high += 0x10000, low |= ((HOST_WIDE_INT) -1) << 16;
896
897 operands[3] = GEN_INT (high);
898 operands[4] = GEN_INT (low);
899 }")
900
901 (define_insn "one_cmplsi2"
902 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
903 (not:SI (match_operand:SI 1 "gpc_reg_operand" "r")))]
904 ""
905 "nor %0,%1,%1")
906
907 (define_insn ""
908 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
909 (compare:CC (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
910 (const_int 0)))
911 (clobber (match_scratch:SI 2 "=r"))]
912 ""
913 "nor. %2,%1,%1"
914 [(set_attr "type" "compare")])
915
916 (define_insn ""
917 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
918 (compare:CC (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
919 (const_int 0)))
920 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
921 (not:SI (match_dup 1)))]
922 ""
923 "nor. %0,%1,%1"
924 [(set_attr "type" "compare")])
925
926 (define_insn ""
927 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
928 (minus:SI (match_operand:SI 1 "reg_or_short_operand" "rI")
929 (match_operand:SI 2 "gpc_reg_operand" "r")))]
930 "! TARGET_POWERPC"
931 "{sf%I1|subf%I1c} %0,%2,%1")
932
933 (define_insn ""
934 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
935 (minus:SI (match_operand:SI 1 "reg_or_short_operand" "r,I")
936 (match_operand:SI 2 "gpc_reg_operand" "r,r")))]
937 "TARGET_POWERPC"
938 "@
939 subf %0,%2,%1
940 subfic %0,%2,%1")
941
942 (define_insn ""
943 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
944 (compare:CC (minus:SI (match_operand:SI 1 "gpc_reg_operand" "r")
945 (match_operand:SI 2 "gpc_reg_operand" "r"))
946 (const_int 0)))
947 (clobber (match_scratch:SI 3 "=r"))]
948 "! TARGET_POWERPC"
949 "{sf.|subfc.} %3,%2,%1"
950 [(set_attr "type" "compare")])
951
952 (define_insn ""
953 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
954 (compare:CC (minus:SI (match_operand:SI 1 "gpc_reg_operand" "r")
955 (match_operand:SI 2 "gpc_reg_operand" "r"))
956 (const_int 0)))
957 (clobber (match_scratch:SI 3 "=r"))]
958 "TARGET_POWERPC"
959 "subf. %3,%2,%1"
960 [(set_attr "type" "compare")])
961
962 (define_insn ""
963 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
964 (compare:CC (minus:SI (match_operand:SI 1 "gpc_reg_operand" "r")
965 (match_operand:SI 2 "gpc_reg_operand" "r"))
966 (const_int 0)))
967 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
968 (minus:SI (match_dup 1) (match_dup 2)))]
969 "! TARGET_POWERPC"
970 "{sf.|subfc.} %0,%2,%1"
971 [(set_attr "type" "compare")])
972
973 (define_insn ""
974 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
975 (compare:CC (minus:SI (match_operand:SI 1 "gpc_reg_operand" "r")
976 (match_operand:SI 2 "gpc_reg_operand" "r"))
977 (const_int 0)))
978 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
979 (minus:SI (match_dup 1) (match_dup 2)))]
980 "TARGET_POWERPC"
981 "subf. %0,%2,%1"
982 [(set_attr "type" "compare")])
983
984 (define_expand "subsi3"
985 [(set (match_operand:SI 0 "gpc_reg_operand" "")
986 (minus:SI (match_operand:SI 1 "reg_or_short_operand" "")
987 (match_operand:SI 2 "reg_or_cint_operand" "")))]
988 ""
989 "
990 {
991 if (GET_CODE (operands[2]) == CONST_INT)
992 {
993 emit_insn (gen_addsi3 (operands[0], operands[1],
994 negate_rtx (SImode, operands[2])));
995 DONE;
996 }
997 }")
998
999 ;; For SMIN, SMAX, UMIN, and UMAX, we use DEFINE_EXPAND's that involve a doz[i]
1000 ;; instruction and some auxiliary computations. Then we just have a single
1001 ;; DEFINE_INSN for doz[i] and the define_splits to make them if made by
1002 ;; combine.
1003
1004 (define_expand "sminsi3"
1005 [(set (match_dup 3)
1006 (if_then_else:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "")
1007 (match_operand:SI 2 "reg_or_short_operand" ""))
1008 (const_int 0)
1009 (minus:SI (match_dup 2) (match_dup 1))))
1010 (set (match_operand:SI 0 "gpc_reg_operand" "")
1011 (minus:SI (match_dup 2) (match_dup 3)))]
1012 "TARGET_POWER"
1013 "
1014 { operands[3] = gen_reg_rtx (SImode); }")
1015
1016 (define_split
1017 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1018 (smin:SI (match_operand:SI 1 "gpc_reg_operand" "")
1019 (match_operand:SI 2 "reg_or_short_operand" "")))
1020 (clobber (match_operand:SI 3 "gpc_reg_operand" ""))]
1021 "TARGET_POWER"
1022 [(set (match_dup 3)
1023 (if_then_else:SI (gt:SI (match_dup 1) (match_dup 2))
1024 (const_int 0)
1025 (minus:SI (match_dup 2) (match_dup 1))))
1026 (set (match_dup 0) (minus:SI (match_dup 2) (match_dup 3)))]
1027 "")
1028
1029 (define_expand "smaxsi3"
1030 [(set (match_dup 3)
1031 (if_then_else:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "")
1032 (match_operand:SI 2 "reg_or_short_operand" ""))
1033 (const_int 0)
1034 (minus:SI (match_dup 2) (match_dup 1))))
1035 (set (match_operand:SI 0 "gpc_reg_operand" "")
1036 (plus:SI (match_dup 3) (match_dup 1)))]
1037 "TARGET_POWER"
1038 "
1039 { operands[3] = gen_reg_rtx (SImode); }")
1040
1041 (define_split
1042 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1043 (smax:SI (match_operand:SI 1 "gpc_reg_operand" "")
1044 (match_operand:SI 2 "reg_or_short_operand" "")))
1045 (clobber (match_operand:SI 3 "gpc_reg_operand" ""))]
1046 "TARGET_POWER"
1047 [(set (match_dup 3)
1048 (if_then_else:SI (gt:SI (match_dup 1) (match_dup 2))
1049 (const_int 0)
1050 (minus:SI (match_dup 2) (match_dup 1))))
1051 (set (match_dup 0) (plus:SI (match_dup 3) (match_dup 1)))]
1052 "")
1053
1054 (define_expand "uminsi3"
1055 [(set (match_dup 3) (xor:SI (match_operand:SI 1 "gpc_reg_operand" "")
1056 (match_dup 5)))
1057 (set (match_dup 4) (xor:SI (match_operand:SI 2 "gpc_reg_operand" "")
1058 (match_dup 5)))
1059 (set (match_dup 3) (if_then_else:SI (gt (match_dup 3) (match_dup 4))
1060 (const_int 0)
1061 (minus:SI (match_dup 4) (match_dup 3))))
1062 (set (match_operand:SI 0 "gpc_reg_operand" "")
1063 (minus:SI (match_dup 2) (match_dup 3)))]
1064 "TARGET_POWER"
1065 "
1066 {
1067 operands[3] = gen_reg_rtx (SImode);
1068 operands[4] = gen_reg_rtx (SImode);
1069 operands[5] = GEN_INT (-2147483647 - 1);
1070 }")
1071
1072 (define_expand "umaxsi3"
1073 [(set (match_dup 3) (xor:SI (match_operand:SI 1 "gpc_reg_operand" "")
1074 (match_dup 5)))
1075 (set (match_dup 4) (xor:SI (match_operand:SI 2 "gpc_reg_operand" "")
1076 (match_dup 5)))
1077 (set (match_dup 3) (if_then_else:SI (gt (match_dup 3) (match_dup 4))
1078 (const_int 0)
1079 (minus:SI (match_dup 4) (match_dup 3))))
1080 (set (match_operand:SI 0 "gpc_reg_operand" "")
1081 (plus:SI (match_dup 3) (match_dup 1)))]
1082 "TARGET_POWER"
1083 "
1084 {
1085 operands[3] = gen_reg_rtx (SImode);
1086 operands[4] = gen_reg_rtx (SImode);
1087 operands[5] = GEN_INT (-2147483647 - 1);
1088 }")
1089
1090 (define_insn ""
1091 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1092 (if_then_else:SI (gt (match_operand:SI 1 "gpc_reg_operand" "r")
1093 (match_operand:SI 2 "reg_or_short_operand" "rI"))
1094 (const_int 0)
1095 (minus:SI (match_dup 2) (match_dup 1))))]
1096 "TARGET_POWER"
1097 "doz%I2 %0,%1,%2")
1098
1099 (define_insn ""
1100 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1101 (compare:CC
1102 (if_then_else:SI (gt (match_operand:SI 1 "gpc_reg_operand" "r")
1103 (match_operand:SI 2 "reg_or_short_operand" "rI"))
1104 (const_int 0)
1105 (minus:SI (match_dup 2) (match_dup 1)))
1106 (const_int 0)))
1107 (clobber (match_scratch:SI 3 "=r"))]
1108 "TARGET_POWER"
1109 "doz%I2. %3,%1,%2"
1110 [(set_attr "type" "delayed_compare")])
1111
1112 (define_insn ""
1113 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1114 (compare:CC
1115 (if_then_else:SI (gt (match_operand:SI 1 "gpc_reg_operand" "r")
1116 (match_operand:SI 2 "reg_or_short_operand" "rI"))
1117 (const_int 0)
1118 (minus:SI (match_dup 2) (match_dup 1)))
1119 (const_int 0)))
1120 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1121 (if_then_else:SI (gt (match_dup 1) (match_dup 2))
1122 (const_int 0)
1123 (minus:SI (match_dup 2) (match_dup 1))))]
1124 "TARGET_POWER"
1125 "doz%I2. %0,%1,%2"
1126 [(set_attr "type" "delayed_compare")])
1127
1128 ;; We don't need abs with condition code because such comparisons should
1129 ;; never be done.
1130 (define_expand "abssi2"
1131 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1132 (abs:SI (match_operand:SI 1 "gpc_reg_operand" "")))]
1133 ""
1134 "
1135 {
1136 if (!TARGET_POWER)
1137 {
1138 emit_insn (gen_abssi2_nopower (operands[0], operands[1]));
1139 DONE;
1140 }
1141 }")
1142
1143 (define_insn "abssi2_power"
1144 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1145 (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))]
1146 "TARGET_POWER"
1147 "abs %0,%1")
1148
1149 (define_insn "abssi2_nopower"
1150 [(set (match_operand:SI 0 "gpc_reg_operand" "=&r,r")
1151 (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r,0")))
1152 (clobber (match_scratch:SI 2 "=&r,&r"))]
1153 "!TARGET_POWER"
1154 "*
1155 {
1156 return (TARGET_POWERPC)
1157 ? \"{srai|srawi} %2,%1,31\;xor %0,%2,%1\;subf %0,%2,%0\"
1158 : \"{srai|srawi} %2,%1,31\;xor %0,%2,%1\;{sf|subfc} %0,%2,%0\";
1159 }"
1160 [(set_attr "length" "12")])
1161
1162 (define_split
1163 [(set (match_operand:SI 0 "gpc_reg_operand" "=&r,r")
1164 (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r,0")))
1165 (clobber (match_scratch:SI 2 "=&r,&r"))]
1166 "!TARGET_POWER && reload_completed"
1167 [(set (match_dup 2) (ashiftrt:SI (match_dup 1) (const_int 31)))
1168 (set (match_dup 0) (xor:SI (match_dup 2) (match_dup 1)))
1169 (set (match_dup 0) (minus:SI (match_dup 2) (match_dup 0)))]
1170 "")
1171
1172 (define_insn ""
1173 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1174 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r"))))]
1175 "TARGET_POWER"
1176 "nabs %0,%1")
1177
1178 (define_insn ""
1179 [(set (match_operand:SI 0 "gpc_reg_operand" "=&r,r")
1180 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r,0"))))
1181 (clobber (match_scratch:SI 2 "=&r,&r"))]
1182 "!TARGET_POWER"
1183 "*
1184 {
1185 return (TARGET_POWERPC)
1186 ? \"{srai|srawi} %2,%1,31\;xor %0,%2,%1\;subf %0,%0,%2\"
1187 : \"{srai|srawi} %2,%1,31\;xor %0,%2,%1\;{sf|subfc} %0,%0,%2\";
1188 }"
1189 [(set_attr "length" "12")])
1190
1191 (define_split
1192 [(set (match_operand:SI 0 "gpc_reg_operand" "=&r,r")
1193 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r,0"))))
1194 (clobber (match_scratch:SI 2 "=&r,&r"))]
1195 "!TARGET_POWER && reload_completed"
1196 [(set (match_dup 2) (ashiftrt:SI (match_dup 1) (const_int 31)))
1197 (set (match_dup 0) (xor:SI (match_dup 2) (match_dup 1)))
1198 (set (match_dup 0) (minus:SI (match_dup 0) (match_dup 2)))]
1199 "")
1200
1201 (define_insn "negsi2"
1202 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1203 (neg:SI (match_operand:SI 1 "gpc_reg_operand" "r")))]
1204 ""
1205 "neg %0,%1")
1206
1207 (define_insn ""
1208 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1209 (compare:CC (neg:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1210 (const_int 0)))
1211 (clobber (match_scratch:SI 2 "=r"))]
1212 ""
1213 "neg. %2,%1"
1214 [(set_attr "type" "compare")])
1215
1216 (define_insn ""
1217 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
1218 (compare:CC (neg:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1219 (const_int 0)))
1220 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1221 (neg:SI (match_dup 1)))]
1222 ""
1223 "neg. %0,%1"
1224 [(set_attr "type" "compare")])
1225
1226 (define_insn "ffssi2"
1227 [(set (match_operand:SI 0 "gpc_reg_operand" "=&r")
1228 (ffs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))]
1229 ""
1230 "neg %0,%1\;and %0,%0,%1\;{cntlz|cntlzw} %0,%0\;{sfi|subfic} %0,%0,32"
1231 [(set_attr "length" "16")])
1232
1233 (define_expand "mulsi3"
1234 [(use (match_operand:SI 0 "gpc_reg_operand" ""))
1235 (use (match_operand:SI 1 "gpc_reg_operand" ""))
1236 (use (match_operand:SI 2 "reg_or_short_operand" ""))]
1237 ""
1238 "
1239 {
1240 if (TARGET_POWER)
1241 emit_insn (gen_mulsi3_mq (operands[0], operands[1], operands[2]));
1242 else
1243 emit_insn (gen_mulsi3_no_mq (operands[0], operands[1], operands[2]));
1244 DONE;
1245 }")
1246
1247 (define_insn "mulsi3_mq"
1248 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
1249 (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r")
1250 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
1251 (clobber (match_scratch:SI 3 "=q,q"))]
1252 "TARGET_POWER"
1253 "@
1254 {muls|mullw} %0,%1,%2
1255 {muli|mulli} %0,%1,%2"
1256 [(set_attr "type" "imul")])
1257
1258 (define_insn "mulsi3_no_mq"
1259 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
1260 (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r")
1261 (match_operand:SI 2 "reg_or_short_operand" "r,I")))]
1262 "! TARGET_POWER"
1263 "@
1264 {muls|mullw} %0,%1,%2
1265 {muli|mulli} %0,%1,%2"
1266 [(set_attr "type" "imul")])
1267
1268 (define_insn ""
1269 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1270 (compare:CC (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1271 (match_operand:SI 2 "gpc_reg_operand" "r"))
1272 (const_int 0)))
1273 (clobber (match_scratch:SI 3 "=r"))
1274 (clobber (match_scratch:SI 4 "=q"))]
1275 "TARGET_POWER"
1276 "{muls.|mullw.} %3,%1,%2"
1277 [(set_attr "type" "delayed_compare")])
1278
1279 (define_insn ""
1280 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1281 (compare:CC (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1282 (match_operand:SI 2 "gpc_reg_operand" "r"))
1283 (const_int 0)))
1284 (clobber (match_scratch:SI 3 "=r"))]
1285 "! TARGET_POWER"
1286 "{muls.|mullw.} %3,%1,%2"
1287 [(set_attr "type" "delayed_compare")])
1288
1289 (define_insn ""
1290 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1291 (compare:CC (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1292 (match_operand:SI 2 "gpc_reg_operand" "r"))
1293 (const_int 0)))
1294 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1295 (mult:SI (match_dup 1) (match_dup 2)))
1296 (clobber (match_scratch:SI 4 "=q"))]
1297 "TARGET_POWER"
1298 "{muls.|mullw.} %0,%1,%2"
1299 [(set_attr "type" "delayed_compare")])
1300
1301 (define_insn ""
1302 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1303 (compare:CC (mult:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1304 (match_operand:SI 2 "gpc_reg_operand" "r"))
1305 (const_int 0)))
1306 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1307 (mult:SI (match_dup 1) (match_dup 2)))]
1308 "! TARGET_POWER"
1309 "{muls.|mullw.} %0,%1,%2"
1310 [(set_attr "type" "delayed_compare")])
1311
1312 ;; Operand 1 is divided by operand 2; quotient goes to operand
1313 ;; 0 and remainder to operand 3.
1314 ;; ??? At some point, see what, if anything, we can do about if (x % y == 0).
1315
1316 (define_expand "divmodsi4"
1317 [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "")
1318 (div:SI (match_operand:SI 1 "gpc_reg_operand" "")
1319 (match_operand:SI 2 "gpc_reg_operand" "")))
1320 (set (match_operand:SI 3 "gpc_reg_operand" "")
1321 (mod:SI (match_dup 1) (match_dup 2)))])]
1322 "TARGET_POWER || (! TARGET_POWER && ! TARGET_POWERPC)"
1323 "
1324 {
1325 if (! TARGET_POWER && ! TARGET_POWERPC)
1326 {
1327 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
1328 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
1329 emit_insn (gen_divss_call ());
1330 emit_move_insn (operands[0], gen_rtx (REG, SImode, 3));
1331 emit_move_insn (operands[3], gen_rtx (REG, SImode, 4));
1332 DONE;
1333 }
1334 }")
1335
1336 (define_insn ""
1337 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1338 (div:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1339 (match_operand:SI 2 "gpc_reg_operand" "r")))
1340 (set (match_operand:SI 3 "gpc_reg_operand" "=q")
1341 (mod:SI (match_dup 1) (match_dup 2)))]
1342 "TARGET_POWER"
1343 "divs %0,%1,%2"
1344 [(set_attr "type" "idiv")])
1345
1346 (define_insn ""
1347 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1348 (div:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1349 (match_operand:SI 2 "gpc_reg_operand" "r")))]
1350 "TARGET_POWERPC"
1351 "divw %0,%1,%2"
1352 [(set_attr "type" "idiv")])
1353
1354 (define_expand "udivsi3"
1355 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1356 (udiv:SI (match_operand:SI 1 "gpc_reg_operand" "")
1357 (match_operand:SI 2 "gpc_reg_operand" "")))]
1358 "TARGET_POWERPC || (! TARGET_POWER && ! TARGET_POWERPC)"
1359 "
1360 {
1361 if (! TARGET_POWER && ! TARGET_POWERPC)
1362 {
1363 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
1364 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
1365 emit_insn (gen_quous_call ());
1366 emit_move_insn (operands[0], gen_rtx (REG, SImode, 3));
1367 DONE;
1368 }
1369 }")
1370
1371 (define_insn ""
1372 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1373 (udiv:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1374 (match_operand:SI 2 "gpc_reg_operand" "r")))]
1375 "TARGET_POWERPC"
1376 "divwu %0,%1,%2"
1377 [(set_attr "type" "idiv")])
1378
1379 ;; For powers of two we can do srai/aze for divide and then adjust for
1380 ;; modulus. If it isn't a power of two, FAIL on POWER so divmodsi4 will be
1381 ;; used; for PowerPC, force operands into register and do a normal divide;
1382 ;; for AIX common-mode, use quoss call on register operands.
1383 (define_expand "divsi3"
1384 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1385 (div:SI (match_operand:SI 1 "gpc_reg_operand" "")
1386 (match_operand:SI 2 "reg_or_cint_operand" "")))]
1387 ""
1388 "
1389 {
1390 if (GET_CODE (operands[2]) == CONST_INT
1391 && exact_log2 (INTVAL (operands[2])) >= 0)
1392 ;
1393 else if (TARGET_POWERPC)
1394 operands[2] = force_reg (SImode, operands[2]);
1395 else if (TARGET_POWER)
1396 FAIL;
1397 else
1398 {
1399 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
1400 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
1401 emit_insn (gen_quoss_call ());
1402 emit_move_insn (operands[0], gen_rtx (REG, SImode, 3));
1403 DONE;
1404 }
1405 }")
1406
1407 (define_expand "modsi3"
1408 [(use (match_operand:SI 0 "gpc_reg_operand" ""))
1409 (use (match_operand:SI 1 "gpc_reg_operand" ""))
1410 (use (match_operand:SI 2 "reg_or_cint_operand" ""))]
1411 ""
1412 "
1413 {
1414 int i = exact_log2 (INTVAL (operands[2]));
1415 rtx temp1;
1416 rtx temp2;
1417
1418 if (GET_CODE (operands[2]) != CONST_INT || i < 0)
1419 FAIL;
1420
1421 temp1 = gen_reg_rtx (SImode);
1422 temp2 = gen_reg_rtx (SImode);
1423
1424 emit_insn (gen_divsi3 (temp1, operands[1], operands[2]));
1425 emit_insn (gen_ashlsi3 (temp2, temp1, GEN_INT (i)));
1426 emit_insn (gen_subsi3 (operands[0], operands[1], temp2));
1427 DONE;
1428 }")
1429
1430 (define_insn ""
1431 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1432 (div:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1433 (match_operand:SI 2 "const_int_operand" "N")))]
1434 "exact_log2 (INTVAL (operands[2])) >= 0"
1435 "{srai|srawi} %0,%1,%p2\;{aze|addze} %0,%0"
1436 [(set_attr "length" "8")])
1437
1438 (define_insn ""
1439 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1440 (compare:CC (div:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1441 (match_operand:SI 2 "const_int_operand" "N"))
1442 (const_int 0)))
1443 (clobber (match_scratch:SI 3 "=r"))]
1444 "exact_log2 (INTVAL (operands[2])) >= 0"
1445 "{srai|srawi} %3,%1,%p2\;{aze.|addze.} %3,%3"
1446 [(set_attr "type" "compare")
1447 (set_attr "length" "8")])
1448
1449 (define_insn ""
1450 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1451 (compare:CC (div:SI (match_operand:SI 1 "gpc_reg_operand" "r")
1452 (match_operand:SI 2 "const_int_operand" "N"))
1453 (const_int 0)))
1454 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1455 (div:SI (match_dup 1) (match_dup 2)))]
1456 "exact_log2 (INTVAL (operands[2])) >= 0"
1457 "{srai|srawi} %0,%1,%p2\;{aze.|addze.} %0,%0"
1458 [(set_attr "type" "compare")
1459 (set_attr "length" "8")])
1460
1461 (define_insn ""
1462 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1463 (udiv:SI
1464 (plus:DI (ashift:DI
1465 (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" "r"))
1466 (const_int 32))
1467 (zero_extend:DI (match_operand:SI 4 "register_operand" "2")))
1468 (match_operand:SI 3 "gpc_reg_operand" "r")))
1469 (set (match_operand:SI 2 "register_operand" "=*q")
1470 (umod:SI
1471 (plus:DI (ashift:DI
1472 (zero_extend:DI (match_dup 1)) (const_int 32))
1473 (zero_extend:DI (match_dup 4)))
1474 (match_dup 3)))]
1475 "TARGET_POWER"
1476 "div %0,%1,%3"
1477 [(set_attr "type" "idiv")])
1478
1479 ;; To do unsigned divide we handle the cases of the divisor looking like a
1480 ;; negative number. If it is a constant that is less than 2**31, we don't
1481 ;; have to worry about the branches. So make a few subroutines here.
1482 ;;
1483 ;; First comes the normal case.
1484 (define_expand "udivmodsi4_normal"
1485 [(set (match_dup 4) (const_int 0))
1486 (parallel [(set (match_operand:SI 0 "" "")
1487 (udiv:SI (plus:DI (ashift:DI (zero_extend:DI (match_dup 4))
1488 (const_int 32))
1489 (zero_extend:DI (match_operand:SI 1 "" "")))
1490 (match_operand:SI 2 "" "")))
1491 (set (match_operand:SI 3 "" "")
1492 (umod:SI (plus:DI (ashift:DI (zero_extend:DI (match_dup 4))
1493 (const_int 32))
1494 (zero_extend:DI (match_dup 1)))
1495 (match_dup 2)))])]
1496 "TARGET_POWER"
1497 "
1498 { operands[4] = gen_reg_rtx (SImode); }")
1499
1500 ;; This handles the branches.
1501 (define_expand "udivmodsi4_tests"
1502 [(set (match_operand:SI 0 "" "") (const_int 0))
1503 (set (match_operand:SI 3 "" "") (match_operand:SI 1 "" ""))
1504 (set (match_dup 5) (compare:CCUNS (match_dup 1) (match_operand:SI 2 "" "")))
1505 (set (pc) (if_then_else (ltu (match_dup 5) (const_int 0))
1506 (label_ref (match_operand:SI 4 "" "")) (pc)))
1507 (set (match_dup 0) (const_int 1))
1508 (set (match_dup 3) (minus:SI (match_dup 1) (match_dup 2)))
1509 (set (match_dup 6) (compare:CC (match_dup 2) (const_int 0)))
1510 (set (pc) (if_then_else (lt (match_dup 6) (const_int 0))
1511 (label_ref (match_dup 4)) (pc)))]
1512 "TARGET_POWER"
1513 "
1514 { operands[5] = gen_reg_rtx (CCUNSmode);
1515 operands[6] = gen_reg_rtx (CCmode);
1516 }")
1517
1518 (define_expand "udivmodsi4"
1519 [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "")
1520 (udiv:SI (match_operand:SI 1 "gpc_reg_operand" "")
1521 (match_operand:SI 2 "reg_or_cint_operand" "")))
1522 (set (match_operand:SI 3 "gpc_reg_operand" "")
1523 (umod:SI (match_dup 1) (match_dup 2)))])]
1524 ""
1525 "
1526 {
1527 rtx label = 0;
1528
1529 if (! TARGET_POWER)
1530 if (! TARGET_POWERPC)
1531 {
1532 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
1533 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
1534 emit_insn (gen_divus_call ());
1535 emit_move_insn (operands[0], gen_rtx (REG, SImode, 3));
1536 emit_move_insn (operands[3], gen_rtx (REG, SImode, 4));
1537 DONE;
1538 }
1539 else
1540 FAIL;
1541
1542 if (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) < 0)
1543 {
1544 operands[2] = force_reg (SImode, operands[2]);
1545 label = gen_label_rtx ();
1546 emit (gen_udivmodsi4_tests (operands[0], operands[1], operands[2],
1547 operands[3], label));
1548 }
1549 else
1550 operands[2] = force_reg (SImode, operands[2]);
1551
1552 emit (gen_udivmodsi4_normal (operands[0], operands[1], operands[2],
1553 operands[3]));
1554 if (label)
1555 emit_label (label);
1556
1557 DONE;
1558 }")
1559
1560 ;; AIX architecture-independent common-mode multiply (DImode),
1561 ;; divide/modulus, and quotient subroutine calls. Input operands in R3 and
1562 ;; R4; results in R3 and sometimes R4; link register always clobbered by bla
1563 ;; instruction; R0 sometimes clobbered; also, MQ sometimes clobbered but
1564 ;; assumed unused if generating common-mode, so ignore.
1565 (define_insn "mulh_call"
1566 [(set (reg:SI 3)
1567 (truncate:SI
1568 (lshiftrt:DI (mult:DI (sign_extend:DI (reg:SI 3))
1569 (sign_extend:DI (reg:SI 4)))
1570 (const_int 32))))
1571 (clobber (match_scratch:SI 0 "=l"))]
1572 "! TARGET_POWER && ! TARGET_POWERPC"
1573 "bla __mulh")
1574
1575 (define_insn "mull_call"
1576 [(set (reg:DI 3)
1577 (mult:DI (sign_extend:DI (reg:SI 3))
1578 (sign_extend:DI (reg:SI 4))))
1579 (clobber (match_scratch:SI 0 "=l"))
1580 (clobber (reg:SI 0))]
1581 "! TARGET_POWER && ! TARGET_POWERPC"
1582 "bla __mull")
1583
1584 (define_insn "divss_call"
1585 [(set (reg:SI 3)
1586 (div:SI (reg:SI 3) (reg:SI 4)))
1587 (set (reg:SI 4)
1588 (mod:SI (reg:SI 3) (reg:SI 4)))
1589 (clobber (match_scratch:SI 0 "=l"))
1590 (clobber (reg:SI 0))]
1591 "! TARGET_POWER && ! TARGET_POWERPC"
1592 "bla __divss")
1593
1594 (define_insn "divus_call"
1595 [(set (reg:SI 3)
1596 (udiv:SI (reg:SI 3) (reg:SI 4)))
1597 (set (reg:SI 4)
1598 (umod:SI (reg:SI 3) (reg:SI 4)))
1599 (clobber (match_scratch:SI 0 "=l"))
1600 (clobber (reg:SI 0))
1601 (clobber (match_scratch:CC 1 "=x"))
1602 (clobber (reg:CC 69))]
1603 "! TARGET_POWER && ! TARGET_POWERPC"
1604 "bla __divus")
1605
1606 (define_insn "quoss_call"
1607 [(set (reg:SI 3)
1608 (div:SI (reg:SI 3) (reg:SI 4)))
1609 (clobber (match_scratch:SI 0 "=l"))]
1610 "! TARGET_POWER && ! TARGET_POWERPC"
1611 "bla __quoss")
1612
1613 (define_insn "quous_call"
1614 [(set (reg:SI 3)
1615 (udiv:SI (reg:SI 3) (reg:SI 4)))
1616 (clobber (match_scratch:SI 0 "=l"))
1617 (clobber (reg:SI 0))
1618 (clobber (match_scratch:CC 1 "=x"))
1619 (clobber (reg:CC 69))]
1620 "! TARGET_POWER && ! TARGET_POWERPC"
1621 "bla __quous")
1622 \f
1623 (define_insn "andsi3"
1624 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r")
1625 (and:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r")
1626 (match_operand:SI 2 "and_operand" "?r,L,K,J")))
1627 (clobber (match_scratch:CC 3 "=X,X,x,x"))]
1628 ""
1629 "@
1630 and %0,%1,%2
1631 {rlinm|rlwinm} %0,%1,0,%m2,%M2
1632 {andil.|andi.} %0,%1,%b2
1633 {andiu.|andis.} %0,%1,%u2")
1634
1635 (define_insn ""
1636 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,x")
1637 (compare:CC (and:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r")
1638 (match_operand:SI 2 "and_operand" "r,K,J,L"))
1639 (const_int 0)))
1640 (clobber (match_scratch:SI 3 "=r,r,r,r"))]
1641 ""
1642 "@
1643 and. %3,%1,%2
1644 {andil.|andi.} %3,%1,%b2
1645 {andiu.|andis.} %3,%1,%u2
1646 {rlinm.|rlwinm.} %3,%1,0,%m2,%M2"
1647 [(set_attr "type" "compare,compare,compare,delayed_compare")])
1648
1649 (define_insn ""
1650 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,x,x")
1651 (compare:CC (and:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r")
1652 (match_operand:SI 2 "and_operand" "r,K,J,L"))
1653 (const_int 0)))
1654 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r")
1655 (and:SI (match_dup 1) (match_dup 2)))]
1656 ""
1657 "@
1658 and. %0,%1,%2
1659 {andil.|andi.} %0,%1,%b2
1660 {andiu.|andis.} %0,%1,%u2
1661 {rlinm.|rlwinm.} %0,%1,0,%m2,%M2"
1662 [(set_attr "type" "compare,compare,compare,delayed_compare")])
1663
1664 ;; Take a AND with a constant that cannot be done in a single insn and try to
1665 ;; split it into two insns. This does not verify that the insns are valid
1666 ;; since this need not be done as combine will do it.
1667
1668 (define_split
1669 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1670 (and:SI (match_operand:SI 1 "gpc_reg_operand" "")
1671 (match_operand:SI 2 "non_and_cint_operand" "")))]
1672 ""
1673 [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 3)))
1674 (set (match_dup 0) (and:SI (match_dup 0) (match_dup 4)))]
1675 "
1676 {
1677 int maskval = INTVAL (operands[2]);
1678 int i, transitions, last_bit_value;
1679 int orig = maskval, first_c = maskval, second_c;
1680
1681 /* We know that MASKVAL must have more than 2 bit-transitions. Start at
1682 the low-order bit and count for the third transition. When we get there,
1683 make a first mask that has everything to the left of that position
1684 a one. Then make the second mask to turn off whatever else is needed. */
1685
1686 for (i = 1, transitions = 0, last_bit_value = maskval & 1; i < 32; i++)
1687 {
1688 if (((maskval >>= 1) & 1) != last_bit_value)
1689 last_bit_value ^= 1, transitions++;
1690
1691 if (transitions > 2)
1692 {
1693 first_c |= (~0) << i;
1694 break;
1695 }
1696 }
1697
1698 second_c = orig | ~ first_c;
1699
1700 operands[3] = gen_rtx (CONST_INT, VOIDmode, first_c);
1701 operands[4] = gen_rtx (CONST_INT, VOIDmode, second_c);
1702 }")
1703
1704 (define_insn "iorsi3"
1705 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r")
1706 (ior:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r")
1707 (match_operand:SI 2 "logical_operand" "r,K,J")))]
1708 ""
1709 "@
1710 or %0,%1,%2
1711 {oril|ori} %0,%1,%b2
1712 {oriu|oris} %0,%1,%u2")
1713
1714 (define_insn ""
1715 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1716 (compare:CC (ior:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1717 (match_operand:SI 2 "gpc_reg_operand" "r"))
1718 (const_int 0)))
1719 (clobber (match_scratch:SI 3 "=r"))]
1720 ""
1721 "or. %3,%1,%2"
1722 [(set_attr "type" "compare")])
1723
1724 (define_insn ""
1725 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1726 (compare:CC (ior:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1727 (match_operand:SI 2 "gpc_reg_operand" "r"))
1728 (const_int 0)))
1729 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1730 (ior:SI (match_dup 1) (match_dup 2)))]
1731 ""
1732 "or. %0,%1,%2"
1733 [(set_attr "type" "compare")])
1734
1735 ;; Split an IOR that we can't do in one insn into two insns, each of which
1736 ;; does one 16-bit part. This is used by combine.
1737
1738 (define_split
1739 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1740 (ior:SI (match_operand:SI 1 "gpc_reg_operand" "")
1741 (match_operand:SI 2 "non_logical_cint_operand" "")))]
1742 ""
1743 [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 3)))
1744 (set (match_dup 0) (ior:SI (match_dup 0) (match_dup 4)))]
1745 "
1746 {
1747 operands[3] = gen_rtx (CONST_INT, VOIDmode,
1748 INTVAL (operands[2]) & 0xffff0000);
1749 operands[4] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) & 0xffff);
1750 }")
1751
1752 (define_insn "xorsi3"
1753 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r")
1754 (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r")
1755 (match_operand:SI 2 "logical_operand" "r,K,J")))]
1756 ""
1757 "@
1758 xor %0,%1,%2
1759 {xoril|xori} %0,%1,%b2
1760 {xoriu|xoris} %0,%1,%u2")
1761
1762 (define_insn ""
1763 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1764 (compare:CC (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1765 (match_operand:SI 2 "gpc_reg_operand" "r"))
1766 (const_int 0)))
1767 (clobber (match_scratch:SI 3 "=r"))]
1768 ""
1769 "xor. %3,%1,%2"
1770 [(set_attr "type" "compare")])
1771
1772 (define_insn ""
1773 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1774 (compare:CC (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1775 (match_operand:SI 2 "gpc_reg_operand" "r"))
1776 (const_int 0)))
1777 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1778 (xor:SI (match_dup 1) (match_dup 2)))]
1779 ""
1780 "xor. %0,%1,%2"
1781 [(set_attr "type" "compare")])
1782
1783 ;; Split an XOR that we can't do in one insn into two insns, each of which
1784 ;; does one 16-bit part. This is used by combine.
1785
1786 (define_split
1787 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1788 (xor:SI (match_operand:SI 1 "gpc_reg_operand" "")
1789 (match_operand:SI 2 "non_logical_cint_operand" "")))]
1790 ""
1791 [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 3)))
1792 (set (match_dup 0) (xor:SI (match_dup 0) (match_dup 4)))]
1793 "
1794 {
1795 operands[3] = gen_rtx (CONST_INT, VOIDmode,
1796 INTVAL (operands[2]) & 0xffff0000);
1797 operands[4] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) & 0xffff);
1798 }")
1799
1800 (define_insn ""
1801 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1802 (not:SI (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1803 (match_operand:SI 2 "gpc_reg_operand" "r"))))]
1804 ""
1805 "eqv %0,%1,%2")
1806
1807 (define_insn ""
1808 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1809 (compare:CC (not:SI (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1810 (match_operand:SI 2 "gpc_reg_operand" "r")))
1811 (const_int 0)))
1812 (clobber (match_scratch:SI 3 "=r"))]
1813 ""
1814 "eqv. %3,%1,%2"
1815 [(set_attr "type" "compare")])
1816
1817 (define_insn ""
1818 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1819 (compare:CC (not:SI (xor:SI (match_operand:SI 1 "gpc_reg_operand" "%r")
1820 (match_operand:SI 2 "gpc_reg_operand" "r")))
1821 (const_int 0)))
1822 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1823 (not:SI (xor:SI (match_dup 1) (match_dup 2))))]
1824 ""
1825 "eqv. %0,%1,%2"
1826 [(set_attr "type" "compare")])
1827
1828 (define_insn ""
1829 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1830 (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1831 (match_operand:SI 2 "gpc_reg_operand" "r")))]
1832 ""
1833 "andc %0,%2,%1")
1834
1835 (define_insn ""
1836 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1837 (compare:CC (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1838 (match_operand:SI 2 "gpc_reg_operand" "r"))
1839 (const_int 0)))
1840 (clobber (match_scratch:SI 3 "=r"))]
1841 ""
1842 "andc. %3,%2,%1"
1843 [(set_attr "type" "compare")])
1844
1845 (define_insn ""
1846 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1847 (compare:CC (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1848 (match_operand:SI 2 "gpc_reg_operand" "r"))
1849 (const_int 0)))
1850 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1851 (and:SI (not:SI (match_dup 1)) (match_dup 2)))]
1852 ""
1853 "andc. %0,%2,%1"
1854 [(set_attr "type" "compare")])
1855
1856 (define_insn ""
1857 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1858 (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1859 (match_operand:SI 2 "gpc_reg_operand" "r")))]
1860 ""
1861 "orc %0,%2,%1")
1862
1863 (define_insn ""
1864 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1865 (compare:CC (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1866 (match_operand:SI 2 "gpc_reg_operand" "r"))
1867 (const_int 0)))
1868 (clobber (match_scratch:SI 3 "=r"))]
1869 ""
1870 "orc. %3,%2,%1"
1871 [(set_attr "type" "compare")])
1872
1873 (define_insn ""
1874 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1875 (compare:CC (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
1876 (match_operand:SI 2 "gpc_reg_operand" "r"))
1877 (const_int 0)))
1878 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1879 (ior:SI (not:SI (match_dup 1)) (match_dup 2)))]
1880 ""
1881 "orc. %0,%2,%1"
1882 [(set_attr "type" "compare")])
1883
1884 (define_insn ""
1885 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1886 (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1887 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))))]
1888 ""
1889 "nand %0,%1,%2")
1890
1891 (define_insn ""
1892 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1893 (compare:CC (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1894 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r")))
1895 (const_int 0)))
1896 (clobber (match_scratch:SI 3 "=r"))]
1897 ""
1898 "nand. %3,%1,%2"
1899 [(set_attr "type" "compare")])
1900
1901 (define_insn ""
1902 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1903 (compare:CC (ior:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1904 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r")))
1905 (const_int 0)))
1906 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1907 (ior:SI (not:SI (match_dup 1)) (not:SI (match_dup 2))))]
1908 ""
1909 "nand. %0,%1,%2"
1910 [(set_attr "type" "compare")])
1911
1912 (define_insn ""
1913 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1914 (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1915 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))))]
1916 ""
1917 "nor %0,%1,%2")
1918
1919 (define_insn ""
1920 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
1921 (compare:CC (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1922 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r")))
1923 (const_int 0)))
1924 (clobber (match_scratch:SI 3 "=r"))]
1925 ""
1926 "nor. %3,%1,%2"
1927 [(set_attr "type" "compare")])
1928
1929 (define_insn ""
1930 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1931 (compare:CC (and:SI (not:SI (match_operand:SI 1 "gpc_reg_operand" "%r"))
1932 (not:SI (match_operand:SI 2 "gpc_reg_operand" "r")))
1933 (const_int 0)))
1934 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1935 (and:SI (not:SI (match_dup 1)) (not:SI (match_dup 2))))]
1936 ""
1937 "nor. %0,%1,%2"
1938 [(set_attr "type" "compare")])
1939
1940 ;; maskir insn. We need four forms because things might be in arbitrary
1941 ;; orders. Don't define forms that only set CR fields because these
1942 ;; would modify an input register.
1943
1944 (define_insn ""
1945 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1946 (ior:SI (and:SI (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))
1947 (match_operand:SI 1 "gpc_reg_operand" "0"))
1948 (and:SI (match_dup 2)
1949 (match_operand:SI 3 "gpc_reg_operand" "r"))))]
1950 "TARGET_POWER"
1951 "maskir %0,%3,%2")
1952
1953 (define_insn ""
1954 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1955 (ior:SI (and:SI (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))
1956 (match_operand:SI 1 "gpc_reg_operand" "0"))
1957 (and:SI (match_operand:SI 3 "gpc_reg_operand" "r")
1958 (match_dup 2))))]
1959 "TARGET_POWER"
1960 "maskir %0,%3,%2")
1961
1962 (define_insn ""
1963 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1964 (ior:SI (and:SI (match_operand:SI 2 "gpc_reg_operand" "r")
1965 (match_operand:SI 3 "gpc_reg_operand" "r"))
1966 (and:SI (not:SI (match_dup 2))
1967 (match_operand:SI 1 "gpc_reg_operand" "0"))))]
1968 "TARGET_POWER"
1969 "maskir %0,%3,%2")
1970
1971 (define_insn ""
1972 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1973 (ior:SI (and:SI (match_operand:SI 3 "gpc_reg_operand" "r")
1974 (match_operand:SI 2 "gpc_reg_operand" "r"))
1975 (and:SI (not:SI (match_dup 2))
1976 (match_operand:SI 1 "gpc_reg_operand" "0"))))]
1977 "TARGET_POWER"
1978 "maskir %0,%3,%2")
1979
1980 (define_insn ""
1981 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
1982 (compare:CC
1983 (ior:SI (and:SI (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))
1984 (match_operand:SI 1 "gpc_reg_operand" "0"))
1985 (and:SI (match_dup 2)
1986 (match_operand:SI 3 "gpc_reg_operand" "r")))
1987 (const_int 0)))
1988 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1989 (ior:SI (and:SI (not:SI (match_dup 2)) (match_dup 1))
1990 (and:SI (match_dup 2) (match_dup 3))))]
1991 "TARGET_POWER"
1992 "maskir. %0,%3,%2"
1993 [(set_attr "type" "compare")])
1994
1995 (define_insn ""
1996 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
1997 (compare:CC
1998 (ior:SI (and:SI (not:SI (match_operand:SI 2 "gpc_reg_operand" "r"))
1999 (match_operand:SI 1 "gpc_reg_operand" "0"))
2000 (and:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2001 (match_dup 2)))
2002 (const_int 0)))
2003 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2004 (ior:SI (and:SI (not:SI (match_dup 2)) (match_dup 1))
2005 (and:SI (match_dup 3) (match_dup 2))))]
2006 "TARGET_POWER"
2007 "maskir. %0,%3,%2"
2008 [(set_attr "type" "compare")])
2009
2010 (define_insn ""
2011 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2012 (compare:CC
2013 (ior:SI (and:SI (match_operand:SI 2 "gpc_reg_operand" "r")
2014 (match_operand:SI 3 "gpc_reg_operand" "r"))
2015 (and:SI (not:SI (match_dup 2))
2016 (match_operand:SI 1 "gpc_reg_operand" "0")))
2017 (const_int 0)))
2018 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2019 (ior:SI (and:SI (match_dup 2) (match_dup 3))
2020 (and:SI (not:SI (match_dup 2)) (match_dup 1))))]
2021 "TARGET_POWER"
2022 "maskir. %0,%3,%2"
2023 [(set_attr "type" "compare")])
2024
2025 (define_insn ""
2026 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2027 (compare:CC
2028 (ior:SI (and:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2029 (match_operand:SI 2 "gpc_reg_operand" "r"))
2030 (and:SI (not:SI (match_dup 2))
2031 (match_operand:SI 1 "gpc_reg_operand" "0")))
2032 (const_int 0)))
2033 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2034 (ior:SI (and:SI (match_dup 3) (match_dup 2))
2035 (and:SI (not:SI (match_dup 2)) (match_dup 1))))]
2036 "TARGET_POWER"
2037 "maskir. %0,%3,%2"
2038 [(set_attr "type" "compare")])
2039 \f
2040 ;; Rotate and shift insns, in all their variants. These support shifts,
2041 ;; field inserts and extracts, and various combinations thereof.
2042 (define_expand "insv"
2043 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2044 (match_operand:SI 1 "const_int_operand" "i")
2045 (match_operand:SI 2 "const_int_operand" "i"))
2046 (match_operand:SI 3 "gpc_reg_operand" "r"))]
2047 ""
2048 "
2049 {
2050 /* Do not handle 16/8 bit structures that fit in HI/QI modes directly, since
2051 the (SUBREG:SI (REG:HI xxx)) that is otherwise generated can confuse the
2052 compiler if the address of the structure is taken later. */
2053 if (GET_CODE (operands[0]) == SUBREG
2054 && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD))
2055 FAIL;
2056 }")
2057
2058 (define_insn ""
2059 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2060 (match_operand:SI 1 "const_int_operand" "i")
2061 (match_operand:SI 2 "const_int_operand" "i"))
2062 (match_operand:SI 3 "gpc_reg_operand" "r"))]
2063 ""
2064 "*
2065 {
2066 int start = INTVAL (operands[2]) & 31;
2067 int size = INTVAL (operands[1]) & 31;
2068
2069 operands[4] = gen_rtx (CONST_INT, VOIDmode, 32 - start - size);
2070 operands[1] = gen_rtx (CONST_INT, VOIDmode, start + size - 1);
2071 return \"{rlimi|rlwimi} %0,%3,%h4,%h2,%h1\";
2072 }")
2073
2074 (define_insn ""
2075 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2076 (match_operand:SI 1 "const_int_operand" "i")
2077 (match_operand:SI 2 "const_int_operand" "i"))
2078 (ashift:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2079 (match_operand:SI 4 "const_int_operand" "i")))]
2080 ""
2081 "*
2082 {
2083 int shift = INTVAL (operands[4]) & 31;
2084 int start = INTVAL (operands[2]) & 31;
2085 int size = INTVAL (operands[1]) & 31;
2086
2087 operands[4] = gen_rtx (CONST_INT, VOIDmode, shift - start - size);
2088 operands[1] = gen_rtx (CONST_INT, VOIDmode, start + size - 1);
2089 return \"{rlimi|rlwimi} %0,%3,%h4,%h2,%h1\";
2090 }")
2091
2092 (define_insn ""
2093 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2094 (match_operand:SI 1 "const_int_operand" "i")
2095 (match_operand:SI 2 "const_int_operand" "i"))
2096 (ashiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2097 (match_operand:SI 4 "const_int_operand" "i")))]
2098 ""
2099 "*
2100 {
2101 int shift = INTVAL (operands[4]) & 31;
2102 int start = INTVAL (operands[2]) & 31;
2103 int size = INTVAL (operands[1]) & 31;
2104
2105 operands[4] = gen_rtx (CONST_INT, VOIDmode, 32 - shift - start - size);
2106 operands[1] = gen_rtx (CONST_INT, VOIDmode, start + size - 1);
2107 return \"{rlimi|rlwimi} %0,%3,%h4,%h2,%h1\";
2108 }")
2109
2110 (define_insn ""
2111 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2112 (match_operand:SI 1 "const_int_operand" "i")
2113 (match_operand:SI 2 "const_int_operand" "i"))
2114 (lshiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2115 (match_operand:SI 4 "const_int_operand" "i")))]
2116 ""
2117 "*
2118 {
2119 int shift = INTVAL (operands[4]) & 31;
2120 int start = INTVAL (operands[2]) & 31;
2121 int size = INTVAL (operands[1]) & 31;
2122
2123 operands[4] = gen_rtx (CONST_INT, VOIDmode, 32 - shift - start - size);
2124 operands[1] = gen_rtx (CONST_INT, VOIDmode, start + size - 1);
2125 return \"{rlimi|rlwimi} %0,%3,%h4,%h2,%h1\";
2126 }")
2127
2128 (define_insn ""
2129 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2130 (match_operand:SI 1 "const_int_operand" "i")
2131 (match_operand:SI 2 "const_int_operand" "i"))
2132 (zero_extract:SI (match_operand:SI 3 "gpc_reg_operand" "r")
2133 (match_operand:SI 4 "const_int_operand" "i")
2134 (match_operand:SI 5 "const_int_operand" "i")))]
2135 "INTVAL (operands[4]) >= INTVAL (operands[1])"
2136 "*
2137 {
2138 int extract_start = INTVAL (operands[5]) & 31;
2139 int extract_size = INTVAL (operands[4]) & 31;
2140 int insert_start = INTVAL (operands[2]) & 31;
2141 int insert_size = INTVAL (operands[1]) & 31;
2142
2143 /* Align extract field with insert field */
2144 operands[5] = gen_rtx (CONST_INT, VOIDmode,
2145 extract_start + extract_size - insert_start - insert_size);
2146 operands[1] = gen_rtx (CONST_INT, VOIDmode, insert_start + insert_size - 1);
2147 return \"{rlimi|rlwimi} %0,%3,%h5,%h2,%h1\";
2148 }")
2149
2150 (define_insn ""
2151 [(set (zero_extract:DI (match_operand:DI 0 "gpc_reg_operand" "+r")
2152 (match_operand:DI 1 "const_int_operand" "i")
2153 (match_operand:DI 2 "const_int_operand" "i"))
2154 (match_operand:DI 3 "gpc_reg_operand" "r"))]
2155 "TARGET_POWERPC64"
2156 "*
2157 {
2158 int start = INTVAL (operands[2]) & 63;
2159 int size = INTVAL (operands[1]) & 63;
2160
2161 operands[2] = gen_rtx (CONST_INT, VOIDmode, 64 - start - size);
2162 return \"rldimi %0,%3,%H2,%H1\";
2163 }")
2164
2165 (define_expand "extzv"
2166 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2167 (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2168 (match_operand:SI 2 "const_int_operand" "i")
2169 (match_operand:SI 3 "const_int_operand" "i")))]
2170 ""
2171 "
2172 {
2173 /* Do not handle 16/8 bit structures that fit in HI/QI modes directly, since
2174 the (SUBREG:SI (REG:HI xxx)) that is otherwise generated can confuse the
2175 compiler if the address of the structure is taken later. */
2176 if (GET_CODE (operands[0]) == SUBREG
2177 && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD))
2178 FAIL;
2179 }")
2180
2181 (define_insn ""
2182 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2183 (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2184 (match_operand:SI 2 "const_int_operand" "i")
2185 (match_operand:SI 3 "const_int_operand" "i")))]
2186 ""
2187 "*
2188 {
2189 int start = INTVAL (operands[3]) & 31;
2190 int size = INTVAL (operands[2]) & 31;
2191
2192 if (start + size >= 32)
2193 operands[3] = const0_rtx;
2194 else
2195 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2196 return \"{rlinm|rlwinm} %0,%1,%3,%s2,31\";
2197 }")
2198
2199 (define_insn ""
2200 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2201 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2202 (match_operand:SI 2 "const_int_operand" "i")
2203 (match_operand:SI 3 "const_int_operand" "i"))
2204 (const_int 0)))
2205 (clobber (match_scratch:SI 4 "=r"))]
2206 ""
2207 "*
2208 {
2209 int start = INTVAL (operands[3]) & 31;
2210 int size = INTVAL (operands[2]) & 31;
2211
2212 /* If the bitfield being tested fits in the upper or lower half of a
2213 word, it is possible to use andiu. or andil. to test it. This is
2214 useful because the condition register set-use delay is smaller for
2215 andi[ul]. than for rlinm. This doesn't work when the starting bit
2216 position is 0 because the LT and GT bits may be set wrong. */
2217
2218 if ((start > 0 && start + size <= 16) || start >= 16)
2219 {
2220 operands[3] = gen_rtx (CONST_INT, VOIDmode,
2221 ((1 << (16 - (start & 15)))
2222 - (1 << (16 - (start & 15) - size))));
2223 if (start < 16)
2224 return \"{andiu.|andis.} %4,%1,%3\";
2225 else
2226 return \"{andil.|andi.} %4,%1,%3\";
2227 }
2228
2229 if (start + size >= 32)
2230 operands[3] = const0_rtx;
2231 else
2232 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2233 return \"{rlinm.|rlwinm.} %4,%1,%3,%s2,31\";
2234 }"
2235 [(set_attr "type" "compare")])
2236
2237 (define_insn ""
2238 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2239 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2240 (match_operand:SI 2 "const_int_operand" "i")
2241 (match_operand:SI 3 "const_int_operand" "i"))
2242 (const_int 0)))
2243 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2244 (zero_extract:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
2245 ""
2246 "*
2247 {
2248 int start = INTVAL (operands[3]) & 31;
2249 int size = INTVAL (operands[2]) & 31;
2250
2251 if (start >= 16 && start + size == 32)
2252 {
2253 operands[3] = gen_rtx (CONST_INT, VOIDmode, (1 << (32 - start)) - 1);
2254 return \"{andil.|andi.} %0,%1,%3\";
2255 }
2256
2257 if (start + size >= 32)
2258 operands[3] = const0_rtx;
2259 else
2260 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2261 return \"{rlinm.|rlwinm.} %0,%1,%3,%s2,31\";
2262 }"
2263 [(set_attr "type" "delayed_compare")])
2264
2265 (define_insn ""
2266 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
2267 (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
2268 (match_operand:DI 2 "const_int_operand" "i")
2269 (match_operand:DI 3 "const_int_operand" "i")))]
2270 "TARGET_POWERPC64"
2271 "*
2272 {
2273 int start = INTVAL (operands[3]) & 63;
2274 int size = INTVAL (operands[2]) & 63;
2275
2276 if (start + size >= 64)
2277 operands[3] = const0_rtx;
2278 else
2279 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2280 operands[2] = gen_rtx (CONST_INT, VOIDmode, 64 - size);
2281 return \"rldicl %0,%1,%3,%2\";
2282 }")
2283
2284 (define_insn ""
2285 [(set (match_operand:CC 0 "gpc_reg_operand" "=x")
2286 (compare:CC (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
2287 (match_operand:DI 2 "const_int_operand" "i")
2288 (match_operand:DI 3 "const_int_operand" "i"))
2289 (const_int 0)))
2290 (clobber (match_scratch:DI 4 "=r"))]
2291 "TARGET_POWERPC64"
2292 "*
2293 {
2294 int start = INTVAL (operands[3]) & 63;
2295 int size = INTVAL (operands[2]) & 63;
2296
2297 if (start + size >= 64)
2298 operands[3] = const0_rtx;
2299 else
2300 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2301 operands[2] = gen_rtx (CONST_INT, VOIDmode, 64 - size);
2302 return \"rldicl. %4,%1,%3,%2\";
2303 }")
2304
2305 (define_insn ""
2306 [(set (match_operand:CC 4 "gpc_reg_operand" "=x")
2307 (compare:CC (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
2308 (match_operand:DI 2 "const_int_operand" "i")
2309 (match_operand:DI 3 "const_int_operand" "i"))
2310 (const_int 0)))
2311 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
2312 (zero_extract:DI (match_dup 1) (match_dup 2) (match_dup 3)))]
2313 "TARGET_POWERPC64"
2314 "*
2315 {
2316 int start = INTVAL (operands[3]) & 63;
2317 int size = INTVAL (operands[2]) & 63;
2318
2319 if (start + size >= 64)
2320 operands[3] = const0_rtx;
2321 else
2322 operands[3] = gen_rtx (CONST_INT, VOIDmode, start + size);
2323 operands[2] = gen_rtx (CONST_INT, VOIDmode, 64 - size);
2324 return \"rldicl. %0,%1,%3,%2\";
2325 }")
2326
2327 (define_insn "rotlsi3"
2328 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2329 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2330 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
2331 ""
2332 "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xffffffff")
2333
2334 (define_insn ""
2335 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2336 (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2337 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2338 (const_int 0)))
2339 (clobber (match_scratch:SI 3 "=r"))]
2340 ""
2341 "{rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xffffffff"
2342 [(set_attr "type" "delayed_compare")])
2343
2344 (define_insn ""
2345 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2346 (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2347 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2348 (const_int 0)))
2349 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2350 (rotate:SI (match_dup 1) (match_dup 2)))]
2351 ""
2352 "{rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xffffffff"
2353 [(set_attr "type" "delayed_compare")])
2354
2355 (define_insn ""
2356 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2357 (and:SI (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2358 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2359 (match_operand:SI 3 "mask_operand" "L")))]
2360 ""
2361 "{rl%I2nm|rlw%I2nm} %0,%1,%h2,%m3,%M3")
2362
2363 (define_insn ""
2364 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2365 (compare:CC (and:SI
2366 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2367 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2368 (match_operand:SI 3 "mask_operand" "L"))
2369 (const_int 0)))
2370 (clobber (match_scratch:SI 4 "=r"))]
2371 ""
2372 "{rl%I2nm.|rlw%I2nm.} %4,%1,%h2,%m3,%M3"
2373 [(set_attr "type" "delayed_compare")])
2374
2375 (define_insn ""
2376 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2377 (compare:CC (and:SI
2378 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2379 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2380 (match_operand:SI 3 "mask_operand" "L"))
2381 (const_int 0)))
2382 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2383 (and:SI (rotate:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
2384 ""
2385 "{rl%I2nm.|rlw%I2nm.} %0,%1,%h2,%m3,%M3"
2386 [(set_attr "type" "delayed_compare")])
2387
2388 (define_insn ""
2389 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2390 (zero_extend:SI
2391 (subreg:QI
2392 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2393 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0)))]
2394 ""
2395 "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xff")
2396
2397 (define_insn ""
2398 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2399 (compare:CC (zero_extend:SI
2400 (subreg:QI
2401 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2402 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0))
2403 (const_int 0)))
2404 (clobber (match_scratch:SI 3 "=r"))]
2405 ""
2406 "{rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xff"
2407 [(set_attr "type" "delayed_compare")])
2408
2409 (define_insn ""
2410 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2411 (compare:CC (zero_extend:SI
2412 (subreg:QI
2413 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2414 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0))
2415 (const_int 0)))
2416 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2417 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
2418 ""
2419 "{rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xff"
2420 [(set_attr "type" "delayed_compare")])
2421
2422 (define_insn ""
2423 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2424 (zero_extend:SI
2425 (subreg:HI
2426 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2427 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0)))]
2428 ""
2429 "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xffff")
2430
2431 (define_insn ""
2432 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2433 (compare:CC (zero_extend:SI
2434 (subreg:HI
2435 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2436 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0))
2437 (const_int 0)))
2438 (clobber (match_scratch:SI 3 "=r"))]
2439 ""
2440 "{rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xffff"
2441 [(set_attr "type" "delayed_compare")])
2442
2443 (define_insn ""
2444 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2445 (compare:CC (zero_extend:SI
2446 (subreg:HI
2447 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2448 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0))
2449 (const_int 0)))
2450 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2451 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
2452 ""
2453 "{rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xffff"
2454 [(set_attr "type" "delayed_compare")])
2455
2456 ;; Note that we use "sle." instead of "sl." so that we can set
2457 ;; SHIFT_COUNT_TRUNCATED.
2458
2459 (define_expand "ashlsi3"
2460 [(use (match_operand:SI 0 "gpc_reg_operand" ""))
2461 (use (match_operand:SI 1 "gpc_reg_operand" ""))
2462 (use (match_operand:SI 2 "reg_or_cint_operand" ""))]
2463 ""
2464 "
2465 {
2466 if (TARGET_POWER)
2467 emit_insn (gen_ashlsi3_power (operands[0], operands[1], operands[2]));
2468 else
2469 emit_insn (gen_ashlsi3_no_power (operands[0], operands[1], operands[2]));
2470 DONE;
2471 }")
2472
2473 (define_insn "ashlsi3_power"
2474 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2475 (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2476 (match_operand:SI 2 "reg_or_cint_operand" "r,i")))
2477 (clobber (match_scratch:SI 3 "=q,X"))]
2478 "TARGET_POWER"
2479 "@
2480 sle %0,%1,%2
2481 {sli|slwi} %0,%1,%h2"
2482 [(set_attr "length" "8")])
2483
2484 (define_insn "ashlsi3_no_power"
2485 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2486 (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2487 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
2488 "! TARGET_POWER"
2489 "{sl|slw}%I2 %0,%1,%h2"
2490 [(set_attr "length" "8")])
2491
2492 (define_insn ""
2493 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
2494 (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2495 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2496 (const_int 0)))
2497 (clobber (match_scratch:SI 3 "=r,r"))
2498 (clobber (match_scratch:SI 4 "=q,X"))]
2499 "TARGET_POWER"
2500 "@
2501 sle. %3,%1,%2
2502 {sli.|slwi.} %3,%1,%h2"
2503 [(set_attr "type" "delayed_compare")])
2504
2505 (define_insn ""
2506 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2507 (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2508 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2509 (const_int 0)))
2510 (clobber (match_scratch:SI 3 "=r"))]
2511 "! TARGET_POWER"
2512 "{sl|slw}%I2. %3,%1,%h2"
2513 [(set_attr "type" "delayed_compare")])
2514
2515 (define_insn ""
2516 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
2517 (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2518 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2519 (const_int 0)))
2520 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2521 (ashift:SI (match_dup 1) (match_dup 2)))
2522 (clobber (match_scratch:SI 4 "=q,X"))]
2523 "TARGET_POWER"
2524 "@
2525 sle. %0,%1,%2
2526 {sli.|slwi.} %0,%1,%h2"
2527 [(set_attr "type" "delayed_compare")])
2528
2529 (define_insn ""
2530 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2531 (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2532 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2533 (const_int 0)))
2534 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2535 (ashift:SI (match_dup 1) (match_dup 2)))]
2536 "! TARGET_POWER"
2537 "{sl|slw}%I2. %0,%1,%h2"
2538 [(set_attr "type" "delayed_compare")])
2539
2540 (define_insn ""
2541 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2542 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2543 (match_operand:SI 2 "const_int_operand" "i"))
2544 (match_operand:SI 3 "mask_operand" "L")))]
2545 "includes_lshift_p (operands[2], operands[3])"
2546 "{rlinm|rlwinm} %0,%1,%h2,%m3,%M3")
2547
2548 (define_insn ""
2549 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2550 (compare:CC
2551 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2552 (match_operand:SI 2 "const_int_operand" "i"))
2553 (match_operand:SI 3 "mask_operand" "L"))
2554 (const_int 0)))
2555 (clobber (match_scratch:SI 4 "=r"))]
2556 "includes_lshift_p (operands[2], operands[3])"
2557 "{rlinm.|rlwinm.} %4,%1,%h2,%m3,%M3"
2558 [(set_attr "type" "delayed_compare")])
2559
2560 (define_insn ""
2561 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2562 (compare:CC
2563 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2564 (match_operand:SI 2 "const_int_operand" "i"))
2565 (match_operand:SI 3 "mask_operand" "L"))
2566 (const_int 0)))
2567 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2568 (and:SI (ashift:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
2569 "includes_lshift_p (operands[2], operands[3])"
2570 "{rlinm.|rlwinm.} %0,%1,%h2,%m3,%M3"
2571 [(set_attr "type" "delayed_compare")])
2572
2573 ;; The AIX assembler mis-handles "sri x,x,0", so write that case as
2574 ;; "sli x,x,0".
2575 (define_expand "lshrsi3"
2576 [(use (match_operand:SI 0 "gpc_reg_operand" ""))
2577 (use (match_operand:SI 1 "gpc_reg_operand" ""))
2578 (use (match_operand:SI 2 "reg_or_cint_operand" ""))]
2579 ""
2580 "
2581 {
2582 if (TARGET_POWER)
2583 emit_insn (gen_lshrsi3_power (operands[0], operands[1], operands[2]));
2584 else
2585 emit_insn (gen_lshrsi3_no_power (operands[0], operands[1], operands[2]));
2586 DONE;
2587 }")
2588
2589 (define_insn "lshrsi3_power"
2590 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2591 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2592 (match_operand:SI 2 "reg_or_cint_operand" "r,i")))
2593 (clobber (match_scratch:SI 3 "=q,X"))]
2594 "TARGET_POWER"
2595 "@
2596 sre %0,%1,%2
2597 {s%A2i|s%A2wi} %0,%1,%h2")
2598
2599 (define_insn "lshrsi3_no_power"
2600 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2601 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2602 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
2603 "! TARGET_POWER"
2604 "{sr|srw}%I2 %0,%1,%h2")
2605
2606 (define_insn ""
2607 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
2608 (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2609 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2610 (const_int 0)))
2611 (clobber (match_scratch:SI 3 "=r,r"))
2612 (clobber (match_scratch:SI 4 "=q,X"))]
2613 "TARGET_POWER"
2614 "@
2615 sre. %3,%1,%2
2616 {s%A2i.|s%A2wi.} %3,%1,%h2"
2617 [(set_attr "type" "delayed_compare")])
2618
2619 (define_insn ""
2620 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2621 (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2622 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2623 (const_int 0)))
2624 (clobber (match_scratch:SI 3 "=r"))]
2625 "! TARGET_POWER"
2626 "{sr|srw}%I2. %3,%1,%h2"
2627 [(set_attr "type" "delayed_compare")])
2628
2629 (define_insn ""
2630 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
2631 (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2632 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2633 (const_int 0)))
2634 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2635 (lshiftrt:SI (match_dup 1) (match_dup 2)))
2636 (clobber (match_scratch:SI 4 "=q,X"))]
2637 "TARGET_POWER"
2638 "@
2639 sre. %0,%1,%2
2640 {s%A2i.|s%A2wi.} %0,%1,%h2"
2641 [(set_attr "type" "delayed_compare")])
2642
2643 (define_insn ""
2644 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2645 (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2646 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2647 (const_int 0)))
2648 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2649 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
2650 "! TARGET_POWER"
2651 "{sr|srw}%I2. %0,%1,%h2"
2652 [(set_attr "type" "delayed_compare")])
2653
2654 (define_insn ""
2655 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2656 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2657 (match_operand:SI 2 "const_int_operand" "i"))
2658 (match_operand:SI 3 "mask_operand" "L")))]
2659 "includes_rshift_p (operands[2], operands[3])"
2660 "{rlinm|rlwinm} %0,%1,%s2,%m3,%M3")
2661
2662 (define_insn ""
2663 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2664 (compare:CC
2665 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2666 (match_operand:SI 2 "const_int_operand" "i"))
2667 (match_operand:SI 3 "mask_operand" "L"))
2668 (const_int 0)))
2669 (clobber (match_scratch:SI 4 "=r"))]
2670 "includes_rshift_p (operands[2], operands[3])"
2671 "{rlinm.|rlwinm.} %4,%1,%s2,%m3,%M3"
2672 [(set_attr "type" "delayed_compare")])
2673
2674 (define_insn ""
2675 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
2676 (compare:CC
2677 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2678 (match_operand:SI 2 "const_int_operand" "i"))
2679 (match_operand:SI 3 "mask_operand" "L"))
2680 (const_int 0)))
2681 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2682 (and:SI (lshiftrt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
2683 "includes_rshift_p (operands[2], operands[3])"
2684 "{rlinm.|rlwinm.} %0,%1,%s2,%m3,%M3"
2685 [(set_attr "type" "delayed_compare")])
2686
2687 (define_insn ""
2688 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2689 (zero_extend:SI
2690 (subreg:QI
2691 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2692 (match_operand:SI 2 "const_int_operand" "i")) 0)))]
2693 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 255))"
2694 "{rlinm|rlwinm} %0,%1,%s2,0xff")
2695
2696 (define_insn ""
2697 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2698 (compare:CC
2699 (zero_extend:SI
2700 (subreg:QI
2701 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2702 (match_operand:SI 2 "const_int_operand" "i")) 0))
2703 (const_int 0)))
2704 (clobber (match_scratch:SI 3 "=r"))]
2705 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 255))"
2706 "{rlinm.|rlwinm.} %3,%1,%s2,0xff"
2707 [(set_attr "type" "delayed_compare")])
2708
2709 (define_insn ""
2710 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2711 (compare:CC
2712 (zero_extend:SI
2713 (subreg:QI
2714 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2715 (match_operand:SI 2 "const_int_operand" "i")) 0))
2716 (const_int 0)))
2717 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2718 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
2719 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 255))"
2720 "{rlinm.|rlwinm.} %0,%1,%s2,0xff"
2721 [(set_attr "type" "delayed_compare")])
2722
2723 (define_insn ""
2724 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2725 (zero_extend:SI
2726 (subreg:HI
2727 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2728 (match_operand:SI 2 "const_int_operand" "i")) 0)))]
2729 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 65535))"
2730 "{rlinm|rlwinm} %0,%1,%s2,0xffff")
2731
2732 (define_insn ""
2733 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2734 (compare:CC
2735 (zero_extend:SI
2736 (subreg:HI
2737 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2738 (match_operand:SI 2 "const_int_operand" "i")) 0))
2739 (const_int 0)))
2740 (clobber (match_scratch:SI 3 "=r"))]
2741 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 65535))"
2742 "{rlinm.|rlwinm.} %3,%1,%s2,0xffff"
2743 [(set_attr "type" "delayed_compare")])
2744
2745 (define_insn ""
2746 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2747 (compare:CC
2748 (zero_extend:SI
2749 (subreg:HI
2750 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2751 (match_operand:SI 2 "const_int_operand" "i")) 0))
2752 (const_int 0)))
2753 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2754 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
2755 "includes_rshift_p (operands[2], gen_rtx (CONST_INT, VOIDmode, 65535))"
2756 "{rlinm.|rlwinm.} %0,%1,%s2,0xffff"
2757 [(set_attr "type" "delayed_compare")])
2758
2759 (define_insn ""
2760 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2761 (const_int 1)
2762 (match_operand:SI 1 "gpc_reg_operand" "r"))
2763 (ashiftrt:SI (match_operand:SI 2 "gpc_reg_operand" "r")
2764 (const_int 31)))]
2765 "TARGET_POWER"
2766 "rrib %0,%1,%2")
2767
2768 (define_insn ""
2769 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2770 (const_int 1)
2771 (match_operand:SI 1 "gpc_reg_operand" "r"))
2772 (lshiftrt:SI (match_operand:SI 2 "gpc_reg_operand" "r")
2773 (const_int 31)))]
2774 "TARGET_POWER"
2775 "rrib %0,%1,%2")
2776
2777 (define_insn ""
2778 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
2779 (const_int 1)
2780 (match_operand:SI 1 "gpc_reg_operand" "r"))
2781 (zero_extract:SI (match_operand:SI 2 "gpc_reg_operand" "r")
2782 (const_int 1)
2783 (const_int 0)))]
2784 "TARGET_POWER"
2785 "rrib %0,%1,%2")
2786
2787 (define_expand "ashrsi3"
2788 [(set (match_operand:SI 0 "gpc_reg_operand" "")
2789 (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
2790 (match_operand:SI 2 "reg_or_cint_operand" "")))]
2791 ""
2792 "
2793 {
2794 if (TARGET_POWER)
2795 emit_insn (gen_ashrsi3_power (operands[0], operands[1], operands[2]));
2796 else
2797 emit_insn (gen_ashrsi3_no_power (operands[0], operands[1], operands[2]));
2798 DONE;
2799 }")
2800
2801 (define_insn "ashrsi3_power"
2802 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2803 (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2804 (match_operand:SI 2 "reg_or_cint_operand" "r,i")))
2805 (clobber (match_scratch:SI 3 "=q,X"))]
2806 "TARGET_POWER"
2807 "@
2808 srea %0,%1,%2
2809 {srai|srawi} %0,%1,%h2")
2810
2811 (define_insn "ashrsi3_no_power"
2812 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2813 (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2814 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
2815 "! TARGET_POWER"
2816 "{sra|sraw}%I2 %0,%1,%h2")
2817
2818 (define_insn ""
2819 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
2820 (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2821 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2822 (const_int 0)))
2823 (clobber (match_scratch:SI 3 "=r,r"))
2824 (clobber (match_scratch:SI 4 "=q,X"))]
2825 "TARGET_POWER"
2826 "@
2827 srea. %3,%1,%2
2828 {srai.|srawi.} %3,%1,%h2"
2829 [(set_attr "type" "delayed_compare")])
2830
2831 (define_insn ""
2832 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
2833 (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2834 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2835 (const_int 0)))
2836 (clobber (match_scratch:SI 3 "=r"))]
2837 "! TARGET_POWER"
2838 "{sra|sraw}%I2. %3,%1,%h2"
2839 [(set_attr "type" "delayed_compare")])
2840
2841 (define_insn ""
2842 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
2843 (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
2844 (match_operand:SI 2 "reg_or_cint_operand" "r,i"))
2845 (const_int 0)))
2846 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
2847 (ashiftrt:SI (match_dup 1) (match_dup 2)))
2848 (clobber (match_scratch:SI 4 "=q,X"))]
2849 "TARGET_POWER"
2850 "@
2851 srea. %0,%1,%2
2852 {srai.|srawi.} %0,%1,%h2"
2853 [(set_attr "type" "delayed_compare")])
2854
2855 (define_insn ""
2856 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
2857 (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
2858 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
2859 (const_int 0)))
2860 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
2861 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
2862 "! TARGET_POWER"
2863 "{sra|sraw}%I2. %0,%1,%h2"
2864 [(set_attr "type" "delayed_compare")])
2865 \f
2866 ;; Floating-point insns, excluding normal data motion.
2867 ;;
2868 ;; PowerPC has a full set of single-precision floating point instructions.
2869 ;;
2870 ;; For the POWER architecture, we pretend that we have both SFmode and
2871 ;; DFmode insns, while, in fact, all fp insns are actually done in double.
2872 ;; The only conversions we will do will be when storing to memory. In that
2873 ;; case, we will use the "frsp" instruction before storing.
2874 ;;
2875 ;; Note that when we store into a single-precision memory location, we need to
2876 ;; use the frsp insn first. If the register being stored isn't dead, we
2877 ;; need a scratch register for the frsp. But this is difficult when the store
2878 ;; is done by reload. It is not incorrect to do the frsp on the register in
2879 ;; this case, we just lose precision that we would have otherwise gotten but
2880 ;; is not guaranteed. Perhaps this should be tightened up at some point.
2881
2882 (define_insn "extendsfdf2"
2883 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
2884 (float_extend:DF (match_operand:SF 1 "gpc_reg_operand" "f")))]
2885 "TARGET_HARD_FLOAT"
2886 "*
2887 {
2888 if (REGNO (operands[0]) == REGNO (operands[1]))
2889 return \"\";
2890 else
2891 return \"fmr %0,%1\";
2892 }"
2893 [(set_attr "type" "fp")])
2894
2895 (define_insn "truncdfsf2"
2896 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2897 (float_truncate:SF (match_operand:DF 1 "gpc_reg_operand" "f")))]
2898 "TARGET_HARD_FLOAT"
2899 "frsp %0,%1"
2900 [(set_attr "type" "fp")])
2901
2902 (define_insn "aux_truncdfsf2"
2903 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2904 (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] 0))]
2905 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
2906 "frsp %0,%1"
2907 [(set_attr "type" "fp")])
2908
2909 (define_insn "negsf2"
2910 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2911 (neg:SF (match_operand:SF 1 "gpc_reg_operand" "f")))]
2912 "TARGET_HARD_FLOAT"
2913 "fneg %0,%1"
2914 [(set_attr "type" "fp")])
2915
2916 (define_insn "abssf2"
2917 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2918 (abs:SF (match_operand:SF 1 "gpc_reg_operand" "f")))]
2919 "TARGET_HARD_FLOAT"
2920 "fabs %0,%1"
2921 [(set_attr "type" "fp")])
2922
2923 (define_insn ""
2924 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2925 (neg:SF (abs:SF (match_operand:SF 1 "gpc_reg_operand" "f"))))]
2926 "TARGET_HARD_FLOAT"
2927 "fnabs %0,%1"
2928 [(set_attr "type" "fp")])
2929
2930 (define_expand "addsf3"
2931 [(set (match_operand:SF 0 "gpc_reg_operand" "")
2932 (plus:SF (match_operand:SF 1 "gpc_reg_operand" "")
2933 (match_operand:SF 2 "gpc_reg_operand" "")))]
2934 "TARGET_HARD_FLOAT"
2935 "")
2936
2937 (define_insn ""
2938 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2939 (plus:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
2940 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2941 "TARGET_POWERPC && TARGET_HARD_FLOAT"
2942 "fadds %0,%1,%2"
2943 [(set_attr "type" "fp")])
2944
2945 (define_insn ""
2946 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2947 (plus:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
2948 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2949 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
2950 "{fa|fadd} %0,%1,%2"
2951 [(set_attr "type" "fp")])
2952
2953 (define_expand "subsf3"
2954 [(set (match_operand:SF 0 "gpc_reg_operand" "")
2955 (minus:SF (match_operand:SF 1 "gpc_reg_operand" "")
2956 (match_operand:SF 2 "gpc_reg_operand" "")))]
2957 "TARGET_HARD_FLOAT"
2958 "")
2959
2960 (define_insn ""
2961 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2962 (minus:SF (match_operand:SF 1 "gpc_reg_operand" "f")
2963 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2964 "TARGET_POWERPC && TARGET_HARD_FLOAT"
2965 "fsubs %0,%1,%2"
2966 [(set_attr "type" "fp")])
2967
2968 (define_insn ""
2969 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2970 (minus:SF (match_operand:SF 1 "gpc_reg_operand" "f")
2971 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2972 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
2973 "{fs|fsub} %0,%1,%2"
2974 [(set_attr "type" "fp")])
2975
2976 (define_expand "mulsf3"
2977 [(set (match_operand:SF 0 "gpc_reg_operand" "")
2978 (mult:SF (match_operand:SF 1 "gpc_reg_operand" "")
2979 (match_operand:SF 2 "gpc_reg_operand" "")))]
2980 "TARGET_HARD_FLOAT"
2981 "")
2982
2983 (define_insn ""
2984 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2985 (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
2986 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2987 "TARGET_POWERPC && TARGET_HARD_FLOAT"
2988 "fmuls %0,%1,%2"
2989 [(set_attr "type" "fp")])
2990
2991 (define_insn ""
2992 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
2993 (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
2994 (match_operand:SF 2 "gpc_reg_operand" "f")))]
2995 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
2996 "{fm|fmul} %0,%1,%2"
2997 [(set_attr "type" "dmul")])
2998
2999 (define_expand "divsf3"
3000 [(set (match_operand:SF 0 "gpc_reg_operand" "")
3001 (div:SF (match_operand:SF 1 "gpc_reg_operand" "")
3002 (match_operand:SF 2 "gpc_reg_operand" "")))]
3003 "TARGET_HARD_FLOAT"
3004 "")
3005
3006 (define_insn ""
3007 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3008 (div:SF (match_operand:SF 1 "gpc_reg_operand" "f")
3009 (match_operand:SF 2 "gpc_reg_operand" "f")))]
3010 "TARGET_POWERPC && TARGET_HARD_FLOAT"
3011 "fdivs %0,%1,%2"
3012 [(set_attr "type" "sdiv")])
3013
3014 (define_insn ""
3015 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3016 (div:SF (match_operand:SF 1 "gpc_reg_operand" "f")
3017 (match_operand:SF 2 "gpc_reg_operand" "f")))]
3018 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
3019 "{fd|fdiv} %0,%1,%2"
3020 [(set_attr "type" "ddiv")])
3021
3022 (define_insn ""
3023 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3024 (plus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3025 (match_operand:SF 2 "gpc_reg_operand" "f"))
3026 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3027 "TARGET_POWERPC && TARGET_HARD_FLOAT"
3028 "fmadds %0,%1,%2,%3"
3029 [(set_attr "type" "fp")])
3030
3031 (define_insn ""
3032 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3033 (plus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3034 (match_operand:SF 2 "gpc_reg_operand" "f"))
3035 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3036 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
3037 "{fma|fmadd} %0,%1,%2,%3"
3038 [(set_attr "type" "dmul")])
3039
3040 (define_insn ""
3041 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3042 (minus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3043 (match_operand:SF 2 "gpc_reg_operand" "f"))
3044 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3045 "TARGET_POWERPC && TARGET_HARD_FLOAT"
3046 "fmsubs %0,%1,%2,%3"
3047 [(set_attr "type" "fp")])
3048
3049 (define_insn ""
3050 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3051 (minus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3052 (match_operand:SF 2 "gpc_reg_operand" "f"))
3053 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3054 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
3055 "{fms|fmsub} %0,%1,%2,%3"
3056 [(set_attr "type" "dmul")])
3057
3058 (define_insn ""
3059 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3060 (neg:SF (plus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3061 (match_operand:SF 2 "gpc_reg_operand" "f"))
3062 (match_operand:SF 3 "gpc_reg_operand" "f"))))]
3063 "TARGET_POWERPC && TARGET_HARD_FLOAT"
3064 "fnmadds %0,%1,%2,%3"
3065 [(set_attr "type" "fp")])
3066
3067 (define_insn ""
3068 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3069 (neg:SF (plus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3070 (match_operand:SF 2 "gpc_reg_operand" "f"))
3071 (match_operand:SF 3 "gpc_reg_operand" "f"))))]
3072 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
3073 "{fnma|fnmadd} %0,%1,%2,%3"
3074 [(set_attr "type" "dmul")])
3075
3076 (define_insn ""
3077 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3078 (neg:SF (minus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3079 (match_operand:SF 2 "gpc_reg_operand" "f"))
3080 (match_operand:SF 3 "gpc_reg_operand" "f"))))]
3081 "TARGET_POWERPC && TARGET_HARD_FLOAT"
3082 "fnmsubs %0,%1,%2,%3"
3083 [(set_attr "type" "fp")])
3084
3085 (define_insn ""
3086 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3087 (neg:SF (minus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f")
3088 (match_operand:SF 2 "gpc_reg_operand" "f"))
3089 (match_operand:SF 3 "gpc_reg_operand" "f"))))]
3090 "! TARGET_POWERPC && TARGET_HARD_FLOAT"
3091 "{fnms|fnmsub} %0,%1,%2,%3"
3092 [(set_attr "type" "dmul")])
3093
3094 (define_expand "sqrtsf2"
3095 [(set (match_operand:SF 0 "gpc_reg_operand" "")
3096 (sqrt:SF (match_operand:SF 1 "gpc_reg_operand" "")))]
3097 "(TARGET_PPC_GPOPT || TARGET_POWER2) && TARGET_HARD_FLOAT"
3098 "")
3099
3100 (define_insn ""
3101 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3102 (sqrt:SF (match_operand:SF 1 "gpc_reg_operand" "f")))]
3103 "TARGET_PPC_GPOPT && TARGET_HARD_FLOAT"
3104 "fsqrts %0,%1"
3105 [(set_attr "type" "ssqrt")])
3106
3107 (define_insn ""
3108 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3109 (sqrt:SF (match_operand:SF 1 "gpc_reg_operand" "f")))]
3110 "TARGET_POWER2 && TARGET_HARD_FLOAT"
3111 "fsqrt %0,%1"
3112 [(set_attr "type" "dsqrt")])
3113
3114 ;; For MIN, MAX, and conditional move, we use DEFINE_EXPAND's that involve a
3115 ;; fsel instruction and some auxiliary computations. Then we just have a
3116 ;; single DEFINE_INSN for fsel and the define_splits to make them if made by
3117 ;; combine.
3118 (define_expand "maxsf3"
3119 [(set (match_dup 3)
3120 (minus:SF (match_operand:SF 1 "gpc_reg_operand" "")
3121 (match_operand:SF 2 "gpc_reg_operand" "")))
3122 (set (match_operand:SF 0 "gpc_reg_operand" "")
3123 (if_then_else:SF (ge (match_dup 3)
3124 (const_int 0))
3125 (match_dup 1)
3126 (match_dup 2)))]
3127 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3128 "
3129 { operands[3] = gen_reg_rtx (SFmode); }")
3130
3131 (define_split
3132 [(set (match_operand:SF 0 "gpc_reg_operand" "")
3133 (smax:SF (match_operand:SF 1 "gpc_reg_operand" "")
3134 (match_operand:SF 2 "gpc_reg_operand" "")))
3135 (clobber (match_operand:SF 3 "gpc_reg_operand" ""))]
3136 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3137 [(set (match_dup 3)
3138 (minus:SF (match_dup 1) (match_dup 2)))
3139 (set (match_dup 0)
3140 (if_then_else:SF (ge (match_dup 3)
3141 (const_int 0))
3142 (match_dup 1)
3143 (match_dup 2)))]
3144 "")
3145
3146 (define_expand "minsf3"
3147 [(set (match_dup 3)
3148 (minus:SF (match_operand:SF 2 "gpc_reg_operand" "")
3149 (match_operand:SF 1 "gpc_reg_operand" "")))
3150 (set (match_operand:SF 0 "gpc_reg_operand" "")
3151 (if_then_else:SF (ge (match_dup 3)
3152 (const_int 0))
3153 (match_dup 1)
3154 (match_dup 2)))]
3155 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3156 "
3157 { operands[3] = gen_reg_rtx (SFmode); }")
3158
3159 (define_split
3160 [(set (match_operand:SF 0 "gpc_reg_operand" "")
3161 (smin:SF (match_operand:SF 1 "gpc_reg_operand" "")
3162 (match_operand:SF 2 "gpc_reg_operand" "")))
3163 (clobber (match_operand:SF 3 "gpc_reg_operand" ""))]
3164 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3165 [(set (match_dup 3)
3166 (minus:SF (match_dup 2) (match_dup 1)))
3167 (set (match_dup 0)
3168 (if_then_else:SF (ge (match_dup 3)
3169 (const_int 0))
3170 (match_dup 1)
3171 (match_dup 2)))]
3172 "")
3173
3174 (define_expand "movsfcc"
3175 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3176 (if_then_else:SF (match_operand 1 "comparison_operator" "")
3177 (match_operand:SF 2 "gpc_reg_operand" "f")
3178 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3179 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3180 "
3181 {
3182 rtx temp, op0, op1;
3183 enum rtx_code code = GET_CODE (operands[1]);
3184 if (! rs6000_compare_fp_p)
3185 FAIL;
3186 switch (code)
3187 {
3188 case GE: case EQ: case NE:
3189 op0 = rs6000_compare_op0;
3190 op1 = rs6000_compare_op1;
3191 break;
3192 case GT:
3193 op0 = rs6000_compare_op1;
3194 op1 = rs6000_compare_op0;
3195 temp = operands[2]; operands[2] = operands[3]; operands[3] = temp;
3196 break;
3197 case LE:
3198 op0 = rs6000_compare_op1;
3199 op1 = rs6000_compare_op0;
3200 break;
3201 case LT:
3202 op0 = rs6000_compare_op0;
3203 op1 = rs6000_compare_op1;
3204 temp = operands[2]; operands[2] = operands[3]; operands[3] = temp;
3205 break;
3206 default:
3207 FAIL;
3208 }
3209 if (GET_MODE (rs6000_compare_op0) == DFmode)
3210 {
3211 temp = gen_reg_rtx (DFmode);
3212 emit_insn (gen_subdf3 (temp, op0, op1));
3213 emit_insn (gen_fseldfsf4 (operands[0], temp, operands[2], operands[3]));
3214 if (code == EQ)
3215 {
3216 emit_insn (gen_negdf2 (temp, temp));
3217 emit_insn (gen_fseldfsf4 (operands[0], temp, operands[0], operands[3]));
3218 }
3219 if (code == NE)
3220 {
3221 emit_insn (gen_negdf2 (temp, temp));
3222 emit_insn (gen_fseldfsf4 (operands[0], temp, operands[3], operands[0]));
3223 }
3224 }
3225 else
3226 {
3227 temp = gen_reg_rtx (SFmode);
3228 emit_insn (gen_subsf3 (temp, op0, op1));
3229 emit_insn (gen_fselsfsf4 (operands[0], temp, operands[2], operands[3]));
3230 if (code == EQ)
3231 {
3232 emit_insn (gen_negsf2 (temp, temp));
3233 emit_insn (gen_fselsfsf4 (operands[0], temp, operands[0], operands[3]));
3234 }
3235 if (code == NE)
3236 {
3237 emit_insn (gen_negsf2 (temp, temp));
3238 emit_insn (gen_fselsfsf4 (operands[0], temp, operands[3], operands[0]));
3239 }
3240 }
3241 DONE;
3242 }")
3243
3244 (define_insn "fselsfsf4"
3245 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3246 (if_then_else:SF (ge (match_operand:SF 1 "gpc_reg_operand" "f")
3247 (const_int 0))
3248 (match_operand:SF 2 "gpc_reg_operand" "f")
3249 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3250 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3251 "fsel %0,%1,%2,%3"
3252 [(set_attr "type" "fp")])
3253
3254 (define_insn "fseldfsf4"
3255 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
3256 (if_then_else:SF (ge (match_operand:DF 1 "gpc_reg_operand" "f")
3257 (const_int 0))
3258 (match_operand:SF 2 "gpc_reg_operand" "f")
3259 (match_operand:SF 3 "gpc_reg_operand" "f")))]
3260 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3261 "fsel %0,%1,%2,%3"
3262 [(set_attr "type" "fp")])
3263
3264 (define_insn "negdf2"
3265 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3266 (neg:DF (match_operand:DF 1 "gpc_reg_operand" "f")))]
3267 "TARGET_HARD_FLOAT"
3268 "fneg %0,%1"
3269 [(set_attr "type" "fp")])
3270
3271 (define_insn "absdf2"
3272 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3273 (abs:DF (match_operand:DF 1 "gpc_reg_operand" "f")))]
3274 "TARGET_HARD_FLOAT"
3275 "fabs %0,%1"
3276 [(set_attr "type" "fp")])
3277
3278 (define_insn ""
3279 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3280 (neg:DF (abs:DF (match_operand:DF 1 "gpc_reg_operand" "f"))))]
3281 "TARGET_HARD_FLOAT"
3282 "fnabs %0,%1"
3283 [(set_attr "type" "fp")])
3284
3285 (define_insn "adddf3"
3286 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3287 (plus:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3288 (match_operand:DF 2 "gpc_reg_operand" "f")))]
3289 "TARGET_HARD_FLOAT"
3290 "{fa|fadd} %0,%1,%2"
3291 [(set_attr "type" "fp")])
3292
3293 (define_insn "subdf3"
3294 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3295 (minus:DF (match_operand:DF 1 "gpc_reg_operand" "f")
3296 (match_operand:DF 2 "gpc_reg_operand" "f")))]
3297 "TARGET_HARD_FLOAT"
3298 "{fs|fsub} %0,%1,%2"
3299 [(set_attr "type" "fp")])
3300
3301 (define_insn "muldf3"
3302 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3303 (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3304 (match_operand:DF 2 "gpc_reg_operand" "f")))]
3305 "TARGET_HARD_FLOAT"
3306 "{fm|fmul} %0,%1,%2"
3307 [(set_attr "type" "dmul")])
3308
3309 (define_insn "divdf3"
3310 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3311 (div:DF (match_operand:DF 1 "gpc_reg_operand" "f")
3312 (match_operand:DF 2 "gpc_reg_operand" "f")))]
3313 "TARGET_HARD_FLOAT"
3314 "{fd|fdiv} %0,%1,%2"
3315 [(set_attr "type" "ddiv")])
3316
3317 (define_insn ""
3318 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3319 (plus:DF (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3320 (match_operand:DF 2 "gpc_reg_operand" "f"))
3321 (match_operand:DF 3 "gpc_reg_operand" "f")))]
3322 "TARGET_HARD_FLOAT"
3323 "{fma|fmadd} %0,%1,%2,%3"
3324 [(set_attr "type" "dmul")])
3325
3326 (define_insn ""
3327 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3328 (minus:DF (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3329 (match_operand:DF 2 "gpc_reg_operand" "f"))
3330 (match_operand:DF 3 "gpc_reg_operand" "f")))]
3331 "TARGET_HARD_FLOAT"
3332 "{fms|fmsub} %0,%1,%2,%3"
3333 [(set_attr "type" "dmul")])
3334
3335 (define_insn ""
3336 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3337 (neg:DF (plus:DF (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3338 (match_operand:DF 2 "gpc_reg_operand" "f"))
3339 (match_operand:DF 3 "gpc_reg_operand" "f"))))]
3340 "TARGET_HARD_FLOAT"
3341 "{fnma|fnmadd} %0,%1,%2,%3"
3342 [(set_attr "type" "dmul")])
3343
3344 (define_insn ""
3345 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3346 (neg:DF (minus:DF (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f")
3347 (match_operand:DF 2 "gpc_reg_operand" "f"))
3348 (match_operand:DF 3 "gpc_reg_operand" "f"))))]
3349 "TARGET_HARD_FLOAT"
3350 "{fnms|fnmsub} %0,%1,%2,%3"
3351 [(set_attr "type" "dmul")])
3352
3353 (define_insn "sqrtdf2"
3354 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3355 (sqrt:DF (match_operand:DF 1 "gpc_reg_operand" "f")))]
3356 "(TARGET_PPC_GPOPT || TARGET_POWER2) && TARGET_HARD_FLOAT"
3357 "fsqrt %0,%1"
3358 [(set_attr "type" "dsqrt")])
3359
3360 ;; For MIN, MAX, and conditional move, we use DEFINE_EXPAND's that involve a
3361 ;; fsel instruction and some auxiliary computations. Then we just have a
3362 ;; single DEFINE_INSN for fsel and the define_splits to make them if made by
3363 ;; combine.
3364
3365 (define_expand "maxdf3"
3366 [(set (match_dup 3)
3367 (minus:DF (match_operand:DF 1 "gpc_reg_operand" "")
3368 (match_operand:DF 2 "gpc_reg_operand" "")))
3369 (set (match_operand:DF 0 "gpc_reg_operand" "")
3370 (if_then_else:DF (ge (match_dup 3)
3371 (const_int 0))
3372 (match_dup 1)
3373 (match_dup 2)))]
3374 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3375 "
3376 { operands[3] = gen_reg_rtx (DFmode); }")
3377
3378 (define_split
3379 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3380 (smax:DF (match_operand:DF 1 "gpc_reg_operand" "")
3381 (match_operand:DF 2 "gpc_reg_operand" "")))
3382 (clobber (match_operand:DF 3 "gpc_reg_operand" ""))]
3383 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3384 [(set (match_dup 3)
3385 (minus:DF (match_dup 1) (match_dup 2)))
3386 (set (match_dup 0)
3387 (if_then_else:DF (ge (match_dup 3)
3388 (const_int 0))
3389 (match_dup 1)
3390 (match_dup 2)))]
3391 "")
3392
3393 (define_expand "mindf3"
3394 [(set (match_dup 3)
3395 (minus:DF (match_operand:DF 2 "gpc_reg_operand" "")
3396 (match_operand:DF 1 "gpc_reg_operand" "")))
3397 (set (match_operand:DF 0 "gpc_reg_operand" "")
3398 (if_then_else:DF (ge (match_dup 3)
3399 (const_int 0))
3400 (match_dup 1)
3401 (match_dup 2)))]
3402 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3403 "
3404 { operands[3] = gen_reg_rtx (DFmode); }")
3405
3406 (define_split
3407 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3408 (smin:DF (match_operand:DF 1 "gpc_reg_operand" "")
3409 (match_operand:DF 2 "gpc_reg_operand" "")))
3410 (clobber (match_operand:DF 3 "gpc_reg_operand" ""))]
3411 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3412 [(set (match_dup 3)
3413 (minus:DF (match_dup 2) (match_dup 1)))
3414 (set (match_dup 0)
3415 (if_then_else:DF (ge (match_dup 3)
3416 (const_int 0))
3417 (match_dup 1)
3418 (match_dup 2)))]
3419 "")
3420
3421 (define_expand "movdfcc"
3422 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3423 (if_then_else:DF (match_operand 1 "comparison_operator" "")
3424 (match_operand:DF 2 "gpc_reg_operand" "f")
3425 (match_operand:DF 3 "gpc_reg_operand" "f")))]
3426 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3427 "
3428 {
3429 rtx temp, op0, op1;
3430 enum rtx_code code = GET_CODE (operands[1]);
3431 if (! rs6000_compare_fp_p)
3432 FAIL;
3433 switch (code)
3434 {
3435 case GE: case EQ: case NE:
3436 op0 = rs6000_compare_op0;
3437 op1 = rs6000_compare_op1;
3438 break;
3439 case GT:
3440 op0 = rs6000_compare_op1;
3441 op1 = rs6000_compare_op0;
3442 temp = operands[2]; operands[2] = operands[3]; operands[3] = temp;
3443 break;
3444 case LE:
3445 op0 = rs6000_compare_op1;
3446 op1 = rs6000_compare_op0;
3447 break;
3448 case LT:
3449 op0 = rs6000_compare_op0;
3450 op1 = rs6000_compare_op1;
3451 temp = operands[2]; operands[2] = operands[3]; operands[3] = temp;
3452 break;
3453 default:
3454 FAIL;
3455 }
3456 if (GET_MODE (rs6000_compare_op0) == DFmode)
3457 {
3458 temp = gen_reg_rtx (DFmode);
3459 emit_insn (gen_subdf3 (temp, op0, op1));
3460 emit_insn (gen_fseldfdf4 (operands[0], temp, operands[2], operands[3]));
3461 if (code == EQ)
3462 {
3463 emit_insn (gen_negdf2 (temp, temp));
3464 emit_insn (gen_fseldfdf4 (operands[0], temp, operands[0], operands[3]));
3465 }
3466 if (code == NE)
3467 {
3468 emit_insn (gen_negdf2 (temp, temp));
3469 emit_insn (gen_fseldfdf4 (operands[0], temp, operands[3], operands[0]));
3470 }
3471 }
3472 else
3473 {
3474 temp = gen_reg_rtx (SFmode);
3475 emit_insn (gen_subsf3 (temp, op0, op1));
3476 emit_insn (gen_fselsfdf4 (operands[0], temp, operands[2], operands[3]));
3477 if (code == EQ)
3478 {
3479 emit_insn (gen_negsf2 (temp, temp));
3480 emit_insn (gen_fselsfdf4 (operands[0], temp, operands[0], operands[3]));
3481 }
3482 if (code == NE)
3483 {
3484 emit_insn (gen_negsf2 (temp, temp));
3485 emit_insn (gen_fselsfdf4 (operands[0], temp, operands[3], operands[0]));
3486 }
3487 }
3488 DONE;
3489 }")
3490
3491 (define_insn "fseldfdf4"
3492 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3493 (if_then_else:DF (ge (match_operand:DF 1 "gpc_reg_operand" "f")
3494 (const_int 0))
3495 (match_operand:DF 2 "gpc_reg_operand" "f")
3496 (match_operand:DF 3 "gpc_reg_operand" "f")))]
3497 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT"
3498 "fsel %0,%1,%2,%3"
3499 [(set_attr "type" "fp")])
3500
3501 (define_insn "fselsfdf4"
3502 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3503 (if_then_else:DF (ge (match_operand:SF 1 "gpc_reg_operand" "f")
3504 (const_int 0))
3505 (match_operand:DF 2 "gpc_reg_operand" "f")
3506 (match_operand:DF 3 "gpc_reg_operand" "f")))]
3507 "TARGET_PPC_GFXOPT"
3508 "fsel %0,%1,%2,%3"
3509 [(set_attr "type" "fp")])
3510 \f
3511 ;; Conversions to and from floating-point.
3512 (define_expand "floatsidf2"
3513 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3514 (float:DF (match_operand:SI 1 "gpc_reg_operand" "")))]
3515 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3516 "
3517 {
3518 if (operands[0])
3519 { /* prevent unused warning messages */
3520 rtx high = force_reg (SImode, GEN_INT (0x43300000));
3521 rtx low = gen_reg_rtx (SImode);
3522 rtx df = gen_reg_rtx (DFmode);
3523 rtx adjust = force_reg (DFmode, rs6000_float_const (\"4503601774854144\", DFmode));
3524
3525 emit_insn (gen_xorsi3 (low, operands[1], GEN_INT (0x80000000)));
3526 emit_insn (gen_move_to_float (df, low, high));
3527 emit_insn (gen_subdf3 (operands[0], df, adjust));
3528 DONE;
3529 }
3530 }")
3531
3532 (define_expand "floatunssidf2"
3533 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3534 (unsigned_float:DF (match_operand:SI 1 "gpc_reg_operand" "")))]
3535 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3536 "
3537 {
3538 if (operands[0])
3539 { /* prevent unused warning messages */
3540 rtx high = force_reg (SImode, GEN_INT (0x43300000));
3541 rtx df = gen_reg_rtx (DFmode);
3542 rtx adjust = force_reg (DFmode, rs6000_float_const (\"4503599627370496\", DFmode));
3543
3544 emit_insn (gen_move_to_float (df, operands[1], high));
3545 emit_insn (gen_subdf3 (operands[0], df, adjust));
3546 DONE;
3547 }
3548 }")
3549
3550 (define_expand "move_to_float"
3551 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3552 (unspec [(match_operand:SI 1 "gpc_reg_operand" "")
3553 (match_operand:SI 2 "gpc_reg_operand" "")
3554 (match_dup 3)] 2))]
3555 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3556 "
3557 {
3558 operands[3] = XEXP (rs6000_stack_temp (DFmode, 8, 1), 0);
3559 }")
3560
3561 (define_split
3562 [(set (match_operand:DF 0 "gpc_reg_operand" "")
3563 (unspec [(match_operand:SI 1 "gpc_reg_operand" "")
3564 (match_operand:SI 2 "gpc_reg_operand" "")
3565 (match_operand:SI 3 "offsettable_addr_operand" "")] 2))]
3566 "reload_completed"
3567 [(set (match_dup 4) (match_dup 1))
3568 (set (match_dup 5) (match_dup 2))
3569 (set (match_dup 0) (mem:DF (match_dup 3)))]
3570 "
3571 {
3572 rtx word1 = gen_rtx (MEM, SImode, operands[3]);
3573 rtx word2 = gen_rtx (MEM, SImode, plus_constant (operands[3], 4));
3574
3575 MEM_IN_STRUCT_P (word1) = 1;
3576 MEM_IN_STRUCT_P (word2) = 1;
3577
3578 if (WORDS_BIG_ENDIAN)
3579 {
3580 operands[4] = word2;
3581 operands[5] = word1;
3582 }
3583 else
3584 {
3585 operands[4] = word1;
3586 operands[5] = word2;
3587 }
3588 }")
3589
3590 (define_insn ""
3591 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3592 (unspec [(match_operand:SI 1 "gpc_reg_operand" "r")
3593 (match_operand:SI 2 "gpc_reg_operand" "r")
3594 (match_operand:SI 3 "offsettable_addr_operand" "p")] 2))]
3595 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3596 "#"
3597 [(set_attr "length" "12")])
3598
3599 (define_expand "fix_truncdfsi2"
3600 [(set (match_operand:SI 0 "gpc_reg_operand" "")
3601 (fix:SI (match_operand:DF 1 "gpc_reg_operand" "")))]
3602 "TARGET_HARD_FLOAT"
3603 "
3604 {
3605 if (TARGET_POWER2 || TARGET_POWERPC)
3606 {
3607 rtx stack_slot = rs6000_stack_temp (DImode, 8, 1);
3608 rtx temp = gen_reg_rtx (DImode);
3609
3610 emit_insn (gen_fpcvtsi (temp, operands[1]));
3611 emit_move_insn (stack_slot, temp);
3612 emit_move_insn (operands[0],
3613 gen_rtx (SUBREG, SImode, stack_slot, WORDS_BIG_ENDIAN));
3614 DONE;
3615 }
3616 else
3617 {
3618 emit_insn (gen_trunc_call (operands[0], operands[1],
3619 gen_rtx (SYMBOL_REF, Pmode, RS6000_ITRUNC)));
3620 DONE;
3621 }
3622 }")
3623
3624 (define_insn "fpcvtsi"
3625 [(set (match_operand:DI 0 "gpc_reg_operand" "=f")
3626 (sign_extend:DI
3627 (fix:SI (match_operand:DF 1 "gpc_reg_operand" "f"))))]
3628 "(TARGET_POWER2 || TARGET_POWERPC) && TARGET_HARD_FLOAT"
3629 "{fcirz|fctiwz} %0,%1"
3630 [(set_attr "type" "fp")])
3631
3632 (define_expand "fixuns_truncdfsi2"
3633 [(set (match_operand:SI 0 "gpc_reg_operand" "")
3634 (unsigned_fix:SI (match_operand:DF 1 "gpc_reg_operand" "")))]
3635 "! TARGET_POWER2 && ! TARGET_POWERPC && TARGET_HARD_FLOAT"
3636 "
3637 {
3638 emit_insn (gen_trunc_call (operands[0], operands[1],
3639 gen_rtx (SYMBOL_REF, Pmode, RS6000_UITRUNC)));
3640 DONE;
3641 }")
3642
3643 (define_expand "trunc_call"
3644 [(parallel [(set (match_operand:SI 0 "" "")
3645 (fix:SI (match_operand:DF 1 "" "")))
3646 (use (match_operand:SI 2 "" ""))])]
3647 "TARGET_HARD_FLOAT"
3648 "
3649 {
3650 rtx insns = gen_trunc_call_rtl (operands[0], operands[1], operands[2]);
3651 rtx first = XVECEXP (insns, 0, 0);
3652 rtx last = XVECEXP (insns, 0, XVECLEN (insns, 0) - 1);
3653
3654 REG_NOTES (first) = gen_rtx (INSN_LIST, REG_LIBCALL, last,
3655 REG_NOTES (first));
3656 REG_NOTES (last) = gen_rtx (INSN_LIST, REG_RETVAL, first, REG_NOTES (last));
3657
3658 emit_insn (insns);
3659 DONE;
3660 }")
3661
3662 (define_expand "trunc_call_rtl"
3663 [(set (reg:DF 33) (match_operand:DF 1 "gpc_reg_operand" ""))
3664 (use (reg:DF 33))
3665 (parallel [(set (reg:SI 3)
3666 (call (mem:SI (match_operand 2 "" "")) (const_int 0)))
3667 (use (const_int 0))
3668 (clobber (scratch:SI))])
3669 (set (match_operand:SI 0 "gpc_reg_operand" "")
3670 (reg:SI 3))]
3671 "TARGET_HARD_FLOAT"
3672 "
3673 {
3674 rs6000_trunc_used = 1;
3675 }")
3676
3677 (define_insn "floatdidf2"
3678 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
3679 (float:DF (match_operand:DI 1 "gpc_reg_operand" "f")))]
3680 "TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3681 "fcfid %0,%1"
3682 [(set_attr "type" "fp")])
3683
3684 (define_insn "fix_truncdfdi2"
3685 [(set (match_operand:DI 0 "gpc_reg_operand" "=f")
3686 (fix:DI (match_operand:DF 1 "gpc_reg_operand" "f")))]
3687 "TARGET_POWERPC64 && TARGET_HARD_FLOAT"
3688 "fctidz %0,%1"
3689 [(set_attr "type" "fp")])
3690 \f
3691 ;; Define the DImode operations that can be done in a small number
3692 ;; of instructions. The & constraints are to prevent the register
3693 ;; allocator from allocating registers that overlap with the inputs
3694 ;; (for example, having an input in 7,8 and an output in 6,7). We
3695 ;; also allow for the the output being the same as one of the inputs.
3696
3697 (define_insn "*adddi3_noppc64"
3698 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,&r,r,r")
3699 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,0,0")
3700 (match_operand:DI 2 "reg_or_short_operand" "r,I,r,I")))]
3701 "! TARGET_POWERPC64"
3702 "*
3703 {
3704 if (WORDS_BIG_ENDIAN)
3705 return (GET_CODE (operands[2])) != CONST_INT
3706 ? \"{a|addc} %L0,%L1,%L2\;{ae|adde} %0,%1,%2\"
3707 : \"{ai|addic} %L0,%L1,%2\;{a%G2e|add%G2e} %0,%1\";
3708 else
3709 return (GET_CODE (operands[2])) != CONST_INT
3710 ? \"{a|addc} %0,%1,%2\;{ae|adde} %L0,%L1,%L2\"
3711 : \"{ai|addic} %0,%1,%2\;{a%G2e|add%G2e} %L0,%L1\";
3712 }"
3713 [(set_attr "length" "8")])
3714
3715 (define_insn "*subdi3_noppc64"
3716 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,&r,r,r,r")
3717 (minus:DI (match_operand:DI 1 "reg_or_short_operand" "r,I,0,r,I")
3718 (match_operand:DI 2 "gpc_reg_operand" "r,r,r,0,0")))]
3719 "! TARGET_POWERPC64"
3720 "*
3721 {
3722 if (WORDS_BIG_ENDIAN)
3723 return (GET_CODE (operands[1]) != CONST_INT)
3724 ? \"{sf|subfc} %L0,%L2,%L1\;{sfe|subfe} %0,%2,%1\"
3725 : \"{sfi|subfic} %L0,%L2,%1\;{sf%G1e|subf%G1e} %0,%2\";
3726 else
3727 return (GET_CODE (operands[1]) != CONST_INT)
3728 ? \"{sf|subfc} %0,%2,%1\;{sfe|subfe} %L0,%L2,%L1\"
3729 : \"{sfi|subfic} %0,%2,%1\;{sf%G1e|subf%G1e} %L0,%L2\";
3730 }"
3731 [(set_attr "length" "8")])
3732
3733 (define_insn "*negdi2_noppc64"
3734 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r")
3735 (neg:DI (match_operand:DI 1 "gpc_reg_operand" "r,0")))]
3736 "! TARGET_POWERPC64"
3737 "*
3738 {
3739 return (WORDS_BIG_ENDIAN)
3740 ? \"{sfi|subfic} %L0,%L1,0\;{sfze|subfze} %0,%1\"
3741 : \"{sfi|subfic} %0,%1,0\;{sfze|subfze} %L0,%L1\";
3742 }"
3743 [(set_attr "length" "8")])
3744
3745 (define_expand "mulsidi3"
3746 [(set (match_operand:DI 0 "gpc_reg_operand" "")
3747 (mult:DI (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" ""))
3748 (sign_extend:DI (match_operand:SI 2 "gpc_reg_operand" ""))))]
3749 ""
3750 "
3751 {
3752 if (! TARGET_POWER && ! TARGET_POWERPC)
3753 {
3754 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
3755 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
3756 emit_insn (gen_mull_call ());
3757 if (WORDS_BIG_ENDIAN)
3758 emit_move_insn (operands[0], gen_rtx (REG, DImode, 3));
3759 else
3760 {
3761 emit_move_insn (operand_subword (operands[0], 0, 0, DImode),
3762 gen_rtx (REG, SImode, 3));
3763 emit_move_insn (operand_subword (operands[0], 1, 0, DImode),
3764 gen_rtx (REG, SImode, 4));
3765 }
3766 DONE;
3767 }
3768 else if (TARGET_POWER)
3769 {
3770 emit_insn (gen_mulsidi3_mq (operands[0], operands[1], operands[2]));
3771 DONE;
3772 }
3773 }")
3774
3775 (define_insn "mulsidi3_mq"
3776 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
3777 (mult:DI (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" "%r"))
3778 (sign_extend:DI (match_operand:SI 2 "gpc_reg_operand" "r"))))
3779 (clobber (match_scratch:SI 3 "=q"))]
3780 "TARGET_POWER"
3781 "mul %0,%1,%2\;mfmq %L0"
3782 [(set_attr "type" "imul")
3783 (set_attr "length" "8")])
3784
3785 (define_insn "*mulsidi3_powerpc"
3786 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r")
3787 (mult:DI (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" "%r"))
3788 (sign_extend:DI (match_operand:SI 2 "gpc_reg_operand" "r"))))]
3789 "TARGET_POWERPC && ! TARGET_POWERPC64"
3790 "*
3791 {
3792 return (WORDS_BIG_ENDIAN)
3793 ? \"mulhw %0,%1,%2\;mullw %L0,%1,%2\"
3794 : \"mulhw %L0,%1,%2\;mullw %0,%1,%2\";
3795 }"
3796 [(set_attr "type" "imul")
3797 (set_attr "length" "8")])
3798
3799 (define_split
3800 [(set (match_operand:DI 0 "gpc_reg_operand" "")
3801 (mult:DI (sign_extend:DI (match_operand:SI 1 "gpc_reg_operand" ""))
3802 (sign_extend:DI (match_operand:SI 2 "gpc_reg_operand" ""))))]
3803 "TARGET_POWERPC && ! TARGET_POWERPC64 && reload_completed"
3804 [(set (match_dup 3)
3805 (truncate:SI
3806 (lshiftrt:DI (mult:DI (sign_extend:DI (match_dup 1))
3807 (sign_extend:DI (match_dup 2)))
3808 (const_int 32))))
3809 (set (match_dup 4)
3810 (mult:SI (match_dup 1)
3811 (match_dup 2)))]
3812 "
3813 {
3814 int endian = (WORDS_BIG_ENDIAN == 0);
3815 operands[3] = operand_subword (operands[0], endian, 0, DImode);
3816 operands[4] = operand_subword (operands[0], 1 - endian, 0, DImode);
3817 }")
3818
3819 (define_insn "umulsidi3"
3820 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r")
3821 (mult:DI (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" "%r"))
3822 (zero_extend:DI (match_operand:SI 2 "gpc_reg_operand" "r"))))]
3823 "TARGET_POWERPC && ! TARGET_POWERPC64"
3824 "*
3825 {
3826 return (WORDS_BIG_ENDIAN)
3827 ? \"mulhwu %0,%1,%2\;mullw %L0,%1,%2\"
3828 : \"mulhwu %L0,%1,%2\;mullw %0,%1,%2\";
3829 }"
3830 [(set_attr "type" "imul")
3831 (set_attr "length" "8")])
3832
3833 (define_split
3834 [(set (match_operand:DI 0 "gpc_reg_operand" "")
3835 (mult:DI (zero_extend:DI (match_operand:SI 1 "gpc_reg_operand" ""))
3836 (zero_extend:DI (match_operand:SI 2 "gpc_reg_operand" ""))))]
3837 "TARGET_POWERPC && ! TARGET_POWERPC64 && reload_completed"
3838 [(set (match_dup 3)
3839 (truncate:SI
3840 (lshiftrt:DI (mult:DI (zero_extend:DI (match_dup 1))
3841 (zero_extend:DI (match_dup 2)))
3842 (const_int 32))))
3843 (set (match_dup 4)
3844 (mult:SI (match_dup 1)
3845 (match_dup 2)))]
3846 "
3847 {
3848 int endian = (WORDS_BIG_ENDIAN == 0);
3849 operands[3] = operand_subword (operands[0], endian, 0, DImode);
3850 operands[4] = operand_subword (operands[0], 1 - endian, 0, DImode);
3851 }")
3852
3853 (define_expand "smulsi3_highpart"
3854 [(set (match_operand:SI 0 "gpc_reg_operand" "")
3855 (truncate:SI
3856 (lshiftrt:DI (mult:DI (sign_extend:DI
3857 (match_operand:SI 1 "gpc_reg_operand" "%r"))
3858 (sign_extend:DI
3859 (match_operand:SI 2 "gpc_reg_operand" "r")))
3860 (const_int 32))))]
3861 ""
3862 "
3863 {
3864 if (! TARGET_POWER && ! TARGET_POWERPC)
3865 {
3866 emit_move_insn (gen_rtx (REG, SImode, 3), operands[1]);
3867 emit_move_insn (gen_rtx (REG, SImode, 4), operands[2]);
3868 emit_insn (gen_mulh_call ());
3869 emit_move_insn (operands[0], gen_rtx (REG, SImode, 3));
3870 DONE;
3871 }
3872 else if (TARGET_POWER)
3873 {
3874 emit_insn (gen_smulsi3_highpart_mq (operands[0], operands[1], operands[2]));
3875 DONE;
3876 }
3877 }")
3878
3879 (define_insn "smulsi3_highpart_mq"
3880 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3881 (truncate:SI
3882 (lshiftrt:DI (mult:DI (sign_extend:DI
3883 (match_operand:SI 1 "gpc_reg_operand" "%r"))
3884 (sign_extend:DI
3885 (match_operand:SI 2 "gpc_reg_operand" "r")))
3886 (const_int 32))))
3887 (clobber (match_scratch:SI 3 "=q"))]
3888 "TARGET_POWER"
3889 "mul %0,%1,%2"
3890 [(set_attr "type" "imul")])
3891
3892 (define_insn ""
3893 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3894 (truncate:SI
3895 (lshiftrt:DI (mult:DI (sign_extend:DI
3896 (match_operand:SI 1 "gpc_reg_operand" "%r"))
3897 (sign_extend:DI
3898 (match_operand:SI 2 "gpc_reg_operand" "r")))
3899 (const_int 32))))]
3900 "TARGET_POWERPC"
3901 "mulhw %0,%1,%2"
3902 [(set_attr "type" "imul")])
3903
3904 (define_insn "umulsi3_highpart"
3905 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3906 (truncate:SI
3907 (lshiftrt:DI (mult:DI (zero_extend:DI
3908 (match_operand:SI 1 "gpc_reg_operand" "%r"))
3909 (zero_extend:DI
3910 (match_operand:SI 2 "gpc_reg_operand" "r")))
3911 (const_int 32))))]
3912 "TARGET_POWERPC"
3913 "mulhwu %0,%1,%2"
3914 [(set_attr "type" "imul")])
3915
3916 ;; If operands 0 and 2 are in the same register, we have a problem. But
3917 ;; operands 0 and 1 (the usual case) can be in the same register. That's
3918 ;; why we have the strange constraints below.
3919 (define_insn "ashldi3_power"
3920 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,&r")
3921 (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,0,r")
3922 (match_operand:SI 2 "reg_or_cint_operand" "M,i,r,r")))
3923 (clobber (match_scratch:SI 3 "=X,q,q,q"))]
3924 "TARGET_POWER"
3925 "@
3926 {sli|slwi} %0,%L1,%h2\;{cal %L0,0(0)|li %L0,0}
3927 sl%I2q %L0,%L1,%h2\;sll%I2q %0,%1,%h2
3928 sl%I2q %L0,%L1,%h2\;sll%I2q %0,%1,%h2
3929 sl%I2q %L0,%L1,%h2\;sll%I2q %0,%1,%h2"
3930 [(set_attr "length" "8")])
3931
3932 (define_insn "lshrdi3_power"
3933 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r,r,&r")
3934 (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,0,r")
3935 (match_operand:SI 2 "reg_or_cint_operand" "M,i,r,r")))
3936 (clobber (match_scratch:SI 3 "=X,q,q,q"))]
3937 "TARGET_POWER"
3938 "@
3939 {cal %0,0(0)|li %0,0}\;{s%A2i|s%A2wi} %L0,%1,%h2
3940 sr%I2q %0,%1,%h2\;srl%I2q %L0,%L1,%h2
3941 sr%I2q %0,%1,%h2\;srl%I2q %L0,%L1,%h2
3942 sr%I2q %0,%1,%h2\;srl%I2q %L0,%L1,%h2"
3943 [(set_attr "length" "8")])
3944
3945 ;; Shift by a variable amount is too complex to be worth open-coding. We
3946 ;; just handle shifts by constants.
3947 (define_insn "ashrdi3_power"
3948 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
3949 (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
3950 (match_operand:SI 2 "const_int_operand" "M,i")))
3951 (clobber (match_scratch:SI 3 "=X,q"))]
3952 "TARGET_POWER"
3953 "@
3954 {srai|srawi} %0,%1,31\;{srai|srawi} %L0,%1,%h2
3955 sraiq %0,%1,%h2\;srliq %L0,%L1,%h2"
3956 [(set_attr "length" "8")])
3957 \f
3958 ;; PowerPC64 DImode operations.
3959
3960 (define_expand "adddi3"
3961 [(set (match_operand:DI 0 "gpc_reg_operand" "")
3962 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "")
3963 (match_operand:DI 2 "add_operand" "")))]
3964 ""
3965 "
3966 {
3967 if (! TARGET_POWERPC64 && non_add_cint_operand (operands[2], DImode))
3968 FAIL;
3969 }")
3970
3971 ;; Discourage ai/addic because of carry but provide it in an alternative
3972 ;; allowing register zero as source.
3973
3974 (define_insn ""
3975 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r,?r,r")
3976 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "%r,b,r,b")
3977 (match_operand:DI 2 "add_operand" "r,I,I,J")))]
3978 "TARGET_POWERPC64"
3979 "@
3980 add %0,%1,%2
3981 addi %0,%1,%2
3982 addic %0,%1,%2
3983 addis %0,%1,%u2")
3984
3985 (define_insn ""
3986 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
3987 (compare:CC (plus:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r")
3988 (match_operand:DI 2 "reg_or_short_operand" "r,I"))
3989 (const_int 0)))
3990 (clobber (match_scratch:DI 3 "=r,r"))]
3991 "TARGET_POWERPC64"
3992 "@
3993 add. %3,%1,%2
3994 addic. %3,%1,%2"
3995 [(set_attr "type" "compare")])
3996
3997 (define_insn ""
3998 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
3999 (compare:CC (plus:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r")
4000 (match_operand:DI 2 "reg_or_short_operand" "r,I"))
4001 (const_int 0)))
4002 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
4003 (plus:DI (match_dup 1) (match_dup 2)))]
4004 "TARGET_POWERPC64"
4005 "@
4006 add. %0,%1,%2
4007 addic. %0,%1,%2"
4008 [(set_attr "type" "compare")])
4009
4010 ;; Split an add that we can't do in one insn into two insns, each of which
4011 ;; does one 16-bit part. This is used by combine. Note that the low-order
4012 ;; add should be last in case the result gets used in an address.
4013
4014 (define_split
4015 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4016 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "")
4017 (match_operand:DI 2 "non_add_cint_operand" "")))]
4018 "TARGET_POWERPC64"
4019 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 3)))
4020 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
4021 "
4022 {
4023 HOST_WIDE_INT low = INTVAL (operands[2]) & 0xffff;
4024 HOST_WIDE_INT high = INTVAL (operands[2]) & (~ (HOST_WIDE_INT) 0xffff);
4025
4026 if (low & 0x8000)
4027 high+=0x10000, low |= ((HOST_WIDE_INT) -1) << 16;
4028
4029 operands[3] = GEN_INT (high);
4030 operands[4] = GEN_INT (low);
4031 }")
4032
4033 (define_insn "one_cmpldi2"
4034 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4035 (not:DI (match_operand:DI 1 "gpc_reg_operand" "r")))]
4036 "TARGET_POWERPC64"
4037 "nor %0,%1,%1")
4038
4039 (define_insn ""
4040 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4041 (compare:CC (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4042 (const_int 0)))
4043 (clobber (match_scratch:DI 2 "=r"))]
4044 "TARGET_POWERPC64"
4045 "nor. %2,%1,%1"
4046 [(set_attr "type" "compare")])
4047
4048 (define_insn ""
4049 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
4050 (compare:CC (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4051 (const_int 0)))
4052 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4053 (not:DI (match_dup 1)))]
4054 "TARGET_POWERPC64"
4055 "nor. %0,%1,%1"
4056 [(set_attr "type" "compare")])
4057
4058 (define_insn ""
4059 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
4060 (minus:DI (match_operand:DI 1 "reg_or_short_operand" "r,I")
4061 (match_operand:DI 2 "gpc_reg_operand" "r,r")))]
4062 "TARGET_POWERPC64"
4063 "@
4064 subf %0,%2,%1
4065 subfic %0,%2,%1")
4066
4067 (define_insn ""
4068 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4069 (compare:CC (minus:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4070 (match_operand:DI 2 "gpc_reg_operand" "r"))
4071 (const_int 0)))
4072 (clobber (match_scratch:DI 3 "=r"))]
4073 "TARGET_POWERPC64"
4074 "subf. %3,%2,%1"
4075 [(set_attr "type" "compare")])
4076
4077 (define_insn ""
4078 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4079 (compare:CC (minus:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4080 (match_operand:DI 2 "gpc_reg_operand" "r"))
4081 (const_int 0)))
4082 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4083 (minus:DI (match_dup 1) (match_dup 2)))]
4084 "TARGET_POWERPC64"
4085 "subf. %0,%2,%1"
4086 [(set_attr "type" "compare")])
4087
4088 (define_expand "subdi3"
4089 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4090 (minus:DI (match_operand:DI 1 "reg_or_short_operand" "")
4091 (match_operand:DI 2 "reg_or_cint_operand" "")))]
4092 ""
4093 "
4094 {
4095 if (GET_CODE (operands[2]) == CONST_INT)
4096 {
4097 emit_insn (gen_adddi3 (operands[0], operands[1],
4098 negate_rtx (DImode, operands[2])));
4099 DONE;
4100 }
4101 }")
4102
4103 (define_insn "absdi2"
4104 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r")
4105 (abs:DI (match_operand:DI 1 "gpc_reg_operand" "r,0")))
4106 (clobber (match_scratch:DI 2 "=&r,&r"))]
4107 "TARGET_POWERPC64"
4108 "sradi %2,%1,31\;xor %0,%2,%1\;subf %0,%2,%0"
4109 [(set_attr "length" "12")])
4110
4111 (define_split
4112 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r")
4113 (abs:DI (match_operand:DI 1 "gpc_reg_operand" "r,0")))
4114 (clobber (match_scratch:DI 2 "=&r,&r"))]
4115 "TARGET_POWERPC64 && reload_completed"
4116 [(set (match_dup 2) (ashiftrt:DI (match_dup 1) (const_int 31)))
4117 (set (match_dup 0) (xor:DI (match_dup 2) (match_dup 1)))
4118 (set (match_dup 0) (minus:DI (match_dup 2) (match_dup 0)))]
4119 "")
4120
4121 (define_insn ""
4122 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r")
4123 (neg:DI (abs:DI (match_operand:DI 1 "gpc_reg_operand" "r,0"))))
4124 (clobber (match_scratch:DI 2 "=&r,&r"))]
4125 "TARGET_POWERPC64"
4126 "sradi %2,%1,31\;xor %0,%2,%1\;subf %0,%0,%2"
4127 [(set_attr "length" "12")])
4128
4129 (define_split
4130 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,r")
4131 (neg:DI (abs:DI (match_operand:DI 1 "gpc_reg_operand" "r,0"))))
4132 (clobber (match_scratch:DI 2 "=&r,&r"))]
4133 "TARGET_POWERPC64 && reload_completed"
4134 [(set (match_dup 2) (ashiftrt:DI (match_dup 1) (const_int 31)))
4135 (set (match_dup 0) (xor:DI (match_dup 2) (match_dup 1)))
4136 (set (match_dup 0) (minus:DI (match_dup 0) (match_dup 2)))]
4137 "")
4138
4139 (define_expand "negdi2"
4140 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4141 (neg:DI (match_operand:DI 1 "gpc_reg_operand" "")))]
4142 ""
4143 "")
4144
4145 (define_insn ""
4146 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4147 (neg:DI (match_operand:DI 1 "gpc_reg_operand" "r")))]
4148 "TARGET_POWERPC64"
4149 "neg %0,%1")
4150
4151 (define_insn ""
4152 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4153 (compare:CC (neg:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4154 (const_int 0)))
4155 (clobber (match_scratch:DI 2 "=r"))]
4156 "TARGET_POWERPC64"
4157 "neg. %2,%1"
4158 [(set_attr "type" "compare")])
4159
4160 (define_insn ""
4161 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
4162 (compare:CC (neg:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4163 (const_int 0)))
4164 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4165 (neg:DI (match_dup 1)))]
4166 "TARGET_POWERPC64"
4167 "neg. %0,%1"
4168 [(set_attr "type" "compare")])
4169
4170 (define_insn "ffsdi2"
4171 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r")
4172 (ffs:DI (match_operand:DI 1 "gpc_reg_operand" "r")))]
4173 "TARGET_POWERPC64"
4174 "neg %0,%1\;and %0,%0,%1\;cntlzd %0,%0\;subfic %0,%0,64"
4175 [(set_attr "length" "16")])
4176
4177 (define_insn "muldi3"
4178 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4179 (mult:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4180 (match_operand:DI 2 "gpc_reg_operand" "r")))]
4181 "TARGET_POWERPC64"
4182 "mulld %0,%1,%2"
4183 [(set_attr "type" "imul")])
4184
4185 (define_insn "smuldi3_highpart"
4186 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4187 (truncate:DI
4188 (lshiftrt:TI (mult:TI (sign_extend:TI
4189 (match_operand:DI 1 "gpc_reg_operand" "%r"))
4190 (sign_extend:TI
4191 (match_operand:DI 2 "gpc_reg_operand" "r")))
4192 (const_int 64))))]
4193 "TARGET_POWERPC64"
4194 "mulhd %0,%1,%2"
4195 [(set_attr "type" "imul")])
4196
4197 (define_insn "umuldi3_highpart"
4198 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4199 (truncate:DI
4200 (lshiftrt:TI (mult:TI (zero_extend:TI
4201 (match_operand:DI 1 "gpc_reg_operand" "%r"))
4202 (zero_extend:TI
4203 (match_operand:DI 2 "gpc_reg_operand" "r")))
4204 (const_int 64))))]
4205 "TARGET_POWERPC64"
4206 "mulhdu %0,%1,%2"
4207 [(set_attr "type" "imul")])
4208
4209 (define_expand "divdi3"
4210 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4211 (div:DI (match_operand:DI 1 "gpc_reg_operand" "")
4212 (match_operand:DI 2 "reg_or_cint_operand" "")))]
4213 "TARGET_POWERPC64"
4214 "
4215 {
4216 if (GET_CODE (operands[2]) == CONST_INT
4217 && exact_log2 (INTVAL (operands[2])) >= 0)
4218 ;
4219 else
4220 operands[2] = force_reg (DImode, operands[2]);
4221 }")
4222
4223 (define_expand "moddi3"
4224 [(use (match_operand:DI 0 "gpc_reg_operand" ""))
4225 (use (match_operand:DI 1 "gpc_reg_operand" ""))
4226 (use (match_operand:DI 2 "reg_or_cint_operand" ""))]
4227 "TARGET_POWERPC64"
4228 "
4229 {
4230 int i = exact_log2 (INTVAL (operands[2]));
4231 rtx temp1;
4232 rtx temp2;
4233
4234 if (GET_CODE (operands[2]) != CONST_INT || i < 0)
4235 FAIL;
4236
4237 temp1 = gen_reg_rtx (DImode);
4238 temp2 = gen_reg_rtx (DImode);
4239
4240 emit_insn (gen_divdi3 (temp1, operands[1], operands[2]));
4241 emit_insn (gen_ashldi3 (temp2, temp1, GEN_INT (i)));
4242 emit_insn (gen_subdi3 (operands[0], operands[1], temp2));
4243 DONE;
4244 }")
4245
4246 (define_insn ""
4247 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4248 (div:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4249 (match_operand:DI 2 "const_int_operand" "N")))]
4250 "TARGET_POWERPC64 && exact_log2 (INTVAL (operands[2])) >= 0"
4251 "sradi %0,%1,%p2\;addze %0,%0"
4252 [(set_attr "length" "8")])
4253
4254 (define_insn ""
4255 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4256 (compare:CC (div:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4257 (match_operand:DI 2 "const_int_operand" "N"))
4258 (const_int 0)))
4259 (clobber (match_scratch:DI 3 "=r"))]
4260 "TARGET_POWERPC64 && exact_log2 (INTVAL (operands[2])) >= 0"
4261 "sradi %3,%1,%p2\;addze. %3,%3"
4262 [(set_attr "type" "compare")
4263 (set_attr "length" "8")])
4264
4265 (define_insn ""
4266 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4267 (compare:CC (div:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4268 (match_operand:DI 2 "const_int_operand" "N"))
4269 (const_int 0)))
4270 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4271 (div:DI (match_dup 1) (match_dup 2)))]
4272 "TARGET_POWERPC64 && exact_log2 (INTVAL (operands[2])) >= 0"
4273 "sradi %0,%1,%p2\;addze. %0,%0"
4274 [(set_attr "type" "compare")
4275 (set_attr "length" "8")])
4276
4277 (define_insn ""
4278 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4279 (div:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4280 (match_operand:DI 2 "gpc_reg_operand" "r")))]
4281 "TARGET_POWERPC64"
4282 "divd %0,%1,%2"
4283 [(set_attr "type" "idiv")])
4284
4285 (define_insn "udivdi3"
4286 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4287 (udiv:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4288 (match_operand:DI 2 "gpc_reg_operand" "r")))]
4289 "TARGET_POWERPC64"
4290 "divdu %0,%1,%2"
4291 [(set_attr "type" "idiv")])
4292
4293 (define_insn "rotldi3"
4294 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4295 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4296 (match_operand:DI 2 "reg_or_cint_operand" "ri")))]
4297 "TARGET_POWERPC64"
4298 "rld%I2cl %0,%1,%H2,0")
4299
4300 (define_insn ""
4301 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4302 (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4303 (match_operand:DI 2 "reg_or_cint_operand" "ri"))
4304 (const_int 0)))
4305 (clobber (match_scratch:DI 3 "=r"))]
4306 "TARGET_POWERPC64"
4307 "rld%I2cl. %3,%1,%H2,0"
4308 [(set_attr "type" "delayed_compare")])
4309
4310 (define_insn ""
4311 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4312 (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4313 (match_operand:DI 2 "reg_or_cint_operand" "ri"))
4314 (const_int 0)))
4315 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4316 (rotate:DI (match_dup 1) (match_dup 2)))]
4317 "TARGET_POWERPC64"
4318 "rld%I2cl. %0,%1,%H2,0"
4319 [(set_attr "type" "delayed_compare")])
4320
4321 (define_expand "ashldi3"
4322 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4323 (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "")
4324 (match_operand:SI 2 "reg_or_cint_operand" "")))]
4325 "TARGET_POWERPC64 || TARGET_POWER"
4326 "
4327 {
4328 if (TARGET_POWERPC64)
4329 ;
4330 else if (TARGET_POWER)
4331 {
4332 emit_insn (gen_ashldi3_power (operands[0], operands[1], operands[2]));
4333 DONE;
4334 }
4335 else
4336 FAIL;
4337 }")
4338
4339 (define_insn ""
4340 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4341 (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4342 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
4343 "TARGET_POWERPC64"
4344 "sld%I2 %0,%1,%H2"
4345 [(set_attr "length" "8")])
4346
4347 (define_insn ""
4348 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4349 (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4350 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4351 (const_int 0)))
4352 (clobber (match_scratch:DI 3 "=r"))]
4353 "TARGET_POWERPC64"
4354 "sld%I2. %3,%1,%H2"
4355 [(set_attr "type" "delayed_compare")])
4356
4357 (define_insn ""
4358 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4359 (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4360 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4361 (const_int 0)))
4362 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4363 (ashift:DI (match_dup 1) (match_dup 2)))]
4364 "TARGET_POWERPC64"
4365 "sld%I2. %0,%1,%H2"
4366 [(set_attr "type" "delayed_compare")])
4367
4368 (define_expand "lshrdi3"
4369 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4370 (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "")
4371 (match_operand:SI 2 "reg_or_cint_operand" "")))]
4372 "TARGET_POWERPC64 || TARGET_POWER"
4373 "
4374 {
4375 if (TARGET_POWERPC64)
4376 ;
4377 else if (TARGET_POWER)
4378 {
4379 emit_insn (gen_lshrdi3_power (operands[0], operands[1], operands[2]));
4380 DONE;
4381 }
4382 else
4383 FAIL;
4384 }")
4385
4386 (define_insn ""
4387 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4388 (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4389 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
4390 "TARGET_POWERPC64"
4391 "srd%I2 %0,%1,%H2")
4392
4393 (define_insn ""
4394 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4395 (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4396 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4397 (const_int 0)))
4398 (clobber (match_scratch:DI 3 "=r"))]
4399 "TARGET_POWERPC64"
4400 "srd%I2. %3,%1,%H2"
4401 [(set_attr "type" "delayed_compare")])
4402
4403 (define_insn ""
4404 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4405 (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4406 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4407 (const_int 0)))
4408 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4409 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
4410 "TARGET_POWERPC64"
4411 "srd%I2. %0,%1,%H2"
4412 [(set_attr "type" "delayed_compare")])
4413
4414 (define_expand "ashrdi3"
4415 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4416 (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "")
4417 (match_operand:SI 2 "reg_or_cint_operand" "")))]
4418 "TARGET_POWERPC64 || TARGET_POWER"
4419 "
4420 {
4421 if (TARGET_POWERPC64)
4422 ;
4423 else if (TARGET_POWER && GET_CODE (operands[2]) == CONST_INT)
4424 {
4425 emit_insn (gen_ashrdi3_power (operands[0], operands[1], operands[2]));
4426 DONE;
4427 }
4428 else
4429 FAIL;
4430 }")
4431
4432 (define_insn ""
4433 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4434 (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4435 (match_operand:SI 2 "reg_or_cint_operand" "ri")))]
4436 "TARGET_POWERPC64"
4437 "srad%I2 %0,%1,%H2")
4438
4439 (define_insn ""
4440 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4441 (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4442 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4443 (const_int 0)))
4444 (clobber (match_scratch:DI 3 "=r"))]
4445 "TARGET_POWERPC64"
4446 "srad%I2. %3,%1,%H2"
4447 [(set_attr "type" "delayed_compare")])
4448
4449 (define_insn ""
4450 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4451 (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
4452 (match_operand:SI 2 "reg_or_cint_operand" "ri"))
4453 (const_int 0)))
4454 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4455 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
4456 "TARGET_POWERPC64"
4457 "srad%I2. %0,%1,%H2"
4458 [(set_attr "type" "delayed_compare")])
4459
4460 (define_insn "anddi3"
4461 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r")
4462 (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r")
4463 (match_operand:DI 2 "and_operand" "?r,K,J")))
4464 (clobber (match_scratch:CC 3 "=X,x,x"))]
4465 "TARGET_POWERPC64"
4466 "@
4467 and %0,%1,%2
4468 andi. %0,%1,%b2
4469 andis. %0,%1,%u2")
4470
4471 (define_insn ""
4472 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x")
4473 (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r")
4474 (match_operand:DI 2 "and_operand" "r,K,J"))
4475 (const_int 0)))
4476 (clobber (match_scratch:DI 3 "=r,r,r"))]
4477 "TARGET_POWERPC64"
4478 "@
4479 and. %3,%1,%2
4480 andi. %3,%1,%b2
4481 andis. %3,%1,%u2"
4482 [(set_attr "type" "compare,compare,compare")])
4483
4484 (define_insn ""
4485 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,x")
4486 (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r")
4487 (match_operand:DI 2 "and_operand" "r,K,J"))
4488 (const_int 0)))
4489 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r")
4490 (and:DI (match_dup 1) (match_dup 2)))]
4491 "TARGET_POWERPC64"
4492 "@
4493 and. %0,%1,%2
4494 andi. %0,%1,%b2
4495 andis. %0,%1,%u2"
4496 [(set_attr "type" "compare,compare,compare")])
4497
4498 ;; Take a AND with a constant that cannot be done in a single insn and try to
4499 ;; split it into two insns. This does not verify that the insns are valid
4500 ;; since this need not be done as combine will do it.
4501
4502 (define_split
4503 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4504 (and:DI (match_operand:DI 1 "gpc_reg_operand" "")
4505 (match_operand:DI 2 "non_and_cint_operand" "")))]
4506 "TARGET_POWERPC64"
4507 [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 3)))
4508 (set (match_dup 0) (and:DI (match_dup 0) (match_dup 4)))]
4509 "
4510 {
4511 int maskval = INTVAL (operands[2]);
4512 int i, transitions, last_bit_value;
4513 int orig = maskval, first_c = maskval, second_c;
4514
4515 /* We know that MASKVAL must have more than 2 bit-transitions. Start at
4516 the low-order bit and count for the third transition. When we get there,
4517 make a first mask that has everything to the left of that position
4518 a one. Then make the second mask to turn off whatever else is needed. */
4519
4520 for (i = 1, transitions = 0, last_bit_value = maskval & 1; i < 32; i++)
4521 {
4522 if (((maskval >>= 1) & 1) != last_bit_value)
4523 last_bit_value ^= 1, transitions++;
4524
4525 if (transitions > 2)
4526 {
4527 first_c |= (~0) << i;
4528 break;
4529 }
4530 }
4531
4532 second_c = orig | ~ first_c;
4533
4534 operands[3] = gen_rtx (CONST_INT, VOIDmode, first_c);
4535 operands[4] = gen_rtx (CONST_INT, VOIDmode, second_c);
4536 }")
4537
4538 (define_insn "iordi3"
4539 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r")
4540 (ior:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r")
4541 (match_operand:DI 2 "logical_operand" "r,K,J")))]
4542 "TARGET_POWERPC64"
4543 "@
4544 or %0,%1,%2
4545 ori %0,%1,%b2
4546 oris %0,%1,%u2")
4547
4548 (define_insn ""
4549 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4550 (compare:CC (ior:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4551 (match_operand:DI 2 "gpc_reg_operand" "r"))
4552 (const_int 0)))
4553 (clobber (match_scratch:DI 3 "=r"))]
4554 "TARGET_POWERPC64"
4555 "or. %3,%1,%2"
4556 [(set_attr "type" "compare")])
4557
4558 (define_insn ""
4559 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4560 (compare:CC (ior:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4561 (match_operand:DI 2 "gpc_reg_operand" "r"))
4562 (const_int 0)))
4563 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4564 (ior:DI (match_dup 1) (match_dup 2)))]
4565 "TARGET_POWERPC64"
4566 "or. %0,%1,%2"
4567 [(set_attr "type" "compare")])
4568
4569 ;; Split an IOR that we can't do in one insn into two insns, each of which
4570 ;; does one 16-bit part. This is used by combine.
4571
4572 (define_split
4573 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4574 (ior:DI (match_operand:DI 1 "gpc_reg_operand" "")
4575 (match_operand:DI 2 "non_logical_cint_operand" "")))]
4576 "TARGET_POWERPC64"
4577 [(set (match_dup 0) (ior:DI (match_dup 1) (match_dup 3)))
4578 (set (match_dup 0) (ior:DI (match_dup 0) (match_dup 4)))]
4579 "
4580 {
4581 operands[3] = gen_rtx (CONST_INT, VOIDmode,
4582 INTVAL (operands[2]) & (~ (HOST_WIDE_INT) 0xffff));
4583 operands[4] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) & 0xffff);
4584 }")
4585
4586 (define_insn "xordi3"
4587 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r")
4588 (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r")
4589 (match_operand:DI 2 "logical_operand" "r,K,J")))]
4590 "TARGET_POWERPC64"
4591 "@
4592 xor %0,%1,%2
4593 xori %0,%1,%b2
4594 xoris %0,%1,%u2")
4595
4596 (define_insn ""
4597 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4598 (compare:CC (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4599 (match_operand:DI 2 "gpc_reg_operand" "r"))
4600 (const_int 0)))
4601 (clobber (match_scratch:DI 3 "=r"))]
4602 "TARGET_POWERPC64"
4603 "xor. %3,%1,%2"
4604 [(set_attr "type" "compare")])
4605
4606 (define_insn ""
4607 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4608 (compare:CC (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4609 (match_operand:DI 2 "gpc_reg_operand" "r"))
4610 (const_int 0)))
4611 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4612 (xor:DI (match_dup 1) (match_dup 2)))]
4613 "TARGET_POWERPC64"
4614 "xor. %0,%1,%2"
4615 [(set_attr "type" "compare")])
4616
4617 ;; Split an XOR that we can't do in one insn into two insns, each of which
4618 ;; does one 16-bit part. This is used by combine.
4619
4620 (define_split
4621 [(set (match_operand:DI 0 "gpc_reg_operand" "")
4622 (xor:DI (match_operand:DI 1 "gpc_reg_operand" "")
4623 (match_operand:DI 2 "non_logical_cint_operand" "")))]
4624 "TARGET_POWERPC64"
4625 [(set (match_dup 0) (xor:DI (match_dup 1) (match_dup 3)))
4626 (set (match_dup 0) (xor:DI (match_dup 0) (match_dup 4)))]
4627 "
4628 {
4629 operands[3] = gen_rtx (CONST_INT, VOIDmode,
4630 INTVAL (operands[2]) & 0xffff0000);
4631 operands[4] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2]) & 0xffff);
4632 }")
4633
4634 (define_insn ""
4635 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4636 (not:DI (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4637 (match_operand:DI 2 "gpc_reg_operand" "r"))))]
4638 "TARGET_POWERPC64"
4639 "eqv %0,%1,%2")
4640
4641 (define_insn ""
4642 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4643 (compare:CC (not:DI (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4644 (match_operand:DI 2 "gpc_reg_operand" "r")))
4645 (const_int 0)))
4646 (clobber (match_scratch:DI 3 "=r"))]
4647 "TARGET_POWERPC64"
4648 "eqv. %3,%1,%2"
4649 [(set_attr "type" "compare")])
4650
4651 (define_insn ""
4652 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4653 (compare:CC (not:DI (xor:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
4654 (match_operand:DI 2 "gpc_reg_operand" "r")))
4655 (const_int 0)))
4656 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4657 (not:DI (xor:DI (match_dup 1) (match_dup 2))))]
4658 "TARGET_POWERPC64"
4659 "eqv. %0,%1,%2"
4660 [(set_attr "type" "compare")])
4661
4662 (define_insn ""
4663 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4664 (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4665 (match_operand:DI 2 "gpc_reg_operand" "r")))]
4666 "TARGET_POWERPC64"
4667 "andc %0,%2,%1")
4668
4669 (define_insn ""
4670 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4671 (compare:CC (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4672 (match_operand:DI 2 "gpc_reg_operand" "r"))
4673 (const_int 0)))
4674 (clobber (match_scratch:DI 3 "=r"))]
4675 "TARGET_POWERPC64"
4676 "andc. %3,%2,%1"
4677 [(set_attr "type" "compare")])
4678
4679 (define_insn ""
4680 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4681 (compare:CC (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4682 (match_operand:DI 2 "gpc_reg_operand" "r"))
4683 (const_int 0)))
4684 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4685 (and:DI (not:DI (match_dup 1)) (match_dup 2)))]
4686 "TARGET_POWERPC64"
4687 "andc. %0,%2,%1"
4688 [(set_attr "type" "compare")])
4689
4690 (define_insn ""
4691 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4692 (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4693 (match_operand:DI 2 "gpc_reg_operand" "r")))]
4694 "TARGET_POWERPC64"
4695 "orc %0,%2,%1")
4696
4697 (define_insn ""
4698 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4699 (compare:CC (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4700 (match_operand:DI 2 "gpc_reg_operand" "r"))
4701 (const_int 0)))
4702 (clobber (match_scratch:DI 3 "=r"))]
4703 "TARGET_POWERPC64"
4704 "orc. %3,%2,%1"
4705 [(set_attr "type" "compare")])
4706
4707 (define_insn ""
4708 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4709 (compare:CC (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "r"))
4710 (match_operand:DI 2 "gpc_reg_operand" "r"))
4711 (const_int 0)))
4712 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4713 (ior:DI (not:DI (match_dup 1)) (match_dup 2)))]
4714 "TARGET_POWERPC64"
4715 "orc. %0,%2,%1"
4716 [(set_attr "type" "compare")])
4717
4718 (define_insn ""
4719 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4720 (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4721 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r"))))]
4722 "TARGET_POWERPC64"
4723 "nand %0,%1,%2")
4724
4725 (define_insn ""
4726 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4727 (compare:CC (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4728 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r")))
4729 (const_int 0)))
4730 (clobber (match_scratch:DI 3 "=r"))]
4731 "TARGET_POWERPC64"
4732 "nand. %3,%1,%2"
4733 [(set_attr "type" "compare")])
4734
4735 (define_insn ""
4736 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4737 (compare:CC (ior:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4738 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r")))
4739 (const_int 0)))
4740 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4741 (ior:DI (not:DI (match_dup 1)) (not:DI (match_dup 2))))]
4742 "TARGET_POWERPC64"
4743 "nand. %0,%1,%2"
4744 [(set_attr "type" "compare")])
4745
4746 (define_insn ""
4747 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4748 (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4749 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r"))))]
4750 "TARGET_POWERPC64"
4751 "nor %0,%1,%2")
4752
4753 (define_insn ""
4754 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
4755 (compare:CC (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4756 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r")))
4757 (const_int 0)))
4758 (clobber (match_scratch:DI 3 "=r"))]
4759 "TARGET_POWERPC64"
4760 "nor. %3,%1,%2"
4761 [(set_attr "type" "compare")])
4762
4763 (define_insn ""
4764 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
4765 (compare:CC (and:DI (not:DI (match_operand:DI 1 "gpc_reg_operand" "%r"))
4766 (not:DI (match_operand:DI 2 "gpc_reg_operand" "r")))
4767 (const_int 0)))
4768 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
4769 (and:DI (not:DI (match_dup 1)) (not:DI (match_dup 2))))]
4770 "TARGET_POWERPC64"
4771 "nor. %0,%1,%2"
4772 [(set_attr "type" "compare")])
4773 \f
4774 ;; Now define ways of moving data around.
4775
4776 ;; Elf specific ways of loading addresses for non-PIC code.
4777 ;; The output of this could be r0, but we limit it to base
4778 ;; registers, since almost all uses of this will need it
4779 ;; in a base register shortly.
4780 (define_insn "elf_high"
4781 [(set (match_operand:SI 0 "register_operand" "=b")
4782 (high:SI (match_operand 1 "" "")))]
4783 "TARGET_ELF && !TARGET_64BIT"
4784 "{cau|addis} %0,0,%1@ha")
4785
4786 (define_insn "elf_low"
4787 [(set (match_operand:SI 0 "register_operand" "=r")
4788 (lo_sum:SI (match_operand:SI 1 "register_operand" "b")
4789 (match_operand 2 "" "")))]
4790 "TARGET_ELF && !TARGET_64BIT"
4791 "{cal %0,%a2@l(%1)|addi %0,%1,%2@l}")
4792
4793 ;; For SI, we special-case integers that can't be loaded in one insn. We
4794 ;; do the load 16-bits at a time. We could do this by loading from memory,
4795 ;; and this is even supposed to be faster, but it is simpler not to get
4796 ;; integers in the TOC.
4797 (define_expand "movsi"
4798 [(set (match_operand:SI 0 "general_operand" "")
4799 (match_operand:SI 1 "any_operand" ""))]
4800 ""
4801 "
4802 {
4803 if (GET_CODE (operands[0]) != REG)
4804 operands[1] = force_reg (SImode, operands[1]);
4805
4806 /* Convert a move of a CONST_DOUBLE into a CONST_INT */
4807 if (GET_CODE (operands[1]) == CONST_DOUBLE)
4808 operands[1] = GEN_INT (CONST_DOUBLE_LOW (operands[1]));
4809
4810 /* Use default pattern for address of ELF small data */
4811 if (TARGET_ELF
4812 && DEFAULT_ABI == ABI_V4
4813 && (GET_CODE (operands[1]) == SYMBOL_REF || GET_CODE (operands[1]) == CONST)
4814 && small_data_operand (operands[1], SImode))
4815 {
4816 emit_insn (gen_rtx (SET, VOIDmode, operands[0], operands[1]));
4817 DONE;
4818 }
4819
4820 if (TARGET_ELF && TARGET_NO_TOC && !TARGET_64BIT
4821 && CONSTANT_P (operands[1])
4822 && GET_CODE (operands[1]) != HIGH
4823 && GET_CODE (operands[1]) != CONST_INT)
4824 {
4825 rtx target = (reload_completed || reload_in_progress)
4826 ? operands[0] : gen_reg_rtx (SImode);
4827
4828 /* If this is a function address on -mcall-aixdesc or -mcall-nt,
4829 convert it to the address of the descriptor. */
4830 if ((DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_NT)
4831 && GET_CODE (operands[1]) == SYMBOL_REF
4832 && XSTR (operands[1], 0)[0] == '.')
4833 {
4834 char *name = XSTR (operands[1], 0);
4835 rtx new_ref;
4836 while (*name == '.')
4837 name++;
4838 new_ref = gen_rtx (SYMBOL_REF, Pmode, name);
4839 CONSTANT_POOL_ADDRESS_P (new_ref) = CONSTANT_POOL_ADDRESS_P (operands[1]);
4840 SYMBOL_REF_FLAG (new_ref) = SYMBOL_REF_FLAG (operands[1]);
4841 SYMBOL_REF_USED (new_ref) = SYMBOL_REF_USED (operands[1]);
4842 operands[1] = new_ref;
4843 }
4844
4845 emit_insn (gen_elf_high (target, operands[1]));
4846 emit_insn (gen_elf_low (operands[0], target, operands[1]));
4847 DONE;
4848 }
4849
4850 if (GET_CODE (operands[1]) == CONST
4851 && DEFAULT_ABI == ABI_NT
4852 && !side_effects_p (operands[0]))
4853 {
4854 rtx const_term = const0_rtx;
4855 rtx sym = eliminate_constant_term (XEXP (operands[1], 0), &const_term);
4856 if (sym && GET_CODE (const_term) == CONST_INT
4857 && (GET_CODE (sym) == SYMBOL_REF || GET_CODE (sym) == LABEL_REF))
4858 {
4859 unsigned HOST_WIDE_INT value = INTVAL (const_term);
4860 int new_reg_p = (flag_expensive_optimizations
4861 && !reload_completed
4862 && !reload_in_progress);
4863 rtx tmp1 = (new_reg_p && value != 0) ? gen_reg_rtx (SImode) : operands[0];
4864
4865 emit_insn (gen_movsi (tmp1, sym));
4866 if (INTVAL (const_term) != 0)
4867 {
4868 if (value + 0x8000 < 0x10000)
4869 emit_insn (gen_addsi3 (operands[0], tmp1, GEN_INT (value)));
4870
4871 else
4872 {
4873 HOST_WIDE_INT high_int = value & (~ (HOST_WIDE_INT) 0xffff);
4874 HOST_WIDE_INT low_int = value & 0xffff;
4875 rtx tmp2 = (!new_reg_p || !low_int) ? operands[0] : gen_reg_rtx (Pmode);
4876
4877 if (low_int & 0x8000)
4878 high_int += 0x10000, low_int |= ((HOST_WIDE_INT) -1) << 16;
4879
4880 emit_insn (gen_addsi3 (tmp2, tmp1, GEN_INT (high_int)));
4881 if (low_int)
4882 emit_insn (gen_addsi3 (operands[0], tmp2, GEN_INT (low_int)));
4883 }
4884 }
4885 DONE;
4886 }
4887 else
4888 fatal_insn (\"bad address\", operands[1]);
4889 }
4890
4891 if ((!TARGET_WINDOWS_NT || DEFAULT_ABI != ABI_NT)
4892 && CONSTANT_P (operands[1])
4893 && GET_CODE (operands[1]) != CONST_INT
4894 && GET_CODE (operands[1]) != HIGH
4895 && ! LEGITIMATE_CONSTANT_POOL_ADDRESS_P (operands[1]))
4896 {
4897 /* If we are to limit the number of things we put in the TOC and
4898 this is a symbol plus a constant we can add in one insn,
4899 just put the symbol in the TOC and add the constant. Don't do
4900 this if reload is in progress. */
4901 if (GET_CODE (operands[1]) == CONST
4902 && TARGET_NO_SUM_IN_TOC && ! reload_in_progress
4903 && GET_CODE (XEXP (operands[1], 0)) == PLUS
4904 && add_operand (XEXP (XEXP (operands[1], 0), 1), SImode)
4905 && (GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == LABEL_REF
4906 || GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == SYMBOL_REF)
4907 && ! side_effects_p (operands[0]))
4908 {
4909 rtx sym = force_const_mem (SImode, XEXP (XEXP (operands[1], 0), 0));
4910 rtx other = XEXP (XEXP (operands[1], 0), 1);
4911
4912 emit_insn (gen_addsi3 (operands[0], force_reg (SImode, sym), other));
4913 DONE;
4914 }
4915
4916 operands[1] = force_const_mem (SImode, operands[1]);
4917 if (! memory_address_p (SImode, XEXP (operands[1], 0))
4918 && ! reload_in_progress)
4919 operands[1] = change_address (operands[1], SImode,
4920 XEXP (operands[1], 0));
4921 }
4922 }")
4923
4924 (define_insn ""
4925 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,m,r,r,r,r,r,*q,*c*l,*h")
4926 (match_operand:SI 1 "input_operand" "r,S,T,U,m,r,I,J,n,R,*h,r,r,0"))]
4927 "gpc_reg_operand (operands[0], SImode)
4928 || gpc_reg_operand (operands[1], SImode)"
4929 "@
4930 mr %0,%1
4931 {l|lwz} %0,[toc]%1(2)
4932 {l|lwz} %0,[toc]%l1(2)
4933 {cal|la} %0,%a1
4934 {l%U1%X1|lwz%U1%X1} %0,%1
4935 {st%U0%X0|stw%U0%X0} %1,%0
4936 {lil|li} %0,%1
4937 {liu|lis} %0,%u1
4938 #
4939 {cal|la} %0,%1(%*)
4940 mf%1 %0
4941 mt%0 %1
4942 mt%0 %1
4943 cror 0,0,0"
4944 [(set_attr "type" "*,load,load,*,load,*,*,*,*,*,*,*,mtjmpr,*")
4945 (set_attr "length" "4,4,4,4,4,4,4,4,8,4,4,4,4,4")])
4946
4947 ;; Split a load of a large constant into the appropriate two-insn
4948 ;; sequence.
4949
4950 (define_split
4951 [(set (match_operand:SI 0 "gpc_reg_operand" "")
4952 (match_operand:SI 1 "const_int_operand" ""))]
4953 "(unsigned) (INTVAL (operands[1]) + 0x8000) >= 0x10000
4954 && (INTVAL (operands[1]) & 0xffff) != 0"
4955 [(set (match_dup 0)
4956 (match_dup 2))
4957 (set (match_dup 0)
4958 (ior:SI (match_dup 0)
4959 (match_dup 3)))]
4960 "
4961 {
4962 operands[2] = gen_rtx (CONST_INT, VOIDmode,
4963 INTVAL (operands[1]) & 0xffff0000);
4964 operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff);
4965 }")
4966
4967 (define_insn ""
4968 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
4969 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "r")
4970 (const_int 0)))
4971 (set (match_operand:SI 0 "gpc_reg_operand" "=r") (match_dup 1))]
4972 ""
4973 "mr. %0,%1"
4974 [(set_attr "type" "compare")])
4975 \f
4976 (define_expand "movhi"
4977 [(set (match_operand:HI 0 "general_operand" "")
4978 (match_operand:HI 1 "any_operand" ""))]
4979 ""
4980 "
4981 {
4982 if (GET_CODE (operands[0]) != REG)
4983 operands[1] = force_reg (HImode, operands[1]);
4984
4985 if (CONSTANT_P (operands[1]) && GET_CODE (operands[1]) != CONST_INT)
4986 {
4987 operands[1] = force_const_mem (HImode, operands[1]);
4988 if (! memory_address_p (HImode, XEXP (operands[1], 0))
4989 && ! reload_in_progress)
4990 operands[1] = change_address (operands[1], HImode,
4991 XEXP (operands[1], 0));
4992 }
4993 }")
4994
4995 (define_insn ""
4996 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,m,r,r,*q,*c*l,*h")
4997 (match_operand:HI 1 "input_operand" "r,m,r,i,*h,r,r,0"))]
4998 "gpc_reg_operand (operands[0], HImode)
4999 || gpc_reg_operand (operands[1], HImode)"
5000 "@
5001 mr %0,%1
5002 lhz%U1%X1 %0,%1
5003 sth%U0%X0 %1,%0
5004 {lil|li} %0,%w1
5005 mf%1 %0
5006 mt%0 %1
5007 mt%0 %1
5008 cror 0,0,0"
5009 [(set_attr "type" "*,load,*,*,*,*,mtjmpr,*")])
5010
5011 (define_expand "movqi"
5012 [(set (match_operand:QI 0 "general_operand" "")
5013 (match_operand:QI 1 "any_operand" ""))]
5014 ""
5015 "
5016 {
5017 if (GET_CODE (operands[0]) != REG)
5018 operands[1] = force_reg (QImode, operands[1]);
5019
5020 if (CONSTANT_P (operands[1]) && GET_CODE (operands[1]) != CONST_INT)
5021 {
5022 operands[1] = force_const_mem (QImode, operands[1]);
5023 if (! memory_address_p (QImode, XEXP (operands[1], 0))
5024 && ! reload_in_progress)
5025 operands[1] = change_address (operands[1], QImode,
5026 XEXP (operands[1], 0));
5027 }
5028 }")
5029
5030 (define_insn ""
5031 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,m,r,r,*q,*c*l,*h")
5032 (match_operand:QI 1 "input_operand" "r,m,r,i,*h,r,r,0"))]
5033 "gpc_reg_operand (operands[0], QImode)
5034 || gpc_reg_operand (operands[1], QImode)"
5035 "@
5036 mr %0,%1
5037 lbz%U1%X1 %0,%1
5038 stb%U0%X0 %1,%0
5039 {lil|li} %0,%1
5040 mf%1 %0
5041 mt%0 %1
5042 mt%0 %1
5043 cror 0,0,0"
5044 [(set_attr "type" "*,load,*,*,*,*,mtjmpr,*")])
5045 \f
5046 ;; Here is how to move condition codes around. When we store CC data in
5047 ;; an integer register or memory, we store just the high-order 4 bits.
5048 ;; This lets us not shift in the most common case of CR0.
5049 (define_expand "movcc"
5050 [(set (match_operand:CC 0 "nonimmediate_operand" "")
5051 (match_operand:CC 1 "nonimmediate_operand" ""))]
5052 ""
5053 "")
5054
5055 (define_insn ""
5056 [(set (match_operand:CC 0 "nonimmediate_operand" "=y,x,y,r,r,r,r,m")
5057 (match_operand:CC 1 "nonimmediate_operand" "y,r,r,x,y,r,m,r"))]
5058 "register_operand (operands[0], CCmode)
5059 || register_operand (operands[1], CCmode)"
5060 "@
5061 mcrf %0,%1
5062 mtcrf 128,%1
5063 {rlinm|rlwinm} %1,%1,%F0,0xffffffff\;mtcrf %R0,%1\;{rlinm|rlwinm} %1,%1,%f0,0xffffffff
5064 mfcr %0
5065 mfcr %0\;{rlinm|rlwinm} %0,%0,%f1,0xf0000000
5066 mr %0,%1
5067 {l%U1%X1|lwz%U1%X1} %0,%1
5068 {st%U0%U1|stw%U0%U1} %1,%0"
5069 [(set_attr "type" "*,*,*,compare,*,*,load,*")
5070 (set_attr "length" "*,*,12,*,8,*,*,*")])
5071 \f
5072 ;; For floating-point, we normally deal with the floating-point registers
5073 ;; unless -msoft-float is used. The sole exception is that parameter passing
5074 ;; can produce floating-point values in fixed-point registers. Unless the
5075 ;; value is a simple constant or already in memory, we deal with this by
5076 ;; allocating memory and copying the value explicitly via that memory location.
5077 (define_expand "movsf"
5078 [(set (match_operand:SF 0 "nonimmediate_operand" "")
5079 (match_operand:SF 1 "any_operand" ""))]
5080 ""
5081 "
5082 {
5083 /* If we are called from reload, we might be getting a SUBREG of a hard
5084 reg. So expand it. */
5085 if (GET_CODE (operands[0]) == SUBREG
5086 && GET_CODE (SUBREG_REG (operands[0])) == REG
5087 && REGNO (SUBREG_REG (operands[0])) < FIRST_PSEUDO_REGISTER)
5088 operands[0] = alter_subreg (operands[0]);
5089 if (GET_CODE (operands[1]) == SUBREG
5090 && GET_CODE (SUBREG_REG (operands[1])) == REG
5091 && REGNO (SUBREG_REG (operands[1])) < FIRST_PSEUDO_REGISTER)
5092 operands[1] = alter_subreg (operands[1]);
5093
5094 if (TARGET_SOFT_FLOAT && GET_CODE (operands[0]) == MEM)
5095 operands[1] = force_reg (SFmode, operands[1]);
5096
5097 else if (TARGET_HARD_FLOAT)
5098 {
5099 if (GET_CODE (operands[1]) == REG && REGNO (operands[1]) < 32)
5100 {
5101 /* If this is a store to memory or another integer register do the
5102 move directly. Otherwise store to a temporary stack slot and
5103 load from there into a floating point register. */
5104
5105 if (GET_CODE (operands[0]) == MEM
5106 || (GET_CODE (operands[0]) == REG
5107 && (REGNO (operands[0]) < 32
5108 || (reload_in_progress
5109 && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER))))
5110 {
5111 emit_move_insn (operand_subword (operands[0], 0, 0, SFmode),
5112 operand_subword (operands[1], 0, 0, SFmode));
5113 DONE;
5114 }
5115 else
5116 {
5117 rtx stack_slot = assign_stack_temp (SFmode, 4, 0);
5118
5119 emit_move_insn (stack_slot, operands[1]);
5120 emit_move_insn (operands[0], stack_slot);
5121 DONE;
5122 }
5123 }
5124
5125 if (GET_CODE (operands[0]) == MEM)
5126 {
5127 /* If operands[1] is a register, it may have double-precision data
5128 in it, so truncate it to single precision. We need not do
5129 this for POWERPC. */
5130 if (! TARGET_POWERPC && TARGET_HARD_FLOAT
5131 && GET_CODE (operands[1]) == REG)
5132 {
5133 rtx newreg
5134 = reload_in_progress ? operands[1] : gen_reg_rtx (SFmode);
5135 emit_insn (gen_aux_truncdfsf2 (newreg, operands[1]));
5136 operands[1] = newreg;
5137 }
5138
5139 operands[1] = force_reg (SFmode, operands[1]);
5140 }
5141
5142 if (GET_CODE (operands[0]) == REG && REGNO (operands[0]) < 32)
5143 {
5144 if (GET_CODE (operands[1]) == MEM
5145 #if HOST_FLOAT_FORMAT == TARGET_FLOAT_FORMAT && ! defined(REAL_IS_NOT_DOUBLE)
5146 || GET_CODE (operands[1]) == CONST_DOUBLE
5147 #endif
5148 || (GET_CODE (operands[1]) == REG
5149 && (REGNO (operands[1]) < 32
5150 || (reload_in_progress
5151 && REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER))))
5152 {
5153 emit_move_insn (operand_subword (operands[0], 0, 0, SFmode),
5154 operand_subword (operands[1], 0, 0, SFmode));
5155 DONE;
5156 }
5157 else
5158 {
5159 rtx stack_slot = assign_stack_temp (SFmode, 4, 0);
5160
5161 emit_move_insn (stack_slot, operands[1]);
5162 emit_move_insn (operands[0], stack_slot);
5163 DONE;
5164 }
5165 }
5166 }
5167
5168 if (CONSTANT_P (operands[1]))
5169 {
5170 operands[1] = force_const_mem (SFmode, operands[1]);
5171 if (! memory_address_p (SFmode, XEXP (operands[1], 0))
5172 && ! reload_in_progress)
5173 operands[1] = change_address (operands[1], SFmode,
5174 XEXP (operands[1], 0));
5175 }
5176 }")
5177
5178 (define_split
5179 [(set (match_operand:SF 0 "gpc_reg_operand" "")
5180 (match_operand:SF 1 "easy_fp_constant" ""))]
5181 "reload_completed && REGNO (operands[0]) <= 31"
5182 [(set (subreg:SI (match_dup 0) 0) (match_dup 2))]
5183 "
5184 {
5185 long l;
5186 REAL_VALUE_TYPE rv;
5187
5188 REAL_VALUE_FROM_CONST_DOUBLE (rv, operands[1]);
5189 REAL_VALUE_TO_TARGET_SINGLE (rv, l);
5190 operands[2] = GEN_INT(l);
5191 }")
5192
5193 (define_insn ""
5194 [(set (match_operand:SF 0 "fp_reg_or_mem_operand" "=f,f,m")
5195 (match_operand:SF 1 "input_operand" "f,m,f"))]
5196 "(gpc_reg_operand (operands[0], SFmode)
5197 || gpc_reg_operand (operands[1], SFmode)) && TARGET_HARD_FLOAT"
5198 "@
5199 fmr %0,%1
5200 lfs%U1%X1 %0,%1
5201 stfs%U0%X0 %1,%0"
5202 [(set_attr "type" "fp,fpload,*")])
5203
5204 (define_insn ""
5205 [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,m,r,r,r")
5206 (match_operand:SF 1 "input_operand" "r,m,r,I,J,R"))]
5207 "(gpc_reg_operand (operands[0], SFmode)
5208 || gpc_reg_operand (operands[1], SFmode)) && TARGET_SOFT_FLOAT"
5209 "@
5210 mr %0,%1
5211 {l%U1%X1|lwz%U1%X1} %0,%1
5212 {st%U0%X0|stw%U0%X0} %1,%0
5213 {lil|li} %0,%1
5214 {liu|lis} %0,%u1
5215 {cal|la} %0,%1(%*)"
5216 [(set_attr "type" "*,load,*,*,*,*")])
5217
5218 \f
5219 (define_expand "movdf"
5220 [(set (match_operand:DF 0 "nonimmediate_operand" "")
5221 (match_operand:DF 1 "any_operand" ""))]
5222 ""
5223 "
5224 {
5225 if (GET_CODE (operands[0]) != REG)
5226 operands[1] = force_reg (DFmode, operands[1]);
5227
5228 /* Stores between FPR and any non-FPR registers must go through a
5229 temporary stack slot. */
5230
5231 if (TARGET_POWERPC64
5232 && GET_CODE (operands[0]) == REG && GET_CODE (operands[1]) == REG
5233 && ((FP_REGNO_P (REGNO (operands[0]))
5234 && ! FP_REGNO_P (REGNO (operands[1])))
5235 || (FP_REGNO_P (REGNO (operands[1]))
5236 && ! FP_REGNO_P (REGNO (operands[0])))))
5237 {
5238 rtx stack_slot = assign_stack_temp (DFmode, 8, 0);
5239
5240 emit_move_insn (stack_slot, operands[1]);
5241 emit_move_insn (operands[0], stack_slot);
5242 DONE;
5243 }
5244
5245 if (CONSTANT_P (operands[1]) && ! easy_fp_constant (operands[1], DFmode))
5246 {
5247 operands[1] = force_const_mem (DFmode, operands[1]);
5248 if (! memory_address_p (DFmode, XEXP (operands[1], 0))
5249 && ! reload_in_progress)
5250 operands[1] = change_address (operands[1], DFmode,
5251 XEXP (operands[1], 0));
5252 }
5253 }")
5254
5255 (define_split
5256 [(set (match_operand:DF 0 "gpc_reg_operand" "")
5257 (match_operand:DF 1 "easy_fp_constant" ""))]
5258 "TARGET_32BIT && reload_completed && REGNO (operands[0]) <= 31"
5259 [(set (match_dup 2) (match_dup 3))
5260 (set (match_dup 4) (match_dup 5))]
5261 "
5262 { operands[2] = operand_subword (operands[0], 0, 0, DFmode);
5263 operands[3] = operand_subword (operands[1], 0, 0, DFmode);
5264 operands[4] = operand_subword (operands[0], 1, 0, DFmode);
5265 operands[5] = operand_subword (operands[1], 1, 0, DFmode); }")
5266
5267 (define_split
5268 [(set (match_operand:DF 0 "gpc_reg_operand" "")
5269 (match_operand:DF 1 "easy_fp_constant" ""))]
5270 "TARGET_64BIT && reload_completed && REGNO (operands[0]) <= 31"
5271 [(set (subreg:DI (match_dup 0) 0) (subreg:DI (match_dup 1) 0))]
5272 "")
5273
5274 ;; Don't have reload use general registers to load a constant. First,
5275 ;; it might not work if the output operand has is the equivalent of
5276 ;; a non-offsettable memref, but also it is less efficient than loading
5277 ;; the constant into an FP register, since it will probably be used there.
5278 ;; The "??" is a kludge until we can figure out a more reasonable way
5279 ;; of handling these non-offsettable values.
5280 (define_insn ""
5281 [(set (match_operand:DF 0 "nonimmediate_operand" "=!r,??r,o,!r,f,f,m")
5282 (match_operand:DF 1 "input_operand" "r,o,r,G,f,m,f"))]
5283 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT
5284 && (register_operand (operands[0], DFmode)
5285 || register_operand (operands[1], DFmode))"
5286 "*
5287 {
5288 switch (which_alternative)
5289 {
5290 case 0:
5291 /* We normally copy the low-numbered register first. However, if
5292 the first register operand 0 is the same as the second register of
5293 operand 1, we must copy in the opposite order. */
5294 if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
5295 return \"mr %L0,%L1\;mr %0,%1\";
5296 else
5297 return \"mr %0,%1\;mr %L0,%L1\";
5298 case 1:
5299 /* If the low-address word is used in the address, we must load it
5300 last. Otherwise, load it first. Note that we cannot have
5301 auto-increment in that case since the address register is known to be
5302 dead. */
5303 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5304 operands [1], 0))
5305 return \"{l|lwz} %L0,%L1\;{l|lwz} %0,%1\";
5306 else
5307 return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\";
5308 case 2:
5309 return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\";
5310 case 3:
5311 return \"#\";
5312 case 4:
5313 return \"fmr %0,%1\";
5314 case 5:
5315 return \"lfd%U1%X1 %0,%1\";
5316 case 6:
5317 return \"stfd%U0%X0 %1,%0\";
5318 }
5319 }"
5320 [(set_attr "type" "*,load,*,*,fp,fpload,*")
5321 (set_attr "length" "8,8,8,8,*,*,*")])
5322
5323 (define_insn ""
5324 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,o,r")
5325 (match_operand:DF 1 "input_operand" "r,o,r,G"))]
5326 "! TARGET_POWERPC64 && TARGET_SOFT_FLOAT
5327 && (register_operand (operands[0], DFmode)
5328 || register_operand (operands[1], DFmode))"
5329 "*
5330 {
5331 switch (which_alternative)
5332 {
5333 case 0:
5334 /* We normally copy the low-numbered register first. However, if
5335 the first register operand 0 is the same as the second register of
5336 operand 1, we must copy in the opposite order. */
5337 if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
5338 return \"mr %L0,%L1\;mr %0,%1\";
5339 else
5340 return \"mr %0,%1\;mr %L0,%L1\";
5341 case 1:
5342 /* If the low-address word is used in the address, we must load it
5343 last. Otherwise, load it first. Note that we cannot have
5344 auto-increment in that case since the address register is known to be
5345 dead. */
5346 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5347 operands [1], 0))
5348 return \"{l|lwz} %L0,%L1\;{l|lwz} %0,%1\";
5349 else
5350 return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\";
5351 case 2:
5352 return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\";
5353 case 3:
5354 return \"#\";
5355 }
5356 }"
5357 [(set_attr "type" "*,load,*,*")
5358 (set_attr "length" "8,8,8,8")])
5359
5360 (define_insn ""
5361 [(set (match_operand:DF 0 "nonimmediate_operand" "=!r,??r,o,!r,f,f,m")
5362 (match_operand:DF 1 "input_operand" "r,o,r,G,f,m,f"))]
5363 "TARGET_POWERPC64 && TARGET_HARD_FLOAT
5364 && (register_operand (operands[0], DFmode)
5365 || register_operand (operands[1], DFmode))"
5366 "@
5367 mr %0,%1
5368 ld%U1%X1 %0,%1
5369 std%U0%X0 %1,%0
5370 #
5371 fmr %0,%1
5372 lfd%U1%X1 %0,%1
5373 stfd%U0%X0 %1,%0"
5374 [(set_attr "type" "*,load,*,*,fp,fpload,*")])
5375
5376 (define_insn ""
5377 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,o,r")
5378 (match_operand:DF 1 "input_operand" "r,o,r,G"))]
5379 "TARGET_POWERPC64 && TARGET_SOFT_FLOAT
5380 && (register_operand (operands[0], DFmode)
5381 || register_operand (operands[1], DFmode))"
5382 "@
5383 mr %0,%1
5384 ld%U1%X1 %0,%1
5385 std%U0%X0 %1,%0
5386 #"
5387 [(set_attr "type" "*,load,*,*")])
5388 \f
5389 ;; Next come the multi-word integer load and store and the load and store
5390 ;; multiple insns.
5391 (define_expand "movdi"
5392 [(set (match_operand:DI 0 "general_operand" "")
5393 (match_operand:DI 1 "any_operand" ""))]
5394 ""
5395 "
5396 {
5397 if (! TARGET_64BIT && ! general_operand (operands[1], DImode))
5398 FAIL;
5399
5400 if (GET_CODE (operands[0]) != REG)
5401 operands[1] = force_reg (DImode, operands[1]);
5402
5403 if (GET_CODE (operands[1]) == CONST_DOUBLE
5404 || GET_CODE (operands[1]) == CONST_INT)
5405 {
5406 HOST_WIDE_INT low;
5407 HOST_WIDE_INT high;
5408
5409 if (GET_CODE (operands[1]) == CONST_DOUBLE)
5410 {
5411 low = CONST_DOUBLE_LOW (operands[1]);
5412 high = CONST_DOUBLE_HIGH (operands[1]);
5413 }
5414 else
5415 #if HOST_BITS_PER_WIDE_INT == 32
5416 {
5417 low = INTVAL (operands[1]);
5418 high = (low < 0) ? ~0 : 0;
5419 }
5420 #else
5421 {
5422 low = INTVAL (operands[1]) & 0xffffffff;
5423 high = (HOST_WIDE_INT) INTVAL (operands[1]) >> 32;
5424 }
5425 #endif
5426
5427 if (! TARGET_POWERPC64)
5428 {
5429 emit_move_insn (gen_rtx (SUBREG, SImode, operands[0],
5430 WORDS_BIG_ENDIAN), GEN_INT (low));
5431
5432 emit_move_insn (gen_rtx (SUBREG, SImode, operands[0],
5433 ! WORDS_BIG_ENDIAN), GEN_INT (high));
5434 DONE;
5435 }
5436 else
5437 {
5438 if (high + 0x8000 >= 0x10000)
5439 {
5440 emit_move_insn (gen_rtx (SUBREG, SImode, operands[0], 1),
5441 GEN_INT (high));
5442 emit_insn (gen_ashldi3 (operands[0], operands[0], GEN_INT(32)));
5443 if (low)
5444 {
5445 HOST_WIDE_INT low_low = low & 0xffff;
5446 HOST_WIDE_INT low_high = low & (~ (HOST_WIDE_INT) 0xffff);
5447 if (low_high)
5448 emit_insn (gen_iordi3 (operands[0], operands[0],
5449 GEN_INT (low_high)));
5450 if (low_low)
5451 emit_insn (gen_iordi3 (operands[0], operands[0],
5452 GEN_INT (low_low)));
5453 }
5454 }
5455 else if (low)
5456 emit_move_insn (gen_rtx (SUBREG, SImode, operands[0], 1),
5457 GEN_INT (low));
5458 DONE;
5459 }
5460 }
5461
5462 /* Stores between FPR and any non-FPR registers must go through a
5463 temporary stack slot. */
5464
5465 if (GET_CODE (operands[0]) == REG && GET_CODE (operands[1]) == REG
5466 && ((FP_REGNO_P (REGNO (operands[0]))
5467 && ! FP_REGNO_P (REGNO (operands[1])))
5468 || (FP_REGNO_P (REGNO (operands[1]))
5469 && ! FP_REGNO_P (REGNO (operands[0])))))
5470 {
5471 rtx stack_slot = assign_stack_temp (DImode, 8, 0);
5472
5473 emit_move_insn (stack_slot, operands[1]);
5474 emit_move_insn (operands[0], stack_slot);
5475 DONE;
5476 }
5477 }")
5478
5479 (define_insn ""
5480 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,m,f,f,m")
5481 (match_operand:DI 1 "input_operand" "r,m,r,f,m,f"))]
5482 "! TARGET_POWERPC64 && (gpc_reg_operand (operands[0], DImode)
5483 || gpc_reg_operand (operands[1], DImode))"
5484 "*
5485 {
5486 switch (which_alternative)
5487 {
5488 case 0:
5489 /* We normally copy the low-numbered register first. However, if
5490 the first register operand 0 is the same as the second register of
5491 operand 1, we must copy in the opposite order. */
5492 if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
5493 return \"mr %L0,%L1\;mr %0,%1\";
5494 else
5495 return \"mr %0,%1\;mr %L0,%L1\";
5496 case 1:
5497 /* If the low-address word is used in the address, we must load it
5498 last. Otherwise, load it first. Note that we cannot have
5499 auto-increment in that case since the address register is known to be
5500 dead. */
5501 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5502 operands [1], 0))
5503 return \"{l|lwz} %L0,%L1\;{l|lwz} %0,%1\";
5504 else
5505 return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\";
5506 case 2:
5507 return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\";
5508 case 3:
5509 return \"fmr %0,%1\";
5510 case 4:
5511 return \"lfd%U1%X1 %0,%1\";
5512 case 5:
5513 return \"stfd%U0%X0 %1,%0\";
5514 }
5515 }"
5516 [(set_attr "type" "*,load,*,fp,fpload,*")
5517 (set_attr "length" "8,8,8,*,*,*")])
5518
5519 (define_insn ""
5520 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,m,r,r,r,r,f,f,m,r,*h,*h")
5521 (match_operand:DI 1 "input_operand" "r,m,r,I,J,n,R,f,m,f,*h,r,0"))]
5522 "TARGET_POWERPC64 && (gpc_reg_operand (operands[0], DImode)
5523 || gpc_reg_operand (operands[1], DImode))"
5524 "@
5525 mr %0,%1
5526 ld%U1%X1 %0,%1
5527 std%U0%X0 %1,%0
5528 li %0,%1
5529 lis %0,%u1
5530 #
5531 {cal|la} %0,%1(%*)
5532 fmr %0,%1
5533 lfd%U1%X1 %0,%1
5534 stfd%U0%X0 %1,%0
5535 mf%1 %0
5536 mt%0 %1
5537 cror 0,0,0"
5538 [(set_attr "type" "*,load,*,*,*,*,*,fp,fpload,*,*,mtjmpr,*")
5539 (set_attr "length" "4,4,4,4,4,20,4,4,4,4,4,4,4")])
5540
5541 ;; Split a load of a large constant into the appropriate five-instruction
5542 ;; sequence. The expansion in movdi tries to perform the minimum number of
5543 ;; steps, but here we have to handle anything in a constant number of insns.
5544
5545 (define_split
5546 [(set (match_operand:DI 0 "gpc_reg_operand" "")
5547 (match_operand:DI 1 "const_double_operand" ""))]
5548 "TARGET_POWERPC64"
5549 [(set (match_dup 0)
5550 (match_dup 2))
5551 (set (match_dup 0)
5552 (ior:DI (match_dup 0)
5553 (match_dup 3)))
5554 (set (match_dup 0)
5555 (ashift:DI (match_dup 0)
5556 (const_int 32)))
5557 (set (match_dup 0)
5558 (ior:DI (match_dup 0)
5559 (match_dup 4)))
5560 (set (match_dup 0)
5561 (ior:DI (match_dup 0)
5562 (match_dup 5)))]
5563 "
5564 {
5565 HOST_WIDE_INT low;
5566 HOST_WIDE_INT high;
5567
5568 if (GET_CODE (operands[1]) == CONST_DOUBLE)
5569 {
5570 low = CONST_DOUBLE_LOW (operands[1]);
5571 high = CONST_DOUBLE_HIGH (operands[1]);
5572 }
5573 else
5574 #if HOST_BITS_PER_WIDE_INT == 32
5575 {
5576 low = INTVAL (operands[1]);
5577 high = (low < 0) ? ~0 : 0;
5578 }
5579 #else
5580 {
5581 low = INTVAL (operands[1]) & 0xffffffff;
5582 high = (HOST_WIDE_INT) INTVAL (operands[1]) >> 32;
5583 }
5584 #endif
5585
5586 if ((high + 0x8000) < 0x10000
5587 && ((low & 0xffff) == 0 || (low & (~ (HOST_WIDE_INT) 0xffff)) == 0))
5588 FAIL;
5589
5590 operands[2] = GEN_INT (high & (~ (HOST_WIDE_INT) 0xffff));
5591 operands[3] = GEN_INT (high & 0xffff);
5592 operands[4] = GEN_INT (low & (~ (HOST_WIDE_INT) 0xffff));
5593 operands[5] = GEN_INT (low & 0xffff);
5594 }")
5595
5596 (define_insn ""
5597 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
5598 (compare:CC (match_operand:DI 1 "gpc_reg_operand" "r")
5599 (const_int 0)))
5600 (set (match_operand:DI 0 "gpc_reg_operand" "=r") (match_dup 1))]
5601 "TARGET_POWERPC64"
5602 "mr. %0,%1"
5603 [(set_attr "type" "compare")])
5604 \f
5605 ;; TImode is similar, except that we usually want to compute the address into
5606 ;; a register and use lsi/stsi (the exception is during reload). MQ is also
5607 ;; clobbered in stsi for POWER, so we need a SCRATCH for it.
5608 (define_expand "movti"
5609 [(parallel [(set (match_operand:TI 0 "general_operand" "")
5610 (match_operand:TI 1 "general_operand" ""))
5611 (clobber (scratch:SI))])]
5612 "TARGET_STRING || TARGET_POWERPC64"
5613 "
5614 {
5615 if (GET_CODE (operands[0]) == MEM)
5616 operands[1] = force_reg (TImode, operands[1]);
5617
5618 if (GET_CODE (operands[0]) == MEM
5619 && GET_CODE (XEXP (operands[0], 0)) != REG
5620 && ! reload_in_progress)
5621 operands[0] = change_address (operands[0], TImode,
5622 copy_addr_to_reg (XEXP (operands[0], 0)));
5623
5624 if (GET_CODE (operands[1]) == MEM
5625 && GET_CODE (XEXP (operands[1], 0)) != REG
5626 && ! reload_in_progress)
5627 operands[1] = change_address (operands[1], TImode,
5628 copy_addr_to_reg (XEXP (operands[1], 0)));
5629 }")
5630
5631 ;; We say that MQ is clobbered in the last alternative because the first
5632 ;; alternative would never get used otherwise since it would need a reload
5633 ;; while the 2nd alternative would not. We put memory cases first so they
5634 ;; are preferred. Otherwise, we'd try to reload the output instead of
5635 ;; giving the SCRATCH mq.
5636 (define_insn ""
5637 [(set (match_operand:TI 0 "reg_or_mem_operand" "=Q,m,????r,????r,????r")
5638 (match_operand:TI 1 "reg_or_mem_operand" "r,r,r,Q,m"))
5639 (clobber (match_scratch:SI 2 "=q,q#X,X,X,X"))]
5640 "TARGET_STRING && TARGET_POWER && ! TARGET_POWERPC64
5641 && (gpc_reg_operand (operands[0], TImode) || gpc_reg_operand (operands[1], TImode))"
5642 "*
5643 {
5644 switch (which_alternative)
5645 {
5646 default:
5647 abort ();
5648
5649 case 0:
5650 return \"{stsi|stswi} %1,%P0,16\";
5651
5652 case 1:
5653 return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\;{st|stw} %Y1,%Y0\;{st|stw} %Z1,%Z0\";
5654
5655 case 2:
5656 /* Normally copy registers with lowest numbered register copied first.
5657 But copy in the other order if the first register of the output
5658 is the second, third, or fourth register in the input. */
5659 if (REGNO (operands[0]) >= REGNO (operands[1]) + 1
5660 && REGNO (operands[0]) <= REGNO (operands[1]) + 3)
5661 return \"mr %Z0,%Z1\;mr %Y0,%Y1\;mr %L0,%L1\;mr %0,%1\";
5662 else
5663 return \"mr %0,%1\;mr %L0,%L1\;mr %Y0,%Y1\;mr %Z0,%Z1\";
5664 case 3:
5665 /* If the address is not used in the output, we can use lsi. Otherwise,
5666 fall through to generating four loads. */
5667 if (! reg_overlap_mentioned_p (operands[0], operands[1]))
5668 return \"{lsi|lswi} %0,%P1,16\";
5669 /* ... fall through ... */
5670 case 4:
5671 /* If the address register is the same as the register for the lowest-
5672 addressed word, load it last. Similarly for the next two words.
5673 Otherwise load lowest address to highest. */
5674 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5675 operands[1], 0))
5676 return \"{l|lwz} %L0,%L1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\;{l|lwz} %0,%1\";
5677 else if (refers_to_regno_p (REGNO (operands[0]) + 1,
5678 REGNO (operands[0]) + 2, operands[1], 0))
5679 return \"{l|lwz} %0,%1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\;{l|lwz} %L0,%L1\";
5680 else if (refers_to_regno_p (REGNO (operands[0]) + 2,
5681 REGNO (operands[0]) + 3, operands[1], 0))
5682 return \"{l|lwz} %0,%1\;{l|lwz} %L0,%L1\;{l|lwz} %Z0,%Z1\;{l|lwz} %Y0,%Y1\";
5683 else
5684 return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\";
5685 }
5686 }"
5687 [(set_attr "type" "*,load,load,*,*")
5688 (set_attr "length" "*,16,16,*,16")])
5689
5690 (define_insn ""
5691 [(set (match_operand:TI 0 "reg_or_mem_operand" "=m,????r,????r")
5692 (match_operand:TI 1 "reg_or_mem_operand" "r,r,m"))
5693 (clobber (match_scratch:SI 2 "=X,X,X"))]
5694 "TARGET_STRING && !TARGET_POWER && ! TARGET_POWERPC64
5695 && (gpc_reg_operand (operands[0], TImode) || gpc_reg_operand (operands[1], TImode))"
5696 "*
5697 {
5698 switch (which_alternative)
5699 {
5700 default:
5701 abort ();
5702
5703 case 0:
5704 return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\;{st|stw} %Y1,%Y0\;{st|stw} %Z1,%Z0\";
5705
5706 case 1:
5707 /* Normally copy registers with lowest numbered register copied first.
5708 But copy in the other order if the first register of the output
5709 is the second, third, or fourth register in the input. */
5710 if (REGNO (operands[0]) >= REGNO (operands[1]) + 1
5711 && REGNO (operands[0]) <= REGNO (operands[1]) + 3)
5712 return \"mr %Z0,%Z1\;mr %Y0,%Y1\;mr %L0,%L1\;mr %0,%1\";
5713 else
5714 return \"mr %0,%1\;mr %L0,%L1\;mr %Y0,%Y1\;mr %Z0,%Z1\";
5715 case 2:
5716 /* If the address register is the same as the register for the lowest-
5717 addressed word, load it last. Similarly for the next two words.
5718 Otherwise load lowest address to highest. */
5719 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5720 operands[1], 0))
5721 return \"{l|lwz} %L0,%L1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\;{l|lwz} %0,%1\";
5722 else if (refers_to_regno_p (REGNO (operands[0]) + 1,
5723 REGNO (operands[0]) + 2, operands[1], 0))
5724 return \"{l|lwz} %0,%1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\;{l|lwz} %L0,%L1\";
5725 else if (refers_to_regno_p (REGNO (operands[0]) + 2,
5726 REGNO (operands[0]) + 3, operands[1], 0))
5727 return \"{l|lwz} %0,%1\;{l|lwz} %L0,%L1\;{l|lwz} %Z0,%Z1\;{l|lwz} %Y0,%Y1\";
5728 else
5729 return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\;{l|lwz} %Y0,%Y1\;{l|lwz} %Z0,%Z1\";
5730 }
5731 }"
5732 [(set_attr "type" "load,*,*")
5733 (set_attr "length" "16,16,16")])
5734
5735 (define_insn ""
5736 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,r,m")
5737 (match_operand:TI 1 "input_operand" "r,m,r"))]
5738 "TARGET_POWERPC64 && (gpc_reg_operand (operands[0], TImode)
5739 || gpc_reg_operand (operands[1], TImode))"
5740 "*
5741 {
5742 switch (which_alternative)
5743 {
5744 case 0:
5745 /* We normally copy the low-numbered register first. However, if
5746 the first register operand 0 is the same as the second register of
5747 operand 1, we must copy in the opposite order. */
5748 if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
5749 return \"mr %L0,%L1\;mr %0,%1\";
5750 else
5751 return \"mr %0,%1\;mr %L0,%L1\";
5752 case 1:
5753 /* If the low-address word is used in the address, we must load it
5754 last. Otherwise, load it first. Note that we cannot have
5755 auto-increment in that case since the address register is known to be
5756 dead. */
5757 if (refers_to_regno_p (REGNO (operands[0]), REGNO (operands[0]) + 1,
5758 operands [1], 0))
5759 return \"ld %L0,%L1\;ld %0,%1\";
5760 else
5761 return \"ld%U1 %0,%1\;ld %L0,%L1\";
5762 case 2:
5763 return \"std%U0 %1,%0\;std %L1,%L0\";
5764 }
5765 }"
5766 [(set_attr "type" "*,load,*")
5767 (set_attr "length" "8,8,8")])
5768 \f
5769 (define_expand "load_multiple"
5770 [(match_par_dup 3 [(set (match_operand:SI 0 "" "")
5771 (match_operand:SI 1 "" ""))
5772 (use (match_operand:SI 2 "" ""))])]
5773 "TARGET_STRING"
5774 "
5775 {
5776 int regno;
5777 int count;
5778 rtx from;
5779 int i;
5780
5781 /* Support only loading a constant number of fixed-point registers from
5782 memory and only bother with this if more than two; the machine
5783 doesn't support more than eight. */
5784 if (GET_CODE (operands[2]) != CONST_INT
5785 || INTVAL (operands[2]) <= 2
5786 || INTVAL (operands[2]) > 8
5787 || GET_CODE (operands[1]) != MEM
5788 || GET_CODE (operands[0]) != REG
5789 || REGNO (operands[0]) >= 32)
5790 FAIL;
5791
5792 count = INTVAL (operands[2]);
5793 regno = REGNO (operands[0]);
5794
5795 operands[3] = gen_rtx (PARALLEL, VOIDmode, rtvec_alloc (count));
5796 from = force_reg (SImode, XEXP (operands[1], 0));
5797
5798 for (i = 0; i < count; i++)
5799 XVECEXP (operands[3], 0, i)
5800 = gen_rtx (SET, VOIDmode, gen_rtx (REG, SImode, regno + i),
5801 gen_rtx (MEM, SImode, plus_constant (from, i * 4)));
5802 }")
5803
5804 (define_insn ""
5805 [(match_parallel 0 "load_multiple_operation"
5806 [(set (match_operand:SI 1 "gpc_reg_operand" "=r")
5807 (mem:SI (match_operand:SI 2 "register_operand" "b")))])]
5808 "TARGET_STRING"
5809 "*
5810 {
5811 /* We have to handle the case where the pseudo used to contain the address
5812 is assigned to one of the output registers. */
5813 int i, j;
5814 int words = XVECLEN (operands[0], 0);
5815 rtx xop[10];
5816
5817 if (XVECLEN (operands[0], 0) == 1)
5818 return \"{l|lwz} %1,0(%2)\";
5819
5820 for (i = 0; i < words; i++)
5821 if (refers_to_regno_p (REGNO (operands[1]) + i,
5822 REGNO (operands[1]) + i + 1, operands[2], 0))
5823 {
5824 if (i == words-1)
5825 {
5826 xop[0] = operands[1];
5827 xop[1] = operands[2];
5828 xop[2] = GEN_INT (4 * (words-1));
5829 output_asm_insn (\"{lsi|lswi} %0,%1,%2\;{l|lwz} %1,%2(%1)\", xop);
5830 return \"\";
5831 }
5832 else if (i == 0)
5833 {
5834 xop[0] = operands[1];
5835 xop[1] = gen_rtx (REG, SImode, REGNO (operands[1]) + 1);
5836 xop[2] = GEN_INT (4 * (words-1));
5837 output_asm_insn (\"{cal %0,4(%0)|addi %0,%0,4}\;{lsi|lswi} %1,%0,%2\;{l|lwz} %0,-4(%0)\", xop);
5838 return \"\";
5839 }
5840 else
5841 {
5842 for (j = 0; j < words; j++)
5843 if (j != i)
5844 {
5845 xop[0] = gen_rtx (REG, SImode, REGNO (operands[1]) + j);
5846 xop[1] = operands[2];
5847 xop[2] = GEN_INT (j * 4);
5848 output_asm_insn (\"{l|lwz} %0,%2(%1)\", xop);
5849 }
5850 xop[0] = operands[2];
5851 xop[1] = GEN_INT (i * 4);
5852 output_asm_insn (\"{l|lwz} %0,%1(%0)\", xop);
5853 return \"\";
5854 }
5855 }
5856
5857 return \"{lsi|lswi} %1,%2,%N0\";
5858 }"
5859 [(set_attr "type" "load")
5860 (set_attr "length" "32")])
5861 \f
5862
5863 (define_expand "store_multiple"
5864 [(match_par_dup 3 [(set (match_operand:SI 0 "" "")
5865 (match_operand:SI 1 "" ""))
5866 (clobber (scratch:SI))
5867 (use (match_operand:SI 2 "" ""))])]
5868 "TARGET_STRING"
5869 "
5870 {
5871 int regno;
5872 int count;
5873 rtx to;
5874 int i;
5875
5876 /* Support only storing a constant number of fixed-point registers to
5877 memory and only bother with this if more than two; the machine
5878 doesn't support more than eight. */
5879 if (GET_CODE (operands[2]) != CONST_INT
5880 || INTVAL (operands[2]) <= 2
5881 || INTVAL (operands[2]) > 8
5882 || GET_CODE (operands[0]) != MEM
5883 || GET_CODE (operands[1]) != REG
5884 || REGNO (operands[1]) >= 32)
5885 FAIL;
5886
5887 count = INTVAL (operands[2]);
5888 regno = REGNO (operands[1]);
5889
5890 operands[3] = gen_rtx (PARALLEL, VOIDmode, rtvec_alloc (count + 1));
5891 to = force_reg (SImode, XEXP (operands[0], 0));
5892
5893 XVECEXP (operands[3], 0, 0)
5894 = gen_rtx (SET, VOIDmode, gen_rtx (MEM, SImode, to), operands[1]);
5895 XVECEXP (operands[3], 0, 1) = gen_rtx (CLOBBER, VOIDmode,
5896 gen_rtx (SCRATCH, SImode));
5897
5898 for (i = 1; i < count; i++)
5899 XVECEXP (operands[3], 0, i + 1)
5900 = gen_rtx (SET, VOIDmode,
5901 gen_rtx (MEM, SImode, plus_constant (to, i * 4)),
5902 gen_rtx (REG, SImode, regno + i));
5903 }")
5904
5905 (define_insn ""
5906 [(match_parallel 0 "store_multiple_operation"
5907 [(set (match_operand:SI 1 "indirect_operand" "=Q")
5908 (match_operand:SI 2 "gpc_reg_operand" "r"))
5909 (clobber (match_scratch:SI 3 "=q"))])]
5910 "TARGET_STRING && TARGET_POWER"
5911 "{stsi|stswi} %2,%P1,%O0")
5912
5913 (define_insn ""
5914 [(match_parallel 0 "store_multiple_operation"
5915 [(set (mem:SI (match_operand:SI 1 "register_operand" "b"))
5916 (match_operand:SI 2 "gpc_reg_operand" "r"))
5917 (clobber (match_scratch:SI 3 "X"))])]
5918 "TARGET_STRING && !TARGET_POWER"
5919 "{stsi|stswi} %2,%1,%O0")
5920
5921 \f
5922 ;; String/block move insn.
5923 ;; Argument 0 is the destination
5924 ;; Argument 1 is the source
5925 ;; Argument 2 is the length
5926 ;; Argument 3 is the alignment
5927
5928 (define_expand "movstrsi"
5929 [(parallel [(set (match_operand:BLK 0 "" "")
5930 (match_operand:BLK 1 "" ""))
5931 (use (match_operand:SI 2 "" ""))
5932 (use (match_operand:SI 3 "" ""))])]
5933 ""
5934 "
5935 {
5936 if (expand_block_move (operands))
5937 DONE;
5938 else
5939 FAIL;
5940 }")
5941
5942 ;; Move up to 32 bytes at a time. The fixed registers are needed because the
5943 ;; register allocator doesn't have a clue about allocating 8 word registers
5944 (define_expand "movstrsi_8reg"
5945 [(parallel [(set (match_operand 0 "" "")
5946 (match_operand 1 "" ""))
5947 (use (match_operand 2 "" ""))
5948 (use (match_operand 3 "" ""))
5949 (clobber (reg:SI 5))
5950 (clobber (reg:SI 6))
5951 (clobber (reg:SI 7))
5952 (clobber (reg:SI 8))
5953 (clobber (reg:SI 9))
5954 (clobber (reg:SI 10))
5955 (clobber (reg:SI 11))
5956 (clobber (reg:SI 12))
5957 (clobber (match_scratch:SI 4 ""))])]
5958 "TARGET_STRING"
5959 "")
5960
5961 (define_insn ""
5962 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
5963 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
5964 (use (match_operand:SI 2 "immediate_operand" "i"))
5965 (use (match_operand:SI 3 "immediate_operand" "i"))
5966 (clobber (match_operand:SI 4 "register_operand" "=r"))
5967 (clobber (reg:SI 6))
5968 (clobber (reg:SI 7))
5969 (clobber (reg:SI 8))
5970 (clobber (reg:SI 9))
5971 (clobber (reg:SI 10))
5972 (clobber (reg:SI 11))
5973 (clobber (reg:SI 12))
5974 (clobber (match_scratch:SI 5 "=q"))]
5975 "TARGET_STRING && TARGET_POWER
5976 && ((INTVAL (operands[2]) > 24 && INTVAL (operands[2]) < 32) || INTVAL (operands[2]) == 0)
5977 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 12)
5978 && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 12)
5979 && REGNO (operands[4]) == 5"
5980 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
5981 [(set_attr "length" "8")])
5982
5983 (define_insn ""
5984 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
5985 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
5986 (use (match_operand:SI 2 "immediate_operand" "i"))
5987 (use (match_operand:SI 3 "immediate_operand" "i"))
5988 (clobber (match_operand:SI 4 "register_operand" "=r"))
5989 (clobber (reg:SI 6))
5990 (clobber (reg:SI 7))
5991 (clobber (reg:SI 8))
5992 (clobber (reg:SI 9))
5993 (clobber (reg:SI 10))
5994 (clobber (reg:SI 11))
5995 (clobber (reg:SI 12))
5996 (clobber (match_scratch:SI 5 "X"))]
5997 "TARGET_STRING && !TARGET_POWER
5998 && ((INTVAL (operands[2]) > 24 && INTVAL (operands[2]) < 32) || INTVAL (operands[2]) == 0)
5999 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 12)
6000 && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 12)
6001 && REGNO (operands[4]) == 5"
6002 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6003 [(set_attr "length" "8")])
6004
6005 ;; Move up to 24 bytes at a time. The fixed registers are needed because the
6006 ;; register allocator doesn't have a clue about allocating 6 word registers
6007 (define_expand "movstrsi_6reg"
6008 [(parallel [(set (match_operand 0 "" "")
6009 (match_operand 1 "" ""))
6010 (use (match_operand 2 "" ""))
6011 (use (match_operand 3 "" ""))
6012 (clobber (reg:SI 7))
6013 (clobber (reg:SI 8))
6014 (clobber (reg:SI 9))
6015 (clobber (reg:SI 10))
6016 (clobber (reg:SI 11))
6017 (clobber (reg:SI 12))
6018 (clobber (match_scratch:SI 4 ""))])]
6019 "TARGET_STRING"
6020 "")
6021
6022 (define_insn ""
6023 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6024 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6025 (use (match_operand:SI 2 "immediate_operand" "i"))
6026 (use (match_operand:SI 3 "immediate_operand" "i"))
6027 (clobber (match_operand:SI 4 "register_operand" "=r"))
6028 (clobber (reg:SI 8))
6029 (clobber (reg:SI 9))
6030 (clobber (reg:SI 10))
6031 (clobber (reg:SI 11))
6032 (clobber (reg:SI 12))
6033 (clobber (match_scratch:SI 5 "=q"))]
6034 "TARGET_STRING && TARGET_POWER
6035 && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 24
6036 && (REGNO (operands[0]) < 7 || REGNO (operands[0]) > 12)
6037 && (REGNO (operands[1]) < 7 || REGNO (operands[1]) > 12)
6038 && REGNO (operands[4]) == 7"
6039 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6040 [(set_attr "length" "8")])
6041
6042 (define_insn ""
6043 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6044 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6045 (use (match_operand:SI 2 "immediate_operand" "i"))
6046 (use (match_operand:SI 3 "immediate_operand" "i"))
6047 (clobber (match_operand:SI 4 "register_operand" "=r"))
6048 (clobber (reg:SI 8))
6049 (clobber (reg:SI 9))
6050 (clobber (reg:SI 10))
6051 (clobber (reg:SI 11))
6052 (clobber (reg:SI 12))
6053 (clobber (match_scratch:SI 5 "X"))]
6054 "TARGET_STRING && !TARGET_POWER
6055 && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 32
6056 && (REGNO (operands[0]) < 7 || REGNO (operands[0]) > 12)
6057 && (REGNO (operands[1]) < 7 || REGNO (operands[1]) > 12)
6058 && REGNO (operands[4]) == 7"
6059 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6060 [(set_attr "length" "8")])
6061
6062 ;; Move up to 16 bytes at a time, using 4 fixed registers to avoid spill problems
6063 ;; with TImode
6064 (define_expand "movstrsi_4reg"
6065 [(parallel [(set (match_operand 0 "" "")
6066 (match_operand 1 "" ""))
6067 (use (match_operand 2 "" ""))
6068 (use (match_operand 3 "" ""))
6069 (clobber (reg:SI 9))
6070 (clobber (reg:SI 10))
6071 (clobber (reg:SI 11))
6072 (clobber (reg:SI 12))
6073 (clobber (match_scratch:SI 4 ""))])]
6074 "TARGET_STRING"
6075 "")
6076
6077 (define_insn ""
6078 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6079 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6080 (use (match_operand:SI 2 "immediate_operand" "i"))
6081 (use (match_operand:SI 3 "immediate_operand" "i"))
6082 (clobber (match_operand:SI 4 "register_operand" "=r"))
6083 (clobber (reg:SI 10))
6084 (clobber (reg:SI 11))
6085 (clobber (reg:SI 12))
6086 (clobber (match_scratch:SI 5 "=q"))]
6087 "TARGET_STRING && TARGET_POWER
6088 && INTVAL (operands[2]) > 8 && INTVAL (operands[2]) <= 16
6089 && (REGNO (operands[0]) < 9 || REGNO (operands[0]) > 12)
6090 && (REGNO (operands[1]) < 9 || REGNO (operands[1]) > 12)
6091 && REGNO (operands[4]) == 9"
6092 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6093 [(set_attr "length" "8")])
6094
6095 (define_insn ""
6096 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6097 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6098 (use (match_operand:SI 2 "immediate_operand" "i"))
6099 (use (match_operand:SI 3 "immediate_operand" "i"))
6100 (clobber (match_operand:SI 4 "register_operand" "=r"))
6101 (clobber (reg:SI 10))
6102 (clobber (reg:SI 11))
6103 (clobber (reg:SI 12))
6104 (clobber (match_scratch:SI 5 "X"))]
6105 "TARGET_STRING && !TARGET_POWER
6106 && INTVAL (operands[2]) > 8 && INTVAL (operands[2]) <= 16
6107 && (REGNO (operands[0]) < 9 || REGNO (operands[0]) > 12)
6108 && (REGNO (operands[1]) < 9 || REGNO (operands[1]) > 12)
6109 && REGNO (operands[4]) == 9"
6110 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6111 [(set_attr "length" "8")])
6112
6113 ;; Move up to 8 bytes at a time.
6114 (define_expand "movstrsi_2reg"
6115 [(parallel [(set (match_operand 0 "" "")
6116 (match_operand 1 "" ""))
6117 (use (match_operand 2 "" ""))
6118 (use (match_operand 3 "" ""))
6119 (clobber (match_scratch:DI 4 ""))
6120 (clobber (match_scratch:SI 5 ""))])]
6121 "TARGET_STRING && !TARGET_64BIT"
6122 "")
6123
6124 (define_insn ""
6125 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6126 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6127 (use (match_operand:SI 2 "immediate_operand" "i"))
6128 (use (match_operand:SI 3 "immediate_operand" "i"))
6129 (clobber (match_scratch:DI 4 "=&r"))
6130 (clobber (match_scratch:SI 5 "=q"))]
6131 "TARGET_STRING && TARGET_POWER && !TARGET_64BIT
6132 && INTVAL (operands[2]) > 4 && INTVAL (operands[2]) <= 8"
6133 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6134 [(set_attr "length" "8")])
6135
6136 (define_insn ""
6137 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6138 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6139 (use (match_operand:SI 2 "immediate_operand" "i"))
6140 (use (match_operand:SI 3 "immediate_operand" "i"))
6141 (clobber (match_scratch:DI 4 "=&r"))
6142 (clobber (match_scratch:SI 5 "X"))]
6143 "TARGET_STRING && !TARGET_POWER && !TARGET_64BIT
6144 && INTVAL (operands[2]) > 4 && INTVAL (operands[2]) <= 8"
6145 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6146 [(set_attr "length" "8")])
6147
6148 ;; Move up to 4 bytes at a time.
6149 (define_expand "movstrsi_1reg"
6150 [(parallel [(set (match_operand 0 "" "")
6151 (match_operand 1 "" ""))
6152 (use (match_operand 2 "" ""))
6153 (use (match_operand 3 "" ""))
6154 (clobber (match_scratch:SI 4 ""))
6155 (clobber (match_scratch:SI 5 ""))])]
6156 "TARGET_STRING"
6157 "")
6158
6159 (define_insn ""
6160 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6161 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6162 (use (match_operand:SI 2 "immediate_operand" "i"))
6163 (use (match_operand:SI 3 "immediate_operand" "i"))
6164 (clobber (match_scratch:SI 4 "=&r"))
6165 (clobber (match_scratch:SI 5 "=q"))]
6166 "TARGET_STRING && TARGET_POWER
6167 && INTVAL (operands[2]) > 0 && INTVAL (operands[2]) <= 4"
6168 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6169 [(set_attr "length" "8")])
6170
6171 (define_insn ""
6172 [(set (mem:BLK (match_operand:SI 0 "register_operand" "b"))
6173 (mem:BLK (match_operand:SI 1 "register_operand" "b")))
6174 (use (match_operand:SI 2 "immediate_operand" "i"))
6175 (use (match_operand:SI 3 "immediate_operand" "i"))
6176 (clobber (match_scratch:SI 4 "=&r"))
6177 (clobber (match_scratch:SI 5 "X"))]
6178 "TARGET_STRING && !TARGET_POWER
6179 && INTVAL (operands[2]) > 0 && INTVAL (operands[2]) <= 4"
6180 "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2"
6181 [(set_attr "length" "8")])
6182
6183 \f
6184 ;; Define insns that do load or store with update. Some of these we can
6185 ;; get by using pre-decrement or pre-increment, but the hardware can also
6186 ;; do cases where the increment is not the size of the object.
6187 ;;
6188 ;; In all these cases, we use operands 0 and 1 for the register being
6189 ;; incremented because those are the operands that local-alloc will
6190 ;; tie and these are the pair most likely to be tieable (and the ones
6191 ;; that will benefit the most).
6192
6193 (define_insn ""
6194 [(set (match_operand:DI 3 "gpc_reg_operand" "=r,r")
6195 (mem:DI (plus:DI (match_operand:DI 1 "gpc_reg_operand" "0,0")
6196 (match_operand:DI 2 "reg_or_short_operand" "r,I"))))
6197 (set (match_operand:DI 0 "gpc_reg_operand" "=b,b")
6198 (plus:DI (match_dup 1) (match_dup 2)))]
6199 "TARGET_POWERPC64"
6200 "@
6201 ldux %3,%0,%2
6202 ldu %3,%2(%0)"
6203 [(set_attr "type" "load")])
6204
6205 (define_insn ""
6206 [(set (match_operand:DI 3 "gpc_reg_operand" "=r")
6207 (sign_extend:DI
6208 (mem:SI (plus:DI (match_operand:DI 1 "gpc_reg_operand" "0")
6209 (match_operand:DI 2 "gpc_reg_operand" "r")))))
6210 (set (match_operand:DI 0 "gpc_reg_operand" "=b")
6211 (plus:DI (match_dup 1) (match_dup 2)))]
6212 "TARGET_POWERPC64"
6213 "lwaux %3,%0,%2"
6214 [(set_attr "type" "load")])
6215
6216 (define_insn "movdi_update"
6217 [(set (mem:DI (plus:DI (match_operand:DI 1 "gpc_reg_operand" "0,0")
6218 (match_operand:DI 2 "reg_or_short_operand" "r,I")))
6219 (match_operand:DI 3 "gpc_reg_operand" "r,r"))
6220 (set (match_operand:DI 0 "gpc_reg_operand" "=b,b")
6221 (plus:DI (match_dup 1) (match_dup 2)))]
6222 "TARGET_POWERPC64"
6223 "@
6224 stdux %3,%0,%2
6225 stdu %3,%2(%0)")
6226
6227 (define_insn ""
6228 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
6229 (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6230 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
6231 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6232 (plus:SI (match_dup 1) (match_dup 2)))]
6233 ""
6234 "@
6235 {lux|lwzux} %3,%0,%2
6236 {lu|lwzu} %3,%2(%0)"
6237 [(set_attr "type" "load")])
6238
6239 (define_insn "movsi_update"
6240 [(set (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6241 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
6242 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
6243 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6244 (plus:SI (match_dup 1) (match_dup 2)))]
6245 ""
6246 "@
6247 {stux|stwux} %3,%0,%2
6248 {stu|stwu} %3,%2(%0)")
6249
6250 (define_insn ""
6251 [(set (match_operand:HI 3 "gpc_reg_operand" "=r,r")
6252 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6253 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
6254 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6255 (plus:SI (match_dup 1) (match_dup 2)))]
6256 ""
6257 "@
6258 lhzux %3,%0,%2
6259 lhzu %3,%2(%0)"
6260 [(set_attr "type" "load")])
6261
6262 (define_insn ""
6263 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
6264 (zero_extend:SI
6265 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6266 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
6267 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6268 (plus:SI (match_dup 1) (match_dup 2)))]
6269 ""
6270 "@
6271 lhzux %3,%0,%2
6272 lhzu %3,%2(%0)"
6273 [(set_attr "type" "load")])
6274
6275 (define_insn ""
6276 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
6277 (sign_extend:SI
6278 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6279 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
6280 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6281 (plus:SI (match_dup 1) (match_dup 2)))]
6282 ""
6283 "@
6284 lhaux %3,%0,%2
6285 lhau %3,%2(%0)"
6286 [(set_attr "type" "load")])
6287
6288 (define_insn ""
6289 [(set (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6290 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
6291 (match_operand:HI 3 "gpc_reg_operand" "r,r"))
6292 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6293 (plus:SI (match_dup 1) (match_dup 2)))]
6294 ""
6295 "@
6296 sthux %3,%0,%2
6297 sthu %3,%2(%0)")
6298
6299 (define_insn ""
6300 [(set (match_operand:QI 3 "gpc_reg_operand" "=r,r")
6301 (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6302 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
6303 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6304 (plus:SI (match_dup 1) (match_dup 2)))]
6305 ""
6306 "@
6307 lbzux %3,%0,%2
6308 lbzu %3,%2(%0)"
6309 [(set_attr "type" "load")])
6310
6311 (define_insn ""
6312 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
6313 (zero_extend:SI
6314 (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6315 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
6316 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6317 (plus:SI (match_dup 1) (match_dup 2)))]
6318 ""
6319 "@
6320 lbzux %3,%0,%2
6321 lbzu %3,%2(%0)"
6322 [(set_attr "type" "load")])
6323
6324 (define_insn ""
6325 [(set (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6326 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
6327 (match_operand:QI 3 "gpc_reg_operand" "r,r"))
6328 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6329 (plus:SI (match_dup 1) (match_dup 2)))]
6330 ""
6331 "@
6332 stbux %3,%0,%2
6333 stbu %3,%2(%0)")
6334
6335 (define_insn ""
6336 [(set (match_operand:SF 3 "gpc_reg_operand" "=f,f")
6337 (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6338 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
6339 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6340 (plus:SI (match_dup 1) (match_dup 2)))]
6341 "TARGET_HARD_FLOAT"
6342 "@
6343 lfsux %3,%0,%2
6344 lfsu %3,%2(%0)"
6345 [(set_attr "type" "fpload")])
6346
6347 (define_insn ""
6348 [(set (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6349 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
6350 (match_operand:SF 3 "gpc_reg_operand" "f,f"))
6351 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6352 (plus:SI (match_dup 1) (match_dup 2)))]
6353 "TARGET_HARD_FLOAT"
6354 "@
6355 stfsux %3,%0,%2
6356 stfsu %3,%2(%0)")
6357
6358 (define_insn ""
6359 [(set (match_operand:DF 3 "gpc_reg_operand" "=f,f")
6360 (mem:DF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6361 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
6362 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6363 (plus:SI (match_dup 1) (match_dup 2)))]
6364 "TARGET_HARD_FLOAT"
6365 "@
6366 lfdux %3,%0,%2
6367 lfdu %3,%2(%0)"
6368 [(set_attr "type" "fpload")])
6369
6370 (define_insn ""
6371 [(set (mem:DF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
6372 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
6373 (match_operand:DF 3 "gpc_reg_operand" "f,f"))
6374 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
6375 (plus:SI (match_dup 1) (match_dup 2)))]
6376 "TARGET_HARD_FLOAT"
6377 "@
6378 stfdux %3,%0,%2
6379 stfdu %3,%2(%0)")
6380
6381 ;; Peephole to convert two consecutive FP loads or stores into lfq/stfq.
6382
6383 (define_peephole
6384 [(set (match_operand:DF 0 "gpc_reg_operand" "=f")
6385 (match_operand:DF 1 "memory_operand" ""))
6386 (set (match_operand:DF 2 "gpc_reg_operand" "=f")
6387 (match_operand:DF 3 "memory_operand" ""))]
6388 "TARGET_POWER2
6389 && TARGET_HARD_FLOAT
6390 && registers_ok_for_quad_peep (operands[0], operands[2])
6391 && ! MEM_VOLATILE_P (operands[1]) && ! MEM_VOLATILE_P (operands[3])
6392 && addrs_ok_for_quad_peep (XEXP (operands[1], 0), XEXP (operands[3], 0))"
6393 "lfq%U1%X1 %0,%1")
6394
6395 (define_peephole
6396 [(set (match_operand:DF 0 "memory_operand" "")
6397 (match_operand:DF 1 "gpc_reg_operand" "f"))
6398 (set (match_operand:DF 2 "memory_operand" "")
6399 (match_operand:DF 3 "gpc_reg_operand" "f"))]
6400 "TARGET_POWER2
6401 && TARGET_HARD_FLOAT
6402 && registers_ok_for_quad_peep (operands[1], operands[3])
6403 && ! MEM_VOLATILE_P (operands[0]) && ! MEM_VOLATILE_P (operands[2])
6404 && addrs_ok_for_quad_peep (XEXP (operands[0], 0), XEXP (operands[2], 0))"
6405 "stfq%U0%X0 %1,%0")
6406 \f
6407 ;; Next come insns related to the calling sequence.
6408 ;;
6409 ;; First, an insn to allocate new stack space for dynamic use (e.g., alloca).
6410 ;; We move the back-chain and decrement the stack pointer.
6411
6412 (define_expand "allocate_stack"
6413 [(set (reg:SI 1)
6414 (minus:SI (reg:SI 1) (match_operand:SI 0 "reg_or_short_operand" "")))]
6415 ""
6416 "
6417 { rtx chain = gen_reg_rtx (Pmode);
6418 rtx stack_bot = gen_rtx (MEM, Pmode, stack_pointer_rtx);
6419 rtx neg_op0;
6420
6421 emit_move_insn (chain, stack_bot);
6422
6423 /* Under Windows NT, we need to add stack probes for large/variable allocations,
6424 so do it via a call to the external function alloca, instead of doing it
6425 inline. */
6426 if (DEFAULT_ABI == ABI_NT
6427 && (GET_CODE (operands[0]) != CONST_INT || INTVAL (operands[0]) > 4096))
6428 {
6429 rtx tmp = gen_reg_rtx (SImode);
6430 emit_library_call_value (gen_rtx (SYMBOL_REF, Pmode, \"__allocate_stack\"),
6431 tmp, 0, SImode, 1, operands[0], Pmode);
6432 emit_insn (gen_set_sp (tmp));
6433 DONE;
6434 }
6435
6436 if (GET_CODE (operands[0]) != CONST_INT
6437 || INTVAL (operands[0]) < -32767
6438 || INTVAL (operands[0]) > 32768)
6439 {
6440 neg_op0 = gen_reg_rtx (Pmode);
6441 if (TARGET_32BIT)
6442 emit_insn (gen_negsi2 (neg_op0, operands[0]));
6443 else
6444 emit_insn (gen_negdi2 (neg_op0, operands[0]));
6445 }
6446 else
6447 neg_op0 = GEN_INT (- INTVAL (operands[0]));
6448
6449 if (TARGET_32BIT)
6450 emit_insn (gen_movsi_update (stack_pointer_rtx, stack_pointer_rtx, neg_op0, chain));
6451 else
6452 emit_insn (gen_movdi_update (stack_pointer_rtx, stack_pointer_rtx, neg_op0, chain));
6453
6454 DONE;
6455 }")
6456
6457 ;; Marker to indicate that the stack pointer was changed under NT in
6458 ;; ways not known to the compiler
6459
6460 (define_insn "set_sp"
6461 [(set (reg:SI 1)
6462 (unspec [(match_operand:SI 0 "register_operand" "r")] 7))]
6463 ""
6464 ""
6465 [(set_attr "length" "0")])
6466
6467 ;; These patterns say how to save and restore the stack pointer. We need not
6468 ;; save the stack pointer at function level since we are careful to
6469 ;; preserve the backchain. At block level, we have to restore the backchain
6470 ;; when we restore the stack pointer.
6471 ;;
6472 ;; For nonlocal gotos, we must save both the stack pointer and its
6473 ;; backchain and restore both. Note that in the nonlocal case, the
6474 ;; save area is a memory location.
6475
6476 (define_expand "save_stack_function"
6477 [(use (const_int 0))]
6478 ""
6479 "")
6480
6481 (define_expand "restore_stack_function"
6482 [(use (const_int 0))]
6483 ""
6484 "")
6485
6486 (define_expand "restore_stack_block"
6487 [(set (match_dup 2) (mem:SI (match_operand:SI 0 "register_operand" "")))
6488 (set (match_dup 0) (match_operand:SI 1 "register_operand" ""))
6489 (set (mem:SI (match_dup 0)) (match_dup 2))]
6490 ""
6491 "
6492 { operands[2] = gen_reg_rtx (SImode); }")
6493
6494 (define_expand "save_stack_nonlocal"
6495 [(match_operand:DI 0 "memory_operand" "")
6496 (match_operand:SI 1 "register_operand" "")]
6497 ""
6498 "
6499 {
6500 rtx temp = gen_reg_rtx (SImode);
6501
6502 /* Copy the backchain to the first word, sp to the second. */
6503 emit_move_insn (temp, gen_rtx (MEM, SImode, operands[1]));
6504 emit_move_insn (operand_subword (operands[0], 0, 0, DImode), temp);
6505 emit_move_insn (operand_subword (operands[0], 1, 0, DImode), operands[1]);
6506 DONE;
6507 }")
6508
6509 (define_expand "restore_stack_nonlocal"
6510 [(match_operand:SI 0 "register_operand" "")
6511 (match_operand:DI 1 "memory_operand" "")]
6512 ""
6513 "
6514 {
6515 rtx temp = gen_reg_rtx (SImode);
6516
6517 /* Restore the backchain from the first word, sp from the second. */
6518 emit_move_insn (temp, operand_subword (operands[1], 0, 0, DImode));
6519 emit_move_insn (operands[0], operand_subword (operands[1], 1, 0, DImode));
6520 emit_move_insn (gen_rtx (MEM, SImode, operands[0]), temp);
6521 DONE;
6522 }")
6523 \f
6524
6525 ;; A function pointer under AIX is a pointer to a data area whose first word
6526 ;; contains the actual address of the function, whose second word contains a
6527 ;; pointer to its TOC, and whose third word contains a value to place in the
6528 ;; static chain register (r11). Note that if we load the static chain, our
6529 ;; "trampoline" need not have any executable code.
6530 ;;
6531 ;; operands[0] is a register pointing to the 3 word descriptor (aka, the function address)
6532 ;; operands[1] is the stack size to clean up
6533 ;; operands[2] is the value FUNCTION_ARG returns for the VOID argument (must be 0 for AIX)
6534 ;; operands[3] is location to store the TOC
6535 ;; operands[4] is the TOC register
6536 ;; operands[5] is the static chain register
6537 ;;
6538 ;; We do not break this into separate insns, so that the scheduler will not try
6539 ;; to move the load of the new TOC before any loads from the TOC.
6540
6541 (define_insn "call_indirect_aix"
6542 [(call (mem:SI (match_operand:SI 0 "register_operand" "b"))
6543 (match_operand 1 "const_int_operand" "n"))
6544 (use (match_operand 2 "const_int_operand" "n"))
6545 (use (match_operand 3 "offsettable_addr_operand" "p"))
6546 (use (match_operand 4 "register_operand" "r"))
6547 (clobber (match_operand 5 "register_operand" "=r"))
6548 (clobber (match_scratch:SI 6 "=&r"))
6549 (clobber (match_scratch:SI 7 "=l"))]
6550 "DEFAULT_ABI == ABI_AIX
6551 && (INTVAL (operands[2]) == CALL_NORMAL || (INTVAL (operands[2]) & CALL_LONG) != 0)"
6552 "{st|stw} %4,%a3\;{l|lwz} %6,0(%0)\;{l|lwz} %4,4(%0)\;mt%7 %6\;{l|lwz} %5,8(%0)\;{brl|blrl}\;{l|lwz} %4,%a3"
6553 [(set_attr "length" "28")])
6554
6555 (define_insn "call_value_indirect_aix"
6556 [(set (match_operand 0 "register_operand" "fg")
6557 (call (mem:SI (match_operand:SI 1 "register_operand" "b"))
6558 (match_operand 2 "const_int_operand" "n")))
6559 (use (match_operand 3 "const_int_operand" "n"))
6560 (use (match_operand 4 "offsettable_addr_operand" "p"))
6561 (use (match_operand 5 "register_operand" "r"))
6562 (clobber (match_operand 6 "register_operand" "=r"))
6563 (clobber (match_scratch:SI 7 "=&r"))
6564 (clobber (match_scratch:SI 8 "=l"))]
6565 "DEFAULT_ABI == ABI_AIX
6566 && (INTVAL (operands[3]) == CALL_NORMAL || (INTVAL (operands[3]) & CALL_LONG) != 0)"
6567 "{st|stw} %5,%a4\;{l|lwz} %7,0(%1)\;{l|lwz} %5,4(%1);\;mt%8 %7\;{l|lwz} %6,8(%1)\;{brl|blrl}\;{l|lwz} %5,%a4"
6568 [(set_attr "length" "28")])
6569
6570 ;; A function pointer undef NT is a pointer to a data area whose first word
6571 ;; contains the actual address of the function, whose second word contains a
6572 ;; pointer to its TOC. The static chain is not stored under NT, which means
6573 ;; that we need a trampoline.
6574 ;;
6575 ;; operands[0] is an SImode pseudo in which we place the address of the function.
6576 ;; operands[1] is the stack size to clean up
6577 ;; operands[2] is the value FUNCTION_ARG returns for the VOID argument (must be 0 for NT)
6578 ;; operands[3] is location to store the TOC
6579 ;; operands[4] is the TOC register
6580 ;;
6581 ;; We do not break this into separate insns, so that the scheduler will not try
6582 ;; to move the load of the new TOC before any loads from the TOC.
6583
6584 (define_insn "call_indirect_nt"
6585 [(call (mem:SI (match_operand:SI 0 "register_operand" "b"))
6586 (match_operand 1 "const_int_operand" "n"))
6587 (use (match_operand 2 "const_int_operand" "n"))
6588 (use (match_operand 3 "offsettable_addr_operand" "p"))
6589 (use (match_operand 4 "register_operand" "r"))
6590 (clobber (match_scratch:SI 5 "=&r"))
6591 (clobber (match_scratch:SI 6 "=l"))]
6592 "DEFAULT_ABI == ABI_NT
6593 && (INTVAL (operands[2]) == CALL_NORMAL || (INTVAL (operands[2]) & CALL_LONG) != 0)"
6594 "{st|stw} %4,%a3\;{l|lwz} %5,0(%0)\;{l|lwz} %4,4(%0)\;mt%6 %5\;{brl|blrl}\;{l|lwz} %4,%a3"
6595 [(set_attr "length" "24")])
6596
6597 (define_insn "call_value_indirect_nt"
6598 [(set (match_operand 0 "register_operand" "fg")
6599 (call (mem:SI (match_operand:SI 1 "register_operand" "b"))
6600 (match_operand 2 "const_int_operand" "n")))
6601 (use (match_operand 3 "const_int_operand" "n"))
6602 (use (match_operand 4 "offsettable_addr_operand" "p"))
6603 (use (match_operand 5 "register_operand" "r"))
6604 (clobber (match_scratch:SI 6 "=&r"))
6605 (clobber (match_scratch:SI 7 "=l"))]
6606 "DEFAULT_ABI == ABI_NT
6607 && (INTVAL (operands[3]) == CALL_NORMAL || (INTVAL (operands[3]) & CALL_LONG) != 0)"
6608 "{st|stw} %5,%a4\;{l|lwz} %6,0(%1)\;{l|lwz} %5,4(%1)\;mt%7 %6\;{brl|blrl}\;{l|lwz} %5,%a4"
6609 [(set_attr "length" "24")])
6610
6611 ;; A function pointer under System V is just a normal pointer
6612 ;; operands[0] is the function pointer
6613 ;; operands[1] is the stack size to clean up
6614 ;; operands[2] is the value FUNCTION_ARG returns for the VOID argument which indicates how to set cr1
6615
6616 (define_insn "call_indirect_sysv"
6617 [(call (mem:SI (match_operand:SI 0 "register_operand" "l,l"))
6618 (match_operand 1 "const_int_operand" "n,n"))
6619 (use (match_operand 2 "const_int_operand" "O,n"))
6620 (clobber (match_scratch:SI 3 "=l,l"))]
6621 "DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_AIX_NODESC"
6622 "*
6623 {
6624 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
6625 output_asm_insn (\"crxor 6,6,6\", operands);
6626
6627 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
6628 output_asm_insn (\"creqv 6,6,6\", operands);
6629
6630 return \"{brl|blrl}\";
6631 }"
6632 [(set_attr "length" "4,8")])
6633
6634 (define_insn "call_value_indirect_sysv"
6635 [(set (match_operand 0 "register_operand" "=fg,fg")
6636 (call (mem:SI (match_operand:SI 1 "register_operand" "l,l"))
6637 (match_operand 2 "const_int_operand" "n,n")))
6638 (use (match_operand 3 "const_int_operand" "O,n"))
6639 (clobber (match_scratch:SI 4 "=l,l"))]
6640 "DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_AIX_NODESC"
6641 "*
6642 {
6643 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
6644 output_asm_insn (\"crxor 6,6,6\", operands);
6645
6646 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
6647 output_asm_insn (\"creqv 6,6,6\", operands);
6648
6649 return \"{brl|blrl}\";
6650 }"
6651 [(set_attr "length" "4,8")])
6652
6653 ;; Now the definitions for the call and call_value insns
6654 (define_expand "call"
6655 [(parallel [(call (mem:SI (match_operand:SI 0 "address_operand" ""))
6656 (match_operand 1 "" ""))
6657 (use (match_operand 2 "" ""))
6658 (clobber (scratch:SI))])]
6659 ""
6660 "
6661 {
6662 if (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != CONST_INT)
6663 abort ();
6664
6665 operands[0] = XEXP (operands[0], 0);
6666
6667 /* Convert NT DLL imports into an indirect call. */
6668 if (GET_CODE (operands[0]) == SYMBOL_REF
6669 && (INTVAL (operands[2]) & CALL_NT_DLLIMPORT) != 0)
6670 {
6671 operands[0] = rs6000_dll_import_ref (operands[0]);
6672 operands[2] = GEN_INT ((int)CALL_NORMAL);
6673 }
6674
6675 if (GET_CODE (operands[0]) != SYMBOL_REF
6676 || (INTVAL (operands[2]) & CALL_LONG) != 0)
6677 {
6678 if (INTVAL (operands[2]) & CALL_LONG)
6679 operands[0] = rs6000_longcall_ref (operands[0]);
6680
6681 if (DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_AIX_NODESC)
6682 emit_call_insn (gen_call_indirect_sysv (force_reg (Pmode, operands[0]),
6683 operands[1], operands[2]));
6684 else
6685 {
6686 rtx toc_reg = gen_rtx (REG, Pmode, 2);
6687 rtx toc_addr = RS6000_SAVE_TOC;
6688
6689 if (DEFAULT_ABI == ABI_AIX)
6690 {
6691 /* AIX function pointers are really pointers to a three word area */
6692 rtx static_chain = gen_rtx (REG, Pmode, STATIC_CHAIN_REGNUM);
6693 emit_call_insn (gen_call_indirect_aix (force_reg (Pmode, operands[0]),
6694 operands[1], operands[2],
6695 toc_addr, toc_reg, static_chain));
6696 }
6697 else if (DEFAULT_ABI == ABI_NT)
6698 {
6699 /* NT function pointers are really pointers to a two word area */
6700 rs6000_save_toc_p = 1;
6701 emit_call_insn (gen_call_indirect_nt (force_reg (Pmode, operands[0]),
6702 operands[1], operands[2],
6703 toc_addr, toc_reg));
6704 }
6705 else
6706 abort ();
6707 }
6708 DONE;
6709 }
6710 }")
6711
6712 (define_expand "call_value"
6713 [(parallel [(set (match_operand 0 "" "")
6714 (call (mem:SI (match_operand:SI 1 "address_operand" ""))
6715 (match_operand 2 "" "")))
6716 (use (match_operand 3 "" ""))
6717 (clobber (scratch:SI))])]
6718 ""
6719 "
6720 {
6721 if (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != CONST_INT)
6722 abort ();
6723
6724 operands[1] = XEXP (operands[1], 0);
6725
6726 /* Convert NT DLL imports into an indirect call. */
6727 if (GET_CODE (operands[1]) == SYMBOL_REF
6728 && (INTVAL (operands[3]) & CALL_NT_DLLIMPORT) != 0)
6729 {
6730 operands[1] = rs6000_dll_import_ref (operands[1]);
6731 operands[3] = GEN_INT ((int)CALL_NORMAL);
6732 }
6733
6734 if (GET_CODE (operands[1]) != SYMBOL_REF
6735 || (INTVAL (operands[3]) & CALL_LONG) != 0)
6736 {
6737 if (INTVAL (operands[2]) & CALL_LONG)
6738 operands[1] = rs6000_longcall_ref (operands[1]);
6739
6740 if (DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_AIX_NODESC)
6741 emit_call_insn (gen_call_value_indirect_sysv (operands[0], operands[1],
6742 operands[2], operands[3]));
6743 else
6744 {
6745 rtx toc_reg = gen_rtx (REG, Pmode, 2);
6746 rtx toc_addr = RS6000_SAVE_TOC;
6747
6748 if (DEFAULT_ABI == ABI_AIX)
6749 {
6750 /* AIX function pointers are really pointers to a three word area */
6751 rtx static_chain = gen_rtx (REG, Pmode, STATIC_CHAIN_REGNUM);
6752 emit_call_insn (gen_call_value_indirect_aix (operands[0],
6753 force_reg (Pmode, operands[1]),
6754 operands[2], operands[3],
6755 toc_addr, toc_reg, static_chain));
6756 }
6757 else if (DEFAULT_ABI == ABI_NT)
6758 {
6759 /* NT function pointers are really pointers to a two word area */
6760 rs6000_save_toc_p = 1;
6761 emit_call_insn (gen_call_value_indirect_nt (operands[0],
6762 force_reg (Pmode, operands[1]),
6763 operands[2], operands[3],
6764 toc_addr, toc_reg));
6765 }
6766 else
6767 abort ();
6768 }
6769 DONE;
6770 }
6771 }")
6772
6773 ;; Call to function in current module. No TOC pointer reload needed.
6774 ;; Operand2 is non-zero if we are using the V.4 calling sequence and
6775 ;; either the function was not prototyped, or it was prototyped as a
6776 ;; variable argument function. It is > 0 if FP registers were passed
6777 ;; and < 0 if they were not.
6778
6779 (define_insn ""
6780 [(call (mem:SI (match_operand:SI 0 "current_file_function_operand" "s,s"))
6781 (match_operand 1 "" "g,g"))
6782 (use (match_operand:SI 2 "immediate_operand" "O,n"))
6783 (clobber (match_scratch:SI 3 "=l,l"))]
6784 "INTVAL (operands[2]) != CALL_LONG"
6785 "*
6786 {
6787 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
6788 output_asm_insn (\"crxor 6,6,6\", operands);
6789
6790 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
6791 output_asm_insn (\"creqv 6,6,6\", operands);
6792
6793 return \"bl %z0\";
6794 }"
6795 [(set_attr "length" "4,8")])
6796
6797 ;; Call to function which may be in another module. Restore the TOC
6798 ;; pointer (r2) after the call unless this is System V.
6799 ;; Operand2 is non-zero if we are using the V.4 calling sequence and
6800 ;; either the function was not prototyped, or it was prototyped as a
6801 ;; variable argument function. It is > 0 if FP registers were passed
6802 ;; and < 0 if they were not.
6803
6804 (define_insn ""
6805 [(call (mem:SI (match_operand:SI 0 "call_operand" "s,s"))
6806 (match_operand 1 "" "fg,fg"))
6807 (use (match_operand:SI 2 "immediate_operand" "O,n"))
6808 (clobber (match_scratch:SI 3 "=l,l"))]
6809 "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_NT)
6810 && INTVAL (operands[2]) != CALL_LONG"
6811 "*
6812 {
6813 /* Indirect calls should go through call_indirect */
6814 if (GET_CODE (operands[0]) == REG)
6815 abort ();
6816
6817 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
6818 output_asm_insn (\"crxor 6,6,6\", operands);
6819
6820 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
6821 output_asm_insn (\"creqv 6,6,6\", operands);
6822
6823 return (TARGET_WINDOWS_NT) ? \"bl %z0\;.znop %z0\" : \"bl %z0\;%.\";
6824 }"
6825 [(set_attr "length" "8,12")])
6826
6827 (define_insn ""
6828 [(call (mem:SI (match_operand:SI 0 "call_operand" "s,s"))
6829 (match_operand 1 "" "fg,fg"))
6830 (use (match_operand:SI 2 "immediate_operand" "O,n"))
6831 (clobber (match_scratch:SI 3 "=l,l"))]
6832 "(DEFAULT_ABI == ABI_AIX_NODESC || DEFAULT_ABI == ABI_V4)
6833 && INTVAL (operands[2]) != CALL_LONG"
6834 "*
6835 {
6836 /* Indirect calls should go through call_indirect */
6837 if (GET_CODE (operands[0]) == REG)
6838 abort ();
6839
6840 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
6841 output_asm_insn (\"crxor 6,6,6\", operands);
6842
6843 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
6844 output_asm_insn (\"creqv 6,6,6\", operands);
6845
6846 return \"bl %z0\";
6847 }"
6848 [(set_attr "length" "4,8")])
6849
6850 (define_insn ""
6851 [(set (match_operand 0 "" "=fg,fg")
6852 (call (mem:SI (match_operand:SI 1 "current_file_function_operand" "s,s"))
6853 (match_operand 2 "" "g,g")))
6854 (use (match_operand:SI 3 "immediate_operand" "O,n"))
6855 (clobber (match_scratch:SI 4 "=l,l"))]
6856 "INTVAL (operands[3]) != CALL_LONG"
6857 "*
6858 {
6859 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
6860 output_asm_insn (\"crxor 6,6,6\", operands);
6861
6862 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
6863 output_asm_insn (\"creqv 6,6,6\", operands);
6864
6865 return \"bl %z1\";
6866 }"
6867 [(set_attr "length" "4,8")])
6868
6869 (define_insn ""
6870 [(set (match_operand 0 "" "=fg,fg")
6871 (call (mem:SI (match_operand:SI 1 "call_operand" "s,s"))
6872 (match_operand 2 "" "fg,fg")))
6873 (use (match_operand:SI 3 "immediate_operand" "O,n"))
6874 (clobber (match_scratch:SI 4 "=l,l"))]
6875 "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_NT)
6876 && INTVAL (operands[3]) != CALL_LONG"
6877 "*
6878 {
6879 /* This should be handled by call_value_indirect */
6880 if (GET_CODE (operands[1]) == REG)
6881 abort ();
6882
6883 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
6884 output_asm_insn (\"crxor 6,6,6\", operands);
6885
6886 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
6887 output_asm_insn (\"creqv 6,6,6\", operands);
6888
6889 return (TARGET_WINDOWS_NT) ? \"bl %z1\;.znop %z1\" : \"bl %z1\;%.\";
6890 }"
6891 [(set_attr "length" "8,12")])
6892
6893 (define_insn ""
6894 [(set (match_operand 0 "" "=fg,fg")
6895 (call (mem:SI (match_operand:SI 1 "call_operand" "s,s"))
6896 (match_operand 2 "" "fg,fg")))
6897 (use (match_operand:SI 3 "immediate_operand" "O,n"))
6898 (clobber (match_scratch:SI 4 "=l,l"))]
6899 "(DEFAULT_ABI == ABI_AIX_NODESC || DEFAULT_ABI == ABI_V4)
6900 && INTVAL (operands[3]) != CALL_LONG"
6901 "*
6902 {
6903 /* This should be handled by call_value_indirect */
6904 if (GET_CODE (operands[1]) == REG)
6905 abort ();
6906
6907 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
6908 output_asm_insn (\"crxor 6,6,6\", operands);
6909
6910 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
6911 output_asm_insn (\"creqv 6,6,6\", operands);
6912
6913 return \"bl %z1\";
6914 }"
6915 [(set_attr "length" "4,8")])
6916
6917
6918 ;; Call subroutine returning any type.
6919
6920 (define_expand "untyped_call"
6921 [(parallel [(call (match_operand 0 "" "")
6922 (const_int 0))
6923 (match_operand 1 "" "")
6924 (match_operand 2 "" "")])]
6925 ""
6926 "
6927 {
6928 int i;
6929
6930 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx, const0_rtx));
6931
6932 for (i = 0; i < XVECLEN (operands[2], 0); i++)
6933 {
6934 rtx set = XVECEXP (operands[2], 0, i);
6935 emit_move_insn (SET_DEST (set), SET_SRC (set));
6936 }
6937
6938 /* The optimizer does not know that the call sets the function value
6939 registers we stored in the result block. We avoid problems by
6940 claiming that all hard registers are used and clobbered at this
6941 point. */
6942 emit_insn (gen_blockage ());
6943
6944 DONE;
6945 }")
6946
6947 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
6948 ;; all of memory. This blocks insns from being moved across this point.
6949
6950 (define_insn "blockage"
6951 [(unspec_volatile [(const_int 0)] 0)]
6952 ""
6953 "")
6954
6955 ;; Synchronize instructions/data caches for V.4 trampolines
6956 ;; The extra memory_operand is to prevent the optimizer from
6957 ;; deleting insns with "no" effect.
6958 (define_insn "icbi"
6959 [(unspec [(match_operand 0 "memory_operand" "=m")
6960 (match_operand 1 "register_operand" "b")
6961 (match_operand 2 "register_operand" "r")] 3)]
6962 "TARGET_POWERPC"
6963 "icbi %1,%2")
6964
6965 (define_insn "dcbst"
6966 [(unspec [(match_operand 0 "memory_operand" "=m")
6967 (match_operand 1 "register_operand" "b")
6968 (match_operand 2 "register_operand" "r")] 4)]
6969 "TARGET_POWERPC"
6970 "dcbst %1,%2")
6971
6972 (define_insn "sync"
6973 [(unspec [(match_operand 0 "memory_operand" "=m")] 5)]
6974 ""
6975 "{dcs|sync}")
6976
6977 (define_insn "isync"
6978 [(unspec [(match_operand 0 "memory_operand" "=m")] 6)]
6979 ""
6980 "{ics|isync}")
6981
6982 \f
6983 ;; Compare insns are next. Note that the RS/6000 has two types of compares,
6984 ;; signed & unsigned, and one type of branch.
6985 ;;
6986 ;; Start with the DEFINE_EXPANDs to generate the rtl for compares, scc
6987 ;; insns, and branches. We store the operands of compares until we see
6988 ;; how it is used.
6989 (define_expand "cmpsi"
6990 [(set (cc0)
6991 (compare (match_operand:SI 0 "gpc_reg_operand" "")
6992 (match_operand:SI 1 "reg_or_short_operand" "")))]
6993 ""
6994 "
6995 {
6996 /* Take care of the possibility that operands[1] might be negative but
6997 this might be a logical operation. That insn doesn't exist. */
6998 if (GET_CODE (operands[1]) == CONST_INT
6999 && INTVAL (operands[1]) < 0)
7000 operands[1] = force_reg (SImode, operands[1]);
7001
7002 rs6000_compare_op0 = operands[0];
7003 rs6000_compare_op1 = operands[1];
7004 rs6000_compare_fp_p = 0;
7005 DONE;
7006 }")
7007
7008 (define_expand "cmpdi"
7009 [(set (cc0)
7010 (compare (match_operand:DI 0 "gpc_reg_operand" "")
7011 (match_operand:DI 1 "reg_or_short_operand" "")))]
7012 "TARGET_POWERPC64"
7013 "
7014 {
7015 /* Take care of the possibility that operands[1] might be negative but
7016 this might be a logical operation. That insn doesn't exist. */
7017 if (GET_CODE (operands[1]) == CONST_INT
7018 && INTVAL (operands[1]) < 0)
7019 operands[1] = force_reg (DImode, operands[1]);
7020
7021 rs6000_compare_op0 = operands[0];
7022 rs6000_compare_op1 = operands[1];
7023 rs6000_compare_fp_p = 0;
7024 DONE;
7025 }")
7026
7027 (define_expand "cmpsf"
7028 [(set (cc0) (compare (match_operand:SF 0 "gpc_reg_operand" "")
7029 (match_operand:SF 1 "gpc_reg_operand" "")))]
7030 "TARGET_HARD_FLOAT"
7031 "
7032 {
7033 rs6000_compare_op0 = operands[0];
7034 rs6000_compare_op1 = operands[1];
7035 rs6000_compare_fp_p = 1;
7036 DONE;
7037 }")
7038
7039 (define_expand "cmpdf"
7040 [(set (cc0) (compare (match_operand:DF 0 "gpc_reg_operand" "")
7041 (match_operand:DF 1 "gpc_reg_operand" "")))]
7042 "TARGET_HARD_FLOAT"
7043 "
7044 {
7045 rs6000_compare_op0 = operands[0];
7046 rs6000_compare_op1 = operands[1];
7047 rs6000_compare_fp_p = 1;
7048 DONE;
7049 }")
7050
7051 (define_expand "beq"
7052 [(set (match_dup 2) (match_dup 1))
7053 (set (pc)
7054 (if_then_else (eq (match_dup 2)
7055 (const_int 0))
7056 (label_ref (match_operand 0 "" ""))
7057 (pc)))]
7058 ""
7059 "
7060 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7061 operands[1] = gen_rtx (COMPARE, mode,
7062 rs6000_compare_op0, rs6000_compare_op1);
7063 operands[2] = gen_reg_rtx (mode);
7064 }")
7065
7066 (define_expand "bne"
7067 [(set (match_dup 2) (match_dup 1))
7068 (set (pc)
7069 (if_then_else (ne (match_dup 2)
7070 (const_int 0))
7071 (label_ref (match_operand 0 "" ""))
7072 (pc)))]
7073 ""
7074 "
7075 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7076 operands[1] = gen_rtx (COMPARE, mode,
7077 rs6000_compare_op0, rs6000_compare_op1);
7078 operands[2] = gen_reg_rtx (mode);
7079 }")
7080
7081 (define_expand "blt"
7082 [(set (match_dup 2) (match_dup 1))
7083 (set (pc)
7084 (if_then_else (lt (match_dup 2)
7085 (const_int 0))
7086 (label_ref (match_operand 0 "" ""))
7087 (pc)))]
7088 ""
7089 "
7090 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7091 operands[1] = gen_rtx (COMPARE, mode,
7092 rs6000_compare_op0, rs6000_compare_op1);
7093 operands[2] = gen_reg_rtx (mode);
7094 }")
7095
7096 (define_expand "bgt"
7097 [(set (match_dup 2) (match_dup 1))
7098 (set (pc)
7099 (if_then_else (gt (match_dup 2)
7100 (const_int 0))
7101 (label_ref (match_operand 0 "" ""))
7102 (pc)))]
7103 ""
7104 "
7105 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7106 operands[1] = gen_rtx (COMPARE, mode,
7107 rs6000_compare_op0, rs6000_compare_op1);
7108 operands[2] = gen_reg_rtx (mode);
7109 }")
7110
7111 (define_expand "ble"
7112 [(set (match_dup 2) (match_dup 1))
7113 (set (pc)
7114 (if_then_else (le (match_dup 2)
7115 (const_int 0))
7116 (label_ref (match_operand 0 "" ""))
7117 (pc)))]
7118 ""
7119 "
7120 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7121 operands[1] = gen_rtx (COMPARE, mode,
7122 rs6000_compare_op0, rs6000_compare_op1);
7123 operands[2] = gen_reg_rtx (mode);
7124 }")
7125
7126 (define_expand "bge"
7127 [(set (match_dup 2) (match_dup 1))
7128 (set (pc)
7129 (if_then_else (ge (match_dup 2)
7130 (const_int 0))
7131 (label_ref (match_operand 0 "" ""))
7132 (pc)))]
7133 ""
7134 "
7135 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7136 operands[1] = gen_rtx (COMPARE, mode,
7137 rs6000_compare_op0, rs6000_compare_op1);
7138 operands[2] = gen_reg_rtx (mode);
7139 }")
7140
7141 (define_expand "bgtu"
7142 [(set (match_dup 2) (match_dup 1))
7143 (set (pc)
7144 (if_then_else (gtu (match_dup 2)
7145 (const_int 0))
7146 (label_ref (match_operand 0 "" ""))
7147 (pc)))]
7148 ""
7149 "
7150 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7151 rs6000_compare_op0, rs6000_compare_op1);
7152 operands[2] = gen_reg_rtx (CCUNSmode);
7153 }")
7154
7155 (define_expand "bltu"
7156 [(set (match_dup 2) (match_dup 1))
7157 (set (pc)
7158 (if_then_else (ltu (match_dup 2)
7159 (const_int 0))
7160 (label_ref (match_operand 0 "" ""))
7161 (pc)))]
7162 ""
7163 "
7164 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7165 rs6000_compare_op0, rs6000_compare_op1);
7166 operands[2] = gen_reg_rtx (CCUNSmode);
7167 }")
7168
7169 (define_expand "bgeu"
7170 [(set (match_dup 2) (match_dup 1))
7171 (set (pc)
7172 (if_then_else (geu (match_dup 2)
7173 (const_int 0))
7174 (label_ref (match_operand 0 "" ""))
7175 (pc)))]
7176 ""
7177 "
7178 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7179 rs6000_compare_op0, rs6000_compare_op1);
7180 operands[2] = gen_reg_rtx (CCUNSmode);
7181 }")
7182
7183 (define_expand "bleu"
7184 [(set (match_dup 2) (match_dup 1))
7185 (set (pc)
7186 (if_then_else (leu (match_dup 2)
7187 (const_int 0))
7188 (label_ref (match_operand 0 "" ""))
7189 (pc)))]
7190 ""
7191 "
7192 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7193 rs6000_compare_op0, rs6000_compare_op1);
7194 operands[2] = gen_reg_rtx (CCUNSmode);
7195 }")
7196
7197 ;; For SNE, we would prefer that the xor/abs sequence be used for integers.
7198 ;; For SEQ, likewise, except that comparisons with zero should be done
7199 ;; with an scc insns. However, due to the order that combine see the
7200 ;; resulting insns, we must, in fact, allow SEQ for integers. Fail in
7201 ;; the cases we don't want to handle.
7202 (define_expand "seq"
7203 [(set (match_dup 2) (match_dup 1))
7204 (set (match_operand:SI 0 "gpc_reg_operand" "")
7205 (eq:SI (match_dup 2) (const_int 0)))]
7206 ""
7207 "
7208 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7209 operands[1] = gen_rtx (COMPARE, mode,
7210 rs6000_compare_op0, rs6000_compare_op1);
7211 operands[2] = gen_reg_rtx (mode);
7212 }")
7213
7214 (define_expand "sne"
7215 [(set (match_dup 2) (match_dup 1))
7216 (set (match_operand:SI 0 "gpc_reg_operand" "")
7217 (ne:SI (match_dup 2) (const_int 0)))]
7218 ""
7219 "
7220 { if (! rs6000_compare_fp_p)
7221 FAIL;
7222
7223 operands[1] = gen_rtx (COMPARE, CCFPmode,
7224 rs6000_compare_op0, rs6000_compare_op1);
7225 operands[2] = gen_reg_rtx (CCFPmode);
7226 }")
7227
7228 ;; A > 0 is best done using the portable sequence, so fail in that case.
7229 (define_expand "sgt"
7230 [(set (match_dup 2) (match_dup 1))
7231 (set (match_operand:SI 0 "gpc_reg_operand" "")
7232 (gt:SI (match_dup 2) (const_int 0)))]
7233 ""
7234 "
7235 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7236
7237 if (! rs6000_compare_fp_p && rs6000_compare_op1 == const0_rtx)
7238 FAIL;
7239
7240 operands[1] = gen_rtx (COMPARE, mode,
7241 rs6000_compare_op0, rs6000_compare_op1);
7242 operands[2] = gen_reg_rtx (mode);
7243 }")
7244
7245 ;; A < 0 is best done in the portable way for A an integer.
7246 (define_expand "slt"
7247 [(set (match_dup 2) (match_dup 1))
7248 (set (match_operand:SI 0 "gpc_reg_operand" "")
7249 (lt:SI (match_dup 2) (const_int 0)))]
7250 ""
7251 "
7252 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7253
7254 if (! rs6000_compare_fp_p && rs6000_compare_op1 == const0_rtx)
7255 FAIL;
7256
7257 operands[1] = gen_rtx (COMPARE, mode,
7258 rs6000_compare_op0, rs6000_compare_op1);
7259 operands[2] = gen_reg_rtx (mode);
7260 }")
7261
7262 (define_expand "sge"
7263 [(set (match_dup 2) (match_dup 1))
7264 (set (match_operand:SI 0 "gpc_reg_operand" "")
7265 (ge:SI (match_dup 2) (const_int 0)))]
7266 ""
7267 "
7268 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7269 operands[1] = gen_rtx (COMPARE, mode,
7270 rs6000_compare_op0, rs6000_compare_op1);
7271 operands[2] = gen_reg_rtx (mode);
7272 }")
7273
7274 ;; A <= 0 is best done the portable way for A an integer.
7275 (define_expand "sle"
7276 [(set (match_dup 2) (match_dup 1))
7277 (set (match_operand:SI 0 "gpc_reg_operand" "")
7278 (le:SI (match_dup 2) (const_int 0)))]
7279 ""
7280 "
7281 { enum machine_mode mode = rs6000_compare_fp_p ? CCFPmode : CCmode;
7282
7283 if (! rs6000_compare_fp_p && rs6000_compare_op1 == const0_rtx)
7284 FAIL;
7285
7286 operands[1] = gen_rtx (COMPARE, mode,
7287 rs6000_compare_op0, rs6000_compare_op1);
7288 operands[2] = gen_reg_rtx (mode);
7289 }")
7290
7291 (define_expand "sgtu"
7292 [(set (match_dup 2) (match_dup 1))
7293 (set (match_operand:SI 0 "gpc_reg_operand" "")
7294 (gtu:SI (match_dup 2) (const_int 0)))]
7295 ""
7296 "
7297 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7298 rs6000_compare_op0, rs6000_compare_op1);
7299 operands[2] = gen_reg_rtx (CCUNSmode);
7300 }")
7301
7302 (define_expand "sltu"
7303 [(set (match_dup 2) (match_dup 1))
7304 (set (match_operand:SI 0 "gpc_reg_operand" "")
7305 (ltu:SI (match_dup 2) (const_int 0)))]
7306 ""
7307 "
7308 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7309 rs6000_compare_op0, rs6000_compare_op1);
7310 operands[2] = gen_reg_rtx (CCUNSmode);
7311 }")
7312
7313 (define_expand "sgeu"
7314 [(set (match_dup 2) (match_dup 1))
7315 (set (match_operand:SI 0 "gpc_reg_operand" "")
7316 (geu:SI (match_dup 2) (const_int 0)))]
7317 ""
7318 "
7319 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7320 rs6000_compare_op0, rs6000_compare_op1);
7321 operands[2] = gen_reg_rtx (CCUNSmode);
7322 }")
7323
7324 (define_expand "sleu"
7325 [(set (match_dup 2) (match_dup 1))
7326 (set (match_operand:SI 0 "gpc_reg_operand" "")
7327 (leu:SI (match_dup 2) (const_int 0)))]
7328 ""
7329 "
7330 { operands[1] = gen_rtx (COMPARE, CCUNSmode,
7331 rs6000_compare_op0, rs6000_compare_op1);
7332 operands[2] = gen_reg_rtx (CCUNSmode);
7333 }")
7334 \f
7335 ;; Here are the actual compare insns.
7336 (define_insn ""
7337 [(set (match_operand:CC 0 "cc_reg_operand" "=y")
7338 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "r")
7339 (match_operand:SI 2 "reg_or_short_operand" "rI")))]
7340 ""
7341 "{cmp%I2|cmpw%I2} %0,%1,%2"
7342 [(set_attr "type" "compare")])
7343
7344 (define_insn ""
7345 [(set (match_operand:CC 0 "cc_reg_operand" "=y")
7346 (compare:CC (match_operand:DI 1 "gpc_reg_operand" "r")
7347 (match_operand:DI 2 "reg_or_short_operand" "rI")))]
7348 "TARGET_POWERPC64"
7349 "cmpd%I2 %0,%1,%2"
7350 [(set_attr "type" "compare")])
7351
7352 ;; If we are comparing a register for equality with a large constant,
7353 ;; we can do this with an XOR followed by a compare. But we need a scratch
7354 ;; register for the result of the XOR.
7355
7356 (define_split
7357 [(set (match_operand:CC 0 "cc_reg_operand" "")
7358 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "")
7359 (match_operand:SI 2 "non_short_cint_operand" "")))
7360 (clobber (match_operand:SI 3 "gpc_reg_operand" ""))]
7361 "find_single_use (operands[0], insn, 0)
7362 && (GET_CODE (*find_single_use (operands[0], insn, 0)) == EQ
7363 || GET_CODE (*find_single_use (operands[0], insn, 0)) == NE)"
7364 [(set (match_dup 3) (xor:SI (match_dup 1) (match_dup 4)))
7365 (set (match_dup 0) (compare:CC (match_dup 3) (match_dup 5)))]
7366 "
7367 {
7368 /* Get the constant we are comparing against, C, and see what it looks like
7369 sign-extended to 16 bits. Then see what constant could be XOR'ed
7370 with C to get the sign-extended value. */
7371
7372 int c = INTVAL (operands[2]);
7373 int sextc = (c << 16) >> 16;
7374 int xorv = c ^ sextc;
7375
7376 operands[4] = gen_rtx (CONST_INT, VOIDmode, xorv);
7377 operands[5] = gen_rtx (CONST_INT, VOIDmode, sextc);
7378 }")
7379
7380 (define_insn ""
7381 [(set (match_operand:CCUNS 0 "cc_reg_operand" "=y")
7382 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "r")
7383 (match_operand:SI 2 "reg_or_u_short_operand" "rI")))]
7384 ""
7385 "{cmpl%I2|cmplw%I2} %0,%1,%W2"
7386 [(set_attr "type" "compare")])
7387
7388 (define_insn ""
7389 [(set (match_operand:CCUNS 0 "cc_reg_operand" "=y")
7390 (compare:CCUNS (match_operand:DI 1 "gpc_reg_operand" "r")
7391 (match_operand:DI 2 "reg_or_u_short_operand" "rI")))]
7392 ""
7393 "cmpld%I2 %0,%1,%W2"
7394 [(set_attr "type" "compare")])
7395
7396 ;; The following two insns don't exist as single insns, but if we provide
7397 ;; them, we can swap an add and compare, which will enable us to overlap more
7398 ;; of the required delay between a compare and branch. We generate code for
7399 ;; them by splitting.
7400
7401 (define_insn ""
7402 [(set (match_operand:CC 3 "cc_reg_operand" "=y")
7403 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "r")
7404 (match_operand:SI 2 "short_cint_operand" "i")))
7405 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7406 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "i")))]
7407 ""
7408 "#"
7409 [(set_attr "length" "8")])
7410
7411 (define_insn ""
7412 [(set (match_operand:CCUNS 3 "cc_reg_operand" "=y")
7413 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "r")
7414 (match_operand:SI 2 "u_short_cint_operand" "i")))
7415 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7416 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "i")))]
7417 ""
7418 "#"
7419 [(set_attr "length" "8")])
7420
7421 (define_split
7422 [(set (match_operand:CC 3 "cc_reg_operand" "")
7423 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "")
7424 (match_operand:SI 2 "short_cint_operand" "")))
7425 (set (match_operand:SI 0 "gpc_reg_operand" "")
7426 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "")))]
7427 ""
7428 [(set (match_dup 3) (compare:CC (match_dup 1) (match_dup 2)))
7429 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 4)))])
7430
7431 (define_split
7432 [(set (match_operand:CCUNS 3 "cc_reg_operand" "")
7433 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "")
7434 (match_operand:SI 2 "u_short_cint_operand" "")))
7435 (set (match_operand:SI 0 "gpc_reg_operand" "")
7436 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "")))]
7437 ""
7438 [(set (match_dup 3) (compare:CCUNS (match_dup 1) (match_dup 2)))
7439 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 4)))])
7440
7441 (define_insn ""
7442 [(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
7443 (compare:CCFP (match_operand:SF 1 "gpc_reg_operand" "f")
7444 (match_operand:SF 2 "gpc_reg_operand" "f")))]
7445 "TARGET_HARD_FLOAT"
7446 "fcmpu %0,%1,%2"
7447 [(set_attr "type" "fpcompare")])
7448
7449 (define_insn ""
7450 [(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
7451 (compare:CCFP (match_operand:DF 1 "gpc_reg_operand" "f")
7452 (match_operand:DF 2 "gpc_reg_operand" "f")))]
7453 "TARGET_HARD_FLOAT"
7454 "fcmpu %0,%1,%2"
7455 [(set_attr "type" "fpcompare")])
7456 \f
7457 ;; Now we have the scc insns. We can do some combinations because of the
7458 ;; way the machine works.
7459 ;;
7460 ;; Note that this is probably faster if we can put an insn between the
7461 ;; mfcr and rlinm, but this is tricky. Let's leave it for now. In most
7462 ;; cases the insns below which don't use an intermediate CR field will
7463 ;; be used instead.
7464 (define_insn ""
7465 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7466 (match_operator:SI 1 "scc_comparison_operator"
7467 [(match_operand 2 "cc_reg_operand" "y")
7468 (const_int 0)]))]
7469 ""
7470 "%D1mfcr %0\;{rlinm|rlwinm} %0,%0,%J1,1"
7471 [(set_attr "length" "12")])
7472
7473 (define_insn ""
7474 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7475 (compare:CC (match_operator:SI 1 "scc_comparison_operator"
7476 [(match_operand 2 "cc_reg_operand" "y")
7477 (const_int 0)])
7478 (const_int 0)))
7479 (set (match_operand:SI 3 "gpc_reg_operand" "=r")
7480 (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7481 ""
7482 "%D1mfcr %3\;{rlinm.|rlwinm.} %3,%3,%J1,1"
7483 [(set_attr "type" "delayed_compare")
7484 (set_attr "length" "12")])
7485
7486 (define_insn ""
7487 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7488 (ashift:SI (match_operator:SI 1 "scc_comparison_operator"
7489 [(match_operand 2 "cc_reg_operand" "y")
7490 (const_int 0)])
7491 (match_operand:SI 3 "const_int_operand" "n")))]
7492 ""
7493 "*
7494 {
7495 int is_bit = ccr_bit (operands[1], 1);
7496 int put_bit = 31 - (INTVAL (operands[3]) & 31);
7497 int count;
7498
7499 if (is_bit >= put_bit)
7500 count = is_bit - put_bit;
7501 else
7502 count = 32 - (put_bit - is_bit);
7503
7504 operands[4] = gen_rtx (CONST_INT, VOIDmode, count);
7505 operands[5] = gen_rtx (CONST_INT, VOIDmode, put_bit);
7506
7507 return \"%D1mfcr %0\;{rlinm|rlwinm} %0,%0,%4,%5,%5\";
7508 }"
7509 [(set_attr "length" "12")])
7510
7511 (define_insn ""
7512 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7513 (compare:CC
7514 (ashift:SI (match_operator:SI 1 "scc_comparison_operator"
7515 [(match_operand 2 "cc_reg_operand" "y")
7516 (const_int 0)])
7517 (match_operand:SI 3 "const_int_operand" "n"))
7518 (const_int 0)))
7519 (set (match_operand:SI 4 "gpc_reg_operand" "=r")
7520 (ashift:SI (match_op_dup 1 [(match_dup 2) (const_int 0)])
7521 (match_dup 3)))]
7522 ""
7523 "*
7524 {
7525 int is_bit = ccr_bit (operands[1], 1);
7526 int put_bit = 31 - (INTVAL (operands[3]) & 31);
7527 int count;
7528
7529 if (is_bit >= put_bit)
7530 count = is_bit - put_bit;
7531 else
7532 count = 32 - (put_bit - is_bit);
7533
7534 operands[5] = gen_rtx (CONST_INT, VOIDmode, count);
7535 operands[6] = gen_rtx (CONST_INT, VOIDmode, put_bit);
7536
7537 return \"%D1mfcr %4\;{rlinm.|rlwinm.} %4,%4,%5,%6,%6\";
7538 }"
7539 [(set_attr "type" "delayed_compare")
7540 (set_attr "length" "12")])
7541
7542 ;; If we are comparing the result of two comparisons, this can be done
7543 ;; using creqv or crxor.
7544
7545 (define_insn ""
7546 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=y")
7547 (compare:CCEQ (match_operator 1 "scc_comparison_operator"
7548 [(match_operand 2 "cc_reg_operand" "y")
7549 (const_int 0)])
7550 (match_operator 3 "scc_comparison_operator"
7551 [(match_operand 4 "cc_reg_operand" "y")
7552 (const_int 0)])))]
7553 "REGNO (operands[2]) != REGNO (operands[4])"
7554 "*
7555 {
7556 enum rtx_code code1, code2;
7557
7558 code1 = GET_CODE (operands[1]);
7559 code2 = GET_CODE (operands[3]);
7560
7561 if ((code1 == EQ || code1 == LT || code1 == GT
7562 || code1 == LTU || code1 == GTU
7563 || (code1 != NE && GET_MODE (operands[2]) == CCFPmode))
7564 !=
7565 (code2 == EQ || code2 == LT || code2 == GT
7566 || code2 == LTU || code2 == GTU
7567 || (code2 != NE && GET_MODE (operands[4]) == CCFPmode)))
7568 return \"%C1%C3crxor %E0,%j1,%j3\";
7569 else
7570 return \"%C1%C3creqv %E0,%j1,%j3\";
7571 }"
7572 [(set_attr "length" "12")])
7573
7574 ;; There is a 3 cycle delay between consecutive mfcr instructions
7575 ;; so it is useful to combine 2 scc instructions to use only one mfcr.
7576
7577 (define_peephole
7578 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7579 (match_operator:SI 1 "scc_comparison_operator"
7580 [(match_operand 2 "cc_reg_operand" "y")
7581 (const_int 0)]))
7582 (set (match_operand:SI 3 "gpc_reg_operand" "=r")
7583 (match_operator:SI 4 "scc_comparison_operator"
7584 [(match_operand 5 "cc_reg_operand" "y")
7585 (const_int 0)]))]
7586 "REGNO (operands[2]) != REGNO (operands[5])"
7587 "%D1%D4mfcr %3\;{rlinm|rlwinm} %0,%3,%J1,1\;{rlinm|rlwinm} %3,%3,%J4,1"
7588 [(set_attr "length" "20")])
7589
7590 ;; There are some scc insns that can be done directly, without a compare.
7591 ;; These are faster because they don't involve the communications between
7592 ;; the FXU and branch units. In fact, we will be replacing all of the
7593 ;; integer scc insns here or in the portable methods in emit_store_flag.
7594 ;;
7595 ;; Also support (neg (scc ..)) since that construct is used to replace
7596 ;; branches, (plus (scc ..) ..) since that construct is common and
7597 ;; takes no more insns than scc, and (and (neg (scc ..)) ..) in the
7598 ;; cases where it is no more expensive than (neg (scc ..)).
7599
7600 ;; Have reload force a constant into a register for the simple insns that
7601 ;; otherwise won't accept constants. We do this because it is faster than
7602 ;; the cmp/mfcr sequence we would otherwise generate.
7603
7604 (define_insn ""
7605 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r")
7606 (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7607 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I")))
7608 (clobber (match_scratch:SI 3 "=r,&r,r,r,r"))]
7609 ""
7610 "@
7611 xor %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0
7612 {sfi|subfic} %3,%1,0\;{ae|adde} %0,%3,%1
7613 {xoril|xori} %0,%1,%b2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0
7614 {xoriu|xoris} %0,%1,%u2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0
7615 {sfi|subfic} %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0"
7616 [(set_attr "length" "12,8,12,12,12")])
7617
7618 (define_insn ""
7619 [(set (match_operand:CC 4 "cc_reg_operand" "=x,x,x,x,x")
7620 (compare:CC
7621 (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7622 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I"))
7623 (const_int 0)))
7624 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r")
7625 (eq:SI (match_dup 1) (match_dup 2)))
7626 (clobber (match_scratch:SI 3 "=r,&r,r,r,r"))]
7627 ""
7628 "@
7629 xor %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae.|adde.} %0,%3,%0
7630 {sfi|subfic} %3,%1,0\;{ae.|adde.} %0,%3,%1
7631 {xoril|xori} %0,%1,%b2\;{sfi|subfic} %3,%0,0\;{ae.|adde.} %0,%3,%0
7632 {xoriu|xoris} %0,%1,%u2\;{sfi|subfic} %3,%0,0\;{ae.|adde.} %0,%3,%0
7633 {sfi|subfic} %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae.|adde.} %0,%3,%0"
7634 [(set_attr "type" "compare")
7635 (set_attr "length" "12,8,12,12,12")])
7636
7637 ;; We have insns of the form shown by the first define_insn below. If
7638 ;; there is something inside the comparison operation, we must split it.
7639 (define_split
7640 [(set (match_operand:SI 0 "gpc_reg_operand" "")
7641 (plus:SI (match_operator 1 "comparison_operator"
7642 [(match_operand:SI 2 "" "")
7643 (match_operand:SI 3
7644 "reg_or_cint_operand" "")])
7645 (match_operand:SI 4 "gpc_reg_operand" "")))
7646 (clobber (match_operand:SI 5 "register_operand" ""))]
7647 "! gpc_reg_operand (operands[2], SImode)"
7648 [(set (match_dup 5) (match_dup 2))
7649 (set (match_dup 2) (plus:SI (match_op_dup 1 [(match_dup 2) (match_dup 3)])
7650 (match_dup 4)))])
7651
7652 (define_insn ""
7653 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r")
7654 (plus:SI (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7655 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I"))
7656 (match_operand:SI 3 "gpc_reg_operand" "r,r,r,r,r")))
7657 (clobber (match_scratch:SI 4 "=&r,&r,&r,&r,&r"))]
7658 ""
7659 "@
7660 xor %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3
7661 {sfi|subfic} %4,%1,0\;{aze|addze} %0,%3
7662 {xoril|xori} %4,%1,%b2\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3
7663 {xoriu|xoris} %4,%1,%u2\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3
7664 {sfi|subfic} %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3"
7665 [(set_attr "length" "12,8,12,12,12")])
7666
7667 (define_insn ""
7668 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,x,x")
7669 (compare:CC
7670 (plus:SI
7671 (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7672 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I"))
7673 (match_operand:SI 3 "gpc_reg_operand" "r,r,r,r,r"))
7674 (const_int 0)))
7675 (clobber (match_scratch:SI 4 "=&r,&r,&r,&r,&r"))]
7676 ""
7677 "@
7678 xor %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3
7679 {sfi|subfic} %4,%1,0\;{aze.|addze.} %0,%3
7680 {xoril|xori} %4,%1,%b2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3
7681 {xoriu|xoris} %4,%1,%u2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3
7682 {sfi|subfic} %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3"
7683 [(set_attr "type" "compare")
7684 (set_attr "length" "12,8,12,12,12")])
7685
7686 (define_insn ""
7687 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x,x,x,x")
7688 (compare:CC
7689 (plus:SI
7690 (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7691 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I"))
7692 (match_operand:SI 3 "gpc_reg_operand" "r,r,r,r,r"))
7693 (const_int 0)))
7694 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r")
7695 (plus:SI (eq:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
7696 (clobber (match_scratch:SI 4 "=&r,&r,&r,&r,&r"))]
7697 ""
7698 "@
7699 xor %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3
7700 {sfi|subfic} %4,%1,0\;{aze.|addze.} %4,%3
7701 {xoril|xori} %4,%1,%b2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3
7702 {xoriu|xoris} %4,%1,%u2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3
7703 {sfi|subfic} %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3"
7704 [(set_attr "type" "compare")
7705 (set_attr "length" "12,8,12,12,12")])
7706
7707 (define_insn ""
7708 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r")
7709 (neg:SI (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r")
7710 (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,J,I"))))]
7711 ""
7712 "@
7713 xor %0,%1,%2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0
7714 {ai|addic} %0,%1,-1\;{sfe|subfe} %0,%0,%0
7715 {xoril|xori} %0,%1,%b2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0
7716 {xoriu|xoris} %0,%1,%u2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0
7717 {sfi|subfic} %0,%1,%2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0"
7718 [(set_attr "length" "12,8,12,12,12")])
7719
7720 ;; Simplify (ne X (const_int 0)) on the PowerPC. No need to on the Power,
7721 ;; since it nabs/sr is just as fast.
7722 (define_insn ""
7723 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7724 (lshiftrt:SI (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))
7725 (const_int 31)))
7726 (clobber (match_scratch:SI 2 "=&r"))]
7727 "!TARGET_POWER"
7728 "{ai|addic} %2,%1,-1\;{sfe|subfe} %0,%2,%1"
7729 [(set_attr "length" "8")])
7730
7731 ;; This is what (plus (ne X (const_int 0)) Y) looks like.
7732 (define_insn ""
7733 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7734 (plus:SI (lshiftrt:SI
7735 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))
7736 (const_int 31))
7737 (match_operand:SI 2 "gpc_reg_operand" "r")))
7738 (clobber (match_scratch:SI 3 "=&r"))]
7739 ""
7740 "{ai|addic} %3,%1,-1\;{aze|addze} %0,%2"
7741 [(set_attr "length" "8")])
7742
7743 (define_insn ""
7744 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7745 (compare:CC
7746 (plus:SI (lshiftrt:SI
7747 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))
7748 (const_int 31))
7749 (match_operand:SI 2 "gpc_reg_operand" "r"))
7750 (const_int 0)))
7751 (clobber (match_scratch:SI 3 "=&r"))]
7752 ""
7753 "{ai|addic} %3,%1,-1\;{aze.|addze.} %3,%2"
7754 [(set_attr "type" "compare")
7755 (set_attr "length" "8")])
7756
7757 (define_insn ""
7758 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
7759 (compare:CC
7760 (plus:SI (lshiftrt:SI
7761 (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r")))
7762 (const_int 31))
7763 (match_operand:SI 2 "gpc_reg_operand" "r"))
7764 (const_int 0)))
7765 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7766 (plus:SI (lshiftrt:SI (neg:SI (abs:SI (match_dup 1))) (const_int 31))
7767 (match_dup 2)))
7768 (clobber (match_scratch:SI 3 "=&r"))]
7769 ""
7770 "{ai|addic} %3,%1,-1\;{aze.|addze.} %0,%2"
7771 [(set_attr "type" "compare")
7772 (set_attr "length" "8")])
7773
7774 (define_insn ""
7775 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
7776 (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7777 (match_operand:SI 2 "reg_or_short_operand" "r,O")))
7778 (clobber (match_scratch:SI 3 "=r,X"))]
7779 "TARGET_POWER"
7780 "@
7781 doz %3,%2,%1\;{sfi|subfic} %0,%3,0\;{ae|adde} %0,%0,%3
7782 {ai|addic} %0,%1,-1\;{aze|addze} %0,%0\;{sri|srwi} %0,%0,31"
7783 [(set_attr "length" "12")])
7784
7785 (define_insn ""
7786 [(set (match_operand:CC 4 "cc_reg_operand" "=x,x")
7787 (compare:CC
7788 (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7789 (match_operand:SI 2 "reg_or_short_operand" "r,O"))
7790 (const_int 0)))
7791 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
7792 (le:SI (match_dup 1) (match_dup 2)))
7793 (clobber (match_scratch:SI 3 "=r,X"))]
7794 "TARGET_POWER"
7795 "@
7796 doz %3,%2,%1\;{sfi|subfic} %0,%3,0\;{ae.|adde.} %0,%0,%3
7797 {ai|addic} %0,%1,-1\;{aze|addze} %0,%0\;{sri.|srwi.} %0,%0,31"
7798 [(set_attr "type" "compare,delayed_compare")
7799 (set_attr "length" "12")])
7800
7801 (define_insn ""
7802 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
7803 (plus:SI (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7804 (match_operand:SI 2 "reg_or_short_operand" "r,O"))
7805 (match_operand:SI 3 "gpc_reg_operand" "r,r")))
7806 (clobber (match_scratch:SI 4 "=&r,&r"))]
7807 "TARGET_POWER"
7808 "@
7809 doz %4,%2,%1\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3
7810 {srai|srawi} %4,%1,31\;{sf|subfc} %4,%1,%4\;{aze|addze} %0,%3"
7811 [(set_attr "length" "12")])
7812
7813 (define_insn ""
7814 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
7815 (compare:CC
7816 (plus:SI (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7817 (match_operand:SI 2 "reg_or_short_operand" "r,O"))
7818 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
7819 (const_int 0)))
7820 (clobber (match_scratch:SI 4 "=&r,&r"))]
7821 "TARGET_POWER"
7822 "@
7823 doz %4,%2,%1\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3
7824 {srai|srawi} %4,%1,31\;{sf|subfc} %4,%1,%4\;{aze.|addze.} %4,%3"
7825 [(set_attr "type" "compare")
7826 (set_attr "length" "12")])
7827
7828 (define_insn ""
7829 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x")
7830 (compare:CC
7831 (plus:SI (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7832 (match_operand:SI 2 "reg_or_short_operand" "r,O"))
7833 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
7834 (const_int 0)))
7835 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
7836 (plus:SI (le:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
7837 (clobber (match_scratch:SI 4 "=&r,&r"))]
7838 "TARGET_POWER"
7839 "@
7840 doz %4,%2,%1\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3
7841 {srai|srawi} %4,%1,31\;{sf|subfc} %4,%1,%4\;{aze.|addze.} %0,%3"
7842 [(set_attr "type" "compare")
7843 (set_attr "length" "12")])
7844
7845 (define_insn ""
7846 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
7847 (neg:SI (le:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
7848 (match_operand:SI 2 "reg_or_short_operand" "r,O"))))]
7849 "TARGET_POWER"
7850 "@
7851 doz %0,%2,%1\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0
7852 {ai|addic} %0,%1,-1\;{aze|addze} %0,%0\;{srai|srawi} %0,%0,31"
7853 [(set_attr "length" "12")])
7854
7855 (define_insn ""
7856 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7857 (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7858 (match_operand:SI 2 "reg_or_short_operand" "rI")))]
7859 ""
7860 "{sf%I2|subf%I2c} %0,%1,%2\;{cal %0,0(0)|li %0,0}\;{ae|adde} %0,%0,%0"
7861 [(set_attr "length" "12")])
7862
7863 (define_insn ""
7864 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
7865 (compare:CC
7866 (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7867 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7868 (const_int 0)))
7869 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7870 (leu:SI (match_dup 1) (match_dup 2)))]
7871 ""
7872 "{sf%I2|subf%I2c} %0,%1,%2\;{cal %0,0(0)|li %0,0}\;{ae.|adde.} %0,%0,%0"
7873 [(set_attr "type" "compare")
7874 (set_attr "length" "12")])
7875
7876 (define_insn ""
7877 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7878 (plus:SI (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7879 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7880 (match_operand:SI 3 "gpc_reg_operand" "r")))
7881 (clobber (match_scratch:SI 4 "=&r"))]
7882 ""
7883 "{sf%I2|subf%I2c} %4,%1,%2\;{aze|addze} %0,%3"
7884 [(set_attr "length" "8")])
7885
7886 (define_insn ""
7887 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7888 (compare:CC
7889 (plus:SI (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7890 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7891 (match_operand:SI 3 "gpc_reg_operand" "r"))
7892 (const_int 0)))
7893 (clobber (match_scratch:SI 4 "=&r"))]
7894 ""
7895 "{sf%I2|subf%I2c} %4,%1,%2\;{aze.|addze.} %4,%3"
7896 [(set_attr "type" "compare")
7897 (set_attr "length" "8")])
7898
7899 (define_insn ""
7900 [(set (match_operand:CC 5 "cc_reg_operand" "=x")
7901 (compare:CC
7902 (plus:SI (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7903 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7904 (match_operand:SI 3 "gpc_reg_operand" "r"))
7905 (const_int 0)))
7906 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7907 (plus:SI (leu:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
7908 (clobber (match_scratch:SI 4 "=&r"))]
7909 ""
7910 "{sf%I2|subf%I2c} %4,%1,%2\;{aze.|addze.} %0,%3"
7911 [(set_attr "type" "compare")
7912 (set_attr "length" "8")])
7913
7914 (define_insn ""
7915 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7916 (neg:SI (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7917 (match_operand:SI 2 "reg_or_short_operand" "rI"))))]
7918 ""
7919 "{sf%I2|subf%I2c} %0,%1,%2\;{sfe|subfe} %0,%0,%0\;nand %0,%0,%0"
7920 [(set_attr "length" "12")])
7921
7922 (define_insn ""
7923 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7924 (and:SI (neg:SI
7925 (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7926 (match_operand:SI 2 "reg_or_short_operand" "rI")))
7927 (match_operand:SI 3 "gpc_reg_operand" "r")))
7928 (clobber (match_scratch:SI 4 "=&r"))]
7929 ""
7930 "{sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;andc %0,%3,%4"
7931 [(set_attr "length" "12")])
7932
7933 (define_insn ""
7934 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7935 (compare:CC
7936 (and:SI (neg:SI
7937 (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7938 (match_operand:SI 2 "reg_or_short_operand" "rI")))
7939 (match_operand:SI 3 "gpc_reg_operand" "r"))
7940 (const_int 0)))
7941 (clobber (match_scratch:SI 4 "=&r"))]
7942 ""
7943 "{sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;andc. %4,%3,%4"
7944 [(set_attr "type" "compare")
7945 (set_attr "length" "12")])
7946
7947 (define_insn ""
7948 [(set (match_operand:CC 5 "cc_reg_operand" "=x")
7949 (compare:CC
7950 (and:SI (neg:SI
7951 (leu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7952 (match_operand:SI 2 "reg_or_short_operand" "rI")))
7953 (match_operand:SI 3 "gpc_reg_operand" "r"))
7954 (const_int 0)))
7955 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7956 (and:SI (neg:SI (leu:SI (match_dup 1) (match_dup 2))) (match_dup 3)))
7957 (clobber (match_scratch:SI 4 "=&r"))]
7958 ""
7959 "{sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;andc. %0,%3,%4"
7960 [(set_attr "type" "compare")
7961 (set_attr "length" "12")])
7962
7963 (define_insn ""
7964 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7965 (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7966 (match_operand:SI 2 "reg_or_short_operand" "rI")))]
7967 "TARGET_POWER"
7968 "doz%I2 %0,%1,%2\;nabs %0,%0\;{sri|srwi} %0,%0,31"
7969 [(set_attr "length" "12")])
7970
7971 (define_insn ""
7972 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
7973 (compare:CC
7974 (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7975 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7976 (const_int 0)))
7977 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
7978 (lt:SI (match_dup 1) (match_dup 2)))]
7979 "TARGET_POWER"
7980 "doz%I2 %0,%1,%2\;nabs %0,%0\;{sri.|srwi.} %0,%0,31"
7981 [(set_attr "type" "delayed_compare")
7982 (set_attr "length" "12")])
7983
7984 (define_insn ""
7985 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7986 (plus:SI (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7987 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7988 (match_operand:SI 3 "gpc_reg_operand" "r")))
7989 (clobber (match_scratch:SI 4 "=&r"))]
7990 "TARGET_POWER"
7991 "doz%I2 %4,%1,%2\;{ai|addic} %4,%4,-1\;{aze|addze} %0,%3"
7992 [(set_attr "length" "12")])
7993
7994 (define_insn ""
7995 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
7996 (compare:CC
7997 (plus:SI (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
7998 (match_operand:SI 2 "reg_or_short_operand" "rI"))
7999 (match_operand:SI 3 "gpc_reg_operand" "r"))
8000 (const_int 0)))
8001 (clobber (match_scratch:SI 4 "=&r"))]
8002 "TARGET_POWER"
8003 "doz%I2 %4,%1,%2\;{ai|addic} %4,%4,-1\;{aze.|addze.} %4,%3"
8004 [(set_attr "type" "compare")
8005 (set_attr "length" "12")])
8006
8007 (define_insn ""
8008 [(set (match_operand:CC 5 "cc_reg_operand" "=x")
8009 (compare:CC
8010 (plus:SI (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8011 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8012 (match_operand:SI 3 "gpc_reg_operand" "r"))
8013 (const_int 0)))
8014 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8015 (plus:SI (lt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8016 (clobber (match_scratch:SI 4 "=&r"))]
8017 "TARGET_POWER"
8018 "doz%I2 %4,%1,%2\;{ai|addic} %4,%4,-1\;{aze.|addze.} %0,%3"
8019 [(set_attr "type" "compare")
8020 (set_attr "length" "12")])
8021
8022 (define_insn ""
8023 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8024 (neg:SI (lt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8025 (match_operand:SI 2 "reg_or_short_operand" "rI"))))]
8026 "TARGET_POWER"
8027 "doz%I2 %0,%1,%2\;nabs %0,%0\;{srai|srawi} %0,%0,31"
8028 [(set_attr "length" "12")])
8029
8030 (define_insn ""
8031 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8032 (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8033 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P")))]
8034 ""
8035 "@
8036 {sf|subfc} %0,%2,%1\;{sfe|subfe} %0,%0,%0\;neg %0,%0
8037 {ai|addic} %0,%1,%n2\;{sfe|subfe} %0,%0,%0\;neg %0,%0"
8038 [(set_attr "length" "12")])
8039
8040 (define_insn ""
8041 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
8042 (compare:CC
8043 (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8044 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8045 (const_int 0)))
8046 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8047 (ltu:SI (match_dup 1) (match_dup 2)))]
8048 ""
8049 "@
8050 {sf|subfc} %0,%2,%1\;{sfe|subfe} %0,%0,%0\;neg. %0,%0
8051 {ai|addic} %0,%1,%n2\;{sfe|subfe} %0,%0,%0\;neg. %0,%0"
8052 [(set_attr "type" "compare")
8053 (set_attr "length" "12")])
8054
8055 (define_insn ""
8056 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r")
8057 (plus:SI (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r")
8058 (match_operand:SI 2 "reg_or_neg_short_operand" "r,r,P,P"))
8059 (match_operand:SI 3 "reg_or_short_operand" "r,I,r,I")))
8060 (clobber (match_scratch:SI 4 "=&r,r,&r,r"))]
8061 ""
8062 "@
8063 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3
8064 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3
8065 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3
8066 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3"
8067 [(set_attr "length" "12")])
8068
8069 (define_insn ""
8070 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
8071 (compare:CC
8072 (plus:SI (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8073 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8074 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8075 (const_int 0)))
8076 (clobber (match_scratch:SI 4 "=&r,&r"))]
8077 ""
8078 "@
8079 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %4,%4,%3
8080 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %4,%4,%3"
8081 [(set_attr "type" "compare")
8082 (set_attr "length" "12")])
8083
8084 (define_insn ""
8085 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x")
8086 (compare:CC
8087 (plus:SI (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8088 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8089 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8090 (const_int 0)))
8091 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8092 (plus:SI (ltu:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8093 (clobber (match_scratch:SI 4 "=&r,&r"))]
8094 ""
8095 "@
8096 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %0,%4,%3
8097 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %0,%4,%3"
8098 [(set_attr "type" "compare")
8099 (set_attr "length" "12")])
8100
8101 (define_insn ""
8102 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8103 (neg:SI (ltu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8104 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))))]
8105 ""
8106 "@
8107 {sf|subfc} %0,%2,%1\;{sfe|subfe} %0,%0,%0
8108 {ai|addic} %0,%1,%n2\;{sfe|subfe} %0,%0,%0"
8109 [(set_attr "length" "8")])
8110
8111 (define_insn ""
8112 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8113 (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8114 (match_operand:SI 2 "reg_or_short_operand" "rI")))
8115 (clobber (match_scratch:SI 3 "=r"))]
8116 "TARGET_POWER"
8117 "doz%I2 %3,%1,%2\;{sfi|subfic} %0,%3,0\;{ae|adde} %0,%0,%3"
8118 [(set_attr "length" "12")])
8119
8120 (define_insn ""
8121 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
8122 (compare:CC
8123 (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8124 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8125 (const_int 0)))
8126 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8127 (ge:SI (match_dup 1) (match_dup 2)))
8128 (clobber (match_scratch:SI 3 "=r"))]
8129 "TARGET_POWER"
8130 "doz%I2 %3,%1,%2\;{sfi|subfic} %0,%3,0\;{ae.|adde.} %0,%0,%3"
8131 [(set_attr "type" "compare")
8132 (set_attr "length" "12")])
8133
8134 (define_insn ""
8135 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8136 (plus:SI (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8137 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8138 (match_operand:SI 3 "gpc_reg_operand" "r")))
8139 (clobber (match_scratch:SI 4 "=&r"))]
8140 "TARGET_POWER"
8141 "doz%I2 %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze|addze} %0,%3"
8142 [(set_attr "length" "12")])
8143
8144 (define_insn ""
8145 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
8146 (compare:CC
8147 (plus:SI (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8148 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8149 (match_operand:SI 3 "gpc_reg_operand" "r"))
8150 (const_int 0)))
8151 (clobber (match_scratch:SI 4 "=&r"))]
8152 "TARGET_POWER"
8153 "doz%I2 %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3"
8154 [(set_attr "type" "compare")
8155 (set_attr "length" "12")])
8156
8157 (define_insn ""
8158 [(set (match_operand:CC 5 "cc_reg_operand" "=x")
8159 (compare:CC
8160 (plus:SI (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8161 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8162 (match_operand:SI 3 "gpc_reg_operand" "r"))
8163 (const_int 0)))
8164 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8165 (plus:SI (ge:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8166 (clobber (match_scratch:SI 4 "=&r"))]
8167 "TARGET_POWER"
8168 "doz%I2 %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %0,%3"
8169 [(set_attr "type" "compare")
8170 (set_attr "length" "12")])
8171
8172 (define_insn ""
8173 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8174 (neg:SI (ge:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8175 (match_operand:SI 2 "reg_or_short_operand" "rI"))))]
8176 "TARGET_POWER"
8177 "doz%I2 %0,%1,%2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0"
8178 [(set_attr "length" "12")])
8179
8180 ;; This is (and (neg (ge X (const_int 0))) Y).
8181 (define_insn ""
8182 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8183 (and:SI (neg:SI
8184 (lshiftrt:SI
8185 (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
8186 (const_int 31)))
8187 (match_operand:SI 2 "gpc_reg_operand" "r")))
8188 (clobber (match_scratch:SI 3 "=&r"))]
8189 ""
8190 "{srai|srawi} %3,%1,31\;andc %0,%2,%3"
8191 [(set_attr "length" "8")])
8192
8193 (define_insn ""
8194 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
8195 (compare:CC
8196 (and:SI (neg:SI
8197 (lshiftrt:SI
8198 (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
8199 (const_int 31)))
8200 (match_operand:SI 2 "gpc_reg_operand" "r"))
8201 (const_int 0)))
8202 (clobber (match_scratch:SI 3 "=&r"))]
8203 ""
8204 "{srai|srawi} %3,%1,31\;andc. %3,%2,%3"
8205 [(set_attr "type" "compare")
8206 (set_attr "length" "8")])
8207
8208 (define_insn ""
8209 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
8210 (compare:CC
8211 (and:SI (neg:SI
8212 (lshiftrt:SI
8213 (not:SI (match_operand:SI 1 "gpc_reg_operand" "r"))
8214 (const_int 31)))
8215 (match_operand:SI 2 "gpc_reg_operand" "r"))
8216 (const_int 0)))
8217 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8218 (and:SI (neg:SI (lshiftrt:SI (not:SI (match_dup 1))
8219 (const_int 31)))
8220 (match_dup 2)))
8221 (clobber (match_scratch:SI 3 "=&r"))]
8222 ""
8223 "{srai|srawi} %3,%1,31\;andc. %0,%2,%3"
8224 [(set_attr "type" "compare")
8225 (set_attr "length" "8")])
8226
8227 (define_insn ""
8228 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8229 (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8230 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P")))]
8231 ""
8232 "@
8233 {sf|subfc} %0,%2,%1\;{cal %0,0(0)|li %0,0}\;{ae|adde} %0,%0,%0
8234 {ai|addic} %0,%1,%n2\;{cal %0,0(0)|li %0,0}\;{ae|adde} %0,%0,%0"
8235 [(set_attr "length" "12")])
8236
8237 (define_insn ""
8238 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x")
8239 (compare:CC
8240 (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8241 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8242 (const_int 0)))
8243 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8244 (geu:SI (match_dup 1) (match_dup 2)))]
8245 ""
8246 "@
8247 {sf|subfc} %0,%2,%1\;{cal %0,0(0)|li %0,0}\;{ae.|adde.} %0,%0,%0
8248 {ai|addic} %0,%1,%n2\;{cal %0,0(0)|li %0,0}\;{ae.|adde.} %0,%0,%0"
8249 [(set_attr "type" "compare")
8250 (set_attr "length" "12")])
8251
8252 (define_insn ""
8253 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8254 (plus:SI (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8255 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8256 (match_operand:SI 3 "gpc_reg_operand" "r,r")))
8257 (clobber (match_scratch:SI 4 "=&r,&r"))]
8258 ""
8259 "@
8260 {sf|subfc} %4,%2,%1\;{aze|addze} %0,%3
8261 {ai|addic} %4,%1,%n2\;{aze|addze} %0,%3"
8262 [(set_attr "length" "8")])
8263
8264 (define_insn ""
8265 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
8266 (compare:CC
8267 (plus:SI (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8268 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8269 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8270 (const_int 0)))
8271 (clobber (match_scratch:SI 4 "=&r,&r"))]
8272 ""
8273 "@
8274 {sf|subfc} %4,%2,%1\;{aze.|addze.} %4,%3
8275 {ai|addic} %4,%1,%n2\;{aze.|addze.} %4,%3"
8276 [(set_attr "type" "compare")
8277 (set_attr "length" "8")])
8278
8279 (define_insn ""
8280 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x")
8281 (compare:CC
8282 (plus:SI (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8283 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P"))
8284 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8285 (const_int 0)))
8286 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8287 (plus:SI (geu:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8288 (clobber (match_scratch:SI 4 "=&r,&r"))]
8289 ""
8290 "@
8291 {sf|subfc} %4,%2,%1\;{aze.|addze.} %0,%3
8292 {ai|addic} %4,%1,%n2\;{aze.|addze.} %4,%3"
8293 [(set_attr "type" "compare")
8294 (set_attr "length" "8")])
8295
8296 (define_insn ""
8297 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8298 (neg:SI (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8299 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))]
8300 ""
8301 "@
8302 {sf|subfc} %0,%2,%1\;{sfe|subfe} %0,%0,%0\;nand %0,%0,%0
8303 {sfi|subfic} %0,%1,-1\;{a%I2|add%I2c} %0,%0,%2\;{sfe|subfe} %0,%0,%0"
8304 [(set_attr "length" "12")])
8305
8306 (define_insn ""
8307 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8308 (and:SI (neg:SI
8309 (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8310 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P")))
8311 (match_operand:SI 3 "gpc_reg_operand" "r,r")))
8312 (clobber (match_scratch:SI 4 "=&r,&r"))]
8313 ""
8314 "@
8315 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;andc %0,%3,%4
8316 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;andc %0,%3,%4"
8317 [(set_attr "length" "12")])
8318
8319 (define_insn ""
8320 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
8321 (compare:CC
8322 (and:SI (neg:SI
8323 (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8324 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P")))
8325 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8326 (const_int 0)))
8327 (clobber (match_scratch:SI 4 "=&r,&r"))]
8328 ""
8329 "@
8330 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;andc. %4,%3,%4
8331 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;andc. %4,%3,%4"
8332 [(set_attr "type" "compare")
8333 (set_attr "length" "12")])
8334
8335 (define_insn ""
8336 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x")
8337 (compare:CC
8338 (and:SI (neg:SI
8339 (geu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8340 (match_operand:SI 2 "reg_or_neg_short_operand" "r,P")))
8341 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8342 (const_int 0)))
8343 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8344 (and:SI (neg:SI (geu:SI (match_dup 1) (match_dup 2))) (match_dup 3)))
8345 (clobber (match_scratch:SI 4 "=&r,&r"))]
8346 ""
8347 "@
8348 {sf|subfc} %4,%2,%1\;{sfe|subfe} %4,%4,%4\;andc. %0,%3,%4
8349 {ai|addic} %4,%1,%n2\;{sfe|subfe} %4,%4,%4\;andc. %0,%3,%4"
8350 [(set_attr "type" "compare")
8351 (set_attr "length" "12")])
8352
8353 (define_insn ""
8354 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8355 (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8356 (const_int 0)))]
8357 ""
8358 "{sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{sri|srwi} %0,%0,31"
8359 [(set_attr "length" "12")])
8360
8361 (define_insn ""
8362 [(set (match_operand:CC 2 "cc_reg_operand" "=x")
8363 (compare:CC
8364 (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8365 (const_int 0))
8366 (const_int 0)))
8367 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8368 (gt:SI (match_dup 1) (const_int 0)))]
8369 ""
8370 "{sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{sri.|srwi.} %0,%0,31"
8371 [(set_attr "type" "delayed_compare")
8372 (set_attr "length" "12")])
8373
8374 (define_insn ""
8375 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8376 (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8377 (match_operand:SI 2 "reg_or_short_operand" "r")))]
8378 "TARGET_POWER"
8379 "doz %0,%2,%1\;nabs %0,%0\;{sri|srwi} %0,%0,31"
8380 [(set_attr "length" "12")])
8381
8382 (define_insn ""
8383 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
8384 (compare:CC
8385 (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8386 (match_operand:SI 2 "reg_or_short_operand" "r"))
8387 (const_int 0)))
8388 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8389 (gt:SI (match_dup 1) (match_dup 2)))]
8390 "TARGET_POWER"
8391 "doz %0,%2,%1\;nabs %0,%0\;{sri.|srwi.} %0,%0,31"
8392 [(set_attr "type" "delayed_compare")
8393 (set_attr "length" "12")])
8394
8395 (define_insn ""
8396 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8397 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8398 (const_int 0))
8399 (match_operand:SI 2 "gpc_reg_operand" "r")))
8400 (clobber (match_scratch:SI 3 "=&r"))]
8401 ""
8402 "{a|addc} %3,%1,%1\;{sfe|subfe} %3,%1,%3\;{aze|addze} %0,%2"
8403 [(set_attr "length" "12")])
8404
8405 (define_insn ""
8406 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
8407 (compare:CC
8408 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8409 (const_int 0))
8410 (match_operand:SI 2 "gpc_reg_operand" "r"))
8411 (const_int 0)))
8412 (clobber (match_scratch:SI 3 "=&r"))]
8413 ""
8414 "{a|addc} %3,%1,%1\;{sfe|subfe} %3,%1,%3\;{aze.|addze.} %0,%2"
8415 [(set_attr "type" "compare")
8416 (set_attr "length" "12")])
8417
8418 (define_insn ""
8419 [(set (match_operand:CC 4 "cc_reg_operand" "=x")
8420 (compare:CC
8421 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8422 (const_int 0))
8423 (match_operand:SI 2 "gpc_reg_operand" "r"))
8424 (const_int 0)))
8425 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8426 (plus:SI (gt:SI (match_dup 1) (const_int 0)) (match_dup 2)))
8427 (clobber (match_scratch:SI 3 "=&r"))]
8428 ""
8429 "{a|addc} %3,%1,%1\;{sfe|subfe} %3,%1,%3\;{aze.|addze.} %3,%2"
8430 [(set_attr "type" "compare")
8431 (set_attr "length" "12")])
8432
8433 (define_insn ""
8434 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8435 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8436 (match_operand:SI 2 "reg_or_short_operand" "r"))
8437 (match_operand:SI 3 "gpc_reg_operand" "r")))
8438 (clobber (match_scratch:SI 4 "=&r"))]
8439 "TARGET_POWER"
8440 "doz %4,%2,%1\;{ai|addic} %4,%4,-1\;{aze|addze} %0,%3"
8441 [(set_attr "length" "12")])
8442
8443 (define_insn ""
8444 [(set (match_operand:CC 0 "cc_reg_operand" "=x")
8445 (compare:CC
8446 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8447 (match_operand:SI 2 "reg_or_short_operand" "r"))
8448 (match_operand:SI 3 "gpc_reg_operand" "r"))
8449 (const_int 0)))
8450 (clobber (match_scratch:SI 4 "=&r"))]
8451 "TARGET_POWER"
8452 "doz %4,%2,%1\;{ai|addic} %4,%4,-1\;{aze.|addze.} %4,%3"
8453 [(set_attr "type" "compare")
8454 (set_attr "length" "12")])
8455
8456 (define_insn ""
8457 [(set (match_operand:CC 5 "cc_reg_operand" "=x")
8458 (compare:CC
8459 (plus:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8460 (match_operand:SI 2 "reg_or_short_operand" "r"))
8461 (match_operand:SI 3 "gpc_reg_operand" "r"))
8462 (const_int 0)))
8463 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8464 (plus:SI (gt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8465 (clobber (match_scratch:SI 4 "=&r"))]
8466 "TARGET_POWER"
8467 "doz %4,%2,%1\;{ai|addic} %4,%4,-1\;{aze.|addze.} %0,%3"
8468 [(set_attr "type" "compare")
8469 (set_attr "length" "12")])
8470
8471 (define_insn ""
8472 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8473 (neg:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8474 (const_int 0))))]
8475 ""
8476 "{sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{srai|srawi} %0,%0,31"
8477 [(set_attr "length" "12")])
8478
8479 (define_insn ""
8480 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8481 (neg:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8482 (match_operand:SI 2 "reg_or_short_operand" "r"))))]
8483 "TARGET_POWER"
8484 "doz %0,%2,%1\;nabs %0,%0\;{srai|srawi} %0,%0,31"
8485 [(set_attr "length" "12")])
8486
8487 (define_insn ""
8488 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8489 (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8490 (match_operand:SI 2 "reg_or_short_operand" "rI")))]
8491 ""
8492 "{sf%I2|subf%I2c} %0,%1,%2\;{sfe|subfe} %0,%0,%0\;neg %0,%0"
8493 [(set_attr "length" "12")])
8494
8495 (define_insn ""
8496 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
8497 (compare:CC
8498 (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8499 (match_operand:SI 2 "reg_or_short_operand" "rI"))
8500 (const_int 0)))
8501 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
8502 (gtu:SI (match_dup 1) (match_dup 2)))]
8503 ""
8504 "{sf%I2|subf%I2c} %0,%1,%2\;{sfe|subfe} %0,%0,%0\;neg. %0,%0"
8505 [(set_attr "type" "compare")
8506 (set_attr "length" "12")])
8507
8508 (define_insn ""
8509 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r")
8510 (plus:SI (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r")
8511 (match_operand:SI 2 "reg_or_short_operand" "I,r,rI"))
8512 (match_operand:SI 3 "reg_or_short_operand" "r,r,I")))
8513 (clobber (match_scratch:SI 4 "=&r,&r,&r"))]
8514 ""
8515 "@
8516 {ai|addic} %4,%1,%k2\;{aze|addze} %0,%3
8517 {sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3
8518 {sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;{sf%I3|subf%I3c} %0,%4,%3"
8519 [(set_attr "length" "8,12,12")])
8520
8521 (define_insn ""
8522 [(set (match_operand:CC 0 "cc_reg_operand" "=x,x")
8523 (compare:CC
8524 (plus:SI (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8525 (match_operand:SI 2 "reg_or_short_operand" "I,r"))
8526 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8527 (const_int 0)))
8528 (clobber (match_scratch:SI 4 "=&r,&r"))]
8529 ""
8530 "@
8531 {ai|addic} %4,%1,%k2\;{aze.|addze.} %0,%3
8532 {sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %0,%4,%3"
8533 [(set_attr "type" "compare")
8534 (set_attr "length" "8,12")])
8535
8536 (define_insn ""
8537 [(set (match_operand:CC 5 "cc_reg_operand" "=x,x")
8538 (compare:CC
8539 (plus:SI (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
8540 (match_operand:SI 2 "reg_or_short_operand" "I,r"))
8541 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
8542 (const_int 0)))
8543 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
8544 (plus:SI (gtu:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
8545 (clobber (match_scratch:SI 4 "=&r,&r"))]
8546 ""
8547 "@
8548 {ai|addic} %4,%1,%k2\;{aze.|addze.} %0,%3
8549 {sf%I2|subf%I2c} %4,%1,%2\;{sfe|subfe} %4,%4,%4\;{sf.|subfc.} %0,%4,%3"
8550 [(set_attr "type" "compare")
8551 (set_attr "length" "8,12")])
8552
8553 (define_insn ""
8554 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8555 (neg:SI (gtu:SI (match_operand:SI 1 "gpc_reg_operand" "r")
8556 (match_operand:SI 2 "reg_or_short_operand" "rI"))))]
8557 ""
8558 "{sf%I2|subf%I2c} %0,%1,%2\;{sfe|subfe} %0,%0,%0"
8559 [(set_attr "length" "8")])
8560 \f
8561 ;; Define both directions of branch and return. If we need a reload
8562 ;; register, we'd rather use CR0 since it is much easier to copy a
8563 ;; register CC value to there.
8564
8565 (define_insn ""
8566 [(set (pc)
8567 (if_then_else (match_operator 1 "branch_comparison_operator"
8568 [(match_operand 2
8569 "cc_reg_operand" "x,?y")
8570 (const_int 0)])
8571 (label_ref (match_operand 0 "" ""))
8572 (pc)))]
8573 ""
8574 "*
8575 {
8576 if (get_attr_length (insn) == 8)
8577 return \"%C1bc %t1,%j1,%l0\";
8578 else
8579 return \"%C1bc %T1,%j1,$+8\;b %l0\";
8580 }"
8581 [(set_attr "type" "branch")])
8582
8583 (define_insn ""
8584 [(set (pc)
8585 (if_then_else (match_operator 0 "branch_comparison_operator"
8586 [(match_operand 1
8587 "cc_reg_operand" "x,?y")
8588 (const_int 0)])
8589 (return)
8590 (pc)))]
8591 "direct_return ()"
8592 "{%C0bcr|%C0bclr} %t0,%j0"
8593 [(set_attr "length" "8")])
8594
8595 (define_insn ""
8596 [(set (pc)
8597 (if_then_else (match_operator 1 "branch_comparison_operator"
8598 [(match_operand 2
8599 "cc_reg_operand" "x,?y")
8600 (const_int 0)])
8601 (pc)
8602 (label_ref (match_operand 0 "" ""))))]
8603 ""
8604 "*
8605 {
8606 if (get_attr_length (insn) == 8)
8607 return \"%C1bc %T1,%j1,%l0\";
8608 else
8609 return \"%C1bc %t1,%j1,$+8\;b %l0\";
8610 }"
8611 [(set_attr "type" "branch")])
8612
8613 (define_insn ""
8614 [(set (pc)
8615 (if_then_else (match_operator 0 "branch_comparison_operator"
8616 [(match_operand 1
8617 "cc_reg_operand" "x,?y")
8618 (const_int 0)])
8619 (pc)
8620 (return)))]
8621 "direct_return ()"
8622 "{%C0bcr|%C0bclr} %T0,%j0"
8623 [(set_attr "length" "8")])
8624
8625 ;; Unconditional branch and return.
8626
8627 (define_insn "jump"
8628 [(set (pc)
8629 (label_ref (match_operand 0 "" "")))]
8630 ""
8631 "b %l0")
8632
8633 (define_insn "return"
8634 [(return)]
8635 "direct_return ()"
8636 "{br|blr}"
8637 [(set_attr "type" "jmpreg")])
8638
8639 (define_insn "indirect_jump"
8640 [(set (pc) (match_operand:SI 0 "register_operand" "c,l"))]
8641 ""
8642 "@
8643 bctr
8644 {br|blr}"
8645 [(set_attr "type" "jmpreg")])
8646
8647 (define_insn ""
8648 [(set (pc) (match_operand:DI 0 "register_operand" "c,l"))]
8649 "TARGET_POWERPC64"
8650 "@
8651 bctr
8652 {br|blr}"
8653 [(set_attr "type" "jmpreg")])
8654
8655 ;; Table jump for switch statements:
8656 (define_expand "tablejump"
8657 [(use (match_operand 0 "" ""))
8658 (use (label_ref (match_operand 1 "" "")))]
8659 ""
8660 "
8661 {
8662 if (TARGET_32BIT)
8663 emit_jump_insn (gen_tablejumpsi (operands[0], operands[1]));
8664 else
8665 emit_jump_insn (gen_tablejumpdi (operands[0], operands[1]));
8666 DONE;
8667 }")
8668
8669 (define_expand "tablejumpsi"
8670 [(set (match_dup 3)
8671 (plus:SI (match_operand:SI 0 "" "")
8672 (match_dup 2)))
8673 (parallel [(set (pc) (match_dup 3))
8674 (use (label_ref (match_operand 1 "" "")))])]
8675 ""
8676 "
8677 { operands[0] = force_reg (SImode, operands[0]);
8678 operands[2] = force_reg (SImode, gen_rtx (LABEL_REF, VOIDmode, operands[1]));
8679 operands[3] = gen_reg_rtx (SImode);
8680 }")
8681
8682 (define_expand "tablejumpdi"
8683 [(set (match_dup 3)
8684 (plus:DI (match_operand:DI 0 "" "")
8685 (match_dup 2)))
8686 (parallel [(set (pc) (match_dup 3))
8687 (use (label_ref (match_operand 1 "" "")))])]
8688 ""
8689 "
8690 { operands[0] = force_reg (DImode, operands[0]);
8691 operands[2] = force_reg (DImode, gen_rtx (LABEL_REF, VOIDmode, operands[1]));
8692 operands[3] = gen_reg_rtx (DImode);
8693 }")
8694
8695 (define_insn ""
8696 [(set (pc)
8697 (match_operand:SI 0 "register_operand" "c,l"))
8698 (use (label_ref (match_operand 1 "" "")))]
8699 ""
8700 "@
8701 bctr
8702 {br|blr}"
8703 [(set_attr "type" "jmpreg")])
8704
8705 (define_insn ""
8706 [(set (pc)
8707 (match_operand:DI 0 "register_operand" "c,l"))
8708 (use (label_ref (match_operand 1 "" "")))]
8709 "TARGET_POWERPC64"
8710 "@
8711 bctr
8712 {br|blr}"
8713 [(set_attr "type" "jmpreg")])
8714
8715 (define_insn "nop"
8716 [(const_int 0)]
8717 ""
8718 "{cror 0,0,0|nop}")
8719 \f
8720 ;; Define the subtract-one-and-jump insns, starting with the template
8721 ;; so loop.c knows what to generate.
8722
8723 (define_expand "decrement_and_branch_on_count"
8724 [(parallel [(set (pc) (if_then_else (ne (match_operand:SI 0 "register_operand" "")
8725 (const_int 1))
8726 (label_ref (match_operand 1 "" ""))
8727 (pc)))
8728 (set (match_dup 0)
8729 (plus:SI (match_dup 0)
8730 (const_int -1)))
8731 (clobber (match_scratch:CC 2 ""))
8732 (clobber (match_scratch:SI 3 ""))])]
8733 ""
8734 "")
8735
8736 ;; We need to be able to do this for any operand, including MEM, or we
8737 ;; will cause reload to blow up since we don't allow output reloads on
8738 ;; JUMP_INSNs.
8739 ;; In order that the length attribute is calculated correctly, the
8740 ;; label MUST be operand 0.
8741
8742 (define_insn ""
8743 [(set (pc)
8744 (if_then_else (ne (match_operand:SI 1 "register_operand" "c,*r,*r")
8745 (const_int 1))
8746 (label_ref (match_operand 0 "" ""))
8747 (pc)))
8748 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8749 (plus:SI (match_dup 1)
8750 (const_int -1)))
8751 (clobber (match_scratch:CC 3 "=X,&x,&x"))
8752 (clobber (match_scratch:SI 4 "=X,X,r"))]
8753 ""
8754 "*
8755 {
8756 if (which_alternative != 0)
8757 return \"#\";
8758 else if (get_attr_length (insn) == 8)
8759 return \"{bdn|bdnz} %l0\";
8760 else
8761 return \"bdz $+8\;b %l0\";
8762 }"
8763 [(set_attr "type" "branch")
8764 (set_attr "length" "*,12,16")])
8765
8766 (define_insn ""
8767 [(set (pc)
8768 (if_then_else (ne (match_operand:SI 1 "register_operand" "c,*r,*r")
8769 (const_int 1))
8770 (pc)
8771 (label_ref (match_operand 0 "" ""))))
8772 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8773 (plus:SI (match_dup 1)
8774 (const_int -1)))
8775 (clobber (match_scratch:CC 3 "=X,&x,&x"))
8776 (clobber (match_scratch:SI 4 "=X,X,r"))]
8777 ""
8778 "*
8779 {
8780 if (which_alternative != 0)
8781 return \"#\";
8782 else if (get_attr_length (insn) == 8)
8783 return \"bdz %l0\";
8784 else
8785 return \"{bdn|bdnz} $+8\;b %l0\";
8786 }"
8787 [(set_attr "type" "branch")
8788 (set_attr "length" "*,12,16")])
8789
8790 ;; Similar, but we can use GE since we have a REG_NONNEG.
8791 (define_insn ""
8792 [(set (pc)
8793 (if_then_else (ge (match_operand:SI 1 "register_operand" "c,*r,*r")
8794 (const_int 0))
8795 (label_ref (match_operand 0 "" ""))
8796 (pc)))
8797 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8798 (plus:SI (match_dup 1)
8799 (const_int -1)))
8800 (clobber (match_scratch:CC 3 "=X,&x,&X"))
8801 (clobber (match_scratch:SI 4 "=X,X,r"))]
8802 "find_reg_note (insn, REG_NONNEG, 0)"
8803 "*
8804 {
8805 if (which_alternative != 0)
8806 return \"#\";
8807 else if (get_attr_length (insn) == 8)
8808 return \"{bdn|bdnz} %l0\";
8809 else
8810 return \"bdz $+8\;b %l0\";
8811 }"
8812 [(set_attr "type" "branch")
8813 (set_attr "length" "*,12,16")])
8814
8815 (define_insn ""
8816 [(set (pc)
8817 (if_then_else (ge (match_operand:SI 1 "register_operand" "c,*r,*r")
8818 (const_int 0))
8819 (pc)
8820 (label_ref (match_operand 0 "" ""))))
8821 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8822 (plus:SI (match_dup 1)
8823 (const_int -1)))
8824 (clobber (match_scratch:CC 3 "=X,&x,&X"))
8825 (clobber (match_scratch:SI 4 "=X,X,r"))]
8826 "find_reg_note (insn, REG_NONNEG, 0)"
8827 "*
8828 {
8829 if (which_alternative != 0)
8830 return \"#\";
8831 else if (get_attr_length (insn) == 8)
8832 return \"bdz %l0\";
8833 else
8834 return \"{bdn|bdnz} $+8\;b %l0\";
8835 }"
8836 [(set_attr "type" "branch")
8837 (set_attr "length" "*,12,16")])
8838
8839 (define_insn ""
8840 [(set (pc)
8841 (if_then_else (eq (match_operand:SI 1 "register_operand" "c,*r,*r")
8842 (const_int 1))
8843 (label_ref (match_operand 0 "" ""))
8844 (pc)))
8845 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8846 (plus:SI (match_dup 1)
8847 (const_int -1)))
8848 (clobber (match_scratch:CC 3 "=X,&x,&x"))
8849 (clobber (match_scratch:SI 4 "=X,X,r"))]
8850 ""
8851 "*
8852 {
8853 if (which_alternative != 0)
8854 return \"#\";
8855 else if (get_attr_length (insn) == 8)
8856 return \"bdz %l0\";
8857 else
8858 return \"{bdn|bdnz} $+8\;b %l0\";
8859 }"
8860 [(set_attr "type" "branch")
8861 (set_attr "length" "*,12,16")])
8862
8863 (define_insn ""
8864 [(set (pc)
8865 (if_then_else (eq (match_operand:SI 1 "register_operand" "c,*r,*r")
8866 (const_int 1))
8867 (pc)
8868 (label_ref (match_operand 0 "" ""))))
8869 (set (match_operand:SI 2 "register_operand" "=1,*r,m*q*c*l")
8870 (plus:SI (match_dup 1)
8871 (const_int -1)))
8872 (clobber (match_scratch:CC 3 "=X,&x,&x"))
8873 (clobber (match_scratch:SI 4 "=X,X,r"))]
8874 ""
8875 "*
8876 {
8877 if (which_alternative != 0)
8878 return \"#\";
8879 else if (get_attr_length (insn) == 8)
8880 return \"{bdn|bdnz} %l0\";
8881 else
8882 return \"bdz $+8\;b %l0\";
8883 }"
8884 [(set_attr "type" "branch")
8885 (set_attr "length" "*,12,16")])
8886
8887 (define_split
8888 [(set (pc)
8889 (if_then_else (match_operator 2 "comparison_operator"
8890 [(match_operand:SI 1 "gpc_reg_operand" "")
8891 (const_int 1)])
8892 (match_operand 5 "" "")
8893 (match_operand 6 "" "")))
8894 (set (match_operand:SI 0 "gpc_reg_operand" "")
8895 (plus:SI (match_dup 1)
8896 (const_int -1)))
8897 (clobber (match_scratch:CC 3 ""))
8898 (clobber (match_scratch:SI 4 ""))]
8899 "reload_completed"
8900 [(parallel [(set (match_dup 3)
8901 (compare:CC (plus:SI (match_dup 1)
8902 (const_int -1))
8903 (const_int 0)))
8904 (set (match_dup 0)
8905 (plus:SI (match_dup 1)
8906 (const_int -1)))])
8907 (set (pc) (if_then_else (match_dup 7)
8908 (match_dup 5)
8909 (match_dup 6)))]
8910 "
8911 { operands[7] = gen_rtx (GET_CODE (operands[2]), VOIDmode, operands[3],
8912 const0_rtx); }")
8913
8914 (define_split
8915 [(set (pc)
8916 (if_then_else (match_operator 2 "comparison_operator"
8917 [(match_operand:SI 1 "gpc_reg_operand" "")
8918 (const_int 1)])
8919 (match_operand 5 "" "")
8920 (match_operand 6 "" "")))
8921 (set (match_operand:SI 0 "general_operand" "")
8922 (plus:SI (match_dup 1) (const_int -1)))
8923 (clobber (match_scratch:CC 3 ""))
8924 (clobber (match_scratch:SI 4 ""))]
8925 "reload_completed && ! gpc_reg_operand (operands[0], SImode)"
8926 [(parallel [(set (match_dup 3)
8927 (compare:CC (plus:SI (match_dup 1)
8928 (const_int -1))
8929 (const_int 0)))
8930 (set (match_dup 4)
8931 (plus:SI (match_dup 1)
8932 (const_int -1)))])
8933 (set (match_dup 0)
8934 (match_dup 4))
8935 (set (pc) (if_then_else (match_dup 7)
8936 (match_dup 5)
8937 (match_dup 6)))]
8938 "
8939 { operands[7] = gen_rtx (GET_CODE (operands[2]), VOIDmode, operands[3],
8940 const0_rtx); }")
This page took 0.396368 seconds and 6 git commands to generate.