S/390: Add -fsplit-stack support
[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 ; Condition code register.
303 (CC_REGNUM 33)
304 ; Thread local storage pointer register.
305 (TP_REGNUM 36)
306 ])
307
308 ; Hardware register names
309
310 (define_constants
311 [
312 ; General purpose registers
313 (GPR0_REGNUM 0)
314 (GPR1_REGNUM 1)
315 (GPR2_REGNUM 2)
316 (GPR6_REGNUM 6)
317 ; Floating point registers.
318 (FPR0_REGNUM 16)
319 (FPR1_REGNUM 20)
320 (FPR2_REGNUM 17)
321 (FPR3_REGNUM 21)
322 (FPR4_REGNUM 18)
323 (FPR5_REGNUM 22)
324 (FPR6_REGNUM 19)
325 (FPR7_REGNUM 23)
326 (FPR8_REGNUM 24)
327 (FPR9_REGNUM 28)
328 (FPR10_REGNUM 25)
329 (FPR11_REGNUM 29)
330 (FPR12_REGNUM 26)
331 (FPR13_REGNUM 30)
332 (FPR14_REGNUM 27)
333 (FPR15_REGNUM 31)
334 (VR0_REGNUM 16)
335 (VR16_REGNUM 38)
336 (VR23_REGNUM 45)
337 (VR24_REGNUM 46)
338 (VR31_REGNUM 53)
339 ])
340
341 ;;
342 ;; PFPO GPR0 argument format
343 ;;
344
345 (define_constants
346 [
347 ; PFPO operation type
348 (PFPO_CONVERT 0x1000000)
349 ; PFPO operand types
350 (PFPO_OP_TYPE_SF 0x5)
351 (PFPO_OP_TYPE_DF 0x6)
352 (PFPO_OP_TYPE_TF 0x7)
353 (PFPO_OP_TYPE_SD 0x8)
354 (PFPO_OP_TYPE_DD 0x9)
355 (PFPO_OP_TYPE_TD 0xa)
356 ; Bitposition of operand types
357 (PFPO_OP0_TYPE_SHIFT 16)
358 (PFPO_OP1_TYPE_SHIFT 8)
359 ])
360
361 ; Immediate operands for tbegin and tbeginc
362 (define_constants [(TBEGIN_MASK 65292)]) ; 0xff0c
363 (define_constants [(TBEGINC_MASK 65288)]) ; 0xff08
364
365 ;; Instruction operand type as used in the Principles of Operation.
366 ;; Used to determine defaults for length and other attribute values.
367
368 (define_attr "op_type"
369 "NN,E,RR,RRE,RX,RS,RSI,RI,SI,S,SS,SSE,RXE,RSE,RIL,RIE,RXY,RSY,SIY,RRF,RRR,SIL,RRS,RIS,VRI,VRR,VRS,VRV,VRX"
370 (const_string "NN"))
371
372 ;; Instruction type attribute used for scheduling.
373
374 (define_attr "type" "none,integer,load,lr,la,larl,lm,stm,
375 cs,vs,store,sem,idiv,
376 imulhi,imulsi,imuldi,
377 branch,jsr,fsimptf,fsimpdf,fsimpsf,fhex,
378 floadtf,floaddf,floadsf,fstoredf,fstoresf,
379 fmultf,fmuldf,fmulsf,fdivtf,fdivdf,fdivsf,
380 ftoi,fsqrttf,fsqrtdf,fsqrtsf,
381 fmadddf,fmaddsf,
382 ftrunctf,ftruncdf, ftruncsd, ftruncdd,
383 itoftf, itofdf, itofsf, itofdd, itoftd,
384 fdivdd, fdivtd, floaddd, floadsd, fmuldd, fmultd,
385 fsimpdd, fsimpsd, fsimptd, fstoredd, fstoresd,
386 ftoidfp, other"
387 (cond [(eq_attr "op_type" "NN") (const_string "other")
388 (eq_attr "op_type" "SS") (const_string "cs")]
389 (const_string "integer")))
390
391 ;; Another attribute used for scheduling purposes:
392 ;; agen: Instruction uses the address generation unit
393 ;; reg: Instruction does not use the agen unit
394
395 (define_attr "atype" "agen,reg"
396 (if_then_else (eq_attr "op_type" "E,RR,RI,RRE,RSI,RIL,RIE,RRF,RRR")
397 (const_string "reg")
398 (const_string "agen")))
399
400 ;; Properties concerning Z10 execution grouping and value forwarding.
401 ;; z10_super: instruction is superscalar.
402 ;; z10_super_c: instruction is superscalar and meets the condition of z10_c.
403 ;; z10_fwd: The instruction reads the value of an operand and stores it into a
404 ;; target register. It can forward this value to a second instruction that reads
405 ;; the same register if that second instruction is issued in the same group.
406 ;; z10_rec: The instruction is in the T pipeline and reads a register. If the
407 ;; instruction in the S pipe writes to the register, then the T instruction
408 ;; can immediately read the new value.
409 ;; z10_fr: union of Z10_fwd and z10_rec.
410 ;; z10_c: second operand of instruction is a register and read with complemented bits.
411 ;;
412 ;; An additional suffix A1, A3, or E1 indicates the respective AGI bypass.
413
414
415 (define_attr "z10prop" "none,
416 z10_super, z10_super_E1, z10_super_A1, z10_super_c, z10_super_c_E1,
417 z10_fwd, z10_fwd_A1, z10_fwd_A3, z10_fwd_E1,
418 z10_rec,
419 z10_fr, z10_fr_A3, z10_fr_E1,
420 z10_c"
421 (const_string "none"))
422
423 ;; Properties concerning Z196 decoding
424 ;; z196_alone: must group alone
425 ;; z196_end: ends a group
426 ;; z196_cracked: instruction is cracked or expanded
427 (define_attr "z196prop" "none,
428 z196_alone, z196_ends,
429 z196_cracked"
430 (const_string "none"))
431
432 (define_attr "mnemonic" "bcr_flush,unknown" (const_string "unknown"))
433
434 ;; Length in bytes.
435
436 (define_attr "length" ""
437 (cond [(eq_attr "op_type" "E,RR") (const_int 2)
438 (eq_attr "op_type" "RX,RI,RRE,RS,RSI,S,SI,RRF,RRR") (const_int 4)]
439 (const_int 6)))
440
441
442 ;; Processor type. This attribute must exactly match the processor_type
443 ;; enumeration in s390.h. The current machine description does not
444 ;; distinguish between g5 and g6, but there are differences between the two
445 ;; CPUs could in theory be modeled.
446
447 (define_attr "cpu" "g5,g6,z900,z990,z9_109,z9_ec,z10,z196,zEC12,z13"
448 (const (symbol_ref "s390_tune_attr")))
449
450 (define_attr "cpu_facility"
451 "standard,ieee,zarch,cpu_zarch,longdisp,extimm,dfp,z10,z196,zEC12,vec"
452 (const_string "standard"))
453
454 (define_attr "enabled" ""
455 (cond [(eq_attr "cpu_facility" "standard")
456 (const_int 1)
457
458 (and (eq_attr "cpu_facility" "ieee")
459 (match_test "TARGET_CPU_IEEE_FLOAT"))
460 (const_int 1)
461
462 (and (eq_attr "cpu_facility" "zarch")
463 (match_test "TARGET_ZARCH"))
464 (const_int 1)
465
466 (and (eq_attr "cpu_facility" "longdisp")
467 (match_test "TARGET_LONG_DISPLACEMENT"))
468 (const_int 1)
469
470 (and (eq_attr "cpu_facility" "extimm")
471 (match_test "TARGET_EXTIMM"))
472 (const_int 1)
473
474 (and (eq_attr "cpu_facility" "dfp")
475 (match_test "TARGET_DFP"))
476 (const_int 1)
477
478 (and (eq_attr "cpu_facility" "cpu_zarch")
479 (match_test "TARGET_CPU_ZARCH"))
480 (const_int 1)
481
482 (and (eq_attr "cpu_facility" "z10")
483 (match_test "TARGET_Z10"))
484 (const_int 1)
485
486 (and (eq_attr "cpu_facility" "z196")
487 (match_test "TARGET_Z196"))
488 (const_int 1)
489
490 (and (eq_attr "cpu_facility" "zEC12")
491 (match_test "TARGET_ZEC12"))
492 (const_int 1)
493
494 (and (eq_attr "cpu_facility" "vec")
495 (match_test "TARGET_VX"))
496 (const_int 1)]
497 (const_int 0)))
498
499 ;; Pipeline description for z900. For lack of anything better,
500 ;; this description is also used for the g5 and g6.
501 (include "2064.md")
502
503 ;; Pipeline description for z990, z9-109 and z9-ec.
504 (include "2084.md")
505
506 ;; Pipeline description for z10
507 (include "2097.md")
508
509 ;; Pipeline description for z196
510 (include "2817.md")
511
512 ;; Pipeline description for zEC12
513 (include "2827.md")
514
515 ;; Predicates
516 (include "predicates.md")
517
518 ;; Constraint definitions
519 (include "constraints.md")
520
521 ;; Other includes
522 (include "tpf.md")
523
524 ;; Iterators
525
526 (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])
527
528 ;; These mode iterators allow floating point patterns to be generated from the
529 ;; same template.
530 (define_mode_iterator FP_ALL [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")
531 (SD "TARGET_HARD_DFP")])
532 (define_mode_iterator FP [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")])
533 (define_mode_iterator BFP [TF DF SF])
534 (define_mode_iterator DFP [TD DD])
535 (define_mode_iterator DFP_ALL [TD DD SD])
536 (define_mode_iterator DSF [DF SF])
537 (define_mode_iterator SD_SF [SF SD])
538 (define_mode_iterator DD_DF [DF DD])
539 (define_mode_iterator TD_TF [TF TD])
540
541 ;; These mode iterators allow 31-bit and 64-bit GPR patterns to be generated
542 ;; from the same template.
543 (define_mode_iterator GPR [(DI "TARGET_ZARCH") SI])
544 (define_mode_iterator DGPR [(TI "TARGET_ZARCH") DI SI])
545 (define_mode_iterator DSI [DI SI])
546 (define_mode_iterator TDI [TI DI])
547
548 ;; These mode iterators allow :P to be used for patterns that operate on
549 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
550 (define_mode_iterator P [(DI "TARGET_64BIT") (SI "!TARGET_64BIT")])
551
552 ;; These macros refer to the actual word_mode of the configuration.
553 ;; This is equal to Pmode except on 31-bit machines in zarch mode.
554 (define_mode_iterator DW [(TI "TARGET_ZARCH") (DI "!TARGET_ZARCH")])
555 (define_mode_iterator W [(DI "TARGET_ZARCH") (SI "!TARGET_ZARCH")])
556
557 ;; Used by the umul pattern to express modes having half the size.
558 (define_mode_attr DWH [(TI "DI") (DI "SI")])
559 (define_mode_attr dwh [(TI "di") (DI "si")])
560
561 ;; This mode iterator allows the QI and HI patterns to be defined from
562 ;; the same template.
563 (define_mode_iterator HQI [HI QI])
564
565 ;; This mode iterator allows the integer patterns to be defined from the
566 ;; same template.
567 (define_mode_iterator INT [(DI "TARGET_ZARCH") SI HI QI])
568 (define_mode_iterator DINT [(TI "TARGET_ZARCH") DI SI HI QI])
569
570 ;; This iterator allows some 'ashift' and 'lshiftrt' pattern to be defined from
571 ;; the same template.
572 (define_code_iterator SHIFT [ashift lshiftrt])
573
574 ;; This iterator allows r[ox]sbg to be defined with the same template
575 (define_code_iterator IXOR [ior xor])
576
577 ;; This iterator is used to expand the patterns for the nearest
578 ;; integer functions.
579 (define_int_iterator FPINT [UNSPEC_FPINT_FLOOR UNSPEC_FPINT_BTRUNC
580 UNSPEC_FPINT_ROUND UNSPEC_FPINT_CEIL
581 UNSPEC_FPINT_NEARBYINT])
582 (define_int_attr fpint_name [(UNSPEC_FPINT_FLOOR "floor")
583 (UNSPEC_FPINT_BTRUNC "btrunc")
584 (UNSPEC_FPINT_ROUND "round")
585 (UNSPEC_FPINT_CEIL "ceil")
586 (UNSPEC_FPINT_NEARBYINT "nearbyint")])
587 (define_int_attr fpint_roundingmode [(UNSPEC_FPINT_FLOOR "7")
588 (UNSPEC_FPINT_BTRUNC "5")
589 (UNSPEC_FPINT_ROUND "1")
590 (UNSPEC_FPINT_CEIL "6")
591 (UNSPEC_FPINT_NEARBYINT "0")])
592
593 ;; This iterator and attribute allow to combine most atomic operations.
594 (define_code_iterator ATOMIC [and ior xor plus minus mult])
595 (define_code_iterator ATOMIC_Z196 [and ior xor plus])
596 (define_code_attr atomic [(and "and") (ior "or") (xor "xor")
597 (plus "add") (minus "sub") (mult "nand")])
598 (define_code_attr noxa [(and "n") (ior "o") (xor "x") (plus "a")])
599
600 ;; In FP templates, a string like "lt<de>br" will expand to "ltxbr" in
601 ;; TF/TDmode, "ltdbr" in DF/DDmode, and "ltebr" in SF/SDmode.
602 (define_mode_attr xde [(TF "x") (DF "d") (SF "e") (TD "x") (DD "d") (SD "e")])
603
604 ;; In FP templates, a <dee> in "m<dee><bt>r" will expand to "mx<bt>r" in
605 ;; TF/TDmode, "md<bt>r" in DF/DDmode, "mee<bt>r" in SFmode and "me<bt>r in
606 ;; SDmode.
607 (define_mode_attr xdee [(TF "x") (DF "d") (SF "ee") (TD "x") (DD "d") (SD "e")])
608
609 ;; In FP templates, "<RRe>" will expand to "RRE" in TFmode and "RR" otherwise.
610 ;; Likewise for "<RXe>".
611 (define_mode_attr RRe [(TF "RRE") (DF "RR") (SF "RR")])
612 (define_mode_attr RXe [(TF "RXE") (DF "RX") (SF "RX")])
613
614 ;; The decimal floating point variants of add, sub, div and mul support 3
615 ;; fp register operands. The following attributes allow to merge the bfp and
616 ;; dfp variants in a single insn definition.
617
618 ;; This attribute is used to set op_type accordingly.
619 (define_mode_attr RRer [(TF "RRE") (DF "RRE") (SF "RRE") (TD "RRR")
620 (DD "RRR") (SD "RRR")])
621
622 ;; This attribute is used in the operand constraint list in order to have the
623 ;; first and the second operand match for bfp modes.
624 (define_mode_attr f0 [(TF "0") (DF "0") (SF "0") (TD "f") (DD "f") (DD "f")])
625
626 ;; This attribute is used to merge the scalar vector instructions into
627 ;; the FP patterns. For non-supported modes (all but DF) it expands
628 ;; to constraints which are supposed to be matched by an earlier
629 ;; variant.
630 (define_mode_attr v0 [(TF "0") (DF "v") (SF "0") (TD "0") (DD "0") (DD "0") (TI "0") (DI "v") (SI "0")])
631 (define_mode_attr vf [(TF "f") (DF "v") (SF "f") (TD "f") (DD "f") (DD "f") (TI "f") (DI "v") (SI "f")])
632 (define_mode_attr vd [(TF "d") (DF "v") (SF "d") (TD "d") (DD "d") (DD "d") (TI "d") (DI "v") (SI "d")])
633
634 ;; This attribute is used in the operand list of the instruction to have an
635 ;; additional operand for the dfp instructions.
636 (define_mode_attr op1 [(TF "") (DF "") (SF "")
637 (TD "%1,") (DD "%1,") (SD "%1,")])
638
639
640 ;; This attribute is used in the operand constraint list
641 ;; for instructions dealing with the sign bit of 32 or 64bit fp values.
642 ;; TFmode values are represented by a fp register pair. Since the
643 ;; sign bit instructions only handle single source and target fp registers
644 ;; these instructions can only be used for TFmode values if the source and
645 ;; target operand uses the same fp register.
646 (define_mode_attr fT0 [(TF "0") (DF "f") (SF "f")])
647
648 ;; In FP templates, "<Rf>" will expand to "f" in TFmode and "R" otherwise.
649 ;; This is used to disable the memory alternative in TFmode patterns.
650 (define_mode_attr Rf [(TF "f") (DF "R") (SF "R") (TD "f") (DD "f") (SD "f")])
651
652 ;; This attribute adds b for bfp instructions and t for dfp instructions and is used
653 ;; within instruction mnemonics.
654 (define_mode_attr bt [(TF "b") (DF "b") (SF "b") (TD "t") (DD "t") (SD "t")])
655
656 ;; This attribute is used within instruction mnemonics. It evaluates to d for dfp
657 ;; modes and to an empty string for bfp modes.
658 (define_mode_attr _d [(TF "") (DF "") (SF "") (TD "d") (DD "d") (SD "d")])
659
660 ;; In GPR and P templates, a constraint like "<d0>" will expand to "d" in DImode
661 ;; and "0" in SImode. This allows to combine instructions of which the 31bit
662 ;; version only operates on one register.
663 (define_mode_attr d0 [(DI "d") (SI "0")])
664
665 ;; In combination with d0 this allows to combine instructions of which the 31bit
666 ;; version only operates on one register. The DImode version needs an additional
667 ;; register for the assembler output.
668 (define_mode_attr 1 [(DI "%1,") (SI "")])
669
670 ;; In SHIFT templates, a string like "s<lr>dl" will expand to "sldl" in
671 ;; 'ashift' and "srdl" in 'lshiftrt'.
672 (define_code_attr lr [(ashift "l") (lshiftrt "r")])
673
674 ;; In SHIFT templates, this attribute holds the correct standard name for the
675 ;; pattern itself and the corresponding function calls.
676 (define_code_attr shift [(ashift "ashl") (lshiftrt "lshr")])
677
678 ;; This attribute handles differences in the instruction 'type' and will result
679 ;; in "RRE" for DImode and "RR" for SImode.
680 (define_mode_attr E [(DI "E") (SI "")])
681
682 ;; This attribute handles differences in the instruction 'type' and makes RX<Y>
683 ;; to result in "RXY" for DImode and "RX" for SImode.
684 (define_mode_attr Y [(DI "Y") (SI "")])
685
686 ;; This attribute handles differences in the instruction 'type' and will result
687 ;; in "RSE" for TImode and "RS" for DImode.
688 (define_mode_attr TE [(TI "E") (DI "")])
689
690 ;; In GPR templates, a string like "lc<g>r" will expand to "lcgr" in DImode
691 ;; and "lcr" in SImode.
692 (define_mode_attr g [(DI "g") (SI "")])
693
694 ;; In GPR templates, a string like "sl<y>" will expand to "slg" in DImode
695 ;; and "sly" in SImode. This is useful because on 64bit the ..g instructions
696 ;; were enhanced with long displacements whereas 31bit instructions got a ..y
697 ;; variant for long displacements.
698 (define_mode_attr y [(DI "g") (SI "y")])
699
700 ;; In DW templates, a string like "cds<g>" will expand to "cdsg" in TImode
701 ;; and "cds" in DImode.
702 (define_mode_attr tg [(TI "g") (DI "")])
703
704 ;; In TDI templates, a string like "c<d>sg".
705 (define_mode_attr td [(TI "d") (DI "")])
706
707 ;; In GPR templates, a string like "c<gf>dbr" will expand to "cgdbr" in DImode
708 ;; and "cfdbr" in SImode.
709 (define_mode_attr gf [(DI "g") (SI "f")])
710
711 ;; In GPR templates, a string like sll<gk> will expand to sllg for DI
712 ;; and sllk for SI. This way it is possible to merge the new z196 SI
713 ;; 3 operands shift instructions into the existing patterns.
714 (define_mode_attr gk [(DI "g") (SI "k")])
715
716 ;; ICM mask required to load MODE value into the lowest subreg
717 ;; of a SImode register.
718 (define_mode_attr icm_lo [(HI "3") (QI "1")])
719
720 ;; In HQI templates, a string like "llg<hc>" will expand to "llgh" in
721 ;; HImode and "llgc" in QImode.
722 (define_mode_attr hc [(HI "h") (QI "c")])
723
724 ;; In P templates, the mode <DBL> will expand to "TI" in DImode and "DI"
725 ;; in SImode.
726 (define_mode_attr DBL [(DI "TI") (SI "DI")])
727
728 ;; This attribute expands to DF for TFmode and to DD for TDmode . It is
729 ;; used for Txmode splitters splitting a Txmode copy into 2 Dxmode copies.
730 (define_mode_attr HALF_TMODE [(TF "DF") (TD "DD")])
731
732 ;; Maximum unsigned integer that fits in MODE.
733 (define_mode_attr max_uint [(HI "65535") (QI "255")])
734
735 ;; Start and end field computations for RISBG et al.
736 (define_mode_attr bfstart [(DI "s") (SI "t")])
737 (define_mode_attr bfend [(DI "e") (SI "f")])
738
739 ;; In place of GET_MODE_BITSIZE (<MODE>mode)
740 (define_mode_attr bitsize [(DI "64") (SI "32") (HI "16") (QI "8")])
741
742 ;; In place of GET_MODE_SIZE (<MODE>mode)
743 (define_mode_attr modesize [(DI "8") (SI "4")])
744
745 ;; Allow return and simple_return to be defined from a single template.
746 (define_code_iterator ANY_RETURN [return simple_return])
747
748
749
750 ; Condition code modes generated by vector fp comparisons. These will
751 ; be used also in single element mode.
752 (define_mode_iterator VFCMP [CCVEQ CCVFH CCVFHE])
753 ; Used with VFCMP to expand part of the mnemonic
754 ; For fp we have a mismatch: eq in the insn name - e in asm
755 (define_mode_attr asm_fcmp [(CCVEQ "e") (CCVFH "h") (CCVFHE "he")])
756 (define_mode_attr insn_cmp [(CCVEQ "eq") (CCVH "h") (CCVHU "hl") (CCVFH "h") (CCVFHE "he")])
757
758
759 (include "vector.md")
760
761 ;;
762 ;;- Compare instructions.
763 ;;
764
765 ; Test-under-Mask instructions
766
767 (define_insn "*tmqi_mem"
768 [(set (reg CC_REGNUM)
769 (compare (and:QI (match_operand:QI 0 "memory_operand" "Q,S")
770 (match_operand:QI 1 "immediate_operand" "n,n"))
771 (match_operand:QI 2 "immediate_operand" "n,n")))]
772 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], false))"
773 "@
774 tm\t%S0,%b1
775 tmy\t%S0,%b1"
776 [(set_attr "op_type" "SI,SIY")
777 (set_attr "z10prop" "z10_super,z10_super")])
778
779 (define_insn "*tmdi_reg"
780 [(set (reg CC_REGNUM)
781 (compare (and:DI (match_operand:DI 0 "nonimmediate_operand" "d,d,d,d")
782 (match_operand:DI 1 "immediate_operand"
783 "N0HD0,N1HD0,N2HD0,N3HD0"))
784 (match_operand:DI 2 "immediate_operand" "n,n,n,n")))]
785 "TARGET_ZARCH
786 && s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
787 && s390_single_part (operands[1], DImode, HImode, 0) >= 0"
788 "@
789 tmhh\t%0,%i1
790 tmhl\t%0,%i1
791 tmlh\t%0,%i1
792 tmll\t%0,%i1"
793 [(set_attr "op_type" "RI")
794 (set_attr "z10prop" "z10_super,z10_super,z10_super,z10_super")])
795
796 (define_insn "*tmsi_reg"
797 [(set (reg CC_REGNUM)
798 (compare (and:SI (match_operand:SI 0 "nonimmediate_operand" "d,d")
799 (match_operand:SI 1 "immediate_operand" "N0HS0,N1HS0"))
800 (match_operand:SI 2 "immediate_operand" "n,n")))]
801 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
802 && s390_single_part (operands[1], SImode, HImode, 0) >= 0"
803 "@
804 tmh\t%0,%i1
805 tml\t%0,%i1"
806 [(set_attr "op_type" "RI")
807 (set_attr "z10prop" "z10_super,z10_super")])
808
809 (define_insn "*tm<mode>_full"
810 [(set (reg CC_REGNUM)
811 (compare (match_operand:HQI 0 "register_operand" "d")
812 (match_operand:HQI 1 "immediate_operand" "n")))]
813 "s390_match_ccmode (insn, s390_tm_ccmode (constm1_rtx, operands[1], true))"
814 "tml\t%0,<max_uint>"
815 [(set_attr "op_type" "RI")
816 (set_attr "z10prop" "z10_super")])
817
818
819 ;
820 ; Load-and-Test instructions
821 ;
822
823 ; tst(di|si) instruction pattern(s).
824
825 (define_insn "*tstdi_sign"
826 [(set (reg CC_REGNUM)
827 (compare
828 (ashiftrt:DI
829 (ashift:DI
830 (subreg:DI (match_operand:SI 0 "nonimmediate_operand" "d,RT") 0)
831 (const_int 32)) (const_int 32))
832 (match_operand:DI 1 "const0_operand" "")))
833 (set (match_operand:DI 2 "register_operand" "=d,d")
834 (sign_extend:DI (match_dup 0)))]
835 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH"
836 "ltgfr\t%2,%0
837 ltgf\t%2,%0"
838 [(set_attr "op_type" "RRE,RXY")
839 (set_attr "cpu_facility" "*,z10")
840 (set_attr "z10prop" "z10_super_E1,z10_super_E1") ])
841
842 ; ltr, lt, ltgr, ltg
843 (define_insn "*tst<mode>_extimm"
844 [(set (reg CC_REGNUM)
845 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
846 (match_operand:GPR 1 "const0_operand" "")))
847 (set (match_operand:GPR 2 "register_operand" "=d,d")
848 (match_dup 0))]
849 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
850 "@
851 lt<g>r\t%2,%0
852 lt<g>\t%2,%0"
853 [(set_attr "op_type" "RR<E>,RXY")
854 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3") ])
855
856 ; ltr, lt, ltgr, ltg
857 (define_insn "*tst<mode>_cconly_extimm"
858 [(set (reg CC_REGNUM)
859 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
860 (match_operand:GPR 1 "const0_operand" "")))
861 (clobber (match_scratch:GPR 2 "=X,d"))]
862 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
863 "@
864 lt<g>r\t%0,%0
865 lt<g>\t%2,%0"
866 [(set_attr "op_type" "RR<E>,RXY")
867 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3")])
868
869 (define_insn "*tstdi"
870 [(set (reg CC_REGNUM)
871 (compare (match_operand:DI 0 "register_operand" "d")
872 (match_operand:DI 1 "const0_operand" "")))
873 (set (match_operand:DI 2 "register_operand" "=d")
874 (match_dup 0))]
875 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH && !TARGET_EXTIMM"
876 "ltgr\t%2,%0"
877 [(set_attr "op_type" "RRE")
878 (set_attr "z10prop" "z10_fr_E1")])
879
880 (define_insn "*tstsi"
881 [(set (reg CC_REGNUM)
882 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
883 (match_operand:SI 1 "const0_operand" "")))
884 (set (match_operand:SI 2 "register_operand" "=d,d,d")
885 (match_dup 0))]
886 "s390_match_ccmode(insn, CCSmode) && !TARGET_EXTIMM"
887 "@
888 ltr\t%2,%0
889 icm\t%2,15,%S0
890 icmy\t%2,15,%S0"
891 [(set_attr "op_type" "RR,RS,RSY")
892 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
893
894 (define_insn "*tstsi_cconly"
895 [(set (reg CC_REGNUM)
896 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
897 (match_operand:SI 1 "const0_operand" "")))
898 (clobber (match_scratch:SI 2 "=X,d,d"))]
899 "s390_match_ccmode(insn, CCSmode)"
900 "@
901 ltr\t%0,%0
902 icm\t%2,15,%S0
903 icmy\t%2,15,%S0"
904 [(set_attr "op_type" "RR,RS,RSY")
905 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
906
907 (define_insn "*tstdi_cconly_31"
908 [(set (reg CC_REGNUM)
909 (compare (match_operand:DI 0 "register_operand" "d")
910 (match_operand:DI 1 "const0_operand" "")))]
911 "s390_match_ccmode(insn, CCSmode) && !TARGET_ZARCH"
912 "srda\t%0,0"
913 [(set_attr "op_type" "RS")
914 (set_attr "atype" "reg")])
915
916 ; ltr, ltgr
917 (define_insn "*tst<mode>_cconly2"
918 [(set (reg CC_REGNUM)
919 (compare (match_operand:GPR 0 "register_operand" "d")
920 (match_operand:GPR 1 "const0_operand" "")))]
921 "s390_match_ccmode(insn, CCSmode)"
922 "lt<g>r\t%0,%0"
923 [(set_attr "op_type" "RR<E>")
924 (set_attr "z10prop" "z10_fr_E1")])
925
926 ; tst(hi|qi) instruction pattern(s).
927
928 (define_insn "*tst<mode>CCT"
929 [(set (reg CC_REGNUM)
930 (compare (match_operand:HQI 0 "nonimmediate_operand" "?Q,?S,d")
931 (match_operand:HQI 1 "const0_operand" "")))
932 (set (match_operand:HQI 2 "register_operand" "=d,d,0")
933 (match_dup 0))]
934 "s390_match_ccmode(insn, CCTmode)"
935 "@
936 icm\t%2,<icm_lo>,%S0
937 icmy\t%2,<icm_lo>,%S0
938 tml\t%0,<max_uint>"
939 [(set_attr "op_type" "RS,RSY,RI")
940 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
941
942 (define_insn "*tsthiCCT_cconly"
943 [(set (reg CC_REGNUM)
944 (compare (match_operand:HI 0 "nonimmediate_operand" "Q,S,d")
945 (match_operand:HI 1 "const0_operand" "")))
946 (clobber (match_scratch:HI 2 "=d,d,X"))]
947 "s390_match_ccmode(insn, CCTmode)"
948 "@
949 icm\t%2,3,%S0
950 icmy\t%2,3,%S0
951 tml\t%0,65535"
952 [(set_attr "op_type" "RS,RSY,RI")
953 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
954
955 (define_insn "*tstqiCCT_cconly"
956 [(set (reg CC_REGNUM)
957 (compare (match_operand:QI 0 "nonimmediate_operand" "?Q,?S,d")
958 (match_operand:QI 1 "const0_operand" "")))]
959 "s390_match_ccmode(insn, CCTmode)"
960 "@
961 cli\t%S0,0
962 cliy\t%S0,0
963 tml\t%0,255"
964 [(set_attr "op_type" "SI,SIY,RI")
965 (set_attr "z10prop" "z10_super,z10_super,z10_super")])
966
967 (define_insn "*tst<mode>"
968 [(set (reg CC_REGNUM)
969 (compare (match_operand:HQI 0 "s_operand" "Q,S")
970 (match_operand:HQI 1 "const0_operand" "")))
971 (set (match_operand:HQI 2 "register_operand" "=d,d")
972 (match_dup 0))]
973 "s390_match_ccmode(insn, CCSmode)"
974 "@
975 icm\t%2,<icm_lo>,%S0
976 icmy\t%2,<icm_lo>,%S0"
977 [(set_attr "op_type" "RS,RSY")
978 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
979
980 (define_insn "*tst<mode>_cconly"
981 [(set (reg CC_REGNUM)
982 (compare (match_operand:HQI 0 "s_operand" "Q,S")
983 (match_operand:HQI 1 "const0_operand" "")))
984 (clobber (match_scratch:HQI 2 "=d,d"))]
985 "s390_match_ccmode(insn, CCSmode)"
986 "@
987 icm\t%2,<icm_lo>,%S0
988 icmy\t%2,<icm_lo>,%S0"
989 [(set_attr "op_type" "RS,RSY")
990 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
991
992
993 ; Compare (equality) instructions
994
995 (define_insn "*cmpdi_cct"
996 [(set (reg CC_REGNUM)
997 (compare (match_operand:DI 0 "nonimmediate_operand" "%d,d,d,d,Q")
998 (match_operand:DI 1 "general_operand" "d,K,Os,RT,BQ")))]
999 "s390_match_ccmode (insn, CCTmode) && TARGET_ZARCH"
1000 "@
1001 cgr\t%0,%1
1002 cghi\t%0,%h1
1003 cgfi\t%0,%1
1004 cg\t%0,%1
1005 #"
1006 [(set_attr "op_type" "RRE,RI,RIL,RXY,SS")
1007 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,*")])
1008
1009 (define_insn "*cmpsi_cct"
1010 [(set (reg CC_REGNUM)
1011 (compare (match_operand:SI 0 "nonimmediate_operand" "%d,d,d,d,d,Q")
1012 (match_operand:SI 1 "general_operand" "d,K,Os,R,T,BQ")))]
1013 "s390_match_ccmode (insn, CCTmode)"
1014 "@
1015 cr\t%0,%1
1016 chi\t%0,%h1
1017 cfi\t%0,%1
1018 c\t%0,%1
1019 cy\t%0,%1
1020 #"
1021 [(set_attr "op_type" "RR,RI,RIL,RX,RXY,SS")
1022 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*")])
1023
1024 ; Compare (signed) instructions
1025
1026 (define_insn "*cmpdi_ccs_sign"
1027 [(set (reg CC_REGNUM)
1028 (compare (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1029 "d,RT,b"))
1030 (match_operand:DI 0 "register_operand" "d, d,d")))]
1031 "s390_match_ccmode(insn, CCSRmode) && TARGET_ZARCH"
1032 "@
1033 cgfr\t%0,%1
1034 cgf\t%0,%1
1035 cgfrl\t%0,%1"
1036 [(set_attr "op_type" "RRE,RXY,RIL")
1037 (set_attr "z10prop" "z10_c,*,*")
1038 (set_attr "type" "*,*,larl")])
1039
1040
1041
1042 (define_insn "*cmpsi_ccs_sign"
1043 [(set (reg CC_REGNUM)
1044 (compare (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T,b"))
1045 (match_operand:SI 0 "register_operand" "d,d,d")))]
1046 "s390_match_ccmode(insn, CCSRmode)"
1047 "@
1048 ch\t%0,%1
1049 chy\t%0,%1
1050 chrl\t%0,%1"
1051 [(set_attr "op_type" "RX,RXY,RIL")
1052 (set_attr "cpu_facility" "*,*,z10")
1053 (set_attr "type" "*,*,larl")
1054 (set_attr "z196prop" "z196_cracked,z196_cracked,z196_cracked")])
1055
1056 (define_insn "*cmphi_ccs_z10"
1057 [(set (reg CC_REGNUM)
1058 (compare (match_operand:HI 0 "s_operand" "Q")
1059 (match_operand:HI 1 "immediate_operand" "K")))]
1060 "s390_match_ccmode(insn, CCSmode) && TARGET_Z10"
1061 "chhsi\t%0,%1"
1062 [(set_attr "op_type" "SIL")
1063 (set_attr "z196prop" "z196_cracked")])
1064
1065 (define_insn "*cmpdi_ccs_signhi_rl"
1066 [(set (reg CC_REGNUM)
1067 (compare (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT,b"))
1068 (match_operand:GPR 0 "register_operand" "d,d")))]
1069 "s390_match_ccmode(insn, CCSRmode) && TARGET_Z10"
1070 "@
1071 cgh\t%0,%1
1072 cghrl\t%0,%1"
1073 [(set_attr "op_type" "RXY,RIL")
1074 (set_attr "type" "*,larl")])
1075
1076 ; cr, chi, cfi, c, cy, cgr, cghi, cgfi, cg, chsi, cghsi, crl, cgrl
1077 (define_insn "*cmp<mode>_ccs"
1078 [(set (reg CC_REGNUM)
1079 (compare (match_operand:GPR 0 "nonimmediate_operand"
1080 "d,d,Q, d,d,d,d")
1081 (match_operand:GPR 1 "general_operand"
1082 "d,K,K,Os,R,T,b")))]
1083 "s390_match_ccmode(insn, CCSmode)"
1084 "@
1085 c<g>r\t%0,%1
1086 c<g>hi\t%0,%h1
1087 c<g>hsi\t%0,%h1
1088 c<g>fi\t%0,%1
1089 c<g>\t%0,%1
1090 c<y>\t%0,%1
1091 c<g>rl\t%0,%1"
1092 [(set_attr "op_type" "RR<E>,RI,SIL,RIL,RX<Y>,RXY,RIL")
1093 (set_attr "cpu_facility" "*,*,z10,extimm,*,*,z10")
1094 (set_attr "type" "*,*,*,*,*,*,larl")
1095 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,z10_super")])
1096
1097
1098 ; Compare (unsigned) instructions
1099
1100 (define_insn "*cmpsi_ccu_zerohi_rlsi"
1101 [(set (reg CC_REGNUM)
1102 (compare (zero_extend:SI (mem:HI (match_operand:SI 1
1103 "larl_operand" "X")))
1104 (match_operand:SI 0 "register_operand" "d")))]
1105 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1106 "clhrl\t%0,%1"
1107 [(set_attr "op_type" "RIL")
1108 (set_attr "type" "larl")
1109 (set_attr "z10prop" "z10_super")])
1110
1111 ; clhrl, clghrl
1112 (define_insn "*cmp<GPR:mode>_ccu_zerohi_rldi"
1113 [(set (reg CC_REGNUM)
1114 (compare (zero_extend:GPR (mem:HI (match_operand:DI 1
1115 "larl_operand" "X")))
1116 (match_operand:GPR 0 "register_operand" "d")))]
1117 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1118 "cl<g>hrl\t%0,%1"
1119 [(set_attr "op_type" "RIL")
1120 (set_attr "type" "larl")
1121 (set_attr "z10prop" "z10_super")])
1122
1123 (define_insn "*cmpdi_ccu_zero"
1124 [(set (reg CC_REGNUM)
1125 (compare (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1126 "d,RT,b"))
1127 (match_operand:DI 0 "register_operand" "d, d,d")))]
1128 "s390_match_ccmode (insn, CCURmode) && TARGET_ZARCH"
1129 "@
1130 clgfr\t%0,%1
1131 clgf\t%0,%1
1132 clgfrl\t%0,%1"
1133 [(set_attr "op_type" "RRE,RXY,RIL")
1134 (set_attr "cpu_facility" "*,*,z10")
1135 (set_attr "type" "*,*,larl")
1136 (set_attr "z10prop" "z10_super_c,z10_super_E1,z10_super")])
1137
1138 (define_insn "*cmpdi_ccu"
1139 [(set (reg CC_REGNUM)
1140 (compare (match_operand:DI 0 "nonimmediate_operand"
1141 "d, d,d,Q, d, Q,BQ")
1142 (match_operand:DI 1 "general_operand"
1143 "d,Op,b,D,RT,BQ,Q")))]
1144 "s390_match_ccmode (insn, CCUmode) && TARGET_ZARCH"
1145 "@
1146 clgr\t%0,%1
1147 clgfi\t%0,%1
1148 clgrl\t%0,%1
1149 clghsi\t%0,%x1
1150 clg\t%0,%1
1151 #
1152 #"
1153 [(set_attr "op_type" "RRE,RIL,RIL,SIL,RXY,SS,SS")
1154 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*")
1155 (set_attr "type" "*,*,larl,*,*,*,*")
1156 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*,*")])
1157
1158 (define_insn "*cmpsi_ccu"
1159 [(set (reg CC_REGNUM)
1160 (compare (match_operand:SI 0 "nonimmediate_operand" "d, d,d,Q,d,d, Q,BQ")
1161 (match_operand:SI 1 "general_operand" "d,Os,b,D,R,T,BQ, Q")))]
1162 "s390_match_ccmode (insn, CCUmode)"
1163 "@
1164 clr\t%0,%1
1165 clfi\t%0,%o1
1166 clrl\t%0,%1
1167 clfhsi\t%0,%x1
1168 cl\t%0,%1
1169 cly\t%0,%1
1170 #
1171 #"
1172 [(set_attr "op_type" "RR,RIL,RIL,SIL,RX,RXY,SS,SS")
1173 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*,*")
1174 (set_attr "type" "*,*,larl,*,*,*,*,*")
1175 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,*,*")])
1176
1177 (define_insn "*cmphi_ccu"
1178 [(set (reg CC_REGNUM)
1179 (compare (match_operand:HI 0 "nonimmediate_operand" "d,d,Q,Q,BQ")
1180 (match_operand:HI 1 "general_operand" "Q,S,D,BQ,Q")))]
1181 "s390_match_ccmode (insn, CCUmode)
1182 && !register_operand (operands[1], HImode)"
1183 "@
1184 clm\t%0,3,%S1
1185 clmy\t%0,3,%S1
1186 clhhsi\t%0,%1
1187 #
1188 #"
1189 [(set_attr "op_type" "RS,RSY,SIL,SS,SS")
1190 (set_attr "cpu_facility" "*,*,z10,*,*")
1191 (set_attr "z10prop" "*,*,z10_super,*,*")])
1192
1193 (define_insn "*cmpqi_ccu"
1194 [(set (reg CC_REGNUM)
1195 (compare (match_operand:QI 0 "nonimmediate_operand" "d,d,Q,S,Q,BQ")
1196 (match_operand:QI 1 "general_operand" "Q,S,n,n,BQ,Q")))]
1197 "s390_match_ccmode (insn, CCUmode)
1198 && !register_operand (operands[1], QImode)"
1199 "@
1200 clm\t%0,1,%S1
1201 clmy\t%0,1,%S1
1202 cli\t%S0,%b1
1203 cliy\t%S0,%b1
1204 #
1205 #"
1206 [(set_attr "op_type" "RS,RSY,SI,SIY,SS,SS")
1207 (set_attr "z10prop" "*,*,z10_super,z10_super,*,*")])
1208
1209
1210 ; Block compare (CLC) instruction patterns.
1211
1212 (define_insn "*clc"
1213 [(set (reg CC_REGNUM)
1214 (compare (match_operand:BLK 0 "memory_operand" "Q")
1215 (match_operand:BLK 1 "memory_operand" "Q")))
1216 (use (match_operand 2 "const_int_operand" "n"))]
1217 "s390_match_ccmode (insn, CCUmode)
1218 && INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
1219 "clc\t%O0(%2,%R0),%S1"
1220 [(set_attr "op_type" "SS")])
1221
1222 (define_split
1223 [(set (reg CC_REGNUM)
1224 (compare (match_operand 0 "memory_operand" "")
1225 (match_operand 1 "memory_operand" "")))]
1226 "reload_completed
1227 && s390_match_ccmode (insn, CCUmode)
1228 && GET_MODE (operands[0]) == GET_MODE (operands[1])
1229 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
1230 [(parallel
1231 [(set (match_dup 0) (match_dup 1))
1232 (use (match_dup 2))])]
1233 {
1234 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
1235 operands[0] = adjust_address (operands[0], BLKmode, 0);
1236 operands[1] = adjust_address (operands[1], BLKmode, 0);
1237
1238 operands[1] = gen_rtx_COMPARE (GET_MODE (SET_DEST (PATTERN (curr_insn))),
1239 operands[0], operands[1]);
1240 operands[0] = SET_DEST (PATTERN (curr_insn));
1241 })
1242
1243
1244 ; (TF|DF|SF|TD|DD|SD) instructions
1245
1246 ; ltxbr, ltdbr, ltebr, ltxtr, ltdtr
1247 (define_insn "*cmp<mode>_ccs_0"
1248 [(set (reg CC_REGNUM)
1249 (compare (match_operand:FP 0 "register_operand" "f")
1250 (match_operand:FP 1 "const0_operand" "")))]
1251 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1252 "lt<xde><bt>r\t%0,%0"
1253 [(set_attr "op_type" "RRE")
1254 (set_attr "type" "fsimp<mode>")])
1255
1256 ; cxtr, cxbr, cdtr, cdbr, cebr, cdb, ceb
1257 (define_insn "*cmp<mode>_ccs"
1258 [(set (reg CC_REGNUM)
1259 (compare (match_operand:FP 0 "register_operand" "f,f")
1260 (match_operand:FP 1 "general_operand" "f,<Rf>")))]
1261 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1262 "@
1263 c<xde><bt>r\t%0,%1
1264 c<xde>b\t%0,%1"
1265 [(set_attr "op_type" "RRE,RXE")
1266 (set_attr "type" "fsimp<mode>")])
1267
1268 ; wfcedbs, wfchdbs, wfchedbs
1269 (define_insn "*vec_cmp<insn_cmp>df_cconly"
1270 [(set (reg:VFCMP CC_REGNUM)
1271 (compare:VFCMP (match_operand:DF 0 "register_operand" "v")
1272 (match_operand:DF 1 "register_operand" "v")))
1273 (clobber (match_scratch:V2DI 2 "=v"))]
1274 "TARGET_Z13 && TARGET_HARD_FLOAT"
1275 "wfc<asm_fcmp>dbs\t%v2,%v0,%v1"
1276 [(set_attr "op_type" "VRR")])
1277
1278 ; Compare and Branch instructions
1279
1280 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1281 ; The following instructions do a complementary access of their second
1282 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1283 (define_insn "*cmp_and_br_signed_<mode>"
1284 [(set (pc)
1285 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1286 [(match_operand:GPR 1 "register_operand" "d,d")
1287 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1288 (label_ref (match_operand 3 "" ""))
1289 (pc)))
1290 (clobber (reg:CC CC_REGNUM))]
1291 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1292 {
1293 if (get_attr_length (insn) == 6)
1294 return which_alternative ?
1295 "c<g>ij%C0\t%1,%c2,%l3" : "c<g>rj%C0\t%1,%2,%l3";
1296 else
1297 return which_alternative ?
1298 "c<g>fi\t%1,%c2\;jg%C0\t%l3" : "c<g>r\t%1,%2\;jg%C0\t%l3";
1299 }
1300 [(set_attr "op_type" "RIE")
1301 (set_attr "type" "branch")
1302 (set_attr "z10prop" "z10_super_c,z10_super")
1303 (set (attr "length")
1304 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1305 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1306 ; 10 byte for cgr/jg
1307
1308 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1309 ; The following instructions do a complementary access of their second
1310 ; operand (z10 only): clrj, clgrj, clr, clgr
1311 (define_insn "*cmp_and_br_unsigned_<mode>"
1312 [(set (pc)
1313 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1314 [(match_operand:GPR 1 "register_operand" "d,d")
1315 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1316 (label_ref (match_operand 3 "" ""))
1317 (pc)))
1318 (clobber (reg:CC CC_REGNUM))]
1319 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1320 {
1321 if (get_attr_length (insn) == 6)
1322 return which_alternative ?
1323 "cl<g>ij%C0\t%1,%b2,%l3" : "cl<g>rj%C0\t%1,%2,%l3";
1324 else
1325 return which_alternative ?
1326 "cl<g>fi\t%1,%b2\;jg%C0\t%l3" : "cl<g>r\t%1,%2\;jg%C0\t%l3";
1327 }
1328 [(set_attr "op_type" "RIE")
1329 (set_attr "type" "branch")
1330 (set_attr "z10prop" "z10_super_c,z10_super")
1331 (set (attr "length")
1332 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1333 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1334 ; 10 byte for clgr/jg
1335
1336 ; And now the same two patterns as above but with a negated CC mask.
1337
1338 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1339 ; The following instructions do a complementary access of their second
1340 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1341 (define_insn "*icmp_and_br_signed_<mode>"
1342 [(set (pc)
1343 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1344 [(match_operand:GPR 1 "register_operand" "d,d")
1345 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1346 (pc)
1347 (label_ref (match_operand 3 "" ""))))
1348 (clobber (reg:CC CC_REGNUM))]
1349 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1350 {
1351 if (get_attr_length (insn) == 6)
1352 return which_alternative ?
1353 "c<g>ij%D0\t%1,%c2,%l3" : "c<g>rj%D0\t%1,%2,%l3";
1354 else
1355 return which_alternative ?
1356 "c<g>fi\t%1,%c2\;jg%D0\t%l3" : "c<g>r\t%1,%2\;jg%D0\t%l3";
1357 }
1358 [(set_attr "op_type" "RIE")
1359 (set_attr "type" "branch")
1360 (set_attr "z10prop" "z10_super_c,z10_super")
1361 (set (attr "length")
1362 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1363 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1364 ; 10 byte for cgr/jg
1365
1366 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1367 ; The following instructions do a complementary access of their second
1368 ; operand (z10 only): clrj, clgrj, clr, clgr
1369 (define_insn "*icmp_and_br_unsigned_<mode>"
1370 [(set (pc)
1371 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1372 [(match_operand:GPR 1 "register_operand" "d,d")
1373 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1374 (pc)
1375 (label_ref (match_operand 3 "" ""))))
1376 (clobber (reg:CC CC_REGNUM))]
1377 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1378 {
1379 if (get_attr_length (insn) == 6)
1380 return which_alternative ?
1381 "cl<g>ij%D0\t%1,%b2,%l3" : "cl<g>rj%D0\t%1,%2,%l3";
1382 else
1383 return which_alternative ?
1384 "cl<g>fi\t%1,%b2\;jg%D0\t%l3" : "cl<g>r\t%1,%2\;jg%D0\t%l3";
1385 }
1386 [(set_attr "op_type" "RIE")
1387 (set_attr "type" "branch")
1388 (set_attr "z10prop" "z10_super_c,z10_super")
1389 (set (attr "length")
1390 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1391 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1392 ; 10 byte for clgr/jg
1393
1394 ;;
1395 ;;- Move instructions.
1396 ;;
1397
1398 ;
1399 ; movti instruction pattern(s).
1400 ;
1401
1402 ; FIXME: More constants are possible by enabling jxx, jyy constraints
1403 ; for TImode (use double-int for the calculations)
1404 (define_insn "movti"
1405 [(set (match_operand:TI 0 "nonimmediate_operand" "=d,QS,v, v, v,v,d, v,QR, d,o")
1406 (match_operand:TI 1 "general_operand" "QS, d,v,j00,jm1,d,v,QR, v,dPRT,d"))]
1407 "TARGET_ZARCH"
1408 "@
1409 lmg\t%0,%N0,%S1
1410 stmg\t%1,%N1,%S0
1411 vlr\t%v0,%v1
1412 vzero\t%v0
1413 vone\t%v0
1414 vlvgp\t%v0,%1,%N1
1415 #
1416 vl\t%v0,%1
1417 vst\t%v1,%0
1418 #
1419 #"
1420 [(set_attr "op_type" "RSY,RSY,VRR,VRI,VRI,VRR,*,VRX,VRX,*,*")
1421 (set_attr "type" "lm,stm,*,*,*,*,*,*,*,*,*")
1422 (set_attr "cpu_facility" "*,*,vec,vec,vec,vec,vec,vec,vec,*,*")])
1423
1424 (define_split
1425 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1426 (match_operand:TI 1 "general_operand" ""))]
1427 "TARGET_ZARCH && reload_completed
1428 && s390_split_ok_p (operands[0], operands[1], TImode, 0)"
1429 [(set (match_dup 2) (match_dup 4))
1430 (set (match_dup 3) (match_dup 5))]
1431 {
1432 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1433 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1434 operands[4] = operand_subword (operands[1], 0, 0, TImode);
1435 operands[5] = operand_subword (operands[1], 1, 0, TImode);
1436 })
1437
1438 (define_split
1439 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1440 (match_operand:TI 1 "general_operand" ""))]
1441 "TARGET_ZARCH && reload_completed
1442 && s390_split_ok_p (operands[0], operands[1], TImode, 1)"
1443 [(set (match_dup 2) (match_dup 4))
1444 (set (match_dup 3) (match_dup 5))]
1445 {
1446 operands[2] = operand_subword (operands[0], 1, 0, TImode);
1447 operands[3] = operand_subword (operands[0], 0, 0, TImode);
1448 operands[4] = operand_subword (operands[1], 1, 0, TImode);
1449 operands[5] = operand_subword (operands[1], 0, 0, TImode);
1450 })
1451
1452 ; Use part of the TImode target reg to perform the address
1453 ; calculation. If the TImode value is supposed to be copied into a VR
1454 ; this splitter is not necessary.
1455 (define_split
1456 [(set (match_operand:TI 0 "register_operand" "")
1457 (match_operand:TI 1 "memory_operand" ""))]
1458 "TARGET_ZARCH && reload_completed
1459 && !VECTOR_REG_P (operands[0])
1460 && !s_operand (operands[1], VOIDmode)"
1461 [(set (match_dup 0) (match_dup 1))]
1462 {
1463 rtx addr = operand_subword (operands[0], 1, 0, TImode);
1464 addr = gen_lowpart (Pmode, addr);
1465 s390_load_address (addr, XEXP (operands[1], 0));
1466 operands[1] = replace_equiv_address (operands[1], addr);
1467 })
1468
1469
1470 ; Split a VR -> GPR TImode move into 2 vector load GR from VR element.
1471 ; For the higher order bits we do simply a DImode move while the
1472 ; second part is done via vec extract. Both will end up as vlgvg.
1473 (define_split
1474 [(set (match_operand:TI 0 "register_operand" "")
1475 (match_operand:TI 1 "register_operand" ""))]
1476 "TARGET_VX && reload_completed
1477 && GENERAL_REG_P (operands[0])
1478 && VECTOR_REG_P (operands[1])"
1479 [(set (match_dup 2) (match_dup 4))
1480 (set (match_dup 3) (unspec:DI [(match_dup 5) (const_int 1)]
1481 UNSPEC_VEC_EXTRACT))]
1482 {
1483 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1484 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1485 operands[4] = gen_rtx_REG (DImode, REGNO (operands[1]));
1486 operands[5] = gen_rtx_REG (V2DImode, REGNO (operands[1]));
1487 })
1488
1489 ;
1490 ; Patterns used for secondary reloads
1491 ;
1492
1493 ; z10 provides move instructions accepting larl memory operands.
1494 ; Unfortunately there is no such variant for QI, TI and FP mode moves.
1495 ; These patterns are also used for unaligned SI and DI accesses.
1496
1497 (define_expand "reload<ALL:mode><P:mode>_tomem_z10"
1498 [(parallel [(match_operand:ALL 0 "memory_operand" "")
1499 (match_operand:ALL 1 "register_operand" "=d")
1500 (match_operand:P 2 "register_operand" "=&a")])]
1501 "TARGET_Z10"
1502 {
1503 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1504 DONE;
1505 })
1506
1507 (define_expand "reload<ALL:mode><P:mode>_toreg_z10"
1508 [(parallel [(match_operand:ALL 0 "register_operand" "=d")
1509 (match_operand:ALL 1 "memory_operand" "")
1510 (match_operand:P 2 "register_operand" "=a")])]
1511 "TARGET_Z10"
1512 {
1513 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1514 DONE;
1515 })
1516
1517 (define_expand "reload<P:mode>_larl_odd_addend_z10"
1518 [(parallel [(match_operand:P 0 "register_operand" "=d")
1519 (match_operand:P 1 "larl_operand" "")
1520 (match_operand:P 2 "register_operand" "=a")])]
1521 "TARGET_Z10"
1522 {
1523 s390_reload_larl_operand (operands[0], operands[1], operands[2]);
1524 DONE;
1525 })
1526
1527 ; Handles loading a PLUS (load address) expression
1528
1529 (define_expand "reload<mode>_plus"
1530 [(parallel [(match_operand:P 0 "register_operand" "=a")
1531 (match_operand:P 1 "s390_plus_operand" "")
1532 (match_operand:P 2 "register_operand" "=&a")])]
1533 ""
1534 {
1535 s390_expand_plus_operand (operands[0], operands[1], operands[2]);
1536 DONE;
1537 })
1538
1539 ; Not all the indirect memory access instructions support the full
1540 ; format (long disp + index + base). So whenever a move from/to such
1541 ; an address is required and the instruction cannot deal with it we do
1542 ; a load address into a scratch register first and use this as the new
1543 ; base register.
1544 ; This in particular is used for:
1545 ; - non-offsetable memory accesses for multiword moves
1546 ; - full vector reg moves with long displacements
1547
1548 (define_expand "reload<mode>_la_in"
1549 [(parallel [(match_operand 0 "register_operand" "")
1550 (match_operand 1 "" "")
1551 (match_operand:P 2 "register_operand" "=&a")])]
1552 ""
1553 {
1554 gcc_assert (MEM_P (operands[1]));
1555 s390_load_address (operands[2], find_replacement (&XEXP (operands[1], 0)));
1556 operands[1] = replace_equiv_address (operands[1], operands[2]);
1557 emit_move_insn (operands[0], operands[1]);
1558 DONE;
1559 })
1560
1561 (define_expand "reload<mode>_la_out"
1562 [(parallel [(match_operand 0 "" "")
1563 (match_operand 1 "register_operand" "")
1564 (match_operand:P 2 "register_operand" "=&a")])]
1565 ""
1566 {
1567 gcc_assert (MEM_P (operands[0]));
1568 s390_load_address (operands[2], find_replacement (&XEXP (operands[0], 0)));
1569 operands[0] = replace_equiv_address (operands[0], operands[2]);
1570 emit_move_insn (operands[0], operands[1]);
1571 DONE;
1572 })
1573
1574 (define_expand "reload<mode>_PIC_addr"
1575 [(parallel [(match_operand 0 "register_operand" "=d")
1576 (match_operand 1 "larl_operand" "")
1577 (match_operand:P 2 "register_operand" "=a")])]
1578 ""
1579 {
1580 rtx new_rtx = legitimize_pic_address (operands[1], operands[2]);
1581 emit_move_insn (operands[0], new_rtx);
1582 })
1583
1584 ;
1585 ; movdi instruction pattern(s).
1586 ;
1587
1588 (define_expand "movdi"
1589 [(set (match_operand:DI 0 "general_operand" "")
1590 (match_operand:DI 1 "general_operand" ""))]
1591 ""
1592 {
1593 /* Handle symbolic constants. */
1594 if (TARGET_64BIT
1595 && (SYMBOLIC_CONST (operands[1])
1596 || (GET_CODE (operands[1]) == PLUS
1597 && XEXP (operands[1], 0) == pic_offset_table_rtx
1598 && SYMBOLIC_CONST (XEXP (operands[1], 1)))))
1599 emit_symbolic_move (operands);
1600 })
1601
1602 (define_insn "*movdi_larl"
1603 [(set (match_operand:DI 0 "register_operand" "=d")
1604 (match_operand:DI 1 "larl_operand" "X"))]
1605 "TARGET_64BIT
1606 && !FP_REG_P (operands[0])"
1607 "larl\t%0,%1"
1608 [(set_attr "op_type" "RIL")
1609 (set_attr "type" "larl")
1610 (set_attr "z10prop" "z10_super_A1")])
1611
1612 (define_insn "*movdi_64"
1613 [(set (match_operand:DI 0 "nonimmediate_operand"
1614 "=d, d, d, d, d, d, d, d,f,d,d,d,d, d,RT,!*f,!*f,!*f,!R,!T,b,Q,d,t,Q,t,v,v,v,d, v,QR")
1615 (match_operand:DI 1 "general_operand"
1616 " K,N0HD0,N1HD0,N2HD0,N3HD0,Os,N0SD0,N1SD0,d,f,L,b,d,RT, d, *f, R, T,*f,*f,d,K,t,d,t,Q,K,v,d,v,QR, v"))]
1617 "TARGET_ZARCH"
1618 "@
1619 lghi\t%0,%h1
1620 llihh\t%0,%i1
1621 llihl\t%0,%i1
1622 llilh\t%0,%i1
1623 llill\t%0,%i1
1624 lgfi\t%0,%1
1625 llihf\t%0,%k1
1626 llilf\t%0,%k1
1627 ldgr\t%0,%1
1628 lgdr\t%0,%1
1629 lay\t%0,%a1
1630 lgrl\t%0,%1
1631 lgr\t%0,%1
1632 lg\t%0,%1
1633 stg\t%1,%0
1634 ldr\t%0,%1
1635 ld\t%0,%1
1636 ldy\t%0,%1
1637 std\t%1,%0
1638 stdy\t%1,%0
1639 stgrl\t%1,%0
1640 mvghi\t%0,%1
1641 #
1642 #
1643 stam\t%1,%N1,%S0
1644 lam\t%0,%N0,%S1
1645 vleig\t%v0,%h1,0
1646 vlr\t%v0,%v1
1647 vlvgg\t%v0,%1,0
1648 vlgvg\t%0,%v1,0
1649 vleg\t%v0,%1,0
1650 vsteg\t%v1,%0,0"
1651 [(set_attr "op_type" "RI,RI,RI,RI,RI,RIL,RIL,RIL,RRE,RRE,RXY,RIL,RRE,RXY,
1652 RXY,RR,RX,RXY,RX,RXY,RIL,SIL,*,*,RS,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1653 (set_attr "type" "*,*,*,*,*,*,*,*,floaddf,floaddf,la,larl,lr,load,store,
1654 floaddf,floaddf,floaddf,fstoredf,fstoredf,larl,*,*,*,*,
1655 *,*,*,*,*,*,*")
1656 (set_attr "cpu_facility" "*,*,*,*,*,extimm,extimm,extimm,dfp,dfp,longdisp,
1657 z10,*,*,*,*,*,longdisp,*,longdisp,
1658 z10,z10,*,*,*,*,vec,vec,vec,vec,vec,vec")
1659 (set_attr "z10prop" "z10_fwd_A1,
1660 z10_fwd_E1,
1661 z10_fwd_E1,
1662 z10_fwd_E1,
1663 z10_fwd_E1,
1664 z10_fwd_A1,
1665 z10_fwd_E1,
1666 z10_fwd_E1,
1667 *,
1668 *,
1669 z10_fwd_A1,
1670 z10_fwd_A3,
1671 z10_fr_E1,
1672 z10_fwd_A3,
1673 z10_rec,
1674 *,
1675 *,
1676 *,
1677 *,
1678 *,
1679 z10_rec,
1680 z10_super,
1681 *,
1682 *,
1683 *,
1684 *,*,*,*,*,*,*")
1685 ])
1686
1687 (define_split
1688 [(set (match_operand:DI 0 "register_operand" "")
1689 (match_operand:DI 1 "register_operand" ""))]
1690 "TARGET_ZARCH && ACCESS_REG_P (operands[1])"
1691 [(set (match_dup 2) (match_dup 3))
1692 (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
1693 (set (strict_low_part (match_dup 2)) (match_dup 4))]
1694 "operands[2] = gen_lowpart (SImode, operands[0]);
1695 s390_split_access_reg (operands[1], &operands[4], &operands[3]);")
1696
1697 (define_split
1698 [(set (match_operand:DI 0 "register_operand" "")
1699 (match_operand:DI 1 "register_operand" ""))]
1700 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1701 && dead_or_set_p (insn, operands[1])"
1702 [(set (match_dup 3) (match_dup 2))
1703 (set (match_dup 1) (lshiftrt:DI (match_dup 1) (const_int 32)))
1704 (set (match_dup 4) (match_dup 2))]
1705 "operands[2] = gen_lowpart (SImode, operands[1]);
1706 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1707
1708 (define_split
1709 [(set (match_operand:DI 0 "register_operand" "")
1710 (match_operand:DI 1 "register_operand" ""))]
1711 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1712 && !dead_or_set_p (insn, operands[1])"
1713 [(set (match_dup 3) (match_dup 2))
1714 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))
1715 (set (match_dup 4) (match_dup 2))
1716 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))]
1717 "operands[2] = gen_lowpart (SImode, operands[1]);
1718 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1719
1720 (define_insn "*movdi_31"
1721 [(set (match_operand:DI 0 "nonimmediate_operand"
1722 "=d,d,Q,S,d ,o,!*f,!*f,!*f,!R,!T,d")
1723 (match_operand:DI 1 "general_operand"
1724 " Q,S,d,d,dPRT,d, *f, R, T,*f,*f,b"))]
1725 "!TARGET_ZARCH"
1726 "@
1727 lm\t%0,%N0,%S1
1728 lmy\t%0,%N0,%S1
1729 stm\t%1,%N1,%S0
1730 stmy\t%1,%N1,%S0
1731 #
1732 #
1733 ldr\t%0,%1
1734 ld\t%0,%1
1735 ldy\t%0,%1
1736 std\t%1,%0
1737 stdy\t%1,%0
1738 #"
1739 [(set_attr "op_type" "RS,RSY,RS,RSY,*,*,RR,RX,RXY,RX,RXY,*")
1740 (set_attr "type" "lm,lm,stm,stm,*,*,floaddf,floaddf,floaddf,fstoredf,fstoredf,*")
1741 (set_attr "cpu_facility" "*,*,*,*,*,*,*,*,*,*,*,z10")])
1742
1743 ; For a load from a symbol ref we can use one of the target registers
1744 ; together with larl to load the address.
1745 (define_split
1746 [(set (match_operand:DI 0 "register_operand" "")
1747 (match_operand:DI 1 "memory_operand" ""))]
1748 "!TARGET_ZARCH && reload_completed && TARGET_Z10
1749 && larl_operand (XEXP (operands[1], 0), SImode)"
1750 [(set (match_dup 2) (match_dup 3))
1751 (set (match_dup 0) (match_dup 1))]
1752 {
1753 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1754 operands[3] = XEXP (operands[1], 0);
1755 operands[1] = replace_equiv_address (operands[1], operands[2]);
1756 })
1757
1758 (define_split
1759 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1760 (match_operand:DI 1 "general_operand" ""))]
1761 "!TARGET_ZARCH && reload_completed
1762 && s390_split_ok_p (operands[0], operands[1], DImode, 0)"
1763 [(set (match_dup 2) (match_dup 4))
1764 (set (match_dup 3) (match_dup 5))]
1765 {
1766 operands[2] = operand_subword (operands[0], 0, 0, DImode);
1767 operands[3] = operand_subword (operands[0], 1, 0, DImode);
1768 operands[4] = operand_subword (operands[1], 0, 0, DImode);
1769 operands[5] = operand_subword (operands[1], 1, 0, DImode);
1770 })
1771
1772 (define_split
1773 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1774 (match_operand:DI 1 "general_operand" ""))]
1775 "!TARGET_ZARCH && reload_completed
1776 && s390_split_ok_p (operands[0], operands[1], DImode, 1)"
1777 [(set (match_dup 2) (match_dup 4))
1778 (set (match_dup 3) (match_dup 5))]
1779 {
1780 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1781 operands[3] = operand_subword (operands[0], 0, 0, DImode);
1782 operands[4] = operand_subword (operands[1], 1, 0, DImode);
1783 operands[5] = operand_subword (operands[1], 0, 0, DImode);
1784 })
1785
1786 (define_split
1787 [(set (match_operand:DI 0 "register_operand" "")
1788 (match_operand:DI 1 "memory_operand" ""))]
1789 "!TARGET_ZARCH && reload_completed
1790 && !FP_REG_P (operands[0])
1791 && !s_operand (operands[1], VOIDmode)"
1792 [(set (match_dup 0) (match_dup 1))]
1793 {
1794 rtx addr = operand_subword (operands[0], 1, 0, DImode);
1795 s390_load_address (addr, XEXP (operands[1], 0));
1796 operands[1] = replace_equiv_address (operands[1], addr);
1797 })
1798
1799 (define_peephole2
1800 [(set (match_operand:DI 0 "register_operand" "")
1801 (mem:DI (match_operand 1 "address_operand" "")))]
1802 "TARGET_ZARCH
1803 && !FP_REG_P (operands[0])
1804 && GET_CODE (operands[1]) == SYMBOL_REF
1805 && CONSTANT_POOL_ADDRESS_P (operands[1])
1806 && get_pool_mode (operands[1]) == DImode
1807 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1808 [(set (match_dup 0) (match_dup 2))]
1809 "operands[2] = get_pool_constant (operands[1]);")
1810
1811 (define_insn "*la_64"
1812 [(set (match_operand:DI 0 "register_operand" "=d,d")
1813 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))]
1814 "TARGET_64BIT"
1815 "@
1816 la\t%0,%a1
1817 lay\t%0,%a1"
1818 [(set_attr "op_type" "RX,RXY")
1819 (set_attr "type" "la")
1820 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
1821
1822 (define_peephole2
1823 [(parallel
1824 [(set (match_operand:DI 0 "register_operand" "")
1825 (match_operand:QI 1 "address_operand" ""))
1826 (clobber (reg:CC CC_REGNUM))])]
1827 "TARGET_64BIT
1828 && preferred_la_operand_p (operands[1], const0_rtx)"
1829 [(set (match_dup 0) (match_dup 1))]
1830 "")
1831
1832 (define_peephole2
1833 [(set (match_operand:DI 0 "register_operand" "")
1834 (match_operand:DI 1 "register_operand" ""))
1835 (parallel
1836 [(set (match_dup 0)
1837 (plus:DI (match_dup 0)
1838 (match_operand:DI 2 "nonmemory_operand" "")))
1839 (clobber (reg:CC CC_REGNUM))])]
1840 "TARGET_64BIT
1841 && !reg_overlap_mentioned_p (operands[0], operands[2])
1842 && preferred_la_operand_p (operands[1], operands[2])"
1843 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
1844 "")
1845
1846 ;
1847 ; movsi instruction pattern(s).
1848 ;
1849
1850 (define_expand "movsi"
1851 [(set (match_operand:SI 0 "general_operand" "")
1852 (match_operand:SI 1 "general_operand" ""))]
1853 ""
1854 {
1855 /* Handle symbolic constants. */
1856 if (!TARGET_64BIT
1857 && (SYMBOLIC_CONST (operands[1])
1858 || (GET_CODE (operands[1]) == PLUS
1859 && XEXP (operands[1], 0) == pic_offset_table_rtx
1860 && SYMBOLIC_CONST (XEXP(operands[1], 1)))))
1861 emit_symbolic_move (operands);
1862 })
1863
1864 (define_insn "*movsi_larl"
1865 [(set (match_operand:SI 0 "register_operand" "=d")
1866 (match_operand:SI 1 "larl_operand" "X"))]
1867 "!TARGET_64BIT && TARGET_CPU_ZARCH
1868 && !FP_REG_P (operands[0])"
1869 "larl\t%0,%1"
1870 [(set_attr "op_type" "RIL")
1871 (set_attr "type" "larl")
1872 (set_attr "z10prop" "z10_fwd_A1")])
1873
1874 (define_insn "*movsi_zarch"
1875 [(set (match_operand:SI 0 "nonimmediate_operand"
1876 "=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,QR")
1877 (match_operand:SI 1 "general_operand"
1878 " 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,QR, v"))]
1879 "TARGET_ZARCH"
1880 "@
1881 lhi\t%0,%h1
1882 llilh\t%0,%i1
1883 llill\t%0,%i1
1884 iilf\t%0,%o1
1885 lay\t%0,%a1
1886 lrl\t%0,%1
1887 lr\t%0,%1
1888 l\t%0,%1
1889 ly\t%0,%1
1890 st\t%1,%0
1891 sty\t%1,%0
1892 lder\t%0,%1
1893 ler\t%0,%1
1894 lde\t%0,%1
1895 le\t%0,%1
1896 ley\t%0,%1
1897 ste\t%1,%0
1898 stey\t%1,%0
1899 ear\t%0,%1
1900 sar\t%0,%1
1901 stam\t%1,%1,%S0
1902 strl\t%1,%0
1903 mvhi\t%0,%1
1904 lam\t%0,%0,%S1
1905 vleif\t%v0,%h1,0
1906 vlr\t%v0,%v1
1907 vlvgf\t%v0,%1,0
1908 vlgvf\t%0,%v1,0
1909 vlef\t%v0,%1,0
1910 vstef\t%v1,%0,0"
1911 [(set_attr "op_type" "RI,RI,RI,RIL,RXY,RIL,RR,RX,RXY,RX,RXY,
1912 RRE,RR,RXE,RX,RXY,RX,RXY,RRE,RRE,RS,RIL,SIL,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1913 (set_attr "type" "*,
1914 *,
1915 *,
1916 *,
1917 la,
1918 larl,
1919 lr,
1920 load,
1921 load,
1922 store,
1923 store,
1924 floadsf,
1925 floadsf,
1926 floadsf,
1927 floadsf,
1928 floadsf,
1929 fstoresf,
1930 fstoresf,
1931 *,
1932 *,
1933 *,
1934 larl,
1935 *,
1936 *,*,*,*,*,*,*")
1937 (set_attr "cpu_facility" "*,*,*,extimm,longdisp,z10,*,*,longdisp,*,longdisp,
1938 vec,*,vec,*,longdisp,*,longdisp,*,*,*,z10,z10,*,vec,vec,vec,vec,vec,vec")
1939 (set_attr "z10prop" "z10_fwd_A1,
1940 z10_fwd_E1,
1941 z10_fwd_E1,
1942 z10_fwd_A1,
1943 z10_fwd_A1,
1944 z10_fwd_A3,
1945 z10_fr_E1,
1946 z10_fwd_A3,
1947 z10_fwd_A3,
1948 z10_rec,
1949 z10_rec,
1950 *,
1951 *,
1952 *,
1953 *,
1954 *,
1955 *,
1956 *,
1957 z10_super_E1,
1958 z10_super,
1959 *,
1960 z10_rec,
1961 z10_super,
1962 *,*,*,*,*,*,*")])
1963
1964 (define_insn "*movsi_esa"
1965 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,R,!*f,!*f,!*f,!*f,!R,d,t,Q,t")
1966 (match_operand:SI 1 "general_operand" "K,d,R,d, *f, *f, R, R,*f,t,d,t,Q"))]
1967 "!TARGET_ZARCH"
1968 "@
1969 lhi\t%0,%h1
1970 lr\t%0,%1
1971 l\t%0,%1
1972 st\t%1,%0
1973 lder\t%0,%1
1974 ler\t%0,%1
1975 lde\t%0,%1
1976 le\t%0,%1
1977 ste\t%1,%0
1978 ear\t%0,%1
1979 sar\t%0,%1
1980 stam\t%1,%1,%S0
1981 lam\t%0,%0,%S1"
1982 [(set_attr "op_type" "RI,RR,RX,RX,RRE,RR,RXE,RX,RX,RRE,RRE,RS,RS")
1983 (set_attr "type" "*,lr,load,store,floadsf,floadsf,floadsf,floadsf,fstoresf,*,*,*,*")
1984 (set_attr "z10prop" "z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_rec,*,*,*,*,*,z10_super_E1,
1985 z10_super,*,*")
1986 (set_attr "cpu_facility" "*,*,*,*,vec,*,vec,*,*,*,*,*,*")
1987 ])
1988
1989 (define_peephole2
1990 [(set (match_operand:SI 0 "register_operand" "")
1991 (mem:SI (match_operand 1 "address_operand" "")))]
1992 "!FP_REG_P (operands[0])
1993 && GET_CODE (operands[1]) == SYMBOL_REF
1994 && CONSTANT_POOL_ADDRESS_P (operands[1])
1995 && get_pool_mode (operands[1]) == SImode
1996 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1997 [(set (match_dup 0) (match_dup 2))]
1998 "operands[2] = get_pool_constant (operands[1]);")
1999
2000 (define_insn "*la_31"
2001 [(set (match_operand:SI 0 "register_operand" "=d,d")
2002 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))]
2003 "!TARGET_64BIT && legitimate_la_operand_p (operands[1])"
2004 "@
2005 la\t%0,%a1
2006 lay\t%0,%a1"
2007 [(set_attr "op_type" "RX,RXY")
2008 (set_attr "type" "la")
2009 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2010
2011 (define_peephole2
2012 [(parallel
2013 [(set (match_operand:SI 0 "register_operand" "")
2014 (match_operand:QI 1 "address_operand" ""))
2015 (clobber (reg:CC CC_REGNUM))])]
2016 "!TARGET_64BIT
2017 && preferred_la_operand_p (operands[1], const0_rtx)"
2018 [(set (match_dup 0) (match_dup 1))]
2019 "")
2020
2021 (define_peephole2
2022 [(set (match_operand:SI 0 "register_operand" "")
2023 (match_operand:SI 1 "register_operand" ""))
2024 (parallel
2025 [(set (match_dup 0)
2026 (plus:SI (match_dup 0)
2027 (match_operand:SI 2 "nonmemory_operand" "")))
2028 (clobber (reg:CC CC_REGNUM))])]
2029 "!TARGET_64BIT
2030 && !reg_overlap_mentioned_p (operands[0], operands[2])
2031 && preferred_la_operand_p (operands[1], operands[2])"
2032 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2033 "")
2034
2035 (define_insn "*la_31_and"
2036 [(set (match_operand:SI 0 "register_operand" "=d,d")
2037 (and:SI (match_operand:QI 1 "address_operand" "ZQZR,ZSZT")
2038 (const_int 2147483647)))]
2039 "!TARGET_64BIT"
2040 "@
2041 la\t%0,%a1
2042 lay\t%0,%a1"
2043 [(set_attr "op_type" "RX,RXY")
2044 (set_attr "type" "la")
2045 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2046
2047 (define_insn_and_split "*la_31_and_cc"
2048 [(set (match_operand:SI 0 "register_operand" "=d")
2049 (and:SI (match_operand:QI 1 "address_operand" "p")
2050 (const_int 2147483647)))
2051 (clobber (reg:CC CC_REGNUM))]
2052 "!TARGET_64BIT"
2053 "#"
2054 "&& reload_completed"
2055 [(set (match_dup 0)
2056 (and:SI (match_dup 1) (const_int 2147483647)))]
2057 ""
2058 [(set_attr "op_type" "RX")
2059 (set_attr "type" "la")])
2060
2061 (define_insn "force_la_31"
2062 [(set (match_operand:SI 0 "register_operand" "=d,d")
2063 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))
2064 (use (const_int 0))]
2065 "!TARGET_64BIT"
2066 "@
2067 la\t%0,%a1
2068 lay\t%0,%a1"
2069 [(set_attr "op_type" "RX")
2070 (set_attr "type" "la")
2071 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2072
2073 ;
2074 ; movhi instruction pattern(s).
2075 ;
2076
2077 (define_expand "movhi"
2078 [(set (match_operand:HI 0 "nonimmediate_operand" "")
2079 (match_operand:HI 1 "general_operand" ""))]
2080 ""
2081 {
2082 /* Make it explicit that loading a register from memory
2083 always sign-extends (at least) to SImode. */
2084 if (optimize && can_create_pseudo_p ()
2085 && register_operand (operands[0], VOIDmode)
2086 && GET_CODE (operands[1]) == MEM)
2087 {
2088 rtx tmp = gen_reg_rtx (SImode);
2089 rtx ext = gen_rtx_SIGN_EXTEND (SImode, operands[1]);
2090 emit_insn (gen_rtx_SET (tmp, ext));
2091 operands[1] = gen_lowpart (HImode, tmp);
2092 }
2093 })
2094
2095 (define_insn "*movhi"
2096 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,d,R,T,b,Q,v,v,v,d, v,QR")
2097 (match_operand:HI 1 "general_operand" " d,n,R,T,b,d,d,d,K,K,v,d,v,QR, v"))]
2098 ""
2099 "@
2100 lr\t%0,%1
2101 lhi\t%0,%h1
2102 lh\t%0,%1
2103 lhy\t%0,%1
2104 lhrl\t%0,%1
2105 sth\t%1,%0
2106 sthy\t%1,%0
2107 sthrl\t%1,%0
2108 mvhhi\t%0,%1
2109 vleih\t%v0,%h1,0
2110 vlr\t%v0,%v1
2111 vlvgh\t%v0,%1,0
2112 vlgvh\t%0,%v1,0
2113 vleh\t%v0,%1,0
2114 vsteh\t%v1,%0,0"
2115 [(set_attr "op_type" "RR,RI,RX,RXY,RIL,RX,RXY,RIL,SIL,VRI,VRR,VRS,VRS,VRX,VRX")
2116 (set_attr "type" "lr,*,*,*,larl,store,store,store,*,*,*,*,*,*,*")
2117 (set_attr "cpu_facility" "*,*,*,*,z10,*,*,z10,z10,vec,vec,vec,vec,vec,vec")
2118 (set_attr "z10prop" "z10_fr_E1,
2119 z10_fwd_A1,
2120 z10_super_E1,
2121 z10_super_E1,
2122 z10_super_E1,
2123 z10_rec,
2124 z10_rec,
2125 z10_rec,
2126 z10_super,*,*,*,*,*,*")])
2127
2128 (define_peephole2
2129 [(set (match_operand:HI 0 "register_operand" "")
2130 (mem:HI (match_operand 1 "address_operand" "")))]
2131 "GET_CODE (operands[1]) == SYMBOL_REF
2132 && CONSTANT_POOL_ADDRESS_P (operands[1])
2133 && get_pool_mode (operands[1]) == HImode
2134 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2135 [(set (match_dup 0) (match_dup 2))]
2136 "operands[2] = get_pool_constant (operands[1]);")
2137
2138 ;
2139 ; movqi instruction pattern(s).
2140 ;
2141
2142 (define_expand "movqi"
2143 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2144 (match_operand:QI 1 "general_operand" ""))]
2145 ""
2146 {
2147 /* On z/Architecture, zero-extending from memory to register
2148 is just as fast as a QImode load. */
2149 if (TARGET_ZARCH && optimize && can_create_pseudo_p ()
2150 && register_operand (operands[0], VOIDmode)
2151 && GET_CODE (operands[1]) == MEM)
2152 {
2153 rtx tmp = gen_reg_rtx (DImode);
2154 rtx ext = gen_rtx_ZERO_EXTEND (DImode, operands[1]);
2155 emit_insn (gen_rtx_SET (tmp, ext));
2156 operands[1] = gen_lowpart (QImode, tmp);
2157 }
2158 })
2159
2160 (define_insn "*movqi"
2161 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,T,Q,S,?Q,v,v,v,d, v,QR")
2162 (match_operand:QI 1 "general_operand" " d,n,R,T,d,d,n,n,?Q,K,v,d,v,QR, v"))]
2163 ""
2164 "@
2165 lr\t%0,%1
2166 lhi\t%0,%b1
2167 ic\t%0,%1
2168 icy\t%0,%1
2169 stc\t%1,%0
2170 stcy\t%1,%0
2171 mvi\t%S0,%b1
2172 mviy\t%S0,%b1
2173 #
2174 vleib\t%v0,%b1,0
2175 vlr\t%v0,%v1
2176 vlvgb\t%v0,%1,0
2177 vlgvb\t%0,%v1,0
2178 vleb\t%v0,%1,0
2179 vsteb\t%v1,%0,0"
2180 [(set_attr "op_type" "RR,RI,RX,RXY,RX,RXY,SI,SIY,SS,VRI,VRR,VRS,VRS,VRX,VRX")
2181 (set_attr "type" "lr,*,*,*,store,store,store,store,*,*,*,*,*,*,*")
2182 (set_attr "cpu_facility" "*,*,*,*,*,*,*,*,*,vec,vec,vec,vec,vec,vec")
2183 (set_attr "z10prop" "z10_fr_E1,
2184 z10_fwd_A1,
2185 z10_super_E1,
2186 z10_super_E1,
2187 z10_rec,
2188 z10_rec,
2189 z10_super,
2190 z10_super,
2191 *,*,*,*,*,*,*")])
2192
2193 (define_peephole2
2194 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2195 (mem:QI (match_operand 1 "address_operand" "")))]
2196 "GET_CODE (operands[1]) == SYMBOL_REF
2197 && CONSTANT_POOL_ADDRESS_P (operands[1])
2198 && get_pool_mode (operands[1]) == QImode
2199 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2200 [(set (match_dup 0) (match_dup 2))]
2201 "operands[2] = get_pool_constant (operands[1]);")
2202
2203 ;
2204 ; movstrictqi instruction pattern(s).
2205 ;
2206
2207 (define_insn "*movstrictqi"
2208 [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d,d"))
2209 (match_operand:QI 1 "memory_operand" "R,T"))]
2210 ""
2211 "@
2212 ic\t%0,%1
2213 icy\t%0,%1"
2214 [(set_attr "op_type" "RX,RXY")
2215 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2216
2217 ;
2218 ; movstricthi instruction pattern(s).
2219 ;
2220
2221 (define_insn "*movstricthi"
2222 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d,d"))
2223 (match_operand:HI 1 "memory_operand" "Q,S"))
2224 (clobber (reg:CC CC_REGNUM))]
2225 ""
2226 "@
2227 icm\t%0,3,%S1
2228 icmy\t%0,3,%S1"
2229 [(set_attr "op_type" "RS,RSY")
2230 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2231
2232 ;
2233 ; movstrictsi instruction pattern(s).
2234 ;
2235
2236 (define_insn "movstrictsi"
2237 [(set (strict_low_part (match_operand:SI 0 "register_operand" "+d,d,d,d"))
2238 (match_operand:SI 1 "general_operand" "d,R,T,t"))]
2239 "TARGET_ZARCH"
2240 "@
2241 lr\t%0,%1
2242 l\t%0,%1
2243 ly\t%0,%1
2244 ear\t%0,%1"
2245 [(set_attr "op_type" "RR,RX,RXY,RRE")
2246 (set_attr "type" "lr,load,load,*")
2247 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_super_E1")])
2248
2249 ;
2250 ; mov(tf|td) instruction pattern(s).
2251 ;
2252
2253 (define_expand "mov<mode>"
2254 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2255 (match_operand:TD_TF 1 "general_operand" ""))]
2256 ""
2257 "")
2258
2259 (define_insn "*mov<mode>_64"
2260 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o, d,QS, d,o")
2261 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,QS, d,dRT,d"))]
2262 "TARGET_ZARCH"
2263 "@
2264 lzxr\t%0
2265 lxr\t%0,%1
2266 #
2267 #
2268 lmg\t%0,%N0,%S1
2269 stmg\t%1,%N1,%S0
2270 #
2271 #"
2272 [(set_attr "op_type" "RRE,RRE,*,*,RSY,RSY,*,*")
2273 (set_attr "type" "fsimptf,fsimptf,*,*,lm,stm,*,*")
2274 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*")])
2275
2276 (define_insn "*mov<mode>_31"
2277 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o")
2278 (match_operand:TD_TF 1 "general_operand" " G,f,o,f"))]
2279 "!TARGET_ZARCH"
2280 "@
2281 lzxr\t%0
2282 lxr\t%0,%1
2283 #
2284 #"
2285 [(set_attr "op_type" "RRE,RRE,*,*")
2286 (set_attr "type" "fsimptf,fsimptf,*,*")
2287 (set_attr "cpu_facility" "z196,*,*,*")])
2288
2289 ; TFmode in GPRs splitters
2290
2291 (define_split
2292 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2293 (match_operand:TD_TF 1 "general_operand" ""))]
2294 "TARGET_ZARCH && reload_completed
2295 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2296 [(set (match_dup 2) (match_dup 4))
2297 (set (match_dup 3) (match_dup 5))]
2298 {
2299 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2300 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2301 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2302 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2303 })
2304
2305 (define_split
2306 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2307 (match_operand:TD_TF 1 "general_operand" ""))]
2308 "TARGET_ZARCH && reload_completed
2309 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2310 [(set (match_dup 2) (match_dup 4))
2311 (set (match_dup 3) (match_dup 5))]
2312 {
2313 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2314 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2315 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2316 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2317 })
2318
2319 (define_split
2320 [(set (match_operand:TD_TF 0 "register_operand" "")
2321 (match_operand:TD_TF 1 "memory_operand" ""))]
2322 "TARGET_ZARCH && reload_completed
2323 && GENERAL_REG_P (operands[0])
2324 && !s_operand (operands[1], VOIDmode)"
2325 [(set (match_dup 0) (match_dup 1))]
2326 {
2327 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2328 addr = gen_lowpart (Pmode, addr);
2329 s390_load_address (addr, XEXP (operands[1], 0));
2330 operands[1] = replace_equiv_address (operands[1], addr);
2331 })
2332
2333 ; TFmode in BFPs splitters
2334
2335 (define_split
2336 [(set (match_operand:TD_TF 0 "register_operand" "")
2337 (match_operand:TD_TF 1 "memory_operand" ""))]
2338 "reload_completed && offsettable_memref_p (operands[1])
2339 && FP_REG_P (operands[0])"
2340 [(set (match_dup 2) (match_dup 4))
2341 (set (match_dup 3) (match_dup 5))]
2342 {
2343 operands[2] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2344 <MODE>mode, 0);
2345 operands[3] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2346 <MODE>mode, 8);
2347 operands[4] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 0);
2348 operands[5] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 8);
2349 })
2350
2351 (define_split
2352 [(set (match_operand:TD_TF 0 "memory_operand" "")
2353 (match_operand:TD_TF 1 "register_operand" ""))]
2354 "reload_completed && offsettable_memref_p (operands[0])
2355 && FP_REG_P (operands[1])"
2356 [(set (match_dup 2) (match_dup 4))
2357 (set (match_dup 3) (match_dup 5))]
2358 {
2359 operands[2] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 0);
2360 operands[3] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 8);
2361 operands[4] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2362 <MODE>mode, 0);
2363 operands[5] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2364 <MODE>mode, 8);
2365 })
2366
2367 ;
2368 ; mov(df|dd) instruction pattern(s).
2369 ;
2370
2371 (define_expand "mov<mode>"
2372 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2373 (match_operand:DD_DF 1 "general_operand" ""))]
2374 ""
2375 "")
2376
2377 (define_insn "*mov<mode>_64dfp"
2378 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2379 "=f,f,f,d,f,f,R,T,d,d,d, d,b,RT,v,v,d,v,QR")
2380 (match_operand:DD_DF 1 "general_operand"
2381 " G,f,d,f,R,T,f,f,G,d,b,RT,d, d,v,d,v,QR,v"))]
2382 "TARGET_DFP"
2383 "@
2384 lzdr\t%0
2385 ldr\t%0,%1
2386 ldgr\t%0,%1
2387 lgdr\t%0,%1
2388 ld\t%0,%1
2389 ldy\t%0,%1
2390 std\t%1,%0
2391 stdy\t%1,%0
2392 lghi\t%0,0
2393 lgr\t%0,%1
2394 lgrl\t%0,%1
2395 lg\t%0,%1
2396 stgrl\t%1,%0
2397 stg\t%1,%0
2398 vlr\t%v0,%v1
2399 vlvgg\t%v0,%1,0
2400 vlgvg\t%0,%v1,0
2401 vleg\t%0,%1,0
2402 vsteg\t%1,%0,0"
2403 [(set_attr "op_type" "RRE,RR,RRE,RRE,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRS,VRS,VRX,VRX")
2404 (set_attr "type" "fsimpdf,floaddf,floaddf,floaddf,floaddf,floaddf,
2405 fstoredf,fstoredf,*,lr,load,load,store,store,*,*,*,load,store")
2406 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*,*,*")
2407 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,*,*,z10,*,z10,*,vec,vec,vec,vec,vec")])
2408
2409 (define_insn "*mov<mode>_64"
2410 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "=f,f,f,f,R,T,d,d,d, d,b,RT,v,v,QR")
2411 (match_operand:DD_DF 1 "general_operand" " G,f,R,T,f,f,G,d,b,RT,d, d,v,QR,v"))]
2412 "TARGET_ZARCH"
2413 "@
2414 lzdr\t%0
2415 ldr\t%0,%1
2416 ld\t%0,%1
2417 ldy\t%0,%1
2418 std\t%1,%0
2419 stdy\t%1,%0
2420 lghi\t%0,0
2421 lgr\t%0,%1
2422 lgrl\t%0,%1
2423 lg\t%0,%1
2424 stgrl\t%1,%0
2425 stg\t%1,%0
2426 vlr\t%v0,%v1
2427 vleg\t%v0,%1,0
2428 vsteg\t%v1,%0,0"
2429 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRX,VRX")
2430 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2431 fstore<mode>,fstore<mode>,*,lr,load,load,store,store,*,load,store")
2432 (set_attr "z10prop" "*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*")
2433 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,z10,*,z10,*,vec,vec,vec")])
2434
2435 (define_insn "*mov<mode>_31"
2436 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2437 "=f,f,f,f,R,T,d,d,Q,S, d,o")
2438 (match_operand:DD_DF 1 "general_operand"
2439 " G,f,R,T,f,f,Q,S,d,d,dPRT,d"))]
2440 "!TARGET_ZARCH"
2441 "@
2442 lzdr\t%0
2443 ldr\t%0,%1
2444 ld\t%0,%1
2445 ldy\t%0,%1
2446 std\t%1,%0
2447 stdy\t%1,%0
2448 lm\t%0,%N0,%S1
2449 lmy\t%0,%N0,%S1
2450 stm\t%1,%N1,%S0
2451 stmy\t%1,%N1,%S0
2452 #
2453 #"
2454 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RS,RSY,RS,RSY,*,*")
2455 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2456 fstore<mode>,fstore<mode>,lm,lm,stm,stm,*,*")
2457 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,*,*,*,*")])
2458
2459 (define_split
2460 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2461 (match_operand:DD_DF 1 "general_operand" ""))]
2462 "!TARGET_ZARCH && reload_completed
2463 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2464 [(set (match_dup 2) (match_dup 4))
2465 (set (match_dup 3) (match_dup 5))]
2466 {
2467 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2468 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2469 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2470 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2471 })
2472
2473 (define_split
2474 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2475 (match_operand:DD_DF 1 "general_operand" ""))]
2476 "!TARGET_ZARCH && reload_completed
2477 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2478 [(set (match_dup 2) (match_dup 4))
2479 (set (match_dup 3) (match_dup 5))]
2480 {
2481 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2482 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2483 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2484 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2485 })
2486
2487 (define_split
2488 [(set (match_operand:DD_DF 0 "register_operand" "")
2489 (match_operand:DD_DF 1 "memory_operand" ""))]
2490 "!TARGET_ZARCH && reload_completed
2491 && !FP_REG_P (operands[0])
2492 && !s_operand (operands[1], VOIDmode)"
2493 [(set (match_dup 0) (match_dup 1))]
2494 {
2495 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2496 s390_load_address (addr, XEXP (operands[1], 0));
2497 operands[1] = replace_equiv_address (operands[1], addr);
2498 })
2499
2500 ;
2501 ; mov(sf|sd) instruction pattern(s).
2502 ;
2503
2504 (define_insn "mov<mode>"
2505 [(set (match_operand:SD_SF 0 "nonimmediate_operand"
2506 "=f,f,f,f,f,f,R,T,d,d,d,d,d,b,R,T,v,v,v,d,v,QR")
2507 (match_operand:SD_SF 1 "general_operand"
2508 " G,f,f,R,R,T,f,f,G,d,b,R,T,d,d,d,v,G,d,v,QR,v"))]
2509 ""
2510 "@
2511 lzer\t%0
2512 lder\t%0,%1
2513 ler\t%0,%1
2514 lde\t%0,%1
2515 le\t%0,%1
2516 ley\t%0,%1
2517 ste\t%1,%0
2518 stey\t%1,%0
2519 lhi\t%0,0
2520 lr\t%0,%1
2521 lrl\t%0,%1
2522 l\t%0,%1
2523 ly\t%0,%1
2524 strl\t%1,%0
2525 st\t%1,%0
2526 sty\t%1,%0
2527 vlr\t%v0,%v1
2528 vleif\t%v0,0
2529 vlvgf\t%v0,%1,0
2530 vlgvf\t%0,%v1,0
2531 vleg\t%0,%1,0
2532 vsteg\t%1,%0,0"
2533 [(set_attr "op_type" "RRE,RRE,RR,RXE,RX,RXY,RX,RXY,RI,RR,RIL,RX,RXY,RIL,RX,RXY,VRR,VRI,VRS,VRS,VRX,VRX")
2534 (set_attr "type" "fsimpsf,fsimpsf,fload<mode>,fload<mode>,fload<mode>,fload<mode>,
2535 fstore<mode>,fstore<mode>,*,lr,load,load,load,store,store,store,*,*,*,*,load,store")
2536 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,z10_rec,*,*,*,*,*,*")
2537 (set_attr "cpu_facility" "z196,vec,*,vec,*,*,*,*,*,*,z10,*,*,z10,*,*,vec,vec,vec,vec,vec,vec")])
2538
2539 ;
2540 ; movcc instruction pattern
2541 ;
2542
2543 (define_insn "movcc"
2544 [(set (match_operand:CC 0 "nonimmediate_operand" "=d,c,d,d,d,R,T")
2545 (match_operand:CC 1 "nonimmediate_operand" " d,d,c,R,T,d,d"))]
2546 ""
2547 "@
2548 lr\t%0,%1
2549 tmh\t%1,12288
2550 ipm\t%0
2551 l\t%0,%1
2552 ly\t%0,%1
2553 st\t%1,%0
2554 sty\t%1,%0"
2555 [(set_attr "op_type" "RR,RI,RRE,RX,RXY,RX,RXY")
2556 (set_attr "type" "lr,*,*,load,load,store,store")
2557 (set_attr "z10prop" "z10_fr_E1,z10_super,*,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec")
2558 (set_attr "z196prop" "*,*,z196_ends,*,*,*,*")])
2559
2560 ;
2561 ; Block move (MVC) patterns.
2562 ;
2563
2564 (define_insn "*mvc"
2565 [(set (match_operand:BLK 0 "memory_operand" "=Q")
2566 (match_operand:BLK 1 "memory_operand" "Q"))
2567 (use (match_operand 2 "const_int_operand" "n"))]
2568 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
2569 "mvc\t%O0(%2,%R0),%S1"
2570 [(set_attr "op_type" "SS")])
2571
2572 ; This splitter converts a QI to QI mode copy into a BLK mode copy in
2573 ; order to have it implemented with mvc.
2574
2575 (define_split
2576 [(set (match_operand:QI 0 "memory_operand" "")
2577 (match_operand:QI 1 "memory_operand" ""))]
2578 "reload_completed"
2579 [(parallel
2580 [(set (match_dup 0) (match_dup 1))
2581 (use (const_int 1))])]
2582 {
2583 operands[0] = adjust_address (operands[0], BLKmode, 0);
2584 operands[1] = adjust_address (operands[1], BLKmode, 0);
2585 })
2586
2587
2588 (define_peephole2
2589 [(parallel
2590 [(set (match_operand:BLK 0 "memory_operand" "")
2591 (match_operand:BLK 1 "memory_operand" ""))
2592 (use (match_operand 2 "const_int_operand" ""))])
2593 (parallel
2594 [(set (match_operand:BLK 3 "memory_operand" "")
2595 (match_operand:BLK 4 "memory_operand" ""))
2596 (use (match_operand 5 "const_int_operand" ""))])]
2597 "s390_offset_p (operands[0], operands[3], operands[2])
2598 && s390_offset_p (operands[1], operands[4], operands[2])
2599 && !s390_overlap_p (operands[0], operands[1],
2600 INTVAL (operands[2]) + INTVAL (operands[5]))
2601 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
2602 [(parallel
2603 [(set (match_dup 6) (match_dup 7))
2604 (use (match_dup 8))])]
2605 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
2606 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
2607 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
2608
2609
2610 ;
2611 ; load_multiple pattern(s).
2612 ;
2613 ; ??? Due to reload problems with replacing registers inside match_parallel
2614 ; we currently support load_multiple/store_multiple only after reload.
2615 ;
2616
2617 (define_expand "load_multiple"
2618 [(match_par_dup 3 [(set (match_operand 0 "" "")
2619 (match_operand 1 "" ""))
2620 (use (match_operand 2 "" ""))])]
2621 "reload_completed"
2622 {
2623 machine_mode mode;
2624 int regno;
2625 int count;
2626 rtx from;
2627 int i, off;
2628
2629 /* Support only loading a constant number of fixed-point registers from
2630 memory and only bother with this if more than two */
2631 if (GET_CODE (operands[2]) != CONST_INT
2632 || INTVAL (operands[2]) < 2
2633 || INTVAL (operands[2]) > 16
2634 || GET_CODE (operands[1]) != MEM
2635 || GET_CODE (operands[0]) != REG
2636 || REGNO (operands[0]) >= 16)
2637 FAIL;
2638
2639 count = INTVAL (operands[2]);
2640 regno = REGNO (operands[0]);
2641 mode = GET_MODE (operands[0]);
2642 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2643 FAIL;
2644
2645 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2646 if (!can_create_pseudo_p ())
2647 {
2648 if (GET_CODE (XEXP (operands[1], 0)) == REG)
2649 {
2650 from = XEXP (operands[1], 0);
2651 off = 0;
2652 }
2653 else if (GET_CODE (XEXP (operands[1], 0)) == PLUS
2654 && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == REG
2655 && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == CONST_INT)
2656 {
2657 from = XEXP (XEXP (operands[1], 0), 0);
2658 off = INTVAL (XEXP (XEXP (operands[1], 0), 1));
2659 }
2660 else
2661 FAIL;
2662 }
2663 else
2664 {
2665 from = force_reg (Pmode, XEXP (operands[1], 0));
2666 off = 0;
2667 }
2668
2669 for (i = 0; i < count; i++)
2670 XVECEXP (operands[3], 0, i)
2671 = gen_rtx_SET (gen_rtx_REG (mode, regno + i),
2672 change_address (operands[1], mode,
2673 plus_constant (Pmode, from,
2674 off + i * GET_MODE_SIZE (mode))));
2675 })
2676
2677 (define_insn "*load_multiple_di"
2678 [(match_parallel 0 "load_multiple_operation"
2679 [(set (match_operand:DI 1 "register_operand" "=r")
2680 (match_operand:DI 2 "s_operand" "QS"))])]
2681 "reload_completed && TARGET_ZARCH"
2682 {
2683 int words = XVECLEN (operands[0], 0);
2684 operands[0] = gen_rtx_REG (DImode, REGNO (operands[1]) + words - 1);
2685 return "lmg\t%1,%0,%S2";
2686 }
2687 [(set_attr "op_type" "RSY")
2688 (set_attr "type" "lm")])
2689
2690 (define_insn "*load_multiple_si"
2691 [(match_parallel 0 "load_multiple_operation"
2692 [(set (match_operand:SI 1 "register_operand" "=r,r")
2693 (match_operand:SI 2 "s_operand" "Q,S"))])]
2694 "reload_completed"
2695 {
2696 int words = XVECLEN (operands[0], 0);
2697 operands[0] = gen_rtx_REG (SImode, REGNO (operands[1]) + words - 1);
2698 return which_alternative == 0 ? "lm\t%1,%0,%S2" : "lmy\t%1,%0,%S2";
2699 }
2700 [(set_attr "op_type" "RS,RSY")
2701 (set_attr "type" "lm")])
2702
2703 ;
2704 ; store multiple pattern(s).
2705 ;
2706
2707 (define_expand "store_multiple"
2708 [(match_par_dup 3 [(set (match_operand 0 "" "")
2709 (match_operand 1 "" ""))
2710 (use (match_operand 2 "" ""))])]
2711 "reload_completed"
2712 {
2713 machine_mode mode;
2714 int regno;
2715 int count;
2716 rtx to;
2717 int i, off;
2718
2719 /* Support only storing a constant number of fixed-point registers to
2720 memory and only bother with this if more than two. */
2721 if (GET_CODE (operands[2]) != CONST_INT
2722 || INTVAL (operands[2]) < 2
2723 || INTVAL (operands[2]) > 16
2724 || GET_CODE (operands[0]) != MEM
2725 || GET_CODE (operands[1]) != REG
2726 || REGNO (operands[1]) >= 16)
2727 FAIL;
2728
2729 count = INTVAL (operands[2]);
2730 regno = REGNO (operands[1]);
2731 mode = GET_MODE (operands[1]);
2732 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2733 FAIL;
2734
2735 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2736
2737 if (!can_create_pseudo_p ())
2738 {
2739 if (GET_CODE (XEXP (operands[0], 0)) == REG)
2740 {
2741 to = XEXP (operands[0], 0);
2742 off = 0;
2743 }
2744 else if (GET_CODE (XEXP (operands[0], 0)) == PLUS
2745 && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
2746 && GET_CODE (XEXP (XEXP (operands[0], 0), 1)) == CONST_INT)
2747 {
2748 to = XEXP (XEXP (operands[0], 0), 0);
2749 off = INTVAL (XEXP (XEXP (operands[0], 0), 1));
2750 }
2751 else
2752 FAIL;
2753 }
2754 else
2755 {
2756 to = force_reg (Pmode, XEXP (operands[0], 0));
2757 off = 0;
2758 }
2759
2760 for (i = 0; i < count; i++)
2761 XVECEXP (operands[3], 0, i)
2762 = gen_rtx_SET (change_address (operands[0], mode,
2763 plus_constant (Pmode, to,
2764 off + i * GET_MODE_SIZE (mode))),
2765 gen_rtx_REG (mode, regno + i));
2766 })
2767
2768 (define_insn "*store_multiple_di"
2769 [(match_parallel 0 "store_multiple_operation"
2770 [(set (match_operand:DI 1 "s_operand" "=QS")
2771 (match_operand:DI 2 "register_operand" "r"))])]
2772 "reload_completed && TARGET_ZARCH"
2773 {
2774 int words = XVECLEN (operands[0], 0);
2775 operands[0] = gen_rtx_REG (DImode, REGNO (operands[2]) + words - 1);
2776 return "stmg\t%2,%0,%S1";
2777 }
2778 [(set_attr "op_type" "RSY")
2779 (set_attr "type" "stm")])
2780
2781
2782 (define_insn "*store_multiple_si"
2783 [(match_parallel 0 "store_multiple_operation"
2784 [(set (match_operand:SI 1 "s_operand" "=Q,S")
2785 (match_operand:SI 2 "register_operand" "r,r"))])]
2786 "reload_completed"
2787 {
2788 int words = XVECLEN (operands[0], 0);
2789 operands[0] = gen_rtx_REG (SImode, REGNO (operands[2]) + words - 1);
2790 return which_alternative == 0 ? "stm\t%2,%0,%S1" : "stmy\t%2,%0,%S1";
2791 }
2792 [(set_attr "op_type" "RS,RSY")
2793 (set_attr "type" "stm")])
2794
2795 ;;
2796 ;; String instructions.
2797 ;;
2798
2799 (define_insn "*execute_rl"
2800 [(match_parallel 0 "execute_operation"
2801 [(unspec [(match_operand 1 "register_operand" "a")
2802 (match_operand 2 "" "")
2803 (match_operand:SI 3 "larl_operand" "X")] UNSPEC_EXECUTE)])]
2804 "TARGET_Z10 && GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2805 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2806 "exrl\t%1,%3"
2807 [(set_attr "op_type" "RIL")
2808 (set_attr "type" "cs")])
2809
2810 (define_insn "*execute"
2811 [(match_parallel 0 "execute_operation"
2812 [(unspec [(match_operand 1 "register_operand" "a")
2813 (match_operand:BLK 2 "memory_operand" "R")
2814 (match_operand 3 "" "")] UNSPEC_EXECUTE)])]
2815 "GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2816 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2817 "ex\t%1,%2"
2818 [(set_attr "op_type" "RX")
2819 (set_attr "type" "cs")])
2820
2821
2822 ;
2823 ; strlenM instruction pattern(s).
2824 ;
2825
2826 (define_expand "strlen<mode>"
2827 [(match_operand:P 0 "register_operand" "") ; result
2828 (match_operand:BLK 1 "memory_operand" "") ; input string
2829 (match_operand:SI 2 "immediate_operand" "") ; search character
2830 (match_operand:SI 3 "immediate_operand" "")] ; known alignment
2831 ""
2832 {
2833 if (!TARGET_VX || operands[2] != const0_rtx)
2834 emit_insn (gen_strlen_srst<mode> (operands[0], operands[1],
2835 operands[2], operands[3]));
2836 else
2837 s390_expand_vec_strlen (operands[0], operands[1], operands[3]);
2838
2839 DONE;
2840 })
2841
2842 (define_expand "strlen_srst<mode>"
2843 [(set (reg:SI 0) (match_operand:SI 2 "immediate_operand" ""))
2844 (parallel
2845 [(set (match_dup 4)
2846 (unspec:P [(const_int 0)
2847 (match_operand:BLK 1 "memory_operand" "")
2848 (reg:SI 0)
2849 (match_operand 3 "immediate_operand" "")] UNSPEC_SRST))
2850 (clobber (scratch:P))
2851 (clobber (reg:CC CC_REGNUM))])
2852 (parallel
2853 [(set (match_operand:P 0 "register_operand" "")
2854 (minus:P (match_dup 4) (match_dup 5)))
2855 (clobber (reg:CC CC_REGNUM))])]
2856 ""
2857 {
2858 operands[4] = gen_reg_rtx (Pmode);
2859 operands[5] = gen_reg_rtx (Pmode);
2860 emit_move_insn (operands[5], force_operand (XEXP (operands[1], 0), NULL_RTX));
2861 operands[1] = replace_equiv_address (operands[1], operands[5]);
2862 })
2863
2864 (define_insn "*strlen<mode>"
2865 [(set (match_operand:P 0 "register_operand" "=a")
2866 (unspec:P [(match_operand:P 2 "general_operand" "0")
2867 (mem:BLK (match_operand:P 3 "register_operand" "1"))
2868 (reg:SI 0)
2869 (match_operand 4 "immediate_operand" "")] UNSPEC_SRST))
2870 (clobber (match_scratch:P 1 "=a"))
2871 (clobber (reg:CC CC_REGNUM))]
2872 ""
2873 "srst\t%0,%1\;jo\t.-4"
2874 [(set_attr "length" "8")
2875 (set_attr "type" "vs")])
2876
2877 ;
2878 ; cmpstrM instruction pattern(s).
2879 ;
2880
2881 (define_expand "cmpstrsi"
2882 [(set (reg:SI 0) (const_int 0))
2883 (parallel
2884 [(clobber (match_operand 3 "" ""))
2885 (clobber (match_dup 4))
2886 (set (reg:CCU CC_REGNUM)
2887 (compare:CCU (match_operand:BLK 1 "memory_operand" "")
2888 (match_operand:BLK 2 "memory_operand" "")))
2889 (use (reg:SI 0))])
2890 (parallel
2891 [(set (match_operand:SI 0 "register_operand" "=d")
2892 (unspec:SI [(reg:CCU CC_REGNUM)] UNSPEC_STRCMPCC_TO_INT))
2893 (clobber (reg:CC CC_REGNUM))])]
2894 ""
2895 {
2896 /* As the result of CMPINT is inverted compared to what we need,
2897 we have to swap the operands. */
2898 rtx op1 = operands[2];
2899 rtx op2 = operands[1];
2900 rtx addr1 = gen_reg_rtx (Pmode);
2901 rtx addr2 = gen_reg_rtx (Pmode);
2902
2903 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
2904 emit_move_insn (addr2, force_operand (XEXP (op2, 0), NULL_RTX));
2905 operands[1] = replace_equiv_address_nv (op1, addr1);
2906 operands[2] = replace_equiv_address_nv (op2, addr2);
2907 operands[3] = addr1;
2908 operands[4] = addr2;
2909 })
2910
2911 (define_insn "*cmpstr<mode>"
2912 [(clobber (match_operand:P 0 "register_operand" "=d"))
2913 (clobber (match_operand:P 1 "register_operand" "=d"))
2914 (set (reg:CCU CC_REGNUM)
2915 (compare:CCU (mem:BLK (match_operand:P 2 "register_operand" "0"))
2916 (mem:BLK (match_operand:P 3 "register_operand" "1"))))
2917 (use (reg:SI 0))]
2918 ""
2919 "clst\t%0,%1\;jo\t.-4"
2920 [(set_attr "length" "8")
2921 (set_attr "type" "vs")])
2922
2923 ;
2924 ; movstr instruction pattern.
2925 ;
2926
2927 (define_expand "movstr"
2928 [(match_operand 0 "register_operand" "")
2929 (match_operand 1 "memory_operand" "")
2930 (match_operand 2 "memory_operand" "")]
2931 ""
2932 {
2933 if (TARGET_64BIT)
2934 emit_insn (gen_movstrdi (operands[0], operands[1], operands[2]));
2935 else
2936 emit_insn (gen_movstrsi (operands[0], operands[1], operands[2]));
2937 DONE;
2938 })
2939
2940 (define_expand "movstr<P:mode>"
2941 [(set (reg:SI 0) (const_int 0))
2942 (parallel
2943 [(clobber (match_dup 3))
2944 (set (match_operand:BLK 1 "memory_operand" "")
2945 (match_operand:BLK 2 "memory_operand" ""))
2946 (set (match_operand:P 0 "register_operand" "")
2947 (unspec:P [(match_dup 1)
2948 (match_dup 2)
2949 (reg:SI 0)] UNSPEC_MVST))
2950 (clobber (reg:CC CC_REGNUM))])]
2951 ""
2952 {
2953 rtx addr1 = gen_reg_rtx (Pmode);
2954 rtx addr2 = gen_reg_rtx (Pmode);
2955
2956 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
2957 emit_move_insn (addr2, force_operand (XEXP (operands[2], 0), NULL_RTX));
2958 operands[1] = replace_equiv_address_nv (operands[1], addr1);
2959 operands[2] = replace_equiv_address_nv (operands[2], addr2);
2960 operands[3] = addr2;
2961 })
2962
2963 (define_insn "*movstr"
2964 [(clobber (match_operand:P 2 "register_operand" "=d"))
2965 (set (mem:BLK (match_operand:P 1 "register_operand" "0"))
2966 (mem:BLK (match_operand:P 3 "register_operand" "2")))
2967 (set (match_operand:P 0 "register_operand" "=d")
2968 (unspec:P [(mem:BLK (match_dup 1))
2969 (mem:BLK (match_dup 3))
2970 (reg:SI 0)] UNSPEC_MVST))
2971 (clobber (reg:CC CC_REGNUM))]
2972 ""
2973 "mvst\t%1,%2\;jo\t.-4"
2974 [(set_attr "length" "8")
2975 (set_attr "type" "vs")])
2976
2977
2978 ;
2979 ; movmemM instruction pattern(s).
2980 ;
2981
2982 (define_expand "movmem<mode>"
2983 [(set (match_operand:BLK 0 "memory_operand" "") ; destination
2984 (match_operand:BLK 1 "memory_operand" "")) ; source
2985 (use (match_operand:GPR 2 "general_operand" "")) ; count
2986 (match_operand 3 "" "")]
2987 ""
2988 {
2989 if (s390_expand_movmem (operands[0], operands[1], operands[2]))
2990 DONE;
2991 else
2992 FAIL;
2993 })
2994
2995 ; Move a block that is up to 256 bytes in length.
2996 ; The block length is taken as (operands[2] % 256) + 1.
2997
2998 (define_expand "movmem_short"
2999 [(parallel
3000 [(set (match_operand:BLK 0 "memory_operand" "")
3001 (match_operand:BLK 1 "memory_operand" ""))
3002 (use (match_operand 2 "nonmemory_operand" ""))
3003 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3004 (clobber (match_dup 3))])]
3005 ""
3006 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3007
3008 (define_insn "*movmem_short"
3009 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3010 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q"))
3011 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3012 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3013 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3014 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3015 "#"
3016 [(set_attr "type" "cs")
3017 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3018
3019 (define_split
3020 [(set (match_operand:BLK 0 "memory_operand" "")
3021 (match_operand:BLK 1 "memory_operand" ""))
3022 (use (match_operand 2 "const_int_operand" ""))
3023 (use (match_operand 3 "immediate_operand" ""))
3024 (clobber (scratch))]
3025 "reload_completed"
3026 [(parallel
3027 [(set (match_dup 0) (match_dup 1))
3028 (use (match_dup 2))])]
3029 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3030
3031 (define_split
3032 [(set (match_operand:BLK 0 "memory_operand" "")
3033 (match_operand:BLK 1 "memory_operand" ""))
3034 (use (match_operand 2 "register_operand" ""))
3035 (use (match_operand 3 "memory_operand" ""))
3036 (clobber (scratch))]
3037 "reload_completed"
3038 [(parallel
3039 [(unspec [(match_dup 2) (match_dup 3)
3040 (const_int 0)] UNSPEC_EXECUTE)
3041 (set (match_dup 0) (match_dup 1))
3042 (use (const_int 1))])]
3043 "")
3044
3045 (define_split
3046 [(set (match_operand:BLK 0 "memory_operand" "")
3047 (match_operand:BLK 1 "memory_operand" ""))
3048 (use (match_operand 2 "register_operand" ""))
3049 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3050 (clobber (scratch))]
3051 "TARGET_Z10 && reload_completed"
3052 [(parallel
3053 [(unspec [(match_dup 2) (const_int 0)
3054 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3055 (set (match_dup 0) (match_dup 1))
3056 (use (const_int 1))])]
3057 "operands[3] = gen_label_rtx ();")
3058
3059 (define_split
3060 [(set (match_operand:BLK 0 "memory_operand" "")
3061 (match_operand:BLK 1 "memory_operand" ""))
3062 (use (match_operand 2 "register_operand" ""))
3063 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3064 (clobber (match_operand 3 "register_operand" ""))]
3065 "reload_completed && TARGET_CPU_ZARCH"
3066 [(set (match_dup 3) (label_ref (match_dup 4)))
3067 (parallel
3068 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3069 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3070 (set (match_dup 0) (match_dup 1))
3071 (use (const_int 1))])]
3072 "operands[4] = gen_label_rtx ();")
3073
3074 ; Move a block of arbitrary length.
3075
3076 (define_expand "movmem_long"
3077 [(parallel
3078 [(clobber (match_dup 2))
3079 (clobber (match_dup 3))
3080 (set (match_operand:BLK 0 "memory_operand" "")
3081 (match_operand:BLK 1 "memory_operand" ""))
3082 (use (match_operand 2 "general_operand" ""))
3083 (use (match_dup 3))
3084 (clobber (reg:CC CC_REGNUM))])]
3085 ""
3086 {
3087 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3088 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3089 rtx reg0 = gen_reg_rtx (dreg_mode);
3090 rtx reg1 = gen_reg_rtx (dreg_mode);
3091 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3092 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3093 rtx len0 = gen_lowpart (Pmode, reg0);
3094 rtx len1 = gen_lowpart (Pmode, reg1);
3095
3096 emit_clobber (reg0);
3097 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3098 emit_move_insn (len0, operands[2]);
3099
3100 emit_clobber (reg1);
3101 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3102 emit_move_insn (len1, operands[2]);
3103
3104 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3105 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3106 operands[2] = reg0;
3107 operands[3] = reg1;
3108 })
3109
3110 (define_insn "*movmem_long"
3111 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3112 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3113 (set (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3114 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0)))
3115 (use (match_dup 2))
3116 (use (match_dup 3))
3117 (clobber (reg:CC CC_REGNUM))]
3118 "TARGET_64BIT || !TARGET_ZARCH"
3119 "mvcle\t%0,%1,0\;jo\t.-4"
3120 [(set_attr "length" "8")
3121 (set_attr "type" "vs")])
3122
3123 (define_insn "*movmem_long_31z"
3124 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3125 (clobber (match_operand:TI 1 "register_operand" "=d"))
3126 (set (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3127 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4)))
3128 (use (match_dup 2))
3129 (use (match_dup 3))
3130 (clobber (reg:CC CC_REGNUM))]
3131 "!TARGET_64BIT && TARGET_ZARCH"
3132 "mvcle\t%0,%1,0\;jo\t.-4"
3133 [(set_attr "length" "8")
3134 (set_attr "type" "vs")])
3135
3136
3137 ;
3138 ; Test data class.
3139 ;
3140
3141 (define_expand "signbit<mode>2"
3142 [(set (reg:CCZ CC_REGNUM)
3143 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3144 (match_dup 2)]
3145 UNSPEC_TDC_INSN))
3146 (set (match_operand:SI 0 "register_operand" "=d")
3147 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3148 "TARGET_HARD_FLOAT"
3149 {
3150 operands[2] = GEN_INT (S390_TDC_SIGNBIT_SET);
3151 })
3152
3153 (define_expand "isinf<mode>2"
3154 [(set (reg:CCZ CC_REGNUM)
3155 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3156 (match_dup 2)]
3157 UNSPEC_TDC_INSN))
3158 (set (match_operand:SI 0 "register_operand" "=d")
3159 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3160 "TARGET_HARD_FLOAT"
3161 {
3162 operands[2] = GEN_INT (S390_TDC_INFINITY);
3163 })
3164
3165 ; This extracts CC into a GPR properly shifted. The actual IPM
3166 ; instruction will be issued by reload. The constraint of operand 1
3167 ; forces reload to use a GPR. So reload will issue a movcc insn for
3168 ; copying CC into a GPR first.
3169 (define_insn_and_split "*cc_to_int"
3170 [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3171 (unspec:SI [(match_operand 1 "register_operand" "0")]
3172 UNSPEC_CC_TO_INT))]
3173 "operands != NULL"
3174 "#"
3175 "reload_completed"
3176 [(set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 28)))])
3177
3178 ; This insn is used to generate all variants of the Test Data Class
3179 ; instruction, namely tcxb, tcdb, and tceb. The insn's first operand
3180 ; is the register to be tested and the second one is the bit mask
3181 ; specifying the required test(s).
3182 ;
3183 ; tcxb, tcdb, tceb, tdcxt, tdcdt, tdcet
3184 (define_insn "*TDC_insn_<mode>"
3185 [(set (reg:CCZ CC_REGNUM)
3186 (unspec:CCZ [(match_operand:FP_ALL 0 "register_operand" "f")
3187 (match_operand:SI 1 "const_int_operand")] UNSPEC_TDC_INSN))]
3188 "TARGET_HARD_FLOAT"
3189 "t<_d>c<xde><bt>\t%0,%1"
3190 [(set_attr "op_type" "RXE")
3191 (set_attr "type" "fsimp<mode>")])
3192
3193
3194
3195 ;
3196 ; setmemM instruction pattern(s).
3197 ;
3198
3199 (define_expand "setmem<mode>"
3200 [(set (match_operand:BLK 0 "memory_operand" "")
3201 (match_operand:QI 2 "general_operand" ""))
3202 (use (match_operand:GPR 1 "general_operand" ""))
3203 (match_operand 3 "" "")]
3204 ""
3205 "s390_expand_setmem (operands[0], operands[1], operands[2]); DONE;")
3206
3207 ; Clear a block that is up to 256 bytes in length.
3208 ; The block length is taken as (operands[1] % 256) + 1.
3209
3210 (define_expand "clrmem_short"
3211 [(parallel
3212 [(set (match_operand:BLK 0 "memory_operand" "")
3213 (const_int 0))
3214 (use (match_operand 1 "nonmemory_operand" ""))
3215 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3216 (clobber (match_dup 2))
3217 (clobber (reg:CC CC_REGNUM))])]
3218 ""
3219 "operands[2] = gen_rtx_SCRATCH (Pmode);")
3220
3221 (define_insn "*clrmem_short"
3222 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3223 (const_int 0))
3224 (use (match_operand 1 "nonmemory_operand" "n,a,a,a"))
3225 (use (match_operand 2 "immediate_operand" "X,R,X,X"))
3226 (clobber (match_scratch:P 3 "=X,X,X,&a"))
3227 (clobber (reg:CC CC_REGNUM))]
3228 "(GET_MODE (operands[1]) == Pmode || GET_MODE (operands[1]) == VOIDmode)"
3229 "#"
3230 [(set_attr "type" "cs")
3231 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3232
3233 (define_split
3234 [(set (match_operand:BLK 0 "memory_operand" "")
3235 (const_int 0))
3236 (use (match_operand 1 "const_int_operand" ""))
3237 (use (match_operand 2 "immediate_operand" ""))
3238 (clobber (scratch))
3239 (clobber (reg:CC CC_REGNUM))]
3240 "reload_completed"
3241 [(parallel
3242 [(set (match_dup 0) (const_int 0))
3243 (use (match_dup 1))
3244 (clobber (reg:CC CC_REGNUM))])]
3245 "operands[1] = GEN_INT ((INTVAL (operands[1]) & 0xff) + 1);")
3246
3247 (define_split
3248 [(set (match_operand:BLK 0 "memory_operand" "")
3249 (const_int 0))
3250 (use (match_operand 1 "register_operand" ""))
3251 (use (match_operand 2 "memory_operand" ""))
3252 (clobber (scratch))
3253 (clobber (reg:CC CC_REGNUM))]
3254 "reload_completed"
3255 [(parallel
3256 [(unspec [(match_dup 1) (match_dup 2)
3257 (const_int 0)] UNSPEC_EXECUTE)
3258 (set (match_dup 0) (const_int 0))
3259 (use (const_int 1))
3260 (clobber (reg:CC CC_REGNUM))])]
3261 "")
3262
3263 (define_split
3264 [(set (match_operand:BLK 0 "memory_operand" "")
3265 (const_int 0))
3266 (use (match_operand 1 "register_operand" ""))
3267 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3268 (clobber (scratch))
3269 (clobber (reg:CC CC_REGNUM))]
3270 "TARGET_Z10 && reload_completed"
3271 [(parallel
3272 [(unspec [(match_dup 1) (const_int 0)
3273 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3274 (set (match_dup 0) (const_int 0))
3275 (use (const_int 1))
3276 (clobber (reg:CC CC_REGNUM))])]
3277 "operands[3] = gen_label_rtx ();")
3278
3279 (define_split
3280 [(set (match_operand:BLK 0 "memory_operand" "")
3281 (const_int 0))
3282 (use (match_operand 1 "register_operand" ""))
3283 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3284 (clobber (match_operand 2 "register_operand" ""))
3285 (clobber (reg:CC CC_REGNUM))]
3286 "reload_completed && TARGET_CPU_ZARCH"
3287 [(set (match_dup 2) (label_ref (match_dup 3)))
3288 (parallel
3289 [(unspec [(match_dup 1) (mem:BLK (match_dup 2))
3290 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3291 (set (match_dup 0) (const_int 0))
3292 (use (const_int 1))
3293 (clobber (reg:CC CC_REGNUM))])]
3294 "operands[3] = gen_label_rtx ();")
3295
3296 ; Initialize a block of arbitrary length with (operands[2] % 256).
3297
3298 (define_expand "setmem_long_<P:mode>"
3299 [(parallel
3300 [(clobber (match_dup 1))
3301 (set (match_operand:BLK 0 "memory_operand" "")
3302 (unspec:BLK [(match_operand:P 2 "shift_count_or_setmem_operand" "")
3303 (match_dup 4)] UNSPEC_REPLICATE_BYTE))
3304 (use (match_dup 3))
3305 (clobber (reg:CC CC_REGNUM))])]
3306 ""
3307 {
3308 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3309 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3310 rtx reg0 = gen_reg_rtx (dreg_mode);
3311 rtx reg1 = gen_reg_rtx (dreg_mode);
3312 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3313 rtx len0 = gen_lowpart (Pmode, reg0);
3314
3315 emit_clobber (reg0);
3316 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3317 emit_move_insn (len0, operands[1]);
3318
3319 emit_move_insn (reg1, const0_rtx);
3320
3321 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3322 operands[1] = reg0;
3323 operands[3] = reg1;
3324 operands[4] = gen_lowpart (Pmode, operands[1]);
3325 })
3326
3327 ; Patterns for 31 bit + Esa and 64 bit + Zarch.
3328
3329 (define_insn "*setmem_long"
3330 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3331 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3332 (unspec:BLK [(match_operand:P 2 "shift_count_or_setmem_operand" "Y")
3333 (subreg:P (match_dup 3) <modesize>)]
3334 UNSPEC_REPLICATE_BYTE))
3335 (use (match_operand:<DBL> 1 "register_operand" "d"))
3336 (clobber (reg:CC CC_REGNUM))]
3337 "TARGET_64BIT || !TARGET_ZARCH"
3338 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3339 [(set_attr "length" "8")
3340 (set_attr "type" "vs")])
3341
3342 (define_insn "*setmem_long_and"
3343 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3344 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3345 (unspec:BLK [(and:P
3346 (match_operand:P 2 "shift_count_or_setmem_operand" "Y")
3347 (match_operand:P 4 "const_int_operand" "n"))
3348 (subreg:P (match_dup 3) <modesize>)]
3349 UNSPEC_REPLICATE_BYTE))
3350 (use (match_operand:<DBL> 1 "register_operand" "d"))
3351 (clobber (reg:CC CC_REGNUM))]
3352 "(TARGET_64BIT || !TARGET_ZARCH) &&
3353 (INTVAL (operands[4]) & 255) == 255"
3354 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3355 [(set_attr "length" "8")
3356 (set_attr "type" "vs")])
3357
3358 ; Variants for 31 bit + Zarch, necessary because of the odd in-register offsets
3359 ; of the SImode subregs.
3360
3361 (define_insn "*setmem_long_31z"
3362 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3363 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3364 (unspec:BLK [(match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
3365 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3366 (use (match_operand:TI 1 "register_operand" "d"))
3367 (clobber (reg:CC CC_REGNUM))]
3368 "!TARGET_64BIT && TARGET_ZARCH"
3369 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3370 [(set_attr "length" "8")
3371 (set_attr "type" "vs")])
3372
3373 (define_insn "*setmem_long_and_31z"
3374 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3375 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3376 (unspec:BLK [(and:SI
3377 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
3378 (match_operand:SI 4 "const_int_operand" "n"))
3379 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3380 (use (match_operand:TI 1 "register_operand" "d"))
3381 (clobber (reg:CC CC_REGNUM))]
3382 "(!TARGET_64BIT && TARGET_ZARCH) &&
3383 (INTVAL (operands[4]) & 255) == 255"
3384 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3385 [(set_attr "length" "8")
3386 (set_attr "type" "vs")])
3387
3388 ;
3389 ; cmpmemM instruction pattern(s).
3390 ;
3391
3392 (define_expand "cmpmemsi"
3393 [(set (match_operand:SI 0 "register_operand" "")
3394 (compare:SI (match_operand:BLK 1 "memory_operand" "")
3395 (match_operand:BLK 2 "memory_operand" "") ) )
3396 (use (match_operand:SI 3 "general_operand" ""))
3397 (use (match_operand:SI 4 "" ""))]
3398 ""
3399 {
3400 if (s390_expand_cmpmem (operands[0], operands[1],
3401 operands[2], operands[3]))
3402 DONE;
3403 else
3404 FAIL;
3405 })
3406
3407 ; Compare a block that is up to 256 bytes in length.
3408 ; The block length is taken as (operands[2] % 256) + 1.
3409
3410 (define_expand "cmpmem_short"
3411 [(parallel
3412 [(set (reg:CCU CC_REGNUM)
3413 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3414 (match_operand:BLK 1 "memory_operand" "")))
3415 (use (match_operand 2 "nonmemory_operand" ""))
3416 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3417 (clobber (match_dup 3))])]
3418 ""
3419 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3420
3421 (define_insn "*cmpmem_short"
3422 [(set (reg:CCU CC_REGNUM)
3423 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
3424 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
3425 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3426 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3427 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3428 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3429 "#"
3430 [(set_attr "type" "cs")
3431 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3432
3433 (define_split
3434 [(set (reg:CCU CC_REGNUM)
3435 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3436 (match_operand:BLK 1 "memory_operand" "")))
3437 (use (match_operand 2 "const_int_operand" ""))
3438 (use (match_operand 3 "immediate_operand" ""))
3439 (clobber (scratch))]
3440 "reload_completed"
3441 [(parallel
3442 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3443 (use (match_dup 2))])]
3444 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3445
3446 (define_split
3447 [(set (reg:CCU CC_REGNUM)
3448 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3449 (match_operand:BLK 1 "memory_operand" "")))
3450 (use (match_operand 2 "register_operand" ""))
3451 (use (match_operand 3 "memory_operand" ""))
3452 (clobber (scratch))]
3453 "reload_completed"
3454 [(parallel
3455 [(unspec [(match_dup 2) (match_dup 3)
3456 (const_int 0)] UNSPEC_EXECUTE)
3457 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3458 (use (const_int 1))])]
3459 "")
3460
3461 (define_split
3462 [(set (reg:CCU CC_REGNUM)
3463 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3464 (match_operand:BLK 1 "memory_operand" "")))
3465 (use (match_operand 2 "register_operand" ""))
3466 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3467 (clobber (scratch))]
3468 "TARGET_Z10 && reload_completed"
3469 [(parallel
3470 [(unspec [(match_dup 2) (const_int 0)
3471 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3472 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3473 (use (const_int 1))])]
3474 "operands[4] = gen_label_rtx ();")
3475
3476 (define_split
3477 [(set (reg:CCU CC_REGNUM)
3478 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3479 (match_operand:BLK 1 "memory_operand" "")))
3480 (use (match_operand 2 "register_operand" ""))
3481 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3482 (clobber (match_operand 3 "register_operand" ""))]
3483 "reload_completed && TARGET_CPU_ZARCH"
3484 [(set (match_dup 3) (label_ref (match_dup 4)))
3485 (parallel
3486 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3487 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3488 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3489 (use (const_int 1))])]
3490 "operands[4] = gen_label_rtx ();")
3491
3492 ; Compare a block of arbitrary length.
3493
3494 (define_expand "cmpmem_long"
3495 [(parallel
3496 [(clobber (match_dup 2))
3497 (clobber (match_dup 3))
3498 (set (reg:CCU CC_REGNUM)
3499 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3500 (match_operand:BLK 1 "memory_operand" "")))
3501 (use (match_operand 2 "general_operand" ""))
3502 (use (match_dup 3))])]
3503 ""
3504 {
3505 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3506 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3507 rtx reg0 = gen_reg_rtx (dreg_mode);
3508 rtx reg1 = gen_reg_rtx (dreg_mode);
3509 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3510 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3511 rtx len0 = gen_lowpart (Pmode, reg0);
3512 rtx len1 = gen_lowpart (Pmode, reg1);
3513
3514 emit_clobber (reg0);
3515 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3516 emit_move_insn (len0, operands[2]);
3517
3518 emit_clobber (reg1);
3519 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3520 emit_move_insn (len1, operands[2]);
3521
3522 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3523 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3524 operands[2] = reg0;
3525 operands[3] = reg1;
3526 })
3527
3528 (define_insn "*cmpmem_long"
3529 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3530 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3531 (set (reg:CCU CC_REGNUM)
3532 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3533 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
3534 (use (match_dup 2))
3535 (use (match_dup 3))]
3536 "TARGET_64BIT || !TARGET_ZARCH"
3537 "clcle\t%0,%1,0\;jo\t.-4"
3538 [(set_attr "length" "8")
3539 (set_attr "type" "vs")])
3540
3541 (define_insn "*cmpmem_long_31z"
3542 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3543 (clobber (match_operand:TI 1 "register_operand" "=d"))
3544 (set (reg:CCU CC_REGNUM)
3545 (compare:CCU (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3546 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4))))
3547 (use (match_dup 2))
3548 (use (match_dup 3))]
3549 "!TARGET_64BIT && TARGET_ZARCH"
3550 "clcle\t%0,%1,0\;jo\t.-4"
3551 [(set_attr "op_type" "NN")
3552 (set_attr "type" "vs")
3553 (set_attr "length" "8")])
3554
3555 ; Convert CCUmode condition code to integer.
3556 ; Result is zero if EQ, positive if LTU, negative if GTU.
3557
3558 (define_insn_and_split "cmpint"
3559 [(set (match_operand:SI 0 "register_operand" "=d")
3560 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3561 UNSPEC_STRCMPCC_TO_INT))
3562 (clobber (reg:CC CC_REGNUM))]
3563 ""
3564 "#"
3565 "reload_completed"
3566 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3567 (parallel
3568 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
3569 (clobber (reg:CC CC_REGNUM))])])
3570
3571 (define_insn_and_split "*cmpint_cc"
3572 [(set (reg CC_REGNUM)
3573 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3574 UNSPEC_STRCMPCC_TO_INT)
3575 (const_int 0)))
3576 (set (match_operand:SI 0 "register_operand" "=d")
3577 (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT))]
3578 "s390_match_ccmode (insn, CCSmode)"
3579 "#"
3580 "&& reload_completed"
3581 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3582 (parallel
3583 [(set (match_dup 2) (match_dup 3))
3584 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
3585 {
3586 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
3587 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3588 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3589 })
3590
3591 (define_insn_and_split "*cmpint_sign"
3592 [(set (match_operand:DI 0 "register_operand" "=d")
3593 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3594 UNSPEC_STRCMPCC_TO_INT)))
3595 (clobber (reg:CC CC_REGNUM))]
3596 "TARGET_ZARCH"
3597 "#"
3598 "&& reload_completed"
3599 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3600 (parallel
3601 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
3602 (clobber (reg:CC CC_REGNUM))])])
3603
3604 (define_insn_and_split "*cmpint_sign_cc"
3605 [(set (reg CC_REGNUM)
3606 (compare (ashiftrt:DI (ashift:DI (subreg:DI
3607 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3608 UNSPEC_STRCMPCC_TO_INT) 0)
3609 (const_int 32)) (const_int 32))
3610 (const_int 0)))
3611 (set (match_operand:DI 0 "register_operand" "=d")
3612 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT)))]
3613 "s390_match_ccmode (insn, CCSmode) && TARGET_ZARCH"
3614 "#"
3615 "&& reload_completed"
3616 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3617 (parallel
3618 [(set (match_dup 2) (match_dup 3))
3619 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
3620 {
3621 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
3622 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3623 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3624 })
3625
3626
3627 ;;
3628 ;;- Conversion instructions.
3629 ;;
3630
3631 (define_insn "*sethighpartsi"
3632 [(set (match_operand:SI 0 "register_operand" "=d,d")
3633 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
3634 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3635 (clobber (reg:CC CC_REGNUM))]
3636 ""
3637 "@
3638 icm\t%0,%2,%S1
3639 icmy\t%0,%2,%S1"
3640 [(set_attr "op_type" "RS,RSY")
3641 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3642
3643 (define_insn "*sethighpartdi_64"
3644 [(set (match_operand:DI 0 "register_operand" "=d")
3645 (unspec:DI [(match_operand:BLK 1 "s_operand" "QS")
3646 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
3647 (clobber (reg:CC CC_REGNUM))]
3648 "TARGET_ZARCH"
3649 "icmh\t%0,%2,%S1"
3650 [(set_attr "op_type" "RSY")
3651 (set_attr "z10prop" "z10_super")])
3652
3653 (define_insn "*sethighpartdi_31"
3654 [(set (match_operand:DI 0 "register_operand" "=d,d")
3655 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
3656 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3657 (clobber (reg:CC CC_REGNUM))]
3658 "!TARGET_ZARCH"
3659 "@
3660 icm\t%0,%2,%S1
3661 icmy\t%0,%2,%S1"
3662 [(set_attr "op_type" "RS,RSY")
3663 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3664
3665 ;
3666 ; extv instruction patterns
3667 ;
3668
3669 ; FIXME: This expander needs to be converted from DI to GPR as well
3670 ; after resolving some issues with it.
3671
3672 (define_expand "extzv"
3673 [(parallel
3674 [(set (match_operand:DI 0 "register_operand" "=d")
3675 (zero_extract:DI
3676 (match_operand:DI 1 "register_operand" "d")
3677 (match_operand 2 "const_int_operand" "") ; size
3678 (match_operand 3 "const_int_operand" ""))) ; start
3679 (clobber (reg:CC CC_REGNUM))])]
3680 "TARGET_Z10"
3681 {
3682 /* Starting with zEC12 there is risbgn not clobbering CC. */
3683 if (TARGET_ZEC12)
3684 {
3685 emit_move_insn (operands[0],
3686 gen_rtx_ZERO_EXTRACT (DImode,
3687 operands[1],
3688 operands[2],
3689 operands[3]));
3690 DONE;
3691 }
3692 })
3693
3694 (define_insn "*extzv<mode>_zEC12"
3695 [(set (match_operand:GPR 0 "register_operand" "=d")
3696 (zero_extract:GPR
3697 (match_operand:GPR 1 "register_operand" "d")
3698 (match_operand 2 "const_int_operand" "") ; size
3699 (match_operand 3 "const_int_operand" "")))] ; start]
3700 "TARGET_ZEC12"
3701 "risbgn\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3702 [(set_attr "op_type" "RIE")])
3703
3704 (define_insn "*extzv<mode>_z10"
3705 [(set (match_operand:GPR 0 "register_operand" "=d")
3706 (zero_extract:GPR
3707 (match_operand:GPR 1 "register_operand" "d")
3708 (match_operand 2 "const_int_operand" "") ; size
3709 (match_operand 3 "const_int_operand" ""))) ; start
3710 (clobber (reg:CC CC_REGNUM))]
3711 "TARGET_Z10"
3712 "risbg\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3713 [(set_attr "op_type" "RIE")
3714 (set_attr "z10prop" "z10_super_E1")])
3715
3716 (define_insn_and_split "*pre_z10_extzv<mode>"
3717 [(set (match_operand:GPR 0 "register_operand" "=d")
3718 (zero_extract:GPR (match_operand:QI 1 "s_operand" "QS")
3719 (match_operand 2 "nonzero_shift_count_operand" "")
3720 (const_int 0)))
3721 (clobber (reg:CC CC_REGNUM))]
3722 "!TARGET_Z10"
3723 "#"
3724 "&& reload_completed"
3725 [(parallel
3726 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3727 (clobber (reg:CC CC_REGNUM))])
3728 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3729 {
3730 int bitsize = INTVAL (operands[2]);
3731 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3732 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3733
3734 operands[1] = adjust_address (operands[1], BLKmode, 0);
3735 set_mem_size (operands[1], size);
3736 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3737 operands[3] = GEN_INT (mask);
3738 })
3739
3740 (define_insn_and_split "*pre_z10_extv<mode>"
3741 [(set (match_operand:GPR 0 "register_operand" "=d")
3742 (sign_extract:GPR (match_operand:QI 1 "s_operand" "QS")
3743 (match_operand 2 "nonzero_shift_count_operand" "")
3744 (const_int 0)))
3745 (clobber (reg:CC CC_REGNUM))]
3746 ""
3747 "#"
3748 "&& reload_completed"
3749 [(parallel
3750 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3751 (clobber (reg:CC CC_REGNUM))])
3752 (parallel
3753 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3754 (clobber (reg:CC CC_REGNUM))])]
3755 {
3756 int bitsize = INTVAL (operands[2]);
3757 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3758 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3759
3760 operands[1] = adjust_address (operands[1], BLKmode, 0);
3761 set_mem_size (operands[1], size);
3762 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3763 operands[3] = GEN_INT (mask);
3764 })
3765
3766 ;
3767 ; insv instruction patterns
3768 ;
3769
3770 (define_expand "insv"
3771 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3772 (match_operand 1 "const_int_operand" "")
3773 (match_operand 2 "const_int_operand" ""))
3774 (match_operand 3 "general_operand" ""))]
3775 ""
3776 {
3777 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3778 DONE;
3779 FAIL;
3780 })
3781
3782
3783 ; The normal RTL expansion will never generate a zero_extract where
3784 ; the location operand isn't word mode. However, we do this in the
3785 ; back-end when generating atomic operations. See s390_two_part_insv.
3786 (define_insn "*insv<mode>_zEC12"
3787 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3788 (match_operand 1 "const_int_operand" "I") ; size
3789 (match_operand 2 "const_int_operand" "I")) ; pos
3790 (match_operand:GPR 3 "nonimmediate_operand" "d"))]
3791 "TARGET_ZEC12
3792 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3793 "risbgn\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3794 [(set_attr "op_type" "RIE")])
3795
3796 (define_insn "*insv<mode>_z10"
3797 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3798 (match_operand 1 "const_int_operand" "I") ; size
3799 (match_operand 2 "const_int_operand" "I")) ; pos
3800 (match_operand:GPR 3 "nonimmediate_operand" "d"))
3801 (clobber (reg:CC CC_REGNUM))]
3802 "TARGET_Z10
3803 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3804 "risbg\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3805 [(set_attr "op_type" "RIE")
3806 (set_attr "z10prop" "z10_super_E1")])
3807
3808 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3809 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3810 (define_insn "*insv<mode>_zEC12_noshift"
3811 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3812 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3813 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3814 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3815 (match_operand:GPR 4 "const_int_operand" ""))))]
3816 "TARGET_ZEC12 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3817 "risbgn\t%0,%1,%<bfstart>2,%<bfend>2,0"
3818 [(set_attr "op_type" "RIE")])
3819
3820 (define_insn "*insv<mode>_z10_noshift"
3821 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3822 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3823 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3824 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3825 (match_operand:GPR 4 "const_int_operand" ""))))
3826 (clobber (reg:CC CC_REGNUM))]
3827 "TARGET_Z10 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3828 "risbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3829 [(set_attr "op_type" "RIE")
3830 (set_attr "z10prop" "z10_super_E1")])
3831
3832 ; Implement appending Y on the left of S bits of X
3833 ; x = (y << s) | (x & ((1 << s) - 1))
3834 (define_insn "*insv<mode>_zEC12_appendbitsleft"
3835 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3836 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3837 (match_operand:GPR 2 "immediate_operand" ""))
3838 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3839 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3840 "TARGET_ZEC12 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3841 "risbgn\t%0,%3,64-<bitsize>,64-%4-1,%4"
3842 [(set_attr "op_type" "RIE")
3843 (set_attr "z10prop" "z10_super_E1")])
3844
3845 (define_insn "*insv<mode>_z10_appendbitsleft"
3846 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3847 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3848 (match_operand:GPR 2 "immediate_operand" ""))
3849 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3850 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
3851 (clobber (reg:CC CC_REGNUM))]
3852 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3853 "risbg\t%0,%3,64-<bitsize>,64-%4-1,%4"
3854 [(set_attr "op_type" "RIE")
3855 (set_attr "z10prop" "z10_super_E1")])
3856
3857 ; z = (x << c) | (y >> d) with (x << c) and (y >> d) not overlapping after shifting
3858 ; -> z = y >> d; z = (x << c) | (z & ((1 << c) - 1))
3859 ; -> z = y >> d; z = risbg;
3860
3861 (define_split
3862 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
3863 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
3864 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
3865 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
3866 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3867 "TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
3868 [(set (match_dup 0)
3869 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
3870 (set (match_dup 0)
3871 (ior:GPR (and:GPR (match_dup 0) (match_dup 5))
3872 (ashift:GPR (match_dup 3) (match_dup 4))))]
3873 {
3874 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
3875 })
3876
3877 (define_split
3878 [(parallel
3879 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
3880 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
3881 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
3882 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
3883 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
3884 (clobber (reg:CC CC_REGNUM))])]
3885 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
3886 [(set (match_dup 0)
3887 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
3888 (parallel
3889 [(set (match_dup 0)
3890 (ior:GPR (and:GPR (match_dup 0) (match_dup 5))
3891 (ashift:GPR (match_dup 3) (match_dup 4))))
3892 (clobber (reg:CC CC_REGNUM))])]
3893 {
3894 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
3895 })
3896
3897 (define_insn "*r<noxa>sbg_<mode>_noshift"
3898 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3899 (IXOR:GPR
3900 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3901 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3902 (match_operand:GPR 3 "nonimmediate_operand" "0")))
3903 (clobber (reg:CC CC_REGNUM))]
3904 "TARGET_Z10"
3905 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3906 [(set_attr "op_type" "RIE")])
3907
3908 (define_insn "*r<noxa>sbg_di_rotl"
3909 [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
3910 (IXOR:DI
3911 (and:DI
3912 (rotate:DI
3913 (match_operand:DI 1 "nonimmediate_operand" "d")
3914 (match_operand:DI 3 "const_int_operand" ""))
3915 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3916 (match_operand:DI 4 "nonimmediate_operand" "0")))
3917 (clobber (reg:CC CC_REGNUM))]
3918 "TARGET_Z10"
3919 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%b3"
3920 [(set_attr "op_type" "RIE")])
3921
3922 (define_insn "*r<noxa>sbg_<mode>_srl"
3923 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3924 (IXOR:GPR
3925 (and:GPR
3926 (lshiftrt:GPR
3927 (match_operand:GPR 1 "nonimmediate_operand" "d")
3928 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
3929 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3930 (match_operand:GPR 4 "nonimmediate_operand" "0")))
3931 (clobber (reg:CC CC_REGNUM))]
3932 "TARGET_Z10
3933 && s390_extzv_shift_ok (<bitsize>, 64 - INTVAL (operands[3]),
3934 INTVAL (operands[2]))"
3935 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,64-%3"
3936 [(set_attr "op_type" "RIE")])
3937
3938 (define_insn "*r<noxa>sbg_<mode>_sll"
3939 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3940 (IXOR:GPR
3941 (and:GPR
3942 (ashift:GPR
3943 (match_operand:GPR 1 "nonimmediate_operand" "d")
3944 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
3945 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3946 (match_operand:GPR 4 "nonimmediate_operand" "0")))
3947 (clobber (reg:CC CC_REGNUM))]
3948 "TARGET_Z10
3949 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[3]),
3950 INTVAL (operands[2]))"
3951 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%3"
3952 [(set_attr "op_type" "RIE")])
3953
3954 ;; These two are generated by combine for s.bf &= val.
3955 ;; ??? For bitfields smaller than 32-bits, we wind up with SImode
3956 ;; shifts and ands, which results in some truly awful patterns
3957 ;; including subregs of operations. Rather unnecessisarily, IMO.
3958 ;; Instead of
3959 ;;
3960 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
3961 ;; (const_int 24 [0x18])
3962 ;; (const_int 0 [0]))
3963 ;; (subreg:DI (and:SI (subreg:SI (lshiftrt:DI (reg/v:DI 50 [ s ])
3964 ;; (const_int 40 [0x28])) 4)
3965 ;; (reg:SI 4 %r4 [ y+4 ])) 0))
3966 ;;
3967 ;; we should instead generate
3968 ;;
3969 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
3970 ;; (const_int 24 [0x18])
3971 ;; (const_int 0 [0]))
3972 ;; (and:DI (lshiftrt:DI (reg/v:DI 50 [ s ])
3973 ;; (const_int 40 [0x28]))
3974 ;; (subreg:DI (reg:SI 4 %r4 [ y+4 ]) 0)))
3975 ;;
3976 ;; by noticing that we can push down the outer paradoxical subreg
3977 ;; into the operation.
3978
3979 (define_insn "*insv_rnsbg_noshift"
3980 [(set (zero_extract:DI
3981 (match_operand:DI 0 "nonimmediate_operand" "+d")
3982 (match_operand 1 "const_int_operand" "")
3983 (match_operand 2 "const_int_operand" ""))
3984 (and:DI
3985 (match_dup 0)
3986 (match_operand:DI 3 "nonimmediate_operand" "d")))
3987 (clobber (reg:CC CC_REGNUM))]
3988 "TARGET_Z10
3989 && INTVAL (operands[1]) + INTVAL (operands[2]) == 64"
3990 "rnsbg\t%0,%3,%2,63,0"
3991 [(set_attr "op_type" "RIE")])
3992
3993 (define_insn "*insv_rnsbg_srl"
3994 [(set (zero_extract:DI
3995 (match_operand:DI 0 "nonimmediate_operand" "+d")
3996 (match_operand 1 "const_int_operand" "")
3997 (match_operand 2 "const_int_operand" ""))
3998 (and:DI
3999 (lshiftrt:DI
4000 (match_dup 0)
4001 (match_operand 3 "const_int_operand" ""))
4002 (match_operand:DI 4 "nonimmediate_operand" "d")))
4003 (clobber (reg:CC CC_REGNUM))]
4004 "TARGET_Z10
4005 && INTVAL (operands[3]) == 64 - INTVAL (operands[1]) - INTVAL (operands[2])"
4006 "rnsbg\t%0,%4,%2,%2+%1-1,%3"
4007 [(set_attr "op_type" "RIE")])
4008
4009 (define_insn "*insv<mode>_mem_reg"
4010 [(set (zero_extract:W (match_operand:QI 0 "memory_operand" "+Q,S")
4011 (match_operand 1 "const_int_operand" "n,n")
4012 (const_int 0))
4013 (match_operand:W 2 "register_operand" "d,d"))]
4014 "INTVAL (operands[1]) > 0
4015 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4016 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4017 {
4018 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4019
4020 operands[1] = GEN_INT ((1ul << size) - 1);
4021 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
4022 : "stcmy\t%2,%1,%S0";
4023 }
4024 [(set_attr "op_type" "RS,RSY")
4025 (set_attr "z10prop" "z10_super,z10_super")])
4026
4027 (define_insn "*insvdi_mem_reghigh"
4028 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+QS")
4029 (match_operand 1 "const_int_operand" "n")
4030 (const_int 0))
4031 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
4032 (const_int 32)))]
4033 "TARGET_ZARCH
4034 && INTVAL (operands[1]) > 0
4035 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4036 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4037 {
4038 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4039
4040 operands[1] = GEN_INT ((1ul << size) - 1);
4041 return "stcmh\t%2,%1,%S0";
4042 }
4043 [(set_attr "op_type" "RSY")
4044 (set_attr "z10prop" "z10_super")])
4045
4046 (define_insn "*insvdi_reg_imm"
4047 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4048 (const_int 16)
4049 (match_operand 1 "const_int_operand" "n"))
4050 (match_operand:DI 2 "const_int_operand" "n"))]
4051 "TARGET_ZARCH
4052 && INTVAL (operands[1]) >= 0
4053 && INTVAL (operands[1]) < BITS_PER_WORD
4054 && INTVAL (operands[1]) % 16 == 0"
4055 {
4056 switch (BITS_PER_WORD - INTVAL (operands[1]))
4057 {
4058 case 64: return "iihh\t%0,%x2"; break;
4059 case 48: return "iihl\t%0,%x2"; break;
4060 case 32: return "iilh\t%0,%x2"; break;
4061 case 16: return "iill\t%0,%x2"; break;
4062 default: gcc_unreachable();
4063 }
4064 }
4065 [(set_attr "op_type" "RI")
4066 (set_attr "z10prop" "z10_super_E1")])
4067
4068 ; Update the left-most 32 bit of a DI.
4069 (define_insn "*insv_h_di_reg_extimm"
4070 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4071 (const_int 32)
4072 (const_int 0))
4073 (match_operand:DI 1 "const_int_operand" "n"))]
4074 "TARGET_EXTIMM"
4075 "iihf\t%0,%o1"
4076 [(set_attr "op_type" "RIL")
4077 (set_attr "z10prop" "z10_fwd_E1")])
4078
4079 ; Update the right-most 32 bit of a DI.
4080 (define_insn "*insv_l_di_reg_extimm"
4081 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4082 (const_int 32)
4083 (const_int 32))
4084 (match_operand:DI 1 "const_int_operand" "n"))]
4085 "TARGET_EXTIMM"
4086 "iilf\t%0,%o1"
4087 [(set_attr "op_type" "RIL")
4088 (set_attr "z10prop" "z10_fwd_A1")])
4089
4090 ;
4091 ; extendsidi2 instruction pattern(s).
4092 ;
4093
4094 (define_expand "extendsidi2"
4095 [(set (match_operand:DI 0 "register_operand" "")
4096 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4097 ""
4098 {
4099 if (!TARGET_ZARCH)
4100 {
4101 emit_clobber (operands[0]);
4102 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
4103 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
4104 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
4105 DONE;
4106 }
4107 })
4108
4109 (define_insn "*extendsidi2"
4110 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4111 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
4112 "TARGET_ZARCH"
4113 "@
4114 lgfr\t%0,%1
4115 lgf\t%0,%1
4116 lgfrl\t%0,%1"
4117 [(set_attr "op_type" "RRE,RXY,RIL")
4118 (set_attr "type" "*,*,larl")
4119 (set_attr "cpu_facility" "*,*,z10")
4120 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4121
4122 ;
4123 ; extend(hi|qi)(si|di)2 instruction pattern(s).
4124 ;
4125
4126 (define_expand "extend<HQI:mode><DSI:mode>2"
4127 [(set (match_operand:DSI 0 "register_operand" "")
4128 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4129 ""
4130 {
4131 if (<DSI:MODE>mode == DImode && !TARGET_ZARCH)
4132 {
4133 rtx tmp = gen_reg_rtx (SImode);
4134 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
4135 emit_insn (gen_extendsidi2 (operands[0], tmp));
4136 DONE;
4137 }
4138 else if (!TARGET_EXTIMM)
4139 {
4140 rtx bitcount = GEN_INT (<DSI:bitsize> - <HQI:bitsize>);
4141
4142 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
4143 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
4144 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
4145 DONE;
4146 }
4147 })
4148
4149 ;
4150 ; extendhidi2 instruction pattern(s).
4151 ;
4152
4153 (define_insn "*extendhidi2_extimm"
4154 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4155 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,RT,b")))]
4156 "TARGET_ZARCH && TARGET_EXTIMM"
4157 "@
4158 lghr\t%0,%1
4159 lgh\t%0,%1
4160 lghrl\t%0,%1"
4161 [(set_attr "op_type" "RRE,RXY,RIL")
4162 (set_attr "type" "*,*,larl")
4163 (set_attr "cpu_facility" "extimm,extimm,z10")
4164 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4165
4166 (define_insn "*extendhidi2"
4167 [(set (match_operand:DI 0 "register_operand" "=d")
4168 (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT")))]
4169 "TARGET_ZARCH"
4170 "lgh\t%0,%1"
4171 [(set_attr "op_type" "RXY")
4172 (set_attr "z10prop" "z10_super_E1")])
4173
4174 ;
4175 ; extendhisi2 instruction pattern(s).
4176 ;
4177
4178 (define_insn "*extendhisi2_extimm"
4179 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
4180 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
4181 "TARGET_EXTIMM"
4182 "@
4183 lhr\t%0,%1
4184 lh\t%0,%1
4185 lhy\t%0,%1
4186 lhrl\t%0,%1"
4187 [(set_attr "op_type" "RRE,RX,RXY,RIL")
4188 (set_attr "type" "*,*,*,larl")
4189 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")
4190 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,z10_super_E1")])
4191
4192 (define_insn "*extendhisi2"
4193 [(set (match_operand:SI 0 "register_operand" "=d,d")
4194 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
4195 "!TARGET_EXTIMM"
4196 "@
4197 lh\t%0,%1
4198 lhy\t%0,%1"
4199 [(set_attr "op_type" "RX,RXY")
4200 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4201
4202 ;
4203 ; extendqi(si|di)2 instruction pattern(s).
4204 ;
4205
4206 ; lbr, lgbr, lb, lgb
4207 (define_insn "*extendqi<mode>2_extimm"
4208 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4209 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,RT")))]
4210 "TARGET_EXTIMM"
4211 "@
4212 l<g>br\t%0,%1
4213 l<g>b\t%0,%1"
4214 [(set_attr "op_type" "RRE,RXY")
4215 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4216
4217 ; lb, lgb
4218 (define_insn "*extendqi<mode>2"
4219 [(set (match_operand:GPR 0 "register_operand" "=d")
4220 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "RT")))]
4221 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
4222 "l<g>b\t%0,%1"
4223 [(set_attr "op_type" "RXY")
4224 (set_attr "z10prop" "z10_super_E1")])
4225
4226 (define_insn_and_split "*extendqi<mode>2_short_displ"
4227 [(set (match_operand:GPR 0 "register_operand" "=d")
4228 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
4229 (clobber (reg:CC CC_REGNUM))]
4230 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
4231 "#"
4232 "&& reload_completed"
4233 [(parallel
4234 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
4235 (clobber (reg:CC CC_REGNUM))])
4236 (parallel
4237 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
4238 (clobber (reg:CC CC_REGNUM))])]
4239 {
4240 operands[1] = adjust_address (operands[1], BLKmode, 0);
4241 set_mem_size (operands[1], GET_MODE_SIZE (QImode));
4242 operands[2] = GEN_INT (<GPR:bitsize> - BITS_PER_UNIT);
4243 })
4244
4245 ;
4246 ; zero_extendsidi2 instruction pattern(s).
4247 ;
4248
4249 (define_expand "zero_extendsidi2"
4250 [(set (match_operand:DI 0 "register_operand" "")
4251 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4252 ""
4253 {
4254 if (!TARGET_ZARCH)
4255 {
4256 emit_clobber (operands[0]);
4257 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
4258 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
4259 DONE;
4260 }
4261 })
4262
4263 (define_insn "*zero_extendsidi2"
4264 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4265 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
4266 "TARGET_ZARCH"
4267 "@
4268 llgfr\t%0,%1
4269 llgf\t%0,%1
4270 llgfrl\t%0,%1"
4271 [(set_attr "op_type" "RRE,RXY,RIL")
4272 (set_attr "type" "*,*,larl")
4273 (set_attr "cpu_facility" "*,*,z10")
4274 (set_attr "z10prop" "z10_fwd_E1,z10_fwd_A3,z10_fwd_A3")])
4275
4276 ;
4277 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
4278 ;
4279
4280 (define_insn "*llgt_sidi"
4281 [(set (match_operand:DI 0 "register_operand" "=d")
4282 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
4283 (const_int 2147483647)))]
4284 "TARGET_ZARCH"
4285 "llgt\t%0,%1"
4286 [(set_attr "op_type" "RXE")
4287 (set_attr "z10prop" "z10_super_E1")])
4288
4289 (define_insn_and_split "*llgt_sidi_split"
4290 [(set (match_operand:DI 0 "register_operand" "=d")
4291 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
4292 (const_int 2147483647)))
4293 (clobber (reg:CC CC_REGNUM))]
4294 "TARGET_ZARCH"
4295 "#"
4296 "&& reload_completed"
4297 [(set (match_dup 0)
4298 (and:DI (subreg:DI (match_dup 1) 0)
4299 (const_int 2147483647)))]
4300 "")
4301
4302 (define_insn "*llgt_sisi"
4303 [(set (match_operand:SI 0 "register_operand" "=d,d")
4304 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,RT")
4305 (const_int 2147483647)))]
4306 "TARGET_ZARCH"
4307 "@
4308 llgtr\t%0,%1
4309 llgt\t%0,%1"
4310 [(set_attr "op_type" "RRE,RXE")
4311 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4312
4313 (define_insn "*llgt_didi"
4314 [(set (match_operand:DI 0 "register_operand" "=d,d")
4315 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
4316 (const_int 2147483647)))]
4317 "TARGET_ZARCH"
4318 "@
4319 llgtr\t%0,%1
4320 llgt\t%0,%N1"
4321 [(set_attr "op_type" "RRE,RXE")
4322 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4323
4324 (define_split
4325 [(set (match_operand:DSI 0 "register_operand" "")
4326 (and:DSI (match_operand:DSI 1 "nonimmediate_operand" "")
4327 (const_int 2147483647)))
4328 (clobber (reg:CC CC_REGNUM))]
4329 "TARGET_ZARCH && reload_completed"
4330 [(set (match_dup 0)
4331 (and:DSI (match_dup 1)
4332 (const_int 2147483647)))]
4333 "")
4334
4335 ;
4336 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
4337 ;
4338
4339 (define_expand "zero_extend<mode>di2"
4340 [(set (match_operand:DI 0 "register_operand" "")
4341 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4342 ""
4343 {
4344 if (!TARGET_ZARCH)
4345 {
4346 rtx tmp = gen_reg_rtx (SImode);
4347 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
4348 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
4349 DONE;
4350 }
4351 else if (!TARGET_EXTIMM)
4352 {
4353 rtx bitcount = GEN_INT (64 - <HQI:bitsize>);
4354 operands[1] = gen_lowpart (DImode, operands[1]);
4355 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
4356 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
4357 DONE;
4358 }
4359 })
4360
4361 (define_expand "zero_extend<mode>si2"
4362 [(set (match_operand:SI 0 "register_operand" "")
4363 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4364 ""
4365 {
4366 if (!TARGET_EXTIMM)
4367 {
4368 operands[1] = gen_lowpart (SImode, operands[1]);
4369 emit_insn (gen_andsi3 (operands[0], operands[1],
4370 GEN_INT ((1 << <HQI:bitsize>) - 1)));
4371 DONE;
4372 }
4373 })
4374
4375 ; llhrl, llghrl
4376 (define_insn "*zero_extendhi<mode>2_z10"
4377 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4378 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,RT,b")))]
4379 "TARGET_Z10"
4380 "@
4381 ll<g>hr\t%0,%1
4382 ll<g>h\t%0,%1
4383 ll<g>hrl\t%0,%1"
4384 [(set_attr "op_type" "RXY,RRE,RIL")
4385 (set_attr "type" "*,*,larl")
4386 (set_attr "cpu_facility" "*,*,z10")
4387 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3,z10_fwd_A3")])
4388
4389 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
4390 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
4391 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4392 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,RT")))]
4393 "TARGET_EXTIMM"
4394 "@
4395 ll<g><hc>r\t%0,%1
4396 ll<g><hc>\t%0,%1"
4397 [(set_attr "op_type" "RRE,RXY")
4398 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3")])
4399
4400 ; llgh, llgc
4401 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
4402 [(set (match_operand:GPR 0 "register_operand" "=d")
4403 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "RT")))]
4404 "TARGET_ZARCH && !TARGET_EXTIMM"
4405 "llg<hc>\t%0,%1"
4406 [(set_attr "op_type" "RXY")
4407 (set_attr "z10prop" "z10_fwd_A3")])
4408
4409 (define_insn_and_split "*zero_extendhisi2_31"
4410 [(set (match_operand:SI 0 "register_operand" "=&d")
4411 (zero_extend:SI (match_operand:HI 1 "s_operand" "QS")))
4412 (clobber (reg:CC CC_REGNUM))]
4413 "!TARGET_ZARCH"
4414 "#"
4415 "&& reload_completed"
4416 [(set (match_dup 0) (const_int 0))
4417 (parallel
4418 [(set (strict_low_part (match_dup 2)) (match_dup 1))
4419 (clobber (reg:CC CC_REGNUM))])]
4420 "operands[2] = gen_lowpart (HImode, operands[0]);")
4421
4422 (define_insn_and_split "*zero_extendqisi2_31"
4423 [(set (match_operand:SI 0 "register_operand" "=&d")
4424 (zero_extend:SI (match_operand:QI 1 "memory_operand" "RT")))]
4425 "!TARGET_ZARCH"
4426 "#"
4427 "&& reload_completed"
4428 [(set (match_dup 0) (const_int 0))
4429 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4430 "operands[2] = gen_lowpart (QImode, operands[0]);")
4431
4432 ;
4433 ; zero_extendqihi2 instruction pattern(s).
4434 ;
4435
4436 (define_expand "zero_extendqihi2"
4437 [(set (match_operand:HI 0 "register_operand" "")
4438 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4439 "TARGET_ZARCH && !TARGET_EXTIMM"
4440 {
4441 operands[1] = gen_lowpart (HImode, operands[1]);
4442 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
4443 DONE;
4444 })
4445
4446 (define_insn "*zero_extendqihi2_64"
4447 [(set (match_operand:HI 0 "register_operand" "=d")
4448 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
4449 "TARGET_ZARCH && !TARGET_EXTIMM"
4450 "llgc\t%0,%1"
4451 [(set_attr "op_type" "RXY")
4452 (set_attr "z10prop" "z10_fwd_A3")])
4453
4454 (define_insn_and_split "*zero_extendqihi2_31"
4455 [(set (match_operand:HI 0 "register_operand" "=&d")
4456 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
4457 "!TARGET_ZARCH"
4458 "#"
4459 "&& reload_completed"
4460 [(set (match_dup 0) (const_int 0))
4461 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4462 "operands[2] = gen_lowpart (QImode, operands[0]);")
4463
4464 ;
4465 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
4466 ;
4467
4468 (define_expand "fixuns_truncdddi2"
4469 [(parallel
4470 [(set (match_operand:DI 0 "register_operand" "")
4471 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
4472 (unspec:DI [(const_int 5)] UNSPEC_ROUND)
4473 (clobber (reg:CC CC_REGNUM))])]
4474
4475 "TARGET_HARD_DFP"
4476 {
4477 if (!TARGET_Z196)
4478 {
4479 rtx_code_label *label1 = gen_label_rtx ();
4480 rtx_code_label *label2 = gen_label_rtx ();
4481 rtx temp = gen_reg_rtx (TDmode);
4482 REAL_VALUE_TYPE cmp, sub;
4483
4484 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4485 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4486
4487 /* 2^63 can't be represented as 64bit DFP number with full precision. The
4488 solution is doing the check and the subtraction in TD mode and using a
4489 TD -> DI convert afterwards. */
4490 emit_insn (gen_extendddtd2 (temp, operands[1]));
4491 temp = force_reg (TDmode, temp);
4492 emit_cmp_and_jump_insns (temp,
4493 const_double_from_real_value (cmp, TDmode),
4494 LT, NULL_RTX, VOIDmode, 0, label1);
4495 emit_insn (gen_subtd3 (temp, temp,
4496 const_double_from_real_value (sub, TDmode)));
4497 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
4498 emit_jump (label2);
4499
4500 emit_label (label1);
4501 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1], GEN_INT (9)));
4502 emit_label (label2);
4503 DONE;
4504 }
4505 })
4506
4507 (define_expand "fixuns_trunctddi2"
4508 [(parallel
4509 [(set (match_operand:DI 0 "register_operand" "")
4510 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))
4511 (unspec:DI [(const_int 5)] UNSPEC_ROUND)
4512 (clobber (reg:CC CC_REGNUM))])]
4513
4514 "TARGET_HARD_DFP"
4515 {
4516 if (!TARGET_Z196)
4517 {
4518 rtx_code_label *label1 = gen_label_rtx ();
4519 rtx_code_label *label2 = gen_label_rtx ();
4520 rtx temp = gen_reg_rtx (TDmode);
4521 REAL_VALUE_TYPE cmp, sub;
4522
4523 operands[1] = force_reg (TDmode, operands[1]);
4524 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4525 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4526
4527 emit_cmp_and_jump_insns (operands[1],
4528 const_double_from_real_value (cmp, TDmode),
4529 LT, NULL_RTX, VOIDmode, 0, label1);
4530 emit_insn (gen_subtd3 (temp, operands[1],
4531 const_double_from_real_value (sub, TDmode)));
4532 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
4533 emit_jump (label2);
4534
4535 emit_label (label1);
4536 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1], GEN_INT (9)));
4537 emit_label (label2);
4538 DONE;
4539 }
4540 })
4541
4542 ;
4543 ; fixuns_trunc(sf|df|tf)(si|di)2 and fix_trunc(sf|df|tf)(si|di)2
4544 ; instruction pattern(s).
4545 ;
4546
4547 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
4548 [(parallel
4549 [(set (match_operand:GPR 0 "register_operand" "")
4550 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))
4551 (unspec:GPR [(const_int 5)] UNSPEC_ROUND)
4552 (clobber (reg:CC CC_REGNUM))])]
4553 "TARGET_HARD_FLOAT"
4554 {
4555 if (!TARGET_Z196)
4556 {
4557 rtx_code_label *label1 = gen_label_rtx ();
4558 rtx_code_label *label2 = gen_label_rtx ();
4559 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
4560 REAL_VALUE_TYPE cmp, sub;
4561
4562 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
4563 real_2expN (&cmp, <GPR:bitsize> - 1, <BFP:MODE>mode);
4564 real_2expN (&sub, <GPR:bitsize>, <BFP:MODE>mode);
4565
4566 emit_cmp_and_jump_insns (operands[1],
4567 const_double_from_real_value (cmp, <BFP:MODE>mode),
4568 LT, NULL_RTX, VOIDmode, 0, label1);
4569 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
4570 const_double_from_real_value (sub, <BFP:MODE>mode)));
4571 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
4572 GEN_INT (7)));
4573 emit_jump (label2);
4574
4575 emit_label (label1);
4576 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
4577 operands[1], GEN_INT (5)));
4578 emit_label (label2);
4579 DONE;
4580 }
4581 })
4582
4583 ; fixuns_trunc(td|dd)si2 expander
4584 (define_expand "fixuns_trunc<mode>si2"
4585 [(parallel
4586 [(set (match_operand:SI 0 "register_operand" "")
4587 (unsigned_fix:SI (match_operand:DFP 1 "register_operand" "")))
4588 (unspec:SI [(const_int 5)] UNSPEC_ROUND)
4589 (clobber (reg:CC CC_REGNUM))])]
4590 "TARGET_Z196 && TARGET_HARD_DFP"
4591 "")
4592
4593 ; fixuns_trunc(tf|df|sf|td|dd)(di|si)2 instruction patterns.
4594
4595 (define_insn "*fixuns_truncdfdi2_z13"
4596 [(set (match_operand:DI 0 "register_operand" "=d,v")
4597 (unsigned_fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4598 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4599 (clobber (reg:CC CC_REGNUM))]
4600 "TARGET_Z13 && TARGET_HARD_FLOAT"
4601 "@
4602 clgdbr\t%0,%h2,%1,0
4603 wclgdb\t%v0,%v1,0,%h2"
4604 [(set_attr "op_type" "RRF,VRR")
4605 (set_attr "type" "ftoi")])
4606
4607 ; clfebr, clfdbr, clfxbr, clgebr, clgdbr, clgxbr
4608 ; clfdtr, clfxtr, clgdtr, clgxtr
4609 (define_insn "*fixuns_trunc<FP:mode><GPR:mode>2_z196"
4610 [(set (match_operand:GPR 0 "register_operand" "=d")
4611 (unsigned_fix:GPR (match_operand:FP 1 "register_operand" "f")))
4612 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4613 (clobber (reg:CC CC_REGNUM))]
4614 "TARGET_Z196 && TARGET_HARD_FLOAT
4615 && (!TARGET_Z13 || <GPR:MODE>mode != DImode || <FP:MODE>mode != DFmode)"
4616 "cl<GPR:gf><FP:xde><FP:bt>r\t%0,%h2,%1,0"
4617 [(set_attr "op_type" "RRF")
4618 (set_attr "type" "ftoi")])
4619
4620 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
4621 [(set (match_operand:GPR 0 "register_operand" "")
4622 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
4623 "TARGET_HARD_FLOAT"
4624 {
4625 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
4626 GEN_INT (5)));
4627 DONE;
4628 })
4629
4630 (define_insn "*fix_truncdfdi2_bfp_z13"
4631 [(set (match_operand:DI 0 "register_operand" "=d,v")
4632 (fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4633 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4634 (clobber (reg:CC CC_REGNUM))]
4635 "TARGET_Z13 && TARGET_HARD_FLOAT"
4636 "@
4637 cgdbr\t%0,%h2,%1
4638 wcgdb\t%v0,%v1,0,%h2"
4639 [(set_attr "op_type" "RRE,VRR")
4640 (set_attr "type" "ftoi")])
4641
4642 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
4643 (define_insn "*fix_trunc<BFP:mode><GPR:mode>2_bfp"
4644 [(set (match_operand:GPR 0 "register_operand" "=d")
4645 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4646 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4647 (clobber (reg:CC CC_REGNUM))]
4648 "TARGET_HARD_FLOAT
4649 && (!TARGET_VX || <GPR:MODE>mode != DImode || <BFP:MODE>mode != DFmode)"
4650 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
4651 [(set_attr "op_type" "RRE")
4652 (set_attr "type" "ftoi")])
4653
4654 (define_expand "fix_trunc<BFP:mode><GPR:mode>2_bfp"
4655 [(parallel
4656 [(set (match_operand:GPR 0 "register_operand" "=d")
4657 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4658 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4659 (clobber (reg:CC CC_REGNUM))])]
4660 "TARGET_HARD_FLOAT")
4661 ;
4662 ; fix_trunc(td|dd)di2 instruction pattern(s).
4663 ;
4664
4665 (define_expand "fix_trunc<mode>di2"
4666 [(set (match_operand:DI 0 "register_operand" "")
4667 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
4668 "TARGET_ZARCH && TARGET_HARD_DFP"
4669 {
4670 operands[1] = force_reg (<MODE>mode, operands[1]);
4671 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
4672 GEN_INT (9)));
4673 DONE;
4674 })
4675
4676 ; cgxtr, cgdtr
4677 (define_insn "fix_trunc<DFP:mode>di2_dfp"
4678 [(set (match_operand:DI 0 "register_operand" "=d")
4679 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
4680 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
4681 (clobber (reg:CC CC_REGNUM))]
4682 "TARGET_ZARCH && TARGET_HARD_DFP"
4683 "cg<DFP:xde>tr\t%0,%h2,%1"
4684 [(set_attr "op_type" "RRF")
4685 (set_attr "type" "ftoidfp")])
4686
4687
4688 ;
4689 ; fix_trunctf(si|di)2 instruction pattern(s).
4690 ;
4691
4692 (define_expand "fix_trunctf<mode>2"
4693 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
4694 (fix:GPR (match_operand:TF 1 "register_operand" "")))
4695 (unspec:GPR [(const_int 5)] UNSPEC_ROUND)
4696 (clobber (reg:CC CC_REGNUM))])]
4697 "TARGET_HARD_FLOAT"
4698 "")
4699
4700
4701 ;
4702 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4703 ;
4704
4705 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
4706 (define_insn "floatdi<mode>2"
4707 [(set (match_operand:FP 0 "register_operand" "=f,<vf>")
4708 (float:FP (match_operand:DI 1 "register_operand" "d,<vd>")))]
4709 "TARGET_ZARCH && TARGET_HARD_FLOAT"
4710 "@
4711 c<xde>g<bt>r\t%0,%1
4712 wcdgb\t%v0,%v1,0,0"
4713 [(set_attr "op_type" "RRE,VRR")
4714 (set_attr "type" "itof<mode>" )
4715 (set_attr "cpu_facility" "*,vec")])
4716
4717 ; cxfbr, cdfbr, cefbr
4718 (define_insn "floatsi<mode>2"
4719 [(set (match_operand:BFP 0 "register_operand" "=f")
4720 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
4721 "TARGET_HARD_FLOAT"
4722 "c<xde>fbr\t%0,%1"
4723 [(set_attr "op_type" "RRE")
4724 (set_attr "type" "itof<mode>" )])
4725
4726 ; cxftr, cdftr
4727 (define_insn "floatsi<mode>2"
4728 [(set (match_operand:DFP 0 "register_operand" "=f")
4729 (float:DFP (match_operand:SI 1 "register_operand" "d")))]
4730 "TARGET_Z196 && TARGET_HARD_FLOAT"
4731 "c<xde>ftr\t%0,0,%1,0"
4732 [(set_attr "op_type" "RRE")
4733 (set_attr "type" "itof<mode>" )])
4734
4735 ;
4736 ; floatuns(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4737 ;
4738
4739 (define_insn "*floatunsdidf2_z13"
4740 [(set (match_operand:DF 0 "register_operand" "=f,v")
4741 (unsigned_float:DF (match_operand:DI 1 "register_operand" "d,v")))]
4742 "TARGET_Z13 && TARGET_HARD_FLOAT"
4743 "@
4744 cdlgbr\t%0,0,%1,0
4745 wcdlgb\t%v0,%v1,0,0"
4746 [(set_attr "op_type" "RRE,VRR")
4747 (set_attr "type" "itofdf")])
4748
4749 ; cxlgbr, cdlgbr, celgbr, cxlgtr, cdlgtr
4750 ; cxlfbr, cdlfbr, celfbr, cxlftr, cdlftr
4751 (define_insn "*floatuns<GPR:mode><FP:mode>2"
4752 [(set (match_operand:FP 0 "register_operand" "=f")
4753 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "d")))]
4754 "TARGET_Z196 && TARGET_HARD_FLOAT
4755 && (!TARGET_VX || <FP:MODE>mode != DFmode || <GPR:MODE>mode != DImode)"
4756 "c<FP:xde>l<GPR:gf><FP:bt>r\t%0,0,%1,0"
4757 [(set_attr "op_type" "RRE")
4758 (set_attr "type" "itof<FP:mode>")])
4759
4760 (define_expand "floatuns<GPR:mode><FP:mode>2"
4761 [(set (match_operand:FP 0 "register_operand" "")
4762 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "")))]
4763 "TARGET_Z196 && TARGET_HARD_FLOAT")
4764
4765 ;
4766 ; truncdfsf2 instruction pattern(s).
4767 ;
4768
4769 (define_insn "truncdfsf2"
4770 [(set (match_operand:SF 0 "register_operand" "=f,v")
4771 (float_truncate:SF (match_operand:DF 1 "register_operand" "f,v")))]
4772 "TARGET_HARD_FLOAT"
4773 "@
4774 ledbr\t%0,%1
4775 wledb\t%v0,%v1,0,0" ; IEEE inexact exception not suppressed
4776 ; According to BFP rounding mode
4777 [(set_attr "op_type" "RRE,VRR")
4778 (set_attr "type" "ftruncdf")
4779 (set_attr "cpu_facility" "*,vec")])
4780
4781 ;
4782 ; trunctf(df|sf)2 instruction pattern(s).
4783 ;
4784
4785 ; ldxbr, lexbr
4786 (define_insn "trunctf<mode>2"
4787 [(set (match_operand:DSF 0 "register_operand" "=f")
4788 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
4789 (clobber (match_scratch:TF 2 "=f"))]
4790 "TARGET_HARD_FLOAT"
4791 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
4792 [(set_attr "length" "6")
4793 (set_attr "type" "ftrunctf")])
4794
4795 ;
4796 ; trunctddd2 and truncddsd2 instruction pattern(s).
4797 ;
4798
4799 (define_insn "trunctddd2"
4800 [(set (match_operand:DD 0 "register_operand" "=f")
4801 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
4802 (clobber (match_scratch:TD 2 "=f"))]
4803 "TARGET_HARD_DFP"
4804 "ldxtr\t%2,0,%1,0\;ldr\t%0,%2"
4805 [(set_attr "length" "6")
4806 (set_attr "type" "ftruncdd")])
4807
4808 (define_insn "truncddsd2"
4809 [(set (match_operand:SD 0 "register_operand" "=f")
4810 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
4811 "TARGET_HARD_DFP"
4812 "ledtr\t%0,0,%1,0"
4813 [(set_attr "op_type" "RRF")
4814 (set_attr "type" "ftruncsd")])
4815
4816 (define_expand "trunctdsd2"
4817 [(parallel
4818 [(set (match_dup 3)
4819 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
4820 (clobber (match_scratch:TD 2 ""))])
4821 (set (match_operand:SD 0 "register_operand" "")
4822 (float_truncate:SD (match_dup 3)))]
4823 "TARGET_HARD_DFP"
4824 {
4825 operands[3] = gen_reg_rtx (DDmode);
4826 })
4827
4828 ;
4829 ; extend(sf|df)(df|tf)2 instruction pattern(s).
4830 ;
4831
4832 (define_insn "*extendsfdf2_z13"
4833 [(set (match_operand:DF 0 "register_operand" "=f,f,v")
4834 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,R,v")))]
4835 "TARGET_Z13 && TARGET_HARD_FLOAT"
4836 "@
4837 ldebr\t%0,%1
4838 ldeb\t%0,%1
4839 wldeb\t%v0,%v1"
4840 [(set_attr "op_type" "RRE,RXE,VRR")
4841 (set_attr "type" "fsimpdf, floaddf,fsimpdf")])
4842
4843 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
4844 (define_insn "*extend<DSF:mode><BFP:mode>2"
4845 [(set (match_operand:BFP 0 "register_operand" "=f,f")
4846 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
4847 "TARGET_HARD_FLOAT
4848 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)
4849 && (!TARGET_VX || <BFP:MODE>mode != DFmode || <DSF:MODE>mode != SFmode)"
4850 "@
4851 l<BFP:xde><DSF:xde>br\t%0,%1
4852 l<BFP:xde><DSF:xde>b\t%0,%1"
4853 [(set_attr "op_type" "RRE,RXE")
4854 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
4855
4856 (define_expand "extend<DSF:mode><BFP:mode>2"
4857 [(set (match_operand:BFP 0 "register_operand" "")
4858 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "")))]
4859 "TARGET_HARD_FLOAT
4860 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)")
4861
4862 ;
4863 ; extendddtd2 and extendsddd2 instruction pattern(s).
4864 ;
4865
4866 (define_insn "extendddtd2"
4867 [(set (match_operand:TD 0 "register_operand" "=f")
4868 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
4869 "TARGET_HARD_DFP"
4870 "lxdtr\t%0,%1,0"
4871 [(set_attr "op_type" "RRF")
4872 (set_attr "type" "fsimptf")])
4873
4874 (define_insn "extendsddd2"
4875 [(set (match_operand:DD 0 "register_operand" "=f")
4876 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
4877 "TARGET_HARD_DFP"
4878 "ldetr\t%0,%1,0"
4879 [(set_attr "op_type" "RRF")
4880 (set_attr "type" "fsimptf")])
4881
4882 (define_expand "extendsdtd2"
4883 [(set (match_dup 2)
4884 (float_extend:DD (match_operand:SD 1 "register_operand" "")))
4885 (set (match_operand:TD 0 "register_operand" "")
4886 (float_extend:TD (match_dup 2)))]
4887 "TARGET_HARD_DFP"
4888 {
4889 operands[2] = gen_reg_rtx (DDmode);
4890 })
4891
4892 ; Binary Floating Point - load fp integer
4893
4894 ; Expanders for: floor, btrunc, round, ceil, and nearbyint
4895 ; For all of them the inexact exceptions are suppressed.
4896
4897 ; fiebra, fidbra, fixbra
4898 (define_insn "<FPINT:fpint_name><BFP:mode>2"
4899 [(set (match_operand:BFP 0 "register_operand" "=f")
4900 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
4901 FPINT))]
4902 "TARGET_Z196"
4903 "fi<BFP:xde>bra\t%0,<FPINT:fpint_roundingmode>,%1,4"
4904 [(set_attr "op_type" "RRF")
4905 (set_attr "type" "fsimp<BFP:mode>")])
4906
4907 ; rint is supposed to raise an inexact exception so we can use the
4908 ; older instructions.
4909
4910 ; fiebr, fidbr, fixbr
4911 (define_insn "rint<BFP:mode>2"
4912 [(set (match_operand:BFP 0 "register_operand" "=f")
4913 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
4914 UNSPEC_FPINT_RINT))]
4915 ""
4916 "fi<BFP:xde>br\t%0,0,%1"
4917 [(set_attr "op_type" "RRF")
4918 (set_attr "type" "fsimp<BFP:mode>")])
4919
4920
4921 ; Decimal Floating Point - load fp integer
4922
4923 ; fidtr, fixtr
4924 (define_insn "<FPINT:fpint_name><DFP:mode>2"
4925 [(set (match_operand:DFP 0 "register_operand" "=f")
4926 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
4927 FPINT))]
4928 "TARGET_HARD_DFP"
4929 "fi<DFP:xde>tr\t%0,<FPINT:fpint_roundingmode>,%1,4"
4930 [(set_attr "op_type" "RRF")
4931 (set_attr "type" "fsimp<DFP:mode>")])
4932
4933 ; fidtr, fixtr
4934 (define_insn "rint<DFP:mode>2"
4935 [(set (match_operand:DFP 0 "register_operand" "=f")
4936 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
4937 UNSPEC_FPINT_RINT))]
4938 "TARGET_HARD_DFP"
4939 "fi<DFP:xde>tr\t%0,0,%1,0"
4940 [(set_attr "op_type" "RRF")
4941 (set_attr "type" "fsimp<DFP:mode>")])
4942
4943 ;
4944 ; Binary <-> Decimal floating point trunc patterns
4945 ;
4946
4947 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
4948 [(set (reg:DFP_ALL FPR0_REGNUM)
4949 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
4950 (use (reg:SI GPR0_REGNUM))
4951 (clobber (reg:CC CC_REGNUM))
4952 (clobber (reg:SI GPR1_REGNUM))]
4953 "TARGET_HARD_DFP"
4954 "pfpo")
4955
4956 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
4957 [(set (reg:BFP FPR0_REGNUM)
4958 (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
4959 (use (reg:SI GPR0_REGNUM))
4960 (clobber (reg:CC CC_REGNUM))
4961 (clobber (reg:SI GPR1_REGNUM))]
4962 "TARGET_HARD_DFP"
4963 "pfpo")
4964
4965 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
4966 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
4967 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4968 (parallel
4969 [(set (reg:DFP_ALL FPR0_REGNUM)
4970 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
4971 (use (reg:SI GPR0_REGNUM))
4972 (clobber (reg:CC CC_REGNUM))
4973 (clobber (reg:SI GPR1_REGNUM))])
4974 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
4975 (reg:DFP_ALL FPR0_REGNUM))]
4976 "TARGET_HARD_DFP
4977 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
4978 {
4979 HOST_WIDE_INT flags;
4980
4981 flags = (PFPO_CONVERT |
4982 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
4983 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
4984
4985 operands[2] = GEN_INT (flags);
4986 })
4987
4988 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
4989 [(set (reg:DFP_ALL FPR4_REGNUM)
4990 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
4991 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4992 (parallel
4993 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
4994 (use (reg:SI GPR0_REGNUM))
4995 (clobber (reg:CC CC_REGNUM))
4996 (clobber (reg:SI GPR1_REGNUM))])
4997 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
4998 "TARGET_HARD_DFP
4999 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
5000 {
5001 HOST_WIDE_INT flags;
5002
5003 flags = (PFPO_CONVERT |
5004 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5005 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5006
5007 operands[2] = GEN_INT (flags);
5008 })
5009
5010 ;
5011 ; Binary <-> Decimal floating point extend patterns
5012 ;
5013
5014 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
5015 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5016 (use (reg:SI GPR0_REGNUM))
5017 (clobber (reg:CC CC_REGNUM))
5018 (clobber (reg:SI GPR1_REGNUM))]
5019 "TARGET_HARD_DFP"
5020 "pfpo")
5021
5022 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
5023 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5024 (use (reg:SI GPR0_REGNUM))
5025 (clobber (reg:CC CC_REGNUM))
5026 (clobber (reg:SI GPR1_REGNUM))]
5027 "TARGET_HARD_DFP"
5028 "pfpo")
5029
5030 (define_expand "extend<BFP:mode><DFP_ALL:mode>2"
5031 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5032 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5033 (parallel
5034 [(set (reg:DFP_ALL FPR0_REGNUM)
5035 (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5036 (use (reg:SI GPR0_REGNUM))
5037 (clobber (reg:CC CC_REGNUM))
5038 (clobber (reg:SI GPR1_REGNUM))])
5039 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5040 (reg:DFP_ALL FPR0_REGNUM))]
5041 "TARGET_HARD_DFP
5042 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5043 {
5044 HOST_WIDE_INT flags;
5045
5046 flags = (PFPO_CONVERT |
5047 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5048 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5049
5050 operands[2] = GEN_INT (flags);
5051 })
5052
5053 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
5054 [(set (reg:DFP_ALL FPR4_REGNUM)
5055 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5056 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5057 (parallel
5058 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5059 (use (reg:SI GPR0_REGNUM))
5060 (clobber (reg:CC CC_REGNUM))
5061 (clobber (reg:SI GPR1_REGNUM))])
5062 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5063 "TARGET_HARD_DFP
5064 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
5065 {
5066 HOST_WIDE_INT flags;
5067
5068 flags = (PFPO_CONVERT |
5069 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5070 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5071
5072 operands[2] = GEN_INT (flags);
5073 })
5074
5075
5076 ;;
5077 ;; ARITHMETIC OPERATIONS
5078 ;;
5079 ; arithmetic operations set the ConditionCode,
5080 ; because of unpredictable Bits in Register for Halfword and Byte
5081 ; the ConditionCode can be set wrong in operations for Halfword and Byte
5082
5083 ;;
5084 ;;- Add instructions.
5085 ;;
5086
5087 ;
5088 ; addti3 instruction pattern(s).
5089 ;
5090
5091 (define_expand "addti3"
5092 [(parallel
5093 [(set (match_operand:TI 0 "register_operand" "")
5094 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5095 (match_operand:TI 2 "general_operand" "") ) )
5096 (clobber (reg:CC CC_REGNUM))])]
5097 "TARGET_ZARCH"
5098 {
5099 /* For z13 we have vaq which doesn't set CC. */
5100 if (TARGET_VX)
5101 {
5102 emit_insn (gen_rtx_SET (operands[0],
5103 gen_rtx_PLUS (TImode,
5104 copy_to_mode_reg (TImode, operands[1]),
5105 copy_to_mode_reg (TImode, operands[2]))));
5106 DONE;
5107 }
5108 })
5109
5110 (define_insn_and_split "*addti3"
5111 [(set (match_operand:TI 0 "register_operand" "=&d")
5112 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
5113 (match_operand:TI 2 "general_operand" "do") ) )
5114 (clobber (reg:CC CC_REGNUM))]
5115 "TARGET_ZARCH"
5116 "#"
5117 "&& reload_completed"
5118 [(parallel
5119 [(set (reg:CCL1 CC_REGNUM)
5120 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
5121 (match_dup 7)))
5122 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
5123 (parallel
5124 [(set (match_dup 3) (plus:DI
5125 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
5126 (match_dup 4)) (match_dup 5)))
5127 (clobber (reg:CC CC_REGNUM))])]
5128 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5129 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5130 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5131 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5132 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5133 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5134 [(set_attr "op_type" "*")
5135 (set_attr "cpu_facility" "*")])
5136
5137 ;
5138 ; adddi3 instruction pattern(s).
5139 ;
5140
5141 (define_expand "adddi3"
5142 [(parallel
5143 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5144 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5145 (match_operand:DI 2 "general_operand" "")))
5146 (clobber (reg:CC CC_REGNUM))])]
5147 ""
5148 "")
5149
5150 (define_insn "*adddi3_sign"
5151 [(set (match_operand:DI 0 "register_operand" "=d,d")
5152 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5153 (match_operand:DI 1 "register_operand" "0,0")))
5154 (clobber (reg:CC CC_REGNUM))]
5155 "TARGET_ZARCH"
5156 "@
5157 agfr\t%0,%2
5158 agf\t%0,%2"
5159 [(set_attr "op_type" "RRE,RXY")
5160 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5161
5162 (define_insn "*adddi3_zero_cc"
5163 [(set (reg CC_REGNUM)
5164 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5165 (match_operand:DI 1 "register_operand" "0,0"))
5166 (const_int 0)))
5167 (set (match_operand:DI 0 "register_operand" "=d,d")
5168 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
5169 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5170 "@
5171 algfr\t%0,%2
5172 algf\t%0,%2"
5173 [(set_attr "op_type" "RRE,RXY")
5174 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5175
5176 (define_insn "*adddi3_zero_cconly"
5177 [(set (reg CC_REGNUM)
5178 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5179 (match_operand:DI 1 "register_operand" "0,0"))
5180 (const_int 0)))
5181 (clobber (match_scratch:DI 0 "=d,d"))]
5182 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5183 "@
5184 algfr\t%0,%2
5185 algf\t%0,%2"
5186 [(set_attr "op_type" "RRE,RXY")
5187 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5188
5189 (define_insn "*adddi3_zero"
5190 [(set (match_operand:DI 0 "register_operand" "=d,d")
5191 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5192 (match_operand:DI 1 "register_operand" "0,0")))
5193 (clobber (reg:CC CC_REGNUM))]
5194 "TARGET_ZARCH"
5195 "@
5196 algfr\t%0,%2
5197 algf\t%0,%2"
5198 [(set_attr "op_type" "RRE,RXY")
5199 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5200
5201 (define_insn_and_split "*adddi3_31z"
5202 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5203 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5204 (match_operand:DI 2 "general_operand" "do") ) )
5205 (clobber (reg:CC CC_REGNUM))]
5206 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5207 "#"
5208 "&& reload_completed"
5209 [(parallel
5210 [(set (reg:CCL1 CC_REGNUM)
5211 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5212 (match_dup 7)))
5213 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5214 (parallel
5215 [(set (match_dup 3) (plus:SI
5216 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
5217 (match_dup 4)) (match_dup 5)))
5218 (clobber (reg:CC CC_REGNUM))])]
5219 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5220 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5221 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5222 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5223 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5224 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5225
5226 (define_insn_and_split "*adddi3_31"
5227 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5228 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5229 (match_operand:DI 2 "general_operand" "do") ) )
5230 (clobber (reg:CC CC_REGNUM))]
5231 "!TARGET_CPU_ZARCH"
5232 "#"
5233 "&& reload_completed"
5234 [(parallel
5235 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
5236 (clobber (reg:CC CC_REGNUM))])
5237 (parallel
5238 [(set (reg:CCL1 CC_REGNUM)
5239 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5240 (match_dup 7)))
5241 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5242 (set (pc)
5243 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
5244 (pc)
5245 (label_ref (match_dup 9))))
5246 (parallel
5247 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
5248 (clobber (reg:CC CC_REGNUM))])
5249 (match_dup 9)]
5250 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5251 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5252 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5253 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5254 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5255 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5256 operands[9] = gen_label_rtx ();")
5257
5258 ;
5259 ; addsi3 instruction pattern(s).
5260 ;
5261
5262 (define_expand "addsi3"
5263 [(parallel
5264 [(set (match_operand:SI 0 "nonimmediate_operand" "")
5265 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5266 (match_operand:SI 2 "general_operand" "")))
5267 (clobber (reg:CC CC_REGNUM))])]
5268 ""
5269 "")
5270
5271 (define_insn "*addsi3_sign"
5272 [(set (match_operand:SI 0 "register_operand" "=d,d")
5273 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
5274 (match_operand:SI 1 "register_operand" "0,0")))
5275 (clobber (reg:CC CC_REGNUM))]
5276 ""
5277 "@
5278 ah\t%0,%2
5279 ahy\t%0,%2"
5280 [(set_attr "op_type" "RX,RXY")
5281 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5282
5283 ;
5284 ; add(di|si)3 instruction pattern(s).
5285 ;
5286
5287 ; ark, agrk, ar, ahi, ahik, aghik, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
5288 (define_insn "*add<mode>3"
5289 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d, d, d,d,d,QS")
5290 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,d, 0, 0,0,0, 0")
5291 (match_operand:GPR 2 "general_operand" " d,d,K,K,Op,On,R,T, C") ) )
5292 (clobber (reg:CC CC_REGNUM))]
5293 ""
5294 "@
5295 a<g>r\t%0,%2
5296 a<g>rk\t%0,%1,%2
5297 a<g>hi\t%0,%h2
5298 a<g>hik\t%0,%1,%h2
5299 al<g>fi\t%0,%2
5300 sl<g>fi\t%0,%n2
5301 a<g>\t%0,%2
5302 a<y>\t%0,%2
5303 a<g>si\t%0,%c2"
5304 [(set_attr "op_type" "RR<E>,RRF,RI,RIE,RIL,RIL,RX<Y>,RXY,SIY")
5305 (set_attr "cpu_facility" "*,z196,*,z196,extimm,extimm,*,*,z10")
5306 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,z10_super_E1,z10_super_E1,
5307 z10_super_E1,z10_super_E1,z10_super_E1")])
5308
5309 ; alr, alfi, slfi, al, aly, alrk, alhsik, algr, algfi, slgfi, alg, alsi, algsi, algrk, alghsik
5310 (define_insn "*add<mode>3_carry1_cc"
5311 [(set (reg CC_REGNUM)
5312 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5313 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5314 (match_dup 1)))
5315 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,d")
5316 (plus:GPR (match_dup 1) (match_dup 2)))]
5317 "s390_match_ccmode (insn, CCL1mode)"
5318 "@
5319 al<g>r\t%0,%2
5320 al<g>rk\t%0,%1,%2
5321 al<g>fi\t%0,%2
5322 sl<g>fi\t%0,%n2
5323 al<g>hsik\t%0,%1,%h2
5324 al<g>\t%0,%2
5325 al<y>\t%0,%2
5326 al<g>si\t%0,%c2"
5327 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5328 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5329 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5330 z10_super_E1,z10_super_E1,z10_super_E1")])
5331
5332 ; alr, al, aly, algr, alg, alrk, algrk
5333 (define_insn "*add<mode>3_carry1_cconly"
5334 [(set (reg CC_REGNUM)
5335 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5336 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5337 (match_dup 1)))
5338 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5339 "s390_match_ccmode (insn, CCL1mode)"
5340 "@
5341 al<g>r\t%0,%2
5342 al<g>rk\t%0,%1,%2
5343 al<g>\t%0,%2
5344 al<y>\t%0,%2"
5345 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5346 (set_attr "cpu_facility" "*,z196,*,*")
5347 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5348
5349 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5350 (define_insn "*add<mode>3_carry2_cc"
5351 [(set (reg CC_REGNUM)
5352 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0, 0")
5353 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T, C"))
5354 (match_dup 2)))
5355 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,RS")
5356 (plus:GPR (match_dup 1) (match_dup 2)))]
5357 "s390_match_ccmode (insn, CCL1mode)"
5358 "@
5359 al<g>r\t%0,%2
5360 al<g>rk\t%0,%1,%2
5361 al<g>fi\t%0,%2
5362 sl<g>fi\t%0,%n2
5363 al<g>hsik\t%0,%1,%h2
5364 al<g>\t%0,%2
5365 al<y>\t%0,%2
5366 al<g>si\t%0,%c2"
5367 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5368 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5369 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5370 z10_super_E1,z10_super_E1,z10_super_E1")])
5371
5372 ; alr, al, aly, algr, alg, alrk, algrk
5373 (define_insn "*add<mode>3_carry2_cconly"
5374 [(set (reg CC_REGNUM)
5375 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5376 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5377 (match_dup 2)))
5378 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5379 "s390_match_ccmode (insn, CCL1mode)"
5380 "@
5381 al<g>r\t%0,%2
5382 al<g>rk\t%0,%1,%2
5383 al<g>\t%0,%2
5384 al<y>\t%0,%2"
5385 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5386 (set_attr "cpu_facility" "*,z196,*,*")
5387 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5388
5389 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5390 (define_insn "*add<mode>3_cc"
5391 [(set (reg CC_REGNUM)
5392 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0, 0")
5393 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T, C"))
5394 (const_int 0)))
5395 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,RS")
5396 (plus:GPR (match_dup 1) (match_dup 2)))]
5397 "s390_match_ccmode (insn, CCLmode)"
5398 "@
5399 al<g>r\t%0,%2
5400 al<g>rk\t%0,%1,%2
5401 al<g>fi\t%0,%2
5402 sl<g>fi\t%0,%n2
5403 al<g>hsik\t%0,%1,%h2
5404 al<g>\t%0,%2
5405 al<y>\t%0,%2
5406 al<g>si\t%0,%c2"
5407 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5408 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5409 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,
5410 *,z10_super_E1,z10_super_E1,z10_super_E1")])
5411
5412 ; alr, al, aly, algr, alg, alrk, algrk
5413 (define_insn "*add<mode>3_cconly"
5414 [(set (reg CC_REGNUM)
5415 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5416 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5417 (const_int 0)))
5418 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5419 "s390_match_ccmode (insn, CCLmode)"
5420 "@
5421 al<g>r\t%0,%2
5422 al<g>rk\t%0,%1,%2
5423 al<g>\t%0,%2
5424 al<y>\t%0,%2"
5425 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5426 (set_attr "cpu_facility" "*,z196,*,*")
5427 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5428
5429 ; alr, al, aly, algr, alg, alrk, algrk
5430 (define_insn "*add<mode>3_cconly2"
5431 [(set (reg CC_REGNUM)
5432 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5433 (neg:GPR (match_operand:GPR 2 "general_operand" "d,d,R,T"))))
5434 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5435 "s390_match_ccmode(insn, CCLmode)"
5436 "@
5437 al<g>r\t%0,%2
5438 al<g>rk\t%0,%1,%2
5439 al<g>\t%0,%2
5440 al<y>\t%0,%2"
5441 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5442 (set_attr "cpu_facility" "*,z196,*,*")
5443 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5444
5445 ; ahi, afi, aghi, agfi, asi, agsi
5446 (define_insn "*add<mode>3_imm_cc"
5447 [(set (reg CC_REGNUM)
5448 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" " 0, d,0, 0")
5449 (match_operand:GPR 2 "const_int_operand" " K, K,Os, C"))
5450 (const_int 0)))
5451 (set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,d,QS")
5452 (plus:GPR (match_dup 1) (match_dup 2)))]
5453 "s390_match_ccmode (insn, CCAmode)
5454 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
5455 || (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
5456 /* Avoid INT32_MIN on 32 bit. */
5457 && (!TARGET_ZARCH || INTVAL (operands[2]) != -0x7fffffff - 1)))"
5458 "@
5459 a<g>hi\t%0,%h2
5460 a<g>hik\t%0,%1,%h2
5461 a<g>fi\t%0,%2
5462 a<g>si\t%0,%c2"
5463 [(set_attr "op_type" "RI,RIE,RIL,SIY")
5464 (set_attr "cpu_facility" "*,z196,extimm,z10")
5465 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5466
5467 ;
5468 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
5469 ;
5470
5471 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5472 ; FIXME: wfadb does not clobber cc
5473 (define_insn "add<mode>3"
5474 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
5475 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>, 0,<v0>")
5476 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))
5477 (clobber (reg:CC CC_REGNUM))]
5478 "TARGET_HARD_FLOAT"
5479 "@
5480 a<xde><bt>r\t%0,<op1>%2
5481 a<xde>b\t%0,%2
5482 wfadb\t%v0,%v1,%v2"
5483 [(set_attr "op_type" "<RRer>,RXE,VRR")
5484 (set_attr "type" "fsimp<mode>")
5485 (set_attr "cpu_facility" "*,*,vec")])
5486
5487 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5488 (define_insn "*add<mode>3_cc"
5489 [(set (reg CC_REGNUM)
5490 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
5491 (match_operand:FP 2 "general_operand" " f,<Rf>"))
5492 (match_operand:FP 3 "const0_operand" "")))
5493 (set (match_operand:FP 0 "register_operand" "=f,f")
5494 (plus:FP (match_dup 1) (match_dup 2)))]
5495 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5496 "@
5497 a<xde><bt>r\t%0,<op1>%2
5498 a<xde>b\t%0,%2"
5499 [(set_attr "op_type" "<RRer>,RXE")
5500 (set_attr "type" "fsimp<mode>")])
5501
5502 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5503 (define_insn "*add<mode>3_cconly"
5504 [(set (reg CC_REGNUM)
5505 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
5506 (match_operand:FP 2 "general_operand" " f,<Rf>"))
5507 (match_operand:FP 3 "const0_operand" "")))
5508 (clobber (match_scratch:FP 0 "=f,f"))]
5509 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5510 "@
5511 a<xde><bt>r\t%0,<op1>%2
5512 a<xde>b\t%0,%2"
5513 [(set_attr "op_type" "<RRer>,RXE")
5514 (set_attr "type" "fsimp<mode>")])
5515
5516 ;
5517 ; Pointer add instruction patterns
5518 ;
5519
5520 ; This will match "*la_64"
5521 (define_expand "addptrdi3"
5522 [(set (match_operand:DI 0 "register_operand" "")
5523 (plus:DI (match_operand:DI 1 "register_operand" "")
5524 (match_operand:DI 2 "nonmemory_operand" "")))]
5525 "TARGET_64BIT"
5526 {
5527 if (GET_CODE (operands[2]) == CONST_INT)
5528 {
5529 HOST_WIDE_INT c = INTVAL (operands[2]);
5530
5531 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5532 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5533 {
5534 operands[2] = force_const_mem (DImode, operands[2]);
5535 operands[2] = force_reg (DImode, operands[2]);
5536 }
5537 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5538 operands[2] = force_reg (DImode, operands[2]);
5539 }
5540 })
5541
5542 ; For 31 bit we have to prevent the generated pattern from matching
5543 ; normal ADDs since la only does a 31 bit add. This is supposed to
5544 ; match "force_la_31".
5545 (define_expand "addptrsi3"
5546 [(parallel
5547 [(set (match_operand:SI 0 "register_operand" "")
5548 (plus:SI (match_operand:SI 1 "register_operand" "")
5549 (match_operand:SI 2 "nonmemory_operand" "")))
5550 (use (const_int 0))])]
5551 "!TARGET_64BIT"
5552 {
5553 if (GET_CODE (operands[2]) == CONST_INT)
5554 {
5555 HOST_WIDE_INT c = INTVAL (operands[2]);
5556
5557 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5558 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5559 {
5560 operands[2] = force_const_mem (SImode, operands[2]);
5561 operands[2] = force_reg (SImode, operands[2]);
5562 }
5563 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5564 operands[2] = force_reg (SImode, operands[2]);
5565 }
5566 })
5567
5568 ;;
5569 ;;- Subtract instructions.
5570 ;;
5571
5572 ;
5573 ; subti3 instruction pattern(s).
5574 ;
5575
5576 (define_expand "subti3"
5577 [(parallel
5578 [(set (match_operand:TI 0 "register_operand" "")
5579 (minus:TI (match_operand:TI 1 "register_operand" "")
5580 (match_operand:TI 2 "general_operand" "") ) )
5581 (clobber (reg:CC CC_REGNUM))])]
5582 "TARGET_ZARCH"
5583 {
5584 /* For z13 we have vaq which doesn't set CC. */
5585 if (TARGET_VX)
5586 {
5587 emit_insn (gen_rtx_SET (operands[0],
5588 gen_rtx_MINUS (TImode,
5589 operands[1],
5590 copy_to_mode_reg (TImode, operands[2]))));
5591 DONE;
5592 }
5593 })
5594
5595 (define_insn_and_split "*subti3"
5596 [(set (match_operand:TI 0 "register_operand" "=&d")
5597 (minus:TI (match_operand:TI 1 "register_operand" "0")
5598 (match_operand:TI 2 "general_operand" "do") ) )
5599 (clobber (reg:CC CC_REGNUM))]
5600 "TARGET_ZARCH"
5601 "#"
5602 "&& reload_completed"
5603 [(parallel
5604 [(set (reg:CCL2 CC_REGNUM)
5605 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
5606 (match_dup 7)))
5607 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
5608 (parallel
5609 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
5610 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
5611 (clobber (reg:CC CC_REGNUM))])]
5612 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5613 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5614 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5615 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5616 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5617 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5618 [(set_attr "op_type" "*")
5619 (set_attr "cpu_facility" "*")])
5620
5621 ;
5622 ; subdi3 instruction pattern(s).
5623 ;
5624
5625 (define_expand "subdi3"
5626 [(parallel
5627 [(set (match_operand:DI 0 "register_operand" "")
5628 (minus:DI (match_operand:DI 1 "register_operand" "")
5629 (match_operand:DI 2 "general_operand" "")))
5630 (clobber (reg:CC CC_REGNUM))])]
5631 ""
5632 "")
5633
5634 (define_insn "*subdi3_sign"
5635 [(set (match_operand:DI 0 "register_operand" "=d,d")
5636 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5637 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
5638 (clobber (reg:CC CC_REGNUM))]
5639 "TARGET_ZARCH"
5640 "@
5641 sgfr\t%0,%2
5642 sgf\t%0,%2"
5643 [(set_attr "op_type" "RRE,RXY")
5644 (set_attr "z10prop" "z10_c,*")
5645 (set_attr "z196prop" "z196_cracked")])
5646
5647 (define_insn "*subdi3_zero_cc"
5648 [(set (reg CC_REGNUM)
5649 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5650 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
5651 (const_int 0)))
5652 (set (match_operand:DI 0 "register_operand" "=d,d")
5653 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
5654 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5655 "@
5656 slgfr\t%0,%2
5657 slgf\t%0,%2"
5658 [(set_attr "op_type" "RRE,RXY")
5659 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5660
5661 (define_insn "*subdi3_zero_cconly"
5662 [(set (reg CC_REGNUM)
5663 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5664 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
5665 (const_int 0)))
5666 (clobber (match_scratch:DI 0 "=d,d"))]
5667 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5668 "@
5669 slgfr\t%0,%2
5670 slgf\t%0,%2"
5671 [(set_attr "op_type" "RRE,RXY")
5672 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5673
5674 (define_insn "*subdi3_zero"
5675 [(set (match_operand:DI 0 "register_operand" "=d,d")
5676 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5677 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
5678 (clobber (reg:CC CC_REGNUM))]
5679 "TARGET_ZARCH"
5680 "@
5681 slgfr\t%0,%2
5682 slgf\t%0,%2"
5683 [(set_attr "op_type" "RRE,RXY")
5684 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5685
5686 (define_insn_and_split "*subdi3_31z"
5687 [(set (match_operand:DI 0 "register_operand" "=&d")
5688 (minus:DI (match_operand:DI 1 "register_operand" "0")
5689 (match_operand:DI 2 "general_operand" "do") ) )
5690 (clobber (reg:CC CC_REGNUM))]
5691 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5692 "#"
5693 "&& reload_completed"
5694 [(parallel
5695 [(set (reg:CCL2 CC_REGNUM)
5696 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5697 (match_dup 7)))
5698 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5699 (parallel
5700 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
5701 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
5702 (clobber (reg:CC CC_REGNUM))])]
5703 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5704 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5705 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5706 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5707 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5708 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5709
5710 (define_insn_and_split "*subdi3_31"
5711 [(set (match_operand:DI 0 "register_operand" "=&d")
5712 (minus:DI (match_operand:DI 1 "register_operand" "0")
5713 (match_operand:DI 2 "general_operand" "do") ) )
5714 (clobber (reg:CC CC_REGNUM))]
5715 "!TARGET_CPU_ZARCH"
5716 "#"
5717 "&& reload_completed"
5718 [(parallel
5719 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
5720 (clobber (reg:CC CC_REGNUM))])
5721 (parallel
5722 [(set (reg:CCL2 CC_REGNUM)
5723 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5724 (match_dup 7)))
5725 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5726 (set (pc)
5727 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
5728 (pc)
5729 (label_ref (match_dup 9))))
5730 (parallel
5731 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
5732 (clobber (reg:CC CC_REGNUM))])
5733 (match_dup 9)]
5734 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5735 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5736 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5737 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5738 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5739 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5740 operands[9] = gen_label_rtx ();")
5741
5742 ;
5743 ; subsi3 instruction pattern(s).
5744 ;
5745
5746 (define_expand "subsi3"
5747 [(parallel
5748 [(set (match_operand:SI 0 "register_operand" "")
5749 (minus:SI (match_operand:SI 1 "register_operand" "")
5750 (match_operand:SI 2 "general_operand" "")))
5751 (clobber (reg:CC CC_REGNUM))])]
5752 ""
5753 "")
5754
5755 (define_insn "*subsi3_sign"
5756 [(set (match_operand:SI 0 "register_operand" "=d,d")
5757 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
5758 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
5759 (clobber (reg:CC CC_REGNUM))]
5760 ""
5761 "@
5762 sh\t%0,%2
5763 shy\t%0,%2"
5764 [(set_attr "op_type" "RX,RXY")
5765 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5766
5767 ;
5768 ; sub(di|si)3 instruction pattern(s).
5769 ;
5770
5771 ; sr, s, sy, sgr, sg, srk, sgrk
5772 (define_insn "*sub<mode>3"
5773 [(set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5774 (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5775 (match_operand:GPR 2 "general_operand" "d,d,R,T") ) )
5776 (clobber (reg:CC CC_REGNUM))]
5777 ""
5778 "@
5779 s<g>r\t%0,%2
5780 s<g>rk\t%0,%1,%2
5781 s<g>\t%0,%2
5782 s<y>\t%0,%2"
5783 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5784 (set_attr "cpu_facility" "*,z196,*,*")
5785 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5786
5787 ; slr, sl, sly, slgr, slg, slrk, slgrk
5788 (define_insn "*sub<mode>3_borrow_cc"
5789 [(set (reg CC_REGNUM)
5790 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5791 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5792 (match_dup 1)))
5793 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5794 (minus:GPR (match_dup 1) (match_dup 2)))]
5795 "s390_match_ccmode (insn, CCL2mode)"
5796 "@
5797 sl<g>r\t%0,%2
5798 sl<g>rk\t%0,%1,%2
5799 sl<g>\t%0,%2
5800 sl<y>\t%0,%2"
5801 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5802 (set_attr "cpu_facility" "*,z196,*,*")
5803 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5804
5805 ; slr, sl, sly, slgr, slg, slrk, slgrk
5806 (define_insn "*sub<mode>3_borrow_cconly"
5807 [(set (reg CC_REGNUM)
5808 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5809 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5810 (match_dup 1)))
5811 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5812 "s390_match_ccmode (insn, CCL2mode)"
5813 "@
5814 sl<g>r\t%0,%2
5815 sl<g>rk\t%0,%1,%2
5816 sl<g>\t%0,%2
5817 sl<y>\t%0,%2"
5818 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5819 (set_attr "cpu_facility" "*,z196,*,*")
5820 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5821
5822 ; slr, sl, sly, slgr, slg, slrk, slgrk
5823 (define_insn "*sub<mode>3_cc"
5824 [(set (reg CC_REGNUM)
5825 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5826 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5827 (const_int 0)))
5828 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5829 (minus:GPR (match_dup 1) (match_dup 2)))]
5830 "s390_match_ccmode (insn, CCLmode)"
5831 "@
5832 sl<g>r\t%0,%2
5833 sl<g>rk\t%0,%1,%2
5834 sl<g>\t%0,%2
5835 sl<y>\t%0,%2"
5836 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5837 (set_attr "cpu_facility" "*,z196,*,*")
5838 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5839
5840 ; slr, sl, sly, slgr, slg, slrk, slgrk
5841 (define_insn "*sub<mode>3_cc2"
5842 [(set (reg CC_REGNUM)
5843 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
5844 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
5845 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5846 (minus:GPR (match_dup 1) (match_dup 2)))]
5847 "s390_match_ccmode (insn, CCL3mode)"
5848 "@
5849 sl<g>r\t%0,%2
5850 sl<g>rk\t%0,%1,%2
5851 sl<g>\t%0,%2
5852 sl<y>\t%0,%2"
5853 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5854 (set_attr "cpu_facility" "*,z196,*,*")
5855 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5856
5857 ; slr, sl, sly, slgr, slg, slrk, slgrk
5858 (define_insn "*sub<mode>3_cconly"
5859 [(set (reg CC_REGNUM)
5860 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5861 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5862 (const_int 0)))
5863 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5864 "s390_match_ccmode (insn, CCLmode)"
5865 "@
5866 sl<g>r\t%0,%2
5867 sl<g>rk\t%0,%1,%2
5868 sl<g>\t%0,%2
5869 sl<y>\t%0,%2"
5870 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5871 (set_attr "cpu_facility" "*,z196,*,*")
5872 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5873
5874
5875 ; slr, sl, sly, slgr, slg, slrk, slgrk
5876 (define_insn "*sub<mode>3_cconly2"
5877 [(set (reg CC_REGNUM)
5878 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
5879 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
5880 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5881 "s390_match_ccmode (insn, CCL3mode)"
5882 "@
5883 sl<g>r\t%0,%2
5884 sl<g>rk\t%0,%1,%2
5885 sl<g>\t%0,%2
5886 sl<y>\t%0,%2"
5887 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5888 (set_attr "cpu_facility" "*,z196,*,*")
5889 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5890
5891
5892 ;
5893 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
5894 ;
5895
5896 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5897 (define_insn "sub<mode>3"
5898 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
5899 (minus:FP (match_operand:FP 1 "register_operand" "<f0>, 0,<v0>")
5900 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))
5901 (clobber (reg:CC CC_REGNUM))]
5902 "TARGET_HARD_FLOAT"
5903 "@
5904 s<xde><bt>r\t%0,<op1>%2
5905 s<xde>b\t%0,%2
5906 wfsdb\t%v0,%v1,%v2"
5907 [(set_attr "op_type" "<RRer>,RXE,VRR")
5908 (set_attr "type" "fsimp<mode>")
5909 (set_attr "cpu_facility" "*,*,vec")])
5910
5911 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5912 (define_insn "*sub<mode>3_cc"
5913 [(set (reg CC_REGNUM)
5914 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
5915 (match_operand:FP 2 "general_operand" "f,<Rf>"))
5916 (match_operand:FP 3 "const0_operand" "")))
5917 (set (match_operand:FP 0 "register_operand" "=f,f")
5918 (minus:FP (match_dup 1) (match_dup 2)))]
5919 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5920 "@
5921 s<xde><bt>r\t%0,<op1>%2
5922 s<xde>b\t%0,%2"
5923 [(set_attr "op_type" "<RRer>,RXE")
5924 (set_attr "type" "fsimp<mode>")])
5925
5926 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5927 (define_insn "*sub<mode>3_cconly"
5928 [(set (reg CC_REGNUM)
5929 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
5930 (match_operand:FP 2 "general_operand" "f,<Rf>"))
5931 (match_operand:FP 3 "const0_operand" "")))
5932 (clobber (match_scratch:FP 0 "=f,f"))]
5933 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5934 "@
5935 s<xde><bt>r\t%0,<op1>%2
5936 s<xde>b\t%0,%2"
5937 [(set_attr "op_type" "<RRer>,RXE")
5938 (set_attr "type" "fsimp<mode>")])
5939
5940
5941 ;;
5942 ;;- Conditional add/subtract instructions.
5943 ;;
5944
5945 ;
5946 ; add(di|si)cc instruction pattern(s).
5947 ;
5948
5949 ; the following 4 patterns are used when the result of an add with
5950 ; carry is checked for an overflow condition
5951
5952 ; op1 + op2 + c < op1
5953
5954 ; alcr, alc, alcgr, alcg
5955 (define_insn "*add<mode>3_alc_carry1_cc"
5956 [(set (reg CC_REGNUM)
5957 (compare
5958 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5959 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5960 (match_operand:GPR 2 "general_operand" "d,RT"))
5961 (match_dup 1)))
5962 (set (match_operand:GPR 0 "register_operand" "=d,d")
5963 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
5964 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5965 "@
5966 alc<g>r\t%0,%2
5967 alc<g>\t%0,%2"
5968 [(set_attr "op_type" "RRE,RXY")
5969 (set_attr "z196prop" "z196_alone,z196_alone")])
5970
5971 ; alcr, alc, alcgr, alcg
5972 (define_insn "*add<mode>3_alc_carry1_cconly"
5973 [(set (reg CC_REGNUM)
5974 (compare
5975 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5976 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5977 (match_operand:GPR 2 "general_operand" "d,RT"))
5978 (match_dup 1)))
5979 (clobber (match_scratch:GPR 0 "=d,d"))]
5980 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5981 "@
5982 alc<g>r\t%0,%2
5983 alc<g>\t%0,%2"
5984 [(set_attr "op_type" "RRE,RXY")
5985 (set_attr "z196prop" "z196_alone,z196_alone")])
5986
5987 ; op1 + op2 + c < op2
5988
5989 ; alcr, alc, alcgr, alcg
5990 (define_insn "*add<mode>3_alc_carry2_cc"
5991 [(set (reg CC_REGNUM)
5992 (compare
5993 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5994 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5995 (match_operand:GPR 2 "general_operand" "d,RT"))
5996 (match_dup 2)))
5997 (set (match_operand:GPR 0 "register_operand" "=d,d")
5998 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
5999 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6000 "@
6001 alc<g>r\t%0,%2
6002 alc<g>\t%0,%2"
6003 [(set_attr "op_type" "RRE,RXY")])
6004
6005 ; alcr, alc, alcgr, alcg
6006 (define_insn "*add<mode>3_alc_carry2_cconly"
6007 [(set (reg CC_REGNUM)
6008 (compare
6009 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6010 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6011 (match_operand:GPR 2 "general_operand" "d,RT"))
6012 (match_dup 2)))
6013 (clobber (match_scratch:GPR 0 "=d,d"))]
6014 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6015 "@
6016 alc<g>r\t%0,%2
6017 alc<g>\t%0,%2"
6018 [(set_attr "op_type" "RRE,RXY")])
6019
6020 ; alcr, alc, alcgr, alcg
6021 (define_insn "*add<mode>3_alc_cc"
6022 [(set (reg CC_REGNUM)
6023 (compare
6024 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6025 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6026 (match_operand:GPR 2 "general_operand" "d,RT"))
6027 (const_int 0)))
6028 (set (match_operand:GPR 0 "register_operand" "=d,d")
6029 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6030 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6031 "@
6032 alc<g>r\t%0,%2
6033 alc<g>\t%0,%2"
6034 [(set_attr "op_type" "RRE,RXY")])
6035
6036 ; alcr, alc, alcgr, alcg
6037 (define_insn "*add<mode>3_alc"
6038 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6039 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6040 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6041 (match_operand:GPR 2 "general_operand" "d,RT")))
6042 (clobber (reg:CC CC_REGNUM))]
6043 "TARGET_CPU_ZARCH"
6044 "@
6045 alc<g>r\t%0,%2
6046 alc<g>\t%0,%2"
6047 [(set_attr "op_type" "RRE,RXY")])
6048
6049 ; slbr, slb, slbgr, slbg
6050 (define_insn "*sub<mode>3_slb_cc"
6051 [(set (reg CC_REGNUM)
6052 (compare
6053 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6054 (match_operand:GPR 2 "general_operand" "d,RT"))
6055 (match_operand:GPR 3 "s390_slb_comparison" ""))
6056 (const_int 0)))
6057 (set (match_operand:GPR 0 "register_operand" "=d,d")
6058 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
6059 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6060 "@
6061 slb<g>r\t%0,%2
6062 slb<g>\t%0,%2"
6063 [(set_attr "op_type" "RRE,RXY")
6064 (set_attr "z10prop" "z10_c,*")])
6065
6066 ; slbr, slb, slbgr, slbg
6067 (define_insn "*sub<mode>3_slb"
6068 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6069 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6070 (match_operand:GPR 2 "general_operand" "d,RT"))
6071 (match_operand:GPR 3 "s390_slb_comparison" "")))
6072 (clobber (reg:CC CC_REGNUM))]
6073 "TARGET_CPU_ZARCH"
6074 "@
6075 slb<g>r\t%0,%2
6076 slb<g>\t%0,%2"
6077 [(set_attr "op_type" "RRE,RXY")
6078 (set_attr "z10prop" "z10_c,*")])
6079
6080 (define_expand "add<mode>cc"
6081 [(match_operand:GPR 0 "register_operand" "")
6082 (match_operand 1 "comparison_operator" "")
6083 (match_operand:GPR 2 "register_operand" "")
6084 (match_operand:GPR 3 "const_int_operand" "")]
6085 "TARGET_CPU_ZARCH"
6086 "if (!s390_expand_addcc (GET_CODE (operands[1]),
6087 XEXP (operands[1], 0), XEXP (operands[1], 1),
6088 operands[0], operands[2],
6089 operands[3])) FAIL; DONE;")
6090
6091 ;
6092 ; scond instruction pattern(s).
6093 ;
6094
6095 (define_insn_and_split "*scond<mode>"
6096 [(set (match_operand:GPR 0 "register_operand" "=&d")
6097 (match_operand:GPR 1 "s390_alc_comparison" ""))
6098 (clobber (reg:CC CC_REGNUM))]
6099 "TARGET_CPU_ZARCH"
6100 "#"
6101 "&& reload_completed"
6102 [(set (match_dup 0) (const_int 0))
6103 (parallel
6104 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
6105 (match_dup 0)))
6106 (clobber (reg:CC CC_REGNUM))])]
6107 "")
6108
6109 (define_insn_and_split "*scond<mode>_neg"
6110 [(set (match_operand:GPR 0 "register_operand" "=&d")
6111 (match_operand:GPR 1 "s390_slb_comparison" ""))
6112 (clobber (reg:CC CC_REGNUM))]
6113 "TARGET_CPU_ZARCH"
6114 "#"
6115 "&& reload_completed"
6116 [(set (match_dup 0) (const_int 0))
6117 (parallel
6118 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
6119 (match_dup 1)))
6120 (clobber (reg:CC CC_REGNUM))])
6121 (parallel
6122 [(set (match_dup 0) (neg:GPR (match_dup 0)))
6123 (clobber (reg:CC CC_REGNUM))])]
6124 "")
6125
6126
6127 (define_expand "cstore<mode>4"
6128 [(set (match_operand:SI 0 "register_operand" "")
6129 (match_operator:SI 1 "s390_scond_operator"
6130 [(match_operand:GPR 2 "register_operand" "")
6131 (match_operand:GPR 3 "general_operand" "")]))]
6132 "TARGET_CPU_ZARCH"
6133 "if (!s390_expand_addcc (GET_CODE (operands[1]), operands[2], operands[3],
6134 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
6135
6136 (define_expand "cstorecc4"
6137 [(parallel
6138 [(set (match_operand:SI 0 "register_operand" "")
6139 (match_operator:SI 1 "s390_eqne_operator"
6140 [(match_operand:CCZ1 2 "register_operand")
6141 (match_operand 3 "const0_operand")]))
6142 (clobber (reg:CC CC_REGNUM))])]
6143 ""
6144 "emit_insn (gen_sne (operands[0], operands[2]));
6145 if (GET_CODE (operands[1]) == EQ)
6146 emit_insn (gen_xorsi3 (operands[0], operands[0], const1_rtx));
6147 DONE;")
6148
6149 (define_insn_and_split "sne"
6150 [(set (match_operand:SI 0 "register_operand" "=d")
6151 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
6152 (const_int 0)))
6153 (clobber (reg:CC CC_REGNUM))]
6154 ""
6155 "#"
6156 "reload_completed"
6157 [(parallel
6158 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
6159 (clobber (reg:CC CC_REGNUM))])])
6160
6161
6162 ;;
6163 ;; - Conditional move instructions (introduced with z196)
6164 ;;
6165
6166 (define_expand "mov<mode>cc"
6167 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
6168 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
6169 (match_operand:GPR 2 "nonimmediate_operand" "")
6170 (match_operand:GPR 3 "nonimmediate_operand" "")))]
6171 "TARGET_Z196"
6172 {
6173 /* Emit the comparison insn in case we do not already have a comparison result. */
6174 if (!s390_comparison (operands[1], VOIDmode))
6175 operands[1] = s390_emit_compare (GET_CODE (operands[1]),
6176 XEXP (operands[1], 0),
6177 XEXP (operands[1], 1));
6178 })
6179
6180 ; locr, loc, stoc, locgr, locg, stocg
6181 (define_insn_and_split "*mov<mode>cc"
6182 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,QS,QS,&d")
6183 (if_then_else:GPR
6184 (match_operator 1 "s390_comparison"
6185 [(match_operand 2 "cc_reg_operand" " c,c, c, c, c, c, c")
6186 (match_operand 5 "const_int_operand" "")])
6187 (match_operand:GPR 3 "nonimmediate_operand" " d,0,QS, 0, d, 0,QS")
6188 (match_operand:GPR 4 "nonimmediate_operand" " 0,d, 0,QS, 0, d,QS")))]
6189 "TARGET_Z196"
6190 "@
6191 loc<g>r%C1\t%0,%3
6192 loc<g>r%D1\t%0,%4
6193 loc<g>%C1\t%0,%3
6194 loc<g>%D1\t%0,%4
6195 stoc<g>%C1\t%3,%0
6196 stoc<g>%D1\t%4,%0
6197 #"
6198 "&& reload_completed
6199 && MEM_P (operands[3]) && MEM_P (operands[4])"
6200 [(set (match_dup 0)
6201 (if_then_else:GPR
6202 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6203 (match_dup 3)
6204 (match_dup 0)))
6205 (set (match_dup 0)
6206 (if_then_else:GPR
6207 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6208 (match_dup 0)
6209 (match_dup 4)))]
6210 ""
6211 [(set_attr "op_type" "RRF,RRF,RSY,RSY,RSY,RSY,*")])
6212
6213 ;;
6214 ;;- Multiply instructions.
6215 ;;
6216
6217 ;
6218 ; muldi3 instruction pattern(s).
6219 ;
6220
6221 (define_insn "*muldi3_sign"
6222 [(set (match_operand:DI 0 "register_operand" "=d,d")
6223 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
6224 (match_operand:DI 1 "register_operand" "0,0")))]
6225 "TARGET_ZARCH"
6226 "@
6227 msgfr\t%0,%2
6228 msgf\t%0,%2"
6229 [(set_attr "op_type" "RRE,RXY")
6230 (set_attr "type" "imuldi")])
6231
6232 (define_insn "muldi3"
6233 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
6234 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
6235 (match_operand:DI 2 "general_operand" "d,K,RT,Os")))]
6236 "TARGET_ZARCH"
6237 "@
6238 msgr\t%0,%2
6239 mghi\t%0,%h2
6240 msg\t%0,%2
6241 msgfi\t%0,%2"
6242 [(set_attr "op_type" "RRE,RI,RXY,RIL")
6243 (set_attr "type" "imuldi")
6244 (set_attr "cpu_facility" "*,*,*,z10")])
6245
6246 ;
6247 ; mulsi3 instruction pattern(s).
6248 ;
6249
6250 (define_insn "*mulsi3_sign"
6251 [(set (match_operand:SI 0 "register_operand" "=d,d")
6252 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
6253 (match_operand:SI 1 "register_operand" "0,0")))]
6254 ""
6255 "@
6256 mh\t%0,%2
6257 mhy\t%0,%2"
6258 [(set_attr "op_type" "RX,RXY")
6259 (set_attr "type" "imulhi")
6260 (set_attr "cpu_facility" "*,z10")])
6261
6262 (define_insn "mulsi3"
6263 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
6264 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
6265 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
6266 ""
6267 "@
6268 msr\t%0,%2
6269 mhi\t%0,%h2
6270 ms\t%0,%2
6271 msy\t%0,%2
6272 msfi\t%0,%2"
6273 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
6274 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
6275 (set_attr "cpu_facility" "*,*,*,*,z10")])
6276
6277 ;
6278 ; mulsidi3 instruction pattern(s).
6279 ;
6280
6281 (define_insn "mulsidi3"
6282 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
6283 (mult:DI (sign_extend:DI
6284 (match_operand:SI 1 "register_operand" "%0,0,0"))
6285 (sign_extend:DI
6286 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
6287 "!TARGET_ZARCH"
6288 "@
6289 mr\t%0,%2
6290 m\t%0,%2
6291 mfy\t%0,%2"
6292 [(set_attr "op_type" "RR,RX,RXY")
6293 (set_attr "type" "imulsi")
6294 (set_attr "cpu_facility" "*,*,z10")])
6295
6296 ;
6297 ; umul instruction pattern(s).
6298 ;
6299
6300 ; mlr, ml, mlgr, mlg
6301 (define_insn "umul<dwh><mode>3"
6302 [(set (match_operand:DW 0 "register_operand" "=d, d")
6303 (mult:DW (zero_extend:DW
6304 (match_operand:<DWH> 1 "register_operand" "%0, 0"))
6305 (zero_extend:DW
6306 (match_operand:<DWH> 2 "nonimmediate_operand" " d,RT"))))]
6307 "TARGET_CPU_ZARCH"
6308 "@
6309 ml<tg>r\t%0,%2
6310 ml<tg>\t%0,%2"
6311 [(set_attr "op_type" "RRE,RXY")
6312 (set_attr "type" "imul<dwh>")])
6313
6314 ;
6315 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
6316 ;
6317
6318 ; mxbr, mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
6319 (define_insn "mul<mode>3"
6320 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
6321 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>, 0,<v0>")
6322 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))]
6323 "TARGET_HARD_FLOAT"
6324 "@
6325 m<xdee><bt>r\t%0,<op1>%2
6326 m<xdee>b\t%0,%2
6327 wfmdb\t%v0,%v1,%v2"
6328 [(set_attr "op_type" "<RRer>,RXE,VRR")
6329 (set_attr "type" "fmul<mode>")
6330 (set_attr "cpu_facility" "*,*,vec")])
6331
6332 ; madbr, maebr, maxb, madb, maeb
6333 (define_insn "fma<mode>4"
6334 [(set (match_operand:DSF 0 "register_operand" "=f,f,<vf>")
6335 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,<vf>")
6336 (match_operand:DSF 2 "nonimmediate_operand" "f,R,<vf>")
6337 (match_operand:DSF 3 "register_operand" "0,0,<v0>")))]
6338 "TARGET_HARD_FLOAT"
6339 "@
6340 ma<xde>br\t%0,%1,%2
6341 ma<xde>b\t%0,%1,%2
6342 wfmadb\t%v0,%v1,%v2,%v3"
6343 [(set_attr "op_type" "RRE,RXE,VRR")
6344 (set_attr "type" "fmadd<mode>")
6345 (set_attr "cpu_facility" "*,*,vec")])
6346
6347 ; msxbr, msdbr, msebr, msxb, msdb, mseb
6348 (define_insn "fms<mode>4"
6349 [(set (match_operand:DSF 0 "register_operand" "=f,f,<vf>")
6350 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,<vf>")
6351 (match_operand:DSF 2 "nonimmediate_operand" "f,R,<vf>")
6352 (neg:DSF (match_operand:DSF 3 "register_operand" "0,0,<v0>"))))]
6353 "TARGET_HARD_FLOAT"
6354 "@
6355 ms<xde>br\t%0,%1,%2
6356 ms<xde>b\t%0,%1,%2
6357 wfmsdb\t%v0,%v1,%v2,%v3"
6358 [(set_attr "op_type" "RRE,RXE,VRR")
6359 (set_attr "type" "fmadd<mode>")
6360 (set_attr "cpu_facility" "*,*,vec")])
6361
6362 ;;
6363 ;;- Divide and modulo instructions.
6364 ;;
6365
6366 ;
6367 ; divmoddi4 instruction pattern(s).
6368 ;
6369
6370 (define_expand "divmoddi4"
6371 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6372 (div:DI (match_operand:DI 1 "register_operand" "")
6373 (match_operand:DI 2 "general_operand" "")))
6374 (set (match_operand:DI 3 "general_operand" "")
6375 (mod:DI (match_dup 1) (match_dup 2)))])
6376 (clobber (match_dup 4))]
6377 "TARGET_ZARCH"
6378 {
6379 rtx insn, div_equal, mod_equal;
6380
6381 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
6382 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
6383
6384 operands[4] = gen_reg_rtx(TImode);
6385 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
6386
6387 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6388 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6389
6390 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6391 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6392
6393 DONE;
6394 })
6395
6396 (define_insn "divmodtidi3"
6397 [(set (match_operand:TI 0 "register_operand" "=d,d")
6398 (ior:TI
6399 (ashift:TI
6400 (zero_extend:TI
6401 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6402 (match_operand:DI 2 "general_operand" "d,RT")))
6403 (const_int 64))
6404 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
6405 "TARGET_ZARCH"
6406 "@
6407 dsgr\t%0,%2
6408 dsg\t%0,%2"
6409 [(set_attr "op_type" "RRE,RXY")
6410 (set_attr "type" "idiv")])
6411
6412 (define_insn "divmodtisi3"
6413 [(set (match_operand:TI 0 "register_operand" "=d,d")
6414 (ior:TI
6415 (ashift:TI
6416 (zero_extend:TI
6417 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6418 (sign_extend:DI
6419 (match_operand:SI 2 "nonimmediate_operand" "d,RT"))))
6420 (const_int 64))
6421 (zero_extend:TI
6422 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
6423 "TARGET_ZARCH"
6424 "@
6425 dsgfr\t%0,%2
6426 dsgf\t%0,%2"
6427 [(set_attr "op_type" "RRE,RXY")
6428 (set_attr "type" "idiv")])
6429
6430 ;
6431 ; udivmoddi4 instruction pattern(s).
6432 ;
6433
6434 (define_expand "udivmoddi4"
6435 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6436 (udiv:DI (match_operand:DI 1 "general_operand" "")
6437 (match_operand:DI 2 "nonimmediate_operand" "")))
6438 (set (match_operand:DI 3 "general_operand" "")
6439 (umod:DI (match_dup 1) (match_dup 2)))])
6440 (clobber (match_dup 4))]
6441 "TARGET_ZARCH"
6442 {
6443 rtx insn, div_equal, mod_equal, equal;
6444
6445 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
6446 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
6447 equal = gen_rtx_IOR (TImode,
6448 gen_rtx_ASHIFT (TImode,
6449 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
6450 GEN_INT (64)),
6451 gen_rtx_ZERO_EXTEND (TImode, div_equal));
6452
6453 operands[4] = gen_reg_rtx(TImode);
6454 emit_clobber (operands[4]);
6455 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
6456 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
6457
6458 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
6459 set_unique_reg_note (insn, REG_EQUAL, equal);
6460
6461 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6462 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6463
6464 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6465 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6466
6467 DONE;
6468 })
6469
6470 (define_insn "udivmodtidi3"
6471 [(set (match_operand:TI 0 "register_operand" "=d,d")
6472 (ior:TI
6473 (ashift:TI
6474 (zero_extend:TI
6475 (truncate:DI
6476 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
6477 (zero_extend:TI
6478 (match_operand:DI 2 "nonimmediate_operand" "d,RT")))))
6479 (const_int 64))
6480 (zero_extend:TI
6481 (truncate:DI
6482 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
6483 "TARGET_ZARCH"
6484 "@
6485 dlgr\t%0,%2
6486 dlg\t%0,%2"
6487 [(set_attr "op_type" "RRE,RXY")
6488 (set_attr "type" "idiv")])
6489
6490 ;
6491 ; divmodsi4 instruction pattern(s).
6492 ;
6493
6494 (define_expand "divmodsi4"
6495 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6496 (div:SI (match_operand:SI 1 "general_operand" "")
6497 (match_operand:SI 2 "nonimmediate_operand" "")))
6498 (set (match_operand:SI 3 "general_operand" "")
6499 (mod:SI (match_dup 1) (match_dup 2)))])
6500 (clobber (match_dup 4))]
6501 "!TARGET_ZARCH"
6502 {
6503 rtx insn, div_equal, mod_equal, equal;
6504
6505 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
6506 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
6507 equal = gen_rtx_IOR (DImode,
6508 gen_rtx_ASHIFT (DImode,
6509 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6510 GEN_INT (32)),
6511 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6512
6513 operands[4] = gen_reg_rtx(DImode);
6514 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
6515
6516 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
6517 set_unique_reg_note (insn, REG_EQUAL, equal);
6518
6519 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6520 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6521
6522 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6523 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6524
6525 DONE;
6526 })
6527
6528 (define_insn "divmoddisi3"
6529 [(set (match_operand:DI 0 "register_operand" "=d,d")
6530 (ior:DI
6531 (ashift:DI
6532 (zero_extend:DI
6533 (truncate:SI
6534 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6535 (sign_extend:DI
6536 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
6537 (const_int 32))
6538 (zero_extend:DI
6539 (truncate:SI
6540 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
6541 "!TARGET_ZARCH"
6542 "@
6543 dr\t%0,%2
6544 d\t%0,%2"
6545 [(set_attr "op_type" "RR,RX")
6546 (set_attr "type" "idiv")])
6547
6548 ;
6549 ; udivsi3 and umodsi3 instruction pattern(s).
6550 ;
6551
6552 (define_expand "udivmodsi4"
6553 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6554 (udiv:SI (match_operand:SI 1 "general_operand" "")
6555 (match_operand:SI 2 "nonimmediate_operand" "")))
6556 (set (match_operand:SI 3 "general_operand" "")
6557 (umod:SI (match_dup 1) (match_dup 2)))])
6558 (clobber (match_dup 4))]
6559 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6560 {
6561 rtx insn, div_equal, mod_equal, equal;
6562
6563 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6564 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6565 equal = gen_rtx_IOR (DImode,
6566 gen_rtx_ASHIFT (DImode,
6567 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6568 GEN_INT (32)),
6569 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6570
6571 operands[4] = gen_reg_rtx(DImode);
6572 emit_clobber (operands[4]);
6573 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
6574 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
6575
6576 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
6577 set_unique_reg_note (insn, REG_EQUAL, equal);
6578
6579 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6580 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6581
6582 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6583 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6584
6585 DONE;
6586 })
6587
6588 (define_insn "udivmoddisi3"
6589 [(set (match_operand:DI 0 "register_operand" "=d,d")
6590 (ior:DI
6591 (ashift:DI
6592 (zero_extend:DI
6593 (truncate:SI
6594 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
6595 (zero_extend:DI
6596 (match_operand:SI 2 "nonimmediate_operand" "d,RT")))))
6597 (const_int 32))
6598 (zero_extend:DI
6599 (truncate:SI
6600 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
6601 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6602 "@
6603 dlr\t%0,%2
6604 dl\t%0,%2"
6605 [(set_attr "op_type" "RRE,RXY")
6606 (set_attr "type" "idiv")])
6607
6608 (define_expand "udivsi3"
6609 [(set (match_operand:SI 0 "register_operand" "=d")
6610 (udiv:SI (match_operand:SI 1 "general_operand" "")
6611 (match_operand:SI 2 "general_operand" "")))
6612 (clobber (match_dup 3))]
6613 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6614 {
6615 rtx insn, udiv_equal, umod_equal, equal;
6616
6617 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6618 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6619 equal = gen_rtx_IOR (DImode,
6620 gen_rtx_ASHIFT (DImode,
6621 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6622 GEN_INT (32)),
6623 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6624
6625 operands[3] = gen_reg_rtx (DImode);
6626
6627 if (CONSTANT_P (operands[2]))
6628 {
6629 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
6630 {
6631 rtx_code_label *label1 = gen_label_rtx ();
6632
6633 operands[1] = make_safe_from (operands[1], operands[0]);
6634 emit_move_insn (operands[0], const0_rtx);
6635 emit_cmp_and_jump_insns (operands[1], operands[2], LT, NULL_RTX,
6636 SImode, 1, label1);
6637 emit_move_insn (operands[0], const1_rtx);
6638 emit_label (label1);
6639 }
6640 else
6641 {
6642 operands[2] = force_reg (SImode, operands[2]);
6643 operands[2] = make_safe_from (operands[2], operands[0]);
6644
6645 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6646 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6647 operands[2]));
6648 set_unique_reg_note (insn, REG_EQUAL, equal);
6649
6650 insn = emit_move_insn (operands[0],
6651 gen_lowpart (SImode, operands[3]));
6652 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6653 }
6654 }
6655 else
6656 {
6657 rtx_code_label *label1 = gen_label_rtx ();
6658 rtx_code_label *label2 = gen_label_rtx ();
6659 rtx_code_label *label3 = gen_label_rtx ();
6660
6661 operands[1] = force_reg (SImode, operands[1]);
6662 operands[1] = make_safe_from (operands[1], operands[0]);
6663 operands[2] = force_reg (SImode, operands[2]);
6664 operands[2] = make_safe_from (operands[2], operands[0]);
6665
6666 emit_move_insn (operands[0], const0_rtx);
6667 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6668 SImode, 1, label3);
6669 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6670 SImode, 0, label2);
6671 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6672 SImode, 0, label1);
6673 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6674 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6675 operands[2]));
6676 set_unique_reg_note (insn, REG_EQUAL, equal);
6677
6678 insn = emit_move_insn (operands[0],
6679 gen_lowpart (SImode, operands[3]));
6680 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6681
6682 emit_jump (label3);
6683 emit_label (label1);
6684 emit_move_insn (operands[0], operands[1]);
6685 emit_jump (label3);
6686 emit_label (label2);
6687 emit_move_insn (operands[0], const1_rtx);
6688 emit_label (label3);
6689 }
6690 emit_move_insn (operands[0], operands[0]);
6691 DONE;
6692 })
6693
6694 (define_expand "umodsi3"
6695 [(set (match_operand:SI 0 "register_operand" "=d")
6696 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
6697 (match_operand:SI 2 "nonimmediate_operand" "")))
6698 (clobber (match_dup 3))]
6699 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6700 {
6701 rtx insn, udiv_equal, umod_equal, equal;
6702
6703 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6704 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6705 equal = gen_rtx_IOR (DImode,
6706 gen_rtx_ASHIFT (DImode,
6707 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6708 GEN_INT (32)),
6709 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6710
6711 operands[3] = gen_reg_rtx (DImode);
6712
6713 if (CONSTANT_P (operands[2]))
6714 {
6715 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
6716 {
6717 rtx_code_label *label1 = gen_label_rtx ();
6718
6719 operands[1] = make_safe_from (operands[1], operands[0]);
6720 emit_move_insn (operands[0], operands[1]);
6721 emit_cmp_and_jump_insns (operands[0], operands[2], LT, NULL_RTX,
6722 SImode, 1, label1);
6723 emit_insn (gen_abssi2 (operands[0], operands[2]));
6724 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
6725 emit_label (label1);
6726 }
6727 else
6728 {
6729 operands[2] = force_reg (SImode, operands[2]);
6730 operands[2] = make_safe_from (operands[2], operands[0]);
6731
6732 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6733 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6734 operands[2]));
6735 set_unique_reg_note (insn, REG_EQUAL, equal);
6736
6737 insn = emit_move_insn (operands[0],
6738 gen_highpart (SImode, operands[3]));
6739 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6740 }
6741 }
6742 else
6743 {
6744 rtx_code_label *label1 = gen_label_rtx ();
6745 rtx_code_label *label2 = gen_label_rtx ();
6746 rtx_code_label *label3 = gen_label_rtx ();
6747
6748 operands[1] = force_reg (SImode, operands[1]);
6749 operands[1] = make_safe_from (operands[1], operands[0]);
6750 operands[2] = force_reg (SImode, operands[2]);
6751 operands[2] = make_safe_from (operands[2], operands[0]);
6752
6753 emit_move_insn(operands[0], operands[1]);
6754 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6755 SImode, 1, label3);
6756 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6757 SImode, 0, label2);
6758 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6759 SImode, 0, label1);
6760 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6761 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6762 operands[2]));
6763 set_unique_reg_note (insn, REG_EQUAL, equal);
6764
6765 insn = emit_move_insn (operands[0],
6766 gen_highpart (SImode, operands[3]));
6767 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6768
6769 emit_jump (label3);
6770 emit_label (label1);
6771 emit_move_insn (operands[0], const0_rtx);
6772 emit_jump (label3);
6773 emit_label (label2);
6774 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
6775 emit_label (label3);
6776 }
6777 DONE;
6778 })
6779
6780 ;
6781 ; div(df|sf)3 instruction pattern(s).
6782 ;
6783
6784 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
6785 (define_insn "div<mode>3"
6786 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
6787 (div:FP (match_operand:FP 1 "register_operand" "<f0>, 0,<v0>")
6788 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))]
6789 "TARGET_HARD_FLOAT"
6790 "@
6791 d<xde><bt>r\t%0,<op1>%2
6792 d<xde>b\t%0,%2
6793 wfddb\t%v0,%v1,%v2"
6794 [(set_attr "op_type" "<RRer>,RXE,VRR")
6795 (set_attr "type" "fdiv<mode>")
6796 (set_attr "cpu_facility" "*,*,vec")])
6797
6798
6799 ;;
6800 ;;- And instructions.
6801 ;;
6802
6803 (define_expand "and<mode>3"
6804 [(set (match_operand:INT 0 "nonimmediate_operand" "")
6805 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
6806 (match_operand:INT 2 "general_operand" "")))
6807 (clobber (reg:CC CC_REGNUM))]
6808 ""
6809 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
6810
6811 ;
6812 ; anddi3 instruction pattern(s).
6813 ;
6814
6815 (define_insn "*anddi3_cc"
6816 [(set (reg CC_REGNUM)
6817 (compare
6818 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0, d")
6819 (match_operand:DI 2 "general_operand" " d,d,RT,NxxDq"))
6820 (const_int 0)))
6821 (set (match_operand:DI 0 "register_operand" "=d,d, d, d")
6822 (and:DI (match_dup 1) (match_dup 2)))]
6823 "TARGET_ZARCH && s390_match_ccmode(insn, CCTmode)"
6824 "@
6825 ngr\t%0,%2
6826 ngrk\t%0,%1,%2
6827 ng\t%0,%2
6828 risbg\t%0,%1,%s2,128+%e2,0"
6829 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6830 (set_attr "cpu_facility" "*,z196,*,z10")
6831 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6832
6833 (define_insn "*anddi3_cconly"
6834 [(set (reg CC_REGNUM)
6835 (compare
6836 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0, d")
6837 (match_operand:DI 2 "general_operand" " d,d,RT,NxxDq"))
6838 (const_int 0)))
6839 (clobber (match_scratch:DI 0 "=d,d, d, d"))]
6840 "TARGET_ZARCH
6841 && s390_match_ccmode(insn, CCTmode)
6842 /* Do not steal TM patterns. */
6843 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
6844 "@
6845 ngr\t%0,%2
6846 ngrk\t%0,%1,%2
6847 ng\t%0,%2
6848 risbg\t%0,%1,%s2,128+%e2,0"
6849 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6850 (set_attr "cpu_facility" "*,z196,*,z10")
6851 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6852
6853 (define_insn "*anddi3"
6854 [(set (match_operand:DI 0 "nonimmediate_operand"
6855 "=d,d, d, d, d, d, d, d,d,d, d, d, AQ,Q")
6856 (and:DI
6857 (match_operand:DI 1 "nonimmediate_operand"
6858 "%d,o, 0, 0, 0, 0, 0, 0,0,d, 0, d, 0,0")
6859 (match_operand:DI 2 "general_operand"
6860 "M, M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,d,RT,NxxDq,NxQDF,Q")))
6861 (clobber (reg:CC CC_REGNUM))]
6862 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6863 "@
6864 #
6865 #
6866 nihh\t%0,%j2
6867 nihl\t%0,%j2
6868 nilh\t%0,%j2
6869 nill\t%0,%j2
6870 nihf\t%0,%m2
6871 nilf\t%0,%m2
6872 ngr\t%0,%2
6873 ngrk\t%0,%1,%2
6874 ng\t%0,%2
6875 risbg\t%0,%1,%s2,128+%e2,0
6876 #
6877 #"
6878 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,RIE,SI,SS")
6879 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,z196,*,z10,*,*")
6880 (set_attr "z10prop" "*,
6881 *,
6882 z10_super_E1,
6883 z10_super_E1,
6884 z10_super_E1,
6885 z10_super_E1,
6886 z10_super_E1,
6887 z10_super_E1,
6888 z10_super_E1,
6889 *,
6890 z10_super_E1,
6891 z10_super_E1,
6892 *,
6893 *")])
6894
6895 (define_split
6896 [(set (match_operand:DI 0 "s_operand" "")
6897 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
6898 (clobber (reg:CC CC_REGNUM))]
6899 "reload_completed"
6900 [(parallel
6901 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
6902 (clobber (reg:CC CC_REGNUM))])]
6903 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
6904
6905 ;; These two are what combine generates for (ashift (zero_extract)).
6906 (define_insn "*extzv_<mode>_srl"
6907 [(set (match_operand:GPR 0 "register_operand" "=d")
6908 (and:GPR (lshiftrt:GPR
6909 (match_operand:GPR 1 "register_operand" "d")
6910 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
6911 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
6912 (clobber (reg:CC CC_REGNUM))]
6913 "TARGET_Z10
6914 /* Note that even for the SImode pattern, the rotate is always DImode. */
6915 && s390_extzv_shift_ok (<bitsize>, -INTVAL (operands[2]),
6916 INTVAL (operands[3]))"
6917 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,64-%2"
6918 [(set_attr "op_type" "RIE")
6919 (set_attr "z10prop" "z10_super_E1")])
6920
6921 (define_insn "*extzv_<mode>_sll"
6922 [(set (match_operand:GPR 0 "register_operand" "=d")
6923 (and:GPR (ashift:GPR
6924 (match_operand:GPR 1 "register_operand" "d")
6925 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
6926 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
6927 (clobber (reg:CC CC_REGNUM))]
6928 "TARGET_Z10
6929 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[2]),
6930 INTVAL (operands[3]))"
6931 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,%2"
6932 [(set_attr "op_type" "RIE")
6933 (set_attr "z10prop" "z10_super_E1")])
6934
6935
6936 ;
6937 ; andsi3 instruction pattern(s).
6938 ;
6939
6940 (define_insn "*andsi3_cc"
6941 [(set (reg CC_REGNUM)
6942 (compare
6943 (and:SI
6944 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
6945 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
6946 (const_int 0)))
6947 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d, d")
6948 (and:SI (match_dup 1) (match_dup 2)))]
6949 "s390_match_ccmode(insn, CCTmode)"
6950 "@
6951 nilf\t%0,%o2
6952 nr\t%0,%2
6953 nrk\t%0,%1,%2
6954 n\t%0,%2
6955 ny\t%0,%2
6956 risbg\t%0,%1,%t2,128+%f2,0"
6957 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
6958 (set_attr "cpu_facility" "*,*,z196,*,*,z10")
6959 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
6960 z10_super_E1,z10_super_E1,z10_super_E1")])
6961
6962 (define_insn "*andsi3_cconly"
6963 [(set (reg CC_REGNUM)
6964 (compare
6965 (and:SI
6966 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
6967 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
6968 (const_int 0)))
6969 (clobber (match_scratch:SI 0 "=d,d,d,d,d, d"))]
6970 "s390_match_ccmode(insn, CCTmode)
6971 /* Do not steal TM patterns. */
6972 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
6973 "@
6974 nilf\t%0,%o2
6975 nr\t%0,%2
6976 nrk\t%0,%1,%2
6977 n\t%0,%2
6978 ny\t%0,%2
6979 risbg\t%0,%1,%t2,128+%f2,0"
6980 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
6981 (set_attr "cpu_facility" "*,*,z196,*,*,z10")
6982 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
6983 z10_super_E1,z10_super_E1,z10_super_E1")])
6984
6985 (define_insn "*andsi3_zarch"
6986 [(set (match_operand:SI 0 "nonimmediate_operand"
6987 "=d,d, d, d, d,d,d,d,d, d, AQ,Q")
6988 (and:SI (match_operand:SI 1 "nonimmediate_operand"
6989 "%d,o, 0, 0, 0,0,d,0,0, d, 0,0")
6990 (match_operand:SI 2 "general_operand"
6991 " M,M,N0HSF,N1HSF,Os,d,d,R,T,NxxSq,NxQSF,Q")))
6992 (clobber (reg:CC CC_REGNUM))]
6993 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6994 "@
6995 #
6996 #
6997 nilh\t%0,%j2
6998 nill\t%0,%j2
6999 nilf\t%0,%o2
7000 nr\t%0,%2
7001 nrk\t%0,%1,%2
7002 n\t%0,%2
7003 ny\t%0,%2
7004 risbg\t%0,%1,%t2,128+%f2,0
7005 #
7006 #"
7007 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RRF,RX,RXY,RIE,SI,SS")
7008 (set_attr "cpu_facility" "*,*,*,*,*,*,z196,*,*,z10,*,*")
7009 (set_attr "z10prop" "*,
7010 *,
7011 z10_super_E1,
7012 z10_super_E1,
7013 z10_super_E1,
7014 z10_super_E1,
7015 *,
7016 z10_super_E1,
7017 z10_super_E1,
7018 z10_super_E1,
7019 *,
7020 *")])
7021
7022 (define_insn "*andsi3_esa"
7023 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d, AQ,Q")
7024 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0, 0,0")
7025 (match_operand:SI 2 "general_operand" " d,R,NxQSF,Q")))
7026 (clobber (reg:CC CC_REGNUM))]
7027 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7028 "@
7029 nr\t%0,%2
7030 n\t%0,%2
7031 #
7032 #"
7033 [(set_attr "op_type" "RR,RX,SI,SS")
7034 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7035
7036
7037 (define_split
7038 [(set (match_operand:SI 0 "s_operand" "")
7039 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7040 (clobber (reg:CC CC_REGNUM))]
7041 "reload_completed"
7042 [(parallel
7043 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7044 (clobber (reg:CC CC_REGNUM))])]
7045 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7046
7047 ;
7048 ; andhi3 instruction pattern(s).
7049 ;
7050
7051 (define_insn "*andhi3_zarch"
7052 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7053 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7054 (match_operand:HI 2 "general_operand" " d,d,n,NxQHF,Q")))
7055 (clobber (reg:CC CC_REGNUM))]
7056 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7057 "@
7058 nr\t%0,%2
7059 nrk\t%0,%1,%2
7060 nill\t%0,%x2
7061 #
7062 #"
7063 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7064 (set_attr "cpu_facility" "*,z196,*,*,*")
7065 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")
7066 ])
7067
7068 (define_insn "*andhi3_esa"
7069 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7070 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7071 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
7072 (clobber (reg:CC CC_REGNUM))]
7073 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7074 "@
7075 nr\t%0,%2
7076 #
7077 #"
7078 [(set_attr "op_type" "RR,SI,SS")
7079 (set_attr "z10prop" "z10_super_E1,*,*")
7080 ])
7081
7082 (define_split
7083 [(set (match_operand:HI 0 "s_operand" "")
7084 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7085 (clobber (reg:CC CC_REGNUM))]
7086 "reload_completed"
7087 [(parallel
7088 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7089 (clobber (reg:CC CC_REGNUM))])]
7090 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7091
7092 ;
7093 ; andqi3 instruction pattern(s).
7094 ;
7095
7096 (define_insn "*andqi3_zarch"
7097 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7098 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7099 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7100 (clobber (reg:CC CC_REGNUM))]
7101 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7102 "@
7103 nr\t%0,%2
7104 nrk\t%0,%1,%2
7105 nill\t%0,%b2
7106 ni\t%S0,%b2
7107 niy\t%S0,%b2
7108 #"
7109 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7110 (set_attr "cpu_facility" "*,z196,*,*,*,*")
7111 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super,z10_super,*")])
7112
7113 (define_insn "*andqi3_esa"
7114 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7115 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7116 (match_operand:QI 2 "general_operand" "d,n,Q")))
7117 (clobber (reg:CC CC_REGNUM))]
7118 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7119 "@
7120 nr\t%0,%2
7121 ni\t%S0,%b2
7122 #"
7123 [(set_attr "op_type" "RR,SI,SS")
7124 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7125
7126 ;
7127 ; Block and (NC) patterns.
7128 ;
7129
7130 (define_insn "*nc"
7131 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7132 (and:BLK (match_dup 0)
7133 (match_operand:BLK 1 "memory_operand" "Q")))
7134 (use (match_operand 2 "const_int_operand" "n"))
7135 (clobber (reg:CC CC_REGNUM))]
7136 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7137 "nc\t%O0(%2,%R0),%S1"
7138 [(set_attr "op_type" "SS")
7139 (set_attr "z196prop" "z196_cracked")])
7140
7141 (define_split
7142 [(set (match_operand 0 "memory_operand" "")
7143 (and (match_dup 0)
7144 (match_operand 1 "memory_operand" "")))
7145 (clobber (reg:CC CC_REGNUM))]
7146 "reload_completed
7147 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7148 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7149 [(parallel
7150 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
7151 (use (match_dup 2))
7152 (clobber (reg:CC CC_REGNUM))])]
7153 {
7154 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7155 operands[0] = adjust_address (operands[0], BLKmode, 0);
7156 operands[1] = adjust_address (operands[1], BLKmode, 0);
7157 })
7158
7159 (define_peephole2
7160 [(parallel
7161 [(set (match_operand:BLK 0 "memory_operand" "")
7162 (and:BLK (match_dup 0)
7163 (match_operand:BLK 1 "memory_operand" "")))
7164 (use (match_operand 2 "const_int_operand" ""))
7165 (clobber (reg:CC CC_REGNUM))])
7166 (parallel
7167 [(set (match_operand:BLK 3 "memory_operand" "")
7168 (and:BLK (match_dup 3)
7169 (match_operand:BLK 4 "memory_operand" "")))
7170 (use (match_operand 5 "const_int_operand" ""))
7171 (clobber (reg:CC CC_REGNUM))])]
7172 "s390_offset_p (operands[0], operands[3], operands[2])
7173 && s390_offset_p (operands[1], operands[4], operands[2])
7174 && !s390_overlap_p (operands[0], operands[1],
7175 INTVAL (operands[2]) + INTVAL (operands[5]))
7176 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7177 [(parallel
7178 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
7179 (use (match_dup 8))
7180 (clobber (reg:CC CC_REGNUM))])]
7181 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7182 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7183 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7184
7185
7186 ;;
7187 ;;- Bit set (inclusive or) instructions.
7188 ;;
7189
7190 (define_expand "ior<mode>3"
7191 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7192 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
7193 (match_operand:INT 2 "general_operand" "")))
7194 (clobber (reg:CC CC_REGNUM))]
7195 ""
7196 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
7197
7198 ;
7199 ; iordi3 instruction pattern(s).
7200 ;
7201
7202 (define_insn "*iordi3_cc"
7203 [(set (reg CC_REGNUM)
7204 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7205 (match_operand:DI 2 "general_operand" " d,d,RT"))
7206 (const_int 0)))
7207 (set (match_operand:DI 0 "register_operand" "=d,d, d")
7208 (ior:DI (match_dup 1) (match_dup 2)))]
7209 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7210 "@
7211 ogr\t%0,%2
7212 ogrk\t%0,%1,%2
7213 og\t%0,%2"
7214 [(set_attr "op_type" "RRE,RRF,RXY")
7215 (set_attr "cpu_facility" "*,z196,*")
7216 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7217
7218 (define_insn "*iordi3_cconly"
7219 [(set (reg CC_REGNUM)
7220 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7221 (match_operand:DI 2 "general_operand" " d,d,RT"))
7222 (const_int 0)))
7223 (clobber (match_scratch:DI 0 "=d,d,d"))]
7224 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7225 "@
7226 ogr\t%0,%2
7227 ogrk\t%0,%1,%2
7228 og\t%0,%2"
7229 [(set_attr "op_type" "RRE,RRF,RXY")
7230 (set_attr "cpu_facility" "*,z196,*")
7231 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7232
7233 (define_insn "*iordi3"
7234 [(set (match_operand:DI 0 "nonimmediate_operand"
7235 "=d, d, d, d, d, d,d,d, d, AQ,Q")
7236 (ior:DI (match_operand:DI 1 "nonimmediate_operand"
7237 " %0, 0, 0, 0, 0, 0,0,d, 0, 0,0")
7238 (match_operand:DI 2 "general_operand"
7239 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,d,RT,NxQD0,Q")))
7240 (clobber (reg:CC CC_REGNUM))]
7241 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7242 "@
7243 oihh\t%0,%i2
7244 oihl\t%0,%i2
7245 oilh\t%0,%i2
7246 oill\t%0,%i2
7247 oihf\t%0,%k2
7248 oilf\t%0,%k2
7249 ogr\t%0,%2
7250 ogrk\t%0,%1,%2
7251 og\t%0,%2
7252 #
7253 #"
7254 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,SI,SS")
7255 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,z196,*,*,*")
7256 (set_attr "z10prop" "z10_super_E1,
7257 z10_super_E1,
7258 z10_super_E1,
7259 z10_super_E1,
7260 z10_super_E1,
7261 z10_super_E1,
7262 z10_super_E1,
7263 *,
7264 z10_super_E1,
7265 *,
7266 *")])
7267
7268 (define_split
7269 [(set (match_operand:DI 0 "s_operand" "")
7270 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7271 (clobber (reg:CC CC_REGNUM))]
7272 "reload_completed"
7273 [(parallel
7274 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7275 (clobber (reg:CC CC_REGNUM))])]
7276 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7277
7278 ;
7279 ; iorsi3 instruction pattern(s).
7280 ;
7281
7282 (define_insn "*iorsi3_cc"
7283 [(set (reg CC_REGNUM)
7284 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7285 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7286 (const_int 0)))
7287 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7288 (ior:SI (match_dup 1) (match_dup 2)))]
7289 "s390_match_ccmode(insn, CCTmode)"
7290 "@
7291 oilf\t%0,%o2
7292 or\t%0,%2
7293 ork\t%0,%1,%2
7294 o\t%0,%2
7295 oy\t%0,%2"
7296 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7297 (set_attr "cpu_facility" "*,*,z196,*,*")
7298 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7299
7300 (define_insn "*iorsi3_cconly"
7301 [(set (reg CC_REGNUM)
7302 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7303 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7304 (const_int 0)))
7305 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7306 "s390_match_ccmode(insn, CCTmode)"
7307 "@
7308 oilf\t%0,%o2
7309 or\t%0,%2
7310 ork\t%0,%1,%2
7311 o\t%0,%2
7312 oy\t%0,%2"
7313 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7314 (set_attr "cpu_facility" "*,*,z196,*,*")
7315 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7316
7317 (define_insn "*iorsi3_zarch"
7318 [(set (match_operand:SI 0 "nonimmediate_operand" "=d, d, d,d,d,d,d, AQ,Q")
7319 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0, 0, 0,0,d,0,0, 0,0")
7320 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,d,R,T,NxQS0,Q")))
7321 (clobber (reg:CC CC_REGNUM))]
7322 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7323 "@
7324 oilh\t%0,%i2
7325 oill\t%0,%i2
7326 oilf\t%0,%o2
7327 or\t%0,%2
7328 ork\t%0,%1,%2
7329 o\t%0,%2
7330 oy\t%0,%2
7331 #
7332 #"
7333 [(set_attr "op_type" "RI,RI,RIL,RR,RRF,RX,RXY,SI,SS")
7334 (set_attr "cpu_facility" "*,*,*,*,z196,*,*,*,*")
7335 (set_attr "z10prop" "z10_super_E1,
7336 z10_super_E1,
7337 z10_super_E1,
7338 z10_super_E1,
7339 *,
7340 z10_super_E1,
7341 z10_super_E1,
7342 *,
7343 *")])
7344
7345 (define_insn "*iorsi3_esa"
7346 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
7347 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
7348 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
7349 (clobber (reg:CC CC_REGNUM))]
7350 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7351 "@
7352 or\t%0,%2
7353 o\t%0,%2
7354 #
7355 #"
7356 [(set_attr "op_type" "RR,RX,SI,SS")
7357 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7358
7359 (define_split
7360 [(set (match_operand:SI 0 "s_operand" "")
7361 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7362 (clobber (reg:CC CC_REGNUM))]
7363 "reload_completed"
7364 [(parallel
7365 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7366 (clobber (reg:CC CC_REGNUM))])]
7367 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7368
7369 ;
7370 ; iorhi3 instruction pattern(s).
7371 ;
7372
7373 (define_insn "*iorhi3_zarch"
7374 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7375 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7376 (match_operand:HI 2 "general_operand" " d,d,n,NxQH0,Q")))
7377 (clobber (reg:CC CC_REGNUM))]
7378 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7379 "@
7380 or\t%0,%2
7381 ork\t%0,%1,%2
7382 oill\t%0,%x2
7383 #
7384 #"
7385 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7386 (set_attr "cpu_facility" "*,z196,*,*,*")
7387 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")])
7388
7389 (define_insn "*iorhi3_esa"
7390 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7391 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7392 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
7393 (clobber (reg:CC CC_REGNUM))]
7394 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7395 "@
7396 or\t%0,%2
7397 #
7398 #"
7399 [(set_attr "op_type" "RR,SI,SS")
7400 (set_attr "z10prop" "z10_super_E1,*,*")])
7401
7402 (define_split
7403 [(set (match_operand:HI 0 "s_operand" "")
7404 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7405 (clobber (reg:CC CC_REGNUM))]
7406 "reload_completed"
7407 [(parallel
7408 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7409 (clobber (reg:CC CC_REGNUM))])]
7410 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7411
7412 ;
7413 ; iorqi3 instruction pattern(s).
7414 ;
7415
7416 (define_insn "*iorqi3_zarch"
7417 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7418 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7419 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7420 (clobber (reg:CC CC_REGNUM))]
7421 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7422 "@
7423 or\t%0,%2
7424 ork\t%0,%1,%2
7425 oill\t%0,%b2
7426 oi\t%S0,%b2
7427 oiy\t%S0,%b2
7428 #"
7429 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7430 (set_attr "cpu_facility" "*,z196,*,*,*,*")
7431 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,
7432 z10_super,z10_super,*")])
7433
7434 (define_insn "*iorqi3_esa"
7435 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7436 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7437 (match_operand:QI 2 "general_operand" "d,n,Q")))
7438 (clobber (reg:CC CC_REGNUM))]
7439 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7440 "@
7441 or\t%0,%2
7442 oi\t%S0,%b2
7443 #"
7444 [(set_attr "op_type" "RR,SI,SS")
7445 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7446
7447 ;
7448 ; Block inclusive or (OC) patterns.
7449 ;
7450
7451 (define_insn "*oc"
7452 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7453 (ior:BLK (match_dup 0)
7454 (match_operand:BLK 1 "memory_operand" "Q")))
7455 (use (match_operand 2 "const_int_operand" "n"))
7456 (clobber (reg:CC CC_REGNUM))]
7457 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7458 "oc\t%O0(%2,%R0),%S1"
7459 [(set_attr "op_type" "SS")
7460 (set_attr "z196prop" "z196_cracked")])
7461
7462 (define_split
7463 [(set (match_operand 0 "memory_operand" "")
7464 (ior (match_dup 0)
7465 (match_operand 1 "memory_operand" "")))
7466 (clobber (reg:CC CC_REGNUM))]
7467 "reload_completed
7468 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7469 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7470 [(parallel
7471 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
7472 (use (match_dup 2))
7473 (clobber (reg:CC CC_REGNUM))])]
7474 {
7475 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7476 operands[0] = adjust_address (operands[0], BLKmode, 0);
7477 operands[1] = adjust_address (operands[1], BLKmode, 0);
7478 })
7479
7480 (define_peephole2
7481 [(parallel
7482 [(set (match_operand:BLK 0 "memory_operand" "")
7483 (ior:BLK (match_dup 0)
7484 (match_operand:BLK 1 "memory_operand" "")))
7485 (use (match_operand 2 "const_int_operand" ""))
7486 (clobber (reg:CC CC_REGNUM))])
7487 (parallel
7488 [(set (match_operand:BLK 3 "memory_operand" "")
7489 (ior:BLK (match_dup 3)
7490 (match_operand:BLK 4 "memory_operand" "")))
7491 (use (match_operand 5 "const_int_operand" ""))
7492 (clobber (reg:CC CC_REGNUM))])]
7493 "s390_offset_p (operands[0], operands[3], operands[2])
7494 && s390_offset_p (operands[1], operands[4], operands[2])
7495 && !s390_overlap_p (operands[0], operands[1],
7496 INTVAL (operands[2]) + INTVAL (operands[5]))
7497 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7498 [(parallel
7499 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
7500 (use (match_dup 8))
7501 (clobber (reg:CC CC_REGNUM))])]
7502 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7503 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7504 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7505
7506
7507 ;;
7508 ;;- Xor instructions.
7509 ;;
7510
7511 (define_expand "xor<mode>3"
7512 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7513 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
7514 (match_operand:INT 2 "general_operand" "")))
7515 (clobber (reg:CC CC_REGNUM))]
7516 ""
7517 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
7518
7519 ; Combine replaces (xor (x) (const_int -1)) with (not (x)) when doing
7520 ; simplifications. So its better to have something matching.
7521 (define_split
7522 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7523 (not:INT (match_operand:INT 1 "nonimmediate_operand" "")))]
7524 ""
7525 [(parallel
7526 [(set (match_dup 0) (xor:INT (match_dup 1) (match_dup 2)))
7527 (clobber (reg:CC CC_REGNUM))])]
7528 {
7529 operands[2] = constm1_rtx;
7530 if (!s390_logical_operator_ok_p (operands))
7531 FAIL;
7532 })
7533
7534 ;
7535 ; xordi3 instruction pattern(s).
7536 ;
7537
7538 (define_insn "*xordi3_cc"
7539 [(set (reg CC_REGNUM)
7540 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7541 (match_operand:DI 2 "general_operand" " d,d,RT"))
7542 (const_int 0)))
7543 (set (match_operand:DI 0 "register_operand" "=d,d, d")
7544 (xor:DI (match_dup 1) (match_dup 2)))]
7545 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7546 "@
7547 xgr\t%0,%2
7548 xgrk\t%0,%1,%2
7549 xg\t%0,%2"
7550 [(set_attr "op_type" "RRE,RRF,RXY")
7551 (set_attr "cpu_facility" "*,z196,*")
7552 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7553
7554 (define_insn "*xordi3_cconly"
7555 [(set (reg CC_REGNUM)
7556 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7557 (match_operand:DI 2 "general_operand" " d,d,RT"))
7558 (const_int 0)))
7559 (clobber (match_scratch:DI 0 "=d,d, d"))]
7560 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7561 "@
7562 xgr\t%0,%2
7563 xgrk\t%0,%1,%2
7564 xg\t%0,%2"
7565 [(set_attr "op_type" "RRE,RRF,RXY")
7566 (set_attr "cpu_facility" "*,z196,*")
7567 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7568
7569 (define_insn "*xordi3"
7570 [(set (match_operand:DI 0 "nonimmediate_operand" "=d, d,d,d, d, AQ,Q")
7571 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0, 0,0,d, 0, 0,0")
7572 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,d,RT,NxQD0,Q")))
7573 (clobber (reg:CC CC_REGNUM))]
7574 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7575 "@
7576 xihf\t%0,%k2
7577 xilf\t%0,%k2
7578 xgr\t%0,%2
7579 xgrk\t%0,%1,%2
7580 xg\t%0,%2
7581 #
7582 #"
7583 [(set_attr "op_type" "RIL,RIL,RRE,RRF,RXY,SI,SS")
7584 (set_attr "cpu_facility" "extimm,extimm,*,z196,*,*,*")
7585 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,
7586 *,z10_super_E1,*,*")])
7587
7588 (define_split
7589 [(set (match_operand:DI 0 "s_operand" "")
7590 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7591 (clobber (reg:CC CC_REGNUM))]
7592 "reload_completed"
7593 [(parallel
7594 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7595 (clobber (reg:CC CC_REGNUM))])]
7596 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7597
7598 ;
7599 ; xorsi3 instruction pattern(s).
7600 ;
7601
7602 (define_insn "*xorsi3_cc"
7603 [(set (reg CC_REGNUM)
7604 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7605 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7606 (const_int 0)))
7607 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7608 (xor:SI (match_dup 1) (match_dup 2)))]
7609 "s390_match_ccmode(insn, CCTmode)"
7610 "@
7611 xilf\t%0,%o2
7612 xr\t%0,%2
7613 xrk\t%0,%1,%2
7614 x\t%0,%2
7615 xy\t%0,%2"
7616 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7617 (set_attr "cpu_facility" "*,*,z196,*,*")
7618 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7619 z10_super_E1,z10_super_E1")])
7620
7621 (define_insn "*xorsi3_cconly"
7622 [(set (reg CC_REGNUM)
7623 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7624 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7625 (const_int 0)))
7626 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7627 "s390_match_ccmode(insn, CCTmode)"
7628 "@
7629 xilf\t%0,%o2
7630 xr\t%0,%2
7631 xrk\t%0,%1,%2
7632 x\t%0,%2
7633 xy\t%0,%2"
7634 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7635 (set_attr "cpu_facility" "*,*,z196,*,*")
7636 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7637 z10_super_E1,z10_super_E1")])
7638
7639 (define_insn "*xorsi3"
7640 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d, AQ,Q")
7641 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, 0,0")
7642 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxQS0,Q")))
7643 (clobber (reg:CC CC_REGNUM))]
7644 "s390_logical_operator_ok_p (operands)"
7645 "@
7646 xilf\t%0,%o2
7647 xr\t%0,%2
7648 xrk\t%0,%1,%2
7649 x\t%0,%2
7650 xy\t%0,%2
7651 #
7652 #"
7653 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,SI,SS")
7654 (set_attr "cpu_facility" "*,*,z196,*,*,*,*")
7655 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7656 z10_super_E1,z10_super_E1,*,*")])
7657
7658 (define_split
7659 [(set (match_operand:SI 0 "s_operand" "")
7660 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7661 (clobber (reg:CC CC_REGNUM))]
7662 "reload_completed"
7663 [(parallel
7664 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7665 (clobber (reg:CC CC_REGNUM))])]
7666 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7667
7668 ;
7669 ; xorhi3 instruction pattern(s).
7670 ;
7671
7672 (define_insn "*xorhi3"
7673 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7674 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,d, 0,0")
7675 (match_operand:HI 2 "general_operand" "Os,d,d,NxQH0,Q")))
7676 (clobber (reg:CC CC_REGNUM))]
7677 "s390_logical_operator_ok_p (operands)"
7678 "@
7679 xilf\t%0,%x2
7680 xr\t%0,%2
7681 xrk\t%0,%1,%2
7682 #
7683 #"
7684 [(set_attr "op_type" "RIL,RR,RRF,SI,SS")
7685 (set_attr "cpu_facility" "*,*,z196,*,*")
7686 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*,*")])
7687
7688 (define_split
7689 [(set (match_operand:HI 0 "s_operand" "")
7690 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7691 (clobber (reg:CC CC_REGNUM))]
7692 "reload_completed"
7693 [(parallel
7694 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7695 (clobber (reg:CC CC_REGNUM))])]
7696 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7697
7698 ;
7699 ; xorqi3 instruction pattern(s).
7700 ;
7701
7702 (define_insn "*xorqi3"
7703 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7704 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,d,0,0,0")
7705 (match_operand:QI 2 "general_operand" "Os,d,d,n,n,Q")))
7706 (clobber (reg:CC CC_REGNUM))]
7707 "s390_logical_operator_ok_p (operands)"
7708 "@
7709 xilf\t%0,%b2
7710 xr\t%0,%2
7711 xrk\t%0,%1,%2
7712 xi\t%S0,%b2
7713 xiy\t%S0,%b2
7714 #"
7715 [(set_attr "op_type" "RIL,RR,RRF,SI,SIY,SS")
7716 (set_attr "cpu_facility" "*,*,z196,*,*,*")
7717 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super,z10_super,*")])
7718
7719
7720 ;
7721 ; Block exclusive or (XC) patterns.
7722 ;
7723
7724 (define_insn "*xc"
7725 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7726 (xor:BLK (match_dup 0)
7727 (match_operand:BLK 1 "memory_operand" "Q")))
7728 (use (match_operand 2 "const_int_operand" "n"))
7729 (clobber (reg:CC CC_REGNUM))]
7730 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7731 "xc\t%O0(%2,%R0),%S1"
7732 [(set_attr "op_type" "SS")])
7733
7734 (define_split
7735 [(set (match_operand 0 "memory_operand" "")
7736 (xor (match_dup 0)
7737 (match_operand 1 "memory_operand" "")))
7738 (clobber (reg:CC CC_REGNUM))]
7739 "reload_completed
7740 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7741 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7742 [(parallel
7743 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
7744 (use (match_dup 2))
7745 (clobber (reg:CC CC_REGNUM))])]
7746 {
7747 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7748 operands[0] = adjust_address (operands[0], BLKmode, 0);
7749 operands[1] = adjust_address (operands[1], BLKmode, 0);
7750 })
7751
7752 (define_peephole2
7753 [(parallel
7754 [(set (match_operand:BLK 0 "memory_operand" "")
7755 (xor:BLK (match_dup 0)
7756 (match_operand:BLK 1 "memory_operand" "")))
7757 (use (match_operand 2 "const_int_operand" ""))
7758 (clobber (reg:CC CC_REGNUM))])
7759 (parallel
7760 [(set (match_operand:BLK 3 "memory_operand" "")
7761 (xor:BLK (match_dup 3)
7762 (match_operand:BLK 4 "memory_operand" "")))
7763 (use (match_operand 5 "const_int_operand" ""))
7764 (clobber (reg:CC CC_REGNUM))])]
7765 "s390_offset_p (operands[0], operands[3], operands[2])
7766 && s390_offset_p (operands[1], operands[4], operands[2])
7767 && !s390_overlap_p (operands[0], operands[1],
7768 INTVAL (operands[2]) + INTVAL (operands[5]))
7769 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7770 [(parallel
7771 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
7772 (use (match_dup 8))
7773 (clobber (reg:CC CC_REGNUM))])]
7774 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7775 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7776 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7777
7778 ;
7779 ; Block xor (XC) patterns with src == dest.
7780 ;
7781
7782 (define_insn "*xc_zero"
7783 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7784 (const_int 0))
7785 (use (match_operand 1 "const_int_operand" "n"))
7786 (clobber (reg:CC CC_REGNUM))]
7787 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
7788 "xc\t%O0(%1,%R0),%S0"
7789 [(set_attr "op_type" "SS")
7790 (set_attr "z196prop" "z196_cracked")])
7791
7792 (define_peephole2
7793 [(parallel
7794 [(set (match_operand:BLK 0 "memory_operand" "")
7795 (const_int 0))
7796 (use (match_operand 1 "const_int_operand" ""))
7797 (clobber (reg:CC CC_REGNUM))])
7798 (parallel
7799 [(set (match_operand:BLK 2 "memory_operand" "")
7800 (const_int 0))
7801 (use (match_operand 3 "const_int_operand" ""))
7802 (clobber (reg:CC CC_REGNUM))])]
7803 "s390_offset_p (operands[0], operands[2], operands[1])
7804 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
7805 [(parallel
7806 [(set (match_dup 4) (const_int 0))
7807 (use (match_dup 5))
7808 (clobber (reg:CC CC_REGNUM))])]
7809 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7810 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
7811
7812
7813 ;;
7814 ;;- Negate instructions.
7815 ;;
7816
7817 ;
7818 ; neg(di|si)2 instruction pattern(s).
7819 ;
7820
7821 (define_expand "neg<mode>2"
7822 [(parallel
7823 [(set (match_operand:DSI 0 "register_operand" "=d")
7824 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
7825 (clobber (reg:CC CC_REGNUM))])]
7826 ""
7827 "")
7828
7829 (define_insn "*negdi2_sign_cc"
7830 [(set (reg CC_REGNUM)
7831 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
7832 (match_operand:SI 1 "register_operand" "d") 0)
7833 (const_int 32)) (const_int 32)))
7834 (const_int 0)))
7835 (set (match_operand:DI 0 "register_operand" "=d")
7836 (neg:DI (sign_extend:DI (match_dup 1))))]
7837 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
7838 "lcgfr\t%0,%1"
7839 [(set_attr "op_type" "RRE")
7840 (set_attr "z10prop" "z10_c")])
7841
7842 (define_insn "*negdi2_sign"
7843 [(set (match_operand:DI 0 "register_operand" "=d")
7844 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
7845 (clobber (reg:CC CC_REGNUM))]
7846 "TARGET_ZARCH"
7847 "lcgfr\t%0,%1"
7848 [(set_attr "op_type" "RRE")
7849 (set_attr "z10prop" "z10_c")])
7850
7851 ; lcr, lcgr
7852 (define_insn "*neg<mode>2_cc"
7853 [(set (reg CC_REGNUM)
7854 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
7855 (const_int 0)))
7856 (set (match_operand:GPR 0 "register_operand" "=d")
7857 (neg:GPR (match_dup 1)))]
7858 "s390_match_ccmode (insn, CCAmode)"
7859 "lc<g>r\t%0,%1"
7860 [(set_attr "op_type" "RR<E>")
7861 (set_attr "z10prop" "z10_super_c_E1")])
7862
7863 ; lcr, lcgr
7864 (define_insn "*neg<mode>2_cconly"
7865 [(set (reg CC_REGNUM)
7866 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
7867 (const_int 0)))
7868 (clobber (match_scratch:GPR 0 "=d"))]
7869 "s390_match_ccmode (insn, CCAmode)"
7870 "lc<g>r\t%0,%1"
7871 [(set_attr "op_type" "RR<E>")
7872 (set_attr "z10prop" "z10_super_c_E1")])
7873
7874 ; lcr, lcgr
7875 (define_insn "*neg<mode>2"
7876 [(set (match_operand:GPR 0 "register_operand" "=d")
7877 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
7878 (clobber (reg:CC CC_REGNUM))]
7879 ""
7880 "lc<g>r\t%0,%1"
7881 [(set_attr "op_type" "RR<E>")
7882 (set_attr "z10prop" "z10_super_c_E1")])
7883
7884 (define_insn "*negdi2_31"
7885 [(set (match_operand:DI 0 "register_operand" "=d")
7886 (neg:DI (match_operand:DI 1 "register_operand" "d")))
7887 (clobber (reg:CC CC_REGNUM))]
7888 "!TARGET_ZARCH"
7889 "#")
7890
7891 ; Split a DImode NEG on 31bit into 2 SImode NEGs
7892
7893 ; Doing the twos complement separately on the SImode parts does an
7894 ; unwanted +1 on the high part which needs to be subtracted afterwards
7895 ; ... unless the +1 on the low part created an overflow.
7896
7897 (define_split
7898 [(set (match_operand:DI 0 "register_operand" "")
7899 (neg:DI (match_operand:DI 1 "register_operand" "")))
7900 (clobber (reg:CC CC_REGNUM))]
7901 "!TARGET_ZARCH
7902 && (REGNO (operands[0]) == REGNO (operands[1])
7903 || s390_split_ok_p (operands[0], operands[1], DImode, 0))
7904 && reload_completed"
7905 [(parallel
7906 [(set (match_dup 2) (neg:SI (match_dup 3)))
7907 (clobber (reg:CC CC_REGNUM))])
7908 (parallel
7909 [(set (reg:CCAP CC_REGNUM)
7910 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
7911 (set (match_dup 4) (neg:SI (match_dup 5)))])
7912 (set (pc)
7913 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
7914 (pc)
7915 (label_ref (match_dup 6))))
7916 (parallel
7917 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
7918 (clobber (reg:CC CC_REGNUM))])
7919 (match_dup 6)]
7920 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
7921 operands[3] = operand_subword (operands[1], 0, 0, DImode);
7922 operands[4] = operand_subword (operands[0], 1, 0, DImode);
7923 operands[5] = operand_subword (operands[1], 1, 0, DImode);
7924 operands[6] = gen_label_rtx ();")
7925
7926 ; Like above but first make a copy of the low part of the src operand
7927 ; since it might overlap with the high part of the destination.
7928
7929 (define_split
7930 [(set (match_operand:DI 0 "register_operand" "")
7931 (neg:DI (match_operand:DI 1 "register_operand" "")))
7932 (clobber (reg:CC CC_REGNUM))]
7933 "!TARGET_ZARCH
7934 && s390_split_ok_p (operands[0], operands[1], DImode, 1)
7935 && reload_completed"
7936 [; Make a backup of op5 first
7937 (set (match_dup 4) (match_dup 5))
7938 ; Setting op2 here might clobber op5
7939 (parallel
7940 [(set (match_dup 2) (neg:SI (match_dup 3)))
7941 (clobber (reg:CC CC_REGNUM))])
7942 (parallel
7943 [(set (reg:CCAP CC_REGNUM)
7944 (compare:CCAP (neg:SI (match_dup 4)) (const_int 0)))
7945 (set (match_dup 4) (neg:SI (match_dup 4)))])
7946 (set (pc)
7947 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
7948 (pc)
7949 (label_ref (match_dup 6))))
7950 (parallel
7951 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
7952 (clobber (reg:CC CC_REGNUM))])
7953 (match_dup 6)]
7954 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
7955 operands[3] = operand_subword (operands[1], 0, 0, DImode);
7956 operands[4] = operand_subword (operands[0], 1, 0, DImode);
7957 operands[5] = operand_subword (operands[1], 1, 0, DImode);
7958 operands[6] = gen_label_rtx ();")
7959
7960 ;
7961 ; neg(df|sf)2 instruction pattern(s).
7962 ;
7963
7964 (define_expand "neg<mode>2"
7965 [(parallel
7966 [(set (match_operand:BFP 0 "register_operand" "=f")
7967 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
7968 (clobber (reg:CC CC_REGNUM))])]
7969 "TARGET_HARD_FLOAT"
7970 "")
7971
7972 ; lcxbr, lcdbr, lcebr
7973 (define_insn "*neg<mode>2_cc"
7974 [(set (reg CC_REGNUM)
7975 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
7976 (match_operand:BFP 2 "const0_operand" "")))
7977 (set (match_operand:BFP 0 "register_operand" "=f")
7978 (neg:BFP (match_dup 1)))]
7979 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7980 "lc<xde>br\t%0,%1"
7981 [(set_attr "op_type" "RRE")
7982 (set_attr "type" "fsimp<mode>")])
7983
7984 ; lcxbr, lcdbr, lcebr
7985 (define_insn "*neg<mode>2_cconly"
7986 [(set (reg CC_REGNUM)
7987 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
7988 (match_operand:BFP 2 "const0_operand" "")))
7989 (clobber (match_scratch:BFP 0 "=f"))]
7990 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7991 "lc<xde>br\t%0,%1"
7992 [(set_attr "op_type" "RRE")
7993 (set_attr "type" "fsimp<mode>")])
7994
7995 ; lcdfr
7996 (define_insn "*neg<mode>2_nocc"
7997 [(set (match_operand:FP 0 "register_operand" "=f")
7998 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
7999 "TARGET_DFP"
8000 "lcdfr\t%0,%1"
8001 [(set_attr "op_type" "RRE")
8002 (set_attr "type" "fsimp<mode>")])
8003
8004 ; lcxbr, lcdbr, lcebr
8005 ; FIXME: wflcdb does not clobber cc
8006 (define_insn "*neg<mode>2"
8007 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
8008 (neg:BFP (match_operand:BFP 1 "register_operand" "f,<vf>")))
8009 (clobber (reg:CC CC_REGNUM))]
8010 "TARGET_HARD_FLOAT"
8011 "@
8012 lc<xde>br\t%0,%1
8013 wflcdb\t%0,%1"
8014 [(set_attr "op_type" "RRE,VRR")
8015 (set_attr "cpu_facility" "*,vec")
8016 (set_attr "type" "fsimp<mode>,*")])
8017
8018
8019 ;;
8020 ;;- Absolute value instructions.
8021 ;;
8022
8023 ;
8024 ; abs(di|si)2 instruction pattern(s).
8025 ;
8026
8027 (define_insn "*absdi2_sign_cc"
8028 [(set (reg CC_REGNUM)
8029 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8030 (match_operand:SI 1 "register_operand" "d") 0)
8031 (const_int 32)) (const_int 32)))
8032 (const_int 0)))
8033 (set (match_operand:DI 0 "register_operand" "=d")
8034 (abs:DI (sign_extend:DI (match_dup 1))))]
8035 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8036 "lpgfr\t%0,%1"
8037 [(set_attr "op_type" "RRE")
8038 (set_attr "z10prop" "z10_c")])
8039
8040 (define_insn "*absdi2_sign"
8041 [(set (match_operand:DI 0 "register_operand" "=d")
8042 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8043 (clobber (reg:CC CC_REGNUM))]
8044 "TARGET_ZARCH"
8045 "lpgfr\t%0,%1"
8046 [(set_attr "op_type" "RRE")
8047 (set_attr "z10prop" "z10_c")])
8048
8049 ; lpr, lpgr
8050 (define_insn "*abs<mode>2_cc"
8051 [(set (reg CC_REGNUM)
8052 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
8053 (const_int 0)))
8054 (set (match_operand:GPR 0 "register_operand" "=d")
8055 (abs:GPR (match_dup 1)))]
8056 "s390_match_ccmode (insn, CCAmode)"
8057 "lp<g>r\t%0,%1"
8058 [(set_attr "op_type" "RR<E>")
8059 (set_attr "z10prop" "z10_c")])
8060
8061 ; lpr, lpgr
8062 (define_insn "*abs<mode>2_cconly"
8063 [(set (reg CC_REGNUM)
8064 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
8065 (const_int 0)))
8066 (clobber (match_scratch:GPR 0 "=d"))]
8067 "s390_match_ccmode (insn, CCAmode)"
8068 "lp<g>r\t%0,%1"
8069 [(set_attr "op_type" "RR<E>")
8070 (set_attr "z10prop" "z10_c")])
8071
8072 ; lpr, lpgr
8073 (define_insn "abs<mode>2"
8074 [(set (match_operand:GPR 0 "register_operand" "=d")
8075 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8076 (clobber (reg:CC CC_REGNUM))]
8077 ""
8078 "lp<g>r\t%0,%1"
8079 [(set_attr "op_type" "RR<E>")
8080 (set_attr "z10prop" "z10_c")])
8081
8082 ;
8083 ; abs(df|sf)2 instruction pattern(s).
8084 ;
8085
8086 (define_expand "abs<mode>2"
8087 [(parallel
8088 [(set (match_operand:BFP 0 "register_operand" "=f")
8089 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8090 (clobber (reg:CC CC_REGNUM))])]
8091 "TARGET_HARD_FLOAT"
8092 "")
8093
8094 ; lpxbr, lpdbr, lpebr
8095 (define_insn "*abs<mode>2_cc"
8096 [(set (reg CC_REGNUM)
8097 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8098 (match_operand:BFP 2 "const0_operand" "")))
8099 (set (match_operand:BFP 0 "register_operand" "=f")
8100 (abs:BFP (match_dup 1)))]
8101 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8102 "lp<xde>br\t%0,%1"
8103 [(set_attr "op_type" "RRE")
8104 (set_attr "type" "fsimp<mode>")])
8105
8106 ; lpxbr, lpdbr, lpebr
8107 (define_insn "*abs<mode>2_cconly"
8108 [(set (reg CC_REGNUM)
8109 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8110 (match_operand:BFP 2 "const0_operand" "")))
8111 (clobber (match_scratch:BFP 0 "=f"))]
8112 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8113 "lp<xde>br\t%0,%1"
8114 [(set_attr "op_type" "RRE")
8115 (set_attr "type" "fsimp<mode>")])
8116
8117 ; lpdfr
8118 (define_insn "*abs<mode>2_nocc"
8119 [(set (match_operand:FP 0 "register_operand" "=f")
8120 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8121 "TARGET_DFP"
8122 "lpdfr\t%0,%1"
8123 [(set_attr "op_type" "RRE")
8124 (set_attr "type" "fsimp<mode>")])
8125
8126 ; lpxbr, lpdbr, lpebr
8127 ; FIXME: wflpdb does not clobber cc
8128 (define_insn "*abs<mode>2"
8129 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
8130 (abs:BFP (match_operand:BFP 1 "register_operand" "f,<vf>")))
8131 (clobber (reg:CC CC_REGNUM))]
8132 "TARGET_HARD_FLOAT"
8133 "@
8134 lp<xde>br\t%0,%1
8135 wflpdb\t%0,%1"
8136 [(set_attr "op_type" "RRE,VRR")
8137 (set_attr "cpu_facility" "*,vec")
8138 (set_attr "type" "fsimp<mode>,*")])
8139
8140
8141 ;;
8142 ;;- Negated absolute value instructions
8143 ;;
8144
8145 ;
8146 ; Integer
8147 ;
8148
8149 (define_insn "*negabsdi2_sign_cc"
8150 [(set (reg CC_REGNUM)
8151 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8152 (match_operand:SI 1 "register_operand" "d") 0)
8153 (const_int 32)) (const_int 32))))
8154 (const_int 0)))
8155 (set (match_operand:DI 0 "register_operand" "=d")
8156 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
8157 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8158 "lngfr\t%0,%1"
8159 [(set_attr "op_type" "RRE")
8160 (set_attr "z10prop" "z10_c")])
8161
8162 (define_insn "*negabsdi2_sign"
8163 [(set (match_operand:DI 0 "register_operand" "=d")
8164 (neg:DI (abs:DI (sign_extend:DI
8165 (match_operand:SI 1 "register_operand" "d")))))
8166 (clobber (reg:CC CC_REGNUM))]
8167 "TARGET_ZARCH"
8168 "lngfr\t%0,%1"
8169 [(set_attr "op_type" "RRE")
8170 (set_attr "z10prop" "z10_c")])
8171
8172 ; lnr, lngr
8173 (define_insn "*negabs<mode>2_cc"
8174 [(set (reg CC_REGNUM)
8175 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8176 (const_int 0)))
8177 (set (match_operand:GPR 0 "register_operand" "=d")
8178 (neg:GPR (abs:GPR (match_dup 1))))]
8179 "s390_match_ccmode (insn, CCAmode)"
8180 "ln<g>r\t%0,%1"
8181 [(set_attr "op_type" "RR<E>")
8182 (set_attr "z10prop" "z10_c")])
8183
8184 ; lnr, lngr
8185 (define_insn "*negabs<mode>2_cconly"
8186 [(set (reg CC_REGNUM)
8187 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8188 (const_int 0)))
8189 (clobber (match_scratch:GPR 0 "=d"))]
8190 "s390_match_ccmode (insn, CCAmode)"
8191 "ln<g>r\t%0,%1"
8192 [(set_attr "op_type" "RR<E>")
8193 (set_attr "z10prop" "z10_c")])
8194
8195 ; lnr, lngr
8196 (define_insn "*negabs<mode>2"
8197 [(set (match_operand:GPR 0 "register_operand" "=d")
8198 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
8199 (clobber (reg:CC CC_REGNUM))]
8200 ""
8201 "ln<g>r\t%0,%1"
8202 [(set_attr "op_type" "RR<E>")
8203 (set_attr "z10prop" "z10_c")])
8204
8205 ;
8206 ; Floating point
8207 ;
8208
8209 ; lnxbr, lndbr, lnebr
8210 (define_insn "*negabs<mode>2_cc"
8211 [(set (reg CC_REGNUM)
8212 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8213 (match_operand:BFP 2 "const0_operand" "")))
8214 (set (match_operand:BFP 0 "register_operand" "=f")
8215 (neg:BFP (abs:BFP (match_dup 1))))]
8216 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8217 "ln<xde>br\t%0,%1"
8218 [(set_attr "op_type" "RRE")
8219 (set_attr "type" "fsimp<mode>")])
8220
8221 ; lnxbr, lndbr, lnebr
8222 (define_insn "*negabs<mode>2_cconly"
8223 [(set (reg CC_REGNUM)
8224 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8225 (match_operand:BFP 2 "const0_operand" "")))
8226 (clobber (match_scratch:BFP 0 "=f"))]
8227 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8228 "ln<xde>br\t%0,%1"
8229 [(set_attr "op_type" "RRE")
8230 (set_attr "type" "fsimp<mode>")])
8231
8232 ; lndfr
8233 (define_insn "*negabs<mode>2_nocc"
8234 [(set (match_operand:FP 0 "register_operand" "=f")
8235 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
8236 "TARGET_DFP"
8237 "lndfr\t%0,%1"
8238 [(set_attr "op_type" "RRE")
8239 (set_attr "type" "fsimp<mode>")])
8240
8241 ; lnxbr, lndbr, lnebr
8242 ; FIXME: wflndb does not clobber cc
8243 (define_insn "*negabs<mode>2"
8244 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
8245 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f,<vf>"))))
8246 (clobber (reg:CC CC_REGNUM))]
8247 "TARGET_HARD_FLOAT"
8248 "@
8249 ln<xde>br\t%0,%1
8250 wflndb\t%0,%1"
8251 [(set_attr "op_type" "RRE,VRR")
8252 (set_attr "cpu_facility" "*,vec")
8253 (set_attr "type" "fsimp<mode>,*")])
8254
8255 ;;
8256 ;;- Square root instructions.
8257 ;;
8258
8259 ;
8260 ; sqrt(df|sf)2 instruction pattern(s).
8261 ;
8262
8263 ; sqxbr, sqdbr, sqebr, sqdb, sqeb
8264 (define_insn "sqrt<mode>2"
8265 [(set (match_operand:BFP 0 "register_operand" "=f, f,<vf>")
8266 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,<Rf>,<vf>")))]
8267 "TARGET_HARD_FLOAT"
8268 "@
8269 sq<xde>br\t%0,%1
8270 sq<xde>b\t%0,%1
8271 wfsqdb\t%v0,%v1"
8272 [(set_attr "op_type" "RRE,RXE,VRR")
8273 (set_attr "type" "fsqrt<mode>")
8274 (set_attr "cpu_facility" "*,*,vec")])
8275
8276
8277 ;;
8278 ;;- One complement instructions.
8279 ;;
8280
8281 ;
8282 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
8283 ;
8284
8285 (define_expand "one_cmpl<mode>2"
8286 [(parallel
8287 [(set (match_operand:INT 0 "register_operand" "")
8288 (xor:INT (match_operand:INT 1 "register_operand" "")
8289 (const_int -1)))
8290 (clobber (reg:CC CC_REGNUM))])]
8291 ""
8292 "")
8293
8294
8295 ;;
8296 ;; Find leftmost bit instructions.
8297 ;;
8298
8299 (define_expand "clzdi2"
8300 [(set (match_operand:DI 0 "register_operand" "=d")
8301 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
8302 "TARGET_EXTIMM && TARGET_ZARCH"
8303 {
8304 rtx insn, clz_equal;
8305 rtx wide_reg = gen_reg_rtx (TImode);
8306 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
8307
8308 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
8309
8310 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
8311
8312 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
8313 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
8314
8315 DONE;
8316 })
8317
8318 (define_insn "clztidi2"
8319 [(set (match_operand:TI 0 "register_operand" "=d")
8320 (ior:TI
8321 (ashift:TI
8322 (zero_extend:TI
8323 (xor:DI (match_operand:DI 1 "register_operand" "d")
8324 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
8325 (subreg:SI (clz:DI (match_dup 1)) 4))))
8326
8327 (const_int 64))
8328 (zero_extend:TI (clz:DI (match_dup 1)))))
8329 (clobber (reg:CC CC_REGNUM))]
8330 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
8331 == (unsigned HOST_WIDE_INT) 1 << 63
8332 && TARGET_EXTIMM && TARGET_ZARCH"
8333 "flogr\t%0,%1"
8334 [(set_attr "op_type" "RRE")])
8335
8336
8337 ;;
8338 ;;- Rotate instructions.
8339 ;;
8340
8341 ;
8342 ; rotl(di|si)3 instruction pattern(s).
8343 ;
8344
8345 ; rll, rllg
8346 (define_insn "rotl<mode>3"
8347 [(set (match_operand:GPR 0 "register_operand" "=d")
8348 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8349 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
8350 "TARGET_CPU_ZARCH"
8351 "rll<g>\t%0,%1,%Y2"
8352 [(set_attr "op_type" "RSE")
8353 (set_attr "atype" "reg")
8354 (set_attr "z10prop" "z10_super_E1")])
8355
8356 ; rll, rllg
8357 (define_insn "*rotl<mode>3_and"
8358 [(set (match_operand:GPR 0 "register_operand" "=d")
8359 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8360 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8361 (match_operand:SI 3 "const_int_operand" "n"))))]
8362 "TARGET_CPU_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8363 "rll<g>\t%0,%1,%Y2"
8364 [(set_attr "op_type" "RSE")
8365 (set_attr "atype" "reg")
8366 (set_attr "z10prop" "z10_super_E1")])
8367
8368
8369 ;;
8370 ;;- Shift instructions.
8371 ;;
8372
8373 ;
8374 ; (ashl|lshr)(di|si)3 instruction pattern(s).
8375 ; Left shifts and logical right shifts
8376
8377 (define_expand "<shift><mode>3"
8378 [(set (match_operand:DSI 0 "register_operand" "")
8379 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
8380 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))]
8381 ""
8382 "")
8383
8384 ; sldl, srdl
8385 (define_insn "*<shift>di3_31"
8386 [(set (match_operand:DI 0 "register_operand" "=d")
8387 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8388 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
8389 "!TARGET_ZARCH"
8390 "s<lr>dl\t%0,%Y2"
8391 [(set_attr "op_type" "RS")
8392 (set_attr "atype" "reg")
8393 (set_attr "z196prop" "z196_cracked")])
8394
8395 ; sll, srl, sllg, srlg, sllk, srlk
8396 (define_insn "*<shift><mode>3"
8397 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8398 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8399 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")))]
8400 ""
8401 "@
8402 s<lr>l<g>\t%0,<1>%Y2
8403 s<lr>l<gk>\t%0,%1,%Y2"
8404 [(set_attr "op_type" "RS<E>,RSY")
8405 (set_attr "atype" "reg,reg")
8406 (set_attr "cpu_facility" "*,z196")
8407 (set_attr "z10prop" "z10_super_E1,*")])
8408
8409 ; sldl, srdl
8410 (define_insn "*<shift>di3_31_and"
8411 [(set (match_operand:DI 0 "register_operand" "=d")
8412 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8413 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8414 (match_operand:SI 3 "const_int_operand" "n"))))]
8415 "!TARGET_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8416 "s<lr>dl\t%0,%Y2"
8417 [(set_attr "op_type" "RS")
8418 (set_attr "atype" "reg")])
8419
8420 ; sll, srl, sllg, srlg, sllk, srlk
8421 (define_insn "*<shift><mode>3_and"
8422 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8423 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8424 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8425 (match_operand:SI 3 "const_int_operand" "n,n"))))]
8426 "(INTVAL (operands[3]) & 63) == 63"
8427 "@
8428 s<lr>l<g>\t%0,<1>%Y2
8429 s<lr>l<gk>\t%0,%1,%Y2"
8430 [(set_attr "op_type" "RS<E>,RSY")
8431 (set_attr "atype" "reg,reg")
8432 (set_attr "cpu_facility" "*,z196")
8433 (set_attr "z10prop" "z10_super_E1,*")])
8434
8435 ;
8436 ; ashr(di|si)3 instruction pattern(s).
8437 ; Arithmetic right shifts
8438
8439 (define_expand "ashr<mode>3"
8440 [(parallel
8441 [(set (match_operand:DSI 0 "register_operand" "")
8442 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
8443 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))
8444 (clobber (reg:CC CC_REGNUM))])]
8445 ""
8446 "")
8447
8448 (define_insn "*ashrdi3_cc_31"
8449 [(set (reg CC_REGNUM)
8450 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8451 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
8452 (const_int 0)))
8453 (set (match_operand:DI 0 "register_operand" "=d")
8454 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
8455 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)"
8456 "srda\t%0,%Y2"
8457 [(set_attr "op_type" "RS")
8458 (set_attr "atype" "reg")])
8459
8460 (define_insn "*ashrdi3_cconly_31"
8461 [(set (reg CC_REGNUM)
8462 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8463 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
8464 (const_int 0)))
8465 (clobber (match_scratch:DI 0 "=d"))]
8466 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)"
8467 "srda\t%0,%Y2"
8468 [(set_attr "op_type" "RS")
8469 (set_attr "atype" "reg")])
8470
8471 (define_insn "*ashrdi3_31"
8472 [(set (match_operand:DI 0 "register_operand" "=d")
8473 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8474 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))
8475 (clobber (reg:CC CC_REGNUM))]
8476 "!TARGET_ZARCH"
8477 "srda\t%0,%Y2"
8478 [(set_attr "op_type" "RS")
8479 (set_attr "atype" "reg")])
8480
8481 ; sra, srag, srak
8482 (define_insn "*ashr<mode>3_cc"
8483 [(set (reg CC_REGNUM)
8484 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8485 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y"))
8486 (const_int 0)))
8487 (set (match_operand:GPR 0 "register_operand" "=d,d")
8488 (ashiftrt:GPR (match_dup 1) (match_dup 2)))]
8489 "s390_match_ccmode(insn, CCSmode)"
8490 "@
8491 sra<g>\t%0,<1>%Y2
8492 sra<gk>\t%0,%1,%Y2"
8493 [(set_attr "op_type" "RS<E>,RSY")
8494 (set_attr "atype" "reg,reg")
8495 (set_attr "cpu_facility" "*,z196")
8496 (set_attr "z10prop" "z10_super_E1,*")])
8497
8498 ; sra, srag, srak
8499 (define_insn "*ashr<mode>3_cconly"
8500 [(set (reg CC_REGNUM)
8501 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8502 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y"))
8503 (const_int 0)))
8504 (clobber (match_scratch:GPR 0 "=d,d"))]
8505 "s390_match_ccmode(insn, CCSmode)"
8506 "@
8507 sra<g>\t%0,<1>%Y2
8508 sra<gk>\t%0,%1,%Y2"
8509 [(set_attr "op_type" "RS<E>,RSY")
8510 (set_attr "atype" "reg,reg")
8511 (set_attr "cpu_facility" "*,z196")
8512 (set_attr "z10prop" "z10_super_E1,*")])
8513
8514 ; sra, srag
8515 (define_insn "*ashr<mode>3"
8516 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8517 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8518 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")))
8519 (clobber (reg:CC CC_REGNUM))]
8520 ""
8521 "@
8522 sra<g>\t%0,<1>%Y2
8523 sra<gk>\t%0,%1,%Y2"
8524 [(set_attr "op_type" "RS<E>,RSY")
8525 (set_attr "atype" "reg,reg")
8526 (set_attr "cpu_facility" "*,z196")
8527 (set_attr "z10prop" "z10_super_E1,*")])
8528
8529
8530 ; shift pattern with implicit ANDs
8531
8532 (define_insn "*ashrdi3_cc_31_and"
8533 [(set (reg CC_REGNUM)
8534 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8535 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8536 (match_operand:SI 3 "const_int_operand" "n")))
8537 (const_int 0)))
8538 (set (match_operand:DI 0 "register_operand" "=d")
8539 (ashiftrt:DI (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
8540 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)
8541 && (INTVAL (operands[3]) & 63) == 63"
8542 "srda\t%0,%Y2"
8543 [(set_attr "op_type" "RS")
8544 (set_attr "atype" "reg")])
8545
8546 (define_insn "*ashrdi3_cconly_31_and"
8547 [(set (reg CC_REGNUM)
8548 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8549 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8550 (match_operand:SI 3 "const_int_operand" "n")))
8551 (const_int 0)))
8552 (clobber (match_scratch:DI 0 "=d"))]
8553 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)
8554 && (INTVAL (operands[3]) & 63) == 63"
8555 "srda\t%0,%Y2"
8556 [(set_attr "op_type" "RS")
8557 (set_attr "atype" "reg")])
8558
8559 (define_insn "*ashrdi3_31_and"
8560 [(set (match_operand:DI 0 "register_operand" "=d")
8561 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8562 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8563 (match_operand:SI 3 "const_int_operand" "n"))))
8564 (clobber (reg:CC CC_REGNUM))]
8565 "!TARGET_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8566 "srda\t%0,%Y2"
8567 [(set_attr "op_type" "RS")
8568 (set_attr "atype" "reg")])
8569
8570 ; sra, srag, srak
8571 (define_insn "*ashr<mode>3_cc_and"
8572 [(set (reg CC_REGNUM)
8573 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8574 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8575 (match_operand:SI 3 "const_int_operand" "n,n")))
8576 (const_int 0)))
8577 (set (match_operand:GPR 0 "register_operand" "=d,d")
8578 (ashiftrt:GPR (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
8579 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
8580 "@
8581 sra<g>\t%0,<1>%Y2
8582 sra<gk>\t%0,%1,%Y2"
8583 [(set_attr "op_type" "RS<E>,RSY")
8584 (set_attr "atype" "reg,reg")
8585 (set_attr "cpu_facility" "*,z196")
8586 (set_attr "z10prop" "z10_super_E1,*")])
8587
8588 ; sra, srag, srak
8589 (define_insn "*ashr<mode>3_cconly_and"
8590 [(set (reg CC_REGNUM)
8591 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8592 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8593 (match_operand:SI 3 "const_int_operand" "n,n")))
8594 (const_int 0)))
8595 (clobber (match_scratch:GPR 0 "=d,d"))]
8596 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
8597 "@
8598 sra<g>\t%0,<1>%Y2
8599 sra<gk>\t%0,%1,%Y2"
8600 [(set_attr "op_type" "RS<E>,RSY")
8601 (set_attr "atype" "reg,reg")
8602 (set_attr "cpu_facility" "*,z196")
8603 (set_attr "z10prop" "z10_super_E1,*")])
8604
8605 ; sra, srag, srak
8606 (define_insn "*ashr<mode>3_and"
8607 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8608 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8609 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8610 (match_operand:SI 3 "const_int_operand" "n,n"))))
8611 (clobber (reg:CC CC_REGNUM))]
8612 "(INTVAL (operands[3]) & 63) == 63"
8613 "@
8614 sra<g>\t%0,<1>%Y2
8615 sra<gk>\t%0,%1,%Y2"
8616 [(set_attr "op_type" "RS<E>,RSY")
8617 (set_attr "atype" "reg,reg")
8618 (set_attr "cpu_facility" "*,z196")
8619 (set_attr "z10prop" "z10_super_E1,*")])
8620
8621
8622 ;;
8623 ;; Branch instruction patterns.
8624 ;;
8625
8626 (define_expand "cbranch<mode>4"
8627 [(set (pc)
8628 (if_then_else (match_operator 0 "comparison_operator"
8629 [(match_operand:GPR 1 "register_operand" "")
8630 (match_operand:GPR 2 "general_operand" "")])
8631 (label_ref (match_operand 3 "" ""))
8632 (pc)))]
8633 ""
8634 "s390_emit_jump (operands[3],
8635 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8636 DONE;")
8637
8638 (define_expand "cbranch<mode>4"
8639 [(set (pc)
8640 (if_then_else (match_operator 0 "comparison_operator"
8641 [(match_operand:FP 1 "register_operand" "")
8642 (match_operand:FP 2 "general_operand" "")])
8643 (label_ref (match_operand 3 "" ""))
8644 (pc)))]
8645 "TARGET_HARD_FLOAT"
8646 "s390_emit_jump (operands[3],
8647 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8648 DONE;")
8649
8650 (define_expand "cbranchcc4"
8651 [(set (pc)
8652 (if_then_else (match_operator 0 "s390_comparison"
8653 [(match_operand 1 "cc_reg_operand" "")
8654 (match_operand 2 "const_int_operand" "")])
8655 (label_ref (match_operand 3 "" ""))
8656 (pc)))]
8657 ""
8658 "")
8659
8660
8661 ;;
8662 ;;- Conditional jump instructions.
8663 ;;
8664
8665 (define_insn "*cjump_64"
8666 [(set (pc)
8667 (if_then_else
8668 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8669 (match_operand 2 "const_int_operand" "")])
8670 (label_ref (match_operand 0 "" ""))
8671 (pc)))]
8672 "TARGET_CPU_ZARCH"
8673 {
8674 if (get_attr_length (insn) == 4)
8675 return "j%C1\t%l0";
8676 else
8677 return "jg%C1\t%l0";
8678 }
8679 [(set_attr "op_type" "RI")
8680 (set_attr "type" "branch")
8681 (set (attr "length")
8682 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8683 (const_int 4) (const_int 6)))])
8684
8685 (define_insn "*cjump_31"
8686 [(set (pc)
8687 (if_then_else
8688 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8689 (match_operand 2 "const_int_operand" "")])
8690 (label_ref (match_operand 0 "" ""))
8691 (pc)))]
8692 "!TARGET_CPU_ZARCH"
8693 {
8694 gcc_assert (get_attr_length (insn) == 4);
8695 return "j%C1\t%l0";
8696 }
8697 [(set_attr "op_type" "RI")
8698 (set_attr "type" "branch")
8699 (set (attr "length")
8700 (if_then_else (not (match_test "flag_pic"))
8701 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8702 (const_int 4) (const_int 6))
8703 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8704 (const_int 4) (const_int 8))))])
8705
8706 (define_insn "*cjump_long"
8707 [(set (pc)
8708 (if_then_else
8709 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8710 (match_operand 0 "address_operand" "ZQZR")
8711 (pc)))]
8712 ""
8713 {
8714 if (get_attr_op_type (insn) == OP_TYPE_RR)
8715 return "b%C1r\t%0";
8716 else
8717 return "b%C1\t%a0";
8718 }
8719 [(set (attr "op_type")
8720 (if_then_else (match_operand 0 "register_operand" "")
8721 (const_string "RR") (const_string "RX")))
8722 (set_attr "type" "branch")
8723 (set_attr "atype" "agen")])
8724
8725 ;; A conditional return instruction.
8726 (define_insn "*c<code>"
8727 [(set (pc)
8728 (if_then_else
8729 (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8730 (ANY_RETURN)
8731 (pc)))]
8732 "s390_can_use_<code>_insn ()"
8733 "b%C0r\t%%r14"
8734 [(set_attr "op_type" "RR")
8735 (set_attr "type" "jsr")
8736 (set_attr "atype" "agen")])
8737
8738 ;;
8739 ;;- Negated conditional jump instructions.
8740 ;;
8741
8742 (define_insn "*icjump_64"
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 if (get_attr_length (insn) == 4)
8751 return "j%D1\t%l0";
8752 else
8753 return "jg%D1\t%l0";
8754 }
8755 [(set_attr "op_type" "RI")
8756 (set_attr "type" "branch")
8757 (set (attr "length")
8758 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8759 (const_int 4) (const_int 6)))])
8760
8761 (define_insn "*icjump_31"
8762 [(set (pc)
8763 (if_then_else
8764 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8765 (pc)
8766 (label_ref (match_operand 0 "" ""))))]
8767 "!TARGET_CPU_ZARCH"
8768 {
8769 gcc_assert (get_attr_length (insn) == 4);
8770 return "j%D1\t%l0";
8771 }
8772 [(set_attr "op_type" "RI")
8773 (set_attr "type" "branch")
8774 (set (attr "length")
8775 (if_then_else (not (match_test "flag_pic"))
8776 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8777 (const_int 4) (const_int 6))
8778 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8779 (const_int 4) (const_int 8))))])
8780
8781 (define_insn "*icjump_long"
8782 [(set (pc)
8783 (if_then_else
8784 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8785 (pc)
8786 (match_operand 0 "address_operand" "ZQZR")))]
8787 ""
8788 {
8789 if (get_attr_op_type (insn) == OP_TYPE_RR)
8790 return "b%D1r\t%0";
8791 else
8792 return "b%D1\t%a0";
8793 }
8794 [(set (attr "op_type")
8795 (if_then_else (match_operand 0 "register_operand" "")
8796 (const_string "RR") (const_string "RX")))
8797 (set_attr "type" "branch")
8798 (set_attr "atype" "agen")])
8799
8800 ;;
8801 ;;- Trap instructions.
8802 ;;
8803
8804 (define_insn "trap"
8805 [(trap_if (const_int 1) (const_int 0))]
8806 ""
8807 "j\t.+2"
8808 [(set_attr "op_type" "RI")
8809 (set_attr "type" "branch")])
8810
8811 (define_expand "ctrap<mode>4"
8812 [(trap_if (match_operator 0 "comparison_operator"
8813 [(match_operand:GPR 1 "register_operand" "")
8814 (match_operand:GPR 2 "general_operand" "")])
8815 (match_operand 3 "const0_operand" ""))]
8816 ""
8817 {
8818 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8819 operands[1], operands[2]);
8820 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8821 DONE;
8822 })
8823
8824 (define_expand "ctrap<mode>4"
8825 [(trap_if (match_operator 0 "comparison_operator"
8826 [(match_operand:FP 1 "register_operand" "")
8827 (match_operand:FP 2 "general_operand" "")])
8828 (match_operand 3 "const0_operand" ""))]
8829 ""
8830 {
8831 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8832 operands[1], operands[2]);
8833 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8834 DONE;
8835 })
8836
8837 (define_insn "condtrap"
8838 [(trap_if (match_operator 0 "s390_comparison"
8839 [(match_operand 1 "cc_reg_operand" "c")
8840 (const_int 0)])
8841 (const_int 0))]
8842 ""
8843 "j%C0\t.+2";
8844 [(set_attr "op_type" "RI")
8845 (set_attr "type" "branch")])
8846
8847 ; crt, cgrt, cit, cgit
8848 (define_insn "*cmp_and_trap_signed_int<mode>"
8849 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
8850 [(match_operand:GPR 1 "register_operand" "d,d")
8851 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
8852 (const_int 0))]
8853 "TARGET_Z10"
8854 "@
8855 c<g>rt%C0\t%1,%2
8856 c<g>it%C0\t%1,%h2"
8857 [(set_attr "op_type" "RRF,RIE")
8858 (set_attr "type" "branch")
8859 (set_attr "z10prop" "z10_super_c,z10_super")])
8860
8861 ; clrt, clgrt, clfit, clgit, clt, clgt
8862 (define_insn "*cmp_and_trap_unsigned_int<mode>"
8863 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
8864 [(match_operand:GPR 1 "register_operand" "d,d, d")
8865 (match_operand:GPR 2 "general_operand" "d,D,RT")])
8866 (const_int 0))]
8867 "TARGET_Z10"
8868 "@
8869 cl<g>rt%C0\t%1,%2
8870 cl<gf>it%C0\t%1,%x2
8871 cl<g>t%C0\t%1,%2"
8872 [(set_attr "op_type" "RRF,RIE,RSY")
8873 (set_attr "type" "branch")
8874 (set_attr "z10prop" "z10_super_c,z10_super,*")
8875 (set_attr "cpu_facility" "z10,z10,zEC12")])
8876
8877 ; lat, lgat
8878 (define_insn "*load_and_trap<mode>"
8879 [(trap_if (eq (match_operand:GPR 0 "memory_operand" "RT")
8880 (const_int 0))
8881 (const_int 0))
8882 (set (match_operand:GPR 1 "register_operand" "=d")
8883 (match_dup 0))]
8884 "TARGET_ZEC12"
8885 "l<g>at\t%1,%0"
8886 [(set_attr "op_type" "RXY")])
8887
8888
8889 ;;
8890 ;;- Loop instructions.
8891 ;;
8892 ;; This is all complicated by the fact that since this is a jump insn
8893 ;; we must handle our own output reloads.
8894
8895 ;; branch on index
8896
8897 ; This splitter will be matched by combine and has to add the 2 moves
8898 ; necessary to load the compare and the increment values into a
8899 ; register pair as needed by brxle.
8900
8901 (define_insn_and_split "*brx_stage1_<GPR:mode>"
8902 [(set (pc)
8903 (if_then_else
8904 (match_operator 6 "s390_brx_operator"
8905 [(plus:GPR (match_operand:GPR 1 "register_operand" "")
8906 (match_operand:GPR 2 "general_operand" ""))
8907 (match_operand:GPR 3 "register_operand" "")])
8908 (label_ref (match_operand 0 "" ""))
8909 (pc)))
8910 (set (match_operand:GPR 4 "nonimmediate_operand" "")
8911 (plus:GPR (match_dup 1) (match_dup 2)))
8912 (clobber (match_scratch:GPR 5 ""))]
8913 "TARGET_CPU_ZARCH"
8914 "#"
8915 "!reload_completed && !reload_in_progress"
8916 [(set (match_dup 7) (match_dup 2)) ; the increment
8917 (set (match_dup 8) (match_dup 3)) ; the comparison value
8918 (parallel [(set (pc)
8919 (if_then_else
8920 (match_op_dup 6
8921 [(plus:GPR (match_dup 1) (match_dup 7))
8922 (match_dup 8)])
8923 (label_ref (match_dup 0))
8924 (pc)))
8925 (set (match_dup 4)
8926 (plus:GPR (match_dup 1) (match_dup 7)))
8927 (clobber (match_dup 5))
8928 (clobber (reg:CC CC_REGNUM))])]
8929 {
8930 rtx dreg = gen_reg_rtx (word_mode == DImode ? TImode : DImode);
8931 operands[7] = gen_lowpart (<GPR:MODE>mode,
8932 gen_highpart (word_mode, dreg));
8933 operands[8] = gen_lowpart (<GPR:MODE>mode,
8934 gen_lowpart (word_mode, dreg));
8935 })
8936
8937 ; brxlg, brxhg
8938
8939 (define_insn_and_split "*brxg_64bit"
8940 [(set (pc)
8941 (if_then_else
8942 (match_operator 5 "s390_brx_operator"
8943 [(plus:DI (match_operand:DI 1 "register_operand" "d,d,d")
8944 (subreg:DI (match_operand:TI 2 "register_operand" "d,d,d") 0))
8945 (subreg:DI (match_dup 2) 8)])
8946 (label_ref (match_operand 0 "" ""))
8947 (pc)))
8948 (set (match_operand:DI 3 "nonimmediate_operand" "=1,?X,?X")
8949 (plus:DI (match_dup 1)
8950 (subreg:DI (match_dup 2) 0)))
8951 (clobber (match_scratch:DI 4 "=X,&1,&?d"))
8952 (clobber (reg:CC CC_REGNUM))]
8953 "TARGET_ZARCH"
8954 {
8955 if (which_alternative != 0)
8956 return "#";
8957 else if (get_attr_length (insn) == 6)
8958 return "brx%E5g\t%1,%2,%l0";
8959 else
8960 return "agr\t%1,%2\;cgr\t%1,%M2\;jg%C5\t%l0";
8961 }
8962 "&& reload_completed
8963 && (!REG_P (operands[3])
8964 || !rtx_equal_p (operands[1], operands[3]))"
8965 [(set (match_dup 4) (match_dup 1))
8966 (parallel [(set (match_dup 4) (plus:DI (match_dup 4) (subreg:DI (match_dup 2) 0)))
8967 (clobber (reg:CC CC_REGNUM))])
8968 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:DI (match_dup 2) 8)))
8969 (set (match_dup 3) (match_dup 4))
8970 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8971 (label_ref (match_dup 0))
8972 (pc)))]
8973 ""
8974 [(set_attr "op_type" "RIE")
8975 (set_attr "type" "branch")
8976 (set (attr "length")
8977 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8978 (const_int 6) (const_int 16)))])
8979
8980 ; brxle, brxh
8981
8982 (define_insn_and_split "*brx_64bit"
8983 [(set (pc)
8984 (if_then_else
8985 (match_operator 5 "s390_brx_operator"
8986 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
8987 (subreg:SI (match_operand:TI 2 "register_operand" "d,d,d") 4))
8988 (subreg:SI (match_dup 2) 12)])
8989 (label_ref (match_operand 0 "" ""))
8990 (pc)))
8991 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
8992 (plus:SI (match_dup 1)
8993 (subreg:SI (match_dup 2) 4)))
8994 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
8995 (clobber (reg:CC CC_REGNUM))]
8996 "TARGET_ZARCH"
8997 {
8998 if (which_alternative != 0)
8999 return "#";
9000 else if (get_attr_length (insn) == 6)
9001 return "brx%C5\t%1,%2,%l0";
9002 else
9003 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9004 }
9005 "&& reload_completed
9006 && (!REG_P (operands[3])
9007 || !rtx_equal_p (operands[1], operands[3]))"
9008 [(set (match_dup 4) (match_dup 1))
9009 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 4)))
9010 (clobber (reg:CC CC_REGNUM))])
9011 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 12)))
9012 (set (match_dup 3) (match_dup 4))
9013 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9014 (label_ref (match_dup 0))
9015 (pc)))]
9016 ""
9017 [(set_attr "op_type" "RSI")
9018 (set_attr "type" "branch")
9019 (set (attr "length")
9020 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9021 (const_int 6) (const_int 14)))])
9022
9023 ; brxle, brxh
9024
9025 (define_insn_and_split "*brx_31bit"
9026 [(set (pc)
9027 (if_then_else
9028 (match_operator 5 "s390_brx_operator"
9029 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9030 (subreg:SI (match_operand:DI 2 "register_operand" "d,d,d") 0))
9031 (subreg:SI (match_dup 2) 4)])
9032 (label_ref (match_operand 0 "" ""))
9033 (pc)))
9034 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9035 (plus:SI (match_dup 1)
9036 (subreg:SI (match_dup 2) 0)))
9037 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9038 (clobber (reg:CC CC_REGNUM))]
9039 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
9040 {
9041 if (which_alternative != 0)
9042 return "#";
9043 else if (get_attr_length (insn) == 6)
9044 return "brx%C5\t%1,%2,%l0";
9045 else
9046 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9047 }
9048 "&& reload_completed
9049 && (!REG_P (operands[3])
9050 || !rtx_equal_p (operands[1], operands[3]))"
9051 [(set (match_dup 4) (match_dup 1))
9052 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 0)))
9053 (clobber (reg:CC CC_REGNUM))])
9054 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 4)))
9055 (set (match_dup 3) (match_dup 4))
9056 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9057 (label_ref (match_dup 0))
9058 (pc)))]
9059 ""
9060 [(set_attr "op_type" "RSI")
9061 (set_attr "type" "branch")
9062 (set (attr "length")
9063 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9064 (const_int 6) (const_int 14)))])
9065
9066
9067 ;; branch on count
9068
9069 (define_expand "doloop_end"
9070 [(use (match_operand 0 "" "")) ; loop pseudo
9071 (use (match_operand 1 "" ""))] ; label
9072 ""
9073 {
9074 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
9075 emit_jump_insn (gen_doloop_si31 (operands[1], operands[0], operands[0]));
9076 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
9077 emit_jump_insn (gen_doloop_si64 (operands[1], operands[0], operands[0]));
9078 else if (GET_MODE (operands[0]) == DImode && TARGET_ZARCH)
9079 emit_jump_insn (gen_doloop_di (operands[1], operands[0], operands[0]));
9080 else
9081 FAIL;
9082
9083 DONE;
9084 })
9085
9086 (define_insn_and_split "doloop_si64"
9087 [(set (pc)
9088 (if_then_else
9089 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9090 (const_int 1))
9091 (label_ref (match_operand 0 "" ""))
9092 (pc)))
9093 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9094 (plus:SI (match_dup 1) (const_int -1)))
9095 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9096 (clobber (reg:CC CC_REGNUM))]
9097 "TARGET_CPU_ZARCH"
9098 {
9099 if (which_alternative != 0)
9100 return "#";
9101 else if (get_attr_length (insn) == 4)
9102 return "brct\t%1,%l0";
9103 else
9104 return "ahi\t%1,-1\;jgne\t%l0";
9105 }
9106 "&& reload_completed
9107 && (! REG_P (operands[2])
9108 || ! rtx_equal_p (operands[1], operands[2]))"
9109 [(set (match_dup 3) (match_dup 1))
9110 (parallel [(set (reg:CCAN CC_REGNUM)
9111 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9112 (const_int 0)))
9113 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9114 (set (match_dup 2) (match_dup 3))
9115 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9116 (label_ref (match_dup 0))
9117 (pc)))]
9118 ""
9119 [(set_attr "op_type" "RI")
9120 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9121 ; hurt us in the (rare) case of ahi.
9122 (set_attr "z10prop" "z10_super_E1")
9123 (set_attr "type" "branch")
9124 (set (attr "length")
9125 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9126 (const_int 4) (const_int 10)))])
9127
9128 (define_insn_and_split "doloop_si31"
9129 [(set (pc)
9130 (if_then_else
9131 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9132 (const_int 1))
9133 (label_ref (match_operand 0 "" ""))
9134 (pc)))
9135 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9136 (plus:SI (match_dup 1) (const_int -1)))
9137 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9138 (clobber (reg:CC CC_REGNUM))]
9139 "!TARGET_CPU_ZARCH"
9140 {
9141 if (which_alternative != 0)
9142 return "#";
9143 else if (get_attr_length (insn) == 4)
9144 return "brct\t%1,%l0";
9145 else
9146 gcc_unreachable ();
9147 }
9148 "&& reload_completed
9149 && (! REG_P (operands[2])
9150 || ! rtx_equal_p (operands[1], operands[2]))"
9151 [(set (match_dup 3) (match_dup 1))
9152 (parallel [(set (reg:CCAN CC_REGNUM)
9153 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9154 (const_int 0)))
9155 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9156 (set (match_dup 2) (match_dup 3))
9157 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9158 (label_ref (match_dup 0))
9159 (pc)))]
9160 ""
9161 [(set_attr "op_type" "RI")
9162 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9163 ; hurt us in the (rare) case of ahi.
9164 (set_attr "z10prop" "z10_super_E1")
9165 (set_attr "type" "branch")
9166 (set (attr "length")
9167 (if_then_else (not (match_test "flag_pic"))
9168 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9169 (const_int 4) (const_int 6))
9170 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9171 (const_int 4) (const_int 8))))])
9172
9173 (define_insn "*doloop_si_long"
9174 [(set (pc)
9175 (if_then_else
9176 (ne (match_operand:SI 1 "register_operand" "d")
9177 (const_int 1))
9178 (match_operand 0 "address_operand" "ZQZR")
9179 (pc)))
9180 (set (match_operand:SI 2 "register_operand" "=1")
9181 (plus:SI (match_dup 1) (const_int -1)))
9182 (clobber (match_scratch:SI 3 "=X"))
9183 (clobber (reg:CC CC_REGNUM))]
9184 "!TARGET_CPU_ZARCH"
9185 {
9186 if (get_attr_op_type (insn) == OP_TYPE_RR)
9187 return "bctr\t%1,%0";
9188 else
9189 return "bct\t%1,%a0";
9190 }
9191 [(set (attr "op_type")
9192 (if_then_else (match_operand 0 "register_operand" "")
9193 (const_string "RR") (const_string "RX")))
9194 (set_attr "type" "branch")
9195 (set_attr "atype" "agen")
9196 (set_attr "z10prop" "z10_c")
9197 (set_attr "z196prop" "z196_cracked")])
9198
9199 (define_insn_and_split "doloop_di"
9200 [(set (pc)
9201 (if_then_else
9202 (ne (match_operand:DI 1 "register_operand" "d,d,d")
9203 (const_int 1))
9204 (label_ref (match_operand 0 "" ""))
9205 (pc)))
9206 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
9207 (plus:DI (match_dup 1) (const_int -1)))
9208 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
9209 (clobber (reg:CC CC_REGNUM))]
9210 "TARGET_ZARCH"
9211 {
9212 if (which_alternative != 0)
9213 return "#";
9214 else if (get_attr_length (insn) == 4)
9215 return "brctg\t%1,%l0";
9216 else
9217 return "aghi\t%1,-1\;jgne\t%l0";
9218 }
9219 "&& reload_completed
9220 && (! REG_P (operands[2])
9221 || ! rtx_equal_p (operands[1], operands[2]))"
9222 [(set (match_dup 3) (match_dup 1))
9223 (parallel [(set (reg:CCAN CC_REGNUM)
9224 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
9225 (const_int 0)))
9226 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
9227 (set (match_dup 2) (match_dup 3))
9228 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9229 (label_ref (match_dup 0))
9230 (pc)))]
9231 ""
9232 [(set_attr "op_type" "RI")
9233 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9234 ; hurt us in the (rare) case of ahi.
9235 (set_attr "z10prop" "z10_super_E1")
9236 (set_attr "type" "branch")
9237 (set (attr "length")
9238 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9239 (const_int 4) (const_int 10)))])
9240
9241 ;;
9242 ;;- Unconditional jump instructions.
9243 ;;
9244
9245 ;
9246 ; jump instruction pattern(s).
9247 ;
9248
9249 (define_expand "jump"
9250 [(match_operand 0 "" "")]
9251 ""
9252 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
9253
9254 (define_insn "*jump64"
9255 [(set (pc) (label_ref (match_operand 0 "" "")))]
9256 "TARGET_CPU_ZARCH"
9257 {
9258 if (get_attr_length (insn) == 4)
9259 return "j\t%l0";
9260 else
9261 return "jg\t%l0";
9262 }
9263 [(set_attr "op_type" "RI")
9264 (set_attr "type" "branch")
9265 (set (attr "length")
9266 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9267 (const_int 4) (const_int 6)))])
9268
9269 (define_insn "*jump31"
9270 [(set (pc) (label_ref (match_operand 0 "" "")))]
9271 "!TARGET_CPU_ZARCH"
9272 {
9273 gcc_assert (get_attr_length (insn) == 4);
9274 return "j\t%l0";
9275 }
9276 [(set_attr "op_type" "RI")
9277 (set_attr "type" "branch")
9278 (set (attr "length")
9279 (if_then_else (not (match_test "flag_pic"))
9280 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9281 (const_int 4) (const_int 6))
9282 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9283 (const_int 4) (const_int 8))))])
9284
9285 ;
9286 ; indirect-jump instruction pattern(s).
9287 ;
9288
9289 (define_insn "indirect_jump"
9290 [(set (pc) (match_operand 0 "address_operand" "ZQZR"))]
9291 ""
9292 {
9293 if (get_attr_op_type (insn) == OP_TYPE_RR)
9294 return "br\t%0";
9295 else
9296 return "b\t%a0";
9297 }
9298 [(set (attr "op_type")
9299 (if_then_else (match_operand 0 "register_operand" "")
9300 (const_string "RR") (const_string "RX")))
9301 (set_attr "type" "branch")
9302 (set_attr "atype" "agen")])
9303
9304 ;
9305 ; casesi instruction pattern(s).
9306 ;
9307
9308 (define_insn "casesi_jump"
9309 [(set (pc) (match_operand 0 "address_operand" "ZQZR"))
9310 (use (label_ref (match_operand 1 "" "")))]
9311 ""
9312 {
9313 if (get_attr_op_type (insn) == OP_TYPE_RR)
9314 return "br\t%0";
9315 else
9316 return "b\t%a0";
9317 }
9318 [(set (attr "op_type")
9319 (if_then_else (match_operand 0 "register_operand" "")
9320 (const_string "RR") (const_string "RX")))
9321 (set_attr "type" "branch")
9322 (set_attr "atype" "agen")])
9323
9324 (define_expand "casesi"
9325 [(match_operand:SI 0 "general_operand" "")
9326 (match_operand:SI 1 "general_operand" "")
9327 (match_operand:SI 2 "general_operand" "")
9328 (label_ref (match_operand 3 "" ""))
9329 (label_ref (match_operand 4 "" ""))]
9330 ""
9331 {
9332 rtx index = gen_reg_rtx (SImode);
9333 rtx base = gen_reg_rtx (Pmode);
9334 rtx target = gen_reg_rtx (Pmode);
9335
9336 emit_move_insn (index, operands[0]);
9337 emit_insn (gen_subsi3 (index, index, operands[1]));
9338 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
9339 operands[4]);
9340
9341 if (Pmode != SImode)
9342 index = convert_to_mode (Pmode, index, 1);
9343 if (GET_CODE (index) != REG)
9344 index = copy_to_mode_reg (Pmode, index);
9345
9346 if (TARGET_64BIT)
9347 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
9348 else
9349 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
9350
9351 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
9352
9353 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
9354 emit_move_insn (target, index);
9355
9356 if (flag_pic)
9357 target = gen_rtx_PLUS (Pmode, base, target);
9358 emit_jump_insn (gen_casesi_jump (target, operands[3]));
9359
9360 DONE;
9361 })
9362
9363
9364 ;;
9365 ;;- Jump to subroutine.
9366 ;;
9367 ;;
9368
9369 ;
9370 ; untyped call instruction pattern(s).
9371 ;
9372
9373 ;; Call subroutine returning any type.
9374 (define_expand "untyped_call"
9375 [(parallel [(call (match_operand 0 "" "")
9376 (const_int 0))
9377 (match_operand 1 "" "")
9378 (match_operand 2 "" "")])]
9379 ""
9380 {
9381 int i;
9382
9383 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
9384
9385 for (i = 0; i < XVECLEN (operands[2], 0); i++)
9386 {
9387 rtx set = XVECEXP (operands[2], 0, i);
9388 emit_move_insn (SET_DEST (set), SET_SRC (set));
9389 }
9390
9391 /* The optimizer does not know that the call sets the function value
9392 registers we stored in the result block. We avoid problems by
9393 claiming that all hard registers are used and clobbered at this
9394 point. */
9395 emit_insn (gen_blockage ());
9396
9397 DONE;
9398 })
9399
9400 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
9401 ;; all of memory. This blocks insns from being moved across this point.
9402
9403 (define_insn "blockage"
9404 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
9405 ""
9406 ""
9407 [(set_attr "type" "none")
9408 (set_attr "length" "0")])
9409
9410 ;
9411 ; sibcall patterns
9412 ;
9413
9414 (define_expand "sibcall"
9415 [(call (match_operand 0 "" "")
9416 (match_operand 1 "" ""))]
9417 ""
9418 {
9419 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
9420 DONE;
9421 })
9422
9423 (define_insn "*sibcall_br"
9424 [(call (mem:QI (reg SIBCALL_REGNUM))
9425 (match_operand 0 "const_int_operand" "n"))]
9426 "SIBLING_CALL_P (insn)
9427 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
9428 "br\t%%r1"
9429 [(set_attr "op_type" "RR")
9430 (set_attr "type" "branch")
9431 (set_attr "atype" "agen")])
9432
9433 (define_insn "*sibcall_brc"
9434 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9435 (match_operand 1 "const_int_operand" "n"))]
9436 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9437 "j\t%0"
9438 [(set_attr "op_type" "RI")
9439 (set_attr "type" "branch")])
9440
9441 (define_insn "*sibcall_brcl"
9442 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9443 (match_operand 1 "const_int_operand" "n"))]
9444 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9445 "jg\t%0"
9446 [(set_attr "op_type" "RIL")
9447 (set_attr "type" "branch")])
9448
9449 ;
9450 ; sibcall_value patterns
9451 ;
9452
9453 (define_expand "sibcall_value"
9454 [(set (match_operand 0 "" "")
9455 (call (match_operand 1 "" "")
9456 (match_operand 2 "" "")))]
9457 ""
9458 {
9459 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
9460 DONE;
9461 })
9462
9463 (define_insn "*sibcall_value_br"
9464 [(set (match_operand 0 "" "")
9465 (call (mem:QI (reg SIBCALL_REGNUM))
9466 (match_operand 1 "const_int_operand" "n")))]
9467 "SIBLING_CALL_P (insn)
9468 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
9469 "br\t%%r1"
9470 [(set_attr "op_type" "RR")
9471 (set_attr "type" "branch")
9472 (set_attr "atype" "agen")])
9473
9474 (define_insn "*sibcall_value_brc"
9475 [(set (match_operand 0 "" "")
9476 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9477 (match_operand 2 "const_int_operand" "n")))]
9478 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9479 "j\t%1"
9480 [(set_attr "op_type" "RI")
9481 (set_attr "type" "branch")])
9482
9483 (define_insn "*sibcall_value_brcl"
9484 [(set (match_operand 0 "" "")
9485 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9486 (match_operand 2 "const_int_operand" "n")))]
9487 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9488 "jg\t%1"
9489 [(set_attr "op_type" "RIL")
9490 (set_attr "type" "branch")])
9491
9492
9493 ;
9494 ; call instruction pattern(s).
9495 ;
9496
9497 (define_expand "call"
9498 [(call (match_operand 0 "" "")
9499 (match_operand 1 "" ""))
9500 (use (match_operand 2 "" ""))]
9501 ""
9502 {
9503 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
9504 gen_rtx_REG (Pmode, RETURN_REGNUM));
9505 DONE;
9506 })
9507
9508 (define_insn "*bras"
9509 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9510 (match_operand 1 "const_int_operand" "n"))
9511 (clobber (match_operand 2 "register_operand" "=r"))]
9512 "!SIBLING_CALL_P (insn)
9513 && TARGET_SMALL_EXEC
9514 && GET_MODE (operands[2]) == Pmode"
9515 "bras\t%2,%0"
9516 [(set_attr "op_type" "RI")
9517 (set_attr "type" "jsr")
9518 (set_attr "z196prop" "z196_cracked")])
9519
9520 (define_insn "*brasl"
9521 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9522 (match_operand 1 "const_int_operand" "n"))
9523 (clobber (match_operand 2 "register_operand" "=r"))]
9524 "!SIBLING_CALL_P (insn)
9525 && TARGET_CPU_ZARCH
9526 && GET_MODE (operands[2]) == Pmode"
9527 "brasl\t%2,%0"
9528 [(set_attr "op_type" "RIL")
9529 (set_attr "type" "jsr")
9530 (set_attr "z196prop" "z196_cracked")])
9531
9532 (define_insn "*basr"
9533 [(call (mem:QI (match_operand 0 "address_operand" "ZQZR"))
9534 (match_operand 1 "const_int_operand" "n"))
9535 (clobber (match_operand 2 "register_operand" "=r"))]
9536 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
9537 {
9538 if (get_attr_op_type (insn) == OP_TYPE_RR)
9539 return "basr\t%2,%0";
9540 else
9541 return "bas\t%2,%a0";
9542 }
9543 [(set (attr "op_type")
9544 (if_then_else (match_operand 0 "register_operand" "")
9545 (const_string "RR") (const_string "RX")))
9546 (set_attr "type" "jsr")
9547 (set_attr "atype" "agen")
9548 (set_attr "z196prop" "z196_cracked")])
9549
9550 ;
9551 ; call_value instruction pattern(s).
9552 ;
9553
9554 (define_expand "call_value"
9555 [(set (match_operand 0 "" "")
9556 (call (match_operand 1 "" "")
9557 (match_operand 2 "" "")))
9558 (use (match_operand 3 "" ""))]
9559 ""
9560 {
9561 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
9562 gen_rtx_REG (Pmode, RETURN_REGNUM));
9563 DONE;
9564 })
9565
9566 (define_insn "*bras_r"
9567 [(set (match_operand 0 "" "")
9568 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9569 (match_operand:SI 2 "const_int_operand" "n")))
9570 (clobber (match_operand 3 "register_operand" "=r"))]
9571 "!SIBLING_CALL_P (insn)
9572 && TARGET_SMALL_EXEC
9573 && GET_MODE (operands[3]) == Pmode"
9574 "bras\t%3,%1"
9575 [(set_attr "op_type" "RI")
9576 (set_attr "type" "jsr")
9577 (set_attr "z196prop" "z196_cracked")])
9578
9579 (define_insn "*brasl_r"
9580 [(set (match_operand 0 "" "")
9581 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9582 (match_operand 2 "const_int_operand" "n")))
9583 (clobber (match_operand 3 "register_operand" "=r"))]
9584 "!SIBLING_CALL_P (insn)
9585 && TARGET_CPU_ZARCH
9586 && GET_MODE (operands[3]) == Pmode"
9587 "brasl\t%3,%1"
9588 [(set_attr "op_type" "RIL")
9589 (set_attr "type" "jsr")
9590 (set_attr "z196prop" "z196_cracked")])
9591
9592 (define_insn "*basr_r"
9593 [(set (match_operand 0 "" "")
9594 (call (mem:QI (match_operand 1 "address_operand" "ZQZR"))
9595 (match_operand 2 "const_int_operand" "n")))
9596 (clobber (match_operand 3 "register_operand" "=r"))]
9597 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9598 {
9599 if (get_attr_op_type (insn) == OP_TYPE_RR)
9600 return "basr\t%3,%1";
9601 else
9602 return "bas\t%3,%a1";
9603 }
9604 [(set (attr "op_type")
9605 (if_then_else (match_operand 1 "register_operand" "")
9606 (const_string "RR") (const_string "RX")))
9607 (set_attr "type" "jsr")
9608 (set_attr "atype" "agen")
9609 (set_attr "z196prop" "z196_cracked")])
9610
9611 ;;
9612 ;;- Thread-local storage support.
9613 ;;
9614
9615 (define_expand "get_thread_pointer<mode>"
9616 [(set (match_operand:P 0 "nonimmediate_operand" "") (reg:P TP_REGNUM))]
9617 ""
9618 "")
9619
9620 (define_expand "set_thread_pointer<mode>"
9621 [(set (reg:P TP_REGNUM) (match_operand:P 0 "nonimmediate_operand" ""))
9622 (set (reg:P TP_REGNUM) (unspec_volatile:P [(reg:P TP_REGNUM)] UNSPECV_SET_TP))]
9623 ""
9624 "")
9625
9626 (define_insn "*set_tp"
9627 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
9628 ""
9629 ""
9630 [(set_attr "type" "none")
9631 (set_attr "length" "0")])
9632
9633 (define_insn "*tls_load_64"
9634 [(set (match_operand:DI 0 "register_operand" "=d")
9635 (unspec:DI [(match_operand:DI 1 "memory_operand" "RT")
9636 (match_operand:DI 2 "" "")]
9637 UNSPEC_TLS_LOAD))]
9638 "TARGET_64BIT"
9639 "lg\t%0,%1%J2"
9640 [(set_attr "op_type" "RXE")
9641 (set_attr "z10prop" "z10_fwd_A3")])
9642
9643 (define_insn "*tls_load_31"
9644 [(set (match_operand:SI 0 "register_operand" "=d,d")
9645 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
9646 (match_operand:SI 2 "" "")]
9647 UNSPEC_TLS_LOAD))]
9648 "!TARGET_64BIT"
9649 "@
9650 l\t%0,%1%J2
9651 ly\t%0,%1%J2"
9652 [(set_attr "op_type" "RX,RXY")
9653 (set_attr "type" "load")
9654 (set_attr "z10prop" "z10_fwd_A3,z10_fwd_A3")])
9655
9656 (define_insn "*bras_tls"
9657 [(set (match_operand 0 "" "")
9658 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9659 (match_operand 2 "const_int_operand" "n")))
9660 (clobber (match_operand 3 "register_operand" "=r"))
9661 (use (match_operand 4 "" ""))]
9662 "!SIBLING_CALL_P (insn)
9663 && TARGET_SMALL_EXEC
9664 && GET_MODE (operands[3]) == Pmode"
9665 "bras\t%3,%1%J4"
9666 [(set_attr "op_type" "RI")
9667 (set_attr "type" "jsr")
9668 (set_attr "z196prop" "z196_cracked")])
9669
9670 (define_insn "*brasl_tls"
9671 [(set (match_operand 0 "" "")
9672 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9673 (match_operand 2 "const_int_operand" "n")))
9674 (clobber (match_operand 3 "register_operand" "=r"))
9675 (use (match_operand 4 "" ""))]
9676 "!SIBLING_CALL_P (insn)
9677 && TARGET_CPU_ZARCH
9678 && GET_MODE (operands[3]) == Pmode"
9679 "brasl\t%3,%1%J4"
9680 [(set_attr "op_type" "RIL")
9681 (set_attr "type" "jsr")
9682 (set_attr "z196prop" "z196_cracked")])
9683
9684 (define_insn "*basr_tls"
9685 [(set (match_operand 0 "" "")
9686 (call (mem:QI (match_operand 1 "address_operand" "ZQZR"))
9687 (match_operand 2 "const_int_operand" "n")))
9688 (clobber (match_operand 3 "register_operand" "=r"))
9689 (use (match_operand 4 "" ""))]
9690 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9691 {
9692 if (get_attr_op_type (insn) == OP_TYPE_RR)
9693 return "basr\t%3,%1%J4";
9694 else
9695 return "bas\t%3,%a1%J4";
9696 }
9697 [(set (attr "op_type")
9698 (if_then_else (match_operand 1 "register_operand" "")
9699 (const_string "RR") (const_string "RX")))
9700 (set_attr "type" "jsr")
9701 (set_attr "atype" "agen")
9702 (set_attr "z196prop" "z196_cracked")])
9703
9704 ;;
9705 ;;- Atomic operations
9706 ;;
9707
9708 ;
9709 ; memory barrier patterns.
9710 ;
9711
9712 (define_expand "mem_signal_fence"
9713 [(match_operand:SI 0 "const_int_operand")] ;; model
9714 ""
9715 {
9716 /* The s390 memory model is strong enough not to require any
9717 barrier in order to synchronize a thread with itself. */
9718 DONE;
9719 })
9720
9721 (define_expand "mem_thread_fence"
9722 [(match_operand:SI 0 "const_int_operand")] ;; model
9723 ""
9724 {
9725 /* Unless this is a SEQ_CST fence, the s390 memory model is strong
9726 enough not to require barriers of any kind. */
9727 if (is_mm_seq_cst (memmodel_from_int (INTVAL (operands[0]))))
9728 {
9729 rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
9730 MEM_VOLATILE_P (mem) = 1;
9731 emit_insn (gen_mem_thread_fence_1 (mem));
9732 }
9733 DONE;
9734 })
9735
9736 ; Although bcr is superscalar on Z10, this variant will never
9737 ; become part of an execution group.
9738 ; With z196 we can make use of the fast-BCR-serialization facility.
9739 ; This allows for a slightly faster sync which is sufficient for our
9740 ; purposes.
9741 (define_insn "mem_thread_fence_1"
9742 [(set (match_operand:BLK 0 "" "")
9743 (unspec:BLK [(match_dup 0)] UNSPEC_MB))]
9744 ""
9745 {
9746 if (TARGET_Z196)
9747 return "bcr\t14,0";
9748 else
9749 return "bcr\t15,0";
9750 }
9751 [(set_attr "op_type" "RR")
9752 (set_attr "mnemonic" "bcr_flush")
9753 (set_attr "z196prop" "z196_alone")])
9754
9755 ;
9756 ; atomic load/store operations
9757 ;
9758
9759 ; Atomic loads need not examine the memory model at all.
9760 (define_expand "atomic_load<mode>"
9761 [(match_operand:DINT 0 "register_operand") ;; output
9762 (match_operand:DINT 1 "memory_operand") ;; memory
9763 (match_operand:SI 2 "const_int_operand")] ;; model
9764 ""
9765 {
9766 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9767 FAIL;
9768
9769 if (<MODE>mode == TImode)
9770 emit_insn (gen_atomic_loadti_1 (operands[0], operands[1]));
9771 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9772 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1]));
9773 else
9774 emit_move_insn (operands[0], operands[1]);
9775 DONE;
9776 })
9777
9778 ; Different from movdi_31 in that we want no splitters.
9779 (define_insn "atomic_loaddi_1"
9780 [(set (match_operand:DI 0 "register_operand" "=d,d,!*f,!*f")
9781 (unspec:DI [(match_operand:DI 1 "memory_operand" "Q,S,R,T")]
9782 UNSPEC_MOVA))]
9783 "!TARGET_ZARCH"
9784 "@
9785 lm\t%0,%M0,%S1
9786 lmy\t%0,%M0,%S1
9787 ld\t%0,%1
9788 ldy\t%0,%1"
9789 [(set_attr "op_type" "RS,RSY,RS,RSY")
9790 (set_attr "type" "lm,lm,floaddf,floaddf")])
9791
9792 (define_insn "atomic_loadti_1"
9793 [(set (match_operand:TI 0 "register_operand" "=r")
9794 (unspec:TI [(match_operand:TI 1 "memory_operand" "RT")]
9795 UNSPEC_MOVA))]
9796 "TARGET_ZARCH"
9797 "lpq\t%0,%1"
9798 [(set_attr "op_type" "RXY")
9799 (set_attr "type" "other")])
9800
9801 ; Atomic stores must(?) enforce sequential consistency.
9802 (define_expand "atomic_store<mode>"
9803 [(match_operand:DINT 0 "memory_operand") ;; memory
9804 (match_operand:DINT 1 "register_operand") ;; input
9805 (match_operand:SI 2 "const_int_operand")] ;; model
9806 ""
9807 {
9808 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
9809
9810 if (MEM_ALIGN (operands[0]) < GET_MODE_BITSIZE (GET_MODE (operands[0])))
9811 FAIL;
9812
9813 if (<MODE>mode == TImode)
9814 emit_insn (gen_atomic_storeti_1 (operands[0], operands[1]));
9815 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9816 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1]));
9817 else
9818 emit_move_insn (operands[0], operands[1]);
9819 if (is_mm_seq_cst (model))
9820 emit_insn (gen_mem_thread_fence (operands[2]));
9821 DONE;
9822 })
9823
9824 ; Different from movdi_31 in that we want no splitters.
9825 (define_insn "atomic_storedi_1"
9826 [(set (match_operand:DI 0 "memory_operand" "=Q,S,R,T")
9827 (unspec:DI [(match_operand:DI 1 "register_operand" "d,d,!*f,!*f")]
9828 UNSPEC_MOVA))]
9829 "!TARGET_ZARCH"
9830 "@
9831 stm\t%1,%N1,%S0
9832 stmy\t%1,%N1,%S0
9833 std %1,%0
9834 stdy %1,%0"
9835 [(set_attr "op_type" "RS,RSY,RS,RSY")
9836 (set_attr "type" "stm,stm,fstoredf,fstoredf")])
9837
9838 (define_insn "atomic_storeti_1"
9839 [(set (match_operand:TI 0 "memory_operand" "=RT")
9840 (unspec:TI [(match_operand:TI 1 "register_operand" "r")]
9841 UNSPEC_MOVA))]
9842 "TARGET_ZARCH"
9843 "stpq\t%1,%0"
9844 [(set_attr "op_type" "RXY")
9845 (set_attr "type" "other")])
9846
9847 ;
9848 ; compare and swap patterns.
9849 ;
9850
9851 (define_expand "atomic_compare_and_swap<mode>"
9852 [(match_operand:SI 0 "register_operand") ;; bool success output
9853 (match_operand:DGPR 1 "nonimmediate_operand");; oldval output
9854 (match_operand:DGPR 2 "memory_operand") ;; memory
9855 (match_operand:DGPR 3 "register_operand") ;; expected intput
9856 (match_operand:DGPR 4 "register_operand") ;; newval intput
9857 (match_operand:SI 5 "const_int_operand") ;; is_weak
9858 (match_operand:SI 6 "const_int_operand") ;; success model
9859 (match_operand:SI 7 "const_int_operand")] ;; failure model
9860 ""
9861 {
9862 rtx cc, cmp, output = operands[1];
9863
9864 if (!register_operand (output, <MODE>mode))
9865 output = gen_reg_rtx (<MODE>mode);
9866
9867 if (MEM_ALIGN (operands[2]) < GET_MODE_BITSIZE (GET_MODE (operands[2])))
9868 FAIL;
9869
9870 emit_insn (gen_atomic_compare_and_swap<mode>_internal
9871 (output, operands[2], operands[3], operands[4]));
9872
9873 /* We deliberately accept non-register operands in the predicate
9874 to ensure the write back to the output operand happens *before*
9875 the store-flags code below. This makes it easier for combine
9876 to merge the store-flags code with a potential test-and-branch
9877 pattern following (immediately!) afterwards. */
9878 if (output != operands[1])
9879 emit_move_insn (operands[1], output);
9880
9881 cc = gen_rtx_REG (CCZ1mode, CC_REGNUM);
9882 cmp = gen_rtx_EQ (SImode, cc, const0_rtx);
9883 emit_insn (gen_cstorecc4 (operands[0], cmp, cc, const0_rtx));
9884 DONE;
9885 })
9886
9887 (define_expand "atomic_compare_and_swap<mode>"
9888 [(match_operand:SI 0 "register_operand") ;; bool success output
9889 (match_operand:HQI 1 "nonimmediate_operand") ;; oldval output
9890 (match_operand:HQI 2 "memory_operand") ;; memory
9891 (match_operand:HQI 3 "general_operand") ;; expected intput
9892 (match_operand:HQI 4 "general_operand") ;; newval intput
9893 (match_operand:SI 5 "const_int_operand") ;; is_weak
9894 (match_operand:SI 6 "const_int_operand") ;; success model
9895 (match_operand:SI 7 "const_int_operand")] ;; failure model
9896 ""
9897 {
9898 s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1], operands[2],
9899 operands[3], operands[4], INTVAL (operands[5]));
9900 DONE;
9901 })
9902
9903 (define_expand "atomic_compare_and_swap<mode>_internal"
9904 [(parallel
9905 [(set (match_operand:DGPR 0 "register_operand")
9906 (match_operand:DGPR 1 "memory_operand"))
9907 (set (match_dup 1)
9908 (unspec_volatile:DGPR
9909 [(match_dup 1)
9910 (match_operand:DGPR 2 "register_operand")
9911 (match_operand:DGPR 3 "register_operand")]
9912 UNSPECV_CAS))
9913 (set (reg:CCZ1 CC_REGNUM)
9914 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
9915 "")
9916
9917 ; cdsg, csg
9918 (define_insn "*atomic_compare_and_swap<mode>_1"
9919 [(set (match_operand:TDI 0 "register_operand" "=r")
9920 (match_operand:TDI 1 "memory_operand" "+QS"))
9921 (set (match_dup 1)
9922 (unspec_volatile:TDI
9923 [(match_dup 1)
9924 (match_operand:TDI 2 "register_operand" "0")
9925 (match_operand:TDI 3 "register_operand" "r")]
9926 UNSPECV_CAS))
9927 (set (reg:CCZ1 CC_REGNUM)
9928 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9929 "TARGET_ZARCH"
9930 "c<td>sg\t%0,%3,%S1"
9931 [(set_attr "op_type" "RSY")
9932 (set_attr "type" "sem")])
9933
9934 ; cds, cdsy
9935 (define_insn "*atomic_compare_and_swapdi_2"
9936 [(set (match_operand:DI 0 "register_operand" "=r,r")
9937 (match_operand:DI 1 "memory_operand" "+Q,S"))
9938 (set (match_dup 1)
9939 (unspec_volatile:DI
9940 [(match_dup 1)
9941 (match_operand:DI 2 "register_operand" "0,0")
9942 (match_operand:DI 3 "register_operand" "r,r")]
9943 UNSPECV_CAS))
9944 (set (reg:CCZ1 CC_REGNUM)
9945 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9946 "!TARGET_ZARCH"
9947 "@
9948 cds\t%0,%3,%S1
9949 cdsy\t%0,%3,%S1"
9950 [(set_attr "op_type" "RS,RSY")
9951 (set_attr "type" "sem")])
9952
9953 ; cs, csy
9954 (define_insn "*atomic_compare_and_swapsi_3"
9955 [(set (match_operand:SI 0 "register_operand" "=r,r")
9956 (match_operand:SI 1 "memory_operand" "+Q,S"))
9957 (set (match_dup 1)
9958 (unspec_volatile:SI
9959 [(match_dup 1)
9960 (match_operand:SI 2 "register_operand" "0,0")
9961 (match_operand:SI 3 "register_operand" "r,r")]
9962 UNSPECV_CAS))
9963 (set (reg:CCZ1 CC_REGNUM)
9964 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9965 ""
9966 "@
9967 cs\t%0,%3,%S1
9968 csy\t%0,%3,%S1"
9969 [(set_attr "op_type" "RS,RSY")
9970 (set_attr "type" "sem")])
9971
9972 ;
9973 ; Other atomic instruction patterns.
9974 ;
9975
9976 ; z196 load and add, xor, or and and instructions
9977
9978 (define_expand "atomic_fetch_<atomic><mode>"
9979 [(match_operand:GPR 0 "register_operand") ;; val out
9980 (ATOMIC_Z196:GPR
9981 (match_operand:GPR 1 "memory_operand") ;; memory
9982 (match_operand:GPR 2 "register_operand")) ;; val in
9983 (match_operand:SI 3 "const_int_operand")] ;; model
9984 "TARGET_Z196"
9985 {
9986 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9987 FAIL;
9988
9989 emit_insn (gen_atomic_fetch_<atomic><mode>_iaf
9990 (operands[0], operands[1], operands[2]));
9991 DONE;
9992 })
9993
9994 ; lan, lang, lao, laog, lax, laxg, laa, laag
9995 (define_insn "atomic_fetch_<atomic><mode>_iaf"
9996 [(set (match_operand:GPR 0 "register_operand" "=d")
9997 (match_operand:GPR 1 "memory_operand" "+QS"))
9998 (set (match_dup 1)
9999 (unspec_volatile:GPR
10000 [(ATOMIC_Z196:GPR (match_dup 1)
10001 (match_operand:GPR 2 "general_operand" "d"))]
10002 UNSPECV_ATOMIC_OP))
10003 (clobber (reg:CC CC_REGNUM))]
10004 "TARGET_Z196"
10005 "la<noxa><g>\t%0,%2,%1"
10006 [(set_attr "op_type" "RSY")
10007 (set_attr "type" "sem")])
10008
10009 ;; For SImode and larger, the optabs.c code will do just fine in
10010 ;; expanding a compare-and-swap loop. For QI/HImode, we can do
10011 ;; better by expanding our own loop.
10012
10013 (define_expand "atomic_<atomic><mode>"
10014 [(ATOMIC:HQI
10015 (match_operand:HQI 0 "memory_operand") ;; memory
10016 (match_operand:HQI 1 "general_operand")) ;; val in
10017 (match_operand:SI 2 "const_int_operand")] ;; model
10018 ""
10019 {
10020 s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
10021 operands[1], false);
10022 DONE;
10023 })
10024
10025 (define_expand "atomic_fetch_<atomic><mode>"
10026 [(match_operand:HQI 0 "register_operand") ;; val out
10027 (ATOMIC:HQI
10028 (match_operand:HQI 1 "memory_operand") ;; memory
10029 (match_operand:HQI 2 "general_operand")) ;; val in
10030 (match_operand:SI 3 "const_int_operand")] ;; model
10031 ""
10032 {
10033 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10034 operands[2], false);
10035 DONE;
10036 })
10037
10038 (define_expand "atomic_<atomic>_fetch<mode>"
10039 [(match_operand:HQI 0 "register_operand") ;; val out
10040 (ATOMIC:HQI
10041 (match_operand:HQI 1 "memory_operand") ;; memory
10042 (match_operand:HQI 2 "general_operand")) ;; val in
10043 (match_operand:SI 3 "const_int_operand")] ;; model
10044 ""
10045 {
10046 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10047 operands[2], true);
10048 DONE;
10049 })
10050
10051 (define_expand "atomic_exchange<mode>"
10052 [(match_operand:HQI 0 "register_operand") ;; val out
10053 (match_operand:HQI 1 "memory_operand") ;; memory
10054 (match_operand:HQI 2 "general_operand") ;; val in
10055 (match_operand:SI 3 "const_int_operand")] ;; model
10056 ""
10057 {
10058 s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
10059 operands[2], false);
10060 DONE;
10061 })
10062
10063 ;;
10064 ;;- Miscellaneous instructions.
10065 ;;
10066
10067 ;
10068 ; allocate stack instruction pattern(s).
10069 ;
10070
10071 (define_expand "allocate_stack"
10072 [(match_operand 0 "general_operand" "")
10073 (match_operand 1 "general_operand" "")]
10074 "TARGET_BACKCHAIN"
10075 {
10076 rtx temp = gen_reg_rtx (Pmode);
10077
10078 emit_move_insn (temp, s390_back_chain_rtx ());
10079 anti_adjust_stack (operands[1]);
10080 emit_move_insn (s390_back_chain_rtx (), temp);
10081
10082 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
10083 DONE;
10084 })
10085
10086
10087 ;
10088 ; setjmp instruction pattern.
10089 ;
10090
10091 (define_expand "builtin_setjmp_receiver"
10092 [(match_operand 0 "" "")]
10093 "flag_pic"
10094 {
10095 emit_insn (s390_load_got ());
10096 emit_use (pic_offset_table_rtx);
10097 DONE;
10098 })
10099
10100 ;; These patterns say how to save and restore the stack pointer. We need not
10101 ;; save the stack pointer at function level since we are careful to
10102 ;; preserve the backchain. At block level, we have to restore the backchain
10103 ;; when we restore the stack pointer.
10104 ;;
10105 ;; For nonlocal gotos, we must save both the stack pointer and its
10106 ;; backchain and restore both. Note that in the nonlocal case, the
10107 ;; save area is a memory location.
10108
10109 (define_expand "save_stack_function"
10110 [(match_operand 0 "general_operand" "")
10111 (match_operand 1 "general_operand" "")]
10112 ""
10113 "DONE;")
10114
10115 (define_expand "restore_stack_function"
10116 [(match_operand 0 "general_operand" "")
10117 (match_operand 1 "general_operand" "")]
10118 ""
10119 "DONE;")
10120
10121 (define_expand "restore_stack_block"
10122 [(match_operand 0 "register_operand" "")
10123 (match_operand 1 "register_operand" "")]
10124 "TARGET_BACKCHAIN"
10125 {
10126 rtx temp = gen_reg_rtx (Pmode);
10127
10128 emit_move_insn (temp, s390_back_chain_rtx ());
10129 emit_move_insn (operands[0], operands[1]);
10130 emit_move_insn (s390_back_chain_rtx (), temp);
10131
10132 DONE;
10133 })
10134
10135 (define_expand "save_stack_nonlocal"
10136 [(match_operand 0 "memory_operand" "")
10137 (match_operand 1 "register_operand" "")]
10138 ""
10139 {
10140 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10141
10142 /* Copy the backchain to the first word, sp to the second and the
10143 literal pool base to the third. */
10144
10145 rtx save_bc = adjust_address (operands[0], Pmode, 0);
10146 rtx save_sp = adjust_address (operands[0], Pmode, GET_MODE_SIZE (Pmode));
10147 rtx save_bp = adjust_address (operands[0], Pmode, 2 * GET_MODE_SIZE (Pmode));
10148
10149 if (TARGET_BACKCHAIN)
10150 emit_move_insn (save_bc, force_reg (Pmode, s390_back_chain_rtx ()));
10151
10152 emit_move_insn (save_sp, operands[1]);
10153 emit_move_insn (save_bp, base);
10154
10155 DONE;
10156 })
10157
10158 (define_expand "restore_stack_nonlocal"
10159 [(match_operand 0 "register_operand" "")
10160 (match_operand 1 "memory_operand" "")]
10161 ""
10162 {
10163 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10164 rtx temp = NULL_RTX;
10165
10166 /* Restore the backchain from the first word, sp from the second and the
10167 literal pool base from the third. */
10168
10169 rtx save_bc = adjust_address (operands[1], Pmode, 0);
10170 rtx save_sp = adjust_address (operands[1], Pmode, GET_MODE_SIZE (Pmode));
10171 rtx save_bp = adjust_address (operands[1], Pmode, 2 * GET_MODE_SIZE (Pmode));
10172
10173 if (TARGET_BACKCHAIN)
10174 temp = force_reg (Pmode, save_bc);
10175
10176 emit_move_insn (base, save_bp);
10177 emit_move_insn (operands[0], save_sp);
10178
10179 if (temp)
10180 emit_move_insn (s390_back_chain_rtx (), temp);
10181
10182 emit_use (base);
10183 DONE;
10184 })
10185
10186 (define_expand "exception_receiver"
10187 [(const_int 0)]
10188 ""
10189 {
10190 s390_set_has_landing_pad_p (true);
10191 DONE;
10192 })
10193
10194 ;
10195 ; nop instruction pattern(s).
10196 ;
10197
10198 (define_insn "nop"
10199 [(const_int 0)]
10200 ""
10201 "lr\t0,0"
10202 [(set_attr "op_type" "RR")
10203 (set_attr "z10prop" "z10_fr_E1")])
10204
10205 (define_insn "nop1"
10206 [(const_int 1)]
10207 ""
10208 "lr\t1,1"
10209 [(set_attr "op_type" "RR")])
10210
10211 ;;- Undeletable nops (used for hotpatching)
10212
10213 (define_insn "nop_2_byte"
10214 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_2_BYTE)]
10215 ""
10216 "nopr\t%%r7"
10217 [(set_attr "op_type" "RR")])
10218
10219 (define_insn "nop_4_byte"
10220 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_4_BYTE)]
10221 ""
10222 "nop\t0"
10223 [(set_attr "op_type" "RX")])
10224
10225 (define_insn "nop_6_byte"
10226 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_6_BYTE)]
10227 "TARGET_CPU_ZARCH"
10228 "brcl\t0, 0"
10229 [(set_attr "op_type" "RIL")])
10230
10231
10232 ;
10233 ; Special literal pool access instruction pattern(s).
10234 ;
10235
10236 (define_insn "*pool_entry"
10237 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
10238 UNSPECV_POOL_ENTRY)]
10239 ""
10240 {
10241 machine_mode mode = GET_MODE (PATTERN (insn));
10242 unsigned int align = GET_MODE_BITSIZE (mode);
10243 s390_output_pool_entry (operands[0], mode, align);
10244 return "";
10245 }
10246 [(set (attr "length")
10247 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
10248
10249 (define_insn "pool_align"
10250 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
10251 UNSPECV_POOL_ALIGN)]
10252 ""
10253 ".align\t%0"
10254 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10255
10256 (define_insn "pool_section_start"
10257 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
10258 ""
10259 {
10260 switch_to_section (targetm.asm_out.function_rodata_section
10261 (current_function_decl));
10262 return "";
10263 }
10264 [(set_attr "length" "0")])
10265
10266 (define_insn "pool_section_end"
10267 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
10268 ""
10269 {
10270 switch_to_section (current_function_section ());
10271 return "";
10272 }
10273 [(set_attr "length" "0")])
10274
10275 (define_insn "main_base_31_small"
10276 [(set (match_operand 0 "register_operand" "=a")
10277 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10278 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10279 "basr\t%0,0"
10280 [(set_attr "op_type" "RR")
10281 (set_attr "type" "la")
10282 (set_attr "z196prop" "z196_cracked")])
10283
10284 (define_insn "main_base_31_large"
10285 [(set (match_operand 0 "register_operand" "=a")
10286 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
10287 (set (pc) (label_ref (match_operand 2 "" "")))]
10288 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10289 "bras\t%0,%2"
10290 [(set_attr "op_type" "RI")
10291 (set_attr "z196prop" "z196_cracked")])
10292
10293 (define_insn "main_base_64"
10294 [(set (match_operand 0 "register_operand" "=a")
10295 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10296 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10297 "larl\t%0,%1"
10298 [(set_attr "op_type" "RIL")
10299 (set_attr "type" "larl")
10300 (set_attr "z10prop" "z10_fwd_A1")])
10301
10302 (define_insn "main_pool"
10303 [(set (match_operand 0 "register_operand" "=a")
10304 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
10305 "GET_MODE (operands[0]) == Pmode"
10306 {
10307 gcc_unreachable ();
10308 }
10309 [(set (attr "type")
10310 (if_then_else (match_test "TARGET_CPU_ZARCH")
10311 (const_string "larl") (const_string "la")))])
10312
10313 (define_insn "reload_base_31"
10314 [(set (match_operand 0 "register_operand" "=a")
10315 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10316 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10317 "basr\t%0,0\;la\t%0,%1-.(%0)"
10318 [(set_attr "length" "6")
10319 (set_attr "type" "la")
10320 (set_attr "z196prop" "z196_cracked")])
10321
10322 (define_insn "reload_base_64"
10323 [(set (match_operand 0 "register_operand" "=a")
10324 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10325 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10326 "larl\t%0,%1"
10327 [(set_attr "op_type" "RIL")
10328 (set_attr "type" "larl")
10329 (set_attr "z10prop" "z10_fwd_A1")])
10330
10331 (define_insn "pool"
10332 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
10333 ""
10334 {
10335 gcc_unreachable ();
10336 }
10337 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10338
10339 ;;
10340 ;; Insns related to generating the function prologue and epilogue.
10341 ;;
10342
10343
10344 (define_expand "prologue"
10345 [(use (const_int 0))]
10346 ""
10347 "s390_emit_prologue (); DONE;")
10348
10349 (define_expand "epilogue"
10350 [(use (const_int 1))]
10351 ""
10352 "s390_emit_epilogue (false); DONE;")
10353
10354 (define_expand "sibcall_epilogue"
10355 [(use (const_int 0))]
10356 ""
10357 "s390_emit_epilogue (true); DONE;")
10358
10359 ;; A direct return instruction, without using an epilogue.
10360 (define_insn "<code>"
10361 [(ANY_RETURN)]
10362 "s390_can_use_<code>_insn ()"
10363 "br\t%%r14"
10364 [(set_attr "op_type" "RR")
10365 (set_attr "type" "jsr")
10366 (set_attr "atype" "agen")])
10367
10368 (define_insn "*return"
10369 [(return)
10370 (use (match_operand 0 "register_operand" "a"))]
10371 "GET_MODE (operands[0]) == Pmode"
10372 "br\t%0"
10373 [(set_attr "op_type" "RR")
10374 (set_attr "type" "jsr")
10375 (set_attr "atype" "agen")])
10376
10377
10378 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
10379 ;; pointer. This is used for compatibility.
10380
10381 (define_expand "ptr_extend"
10382 [(set (match_operand:DI 0 "register_operand" "=r")
10383 (match_operand:SI 1 "register_operand" "r"))]
10384 "TARGET_64BIT"
10385 {
10386 emit_insn (gen_anddi3 (operands[0],
10387 gen_lowpart (DImode, operands[1]),
10388 GEN_INT (0x7fffffff)));
10389 DONE;
10390 })
10391
10392 ;; Instruction definition to expand eh_return macro to support
10393 ;; swapping in special linkage return addresses.
10394
10395 (define_expand "eh_return"
10396 [(use (match_operand 0 "register_operand" ""))]
10397 "TARGET_TPF"
10398 {
10399 s390_emit_tpf_eh_return (operands[0]);
10400 DONE;
10401 })
10402
10403 ;
10404 ; Stack Protector Patterns
10405 ;
10406
10407 (define_expand "stack_protect_set"
10408 [(set (match_operand 0 "memory_operand" "")
10409 (match_operand 1 "memory_operand" ""))]
10410 ""
10411 {
10412 #ifdef TARGET_THREAD_SSP_OFFSET
10413 operands[1]
10414 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10415 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10416 #endif
10417 if (TARGET_64BIT)
10418 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
10419 else
10420 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
10421
10422 DONE;
10423 })
10424
10425 (define_insn "stack_protect_set<mode>"
10426 [(set (match_operand:DSI 0 "memory_operand" "=Q")
10427 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
10428 ""
10429 "mvc\t%O0(%G0,%R0),%S1"
10430 [(set_attr "op_type" "SS")])
10431
10432 (define_expand "stack_protect_test"
10433 [(set (reg:CC CC_REGNUM)
10434 (compare (match_operand 0 "memory_operand" "")
10435 (match_operand 1 "memory_operand" "")))
10436 (match_operand 2 "" "")]
10437 ""
10438 {
10439 rtx cc_reg, test;
10440 #ifdef TARGET_THREAD_SSP_OFFSET
10441 operands[1]
10442 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10443 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10444 #endif
10445 if (TARGET_64BIT)
10446 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
10447 else
10448 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
10449
10450 cc_reg = gen_rtx_REG (CCZmode, CC_REGNUM);
10451 test = gen_rtx_EQ (VOIDmode, cc_reg, const0_rtx);
10452 emit_jump_insn (gen_cbranchcc4 (test, cc_reg, const0_rtx, operands[2]));
10453 DONE;
10454 })
10455
10456 (define_insn "stack_protect_test<mode>"
10457 [(set (reg:CCZ CC_REGNUM)
10458 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
10459 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
10460 ""
10461 "clc\t%O0(%G0,%R0),%S1"
10462 [(set_attr "op_type" "SS")])
10463
10464 ; This is used in s390_emit_prologue in order to prevent insns
10465 ; adjusting the stack pointer to be moved over insns writing stack
10466 ; slots using a copy of the stack pointer in a different register.
10467 (define_insn "stack_tie"
10468 [(set (match_operand:BLK 0 "memory_operand" "+m")
10469 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
10470 ""
10471 ""
10472 [(set_attr "length" "0")])
10473
10474
10475 ;
10476 ; Data prefetch patterns
10477 ;
10478
10479 (define_insn "prefetch"
10480 [(prefetch (match_operand 0 "address_operand" "ZQZRZSZT,X")
10481 (match_operand:SI 1 "const_int_operand" " n,n")
10482 (match_operand:SI 2 "const_int_operand" " n,n"))]
10483 "TARGET_Z10"
10484 {
10485 switch (which_alternative)
10486 {
10487 case 0:
10488 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
10489 case 1:
10490 if (larl_operand (operands[0], Pmode))
10491 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
10492 default:
10493
10494 /* This might be reached for symbolic operands with an odd
10495 addend. We simply omit the prefetch for such rare cases. */
10496
10497 return "";
10498 }
10499 }
10500 [(set_attr "type" "load,larl")
10501 (set_attr "op_type" "RXY,RIL")
10502 (set_attr "z10prop" "z10_super")
10503 (set_attr "z196prop" "z196_alone")])
10504
10505
10506 ;
10507 ; Byte swap instructions
10508 ;
10509
10510 ; FIXME: There is also mvcin but we cannot use it since src and target
10511 ; may overlap.
10512 (define_insn "bswap<mode>2"
10513 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,RT")
10514 (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,RT, d")))]
10515 "TARGET_CPU_ZARCH"
10516 "@
10517 lrv<g>r\t%0,%1
10518 lrv<g>\t%0,%1
10519 strv<g>\t%1,%0"
10520 [(set_attr "type" "*,load,store")
10521 (set_attr "op_type" "RRE,RXY,RXY")
10522 (set_attr "z10prop" "z10_super")])
10523
10524 (define_insn "bswaphi2"
10525 [(set (match_operand:HI 0 "nonimmediate_operand" "=d, d,RT")
10526 (bswap:HI (match_operand:HI 1 "nonimmediate_operand" " d,RT, d")))]
10527 "TARGET_CPU_ZARCH"
10528 "@
10529 #
10530 lrvh\t%0,%1
10531 strvh\t%1,%0"
10532 [(set_attr "type" "*,load,store")
10533 (set_attr "op_type" "RRE,RXY,RXY")
10534 (set_attr "z10prop" "z10_super")])
10535
10536 (define_split
10537 [(set (match_operand:HI 0 "register_operand" "")
10538 (bswap:HI (match_operand:HI 1 "register_operand" "")))]
10539 "TARGET_CPU_ZARCH"
10540 [(set (match_dup 2) (bswap:SI (match_dup 3)))
10541 (set (match_dup 2) (lshiftrt:SI (match_dup 2) (const_int 16)))]
10542 {
10543 operands[2] = simplify_gen_subreg (SImode, operands[0], HImode, 0);
10544 operands[3] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
10545 })
10546
10547
10548 ;
10549 ; Population count instruction
10550 ;
10551
10552 ; The S/390 popcount instruction counts the bits of op1 in 8 byte
10553 ; portions and stores the result in the corresponding bytes in op0.
10554 (define_insn "*popcount<mode>"
10555 [(set (match_operand:INT 0 "register_operand" "=d")
10556 (unspec:INT [(match_operand:INT 1 "register_operand" "d")] UNSPEC_POPCNT))
10557 (clobber (reg:CC CC_REGNUM))]
10558 "TARGET_Z196"
10559 "popcnt\t%0,%1"
10560 [(set_attr "op_type" "RRE")])
10561
10562 (define_expand "popcountdi2"
10563 [; popcnt op0, op1
10564 (parallel [(set (match_operand:DI 0 "register_operand" "")
10565 (unspec:DI [(match_operand:DI 1 "register_operand")]
10566 UNSPEC_POPCNT))
10567 (clobber (reg:CC CC_REGNUM))])
10568 ; sllg op2, op0, 32
10569 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 32)))
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, 16
10574 (set (match_dup 2)
10575 (ashift:DI (match_dup 0) (const_int 16)))
10576 ; agr op0, op2
10577 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10578 (clobber (reg:CC CC_REGNUM))])
10579 ; sllg op2, op0, 8
10580 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 8)))
10581 ; agr op0, op2
10582 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10583 (clobber (reg:CC CC_REGNUM))])
10584 ; srlg op0, op0, 56
10585 (set (match_dup 0) (lshiftrt:DI (match_dup 0) (const_int 56)))]
10586 "TARGET_Z196 && TARGET_64BIT"
10587 "operands[2] = gen_reg_rtx (DImode);")
10588
10589 (define_expand "popcountsi2"
10590 [; popcnt op0, op1
10591 (parallel [(set (match_operand:SI 0 "register_operand" "")
10592 (unspec:SI [(match_operand:SI 1 "register_operand")]
10593 UNSPEC_POPCNT))
10594 (clobber (reg:CC CC_REGNUM))])
10595 ; sllk op2, op0, 16
10596 (set (match_dup 2)
10597 (ashift:SI (match_dup 0) (const_int 16)))
10598 ; ar op0, op2
10599 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10600 (clobber (reg:CC CC_REGNUM))])
10601 ; sllk op2, op0, 8
10602 (set (match_dup 2) (ashift:SI (match_dup 0) (const_int 8)))
10603 ; ar op0, op2
10604 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10605 (clobber (reg:CC CC_REGNUM))])
10606 ; srl op0, op0, 24
10607 (set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 24)))]
10608 "TARGET_Z196"
10609 "operands[2] = gen_reg_rtx (SImode);")
10610
10611 (define_expand "popcounthi2"
10612 [; popcnt op0, op1
10613 (parallel [(set (match_operand:HI 0 "register_operand" "")
10614 (unspec:HI [(match_operand:HI 1 "register_operand")]
10615 UNSPEC_POPCNT))
10616 (clobber (reg:CC CC_REGNUM))])
10617 ; sllk op2, op0, 8
10618 (set (match_dup 2)
10619 (ashift:SI (match_dup 0) (const_int 8)))
10620 ; ar op0, op2
10621 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10622 (clobber (reg:CC CC_REGNUM))])
10623 ; srl op0, op0, 8
10624 (set (match_dup 0) (lshiftrt:HI (match_dup 0) (const_int 8)))]
10625 "TARGET_Z196"
10626 "operands[2] = gen_reg_rtx (SImode);")
10627
10628 (define_expand "popcountqi2"
10629 [; popcnt op0, op1
10630 (parallel [(set (match_operand:QI 0 "register_operand" "")
10631 (unspec:QI [(match_operand:QI 1 "register_operand")]
10632 UNSPEC_POPCNT))
10633 (clobber (reg:CC CC_REGNUM))])]
10634 "TARGET_Z196"
10635 "")
10636
10637 ;;
10638 ;;- Copy sign instructions
10639 ;;
10640
10641 (define_insn "copysign<mode>3"
10642 [(set (match_operand:FP 0 "register_operand" "=f")
10643 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
10644 (match_operand:FP 2 "register_operand" "f")]
10645 UNSPEC_COPYSIGN))]
10646 "TARGET_Z196"
10647 "cpsdr\t%0,%2,%1"
10648 [(set_attr "op_type" "RRF")
10649 (set_attr "type" "fsimp<mode>")])
10650
10651
10652 ;;
10653 ;;- Transactional execution instructions
10654 ;;
10655
10656 ; This splitter helps combine to make use of CC directly when
10657 ; comparing the integer result of a tbegin builtin with a constant.
10658 ; The unspec is already removed by canonicalize_comparison. So this
10659 ; splitters only job is to turn the PARALLEL into separate insns
10660 ; again. Unfortunately this only works with the very first cc/int
10661 ; compare since combine is not able to deal with data flow across
10662 ; basic block boundaries.
10663
10664 ; It needs to be an insn pattern as well since combine does not apply
10665 ; the splitter directly. Combine would only use it if it actually
10666 ; would reduce the number of instructions.
10667 (define_insn_and_split "*ccraw_to_int"
10668 [(set (pc)
10669 (if_then_else
10670 (match_operator 0 "s390_eqne_operator"
10671 [(reg:CCRAW CC_REGNUM)
10672 (match_operand 1 "const_int_operand" "")])
10673 (label_ref (match_operand 2 "" ""))
10674 (pc)))
10675 (set (match_operand:SI 3 "register_operand" "=d")
10676 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10677 ""
10678 "#"
10679 ""
10680 [(set (match_dup 3)
10681 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))
10682 (set (pc)
10683 (if_then_else (match_op_dup 0 [(reg:CCRAW CC_REGNUM) (match_dup 1)])
10684 (label_ref (match_dup 2))
10685 (pc)))]
10686 "")
10687
10688 ; Non-constrained transaction begin
10689
10690 (define_expand "tbegin"
10691 [(match_operand:SI 0 "register_operand" "")
10692 (match_operand:BLK 1 "memory_operand" "")]
10693 "TARGET_HTM"
10694 {
10695 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, true);
10696 DONE;
10697 })
10698
10699 (define_expand "tbegin_nofloat"
10700 [(match_operand:SI 0 "register_operand" "")
10701 (match_operand:BLK 1 "memory_operand" "")]
10702 "TARGET_HTM"
10703 {
10704 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, false);
10705 DONE;
10706 })
10707
10708 (define_expand "tbegin_retry"
10709 [(match_operand:SI 0 "register_operand" "")
10710 (match_operand:BLK 1 "memory_operand" "")
10711 (match_operand:SI 2 "general_operand" "")]
10712 "TARGET_HTM"
10713 {
10714 s390_expand_tbegin (operands[0], operands[1], operands[2], true);
10715 DONE;
10716 })
10717
10718 (define_expand "tbegin_retry_nofloat"
10719 [(match_operand:SI 0 "register_operand" "")
10720 (match_operand:BLK 1 "memory_operand" "")
10721 (match_operand:SI 2 "general_operand" "")]
10722 "TARGET_HTM"
10723 {
10724 s390_expand_tbegin (operands[0], operands[1], operands[2], false);
10725 DONE;
10726 })
10727
10728 ; Clobber VRs since they don't get restored
10729 (define_insn "tbegin_1_z13"
10730 [(set (reg:CCRAW CC_REGNUM)
10731 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10732 UNSPECV_TBEGIN))
10733 (set (match_operand:BLK 1 "memory_operand" "=Q")
10734 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10735 (clobber (reg:TI 16)) (clobber (reg:TI 38))
10736 (clobber (reg:TI 17)) (clobber (reg:TI 39))
10737 (clobber (reg:TI 18)) (clobber (reg:TI 40))
10738 (clobber (reg:TI 19)) (clobber (reg:TI 41))
10739 (clobber (reg:TI 20)) (clobber (reg:TI 42))
10740 (clobber (reg:TI 21)) (clobber (reg:TI 43))
10741 (clobber (reg:TI 22)) (clobber (reg:TI 44))
10742 (clobber (reg:TI 23)) (clobber (reg:TI 45))
10743 (clobber (reg:TI 24)) (clobber (reg:TI 46))
10744 (clobber (reg:TI 25)) (clobber (reg:TI 47))
10745 (clobber (reg:TI 26)) (clobber (reg:TI 48))
10746 (clobber (reg:TI 27)) (clobber (reg:TI 49))
10747 (clobber (reg:TI 28)) (clobber (reg:TI 50))
10748 (clobber (reg:TI 29)) (clobber (reg:TI 51))
10749 (clobber (reg:TI 30)) (clobber (reg:TI 52))
10750 (clobber (reg:TI 31)) (clobber (reg:TI 53))]
10751 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10752 ; not supposed to be used for immediates (see genpreds.c).
10753 "TARGET_VX && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10754 "tbegin\t%1,%x0"
10755 [(set_attr "op_type" "SIL")])
10756
10757 (define_insn "tbegin_1"
10758 [(set (reg:CCRAW CC_REGNUM)
10759 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10760 UNSPECV_TBEGIN))
10761 (set (match_operand:BLK 1 "memory_operand" "=Q")
10762 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10763 (clobber (reg:DF 16))
10764 (clobber (reg:DF 17))
10765 (clobber (reg:DF 18))
10766 (clobber (reg:DF 19))
10767 (clobber (reg:DF 20))
10768 (clobber (reg:DF 21))
10769 (clobber (reg:DF 22))
10770 (clobber (reg:DF 23))
10771 (clobber (reg:DF 24))
10772 (clobber (reg:DF 25))
10773 (clobber (reg:DF 26))
10774 (clobber (reg:DF 27))
10775 (clobber (reg:DF 28))
10776 (clobber (reg:DF 29))
10777 (clobber (reg:DF 30))
10778 (clobber (reg:DF 31))]
10779 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10780 ; not supposed to be used for immediates (see genpreds.c).
10781 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10782 "tbegin\t%1,%x0"
10783 [(set_attr "op_type" "SIL")])
10784
10785 ; Same as above but without the FPR clobbers
10786 (define_insn "tbegin_nofloat_1"
10787 [(set (reg:CCRAW CC_REGNUM)
10788 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10789 UNSPECV_TBEGIN))
10790 (set (match_operand:BLK 1 "memory_operand" "=Q")
10791 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))]
10792 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10793 "tbegin\t%1,%x0"
10794 [(set_attr "op_type" "SIL")])
10795
10796
10797 ; Constrained transaction begin
10798
10799 (define_expand "tbeginc"
10800 [(set (reg:CCRAW CC_REGNUM)
10801 (unspec_volatile:CCRAW [(const_int TBEGINC_MASK)]
10802 UNSPECV_TBEGINC))]
10803 "TARGET_HTM"
10804 "")
10805
10806 (define_insn "*tbeginc_1"
10807 [(set (reg:CCRAW CC_REGNUM)
10808 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" " D")]
10809 UNSPECV_TBEGINC))]
10810 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10811 "tbeginc\t0,%x0"
10812 [(set_attr "op_type" "SIL")])
10813
10814 ; Transaction end
10815
10816 (define_expand "tend"
10817 [(set (reg:CCRAW CC_REGNUM)
10818 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))
10819 (set (match_operand:SI 0 "register_operand" "")
10820 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10821 "TARGET_HTM"
10822 "")
10823
10824 (define_insn "*tend_1"
10825 [(set (reg:CCRAW CC_REGNUM)
10826 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))]
10827 "TARGET_HTM"
10828 "tend"
10829 [(set_attr "op_type" "S")])
10830
10831 ; Transaction abort
10832
10833 (define_expand "tabort"
10834 [(unspec_volatile [(match_operand:SI 0 "shift_count_or_setmem_operand" "")]
10835 UNSPECV_TABORT)]
10836 "TARGET_HTM && operands != NULL"
10837 {
10838 if (CONST_INT_P (operands[0])
10839 && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 255)
10840 {
10841 error ("Invalid transaction abort code: " HOST_WIDE_INT_PRINT_DEC
10842 ". Values in range 0 through 255 are reserved.",
10843 INTVAL (operands[0]));
10844 FAIL;
10845 }
10846 })
10847
10848 (define_insn "*tabort_1"
10849 [(unspec_volatile [(match_operand:SI 0 "shift_count_or_setmem_operand" "Y")]
10850 UNSPECV_TABORT)]
10851 "TARGET_HTM && operands != NULL"
10852 "tabort\t%Y0"
10853 [(set_attr "op_type" "S")])
10854
10855 ; Transaction extract nesting depth
10856
10857 (define_insn "etnd"
10858 [(set (match_operand:SI 0 "register_operand" "=d")
10859 (unspec_volatile:SI [(const_int 0)] UNSPECV_ETND))]
10860 "TARGET_HTM"
10861 "etnd\t%0"
10862 [(set_attr "op_type" "RRE")])
10863
10864 ; Non-transactional store
10865
10866 (define_insn "ntstg"
10867 [(set (match_operand:DI 0 "memory_operand" "=RT")
10868 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "d")]
10869 UNSPECV_NTSTG))]
10870 "TARGET_HTM"
10871 "ntstg\t%1,%0"
10872 [(set_attr "op_type" "RXY")])
10873
10874 ; Transaction perform processor assist
10875
10876 (define_expand "tx_assist"
10877 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")
10878 (reg:SI GPR0_REGNUM)
10879 (const_int 1)]
10880 UNSPECV_PPA)]
10881 "TARGET_HTM"
10882 "")
10883
10884 (define_insn "*ppa"
10885 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")
10886 (match_operand:SI 1 "register_operand" "d")
10887 (match_operand 2 "const_int_operand" "I")]
10888 UNSPECV_PPA)]
10889 "TARGET_HTM && INTVAL (operands[2]) < 16"
10890 "ppa\t%0,%1,%2"
10891 [(set_attr "op_type" "RRF")])
10892
10893
10894 ; Set and get floating point control register
10895
10896 (define_insn "sfpc"
10897 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")]
10898 UNSPECV_SFPC)]
10899 "TARGET_HARD_FLOAT"
10900 "sfpc\t%0")
10901
10902 (define_insn "efpc"
10903 [(set (match_operand:SI 0 "register_operand" "=d")
10904 (unspec_volatile:SI [(const_int 0)] UNSPECV_EFPC))]
10905 "TARGET_HARD_FLOAT"
10906 "efpc\t%0")
10907
10908
10909 ; Load count to block boundary
10910
10911 (define_insn "lcbb"
10912 [(set (match_operand:SI 0 "register_operand" "=d")
10913 (unspec:SI [(match_operand:SI 1 "address_operand" "ZQZR")
10914 (match_operand:SI 2 "immediate_operand" "C")] UNSPEC_LCBB))
10915 (clobber (reg:CC CC_REGNUM))]
10916 "TARGET_Z13"
10917 "lcbb\t%0,%1,%b2"
10918 [(set_attr "op_type" "VRX")])
10919
10920 ; Handle -fsplit-stack.
10921
10922 (define_expand "split_stack_prologue"
10923 [(const_int 0)]
10924 ""
10925 {
10926 s390_expand_split_stack_prologue ();
10927 DONE;
10928 })
10929
10930 ;; If there are operand 0 bytes available on the stack, jump to
10931 ;; operand 1.
10932
10933 (define_expand "split_stack_space_check"
10934 [(set (pc) (if_then_else
10935 (ltu (minus (reg 15)
10936 (match_operand 0 "register_operand"))
10937 (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
10938 (label_ref (match_operand 1))
10939 (pc)))]
10940 ""
10941 {
10942 /* Offset from thread pointer to __private_ss. */
10943 int psso = TARGET_64BIT ? 0x38 : 0x20;
10944 rtx tp = s390_get_thread_pointer ();
10945 rtx guard = gen_rtx_MEM (Pmode, plus_constant (Pmode, tp, psso));
10946 rtx reg = gen_reg_rtx (Pmode);
10947 rtx cc;
10948 if (TARGET_64BIT)
10949 emit_insn (gen_subdi3 (reg, stack_pointer_rtx, operands[0]));
10950 else
10951 emit_insn (gen_subsi3 (reg, stack_pointer_rtx, operands[0]));
10952 cc = s390_emit_compare (GT, reg, guard);
10953 s390_emit_jump (operands[1], cc);
10954
10955 DONE;
10956 })
10957
10958 ;; __morestack parameter block for split stack prologue. Parameters are:
10959 ;; parameter block label, label to be called by __morestack, frame size,
10960 ;; stack parameter size.
10961
10962 (define_insn "split_stack_data"
10963 [(unspec_volatile [(match_operand 0 "" "X")
10964 (match_operand 1 "" "X")
10965 (match_operand 2 "const_int_operand" "X")
10966 (match_operand 3 "const_int_operand" "X")]
10967 UNSPECV_SPLIT_STACK_DATA)]
10968 "TARGET_CPU_ZARCH"
10969 {
10970 switch_to_section (targetm.asm_out.function_rodata_section
10971 (current_function_decl));
10972
10973 if (TARGET_64BIT)
10974 output_asm_insn (".align\t8", operands);
10975 else
10976 output_asm_insn (".align\t4", operands);
10977 (*targetm.asm_out.internal_label) (asm_out_file, "L",
10978 CODE_LABEL_NUMBER (operands[0]));
10979 if (TARGET_64BIT)
10980 {
10981 output_asm_insn (".quad\t%2", operands);
10982 output_asm_insn (".quad\t%3", operands);
10983 output_asm_insn (".quad\t%1-%0", operands);
10984 }
10985 else
10986 {
10987 output_asm_insn (".long\t%2", operands);
10988 output_asm_insn (".long\t%3", operands);
10989 output_asm_insn (".long\t%1-%0", operands);
10990 }
10991
10992 switch_to_section (current_function_section ());
10993 return "";
10994 }
10995 [(set_attr "length" "0")])
10996
10997
10998 ;; A jg with minimal fuss for use in split stack prologue.
10999
11000 (define_expand "split_stack_call"
11001 [(match_operand 0 "bras_sym_operand" "X")
11002 (match_operand 1 "" "")]
11003 "TARGET_CPU_ZARCH"
11004 {
11005 if (TARGET_64BIT)
11006 emit_jump_insn (gen_split_stack_call_di (operands[0], operands[1]));
11007 else
11008 emit_jump_insn (gen_split_stack_call_si (operands[0], operands[1]));
11009 DONE;
11010 })
11011
11012 (define_insn "split_stack_call_<mode>"
11013 [(set (pc) (label_ref (match_operand 1 "" "")))
11014 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11015 (reg:P 1)]
11016 UNSPECV_SPLIT_STACK_CALL))]
11017 "TARGET_CPU_ZARCH"
11018 "jg\t%0"
11019 [(set_attr "op_type" "RIL")
11020 (set_attr "type" "branch")])
11021
11022 ;; Also a conditional one.
11023
11024 (define_expand "split_stack_cond_call"
11025 [(match_operand 0 "bras_sym_operand" "X")
11026 (match_operand 1 "" "")
11027 (match_operand 2 "" "")]
11028 "TARGET_CPU_ZARCH"
11029 {
11030 if (TARGET_64BIT)
11031 emit_jump_insn (gen_split_stack_cond_call_di (operands[0], operands[1], operands[2]));
11032 else
11033 emit_jump_insn (gen_split_stack_cond_call_si (operands[0], operands[1], operands[2]));
11034 DONE;
11035 })
11036
11037 (define_insn "split_stack_cond_call_<mode>"
11038 [(set (pc)
11039 (if_then_else
11040 (match_operand 1 "" "")
11041 (label_ref (match_operand 2 "" ""))
11042 (pc)))
11043 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11044 (reg:P 1)]
11045 UNSPECV_SPLIT_STACK_CALL))]
11046 "TARGET_CPU_ZARCH"
11047 "jg%C1\t%0"
11048 [(set_attr "op_type" "RIL")
11049 (set_attr "type" "branch")])