S/390: Add support for z13 instructions lochi and locghi.
[gcc.git] / gcc / config / s390 / s390.md
1 ;;- Machine description for GNU compiler -- S/390 / zSeries version.
2 ;; Copyright (C) 1999-2016 Free Software Foundation, Inc.
3 ;; Contributed by Hartmut Penner (hpenner@de.ibm.com) and
4 ;; Ulrich Weigand (uweigand@de.ibm.com) and
5 ;; Andreas Krebbel (Andreas.Krebbel@de.ibm.com)
6
7 ;; This file is part of GCC.
8
9 ;; GCC is free software; you can redistribute it and/or modify it under
10 ;; the terms of the GNU General Public License as published by the Free
11 ;; Software Foundation; either version 3, or (at your option) any later
12 ;; version.
13
14 ;; GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 ;; WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 ;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 ;; for more details.
18
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GCC; see the file COPYING3. If not see
21 ;; <http://www.gnu.org/licenses/>.
22
23 ;;
24 ;; See constraints.md for a description of constraints specific to s390.
25 ;;
26
27 ;; Special formats used for outputting 390 instructions.
28 ;;
29 ;; %C: print opcode suffix for branch condition.
30 ;; %D: print opcode suffix for inverse branch condition.
31 ;; %J: print tls_load/tls_gdcall/tls_ldcall suffix
32 ;; %G: print the size of the operand in bytes.
33 ;; %O: print only the displacement of a memory reference.
34 ;; %R: print only the base register of a memory reference.
35 ;; %S: print S-type memory reference (base+displacement).
36 ;; %N: print the second word of a DImode operand.
37 ;; %M: print the second word of a TImode operand.
38 ;; %Y: print shift count operand.
39 ;;
40 ;; %b: print integer X as if it's an unsigned byte.
41 ;; %c: print integer X as if it's an signed byte.
42 ;; %x: print integer X as if it's an unsigned halfword.
43 ;; %h: print integer X as if it's a signed halfword.
44 ;; %i: print the first nonzero HImode part of X.
45 ;; %j: print the first HImode part unequal to -1 of X.
46 ;; %k: print the first nonzero SImode part of X.
47 ;; %m: print the first SImode part unequal to -1 of X.
48 ;; %o: print integer X as if it's an unsigned 32bit word.
49 ;;
50 ;; We have a special constraint for pattern matching.
51 ;;
52 ;; s_operand -- Matches a valid S operand in a RS, SI or SS type instruction.
53 ;;
54
55 ;;
56 ;; UNSPEC usage
57 ;;
58
59 (define_c_enum "unspec" [
60 ; Miscellaneous
61 UNSPEC_ROUND
62 UNSPEC_ICM
63 UNSPEC_TIE
64
65 ; Convert CC into a str comparison result and copy it into an
66 ; integer register
67 ; cc0->0, cc1->1, cc2->-1, (cc3->-1)
68 UNSPEC_STRCMPCC_TO_INT
69
70 ; Copy CC as is into the lower 2 bits of an integer register
71 UNSPEC_CC_TO_INT
72
73 ; The right hand side of an setmem
74 UNSPEC_REPLICATE_BYTE
75
76 ; GOT/PLT and lt-relative accesses
77 UNSPEC_LTREL_OFFSET
78 UNSPEC_LTREL_BASE
79 UNSPEC_POOL_OFFSET
80 UNSPEC_GOTENT
81 UNSPEC_GOT
82 UNSPEC_GOTOFF
83 UNSPEC_PLT
84 UNSPEC_PLTOFF
85
86 ; Literal pool
87 UNSPEC_RELOAD_BASE
88 UNSPEC_MAIN_BASE
89 UNSPEC_LTREF
90 UNSPEC_INSN
91 UNSPEC_EXECUTE
92
93 ; Atomic Support
94 UNSPEC_MB
95 UNSPEC_MOVA
96
97 ; TLS relocation specifiers
98 UNSPEC_TLSGD
99 UNSPEC_TLSLDM
100 UNSPEC_NTPOFF
101 UNSPEC_DTPOFF
102 UNSPEC_GOTNTPOFF
103 UNSPEC_INDNTPOFF
104
105 ; TLS support
106 UNSPEC_TLSLDM_NTPOFF
107 UNSPEC_TLS_LOAD
108
109 ; String Functions
110 UNSPEC_SRST
111 UNSPEC_MVST
112
113 ; Stack Smashing Protector
114 UNSPEC_SP_SET
115 UNSPEC_SP_TEST
116
117 ; Split stack support
118 UNSPEC_STACK_CHECK
119
120 ; Test Data Class (TDC)
121 UNSPEC_TDC_INSN
122
123 ; Population Count
124 UNSPEC_POPCNT
125 UNSPEC_COPYSIGN
126
127 ; Load FP Integer
128 UNSPEC_FPINT_FLOOR
129 UNSPEC_FPINT_BTRUNC
130 UNSPEC_FPINT_ROUND
131 UNSPEC_FPINT_CEIL
132 UNSPEC_FPINT_NEARBYINT
133 UNSPEC_FPINT_RINT
134
135 UNSPEC_LCBB
136
137 ; Vector
138 UNSPEC_VEC_SMULT_HI
139 UNSPEC_VEC_UMULT_HI
140 UNSPEC_VEC_SMULT_LO
141 UNSPEC_VEC_SMULT_EVEN
142 UNSPEC_VEC_UMULT_EVEN
143 UNSPEC_VEC_SMULT_ODD
144 UNSPEC_VEC_UMULT_ODD
145
146 UNSPEC_VEC_VMAL
147 UNSPEC_VEC_VMAH
148 UNSPEC_VEC_VMALH
149 UNSPEC_VEC_VMAE
150 UNSPEC_VEC_VMALE
151 UNSPEC_VEC_VMAO
152 UNSPEC_VEC_VMALO
153
154 UNSPEC_VEC_GATHER
155 UNSPEC_VEC_EXTRACT
156 UNSPEC_VEC_INSERT_AND_ZERO
157 UNSPEC_VEC_LOAD_BNDRY
158 UNSPEC_VEC_LOAD_LEN
159 UNSPEC_VEC_MERGEH
160 UNSPEC_VEC_MERGEL
161 UNSPEC_VEC_PACK
162 UNSPEC_VEC_PACK_SATURATE
163 UNSPEC_VEC_PACK_SATURATE_CC
164 UNSPEC_VEC_PACK_SATURATE_GENCC
165 UNSPEC_VEC_PACK_UNSIGNED_SATURATE
166 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC
167 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC
168 UNSPEC_VEC_PERM
169 UNSPEC_VEC_PERMI
170 UNSPEC_VEC_EXTEND
171 UNSPEC_VEC_STORE_LEN
172 UNSPEC_VEC_UNPACKH
173 UNSPEC_VEC_UNPACKH_L
174 UNSPEC_VEC_UNPACKL
175 UNSPEC_VEC_UNPACKL_L
176 UNSPEC_VEC_ADDC
177 UNSPEC_VEC_ADDC_U128
178 UNSPEC_VEC_ADDE_U128
179 UNSPEC_VEC_ADDEC_U128
180 UNSPEC_VEC_AVG
181 UNSPEC_VEC_AVGU
182 UNSPEC_VEC_CHECKSUM
183 UNSPEC_VEC_GFMSUM
184 UNSPEC_VEC_GFMSUM_128
185 UNSPEC_VEC_GFMSUM_ACCUM
186 UNSPEC_VEC_GFMSUM_ACCUM_128
187 UNSPEC_VEC_SET
188
189 UNSPEC_VEC_VSUMG
190 UNSPEC_VEC_VSUMQ
191 UNSPEC_VEC_VSUM
192 UNSPEC_VEC_RL_MASK
193 UNSPEC_VEC_SLL
194 UNSPEC_VEC_SLB
195 UNSPEC_VEC_SLDB
196 UNSPEC_VEC_SRAL
197 UNSPEC_VEC_SRAB
198 UNSPEC_VEC_SRL
199 UNSPEC_VEC_SRLB
200
201 UNSPEC_VEC_SUB_U128
202 UNSPEC_VEC_SUBC
203 UNSPEC_VEC_SUBC_U128
204 UNSPEC_VEC_SUBE_U128
205 UNSPEC_VEC_SUBEC_U128
206
207 UNSPEC_VEC_TEST_MASK
208
209 UNSPEC_VEC_VFAE
210 UNSPEC_VEC_VFAECC
211
212 UNSPEC_VEC_VFEE
213 UNSPEC_VEC_VFEECC
214 UNSPEC_VEC_VFENE
215 UNSPEC_VEC_VFENECC
216
217 UNSPEC_VEC_VISTR
218 UNSPEC_VEC_VISTRCC
219
220 UNSPEC_VEC_VSTRC
221 UNSPEC_VEC_VSTRCCC
222
223 UNSPEC_VEC_VCDGB
224 UNSPEC_VEC_VCDLGB
225
226 UNSPEC_VEC_VCGDB
227 UNSPEC_VEC_VCLGDB
228
229 UNSPEC_VEC_VFIDB
230
231 UNSPEC_VEC_VLDEB
232 UNSPEC_VEC_VLEDB
233
234 UNSPEC_VEC_VFTCIDB
235 UNSPEC_VEC_VFTCIDBCC
236 ])
237
238 ;;
239 ;; UNSPEC_VOLATILE usage
240 ;;
241
242 (define_c_enum "unspecv" [
243 ; Blockage
244 UNSPECV_BLOCKAGE
245
246 ; TPF Support
247 UNSPECV_TPF_PROLOGUE
248 UNSPECV_TPF_EPILOGUE
249
250 ; Literal pool
251 UNSPECV_POOL
252 UNSPECV_POOL_SECTION
253 UNSPECV_POOL_ALIGN
254 UNSPECV_POOL_ENTRY
255 UNSPECV_MAIN_POOL
256
257 ; TLS support
258 UNSPECV_SET_TP
259
260 ; Atomic Support
261 UNSPECV_CAS
262 UNSPECV_ATOMIC_OP
263
264 ; Hotpatching (unremovable NOPs)
265 UNSPECV_NOP_2_BYTE
266 UNSPECV_NOP_4_BYTE
267 UNSPECV_NOP_6_BYTE
268
269 ; Transactional Execution support
270 UNSPECV_TBEGIN
271 UNSPECV_TBEGIN_TDB
272 UNSPECV_TBEGINC
273 UNSPECV_TEND
274 UNSPECV_TABORT
275 UNSPECV_ETND
276 UNSPECV_NTSTG
277 UNSPECV_PPA
278
279 ; Set and get floating point control register
280 UNSPECV_SFPC
281 UNSPECV_EFPC
282
283 ; Split stack support
284 UNSPECV_SPLIT_STACK_CALL
285 UNSPECV_SPLIT_STACK_DATA
286 ])
287
288 ;;
289 ;; Registers
290 ;;
291
292 ; Registers with special meaning
293
294 (define_constants
295 [
296 ; Sibling call register.
297 (SIBCALL_REGNUM 1)
298 ; Literal pool base register.
299 (BASE_REGNUM 13)
300 ; Return address register.
301 (RETURN_REGNUM 14)
302 ; Stack pointer register.
303 (STACK_REGNUM 15)
304 ; Condition code register.
305 (CC_REGNUM 33)
306 ; Thread local storage pointer register.
307 (TP_REGNUM 36)
308 ])
309
310 ; Hardware register names
311
312 (define_constants
313 [
314 ; General purpose registers
315 (GPR0_REGNUM 0)
316 (GPR1_REGNUM 1)
317 (GPR2_REGNUM 2)
318 (GPR6_REGNUM 6)
319 ; Floating point registers.
320 (FPR0_REGNUM 16)
321 (FPR1_REGNUM 20)
322 (FPR2_REGNUM 17)
323 (FPR3_REGNUM 21)
324 (FPR4_REGNUM 18)
325 (FPR5_REGNUM 22)
326 (FPR6_REGNUM 19)
327 (FPR7_REGNUM 23)
328 (FPR8_REGNUM 24)
329 (FPR9_REGNUM 28)
330 (FPR10_REGNUM 25)
331 (FPR11_REGNUM 29)
332 (FPR12_REGNUM 26)
333 (FPR13_REGNUM 30)
334 (FPR14_REGNUM 27)
335 (FPR15_REGNUM 31)
336 (VR0_REGNUM 16)
337 (VR16_REGNUM 38)
338 (VR23_REGNUM 45)
339 (VR24_REGNUM 46)
340 (VR31_REGNUM 53)
341 ])
342
343 ; Rounding modes for binary floating point numbers
344 (define_constants
345 [(BFP_RND_CURRENT 0)
346 (BFP_RND_NEAREST_TIE_AWAY_FROM_0 1)
347 (BFP_RND_PREP_FOR_SHORT_PREC 3)
348 (BFP_RND_NEAREST_TIE_TO_EVEN 4)
349 (BFP_RND_TOWARD_0 5)
350 (BFP_RND_TOWARD_INF 6)
351 (BFP_RND_TOWARD_MINF 7)])
352
353 ; Rounding modes for decimal floating point numbers
354 ; 1-7 were introduced with the floating point extension facility
355 ; available with z196
356 ; With these rounding modes (1-7) a quantum exception might occur
357 ; which is suppressed for the other modes.
358 (define_constants
359 [(DFP_RND_CURRENT 0)
360 (DFP_RND_NEAREST_TIE_AWAY_FROM_0_QUANTEXC 1)
361 (DFP_RND_CURRENT_QUANTEXC 2)
362 (DFP_RND_PREP_FOR_SHORT_PREC_QUANTEXC 3)
363 (DFP_RND_NEAREST_TIE_TO_EVEN_QUANTEXC 4)
364 (DFP_RND_TOWARD_0_QUANTEXC 5)
365 (DFP_RND_TOWARD_INF_QUANTEXC 6)
366 (DFP_RND_TOWARD_MINF_QUANTEXC 7)
367 (DFP_RND_NEAREST_TIE_TO_EVEN 8)
368 (DFP_RND_TOWARD_0 9)
369 (DFP_RND_TOWARD_INF 10)
370 (DFP_RND_TOWARD_MINF 11)
371 (DFP_RND_NEAREST_TIE_AWAY_FROM_0 12)
372 (DFP_RND_NEAREST_TIE_TO_0 13)
373 (DFP_RND_AWAY_FROM_0 14)
374 (DFP_RND_PREP_FOR_SHORT_PREC 15)])
375
376 ;;
377 ;; PFPO GPR0 argument format
378 ;;
379
380 (define_constants
381 [
382 ; PFPO operation type
383 (PFPO_CONVERT 0x1000000)
384 ; PFPO operand types
385 (PFPO_OP_TYPE_SF 0x5)
386 (PFPO_OP_TYPE_DF 0x6)
387 (PFPO_OP_TYPE_TF 0x7)
388 (PFPO_OP_TYPE_SD 0x8)
389 (PFPO_OP_TYPE_DD 0x9)
390 (PFPO_OP_TYPE_TD 0xa)
391 ; Bitposition of operand types
392 (PFPO_OP0_TYPE_SHIFT 16)
393 (PFPO_OP1_TYPE_SHIFT 8)
394 ])
395
396 ; Immediate operands for tbegin and tbeginc
397 (define_constants [(TBEGIN_MASK 65292)]) ; 0xff0c
398 (define_constants [(TBEGINC_MASK 65288)]) ; 0xff08
399
400 ;; Instruction operand type as used in the Principles of Operation.
401 ;; Used to determine defaults for length and other attribute values.
402
403 (define_attr "op_type"
404 "NN,E,RR,RRE,RX,RS,RSI,RI,SI,S,SS,SSE,RXE,RSE,RIL,RIE,RXY,RSY,SIY,RRF,SIL,RRS,RIS,VRI,VRR,VRS,VRV,VRX"
405 (const_string "NN"))
406
407 ;; Instruction type attribute used for scheduling.
408
409 (define_attr "type" "none,integer,load,lr,la,larl,lm,stm,
410 cs,vs,store,sem,idiv,
411 imulhi,imulsi,imuldi,
412 branch,jsr,fsimptf,fsimpdf,fsimpsf,fhex,
413 floadtf,floaddf,floadsf,fstoredf,fstoresf,
414 fmultf,fmuldf,fmulsf,fdivtf,fdivdf,fdivsf,
415 ftoi,fsqrttf,fsqrtdf,fsqrtsf,
416 fmadddf,fmaddsf,
417 ftrunctf,ftruncdf, ftruncsd, ftruncdd,
418 itoftf, itofdf, itofsf, itofdd, itoftd,
419 fdivdd, fdivtd, floaddd, floadsd, fmuldd, fmultd,
420 fsimpdd, fsimpsd, fsimptd, fstoredd, fstoresd,
421 ftoidfp, other"
422 (cond [(eq_attr "op_type" "NN") (const_string "other")
423 (eq_attr "op_type" "SS") (const_string "cs")]
424 (const_string "integer")))
425
426 ;; Another attribute used for scheduling purposes:
427 ;; agen: Instruction uses the address generation unit
428 ;; reg: Instruction does not use the agen unit
429
430 (define_attr "atype" "agen,reg"
431 (if_then_else (eq_attr "op_type" "E,RR,RI,RRE,RSI,RIL,RIE,RRF")
432 (const_string "reg")
433 (const_string "agen")))
434
435 ;; Properties concerning Z10 execution grouping and value forwarding.
436 ;; z10_super: instruction is superscalar.
437 ;; z10_super_c: instruction is superscalar and meets the condition of z10_c.
438 ;; z10_fwd: The instruction reads the value of an operand and stores it into a
439 ;; target register. It can forward this value to a second instruction that reads
440 ;; the same register if that second instruction is issued in the same group.
441 ;; z10_rec: The instruction is in the T pipeline and reads a register. If the
442 ;; instruction in the S pipe writes to the register, then the T instruction
443 ;; can immediately read the new value.
444 ;; z10_fr: union of Z10_fwd and z10_rec.
445 ;; z10_c: second operand of instruction is a register and read with complemented bits.
446 ;;
447 ;; An additional suffix A1, A3, or E1 indicates the respective AGI bypass.
448
449
450 (define_attr "z10prop" "none,
451 z10_super, z10_super_E1, z10_super_A1, z10_super_c, z10_super_c_E1,
452 z10_fwd, z10_fwd_A1, z10_fwd_A3, z10_fwd_E1,
453 z10_rec,
454 z10_fr, z10_fr_A3, z10_fr_E1,
455 z10_c"
456 (const_string "none"))
457
458 ;; Properties concerning Z196 decoding
459 ;; z196_alone: must group alone
460 ;; z196_end: ends a group
461 ;; z196_cracked: instruction is cracked or expanded
462 (define_attr "z196prop" "none,
463 z196_alone, z196_ends,
464 z196_cracked"
465 (const_string "none"))
466
467 (define_attr "mnemonic" "bcr_flush,unknown" (const_string "unknown"))
468
469 ;; Length in bytes.
470
471 (define_attr "length" ""
472 (cond [(eq_attr "op_type" "E,RR") (const_int 2)
473 (eq_attr "op_type" "RX,RI,RRE,RS,RSI,S,SI,RRF") (const_int 4)]
474 (const_int 6)))
475
476
477 ;; Processor type. This attribute must exactly match the processor_type
478 ;; enumeration in s390.h. The current machine description does not
479 ;; distinguish between g5 and g6, but there are differences between the two
480 ;; CPUs could in theory be modeled.
481
482 (define_attr "cpu" "g5,g6,z900,z990,z9_109,z9_ec,z10,z196,zEC12,z13"
483 (const (symbol_ref "s390_tune_attr")))
484
485 (define_attr "cpu_facility"
486 "standard,ieee,zarch,cpu_zarch,longdisp,extimm,dfp,z10,z196,zEC12,vec,z13"
487 (const_string "standard"))
488
489 (define_attr "enabled" ""
490 (cond [(eq_attr "cpu_facility" "standard")
491 (const_int 1)
492
493 (and (eq_attr "cpu_facility" "ieee")
494 (match_test "TARGET_CPU_IEEE_FLOAT"))
495 (const_int 1)
496
497 (and (eq_attr "cpu_facility" "zarch")
498 (match_test "TARGET_ZARCH"))
499 (const_int 1)
500
501 (and (eq_attr "cpu_facility" "longdisp")
502 (match_test "TARGET_LONG_DISPLACEMENT"))
503 (const_int 1)
504
505 (and (eq_attr "cpu_facility" "extimm")
506 (match_test "TARGET_EXTIMM"))
507 (const_int 1)
508
509 (and (eq_attr "cpu_facility" "dfp")
510 (match_test "TARGET_DFP"))
511 (const_int 1)
512
513 (and (eq_attr "cpu_facility" "cpu_zarch")
514 (match_test "TARGET_CPU_ZARCH"))
515 (const_int 1)
516
517 (and (eq_attr "cpu_facility" "z10")
518 (match_test "TARGET_Z10"))
519 (const_int 1)
520
521 (and (eq_attr "cpu_facility" "z196")
522 (match_test "TARGET_Z196"))
523 (const_int 1)
524
525 (and (eq_attr "cpu_facility" "zEC12")
526 (match_test "TARGET_ZEC12"))
527 (const_int 1)
528
529 (and (eq_attr "cpu_facility" "vec")
530 (match_test "TARGET_VX"))
531 (const_int 1)
532
533 (and (eq_attr "cpu_facility" "z13")
534 (match_test "TARGET_Z13"))
535 (const_int 1)
536 ]
537 (const_int 0)))
538
539 ;; Pipeline description for z900. For lack of anything better,
540 ;; this description is also used for the g5 and g6.
541 (include "2064.md")
542
543 ;; Pipeline description for z990, z9-109 and z9-ec.
544 (include "2084.md")
545
546 ;; Pipeline description for z10
547 (include "2097.md")
548
549 ;; Pipeline description for z196
550 (include "2817.md")
551
552 ;; Pipeline description for zEC12
553 (include "2827.md")
554
555 ;; Pipeline description for z13
556 (include "2964.md")
557
558 ;; Predicates
559 (include "predicates.md")
560
561 ;; Constraint definitions
562 (include "constraints.md")
563
564 ;; Other includes
565 (include "tpf.md")
566
567 ;; Iterators
568
569 (define_mode_iterator ALL [TI DI SI HI QI TF DF SF TD DD SD V1QI V2QI V4QI V8QI V16QI V1HI V2HI V4HI V8HI V1SI V2SI V4SI V1DI V2DI V1SF V2SF V4SF V1TI V1DF V2DF V1TF])
570
571 ;; These mode iterators allow floating point patterns to be generated from the
572 ;; same template.
573 (define_mode_iterator FP_ALL [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")
574 (SD "TARGET_HARD_DFP")])
575 (define_mode_iterator FP [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")])
576 (define_mode_iterator BFP [TF DF SF])
577 (define_mode_iterator DFP [TD DD])
578 (define_mode_iterator DFP_ALL [TD DD SD])
579 (define_mode_iterator DSF [DF SF])
580 (define_mode_iterator SD_SF [SF SD])
581 (define_mode_iterator DD_DF [DF DD])
582 (define_mode_iterator TD_TF [TF TD])
583
584 ;; These mode iterators allow 31-bit and 64-bit GPR patterns to be generated
585 ;; from the same template.
586 (define_mode_iterator GPR [(DI "TARGET_ZARCH") SI])
587 (define_mode_iterator DGPR [(TI "TARGET_ZARCH") DI SI])
588 (define_mode_iterator DSI [DI SI])
589 (define_mode_iterator TDI [TI DI])
590
591 ;; These mode iterators allow :P to be used for patterns that operate on
592 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
593 (define_mode_iterator P [(DI "TARGET_64BIT") (SI "!TARGET_64BIT")])
594
595 ;; These macros refer to the actual word_mode of the configuration.
596 ;; This is equal to Pmode except on 31-bit machines in zarch mode.
597 (define_mode_iterator DW [(TI "TARGET_ZARCH") (DI "!TARGET_ZARCH")])
598 (define_mode_iterator W [(DI "TARGET_ZARCH") (SI "!TARGET_ZARCH")])
599
600 ;; Used by the umul pattern to express modes having half the size.
601 (define_mode_attr DWH [(TI "DI") (DI "SI")])
602 (define_mode_attr dwh [(TI "di") (DI "si")])
603
604 ;; This mode iterator allows the QI and HI patterns to be defined from
605 ;; the same template.
606 (define_mode_iterator HQI [HI QI])
607
608 ;; This mode iterator allows the integer patterns to be defined from the
609 ;; same template.
610 (define_mode_iterator INT [(DI "TARGET_ZARCH") SI HI QI])
611 (define_mode_iterator DINT [(TI "TARGET_ZARCH") DI SI HI QI])
612
613 ;; This iterator allows some 'ashift' and 'lshiftrt' pattern to be defined from
614 ;; the same template.
615 (define_code_iterator SHIFT [ashift lshiftrt])
616
617 ;; This iterator allows r[ox]sbg to be defined with the same template
618 (define_code_iterator IXOR [ior xor])
619
620 ;; This iterator is used to expand the patterns for the nearest
621 ;; integer functions.
622 (define_int_iterator FPINT [UNSPEC_FPINT_FLOOR UNSPEC_FPINT_BTRUNC
623 UNSPEC_FPINT_ROUND UNSPEC_FPINT_CEIL
624 UNSPEC_FPINT_NEARBYINT])
625 (define_int_attr fpint_name [(UNSPEC_FPINT_FLOOR "floor")
626 (UNSPEC_FPINT_BTRUNC "btrunc")
627 (UNSPEC_FPINT_ROUND "round")
628 (UNSPEC_FPINT_CEIL "ceil")
629 (UNSPEC_FPINT_NEARBYINT "nearbyint")])
630 (define_int_attr fpint_roundingmode [(UNSPEC_FPINT_FLOOR "7")
631 (UNSPEC_FPINT_BTRUNC "5")
632 (UNSPEC_FPINT_ROUND "1")
633 (UNSPEC_FPINT_CEIL "6")
634 (UNSPEC_FPINT_NEARBYINT "0")])
635
636 ;; This iterator and attribute allow to combine most atomic operations.
637 (define_code_iterator ATOMIC [and ior xor plus minus mult])
638 (define_code_iterator ATOMIC_Z196 [and ior xor plus])
639 (define_code_attr atomic [(and "and") (ior "or") (xor "xor")
640 (plus "add") (minus "sub") (mult "nand")])
641 (define_code_attr noxa [(and "n") (ior "o") (xor "x") (plus "a")])
642
643 ;; In FP templates, a string like "lt<de>br" will expand to "ltxbr" in
644 ;; TF/TDmode, "ltdbr" in DF/DDmode, and "ltebr" in SF/SDmode.
645 (define_mode_attr xde [(TF "x") (DF "d") (SF "e") (TD "x") (DD "d") (SD "e")])
646
647 ;; In FP templates, a <dee> in "m<dee><bt>r" will expand to "mx<bt>r" in
648 ;; TF/TDmode, "md<bt>r" in DF/DDmode, "mee<bt>r" in SFmode and "me<bt>r in
649 ;; SDmode.
650 (define_mode_attr xdee [(TF "x") (DF "d") (SF "ee") (TD "x") (DD "d") (SD "e")])
651
652 ;; In FP templates, "<RRe>" will expand to "RRE" in TFmode and "RR" otherwise.
653 ;; Likewise for "<RXe>".
654 (define_mode_attr RRe [(TF "RRE") (DF "RR") (SF "RR")])
655 (define_mode_attr RXe [(TF "RXE") (DF "RX") (SF "RX")])
656
657 ;; The decimal floating point variants of add, sub, div and mul support 3
658 ;; fp register operands. The following attributes allow to merge the bfp and
659 ;; dfp variants in a single insn definition.
660
661 ;; These mode attributes are supposed to be used in the `enabled' insn
662 ;; attribute to disable certain alternatives for certain modes.
663 (define_mode_attr nBFP [(TF "0") (DF "0") (SF "0") (TD "*") (DD "*") (DD "*")])
664 (define_mode_attr nDFP [(TF "*") (DF "*") (SF "*") (TD "0") (DD "0") (DD "0")])
665 (define_mode_attr DSF [(TF "0") (DF "*") (SF "*") (TD "0") (DD "0") (SD "0")])
666 (define_mode_attr DFDI [(TF "0") (DF "*") (SF "0")
667 (TD "0") (DD "0") (DD "0")
668 (TI "0") (DI "*") (SI "0")])
669
670 ;; This attribute is used in the operand constraint list
671 ;; for instructions dealing with the sign bit of 32 or 64bit fp values.
672 ;; TFmode values are represented by a fp register pair. Since the
673 ;; sign bit instructions only handle single source and target fp registers
674 ;; these instructions can only be used for TFmode values if the source and
675 ;; target operand uses the same fp register.
676 (define_mode_attr fT0 [(TF "0") (DF "f") (SF "f")])
677
678 ;; This attribute adds b for bfp instructions and t for dfp instructions and is used
679 ;; within instruction mnemonics.
680 (define_mode_attr bt [(TF "b") (DF "b") (SF "b") (TD "t") (DD "t") (SD "t")])
681
682 ;; This attribute is used within instruction mnemonics. It evaluates to d for dfp
683 ;; modes and to an empty string for bfp modes.
684 (define_mode_attr _d [(TF "") (DF "") (SF "") (TD "d") (DD "d") (SD "d")])
685
686 ;; In GPR and P templates, a constraint like "<d0>" will expand to "d" in DImode
687 ;; and "0" in SImode. This allows to combine instructions of which the 31bit
688 ;; version only operates on one register.
689 (define_mode_attr d0 [(DI "d") (SI "0")])
690
691 ;; In combination with d0 this allows to combine instructions of which the 31bit
692 ;; version only operates on one register. The DImode version needs an additional
693 ;; register for the assembler output.
694 (define_mode_attr 1 [(DI "%1,") (SI "")])
695
696 ;; In SHIFT templates, a string like "s<lr>dl" will expand to "sldl" in
697 ;; 'ashift' and "srdl" in 'lshiftrt'.
698 (define_code_attr lr [(ashift "l") (lshiftrt "r")])
699
700 ;; In SHIFT templates, this attribute holds the correct standard name for the
701 ;; pattern itself and the corresponding function calls.
702 (define_code_attr shift [(ashift "ashl") (lshiftrt "lshr")])
703
704 ;; This attribute handles differences in the instruction 'type' and will result
705 ;; in "RRE" for DImode and "RR" for SImode.
706 (define_mode_attr E [(DI "E") (SI "")])
707
708 ;; This attribute handles differences in the instruction 'type' and makes RX<Y>
709 ;; to result in "RXY" for DImode and "RX" for SImode.
710 (define_mode_attr Y [(DI "Y") (SI "")])
711
712 ;; This attribute handles differences in the instruction 'type' and will result
713 ;; in "RSE" for TImode and "RS" for DImode.
714 (define_mode_attr TE [(TI "E") (DI "")])
715
716 ;; In GPR templates, a string like "lc<g>r" will expand to "lcgr" in DImode
717 ;; and "lcr" in SImode.
718 (define_mode_attr g [(DI "g") (SI "")])
719
720 ;; In GPR templates, a string like "sl<y>" will expand to "slg" in DImode
721 ;; and "sly" in SImode. This is useful because on 64bit the ..g instructions
722 ;; were enhanced with long displacements whereas 31bit instructions got a ..y
723 ;; variant for long displacements.
724 (define_mode_attr y [(DI "g") (SI "y")])
725
726 ;; In DW templates, a string like "cds<g>" will expand to "cdsg" in TImode
727 ;; and "cds" in DImode.
728 (define_mode_attr tg [(TI "g") (DI "")])
729
730 ;; In TDI templates, a string like "c<d>sg".
731 (define_mode_attr td [(TI "d") (DI "")])
732
733 ;; In GPR templates, a string like "c<gf>dbr" will expand to "cgdbr" in DImode
734 ;; and "cfdbr" in SImode.
735 (define_mode_attr gf [(DI "g") (SI "f")])
736
737 ;; In GPR templates, a string like sll<gk> will expand to sllg for DI
738 ;; and sllk for SI. This way it is possible to merge the new z196 SI
739 ;; 3 operands shift instructions into the existing patterns.
740 (define_mode_attr gk [(DI "g") (SI "k")])
741
742 ;; ICM mask required to load MODE value into the lowest subreg
743 ;; of a SImode register.
744 (define_mode_attr icm_lo [(HI "3") (QI "1")])
745
746 ;; In HQI templates, a string like "llg<hc>" will expand to "llgh" in
747 ;; HImode and "llgc" in QImode.
748 (define_mode_attr hc [(HI "h") (QI "c")])
749
750 ;; In P templates, the mode <DBL> will expand to "TI" in DImode and "DI"
751 ;; in SImode.
752 (define_mode_attr DBL [(DI "TI") (SI "DI")])
753
754 ;; This attribute expands to DF for TFmode and to DD for TDmode . It is
755 ;; used for Txmode splitters splitting a Txmode copy into 2 Dxmode copies.
756 (define_mode_attr HALF_TMODE [(TF "DF") (TD "DD")])
757
758 ;; Maximum unsigned integer that fits in MODE.
759 (define_mode_attr max_uint [(HI "65535") (QI "255")])
760
761 ;; Start and end field computations for RISBG et al.
762 (define_mode_attr bfstart [(DI "s") (SI "t")])
763 (define_mode_attr bfend [(DI "e") (SI "f")])
764
765 ;; In place of GET_MODE_BITSIZE (<MODE>mode)
766 (define_mode_attr bitsize [(DI "64") (SI "32") (HI "16") (QI "8")])
767
768 ;; In place of GET_MODE_SIZE (<MODE>mode)
769 (define_mode_attr modesize [(DI "8") (SI "4")])
770
771 ;; Allow return and simple_return to be defined from a single template.
772 (define_code_iterator ANY_RETURN [return simple_return])
773
774
775
776 ; Condition code modes generated by vector fp comparisons. These will
777 ; be used also in single element mode.
778 (define_mode_iterator VFCMP [CCVEQ CCVFH CCVFHE])
779 ; Used with VFCMP to expand part of the mnemonic
780 ; For fp we have a mismatch: eq in the insn name - e in asm
781 (define_mode_attr asm_fcmp [(CCVEQ "e") (CCVFH "h") (CCVFHE "he")])
782 (define_mode_attr insn_cmp [(CCVEQ "eq") (CCVH "h") (CCVHU "hl") (CCVFH "h") (CCVFHE "he")])
783
784 ;; Subst pattern definitions
785 (include "subst.md")
786
787 (include "vector.md")
788
789 ;;
790 ;;- Compare instructions.
791 ;;
792
793 ; Test-under-Mask instructions
794
795 (define_insn "*tmqi_mem"
796 [(set (reg CC_REGNUM)
797 (compare (and:QI (match_operand:QI 0 "memory_operand" "Q,S")
798 (match_operand:QI 1 "immediate_operand" "n,n"))
799 (match_operand:QI 2 "immediate_operand" "n,n")))]
800 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], false))"
801 "@
802 tm\t%S0,%b1
803 tmy\t%S0,%b1"
804 [(set_attr "op_type" "SI,SIY")
805 (set_attr "cpu_facility" "*,longdisp")
806 (set_attr "z10prop" "z10_super,z10_super")])
807
808 (define_insn "*tmdi_reg"
809 [(set (reg CC_REGNUM)
810 (compare (and:DI (match_operand:DI 0 "nonimmediate_operand" "d,d,d,d")
811 (match_operand:DI 1 "immediate_operand"
812 "N0HD0,N1HD0,N2HD0,N3HD0"))
813 (match_operand:DI 2 "immediate_operand" "n,n,n,n")))]
814 "TARGET_ZARCH
815 && s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
816 && s390_single_part (operands[1], DImode, HImode, 0) >= 0"
817 "@
818 tmhh\t%0,%i1
819 tmhl\t%0,%i1
820 tmlh\t%0,%i1
821 tmll\t%0,%i1"
822 [(set_attr "op_type" "RI")
823 (set_attr "z10prop" "z10_super,z10_super,z10_super,z10_super")])
824
825 (define_insn "*tmsi_reg"
826 [(set (reg CC_REGNUM)
827 (compare (and:SI (match_operand:SI 0 "nonimmediate_operand" "d,d")
828 (match_operand:SI 1 "immediate_operand" "N0HS0,N1HS0"))
829 (match_operand:SI 2 "immediate_operand" "n,n")))]
830 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
831 && s390_single_part (operands[1], SImode, HImode, 0) >= 0"
832 "@
833 tmh\t%0,%i1
834 tml\t%0,%i1"
835 [(set_attr "op_type" "RI")
836 (set_attr "z10prop" "z10_super,z10_super")])
837
838 (define_insn "*tm<mode>_full"
839 [(set (reg CC_REGNUM)
840 (compare (match_operand:HQI 0 "register_operand" "d")
841 (match_operand:HQI 1 "immediate_operand" "n")))]
842 "s390_match_ccmode (insn, s390_tm_ccmode (constm1_rtx, operands[1], true))"
843 "tml\t%0,<max_uint>"
844 [(set_attr "op_type" "RI")
845 (set_attr "z10prop" "z10_super")])
846
847
848 ;
849 ; Load-and-Test instructions
850 ;
851
852 ; tst(di|si) instruction pattern(s).
853
854 (define_insn "*tstdi_sign"
855 [(set (reg CC_REGNUM)
856 (compare
857 (ashiftrt:DI
858 (ashift:DI
859 (subreg:DI (match_operand:SI 0 "nonimmediate_operand" "d,T") 0)
860 (const_int 32)) (const_int 32))
861 (match_operand:DI 1 "const0_operand" "")))
862 (set (match_operand:DI 2 "register_operand" "=d,d")
863 (sign_extend:DI (match_dup 0)))]
864 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH"
865 "ltgfr\t%2,%0
866 ltgf\t%2,%0"
867 [(set_attr "op_type" "RRE,RXY")
868 (set_attr "cpu_facility" "*,z10")
869 (set_attr "z10prop" "z10_super_E1,z10_super_E1") ])
870
871 ; ltr, lt, ltgr, ltg
872 (define_insn "*tst<mode>_extimm"
873 [(set (reg CC_REGNUM)
874 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,T")
875 (match_operand:GPR 1 "const0_operand" "")))
876 (set (match_operand:GPR 2 "register_operand" "=d,d")
877 (match_dup 0))]
878 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
879 "@
880 lt<g>r\t%2,%0
881 lt<g>\t%2,%0"
882 [(set_attr "op_type" "RR<E>,RXY")
883 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3") ])
884
885 ; ltr, lt, ltgr, ltg
886 (define_insn "*tst<mode>_cconly_extimm"
887 [(set (reg CC_REGNUM)
888 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,T")
889 (match_operand:GPR 1 "const0_operand" "")))
890 (clobber (match_scratch:GPR 2 "=X,d"))]
891 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
892 "@
893 lt<g>r\t%0,%0
894 lt<g>\t%2,%0"
895 [(set_attr "op_type" "RR<E>,RXY")
896 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3")])
897
898 (define_insn "*tstdi"
899 [(set (reg CC_REGNUM)
900 (compare (match_operand:DI 0 "register_operand" "d")
901 (match_operand:DI 1 "const0_operand" "")))
902 (set (match_operand:DI 2 "register_operand" "=d")
903 (match_dup 0))]
904 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH && !TARGET_EXTIMM"
905 "ltgr\t%2,%0"
906 [(set_attr "op_type" "RRE")
907 (set_attr "z10prop" "z10_fr_E1")])
908
909 (define_insn "*tstsi"
910 [(set (reg CC_REGNUM)
911 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
912 (match_operand:SI 1 "const0_operand" "")))
913 (set (match_operand:SI 2 "register_operand" "=d,d,d")
914 (match_dup 0))]
915 "s390_match_ccmode(insn, CCSmode) && !TARGET_EXTIMM"
916 "@
917 ltr\t%2,%0
918 icm\t%2,15,%S0
919 icmy\t%2,15,%S0"
920 [(set_attr "op_type" "RR,RS,RSY")
921 (set_attr "cpu_facility" "*,*,longdisp")
922 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
923
924 (define_insn "*tstsi_cconly"
925 [(set (reg CC_REGNUM)
926 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
927 (match_operand:SI 1 "const0_operand" "")))
928 (clobber (match_scratch:SI 2 "=X,d,d"))]
929 "s390_match_ccmode(insn, CCSmode)"
930 "@
931 ltr\t%0,%0
932 icm\t%2,15,%S0
933 icmy\t%2,15,%S0"
934 [(set_attr "op_type" "RR,RS,RSY")
935 (set_attr "cpu_facility" "*,*,longdisp")
936 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
937
938 (define_insn "*tstdi_cconly_31"
939 [(set (reg CC_REGNUM)
940 (compare (match_operand:DI 0 "register_operand" "d")
941 (match_operand:DI 1 "const0_operand" "")))]
942 "s390_match_ccmode(insn, CCSmode) && !TARGET_ZARCH"
943 "srda\t%0,0"
944 [(set_attr "op_type" "RS")
945 (set_attr "atype" "reg")])
946
947 ; ltr, ltgr
948 (define_insn "*tst<mode>_cconly2"
949 [(set (reg CC_REGNUM)
950 (compare (match_operand:GPR 0 "register_operand" "d")
951 (match_operand:GPR 1 "const0_operand" "")))]
952 "s390_match_ccmode(insn, CCSmode)"
953 "lt<g>r\t%0,%0"
954 [(set_attr "op_type" "RR<E>")
955 (set_attr "z10prop" "z10_fr_E1")])
956
957 ; tst(hi|qi) instruction pattern(s).
958
959 (define_insn "*tst<mode>CCT"
960 [(set (reg CC_REGNUM)
961 (compare (match_operand:HQI 0 "nonimmediate_operand" "?Q,?S,d")
962 (match_operand:HQI 1 "const0_operand" "")))
963 (set (match_operand:HQI 2 "register_operand" "=d,d,0")
964 (match_dup 0))]
965 "s390_match_ccmode(insn, CCTmode)"
966 "@
967 icm\t%2,<icm_lo>,%S0
968 icmy\t%2,<icm_lo>,%S0
969 tml\t%0,<max_uint>"
970 [(set_attr "op_type" "RS,RSY,RI")
971 (set_attr "cpu_facility" "*,longdisp,*")
972 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
973
974 (define_insn "*tsthiCCT_cconly"
975 [(set (reg CC_REGNUM)
976 (compare (match_operand:HI 0 "nonimmediate_operand" "Q,S,d")
977 (match_operand:HI 1 "const0_operand" "")))
978 (clobber (match_scratch:HI 2 "=d,d,X"))]
979 "s390_match_ccmode(insn, CCTmode)"
980 "@
981 icm\t%2,3,%S0
982 icmy\t%2,3,%S0
983 tml\t%0,65535"
984 [(set_attr "op_type" "RS,RSY,RI")
985 (set_attr "cpu_facility" "*,longdisp,*")
986 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
987
988 (define_insn "*tstqiCCT_cconly"
989 [(set (reg CC_REGNUM)
990 (compare (match_operand:QI 0 "nonimmediate_operand" "?Q,?S,d")
991 (match_operand:QI 1 "const0_operand" "")))]
992 "s390_match_ccmode(insn, CCTmode)"
993 "@
994 cli\t%S0,0
995 cliy\t%S0,0
996 tml\t%0,255"
997 [(set_attr "op_type" "SI,SIY,RI")
998 (set_attr "cpu_facility" "*,longdisp,*")
999 (set_attr "z10prop" "z10_super,z10_super,z10_super")])
1000
1001 (define_insn "*tst<mode>"
1002 [(set (reg CC_REGNUM)
1003 (compare (match_operand:HQI 0 "s_operand" "Q,S")
1004 (match_operand:HQI 1 "const0_operand" "")))
1005 (set (match_operand:HQI 2 "register_operand" "=d,d")
1006 (match_dup 0))]
1007 "s390_match_ccmode(insn, CCSmode)"
1008 "@
1009 icm\t%2,<icm_lo>,%S0
1010 icmy\t%2,<icm_lo>,%S0"
1011 [(set_attr "op_type" "RS,RSY")
1012 (set_attr "cpu_facility" "*,longdisp")
1013 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
1014
1015 (define_insn "*tst<mode>_cconly"
1016 [(set (reg CC_REGNUM)
1017 (compare (match_operand:HQI 0 "s_operand" "Q,S")
1018 (match_operand:HQI 1 "const0_operand" "")))
1019 (clobber (match_scratch:HQI 2 "=d,d"))]
1020 "s390_match_ccmode(insn, CCSmode)"
1021 "@
1022 icm\t%2,<icm_lo>,%S0
1023 icmy\t%2,<icm_lo>,%S0"
1024 [(set_attr "op_type" "RS,RSY")
1025 (set_attr "cpu_facility" "*,longdisp")
1026 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
1027
1028
1029 ; Compare (equality) instructions
1030
1031 (define_insn "*cmpdi_cct"
1032 [(set (reg CC_REGNUM)
1033 (compare (match_operand:DI 0 "nonimmediate_operand" "%d,d,d,d,Q")
1034 (match_operand:DI 1 "general_operand" "d,K,Os,T,BQ")))]
1035 "s390_match_ccmode (insn, CCTmode) && TARGET_ZARCH"
1036 "@
1037 cgr\t%0,%1
1038 cghi\t%0,%h1
1039 cgfi\t%0,%1
1040 cg\t%0,%1
1041 #"
1042 [(set_attr "op_type" "RRE,RI,RIL,RXY,SS")
1043 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,*")])
1044
1045 (define_insn "*cmpsi_cct"
1046 [(set (reg CC_REGNUM)
1047 (compare (match_operand:SI 0 "nonimmediate_operand" "%d,d,d,d,d,Q")
1048 (match_operand:SI 1 "general_operand" "d,K,Os,R,T,BQ")))]
1049 "s390_match_ccmode (insn, CCTmode)"
1050 "@
1051 cr\t%0,%1
1052 chi\t%0,%h1
1053 cfi\t%0,%1
1054 c\t%0,%1
1055 cy\t%0,%1
1056 #"
1057 [(set_attr "op_type" "RR,RI,RIL,RX,RXY,SS")
1058 (set_attr "cpu_facility" "*,*,*,*,longdisp,*")
1059 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*")])
1060
1061 ; Compare (signed) instructions
1062
1063 (define_insn "*cmpdi_ccs_sign"
1064 [(set (reg CC_REGNUM)
1065 (compare (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1066 "d,T,b"))
1067 (match_operand:DI 0 "register_operand" "d, d,d")))]
1068 "s390_match_ccmode(insn, CCSRmode) && TARGET_ZARCH"
1069 "@
1070 cgfr\t%0,%1
1071 cgf\t%0,%1
1072 cgfrl\t%0,%1"
1073 [(set_attr "op_type" "RRE,RXY,RIL")
1074 (set_attr "z10prop" "z10_c,*,*")
1075 (set_attr "type" "*,*,larl")])
1076
1077
1078
1079 (define_insn "*cmpsi_ccs_sign"
1080 [(set (reg CC_REGNUM)
1081 (compare (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T,b"))
1082 (match_operand:SI 0 "register_operand" "d,d,d")))]
1083 "s390_match_ccmode(insn, CCSRmode)"
1084 "@
1085 ch\t%0,%1
1086 chy\t%0,%1
1087 chrl\t%0,%1"
1088 [(set_attr "op_type" "RX,RXY,RIL")
1089 (set_attr "cpu_facility" "*,longdisp,z10")
1090 (set_attr "type" "*,*,larl")
1091 (set_attr "z196prop" "z196_cracked,z196_cracked,z196_cracked")])
1092
1093 (define_insn "*cmphi_ccs_z10"
1094 [(set (reg CC_REGNUM)
1095 (compare (match_operand:HI 0 "s_operand" "Q")
1096 (match_operand:HI 1 "immediate_operand" "K")))]
1097 "s390_match_ccmode(insn, CCSmode) && TARGET_Z10"
1098 "chhsi\t%0,%1"
1099 [(set_attr "op_type" "SIL")
1100 (set_attr "z196prop" "z196_cracked")])
1101
1102 (define_insn "*cmpdi_ccs_signhi_rl"
1103 [(set (reg CC_REGNUM)
1104 (compare (sign_extend:DI (match_operand:HI 1 "memory_operand" "T,b"))
1105 (match_operand:GPR 0 "register_operand" "d,d")))]
1106 "s390_match_ccmode(insn, CCSRmode) && TARGET_Z10"
1107 "@
1108 cgh\t%0,%1
1109 cghrl\t%0,%1"
1110 [(set_attr "op_type" "RXY,RIL")
1111 (set_attr "type" "*,larl")])
1112
1113 ; cr, chi, cfi, c, cy, cgr, cghi, cgfi, cg, chsi, cghsi, crl, cgrl
1114 (define_insn "*cmp<mode>_ccs"
1115 [(set (reg CC_REGNUM)
1116 (compare (match_operand:GPR 0 "nonimmediate_operand"
1117 "d,d,Q, d,d,d,d")
1118 (match_operand:GPR 1 "general_operand"
1119 "d,K,K,Os,R,T,b")))]
1120 "s390_match_ccmode(insn, CCSmode)"
1121 "@
1122 c<g>r\t%0,%1
1123 c<g>hi\t%0,%h1
1124 c<g>hsi\t%0,%h1
1125 c<g>fi\t%0,%1
1126 c<g>\t%0,%1
1127 c<y>\t%0,%1
1128 c<g>rl\t%0,%1"
1129 [(set_attr "op_type" "RR<E>,RI,SIL,RIL,RX<Y>,RXY,RIL")
1130 (set_attr "cpu_facility" "*,*,z10,extimm,*,longdisp,z10")
1131 (set_attr "type" "*,*,*,*,*,*,larl")
1132 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,z10_super")])
1133
1134
1135 ; Compare (unsigned) instructions
1136
1137 (define_insn "*cmpsi_ccu_zerohi_rlsi"
1138 [(set (reg CC_REGNUM)
1139 (compare (zero_extend:SI (mem:HI (match_operand:SI 1
1140 "larl_operand" "X")))
1141 (match_operand:SI 0 "register_operand" "d")))]
1142 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1143 "clhrl\t%0,%1"
1144 [(set_attr "op_type" "RIL")
1145 (set_attr "type" "larl")
1146 (set_attr "z10prop" "z10_super")])
1147
1148 ; clhrl, clghrl
1149 (define_insn "*cmp<GPR:mode>_ccu_zerohi_rldi"
1150 [(set (reg CC_REGNUM)
1151 (compare (zero_extend:GPR (mem:HI (match_operand:DI 1
1152 "larl_operand" "X")))
1153 (match_operand:GPR 0 "register_operand" "d")))]
1154 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1155 "cl<g>hrl\t%0,%1"
1156 [(set_attr "op_type" "RIL")
1157 (set_attr "type" "larl")
1158 (set_attr "z10prop" "z10_super")])
1159
1160 (define_insn "*cmpdi_ccu_zero"
1161 [(set (reg CC_REGNUM)
1162 (compare (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1163 "d,T,b"))
1164 (match_operand:DI 0 "register_operand" "d,d,d")))]
1165 "s390_match_ccmode (insn, CCURmode) && TARGET_ZARCH"
1166 "@
1167 clgfr\t%0,%1
1168 clgf\t%0,%1
1169 clgfrl\t%0,%1"
1170 [(set_attr "op_type" "RRE,RXY,RIL")
1171 (set_attr "cpu_facility" "*,*,z10")
1172 (set_attr "type" "*,*,larl")
1173 (set_attr "z10prop" "z10_super_c,z10_super_E1,z10_super")])
1174
1175 (define_insn "*cmpdi_ccu"
1176 [(set (reg CC_REGNUM)
1177 (compare (match_operand:DI 0 "nonimmediate_operand"
1178 "d, d,d,Q,d, Q,BQ")
1179 (match_operand:DI 1 "general_operand"
1180 "d,Op,b,D,T,BQ,Q")))]
1181 "s390_match_ccmode (insn, CCUmode) && TARGET_ZARCH"
1182 "@
1183 clgr\t%0,%1
1184 clgfi\t%0,%1
1185 clgrl\t%0,%1
1186 clghsi\t%0,%x1
1187 clg\t%0,%1
1188 #
1189 #"
1190 [(set_attr "op_type" "RRE,RIL,RIL,SIL,RXY,SS,SS")
1191 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*")
1192 (set_attr "type" "*,*,larl,*,*,*,*")
1193 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*,*")])
1194
1195 (define_insn "*cmpsi_ccu"
1196 [(set (reg CC_REGNUM)
1197 (compare (match_operand:SI 0 "nonimmediate_operand" "d, d,d,Q,d,d, Q,BQ")
1198 (match_operand:SI 1 "general_operand" "d,Os,b,D,R,T,BQ, Q")))]
1199 "s390_match_ccmode (insn, CCUmode)"
1200 "@
1201 clr\t%0,%1
1202 clfi\t%0,%o1
1203 clrl\t%0,%1
1204 clfhsi\t%0,%x1
1205 cl\t%0,%1
1206 cly\t%0,%1
1207 #
1208 #"
1209 [(set_attr "op_type" "RR,RIL,RIL,SIL,RX,RXY,SS,SS")
1210 (set_attr "cpu_facility" "*,extimm,z10,z10,*,longdisp,*,*")
1211 (set_attr "type" "*,*,larl,*,*,*,*,*")
1212 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,*,*")])
1213
1214 (define_insn "*cmphi_ccu"
1215 [(set (reg CC_REGNUM)
1216 (compare (match_operand:HI 0 "nonimmediate_operand" "d,d,Q,Q,BQ")
1217 (match_operand:HI 1 "general_operand" "Q,S,D,BQ,Q")))]
1218 "s390_match_ccmode (insn, CCUmode)
1219 && !register_operand (operands[1], HImode)"
1220 "@
1221 clm\t%0,3,%S1
1222 clmy\t%0,3,%S1
1223 clhhsi\t%0,%1
1224 #
1225 #"
1226 [(set_attr "op_type" "RS,RSY,SIL,SS,SS")
1227 (set_attr "cpu_facility" "*,longdisp,z10,*,*")
1228 (set_attr "z10prop" "*,*,z10_super,*,*")])
1229
1230 (define_insn "*cmpqi_ccu"
1231 [(set (reg CC_REGNUM)
1232 (compare (match_operand:QI 0 "nonimmediate_operand" "d,d,Q,S,Q,BQ")
1233 (match_operand:QI 1 "general_operand" "Q,S,n,n,BQ,Q")))]
1234 "s390_match_ccmode (insn, CCUmode)
1235 && !register_operand (operands[1], QImode)"
1236 "@
1237 clm\t%0,1,%S1
1238 clmy\t%0,1,%S1
1239 cli\t%S0,%b1
1240 cliy\t%S0,%b1
1241 #
1242 #"
1243 [(set_attr "op_type" "RS,RSY,SI,SIY,SS,SS")
1244 (set_attr "cpu_facility" "*,longdisp,*,longdisp,*,*")
1245 (set_attr "z10prop" "*,*,z10_super,z10_super,*,*")])
1246
1247
1248 ; Block compare (CLC) instruction patterns.
1249
1250 (define_insn "*clc"
1251 [(set (reg CC_REGNUM)
1252 (compare (match_operand:BLK 0 "memory_operand" "Q")
1253 (match_operand:BLK 1 "memory_operand" "Q")))
1254 (use (match_operand 2 "const_int_operand" "n"))]
1255 "s390_match_ccmode (insn, CCUmode)
1256 && INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
1257 "clc\t%O0(%2,%R0),%S1"
1258 [(set_attr "op_type" "SS")])
1259
1260 (define_split
1261 [(set (reg CC_REGNUM)
1262 (compare (match_operand 0 "memory_operand" "")
1263 (match_operand 1 "memory_operand" "")))]
1264 "reload_completed
1265 && s390_match_ccmode (insn, CCUmode)
1266 && GET_MODE (operands[0]) == GET_MODE (operands[1])
1267 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
1268 [(parallel
1269 [(set (match_dup 0) (match_dup 1))
1270 (use (match_dup 2))])]
1271 {
1272 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
1273 operands[0] = adjust_address (operands[0], BLKmode, 0);
1274 operands[1] = adjust_address (operands[1], BLKmode, 0);
1275
1276 operands[1] = gen_rtx_COMPARE (GET_MODE (SET_DEST (PATTERN (curr_insn))),
1277 operands[0], operands[1]);
1278 operands[0] = SET_DEST (PATTERN (curr_insn));
1279 })
1280
1281
1282 ; (TF|DF|SF|TD|DD|SD) instructions
1283
1284 ; ltxbr, ltdbr, ltebr, ltxtr, ltdtr
1285 (define_insn "*cmp<mode>_ccs_0"
1286 [(set (reg CC_REGNUM)
1287 (compare (match_operand:FP 0 "register_operand" "f")
1288 (match_operand:FP 1 "const0_operand" "")))]
1289 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1290 "lt<xde><bt>r\t%0,%0"
1291 [(set_attr "op_type" "RRE")
1292 (set_attr "type" "fsimp<mode>")])
1293
1294 ; cxtr, cxbr, cdtr, cdbr, cebr, cdb, ceb
1295 (define_insn "*cmp<mode>_ccs"
1296 [(set (reg CC_REGNUM)
1297 (compare (match_operand:FP 0 "register_operand" "f,f")
1298 (match_operand:FP 1 "general_operand" "f,R")))]
1299 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1300 "@
1301 c<xde><bt>r\t%0,%1
1302 c<xde>b\t%0,%1"
1303 [(set_attr "op_type" "RRE,RXE")
1304 (set_attr "type" "fsimp<mode>")
1305 (set_attr "enabled" "*,<DSF>")])
1306
1307 ; wfcedbs, wfchdbs, wfchedbs
1308 (define_insn "*vec_cmp<insn_cmp>df_cconly"
1309 [(set (reg:VFCMP CC_REGNUM)
1310 (compare:VFCMP (match_operand:DF 0 "register_operand" "v")
1311 (match_operand:DF 1 "register_operand" "v")))
1312 (clobber (match_scratch:V2DI 2 "=v"))]
1313 "TARGET_VX && TARGET_HARD_FLOAT"
1314 "wfc<asm_fcmp>dbs\t%v2,%v0,%v1"
1315 [(set_attr "op_type" "VRR")])
1316
1317 ; Compare and Branch instructions
1318
1319 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1320 ; The following instructions do a complementary access of their second
1321 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1322 (define_insn "*cmp_and_br_signed_<mode>"
1323 [(set (pc)
1324 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1325 [(match_operand:GPR 1 "register_operand" "d,d")
1326 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1327 (label_ref (match_operand 3 "" ""))
1328 (pc)))
1329 (clobber (reg:CC CC_REGNUM))]
1330 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1331 {
1332 if (get_attr_length (insn) == 6)
1333 return which_alternative ?
1334 "c<g>ij%C0\t%1,%c2,%l3" : "c<g>rj%C0\t%1,%2,%l3";
1335 else
1336 return which_alternative ?
1337 "c<g>fi\t%1,%c2\;jg%C0\t%l3" : "c<g>r\t%1,%2\;jg%C0\t%l3";
1338 }
1339 [(set_attr "op_type" "RIE")
1340 (set_attr "type" "branch")
1341 (set_attr "z10prop" "z10_super_c,z10_super")
1342 (set (attr "length")
1343 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1344 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1345 ; 10 byte for cgr/jg
1346
1347 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1348 ; The following instructions do a complementary access of their second
1349 ; operand (z10 only): clrj, clgrj, clr, clgr
1350 (define_insn "*cmp_and_br_unsigned_<mode>"
1351 [(set (pc)
1352 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1353 [(match_operand:GPR 1 "register_operand" "d,d")
1354 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1355 (label_ref (match_operand 3 "" ""))
1356 (pc)))
1357 (clobber (reg:CC CC_REGNUM))]
1358 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1359 {
1360 if (get_attr_length (insn) == 6)
1361 return which_alternative ?
1362 "cl<g>ij%C0\t%1,%b2,%l3" : "cl<g>rj%C0\t%1,%2,%l3";
1363 else
1364 return which_alternative ?
1365 "cl<g>fi\t%1,%b2\;jg%C0\t%l3" : "cl<g>r\t%1,%2\;jg%C0\t%l3";
1366 }
1367 [(set_attr "op_type" "RIE")
1368 (set_attr "type" "branch")
1369 (set_attr "z10prop" "z10_super_c,z10_super")
1370 (set (attr "length")
1371 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1372 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1373 ; 10 byte for clgr/jg
1374
1375 ; And now the same two patterns as above but with a negated CC mask.
1376
1377 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1378 ; The following instructions do a complementary access of their second
1379 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1380 (define_insn "*icmp_and_br_signed_<mode>"
1381 [(set (pc)
1382 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1383 [(match_operand:GPR 1 "register_operand" "d,d")
1384 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1385 (pc)
1386 (label_ref (match_operand 3 "" ""))))
1387 (clobber (reg:CC CC_REGNUM))]
1388 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1389 {
1390 if (get_attr_length (insn) == 6)
1391 return which_alternative ?
1392 "c<g>ij%D0\t%1,%c2,%l3" : "c<g>rj%D0\t%1,%2,%l3";
1393 else
1394 return which_alternative ?
1395 "c<g>fi\t%1,%c2\;jg%D0\t%l3" : "c<g>r\t%1,%2\;jg%D0\t%l3";
1396 }
1397 [(set_attr "op_type" "RIE")
1398 (set_attr "type" "branch")
1399 (set_attr "z10prop" "z10_super_c,z10_super")
1400 (set (attr "length")
1401 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1402 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1403 ; 10 byte for cgr/jg
1404
1405 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1406 ; The following instructions do a complementary access of their second
1407 ; operand (z10 only): clrj, clgrj, clr, clgr
1408 (define_insn "*icmp_and_br_unsigned_<mode>"
1409 [(set (pc)
1410 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1411 [(match_operand:GPR 1 "register_operand" "d,d")
1412 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1413 (pc)
1414 (label_ref (match_operand 3 "" ""))))
1415 (clobber (reg:CC CC_REGNUM))]
1416 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1417 {
1418 if (get_attr_length (insn) == 6)
1419 return which_alternative ?
1420 "cl<g>ij%D0\t%1,%b2,%l3" : "cl<g>rj%D0\t%1,%2,%l3";
1421 else
1422 return which_alternative ?
1423 "cl<g>fi\t%1,%b2\;jg%D0\t%l3" : "cl<g>r\t%1,%2\;jg%D0\t%l3";
1424 }
1425 [(set_attr "op_type" "RIE")
1426 (set_attr "type" "branch")
1427 (set_attr "z10prop" "z10_super_c,z10_super")
1428 (set (attr "length")
1429 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1430 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1431 ; 10 byte for clgr/jg
1432
1433 ;;
1434 ;;- Move instructions.
1435 ;;
1436
1437 ;
1438 ; movti instruction pattern(s).
1439 ;
1440
1441 ; FIXME: More constants are possible by enabling jxx, jyy constraints
1442 ; for TImode (use double-int for the calculations)
1443 (define_insn "movti"
1444 [(set (match_operand:TI 0 "nonimmediate_operand" "=d,S,v, v, v,v,d,v,R, d,o")
1445 (match_operand:TI 1 "general_operand" " S,d,v,j00,jm1,d,v,R,v,dPT,d"))]
1446 "TARGET_ZARCH"
1447 "@
1448 lmg\t%0,%N0,%S1
1449 stmg\t%1,%N1,%S0
1450 vlr\t%v0,%v1
1451 vzero\t%v0
1452 vone\t%v0
1453 vlvgp\t%v0,%1,%N1
1454 #
1455 vl\t%v0,%1
1456 vst\t%v1,%0
1457 #
1458 #"
1459 [(set_attr "op_type" "RSY,RSY,VRR,VRI,VRI,VRR,*,VRX,VRX,*,*")
1460 (set_attr "type" "lm,stm,*,*,*,*,*,*,*,*,*")
1461 (set_attr "cpu_facility" "*,*,vec,vec,vec,vec,vec,vec,vec,*,*")])
1462
1463 (define_split
1464 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1465 (match_operand:TI 1 "general_operand" ""))]
1466 "TARGET_ZARCH && reload_completed
1467 && s390_split_ok_p (operands[0], operands[1], TImode, 0)"
1468 [(set (match_dup 2) (match_dup 4))
1469 (set (match_dup 3) (match_dup 5))]
1470 {
1471 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1472 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1473 operands[4] = operand_subword (operands[1], 0, 0, TImode);
1474 operands[5] = operand_subword (operands[1], 1, 0, TImode);
1475 })
1476
1477 (define_split
1478 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1479 (match_operand:TI 1 "general_operand" ""))]
1480 "TARGET_ZARCH && reload_completed
1481 && s390_split_ok_p (operands[0], operands[1], TImode, 1)"
1482 [(set (match_dup 2) (match_dup 4))
1483 (set (match_dup 3) (match_dup 5))]
1484 {
1485 operands[2] = operand_subword (operands[0], 1, 0, TImode);
1486 operands[3] = operand_subword (operands[0], 0, 0, TImode);
1487 operands[4] = operand_subword (operands[1], 1, 0, TImode);
1488 operands[5] = operand_subword (operands[1], 0, 0, TImode);
1489 })
1490
1491 ; Use part of the TImode target reg to perform the address
1492 ; calculation. If the TImode value is supposed to be copied into a VR
1493 ; this splitter is not necessary.
1494 (define_split
1495 [(set (match_operand:TI 0 "register_operand" "")
1496 (match_operand:TI 1 "memory_operand" ""))]
1497 "TARGET_ZARCH && reload_completed
1498 && !VECTOR_REG_P (operands[0])
1499 && !s_operand (operands[1], VOIDmode)"
1500 [(set (match_dup 0) (match_dup 1))]
1501 {
1502 rtx addr = operand_subword (operands[0], 1, 0, TImode);
1503 addr = gen_lowpart (Pmode, addr);
1504 s390_load_address (addr, XEXP (operands[1], 0));
1505 operands[1] = replace_equiv_address (operands[1], addr);
1506 })
1507
1508
1509 ; Split a VR -> GPR TImode move into 2 vector load GR from VR element.
1510 ; For the higher order bits we do simply a DImode move while the
1511 ; second part is done via vec extract. Both will end up as vlgvg.
1512 (define_split
1513 [(set (match_operand:TI 0 "register_operand" "")
1514 (match_operand:TI 1 "register_operand" ""))]
1515 "TARGET_VX && reload_completed
1516 && GENERAL_REG_P (operands[0])
1517 && VECTOR_REG_P (operands[1])"
1518 [(set (match_dup 2) (match_dup 4))
1519 (set (match_dup 3) (unspec:DI [(match_dup 5) (const_int 1)]
1520 UNSPEC_VEC_EXTRACT))]
1521 {
1522 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1523 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1524 operands[4] = gen_rtx_REG (DImode, REGNO (operands[1]));
1525 operands[5] = gen_rtx_REG (V2DImode, REGNO (operands[1]));
1526 })
1527
1528 ;
1529 ; Patterns used for secondary reloads
1530 ;
1531
1532 ; z10 provides move instructions accepting larl memory operands.
1533 ; Unfortunately there is no such variant for QI, TI and FP mode moves.
1534 ; These patterns are also used for unaligned SI and DI accesses.
1535
1536 (define_expand "reload<ALL:mode><P:mode>_tomem_z10"
1537 [(parallel [(match_operand:ALL 0 "memory_operand" "")
1538 (match_operand:ALL 1 "register_operand" "=d")
1539 (match_operand:P 2 "register_operand" "=&a")])]
1540 "TARGET_Z10"
1541 {
1542 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1543 DONE;
1544 })
1545
1546 (define_expand "reload<ALL:mode><P:mode>_toreg_z10"
1547 [(parallel [(match_operand:ALL 0 "register_operand" "=d")
1548 (match_operand:ALL 1 "memory_operand" "")
1549 (match_operand:P 2 "register_operand" "=a")])]
1550 "TARGET_Z10"
1551 {
1552 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1553 DONE;
1554 })
1555
1556 (define_expand "reload<P:mode>_larl_odd_addend_z10"
1557 [(parallel [(match_operand:P 0 "register_operand" "=d")
1558 (match_operand:P 1 "larl_operand" "")
1559 (match_operand:P 2 "register_operand" "=a")])]
1560 "TARGET_Z10"
1561 {
1562 s390_reload_larl_operand (operands[0], operands[1], operands[2]);
1563 DONE;
1564 })
1565
1566 ; Handles loading a PLUS (load address) expression
1567
1568 (define_expand "reload<mode>_plus"
1569 [(parallel [(match_operand:P 0 "register_operand" "=a")
1570 (match_operand:P 1 "s390_plus_operand" "")
1571 (match_operand:P 2 "register_operand" "=&a")])]
1572 ""
1573 {
1574 s390_expand_plus_operand (operands[0], operands[1], operands[2]);
1575 DONE;
1576 })
1577
1578 ; Not all the indirect memory access instructions support the full
1579 ; format (long disp + index + base). So whenever a move from/to such
1580 ; an address is required and the instruction cannot deal with it we do
1581 ; a load address into a scratch register first and use this as the new
1582 ; base register.
1583 ; This in particular is used for:
1584 ; - non-offsetable memory accesses for multiword moves
1585 ; - full vector reg moves with long displacements
1586
1587 (define_expand "reload<mode>_la_in"
1588 [(parallel [(match_operand 0 "register_operand" "")
1589 (match_operand 1 "" "")
1590 (match_operand:P 2 "register_operand" "=&a")])]
1591 ""
1592 {
1593 gcc_assert (MEM_P (operands[1]));
1594 s390_load_address (operands[2], find_replacement (&XEXP (operands[1], 0)));
1595 operands[1] = replace_equiv_address (operands[1], operands[2]);
1596 emit_move_insn (operands[0], operands[1]);
1597 DONE;
1598 })
1599
1600 (define_expand "reload<mode>_la_out"
1601 [(parallel [(match_operand 0 "" "")
1602 (match_operand 1 "register_operand" "")
1603 (match_operand:P 2 "register_operand" "=&a")])]
1604 ""
1605 {
1606 gcc_assert (MEM_P (operands[0]));
1607 s390_load_address (operands[2], find_replacement (&XEXP (operands[0], 0)));
1608 operands[0] = replace_equiv_address (operands[0], operands[2]);
1609 emit_move_insn (operands[0], operands[1]);
1610 DONE;
1611 })
1612
1613 (define_expand "reload<mode>_PIC_addr"
1614 [(parallel [(match_operand 0 "register_operand" "=d")
1615 (match_operand 1 "larl_operand" "")
1616 (match_operand:P 2 "register_operand" "=a")])]
1617 ""
1618 {
1619 rtx new_rtx = legitimize_pic_address (operands[1], operands[2]);
1620 emit_move_insn (operands[0], new_rtx);
1621 })
1622
1623 ;
1624 ; movdi instruction pattern(s).
1625 ;
1626
1627 (define_expand "movdi"
1628 [(set (match_operand:DI 0 "general_operand" "")
1629 (match_operand:DI 1 "general_operand" ""))]
1630 ""
1631 {
1632 /* Handle symbolic constants. */
1633 if (TARGET_64BIT
1634 && (SYMBOLIC_CONST (operands[1])
1635 || (GET_CODE (operands[1]) == PLUS
1636 && XEXP (operands[1], 0) == pic_offset_table_rtx
1637 && SYMBOLIC_CONST (XEXP (operands[1], 1)))))
1638 emit_symbolic_move (operands);
1639 })
1640
1641 (define_insn "*movdi_larl"
1642 [(set (match_operand:DI 0 "register_operand" "=d")
1643 (match_operand:DI 1 "larl_operand" "X"))]
1644 "TARGET_64BIT
1645 && !FP_REG_P (operands[0])"
1646 "larl\t%0,%1"
1647 [(set_attr "op_type" "RIL")
1648 (set_attr "type" "larl")
1649 (set_attr "z10prop" "z10_super_A1")])
1650
1651 (define_insn "*movdi_64"
1652 [(set (match_operand:DI 0 "nonimmediate_operand"
1653 "=d, d, d, d, d, d, d, d,f,d,d,d,d,d,T,!*f,!*f,!*f,!R,!T,b,Q,d,t,Q,t,v,v,v,d,v,R")
1654 (match_operand:DI 1 "general_operand"
1655 " K,N0HD0,N1HD0,N2HD0,N3HD0,Os,N0SD0,N1SD0,d,f,L,b,d,T,d, *f, R, T,*f,*f,d,K,t,d,t,Q,K,v,d,v,R,v"))]
1656 "TARGET_ZARCH"
1657 "@
1658 lghi\t%0,%h1
1659 llihh\t%0,%i1
1660 llihl\t%0,%i1
1661 llilh\t%0,%i1
1662 llill\t%0,%i1
1663 lgfi\t%0,%1
1664 llihf\t%0,%k1
1665 llilf\t%0,%k1
1666 ldgr\t%0,%1
1667 lgdr\t%0,%1
1668 lay\t%0,%a1
1669 lgrl\t%0,%1
1670 lgr\t%0,%1
1671 lg\t%0,%1
1672 stg\t%1,%0
1673 ldr\t%0,%1
1674 ld\t%0,%1
1675 ldy\t%0,%1
1676 std\t%1,%0
1677 stdy\t%1,%0
1678 stgrl\t%1,%0
1679 mvghi\t%0,%1
1680 #
1681 #
1682 stam\t%1,%N1,%S0
1683 lam\t%0,%N0,%S1
1684 vleig\t%v0,%h1,0
1685 vlr\t%v0,%v1
1686 vlvgg\t%v0,%1,0
1687 vlgvg\t%0,%v1,0
1688 vleg\t%v0,%1,0
1689 vsteg\t%v1,%0,0"
1690 [(set_attr "op_type" "RI,RI,RI,RI,RI,RIL,RIL,RIL,RRE,RRE,RXY,RIL,RRE,RXY,
1691 RXY,RR,RX,RXY,RX,RXY,RIL,SIL,*,*,RS,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1692 (set_attr "type" "*,*,*,*,*,*,*,*,floaddf,floaddf,la,larl,lr,load,store,
1693 floaddf,floaddf,floaddf,fstoredf,fstoredf,larl,*,*,*,*,
1694 *,*,*,*,*,*,*")
1695 (set_attr "cpu_facility" "*,*,*,*,*,extimm,extimm,extimm,dfp,dfp,longdisp,
1696 z10,*,*,*,*,*,longdisp,*,longdisp,
1697 z10,z10,*,*,*,*,vec,vec,vec,vec,vec,vec")
1698 (set_attr "z10prop" "z10_fwd_A1,
1699 z10_fwd_E1,
1700 z10_fwd_E1,
1701 z10_fwd_E1,
1702 z10_fwd_E1,
1703 z10_fwd_A1,
1704 z10_fwd_E1,
1705 z10_fwd_E1,
1706 *,
1707 *,
1708 z10_fwd_A1,
1709 z10_fwd_A3,
1710 z10_fr_E1,
1711 z10_fwd_A3,
1712 z10_rec,
1713 *,
1714 *,
1715 *,
1716 *,
1717 *,
1718 z10_rec,
1719 z10_super,
1720 *,
1721 *,
1722 *,
1723 *,*,*,*,*,*,*")
1724 ])
1725
1726 (define_split
1727 [(set (match_operand:DI 0 "register_operand" "")
1728 (match_operand:DI 1 "register_operand" ""))]
1729 "TARGET_ZARCH && ACCESS_REG_P (operands[1])"
1730 [(set (match_dup 2) (match_dup 3))
1731 (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
1732 (set (strict_low_part (match_dup 2)) (match_dup 4))]
1733 "operands[2] = gen_lowpart (SImode, operands[0]);
1734 s390_split_access_reg (operands[1], &operands[4], &operands[3]);")
1735
1736 (define_split
1737 [(set (match_operand:DI 0 "register_operand" "")
1738 (match_operand:DI 1 "register_operand" ""))]
1739 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1740 && dead_or_set_p (insn, operands[1])"
1741 [(set (match_dup 3) (match_dup 2))
1742 (set (match_dup 1) (lshiftrt:DI (match_dup 1) (const_int 32)))
1743 (set (match_dup 4) (match_dup 2))]
1744 "operands[2] = gen_lowpart (SImode, operands[1]);
1745 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1746
1747 (define_split
1748 [(set (match_operand:DI 0 "register_operand" "")
1749 (match_operand:DI 1 "register_operand" ""))]
1750 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1751 && !dead_or_set_p (insn, operands[1])"
1752 [(set (match_dup 3) (match_dup 2))
1753 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))
1754 (set (match_dup 4) (match_dup 2))
1755 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))]
1756 "operands[2] = gen_lowpart (SImode, operands[1]);
1757 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1758
1759 (define_insn "*movdi_31"
1760 [(set (match_operand:DI 0 "nonimmediate_operand"
1761 "=d,d,Q,S,d ,o,!*f,!*f,!*f,!R,!T,d")
1762 (match_operand:DI 1 "general_operand"
1763 " Q,S,d,d,dPT,d, *f, R, T,*f,*f,b"))]
1764 "!TARGET_ZARCH"
1765 "@
1766 lm\t%0,%N0,%S1
1767 lmy\t%0,%N0,%S1
1768 stm\t%1,%N1,%S0
1769 stmy\t%1,%N1,%S0
1770 #
1771 #
1772 ldr\t%0,%1
1773 ld\t%0,%1
1774 ldy\t%0,%1
1775 std\t%1,%0
1776 stdy\t%1,%0
1777 #"
1778 [(set_attr "op_type" "RS,RSY,RS,RSY,*,*,RR,RX,RXY,RX,RXY,*")
1779 (set_attr "type" "lm,lm,stm,stm,*,*,floaddf,floaddf,floaddf,fstoredf,fstoredf,*")
1780 (set_attr "cpu_facility" "*,longdisp,*,longdisp,*,*,*,*,longdisp,*,longdisp,z10")])
1781
1782 ; For a load from a symbol ref we can use one of the target registers
1783 ; together with larl to load the address.
1784 (define_split
1785 [(set (match_operand:DI 0 "register_operand" "")
1786 (match_operand:DI 1 "memory_operand" ""))]
1787 "!TARGET_ZARCH && reload_completed && TARGET_Z10
1788 && larl_operand (XEXP (operands[1], 0), SImode)"
1789 [(set (match_dup 2) (match_dup 3))
1790 (set (match_dup 0) (match_dup 1))]
1791 {
1792 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1793 operands[3] = XEXP (operands[1], 0);
1794 operands[1] = replace_equiv_address (operands[1], operands[2]);
1795 })
1796
1797 (define_split
1798 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1799 (match_operand:DI 1 "general_operand" ""))]
1800 "!TARGET_ZARCH && reload_completed
1801 && s390_split_ok_p (operands[0], operands[1], DImode, 0)"
1802 [(set (match_dup 2) (match_dup 4))
1803 (set (match_dup 3) (match_dup 5))]
1804 {
1805 operands[2] = operand_subword (operands[0], 0, 0, DImode);
1806 operands[3] = operand_subword (operands[0], 1, 0, DImode);
1807 operands[4] = operand_subword (operands[1], 0, 0, DImode);
1808 operands[5] = operand_subword (operands[1], 1, 0, DImode);
1809 })
1810
1811 (define_split
1812 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1813 (match_operand:DI 1 "general_operand" ""))]
1814 "!TARGET_ZARCH && reload_completed
1815 && s390_split_ok_p (operands[0], operands[1], DImode, 1)"
1816 [(set (match_dup 2) (match_dup 4))
1817 (set (match_dup 3) (match_dup 5))]
1818 {
1819 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1820 operands[3] = operand_subword (operands[0], 0, 0, DImode);
1821 operands[4] = operand_subword (operands[1], 1, 0, DImode);
1822 operands[5] = operand_subword (operands[1], 0, 0, DImode);
1823 })
1824
1825 (define_split
1826 [(set (match_operand:DI 0 "register_operand" "")
1827 (match_operand:DI 1 "memory_operand" ""))]
1828 "!TARGET_ZARCH && reload_completed
1829 && !FP_REG_P (operands[0])
1830 && !s_operand (operands[1], VOIDmode)"
1831 [(set (match_dup 0) (match_dup 1))]
1832 {
1833 rtx addr = operand_subword (operands[0], 1, 0, DImode);
1834 s390_load_address (addr, XEXP (operands[1], 0));
1835 operands[1] = replace_equiv_address (operands[1], addr);
1836 })
1837
1838 (define_peephole2
1839 [(set (match_operand:DI 0 "register_operand" "")
1840 (mem:DI (match_operand 1 "address_operand" "")))]
1841 "TARGET_ZARCH
1842 && !FP_REG_P (operands[0])
1843 && GET_CODE (operands[1]) == SYMBOL_REF
1844 && CONSTANT_POOL_ADDRESS_P (operands[1])
1845 && get_pool_mode (operands[1]) == DImode
1846 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1847 [(set (match_dup 0) (match_dup 2))]
1848 "operands[2] = get_pool_constant (operands[1]);")
1849
1850 (define_insn "*la_64"
1851 [(set (match_operand:DI 0 "register_operand" "=d,d")
1852 (match_operand:QI 1 "address_operand" "ZR,ZT"))]
1853 "TARGET_64BIT"
1854 "@
1855 la\t%0,%a1
1856 lay\t%0,%a1"
1857 [(set_attr "op_type" "RX,RXY")
1858 (set_attr "type" "la")
1859 (set_attr "cpu_facility" "*,longdisp")
1860 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
1861
1862 (define_peephole2
1863 [(parallel
1864 [(set (match_operand:DI 0 "register_operand" "")
1865 (match_operand:QI 1 "address_operand" ""))
1866 (clobber (reg:CC CC_REGNUM))])]
1867 "TARGET_64BIT
1868 && preferred_la_operand_p (operands[1], const0_rtx)"
1869 [(set (match_dup 0) (match_dup 1))]
1870 "")
1871
1872 (define_peephole2
1873 [(set (match_operand:DI 0 "register_operand" "")
1874 (match_operand:DI 1 "register_operand" ""))
1875 (parallel
1876 [(set (match_dup 0)
1877 (plus:DI (match_dup 0)
1878 (match_operand:DI 2 "nonmemory_operand" "")))
1879 (clobber (reg:CC CC_REGNUM))])]
1880 "TARGET_64BIT
1881 && !reg_overlap_mentioned_p (operands[0], operands[2])
1882 && preferred_la_operand_p (operands[1], operands[2])"
1883 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
1884 "")
1885
1886 ;
1887 ; movsi instruction pattern(s).
1888 ;
1889
1890 (define_expand "movsi"
1891 [(set (match_operand:SI 0 "general_operand" "")
1892 (match_operand:SI 1 "general_operand" ""))]
1893 ""
1894 {
1895 /* Handle symbolic constants. */
1896 if (!TARGET_64BIT
1897 && (SYMBOLIC_CONST (operands[1])
1898 || (GET_CODE (operands[1]) == PLUS
1899 && XEXP (operands[1], 0) == pic_offset_table_rtx
1900 && SYMBOLIC_CONST (XEXP(operands[1], 1)))))
1901 emit_symbolic_move (operands);
1902 })
1903
1904 (define_insn "*movsi_larl"
1905 [(set (match_operand:SI 0 "register_operand" "=d")
1906 (match_operand:SI 1 "larl_operand" "X"))]
1907 "!TARGET_64BIT && TARGET_CPU_ZARCH
1908 && !FP_REG_P (operands[0])"
1909 "larl\t%0,%1"
1910 [(set_attr "op_type" "RIL")
1911 (set_attr "type" "larl")
1912 (set_attr "z10prop" "z10_fwd_A1")])
1913
1914 (define_insn "*movsi_zarch"
1915 [(set (match_operand:SI 0 "nonimmediate_operand"
1916 "=d, d, d, d,d,d,d,d,d,R,T,!*f,!*f,!*f,!*f,!*f,!R,!T,d,t,Q,b,Q,t,v,v,v,d,v,R")
1917 (match_operand:SI 1 "general_operand"
1918 " K,N0HS0,N1HS0,Os,L,b,d,R,T,d,d, *f, *f, R, R, T,*f,*f,t,d,t,d,K,Q,K,v,d,v,R,v"))]
1919 "TARGET_ZARCH"
1920 "@
1921 lhi\t%0,%h1
1922 llilh\t%0,%i1
1923 llill\t%0,%i1
1924 iilf\t%0,%o1
1925 lay\t%0,%a1
1926 lrl\t%0,%1
1927 lr\t%0,%1
1928 l\t%0,%1
1929 ly\t%0,%1
1930 st\t%1,%0
1931 sty\t%1,%0
1932 ldr\t%0,%1
1933 ler\t%0,%1
1934 lde\t%0,%1
1935 le\t%0,%1
1936 ley\t%0,%1
1937 ste\t%1,%0
1938 stey\t%1,%0
1939 ear\t%0,%1
1940 sar\t%0,%1
1941 stam\t%1,%1,%S0
1942 strl\t%1,%0
1943 mvhi\t%0,%1
1944 lam\t%0,%0,%S1
1945 vleif\t%v0,%h1,0
1946 vlr\t%v0,%v1
1947 vlvgf\t%v0,%1,0
1948 vlgvf\t%0,%v1,0
1949 vlef\t%v0,%1,0
1950 vstef\t%v1,%0,0"
1951 [(set_attr "op_type" "RI,RI,RI,RIL,RXY,RIL,RR,RX,RXY,RX,RXY,
1952 RR,RR,RXE,RX,RXY,RX,RXY,RRE,RRE,RS,RIL,SIL,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1953 (set_attr "type" "*,
1954 *,
1955 *,
1956 *,
1957 la,
1958 larl,
1959 lr,
1960 load,
1961 load,
1962 store,
1963 store,
1964 floadsf,
1965 floadsf,
1966 floadsf,
1967 floadsf,
1968 floadsf,
1969 fstoresf,
1970 fstoresf,
1971 *,
1972 *,
1973 *,
1974 larl,
1975 *,
1976 *,*,*,*,*,*,*")
1977 (set_attr "cpu_facility" "*,*,*,extimm,longdisp,z10,*,*,longdisp,*,longdisp,
1978 vec,*,vec,*,longdisp,*,longdisp,*,*,*,z10,z10,*,vec,vec,vec,vec,vec,vec")
1979 (set_attr "z10prop" "z10_fwd_A1,
1980 z10_fwd_E1,
1981 z10_fwd_E1,
1982 z10_fwd_A1,
1983 z10_fwd_A1,
1984 z10_fwd_A3,
1985 z10_fr_E1,
1986 z10_fwd_A3,
1987 z10_fwd_A3,
1988 z10_rec,
1989 z10_rec,
1990 *,
1991 *,
1992 *,
1993 *,
1994 *,
1995 *,
1996 *,
1997 z10_super_E1,
1998 z10_super,
1999 *,
2000 z10_rec,
2001 z10_super,
2002 *,*,*,*,*,*,*")])
2003
2004 (define_insn "*movsi_esa"
2005 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,R,!*f,!*f,!*f,!*f,!R,d,t,Q,t")
2006 (match_operand:SI 1 "general_operand" "K,d,R,d, *f, *f, R, R,*f,t,d,t,Q"))]
2007 "!TARGET_ZARCH"
2008 "@
2009 lhi\t%0,%h1
2010 lr\t%0,%1
2011 l\t%0,%1
2012 st\t%1,%0
2013 ldr\t%0,%1
2014 ler\t%0,%1
2015 lde\t%0,%1
2016 le\t%0,%1
2017 ste\t%1,%0
2018 ear\t%0,%1
2019 sar\t%0,%1
2020 stam\t%1,%1,%S0
2021 lam\t%0,%0,%S1"
2022 [(set_attr "op_type" "RI,RR,RX,RX,RR,RR,RXE,RX,RX,RRE,RRE,RS,RS")
2023 (set_attr "type" "*,lr,load,store,floadsf,floadsf,floadsf,floadsf,fstoresf,*,*,*,*")
2024 (set_attr "z10prop" "z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_rec,*,*,*,*,*,z10_super_E1,
2025 z10_super,*,*")
2026 (set_attr "cpu_facility" "*,*,*,*,vec,*,vec,*,*,*,*,*,*")
2027 ])
2028
2029 (define_peephole2
2030 [(set (match_operand:SI 0 "register_operand" "")
2031 (mem:SI (match_operand 1 "address_operand" "")))]
2032 "!FP_REG_P (operands[0])
2033 && GET_CODE (operands[1]) == SYMBOL_REF
2034 && CONSTANT_POOL_ADDRESS_P (operands[1])
2035 && get_pool_mode (operands[1]) == SImode
2036 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
2037 [(set (match_dup 0) (match_dup 2))]
2038 "operands[2] = get_pool_constant (operands[1]);")
2039
2040 (define_insn "*la_31"
2041 [(set (match_operand:SI 0 "register_operand" "=d,d")
2042 (match_operand:QI 1 "address_operand" "ZR,ZT"))]
2043 "!TARGET_64BIT && legitimate_la_operand_p (operands[1])"
2044 "@
2045 la\t%0,%a1
2046 lay\t%0,%a1"
2047 [(set_attr "op_type" "RX,RXY")
2048 (set_attr "type" "la")
2049 (set_attr "cpu_facility" "*,longdisp")
2050 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2051
2052 (define_peephole2
2053 [(parallel
2054 [(set (match_operand:SI 0 "register_operand" "")
2055 (match_operand:QI 1 "address_operand" ""))
2056 (clobber (reg:CC CC_REGNUM))])]
2057 "!TARGET_64BIT
2058 && preferred_la_operand_p (operands[1], const0_rtx)"
2059 [(set (match_dup 0) (match_dup 1))]
2060 "")
2061
2062 (define_peephole2
2063 [(set (match_operand:SI 0 "register_operand" "")
2064 (match_operand:SI 1 "register_operand" ""))
2065 (parallel
2066 [(set (match_dup 0)
2067 (plus:SI (match_dup 0)
2068 (match_operand:SI 2 "nonmemory_operand" "")))
2069 (clobber (reg:CC CC_REGNUM))])]
2070 "!TARGET_64BIT
2071 && !reg_overlap_mentioned_p (operands[0], operands[2])
2072 && preferred_la_operand_p (operands[1], operands[2])"
2073 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2074 "")
2075
2076 (define_insn "*la_31_and"
2077 [(set (match_operand:SI 0 "register_operand" "=d,d")
2078 (and:SI (match_operand:QI 1 "address_operand" "ZR,ZT")
2079 (const_int 2147483647)))]
2080 "!TARGET_64BIT"
2081 "@
2082 la\t%0,%a1
2083 lay\t%0,%a1"
2084 [(set_attr "op_type" "RX,RXY")
2085 (set_attr "type" "la")
2086 (set_attr "cpu_facility" "*,longdisp")
2087 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2088
2089 (define_insn_and_split "*la_31_and_cc"
2090 [(set (match_operand:SI 0 "register_operand" "=d")
2091 (and:SI (match_operand:QI 1 "address_operand" "p")
2092 (const_int 2147483647)))
2093 (clobber (reg:CC CC_REGNUM))]
2094 "!TARGET_64BIT"
2095 "#"
2096 "&& reload_completed"
2097 [(set (match_dup 0)
2098 (and:SI (match_dup 1) (const_int 2147483647)))]
2099 ""
2100 [(set_attr "op_type" "RX")
2101 (set_attr "type" "la")])
2102
2103 (define_insn "force_la_31"
2104 [(set (match_operand:SI 0 "register_operand" "=d,d")
2105 (match_operand:QI 1 "address_operand" "ZR,ZT"))
2106 (use (const_int 0))]
2107 "!TARGET_64BIT"
2108 "@
2109 la\t%0,%a1
2110 lay\t%0,%a1"
2111 [(set_attr "op_type" "RX")
2112 (set_attr "type" "la")
2113 (set_attr "cpu_facility" "*,longdisp")
2114 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2115
2116 ;
2117 ; movhi instruction pattern(s).
2118 ;
2119
2120 (define_expand "movhi"
2121 [(set (match_operand:HI 0 "nonimmediate_operand" "")
2122 (match_operand:HI 1 "general_operand" ""))]
2123 ""
2124 {
2125 /* Make it explicit that loading a register from memory
2126 always sign-extends (at least) to SImode. */
2127 if (optimize && can_create_pseudo_p ()
2128 && register_operand (operands[0], VOIDmode)
2129 && GET_CODE (operands[1]) == MEM)
2130 {
2131 rtx tmp = gen_reg_rtx (SImode);
2132 rtx ext = gen_rtx_SIGN_EXTEND (SImode, operands[1]);
2133 emit_insn (gen_rtx_SET (tmp, ext));
2134 operands[1] = gen_lowpart (HImode, tmp);
2135 }
2136 })
2137
2138 (define_insn "*movhi"
2139 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,d,R,T,b,Q,v,v,v,d,v,R")
2140 (match_operand:HI 1 "general_operand" " d,n,R,T,b,d,d,d,K,K,v,d,v,R,v"))]
2141 ""
2142 "@
2143 lr\t%0,%1
2144 lhi\t%0,%h1
2145 lh\t%0,%1
2146 lhy\t%0,%1
2147 lhrl\t%0,%1
2148 sth\t%1,%0
2149 sthy\t%1,%0
2150 sthrl\t%1,%0
2151 mvhhi\t%0,%1
2152 vleih\t%v0,%h1,0
2153 vlr\t%v0,%v1
2154 vlvgh\t%v0,%1,0
2155 vlgvh\t%0,%v1,0
2156 vleh\t%v0,%1,0
2157 vsteh\t%v1,%0,0"
2158 [(set_attr "op_type" "RR,RI,RX,RXY,RIL,RX,RXY,RIL,SIL,VRI,VRR,VRS,VRS,VRX,VRX")
2159 (set_attr "type" "lr,*,*,*,larl,store,store,store,*,*,*,*,*,*,*")
2160 (set_attr "cpu_facility" "*,*,*,longdisp,z10,*,longdisp,z10,z10,vec,vec,vec,vec,vec,vec")
2161 (set_attr "z10prop" "z10_fr_E1,
2162 z10_fwd_A1,
2163 z10_super_E1,
2164 z10_super_E1,
2165 z10_super_E1,
2166 z10_rec,
2167 z10_rec,
2168 z10_rec,
2169 z10_super,*,*,*,*,*,*")])
2170
2171 (define_peephole2
2172 [(set (match_operand:HI 0 "register_operand" "")
2173 (mem:HI (match_operand 1 "address_operand" "")))]
2174 "GET_CODE (operands[1]) == SYMBOL_REF
2175 && CONSTANT_POOL_ADDRESS_P (operands[1])
2176 && get_pool_mode (operands[1]) == HImode
2177 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2178 [(set (match_dup 0) (match_dup 2))]
2179 "operands[2] = get_pool_constant (operands[1]);")
2180
2181 ;
2182 ; movqi instruction pattern(s).
2183 ;
2184
2185 (define_expand "movqi"
2186 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2187 (match_operand:QI 1 "general_operand" ""))]
2188 ""
2189 {
2190 /* On z/Architecture, zero-extending from memory to register
2191 is just as fast as a QImode load. */
2192 if (TARGET_ZARCH && optimize && can_create_pseudo_p ()
2193 && register_operand (operands[0], VOIDmode)
2194 && GET_CODE (operands[1]) == MEM)
2195 {
2196 rtx tmp = gen_reg_rtx (DImode);
2197 rtx ext = gen_rtx_ZERO_EXTEND (DImode, operands[1]);
2198 emit_insn (gen_rtx_SET (tmp, ext));
2199 operands[1] = gen_lowpart (QImode, tmp);
2200 }
2201 })
2202
2203 (define_insn "*movqi"
2204 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,T,Q,S,?Q,v,v,v,d,v,R")
2205 (match_operand:QI 1 "general_operand" " d,n,R,T,d,d,n,n,?Q,K,v,d,v,R,v"))]
2206 ""
2207 "@
2208 lr\t%0,%1
2209 lhi\t%0,%b1
2210 ic\t%0,%1
2211 icy\t%0,%1
2212 stc\t%1,%0
2213 stcy\t%1,%0
2214 mvi\t%S0,%b1
2215 mviy\t%S0,%b1
2216 #
2217 vleib\t%v0,%b1,0
2218 vlr\t%v0,%v1
2219 vlvgb\t%v0,%1,0
2220 vlgvb\t%0,%v1,0
2221 vleb\t%v0,%1,0
2222 vsteb\t%v1,%0,0"
2223 [(set_attr "op_type" "RR,RI,RX,RXY,RX,RXY,SI,SIY,SS,VRI,VRR,VRS,VRS,VRX,VRX")
2224 (set_attr "type" "lr,*,*,*,store,store,store,store,*,*,*,*,*,*,*")
2225 (set_attr "cpu_facility" "*,*,*,longdisp,*,longdisp,*,longdisp,*,vec,vec,vec,vec,vec,vec")
2226 (set_attr "z10prop" "z10_fr_E1,
2227 z10_fwd_A1,
2228 z10_super_E1,
2229 z10_super_E1,
2230 z10_rec,
2231 z10_rec,
2232 z10_super,
2233 z10_super,
2234 *,*,*,*,*,*,*")])
2235
2236 (define_peephole2
2237 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2238 (mem:QI (match_operand 1 "address_operand" "")))]
2239 "GET_CODE (operands[1]) == SYMBOL_REF
2240 && CONSTANT_POOL_ADDRESS_P (operands[1])
2241 && get_pool_mode (operands[1]) == QImode
2242 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2243 [(set (match_dup 0) (match_dup 2))]
2244 "operands[2] = get_pool_constant (operands[1]);")
2245
2246 ;
2247 ; movstrictqi instruction pattern(s).
2248 ;
2249
2250 (define_insn "*movstrictqi"
2251 [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d,d"))
2252 (match_operand:QI 1 "memory_operand" "R,T"))]
2253 ""
2254 "@
2255 ic\t%0,%1
2256 icy\t%0,%1"
2257 [(set_attr "op_type" "RX,RXY")
2258 (set_attr "cpu_facility" "*,longdisp")
2259 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2260
2261 ;
2262 ; movstricthi instruction pattern(s).
2263 ;
2264
2265 (define_insn "*movstricthi"
2266 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d,d"))
2267 (match_operand:HI 1 "memory_operand" "Q,S"))
2268 (clobber (reg:CC CC_REGNUM))]
2269 ""
2270 "@
2271 icm\t%0,3,%S1
2272 icmy\t%0,3,%S1"
2273 [(set_attr "op_type" "RS,RSY")
2274 (set_attr "cpu_facility" "*,longdisp")
2275 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2276
2277 ;
2278 ; movstrictsi instruction pattern(s).
2279 ;
2280
2281 (define_insn "movstrictsi"
2282 [(set (strict_low_part (match_operand:SI 0 "register_operand" "+d,d,d,d"))
2283 (match_operand:SI 1 "general_operand" "d,R,T,t"))]
2284 "TARGET_ZARCH"
2285 "@
2286 lr\t%0,%1
2287 l\t%0,%1
2288 ly\t%0,%1
2289 ear\t%0,%1"
2290 [(set_attr "op_type" "RR,RX,RXY,RRE")
2291 (set_attr "type" "lr,load,load,*")
2292 (set_attr "cpu_facility" "*,*,longdisp,*")
2293 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_super_E1")])
2294
2295 ;
2296 ; mov(tf|td) instruction pattern(s).
2297 ;
2298
2299 (define_expand "mov<mode>"
2300 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2301 (match_operand:TD_TF 1 "general_operand" ""))]
2302 ""
2303 "")
2304
2305 (define_insn "*mov<mode>_64"
2306 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o,d,S, d,o")
2307 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,S,d,dT,d"))]
2308 "TARGET_ZARCH"
2309 "@
2310 lzxr\t%0
2311 lxr\t%0,%1
2312 #
2313 #
2314 lmg\t%0,%N0,%S1
2315 stmg\t%1,%N1,%S0
2316 #
2317 #"
2318 [(set_attr "op_type" "RRE,RRE,*,*,RSY,RSY,*,*")
2319 (set_attr "type" "fsimptf,fsimptf,*,*,lm,stm,*,*")
2320 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*")])
2321
2322 (define_insn "*mov<mode>_31"
2323 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o")
2324 (match_operand:TD_TF 1 "general_operand" " G,f,o,f"))]
2325 "!TARGET_ZARCH"
2326 "@
2327 lzxr\t%0
2328 lxr\t%0,%1
2329 #
2330 #"
2331 [(set_attr "op_type" "RRE,RRE,*,*")
2332 (set_attr "type" "fsimptf,fsimptf,*,*")
2333 (set_attr "cpu_facility" "z196,*,*,*")])
2334
2335 ; TFmode in GPRs splitters
2336
2337 (define_split
2338 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2339 (match_operand:TD_TF 1 "general_operand" ""))]
2340 "TARGET_ZARCH && reload_completed
2341 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2342 [(set (match_dup 2) (match_dup 4))
2343 (set (match_dup 3) (match_dup 5))]
2344 {
2345 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2346 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2347 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2348 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2349 })
2350
2351 (define_split
2352 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2353 (match_operand:TD_TF 1 "general_operand" ""))]
2354 "TARGET_ZARCH && reload_completed
2355 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2356 [(set (match_dup 2) (match_dup 4))
2357 (set (match_dup 3) (match_dup 5))]
2358 {
2359 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2360 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2361 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2362 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2363 })
2364
2365 (define_split
2366 [(set (match_operand:TD_TF 0 "register_operand" "")
2367 (match_operand:TD_TF 1 "memory_operand" ""))]
2368 "TARGET_ZARCH && reload_completed
2369 && GENERAL_REG_P (operands[0])
2370 && !s_operand (operands[1], VOIDmode)"
2371 [(set (match_dup 0) (match_dup 1))]
2372 {
2373 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2374 addr = gen_lowpart (Pmode, addr);
2375 s390_load_address (addr, XEXP (operands[1], 0));
2376 operands[1] = replace_equiv_address (operands[1], addr);
2377 })
2378
2379 ; TFmode in BFPs splitters
2380
2381 (define_split
2382 [(set (match_operand:TD_TF 0 "register_operand" "")
2383 (match_operand:TD_TF 1 "memory_operand" ""))]
2384 "reload_completed && offsettable_memref_p (operands[1])
2385 && FP_REG_P (operands[0])"
2386 [(set (match_dup 2) (match_dup 4))
2387 (set (match_dup 3) (match_dup 5))]
2388 {
2389 operands[2] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2390 <MODE>mode, 0);
2391 operands[3] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2392 <MODE>mode, 8);
2393 operands[4] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 0);
2394 operands[5] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 8);
2395 })
2396
2397 (define_split
2398 [(set (match_operand:TD_TF 0 "memory_operand" "")
2399 (match_operand:TD_TF 1 "register_operand" ""))]
2400 "reload_completed && offsettable_memref_p (operands[0])
2401 && FP_REG_P (operands[1])"
2402 [(set (match_dup 2) (match_dup 4))
2403 (set (match_dup 3) (match_dup 5))]
2404 {
2405 operands[2] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 0);
2406 operands[3] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 8);
2407 operands[4] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2408 <MODE>mode, 0);
2409 operands[5] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2410 <MODE>mode, 8);
2411 })
2412
2413 ;
2414 ; mov(df|dd) instruction pattern(s).
2415 ;
2416
2417 (define_expand "mov<mode>"
2418 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2419 (match_operand:DD_DF 1 "general_operand" ""))]
2420 ""
2421 "")
2422
2423 (define_insn "*mov<mode>_64dfp"
2424 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2425 "=f,f,f,d,f,f,R,T,d,d,d,d,b,T,v,v,d,v,R")
2426 (match_operand:DD_DF 1 "general_operand"
2427 " G,f,d,f,R,T,f,f,G,d,b,T,d,d,v,d,v,R,v"))]
2428 "TARGET_DFP"
2429 "@
2430 lzdr\t%0
2431 ldr\t%0,%1
2432 ldgr\t%0,%1
2433 lgdr\t%0,%1
2434 ld\t%0,%1
2435 ldy\t%0,%1
2436 std\t%1,%0
2437 stdy\t%1,%0
2438 lghi\t%0,0
2439 lgr\t%0,%1
2440 lgrl\t%0,%1
2441 lg\t%0,%1
2442 stgrl\t%1,%0
2443 stg\t%1,%0
2444 vlr\t%v0,%v1
2445 vlvgg\t%v0,%1,0
2446 vlgvg\t%0,%v1,0
2447 vleg\t%0,%1,0
2448 vsteg\t%1,%0,0"
2449 [(set_attr "op_type" "RRE,RR,RRE,RRE,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRS,VRS,VRX,VRX")
2450 (set_attr "type" "fsimpdf,floaddf,floaddf,floaddf,floaddf,floaddf,
2451 fstoredf,fstoredf,*,lr,load,load,store,store,*,*,*,load,store")
2452 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*,*,*")
2453 (set_attr "cpu_facility" "z196,*,*,*,*,longdisp,*,longdisp,*,*,z10,*,z10,*,vec,vec,vec,vec,vec")])
2454
2455 (define_insn "*mov<mode>_64"
2456 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "=f,f,f,f,R,T,d,d,d,d,b,T,v,v,R")
2457 (match_operand:DD_DF 1 "general_operand" " G,f,R,T,f,f,G,d,b,T,d,d,v,R,v"))]
2458 "TARGET_ZARCH"
2459 "@
2460 lzdr\t%0
2461 ldr\t%0,%1
2462 ld\t%0,%1
2463 ldy\t%0,%1
2464 std\t%1,%0
2465 stdy\t%1,%0
2466 lghi\t%0,0
2467 lgr\t%0,%1
2468 lgrl\t%0,%1
2469 lg\t%0,%1
2470 stgrl\t%1,%0
2471 stg\t%1,%0
2472 vlr\t%v0,%v1
2473 vleg\t%v0,%1,0
2474 vsteg\t%v1,%0,0"
2475 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRX,VRX")
2476 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2477 fstore<mode>,fstore<mode>,*,lr,load,load,store,store,*,load,store")
2478 (set_attr "z10prop" "*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*")
2479 (set_attr "cpu_facility" "z196,*,*,longdisp,*,longdisp,*,*,z10,*,z10,*,vec,vec,vec")])
2480
2481 (define_insn "*mov<mode>_31"
2482 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2483 "=f,f,f,f,R,T,d,d,Q,S, d,o")
2484 (match_operand:DD_DF 1 "general_operand"
2485 " G,f,R,T,f,f,Q,S,d,d,dPT,d"))]
2486 "!TARGET_ZARCH"
2487 "@
2488 lzdr\t%0
2489 ldr\t%0,%1
2490 ld\t%0,%1
2491 ldy\t%0,%1
2492 std\t%1,%0
2493 stdy\t%1,%0
2494 lm\t%0,%N0,%S1
2495 lmy\t%0,%N0,%S1
2496 stm\t%1,%N1,%S0
2497 stmy\t%1,%N1,%S0
2498 #
2499 #"
2500 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RS,RSY,RS,RSY,*,*")
2501 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2502 fstore<mode>,fstore<mode>,lm,lm,stm,stm,*,*")
2503 (set_attr "cpu_facility" "z196,*,*,longdisp,*,longdisp,*,longdisp,*,longdisp,*,*")])
2504
2505 (define_split
2506 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2507 (match_operand:DD_DF 1 "general_operand" ""))]
2508 "!TARGET_ZARCH && reload_completed
2509 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2510 [(set (match_dup 2) (match_dup 4))
2511 (set (match_dup 3) (match_dup 5))]
2512 {
2513 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2514 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2515 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2516 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2517 })
2518
2519 (define_split
2520 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2521 (match_operand:DD_DF 1 "general_operand" ""))]
2522 "!TARGET_ZARCH && reload_completed
2523 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2524 [(set (match_dup 2) (match_dup 4))
2525 (set (match_dup 3) (match_dup 5))]
2526 {
2527 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2528 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2529 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2530 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2531 })
2532
2533 (define_split
2534 [(set (match_operand:DD_DF 0 "register_operand" "")
2535 (match_operand:DD_DF 1 "memory_operand" ""))]
2536 "!TARGET_ZARCH && reload_completed
2537 && !FP_REG_P (operands[0])
2538 && !s_operand (operands[1], VOIDmode)"
2539 [(set (match_dup 0) (match_dup 1))]
2540 {
2541 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2542 s390_load_address (addr, XEXP (operands[1], 0));
2543 operands[1] = replace_equiv_address (operands[1], addr);
2544 })
2545
2546 ;
2547 ; mov(sf|sd) instruction pattern(s).
2548 ;
2549
2550 (define_insn "mov<mode>"
2551 [(set (match_operand:SD_SF 0 "nonimmediate_operand"
2552 "=f,f,f,f,f,f,R,T,d,d,d,d,d,b,R,T,v,v,v,d,v,R")
2553 (match_operand:SD_SF 1 "general_operand"
2554 " G,f,f,R,R,T,f,f,G,d,b,R,T,d,d,d,v,G,d,v,R,v"))]
2555 ""
2556 "@
2557 lzer\t%0
2558 ldr\t%0,%1
2559 ler\t%0,%1
2560 lde\t%0,%1
2561 le\t%0,%1
2562 ley\t%0,%1
2563 ste\t%1,%0
2564 stey\t%1,%0
2565 lhi\t%0,0
2566 lr\t%0,%1
2567 lrl\t%0,%1
2568 l\t%0,%1
2569 ly\t%0,%1
2570 strl\t%1,%0
2571 st\t%1,%0
2572 sty\t%1,%0
2573 vlr\t%v0,%v1
2574 vleif\t%v0,0
2575 vlvgf\t%v0,%1,0
2576 vlgvf\t%0,%v1,0
2577 vleg\t%0,%1,0
2578 vsteg\t%1,%0,0"
2579 [(set_attr "op_type" "RRE,RR,RR,RXE,RX,RXY,RX,RXY,RI,RR,RIL,RX,RXY,RIL,RX,RXY,VRR,VRI,VRS,VRS,VRX,VRX")
2580 (set_attr "type" "fsimpsf,fsimpsf,fload<mode>,fload<mode>,fload<mode>,fload<mode>,
2581 fstore<mode>,fstore<mode>,*,lr,load,load,load,store,store,store,*,*,*,*,load,store")
2582 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,z10_rec,*,*,*,*,*,*")
2583 (set_attr "cpu_facility" "z196,vec,*,vec,*,longdisp,*,longdisp,*,*,z10,*,longdisp,z10,*,longdisp,vec,vec,vec,vec,vec,vec")])
2584
2585 ;
2586 ; movcc instruction pattern
2587 ;
2588
2589 (define_insn "movcc"
2590 [(set (match_operand:CC 0 "nonimmediate_operand" "=d,c,d,d,d,R,T")
2591 (match_operand:CC 1 "nonimmediate_operand" " d,d,c,R,T,d,d"))]
2592 ""
2593 "@
2594 lr\t%0,%1
2595 tmh\t%1,12288
2596 ipm\t%0
2597 l\t%0,%1
2598 ly\t%0,%1
2599 st\t%1,%0
2600 sty\t%1,%0"
2601 [(set_attr "op_type" "RR,RI,RRE,RX,RXY,RX,RXY")
2602 (set_attr "type" "lr,*,*,load,load,store,store")
2603 (set_attr "cpu_facility" "*,*,*,*,longdisp,*,longdisp")
2604 (set_attr "z10prop" "z10_fr_E1,z10_super,*,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec")
2605 (set_attr "z196prop" "*,*,z196_ends,*,*,*,*")])
2606
2607 ;
2608 ; Block move (MVC) patterns.
2609 ;
2610
2611 (define_insn "*mvc"
2612 [(set (match_operand:BLK 0 "memory_operand" "=Q")
2613 (match_operand:BLK 1 "memory_operand" "Q"))
2614 (use (match_operand 2 "const_int_operand" "n"))]
2615 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
2616 "mvc\t%O0(%2,%R0),%S1"
2617 [(set_attr "op_type" "SS")])
2618
2619 ; This splitter converts a QI to QI mode copy into a BLK mode copy in
2620 ; order to have it implemented with mvc.
2621
2622 (define_split
2623 [(set (match_operand:QI 0 "memory_operand" "")
2624 (match_operand:QI 1 "memory_operand" ""))]
2625 "reload_completed"
2626 [(parallel
2627 [(set (match_dup 0) (match_dup 1))
2628 (use (const_int 1))])]
2629 {
2630 operands[0] = adjust_address (operands[0], BLKmode, 0);
2631 operands[1] = adjust_address (operands[1], BLKmode, 0);
2632 })
2633
2634
2635 (define_peephole2
2636 [(parallel
2637 [(set (match_operand:BLK 0 "memory_operand" "")
2638 (match_operand:BLK 1 "memory_operand" ""))
2639 (use (match_operand 2 "const_int_operand" ""))])
2640 (parallel
2641 [(set (match_operand:BLK 3 "memory_operand" "")
2642 (match_operand:BLK 4 "memory_operand" ""))
2643 (use (match_operand 5 "const_int_operand" ""))])]
2644 "s390_offset_p (operands[0], operands[3], operands[2])
2645 && s390_offset_p (operands[1], operands[4], operands[2])
2646 && !s390_overlap_p (operands[0], operands[1],
2647 INTVAL (operands[2]) + INTVAL (operands[5]))
2648 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
2649 [(parallel
2650 [(set (match_dup 6) (match_dup 7))
2651 (use (match_dup 8))])]
2652 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
2653 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
2654 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
2655
2656
2657 ;
2658 ; load_multiple pattern(s).
2659 ;
2660 ; ??? Due to reload problems with replacing registers inside match_parallel
2661 ; we currently support load_multiple/store_multiple only after reload.
2662 ;
2663
2664 (define_expand "load_multiple"
2665 [(match_par_dup 3 [(set (match_operand 0 "" "")
2666 (match_operand 1 "" ""))
2667 (use (match_operand 2 "" ""))])]
2668 "reload_completed"
2669 {
2670 machine_mode mode;
2671 int regno;
2672 int count;
2673 rtx from;
2674 int i, off;
2675
2676 /* Support only loading a constant number of fixed-point registers from
2677 memory and only bother with this if more than two */
2678 if (GET_CODE (operands[2]) != CONST_INT
2679 || INTVAL (operands[2]) < 2
2680 || INTVAL (operands[2]) > 16
2681 || GET_CODE (operands[1]) != MEM
2682 || GET_CODE (operands[0]) != REG
2683 || REGNO (operands[0]) >= 16)
2684 FAIL;
2685
2686 count = INTVAL (operands[2]);
2687 regno = REGNO (operands[0]);
2688 mode = GET_MODE (operands[0]);
2689 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2690 FAIL;
2691
2692 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2693 if (!can_create_pseudo_p ())
2694 {
2695 if (GET_CODE (XEXP (operands[1], 0)) == REG)
2696 {
2697 from = XEXP (operands[1], 0);
2698 off = 0;
2699 }
2700 else if (GET_CODE (XEXP (operands[1], 0)) == PLUS
2701 && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == REG
2702 && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == CONST_INT)
2703 {
2704 from = XEXP (XEXP (operands[1], 0), 0);
2705 off = INTVAL (XEXP (XEXP (operands[1], 0), 1));
2706 }
2707 else
2708 FAIL;
2709 }
2710 else
2711 {
2712 from = force_reg (Pmode, XEXP (operands[1], 0));
2713 off = 0;
2714 }
2715
2716 for (i = 0; i < count; i++)
2717 XVECEXP (operands[3], 0, i)
2718 = gen_rtx_SET (gen_rtx_REG (mode, regno + i),
2719 change_address (operands[1], mode,
2720 plus_constant (Pmode, from,
2721 off + i * GET_MODE_SIZE (mode))));
2722 })
2723
2724 (define_insn "*load_multiple_di"
2725 [(match_parallel 0 "load_multiple_operation"
2726 [(set (match_operand:DI 1 "register_operand" "=r")
2727 (match_operand:DI 2 "s_operand" "S"))])]
2728 "reload_completed && TARGET_ZARCH"
2729 {
2730 int words = XVECLEN (operands[0], 0);
2731 operands[0] = gen_rtx_REG (DImode, REGNO (operands[1]) + words - 1);
2732 return "lmg\t%1,%0,%S2";
2733 }
2734 [(set_attr "op_type" "RSY")
2735 (set_attr "type" "lm")])
2736
2737 (define_insn "*load_multiple_si"
2738 [(match_parallel 0 "load_multiple_operation"
2739 [(set (match_operand:SI 1 "register_operand" "=r,r")
2740 (match_operand:SI 2 "s_operand" "Q,S"))])]
2741 "reload_completed"
2742 {
2743 int words = XVECLEN (operands[0], 0);
2744 operands[0] = gen_rtx_REG (SImode, REGNO (operands[1]) + words - 1);
2745 return which_alternative == 0 ? "lm\t%1,%0,%S2" : "lmy\t%1,%0,%S2";
2746 }
2747 [(set_attr "op_type" "RS,RSY")
2748 (set_attr "cpu_facility" "*,longdisp")
2749 (set_attr "type" "lm")])
2750
2751 ;
2752 ; store multiple pattern(s).
2753 ;
2754
2755 (define_expand "store_multiple"
2756 [(match_par_dup 3 [(set (match_operand 0 "" "")
2757 (match_operand 1 "" ""))
2758 (use (match_operand 2 "" ""))])]
2759 "reload_completed"
2760 {
2761 machine_mode mode;
2762 int regno;
2763 int count;
2764 rtx to;
2765 int i, off;
2766
2767 /* Support only storing a constant number of fixed-point registers to
2768 memory and only bother with this if more than two. */
2769 if (GET_CODE (operands[2]) != CONST_INT
2770 || INTVAL (operands[2]) < 2
2771 || INTVAL (operands[2]) > 16
2772 || GET_CODE (operands[0]) != MEM
2773 || GET_CODE (operands[1]) != REG
2774 || REGNO (operands[1]) >= 16)
2775 FAIL;
2776
2777 count = INTVAL (operands[2]);
2778 regno = REGNO (operands[1]);
2779 mode = GET_MODE (operands[1]);
2780 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2781 FAIL;
2782
2783 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2784
2785 if (!can_create_pseudo_p ())
2786 {
2787 if (GET_CODE (XEXP (operands[0], 0)) == REG)
2788 {
2789 to = XEXP (operands[0], 0);
2790 off = 0;
2791 }
2792 else if (GET_CODE (XEXP (operands[0], 0)) == PLUS
2793 && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
2794 && GET_CODE (XEXP (XEXP (operands[0], 0), 1)) == CONST_INT)
2795 {
2796 to = XEXP (XEXP (operands[0], 0), 0);
2797 off = INTVAL (XEXP (XEXP (operands[0], 0), 1));
2798 }
2799 else
2800 FAIL;
2801 }
2802 else
2803 {
2804 to = force_reg (Pmode, XEXP (operands[0], 0));
2805 off = 0;
2806 }
2807
2808 for (i = 0; i < count; i++)
2809 XVECEXP (operands[3], 0, i)
2810 = gen_rtx_SET (change_address (operands[0], mode,
2811 plus_constant (Pmode, to,
2812 off + i * GET_MODE_SIZE (mode))),
2813 gen_rtx_REG (mode, regno + i));
2814 })
2815
2816 (define_insn "*store_multiple_di"
2817 [(match_parallel 0 "store_multiple_operation"
2818 [(set (match_operand:DI 1 "s_operand" "=S")
2819 (match_operand:DI 2 "register_operand" "r"))])]
2820 "reload_completed && TARGET_ZARCH"
2821 {
2822 int words = XVECLEN (operands[0], 0);
2823 operands[0] = gen_rtx_REG (DImode, REGNO (operands[2]) + words - 1);
2824 return "stmg\t%2,%0,%S1";
2825 }
2826 [(set_attr "op_type" "RSY")
2827 (set_attr "type" "stm")])
2828
2829
2830 (define_insn "*store_multiple_si"
2831 [(match_parallel 0 "store_multiple_operation"
2832 [(set (match_operand:SI 1 "s_operand" "=Q,S")
2833 (match_operand:SI 2 "register_operand" "r,r"))])]
2834 "reload_completed"
2835 {
2836 int words = XVECLEN (operands[0], 0);
2837 operands[0] = gen_rtx_REG (SImode, REGNO (operands[2]) + words - 1);
2838 return which_alternative == 0 ? "stm\t%2,%0,%S1" : "stmy\t%2,%0,%S1";
2839 }
2840 [(set_attr "op_type" "RS,RSY")
2841 (set_attr "cpu_facility" "*,longdisp")
2842 (set_attr "type" "stm")])
2843
2844 ;;
2845 ;; String instructions.
2846 ;;
2847
2848 (define_insn "*execute_rl"
2849 [(match_parallel 0 "execute_operation"
2850 [(unspec [(match_operand 1 "register_operand" "a")
2851 (match_operand 2 "" "")
2852 (match_operand:SI 3 "larl_operand" "X")] UNSPEC_EXECUTE)])]
2853 "TARGET_Z10 && GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2854 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2855 "exrl\t%1,%3"
2856 [(set_attr "op_type" "RIL")
2857 (set_attr "type" "cs")])
2858
2859 (define_insn "*execute"
2860 [(match_parallel 0 "execute_operation"
2861 [(unspec [(match_operand 1 "register_operand" "a")
2862 (match_operand:BLK 2 "memory_operand" "R")
2863 (match_operand 3 "" "")] UNSPEC_EXECUTE)])]
2864 "GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2865 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2866 "ex\t%1,%2"
2867 [(set_attr "op_type" "RX")
2868 (set_attr "type" "cs")])
2869
2870
2871 ;
2872 ; strlenM instruction pattern(s).
2873 ;
2874
2875 (define_expand "strlen<mode>"
2876 [(match_operand:P 0 "register_operand" "") ; result
2877 (match_operand:BLK 1 "memory_operand" "") ; input string
2878 (match_operand:SI 2 "immediate_operand" "") ; search character
2879 (match_operand:SI 3 "immediate_operand" "")] ; known alignment
2880 ""
2881 {
2882 if (!TARGET_VX || operands[2] != const0_rtx)
2883 emit_insn (gen_strlen_srst<mode> (operands[0], operands[1],
2884 operands[2], operands[3]));
2885 else
2886 s390_expand_vec_strlen (operands[0], operands[1], operands[3]);
2887
2888 DONE;
2889 })
2890
2891 (define_expand "strlen_srst<mode>"
2892 [(set (reg:SI 0) (match_operand:SI 2 "immediate_operand" ""))
2893 (parallel
2894 [(set (match_dup 4)
2895 (unspec:P [(const_int 0)
2896 (match_operand:BLK 1 "memory_operand" "")
2897 (reg:SI 0)
2898 (match_operand 3 "immediate_operand" "")] UNSPEC_SRST))
2899 (clobber (scratch:P))
2900 (clobber (reg:CC CC_REGNUM))])
2901 (parallel
2902 [(set (match_operand:P 0 "register_operand" "")
2903 (minus:P (match_dup 4) (match_dup 5)))
2904 (clobber (reg:CC CC_REGNUM))])]
2905 ""
2906 {
2907 operands[4] = gen_reg_rtx (Pmode);
2908 operands[5] = gen_reg_rtx (Pmode);
2909 emit_move_insn (operands[5], force_operand (XEXP (operands[1], 0), NULL_RTX));
2910 operands[1] = replace_equiv_address (operands[1], operands[5]);
2911 })
2912
2913 (define_insn "*strlen<mode>"
2914 [(set (match_operand:P 0 "register_operand" "=a")
2915 (unspec:P [(match_operand:P 2 "general_operand" "0")
2916 (mem:BLK (match_operand:P 3 "register_operand" "1"))
2917 (reg:SI 0)
2918 (match_operand 4 "immediate_operand" "")] UNSPEC_SRST))
2919 (clobber (match_scratch:P 1 "=a"))
2920 (clobber (reg:CC CC_REGNUM))]
2921 ""
2922 "srst\t%0,%1\;jo\t.-4"
2923 [(set_attr "length" "8")
2924 (set_attr "type" "vs")])
2925
2926 ;
2927 ; cmpstrM instruction pattern(s).
2928 ;
2929
2930 (define_expand "cmpstrsi"
2931 [(set (reg:SI 0) (const_int 0))
2932 (parallel
2933 [(clobber (match_operand 3 "" ""))
2934 (clobber (match_dup 4))
2935 (set (reg:CCU CC_REGNUM)
2936 (compare:CCU (match_operand:BLK 1 "memory_operand" "")
2937 (match_operand:BLK 2 "memory_operand" "")))
2938 (use (reg:SI 0))])
2939 (parallel
2940 [(set (match_operand:SI 0 "register_operand" "=d")
2941 (unspec:SI [(reg:CCU CC_REGNUM)] UNSPEC_STRCMPCC_TO_INT))
2942 (clobber (reg:CC CC_REGNUM))])]
2943 ""
2944 {
2945 /* As the result of CMPINT is inverted compared to what we need,
2946 we have to swap the operands. */
2947 rtx op1 = operands[2];
2948 rtx op2 = operands[1];
2949 rtx addr1 = gen_reg_rtx (Pmode);
2950 rtx addr2 = gen_reg_rtx (Pmode);
2951
2952 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
2953 emit_move_insn (addr2, force_operand (XEXP (op2, 0), NULL_RTX));
2954 operands[1] = replace_equiv_address_nv (op1, addr1);
2955 operands[2] = replace_equiv_address_nv (op2, addr2);
2956 operands[3] = addr1;
2957 operands[4] = addr2;
2958 })
2959
2960 (define_insn "*cmpstr<mode>"
2961 [(clobber (match_operand:P 0 "register_operand" "=d"))
2962 (clobber (match_operand:P 1 "register_operand" "=d"))
2963 (set (reg:CCU CC_REGNUM)
2964 (compare:CCU (mem:BLK (match_operand:P 2 "register_operand" "0"))
2965 (mem:BLK (match_operand:P 3 "register_operand" "1"))))
2966 (use (reg:SI 0))]
2967 ""
2968 "clst\t%0,%1\;jo\t.-4"
2969 [(set_attr "length" "8")
2970 (set_attr "type" "vs")])
2971
2972 ;
2973 ; movstr instruction pattern.
2974 ;
2975
2976 (define_expand "movstr"
2977 [(match_operand 0 "register_operand" "")
2978 (match_operand 1 "memory_operand" "")
2979 (match_operand 2 "memory_operand" "")]
2980 ""
2981 {
2982 if (TARGET_64BIT)
2983 emit_insn (gen_movstrdi (operands[0], operands[1], operands[2]));
2984 else
2985 emit_insn (gen_movstrsi (operands[0], operands[1], operands[2]));
2986 DONE;
2987 })
2988
2989 (define_expand "movstr<P:mode>"
2990 [(set (reg:SI 0) (const_int 0))
2991 (parallel
2992 [(clobber (match_dup 3))
2993 (set (match_operand:BLK 1 "memory_operand" "")
2994 (match_operand:BLK 2 "memory_operand" ""))
2995 (set (match_operand:P 0 "register_operand" "")
2996 (unspec:P [(match_dup 1)
2997 (match_dup 2)
2998 (reg:SI 0)] UNSPEC_MVST))
2999 (clobber (reg:CC CC_REGNUM))])]
3000 ""
3001 {
3002 rtx addr1, addr2;
3003
3004 if (TARGET_VX && optimize_function_for_speed_p (cfun))
3005 {
3006 s390_expand_vec_movstr (operands[0], operands[1], operands[2]);
3007 DONE;
3008 }
3009
3010 addr1 = gen_reg_rtx (Pmode);
3011 addr2 = gen_reg_rtx (Pmode);
3012
3013 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3014 emit_move_insn (addr2, force_operand (XEXP (operands[2], 0), NULL_RTX));
3015 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3016 operands[2] = replace_equiv_address_nv (operands[2], addr2);
3017 operands[3] = addr2;
3018 })
3019
3020 (define_insn "*movstr"
3021 [(clobber (match_operand:P 2 "register_operand" "=d"))
3022 (set (mem:BLK (match_operand:P 1 "register_operand" "0"))
3023 (mem:BLK (match_operand:P 3 "register_operand" "2")))
3024 (set (match_operand:P 0 "register_operand" "=d")
3025 (unspec:P [(mem:BLK (match_dup 1))
3026 (mem:BLK (match_dup 3))
3027 (reg:SI 0)] UNSPEC_MVST))
3028 (clobber (reg:CC CC_REGNUM))]
3029 ""
3030 "mvst\t%1,%2\;jo\t.-4"
3031 [(set_attr "length" "8")
3032 (set_attr "type" "vs")])
3033
3034
3035 ;
3036 ; movmemM instruction pattern(s).
3037 ;
3038
3039 (define_expand "movmem<mode>"
3040 [(set (match_operand:BLK 0 "memory_operand" "") ; destination
3041 (match_operand:BLK 1 "memory_operand" "")) ; source
3042 (use (match_operand:GPR 2 "general_operand" "")) ; count
3043 (match_operand 3 "" "")]
3044 ""
3045 {
3046 if (s390_expand_movmem (operands[0], operands[1], operands[2]))
3047 DONE;
3048 else
3049 FAIL;
3050 })
3051
3052 ; Move a block that is up to 256 bytes in length.
3053 ; The block length is taken as (operands[2] % 256) + 1.
3054
3055 (define_expand "movmem_short"
3056 [(parallel
3057 [(set (match_operand:BLK 0 "memory_operand" "")
3058 (match_operand:BLK 1 "memory_operand" ""))
3059 (use (match_operand 2 "nonmemory_operand" ""))
3060 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3061 (clobber (match_dup 3))])]
3062 ""
3063 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3064
3065 (define_insn "*movmem_short"
3066 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3067 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q"))
3068 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3069 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3070 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3071 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3072 "#"
3073 [(set_attr "type" "cs")
3074 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3075
3076 (define_split
3077 [(set (match_operand:BLK 0 "memory_operand" "")
3078 (match_operand:BLK 1 "memory_operand" ""))
3079 (use (match_operand 2 "const_int_operand" ""))
3080 (use (match_operand 3 "immediate_operand" ""))
3081 (clobber (scratch))]
3082 "reload_completed"
3083 [(parallel
3084 [(set (match_dup 0) (match_dup 1))
3085 (use (match_dup 2))])]
3086 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3087
3088 (define_split
3089 [(set (match_operand:BLK 0 "memory_operand" "")
3090 (match_operand:BLK 1 "memory_operand" ""))
3091 (use (match_operand 2 "register_operand" ""))
3092 (use (match_operand 3 "memory_operand" ""))
3093 (clobber (scratch))]
3094 "reload_completed"
3095 [(parallel
3096 [(unspec [(match_dup 2) (match_dup 3)
3097 (const_int 0)] UNSPEC_EXECUTE)
3098 (set (match_dup 0) (match_dup 1))
3099 (use (const_int 1))])]
3100 "")
3101
3102 (define_split
3103 [(set (match_operand:BLK 0 "memory_operand" "")
3104 (match_operand:BLK 1 "memory_operand" ""))
3105 (use (match_operand 2 "register_operand" ""))
3106 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3107 (clobber (scratch))]
3108 "TARGET_Z10 && reload_completed"
3109 [(parallel
3110 [(unspec [(match_dup 2) (const_int 0)
3111 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3112 (set (match_dup 0) (match_dup 1))
3113 (use (const_int 1))])]
3114 "operands[3] = gen_label_rtx ();")
3115
3116 (define_split
3117 [(set (match_operand:BLK 0 "memory_operand" "")
3118 (match_operand:BLK 1 "memory_operand" ""))
3119 (use (match_operand 2 "register_operand" ""))
3120 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3121 (clobber (match_operand 3 "register_operand" ""))]
3122 "reload_completed && TARGET_CPU_ZARCH"
3123 [(set (match_dup 3) (label_ref (match_dup 4)))
3124 (parallel
3125 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3126 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3127 (set (match_dup 0) (match_dup 1))
3128 (use (const_int 1))])]
3129 "operands[4] = gen_label_rtx ();")
3130
3131 ; Move a block of arbitrary length.
3132
3133 (define_expand "movmem_long"
3134 [(parallel
3135 [(clobber (match_dup 2))
3136 (clobber (match_dup 3))
3137 (set (match_operand:BLK 0 "memory_operand" "")
3138 (match_operand:BLK 1 "memory_operand" ""))
3139 (use (match_operand 2 "general_operand" ""))
3140 (use (match_dup 3))
3141 (clobber (reg:CC CC_REGNUM))])]
3142 ""
3143 {
3144 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3145 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3146 rtx reg0 = gen_reg_rtx (dreg_mode);
3147 rtx reg1 = gen_reg_rtx (dreg_mode);
3148 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3149 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3150 rtx len0 = gen_lowpart (Pmode, reg0);
3151 rtx len1 = gen_lowpart (Pmode, reg1);
3152
3153 emit_clobber (reg0);
3154 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3155 emit_move_insn (len0, operands[2]);
3156
3157 emit_clobber (reg1);
3158 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3159 emit_move_insn (len1, operands[2]);
3160
3161 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3162 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3163 operands[2] = reg0;
3164 operands[3] = reg1;
3165 })
3166
3167 (define_insn "*movmem_long"
3168 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3169 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3170 (set (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3171 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0)))
3172 (use (match_dup 2))
3173 (use (match_dup 3))
3174 (clobber (reg:CC CC_REGNUM))]
3175 "TARGET_64BIT || !TARGET_ZARCH"
3176 "mvcle\t%0,%1,0\;jo\t.-4"
3177 [(set_attr "length" "8")
3178 (set_attr "type" "vs")])
3179
3180 (define_insn "*movmem_long_31z"
3181 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3182 (clobber (match_operand:TI 1 "register_operand" "=d"))
3183 (set (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3184 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4)))
3185 (use (match_dup 2))
3186 (use (match_dup 3))
3187 (clobber (reg:CC CC_REGNUM))]
3188 "!TARGET_64BIT && TARGET_ZARCH"
3189 "mvcle\t%0,%1,0\;jo\t.-4"
3190 [(set_attr "length" "8")
3191 (set_attr "type" "vs")])
3192
3193
3194 ;
3195 ; Test data class.
3196 ;
3197
3198 (define_expand "signbit<mode>2"
3199 [(set (reg:CCZ CC_REGNUM)
3200 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3201 (match_dup 2)]
3202 UNSPEC_TDC_INSN))
3203 (set (match_operand:SI 0 "register_operand" "=d")
3204 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3205 "TARGET_HARD_FLOAT"
3206 {
3207 operands[2] = GEN_INT (S390_TDC_SIGNBIT_SET);
3208 })
3209
3210 (define_expand "isinf<mode>2"
3211 [(set (reg:CCZ CC_REGNUM)
3212 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3213 (match_dup 2)]
3214 UNSPEC_TDC_INSN))
3215 (set (match_operand:SI 0 "register_operand" "=d")
3216 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3217 "TARGET_HARD_FLOAT"
3218 {
3219 operands[2] = GEN_INT (S390_TDC_INFINITY);
3220 })
3221
3222 ; This extracts CC into a GPR properly shifted. The actual IPM
3223 ; instruction will be issued by reload. The constraint of operand 1
3224 ; forces reload to use a GPR. So reload will issue a movcc insn for
3225 ; copying CC into a GPR first.
3226 (define_insn_and_split "*cc_to_int"
3227 [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3228 (unspec:SI [(match_operand 1 "register_operand" "0")]
3229 UNSPEC_CC_TO_INT))]
3230 "operands != NULL"
3231 "#"
3232 "reload_completed"
3233 [(set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 28)))])
3234
3235 ; This insn is used to generate all variants of the Test Data Class
3236 ; instruction, namely tcxb, tcdb, and tceb. The insn's first operand
3237 ; is the register to be tested and the second one is the bit mask
3238 ; specifying the required test(s).
3239 ;
3240 ; tcxb, tcdb, tceb, tdcxt, tdcdt, tdcet
3241 (define_insn "*TDC_insn_<mode>"
3242 [(set (reg:CCZ CC_REGNUM)
3243 (unspec:CCZ [(match_operand:FP_ALL 0 "register_operand" "f")
3244 (match_operand:SI 1 "const_int_operand")] UNSPEC_TDC_INSN))]
3245 "TARGET_HARD_FLOAT"
3246 "t<_d>c<xde><bt>\t%0,%1"
3247 [(set_attr "op_type" "RXE")
3248 (set_attr "type" "fsimp<mode>")])
3249
3250
3251
3252 ;
3253 ; setmemM instruction pattern(s).
3254 ;
3255
3256 (define_expand "setmem<mode>"
3257 [(set (match_operand:BLK 0 "memory_operand" "")
3258 (match_operand:QI 2 "general_operand" ""))
3259 (use (match_operand:GPR 1 "general_operand" ""))
3260 (match_operand 3 "" "")]
3261 ""
3262 "s390_expand_setmem (operands[0], operands[1], operands[2]); DONE;")
3263
3264 ; Clear a block that is up to 256 bytes in length.
3265 ; The block length is taken as (operands[1] % 256) + 1.
3266
3267 (define_expand "clrmem_short"
3268 [(parallel
3269 [(set (match_operand:BLK 0 "memory_operand" "")
3270 (const_int 0))
3271 (use (match_operand 1 "nonmemory_operand" ""))
3272 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3273 (clobber (match_dup 2))
3274 (clobber (reg:CC CC_REGNUM))])]
3275 ""
3276 "operands[2] = gen_rtx_SCRATCH (Pmode);")
3277
3278 (define_insn "*clrmem_short"
3279 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3280 (const_int 0))
3281 (use (match_operand 1 "nonmemory_operand" "n,a,a,a"))
3282 (use (match_operand 2 "immediate_operand" "X,R,X,X"))
3283 (clobber (match_scratch:P 3 "=X,X,X,&a"))
3284 (clobber (reg:CC CC_REGNUM))]
3285 "(GET_MODE (operands[1]) == Pmode || GET_MODE (operands[1]) == VOIDmode)"
3286 "#"
3287 [(set_attr "type" "cs")
3288 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3289
3290 (define_split
3291 [(set (match_operand:BLK 0 "memory_operand" "")
3292 (const_int 0))
3293 (use (match_operand 1 "const_int_operand" ""))
3294 (use (match_operand 2 "immediate_operand" ""))
3295 (clobber (scratch))
3296 (clobber (reg:CC CC_REGNUM))]
3297 "reload_completed"
3298 [(parallel
3299 [(set (match_dup 0) (const_int 0))
3300 (use (match_dup 1))
3301 (clobber (reg:CC CC_REGNUM))])]
3302 "operands[1] = GEN_INT ((INTVAL (operands[1]) & 0xff) + 1);")
3303
3304 (define_split
3305 [(set (match_operand:BLK 0 "memory_operand" "")
3306 (const_int 0))
3307 (use (match_operand 1 "register_operand" ""))
3308 (use (match_operand 2 "memory_operand" ""))
3309 (clobber (scratch))
3310 (clobber (reg:CC CC_REGNUM))]
3311 "reload_completed"
3312 [(parallel
3313 [(unspec [(match_dup 1) (match_dup 2)
3314 (const_int 0)] UNSPEC_EXECUTE)
3315 (set (match_dup 0) (const_int 0))
3316 (use (const_int 1))
3317 (clobber (reg:CC CC_REGNUM))])]
3318 "")
3319
3320 (define_split
3321 [(set (match_operand:BLK 0 "memory_operand" "")
3322 (const_int 0))
3323 (use (match_operand 1 "register_operand" ""))
3324 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3325 (clobber (scratch))
3326 (clobber (reg:CC CC_REGNUM))]
3327 "TARGET_Z10 && reload_completed"
3328 [(parallel
3329 [(unspec [(match_dup 1) (const_int 0)
3330 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3331 (set (match_dup 0) (const_int 0))
3332 (use (const_int 1))
3333 (clobber (reg:CC CC_REGNUM))])]
3334 "operands[3] = gen_label_rtx ();")
3335
3336 (define_split
3337 [(set (match_operand:BLK 0 "memory_operand" "")
3338 (const_int 0))
3339 (use (match_operand 1 "register_operand" ""))
3340 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3341 (clobber (match_operand 2 "register_operand" ""))
3342 (clobber (reg:CC CC_REGNUM))]
3343 "reload_completed && TARGET_CPU_ZARCH"
3344 [(set (match_dup 2) (label_ref (match_dup 3)))
3345 (parallel
3346 [(unspec [(match_dup 1) (mem:BLK (match_dup 2))
3347 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3348 (set (match_dup 0) (const_int 0))
3349 (use (const_int 1))
3350 (clobber (reg:CC CC_REGNUM))])]
3351 "operands[3] = gen_label_rtx ();")
3352
3353 ; Initialize a block of arbitrary length with (operands[2] % 256).
3354
3355 (define_expand "setmem_long_<P:mode>"
3356 [(parallel
3357 [(clobber (match_dup 1))
3358 (set (match_operand:BLK 0 "memory_operand" "")
3359 (unspec:BLK [(match_operand:P 2 "setmem_operand" "")
3360 (match_dup 4)] UNSPEC_REPLICATE_BYTE))
3361 (use (match_dup 3))
3362 (clobber (reg:CC CC_REGNUM))])]
3363 ""
3364 {
3365 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3366 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3367 rtx reg0 = gen_reg_rtx (dreg_mode);
3368 rtx reg1 = gen_reg_rtx (dreg_mode);
3369 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3370 rtx len0 = gen_lowpart (Pmode, reg0);
3371
3372 emit_clobber (reg0);
3373 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3374 emit_move_insn (len0, operands[1]);
3375
3376 emit_move_insn (reg1, const0_rtx);
3377
3378 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3379 operands[1] = reg0;
3380 operands[3] = reg1;
3381 operands[4] = gen_lowpart (Pmode, operands[1]);
3382 })
3383
3384 ; Patterns for 31 bit + Esa and 64 bit + Zarch.
3385
3386 (define_insn "*setmem_long"
3387 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3388 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3389 (unspec:BLK [(match_operand:P 2 "setmem_operand" "Y")
3390 (subreg:P (match_dup 3) <modesize>)]
3391 UNSPEC_REPLICATE_BYTE))
3392 (use (match_operand:<DBL> 1 "register_operand" "d"))
3393 (clobber (reg:CC CC_REGNUM))]
3394 "TARGET_64BIT || !TARGET_ZARCH"
3395 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3396 [(set_attr "length" "8")
3397 (set_attr "type" "vs")])
3398
3399 (define_insn "*setmem_long_and"
3400 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3401 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3402 (unspec:BLK [(and:P
3403 (match_operand:P 2 "setmem_operand" "Y")
3404 (match_operand:P 4 "const_int_operand" "n"))
3405 (subreg:P (match_dup 3) <modesize>)]
3406 UNSPEC_REPLICATE_BYTE))
3407 (use (match_operand:<DBL> 1 "register_operand" "d"))
3408 (clobber (reg:CC CC_REGNUM))]
3409 "(TARGET_64BIT || !TARGET_ZARCH) &&
3410 (INTVAL (operands[4]) & 255) == 255"
3411 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3412 [(set_attr "length" "8")
3413 (set_attr "type" "vs")])
3414
3415 ; Variants for 31 bit + Zarch, necessary because of the odd in-register offsets
3416 ; of the SImode subregs.
3417
3418 (define_insn "*setmem_long_31z"
3419 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3420 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3421 (unspec:BLK [(match_operand:SI 2 "setmem_operand" "Y")
3422 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3423 (use (match_operand:TI 1 "register_operand" "d"))
3424 (clobber (reg:CC CC_REGNUM))]
3425 "!TARGET_64BIT && TARGET_ZARCH"
3426 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3427 [(set_attr "length" "8")
3428 (set_attr "type" "vs")])
3429
3430 (define_insn "*setmem_long_and_31z"
3431 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3432 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3433 (unspec:BLK [(and:SI
3434 (match_operand:SI 2 "setmem_operand" "Y")
3435 (match_operand:SI 4 "const_int_operand" "n"))
3436 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3437 (use (match_operand:TI 1 "register_operand" "d"))
3438 (clobber (reg:CC CC_REGNUM))]
3439 "(!TARGET_64BIT && TARGET_ZARCH) &&
3440 (INTVAL (operands[4]) & 255) == 255"
3441 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3442 [(set_attr "length" "8")
3443 (set_attr "type" "vs")])
3444
3445 ;
3446 ; cmpmemM instruction pattern(s).
3447 ;
3448
3449 (define_expand "cmpmemsi"
3450 [(set (match_operand:SI 0 "register_operand" "")
3451 (compare:SI (match_operand:BLK 1 "memory_operand" "")
3452 (match_operand:BLK 2 "memory_operand" "") ) )
3453 (use (match_operand:SI 3 "general_operand" ""))
3454 (use (match_operand:SI 4 "" ""))]
3455 ""
3456 {
3457 if (s390_expand_cmpmem (operands[0], operands[1],
3458 operands[2], operands[3]))
3459 DONE;
3460 else
3461 FAIL;
3462 })
3463
3464 ; Compare a block that is up to 256 bytes in length.
3465 ; The block length is taken as (operands[2] % 256) + 1.
3466
3467 (define_expand "cmpmem_short"
3468 [(parallel
3469 [(set (reg:CCU CC_REGNUM)
3470 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3471 (match_operand:BLK 1 "memory_operand" "")))
3472 (use (match_operand 2 "nonmemory_operand" ""))
3473 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3474 (clobber (match_dup 3))])]
3475 ""
3476 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3477
3478 (define_insn "*cmpmem_short"
3479 [(set (reg:CCU CC_REGNUM)
3480 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
3481 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
3482 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3483 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3484 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3485 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3486 "#"
3487 [(set_attr "type" "cs")
3488 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3489
3490 (define_split
3491 [(set (reg:CCU CC_REGNUM)
3492 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3493 (match_operand:BLK 1 "memory_operand" "")))
3494 (use (match_operand 2 "const_int_operand" ""))
3495 (use (match_operand 3 "immediate_operand" ""))
3496 (clobber (scratch))]
3497 "reload_completed"
3498 [(parallel
3499 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3500 (use (match_dup 2))])]
3501 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3502
3503 (define_split
3504 [(set (reg:CCU CC_REGNUM)
3505 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3506 (match_operand:BLK 1 "memory_operand" "")))
3507 (use (match_operand 2 "register_operand" ""))
3508 (use (match_operand 3 "memory_operand" ""))
3509 (clobber (scratch))]
3510 "reload_completed"
3511 [(parallel
3512 [(unspec [(match_dup 2) (match_dup 3)
3513 (const_int 0)] UNSPEC_EXECUTE)
3514 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3515 (use (const_int 1))])]
3516 "")
3517
3518 (define_split
3519 [(set (reg:CCU CC_REGNUM)
3520 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3521 (match_operand:BLK 1 "memory_operand" "")))
3522 (use (match_operand 2 "register_operand" ""))
3523 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3524 (clobber (scratch))]
3525 "TARGET_Z10 && reload_completed"
3526 [(parallel
3527 [(unspec [(match_dup 2) (const_int 0)
3528 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3529 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3530 (use (const_int 1))])]
3531 "operands[4] = gen_label_rtx ();")
3532
3533 (define_split
3534 [(set (reg:CCU CC_REGNUM)
3535 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3536 (match_operand:BLK 1 "memory_operand" "")))
3537 (use (match_operand 2 "register_operand" ""))
3538 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3539 (clobber (match_operand 3 "register_operand" ""))]
3540 "reload_completed && TARGET_CPU_ZARCH"
3541 [(set (match_dup 3) (label_ref (match_dup 4)))
3542 (parallel
3543 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3544 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3545 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3546 (use (const_int 1))])]
3547 "operands[4] = gen_label_rtx ();")
3548
3549 ; Compare a block of arbitrary length.
3550
3551 (define_expand "cmpmem_long"
3552 [(parallel
3553 [(clobber (match_dup 2))
3554 (clobber (match_dup 3))
3555 (set (reg:CCU CC_REGNUM)
3556 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3557 (match_operand:BLK 1 "memory_operand" "")))
3558 (use (match_operand 2 "general_operand" ""))
3559 (use (match_dup 3))])]
3560 ""
3561 {
3562 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3563 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3564 rtx reg0 = gen_reg_rtx (dreg_mode);
3565 rtx reg1 = gen_reg_rtx (dreg_mode);
3566 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3567 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3568 rtx len0 = gen_lowpart (Pmode, reg0);
3569 rtx len1 = gen_lowpart (Pmode, reg1);
3570
3571 emit_clobber (reg0);
3572 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3573 emit_move_insn (len0, operands[2]);
3574
3575 emit_clobber (reg1);
3576 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3577 emit_move_insn (len1, operands[2]);
3578
3579 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3580 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3581 operands[2] = reg0;
3582 operands[3] = reg1;
3583 })
3584
3585 (define_insn "*cmpmem_long"
3586 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3587 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3588 (set (reg:CCU CC_REGNUM)
3589 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3590 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
3591 (use (match_dup 2))
3592 (use (match_dup 3))]
3593 "TARGET_64BIT || !TARGET_ZARCH"
3594 "clcle\t%0,%1,0\;jo\t.-4"
3595 [(set_attr "length" "8")
3596 (set_attr "type" "vs")])
3597
3598 (define_insn "*cmpmem_long_31z"
3599 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3600 (clobber (match_operand:TI 1 "register_operand" "=d"))
3601 (set (reg:CCU CC_REGNUM)
3602 (compare:CCU (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3603 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4))))
3604 (use (match_dup 2))
3605 (use (match_dup 3))]
3606 "!TARGET_64BIT && TARGET_ZARCH"
3607 "clcle\t%0,%1,0\;jo\t.-4"
3608 [(set_attr "op_type" "NN")
3609 (set_attr "type" "vs")
3610 (set_attr "length" "8")])
3611
3612 ; Convert CCUmode condition code to integer.
3613 ; Result is zero if EQ, positive if LTU, negative if GTU.
3614
3615 (define_insn_and_split "cmpint"
3616 [(set (match_operand:SI 0 "register_operand" "=d")
3617 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3618 UNSPEC_STRCMPCC_TO_INT))
3619 (clobber (reg:CC CC_REGNUM))]
3620 ""
3621 "#"
3622 "reload_completed"
3623 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3624 (parallel
3625 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
3626 (clobber (reg:CC CC_REGNUM))])])
3627
3628 (define_insn_and_split "*cmpint_cc"
3629 [(set (reg CC_REGNUM)
3630 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3631 UNSPEC_STRCMPCC_TO_INT)
3632 (const_int 0)))
3633 (set (match_operand:SI 0 "register_operand" "=d")
3634 (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT))]
3635 "s390_match_ccmode (insn, CCSmode)"
3636 "#"
3637 "&& reload_completed"
3638 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3639 (parallel
3640 [(set (match_dup 2) (match_dup 3))
3641 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
3642 {
3643 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
3644 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3645 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3646 })
3647
3648 (define_insn_and_split "*cmpint_sign"
3649 [(set (match_operand:DI 0 "register_operand" "=d")
3650 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3651 UNSPEC_STRCMPCC_TO_INT)))
3652 (clobber (reg:CC CC_REGNUM))]
3653 "TARGET_ZARCH"
3654 "#"
3655 "&& reload_completed"
3656 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3657 (parallel
3658 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
3659 (clobber (reg:CC CC_REGNUM))])])
3660
3661 (define_insn_and_split "*cmpint_sign_cc"
3662 [(set (reg CC_REGNUM)
3663 (compare (ashiftrt:DI (ashift:DI (subreg:DI
3664 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3665 UNSPEC_STRCMPCC_TO_INT) 0)
3666 (const_int 32)) (const_int 32))
3667 (const_int 0)))
3668 (set (match_operand:DI 0 "register_operand" "=d")
3669 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT)))]
3670 "s390_match_ccmode (insn, CCSmode) && TARGET_ZARCH"
3671 "#"
3672 "&& reload_completed"
3673 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3674 (parallel
3675 [(set (match_dup 2) (match_dup 3))
3676 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
3677 {
3678 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
3679 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3680 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3681 })
3682
3683
3684 ;;
3685 ;;- Conversion instructions.
3686 ;;
3687
3688 (define_insn "*sethighpartsi"
3689 [(set (match_operand:SI 0 "register_operand" "=d,d")
3690 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
3691 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3692 (clobber (reg:CC CC_REGNUM))]
3693 ""
3694 "@
3695 icm\t%0,%2,%S1
3696 icmy\t%0,%2,%S1"
3697 [(set_attr "op_type" "RS,RSY")
3698 (set_attr "cpu_facility" "*,longdisp")
3699 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3700
3701 (define_insn "*sethighpartdi_64"
3702 [(set (match_operand:DI 0 "register_operand" "=d")
3703 (unspec:DI [(match_operand:BLK 1 "s_operand" "S")
3704 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
3705 (clobber (reg:CC CC_REGNUM))]
3706 "TARGET_ZARCH"
3707 "icmh\t%0,%2,%S1"
3708 [(set_attr "op_type" "RSY")
3709 (set_attr "z10prop" "z10_super")])
3710
3711 (define_insn "*sethighpartdi_31"
3712 [(set (match_operand:DI 0 "register_operand" "=d,d")
3713 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
3714 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3715 (clobber (reg:CC CC_REGNUM))]
3716 "!TARGET_ZARCH"
3717 "@
3718 icm\t%0,%2,%S1
3719 icmy\t%0,%2,%S1"
3720 [(set_attr "op_type" "RS,RSY")
3721 (set_attr "cpu_facility" "*,longdisp")
3722 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3723
3724 ;
3725 ; extv instruction patterns
3726 ;
3727
3728 ; FIXME: This expander needs to be converted from DI to GPR as well
3729 ; after resolving some issues with it.
3730
3731 (define_expand "extzv"
3732 [(parallel
3733 [(set (match_operand:DI 0 "register_operand" "=d")
3734 (zero_extract:DI
3735 (match_operand:DI 1 "register_operand" "d")
3736 (match_operand 2 "const_int_operand" "") ; size
3737 (match_operand 3 "const_int_operand" ""))) ; start
3738 (clobber (reg:CC CC_REGNUM))])]
3739 "TARGET_Z10"
3740 {
3741 /* Starting with zEC12 there is risbgn not clobbering CC. */
3742 if (TARGET_ZEC12)
3743 {
3744 emit_move_insn (operands[0],
3745 gen_rtx_ZERO_EXTRACT (DImode,
3746 operands[1],
3747 operands[2],
3748 operands[3]));
3749 DONE;
3750 }
3751 })
3752
3753 (define_insn "*extzv<mode>_zEC12"
3754 [(set (match_operand:GPR 0 "register_operand" "=d")
3755 (zero_extract:GPR
3756 (match_operand:GPR 1 "register_operand" "d")
3757 (match_operand 2 "const_int_operand" "") ; size
3758 (match_operand 3 "const_int_operand" "")))] ; start]
3759 "TARGET_ZEC12"
3760 "risbgn\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3761 [(set_attr "op_type" "RIE")])
3762
3763 (define_insn "*extzv<mode>_z10"
3764 [(set (match_operand:GPR 0 "register_operand" "=d")
3765 (zero_extract:GPR
3766 (match_operand:GPR 1 "register_operand" "d")
3767 (match_operand 2 "const_int_operand" "") ; size
3768 (match_operand 3 "const_int_operand" ""))) ; start
3769 (clobber (reg:CC CC_REGNUM))]
3770 "TARGET_Z10"
3771 "risbg\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3772 [(set_attr "op_type" "RIE")
3773 (set_attr "z10prop" "z10_super_E1")])
3774
3775 (define_insn_and_split "*pre_z10_extzv<mode>"
3776 [(set (match_operand:GPR 0 "register_operand" "=d")
3777 (zero_extract:GPR (match_operand:QI 1 "s_operand" "S")
3778 (match_operand 2 "nonzero_shift_count_operand" "")
3779 (const_int 0)))
3780 (clobber (reg:CC CC_REGNUM))]
3781 "!TARGET_Z10"
3782 "#"
3783 "&& reload_completed"
3784 [(parallel
3785 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3786 (clobber (reg:CC CC_REGNUM))])
3787 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3788 {
3789 int bitsize = INTVAL (operands[2]);
3790 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3791 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3792
3793 operands[1] = adjust_address (operands[1], BLKmode, 0);
3794 set_mem_size (operands[1], size);
3795 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3796 operands[3] = GEN_INT (mask);
3797 })
3798
3799 (define_insn_and_split "*pre_z10_extv<mode>"
3800 [(set (match_operand:GPR 0 "register_operand" "=d")
3801 (sign_extract:GPR (match_operand:QI 1 "s_operand" "S")
3802 (match_operand 2 "nonzero_shift_count_operand" "")
3803 (const_int 0)))
3804 (clobber (reg:CC CC_REGNUM))]
3805 ""
3806 "#"
3807 "&& reload_completed"
3808 [(parallel
3809 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3810 (clobber (reg:CC CC_REGNUM))])
3811 (parallel
3812 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3813 (clobber (reg:CC CC_REGNUM))])]
3814 {
3815 int bitsize = INTVAL (operands[2]);
3816 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3817 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3818
3819 operands[1] = adjust_address (operands[1], BLKmode, 0);
3820 set_mem_size (operands[1], size);
3821 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3822 operands[3] = GEN_INT (mask);
3823 })
3824
3825 ;
3826 ; insv instruction patterns
3827 ;
3828
3829 (define_expand "insv"
3830 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3831 (match_operand 1 "const_int_operand" "")
3832 (match_operand 2 "const_int_operand" ""))
3833 (match_operand 3 "general_operand" ""))]
3834 ""
3835 {
3836 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3837 DONE;
3838 FAIL;
3839 })
3840
3841
3842 ; The normal RTL expansion will never generate a zero_extract where
3843 ; the location operand isn't word mode. However, we do this in the
3844 ; back-end when generating atomic operations. See s390_two_part_insv.
3845 (define_insn "*insv<mode>_zEC12"
3846 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3847 (match_operand 1 "const_int_operand" "I") ; size
3848 (match_operand 2 "const_int_operand" "I")) ; pos
3849 (match_operand:GPR 3 "nonimmediate_operand" "d"))]
3850 "TARGET_ZEC12
3851 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3852 "risbgn\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3853 [(set_attr "op_type" "RIE")])
3854
3855 (define_insn "*insv<mode>_z10"
3856 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3857 (match_operand 1 "const_int_operand" "I") ; size
3858 (match_operand 2 "const_int_operand" "I")) ; pos
3859 (match_operand:GPR 3 "nonimmediate_operand" "d"))
3860 (clobber (reg:CC CC_REGNUM))]
3861 "TARGET_Z10
3862 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3863 "risbg\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3864 [(set_attr "op_type" "RIE")
3865 (set_attr "z10prop" "z10_super_E1")])
3866
3867 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3868 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3869 (define_insn "*insv<mode>_zEC12_noshift"
3870 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3871 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3872 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3873 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3874 (match_operand:GPR 4 "const_int_operand" ""))))]
3875 "TARGET_ZEC12 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3876 "risbgn\t%0,%1,%<bfstart>2,%<bfend>2,0"
3877 [(set_attr "op_type" "RIE")])
3878
3879 (define_insn "*insv<mode>_z10_noshift"
3880 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3881 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3882 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3883 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3884 (match_operand:GPR 4 "const_int_operand" ""))))
3885 (clobber (reg:CC CC_REGNUM))]
3886 "TARGET_Z10 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3887 "risbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3888 [(set_attr "op_type" "RIE")
3889 (set_attr "z10prop" "z10_super_E1")])
3890
3891 ; Implement appending Y on the left of S bits of X
3892 ; x = (y << s) | (x & ((1 << s) - 1))
3893 (define_insn "*insv<mode>_zEC12_appendbitsleft"
3894 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3895 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3896 (match_operand:GPR 2 "immediate_operand" ""))
3897 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3898 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3899 "TARGET_ZEC12 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3900 "risbgn\t%0,%3,64-<bitsize>,64-%4-1,%4"
3901 [(set_attr "op_type" "RIE")
3902 (set_attr "z10prop" "z10_super_E1")])
3903
3904 (define_insn "*insv<mode>_z10_appendbitsleft"
3905 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3906 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3907 (match_operand:GPR 2 "immediate_operand" ""))
3908 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3909 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
3910 (clobber (reg:CC CC_REGNUM))]
3911 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3912 "risbg\t%0,%3,64-<bitsize>,64-%4-1,%4"
3913 [(set_attr "op_type" "RIE")
3914 (set_attr "z10prop" "z10_super_E1")])
3915
3916 ; z = (x << c) | (y >> d) with (x << c) and (y >> d) not overlapping after shifting
3917 ; -> z = y >> d; z = (x << c) | (z & ((1 << c) - 1))
3918 ; -> z = y >> d; z = risbg;
3919
3920 (define_split
3921 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
3922 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
3923 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
3924 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
3925 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3926 "TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
3927 [(set (match_dup 6)
3928 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
3929 (set (match_dup 0)
3930 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
3931 (ashift:GPR (match_dup 3) (match_dup 4))))]
3932 {
3933 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
3934 if (reg_overlap_mentioned_p (operands[0], operands[3]))
3935 {
3936 if (!can_create_pseudo_p ())
3937 FAIL;
3938 operands[6] = gen_reg_rtx (<MODE>mode);
3939 }
3940 else
3941 operands[6] = operands[0];
3942 })
3943
3944 (define_split
3945 [(parallel
3946 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
3947 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
3948 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
3949 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
3950 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
3951 (clobber (reg:CC CC_REGNUM))])]
3952 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
3953 [(set (match_dup 6)
3954 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
3955 (parallel
3956 [(set (match_dup 0)
3957 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
3958 (ashift:GPR (match_dup 3) (match_dup 4))))
3959 (clobber (reg:CC CC_REGNUM))])]
3960 {
3961 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
3962 if (reg_overlap_mentioned_p (operands[0], operands[3]))
3963 {
3964 if (!can_create_pseudo_p ())
3965 FAIL;
3966 operands[6] = gen_reg_rtx (<MODE>mode);
3967 }
3968 else
3969 operands[6] = operands[0];
3970 })
3971
3972 (define_insn "*r<noxa>sbg_<mode>_noshift"
3973 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3974 (IXOR:GPR
3975 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3976 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3977 (match_operand:GPR 3 "nonimmediate_operand" "0")))
3978 (clobber (reg:CC CC_REGNUM))]
3979 "TARGET_Z10"
3980 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3981 [(set_attr "op_type" "RIE")])
3982
3983 (define_insn "*r<noxa>sbg_di_rotl"
3984 [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
3985 (IXOR:DI
3986 (and:DI
3987 (rotate:DI
3988 (match_operand:DI 1 "nonimmediate_operand" "d")
3989 (match_operand:DI 3 "const_int_operand" ""))
3990 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3991 (match_operand:DI 4 "nonimmediate_operand" "0")))
3992 (clobber (reg:CC CC_REGNUM))]
3993 "TARGET_Z10"
3994 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%b3"
3995 [(set_attr "op_type" "RIE")])
3996
3997 (define_insn "*r<noxa>sbg_<mode>_srl_bitmask"
3998 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3999 (IXOR:GPR
4000 (and:GPR
4001 (lshiftrt:GPR
4002 (match_operand:GPR 1 "nonimmediate_operand" "d")
4003 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4004 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4005 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4006 (clobber (reg:CC CC_REGNUM))]
4007 "TARGET_Z10
4008 && s390_extzv_shift_ok (<bitsize>, 64 - INTVAL (operands[3]),
4009 INTVAL (operands[2]))"
4010 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,64-%3"
4011 [(set_attr "op_type" "RIE")])
4012
4013 (define_insn "*r<noxa>sbg_<mode>_sll_bitmask"
4014 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4015 (IXOR:GPR
4016 (and:GPR
4017 (ashift:GPR
4018 (match_operand:GPR 1 "nonimmediate_operand" "d")
4019 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4020 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4021 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4022 (clobber (reg:CC CC_REGNUM))]
4023 "TARGET_Z10
4024 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[3]),
4025 INTVAL (operands[2]))"
4026 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%3"
4027 [(set_attr "op_type" "RIE")])
4028
4029 ;; unsigned {int,long} a, b
4030 ;; a = a | (b << const_int)
4031 ;; a = a ^ (b << const_int)
4032 (define_insn "*r<noxa>sbg_<mode>_sll"
4033 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4034 (IXOR:GPR
4035 (ashift:GPR
4036 (match_operand:GPR 1 "nonimmediate_operand" "d")
4037 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4038 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4039 (clobber (reg:CC CC_REGNUM))]
4040 "TARGET_Z10"
4041 "r<noxa>sbg\t%0,%1,64-<bitsize>,63-%2,%2"
4042 [(set_attr "op_type" "RIE")])
4043
4044 ;; unsigned {int,long} a, b
4045 ;; a = a | (b >> const_int)
4046 ;; a = a ^ (b >> const_int)
4047 (define_insn "*r<noxa>sbg_<mode>_srl"
4048 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4049 (IXOR:GPR
4050 (lshiftrt:GPR
4051 (match_operand:GPR 1 "nonimmediate_operand" "d")
4052 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4053 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4054 (clobber (reg:CC CC_REGNUM))]
4055 "TARGET_Z10"
4056 "r<noxa>sbg\t%0,%1,64-<bitsize>+%2,63,64-%2"
4057 [(set_attr "op_type" "RIE")])
4058
4059 ;; These two are generated by combine for s.bf &= val.
4060 ;; ??? For bitfields smaller than 32-bits, we wind up with SImode
4061 ;; shifts and ands, which results in some truly awful patterns
4062 ;; including subregs of operations. Rather unnecessisarily, IMO.
4063 ;; Instead of
4064 ;;
4065 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4066 ;; (const_int 24 [0x18])
4067 ;; (const_int 0 [0]))
4068 ;; (subreg:DI (and:SI (subreg:SI (lshiftrt:DI (reg/v:DI 50 [ s ])
4069 ;; (const_int 40 [0x28])) 4)
4070 ;; (reg:SI 4 %r4 [ y+4 ])) 0))
4071 ;;
4072 ;; we should instead generate
4073 ;;
4074 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4075 ;; (const_int 24 [0x18])
4076 ;; (const_int 0 [0]))
4077 ;; (and:DI (lshiftrt:DI (reg/v:DI 50 [ s ])
4078 ;; (const_int 40 [0x28]))
4079 ;; (subreg:DI (reg:SI 4 %r4 [ y+4 ]) 0)))
4080 ;;
4081 ;; by noticing that we can push down the outer paradoxical subreg
4082 ;; into the operation.
4083
4084 (define_insn "*insv_rnsbg_noshift"
4085 [(set (zero_extract:DI
4086 (match_operand:DI 0 "nonimmediate_operand" "+d")
4087 (match_operand 1 "const_int_operand" "")
4088 (match_operand 2 "const_int_operand" ""))
4089 (and:DI
4090 (match_dup 0)
4091 (match_operand:DI 3 "nonimmediate_operand" "d")))
4092 (clobber (reg:CC CC_REGNUM))]
4093 "TARGET_Z10
4094 && INTVAL (operands[1]) + INTVAL (operands[2]) == 64"
4095 "rnsbg\t%0,%3,%2,63,0"
4096 [(set_attr "op_type" "RIE")])
4097
4098 (define_insn "*insv_rnsbg_srl"
4099 [(set (zero_extract:DI
4100 (match_operand:DI 0 "nonimmediate_operand" "+d")
4101 (match_operand 1 "const_int_operand" "")
4102 (match_operand 2 "const_int_operand" ""))
4103 (and:DI
4104 (lshiftrt:DI
4105 (match_dup 0)
4106 (match_operand 3 "const_int_operand" ""))
4107 (match_operand:DI 4 "nonimmediate_operand" "d")))
4108 (clobber (reg:CC CC_REGNUM))]
4109 "TARGET_Z10
4110 && INTVAL (operands[3]) == 64 - INTVAL (operands[1]) - INTVAL (operands[2])"
4111 "rnsbg\t%0,%4,%2,%2+%1-1,%3"
4112 [(set_attr "op_type" "RIE")])
4113
4114 (define_insn "*insv<mode>_mem_reg"
4115 [(set (zero_extract:W (match_operand:QI 0 "memory_operand" "+Q,S")
4116 (match_operand 1 "const_int_operand" "n,n")
4117 (const_int 0))
4118 (match_operand:W 2 "register_operand" "d,d"))]
4119 "INTVAL (operands[1]) > 0
4120 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4121 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4122 {
4123 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4124
4125 operands[1] = GEN_INT ((1ul << size) - 1);
4126 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
4127 : "stcmy\t%2,%1,%S0";
4128 }
4129 [(set_attr "op_type" "RS,RSY")
4130 (set_attr "cpu_facility" "*,longdisp")
4131 (set_attr "z10prop" "z10_super,z10_super")])
4132
4133 (define_insn "*insvdi_mem_reghigh"
4134 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+S")
4135 (match_operand 1 "const_int_operand" "n")
4136 (const_int 0))
4137 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
4138 (const_int 32)))]
4139 "TARGET_ZARCH
4140 && INTVAL (operands[1]) > 0
4141 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4142 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4143 {
4144 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4145
4146 operands[1] = GEN_INT ((1ul << size) - 1);
4147 return "stcmh\t%2,%1,%S0";
4148 }
4149 [(set_attr "op_type" "RSY")
4150 (set_attr "z10prop" "z10_super")])
4151
4152 (define_insn "*insvdi_reg_imm"
4153 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4154 (const_int 16)
4155 (match_operand 1 "const_int_operand" "n"))
4156 (match_operand:DI 2 "const_int_operand" "n"))]
4157 "TARGET_ZARCH
4158 && INTVAL (operands[1]) >= 0
4159 && INTVAL (operands[1]) < BITS_PER_WORD
4160 && INTVAL (operands[1]) % 16 == 0"
4161 {
4162 switch (BITS_PER_WORD - INTVAL (operands[1]))
4163 {
4164 case 64: return "iihh\t%0,%x2"; break;
4165 case 48: return "iihl\t%0,%x2"; break;
4166 case 32: return "iilh\t%0,%x2"; break;
4167 case 16: return "iill\t%0,%x2"; break;
4168 default: gcc_unreachable();
4169 }
4170 }
4171 [(set_attr "op_type" "RI")
4172 (set_attr "z10prop" "z10_super_E1")])
4173
4174 ; Update the left-most 32 bit of a DI.
4175 (define_insn "*insv_h_di_reg_extimm"
4176 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4177 (const_int 32)
4178 (const_int 0))
4179 (match_operand:DI 1 "const_int_operand" "n"))]
4180 "TARGET_EXTIMM"
4181 "iihf\t%0,%o1"
4182 [(set_attr "op_type" "RIL")
4183 (set_attr "z10prop" "z10_fwd_E1")])
4184
4185 ; Update the right-most 32 bit of a DI.
4186 (define_insn "*insv_l_di_reg_extimm"
4187 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4188 (const_int 32)
4189 (const_int 32))
4190 (match_operand:DI 1 "const_int_operand" "n"))]
4191 "TARGET_EXTIMM"
4192 "iilf\t%0,%o1"
4193 [(set_attr "op_type" "RIL")
4194 (set_attr "z10prop" "z10_fwd_A1")])
4195
4196 ;
4197 ; extendsidi2 instruction pattern(s).
4198 ;
4199
4200 (define_expand "extendsidi2"
4201 [(set (match_operand:DI 0 "register_operand" "")
4202 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4203 ""
4204 {
4205 if (!TARGET_ZARCH)
4206 {
4207 emit_clobber (operands[0]);
4208 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
4209 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
4210 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
4211 DONE;
4212 }
4213 })
4214
4215 (define_insn "*extendsidi2"
4216 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4217 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4218 "TARGET_ZARCH"
4219 "@
4220 lgfr\t%0,%1
4221 lgf\t%0,%1
4222 lgfrl\t%0,%1"
4223 [(set_attr "op_type" "RRE,RXY,RIL")
4224 (set_attr "type" "*,*,larl")
4225 (set_attr "cpu_facility" "*,*,z10")
4226 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4227
4228 ;
4229 ; extend(hi|qi)(si|di)2 instruction pattern(s).
4230 ;
4231
4232 (define_expand "extend<HQI:mode><DSI:mode>2"
4233 [(set (match_operand:DSI 0 "register_operand" "")
4234 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4235 ""
4236 {
4237 if (<DSI:MODE>mode == DImode && !TARGET_ZARCH)
4238 {
4239 rtx tmp = gen_reg_rtx (SImode);
4240 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
4241 emit_insn (gen_extendsidi2 (operands[0], tmp));
4242 DONE;
4243 }
4244 else if (!TARGET_EXTIMM)
4245 {
4246 rtx bitcount = GEN_INT (<DSI:bitsize> - <HQI:bitsize>);
4247
4248 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
4249 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
4250 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
4251 DONE;
4252 }
4253 })
4254
4255 ;
4256 ; extendhidi2 instruction pattern(s).
4257 ;
4258
4259 (define_insn "*extendhidi2_extimm"
4260 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4261 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,T,b")))]
4262 "TARGET_ZARCH && TARGET_EXTIMM"
4263 "@
4264 lghr\t%0,%1
4265 lgh\t%0,%1
4266 lghrl\t%0,%1"
4267 [(set_attr "op_type" "RRE,RXY,RIL")
4268 (set_attr "type" "*,*,larl")
4269 (set_attr "cpu_facility" "extimm,extimm,z10")
4270 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4271
4272 (define_insn "*extendhidi2"
4273 [(set (match_operand:DI 0 "register_operand" "=d")
4274 (sign_extend:DI (match_operand:HI 1 "memory_operand" "T")))]
4275 "TARGET_ZARCH"
4276 "lgh\t%0,%1"
4277 [(set_attr "op_type" "RXY")
4278 (set_attr "z10prop" "z10_super_E1")])
4279
4280 ;
4281 ; extendhisi2 instruction pattern(s).
4282 ;
4283
4284 (define_insn "*extendhisi2_extimm"
4285 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
4286 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
4287 "TARGET_EXTIMM"
4288 "@
4289 lhr\t%0,%1
4290 lh\t%0,%1
4291 lhy\t%0,%1
4292 lhrl\t%0,%1"
4293 [(set_attr "op_type" "RRE,RX,RXY,RIL")
4294 (set_attr "type" "*,*,*,larl")
4295 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")
4296 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,z10_super_E1")])
4297
4298 (define_insn "*extendhisi2"
4299 [(set (match_operand:SI 0 "register_operand" "=d,d")
4300 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
4301 "!TARGET_EXTIMM"
4302 "@
4303 lh\t%0,%1
4304 lhy\t%0,%1"
4305 [(set_attr "op_type" "RX,RXY")
4306 (set_attr "cpu_facility" "*,longdisp")
4307 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4308
4309 ;
4310 ; extendqi(si|di)2 instruction pattern(s).
4311 ;
4312
4313 ; lbr, lgbr, lb, lgb
4314 (define_insn "*extendqi<mode>2_extimm"
4315 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4316 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,T")))]
4317 "TARGET_EXTIMM"
4318 "@
4319 l<g>br\t%0,%1
4320 l<g>b\t%0,%1"
4321 [(set_attr "op_type" "RRE,RXY")
4322 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4323
4324 ; lb, lgb
4325 (define_insn "*extendqi<mode>2"
4326 [(set (match_operand:GPR 0 "register_operand" "=d")
4327 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "T")))]
4328 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
4329 "l<g>b\t%0,%1"
4330 [(set_attr "op_type" "RXY")
4331 (set_attr "z10prop" "z10_super_E1")])
4332
4333 (define_insn_and_split "*extendqi<mode>2_short_displ"
4334 [(set (match_operand:GPR 0 "register_operand" "=d")
4335 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
4336 (clobber (reg:CC CC_REGNUM))]
4337 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
4338 "#"
4339 "&& reload_completed"
4340 [(parallel
4341 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
4342 (clobber (reg:CC CC_REGNUM))])
4343 (parallel
4344 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
4345 (clobber (reg:CC CC_REGNUM))])]
4346 {
4347 operands[1] = adjust_address (operands[1], BLKmode, 0);
4348 set_mem_size (operands[1], GET_MODE_SIZE (QImode));
4349 operands[2] = GEN_INT (<GPR:bitsize> - BITS_PER_UNIT);
4350 })
4351
4352 ;
4353 ; zero_extendsidi2 instruction pattern(s).
4354 ;
4355
4356 (define_expand "zero_extendsidi2"
4357 [(set (match_operand:DI 0 "register_operand" "")
4358 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4359 ""
4360 {
4361 if (!TARGET_ZARCH)
4362 {
4363 emit_clobber (operands[0]);
4364 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
4365 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
4366 DONE;
4367 }
4368 })
4369
4370 (define_insn "*zero_extendsidi2"
4371 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4372 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4373 "TARGET_ZARCH"
4374 "@
4375 llgfr\t%0,%1
4376 llgf\t%0,%1
4377 llgfrl\t%0,%1"
4378 [(set_attr "op_type" "RRE,RXY,RIL")
4379 (set_attr "type" "*,*,larl")
4380 (set_attr "cpu_facility" "*,*,z10")
4381 (set_attr "z10prop" "z10_fwd_E1,z10_fwd_A3,z10_fwd_A3")])
4382
4383 ;
4384 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
4385 ;
4386
4387 (define_insn "*llgt_sidi"
4388 [(set (match_operand:DI 0 "register_operand" "=d")
4389 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4390 (const_int 2147483647)))]
4391 "TARGET_ZARCH"
4392 "llgt\t%0,%1"
4393 [(set_attr "op_type" "RXE")
4394 (set_attr "z10prop" "z10_super_E1")])
4395
4396 (define_insn_and_split "*llgt_sidi_split"
4397 [(set (match_operand:DI 0 "register_operand" "=d")
4398 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4399 (const_int 2147483647)))
4400 (clobber (reg:CC CC_REGNUM))]
4401 "TARGET_ZARCH"
4402 "#"
4403 "&& reload_completed"
4404 [(set (match_dup 0)
4405 (and:DI (subreg:DI (match_dup 1) 0)
4406 (const_int 2147483647)))]
4407 "")
4408
4409 (define_insn "*llgt_sisi"
4410 [(set (match_operand:SI 0 "register_operand" "=d,d")
4411 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,T")
4412 (const_int 2147483647)))]
4413 "TARGET_ZARCH"
4414 "@
4415 llgtr\t%0,%1
4416 llgt\t%0,%1"
4417 [(set_attr "op_type" "RRE,RXE")
4418 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4419
4420 (define_insn "*llgt_didi"
4421 [(set (match_operand:DI 0 "register_operand" "=d,d")
4422 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
4423 (const_int 2147483647)))]
4424 "TARGET_ZARCH"
4425 "@
4426 llgtr\t%0,%1
4427 llgt\t%0,%N1"
4428 [(set_attr "op_type" "RRE,RXE")
4429 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4430
4431 (define_split
4432 [(set (match_operand:DSI 0 "register_operand" "")
4433 (and:DSI (match_operand:DSI 1 "nonimmediate_operand" "")
4434 (const_int 2147483647)))
4435 (clobber (reg:CC CC_REGNUM))]
4436 "TARGET_ZARCH && reload_completed"
4437 [(set (match_dup 0)
4438 (and:DSI (match_dup 1)
4439 (const_int 2147483647)))]
4440 "")
4441
4442 ;
4443 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
4444 ;
4445
4446 (define_expand "zero_extend<mode>di2"
4447 [(set (match_operand:DI 0 "register_operand" "")
4448 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4449 ""
4450 {
4451 if (!TARGET_ZARCH)
4452 {
4453 rtx tmp = gen_reg_rtx (SImode);
4454 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
4455 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
4456 DONE;
4457 }
4458 else if (!TARGET_EXTIMM)
4459 {
4460 rtx bitcount = GEN_INT (64 - <HQI:bitsize>);
4461 operands[1] = gen_lowpart (DImode, operands[1]);
4462 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
4463 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
4464 DONE;
4465 }
4466 })
4467
4468 (define_expand "zero_extend<mode>si2"
4469 [(set (match_operand:SI 0 "register_operand" "")
4470 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4471 ""
4472 {
4473 if (!TARGET_EXTIMM)
4474 {
4475 operands[1] = gen_lowpart (SImode, operands[1]);
4476 emit_insn (gen_andsi3 (operands[0], operands[1],
4477 GEN_INT ((1 << <HQI:bitsize>) - 1)));
4478 DONE;
4479 }
4480 })
4481
4482 ; llhrl, llghrl
4483 (define_insn "*zero_extendhi<mode>2_z10"
4484 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4485 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,T,b")))]
4486 "TARGET_Z10"
4487 "@
4488 ll<g>hr\t%0,%1
4489 ll<g>h\t%0,%1
4490 ll<g>hrl\t%0,%1"
4491 [(set_attr "op_type" "RXY,RRE,RIL")
4492 (set_attr "type" "*,*,larl")
4493 (set_attr "cpu_facility" "*,*,z10")
4494 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3,z10_fwd_A3")])
4495
4496 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
4497 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
4498 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4499 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,T")))]
4500 "TARGET_EXTIMM"
4501 "@
4502 ll<g><hc>r\t%0,%1
4503 ll<g><hc>\t%0,%1"
4504 [(set_attr "op_type" "RRE,RXY")
4505 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3")])
4506
4507 ; llgh, llgc
4508 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
4509 [(set (match_operand:GPR 0 "register_operand" "=d")
4510 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "T")))]
4511 "TARGET_ZARCH && !TARGET_EXTIMM"
4512 "llg<hc>\t%0,%1"
4513 [(set_attr "op_type" "RXY")
4514 (set_attr "z10prop" "z10_fwd_A3")])
4515
4516 (define_insn_and_split "*zero_extendhisi2_31"
4517 [(set (match_operand:SI 0 "register_operand" "=&d")
4518 (zero_extend:SI (match_operand:HI 1 "s_operand" "S")))
4519 (clobber (reg:CC CC_REGNUM))]
4520 "!TARGET_ZARCH"
4521 "#"
4522 "&& reload_completed"
4523 [(set (match_dup 0) (const_int 0))
4524 (parallel
4525 [(set (strict_low_part (match_dup 2)) (match_dup 1))
4526 (clobber (reg:CC CC_REGNUM))])]
4527 "operands[2] = gen_lowpart (HImode, operands[0]);")
4528
4529 (define_insn_and_split "*zero_extendqisi2_31"
4530 [(set (match_operand:SI 0 "register_operand" "=&d")
4531 (zero_extend:SI (match_operand:QI 1 "memory_operand" "T")))]
4532 "!TARGET_ZARCH"
4533 "#"
4534 "&& reload_completed"
4535 [(set (match_dup 0) (const_int 0))
4536 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4537 "operands[2] = gen_lowpart (QImode, operands[0]);")
4538
4539 ;
4540 ; zero_extendqihi2 instruction pattern(s).
4541 ;
4542
4543 (define_expand "zero_extendqihi2"
4544 [(set (match_operand:HI 0 "register_operand" "")
4545 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4546 "TARGET_ZARCH && !TARGET_EXTIMM"
4547 {
4548 operands[1] = gen_lowpart (HImode, operands[1]);
4549 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
4550 DONE;
4551 })
4552
4553 (define_insn "*zero_extendqihi2_64"
4554 [(set (match_operand:HI 0 "register_operand" "=d")
4555 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4556 "TARGET_ZARCH && !TARGET_EXTIMM"
4557 "llgc\t%0,%1"
4558 [(set_attr "op_type" "RXY")
4559 (set_attr "z10prop" "z10_fwd_A3")])
4560
4561 (define_insn_and_split "*zero_extendqihi2_31"
4562 [(set (match_operand:HI 0 "register_operand" "=&d")
4563 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4564 "!TARGET_ZARCH"
4565 "#"
4566 "&& reload_completed"
4567 [(set (match_dup 0) (const_int 0))
4568 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4569 "operands[2] = gen_lowpart (QImode, operands[0]);")
4570
4571 ;
4572 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
4573 ;
4574
4575 (define_expand "fixuns_truncdddi2"
4576 [(parallel
4577 [(set (match_operand:DI 0 "register_operand" "")
4578 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
4579 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4580 (clobber (reg:CC CC_REGNUM))])]
4581
4582 "TARGET_HARD_DFP"
4583 {
4584 if (!TARGET_Z196)
4585 {
4586 rtx_code_label *label1 = gen_label_rtx ();
4587 rtx_code_label *label2 = gen_label_rtx ();
4588 rtx temp = gen_reg_rtx (TDmode);
4589 REAL_VALUE_TYPE cmp, sub;
4590
4591 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4592 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4593
4594 /* 2^63 can't be represented as 64bit DFP number with full precision. The
4595 solution is doing the check and the subtraction in TD mode and using a
4596 TD -> DI convert afterwards. */
4597 emit_insn (gen_extendddtd2 (temp, operands[1]));
4598 temp = force_reg (TDmode, temp);
4599 emit_cmp_and_jump_insns (temp,
4600 const_double_from_real_value (cmp, TDmode),
4601 LT, NULL_RTX, VOIDmode, 0, label1);
4602 emit_insn (gen_subtd3 (temp, temp,
4603 const_double_from_real_value (sub, TDmode)));
4604 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4605 GEN_INT (DFP_RND_TOWARD_MINF)));
4606 emit_jump (label2);
4607
4608 emit_label (label1);
4609 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1],
4610 GEN_INT (DFP_RND_TOWARD_0)));
4611 emit_label (label2);
4612 DONE;
4613 }
4614 })
4615
4616 (define_expand "fixuns_trunctddi2"
4617 [(parallel
4618 [(set (match_operand:DI 0 "register_operand" "")
4619 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))
4620 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4621 (clobber (reg:CC CC_REGNUM))])]
4622
4623 "TARGET_HARD_DFP"
4624 {
4625 if (!TARGET_Z196)
4626 {
4627 rtx_code_label *label1 = gen_label_rtx ();
4628 rtx_code_label *label2 = gen_label_rtx ();
4629 rtx temp = gen_reg_rtx (TDmode);
4630 REAL_VALUE_TYPE cmp, sub;
4631
4632 operands[1] = force_reg (TDmode, operands[1]);
4633 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4634 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4635
4636 emit_cmp_and_jump_insns (operands[1],
4637 const_double_from_real_value (cmp, TDmode),
4638 LT, NULL_RTX, VOIDmode, 0, label1);
4639 emit_insn (gen_subtd3 (temp, operands[1],
4640 const_double_from_real_value (sub, TDmode)));
4641 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4642 GEN_INT (DFP_RND_TOWARD_MINF)));
4643 emit_jump (label2);
4644
4645 emit_label (label1);
4646 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1],
4647 GEN_INT (DFP_RND_TOWARD_0)));
4648 emit_label (label2);
4649 DONE;
4650 }
4651 })
4652
4653 ;
4654 ; fixuns_trunc(sf|df|tf)(si|di)2 and fix_trunc(sf|df|tf)(si|di)2
4655 ; instruction pattern(s).
4656 ;
4657
4658 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
4659 [(parallel
4660 [(set (match_operand:GPR 0 "register_operand" "")
4661 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))
4662 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4663 (clobber (reg:CC CC_REGNUM))])]
4664 "TARGET_HARD_FLOAT"
4665 {
4666 if (!TARGET_Z196)
4667 {
4668 rtx_code_label *label1 = gen_label_rtx ();
4669 rtx_code_label *label2 = gen_label_rtx ();
4670 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
4671 REAL_VALUE_TYPE cmp, sub;
4672
4673 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
4674 real_2expN (&cmp, <GPR:bitsize> - 1, <BFP:MODE>mode);
4675 real_2expN (&sub, <GPR:bitsize>, <BFP:MODE>mode);
4676
4677 emit_cmp_and_jump_insns (operands[1],
4678 const_double_from_real_value (cmp, <BFP:MODE>mode),
4679 LT, NULL_RTX, VOIDmode, 0, label1);
4680 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
4681 const_double_from_real_value (sub, <BFP:MODE>mode)));
4682 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
4683 GEN_INT (BFP_RND_TOWARD_MINF)));
4684 emit_jump (label2);
4685
4686 emit_label (label1);
4687 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
4688 operands[1], GEN_INT (BFP_RND_TOWARD_0)));
4689 emit_label (label2);
4690 DONE;
4691 }
4692 })
4693
4694 ; fixuns_trunc(td|dd)si2 expander
4695 (define_expand "fixuns_trunc<mode>si2"
4696 [(parallel
4697 [(set (match_operand:SI 0 "register_operand" "")
4698 (unsigned_fix:SI (match_operand:DFP 1 "register_operand" "")))
4699 (unspec:SI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4700 (clobber (reg:CC CC_REGNUM))])]
4701 "TARGET_Z196 && TARGET_HARD_DFP"
4702 "")
4703
4704 ; fixuns_trunc(tf|df|sf|td|dd)(di|si)2 instruction patterns.
4705
4706 (define_insn "*fixuns_truncdfdi2_z13"
4707 [(set (match_operand:DI 0 "register_operand" "=d,v")
4708 (unsigned_fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4709 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4710 (clobber (reg:CC CC_REGNUM))]
4711 "TARGET_VX && TARGET_HARD_FLOAT"
4712 "@
4713 clgdbr\t%0,%h2,%1,0
4714 wclgdb\t%v0,%v1,0,%h2"
4715 [(set_attr "op_type" "RRF,VRR")
4716 (set_attr "type" "ftoi")])
4717
4718 ; clfebr, clfdbr, clfxbr, clgebr, clgdbr, clgxbr
4719 ; clfdtr, clfxtr, clgdtr, clgxtr
4720 (define_insn "*fixuns_trunc<FP:mode><GPR:mode>2_z196"
4721 [(set (match_operand:GPR 0 "register_operand" "=d")
4722 (unsigned_fix:GPR (match_operand:FP 1 "register_operand" "f")))
4723 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4724 (clobber (reg:CC CC_REGNUM))]
4725 "TARGET_Z196 && TARGET_HARD_FLOAT
4726 && (!TARGET_VX || <GPR:MODE>mode != DImode || <FP:MODE>mode != DFmode)"
4727 "cl<GPR:gf><FP:xde><FP:bt>r\t%0,%h2,%1,0"
4728 [(set_attr "op_type" "RRF")
4729 (set_attr "type" "ftoi")])
4730
4731 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
4732 [(set (match_operand:GPR 0 "register_operand" "")
4733 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
4734 "TARGET_HARD_FLOAT"
4735 {
4736 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
4737 GEN_INT (BFP_RND_TOWARD_0)));
4738 DONE;
4739 })
4740
4741 (define_insn "*fix_truncdfdi2_bfp_z13"
4742 [(set (match_operand:DI 0 "register_operand" "=d,v")
4743 (fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4744 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4745 (clobber (reg:CC CC_REGNUM))]
4746 "TARGET_VX && TARGET_HARD_FLOAT"
4747 "@
4748 cgdbr\t%0,%h2,%1
4749 wcgdb\t%v0,%v1,0,%h2"
4750 [(set_attr "op_type" "RRE,VRR")
4751 (set_attr "type" "ftoi")])
4752
4753 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
4754 (define_insn "*fix_trunc<BFP:mode><GPR:mode>2_bfp"
4755 [(set (match_operand:GPR 0 "register_operand" "=d")
4756 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4757 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4758 (clobber (reg:CC CC_REGNUM))]
4759 "TARGET_HARD_FLOAT
4760 && (!TARGET_VX || <GPR:MODE>mode != DImode || <BFP:MODE>mode != DFmode)"
4761 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
4762 [(set_attr "op_type" "RRE")
4763 (set_attr "type" "ftoi")])
4764
4765 (define_expand "fix_trunc<BFP:mode><GPR:mode>2_bfp"
4766 [(parallel
4767 [(set (match_operand:GPR 0 "register_operand" "=d")
4768 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4769 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4770 (clobber (reg:CC CC_REGNUM))])]
4771 "TARGET_HARD_FLOAT")
4772 ;
4773 ; fix_trunc(td|dd)di2 instruction pattern(s).
4774 ;
4775
4776 (define_expand "fix_trunc<mode>di2"
4777 [(set (match_operand:DI 0 "register_operand" "")
4778 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
4779 "TARGET_ZARCH && TARGET_HARD_DFP"
4780 {
4781 operands[1] = force_reg (<MODE>mode, operands[1]);
4782 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
4783 GEN_INT (DFP_RND_TOWARD_0)));
4784 DONE;
4785 })
4786
4787 ; cgxtr, cgdtr
4788 (define_insn "fix_trunc<DFP:mode>di2_dfp"
4789 [(set (match_operand:DI 0 "register_operand" "=d")
4790 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
4791 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
4792 (clobber (reg:CC CC_REGNUM))]
4793 "TARGET_ZARCH && TARGET_HARD_DFP"
4794 "cg<DFP:xde>tr\t%0,%h2,%1"
4795 [(set_attr "op_type" "RRF")
4796 (set_attr "type" "ftoidfp")])
4797
4798
4799 ;
4800 ; fix_trunctf(si|di)2 instruction pattern(s).
4801 ;
4802
4803 (define_expand "fix_trunctf<mode>2"
4804 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
4805 (fix:GPR (match_operand:TF 1 "register_operand" "")))
4806 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4807 (clobber (reg:CC CC_REGNUM))])]
4808 "TARGET_HARD_FLOAT"
4809 "")
4810
4811
4812 ;
4813 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4814 ;
4815
4816 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
4817 (define_insn "floatdi<mode>2"
4818 [(set (match_operand:FP 0 "register_operand" "=f,v")
4819 (float:FP (match_operand:DI 1 "register_operand" "d,v")))]
4820 "TARGET_ZARCH && TARGET_HARD_FLOAT"
4821 "@
4822 c<xde>g<bt>r\t%0,%1
4823 wcdgb\t%v0,%v1,0,0"
4824 [(set_attr "op_type" "RRE,VRR")
4825 (set_attr "type" "itof<mode>" )
4826 (set_attr "cpu_facility" "*,vec")
4827 (set_attr "enabled" "*,<DFDI>")])
4828
4829 ; cxfbr, cdfbr, cefbr
4830 (define_insn "floatsi<mode>2"
4831 [(set (match_operand:BFP 0 "register_operand" "=f")
4832 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
4833 "TARGET_HARD_FLOAT"
4834 "c<xde>fbr\t%0,%1"
4835 [(set_attr "op_type" "RRE")
4836 (set_attr "type" "itof<mode>" )])
4837
4838 ; cxftr, cdftr
4839 (define_insn "floatsi<mode>2"
4840 [(set (match_operand:DFP 0 "register_operand" "=f")
4841 (float:DFP (match_operand:SI 1 "register_operand" "d")))]
4842 "TARGET_Z196 && TARGET_HARD_FLOAT"
4843 "c<xde>ftr\t%0,0,%1,0"
4844 [(set_attr "op_type" "RRE")
4845 (set_attr "type" "itof<mode>" )])
4846
4847 ;
4848 ; floatuns(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4849 ;
4850
4851 (define_insn "*floatunsdidf2_z13"
4852 [(set (match_operand:DF 0 "register_operand" "=f,v")
4853 (unsigned_float:DF (match_operand:DI 1 "register_operand" "d,v")))]
4854 "TARGET_VX && TARGET_HARD_FLOAT"
4855 "@
4856 cdlgbr\t%0,0,%1,0
4857 wcdlgb\t%v0,%v1,0,0"
4858 [(set_attr "op_type" "RRE,VRR")
4859 (set_attr "type" "itofdf")])
4860
4861 ; cxlgbr, cdlgbr, celgbr, cxlgtr, cdlgtr
4862 ; cxlfbr, cdlfbr, celfbr, cxlftr, cdlftr
4863 (define_insn "*floatuns<GPR:mode><FP:mode>2"
4864 [(set (match_operand:FP 0 "register_operand" "=f")
4865 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "d")))]
4866 "TARGET_Z196 && TARGET_HARD_FLOAT
4867 && (!TARGET_VX || <FP:MODE>mode != DFmode || <GPR:MODE>mode != DImode)"
4868 "c<FP:xde>l<GPR:gf><FP:bt>r\t%0,0,%1,0"
4869 [(set_attr "op_type" "RRE")
4870 (set_attr "type" "itof<FP:mode>")])
4871
4872 (define_expand "floatuns<GPR:mode><FP:mode>2"
4873 [(set (match_operand:FP 0 "register_operand" "")
4874 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "")))]
4875 "TARGET_Z196 && TARGET_HARD_FLOAT")
4876
4877 ;
4878 ; truncdfsf2 instruction pattern(s).
4879 ;
4880
4881 (define_insn "truncdfsf2"
4882 [(set (match_operand:SF 0 "register_operand" "=f,v")
4883 (float_truncate:SF (match_operand:DF 1 "register_operand" "f,v")))]
4884 "TARGET_HARD_FLOAT"
4885 "@
4886 ledbr\t%0,%1
4887 wledb\t%v0,%v1,0,0" ; IEEE inexact exception not suppressed
4888 ; According to BFP rounding mode
4889 [(set_attr "op_type" "RRE,VRR")
4890 (set_attr "type" "ftruncdf")
4891 (set_attr "cpu_facility" "*,vec")])
4892
4893 ;
4894 ; trunctf(df|sf)2 instruction pattern(s).
4895 ;
4896
4897 ; ldxbr, lexbr
4898 (define_insn "trunctf<mode>2"
4899 [(set (match_operand:DSF 0 "register_operand" "=f")
4900 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
4901 (clobber (match_scratch:TF 2 "=f"))]
4902 "TARGET_HARD_FLOAT"
4903 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
4904 [(set_attr "length" "6")
4905 (set_attr "type" "ftrunctf")])
4906
4907 ;
4908 ; trunctddd2 and truncddsd2 instruction pattern(s).
4909 ;
4910
4911
4912 (define_expand "trunctddd2"
4913 [(parallel
4914 [(set (match_operand:DD 0 "register_operand" "")
4915 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
4916 (unspec:DI [(const_int DFP_RND_CURRENT)] UNSPEC_ROUND)
4917 (clobber (scratch:TD))])]
4918 "TARGET_HARD_DFP")
4919
4920 (define_insn "*trunctddd2"
4921 [(set (match_operand:DD 0 "register_operand" "=f")
4922 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
4923 (unspec:DI [(match_operand:DI 2 "const_mask_operand" "I")] UNSPEC_ROUND)
4924 (clobber (match_scratch:TD 3 "=f"))]
4925 "TARGET_HARD_DFP"
4926 "ldxtr\t%3,%2,%1,0\;ldr\t%0,%3"
4927 [(set_attr "length" "6")
4928 (set_attr "type" "ftruncdd")])
4929
4930 (define_insn "truncddsd2"
4931 [(set (match_operand:SD 0 "register_operand" "=f")
4932 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
4933 "TARGET_HARD_DFP"
4934 "ledtr\t%0,0,%1,0"
4935 [(set_attr "op_type" "RRF")
4936 (set_attr "type" "ftruncsd")])
4937
4938 (define_expand "trunctdsd2"
4939 [(parallel
4940 [(set (match_dup 3)
4941 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
4942 (unspec:DI [(const_int DFP_RND_PREP_FOR_SHORT_PREC)] UNSPEC_ROUND)
4943 (clobber (match_scratch:TD 2 ""))])
4944 (set (match_operand:SD 0 "register_operand" "")
4945 (float_truncate:SD (match_dup 3)))]
4946 "TARGET_HARD_DFP"
4947 {
4948 operands[3] = gen_reg_rtx (DDmode);
4949 })
4950
4951 ;
4952 ; extend(sf|df)(df|tf)2 instruction pattern(s).
4953 ;
4954
4955 (define_insn "*extendsfdf2_z13"
4956 [(set (match_operand:DF 0 "register_operand" "=f,f,v")
4957 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,R,v")))]
4958 "TARGET_VX && TARGET_HARD_FLOAT"
4959 "@
4960 ldebr\t%0,%1
4961 ldeb\t%0,%1
4962 wldeb\t%v0,%v1"
4963 [(set_attr "op_type" "RRE,RXE,VRR")
4964 (set_attr "type" "fsimpdf, floaddf,fsimpdf")])
4965
4966 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
4967 (define_insn "*extend<DSF:mode><BFP:mode>2"
4968 [(set (match_operand:BFP 0 "register_operand" "=f,f")
4969 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
4970 "TARGET_HARD_FLOAT
4971 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)
4972 && (!TARGET_VX || <BFP:MODE>mode != DFmode || <DSF:MODE>mode != SFmode)"
4973 "@
4974 l<BFP:xde><DSF:xde>br\t%0,%1
4975 l<BFP:xde><DSF:xde>b\t%0,%1"
4976 [(set_attr "op_type" "RRE,RXE")
4977 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
4978
4979 (define_expand "extend<DSF:mode><BFP:mode>2"
4980 [(set (match_operand:BFP 0 "register_operand" "")
4981 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "")))]
4982 "TARGET_HARD_FLOAT
4983 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)")
4984
4985 ;
4986 ; extendddtd2 and extendsddd2 instruction pattern(s).
4987 ;
4988
4989 (define_insn "extendddtd2"
4990 [(set (match_operand:TD 0 "register_operand" "=f")
4991 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
4992 "TARGET_HARD_DFP"
4993 "lxdtr\t%0,%1,0"
4994 [(set_attr "op_type" "RRF")
4995 (set_attr "type" "fsimptf")])
4996
4997 (define_insn "extendsddd2"
4998 [(set (match_operand:DD 0 "register_operand" "=f")
4999 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
5000 "TARGET_HARD_DFP"
5001 "ldetr\t%0,%1,0"
5002 [(set_attr "op_type" "RRF")
5003 (set_attr "type" "fsimptf")])
5004
5005 (define_expand "extendsdtd2"
5006 [(set (match_dup 2)
5007 (float_extend:DD (match_operand:SD 1 "register_operand" "")))
5008 (set (match_operand:TD 0 "register_operand" "")
5009 (float_extend:TD (match_dup 2)))]
5010 "TARGET_HARD_DFP"
5011 {
5012 operands[2] = gen_reg_rtx (DDmode);
5013 })
5014
5015 ; Binary Floating Point - load fp integer
5016
5017 ; Expanders for: floor, btrunc, round, ceil, and nearbyint
5018 ; For all of them the inexact exceptions are suppressed.
5019
5020 ; fiebra, fidbra, fixbra
5021 (define_insn "<FPINT:fpint_name><BFP:mode>2"
5022 [(set (match_operand:BFP 0 "register_operand" "=f")
5023 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5024 FPINT))]
5025 "TARGET_Z196"
5026 "fi<BFP:xde>bra\t%0,<FPINT:fpint_roundingmode>,%1,4"
5027 [(set_attr "op_type" "RRF")
5028 (set_attr "type" "fsimp<BFP:mode>")])
5029
5030 ; rint is supposed to raise an inexact exception so we can use the
5031 ; older instructions.
5032
5033 ; fiebr, fidbr, fixbr
5034 (define_insn "rint<BFP:mode>2"
5035 [(set (match_operand:BFP 0 "register_operand" "=f")
5036 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5037 UNSPEC_FPINT_RINT))]
5038 ""
5039 "fi<BFP:xde>br\t%0,0,%1"
5040 [(set_attr "op_type" "RRF")
5041 (set_attr "type" "fsimp<BFP:mode>")])
5042
5043
5044 ; Decimal Floating Point - load fp integer
5045
5046 ; fidtr, fixtr
5047 (define_insn "<FPINT:fpint_name><DFP:mode>2"
5048 [(set (match_operand:DFP 0 "register_operand" "=f")
5049 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5050 FPINT))]
5051 "TARGET_HARD_DFP"
5052 "fi<DFP:xde>tr\t%0,<FPINT:fpint_roundingmode>,%1,4"
5053 [(set_attr "op_type" "RRF")
5054 (set_attr "type" "fsimp<DFP:mode>")])
5055
5056 ; fidtr, fixtr
5057 (define_insn "rint<DFP:mode>2"
5058 [(set (match_operand:DFP 0 "register_operand" "=f")
5059 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5060 UNSPEC_FPINT_RINT))]
5061 "TARGET_HARD_DFP"
5062 "fi<DFP:xde>tr\t%0,0,%1,0"
5063 [(set_attr "op_type" "RRF")
5064 (set_attr "type" "fsimp<DFP:mode>")])
5065
5066 ;
5067 ; Binary <-> Decimal floating point trunc patterns
5068 ;
5069
5070 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
5071 [(set (reg:DFP_ALL FPR0_REGNUM)
5072 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5073 (use (reg:SI GPR0_REGNUM))
5074 (clobber (reg:CC CC_REGNUM))
5075 (clobber (reg:SI GPR1_REGNUM))]
5076 "TARGET_HARD_DFP"
5077 "pfpo")
5078
5079 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
5080 [(set (reg:BFP FPR0_REGNUM)
5081 (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5082 (use (reg:SI GPR0_REGNUM))
5083 (clobber (reg:CC CC_REGNUM))
5084 (clobber (reg:SI GPR1_REGNUM))]
5085 "TARGET_HARD_DFP"
5086 "pfpo")
5087
5088 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
5089 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5090 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5091 (parallel
5092 [(set (reg:DFP_ALL FPR0_REGNUM)
5093 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5094 (use (reg:SI GPR0_REGNUM))
5095 (clobber (reg:CC CC_REGNUM))
5096 (clobber (reg:SI GPR1_REGNUM))])
5097 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5098 (reg:DFP_ALL FPR0_REGNUM))]
5099 "TARGET_HARD_DFP
5100 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5101 {
5102 HOST_WIDE_INT flags;
5103
5104 flags = (PFPO_CONVERT |
5105 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5106 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5107
5108 operands[2] = GEN_INT (flags);
5109 })
5110
5111 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
5112 [(set (reg:DFP_ALL FPR4_REGNUM)
5113 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5114 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5115 (parallel
5116 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5117 (use (reg:SI GPR0_REGNUM))
5118 (clobber (reg:CC CC_REGNUM))
5119 (clobber (reg:SI GPR1_REGNUM))])
5120 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5121 "TARGET_HARD_DFP
5122 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
5123 {
5124 HOST_WIDE_INT flags;
5125
5126 flags = (PFPO_CONVERT |
5127 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5128 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5129
5130 operands[2] = GEN_INT (flags);
5131 })
5132
5133 ;
5134 ; Binary <-> Decimal floating point extend patterns
5135 ;
5136
5137 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
5138 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5139 (use (reg:SI GPR0_REGNUM))
5140 (clobber (reg:CC CC_REGNUM))
5141 (clobber (reg:SI GPR1_REGNUM))]
5142 "TARGET_HARD_DFP"
5143 "pfpo")
5144
5145 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
5146 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5147 (use (reg:SI GPR0_REGNUM))
5148 (clobber (reg:CC CC_REGNUM))
5149 (clobber (reg:SI GPR1_REGNUM))]
5150 "TARGET_HARD_DFP"
5151 "pfpo")
5152
5153 (define_expand "extend<BFP:mode><DFP_ALL:mode>2"
5154 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5155 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5156 (parallel
5157 [(set (reg:DFP_ALL FPR0_REGNUM)
5158 (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5159 (use (reg:SI GPR0_REGNUM))
5160 (clobber (reg:CC CC_REGNUM))
5161 (clobber (reg:SI GPR1_REGNUM))])
5162 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5163 (reg:DFP_ALL FPR0_REGNUM))]
5164 "TARGET_HARD_DFP
5165 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5166 {
5167 HOST_WIDE_INT flags;
5168
5169 flags = (PFPO_CONVERT |
5170 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5171 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5172
5173 operands[2] = GEN_INT (flags);
5174 })
5175
5176 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
5177 [(set (reg:DFP_ALL FPR4_REGNUM)
5178 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5179 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5180 (parallel
5181 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5182 (use (reg:SI GPR0_REGNUM))
5183 (clobber (reg:CC CC_REGNUM))
5184 (clobber (reg:SI GPR1_REGNUM))])
5185 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5186 "TARGET_HARD_DFP
5187 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
5188 {
5189 HOST_WIDE_INT flags;
5190
5191 flags = (PFPO_CONVERT |
5192 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5193 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5194
5195 operands[2] = GEN_INT (flags);
5196 })
5197
5198
5199 ;;
5200 ;; ARITHMETIC OPERATIONS
5201 ;;
5202 ; arithmetic operations set the ConditionCode,
5203 ; because of unpredictable Bits in Register for Halfword and Byte
5204 ; the ConditionCode can be set wrong in operations for Halfword and Byte
5205
5206 ;;
5207 ;;- Add instructions.
5208 ;;
5209
5210 ;
5211 ; addti3 instruction pattern(s).
5212 ;
5213
5214 (define_expand "addti3"
5215 [(parallel
5216 [(set (match_operand:TI 0 "register_operand" "")
5217 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5218 (match_operand:TI 2 "general_operand" "") ) )
5219 (clobber (reg:CC CC_REGNUM))])]
5220 "TARGET_ZARCH"
5221 {
5222 /* For z13 we have vaq which doesn't set CC. */
5223 if (TARGET_VX)
5224 {
5225 emit_insn (gen_rtx_SET (operands[0],
5226 gen_rtx_PLUS (TImode,
5227 copy_to_mode_reg (TImode, operands[1]),
5228 copy_to_mode_reg (TImode, operands[2]))));
5229 DONE;
5230 }
5231 })
5232
5233 (define_insn_and_split "*addti3"
5234 [(set (match_operand:TI 0 "register_operand" "=&d")
5235 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
5236 (match_operand:TI 2 "general_operand" "do") ) )
5237 (clobber (reg:CC CC_REGNUM))]
5238 "TARGET_ZARCH"
5239 "#"
5240 "&& reload_completed"
5241 [(parallel
5242 [(set (reg:CCL1 CC_REGNUM)
5243 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
5244 (match_dup 7)))
5245 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
5246 (parallel
5247 [(set (match_dup 3) (plus:DI
5248 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
5249 (match_dup 4)) (match_dup 5)))
5250 (clobber (reg:CC CC_REGNUM))])]
5251 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5252 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5253 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5254 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5255 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5256 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5257 [(set_attr "op_type" "*")
5258 (set_attr "cpu_facility" "*")])
5259
5260 ;
5261 ; adddi3 instruction pattern(s).
5262 ;
5263
5264 (define_expand "adddi3"
5265 [(parallel
5266 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5267 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5268 (match_operand:DI 2 "general_operand" "")))
5269 (clobber (reg:CC CC_REGNUM))])]
5270 ""
5271 "")
5272
5273 (define_insn "*adddi3_sign"
5274 [(set (match_operand:DI 0 "register_operand" "=d,d")
5275 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5276 (match_operand:DI 1 "register_operand" "0,0")))
5277 (clobber (reg:CC CC_REGNUM))]
5278 "TARGET_ZARCH"
5279 "@
5280 agfr\t%0,%2
5281 agf\t%0,%2"
5282 [(set_attr "op_type" "RRE,RXY")
5283 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5284
5285 (define_insn "*adddi3_zero_cc"
5286 [(set (reg CC_REGNUM)
5287 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5288 (match_operand:DI 1 "register_operand" "0,0"))
5289 (const_int 0)))
5290 (set (match_operand:DI 0 "register_operand" "=d,d")
5291 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
5292 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5293 "@
5294 algfr\t%0,%2
5295 algf\t%0,%2"
5296 [(set_attr "op_type" "RRE,RXY")
5297 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5298
5299 (define_insn "*adddi3_zero_cconly"
5300 [(set (reg CC_REGNUM)
5301 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5302 (match_operand:DI 1 "register_operand" "0,0"))
5303 (const_int 0)))
5304 (clobber (match_scratch:DI 0 "=d,d"))]
5305 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5306 "@
5307 algfr\t%0,%2
5308 algf\t%0,%2"
5309 [(set_attr "op_type" "RRE,RXY")
5310 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5311
5312 (define_insn "*adddi3_zero"
5313 [(set (match_operand:DI 0 "register_operand" "=d,d")
5314 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5315 (match_operand:DI 1 "register_operand" "0,0")))
5316 (clobber (reg:CC CC_REGNUM))]
5317 "TARGET_ZARCH"
5318 "@
5319 algfr\t%0,%2
5320 algf\t%0,%2"
5321 [(set_attr "op_type" "RRE,RXY")
5322 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5323
5324 (define_insn_and_split "*adddi3_31z"
5325 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5326 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5327 (match_operand:DI 2 "general_operand" "do") ) )
5328 (clobber (reg:CC CC_REGNUM))]
5329 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5330 "#"
5331 "&& reload_completed"
5332 [(parallel
5333 [(set (reg:CCL1 CC_REGNUM)
5334 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5335 (match_dup 7)))
5336 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5337 (parallel
5338 [(set (match_dup 3) (plus:SI
5339 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
5340 (match_dup 4)) (match_dup 5)))
5341 (clobber (reg:CC CC_REGNUM))])]
5342 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5343 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5344 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5345 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5346 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5347 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5348
5349 (define_insn_and_split "*adddi3_31"
5350 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5351 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5352 (match_operand:DI 2 "general_operand" "do") ) )
5353 (clobber (reg:CC CC_REGNUM))]
5354 "!TARGET_CPU_ZARCH"
5355 "#"
5356 "&& reload_completed"
5357 [(parallel
5358 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
5359 (clobber (reg:CC CC_REGNUM))])
5360 (parallel
5361 [(set (reg:CCL1 CC_REGNUM)
5362 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5363 (match_dup 7)))
5364 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5365 (set (pc)
5366 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
5367 (pc)
5368 (label_ref (match_dup 9))))
5369 (parallel
5370 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
5371 (clobber (reg:CC CC_REGNUM))])
5372 (match_dup 9)]
5373 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5374 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5375 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5376 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5377 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5378 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5379 operands[9] = gen_label_rtx ();")
5380
5381 ;
5382 ; addsi3 instruction pattern(s).
5383 ;
5384
5385 (define_expand "addsi3"
5386 [(parallel
5387 [(set (match_operand:SI 0 "nonimmediate_operand" "")
5388 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5389 (match_operand:SI 2 "general_operand" "")))
5390 (clobber (reg:CC CC_REGNUM))])]
5391 ""
5392 "")
5393
5394 (define_insn "*addsi3_sign"
5395 [(set (match_operand:SI 0 "register_operand" "=d,d")
5396 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
5397 (match_operand:SI 1 "register_operand" "0,0")))
5398 (clobber (reg:CC CC_REGNUM))]
5399 ""
5400 "@
5401 ah\t%0,%2
5402 ahy\t%0,%2"
5403 [(set_attr "op_type" "RX,RXY")
5404 (set_attr "cpu_facility" "*,longdisp")
5405 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5406
5407 ;
5408 ; add(di|si)3 instruction pattern(s).
5409 ;
5410
5411 ; ark, agrk, ar, ahi, ahik, aghik, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
5412 (define_insn "*add<mode>3"
5413 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d, d, d,d,d,S")
5414 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,d, 0, 0,0,0,0")
5415 (match_operand:GPR 2 "general_operand" " d,d,K,K,Op,On,R,T,C") ) )
5416 (clobber (reg:CC CC_REGNUM))]
5417 ""
5418 "@
5419 a<g>r\t%0,%2
5420 a<g>rk\t%0,%1,%2
5421 a<g>hi\t%0,%h2
5422 a<g>hik\t%0,%1,%h2
5423 al<g>fi\t%0,%2
5424 sl<g>fi\t%0,%n2
5425 a<g>\t%0,%2
5426 a<y>\t%0,%2
5427 a<g>si\t%0,%c2"
5428 [(set_attr "op_type" "RR<E>,RRF,RI,RIE,RIL,RIL,RX<Y>,RXY,SIY")
5429 (set_attr "cpu_facility" "*,z196,*,z196,extimm,extimm,*,longdisp,z10")
5430 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,z10_super_E1,z10_super_E1,
5431 z10_super_E1,z10_super_E1,z10_super_E1")])
5432
5433 ; alr, alfi, slfi, al, aly, alrk, alhsik, algr, algfi, slgfi, alg, alsi, algsi, algrk, alghsik
5434 (define_insn "*add<mode>3_carry1_cc"
5435 [(set (reg CC_REGNUM)
5436 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5437 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5438 (match_dup 1)))
5439 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,d")
5440 (plus:GPR (match_dup 1) (match_dup 2)))]
5441 "s390_match_ccmode (insn, CCL1mode)"
5442 "@
5443 al<g>r\t%0,%2
5444 al<g>rk\t%0,%1,%2
5445 al<g>fi\t%0,%2
5446 sl<g>fi\t%0,%n2
5447 al<g>hsik\t%0,%1,%h2
5448 al<g>\t%0,%2
5449 al<y>\t%0,%2
5450 al<g>si\t%0,%c2"
5451 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5452 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5453 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5454 z10_super_E1,z10_super_E1,z10_super_E1")])
5455
5456 ; alr, al, aly, algr, alg, alrk, algrk
5457 (define_insn "*add<mode>3_carry1_cconly"
5458 [(set (reg CC_REGNUM)
5459 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5460 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5461 (match_dup 1)))
5462 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5463 "s390_match_ccmode (insn, CCL1mode)"
5464 "@
5465 al<g>r\t%0,%2
5466 al<g>rk\t%0,%1,%2
5467 al<g>\t%0,%2
5468 al<y>\t%0,%2"
5469 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5470 (set_attr "cpu_facility" "*,z196,*,longdisp")
5471 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5472
5473 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5474 (define_insn "*add<mode>3_carry2_cc"
5475 [(set (reg CC_REGNUM)
5476 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5477 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5478 (match_dup 2)))
5479 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5480 (plus:GPR (match_dup 1) (match_dup 2)))]
5481 "s390_match_ccmode (insn, CCL1mode)"
5482 "@
5483 al<g>r\t%0,%2
5484 al<g>rk\t%0,%1,%2
5485 al<g>fi\t%0,%2
5486 sl<g>fi\t%0,%n2
5487 al<g>hsik\t%0,%1,%h2
5488 al<g>\t%0,%2
5489 al<y>\t%0,%2
5490 al<g>si\t%0,%c2"
5491 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5492 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5493 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5494 z10_super_E1,z10_super_E1,z10_super_E1")])
5495
5496 ; alr, al, aly, algr, alg, alrk, algrk
5497 (define_insn "*add<mode>3_carry2_cconly"
5498 [(set (reg CC_REGNUM)
5499 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5500 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5501 (match_dup 2)))
5502 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5503 "s390_match_ccmode (insn, CCL1mode)"
5504 "@
5505 al<g>r\t%0,%2
5506 al<g>rk\t%0,%1,%2
5507 al<g>\t%0,%2
5508 al<y>\t%0,%2"
5509 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5510 (set_attr "cpu_facility" "*,z196,*,longdisp")
5511 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5512
5513 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5514 (define_insn "*add<mode>3_cc"
5515 [(set (reg CC_REGNUM)
5516 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5517 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5518 (const_int 0)))
5519 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5520 (plus:GPR (match_dup 1) (match_dup 2)))]
5521 "s390_match_ccmode (insn, CCLmode)"
5522 "@
5523 al<g>r\t%0,%2
5524 al<g>rk\t%0,%1,%2
5525 al<g>fi\t%0,%2
5526 sl<g>fi\t%0,%n2
5527 al<g>hsik\t%0,%1,%h2
5528 al<g>\t%0,%2
5529 al<y>\t%0,%2
5530 al<g>si\t%0,%c2"
5531 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5532 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5533 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,
5534 *,z10_super_E1,z10_super_E1,z10_super_E1")])
5535
5536 ; alr, al, aly, algr, alg, alrk, algrk
5537 (define_insn "*add<mode>3_cconly"
5538 [(set (reg CC_REGNUM)
5539 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5540 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5541 (const_int 0)))
5542 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5543 "s390_match_ccmode (insn, CCLmode)"
5544 "@
5545 al<g>r\t%0,%2
5546 al<g>rk\t%0,%1,%2
5547 al<g>\t%0,%2
5548 al<y>\t%0,%2"
5549 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5550 (set_attr "cpu_facility" "*,z196,*,longdisp")
5551 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5552
5553 ; alr, al, aly, algr, alg, alrk, algrk
5554 (define_insn "*add<mode>3_cconly2"
5555 [(set (reg CC_REGNUM)
5556 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5557 (neg:GPR (match_operand:GPR 2 "general_operand" "d,d,R,T"))))
5558 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5559 "s390_match_ccmode(insn, CCLmode)"
5560 "@
5561 al<g>r\t%0,%2
5562 al<g>rk\t%0,%1,%2
5563 al<g>\t%0,%2
5564 al<y>\t%0,%2"
5565 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5566 (set_attr "cpu_facility" "*,z196,*,longdisp")
5567 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5568
5569 ; ahi, afi, aghi, agfi, asi, agsi
5570 (define_insn "*add<mode>3_imm_cc"
5571 [(set (reg CC_REGNUM)
5572 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" " 0, d,0, 0")
5573 (match_operand:GPR 2 "const_int_operand" " K, K,Os,C"))
5574 (const_int 0)))
5575 (set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,d, S")
5576 (plus:GPR (match_dup 1) (match_dup 2)))]
5577 "s390_match_ccmode (insn, CCAmode)
5578 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
5579 || (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
5580 /* Avoid INT32_MIN on 32 bit. */
5581 && (!TARGET_ZARCH || INTVAL (operands[2]) != -0x7fffffff - 1)))"
5582 "@
5583 a<g>hi\t%0,%h2
5584 a<g>hik\t%0,%1,%h2
5585 a<g>fi\t%0,%2
5586 a<g>si\t%0,%c2"
5587 [(set_attr "op_type" "RI,RIE,RIL,SIY")
5588 (set_attr "cpu_facility" "*,z196,extimm,z10")
5589 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5590
5591 ;
5592 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
5593 ;
5594
5595 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5596 ; FIXME: wfadb does not clobber cc
5597 (define_insn "add<mode>3"
5598 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
5599 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
5600 (match_operand:FP 2 "general_operand" "f,f,R,v")))
5601 (clobber (reg:CC CC_REGNUM))]
5602 "TARGET_HARD_FLOAT"
5603 "@
5604 a<xde>tr\t%0,%1,%2
5605 a<xde>br\t%0,%2
5606 a<xde>b\t%0,%2
5607 wfadb\t%v0,%v1,%v2"
5608 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
5609 (set_attr "type" "fsimp<mode>")
5610 (set_attr "cpu_facility" "*,*,*,vec")
5611 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
5612
5613 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5614 (define_insn "*add<mode>3_cc"
5615 [(set (reg CC_REGNUM)
5616 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5617 (match_operand:FP 2 "general_operand" "f,f,R"))
5618 (match_operand:FP 3 "const0_operand" "")))
5619 (set (match_operand:FP 0 "register_operand" "=f,f,f")
5620 (plus:FP (match_dup 1) (match_dup 2)))]
5621 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5622 "@
5623 a<xde>tr\t%0,%1,%2
5624 a<xde>br\t%0,%2
5625 a<xde>b\t%0,%2"
5626 [(set_attr "op_type" "RRF,RRE,RXE")
5627 (set_attr "type" "fsimp<mode>")
5628 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5629
5630 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5631 (define_insn "*add<mode>3_cconly"
5632 [(set (reg CC_REGNUM)
5633 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5634 (match_operand:FP 2 "general_operand" "f,f,R"))
5635 (match_operand:FP 3 "const0_operand" "")))
5636 (clobber (match_scratch:FP 0 "=f,f,f"))]
5637 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5638 "@
5639 a<xde>tr\t%0,%1,%2
5640 a<xde>br\t%0,%2
5641 a<xde>b\t%0,%2"
5642 [(set_attr "op_type" "RRF,RRE,RXE")
5643 (set_attr "type" "fsimp<mode>")
5644 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5645
5646 ;
5647 ; Pointer add instruction patterns
5648 ;
5649
5650 ; This will match "*la_64"
5651 (define_expand "addptrdi3"
5652 [(set (match_operand:DI 0 "register_operand" "")
5653 (plus:DI (match_operand:DI 1 "register_operand" "")
5654 (match_operand:DI 2 "nonmemory_operand" "")))]
5655 "TARGET_64BIT"
5656 {
5657 if (GET_CODE (operands[2]) == CONST_INT)
5658 {
5659 HOST_WIDE_INT c = INTVAL (operands[2]);
5660
5661 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5662 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5663 {
5664 operands[2] = force_const_mem (DImode, operands[2]);
5665 operands[2] = force_reg (DImode, operands[2]);
5666 }
5667 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5668 operands[2] = force_reg (DImode, operands[2]);
5669 }
5670 })
5671
5672 ; For 31 bit we have to prevent the generated pattern from matching
5673 ; normal ADDs since la only does a 31 bit add. This is supposed to
5674 ; match "force_la_31".
5675 (define_expand "addptrsi3"
5676 [(parallel
5677 [(set (match_operand:SI 0 "register_operand" "")
5678 (plus:SI (match_operand:SI 1 "register_operand" "")
5679 (match_operand:SI 2 "nonmemory_operand" "")))
5680 (use (const_int 0))])]
5681 "!TARGET_64BIT"
5682 {
5683 if (GET_CODE (operands[2]) == CONST_INT)
5684 {
5685 HOST_WIDE_INT c = INTVAL (operands[2]);
5686
5687 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5688 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5689 {
5690 operands[2] = force_const_mem (SImode, operands[2]);
5691 operands[2] = force_reg (SImode, operands[2]);
5692 }
5693 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5694 operands[2] = force_reg (SImode, operands[2]);
5695 }
5696 })
5697
5698 ;;
5699 ;;- Subtract instructions.
5700 ;;
5701
5702 ;
5703 ; subti3 instruction pattern(s).
5704 ;
5705
5706 (define_expand "subti3"
5707 [(parallel
5708 [(set (match_operand:TI 0 "register_operand" "")
5709 (minus:TI (match_operand:TI 1 "register_operand" "")
5710 (match_operand:TI 2 "general_operand" "") ) )
5711 (clobber (reg:CC CC_REGNUM))])]
5712 "TARGET_ZARCH"
5713 {
5714 /* For z13 we have vaq which doesn't set CC. */
5715 if (TARGET_VX)
5716 {
5717 emit_insn (gen_rtx_SET (operands[0],
5718 gen_rtx_MINUS (TImode,
5719 operands[1],
5720 copy_to_mode_reg (TImode, operands[2]))));
5721 DONE;
5722 }
5723 })
5724
5725 (define_insn_and_split "*subti3"
5726 [(set (match_operand:TI 0 "register_operand" "=&d")
5727 (minus:TI (match_operand:TI 1 "register_operand" "0")
5728 (match_operand:TI 2 "general_operand" "do") ) )
5729 (clobber (reg:CC CC_REGNUM))]
5730 "TARGET_ZARCH"
5731 "#"
5732 "&& reload_completed"
5733 [(parallel
5734 [(set (reg:CCL2 CC_REGNUM)
5735 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
5736 (match_dup 7)))
5737 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
5738 (parallel
5739 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
5740 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
5741 (clobber (reg:CC CC_REGNUM))])]
5742 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5743 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5744 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5745 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5746 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5747 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5748 [(set_attr "op_type" "*")
5749 (set_attr "cpu_facility" "*")])
5750
5751 ;
5752 ; subdi3 instruction pattern(s).
5753 ;
5754
5755 (define_expand "subdi3"
5756 [(parallel
5757 [(set (match_operand:DI 0 "register_operand" "")
5758 (minus:DI (match_operand:DI 1 "register_operand" "")
5759 (match_operand:DI 2 "general_operand" "")))
5760 (clobber (reg:CC CC_REGNUM))])]
5761 ""
5762 "")
5763
5764 (define_insn "*subdi3_sign"
5765 [(set (match_operand:DI 0 "register_operand" "=d,d")
5766 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5767 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5768 (clobber (reg:CC CC_REGNUM))]
5769 "TARGET_ZARCH"
5770 "@
5771 sgfr\t%0,%2
5772 sgf\t%0,%2"
5773 [(set_attr "op_type" "RRE,RXY")
5774 (set_attr "z10prop" "z10_c,*")
5775 (set_attr "z196prop" "z196_cracked")])
5776
5777 (define_insn "*subdi3_zero_cc"
5778 [(set (reg CC_REGNUM)
5779 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5780 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5781 (const_int 0)))
5782 (set (match_operand:DI 0 "register_operand" "=d,d")
5783 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
5784 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5785 "@
5786 slgfr\t%0,%2
5787 slgf\t%0,%2"
5788 [(set_attr "op_type" "RRE,RXY")
5789 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5790
5791 (define_insn "*subdi3_zero_cconly"
5792 [(set (reg CC_REGNUM)
5793 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5794 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5795 (const_int 0)))
5796 (clobber (match_scratch:DI 0 "=d,d"))]
5797 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5798 "@
5799 slgfr\t%0,%2
5800 slgf\t%0,%2"
5801 [(set_attr "op_type" "RRE,RXY")
5802 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5803
5804 (define_insn "*subdi3_zero"
5805 [(set (match_operand:DI 0 "register_operand" "=d,d")
5806 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5807 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5808 (clobber (reg:CC CC_REGNUM))]
5809 "TARGET_ZARCH"
5810 "@
5811 slgfr\t%0,%2
5812 slgf\t%0,%2"
5813 [(set_attr "op_type" "RRE,RXY")
5814 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5815
5816 (define_insn_and_split "*subdi3_31z"
5817 [(set (match_operand:DI 0 "register_operand" "=&d")
5818 (minus:DI (match_operand:DI 1 "register_operand" "0")
5819 (match_operand:DI 2 "general_operand" "do") ) )
5820 (clobber (reg:CC CC_REGNUM))]
5821 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5822 "#"
5823 "&& reload_completed"
5824 [(parallel
5825 [(set (reg:CCL2 CC_REGNUM)
5826 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5827 (match_dup 7)))
5828 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5829 (parallel
5830 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
5831 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
5832 (clobber (reg:CC CC_REGNUM))])]
5833 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5834 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5835 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5836 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5837 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5838 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5839
5840 (define_insn_and_split "*subdi3_31"
5841 [(set (match_operand:DI 0 "register_operand" "=&d")
5842 (minus:DI (match_operand:DI 1 "register_operand" "0")
5843 (match_operand:DI 2 "general_operand" "do") ) )
5844 (clobber (reg:CC CC_REGNUM))]
5845 "!TARGET_CPU_ZARCH"
5846 "#"
5847 "&& reload_completed"
5848 [(parallel
5849 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
5850 (clobber (reg:CC CC_REGNUM))])
5851 (parallel
5852 [(set (reg:CCL2 CC_REGNUM)
5853 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5854 (match_dup 7)))
5855 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5856 (set (pc)
5857 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
5858 (pc)
5859 (label_ref (match_dup 9))))
5860 (parallel
5861 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
5862 (clobber (reg:CC CC_REGNUM))])
5863 (match_dup 9)]
5864 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5865 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5866 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5867 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5868 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5869 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5870 operands[9] = gen_label_rtx ();")
5871
5872 ;
5873 ; subsi3 instruction pattern(s).
5874 ;
5875
5876 (define_expand "subsi3"
5877 [(parallel
5878 [(set (match_operand:SI 0 "register_operand" "")
5879 (minus:SI (match_operand:SI 1 "register_operand" "")
5880 (match_operand:SI 2 "general_operand" "")))
5881 (clobber (reg:CC CC_REGNUM))])]
5882 ""
5883 "")
5884
5885 (define_insn "*subsi3_sign"
5886 [(set (match_operand:SI 0 "register_operand" "=d,d")
5887 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
5888 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
5889 (clobber (reg:CC CC_REGNUM))]
5890 ""
5891 "@
5892 sh\t%0,%2
5893 shy\t%0,%2"
5894 [(set_attr "op_type" "RX,RXY")
5895 (set_attr "cpu_facility" "*,longdisp")
5896 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5897
5898 ;
5899 ; sub(di|si)3 instruction pattern(s).
5900 ;
5901
5902 ; sr, s, sy, sgr, sg, srk, sgrk
5903 (define_insn "*sub<mode>3"
5904 [(set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5905 (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5906 (match_operand:GPR 2 "general_operand" "d,d,R,T") ) )
5907 (clobber (reg:CC CC_REGNUM))]
5908 ""
5909 "@
5910 s<g>r\t%0,%2
5911 s<g>rk\t%0,%1,%2
5912 s<g>\t%0,%2
5913 s<y>\t%0,%2"
5914 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5915 (set_attr "cpu_facility" "*,z196,*,longdisp")
5916 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5917
5918 ; slr, sl, sly, slgr, slg, slrk, slgrk
5919 (define_insn "*sub<mode>3_borrow_cc"
5920 [(set (reg CC_REGNUM)
5921 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5922 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5923 (match_dup 1)))
5924 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5925 (minus:GPR (match_dup 1) (match_dup 2)))]
5926 "s390_match_ccmode (insn, CCL2mode)"
5927 "@
5928 sl<g>r\t%0,%2
5929 sl<g>rk\t%0,%1,%2
5930 sl<g>\t%0,%2
5931 sl<y>\t%0,%2"
5932 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5933 (set_attr "cpu_facility" "*,z196,*,longdisp")
5934 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5935
5936 ; slr, sl, sly, slgr, slg, slrk, slgrk
5937 (define_insn "*sub<mode>3_borrow_cconly"
5938 [(set (reg CC_REGNUM)
5939 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5940 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5941 (match_dup 1)))
5942 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5943 "s390_match_ccmode (insn, CCL2mode)"
5944 "@
5945 sl<g>r\t%0,%2
5946 sl<g>rk\t%0,%1,%2
5947 sl<g>\t%0,%2
5948 sl<y>\t%0,%2"
5949 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5950 (set_attr "cpu_facility" "*,z196,*,longdisp")
5951 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5952
5953 ; slr, sl, sly, slgr, slg, slrk, slgrk
5954 (define_insn "*sub<mode>3_cc"
5955 [(set (reg CC_REGNUM)
5956 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5957 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5958 (const_int 0)))
5959 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5960 (minus:GPR (match_dup 1) (match_dup 2)))]
5961 "s390_match_ccmode (insn, CCLmode)"
5962 "@
5963 sl<g>r\t%0,%2
5964 sl<g>rk\t%0,%1,%2
5965 sl<g>\t%0,%2
5966 sl<y>\t%0,%2"
5967 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5968 (set_attr "cpu_facility" "*,z196,*,longdisp")
5969 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5970
5971 ; slr, sl, sly, slgr, slg, slrk, slgrk
5972 (define_insn "*sub<mode>3_cc2"
5973 [(set (reg CC_REGNUM)
5974 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
5975 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
5976 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5977 (minus:GPR (match_dup 1) (match_dup 2)))]
5978 "s390_match_ccmode (insn, CCL3mode)"
5979 "@
5980 sl<g>r\t%0,%2
5981 sl<g>rk\t%0,%1,%2
5982 sl<g>\t%0,%2
5983 sl<y>\t%0,%2"
5984 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5985 (set_attr "cpu_facility" "*,z196,*,longdisp")
5986 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5987
5988 ; slr, sl, sly, slgr, slg, slrk, slgrk
5989 (define_insn "*sub<mode>3_cconly"
5990 [(set (reg CC_REGNUM)
5991 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5992 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5993 (const_int 0)))
5994 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5995 "s390_match_ccmode (insn, CCLmode)"
5996 "@
5997 sl<g>r\t%0,%2
5998 sl<g>rk\t%0,%1,%2
5999 sl<g>\t%0,%2
6000 sl<y>\t%0,%2"
6001 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6002 (set_attr "cpu_facility" "*,z196,*,longdisp")
6003 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6004
6005
6006 ; slr, sl, sly, slgr, slg, slrk, slgrk
6007 (define_insn "*sub<mode>3_cconly2"
6008 [(set (reg CC_REGNUM)
6009 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
6010 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
6011 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6012 "s390_match_ccmode (insn, CCL3mode)"
6013 "@
6014 sl<g>r\t%0,%2
6015 sl<g>rk\t%0,%1,%2
6016 sl<g>\t%0,%2
6017 sl<y>\t%0,%2"
6018 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6019 (set_attr "cpu_facility" "*,z196,*,longdisp")
6020 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6021
6022
6023 ;
6024 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
6025 ;
6026
6027 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6028 (define_insn "sub<mode>3"
6029 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6030 (minus:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
6031 (match_operand:FP 2 "general_operand" "f,f,R,v")))
6032 (clobber (reg:CC CC_REGNUM))]
6033 "TARGET_HARD_FLOAT"
6034 "@
6035 s<xde>tr\t%0,%1,%2
6036 s<xde>br\t%0,%2
6037 s<xde>b\t%0,%2
6038 wfsdb\t%v0,%v1,%v2"
6039 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6040 (set_attr "type" "fsimp<mode>")
6041 (set_attr "cpu_facility" "*,*,*,vec")
6042 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6043
6044 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6045 (define_insn "*sub<mode>3_cc"
6046 [(set (reg CC_REGNUM)
6047 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6048 (match_operand:FP 2 "general_operand" "f,f,R"))
6049 (match_operand:FP 3 "const0_operand" "")))
6050 (set (match_operand:FP 0 "register_operand" "=f,f,f")
6051 (minus:FP (match_dup 1) (match_dup 2)))]
6052 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6053 "@
6054 s<xde>tr\t%0,%1,%2
6055 s<xde>br\t%0,%2
6056 s<xde>b\t%0,%2"
6057 [(set_attr "op_type" "RRF,RRE,RXE")
6058 (set_attr "type" "fsimp<mode>")
6059 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6060
6061 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6062 (define_insn "*sub<mode>3_cconly"
6063 [(set (reg CC_REGNUM)
6064 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6065 (match_operand:FP 2 "general_operand" "f,f,R"))
6066 (match_operand:FP 3 "const0_operand" "")))
6067 (clobber (match_scratch:FP 0 "=f,f,f"))]
6068 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6069 "@
6070 s<xde>tr\t%0,%1,%2
6071 s<xde>br\t%0,%2
6072 s<xde>b\t%0,%2"
6073 [(set_attr "op_type" "RRF,RRE,RXE")
6074 (set_attr "type" "fsimp<mode>")
6075 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6076
6077
6078 ;;
6079 ;;- Conditional add/subtract instructions.
6080 ;;
6081
6082 ;
6083 ; add(di|si)cc instruction pattern(s).
6084 ;
6085
6086 ; the following 4 patterns are used when the result of an add with
6087 ; carry is checked for an overflow condition
6088
6089 ; op1 + op2 + c < op1
6090
6091 ; alcr, alc, alcgr, alcg
6092 (define_insn "*add<mode>3_alc_carry1_cc"
6093 [(set (reg CC_REGNUM)
6094 (compare
6095 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6096 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6097 (match_operand:GPR 2 "general_operand" "d,T"))
6098 (match_dup 1)))
6099 (set (match_operand:GPR 0 "register_operand" "=d,d")
6100 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6101 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6102 "@
6103 alc<g>r\t%0,%2
6104 alc<g>\t%0,%2"
6105 [(set_attr "op_type" "RRE,RXY")
6106 (set_attr "z196prop" "z196_alone,z196_alone")])
6107
6108 ; alcr, alc, alcgr, alcg
6109 (define_insn "*add<mode>3_alc_carry1_cconly"
6110 [(set (reg CC_REGNUM)
6111 (compare
6112 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6113 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6114 (match_operand:GPR 2 "general_operand" "d,T"))
6115 (match_dup 1)))
6116 (clobber (match_scratch:GPR 0 "=d,d"))]
6117 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6118 "@
6119 alc<g>r\t%0,%2
6120 alc<g>\t%0,%2"
6121 [(set_attr "op_type" "RRE,RXY")
6122 (set_attr "z196prop" "z196_alone,z196_alone")])
6123
6124 ; op1 + op2 + c < op2
6125
6126 ; alcr, alc, alcgr, alcg
6127 (define_insn "*add<mode>3_alc_carry2_cc"
6128 [(set (reg CC_REGNUM)
6129 (compare
6130 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6131 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6132 (match_operand:GPR 2 "general_operand" "d,T"))
6133 (match_dup 2)))
6134 (set (match_operand:GPR 0 "register_operand" "=d,d")
6135 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6136 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6137 "@
6138 alc<g>r\t%0,%2
6139 alc<g>\t%0,%2"
6140 [(set_attr "op_type" "RRE,RXY")])
6141
6142 ; alcr, alc, alcgr, alcg
6143 (define_insn "*add<mode>3_alc_carry2_cconly"
6144 [(set (reg CC_REGNUM)
6145 (compare
6146 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6147 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6148 (match_operand:GPR 2 "general_operand" "d,T"))
6149 (match_dup 2)))
6150 (clobber (match_scratch:GPR 0 "=d,d"))]
6151 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6152 "@
6153 alc<g>r\t%0,%2
6154 alc<g>\t%0,%2"
6155 [(set_attr "op_type" "RRE,RXY")])
6156
6157 ; alcr, alc, alcgr, alcg
6158 (define_insn "*add<mode>3_alc_cc"
6159 [(set (reg CC_REGNUM)
6160 (compare
6161 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6162 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6163 (match_operand:GPR 2 "general_operand" "d,T"))
6164 (const_int 0)))
6165 (set (match_operand:GPR 0 "register_operand" "=d,d")
6166 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6167 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6168 "@
6169 alc<g>r\t%0,%2
6170 alc<g>\t%0,%2"
6171 [(set_attr "op_type" "RRE,RXY")])
6172
6173 ; alcr, alc, alcgr, alcg
6174 (define_insn "*add<mode>3_alc"
6175 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6176 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6177 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6178 (match_operand:GPR 2 "general_operand" "d,T")))
6179 (clobber (reg:CC CC_REGNUM))]
6180 "TARGET_CPU_ZARCH"
6181 "@
6182 alc<g>r\t%0,%2
6183 alc<g>\t%0,%2"
6184 [(set_attr "op_type" "RRE,RXY")])
6185
6186 ; slbr, slb, slbgr, slbg
6187 (define_insn "*sub<mode>3_slb_cc"
6188 [(set (reg CC_REGNUM)
6189 (compare
6190 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6191 (match_operand:GPR 2 "general_operand" "d,T"))
6192 (match_operand:GPR 3 "s390_slb_comparison" ""))
6193 (const_int 0)))
6194 (set (match_operand:GPR 0 "register_operand" "=d,d")
6195 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
6196 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6197 "@
6198 slb<g>r\t%0,%2
6199 slb<g>\t%0,%2"
6200 [(set_attr "op_type" "RRE,RXY")
6201 (set_attr "z10prop" "z10_c,*")])
6202
6203 ; slbr, slb, slbgr, slbg
6204 (define_insn "*sub<mode>3_slb"
6205 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6206 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6207 (match_operand:GPR 2 "general_operand" "d,T"))
6208 (match_operand:GPR 3 "s390_slb_comparison" "")))
6209 (clobber (reg:CC CC_REGNUM))]
6210 "TARGET_CPU_ZARCH"
6211 "@
6212 slb<g>r\t%0,%2
6213 slb<g>\t%0,%2"
6214 [(set_attr "op_type" "RRE,RXY")
6215 (set_attr "z10prop" "z10_c,*")])
6216
6217 (define_expand "add<mode>cc"
6218 [(match_operand:GPR 0 "register_operand" "")
6219 (match_operand 1 "comparison_operator" "")
6220 (match_operand:GPR 2 "register_operand" "")
6221 (match_operand:GPR 3 "const_int_operand" "")]
6222 "TARGET_CPU_ZARCH"
6223 "if (!s390_expand_addcc (GET_CODE (operands[1]),
6224 XEXP (operands[1], 0), XEXP (operands[1], 1),
6225 operands[0], operands[2],
6226 operands[3])) FAIL; DONE;")
6227
6228 ;
6229 ; scond instruction pattern(s).
6230 ;
6231
6232 (define_insn_and_split "*scond<mode>"
6233 [(set (match_operand:GPR 0 "register_operand" "=&d")
6234 (match_operand:GPR 1 "s390_alc_comparison" ""))
6235 (clobber (reg:CC CC_REGNUM))]
6236 "TARGET_CPU_ZARCH"
6237 "#"
6238 "&& reload_completed"
6239 [(set (match_dup 0) (const_int 0))
6240 (parallel
6241 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
6242 (match_dup 0)))
6243 (clobber (reg:CC CC_REGNUM))])]
6244 "")
6245
6246 (define_insn_and_split "*scond<mode>_neg"
6247 [(set (match_operand:GPR 0 "register_operand" "=&d")
6248 (match_operand:GPR 1 "s390_slb_comparison" ""))
6249 (clobber (reg:CC CC_REGNUM))]
6250 "TARGET_CPU_ZARCH"
6251 "#"
6252 "&& reload_completed"
6253 [(set (match_dup 0) (const_int 0))
6254 (parallel
6255 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
6256 (match_dup 1)))
6257 (clobber (reg:CC CC_REGNUM))])
6258 (parallel
6259 [(set (match_dup 0) (neg:GPR (match_dup 0)))
6260 (clobber (reg:CC CC_REGNUM))])]
6261 "")
6262
6263
6264 (define_expand "cstore<mode>4"
6265 [(set (match_operand:SI 0 "register_operand" "")
6266 (match_operator:SI 1 "s390_scond_operator"
6267 [(match_operand:GPR 2 "register_operand" "")
6268 (match_operand:GPR 3 "general_operand" "")]))]
6269 "TARGET_CPU_ZARCH"
6270 "if (!s390_expand_addcc (GET_CODE (operands[1]), operands[2], operands[3],
6271 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
6272
6273 (define_expand "cstorecc4"
6274 [(parallel
6275 [(set (match_operand:SI 0 "register_operand" "")
6276 (match_operator:SI 1 "s390_eqne_operator"
6277 [(match_operand:CCZ1 2 "register_operand")
6278 (match_operand 3 "const0_operand")]))
6279 (clobber (reg:CC CC_REGNUM))])]
6280 ""
6281 "emit_insn (gen_sne (operands[0], operands[2]));
6282 if (GET_CODE (operands[1]) == EQ)
6283 emit_insn (gen_xorsi3 (operands[0], operands[0], const1_rtx));
6284 DONE;")
6285
6286 (define_insn_and_split "sne"
6287 [(set (match_operand:SI 0 "register_operand" "=d")
6288 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
6289 (const_int 0)))
6290 (clobber (reg:CC CC_REGNUM))]
6291 ""
6292 "#"
6293 "reload_completed"
6294 [(parallel
6295 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
6296 (clobber (reg:CC CC_REGNUM))])])
6297
6298
6299 ;;
6300 ;; - Conditional move instructions (introduced with z196)
6301 ;;
6302
6303 (define_expand "mov<mode>cc"
6304 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
6305 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
6306 (match_operand:GPR 2 "nonimmediate_operand" "")
6307 (match_operand:GPR 3 "nonimmediate_operand" "")))]
6308 "TARGET_Z196"
6309 {
6310 /* Emit the comparison insn in case we do not already have a comparison result. */
6311 if (!s390_comparison (operands[1], VOIDmode))
6312 operands[1] = s390_emit_compare (GET_CODE (operands[1]),
6313 XEXP (operands[1], 0),
6314 XEXP (operands[1], 1));
6315 })
6316
6317 ; locr, loc, stoc, locgr, locg, stocg, lochi, locghi
6318 (define_insn_and_split "*mov<mode>cc"
6319 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,d,S,S,&d")
6320 (if_then_else:GPR
6321 (match_operator 1 "s390_comparison"
6322 [(match_operand 2 "cc_reg_operand" " c,c,c,c,c,c,c,c,c")
6323 (match_operand 5 "const_int_operand" "")])
6324 (match_operand:GPR 3 "loc_operand" " d,0,S,0,K,0,d,0,S")
6325 (match_operand:GPR 4 "loc_operand" " 0,d,0,S,0,K,0,d,S")))]
6326 "TARGET_Z196"
6327 "@
6328 loc<g>r%C1\t%0,%3
6329 loc<g>r%D1\t%0,%4
6330 loc<g>%C1\t%0,%3
6331 loc<g>%D1\t%0,%4
6332 loc<g>hi%C1\t%0,%h3
6333 loc<g>hi%D1\t%0,%h4
6334 stoc<g>%C1\t%3,%0
6335 stoc<g>%D1\t%4,%0
6336 #"
6337 "&& reload_completed
6338 && MEM_P (operands[3]) && MEM_P (operands[4])"
6339 [(set (match_dup 0)
6340 (if_then_else:GPR
6341 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6342 (match_dup 3)
6343 (match_dup 0)))
6344 (set (match_dup 0)
6345 (if_then_else:GPR
6346 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6347 (match_dup 0)
6348 (match_dup 4)))]
6349 ""
6350 [(set_attr "op_type" "RRF,RRF,RSY,RSY,RIE,RIE,RSY,RSY,*")
6351 (set_attr "cpu_facility" "*,*,*,*,z13,z13,*,*,*")])
6352
6353 ;;
6354 ;;- Multiply instructions.
6355 ;;
6356
6357 ;
6358 ; muldi3 instruction pattern(s).
6359 ;
6360
6361 (define_insn "*muldi3_sign"
6362 [(set (match_operand:DI 0 "register_operand" "=d,d")
6363 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
6364 (match_operand:DI 1 "register_operand" "0,0")))]
6365 "TARGET_ZARCH"
6366 "@
6367 msgfr\t%0,%2
6368 msgf\t%0,%2"
6369 [(set_attr "op_type" "RRE,RXY")
6370 (set_attr "type" "imuldi")])
6371
6372 (define_insn "muldi3"
6373 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
6374 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
6375 (match_operand:DI 2 "general_operand" "d,K,T,Os")))]
6376 "TARGET_ZARCH"
6377 "@
6378 msgr\t%0,%2
6379 mghi\t%0,%h2
6380 msg\t%0,%2
6381 msgfi\t%0,%2"
6382 [(set_attr "op_type" "RRE,RI,RXY,RIL")
6383 (set_attr "type" "imuldi")
6384 (set_attr "cpu_facility" "*,*,*,z10")])
6385
6386 ;
6387 ; mulsi3 instruction pattern(s).
6388 ;
6389
6390 (define_insn "*mulsi3_sign"
6391 [(set (match_operand:SI 0 "register_operand" "=d,d")
6392 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
6393 (match_operand:SI 1 "register_operand" "0,0")))]
6394 ""
6395 "@
6396 mh\t%0,%2
6397 mhy\t%0,%2"
6398 [(set_attr "op_type" "RX,RXY")
6399 (set_attr "type" "imulhi")
6400 (set_attr "cpu_facility" "*,z10")])
6401
6402 (define_insn "mulsi3"
6403 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
6404 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
6405 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
6406 ""
6407 "@
6408 msr\t%0,%2
6409 mhi\t%0,%h2
6410 ms\t%0,%2
6411 msy\t%0,%2
6412 msfi\t%0,%2"
6413 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
6414 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
6415 (set_attr "cpu_facility" "*,*,*,longdisp,z10")])
6416
6417 ;
6418 ; mulsidi3 instruction pattern(s).
6419 ;
6420
6421 (define_insn "mulsidi3"
6422 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
6423 (mult:DI (sign_extend:DI
6424 (match_operand:SI 1 "register_operand" "%0,0,0"))
6425 (sign_extend:DI
6426 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
6427 "!TARGET_ZARCH"
6428 "@
6429 mr\t%0,%2
6430 m\t%0,%2
6431 mfy\t%0,%2"
6432 [(set_attr "op_type" "RR,RX,RXY")
6433 (set_attr "type" "imulsi")
6434 (set_attr "cpu_facility" "*,*,z10")])
6435
6436 ;
6437 ; umul instruction pattern(s).
6438 ;
6439
6440 ; mlr, ml, mlgr, mlg
6441 (define_insn "umul<dwh><mode>3"
6442 [(set (match_operand:DW 0 "register_operand" "=d,d")
6443 (mult:DW (zero_extend:DW
6444 (match_operand:<DWH> 1 "register_operand" "%0,0"))
6445 (zero_extend:DW
6446 (match_operand:<DWH> 2 "nonimmediate_operand" " d,T"))))]
6447 "TARGET_CPU_ZARCH"
6448 "@
6449 ml<tg>r\t%0,%2
6450 ml<tg>\t%0,%2"
6451 [(set_attr "op_type" "RRE,RXY")
6452 (set_attr "type" "imul<dwh>")])
6453
6454 ;
6455 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
6456 ;
6457
6458 ; mxbr, mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
6459 (define_insn "mul<mode>3"
6460 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6461 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
6462 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
6463 "TARGET_HARD_FLOAT"
6464 "@
6465 m<xdee>tr\t%0,%1,%2
6466 m<xdee>br\t%0,%2
6467 m<xdee>b\t%0,%2
6468 wfmdb\t%v0,%v1,%v2"
6469 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6470 (set_attr "type" "fmul<mode>")
6471 (set_attr "cpu_facility" "*,*,*,vec")
6472 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6473
6474 ; madbr, maebr, maxb, madb, maeb
6475 (define_insn "fma<mode>4"
6476 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6477 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6478 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6479 (match_operand:DSF 3 "register_operand" "0,0,v")))]
6480 "TARGET_HARD_FLOAT"
6481 "@
6482 ma<xde>br\t%0,%1,%2
6483 ma<xde>b\t%0,%1,%2
6484 wfmadb\t%v0,%v1,%v2,%v3"
6485 [(set_attr "op_type" "RRE,RXE,VRR")
6486 (set_attr "type" "fmadd<mode>")
6487 (set_attr "cpu_facility" "*,*,vec")
6488 (set_attr "enabled" "*,*,<DFDI>")])
6489
6490 ; msxbr, msdbr, msebr, msxb, msdb, mseb
6491 (define_insn "fms<mode>4"
6492 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6493 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6494 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6495 (neg:DSF (match_operand:DSF 3 "register_operand" "0,0,v"))))]
6496 "TARGET_HARD_FLOAT"
6497 "@
6498 ms<xde>br\t%0,%1,%2
6499 ms<xde>b\t%0,%1,%2
6500 wfmsdb\t%v0,%v1,%v2,%v3"
6501 [(set_attr "op_type" "RRE,RXE,VRR")
6502 (set_attr "type" "fmadd<mode>")
6503 (set_attr "cpu_facility" "*,*,vec")
6504 (set_attr "enabled" "*,*,<DFDI>")])
6505
6506 ;;
6507 ;;- Divide and modulo instructions.
6508 ;;
6509
6510 ;
6511 ; divmoddi4 instruction pattern(s).
6512 ;
6513
6514 (define_expand "divmoddi4"
6515 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6516 (div:DI (match_operand:DI 1 "register_operand" "")
6517 (match_operand:DI 2 "general_operand" "")))
6518 (set (match_operand:DI 3 "general_operand" "")
6519 (mod:DI (match_dup 1) (match_dup 2)))])
6520 (clobber (match_dup 4))]
6521 "TARGET_ZARCH"
6522 {
6523 rtx insn, div_equal, mod_equal;
6524
6525 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
6526 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
6527
6528 operands[4] = gen_reg_rtx(TImode);
6529 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
6530
6531 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6532 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6533
6534 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6535 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6536
6537 DONE;
6538 })
6539
6540 (define_insn "divmodtidi3"
6541 [(set (match_operand:TI 0 "register_operand" "=d,d")
6542 (ior:TI
6543 (ashift:TI
6544 (zero_extend:TI
6545 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6546 (match_operand:DI 2 "general_operand" "d,T")))
6547 (const_int 64))
6548 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
6549 "TARGET_ZARCH"
6550 "@
6551 dsgr\t%0,%2
6552 dsg\t%0,%2"
6553 [(set_attr "op_type" "RRE,RXY")
6554 (set_attr "type" "idiv")])
6555
6556 (define_insn "divmodtisi3"
6557 [(set (match_operand:TI 0 "register_operand" "=d,d")
6558 (ior:TI
6559 (ashift:TI
6560 (zero_extend:TI
6561 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6562 (sign_extend:DI
6563 (match_operand:SI 2 "nonimmediate_operand" "d,T"))))
6564 (const_int 64))
6565 (zero_extend:TI
6566 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
6567 "TARGET_ZARCH"
6568 "@
6569 dsgfr\t%0,%2
6570 dsgf\t%0,%2"
6571 [(set_attr "op_type" "RRE,RXY")
6572 (set_attr "type" "idiv")])
6573
6574 ;
6575 ; udivmoddi4 instruction pattern(s).
6576 ;
6577
6578 (define_expand "udivmoddi4"
6579 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6580 (udiv:DI (match_operand:DI 1 "general_operand" "")
6581 (match_operand:DI 2 "nonimmediate_operand" "")))
6582 (set (match_operand:DI 3 "general_operand" "")
6583 (umod:DI (match_dup 1) (match_dup 2)))])
6584 (clobber (match_dup 4))]
6585 "TARGET_ZARCH"
6586 {
6587 rtx insn, div_equal, mod_equal, equal;
6588
6589 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
6590 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
6591 equal = gen_rtx_IOR (TImode,
6592 gen_rtx_ASHIFT (TImode,
6593 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
6594 GEN_INT (64)),
6595 gen_rtx_ZERO_EXTEND (TImode, div_equal));
6596
6597 operands[4] = gen_reg_rtx(TImode);
6598 emit_clobber (operands[4]);
6599 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
6600 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
6601
6602 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
6603 set_unique_reg_note (insn, REG_EQUAL, equal);
6604
6605 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6606 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6607
6608 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6609 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6610
6611 DONE;
6612 })
6613
6614 (define_insn "udivmodtidi3"
6615 [(set (match_operand:TI 0 "register_operand" "=d,d")
6616 (ior:TI
6617 (ashift:TI
6618 (zero_extend:TI
6619 (truncate:DI
6620 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
6621 (zero_extend:TI
6622 (match_operand:DI 2 "nonimmediate_operand" "d,T")))))
6623 (const_int 64))
6624 (zero_extend:TI
6625 (truncate:DI
6626 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
6627 "TARGET_ZARCH"
6628 "@
6629 dlgr\t%0,%2
6630 dlg\t%0,%2"
6631 [(set_attr "op_type" "RRE,RXY")
6632 (set_attr "type" "idiv")])
6633
6634 ;
6635 ; divmodsi4 instruction pattern(s).
6636 ;
6637
6638 (define_expand "divmodsi4"
6639 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6640 (div:SI (match_operand:SI 1 "general_operand" "")
6641 (match_operand:SI 2 "nonimmediate_operand" "")))
6642 (set (match_operand:SI 3 "general_operand" "")
6643 (mod:SI (match_dup 1) (match_dup 2)))])
6644 (clobber (match_dup 4))]
6645 "!TARGET_ZARCH"
6646 {
6647 rtx insn, div_equal, mod_equal, equal;
6648
6649 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
6650 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
6651 equal = gen_rtx_IOR (DImode,
6652 gen_rtx_ASHIFT (DImode,
6653 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6654 GEN_INT (32)),
6655 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6656
6657 operands[4] = gen_reg_rtx(DImode);
6658 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
6659
6660 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
6661 set_unique_reg_note (insn, REG_EQUAL, equal);
6662
6663 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6664 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6665
6666 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6667 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6668
6669 DONE;
6670 })
6671
6672 (define_insn "divmoddisi3"
6673 [(set (match_operand:DI 0 "register_operand" "=d,d")
6674 (ior:DI
6675 (ashift:DI
6676 (zero_extend:DI
6677 (truncate:SI
6678 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6679 (sign_extend:DI
6680 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
6681 (const_int 32))
6682 (zero_extend:DI
6683 (truncate:SI
6684 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
6685 "!TARGET_ZARCH"
6686 "@
6687 dr\t%0,%2
6688 d\t%0,%2"
6689 [(set_attr "op_type" "RR,RX")
6690 (set_attr "type" "idiv")])
6691
6692 ;
6693 ; udivsi3 and umodsi3 instruction pattern(s).
6694 ;
6695
6696 (define_expand "udivmodsi4"
6697 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6698 (udiv:SI (match_operand:SI 1 "general_operand" "")
6699 (match_operand:SI 2 "nonimmediate_operand" "")))
6700 (set (match_operand:SI 3 "general_operand" "")
6701 (umod:SI (match_dup 1) (match_dup 2)))])
6702 (clobber (match_dup 4))]
6703 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6704 {
6705 rtx insn, div_equal, mod_equal, equal;
6706
6707 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6708 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6709 equal = gen_rtx_IOR (DImode,
6710 gen_rtx_ASHIFT (DImode,
6711 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6712 GEN_INT (32)),
6713 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6714
6715 operands[4] = gen_reg_rtx(DImode);
6716 emit_clobber (operands[4]);
6717 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
6718 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
6719
6720 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
6721 set_unique_reg_note (insn, REG_EQUAL, equal);
6722
6723 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6724 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6725
6726 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6727 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6728
6729 DONE;
6730 })
6731
6732 (define_insn "udivmoddisi3"
6733 [(set (match_operand:DI 0 "register_operand" "=d,d")
6734 (ior:DI
6735 (ashift:DI
6736 (zero_extend:DI
6737 (truncate:SI
6738 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
6739 (zero_extend:DI
6740 (match_operand:SI 2 "nonimmediate_operand" "d,T")))))
6741 (const_int 32))
6742 (zero_extend:DI
6743 (truncate:SI
6744 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
6745 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6746 "@
6747 dlr\t%0,%2
6748 dl\t%0,%2"
6749 [(set_attr "op_type" "RRE,RXY")
6750 (set_attr "type" "idiv")])
6751
6752 (define_expand "udivsi3"
6753 [(set (match_operand:SI 0 "register_operand" "=d")
6754 (udiv:SI (match_operand:SI 1 "general_operand" "")
6755 (match_operand:SI 2 "general_operand" "")))
6756 (clobber (match_dup 3))]
6757 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6758 {
6759 rtx insn, udiv_equal, umod_equal, equal;
6760
6761 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6762 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6763 equal = gen_rtx_IOR (DImode,
6764 gen_rtx_ASHIFT (DImode,
6765 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6766 GEN_INT (32)),
6767 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6768
6769 operands[3] = gen_reg_rtx (DImode);
6770
6771 if (CONSTANT_P (operands[2]))
6772 {
6773 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
6774 {
6775 rtx_code_label *label1 = gen_label_rtx ();
6776
6777 operands[1] = make_safe_from (operands[1], operands[0]);
6778 emit_move_insn (operands[0], const0_rtx);
6779 emit_cmp_and_jump_insns (operands[1], operands[2], LT, NULL_RTX,
6780 SImode, 1, label1);
6781 emit_move_insn (operands[0], const1_rtx);
6782 emit_label (label1);
6783 }
6784 else
6785 {
6786 operands[2] = force_reg (SImode, operands[2]);
6787 operands[2] = make_safe_from (operands[2], operands[0]);
6788
6789 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6790 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6791 operands[2]));
6792 set_unique_reg_note (insn, REG_EQUAL, equal);
6793
6794 insn = emit_move_insn (operands[0],
6795 gen_lowpart (SImode, operands[3]));
6796 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6797 }
6798 }
6799 else
6800 {
6801 rtx_code_label *label1 = gen_label_rtx ();
6802 rtx_code_label *label2 = gen_label_rtx ();
6803 rtx_code_label *label3 = gen_label_rtx ();
6804
6805 operands[1] = force_reg (SImode, operands[1]);
6806 operands[1] = make_safe_from (operands[1], operands[0]);
6807 operands[2] = force_reg (SImode, operands[2]);
6808 operands[2] = make_safe_from (operands[2], operands[0]);
6809
6810 emit_move_insn (operands[0], const0_rtx);
6811 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6812 SImode, 1, label3);
6813 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6814 SImode, 0, label2);
6815 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6816 SImode, 0, label1);
6817 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6818 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6819 operands[2]));
6820 set_unique_reg_note (insn, REG_EQUAL, equal);
6821
6822 insn = emit_move_insn (operands[0],
6823 gen_lowpart (SImode, operands[3]));
6824 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6825
6826 emit_jump (label3);
6827 emit_label (label1);
6828 emit_move_insn (operands[0], operands[1]);
6829 emit_jump (label3);
6830 emit_label (label2);
6831 emit_move_insn (operands[0], const1_rtx);
6832 emit_label (label3);
6833 }
6834 emit_move_insn (operands[0], operands[0]);
6835 DONE;
6836 })
6837
6838 (define_expand "umodsi3"
6839 [(set (match_operand:SI 0 "register_operand" "=d")
6840 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
6841 (match_operand:SI 2 "nonimmediate_operand" "")))
6842 (clobber (match_dup 3))]
6843 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6844 {
6845 rtx insn, udiv_equal, umod_equal, equal;
6846
6847 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6848 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6849 equal = gen_rtx_IOR (DImode,
6850 gen_rtx_ASHIFT (DImode,
6851 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6852 GEN_INT (32)),
6853 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6854
6855 operands[3] = gen_reg_rtx (DImode);
6856
6857 if (CONSTANT_P (operands[2]))
6858 {
6859 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
6860 {
6861 rtx_code_label *label1 = gen_label_rtx ();
6862
6863 operands[1] = make_safe_from (operands[1], operands[0]);
6864 emit_move_insn (operands[0], operands[1]);
6865 emit_cmp_and_jump_insns (operands[0], operands[2], LT, NULL_RTX,
6866 SImode, 1, label1);
6867 emit_insn (gen_abssi2 (operands[0], operands[2]));
6868 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
6869 emit_label (label1);
6870 }
6871 else
6872 {
6873 operands[2] = force_reg (SImode, operands[2]);
6874 operands[2] = make_safe_from (operands[2], operands[0]);
6875
6876 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6877 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6878 operands[2]));
6879 set_unique_reg_note (insn, REG_EQUAL, equal);
6880
6881 insn = emit_move_insn (operands[0],
6882 gen_highpart (SImode, operands[3]));
6883 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6884 }
6885 }
6886 else
6887 {
6888 rtx_code_label *label1 = gen_label_rtx ();
6889 rtx_code_label *label2 = gen_label_rtx ();
6890 rtx_code_label *label3 = gen_label_rtx ();
6891
6892 operands[1] = force_reg (SImode, operands[1]);
6893 operands[1] = make_safe_from (operands[1], operands[0]);
6894 operands[2] = force_reg (SImode, operands[2]);
6895 operands[2] = make_safe_from (operands[2], operands[0]);
6896
6897 emit_move_insn(operands[0], operands[1]);
6898 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6899 SImode, 1, label3);
6900 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6901 SImode, 0, label2);
6902 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6903 SImode, 0, label1);
6904 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6905 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6906 operands[2]));
6907 set_unique_reg_note (insn, REG_EQUAL, equal);
6908
6909 insn = emit_move_insn (operands[0],
6910 gen_highpart (SImode, operands[3]));
6911 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6912
6913 emit_jump (label3);
6914 emit_label (label1);
6915 emit_move_insn (operands[0], const0_rtx);
6916 emit_jump (label3);
6917 emit_label (label2);
6918 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
6919 emit_label (label3);
6920 }
6921 DONE;
6922 })
6923
6924 ;
6925 ; div(df|sf)3 instruction pattern(s).
6926 ;
6927
6928 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
6929 (define_insn "div<mode>3"
6930 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6931 (div:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
6932 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
6933 "TARGET_HARD_FLOAT"
6934 "@
6935 d<xde>tr\t%0,%1,%2
6936 d<xde>br\t%0,%2
6937 d<xde>b\t%0,%2
6938 wfddb\t%v0,%v1,%v2"
6939 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6940 (set_attr "type" "fdiv<mode>")
6941 (set_attr "cpu_facility" "*,*,*,vec")
6942 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6943
6944
6945 ;;
6946 ;;- And instructions.
6947 ;;
6948
6949 (define_expand "and<mode>3"
6950 [(set (match_operand:INT 0 "nonimmediate_operand" "")
6951 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
6952 (match_operand:INT 2 "general_operand" "")))
6953 (clobber (reg:CC CC_REGNUM))]
6954 ""
6955 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
6956
6957 ;
6958 ; anddi3 instruction pattern(s).
6959 ;
6960
6961 (define_insn "*anddi3_cc"
6962 [(set (reg CC_REGNUM)
6963 (compare
6964 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
6965 (match_operand:DI 2 "general_operand" " d,d,T,NxxDq"))
6966 (const_int 0)))
6967 (set (match_operand:DI 0 "register_operand" "=d,d,d, d")
6968 (and:DI (match_dup 1) (match_dup 2)))]
6969 "TARGET_ZARCH && s390_match_ccmode(insn, CCTmode)"
6970 "@
6971 ngr\t%0,%2
6972 ngrk\t%0,%1,%2
6973 ng\t%0,%2
6974 risbg\t%0,%1,%s2,128+%e2,0"
6975 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6976 (set_attr "cpu_facility" "*,z196,*,z10")
6977 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6978
6979 (define_insn "*anddi3_cconly"
6980 [(set (reg CC_REGNUM)
6981 (compare
6982 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
6983 (match_operand:DI 2 "general_operand" " d,d,T,NxxDq"))
6984 (const_int 0)))
6985 (clobber (match_scratch:DI 0 "=d,d,d, d"))]
6986 "TARGET_ZARCH
6987 && s390_match_ccmode(insn, CCTmode)
6988 /* Do not steal TM patterns. */
6989 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
6990 "@
6991 ngr\t%0,%2
6992 ngrk\t%0,%1,%2
6993 ng\t%0,%2
6994 risbg\t%0,%1,%s2,128+%e2,0"
6995 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6996 (set_attr "cpu_facility" "*,z196,*,z10")
6997 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6998
6999 (define_insn "*anddi3"
7000 [(set (match_operand:DI 0 "nonimmediate_operand"
7001 "=d,d, d, d, d, d, d, d,d,d,d, d, AQ,Q")
7002 (and:DI
7003 (match_operand:DI 1 "nonimmediate_operand"
7004 "%d,o, 0, 0, 0, 0, 0, 0,0,d,0, d, 0,0")
7005 (match_operand:DI 2 "general_operand"
7006 "M, M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,d,T,NxxDq,NxQDF,Q")))
7007 (clobber (reg:CC CC_REGNUM))]
7008 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7009 "@
7010 #
7011 #
7012 nihh\t%0,%j2
7013 nihl\t%0,%j2
7014 nilh\t%0,%j2
7015 nill\t%0,%j2
7016 nihf\t%0,%m2
7017 nilf\t%0,%m2
7018 ngr\t%0,%2
7019 ngrk\t%0,%1,%2
7020 ng\t%0,%2
7021 risbg\t%0,%1,%s2,128+%e2,0
7022 #
7023 #"
7024 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,RIE,SI,SS")
7025 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,z196,*,z10,*,*")
7026 (set_attr "z10prop" "*,
7027 *,
7028 z10_super_E1,
7029 z10_super_E1,
7030 z10_super_E1,
7031 z10_super_E1,
7032 z10_super_E1,
7033 z10_super_E1,
7034 z10_super_E1,
7035 *,
7036 z10_super_E1,
7037 z10_super_E1,
7038 *,
7039 *")])
7040
7041 (define_split
7042 [(set (match_operand:DI 0 "s_operand" "")
7043 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7044 (clobber (reg:CC CC_REGNUM))]
7045 "reload_completed"
7046 [(parallel
7047 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7048 (clobber (reg:CC CC_REGNUM))])]
7049 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7050
7051 ;; These two are what combine generates for (ashift (zero_extract)).
7052 (define_insn "*extzv_<mode>_srl"
7053 [(set (match_operand:GPR 0 "register_operand" "=d")
7054 (and:GPR (lshiftrt:GPR
7055 (match_operand:GPR 1 "register_operand" "d")
7056 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
7057 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
7058 (clobber (reg:CC CC_REGNUM))]
7059 "TARGET_Z10
7060 /* Note that even for the SImode pattern, the rotate is always DImode. */
7061 && s390_extzv_shift_ok (<bitsize>, -INTVAL (operands[2]),
7062 INTVAL (operands[3]))"
7063 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,64-%2"
7064 [(set_attr "op_type" "RIE")
7065 (set_attr "z10prop" "z10_super_E1")])
7066
7067 (define_insn "*extzv_<mode>_sll"
7068 [(set (match_operand:GPR 0 "register_operand" "=d")
7069 (and:GPR (ashift:GPR
7070 (match_operand:GPR 1 "register_operand" "d")
7071 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
7072 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
7073 (clobber (reg:CC CC_REGNUM))]
7074 "TARGET_Z10
7075 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[2]),
7076 INTVAL (operands[3]))"
7077 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,%2"
7078 [(set_attr "op_type" "RIE")
7079 (set_attr "z10prop" "z10_super_E1")])
7080
7081
7082 ;
7083 ; andsi3 instruction pattern(s).
7084 ;
7085
7086 (define_insn "*andsi3_cc"
7087 [(set (reg CC_REGNUM)
7088 (compare
7089 (and:SI
7090 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7091 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7092 (const_int 0)))
7093 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d, d")
7094 (and:SI (match_dup 1) (match_dup 2)))]
7095 "s390_match_ccmode(insn, CCTmode)"
7096 "@
7097 nilf\t%0,%o2
7098 nr\t%0,%2
7099 nrk\t%0,%1,%2
7100 n\t%0,%2
7101 ny\t%0,%2
7102 risbg\t%0,%1,%t2,128+%f2,0"
7103 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7104 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7105 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7106 z10_super_E1,z10_super_E1,z10_super_E1")])
7107
7108 (define_insn "*andsi3_cconly"
7109 [(set (reg CC_REGNUM)
7110 (compare
7111 (and:SI
7112 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7113 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7114 (const_int 0)))
7115 (clobber (match_scratch:SI 0 "=d,d,d,d,d, d"))]
7116 "s390_match_ccmode(insn, CCTmode)
7117 /* Do not steal TM patterns. */
7118 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
7119 "@
7120 nilf\t%0,%o2
7121 nr\t%0,%2
7122 nrk\t%0,%1,%2
7123 n\t%0,%2
7124 ny\t%0,%2
7125 risbg\t%0,%1,%t2,128+%f2,0"
7126 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7127 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7128 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7129 z10_super_E1,z10_super_E1,z10_super_E1")])
7130
7131 (define_insn "*andsi3_zarch"
7132 [(set (match_operand:SI 0 "nonimmediate_operand"
7133 "=d,d, d, d, d,d,d,d,d, d, AQ,Q")
7134 (and:SI (match_operand:SI 1 "nonimmediate_operand"
7135 "%d,o, 0, 0, 0,0,d,0,0, d, 0,0")
7136 (match_operand:SI 2 "general_operand"
7137 " M,M,N0HSF,N1HSF,Os,d,d,R,T,NxxSq,NxQSF,Q")))
7138 (clobber (reg:CC CC_REGNUM))]
7139 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7140 "@
7141 #
7142 #
7143 nilh\t%0,%j2
7144 nill\t%0,%j2
7145 nilf\t%0,%o2
7146 nr\t%0,%2
7147 nrk\t%0,%1,%2
7148 n\t%0,%2
7149 ny\t%0,%2
7150 risbg\t%0,%1,%t2,128+%f2,0
7151 #
7152 #"
7153 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RRF,RX,RXY,RIE,SI,SS")
7154 (set_attr "cpu_facility" "*,*,*,*,*,*,z196,*,longdisp,z10,*,*")
7155 (set_attr "z10prop" "*,
7156 *,
7157 z10_super_E1,
7158 z10_super_E1,
7159 z10_super_E1,
7160 z10_super_E1,
7161 *,
7162 z10_super_E1,
7163 z10_super_E1,
7164 z10_super_E1,
7165 *,
7166 *")])
7167
7168 (define_insn "*andsi3_esa"
7169 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d, AQ,Q")
7170 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0, 0,0")
7171 (match_operand:SI 2 "general_operand" " d,R,NxQSF,Q")))
7172 (clobber (reg:CC CC_REGNUM))]
7173 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7174 "@
7175 nr\t%0,%2
7176 n\t%0,%2
7177 #
7178 #"
7179 [(set_attr "op_type" "RR,RX,SI,SS")
7180 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7181
7182
7183 (define_split
7184 [(set (match_operand:SI 0 "s_operand" "")
7185 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7186 (clobber (reg:CC CC_REGNUM))]
7187 "reload_completed"
7188 [(parallel
7189 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7190 (clobber (reg:CC CC_REGNUM))])]
7191 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7192
7193 ;
7194 ; andhi3 instruction pattern(s).
7195 ;
7196
7197 (define_insn "*andhi3_zarch"
7198 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7199 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7200 (match_operand:HI 2 "general_operand" " d,d,n,NxQHF,Q")))
7201 (clobber (reg:CC CC_REGNUM))]
7202 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7203 "@
7204 nr\t%0,%2
7205 nrk\t%0,%1,%2
7206 nill\t%0,%x2
7207 #
7208 #"
7209 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7210 (set_attr "cpu_facility" "*,z196,*,*,*")
7211 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")
7212 ])
7213
7214 (define_insn "*andhi3_esa"
7215 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7216 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7217 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
7218 (clobber (reg:CC CC_REGNUM))]
7219 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7220 "@
7221 nr\t%0,%2
7222 #
7223 #"
7224 [(set_attr "op_type" "RR,SI,SS")
7225 (set_attr "z10prop" "z10_super_E1,*,*")
7226 ])
7227
7228 (define_split
7229 [(set (match_operand:HI 0 "s_operand" "")
7230 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7231 (clobber (reg:CC CC_REGNUM))]
7232 "reload_completed"
7233 [(parallel
7234 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7235 (clobber (reg:CC CC_REGNUM))])]
7236 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7237
7238 ;
7239 ; andqi3 instruction pattern(s).
7240 ;
7241
7242 (define_insn "*andqi3_zarch"
7243 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7244 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7245 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7246 (clobber (reg:CC CC_REGNUM))]
7247 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7248 "@
7249 nr\t%0,%2
7250 nrk\t%0,%1,%2
7251 nill\t%0,%b2
7252 ni\t%S0,%b2
7253 niy\t%S0,%b2
7254 #"
7255 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7256 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7257 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super,z10_super,*")])
7258
7259 (define_insn "*andqi3_esa"
7260 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7261 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7262 (match_operand:QI 2 "general_operand" "d,n,Q")))
7263 (clobber (reg:CC CC_REGNUM))]
7264 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7265 "@
7266 nr\t%0,%2
7267 ni\t%S0,%b2
7268 #"
7269 [(set_attr "op_type" "RR,SI,SS")
7270 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7271
7272 ;
7273 ; Block and (NC) patterns.
7274 ;
7275
7276 (define_insn "*nc"
7277 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7278 (and:BLK (match_dup 0)
7279 (match_operand:BLK 1 "memory_operand" "Q")))
7280 (use (match_operand 2 "const_int_operand" "n"))
7281 (clobber (reg:CC CC_REGNUM))]
7282 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7283 "nc\t%O0(%2,%R0),%S1"
7284 [(set_attr "op_type" "SS")
7285 (set_attr "z196prop" "z196_cracked")])
7286
7287 (define_split
7288 [(set (match_operand 0 "memory_operand" "")
7289 (and (match_dup 0)
7290 (match_operand 1 "memory_operand" "")))
7291 (clobber (reg:CC CC_REGNUM))]
7292 "reload_completed
7293 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7294 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7295 [(parallel
7296 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
7297 (use (match_dup 2))
7298 (clobber (reg:CC CC_REGNUM))])]
7299 {
7300 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7301 operands[0] = adjust_address (operands[0], BLKmode, 0);
7302 operands[1] = adjust_address (operands[1], BLKmode, 0);
7303 })
7304
7305 (define_peephole2
7306 [(parallel
7307 [(set (match_operand:BLK 0 "memory_operand" "")
7308 (and:BLK (match_dup 0)
7309 (match_operand:BLK 1 "memory_operand" "")))
7310 (use (match_operand 2 "const_int_operand" ""))
7311 (clobber (reg:CC CC_REGNUM))])
7312 (parallel
7313 [(set (match_operand:BLK 3 "memory_operand" "")
7314 (and:BLK (match_dup 3)
7315 (match_operand:BLK 4 "memory_operand" "")))
7316 (use (match_operand 5 "const_int_operand" ""))
7317 (clobber (reg:CC CC_REGNUM))])]
7318 "s390_offset_p (operands[0], operands[3], operands[2])
7319 && s390_offset_p (operands[1], operands[4], operands[2])
7320 && !s390_overlap_p (operands[0], operands[1],
7321 INTVAL (operands[2]) + INTVAL (operands[5]))
7322 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7323 [(parallel
7324 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
7325 (use (match_dup 8))
7326 (clobber (reg:CC CC_REGNUM))])]
7327 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7328 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7329 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7330
7331
7332 ;;
7333 ;;- Bit set (inclusive or) instructions.
7334 ;;
7335
7336 (define_expand "ior<mode>3"
7337 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7338 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
7339 (match_operand:INT 2 "general_operand" "")))
7340 (clobber (reg:CC CC_REGNUM))]
7341 ""
7342 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
7343
7344 ;
7345 ; iordi3 instruction pattern(s).
7346 ;
7347
7348 (define_insn "*iordi3_cc"
7349 [(set (reg CC_REGNUM)
7350 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7351 (match_operand:DI 2 "general_operand" " d,d,T"))
7352 (const_int 0)))
7353 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7354 (ior:DI (match_dup 1) (match_dup 2)))]
7355 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7356 "@
7357 ogr\t%0,%2
7358 ogrk\t%0,%1,%2
7359 og\t%0,%2"
7360 [(set_attr "op_type" "RRE,RRF,RXY")
7361 (set_attr "cpu_facility" "*,z196,*")
7362 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7363
7364 (define_insn "*iordi3_cconly"
7365 [(set (reg CC_REGNUM)
7366 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7367 (match_operand:DI 2 "general_operand" " d,d,T"))
7368 (const_int 0)))
7369 (clobber (match_scratch:DI 0 "=d,d,d"))]
7370 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7371 "@
7372 ogr\t%0,%2
7373 ogrk\t%0,%1,%2
7374 og\t%0,%2"
7375 [(set_attr "op_type" "RRE,RRF,RXY")
7376 (set_attr "cpu_facility" "*,z196,*")
7377 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7378
7379 (define_insn "*iordi3"
7380 [(set (match_operand:DI 0 "nonimmediate_operand"
7381 "=d, d, d, d, d, d,d,d,d, AQ,Q")
7382 (ior:DI (match_operand:DI 1 "nonimmediate_operand"
7383 " %0, 0, 0, 0, 0, 0,0,d,0, 0,0")
7384 (match_operand:DI 2 "general_operand"
7385 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7386 (clobber (reg:CC CC_REGNUM))]
7387 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7388 "@
7389 oihh\t%0,%i2
7390 oihl\t%0,%i2
7391 oilh\t%0,%i2
7392 oill\t%0,%i2
7393 oihf\t%0,%k2
7394 oilf\t%0,%k2
7395 ogr\t%0,%2
7396 ogrk\t%0,%1,%2
7397 og\t%0,%2
7398 #
7399 #"
7400 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,SI,SS")
7401 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,z196,*,*,*")
7402 (set_attr "z10prop" "z10_super_E1,
7403 z10_super_E1,
7404 z10_super_E1,
7405 z10_super_E1,
7406 z10_super_E1,
7407 z10_super_E1,
7408 z10_super_E1,
7409 *,
7410 z10_super_E1,
7411 *,
7412 *")])
7413
7414 (define_split
7415 [(set (match_operand:DI 0 "s_operand" "")
7416 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7417 (clobber (reg:CC CC_REGNUM))]
7418 "reload_completed"
7419 [(parallel
7420 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7421 (clobber (reg:CC CC_REGNUM))])]
7422 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7423
7424 ;
7425 ; iorsi3 instruction pattern(s).
7426 ;
7427
7428 (define_insn "*iorsi3_cc"
7429 [(set (reg CC_REGNUM)
7430 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7431 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7432 (const_int 0)))
7433 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7434 (ior:SI (match_dup 1) (match_dup 2)))]
7435 "s390_match_ccmode(insn, CCTmode)"
7436 "@
7437 oilf\t%0,%o2
7438 or\t%0,%2
7439 ork\t%0,%1,%2
7440 o\t%0,%2
7441 oy\t%0,%2"
7442 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7443 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7444 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7445
7446 (define_insn "*iorsi3_cconly"
7447 [(set (reg CC_REGNUM)
7448 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7449 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7450 (const_int 0)))
7451 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7452 "s390_match_ccmode(insn, CCTmode)"
7453 "@
7454 oilf\t%0,%o2
7455 or\t%0,%2
7456 ork\t%0,%1,%2
7457 o\t%0,%2
7458 oy\t%0,%2"
7459 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7460 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7461 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7462
7463 (define_insn "*iorsi3_zarch"
7464 [(set (match_operand:SI 0 "nonimmediate_operand" "=d, d, d,d,d,d,d, AQ,Q")
7465 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0, 0, 0,0,d,0,0, 0,0")
7466 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,d,R,T,NxQS0,Q")))
7467 (clobber (reg:CC CC_REGNUM))]
7468 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7469 "@
7470 oilh\t%0,%i2
7471 oill\t%0,%i2
7472 oilf\t%0,%o2
7473 or\t%0,%2
7474 ork\t%0,%1,%2
7475 o\t%0,%2
7476 oy\t%0,%2
7477 #
7478 #"
7479 [(set_attr "op_type" "RI,RI,RIL,RR,RRF,RX,RXY,SI,SS")
7480 (set_attr "cpu_facility" "*,*,*,*,z196,*,longdisp,*,*")
7481 (set_attr "z10prop" "z10_super_E1,
7482 z10_super_E1,
7483 z10_super_E1,
7484 z10_super_E1,
7485 *,
7486 z10_super_E1,
7487 z10_super_E1,
7488 *,
7489 *")])
7490
7491 (define_insn "*iorsi3_esa"
7492 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
7493 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
7494 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
7495 (clobber (reg:CC CC_REGNUM))]
7496 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7497 "@
7498 or\t%0,%2
7499 o\t%0,%2
7500 #
7501 #"
7502 [(set_attr "op_type" "RR,RX,SI,SS")
7503 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7504
7505 (define_split
7506 [(set (match_operand:SI 0 "s_operand" "")
7507 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7508 (clobber (reg:CC CC_REGNUM))]
7509 "reload_completed"
7510 [(parallel
7511 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7512 (clobber (reg:CC CC_REGNUM))])]
7513 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7514
7515 ;
7516 ; iorhi3 instruction pattern(s).
7517 ;
7518
7519 (define_insn "*iorhi3_zarch"
7520 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7521 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7522 (match_operand:HI 2 "general_operand" " d,d,n,NxQH0,Q")))
7523 (clobber (reg:CC CC_REGNUM))]
7524 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7525 "@
7526 or\t%0,%2
7527 ork\t%0,%1,%2
7528 oill\t%0,%x2
7529 #
7530 #"
7531 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7532 (set_attr "cpu_facility" "*,z196,*,*,*")
7533 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")])
7534
7535 (define_insn "*iorhi3_esa"
7536 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7537 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7538 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
7539 (clobber (reg:CC CC_REGNUM))]
7540 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7541 "@
7542 or\t%0,%2
7543 #
7544 #"
7545 [(set_attr "op_type" "RR,SI,SS")
7546 (set_attr "z10prop" "z10_super_E1,*,*")])
7547
7548 (define_split
7549 [(set (match_operand:HI 0 "s_operand" "")
7550 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7551 (clobber (reg:CC CC_REGNUM))]
7552 "reload_completed"
7553 [(parallel
7554 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7555 (clobber (reg:CC CC_REGNUM))])]
7556 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7557
7558 ;
7559 ; iorqi3 instruction pattern(s).
7560 ;
7561
7562 (define_insn "*iorqi3_zarch"
7563 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7564 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7565 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7566 (clobber (reg:CC CC_REGNUM))]
7567 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7568 "@
7569 or\t%0,%2
7570 ork\t%0,%1,%2
7571 oill\t%0,%b2
7572 oi\t%S0,%b2
7573 oiy\t%S0,%b2
7574 #"
7575 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7576 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7577 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,
7578 z10_super,z10_super,*")])
7579
7580 (define_insn "*iorqi3_esa"
7581 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7582 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7583 (match_operand:QI 2 "general_operand" "d,n,Q")))
7584 (clobber (reg:CC CC_REGNUM))]
7585 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7586 "@
7587 or\t%0,%2
7588 oi\t%S0,%b2
7589 #"
7590 [(set_attr "op_type" "RR,SI,SS")
7591 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7592
7593 ;
7594 ; Block inclusive or (OC) patterns.
7595 ;
7596
7597 (define_insn "*oc"
7598 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7599 (ior:BLK (match_dup 0)
7600 (match_operand:BLK 1 "memory_operand" "Q")))
7601 (use (match_operand 2 "const_int_operand" "n"))
7602 (clobber (reg:CC CC_REGNUM))]
7603 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7604 "oc\t%O0(%2,%R0),%S1"
7605 [(set_attr "op_type" "SS")
7606 (set_attr "z196prop" "z196_cracked")])
7607
7608 (define_split
7609 [(set (match_operand 0 "memory_operand" "")
7610 (ior (match_dup 0)
7611 (match_operand 1 "memory_operand" "")))
7612 (clobber (reg:CC CC_REGNUM))]
7613 "reload_completed
7614 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7615 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7616 [(parallel
7617 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
7618 (use (match_dup 2))
7619 (clobber (reg:CC CC_REGNUM))])]
7620 {
7621 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7622 operands[0] = adjust_address (operands[0], BLKmode, 0);
7623 operands[1] = adjust_address (operands[1], BLKmode, 0);
7624 })
7625
7626 (define_peephole2
7627 [(parallel
7628 [(set (match_operand:BLK 0 "memory_operand" "")
7629 (ior:BLK (match_dup 0)
7630 (match_operand:BLK 1 "memory_operand" "")))
7631 (use (match_operand 2 "const_int_operand" ""))
7632 (clobber (reg:CC CC_REGNUM))])
7633 (parallel
7634 [(set (match_operand:BLK 3 "memory_operand" "")
7635 (ior:BLK (match_dup 3)
7636 (match_operand:BLK 4 "memory_operand" "")))
7637 (use (match_operand 5 "const_int_operand" ""))
7638 (clobber (reg:CC CC_REGNUM))])]
7639 "s390_offset_p (operands[0], operands[3], operands[2])
7640 && s390_offset_p (operands[1], operands[4], operands[2])
7641 && !s390_overlap_p (operands[0], operands[1],
7642 INTVAL (operands[2]) + INTVAL (operands[5]))
7643 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7644 [(parallel
7645 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
7646 (use (match_dup 8))
7647 (clobber (reg:CC CC_REGNUM))])]
7648 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7649 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7650 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7651
7652
7653 ;;
7654 ;;- Xor instructions.
7655 ;;
7656
7657 (define_expand "xor<mode>3"
7658 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7659 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
7660 (match_operand:INT 2 "general_operand" "")))
7661 (clobber (reg:CC CC_REGNUM))]
7662 ""
7663 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
7664
7665 ; Combine replaces (xor (x) (const_int -1)) with (not (x)) when doing
7666 ; simplifications. So its better to have something matching.
7667 (define_split
7668 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7669 (not:INT (match_operand:INT 1 "nonimmediate_operand" "")))]
7670 ""
7671 [(parallel
7672 [(set (match_dup 0) (xor:INT (match_dup 1) (match_dup 2)))
7673 (clobber (reg:CC CC_REGNUM))])]
7674 {
7675 operands[2] = constm1_rtx;
7676 if (!s390_logical_operator_ok_p (operands))
7677 FAIL;
7678 })
7679
7680 ;
7681 ; xordi3 instruction pattern(s).
7682 ;
7683
7684 (define_insn "*xordi3_cc"
7685 [(set (reg CC_REGNUM)
7686 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7687 (match_operand:DI 2 "general_operand" " d,d,T"))
7688 (const_int 0)))
7689 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7690 (xor:DI (match_dup 1) (match_dup 2)))]
7691 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7692 "@
7693 xgr\t%0,%2
7694 xgrk\t%0,%1,%2
7695 xg\t%0,%2"
7696 [(set_attr "op_type" "RRE,RRF,RXY")
7697 (set_attr "cpu_facility" "*,z196,*")
7698 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7699
7700 (define_insn "*xordi3_cconly"
7701 [(set (reg CC_REGNUM)
7702 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7703 (match_operand:DI 2 "general_operand" " d,d,T"))
7704 (const_int 0)))
7705 (clobber (match_scratch:DI 0 "=d,d,d"))]
7706 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7707 "@
7708 xgr\t%0,%2
7709 xgrk\t%0,%1,%2
7710 xg\t%0,%2"
7711 [(set_attr "op_type" "RRE,RRF,RXY")
7712 (set_attr "cpu_facility" "*,z196,*")
7713 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7714
7715 (define_insn "*xordi3"
7716 [(set (match_operand:DI 0 "nonimmediate_operand" "=d, d,d,d,d, AQ,Q")
7717 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0, 0,0,d,0, 0,0")
7718 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7719 (clobber (reg:CC CC_REGNUM))]
7720 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7721 "@
7722 xihf\t%0,%k2
7723 xilf\t%0,%k2
7724 xgr\t%0,%2
7725 xgrk\t%0,%1,%2
7726 xg\t%0,%2
7727 #
7728 #"
7729 [(set_attr "op_type" "RIL,RIL,RRE,RRF,RXY,SI,SS")
7730 (set_attr "cpu_facility" "extimm,extimm,*,z196,*,*,*")
7731 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,
7732 *,z10_super_E1,*,*")])
7733
7734 (define_split
7735 [(set (match_operand:DI 0 "s_operand" "")
7736 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7737 (clobber (reg:CC CC_REGNUM))]
7738 "reload_completed"
7739 [(parallel
7740 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7741 (clobber (reg:CC CC_REGNUM))])]
7742 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7743
7744 ;
7745 ; xorsi3 instruction pattern(s).
7746 ;
7747
7748 (define_insn "*xorsi3_cc"
7749 [(set (reg CC_REGNUM)
7750 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7751 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7752 (const_int 0)))
7753 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7754 (xor:SI (match_dup 1) (match_dup 2)))]
7755 "s390_match_ccmode(insn, CCTmode)"
7756 "@
7757 xilf\t%0,%o2
7758 xr\t%0,%2
7759 xrk\t%0,%1,%2
7760 x\t%0,%2
7761 xy\t%0,%2"
7762 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7763 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7764 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7765 z10_super_E1,z10_super_E1")])
7766
7767 (define_insn "*xorsi3_cconly"
7768 [(set (reg CC_REGNUM)
7769 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7770 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7771 (const_int 0)))
7772 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7773 "s390_match_ccmode(insn, CCTmode)"
7774 "@
7775 xilf\t%0,%o2
7776 xr\t%0,%2
7777 xrk\t%0,%1,%2
7778 x\t%0,%2
7779 xy\t%0,%2"
7780 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7781 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7782 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7783 z10_super_E1,z10_super_E1")])
7784
7785 (define_insn "*xorsi3"
7786 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d, AQ,Q")
7787 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, 0,0")
7788 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxQS0,Q")))
7789 (clobber (reg:CC CC_REGNUM))]
7790 "s390_logical_operator_ok_p (operands)"
7791 "@
7792 xilf\t%0,%o2
7793 xr\t%0,%2
7794 xrk\t%0,%1,%2
7795 x\t%0,%2
7796 xy\t%0,%2
7797 #
7798 #"
7799 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,SI,SS")
7800 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*,*")
7801 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7802 z10_super_E1,z10_super_E1,*,*")])
7803
7804 (define_split
7805 [(set (match_operand:SI 0 "s_operand" "")
7806 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7807 (clobber (reg:CC CC_REGNUM))]
7808 "reload_completed"
7809 [(parallel
7810 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7811 (clobber (reg:CC CC_REGNUM))])]
7812 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7813
7814 ;
7815 ; xorhi3 instruction pattern(s).
7816 ;
7817
7818 (define_insn "*xorhi3"
7819 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7820 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,d, 0,0")
7821 (match_operand:HI 2 "general_operand" "Os,d,d,NxQH0,Q")))
7822 (clobber (reg:CC CC_REGNUM))]
7823 "s390_logical_operator_ok_p (operands)"
7824 "@
7825 xilf\t%0,%x2
7826 xr\t%0,%2
7827 xrk\t%0,%1,%2
7828 #
7829 #"
7830 [(set_attr "op_type" "RIL,RR,RRF,SI,SS")
7831 (set_attr "cpu_facility" "*,*,z196,*,*")
7832 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*,*")])
7833
7834 (define_split
7835 [(set (match_operand:HI 0 "s_operand" "")
7836 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7837 (clobber (reg:CC CC_REGNUM))]
7838 "reload_completed"
7839 [(parallel
7840 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7841 (clobber (reg:CC CC_REGNUM))])]
7842 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7843
7844 ;
7845 ; xorqi3 instruction pattern(s).
7846 ;
7847
7848 (define_insn "*xorqi3"
7849 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7850 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,d,0,0,0")
7851 (match_operand:QI 2 "general_operand" "Os,d,d,n,n,Q")))
7852 (clobber (reg:CC CC_REGNUM))]
7853 "s390_logical_operator_ok_p (operands)"
7854 "@
7855 xilf\t%0,%b2
7856 xr\t%0,%2
7857 xrk\t%0,%1,%2
7858 xi\t%S0,%b2
7859 xiy\t%S0,%b2
7860 #"
7861 [(set_attr "op_type" "RIL,RR,RRF,SI,SIY,SS")
7862 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*")
7863 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super,z10_super,*")])
7864
7865
7866 ;
7867 ; Block exclusive or (XC) patterns.
7868 ;
7869
7870 (define_insn "*xc"
7871 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7872 (xor:BLK (match_dup 0)
7873 (match_operand:BLK 1 "memory_operand" "Q")))
7874 (use (match_operand 2 "const_int_operand" "n"))
7875 (clobber (reg:CC CC_REGNUM))]
7876 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7877 "xc\t%O0(%2,%R0),%S1"
7878 [(set_attr "op_type" "SS")])
7879
7880 (define_split
7881 [(set (match_operand 0 "memory_operand" "")
7882 (xor (match_dup 0)
7883 (match_operand 1 "memory_operand" "")))
7884 (clobber (reg:CC CC_REGNUM))]
7885 "reload_completed
7886 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7887 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7888 [(parallel
7889 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
7890 (use (match_dup 2))
7891 (clobber (reg:CC CC_REGNUM))])]
7892 {
7893 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7894 operands[0] = adjust_address (operands[0], BLKmode, 0);
7895 operands[1] = adjust_address (operands[1], BLKmode, 0);
7896 })
7897
7898 (define_peephole2
7899 [(parallel
7900 [(set (match_operand:BLK 0 "memory_operand" "")
7901 (xor:BLK (match_dup 0)
7902 (match_operand:BLK 1 "memory_operand" "")))
7903 (use (match_operand 2 "const_int_operand" ""))
7904 (clobber (reg:CC CC_REGNUM))])
7905 (parallel
7906 [(set (match_operand:BLK 3 "memory_operand" "")
7907 (xor:BLK (match_dup 3)
7908 (match_operand:BLK 4 "memory_operand" "")))
7909 (use (match_operand 5 "const_int_operand" ""))
7910 (clobber (reg:CC CC_REGNUM))])]
7911 "s390_offset_p (operands[0], operands[3], operands[2])
7912 && s390_offset_p (operands[1], operands[4], operands[2])
7913 && !s390_overlap_p (operands[0], operands[1],
7914 INTVAL (operands[2]) + INTVAL (operands[5]))
7915 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7916 [(parallel
7917 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
7918 (use (match_dup 8))
7919 (clobber (reg:CC CC_REGNUM))])]
7920 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7921 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7922 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7923
7924 ;
7925 ; Block xor (XC) patterns with src == dest.
7926 ;
7927
7928 (define_insn "*xc_zero"
7929 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7930 (const_int 0))
7931 (use (match_operand 1 "const_int_operand" "n"))
7932 (clobber (reg:CC CC_REGNUM))]
7933 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
7934 "xc\t%O0(%1,%R0),%S0"
7935 [(set_attr "op_type" "SS")
7936 (set_attr "z196prop" "z196_cracked")])
7937
7938 (define_peephole2
7939 [(parallel
7940 [(set (match_operand:BLK 0 "memory_operand" "")
7941 (const_int 0))
7942 (use (match_operand 1 "const_int_operand" ""))
7943 (clobber (reg:CC CC_REGNUM))])
7944 (parallel
7945 [(set (match_operand:BLK 2 "memory_operand" "")
7946 (const_int 0))
7947 (use (match_operand 3 "const_int_operand" ""))
7948 (clobber (reg:CC CC_REGNUM))])]
7949 "s390_offset_p (operands[0], operands[2], operands[1])
7950 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
7951 [(parallel
7952 [(set (match_dup 4) (const_int 0))
7953 (use (match_dup 5))
7954 (clobber (reg:CC CC_REGNUM))])]
7955 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7956 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
7957
7958
7959 ;;
7960 ;;- Negate instructions.
7961 ;;
7962
7963 ;
7964 ; neg(di|si)2 instruction pattern(s).
7965 ;
7966
7967 (define_expand "neg<mode>2"
7968 [(parallel
7969 [(set (match_operand:DSI 0 "register_operand" "=d")
7970 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
7971 (clobber (reg:CC CC_REGNUM))])]
7972 ""
7973 "")
7974
7975 (define_insn "*negdi2_sign_cc"
7976 [(set (reg CC_REGNUM)
7977 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
7978 (match_operand:SI 1 "register_operand" "d") 0)
7979 (const_int 32)) (const_int 32)))
7980 (const_int 0)))
7981 (set (match_operand:DI 0 "register_operand" "=d")
7982 (neg:DI (sign_extend:DI (match_dup 1))))]
7983 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
7984 "lcgfr\t%0,%1"
7985 [(set_attr "op_type" "RRE")
7986 (set_attr "z10prop" "z10_c")])
7987
7988 (define_insn "*negdi2_sign"
7989 [(set (match_operand:DI 0 "register_operand" "=d")
7990 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
7991 (clobber (reg:CC CC_REGNUM))]
7992 "TARGET_ZARCH"
7993 "lcgfr\t%0,%1"
7994 [(set_attr "op_type" "RRE")
7995 (set_attr "z10prop" "z10_c")])
7996
7997 ; lcr, lcgr
7998 (define_insn "*neg<mode>2_cc"
7999 [(set (reg CC_REGNUM)
8000 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8001 (const_int 0)))
8002 (set (match_operand:GPR 0 "register_operand" "=d")
8003 (neg:GPR (match_dup 1)))]
8004 "s390_match_ccmode (insn, CCAmode)"
8005 "lc<g>r\t%0,%1"
8006 [(set_attr "op_type" "RR<E>")
8007 (set_attr "z10prop" "z10_super_c_E1")])
8008
8009 ; lcr, lcgr
8010 (define_insn "*neg<mode>2_cconly"
8011 [(set (reg CC_REGNUM)
8012 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8013 (const_int 0)))
8014 (clobber (match_scratch:GPR 0 "=d"))]
8015 "s390_match_ccmode (insn, CCAmode)"
8016 "lc<g>r\t%0,%1"
8017 [(set_attr "op_type" "RR<E>")
8018 (set_attr "z10prop" "z10_super_c_E1")])
8019
8020 ; lcr, lcgr
8021 (define_insn "*neg<mode>2"
8022 [(set (match_operand:GPR 0 "register_operand" "=d")
8023 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
8024 (clobber (reg:CC CC_REGNUM))]
8025 ""
8026 "lc<g>r\t%0,%1"
8027 [(set_attr "op_type" "RR<E>")
8028 (set_attr "z10prop" "z10_super_c_E1")])
8029
8030 (define_insn "*negdi2_31"
8031 [(set (match_operand:DI 0 "register_operand" "=d")
8032 (neg:DI (match_operand:DI 1 "register_operand" "d")))
8033 (clobber (reg:CC CC_REGNUM))]
8034 "!TARGET_ZARCH"
8035 "#")
8036
8037 ; Split a DImode NEG on 31bit into 2 SImode NEGs
8038
8039 ; Doing the twos complement separately on the SImode parts does an
8040 ; unwanted +1 on the high part which needs to be subtracted afterwards
8041 ; ... unless the +1 on the low part created an overflow.
8042
8043 (define_split
8044 [(set (match_operand:DI 0 "register_operand" "")
8045 (neg:DI (match_operand:DI 1 "register_operand" "")))
8046 (clobber (reg:CC CC_REGNUM))]
8047 "!TARGET_ZARCH
8048 && (REGNO (operands[0]) == REGNO (operands[1])
8049 || s390_split_ok_p (operands[0], operands[1], DImode, 0))
8050 && reload_completed"
8051 [(parallel
8052 [(set (match_dup 2) (neg:SI (match_dup 3)))
8053 (clobber (reg:CC CC_REGNUM))])
8054 (parallel
8055 [(set (reg:CCAP CC_REGNUM)
8056 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
8057 (set (match_dup 4) (neg:SI (match_dup 5)))])
8058 (set (pc)
8059 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8060 (pc)
8061 (label_ref (match_dup 6))))
8062 (parallel
8063 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8064 (clobber (reg:CC CC_REGNUM))])
8065 (match_dup 6)]
8066 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8067 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8068 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8069 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8070 operands[6] = gen_label_rtx ();")
8071
8072 ; Like above but first make a copy of the low part of the src operand
8073 ; since it might overlap with the high part of the destination.
8074
8075 (define_split
8076 [(set (match_operand:DI 0 "register_operand" "")
8077 (neg:DI (match_operand:DI 1 "register_operand" "")))
8078 (clobber (reg:CC CC_REGNUM))]
8079 "!TARGET_ZARCH
8080 && s390_split_ok_p (operands[0], operands[1], DImode, 1)
8081 && reload_completed"
8082 [; Make a backup of op5 first
8083 (set (match_dup 4) (match_dup 5))
8084 ; Setting op2 here might clobber op5
8085 (parallel
8086 [(set (match_dup 2) (neg:SI (match_dup 3)))
8087 (clobber (reg:CC CC_REGNUM))])
8088 (parallel
8089 [(set (reg:CCAP CC_REGNUM)
8090 (compare:CCAP (neg:SI (match_dup 4)) (const_int 0)))
8091 (set (match_dup 4) (neg:SI (match_dup 4)))])
8092 (set (pc)
8093 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8094 (pc)
8095 (label_ref (match_dup 6))))
8096 (parallel
8097 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8098 (clobber (reg:CC CC_REGNUM))])
8099 (match_dup 6)]
8100 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8101 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8102 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8103 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8104 operands[6] = gen_label_rtx ();")
8105
8106 ;
8107 ; neg(df|sf)2 instruction pattern(s).
8108 ;
8109
8110 (define_expand "neg<mode>2"
8111 [(parallel
8112 [(set (match_operand:BFP 0 "register_operand" "=f")
8113 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
8114 (clobber (reg:CC CC_REGNUM))])]
8115 "TARGET_HARD_FLOAT"
8116 "")
8117
8118 ; lcxbr, lcdbr, lcebr
8119 (define_insn "*neg<mode>2_cc"
8120 [(set (reg CC_REGNUM)
8121 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8122 (match_operand:BFP 2 "const0_operand" "")))
8123 (set (match_operand:BFP 0 "register_operand" "=f")
8124 (neg:BFP (match_dup 1)))]
8125 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8126 "lc<xde>br\t%0,%1"
8127 [(set_attr "op_type" "RRE")
8128 (set_attr "type" "fsimp<mode>")])
8129
8130 ; lcxbr, lcdbr, lcebr
8131 (define_insn "*neg<mode>2_cconly"
8132 [(set (reg CC_REGNUM)
8133 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8134 (match_operand:BFP 2 "const0_operand" "")))
8135 (clobber (match_scratch:BFP 0 "=f"))]
8136 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8137 "lc<xde>br\t%0,%1"
8138 [(set_attr "op_type" "RRE")
8139 (set_attr "type" "fsimp<mode>")])
8140
8141 ; lcdfr
8142 (define_insn "*neg<mode>2_nocc"
8143 [(set (match_operand:FP 0 "register_operand" "=f")
8144 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8145 "TARGET_DFP"
8146 "lcdfr\t%0,%1"
8147 [(set_attr "op_type" "RRE")
8148 (set_attr "type" "fsimp<mode>")])
8149
8150 ; lcxbr, lcdbr, lcebr
8151 ; FIXME: wflcdb does not clobber cc
8152 (define_insn "*neg<mode>2"
8153 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8154 (neg:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8155 (clobber (reg:CC CC_REGNUM))]
8156 "TARGET_HARD_FLOAT"
8157 "@
8158 lc<xde>br\t%0,%1
8159 wflcdb\t%0,%1"
8160 [(set_attr "op_type" "RRE,VRR")
8161 (set_attr "cpu_facility" "*,vec")
8162 (set_attr "type" "fsimp<mode>,*")
8163 (set_attr "enabled" "*,<DFDI>")])
8164
8165
8166 ;;
8167 ;;- Absolute value instructions.
8168 ;;
8169
8170 ;
8171 ; abs(di|si)2 instruction pattern(s).
8172 ;
8173
8174 (define_insn "*absdi2_sign_cc"
8175 [(set (reg CC_REGNUM)
8176 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8177 (match_operand:SI 1 "register_operand" "d") 0)
8178 (const_int 32)) (const_int 32)))
8179 (const_int 0)))
8180 (set (match_operand:DI 0 "register_operand" "=d")
8181 (abs:DI (sign_extend:DI (match_dup 1))))]
8182 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8183 "lpgfr\t%0,%1"
8184 [(set_attr "op_type" "RRE")
8185 (set_attr "z10prop" "z10_c")])
8186
8187 (define_insn "*absdi2_sign"
8188 [(set (match_operand:DI 0 "register_operand" "=d")
8189 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8190 (clobber (reg:CC CC_REGNUM))]
8191 "TARGET_ZARCH"
8192 "lpgfr\t%0,%1"
8193 [(set_attr "op_type" "RRE")
8194 (set_attr "z10prop" "z10_c")])
8195
8196 ; lpr, lpgr
8197 (define_insn "*abs<mode>2_cc"
8198 [(set (reg CC_REGNUM)
8199 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
8200 (const_int 0)))
8201 (set (match_operand:GPR 0 "register_operand" "=d")
8202 (abs:GPR (match_dup 1)))]
8203 "s390_match_ccmode (insn, CCAmode)"
8204 "lp<g>r\t%0,%1"
8205 [(set_attr "op_type" "RR<E>")
8206 (set_attr "z10prop" "z10_c")])
8207
8208 ; lpr, lpgr
8209 (define_insn "*abs<mode>2_cconly"
8210 [(set (reg CC_REGNUM)
8211 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
8212 (const_int 0)))
8213 (clobber (match_scratch:GPR 0 "=d"))]
8214 "s390_match_ccmode (insn, CCAmode)"
8215 "lp<g>r\t%0,%1"
8216 [(set_attr "op_type" "RR<E>")
8217 (set_attr "z10prop" "z10_c")])
8218
8219 ; lpr, lpgr
8220 (define_insn "abs<mode>2"
8221 [(set (match_operand:GPR 0 "register_operand" "=d")
8222 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8223 (clobber (reg:CC CC_REGNUM))]
8224 ""
8225 "lp<g>r\t%0,%1"
8226 [(set_attr "op_type" "RR<E>")
8227 (set_attr "z10prop" "z10_c")])
8228
8229 ;
8230 ; abs(df|sf)2 instruction pattern(s).
8231 ;
8232
8233 (define_expand "abs<mode>2"
8234 [(parallel
8235 [(set (match_operand:BFP 0 "register_operand" "=f")
8236 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8237 (clobber (reg:CC CC_REGNUM))])]
8238 "TARGET_HARD_FLOAT"
8239 "")
8240
8241 ; lpxbr, lpdbr, lpebr
8242 (define_insn "*abs<mode>2_cc"
8243 [(set (reg CC_REGNUM)
8244 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8245 (match_operand:BFP 2 "const0_operand" "")))
8246 (set (match_operand:BFP 0 "register_operand" "=f")
8247 (abs:BFP (match_dup 1)))]
8248 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8249 "lp<xde>br\t%0,%1"
8250 [(set_attr "op_type" "RRE")
8251 (set_attr "type" "fsimp<mode>")])
8252
8253 ; lpxbr, lpdbr, lpebr
8254 (define_insn "*abs<mode>2_cconly"
8255 [(set (reg CC_REGNUM)
8256 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8257 (match_operand:BFP 2 "const0_operand" "")))
8258 (clobber (match_scratch:BFP 0 "=f"))]
8259 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8260 "lp<xde>br\t%0,%1"
8261 [(set_attr "op_type" "RRE")
8262 (set_attr "type" "fsimp<mode>")])
8263
8264 ; lpdfr
8265 (define_insn "*abs<mode>2_nocc"
8266 [(set (match_operand:FP 0 "register_operand" "=f")
8267 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8268 "TARGET_DFP"
8269 "lpdfr\t%0,%1"
8270 [(set_attr "op_type" "RRE")
8271 (set_attr "type" "fsimp<mode>")])
8272
8273 ; lpxbr, lpdbr, lpebr
8274 ; FIXME: wflpdb does not clobber cc
8275 (define_insn "*abs<mode>2"
8276 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8277 (abs:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8278 (clobber (reg:CC CC_REGNUM))]
8279 "TARGET_HARD_FLOAT"
8280 "@
8281 lp<xde>br\t%0,%1
8282 wflpdb\t%0,%1"
8283 [(set_attr "op_type" "RRE,VRR")
8284 (set_attr "cpu_facility" "*,vec")
8285 (set_attr "type" "fsimp<mode>,*")
8286 (set_attr "enabled" "*,<DFDI>")])
8287
8288
8289 ;;
8290 ;;- Negated absolute value instructions
8291 ;;
8292
8293 ;
8294 ; Integer
8295 ;
8296
8297 (define_insn "*negabsdi2_sign_cc"
8298 [(set (reg CC_REGNUM)
8299 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8300 (match_operand:SI 1 "register_operand" "d") 0)
8301 (const_int 32)) (const_int 32))))
8302 (const_int 0)))
8303 (set (match_operand:DI 0 "register_operand" "=d")
8304 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
8305 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8306 "lngfr\t%0,%1"
8307 [(set_attr "op_type" "RRE")
8308 (set_attr "z10prop" "z10_c")])
8309
8310 (define_insn "*negabsdi2_sign"
8311 [(set (match_operand:DI 0 "register_operand" "=d")
8312 (neg:DI (abs:DI (sign_extend:DI
8313 (match_operand:SI 1 "register_operand" "d")))))
8314 (clobber (reg:CC CC_REGNUM))]
8315 "TARGET_ZARCH"
8316 "lngfr\t%0,%1"
8317 [(set_attr "op_type" "RRE")
8318 (set_attr "z10prop" "z10_c")])
8319
8320 ; lnr, lngr
8321 (define_insn "*negabs<mode>2_cc"
8322 [(set (reg CC_REGNUM)
8323 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8324 (const_int 0)))
8325 (set (match_operand:GPR 0 "register_operand" "=d")
8326 (neg:GPR (abs:GPR (match_dup 1))))]
8327 "s390_match_ccmode (insn, CCAmode)"
8328 "ln<g>r\t%0,%1"
8329 [(set_attr "op_type" "RR<E>")
8330 (set_attr "z10prop" "z10_c")])
8331
8332 ; lnr, lngr
8333 (define_insn "*negabs<mode>2_cconly"
8334 [(set (reg CC_REGNUM)
8335 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8336 (const_int 0)))
8337 (clobber (match_scratch:GPR 0 "=d"))]
8338 "s390_match_ccmode (insn, CCAmode)"
8339 "ln<g>r\t%0,%1"
8340 [(set_attr "op_type" "RR<E>")
8341 (set_attr "z10prop" "z10_c")])
8342
8343 ; lnr, lngr
8344 (define_insn "*negabs<mode>2"
8345 [(set (match_operand:GPR 0 "register_operand" "=d")
8346 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
8347 (clobber (reg:CC CC_REGNUM))]
8348 ""
8349 "ln<g>r\t%0,%1"
8350 [(set_attr "op_type" "RR<E>")
8351 (set_attr "z10prop" "z10_c")])
8352
8353 ;
8354 ; Floating point
8355 ;
8356
8357 ; lnxbr, lndbr, lnebr
8358 (define_insn "*negabs<mode>2_cc"
8359 [(set (reg CC_REGNUM)
8360 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8361 (match_operand:BFP 2 "const0_operand" "")))
8362 (set (match_operand:BFP 0 "register_operand" "=f")
8363 (neg:BFP (abs:BFP (match_dup 1))))]
8364 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8365 "ln<xde>br\t%0,%1"
8366 [(set_attr "op_type" "RRE")
8367 (set_attr "type" "fsimp<mode>")])
8368
8369 ; lnxbr, lndbr, lnebr
8370 (define_insn "*negabs<mode>2_cconly"
8371 [(set (reg CC_REGNUM)
8372 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8373 (match_operand:BFP 2 "const0_operand" "")))
8374 (clobber (match_scratch:BFP 0 "=f"))]
8375 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8376 "ln<xde>br\t%0,%1"
8377 [(set_attr "op_type" "RRE")
8378 (set_attr "type" "fsimp<mode>")])
8379
8380 ; lndfr
8381 (define_insn "*negabs<mode>2_nocc"
8382 [(set (match_operand:FP 0 "register_operand" "=f")
8383 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
8384 "TARGET_DFP"
8385 "lndfr\t%0,%1"
8386 [(set_attr "op_type" "RRE")
8387 (set_attr "type" "fsimp<mode>")])
8388
8389 ; lnxbr, lndbr, lnebr
8390 ; FIXME: wflndb does not clobber cc
8391 (define_insn "*negabs<mode>2"
8392 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8393 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f,v"))))
8394 (clobber (reg:CC CC_REGNUM))]
8395 "TARGET_HARD_FLOAT"
8396 "@
8397 ln<xde>br\t%0,%1
8398 wflndb\t%0,%1"
8399 [(set_attr "op_type" "RRE,VRR")
8400 (set_attr "cpu_facility" "*,vec")
8401 (set_attr "type" "fsimp<mode>,*")
8402 (set_attr "enabled" "*,<DFDI>")])
8403
8404 ;;
8405 ;;- Square root instructions.
8406 ;;
8407
8408 ;
8409 ; sqrt(df|sf)2 instruction pattern(s).
8410 ;
8411
8412 ; sqxbr, sqdbr, sqebr, sqdb, sqeb
8413 (define_insn "sqrt<mode>2"
8414 [(set (match_operand:BFP 0 "register_operand" "=f,f,v")
8415 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,R,v")))]
8416 "TARGET_HARD_FLOAT"
8417 "@
8418 sq<xde>br\t%0,%1
8419 sq<xde>b\t%0,%1
8420 wfsqdb\t%v0,%v1"
8421 [(set_attr "op_type" "RRE,RXE,VRR")
8422 (set_attr "type" "fsqrt<mode>")
8423 (set_attr "cpu_facility" "*,*,vec")
8424 (set_attr "enabled" "*,<DSF>,<DFDI>")])
8425
8426
8427 ;;
8428 ;;- One complement instructions.
8429 ;;
8430
8431 ;
8432 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
8433 ;
8434
8435 (define_expand "one_cmpl<mode>2"
8436 [(parallel
8437 [(set (match_operand:INT 0 "register_operand" "")
8438 (xor:INT (match_operand:INT 1 "register_operand" "")
8439 (const_int -1)))
8440 (clobber (reg:CC CC_REGNUM))])]
8441 ""
8442 "")
8443
8444
8445 ;;
8446 ;; Find leftmost bit instructions.
8447 ;;
8448
8449 (define_expand "clzdi2"
8450 [(set (match_operand:DI 0 "register_operand" "=d")
8451 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
8452 "TARGET_EXTIMM && TARGET_ZARCH"
8453 {
8454 rtx insn, clz_equal;
8455 rtx wide_reg = gen_reg_rtx (TImode);
8456 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
8457
8458 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
8459
8460 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
8461
8462 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
8463 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
8464
8465 DONE;
8466 })
8467
8468 (define_insn "clztidi2"
8469 [(set (match_operand:TI 0 "register_operand" "=d")
8470 (ior:TI
8471 (ashift:TI
8472 (zero_extend:TI
8473 (xor:DI (match_operand:DI 1 "register_operand" "d")
8474 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
8475 (subreg:SI (clz:DI (match_dup 1)) 4))))
8476
8477 (const_int 64))
8478 (zero_extend:TI (clz:DI (match_dup 1)))))
8479 (clobber (reg:CC CC_REGNUM))]
8480 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
8481 == (unsigned HOST_WIDE_INT) 1 << 63
8482 && TARGET_EXTIMM && TARGET_ZARCH"
8483 "flogr\t%0,%1"
8484 [(set_attr "op_type" "RRE")])
8485
8486
8487 ;;
8488 ;;- Rotate instructions.
8489 ;;
8490
8491 ;
8492 ; rotl(di|si)3 instruction pattern(s).
8493 ;
8494
8495 (define_expand "rotl<mode>3"
8496 [(set (match_operand:GPR 0 "register_operand" "")
8497 (rotate:GPR (match_operand:GPR 1 "register_operand" "")
8498 (match_operand:SI 2 "nonmemory_operand" "")))]
8499 "TARGET_CPU_ZARCH"
8500 "")
8501
8502 ; rll, rllg
8503 (define_insn "*rotl<mode>3<addr_style_op><masked_op>"
8504 [(set (match_operand:GPR 0 "register_operand" "=d")
8505 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8506 (match_operand:SI 2 "nonmemory_operand" "an")))]
8507 "TARGET_CPU_ZARCH"
8508 "rll<g>\t%0,%1,<addr_style_op_ops>"
8509 [(set_attr "op_type" "RSE")
8510 (set_attr "atype" "reg")
8511 (set_attr "z10prop" "z10_super_E1")])
8512
8513
8514 ;;
8515 ;;- Shift instructions.
8516 ;;
8517
8518 ;
8519 ; (ashl|lshr)(di|si)3 instruction pattern(s).
8520 ; Left shifts and logical right shifts
8521
8522 (define_expand "<shift><mode>3"
8523 [(set (match_operand:DSI 0 "register_operand" "")
8524 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
8525 (match_operand:SI 2 "nonmemory_operand" "")))]
8526 ""
8527 "")
8528
8529 ; ESA 64 bit register pair shift with reg or imm shift count
8530 ; sldl, srdl
8531 (define_insn "*<shift>di3_31<addr_style_op><masked_op>"
8532 [(set (match_operand:DI 0 "register_operand" "=d")
8533 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8534 (match_operand:SI 2 "nonmemory_operand" "an")))]
8535 "!TARGET_ZARCH"
8536 "s<lr>dl\t%0,<addr_style_op_ops>"
8537 [(set_attr "op_type" "RS")
8538 (set_attr "atype" "reg")
8539 (set_attr "z196prop" "z196_cracked")])
8540
8541
8542 ; 64 bit register shift with reg or imm shift count
8543 ; sll, srl, sllg, srlg, sllk, srlk
8544 (define_insn "*<shift><mode>3<addr_style_op><masked_op>"
8545 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8546 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8547 (match_operand:SI 2 "nonmemory_operand" "an,an")))]
8548 ""
8549 "@
8550 s<lr>l<g>\t%0,<1><addr_style_op_ops>
8551 s<lr>l<gk>\t%0,%1,<addr_style_op_ops>"
8552 [(set_attr "op_type" "RS<E>,RSY")
8553 (set_attr "atype" "reg,reg")
8554 (set_attr "cpu_facility" "*,z196")
8555 (set_attr "z10prop" "z10_super_E1,*")])
8556
8557 ;
8558 ; ashr(di|si)3 instruction pattern(s).
8559 ; Arithmetic right shifts
8560
8561 (define_expand "ashr<mode>3"
8562 [(parallel
8563 [(set (match_operand:DSI 0 "register_operand" "")
8564 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
8565 (match_operand:SI 2 "nonmemory_operand" "")))
8566 (clobber (reg:CC CC_REGNUM))])]
8567 ""
8568 "")
8569
8570 ; FIXME: The number of alternatives is doubled here to match the fix
8571 ; number of 2 in the subst pattern for the (clobber (match_scratch...
8572 ; The right fix should be to support match_scratch in the output
8573 ; pattern of a define_subst.
8574 (define_insn "*ashrdi3_31<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8575 [(set (match_operand:DI 0 "register_operand" "=d, d")
8576 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0, 0")
8577 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8578 (clobber (reg:CC CC_REGNUM))]
8579 "!TARGET_ZARCH"
8580 "@
8581 srda\t%0,<addr_style_op_cc_ops>
8582 srda\t%0,<addr_style_op_cc_ops>"
8583 [(set_attr "op_type" "RS")
8584 (set_attr "atype" "reg")])
8585
8586
8587 ; sra, srag
8588 (define_insn "*ashr<mode>3<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8589 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8590 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8591 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8592 (clobber (reg:CC CC_REGNUM))]
8593 ""
8594 "@
8595 sra<g>\t%0,<1><addr_style_op_cc_ops>
8596 sra<gk>\t%0,%1,<addr_style_op_cc_ops>"
8597 [(set_attr "op_type" "RS<E>,RSY")
8598 (set_attr "atype" "reg")
8599 (set_attr "cpu_facility" "*,z196")
8600 (set_attr "z10prop" "z10_super_E1,*")])
8601
8602
8603 ;;
8604 ;; Branch instruction patterns.
8605 ;;
8606
8607 (define_expand "cbranch<mode>4"
8608 [(set (pc)
8609 (if_then_else (match_operator 0 "comparison_operator"
8610 [(match_operand:GPR 1 "register_operand" "")
8611 (match_operand:GPR 2 "general_operand" "")])
8612 (label_ref (match_operand 3 "" ""))
8613 (pc)))]
8614 ""
8615 "s390_emit_jump (operands[3],
8616 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8617 DONE;")
8618
8619 (define_expand "cbranch<mode>4"
8620 [(set (pc)
8621 (if_then_else (match_operator 0 "comparison_operator"
8622 [(match_operand:FP 1 "register_operand" "")
8623 (match_operand:FP 2 "general_operand" "")])
8624 (label_ref (match_operand 3 "" ""))
8625 (pc)))]
8626 "TARGET_HARD_FLOAT"
8627 "s390_emit_jump (operands[3],
8628 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8629 DONE;")
8630
8631 (define_expand "cbranchcc4"
8632 [(set (pc)
8633 (if_then_else (match_operator 0 "s390_comparison"
8634 [(match_operand 1 "cc_reg_operand" "")
8635 (match_operand 2 "const_int_operand" "")])
8636 (label_ref (match_operand 3 "" ""))
8637 (pc)))]
8638 ""
8639 "")
8640
8641
8642 ;;
8643 ;;- Conditional jump instructions.
8644 ;;
8645
8646 (define_insn "*cjump_64"
8647 [(set (pc)
8648 (if_then_else
8649 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8650 (match_operand 2 "const_int_operand" "")])
8651 (label_ref (match_operand 0 "" ""))
8652 (pc)))]
8653 "TARGET_CPU_ZARCH"
8654 {
8655 if (get_attr_length (insn) == 4)
8656 return "j%C1\t%l0";
8657 else
8658 return "jg%C1\t%l0";
8659 }
8660 [(set_attr "op_type" "RI")
8661 (set_attr "type" "branch")
8662 (set (attr "length")
8663 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8664 (const_int 4) (const_int 6)))])
8665
8666 (define_insn "*cjump_31"
8667 [(set (pc)
8668 (if_then_else
8669 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8670 (match_operand 2 "const_int_operand" "")])
8671 (label_ref (match_operand 0 "" ""))
8672 (pc)))]
8673 "!TARGET_CPU_ZARCH"
8674 {
8675 gcc_assert (get_attr_length (insn) == 4);
8676 return "j%C1\t%l0";
8677 }
8678 [(set_attr "op_type" "RI")
8679 (set_attr "type" "branch")
8680 (set (attr "length")
8681 (if_then_else (not (match_test "flag_pic"))
8682 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8683 (const_int 4) (const_int 6))
8684 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8685 (const_int 4) (const_int 8))))])
8686
8687 (define_insn "*cjump_long"
8688 [(set (pc)
8689 (if_then_else
8690 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8691 (match_operand 0 "address_operand" "ZQZR")
8692 (pc)))]
8693 ""
8694 {
8695 if (get_attr_op_type (insn) == OP_TYPE_RR)
8696 return "b%C1r\t%0";
8697 else
8698 return "b%C1\t%a0";
8699 }
8700 [(set (attr "op_type")
8701 (if_then_else (match_operand 0 "register_operand" "")
8702 (const_string "RR") (const_string "RX")))
8703 (set_attr "type" "branch")
8704 (set_attr "atype" "agen")])
8705
8706 ;; A conditional return instruction.
8707 (define_insn "*c<code>"
8708 [(set (pc)
8709 (if_then_else
8710 (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8711 (ANY_RETURN)
8712 (pc)))]
8713 "s390_can_use_<code>_insn ()"
8714 "b%C0r\t%%r14"
8715 [(set_attr "op_type" "RR")
8716 (set_attr "type" "jsr")
8717 (set_attr "atype" "agen")])
8718
8719 ;;
8720 ;;- Negated conditional jump instructions.
8721 ;;
8722
8723 (define_insn "*icjump_64"
8724 [(set (pc)
8725 (if_then_else
8726 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8727 (pc)
8728 (label_ref (match_operand 0 "" ""))))]
8729 "TARGET_CPU_ZARCH"
8730 {
8731 if (get_attr_length (insn) == 4)
8732 return "j%D1\t%l0";
8733 else
8734 return "jg%D1\t%l0";
8735 }
8736 [(set_attr "op_type" "RI")
8737 (set_attr "type" "branch")
8738 (set (attr "length")
8739 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8740 (const_int 4) (const_int 6)))])
8741
8742 (define_insn "*icjump_31"
8743 [(set (pc)
8744 (if_then_else
8745 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8746 (pc)
8747 (label_ref (match_operand 0 "" ""))))]
8748 "!TARGET_CPU_ZARCH"
8749 {
8750 gcc_assert (get_attr_length (insn) == 4);
8751 return "j%D1\t%l0";
8752 }
8753 [(set_attr "op_type" "RI")
8754 (set_attr "type" "branch")
8755 (set (attr "length")
8756 (if_then_else (not (match_test "flag_pic"))
8757 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8758 (const_int 4) (const_int 6))
8759 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8760 (const_int 4) (const_int 8))))])
8761
8762 (define_insn "*icjump_long"
8763 [(set (pc)
8764 (if_then_else
8765 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8766 (pc)
8767 (match_operand 0 "address_operand" "ZQZR")))]
8768 ""
8769 {
8770 if (get_attr_op_type (insn) == OP_TYPE_RR)
8771 return "b%D1r\t%0";
8772 else
8773 return "b%D1\t%a0";
8774 }
8775 [(set (attr "op_type")
8776 (if_then_else (match_operand 0 "register_operand" "")
8777 (const_string "RR") (const_string "RX")))
8778 (set_attr "type" "branch")
8779 (set_attr "atype" "agen")])
8780
8781 ;;
8782 ;;- Trap instructions.
8783 ;;
8784
8785 (define_insn "trap"
8786 [(trap_if (const_int 1) (const_int 0))]
8787 ""
8788 "j\t.+2"
8789 [(set_attr "op_type" "RI")
8790 (set_attr "type" "branch")])
8791
8792 (define_expand "ctrap<mode>4"
8793 [(trap_if (match_operator 0 "comparison_operator"
8794 [(match_operand:GPR 1 "register_operand" "")
8795 (match_operand:GPR 2 "general_operand" "")])
8796 (match_operand 3 "const0_operand" ""))]
8797 ""
8798 {
8799 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8800 operands[1], operands[2]);
8801 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8802 DONE;
8803 })
8804
8805 (define_expand "ctrap<mode>4"
8806 [(trap_if (match_operator 0 "comparison_operator"
8807 [(match_operand:FP 1 "register_operand" "")
8808 (match_operand:FP 2 "general_operand" "")])
8809 (match_operand 3 "const0_operand" ""))]
8810 ""
8811 {
8812 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8813 operands[1], operands[2]);
8814 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8815 DONE;
8816 })
8817
8818 (define_insn "condtrap"
8819 [(trap_if (match_operator 0 "s390_comparison"
8820 [(match_operand 1 "cc_reg_operand" "c")
8821 (const_int 0)])
8822 (const_int 0))]
8823 ""
8824 "j%C0\t.+2";
8825 [(set_attr "op_type" "RI")
8826 (set_attr "type" "branch")])
8827
8828 ; crt, cgrt, cit, cgit
8829 (define_insn "*cmp_and_trap_signed_int<mode>"
8830 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
8831 [(match_operand:GPR 1 "register_operand" "d,d")
8832 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
8833 (const_int 0))]
8834 "TARGET_Z10"
8835 "@
8836 c<g>rt%C0\t%1,%2
8837 c<g>it%C0\t%1,%h2"
8838 [(set_attr "op_type" "RRF,RIE")
8839 (set_attr "type" "branch")
8840 (set_attr "z10prop" "z10_super_c,z10_super")])
8841
8842 ; clrt, clgrt, clfit, clgit, clt, clgt
8843 (define_insn "*cmp_and_trap_unsigned_int<mode>"
8844 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
8845 [(match_operand:GPR 1 "register_operand" "d,d,d")
8846 (match_operand:GPR 2 "general_operand" "d,D,T")])
8847 (const_int 0))]
8848 "TARGET_Z10"
8849 "@
8850 cl<g>rt%C0\t%1,%2
8851 cl<gf>it%C0\t%1,%x2
8852 cl<g>t%C0\t%1,%2"
8853 [(set_attr "op_type" "RRF,RIE,RSY")
8854 (set_attr "type" "branch")
8855 (set_attr "z10prop" "z10_super_c,z10_super,*")
8856 (set_attr "cpu_facility" "z10,z10,zEC12")])
8857
8858 ; lat, lgat
8859 (define_insn "*load_and_trap<mode>"
8860 [(trap_if (eq (match_operand:GPR 0 "memory_operand" "T")
8861 (const_int 0))
8862 (const_int 0))
8863 (set (match_operand:GPR 1 "register_operand" "=d")
8864 (match_dup 0))]
8865 "TARGET_ZEC12"
8866 "l<g>at\t%1,%0"
8867 [(set_attr "op_type" "RXY")])
8868
8869
8870 ;;
8871 ;;- Loop instructions.
8872 ;;
8873 ;; This is all complicated by the fact that since this is a jump insn
8874 ;; we must handle our own output reloads.
8875
8876 ;; branch on index
8877
8878 ; This splitter will be matched by combine and has to add the 2 moves
8879 ; necessary to load the compare and the increment values into a
8880 ; register pair as needed by brxle.
8881
8882 (define_insn_and_split "*brx_stage1_<GPR:mode>"
8883 [(set (pc)
8884 (if_then_else
8885 (match_operator 6 "s390_brx_operator"
8886 [(plus:GPR (match_operand:GPR 1 "register_operand" "")
8887 (match_operand:GPR 2 "general_operand" ""))
8888 (match_operand:GPR 3 "register_operand" "")])
8889 (label_ref (match_operand 0 "" ""))
8890 (pc)))
8891 (set (match_operand:GPR 4 "nonimmediate_operand" "")
8892 (plus:GPR (match_dup 1) (match_dup 2)))
8893 (clobber (match_scratch:GPR 5 ""))]
8894 "TARGET_CPU_ZARCH"
8895 "#"
8896 "!reload_completed && !reload_in_progress"
8897 [(set (match_dup 7) (match_dup 2)) ; the increment
8898 (set (match_dup 8) (match_dup 3)) ; the comparison value
8899 (parallel [(set (pc)
8900 (if_then_else
8901 (match_op_dup 6
8902 [(plus:GPR (match_dup 1) (match_dup 7))
8903 (match_dup 8)])
8904 (label_ref (match_dup 0))
8905 (pc)))
8906 (set (match_dup 4)
8907 (plus:GPR (match_dup 1) (match_dup 7)))
8908 (clobber (match_dup 5))
8909 (clobber (reg:CC CC_REGNUM))])]
8910 {
8911 rtx dreg = gen_reg_rtx (word_mode == DImode ? TImode : DImode);
8912 operands[7] = gen_lowpart (<GPR:MODE>mode,
8913 gen_highpart (word_mode, dreg));
8914 operands[8] = gen_lowpart (<GPR:MODE>mode,
8915 gen_lowpart (word_mode, dreg));
8916 })
8917
8918 ; brxlg, brxhg
8919
8920 (define_insn_and_split "*brxg_64bit"
8921 [(set (pc)
8922 (if_then_else
8923 (match_operator 5 "s390_brx_operator"
8924 [(plus:DI (match_operand:DI 1 "register_operand" "d,d,d")
8925 (subreg:DI (match_operand:TI 2 "register_operand" "d,d,d") 0))
8926 (subreg:DI (match_dup 2) 8)])
8927 (label_ref (match_operand 0 "" ""))
8928 (pc)))
8929 (set (match_operand:DI 3 "nonimmediate_operand" "=1,?X,?X")
8930 (plus:DI (match_dup 1)
8931 (subreg:DI (match_dup 2) 0)))
8932 (clobber (match_scratch:DI 4 "=X,&1,&?d"))
8933 (clobber (reg:CC CC_REGNUM))]
8934 "TARGET_ZARCH"
8935 {
8936 if (which_alternative != 0)
8937 return "#";
8938 else if (get_attr_length (insn) == 6)
8939 return "brx%E5g\t%1,%2,%l0";
8940 else
8941 return "agr\t%1,%2\;cgr\t%1,%M2\;jg%C5\t%l0";
8942 }
8943 "&& reload_completed
8944 && (!REG_P (operands[3])
8945 || !rtx_equal_p (operands[1], operands[3]))"
8946 [(set (match_dup 4) (match_dup 1))
8947 (parallel [(set (match_dup 4) (plus:DI (match_dup 4) (subreg:DI (match_dup 2) 0)))
8948 (clobber (reg:CC CC_REGNUM))])
8949 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:DI (match_dup 2) 8)))
8950 (set (match_dup 3) (match_dup 4))
8951 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8952 (label_ref (match_dup 0))
8953 (pc)))]
8954 ""
8955 [(set_attr "op_type" "RIE")
8956 (set_attr "type" "branch")
8957 (set (attr "length")
8958 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8959 (const_int 6) (const_int 16)))])
8960
8961 ; brxle, brxh
8962
8963 (define_insn_and_split "*brx_64bit"
8964 [(set (pc)
8965 (if_then_else
8966 (match_operator 5 "s390_brx_operator"
8967 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
8968 (subreg:SI (match_operand:TI 2 "register_operand" "d,d,d") 4))
8969 (subreg:SI (match_dup 2) 12)])
8970 (label_ref (match_operand 0 "" ""))
8971 (pc)))
8972 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
8973 (plus:SI (match_dup 1)
8974 (subreg:SI (match_dup 2) 4)))
8975 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
8976 (clobber (reg:CC CC_REGNUM))]
8977 "TARGET_ZARCH"
8978 {
8979 if (which_alternative != 0)
8980 return "#";
8981 else if (get_attr_length (insn) == 6)
8982 return "brx%C5\t%1,%2,%l0";
8983 else
8984 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
8985 }
8986 "&& reload_completed
8987 && (!REG_P (operands[3])
8988 || !rtx_equal_p (operands[1], operands[3]))"
8989 [(set (match_dup 4) (match_dup 1))
8990 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 4)))
8991 (clobber (reg:CC CC_REGNUM))])
8992 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 12)))
8993 (set (match_dup 3) (match_dup 4))
8994 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8995 (label_ref (match_dup 0))
8996 (pc)))]
8997 ""
8998 [(set_attr "op_type" "RSI")
8999 (set_attr "type" "branch")
9000 (set (attr "length")
9001 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9002 (const_int 6) (const_int 14)))])
9003
9004 ; brxle, brxh
9005
9006 (define_insn_and_split "*brx_31bit"
9007 [(set (pc)
9008 (if_then_else
9009 (match_operator 5 "s390_brx_operator"
9010 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9011 (subreg:SI (match_operand:DI 2 "register_operand" "d,d,d") 0))
9012 (subreg:SI (match_dup 2) 4)])
9013 (label_ref (match_operand 0 "" ""))
9014 (pc)))
9015 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9016 (plus:SI (match_dup 1)
9017 (subreg:SI (match_dup 2) 0)))
9018 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9019 (clobber (reg:CC CC_REGNUM))]
9020 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
9021 {
9022 if (which_alternative != 0)
9023 return "#";
9024 else if (get_attr_length (insn) == 6)
9025 return "brx%C5\t%1,%2,%l0";
9026 else
9027 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9028 }
9029 "&& reload_completed
9030 && (!REG_P (operands[3])
9031 || !rtx_equal_p (operands[1], operands[3]))"
9032 [(set (match_dup 4) (match_dup 1))
9033 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 0)))
9034 (clobber (reg:CC CC_REGNUM))])
9035 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 4)))
9036 (set (match_dup 3) (match_dup 4))
9037 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9038 (label_ref (match_dup 0))
9039 (pc)))]
9040 ""
9041 [(set_attr "op_type" "RSI")
9042 (set_attr "type" "branch")
9043 (set (attr "length")
9044 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9045 (const_int 6) (const_int 14)))])
9046
9047
9048 ;; branch on count
9049
9050 (define_expand "doloop_end"
9051 [(use (match_operand 0 "" "")) ; loop pseudo
9052 (use (match_operand 1 "" ""))] ; label
9053 ""
9054 {
9055 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
9056 emit_jump_insn (gen_doloop_si31 (operands[1], operands[0], operands[0]));
9057 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
9058 emit_jump_insn (gen_doloop_si64 (operands[1], operands[0], operands[0]));
9059 else if (GET_MODE (operands[0]) == DImode && TARGET_ZARCH)
9060 emit_jump_insn (gen_doloop_di (operands[1], operands[0], operands[0]));
9061 else
9062 FAIL;
9063
9064 DONE;
9065 })
9066
9067 (define_insn_and_split "doloop_si64"
9068 [(set (pc)
9069 (if_then_else
9070 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9071 (const_int 1))
9072 (label_ref (match_operand 0 "" ""))
9073 (pc)))
9074 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9075 (plus:SI (match_dup 1) (const_int -1)))
9076 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9077 (clobber (reg:CC CC_REGNUM))]
9078 "TARGET_CPU_ZARCH"
9079 {
9080 if (which_alternative != 0)
9081 return "#";
9082 else if (get_attr_length (insn) == 4)
9083 return "brct\t%1,%l0";
9084 else
9085 return "ahi\t%1,-1\;jgne\t%l0";
9086 }
9087 "&& reload_completed
9088 && (! REG_P (operands[2])
9089 || ! rtx_equal_p (operands[1], operands[2]))"
9090 [(set (match_dup 3) (match_dup 1))
9091 (parallel [(set (reg:CCAN CC_REGNUM)
9092 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9093 (const_int 0)))
9094 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9095 (set (match_dup 2) (match_dup 3))
9096 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9097 (label_ref (match_dup 0))
9098 (pc)))]
9099 ""
9100 [(set_attr "op_type" "RI")
9101 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9102 ; hurt us in the (rare) case of ahi.
9103 (set_attr "z10prop" "z10_super_E1")
9104 (set_attr "type" "branch")
9105 (set (attr "length")
9106 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9107 (const_int 4) (const_int 10)))])
9108
9109 (define_insn_and_split "doloop_si31"
9110 [(set (pc)
9111 (if_then_else
9112 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9113 (const_int 1))
9114 (label_ref (match_operand 0 "" ""))
9115 (pc)))
9116 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9117 (plus:SI (match_dup 1) (const_int -1)))
9118 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9119 (clobber (reg:CC CC_REGNUM))]
9120 "!TARGET_CPU_ZARCH"
9121 {
9122 if (which_alternative != 0)
9123 return "#";
9124 else if (get_attr_length (insn) == 4)
9125 return "brct\t%1,%l0";
9126 else
9127 gcc_unreachable ();
9128 }
9129 "&& reload_completed
9130 && (! REG_P (operands[2])
9131 || ! rtx_equal_p (operands[1], operands[2]))"
9132 [(set (match_dup 3) (match_dup 1))
9133 (parallel [(set (reg:CCAN CC_REGNUM)
9134 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9135 (const_int 0)))
9136 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9137 (set (match_dup 2) (match_dup 3))
9138 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9139 (label_ref (match_dup 0))
9140 (pc)))]
9141 ""
9142 [(set_attr "op_type" "RI")
9143 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9144 ; hurt us in the (rare) case of ahi.
9145 (set_attr "z10prop" "z10_super_E1")
9146 (set_attr "type" "branch")
9147 (set (attr "length")
9148 (if_then_else (not (match_test "flag_pic"))
9149 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9150 (const_int 4) (const_int 6))
9151 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9152 (const_int 4) (const_int 8))))])
9153
9154 (define_insn "*doloop_si_long"
9155 [(set (pc)
9156 (if_then_else
9157 (ne (match_operand:SI 1 "register_operand" "d")
9158 (const_int 1))
9159 (match_operand 0 "address_operand" "ZR")
9160 (pc)))
9161 (set (match_operand:SI 2 "register_operand" "=1")
9162 (plus:SI (match_dup 1) (const_int -1)))
9163 (clobber (match_scratch:SI 3 "=X"))
9164 (clobber (reg:CC CC_REGNUM))]
9165 "!TARGET_CPU_ZARCH"
9166 {
9167 if (get_attr_op_type (insn) == OP_TYPE_RR)
9168 return "bctr\t%1,%0";
9169 else
9170 return "bct\t%1,%a0";
9171 }
9172 [(set (attr "op_type")
9173 (if_then_else (match_operand 0 "register_operand" "")
9174 (const_string "RR") (const_string "RX")))
9175 (set_attr "type" "branch")
9176 (set_attr "atype" "agen")
9177 (set_attr "z10prop" "z10_c")
9178 (set_attr "z196prop" "z196_cracked")])
9179
9180 (define_insn_and_split "doloop_di"
9181 [(set (pc)
9182 (if_then_else
9183 (ne (match_operand:DI 1 "register_operand" "d,d,d")
9184 (const_int 1))
9185 (label_ref (match_operand 0 "" ""))
9186 (pc)))
9187 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
9188 (plus:DI (match_dup 1) (const_int -1)))
9189 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
9190 (clobber (reg:CC CC_REGNUM))]
9191 "TARGET_ZARCH"
9192 {
9193 if (which_alternative != 0)
9194 return "#";
9195 else if (get_attr_length (insn) == 4)
9196 return "brctg\t%1,%l0";
9197 else
9198 return "aghi\t%1,-1\;jgne\t%l0";
9199 }
9200 "&& reload_completed
9201 && (! REG_P (operands[2])
9202 || ! rtx_equal_p (operands[1], operands[2]))"
9203 [(set (match_dup 3) (match_dup 1))
9204 (parallel [(set (reg:CCAN CC_REGNUM)
9205 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
9206 (const_int 0)))
9207 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
9208 (set (match_dup 2) (match_dup 3))
9209 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9210 (label_ref (match_dup 0))
9211 (pc)))]
9212 ""
9213 [(set_attr "op_type" "RI")
9214 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9215 ; hurt us in the (rare) case of ahi.
9216 (set_attr "z10prop" "z10_super_E1")
9217 (set_attr "type" "branch")
9218 (set (attr "length")
9219 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9220 (const_int 4) (const_int 10)))])
9221
9222 ;;
9223 ;;- Unconditional jump instructions.
9224 ;;
9225
9226 ;
9227 ; jump instruction pattern(s).
9228 ;
9229
9230 (define_expand "jump"
9231 [(match_operand 0 "" "")]
9232 ""
9233 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
9234
9235 (define_insn "*jump64"
9236 [(set (pc) (label_ref (match_operand 0 "" "")))]
9237 "TARGET_CPU_ZARCH"
9238 {
9239 if (get_attr_length (insn) == 4)
9240 return "j\t%l0";
9241 else
9242 return "jg\t%l0";
9243 }
9244 [(set_attr "op_type" "RI")
9245 (set_attr "type" "branch")
9246 (set (attr "length")
9247 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9248 (const_int 4) (const_int 6)))])
9249
9250 (define_insn "*jump31"
9251 [(set (pc) (label_ref (match_operand 0 "" "")))]
9252 "!TARGET_CPU_ZARCH"
9253 {
9254 gcc_assert (get_attr_length (insn) == 4);
9255 return "j\t%l0";
9256 }
9257 [(set_attr "op_type" "RI")
9258 (set_attr "type" "branch")
9259 (set (attr "length")
9260 (if_then_else (not (match_test "flag_pic"))
9261 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9262 (const_int 4) (const_int 6))
9263 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9264 (const_int 4) (const_int 8))))])
9265
9266 ;
9267 ; indirect-jump instruction pattern(s).
9268 ;
9269
9270 (define_insn "indirect_jump"
9271 [(set (pc) (match_operand 0 "address_operand" "ZR"))]
9272 ""
9273 {
9274 if (get_attr_op_type (insn) == OP_TYPE_RR)
9275 return "br\t%0";
9276 else
9277 return "b\t%a0";
9278 }
9279 [(set (attr "op_type")
9280 (if_then_else (match_operand 0 "register_operand" "")
9281 (const_string "RR") (const_string "RX")))
9282 (set_attr "type" "branch")
9283 (set_attr "atype" "agen")])
9284
9285 ;
9286 ; casesi instruction pattern(s).
9287 ;
9288
9289 (define_insn "casesi_jump"
9290 [(set (pc) (match_operand 0 "address_operand" "ZR"))
9291 (use (label_ref (match_operand 1 "" "")))]
9292 ""
9293 {
9294 if (get_attr_op_type (insn) == OP_TYPE_RR)
9295 return "br\t%0";
9296 else
9297 return "b\t%a0";
9298 }
9299 [(set (attr "op_type")
9300 (if_then_else (match_operand 0 "register_operand" "")
9301 (const_string "RR") (const_string "RX")))
9302 (set_attr "type" "branch")
9303 (set_attr "atype" "agen")])
9304
9305 (define_expand "casesi"
9306 [(match_operand:SI 0 "general_operand" "")
9307 (match_operand:SI 1 "general_operand" "")
9308 (match_operand:SI 2 "general_operand" "")
9309 (label_ref (match_operand 3 "" ""))
9310 (label_ref (match_operand 4 "" ""))]
9311 ""
9312 {
9313 rtx index = gen_reg_rtx (SImode);
9314 rtx base = gen_reg_rtx (Pmode);
9315 rtx target = gen_reg_rtx (Pmode);
9316
9317 emit_move_insn (index, operands[0]);
9318 emit_insn (gen_subsi3 (index, index, operands[1]));
9319 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
9320 operands[4]);
9321
9322 if (Pmode != SImode)
9323 index = convert_to_mode (Pmode, index, 1);
9324 if (GET_CODE (index) != REG)
9325 index = copy_to_mode_reg (Pmode, index);
9326
9327 if (TARGET_64BIT)
9328 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
9329 else
9330 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
9331
9332 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
9333
9334 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
9335 emit_move_insn (target, index);
9336
9337 if (flag_pic)
9338 target = gen_rtx_PLUS (Pmode, base, target);
9339 emit_jump_insn (gen_casesi_jump (target, operands[3]));
9340
9341 DONE;
9342 })
9343
9344
9345 ;;
9346 ;;- Jump to subroutine.
9347 ;;
9348 ;;
9349
9350 ;
9351 ; untyped call instruction pattern(s).
9352 ;
9353
9354 ;; Call subroutine returning any type.
9355 (define_expand "untyped_call"
9356 [(parallel [(call (match_operand 0 "" "")
9357 (const_int 0))
9358 (match_operand 1 "" "")
9359 (match_operand 2 "" "")])]
9360 ""
9361 {
9362 int i;
9363
9364 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
9365
9366 for (i = 0; i < XVECLEN (operands[2], 0); i++)
9367 {
9368 rtx set = XVECEXP (operands[2], 0, i);
9369 emit_move_insn (SET_DEST (set), SET_SRC (set));
9370 }
9371
9372 /* The optimizer does not know that the call sets the function value
9373 registers we stored in the result block. We avoid problems by
9374 claiming that all hard registers are used and clobbered at this
9375 point. */
9376 emit_insn (gen_blockage ());
9377
9378 DONE;
9379 })
9380
9381 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
9382 ;; all of memory. This blocks insns from being moved across this point.
9383
9384 (define_insn "blockage"
9385 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
9386 ""
9387 ""
9388 [(set_attr "type" "none")
9389 (set_attr "length" "0")])
9390
9391 ;
9392 ; sibcall patterns
9393 ;
9394
9395 (define_expand "sibcall"
9396 [(call (match_operand 0 "" "")
9397 (match_operand 1 "" ""))]
9398 ""
9399 {
9400 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
9401 DONE;
9402 })
9403
9404 (define_insn "*sibcall_br"
9405 [(call (mem:QI (reg SIBCALL_REGNUM))
9406 (match_operand 0 "const_int_operand" "n"))]
9407 "SIBLING_CALL_P (insn)
9408 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
9409 "br\t%%r1"
9410 [(set_attr "op_type" "RR")
9411 (set_attr "type" "branch")
9412 (set_attr "atype" "agen")])
9413
9414 (define_insn "*sibcall_brc"
9415 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9416 (match_operand 1 "const_int_operand" "n"))]
9417 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9418 "j\t%0"
9419 [(set_attr "op_type" "RI")
9420 (set_attr "type" "branch")])
9421
9422 (define_insn "*sibcall_brcl"
9423 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9424 (match_operand 1 "const_int_operand" "n"))]
9425 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9426 "jg\t%0"
9427 [(set_attr "op_type" "RIL")
9428 (set_attr "type" "branch")])
9429
9430 ;
9431 ; sibcall_value patterns
9432 ;
9433
9434 (define_expand "sibcall_value"
9435 [(set (match_operand 0 "" "")
9436 (call (match_operand 1 "" "")
9437 (match_operand 2 "" "")))]
9438 ""
9439 {
9440 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
9441 DONE;
9442 })
9443
9444 (define_insn "*sibcall_value_br"
9445 [(set (match_operand 0 "" "")
9446 (call (mem:QI (reg SIBCALL_REGNUM))
9447 (match_operand 1 "const_int_operand" "n")))]
9448 "SIBLING_CALL_P (insn)
9449 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
9450 "br\t%%r1"
9451 [(set_attr "op_type" "RR")
9452 (set_attr "type" "branch")
9453 (set_attr "atype" "agen")])
9454
9455 (define_insn "*sibcall_value_brc"
9456 [(set (match_operand 0 "" "")
9457 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9458 (match_operand 2 "const_int_operand" "n")))]
9459 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9460 "j\t%1"
9461 [(set_attr "op_type" "RI")
9462 (set_attr "type" "branch")])
9463
9464 (define_insn "*sibcall_value_brcl"
9465 [(set (match_operand 0 "" "")
9466 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9467 (match_operand 2 "const_int_operand" "n")))]
9468 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9469 "jg\t%1"
9470 [(set_attr "op_type" "RIL")
9471 (set_attr "type" "branch")])
9472
9473
9474 ;
9475 ; call instruction pattern(s).
9476 ;
9477
9478 (define_expand "call"
9479 [(call (match_operand 0 "" "")
9480 (match_operand 1 "" ""))
9481 (use (match_operand 2 "" ""))]
9482 ""
9483 {
9484 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
9485 gen_rtx_REG (Pmode, RETURN_REGNUM));
9486 DONE;
9487 })
9488
9489 (define_insn "*bras"
9490 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9491 (match_operand 1 "const_int_operand" "n"))
9492 (clobber (match_operand 2 "register_operand" "=r"))]
9493 "!SIBLING_CALL_P (insn)
9494 && TARGET_SMALL_EXEC
9495 && GET_MODE (operands[2]) == Pmode"
9496 "bras\t%2,%0"
9497 [(set_attr "op_type" "RI")
9498 (set_attr "type" "jsr")
9499 (set_attr "z196prop" "z196_cracked")])
9500
9501 (define_insn "*brasl"
9502 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9503 (match_operand 1 "const_int_operand" "n"))
9504 (clobber (match_operand 2 "register_operand" "=r"))]
9505 "!SIBLING_CALL_P (insn)
9506 && TARGET_CPU_ZARCH
9507 && GET_MODE (operands[2]) == Pmode"
9508 "brasl\t%2,%0"
9509 [(set_attr "op_type" "RIL")
9510 (set_attr "type" "jsr")
9511 (set_attr "z196prop" "z196_cracked")])
9512
9513 (define_insn "*basr"
9514 [(call (mem:QI (match_operand 0 "address_operand" "ZR"))
9515 (match_operand 1 "const_int_operand" "n"))
9516 (clobber (match_operand 2 "register_operand" "=r"))]
9517 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
9518 {
9519 if (get_attr_op_type (insn) == OP_TYPE_RR)
9520 return "basr\t%2,%0";
9521 else
9522 return "bas\t%2,%a0";
9523 }
9524 [(set (attr "op_type")
9525 (if_then_else (match_operand 0 "register_operand" "")
9526 (const_string "RR") (const_string "RX")))
9527 (set_attr "type" "jsr")
9528 (set_attr "atype" "agen")
9529 (set_attr "z196prop" "z196_cracked")])
9530
9531 ;
9532 ; call_value instruction pattern(s).
9533 ;
9534
9535 (define_expand "call_value"
9536 [(set (match_operand 0 "" "")
9537 (call (match_operand 1 "" "")
9538 (match_operand 2 "" "")))
9539 (use (match_operand 3 "" ""))]
9540 ""
9541 {
9542 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
9543 gen_rtx_REG (Pmode, RETURN_REGNUM));
9544 DONE;
9545 })
9546
9547 (define_insn "*bras_r"
9548 [(set (match_operand 0 "" "")
9549 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9550 (match_operand:SI 2 "const_int_operand" "n")))
9551 (clobber (match_operand 3 "register_operand" "=r"))]
9552 "!SIBLING_CALL_P (insn)
9553 && TARGET_SMALL_EXEC
9554 && GET_MODE (operands[3]) == Pmode"
9555 "bras\t%3,%1"
9556 [(set_attr "op_type" "RI")
9557 (set_attr "type" "jsr")
9558 (set_attr "z196prop" "z196_cracked")])
9559
9560 (define_insn "*brasl_r"
9561 [(set (match_operand 0 "" "")
9562 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9563 (match_operand 2 "const_int_operand" "n")))
9564 (clobber (match_operand 3 "register_operand" "=r"))]
9565 "!SIBLING_CALL_P (insn)
9566 && TARGET_CPU_ZARCH
9567 && GET_MODE (operands[3]) == Pmode"
9568 "brasl\t%3,%1"
9569 [(set_attr "op_type" "RIL")
9570 (set_attr "type" "jsr")
9571 (set_attr "z196prop" "z196_cracked")])
9572
9573 (define_insn "*basr_r"
9574 [(set (match_operand 0 "" "")
9575 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9576 (match_operand 2 "const_int_operand" "n")))
9577 (clobber (match_operand 3 "register_operand" "=r"))]
9578 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9579 {
9580 if (get_attr_op_type (insn) == OP_TYPE_RR)
9581 return "basr\t%3,%1";
9582 else
9583 return "bas\t%3,%a1";
9584 }
9585 [(set (attr "op_type")
9586 (if_then_else (match_operand 1 "register_operand" "")
9587 (const_string "RR") (const_string "RX")))
9588 (set_attr "type" "jsr")
9589 (set_attr "atype" "agen")
9590 (set_attr "z196prop" "z196_cracked")])
9591
9592 ;;
9593 ;;- Thread-local storage support.
9594 ;;
9595
9596 (define_expand "get_thread_pointer<mode>"
9597 [(set (match_operand:P 0 "nonimmediate_operand" "") (reg:P TP_REGNUM))]
9598 ""
9599 "")
9600
9601 (define_expand "set_thread_pointer<mode>"
9602 [(set (reg:P TP_REGNUM) (match_operand:P 0 "nonimmediate_operand" ""))
9603 (set (reg:P TP_REGNUM) (unspec_volatile:P [(reg:P TP_REGNUM)] UNSPECV_SET_TP))]
9604 ""
9605 "")
9606
9607 (define_insn "*set_tp"
9608 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
9609 ""
9610 ""
9611 [(set_attr "type" "none")
9612 (set_attr "length" "0")])
9613
9614 (define_insn "*tls_load_64"
9615 [(set (match_operand:DI 0 "register_operand" "=d")
9616 (unspec:DI [(match_operand:DI 1 "memory_operand" "T")
9617 (match_operand:DI 2 "" "")]
9618 UNSPEC_TLS_LOAD))]
9619 "TARGET_64BIT"
9620 "lg\t%0,%1%J2"
9621 [(set_attr "op_type" "RXE")
9622 (set_attr "z10prop" "z10_fwd_A3")])
9623
9624 (define_insn "*tls_load_31"
9625 [(set (match_operand:SI 0 "register_operand" "=d,d")
9626 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
9627 (match_operand:SI 2 "" "")]
9628 UNSPEC_TLS_LOAD))]
9629 "!TARGET_64BIT"
9630 "@
9631 l\t%0,%1%J2
9632 ly\t%0,%1%J2"
9633 [(set_attr "op_type" "RX,RXY")
9634 (set_attr "type" "load")
9635 (set_attr "cpu_facility" "*,longdisp")
9636 (set_attr "z10prop" "z10_fwd_A3,z10_fwd_A3")])
9637
9638 (define_insn "*bras_tls"
9639 [(set (match_operand 0 "" "")
9640 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9641 (match_operand 2 "const_int_operand" "n")))
9642 (clobber (match_operand 3 "register_operand" "=r"))
9643 (use (match_operand 4 "" ""))]
9644 "!SIBLING_CALL_P (insn)
9645 && TARGET_SMALL_EXEC
9646 && GET_MODE (operands[3]) == Pmode"
9647 "bras\t%3,%1%J4"
9648 [(set_attr "op_type" "RI")
9649 (set_attr "type" "jsr")
9650 (set_attr "z196prop" "z196_cracked")])
9651
9652 (define_insn "*brasl_tls"
9653 [(set (match_operand 0 "" "")
9654 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9655 (match_operand 2 "const_int_operand" "n")))
9656 (clobber (match_operand 3 "register_operand" "=r"))
9657 (use (match_operand 4 "" ""))]
9658 "!SIBLING_CALL_P (insn)
9659 && TARGET_CPU_ZARCH
9660 && GET_MODE (operands[3]) == Pmode"
9661 "brasl\t%3,%1%J4"
9662 [(set_attr "op_type" "RIL")
9663 (set_attr "type" "jsr")
9664 (set_attr "z196prop" "z196_cracked")])
9665
9666 (define_insn "*basr_tls"
9667 [(set (match_operand 0 "" "")
9668 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9669 (match_operand 2 "const_int_operand" "n")))
9670 (clobber (match_operand 3 "register_operand" "=r"))
9671 (use (match_operand 4 "" ""))]
9672 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9673 {
9674 if (get_attr_op_type (insn) == OP_TYPE_RR)
9675 return "basr\t%3,%1%J4";
9676 else
9677 return "bas\t%3,%a1%J4";
9678 }
9679 [(set (attr "op_type")
9680 (if_then_else (match_operand 1 "register_operand" "")
9681 (const_string "RR") (const_string "RX")))
9682 (set_attr "type" "jsr")
9683 (set_attr "atype" "agen")
9684 (set_attr "z196prop" "z196_cracked")])
9685
9686 ;;
9687 ;;- Atomic operations
9688 ;;
9689
9690 ;
9691 ; memory barrier patterns.
9692 ;
9693
9694 (define_expand "mem_signal_fence"
9695 [(match_operand:SI 0 "const_int_operand")] ;; model
9696 ""
9697 {
9698 /* The s390 memory model is strong enough not to require any
9699 barrier in order to synchronize a thread with itself. */
9700 DONE;
9701 })
9702
9703 (define_expand "mem_thread_fence"
9704 [(match_operand:SI 0 "const_int_operand")] ;; model
9705 ""
9706 {
9707 /* Unless this is a SEQ_CST fence, the s390 memory model is strong
9708 enough not to require barriers of any kind. */
9709 if (is_mm_seq_cst (memmodel_from_int (INTVAL (operands[0]))))
9710 {
9711 rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
9712 MEM_VOLATILE_P (mem) = 1;
9713 emit_insn (gen_mem_thread_fence_1 (mem));
9714 }
9715 DONE;
9716 })
9717
9718 ; Although bcr is superscalar on Z10, this variant will never
9719 ; become part of an execution group.
9720 ; With z196 we can make use of the fast-BCR-serialization facility.
9721 ; This allows for a slightly faster sync which is sufficient for our
9722 ; purposes.
9723 (define_insn "mem_thread_fence_1"
9724 [(set (match_operand:BLK 0 "" "")
9725 (unspec:BLK [(match_dup 0)] UNSPEC_MB))]
9726 ""
9727 {
9728 if (TARGET_Z196)
9729 return "bcr\t14,0";
9730 else
9731 return "bcr\t15,0";
9732 }
9733 [(set_attr "op_type" "RR")
9734 (set_attr "mnemonic" "bcr_flush")
9735 (set_attr "z196prop" "z196_alone")])
9736
9737 ;
9738 ; atomic load/store operations
9739 ;
9740
9741 ; Atomic loads need not examine the memory model at all.
9742 (define_expand "atomic_load<mode>"
9743 [(match_operand:DINT 0 "register_operand") ;; output
9744 (match_operand:DINT 1 "memory_operand") ;; memory
9745 (match_operand:SI 2 "const_int_operand")] ;; model
9746 ""
9747 {
9748 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9749 FAIL;
9750
9751 if (<MODE>mode == TImode)
9752 emit_insn (gen_atomic_loadti_1 (operands[0], operands[1]));
9753 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9754 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1]));
9755 else
9756 emit_move_insn (operands[0], operands[1]);
9757 DONE;
9758 })
9759
9760 ; Different from movdi_31 in that we want no splitters.
9761 (define_insn "atomic_loaddi_1"
9762 [(set (match_operand:DI 0 "register_operand" "=d,d,!*f,!*f")
9763 (unspec:DI [(match_operand:DI 1 "memory_operand" "Q,S,R,T")]
9764 UNSPEC_MOVA))]
9765 "!TARGET_ZARCH"
9766 "@
9767 lm\t%0,%M0,%S1
9768 lmy\t%0,%M0,%S1
9769 ld\t%0,%1
9770 ldy\t%0,%1"
9771 [(set_attr "op_type" "RS,RSY,RS,RSY")
9772 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9773 (set_attr "type" "lm,lm,floaddf,floaddf")])
9774
9775 (define_insn "atomic_loadti_1"
9776 [(set (match_operand:TI 0 "register_operand" "=r")
9777 (unspec:TI [(match_operand:TI 1 "memory_operand" "T")]
9778 UNSPEC_MOVA))]
9779 "TARGET_ZARCH"
9780 "lpq\t%0,%1"
9781 [(set_attr "op_type" "RXY")
9782 (set_attr "type" "other")])
9783
9784 ; Atomic stores must(?) enforce sequential consistency.
9785 (define_expand "atomic_store<mode>"
9786 [(match_operand:DINT 0 "memory_operand") ;; memory
9787 (match_operand:DINT 1 "register_operand") ;; input
9788 (match_operand:SI 2 "const_int_operand")] ;; model
9789 ""
9790 {
9791 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
9792
9793 if (MEM_ALIGN (operands[0]) < GET_MODE_BITSIZE (GET_MODE (operands[0])))
9794 FAIL;
9795
9796 if (<MODE>mode == TImode)
9797 emit_insn (gen_atomic_storeti_1 (operands[0], operands[1]));
9798 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9799 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1]));
9800 else
9801 emit_move_insn (operands[0], operands[1]);
9802 if (is_mm_seq_cst (model))
9803 emit_insn (gen_mem_thread_fence (operands[2]));
9804 DONE;
9805 })
9806
9807 ; Different from movdi_31 in that we want no splitters.
9808 (define_insn "atomic_storedi_1"
9809 [(set (match_operand:DI 0 "memory_operand" "=Q,S,R,T")
9810 (unspec:DI [(match_operand:DI 1 "register_operand" "d,d,!*f,!*f")]
9811 UNSPEC_MOVA))]
9812 "!TARGET_ZARCH"
9813 "@
9814 stm\t%1,%N1,%S0
9815 stmy\t%1,%N1,%S0
9816 std %1,%0
9817 stdy %1,%0"
9818 [(set_attr "op_type" "RS,RSY,RS,RSY")
9819 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9820 (set_attr "type" "stm,stm,fstoredf,fstoredf")])
9821
9822 (define_insn "atomic_storeti_1"
9823 [(set (match_operand:TI 0 "memory_operand" "=T")
9824 (unspec:TI [(match_operand:TI 1 "register_operand" "r")]
9825 UNSPEC_MOVA))]
9826 "TARGET_ZARCH"
9827 "stpq\t%1,%0"
9828 [(set_attr "op_type" "RXY")
9829 (set_attr "type" "other")])
9830
9831 ;
9832 ; compare and swap patterns.
9833 ;
9834
9835 (define_expand "atomic_compare_and_swap<mode>"
9836 [(match_operand:SI 0 "register_operand") ;; bool success output
9837 (match_operand:DGPR 1 "nonimmediate_operand");; oldval output
9838 (match_operand:DGPR 2 "memory_operand") ;; memory
9839 (match_operand:DGPR 3 "register_operand") ;; expected intput
9840 (match_operand:DGPR 4 "register_operand") ;; newval intput
9841 (match_operand:SI 5 "const_int_operand") ;; is_weak
9842 (match_operand:SI 6 "const_int_operand") ;; success model
9843 (match_operand:SI 7 "const_int_operand")] ;; failure model
9844 ""
9845 {
9846 rtx cc, cmp, output = operands[1];
9847
9848 if (!register_operand (output, <MODE>mode))
9849 output = gen_reg_rtx (<MODE>mode);
9850
9851 if (MEM_ALIGN (operands[2]) < GET_MODE_BITSIZE (GET_MODE (operands[2])))
9852 FAIL;
9853
9854 emit_insn (gen_atomic_compare_and_swap<mode>_internal
9855 (output, operands[2], operands[3], operands[4]));
9856
9857 /* We deliberately accept non-register operands in the predicate
9858 to ensure the write back to the output operand happens *before*
9859 the store-flags code below. This makes it easier for combine
9860 to merge the store-flags code with a potential test-and-branch
9861 pattern following (immediately!) afterwards. */
9862 if (output != operands[1])
9863 emit_move_insn (operands[1], output);
9864
9865 cc = gen_rtx_REG (CCZ1mode, CC_REGNUM);
9866 cmp = gen_rtx_EQ (SImode, cc, const0_rtx);
9867 emit_insn (gen_cstorecc4 (operands[0], cmp, cc, const0_rtx));
9868 DONE;
9869 })
9870
9871 (define_expand "atomic_compare_and_swap<mode>"
9872 [(match_operand:SI 0 "register_operand") ;; bool success output
9873 (match_operand:HQI 1 "nonimmediate_operand") ;; oldval output
9874 (match_operand:HQI 2 "memory_operand") ;; memory
9875 (match_operand:HQI 3 "general_operand") ;; expected intput
9876 (match_operand:HQI 4 "general_operand") ;; newval intput
9877 (match_operand:SI 5 "const_int_operand") ;; is_weak
9878 (match_operand:SI 6 "const_int_operand") ;; success model
9879 (match_operand:SI 7 "const_int_operand")] ;; failure model
9880 ""
9881 {
9882 s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1], operands[2],
9883 operands[3], operands[4], INTVAL (operands[5]));
9884 DONE;
9885 })
9886
9887 (define_expand "atomic_compare_and_swap<mode>_internal"
9888 [(parallel
9889 [(set (match_operand:DGPR 0 "register_operand")
9890 (match_operand:DGPR 1 "memory_operand"))
9891 (set (match_dup 1)
9892 (unspec_volatile:DGPR
9893 [(match_dup 1)
9894 (match_operand:DGPR 2 "register_operand")
9895 (match_operand:DGPR 3 "register_operand")]
9896 UNSPECV_CAS))
9897 (set (reg:CCZ1 CC_REGNUM)
9898 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
9899 "")
9900
9901 ; cdsg, csg
9902 (define_insn "*atomic_compare_and_swap<mode>_1"
9903 [(set (match_operand:TDI 0 "register_operand" "=r")
9904 (match_operand:TDI 1 "memory_operand" "+S"))
9905 (set (match_dup 1)
9906 (unspec_volatile:TDI
9907 [(match_dup 1)
9908 (match_operand:TDI 2 "register_operand" "0")
9909 (match_operand:TDI 3 "register_operand" "r")]
9910 UNSPECV_CAS))
9911 (set (reg:CCZ1 CC_REGNUM)
9912 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9913 "TARGET_ZARCH"
9914 "c<td>sg\t%0,%3,%S1"
9915 [(set_attr "op_type" "RSY")
9916 (set_attr "type" "sem")])
9917
9918 ; cds, cdsy
9919 (define_insn "*atomic_compare_and_swapdi_2"
9920 [(set (match_operand:DI 0 "register_operand" "=r,r")
9921 (match_operand:DI 1 "memory_operand" "+Q,S"))
9922 (set (match_dup 1)
9923 (unspec_volatile:DI
9924 [(match_dup 1)
9925 (match_operand:DI 2 "register_operand" "0,0")
9926 (match_operand:DI 3 "register_operand" "r,r")]
9927 UNSPECV_CAS))
9928 (set (reg:CCZ1 CC_REGNUM)
9929 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9930 "!TARGET_ZARCH"
9931 "@
9932 cds\t%0,%3,%S1
9933 cdsy\t%0,%3,%S1"
9934 [(set_attr "op_type" "RS,RSY")
9935 (set_attr "cpu_facility" "*,longdisp")
9936 (set_attr "type" "sem")])
9937
9938 ; cs, csy
9939 (define_insn "*atomic_compare_and_swapsi_3"
9940 [(set (match_operand:SI 0 "register_operand" "=r,r")
9941 (match_operand:SI 1 "memory_operand" "+Q,S"))
9942 (set (match_dup 1)
9943 (unspec_volatile:SI
9944 [(match_dup 1)
9945 (match_operand:SI 2 "register_operand" "0,0")
9946 (match_operand:SI 3 "register_operand" "r,r")]
9947 UNSPECV_CAS))
9948 (set (reg:CCZ1 CC_REGNUM)
9949 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9950 ""
9951 "@
9952 cs\t%0,%3,%S1
9953 csy\t%0,%3,%S1"
9954 [(set_attr "op_type" "RS,RSY")
9955 (set_attr "cpu_facility" "*,longdisp")
9956 (set_attr "type" "sem")])
9957
9958 ;
9959 ; Other atomic instruction patterns.
9960 ;
9961
9962 ; z196 load and add, xor, or and and instructions
9963
9964 (define_expand "atomic_fetch_<atomic><mode>"
9965 [(match_operand:GPR 0 "register_operand") ;; val out
9966 (ATOMIC_Z196:GPR
9967 (match_operand:GPR 1 "memory_operand") ;; memory
9968 (match_operand:GPR 2 "register_operand")) ;; val in
9969 (match_operand:SI 3 "const_int_operand")] ;; model
9970 "TARGET_Z196"
9971 {
9972 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9973 FAIL;
9974
9975 emit_insn (gen_atomic_fetch_<atomic><mode>_iaf
9976 (operands[0], operands[1], operands[2]));
9977 DONE;
9978 })
9979
9980 ; lan, lang, lao, laog, lax, laxg, laa, laag
9981 (define_insn "atomic_fetch_<atomic><mode>_iaf"
9982 [(set (match_operand:GPR 0 "register_operand" "=d")
9983 (match_operand:GPR 1 "memory_operand" "+S"))
9984 (set (match_dup 1)
9985 (unspec_volatile:GPR
9986 [(ATOMIC_Z196:GPR (match_dup 1)
9987 (match_operand:GPR 2 "general_operand" "d"))]
9988 UNSPECV_ATOMIC_OP))
9989 (clobber (reg:CC CC_REGNUM))]
9990 "TARGET_Z196"
9991 "la<noxa><g>\t%0,%2,%1"
9992 [(set_attr "op_type" "RSY")
9993 (set_attr "type" "sem")])
9994
9995 ;; For SImode and larger, the optabs.c code will do just fine in
9996 ;; expanding a compare-and-swap loop. For QI/HImode, we can do
9997 ;; better by expanding our own loop.
9998
9999 (define_expand "atomic_<atomic><mode>"
10000 [(ATOMIC:HQI
10001 (match_operand:HQI 0 "memory_operand") ;; memory
10002 (match_operand:HQI 1 "general_operand")) ;; val in
10003 (match_operand:SI 2 "const_int_operand")] ;; model
10004 ""
10005 {
10006 s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
10007 operands[1], false);
10008 DONE;
10009 })
10010
10011 (define_expand "atomic_fetch_<atomic><mode>"
10012 [(match_operand:HQI 0 "register_operand") ;; val out
10013 (ATOMIC:HQI
10014 (match_operand:HQI 1 "memory_operand") ;; memory
10015 (match_operand:HQI 2 "general_operand")) ;; val in
10016 (match_operand:SI 3 "const_int_operand")] ;; model
10017 ""
10018 {
10019 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10020 operands[2], false);
10021 DONE;
10022 })
10023
10024 (define_expand "atomic_<atomic>_fetch<mode>"
10025 [(match_operand:HQI 0 "register_operand") ;; val out
10026 (ATOMIC:HQI
10027 (match_operand:HQI 1 "memory_operand") ;; memory
10028 (match_operand:HQI 2 "general_operand")) ;; val in
10029 (match_operand:SI 3 "const_int_operand")] ;; model
10030 ""
10031 {
10032 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10033 operands[2], true);
10034 DONE;
10035 })
10036
10037 (define_expand "atomic_exchange<mode>"
10038 [(match_operand:HQI 0 "register_operand") ;; val out
10039 (match_operand:HQI 1 "memory_operand") ;; memory
10040 (match_operand:HQI 2 "general_operand") ;; val in
10041 (match_operand:SI 3 "const_int_operand")] ;; model
10042 ""
10043 {
10044 s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
10045 operands[2], false);
10046 DONE;
10047 })
10048
10049 ;;
10050 ;;- Miscellaneous instructions.
10051 ;;
10052
10053 ;
10054 ; allocate stack instruction pattern(s).
10055 ;
10056
10057 (define_expand "allocate_stack"
10058 [(match_operand 0 "general_operand" "")
10059 (match_operand 1 "general_operand" "")]
10060 "TARGET_BACKCHAIN"
10061 {
10062 rtx temp = gen_reg_rtx (Pmode);
10063
10064 emit_move_insn (temp, s390_back_chain_rtx ());
10065 anti_adjust_stack (operands[1]);
10066 emit_move_insn (s390_back_chain_rtx (), temp);
10067
10068 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
10069 DONE;
10070 })
10071
10072
10073 ;
10074 ; setjmp instruction pattern.
10075 ;
10076
10077 (define_expand "builtin_setjmp_receiver"
10078 [(match_operand 0 "" "")]
10079 "flag_pic"
10080 {
10081 emit_insn (s390_load_got ());
10082 emit_use (pic_offset_table_rtx);
10083 DONE;
10084 })
10085
10086 ;; These patterns say how to save and restore the stack pointer. We need not
10087 ;; save the stack pointer at function level since we are careful to
10088 ;; preserve the backchain. At block level, we have to restore the backchain
10089 ;; when we restore the stack pointer.
10090 ;;
10091 ;; For nonlocal gotos, we must save both the stack pointer and its
10092 ;; backchain and restore both. Note that in the nonlocal case, the
10093 ;; save area is a memory location.
10094
10095 (define_expand "save_stack_function"
10096 [(match_operand 0 "general_operand" "")
10097 (match_operand 1 "general_operand" "")]
10098 ""
10099 "DONE;")
10100
10101 (define_expand "restore_stack_function"
10102 [(match_operand 0 "general_operand" "")
10103 (match_operand 1 "general_operand" "")]
10104 ""
10105 "DONE;")
10106
10107 (define_expand "restore_stack_block"
10108 [(match_operand 0 "register_operand" "")
10109 (match_operand 1 "register_operand" "")]
10110 "TARGET_BACKCHAIN"
10111 {
10112 rtx temp = gen_reg_rtx (Pmode);
10113
10114 emit_move_insn (temp, s390_back_chain_rtx ());
10115 emit_move_insn (operands[0], operands[1]);
10116 emit_move_insn (s390_back_chain_rtx (), temp);
10117
10118 DONE;
10119 })
10120
10121 (define_expand "save_stack_nonlocal"
10122 [(match_operand 0 "memory_operand" "")
10123 (match_operand 1 "register_operand" "")]
10124 ""
10125 {
10126 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10127
10128 /* Copy the backchain to the first word, sp to the second and the
10129 literal pool base to the third. */
10130
10131 rtx save_bc = adjust_address (operands[0], Pmode, 0);
10132 rtx save_sp = adjust_address (operands[0], Pmode, GET_MODE_SIZE (Pmode));
10133 rtx save_bp = adjust_address (operands[0], Pmode, 2 * GET_MODE_SIZE (Pmode));
10134
10135 if (TARGET_BACKCHAIN)
10136 emit_move_insn (save_bc, force_reg (Pmode, s390_back_chain_rtx ()));
10137
10138 emit_move_insn (save_sp, operands[1]);
10139 emit_move_insn (save_bp, base);
10140
10141 DONE;
10142 })
10143
10144 (define_expand "restore_stack_nonlocal"
10145 [(match_operand 0 "register_operand" "")
10146 (match_operand 1 "memory_operand" "")]
10147 ""
10148 {
10149 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10150 rtx temp = NULL_RTX;
10151
10152 /* Restore the backchain from the first word, sp from the second and the
10153 literal pool base from the third. */
10154
10155 rtx save_bc = adjust_address (operands[1], Pmode, 0);
10156 rtx save_sp = adjust_address (operands[1], Pmode, GET_MODE_SIZE (Pmode));
10157 rtx save_bp = adjust_address (operands[1], Pmode, 2 * GET_MODE_SIZE (Pmode));
10158
10159 if (TARGET_BACKCHAIN)
10160 temp = force_reg (Pmode, save_bc);
10161
10162 emit_move_insn (base, save_bp);
10163 emit_move_insn (operands[0], save_sp);
10164
10165 if (temp)
10166 emit_move_insn (s390_back_chain_rtx (), temp);
10167
10168 emit_use (base);
10169 DONE;
10170 })
10171
10172 (define_expand "exception_receiver"
10173 [(const_int 0)]
10174 ""
10175 {
10176 s390_set_has_landing_pad_p (true);
10177 DONE;
10178 })
10179
10180 ;
10181 ; nop instruction pattern(s).
10182 ;
10183
10184 (define_insn "nop"
10185 [(const_int 0)]
10186 ""
10187 "lr\t0,0"
10188 [(set_attr "op_type" "RR")
10189 (set_attr "z10prop" "z10_fr_E1")])
10190
10191 (define_insn "nop1"
10192 [(const_int 1)]
10193 ""
10194 "lr\t1,1"
10195 [(set_attr "op_type" "RR")])
10196
10197 ;;- Undeletable nops (used for hotpatching)
10198
10199 (define_insn "nop_2_byte"
10200 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_2_BYTE)]
10201 ""
10202 "nopr\t%%r7"
10203 [(set_attr "op_type" "RR")])
10204
10205 (define_insn "nop_4_byte"
10206 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_4_BYTE)]
10207 ""
10208 "nop\t0"
10209 [(set_attr "op_type" "RX")])
10210
10211 (define_insn "nop_6_byte"
10212 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_6_BYTE)]
10213 "TARGET_CPU_ZARCH"
10214 "brcl\t0, 0"
10215 [(set_attr "op_type" "RIL")])
10216
10217
10218 ;
10219 ; Special literal pool access instruction pattern(s).
10220 ;
10221
10222 (define_insn "*pool_entry"
10223 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
10224 UNSPECV_POOL_ENTRY)]
10225 ""
10226 {
10227 machine_mode mode = GET_MODE (PATTERN (insn));
10228 unsigned int align = GET_MODE_BITSIZE (mode);
10229 s390_output_pool_entry (operands[0], mode, align);
10230 return "";
10231 }
10232 [(set (attr "length")
10233 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
10234
10235 (define_insn "pool_align"
10236 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
10237 UNSPECV_POOL_ALIGN)]
10238 ""
10239 ".align\t%0"
10240 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10241
10242 (define_insn "pool_section_start"
10243 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
10244 ""
10245 {
10246 switch_to_section (targetm.asm_out.function_rodata_section
10247 (current_function_decl));
10248 return "";
10249 }
10250 [(set_attr "length" "0")])
10251
10252 (define_insn "pool_section_end"
10253 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
10254 ""
10255 {
10256 switch_to_section (current_function_section ());
10257 return "";
10258 }
10259 [(set_attr "length" "0")])
10260
10261 (define_insn "main_base_31_small"
10262 [(set (match_operand 0 "register_operand" "=a")
10263 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10264 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10265 "basr\t%0,0"
10266 [(set_attr "op_type" "RR")
10267 (set_attr "type" "la")
10268 (set_attr "z196prop" "z196_cracked")])
10269
10270 (define_insn "main_base_31_large"
10271 [(set (match_operand 0 "register_operand" "=a")
10272 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
10273 (set (pc) (label_ref (match_operand 2 "" "")))]
10274 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10275 "bras\t%0,%2"
10276 [(set_attr "op_type" "RI")
10277 (set_attr "z196prop" "z196_cracked")])
10278
10279 (define_insn "main_base_64"
10280 [(set (match_operand 0 "register_operand" "=a")
10281 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10282 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10283 "larl\t%0,%1"
10284 [(set_attr "op_type" "RIL")
10285 (set_attr "type" "larl")
10286 (set_attr "z10prop" "z10_fwd_A1")])
10287
10288 (define_insn "main_pool"
10289 [(set (match_operand 0 "register_operand" "=a")
10290 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
10291 "GET_MODE (operands[0]) == Pmode"
10292 {
10293 gcc_unreachable ();
10294 }
10295 [(set (attr "type")
10296 (if_then_else (match_test "TARGET_CPU_ZARCH")
10297 (const_string "larl") (const_string "la")))])
10298
10299 (define_insn "reload_base_31"
10300 [(set (match_operand 0 "register_operand" "=a")
10301 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10302 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10303 "basr\t%0,0\;la\t%0,%1-.(%0)"
10304 [(set_attr "length" "6")
10305 (set_attr "type" "la")
10306 (set_attr "z196prop" "z196_cracked")])
10307
10308 (define_insn "reload_base_64"
10309 [(set (match_operand 0 "register_operand" "=a")
10310 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10311 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10312 "larl\t%0,%1"
10313 [(set_attr "op_type" "RIL")
10314 (set_attr "type" "larl")
10315 (set_attr "z10prop" "z10_fwd_A1")])
10316
10317 (define_insn "pool"
10318 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
10319 ""
10320 {
10321 gcc_unreachable ();
10322 }
10323 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10324
10325 ;;
10326 ;; Insns related to generating the function prologue and epilogue.
10327 ;;
10328
10329
10330 (define_expand "prologue"
10331 [(use (const_int 0))]
10332 ""
10333 "s390_emit_prologue (); DONE;")
10334
10335 (define_expand "epilogue"
10336 [(use (const_int 1))]
10337 ""
10338 "s390_emit_epilogue (false); DONE;")
10339
10340 (define_expand "sibcall_epilogue"
10341 [(use (const_int 0))]
10342 ""
10343 "s390_emit_epilogue (true); DONE;")
10344
10345 ;; A direct return instruction, without using an epilogue.
10346 (define_insn "<code>"
10347 [(ANY_RETURN)]
10348 "s390_can_use_<code>_insn ()"
10349 "br\t%%r14"
10350 [(set_attr "op_type" "RR")
10351 (set_attr "type" "jsr")
10352 (set_attr "atype" "agen")])
10353
10354 (define_insn "*return"
10355 [(return)
10356 (use (match_operand 0 "register_operand" "a"))]
10357 "GET_MODE (operands[0]) == Pmode"
10358 "br\t%0"
10359 [(set_attr "op_type" "RR")
10360 (set_attr "type" "jsr")
10361 (set_attr "atype" "agen")])
10362
10363
10364 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
10365 ;; pointer. This is used for compatibility.
10366
10367 (define_expand "ptr_extend"
10368 [(set (match_operand:DI 0 "register_operand" "=r")
10369 (match_operand:SI 1 "register_operand" "r"))]
10370 "TARGET_64BIT"
10371 {
10372 emit_insn (gen_anddi3 (operands[0],
10373 gen_lowpart (DImode, operands[1]),
10374 GEN_INT (0x7fffffff)));
10375 DONE;
10376 })
10377
10378 ;; Instruction definition to expand eh_return macro to support
10379 ;; swapping in special linkage return addresses.
10380
10381 (define_expand "eh_return"
10382 [(use (match_operand 0 "register_operand" ""))]
10383 "TARGET_TPF"
10384 {
10385 s390_emit_tpf_eh_return (operands[0]);
10386 DONE;
10387 })
10388
10389 ;
10390 ; Stack Protector Patterns
10391 ;
10392
10393 (define_expand "stack_protect_set"
10394 [(set (match_operand 0 "memory_operand" "")
10395 (match_operand 1 "memory_operand" ""))]
10396 ""
10397 {
10398 #ifdef TARGET_THREAD_SSP_OFFSET
10399 operands[1]
10400 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10401 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10402 #endif
10403 if (TARGET_64BIT)
10404 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
10405 else
10406 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
10407
10408 DONE;
10409 })
10410
10411 (define_insn "stack_protect_set<mode>"
10412 [(set (match_operand:DSI 0 "memory_operand" "=Q")
10413 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
10414 ""
10415 "mvc\t%O0(%G0,%R0),%S1"
10416 [(set_attr "op_type" "SS")])
10417
10418 (define_expand "stack_protect_test"
10419 [(set (reg:CC CC_REGNUM)
10420 (compare (match_operand 0 "memory_operand" "")
10421 (match_operand 1 "memory_operand" "")))
10422 (match_operand 2 "" "")]
10423 ""
10424 {
10425 rtx cc_reg, test;
10426 #ifdef TARGET_THREAD_SSP_OFFSET
10427 operands[1]
10428 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10429 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10430 #endif
10431 if (TARGET_64BIT)
10432 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
10433 else
10434 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
10435
10436 cc_reg = gen_rtx_REG (CCZmode, CC_REGNUM);
10437 test = gen_rtx_EQ (VOIDmode, cc_reg, const0_rtx);
10438 emit_jump_insn (gen_cbranchcc4 (test, cc_reg, const0_rtx, operands[2]));
10439 DONE;
10440 })
10441
10442 (define_insn "stack_protect_test<mode>"
10443 [(set (reg:CCZ CC_REGNUM)
10444 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
10445 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
10446 ""
10447 "clc\t%O0(%G0,%R0),%S1"
10448 [(set_attr "op_type" "SS")])
10449
10450 ; This is used in s390_emit_prologue in order to prevent insns
10451 ; adjusting the stack pointer to be moved over insns writing stack
10452 ; slots using a copy of the stack pointer in a different register.
10453 (define_insn "stack_tie"
10454 [(set (match_operand:BLK 0 "memory_operand" "+m")
10455 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
10456 ""
10457 ""
10458 [(set_attr "length" "0")])
10459
10460
10461 (define_insn "stack_restore_from_fpr"
10462 [(set (reg:DI STACK_REGNUM)
10463 (match_operand:DI 0 "register_operand" "f"))
10464 (clobber (mem:BLK (scratch)))]
10465 "TARGET_Z10"
10466 "lgdr\t%%r15,%0"
10467 [(set_attr "op_type" "RRE")])
10468
10469 ;
10470 ; Data prefetch patterns
10471 ;
10472
10473 (define_insn "prefetch"
10474 [(prefetch (match_operand 0 "address_operand" "ZT,X")
10475 (match_operand:SI 1 "const_int_operand" " n,n")
10476 (match_operand:SI 2 "const_int_operand" " n,n"))]
10477 "TARGET_Z10"
10478 {
10479 switch (which_alternative)
10480 {
10481 case 0:
10482 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
10483 case 1:
10484 if (larl_operand (operands[0], Pmode))
10485 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
10486 default:
10487
10488 /* This might be reached for symbolic operands with an odd
10489 addend. We simply omit the prefetch for such rare cases. */
10490
10491 return "";
10492 }
10493 }
10494 [(set_attr "type" "load,larl")
10495 (set_attr "op_type" "RXY,RIL")
10496 (set_attr "z10prop" "z10_super")
10497 (set_attr "z196prop" "z196_alone")])
10498
10499
10500 ;
10501 ; Byte swap instructions
10502 ;
10503
10504 ; FIXME: There is also mvcin but we cannot use it since src and target
10505 ; may overlap.
10506 (define_insn "bswap<mode>2"
10507 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,T")
10508 (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,T,d")))]
10509 "TARGET_CPU_ZARCH"
10510 "@
10511 lrv<g>r\t%0,%1
10512 lrv<g>\t%0,%1
10513 strv<g>\t%1,%0"
10514 [(set_attr "type" "*,load,store")
10515 (set_attr "op_type" "RRE,RXY,RXY")
10516 (set_attr "z10prop" "z10_super")])
10517
10518 (define_insn "bswaphi2"
10519 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,T")
10520 (bswap:HI (match_operand:HI 1 "nonimmediate_operand" " d,T,d")))]
10521 "TARGET_CPU_ZARCH"
10522 "@
10523 #
10524 lrvh\t%0,%1
10525 strvh\t%1,%0"
10526 [(set_attr "type" "*,load,store")
10527 (set_attr "op_type" "RRE,RXY,RXY")
10528 (set_attr "z10prop" "z10_super")])
10529
10530 (define_split
10531 [(set (match_operand:HI 0 "register_operand" "")
10532 (bswap:HI (match_operand:HI 1 "register_operand" "")))]
10533 "TARGET_CPU_ZARCH"
10534 [(set (match_dup 2) (bswap:SI (match_dup 3)))
10535 (set (match_dup 2) (lshiftrt:SI (match_dup 2) (const_int 16)))]
10536 {
10537 operands[2] = simplify_gen_subreg (SImode, operands[0], HImode, 0);
10538 operands[3] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
10539 })
10540
10541
10542 ;
10543 ; Population count instruction
10544 ;
10545
10546 ; The S/390 popcount instruction counts the bits of op1 in 8 byte
10547 ; portions and stores the result in the corresponding bytes in op0.
10548 (define_insn "*popcount<mode>"
10549 [(set (match_operand:INT 0 "register_operand" "=d")
10550 (unspec:INT [(match_operand:INT 1 "register_operand" "d")] UNSPEC_POPCNT))
10551 (clobber (reg:CC CC_REGNUM))]
10552 "TARGET_Z196"
10553 "popcnt\t%0,%1"
10554 [(set_attr "op_type" "RRE")])
10555
10556 (define_expand "popcountdi2"
10557 [; popcnt op0, op1
10558 (parallel [(set (match_operand:DI 0 "register_operand" "")
10559 (unspec:DI [(match_operand:DI 1 "register_operand")]
10560 UNSPEC_POPCNT))
10561 (clobber (reg:CC CC_REGNUM))])
10562 ; sllg op2, op0, 32
10563 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 32)))
10564 ; agr op0, op2
10565 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10566 (clobber (reg:CC CC_REGNUM))])
10567 ; sllg op2, op0, 16
10568 (set (match_dup 2)
10569 (ashift:DI (match_dup 0) (const_int 16)))
10570 ; agr op0, op2
10571 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10572 (clobber (reg:CC CC_REGNUM))])
10573 ; sllg op2, op0, 8
10574 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 8)))
10575 ; agr op0, op2
10576 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10577 (clobber (reg:CC CC_REGNUM))])
10578 ; srlg op0, op0, 56
10579 (set (match_dup 0) (lshiftrt:DI (match_dup 0) (const_int 56)))]
10580 "TARGET_Z196 && TARGET_64BIT"
10581 "operands[2] = gen_reg_rtx (DImode);")
10582
10583 (define_expand "popcountsi2"
10584 [; popcnt op0, op1
10585 (parallel [(set (match_operand:SI 0 "register_operand" "")
10586 (unspec:SI [(match_operand:SI 1 "register_operand")]
10587 UNSPEC_POPCNT))
10588 (clobber (reg:CC CC_REGNUM))])
10589 ; sllk op2, op0, 16
10590 (set (match_dup 2)
10591 (ashift:SI (match_dup 0) (const_int 16)))
10592 ; ar op0, op2
10593 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10594 (clobber (reg:CC CC_REGNUM))])
10595 ; sllk op2, op0, 8
10596 (set (match_dup 2) (ashift:SI (match_dup 0) (const_int 8)))
10597 ; ar op0, op2
10598 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10599 (clobber (reg:CC CC_REGNUM))])
10600 ; srl op0, op0, 24
10601 (set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 24)))]
10602 "TARGET_Z196"
10603 "operands[2] = gen_reg_rtx (SImode);")
10604
10605 (define_expand "popcounthi2"
10606 [; popcnt op0, op1
10607 (parallel [(set (match_operand:HI 0 "register_operand" "")
10608 (unspec:HI [(match_operand:HI 1 "register_operand")]
10609 UNSPEC_POPCNT))
10610 (clobber (reg:CC CC_REGNUM))])
10611 ; sllk op2, op0, 8
10612 (set (match_dup 2)
10613 (ashift:SI (match_dup 0) (const_int 8)))
10614 ; ar op0, op2
10615 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10616 (clobber (reg:CC CC_REGNUM))])
10617 ; srl op0, op0, 8
10618 (set (match_dup 0) (lshiftrt:HI (match_dup 0) (const_int 8)))]
10619 "TARGET_Z196"
10620 "operands[2] = gen_reg_rtx (SImode);")
10621
10622 (define_expand "popcountqi2"
10623 [; popcnt op0, op1
10624 (parallel [(set (match_operand:QI 0 "register_operand" "")
10625 (unspec:QI [(match_operand:QI 1 "register_operand")]
10626 UNSPEC_POPCNT))
10627 (clobber (reg:CC CC_REGNUM))])]
10628 "TARGET_Z196"
10629 "")
10630
10631 ;;
10632 ;;- Copy sign instructions
10633 ;;
10634
10635 (define_insn "copysign<mode>3"
10636 [(set (match_operand:FP 0 "register_operand" "=f")
10637 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
10638 (match_operand:FP 2 "register_operand" "f")]
10639 UNSPEC_COPYSIGN))]
10640 "TARGET_Z196"
10641 "cpsdr\t%0,%2,%1"
10642 [(set_attr "op_type" "RRF")
10643 (set_attr "type" "fsimp<mode>")])
10644
10645
10646 ;;
10647 ;;- Transactional execution instructions
10648 ;;
10649
10650 ; This splitter helps combine to make use of CC directly when
10651 ; comparing the integer result of a tbegin builtin with a constant.
10652 ; The unspec is already removed by canonicalize_comparison. So this
10653 ; splitters only job is to turn the PARALLEL into separate insns
10654 ; again. Unfortunately this only works with the very first cc/int
10655 ; compare since combine is not able to deal with data flow across
10656 ; basic block boundaries.
10657
10658 ; It needs to be an insn pattern as well since combine does not apply
10659 ; the splitter directly. Combine would only use it if it actually
10660 ; would reduce the number of instructions.
10661 (define_insn_and_split "*ccraw_to_int"
10662 [(set (pc)
10663 (if_then_else
10664 (match_operator 0 "s390_eqne_operator"
10665 [(reg:CCRAW CC_REGNUM)
10666 (match_operand 1 "const_int_operand" "")])
10667 (label_ref (match_operand 2 "" ""))
10668 (pc)))
10669 (set (match_operand:SI 3 "register_operand" "=d")
10670 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10671 ""
10672 "#"
10673 ""
10674 [(set (match_dup 3)
10675 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))
10676 (set (pc)
10677 (if_then_else (match_op_dup 0 [(reg:CCRAW CC_REGNUM) (match_dup 1)])
10678 (label_ref (match_dup 2))
10679 (pc)))]
10680 "")
10681
10682 ; Non-constrained transaction begin
10683
10684 (define_expand "tbegin"
10685 [(match_operand:SI 0 "register_operand" "")
10686 (match_operand:BLK 1 "memory_operand" "")]
10687 "TARGET_HTM"
10688 {
10689 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, true);
10690 DONE;
10691 })
10692
10693 (define_expand "tbegin_nofloat"
10694 [(match_operand:SI 0 "register_operand" "")
10695 (match_operand:BLK 1 "memory_operand" "")]
10696 "TARGET_HTM"
10697 {
10698 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, false);
10699 DONE;
10700 })
10701
10702 (define_expand "tbegin_retry"
10703 [(match_operand:SI 0 "register_operand" "")
10704 (match_operand:BLK 1 "memory_operand" "")
10705 (match_operand:SI 2 "general_operand" "")]
10706 "TARGET_HTM"
10707 {
10708 s390_expand_tbegin (operands[0], operands[1], operands[2], true);
10709 DONE;
10710 })
10711
10712 (define_expand "tbegin_retry_nofloat"
10713 [(match_operand:SI 0 "register_operand" "")
10714 (match_operand:BLK 1 "memory_operand" "")
10715 (match_operand:SI 2 "general_operand" "")]
10716 "TARGET_HTM"
10717 {
10718 s390_expand_tbegin (operands[0], operands[1], operands[2], false);
10719 DONE;
10720 })
10721
10722 ; Clobber VRs since they don't get restored
10723 (define_insn "tbegin_1_z13"
10724 [(set (reg:CCRAW CC_REGNUM)
10725 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10726 UNSPECV_TBEGIN))
10727 (set (match_operand:BLK 1 "memory_operand" "=Q")
10728 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10729 (clobber (reg:TI 16)) (clobber (reg:TI 38))
10730 (clobber (reg:TI 17)) (clobber (reg:TI 39))
10731 (clobber (reg:TI 18)) (clobber (reg:TI 40))
10732 (clobber (reg:TI 19)) (clobber (reg:TI 41))
10733 (clobber (reg:TI 20)) (clobber (reg:TI 42))
10734 (clobber (reg:TI 21)) (clobber (reg:TI 43))
10735 (clobber (reg:TI 22)) (clobber (reg:TI 44))
10736 (clobber (reg:TI 23)) (clobber (reg:TI 45))
10737 (clobber (reg:TI 24)) (clobber (reg:TI 46))
10738 (clobber (reg:TI 25)) (clobber (reg:TI 47))
10739 (clobber (reg:TI 26)) (clobber (reg:TI 48))
10740 (clobber (reg:TI 27)) (clobber (reg:TI 49))
10741 (clobber (reg:TI 28)) (clobber (reg:TI 50))
10742 (clobber (reg:TI 29)) (clobber (reg:TI 51))
10743 (clobber (reg:TI 30)) (clobber (reg:TI 52))
10744 (clobber (reg:TI 31)) (clobber (reg:TI 53))]
10745 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10746 ; not supposed to be used for immediates (see genpreds.c).
10747 "TARGET_VX && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10748 "tbegin\t%1,%x0"
10749 [(set_attr "op_type" "SIL")])
10750
10751 (define_insn "tbegin_1"
10752 [(set (reg:CCRAW CC_REGNUM)
10753 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10754 UNSPECV_TBEGIN))
10755 (set (match_operand:BLK 1 "memory_operand" "=Q")
10756 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10757 (clobber (reg:DF 16))
10758 (clobber (reg:DF 17))
10759 (clobber (reg:DF 18))
10760 (clobber (reg:DF 19))
10761 (clobber (reg:DF 20))
10762 (clobber (reg:DF 21))
10763 (clobber (reg:DF 22))
10764 (clobber (reg:DF 23))
10765 (clobber (reg:DF 24))
10766 (clobber (reg:DF 25))
10767 (clobber (reg:DF 26))
10768 (clobber (reg:DF 27))
10769 (clobber (reg:DF 28))
10770 (clobber (reg:DF 29))
10771 (clobber (reg:DF 30))
10772 (clobber (reg:DF 31))]
10773 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10774 ; not supposed to be used for immediates (see genpreds.c).
10775 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10776 "tbegin\t%1,%x0"
10777 [(set_attr "op_type" "SIL")])
10778
10779 ; Same as above but without the FPR clobbers
10780 (define_insn "tbegin_nofloat_1"
10781 [(set (reg:CCRAW CC_REGNUM)
10782 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10783 UNSPECV_TBEGIN))
10784 (set (match_operand:BLK 1 "memory_operand" "=Q")
10785 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))]
10786 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10787 "tbegin\t%1,%x0"
10788 [(set_attr "op_type" "SIL")])
10789
10790
10791 ; Constrained transaction begin
10792
10793 (define_expand "tbeginc"
10794 [(set (reg:CCRAW CC_REGNUM)
10795 (unspec_volatile:CCRAW [(const_int TBEGINC_MASK)]
10796 UNSPECV_TBEGINC))]
10797 "TARGET_HTM"
10798 "")
10799
10800 (define_insn "*tbeginc_1"
10801 [(set (reg:CCRAW CC_REGNUM)
10802 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" " D")]
10803 UNSPECV_TBEGINC))]
10804 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10805 "tbeginc\t0,%x0"
10806 [(set_attr "op_type" "SIL")])
10807
10808 ; Transaction end
10809
10810 (define_expand "tend"
10811 [(set (reg:CCRAW CC_REGNUM)
10812 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))
10813 (set (match_operand:SI 0 "register_operand" "")
10814 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10815 "TARGET_HTM"
10816 "")
10817
10818 (define_insn "*tend_1"
10819 [(set (reg:CCRAW CC_REGNUM)
10820 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))]
10821 "TARGET_HTM"
10822 "tend"
10823 [(set_attr "op_type" "S")])
10824
10825 ; Transaction abort
10826
10827 (define_expand "tabort"
10828 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "")]
10829 UNSPECV_TABORT)]
10830 "TARGET_HTM && operands != NULL"
10831 {
10832 if (CONST_INT_P (operands[0])
10833 && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 255)
10834 {
10835 error ("Invalid transaction abort code: " HOST_WIDE_INT_PRINT_DEC
10836 ". Values in range 0 through 255 are reserved.",
10837 INTVAL (operands[0]));
10838 FAIL;
10839 }
10840 })
10841
10842 (define_insn "*tabort_1"
10843 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "aJ")]
10844 UNSPECV_TABORT)]
10845 "TARGET_HTM && operands != NULL"
10846 "tabort\t%Y0"
10847 [(set_attr "op_type" "S")])
10848
10849 (define_insn "*tabort_1_plus"
10850 [(unspec_volatile [(plus:SI (match_operand:SI 0 "register_operand" "a")
10851 (match_operand:SI 1 "const_int_operand" "J"))]
10852 UNSPECV_TABORT)]
10853 "TARGET_HTM && operands != NULL
10854 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[1]), 'J', \"J\")"
10855 "tabort\t%1(%0)"
10856 [(set_attr "op_type" "S")])
10857
10858 ; Transaction extract nesting depth
10859
10860 (define_insn "etnd"
10861 [(set (match_operand:SI 0 "register_operand" "=d")
10862 (unspec_volatile:SI [(const_int 0)] UNSPECV_ETND))]
10863 "TARGET_HTM"
10864 "etnd\t%0"
10865 [(set_attr "op_type" "RRE")])
10866
10867 ; Non-transactional store
10868
10869 (define_insn "ntstg"
10870 [(set (match_operand:DI 0 "memory_operand" "=T")
10871 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "d")]
10872 UNSPECV_NTSTG))]
10873 "TARGET_HTM"
10874 "ntstg\t%1,%0"
10875 [(set_attr "op_type" "RXY")])
10876
10877 ; Transaction perform processor assist
10878
10879 (define_expand "tx_assist"
10880 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")
10881 (reg:SI GPR0_REGNUM)
10882 (const_int 1)]
10883 UNSPECV_PPA)]
10884 "TARGET_HTM"
10885 "")
10886
10887 (define_insn "*ppa"
10888 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")
10889 (match_operand:SI 1 "register_operand" "d")
10890 (match_operand 2 "const_int_operand" "I")]
10891 UNSPECV_PPA)]
10892 "TARGET_HTM && INTVAL (operands[2]) < 16"
10893 "ppa\t%0,%1,%2"
10894 [(set_attr "op_type" "RRF")])
10895
10896
10897 ; Set and get floating point control register
10898
10899 (define_insn "sfpc"
10900 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")]
10901 UNSPECV_SFPC)]
10902 "TARGET_HARD_FLOAT"
10903 "sfpc\t%0")
10904
10905 (define_insn "efpc"
10906 [(set (match_operand:SI 0 "register_operand" "=d")
10907 (unspec_volatile:SI [(const_int 0)] UNSPECV_EFPC))]
10908 "TARGET_HARD_FLOAT"
10909 "efpc\t%0")
10910
10911
10912 ; Load count to block boundary
10913
10914 (define_insn "lcbb"
10915 [(set (match_operand:SI 0 "register_operand" "=d")
10916 (unspec:SI [(match_operand 1 "address_operand" "ZR")
10917 (match_operand:SI 2 "immediate_operand" "C")] UNSPEC_LCBB))
10918 (clobber (reg:CC CC_REGNUM))]
10919 "TARGET_Z13"
10920 "lcbb\t%0,%a1,%b2"
10921 [(set_attr "op_type" "VRX")])
10922
10923 ; Handle -fsplit-stack.
10924
10925 (define_expand "split_stack_prologue"
10926 [(const_int 0)]
10927 ""
10928 {
10929 s390_expand_split_stack_prologue ();
10930 DONE;
10931 })
10932
10933 ;; If there are operand 0 bytes available on the stack, jump to
10934 ;; operand 1.
10935
10936 (define_expand "split_stack_space_check"
10937 [(set (pc) (if_then_else
10938 (ltu (minus (reg 15)
10939 (match_operand 0 "register_operand"))
10940 (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
10941 (label_ref (match_operand 1))
10942 (pc)))]
10943 ""
10944 {
10945 /* Offset from thread pointer to __private_ss. */
10946 int psso = TARGET_64BIT ? 0x38 : 0x20;
10947 rtx tp = s390_get_thread_pointer ();
10948 rtx guard = gen_rtx_MEM (Pmode, plus_constant (Pmode, tp, psso));
10949 rtx reg = gen_reg_rtx (Pmode);
10950 rtx cc;
10951 if (TARGET_64BIT)
10952 emit_insn (gen_subdi3 (reg, stack_pointer_rtx, operands[0]));
10953 else
10954 emit_insn (gen_subsi3 (reg, stack_pointer_rtx, operands[0]));
10955 cc = s390_emit_compare (GT, reg, guard);
10956 s390_emit_jump (operands[1], cc);
10957
10958 DONE;
10959 })
10960
10961 ;; __morestack parameter block for split stack prologue. Parameters are:
10962 ;; parameter block label, label to be called by __morestack, frame size,
10963 ;; stack parameter size.
10964
10965 (define_insn "split_stack_data"
10966 [(unspec_volatile [(match_operand 0 "" "X")
10967 (match_operand 1 "" "X")
10968 (match_operand 2 "const_int_operand" "X")
10969 (match_operand 3 "const_int_operand" "X")]
10970 UNSPECV_SPLIT_STACK_DATA)]
10971 "TARGET_CPU_ZARCH"
10972 {
10973 switch_to_section (targetm.asm_out.function_rodata_section
10974 (current_function_decl));
10975
10976 if (TARGET_64BIT)
10977 output_asm_insn (".align\t8", operands);
10978 else
10979 output_asm_insn (".align\t4", operands);
10980 (*targetm.asm_out.internal_label) (asm_out_file, "L",
10981 CODE_LABEL_NUMBER (operands[0]));
10982 if (TARGET_64BIT)
10983 {
10984 output_asm_insn (".quad\t%2", operands);
10985 output_asm_insn (".quad\t%3", operands);
10986 output_asm_insn (".quad\t%1-%0", operands);
10987 }
10988 else
10989 {
10990 output_asm_insn (".long\t%2", operands);
10991 output_asm_insn (".long\t%3", operands);
10992 output_asm_insn (".long\t%1-%0", operands);
10993 }
10994
10995 switch_to_section (current_function_section ());
10996 return "";
10997 }
10998 [(set_attr "length" "0")])
10999
11000
11001 ;; A jg with minimal fuss for use in split stack prologue.
11002
11003 (define_expand "split_stack_call"
11004 [(match_operand 0 "bras_sym_operand" "X")
11005 (match_operand 1 "" "")]
11006 "TARGET_CPU_ZARCH"
11007 {
11008 if (TARGET_64BIT)
11009 emit_jump_insn (gen_split_stack_call_di (operands[0], operands[1]));
11010 else
11011 emit_jump_insn (gen_split_stack_call_si (operands[0], operands[1]));
11012 DONE;
11013 })
11014
11015 (define_insn "split_stack_call_<mode>"
11016 [(set (pc) (label_ref (match_operand 1 "" "")))
11017 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11018 (reg:P 1)]
11019 UNSPECV_SPLIT_STACK_CALL))]
11020 "TARGET_CPU_ZARCH"
11021 "jg\t%0"
11022 [(set_attr "op_type" "RIL")
11023 (set_attr "type" "branch")])
11024
11025 ;; Also a conditional one.
11026
11027 (define_expand "split_stack_cond_call"
11028 [(match_operand 0 "bras_sym_operand" "X")
11029 (match_operand 1 "" "")
11030 (match_operand 2 "" "")]
11031 "TARGET_CPU_ZARCH"
11032 {
11033 if (TARGET_64BIT)
11034 emit_jump_insn (gen_split_stack_cond_call_di (operands[0], operands[1], operands[2]));
11035 else
11036 emit_jump_insn (gen_split_stack_cond_call_si (operands[0], operands[1], operands[2]));
11037 DONE;
11038 })
11039
11040 (define_insn "split_stack_cond_call_<mode>"
11041 [(set (pc)
11042 (if_then_else
11043 (match_operand 1 "" "")
11044 (label_ref (match_operand 2 "" ""))
11045 (pc)))
11046 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11047 (reg:P 1)]
11048 UNSPECV_SPLIT_STACK_CALL))]
11049 "TARGET_CPU_ZARCH"
11050 "jg%C1\t%0"
11051 [(set_attr "op_type" "RIL")
11052 (set_attr "type" "branch")])