S/390 zvector builtin support.
[gcc.git] / gcc / config / s390 / s390.md
1 ;;- Machine description for GNU compiler -- S/390 / zSeries version.
2 ;; Copyright (C) 1999-2015 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 ; GOT/PLT and lt-relative accesses
74 UNSPEC_LTREL_OFFSET
75 UNSPEC_LTREL_BASE
76 UNSPEC_POOL_OFFSET
77 UNSPEC_GOTENT
78 UNSPEC_GOT
79 UNSPEC_GOTOFF
80 UNSPEC_PLT
81 UNSPEC_PLTOFF
82
83 ; Literal pool
84 UNSPEC_RELOAD_BASE
85 UNSPEC_MAIN_BASE
86 UNSPEC_LTREF
87 UNSPEC_INSN
88 UNSPEC_EXECUTE
89
90 ; Atomic Support
91 UNSPEC_MB
92 UNSPEC_MOVA
93
94 ; TLS relocation specifiers
95 UNSPEC_TLSGD
96 UNSPEC_TLSLDM
97 UNSPEC_NTPOFF
98 UNSPEC_DTPOFF
99 UNSPEC_GOTNTPOFF
100 UNSPEC_INDNTPOFF
101
102 ; TLS support
103 UNSPEC_TLSLDM_NTPOFF
104 UNSPEC_TLS_LOAD
105
106 ; String Functions
107 UNSPEC_SRST
108 UNSPEC_MVST
109
110 ; Stack Smashing Protector
111 UNSPEC_SP_SET
112 UNSPEC_SP_TEST
113
114 ; Test Data Class (TDC)
115 UNSPEC_TDC_INSN
116
117 ; Population Count
118 UNSPEC_POPCNT
119 UNSPEC_COPYSIGN
120
121 ; Load FP Integer
122 UNSPEC_FPINT_FLOOR
123 UNSPEC_FPINT_BTRUNC
124 UNSPEC_FPINT_ROUND
125 UNSPEC_FPINT_CEIL
126 UNSPEC_FPINT_NEARBYINT
127 UNSPEC_FPINT_RINT
128
129 UNSPEC_LCBB
130
131 ; Vector
132 UNSPEC_VEC_SMULT_HI
133 UNSPEC_VEC_UMULT_HI
134 UNSPEC_VEC_SMULT_LO
135 UNSPEC_VEC_SMULT_EVEN
136 UNSPEC_VEC_UMULT_EVEN
137 UNSPEC_VEC_SMULT_ODD
138 UNSPEC_VEC_UMULT_ODD
139
140 UNSPEC_VEC_VMAL
141 UNSPEC_VEC_VMAH
142 UNSPEC_VEC_VMALH
143 UNSPEC_VEC_VMAE
144 UNSPEC_VEC_VMALE
145 UNSPEC_VEC_VMAO
146 UNSPEC_VEC_VMALO
147
148 UNSPEC_VEC_GATHER
149 UNSPEC_VEC_EXTRACT
150 UNSPEC_VEC_INSERT_AND_ZERO
151 UNSPEC_VEC_LOAD_BNDRY
152 UNSPEC_VEC_LOAD_LEN
153 UNSPEC_VEC_MERGEH
154 UNSPEC_VEC_MERGEL
155 UNSPEC_VEC_PACK
156 UNSPEC_VEC_PACK_SATURATE
157 UNSPEC_VEC_PACK_SATURATE_CC
158 UNSPEC_VEC_PACK_SATURATE_GENCC
159 UNSPEC_VEC_PACK_UNSIGNED_SATURATE
160 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC
161 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC
162 UNSPEC_VEC_PERM
163 UNSPEC_VEC_PERMI
164 UNSPEC_VEC_EXTEND
165 UNSPEC_VEC_STORE_LEN
166 UNSPEC_VEC_UNPACKH
167 UNSPEC_VEC_UNPACKH_L
168 UNSPEC_VEC_UNPACKL
169 UNSPEC_VEC_UNPACKL_L
170 UNSPEC_VEC_ADDC
171 UNSPEC_VEC_ADDC_U128
172 UNSPEC_VEC_ADDE_U128
173 UNSPEC_VEC_ADDEC_U128
174 UNSPEC_VEC_AVG
175 UNSPEC_VEC_AVGU
176 UNSPEC_VEC_CHECKSUM
177 UNSPEC_VEC_GFMSUM
178 UNSPEC_VEC_GFMSUM_128
179 UNSPEC_VEC_GFMSUM_ACCUM
180 UNSPEC_VEC_GFMSUM_ACCUM_128
181 UNSPEC_VEC_SET
182
183 UNSPEC_VEC_VSUMG
184 UNSPEC_VEC_VSUMQ
185 UNSPEC_VEC_VSUM
186 UNSPEC_VEC_RL_MASK
187 UNSPEC_VEC_SLL
188 UNSPEC_VEC_SLB
189 UNSPEC_VEC_SLDB
190 UNSPEC_VEC_SRAL
191 UNSPEC_VEC_SRAB
192 UNSPEC_VEC_SRL
193 UNSPEC_VEC_SRLB
194
195 UNSPEC_VEC_SUB_U128
196 UNSPEC_VEC_SUBC
197 UNSPEC_VEC_SUBC_U128
198 UNSPEC_VEC_SUBE_U128
199 UNSPEC_VEC_SUBEC_U128
200
201 UNSPEC_VEC_TEST_MASK
202
203 UNSPEC_VEC_VFAE
204 UNSPEC_VEC_VFAECC
205
206 UNSPEC_VEC_VFEE
207 UNSPEC_VEC_VFEECC
208 UNSPEC_VEC_VFENE
209 UNSPEC_VEC_VFENECC
210
211 UNSPEC_VEC_VISTR
212 UNSPEC_VEC_VISTRCC
213
214 UNSPEC_VEC_VSTRC
215 UNSPEC_VEC_VSTRCCC
216
217 UNSPEC_VEC_VCDGB
218 UNSPEC_VEC_VCDLGB
219
220 UNSPEC_VEC_VCGDB
221 UNSPEC_VEC_VCLGDB
222
223 UNSPEC_VEC_VFIDB
224
225 UNSPEC_VEC_VLDEB
226 UNSPEC_VEC_VLEDB
227
228 UNSPEC_VEC_VFTCIDB
229 UNSPEC_VEC_VFTCIDBCC
230 ])
231
232 ;;
233 ;; UNSPEC_VOLATILE usage
234 ;;
235
236 (define_c_enum "unspecv" [
237 ; Blockage
238 UNSPECV_BLOCKAGE
239
240 ; TPF Support
241 UNSPECV_TPF_PROLOGUE
242 UNSPECV_TPF_EPILOGUE
243
244 ; Literal pool
245 UNSPECV_POOL
246 UNSPECV_POOL_SECTION
247 UNSPECV_POOL_ALIGN
248 UNSPECV_POOL_ENTRY
249 UNSPECV_MAIN_POOL
250
251 ; TLS support
252 UNSPECV_SET_TP
253
254 ; Atomic Support
255 UNSPECV_CAS
256 UNSPECV_ATOMIC_OP
257
258 ; Hotpatching (unremovable NOPs)
259 UNSPECV_NOP_2_BYTE
260 UNSPECV_NOP_4_BYTE
261 UNSPECV_NOP_6_BYTE
262
263 ; Transactional Execution support
264 UNSPECV_TBEGIN
265 UNSPECV_TBEGIN_TDB
266 UNSPECV_TBEGINC
267 UNSPECV_TEND
268 UNSPECV_TABORT
269 UNSPECV_ETND
270 UNSPECV_NTSTG
271 UNSPECV_PPA
272
273 ; Set and get floating point control register
274 UNSPECV_SFPC
275 UNSPECV_EFPC
276 ])
277
278 ;;
279 ;; Registers
280 ;;
281
282 ; Registers with special meaning
283
284 (define_constants
285 [
286 ; Sibling call register.
287 (SIBCALL_REGNUM 1)
288 ; Literal pool base register.
289 (BASE_REGNUM 13)
290 ; Return address register.
291 (RETURN_REGNUM 14)
292 ; Condition code register.
293 (CC_REGNUM 33)
294 ; Thread local storage pointer register.
295 (TP_REGNUM 36)
296 ])
297
298 ; Hardware register names
299
300 (define_constants
301 [
302 ; General purpose registers
303 (GPR0_REGNUM 0)
304 ; Floating point registers.
305 (FPR0_REGNUM 16)
306 (FPR1_REGNUM 20)
307 (FPR2_REGNUM 17)
308 (FPR3_REGNUM 21)
309 (FPR4_REGNUM 18)
310 (FPR5_REGNUM 22)
311 (FPR6_REGNUM 19)
312 (FPR7_REGNUM 23)
313 (FPR8_REGNUM 24)
314 (FPR9_REGNUM 28)
315 (FPR10_REGNUM 25)
316 (FPR11_REGNUM 29)
317 (FPR12_REGNUM 26)
318 (FPR13_REGNUM 30)
319 (FPR14_REGNUM 27)
320 (FPR15_REGNUM 31)
321 (VR0_REGNUM 16)
322 (VR16_REGNUM 38)
323 (VR23_REGNUM 45)
324 (VR24_REGNUM 46)
325 (VR31_REGNUM 53)
326 ])
327
328 ;;
329 ;; PFPO GPR0 argument format
330 ;;
331
332 (define_constants
333 [
334 ; PFPO operation type
335 (PFPO_CONVERT 0x1000000)
336 ; PFPO operand types
337 (PFPO_OP_TYPE_SF 0x5)
338 (PFPO_OP_TYPE_DF 0x6)
339 (PFPO_OP_TYPE_TF 0x7)
340 (PFPO_OP_TYPE_SD 0x8)
341 (PFPO_OP_TYPE_DD 0x9)
342 (PFPO_OP_TYPE_TD 0xa)
343 ; Bitposition of operand types
344 (PFPO_OP0_TYPE_SHIFT 16)
345 (PFPO_OP1_TYPE_SHIFT 8)
346 ])
347
348 ; Immediate operands for tbegin and tbeginc
349 (define_constants [(TBEGIN_MASK 65292)]) ; 0xff0c
350 (define_constants [(TBEGINC_MASK 65288)]) ; 0xff08
351
352 ;; Instruction operand type as used in the Principles of Operation.
353 ;; Used to determine defaults for length and other attribute values.
354
355 (define_attr "op_type"
356 "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"
357 (const_string "NN"))
358
359 ;; Instruction type attribute used for scheduling.
360
361 (define_attr "type" "none,integer,load,lr,la,larl,lm,stm,
362 cs,vs,store,sem,idiv,
363 imulhi,imulsi,imuldi,
364 branch,jsr,fsimptf,fsimpdf,fsimpsf,fhex,
365 floadtf,floaddf,floadsf,fstoredf,fstoresf,
366 fmultf,fmuldf,fmulsf,fdivtf,fdivdf,fdivsf,
367 ftoi,fsqrttf,fsqrtdf,fsqrtsf,
368 fmadddf,fmaddsf,
369 ftrunctf,ftruncdf, ftruncsd, ftruncdd,
370 itoftf, itofdf, itofsf, itofdd, itoftd,
371 fdivdd, fdivtd, floaddd, floadsd, fmuldd, fmultd,
372 fsimpdd, fsimpsd, fsimptd, fstoredd, fstoresd,
373 ftoidfp, other"
374 (cond [(eq_attr "op_type" "NN") (const_string "other")
375 (eq_attr "op_type" "SS") (const_string "cs")]
376 (const_string "integer")))
377
378 ;; Another attribute used for scheduling purposes:
379 ;; agen: Instruction uses the address generation unit
380 ;; reg: Instruction does not use the agen unit
381
382 (define_attr "atype" "agen,reg"
383 (if_then_else (eq_attr "op_type" "E,RR,RI,RRE,RSI,RIL,RIE,RRF,RRR")
384 (const_string "reg")
385 (const_string "agen")))
386
387 ;; Properties concerning Z10 execution grouping and value forwarding.
388 ;; z10_super: instruction is superscalar.
389 ;; z10_super_c: instruction is superscalar and meets the condition of z10_c.
390 ;; z10_fwd: The instruction reads the value of an operand and stores it into a
391 ;; target register. It can forward this value to a second instruction that reads
392 ;; the same register if that second instruction is issued in the same group.
393 ;; z10_rec: The instruction is in the T pipeline and reads a register. If the
394 ;; instruction in the S pipe writes to the register, then the T instruction
395 ;; can immediately read the new value.
396 ;; z10_fr: union of Z10_fwd and z10_rec.
397 ;; z10_c: second operand of instruction is a register and read with complemented bits.
398 ;;
399 ;; An additional suffix A1, A3, or E1 indicates the respective AGI bypass.
400
401
402 (define_attr "z10prop" "none,
403 z10_super, z10_super_E1, z10_super_A1, z10_super_c, z10_super_c_E1,
404 z10_fwd, z10_fwd_A1, z10_fwd_A3, z10_fwd_E1,
405 z10_rec,
406 z10_fr, z10_fr_A3, z10_fr_E1,
407 z10_c"
408 (const_string "none"))
409
410 ;; Properties concerning Z196 decoding
411 ;; z196_alone: must group alone
412 ;; z196_end: ends a group
413 ;; z196_cracked: instruction is cracked or expanded
414 (define_attr "z196prop" "none,
415 z196_alone, z196_ends,
416 z196_cracked"
417 (const_string "none"))
418
419 (define_attr "mnemonic" "bcr_flush,unknown" (const_string "unknown"))
420
421 ;; Length in bytes.
422
423 (define_attr "length" ""
424 (cond [(eq_attr "op_type" "E,RR") (const_int 2)
425 (eq_attr "op_type" "RX,RI,RRE,RS,RSI,S,SI,RRF,RRR") (const_int 4)]
426 (const_int 6)))
427
428
429 ;; Processor type. This attribute must exactly match the processor_type
430 ;; enumeration in s390.h. The current machine description does not
431 ;; distinguish between g5 and g6, but there are differences between the two
432 ;; CPUs could in theory be modeled.
433
434 (define_attr "cpu" "g5,g6,z900,z990,z9_109,z9_ec,z10,z196,zEC12,z13"
435 (const (symbol_ref "s390_tune_attr")))
436
437 (define_attr "cpu_facility"
438 "standard,ieee,zarch,cpu_zarch,longdisp,extimm,dfp,z10,z196,zEC12,vec"
439 (const_string "standard"))
440
441 (define_attr "enabled" ""
442 (cond [(eq_attr "cpu_facility" "standard")
443 (const_int 1)
444
445 (and (eq_attr "cpu_facility" "ieee")
446 (match_test "TARGET_CPU_IEEE_FLOAT"))
447 (const_int 1)
448
449 (and (eq_attr "cpu_facility" "zarch")
450 (match_test "TARGET_ZARCH"))
451 (const_int 1)
452
453 (and (eq_attr "cpu_facility" "longdisp")
454 (match_test "TARGET_LONG_DISPLACEMENT"))
455 (const_int 1)
456
457 (and (eq_attr "cpu_facility" "extimm")
458 (match_test "TARGET_EXTIMM"))
459 (const_int 1)
460
461 (and (eq_attr "cpu_facility" "dfp")
462 (match_test "TARGET_DFP"))
463 (const_int 1)
464
465 (and (eq_attr "cpu_facility" "cpu_zarch")
466 (match_test "TARGET_CPU_ZARCH"))
467 (const_int 1)
468
469 (and (eq_attr "cpu_facility" "z10")
470 (match_test "TARGET_Z10"))
471 (const_int 1)
472
473 (and (eq_attr "cpu_facility" "z196")
474 (match_test "TARGET_Z196"))
475 (const_int 1)
476
477 (and (eq_attr "cpu_facility" "zEC12")
478 (match_test "TARGET_ZEC12"))
479 (const_int 1)
480
481 (and (eq_attr "cpu_facility" "vec")
482 (match_test "TARGET_VX"))
483 (const_int 1)]
484 (const_int 0)))
485
486 ;; Pipeline description for z900. For lack of anything better,
487 ;; this description is also used for the g5 and g6.
488 (include "2064.md")
489
490 ;; Pipeline description for z990, z9-109 and z9-ec.
491 (include "2084.md")
492
493 ;; Pipeline description for z10
494 (include "2097.md")
495
496 ;; Pipeline description for z196
497 (include "2817.md")
498
499 ;; Pipeline description for zEC12
500 (include "2827.md")
501
502 ;; Predicates
503 (include "predicates.md")
504
505 ;; Constraint definitions
506 (include "constraints.md")
507
508 ;; Other includes
509 (include "tpf.md")
510
511 ;; Iterators
512
513 (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])
514
515 ;; These mode iterators allow floating point patterns to be generated from the
516 ;; same template.
517 (define_mode_iterator FP_ALL [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")
518 (SD "TARGET_HARD_DFP")])
519 (define_mode_iterator FP [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")])
520 (define_mode_iterator BFP [TF DF SF])
521 (define_mode_iterator DFP [TD DD])
522 (define_mode_iterator DFP_ALL [TD DD SD])
523 (define_mode_iterator DSF [DF SF])
524 (define_mode_iterator SD_SF [SF SD])
525 (define_mode_iterator DD_DF [DF DD])
526 (define_mode_iterator TD_TF [TF TD])
527
528 ;; These mode iterators allow 31-bit and 64-bit GPR patterns to be generated
529 ;; from the same template.
530 (define_mode_iterator GPR [(DI "TARGET_ZARCH") SI])
531 (define_mode_iterator DGPR [(TI "TARGET_ZARCH") DI SI])
532 (define_mode_iterator DSI [DI SI])
533 (define_mode_iterator TDI [TI DI])
534
535 ;; These mode iterators allow :P to be used for patterns that operate on
536 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
537 (define_mode_iterator P [(DI "TARGET_64BIT") (SI "!TARGET_64BIT")])
538
539 ;; These macros refer to the actual word_mode of the configuration.
540 ;; This is equal to Pmode except on 31-bit machines in zarch mode.
541 (define_mode_iterator DW [(TI "TARGET_ZARCH") (DI "!TARGET_ZARCH")])
542 (define_mode_iterator W [(DI "TARGET_ZARCH") (SI "!TARGET_ZARCH")])
543
544 ;; Used by the umul pattern to express modes having half the size.
545 (define_mode_attr DWH [(TI "DI") (DI "SI")])
546 (define_mode_attr dwh [(TI "di") (DI "si")])
547
548 ;; This mode iterator allows the QI and HI patterns to be defined from
549 ;; the same template.
550 (define_mode_iterator HQI [HI QI])
551
552 ;; This mode iterator allows the integer patterns to be defined from the
553 ;; same template.
554 (define_mode_iterator INT [(DI "TARGET_ZARCH") SI HI QI])
555 (define_mode_iterator DINT [(TI "TARGET_ZARCH") DI SI HI QI])
556
557 ;; This iterator allows some 'ashift' and 'lshiftrt' pattern to be defined from
558 ;; the same template.
559 (define_code_iterator SHIFT [ashift lshiftrt])
560
561 ;; This iterator allows r[ox]sbg to be defined with the same template
562 (define_code_iterator IXOR [ior xor])
563
564 ;; This iterator is used to expand the patterns for the nearest
565 ;; integer functions.
566 (define_int_iterator FPINT [UNSPEC_FPINT_FLOOR UNSPEC_FPINT_BTRUNC
567 UNSPEC_FPINT_ROUND UNSPEC_FPINT_CEIL
568 UNSPEC_FPINT_NEARBYINT])
569 (define_int_attr fpint_name [(UNSPEC_FPINT_FLOOR "floor")
570 (UNSPEC_FPINT_BTRUNC "btrunc")
571 (UNSPEC_FPINT_ROUND "round")
572 (UNSPEC_FPINT_CEIL "ceil")
573 (UNSPEC_FPINT_NEARBYINT "nearbyint")])
574 (define_int_attr fpint_roundingmode [(UNSPEC_FPINT_FLOOR "7")
575 (UNSPEC_FPINT_BTRUNC "5")
576 (UNSPEC_FPINT_ROUND "1")
577 (UNSPEC_FPINT_CEIL "6")
578 (UNSPEC_FPINT_NEARBYINT "0")])
579
580 ;; This iterator and attribute allow to combine most atomic operations.
581 (define_code_iterator ATOMIC [and ior xor plus minus mult])
582 (define_code_iterator ATOMIC_Z196 [and ior xor plus])
583 (define_code_attr atomic [(and "and") (ior "or") (xor "xor")
584 (plus "add") (minus "sub") (mult "nand")])
585 (define_code_attr noxa [(and "n") (ior "o") (xor "x") (plus "a")])
586
587 ;; In FP templates, a string like "lt<de>br" will expand to "ltxbr" in
588 ;; TF/TDmode, "ltdbr" in DF/DDmode, and "ltebr" in SF/SDmode.
589 (define_mode_attr xde [(TF "x") (DF "d") (SF "e") (TD "x") (DD "d") (SD "e")])
590
591 ;; In FP templates, a <dee> in "m<dee><bt>r" will expand to "mx<bt>r" in
592 ;; TF/TDmode, "md<bt>r" in DF/DDmode, "mee<bt>r" in SFmode and "me<bt>r in
593 ;; SDmode.
594 (define_mode_attr xdee [(TF "x") (DF "d") (SF "ee") (TD "x") (DD "d") (SD "e")])
595
596 ;; In FP templates, "<RRe>" will expand to "RRE" in TFmode and "RR" otherwise.
597 ;; Likewise for "<RXe>".
598 (define_mode_attr RRe [(TF "RRE") (DF "RR") (SF "RR")])
599 (define_mode_attr RXe [(TF "RXE") (DF "RX") (SF "RX")])
600
601 ;; The decimal floating point variants of add, sub, div and mul support 3
602 ;; fp register operands. The following attributes allow to merge the bfp and
603 ;; dfp variants in a single insn definition.
604
605 ;; This attribute is used to set op_type accordingly.
606 (define_mode_attr RRer [(TF "RRE") (DF "RRE") (SF "RRE") (TD "RRR")
607 (DD "RRR") (SD "RRR")])
608
609 ;; This attribute is used in the operand constraint list in order to have the
610 ;; first and the second operand match for bfp modes.
611 (define_mode_attr f0 [(TF "0") (DF "0") (SF "0") (TD "f") (DD "f") (DD "f")])
612
613 ;; This attribute is used to merge the scalar vector instructions into
614 ;; the FP patterns. For non-supported modes (all but DF) it expands
615 ;; to constraints which are supposed to be matched by an earlier
616 ;; variant.
617 (define_mode_attr v0 [(TF "0") (DF "v") (SF "0") (TD "0") (DD "0") (DD "0") (TI "0") (DI "v") (SI "0")])
618 (define_mode_attr vf [(TF "f") (DF "v") (SF "f") (TD "f") (DD "f") (DD "f") (TI "f") (DI "v") (SI "f")])
619 (define_mode_attr vd [(TF "d") (DF "v") (SF "d") (TD "d") (DD "d") (DD "d") (TI "d") (DI "v") (SI "d")])
620
621 ;; This attribute is used in the operand list of the instruction to have an
622 ;; additional operand for the dfp instructions.
623 (define_mode_attr op1 [(TF "") (DF "") (SF "")
624 (TD "%1,") (DD "%1,") (SD "%1,")])
625
626
627 ;; This attribute is used in the operand constraint list
628 ;; for instructions dealing with the sign bit of 32 or 64bit fp values.
629 ;; TFmode values are represented by a fp register pair. Since the
630 ;; sign bit instructions only handle single source and target fp registers
631 ;; these instructions can only be used for TFmode values if the source and
632 ;; target operand uses the same fp register.
633 (define_mode_attr fT0 [(TF "0") (DF "f") (SF "f")])
634
635 ;; In FP templates, "<Rf>" will expand to "f" in TFmode and "R" otherwise.
636 ;; This is used to disable the memory alternative in TFmode patterns.
637 (define_mode_attr Rf [(TF "f") (DF "R") (SF "R") (TD "f") (DD "f") (SD "f")])
638
639 ;; This attribute adds b for bfp instructions and t for dfp instructions and is used
640 ;; within instruction mnemonics.
641 (define_mode_attr bt [(TF "b") (DF "b") (SF "b") (TD "t") (DD "t") (SD "t")])
642
643 ;; This attribute is used within instruction mnemonics. It evaluates to d for dfp
644 ;; modes and to an empty string for bfp modes.
645 (define_mode_attr _d [(TF "") (DF "") (SF "") (TD "d") (DD "d") (SD "d")])
646
647 ;; In GPR and P templates, a constraint like "<d0>" will expand to "d" in DImode
648 ;; and "0" in SImode. This allows to combine instructions of which the 31bit
649 ;; version only operates on one register.
650 (define_mode_attr d0 [(DI "d") (SI "0")])
651
652 ;; In combination with d0 this allows to combine instructions of which the 31bit
653 ;; version only operates on one register. The DImode version needs an additional
654 ;; register for the assembler output.
655 (define_mode_attr 1 [(DI "%1,") (SI "")])
656
657 ;; In SHIFT templates, a string like "s<lr>dl" will expand to "sldl" in
658 ;; 'ashift' and "srdl" in 'lshiftrt'.
659 (define_code_attr lr [(ashift "l") (lshiftrt "r")])
660
661 ;; In SHIFT templates, this attribute holds the correct standard name for the
662 ;; pattern itself and the corresponding function calls.
663 (define_code_attr shift [(ashift "ashl") (lshiftrt "lshr")])
664
665 ;; This attribute handles differences in the instruction 'type' and will result
666 ;; in "RRE" for DImode and "RR" for SImode.
667 (define_mode_attr E [(DI "E") (SI "")])
668
669 ;; This attribute handles differences in the instruction 'type' and makes RX<Y>
670 ;; to result in "RXY" for DImode and "RX" for SImode.
671 (define_mode_attr Y [(DI "Y") (SI "")])
672
673 ;; This attribute handles differences in the instruction 'type' and will result
674 ;; in "RSE" for TImode and "RS" for DImode.
675 (define_mode_attr TE [(TI "E") (DI "")])
676
677 ;; In GPR templates, a string like "lc<g>r" will expand to "lcgr" in DImode
678 ;; and "lcr" in SImode.
679 (define_mode_attr g [(DI "g") (SI "")])
680
681 ;; In GPR templates, a string like "sl<y>" will expand to "slg" in DImode
682 ;; and "sly" in SImode. This is useful because on 64bit the ..g instructions
683 ;; were enhanced with long displacements whereas 31bit instructions got a ..y
684 ;; variant for long displacements.
685 (define_mode_attr y [(DI "g") (SI "y")])
686
687 ;; In DW templates, a string like "cds<g>" will expand to "cdsg" in TImode
688 ;; and "cds" in DImode.
689 (define_mode_attr tg [(TI "g") (DI "")])
690
691 ;; In TDI templates, a string like "c<d>sg".
692 (define_mode_attr td [(TI "d") (DI "")])
693
694 ;; In GPR templates, a string like "c<gf>dbr" will expand to "cgdbr" in DImode
695 ;; and "cfdbr" in SImode.
696 (define_mode_attr gf [(DI "g") (SI "f")])
697
698 ;; In GPR templates, a string like sll<gk> will expand to sllg for DI
699 ;; and sllk for SI. This way it is possible to merge the new z196 SI
700 ;; 3 operands shift instructions into the existing patterns.
701 (define_mode_attr gk [(DI "g") (SI "k")])
702
703 ;; ICM mask required to load MODE value into the lowest subreg
704 ;; of a SImode register.
705 (define_mode_attr icm_lo [(HI "3") (QI "1")])
706
707 ;; In HQI templates, a string like "llg<hc>" will expand to "llgh" in
708 ;; HImode and "llgc" in QImode.
709 (define_mode_attr hc [(HI "h") (QI "c")])
710
711 ;; In P templates, the mode <DBL> will expand to "TI" in DImode and "DI"
712 ;; in SImode.
713 (define_mode_attr DBL [(DI "TI") (SI "DI")])
714
715 ;; This attribute expands to DF for TFmode and to DD for TDmode . It is
716 ;; used for Txmode splitters splitting a Txmode copy into 2 Dxmode copies.
717 (define_mode_attr HALF_TMODE [(TF "DF") (TD "DD")])
718
719 ;; Maximum unsigned integer that fits in MODE.
720 (define_mode_attr max_uint [(HI "65535") (QI "255")])
721
722 ;; Start and end field computations for RISBG et al.
723 (define_mode_attr bfstart [(DI "s") (SI "t")])
724 (define_mode_attr bfend [(DI "e") (SI "f")])
725
726 ;; In place of GET_MODE_BITSIZE (<MODE>mode)
727 (define_mode_attr bitsize [(DI "64") (SI "32") (HI "16") (QI "8")])
728
729 ;; Allow return and simple_return to be defined from a single template.
730 (define_code_iterator ANY_RETURN [return simple_return])
731
732
733
734 ; Condition code modes generated by vector fp comparisons. These will
735 ; be used also in single element mode.
736 (define_mode_iterator VFCMP [CCVEQ CCVFH CCVFHE])
737 ; Used with VFCMP to expand part of the mnemonic
738 ; For fp we have a mismatch: eq in the insn name - e in asm
739 (define_mode_attr asm_fcmp [(CCVEQ "e") (CCVFH "h") (CCVFHE "he")])
740 (define_mode_attr insn_cmp [(CCVEQ "eq") (CCVH "h") (CCVHU "hl") (CCVFH "h") (CCVFHE "he")])
741
742
743 (include "vector.md")
744
745 ;;
746 ;;- Compare instructions.
747 ;;
748
749 ; Test-under-Mask instructions
750
751 (define_insn "*tmqi_mem"
752 [(set (reg CC_REGNUM)
753 (compare (and:QI (match_operand:QI 0 "memory_operand" "Q,S")
754 (match_operand:QI 1 "immediate_operand" "n,n"))
755 (match_operand:QI 2 "immediate_operand" "n,n")))]
756 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], false))"
757 "@
758 tm\t%S0,%b1
759 tmy\t%S0,%b1"
760 [(set_attr "op_type" "SI,SIY")
761 (set_attr "z10prop" "z10_super,z10_super")])
762
763 (define_insn "*tmdi_reg"
764 [(set (reg CC_REGNUM)
765 (compare (and:DI (match_operand:DI 0 "nonimmediate_operand" "d,d,d,d")
766 (match_operand:DI 1 "immediate_operand"
767 "N0HD0,N1HD0,N2HD0,N3HD0"))
768 (match_operand:DI 2 "immediate_operand" "n,n,n,n")))]
769 "TARGET_ZARCH
770 && s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
771 && s390_single_part (operands[1], DImode, HImode, 0) >= 0"
772 "@
773 tmhh\t%0,%i1
774 tmhl\t%0,%i1
775 tmlh\t%0,%i1
776 tmll\t%0,%i1"
777 [(set_attr "op_type" "RI")
778 (set_attr "z10prop" "z10_super,z10_super,z10_super,z10_super")])
779
780 (define_insn "*tmsi_reg"
781 [(set (reg CC_REGNUM)
782 (compare (and:SI (match_operand:SI 0 "nonimmediate_operand" "d,d")
783 (match_operand:SI 1 "immediate_operand" "N0HS0,N1HS0"))
784 (match_operand:SI 2 "immediate_operand" "n,n")))]
785 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
786 && s390_single_part (operands[1], SImode, HImode, 0) >= 0"
787 "@
788 tmh\t%0,%i1
789 tml\t%0,%i1"
790 [(set_attr "op_type" "RI")
791 (set_attr "z10prop" "z10_super,z10_super")])
792
793 (define_insn "*tm<mode>_full"
794 [(set (reg CC_REGNUM)
795 (compare (match_operand:HQI 0 "register_operand" "d")
796 (match_operand:HQI 1 "immediate_operand" "n")))]
797 "s390_match_ccmode (insn, s390_tm_ccmode (constm1_rtx, operands[1], true))"
798 "tml\t%0,<max_uint>"
799 [(set_attr "op_type" "RI")
800 (set_attr "z10prop" "z10_super")])
801
802
803 ;
804 ; Load-and-Test instructions
805 ;
806
807 ; tst(di|si) instruction pattern(s).
808
809 (define_insn "*tstdi_sign"
810 [(set (reg CC_REGNUM)
811 (compare
812 (ashiftrt:DI
813 (ashift:DI
814 (subreg:DI (match_operand:SI 0 "nonimmediate_operand" "d,RT") 0)
815 (const_int 32)) (const_int 32))
816 (match_operand:DI 1 "const0_operand" "")))
817 (set (match_operand:DI 2 "register_operand" "=d,d")
818 (sign_extend:DI (match_dup 0)))]
819 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH"
820 "ltgfr\t%2,%0
821 ltgf\t%2,%0"
822 [(set_attr "op_type" "RRE,RXY")
823 (set_attr "cpu_facility" "*,z10")
824 (set_attr "z10prop" "z10_super_E1,z10_super_E1") ])
825
826 ; ltr, lt, ltgr, ltg
827 (define_insn "*tst<mode>_extimm"
828 [(set (reg CC_REGNUM)
829 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
830 (match_operand:GPR 1 "const0_operand" "")))
831 (set (match_operand:GPR 2 "register_operand" "=d,d")
832 (match_dup 0))]
833 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
834 "@
835 lt<g>r\t%2,%0
836 lt<g>\t%2,%0"
837 [(set_attr "op_type" "RR<E>,RXY")
838 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3") ])
839
840 ; ltr, lt, ltgr, ltg
841 (define_insn "*tst<mode>_cconly_extimm"
842 [(set (reg CC_REGNUM)
843 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
844 (match_operand:GPR 1 "const0_operand" "")))
845 (clobber (match_scratch:GPR 2 "=X,d"))]
846 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
847 "@
848 lt<g>r\t%0,%0
849 lt<g>\t%2,%0"
850 [(set_attr "op_type" "RR<E>,RXY")
851 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3")])
852
853 (define_insn "*tstdi"
854 [(set (reg CC_REGNUM)
855 (compare (match_operand:DI 0 "register_operand" "d")
856 (match_operand:DI 1 "const0_operand" "")))
857 (set (match_operand:DI 2 "register_operand" "=d")
858 (match_dup 0))]
859 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH && !TARGET_EXTIMM"
860 "ltgr\t%2,%0"
861 [(set_attr "op_type" "RRE")
862 (set_attr "z10prop" "z10_fr_E1")])
863
864 (define_insn "*tstsi"
865 [(set (reg CC_REGNUM)
866 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
867 (match_operand:SI 1 "const0_operand" "")))
868 (set (match_operand:SI 2 "register_operand" "=d,d,d")
869 (match_dup 0))]
870 "s390_match_ccmode(insn, CCSmode) && !TARGET_EXTIMM"
871 "@
872 ltr\t%2,%0
873 icm\t%2,15,%S0
874 icmy\t%2,15,%S0"
875 [(set_attr "op_type" "RR,RS,RSY")
876 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
877
878 (define_insn "*tstsi_cconly"
879 [(set (reg CC_REGNUM)
880 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
881 (match_operand:SI 1 "const0_operand" "")))
882 (clobber (match_scratch:SI 2 "=X,d,d"))]
883 "s390_match_ccmode(insn, CCSmode)"
884 "@
885 ltr\t%0,%0
886 icm\t%2,15,%S0
887 icmy\t%2,15,%S0"
888 [(set_attr "op_type" "RR,RS,RSY")
889 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
890
891 (define_insn "*tstdi_cconly_31"
892 [(set (reg CC_REGNUM)
893 (compare (match_operand:DI 0 "register_operand" "d")
894 (match_operand:DI 1 "const0_operand" "")))]
895 "s390_match_ccmode(insn, CCSmode) && !TARGET_ZARCH"
896 "srda\t%0,0"
897 [(set_attr "op_type" "RS")
898 (set_attr "atype" "reg")])
899
900 ; ltr, ltgr
901 (define_insn "*tst<mode>_cconly2"
902 [(set (reg CC_REGNUM)
903 (compare (match_operand:GPR 0 "register_operand" "d")
904 (match_operand:GPR 1 "const0_operand" "")))]
905 "s390_match_ccmode(insn, CCSmode)"
906 "lt<g>r\t%0,%0"
907 [(set_attr "op_type" "RR<E>")
908 (set_attr "z10prop" "z10_fr_E1")])
909
910 ; tst(hi|qi) instruction pattern(s).
911
912 (define_insn "*tst<mode>CCT"
913 [(set (reg CC_REGNUM)
914 (compare (match_operand:HQI 0 "nonimmediate_operand" "?Q,?S,d")
915 (match_operand:HQI 1 "const0_operand" "")))
916 (set (match_operand:HQI 2 "register_operand" "=d,d,0")
917 (match_dup 0))]
918 "s390_match_ccmode(insn, CCTmode)"
919 "@
920 icm\t%2,<icm_lo>,%S0
921 icmy\t%2,<icm_lo>,%S0
922 tml\t%0,<max_uint>"
923 [(set_attr "op_type" "RS,RSY,RI")
924 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
925
926 (define_insn "*tsthiCCT_cconly"
927 [(set (reg CC_REGNUM)
928 (compare (match_operand:HI 0 "nonimmediate_operand" "Q,S,d")
929 (match_operand:HI 1 "const0_operand" "")))
930 (clobber (match_scratch:HI 2 "=d,d,X"))]
931 "s390_match_ccmode(insn, CCTmode)"
932 "@
933 icm\t%2,3,%S0
934 icmy\t%2,3,%S0
935 tml\t%0,65535"
936 [(set_attr "op_type" "RS,RSY,RI")
937 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
938
939 (define_insn "*tstqiCCT_cconly"
940 [(set (reg CC_REGNUM)
941 (compare (match_operand:QI 0 "nonimmediate_operand" "?Q,?S,d")
942 (match_operand:QI 1 "const0_operand" "")))]
943 "s390_match_ccmode(insn, CCTmode)"
944 "@
945 cli\t%S0,0
946 cliy\t%S0,0
947 tml\t%0,255"
948 [(set_attr "op_type" "SI,SIY,RI")
949 (set_attr "z10prop" "z10_super,z10_super,z10_super")])
950
951 (define_insn "*tst<mode>"
952 [(set (reg CC_REGNUM)
953 (compare (match_operand:HQI 0 "s_operand" "Q,S")
954 (match_operand:HQI 1 "const0_operand" "")))
955 (set (match_operand:HQI 2 "register_operand" "=d,d")
956 (match_dup 0))]
957 "s390_match_ccmode(insn, CCSmode)"
958 "@
959 icm\t%2,<icm_lo>,%S0
960 icmy\t%2,<icm_lo>,%S0"
961 [(set_attr "op_type" "RS,RSY")
962 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
963
964 (define_insn "*tst<mode>_cconly"
965 [(set (reg CC_REGNUM)
966 (compare (match_operand:HQI 0 "s_operand" "Q,S")
967 (match_operand:HQI 1 "const0_operand" "")))
968 (clobber (match_scratch:HQI 2 "=d,d"))]
969 "s390_match_ccmode(insn, CCSmode)"
970 "@
971 icm\t%2,<icm_lo>,%S0
972 icmy\t%2,<icm_lo>,%S0"
973 [(set_attr "op_type" "RS,RSY")
974 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
975
976
977 ; Compare (equality) instructions
978
979 (define_insn "*cmpdi_cct"
980 [(set (reg CC_REGNUM)
981 (compare (match_operand:DI 0 "nonimmediate_operand" "%d,d,d,d,Q")
982 (match_operand:DI 1 "general_operand" "d,K,Os,RT,BQ")))]
983 "s390_match_ccmode (insn, CCTmode) && TARGET_ZARCH"
984 "@
985 cgr\t%0,%1
986 cghi\t%0,%h1
987 cgfi\t%0,%1
988 cg\t%0,%1
989 #"
990 [(set_attr "op_type" "RRE,RI,RIL,RXY,SS")
991 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,*")])
992
993 (define_insn "*cmpsi_cct"
994 [(set (reg CC_REGNUM)
995 (compare (match_operand:SI 0 "nonimmediate_operand" "%d,d,d,d,d,Q")
996 (match_operand:SI 1 "general_operand" "d,K,Os,R,T,BQ")))]
997 "s390_match_ccmode (insn, CCTmode)"
998 "@
999 cr\t%0,%1
1000 chi\t%0,%h1
1001 cfi\t%0,%1
1002 c\t%0,%1
1003 cy\t%0,%1
1004 #"
1005 [(set_attr "op_type" "RR,RI,RIL,RX,RXY,SS")
1006 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*")])
1007
1008 ; Compare (signed) instructions
1009
1010 (define_insn "*cmpdi_ccs_sign"
1011 [(set (reg CC_REGNUM)
1012 (compare (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1013 "d,RT,b"))
1014 (match_operand:DI 0 "register_operand" "d, d,d")))]
1015 "s390_match_ccmode(insn, CCSRmode) && TARGET_ZARCH"
1016 "@
1017 cgfr\t%0,%1
1018 cgf\t%0,%1
1019 cgfrl\t%0,%1"
1020 [(set_attr "op_type" "RRE,RXY,RIL")
1021 (set_attr "z10prop" "z10_c,*,*")
1022 (set_attr "type" "*,*,larl")])
1023
1024
1025
1026 (define_insn "*cmpsi_ccs_sign"
1027 [(set (reg CC_REGNUM)
1028 (compare (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T,b"))
1029 (match_operand:SI 0 "register_operand" "d,d,d")))]
1030 "s390_match_ccmode(insn, CCSRmode)"
1031 "@
1032 ch\t%0,%1
1033 chy\t%0,%1
1034 chrl\t%0,%1"
1035 [(set_attr "op_type" "RX,RXY,RIL")
1036 (set_attr "cpu_facility" "*,*,z10")
1037 (set_attr "type" "*,*,larl")
1038 (set_attr "z196prop" "z196_cracked,z196_cracked,z196_cracked")])
1039
1040 (define_insn "*cmphi_ccs_z10"
1041 [(set (reg CC_REGNUM)
1042 (compare (match_operand:HI 0 "s_operand" "Q")
1043 (match_operand:HI 1 "immediate_operand" "K")))]
1044 "s390_match_ccmode(insn, CCSmode) && TARGET_Z10"
1045 "chhsi\t%0,%1"
1046 [(set_attr "op_type" "SIL")
1047 (set_attr "z196prop" "z196_cracked")])
1048
1049 (define_insn "*cmpdi_ccs_signhi_rl"
1050 [(set (reg CC_REGNUM)
1051 (compare (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT,b"))
1052 (match_operand:GPR 0 "register_operand" "d,d")))]
1053 "s390_match_ccmode(insn, CCSRmode) && TARGET_Z10"
1054 "@
1055 cgh\t%0,%1
1056 cghrl\t%0,%1"
1057 [(set_attr "op_type" "RXY,RIL")
1058 (set_attr "type" "*,larl")])
1059
1060 ; cr, chi, cfi, c, cy, cgr, cghi, cgfi, cg, chsi, cghsi, crl, cgrl
1061 (define_insn "*cmp<mode>_ccs"
1062 [(set (reg CC_REGNUM)
1063 (compare (match_operand:GPR 0 "nonimmediate_operand"
1064 "d,d,Q, d,d,d,d")
1065 (match_operand:GPR 1 "general_operand"
1066 "d,K,K,Os,R,T,b")))]
1067 "s390_match_ccmode(insn, CCSmode)"
1068 "@
1069 c<g>r\t%0,%1
1070 c<g>hi\t%0,%h1
1071 c<g>hsi\t%0,%h1
1072 c<g>fi\t%0,%1
1073 c<g>\t%0,%1
1074 c<y>\t%0,%1
1075 c<g>rl\t%0,%1"
1076 [(set_attr "op_type" "RR<E>,RI,SIL,RIL,RX<Y>,RXY,RIL")
1077 (set_attr "cpu_facility" "*,*,z10,extimm,*,*,z10")
1078 (set_attr "type" "*,*,*,*,*,*,larl")
1079 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,z10_super")])
1080
1081
1082 ; Compare (unsigned) instructions
1083
1084 (define_insn "*cmpsi_ccu_zerohi_rlsi"
1085 [(set (reg CC_REGNUM)
1086 (compare (zero_extend:SI (mem:HI (match_operand:SI 1
1087 "larl_operand" "X")))
1088 (match_operand:SI 0 "register_operand" "d")))]
1089 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1090 "clhrl\t%0,%1"
1091 [(set_attr "op_type" "RIL")
1092 (set_attr "type" "larl")
1093 (set_attr "z10prop" "z10_super")])
1094
1095 ; clhrl, clghrl
1096 (define_insn "*cmp<GPR:mode>_ccu_zerohi_rldi"
1097 [(set (reg CC_REGNUM)
1098 (compare (zero_extend:GPR (mem:HI (match_operand:DI 1
1099 "larl_operand" "X")))
1100 (match_operand:GPR 0 "register_operand" "d")))]
1101 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1102 "cl<g>hrl\t%0,%1"
1103 [(set_attr "op_type" "RIL")
1104 (set_attr "type" "larl")
1105 (set_attr "z10prop" "z10_super")])
1106
1107 (define_insn "*cmpdi_ccu_zero"
1108 [(set (reg CC_REGNUM)
1109 (compare (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1110 "d,RT,b"))
1111 (match_operand:DI 0 "register_operand" "d, d,d")))]
1112 "s390_match_ccmode (insn, CCURmode) && TARGET_ZARCH"
1113 "@
1114 clgfr\t%0,%1
1115 clgf\t%0,%1
1116 clgfrl\t%0,%1"
1117 [(set_attr "op_type" "RRE,RXY,RIL")
1118 (set_attr "cpu_facility" "*,*,z10")
1119 (set_attr "type" "*,*,larl")
1120 (set_attr "z10prop" "z10_super_c,z10_super_E1,z10_super")])
1121
1122 (define_insn "*cmpdi_ccu"
1123 [(set (reg CC_REGNUM)
1124 (compare (match_operand:DI 0 "nonimmediate_operand"
1125 "d, d,d,Q, d, Q,BQ")
1126 (match_operand:DI 1 "general_operand"
1127 "d,Op,b,D,RT,BQ,Q")))]
1128 "s390_match_ccmode (insn, CCUmode) && TARGET_ZARCH"
1129 "@
1130 clgr\t%0,%1
1131 clgfi\t%0,%1
1132 clgrl\t%0,%1
1133 clghsi\t%0,%x1
1134 clg\t%0,%1
1135 #
1136 #"
1137 [(set_attr "op_type" "RRE,RIL,RIL,SIL,RXY,SS,SS")
1138 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*")
1139 (set_attr "type" "*,*,larl,*,*,*,*")
1140 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*,*")])
1141
1142 (define_insn "*cmpsi_ccu"
1143 [(set (reg CC_REGNUM)
1144 (compare (match_operand:SI 0 "nonimmediate_operand" "d, d,d,Q,d,d, Q,BQ")
1145 (match_operand:SI 1 "general_operand" "d,Os,b,D,R,T,BQ, Q")))]
1146 "s390_match_ccmode (insn, CCUmode)"
1147 "@
1148 clr\t%0,%1
1149 clfi\t%0,%o1
1150 clrl\t%0,%1
1151 clfhsi\t%0,%x1
1152 cl\t%0,%1
1153 cly\t%0,%1
1154 #
1155 #"
1156 [(set_attr "op_type" "RR,RIL,RIL,SIL,RX,RXY,SS,SS")
1157 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*,*")
1158 (set_attr "type" "*,*,larl,*,*,*,*,*")
1159 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,*,*")])
1160
1161 (define_insn "*cmphi_ccu"
1162 [(set (reg CC_REGNUM)
1163 (compare (match_operand:HI 0 "nonimmediate_operand" "d,d,Q,Q,BQ")
1164 (match_operand:HI 1 "general_operand" "Q,S,D,BQ,Q")))]
1165 "s390_match_ccmode (insn, CCUmode)
1166 && !register_operand (operands[1], HImode)"
1167 "@
1168 clm\t%0,3,%S1
1169 clmy\t%0,3,%S1
1170 clhhsi\t%0,%1
1171 #
1172 #"
1173 [(set_attr "op_type" "RS,RSY,SIL,SS,SS")
1174 (set_attr "cpu_facility" "*,*,z10,*,*")
1175 (set_attr "z10prop" "*,*,z10_super,*,*")])
1176
1177 (define_insn "*cmpqi_ccu"
1178 [(set (reg CC_REGNUM)
1179 (compare (match_operand:QI 0 "nonimmediate_operand" "d,d,Q,S,Q,BQ")
1180 (match_operand:QI 1 "general_operand" "Q,S,n,n,BQ,Q")))]
1181 "s390_match_ccmode (insn, CCUmode)
1182 && !register_operand (operands[1], QImode)"
1183 "@
1184 clm\t%0,1,%S1
1185 clmy\t%0,1,%S1
1186 cli\t%S0,%b1
1187 cliy\t%S0,%b1
1188 #
1189 #"
1190 [(set_attr "op_type" "RS,RSY,SI,SIY,SS,SS")
1191 (set_attr "z10prop" "*,*,z10_super,z10_super,*,*")])
1192
1193
1194 ; Block compare (CLC) instruction patterns.
1195
1196 (define_insn "*clc"
1197 [(set (reg CC_REGNUM)
1198 (compare (match_operand:BLK 0 "memory_operand" "Q")
1199 (match_operand:BLK 1 "memory_operand" "Q")))
1200 (use (match_operand 2 "const_int_operand" "n"))]
1201 "s390_match_ccmode (insn, CCUmode)
1202 && INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
1203 "clc\t%O0(%2,%R0),%S1"
1204 [(set_attr "op_type" "SS")])
1205
1206 (define_split
1207 [(set (reg CC_REGNUM)
1208 (compare (match_operand 0 "memory_operand" "")
1209 (match_operand 1 "memory_operand" "")))]
1210 "reload_completed
1211 && s390_match_ccmode (insn, CCUmode)
1212 && GET_MODE (operands[0]) == GET_MODE (operands[1])
1213 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
1214 [(parallel
1215 [(set (match_dup 0) (match_dup 1))
1216 (use (match_dup 2))])]
1217 {
1218 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
1219 operands[0] = adjust_address (operands[0], BLKmode, 0);
1220 operands[1] = adjust_address (operands[1], BLKmode, 0);
1221
1222 operands[1] = gen_rtx_COMPARE (GET_MODE (SET_DEST (PATTERN (curr_insn))),
1223 operands[0], operands[1]);
1224 operands[0] = SET_DEST (PATTERN (curr_insn));
1225 })
1226
1227
1228 ; (TF|DF|SF|TD|DD|SD) instructions
1229
1230 ; ltxbr, ltdbr, ltebr, ltxtr, ltdtr
1231 (define_insn "*cmp<mode>_ccs_0"
1232 [(set (reg CC_REGNUM)
1233 (compare (match_operand:FP 0 "register_operand" "f")
1234 (match_operand:FP 1 "const0_operand" "")))]
1235 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1236 "lt<xde><bt>r\t%0,%0"
1237 [(set_attr "op_type" "RRE")
1238 (set_attr "type" "fsimp<mode>")])
1239
1240 ; cxtr, cxbr, cdtr, cdbr, cebr, cdb, ceb
1241 (define_insn "*cmp<mode>_ccs"
1242 [(set (reg CC_REGNUM)
1243 (compare (match_operand:FP 0 "register_operand" "f,f")
1244 (match_operand:FP 1 "general_operand" "f,<Rf>")))]
1245 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1246 "@
1247 c<xde><bt>r\t%0,%1
1248 c<xde>b\t%0,%1"
1249 [(set_attr "op_type" "RRE,RXE")
1250 (set_attr "type" "fsimp<mode>")])
1251
1252 ; wfcedbs, wfchdbs, wfchedbs
1253 (define_insn "*vec_cmp<insn_cmp>df_cconly"
1254 [(set (reg:VFCMP CC_REGNUM)
1255 (compare:VFCMP (match_operand:DF 0 "register_operand" "v")
1256 (match_operand:DF 1 "register_operand" "v")))
1257 (clobber (match_scratch:V2DI 2 "=v"))]
1258 "TARGET_Z13 && TARGET_HARD_FLOAT"
1259 "wfc<asm_fcmp>dbs\t%v2,%v0,%v1"
1260 [(set_attr "op_type" "VRR")])
1261
1262 ; Compare and Branch instructions
1263
1264 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1265 ; The following instructions do a complementary access of their second
1266 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1267 (define_insn "*cmp_and_br_signed_<mode>"
1268 [(set (pc)
1269 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1270 [(match_operand:GPR 1 "register_operand" "d,d")
1271 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1272 (label_ref (match_operand 3 "" ""))
1273 (pc)))
1274 (clobber (reg:CC CC_REGNUM))]
1275 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1276 {
1277 if (get_attr_length (insn) == 6)
1278 return which_alternative ?
1279 "c<g>ij%C0\t%1,%c2,%l3" : "c<g>rj%C0\t%1,%2,%l3";
1280 else
1281 return which_alternative ?
1282 "c<g>fi\t%1,%c2\;jg%C0\t%l3" : "c<g>r\t%1,%2\;jg%C0\t%l3";
1283 }
1284 [(set_attr "op_type" "RIE")
1285 (set_attr "type" "branch")
1286 (set_attr "z10prop" "z10_super_c,z10_super")
1287 (set (attr "length")
1288 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1289 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1290 ; 10 byte for cgr/jg
1291
1292 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1293 ; The following instructions do a complementary access of their second
1294 ; operand (z10 only): clrj, clgrj, clr, clgr
1295 (define_insn "*cmp_and_br_unsigned_<mode>"
1296 [(set (pc)
1297 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1298 [(match_operand:GPR 1 "register_operand" "d,d")
1299 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1300 (label_ref (match_operand 3 "" ""))
1301 (pc)))
1302 (clobber (reg:CC CC_REGNUM))]
1303 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1304 {
1305 if (get_attr_length (insn) == 6)
1306 return which_alternative ?
1307 "cl<g>ij%C0\t%1,%b2,%l3" : "cl<g>rj%C0\t%1,%2,%l3";
1308 else
1309 return which_alternative ?
1310 "cl<g>fi\t%1,%b2\;jg%C0\t%l3" : "cl<g>r\t%1,%2\;jg%C0\t%l3";
1311 }
1312 [(set_attr "op_type" "RIE")
1313 (set_attr "type" "branch")
1314 (set_attr "z10prop" "z10_super_c,z10_super")
1315 (set (attr "length")
1316 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1317 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1318 ; 10 byte for clgr/jg
1319
1320 ; And now the same two patterns as above but with a negated CC mask.
1321
1322 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1323 ; The following instructions do a complementary access of their second
1324 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1325 (define_insn "*icmp_and_br_signed_<mode>"
1326 [(set (pc)
1327 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1328 [(match_operand:GPR 1 "register_operand" "d,d")
1329 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1330 (pc)
1331 (label_ref (match_operand 3 "" ""))))
1332 (clobber (reg:CC CC_REGNUM))]
1333 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1334 {
1335 if (get_attr_length (insn) == 6)
1336 return which_alternative ?
1337 "c<g>ij%D0\t%1,%c2,%l3" : "c<g>rj%D0\t%1,%2,%l3";
1338 else
1339 return which_alternative ?
1340 "c<g>fi\t%1,%c2\;jg%D0\t%l3" : "c<g>r\t%1,%2\;jg%D0\t%l3";
1341 }
1342 [(set_attr "op_type" "RIE")
1343 (set_attr "type" "branch")
1344 (set_attr "z10prop" "z10_super_c,z10_super")
1345 (set (attr "length")
1346 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1347 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1348 ; 10 byte for cgr/jg
1349
1350 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1351 ; The following instructions do a complementary access of their second
1352 ; operand (z10 only): clrj, clgrj, clr, clgr
1353 (define_insn "*icmp_and_br_unsigned_<mode>"
1354 [(set (pc)
1355 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1356 [(match_operand:GPR 1 "register_operand" "d,d")
1357 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1358 (pc)
1359 (label_ref (match_operand 3 "" ""))))
1360 (clobber (reg:CC CC_REGNUM))]
1361 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1362 {
1363 if (get_attr_length (insn) == 6)
1364 return which_alternative ?
1365 "cl<g>ij%D0\t%1,%b2,%l3" : "cl<g>rj%D0\t%1,%2,%l3";
1366 else
1367 return which_alternative ?
1368 "cl<g>fi\t%1,%b2\;jg%D0\t%l3" : "cl<g>r\t%1,%2\;jg%D0\t%l3";
1369 }
1370 [(set_attr "op_type" "RIE")
1371 (set_attr "type" "branch")
1372 (set_attr "z10prop" "z10_super_c,z10_super")
1373 (set (attr "length")
1374 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1375 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1376 ; 10 byte for clgr/jg
1377
1378 ;;
1379 ;;- Move instructions.
1380 ;;
1381
1382 ;
1383 ; movti instruction pattern(s).
1384 ;
1385
1386 ; FIXME: More constants are possible by enabling jxx, jyy constraints
1387 ; for TImode (use double-int for the calculations)
1388 (define_insn "movti"
1389 [(set (match_operand:TI 0 "nonimmediate_operand" "=d,QS,v, v, v,v,d, v,QR, d,o")
1390 (match_operand:TI 1 "general_operand" "QS, d,v,j00,jm1,d,v,QR, v,dPRT,d"))]
1391 "TARGET_ZARCH"
1392 "@
1393 lmg\t%0,%N0,%S1
1394 stmg\t%1,%N1,%S0
1395 vlr\t%v0,%v1
1396 vzero\t%v0
1397 vone\t%v0
1398 vlvgp\t%v0,%1,%N1
1399 #
1400 vl\t%v0,%1
1401 vst\t%v1,%0
1402 #
1403 #"
1404 [(set_attr "op_type" "RSY,RSY,VRR,VRI,VRI,VRR,*,VRX,VRX,*,*")
1405 (set_attr "type" "lm,stm,*,*,*,*,*,*,*,*,*")
1406 (set_attr "cpu_facility" "*,*,vec,vec,vec,vec,vec,vec,vec,*,*")])
1407
1408 (define_split
1409 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1410 (match_operand:TI 1 "general_operand" ""))]
1411 "TARGET_ZARCH && reload_completed
1412 && s390_split_ok_p (operands[0], operands[1], TImode, 0)"
1413 [(set (match_dup 2) (match_dup 4))
1414 (set (match_dup 3) (match_dup 5))]
1415 {
1416 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1417 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1418 operands[4] = operand_subword (operands[1], 0, 0, TImode);
1419 operands[5] = operand_subword (operands[1], 1, 0, TImode);
1420 })
1421
1422 (define_split
1423 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1424 (match_operand:TI 1 "general_operand" ""))]
1425 "TARGET_ZARCH && reload_completed
1426 && s390_split_ok_p (operands[0], operands[1], TImode, 1)"
1427 [(set (match_dup 2) (match_dup 4))
1428 (set (match_dup 3) (match_dup 5))]
1429 {
1430 operands[2] = operand_subword (operands[0], 1, 0, TImode);
1431 operands[3] = operand_subword (operands[0], 0, 0, TImode);
1432 operands[4] = operand_subword (operands[1], 1, 0, TImode);
1433 operands[5] = operand_subword (operands[1], 0, 0, TImode);
1434 })
1435
1436 ; Use part of the TImode target reg to perform the address
1437 ; calculation. If the TImode value is supposed to be copied into a VR
1438 ; this splitter is not necessary.
1439 (define_split
1440 [(set (match_operand:TI 0 "register_operand" "")
1441 (match_operand:TI 1 "memory_operand" ""))]
1442 "TARGET_ZARCH && reload_completed
1443 && !VECTOR_REG_P (operands[0])
1444 && !s_operand (operands[1], VOIDmode)"
1445 [(set (match_dup 0) (match_dup 1))]
1446 {
1447 rtx addr = operand_subword (operands[0], 1, 0, TImode);
1448 addr = gen_lowpart (Pmode, addr);
1449 s390_load_address (addr, XEXP (operands[1], 0));
1450 operands[1] = replace_equiv_address (operands[1], addr);
1451 })
1452
1453
1454 ; Split a VR -> GPR TImode move into 2 vector load GR from VR element.
1455 ; For the higher order bits we do simply a DImode move while the
1456 ; second part is done via vec extract. Both will end up as vlgvg.
1457 (define_split
1458 [(set (match_operand:TI 0 "register_operand" "")
1459 (match_operand:TI 1 "register_operand" ""))]
1460 "TARGET_VX && reload_completed
1461 && GENERAL_REG_P (operands[0])
1462 && VECTOR_REG_P (operands[1])"
1463 [(set (match_dup 2) (match_dup 4))
1464 (set (match_dup 3) (unspec:DI [(match_dup 5) (const_int 1)]
1465 UNSPEC_VEC_EXTRACT))]
1466 {
1467 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1468 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1469 operands[4] = gen_rtx_REG (DImode, REGNO (operands[1]));
1470 operands[5] = gen_rtx_REG (V2DImode, REGNO (operands[1]));
1471 })
1472
1473 ;
1474 ; Patterns used for secondary reloads
1475 ;
1476
1477 ; z10 provides move instructions accepting larl memory operands.
1478 ; Unfortunately there is no such variant for QI, TI and FP mode moves.
1479 ; These patterns are also used for unaligned SI and DI accesses.
1480
1481 (define_expand "reload<ALL:mode><P:mode>_tomem_z10"
1482 [(parallel [(match_operand:ALL 0 "memory_operand" "")
1483 (match_operand:ALL 1 "register_operand" "=d")
1484 (match_operand:P 2 "register_operand" "=&a")])]
1485 "TARGET_Z10"
1486 {
1487 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1488 DONE;
1489 })
1490
1491 (define_expand "reload<ALL:mode><P:mode>_toreg_z10"
1492 [(parallel [(match_operand:ALL 0 "register_operand" "=d")
1493 (match_operand:ALL 1 "memory_operand" "")
1494 (match_operand:P 2 "register_operand" "=a")])]
1495 "TARGET_Z10"
1496 {
1497 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1498 DONE;
1499 })
1500
1501 (define_expand "reload<P:mode>_larl_odd_addend_z10"
1502 [(parallel [(match_operand:P 0 "register_operand" "=d")
1503 (match_operand:P 1 "larl_operand" "")
1504 (match_operand:P 2 "register_operand" "=a")])]
1505 "TARGET_Z10"
1506 {
1507 s390_reload_larl_operand (operands[0], operands[1], operands[2]);
1508 DONE;
1509 })
1510
1511 ; Handles loading a PLUS (load address) expression
1512
1513 (define_expand "reload<mode>_plus"
1514 [(parallel [(match_operand:P 0 "register_operand" "=a")
1515 (match_operand:P 1 "s390_plus_operand" "")
1516 (match_operand:P 2 "register_operand" "=&a")])]
1517 ""
1518 {
1519 s390_expand_plus_operand (operands[0], operands[1], operands[2]);
1520 DONE;
1521 })
1522
1523 ; Not all the indirect memory access instructions support the full
1524 ; format (long disp + index + base). So whenever a move from/to such
1525 ; an address is required and the instruction cannot deal with it we do
1526 ; a load address into a scratch register first and use this as the new
1527 ; base register.
1528 ; This in particular is used for:
1529 ; - non-offsetable memory accesses for multiword moves
1530 ; - full vector reg moves with long displacements
1531
1532 (define_expand "reload<mode>_la_in"
1533 [(parallel [(match_operand 0 "register_operand" "")
1534 (match_operand 1 "" "")
1535 (match_operand:P 2 "register_operand" "=&a")])]
1536 ""
1537 {
1538 gcc_assert (MEM_P (operands[1]));
1539 s390_load_address (operands[2], find_replacement (&XEXP (operands[1], 0)));
1540 operands[1] = replace_equiv_address (operands[1], operands[2]);
1541 emit_move_insn (operands[0], operands[1]);
1542 DONE;
1543 })
1544
1545 (define_expand "reload<mode>_la_out"
1546 [(parallel [(match_operand 0 "" "")
1547 (match_operand 1 "register_operand" "")
1548 (match_operand:P 2 "register_operand" "=&a")])]
1549 ""
1550 {
1551 gcc_assert (MEM_P (operands[0]));
1552 s390_load_address (operands[2], find_replacement (&XEXP (operands[0], 0)));
1553 operands[0] = replace_equiv_address (operands[0], operands[2]);
1554 emit_move_insn (operands[0], operands[1]);
1555 DONE;
1556 })
1557
1558 (define_expand "reload<mode>_PIC_addr"
1559 [(parallel [(match_operand 0 "register_operand" "=d")
1560 (match_operand 1 "larl_operand" "")
1561 (match_operand:P 2 "register_operand" "=a")])]
1562 ""
1563 {
1564 rtx new_rtx = legitimize_pic_address (operands[1], operands[2]);
1565 emit_move_insn (operands[0], new_rtx);
1566 })
1567
1568 ;
1569 ; movdi instruction pattern(s).
1570 ;
1571
1572 (define_expand "movdi"
1573 [(set (match_operand:DI 0 "general_operand" "")
1574 (match_operand:DI 1 "general_operand" ""))]
1575 ""
1576 {
1577 /* Handle symbolic constants. */
1578 if (TARGET_64BIT
1579 && (SYMBOLIC_CONST (operands[1])
1580 || (GET_CODE (operands[1]) == PLUS
1581 && XEXP (operands[1], 0) == pic_offset_table_rtx
1582 && SYMBOLIC_CONST (XEXP (operands[1], 1)))))
1583 emit_symbolic_move (operands);
1584 })
1585
1586 (define_insn "*movdi_larl"
1587 [(set (match_operand:DI 0 "register_operand" "=d")
1588 (match_operand:DI 1 "larl_operand" "X"))]
1589 "TARGET_64BIT
1590 && !FP_REG_P (operands[0])"
1591 "larl\t%0,%1"
1592 [(set_attr "op_type" "RIL")
1593 (set_attr "type" "larl")
1594 (set_attr "z10prop" "z10_super_A1")])
1595
1596 (define_insn "*movdi_64"
1597 [(set (match_operand:DI 0 "nonimmediate_operand"
1598 "=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")
1599 (match_operand:DI 1 "general_operand"
1600 " 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"))]
1601 "TARGET_ZARCH"
1602 "@
1603 lghi\t%0,%h1
1604 llihh\t%0,%i1
1605 llihl\t%0,%i1
1606 llilh\t%0,%i1
1607 llill\t%0,%i1
1608 lgfi\t%0,%1
1609 llihf\t%0,%k1
1610 llilf\t%0,%k1
1611 ldgr\t%0,%1
1612 lgdr\t%0,%1
1613 lay\t%0,%a1
1614 lgrl\t%0,%1
1615 lgr\t%0,%1
1616 lg\t%0,%1
1617 stg\t%1,%0
1618 ldr\t%0,%1
1619 ld\t%0,%1
1620 ldy\t%0,%1
1621 std\t%1,%0
1622 stdy\t%1,%0
1623 stgrl\t%1,%0
1624 mvghi\t%0,%1
1625 #
1626 #
1627 stam\t%1,%N1,%S0
1628 lam\t%0,%N0,%S1
1629 vleig\t%v0,%h1,0
1630 vlr\t%v0,%v1
1631 vlvgg\t%v0,%1,0
1632 vlgvg\t%0,%v1,0
1633 vleg\t%v0,%1,0
1634 vsteg\t%v1,%0,0"
1635 [(set_attr "op_type" "RI,RI,RI,RI,RI,RIL,RIL,RIL,RRE,RRE,RXY,RIL,RRE,RXY,
1636 RXY,RR,RX,RXY,RX,RXY,RIL,SIL,*,*,RS,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1637 (set_attr "type" "*,*,*,*,*,*,*,*,floaddf,floaddf,la,larl,lr,load,store,
1638 floaddf,floaddf,floaddf,fstoredf,fstoredf,larl,*,*,*,*,
1639 *,*,*,*,*,*,*")
1640 (set_attr "cpu_facility" "*,*,*,*,*,extimm,extimm,extimm,dfp,dfp,longdisp,
1641 z10,*,*,*,*,*,longdisp,*,longdisp,
1642 z10,z10,*,*,*,*,vec,vec,vec,vec,vec,vec")
1643 (set_attr "z10prop" "z10_fwd_A1,
1644 z10_fwd_E1,
1645 z10_fwd_E1,
1646 z10_fwd_E1,
1647 z10_fwd_E1,
1648 z10_fwd_A1,
1649 z10_fwd_E1,
1650 z10_fwd_E1,
1651 *,
1652 *,
1653 z10_fwd_A1,
1654 z10_fwd_A3,
1655 z10_fr_E1,
1656 z10_fwd_A3,
1657 z10_rec,
1658 *,
1659 *,
1660 *,
1661 *,
1662 *,
1663 z10_rec,
1664 z10_super,
1665 *,
1666 *,
1667 *,
1668 *,*,*,*,*,*,*")
1669 ])
1670
1671 (define_split
1672 [(set (match_operand:DI 0 "register_operand" "")
1673 (match_operand:DI 1 "register_operand" ""))]
1674 "TARGET_ZARCH && ACCESS_REG_P (operands[1])"
1675 [(set (match_dup 2) (match_dup 3))
1676 (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
1677 (set (strict_low_part (match_dup 2)) (match_dup 4))]
1678 "operands[2] = gen_lowpart (SImode, operands[0]);
1679 s390_split_access_reg (operands[1], &operands[4], &operands[3]);")
1680
1681 (define_split
1682 [(set (match_operand:DI 0 "register_operand" "")
1683 (match_operand:DI 1 "register_operand" ""))]
1684 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1685 && dead_or_set_p (insn, operands[1])"
1686 [(set (match_dup 3) (match_dup 2))
1687 (set (match_dup 1) (lshiftrt:DI (match_dup 1) (const_int 32)))
1688 (set (match_dup 4) (match_dup 2))]
1689 "operands[2] = gen_lowpart (SImode, operands[1]);
1690 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1691
1692 (define_split
1693 [(set (match_operand:DI 0 "register_operand" "")
1694 (match_operand:DI 1 "register_operand" ""))]
1695 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1696 && !dead_or_set_p (insn, operands[1])"
1697 [(set (match_dup 3) (match_dup 2))
1698 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))
1699 (set (match_dup 4) (match_dup 2))
1700 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))]
1701 "operands[2] = gen_lowpart (SImode, operands[1]);
1702 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1703
1704 (define_insn "*movdi_31"
1705 [(set (match_operand:DI 0 "nonimmediate_operand"
1706 "=d,d,Q,S,d ,o,!*f,!*f,!*f,!R,!T,d")
1707 (match_operand:DI 1 "general_operand"
1708 " Q,S,d,d,dPRT,d, *f, R, T,*f,*f,b"))]
1709 "!TARGET_ZARCH"
1710 "@
1711 lm\t%0,%N0,%S1
1712 lmy\t%0,%N0,%S1
1713 stm\t%1,%N1,%S0
1714 stmy\t%1,%N1,%S0
1715 #
1716 #
1717 ldr\t%0,%1
1718 ld\t%0,%1
1719 ldy\t%0,%1
1720 std\t%1,%0
1721 stdy\t%1,%0
1722 #"
1723 [(set_attr "op_type" "RS,RSY,RS,RSY,*,*,RR,RX,RXY,RX,RXY,*")
1724 (set_attr "type" "lm,lm,stm,stm,*,*,floaddf,floaddf,floaddf,fstoredf,fstoredf,*")
1725 (set_attr "cpu_facility" "*,*,*,*,*,*,*,*,*,*,*,z10")])
1726
1727 ; For a load from a symbol ref we can use one of the target registers
1728 ; together with larl to load the address.
1729 (define_split
1730 [(set (match_operand:DI 0 "register_operand" "")
1731 (match_operand:DI 1 "memory_operand" ""))]
1732 "!TARGET_ZARCH && reload_completed && TARGET_Z10
1733 && larl_operand (XEXP (operands[1], 0), SImode)"
1734 [(set (match_dup 2) (match_dup 3))
1735 (set (match_dup 0) (match_dup 1))]
1736 {
1737 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1738 operands[3] = XEXP (operands[1], 0);
1739 operands[1] = replace_equiv_address (operands[1], operands[2]);
1740 })
1741
1742 (define_split
1743 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1744 (match_operand:DI 1 "general_operand" ""))]
1745 "!TARGET_ZARCH && reload_completed
1746 && s390_split_ok_p (operands[0], operands[1], DImode, 0)"
1747 [(set (match_dup 2) (match_dup 4))
1748 (set (match_dup 3) (match_dup 5))]
1749 {
1750 operands[2] = operand_subword (operands[0], 0, 0, DImode);
1751 operands[3] = operand_subword (operands[0], 1, 0, DImode);
1752 operands[4] = operand_subword (operands[1], 0, 0, DImode);
1753 operands[5] = operand_subword (operands[1], 1, 0, DImode);
1754 })
1755
1756 (define_split
1757 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1758 (match_operand:DI 1 "general_operand" ""))]
1759 "!TARGET_ZARCH && reload_completed
1760 && s390_split_ok_p (operands[0], operands[1], DImode, 1)"
1761 [(set (match_dup 2) (match_dup 4))
1762 (set (match_dup 3) (match_dup 5))]
1763 {
1764 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1765 operands[3] = operand_subword (operands[0], 0, 0, DImode);
1766 operands[4] = operand_subword (operands[1], 1, 0, DImode);
1767 operands[5] = operand_subword (operands[1], 0, 0, DImode);
1768 })
1769
1770 (define_split
1771 [(set (match_operand:DI 0 "register_operand" "")
1772 (match_operand:DI 1 "memory_operand" ""))]
1773 "!TARGET_ZARCH && reload_completed
1774 && !FP_REG_P (operands[0])
1775 && !s_operand (operands[1], VOIDmode)"
1776 [(set (match_dup 0) (match_dup 1))]
1777 {
1778 rtx addr = operand_subword (operands[0], 1, 0, DImode);
1779 s390_load_address (addr, XEXP (operands[1], 0));
1780 operands[1] = replace_equiv_address (operands[1], addr);
1781 })
1782
1783 (define_peephole2
1784 [(set (match_operand:DI 0 "register_operand" "")
1785 (mem:DI (match_operand 1 "address_operand" "")))]
1786 "TARGET_ZARCH
1787 && !FP_REG_P (operands[0])
1788 && GET_CODE (operands[1]) == SYMBOL_REF
1789 && CONSTANT_POOL_ADDRESS_P (operands[1])
1790 && get_pool_mode (operands[1]) == DImode
1791 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1792 [(set (match_dup 0) (match_dup 2))]
1793 "operands[2] = get_pool_constant (operands[1]);")
1794
1795 (define_insn "*la_64"
1796 [(set (match_operand:DI 0 "register_operand" "=d,d")
1797 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))]
1798 "TARGET_64BIT"
1799 "@
1800 la\t%0,%a1
1801 lay\t%0,%a1"
1802 [(set_attr "op_type" "RX,RXY")
1803 (set_attr "type" "la")
1804 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
1805
1806 (define_peephole2
1807 [(parallel
1808 [(set (match_operand:DI 0 "register_operand" "")
1809 (match_operand:QI 1 "address_operand" ""))
1810 (clobber (reg:CC CC_REGNUM))])]
1811 "TARGET_64BIT
1812 && preferred_la_operand_p (operands[1], const0_rtx)"
1813 [(set (match_dup 0) (match_dup 1))]
1814 "")
1815
1816 (define_peephole2
1817 [(set (match_operand:DI 0 "register_operand" "")
1818 (match_operand:DI 1 "register_operand" ""))
1819 (parallel
1820 [(set (match_dup 0)
1821 (plus:DI (match_dup 0)
1822 (match_operand:DI 2 "nonmemory_operand" "")))
1823 (clobber (reg:CC CC_REGNUM))])]
1824 "TARGET_64BIT
1825 && !reg_overlap_mentioned_p (operands[0], operands[2])
1826 && preferred_la_operand_p (operands[1], operands[2])"
1827 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
1828 "")
1829
1830 ;
1831 ; movsi instruction pattern(s).
1832 ;
1833
1834 (define_expand "movsi"
1835 [(set (match_operand:SI 0 "general_operand" "")
1836 (match_operand:SI 1 "general_operand" ""))]
1837 ""
1838 {
1839 /* Handle symbolic constants. */
1840 if (!TARGET_64BIT
1841 && (SYMBOLIC_CONST (operands[1])
1842 || (GET_CODE (operands[1]) == PLUS
1843 && XEXP (operands[1], 0) == pic_offset_table_rtx
1844 && SYMBOLIC_CONST (XEXP(operands[1], 1)))))
1845 emit_symbolic_move (operands);
1846 })
1847
1848 (define_insn "*movsi_larl"
1849 [(set (match_operand:SI 0 "register_operand" "=d")
1850 (match_operand:SI 1 "larl_operand" "X"))]
1851 "!TARGET_64BIT && TARGET_CPU_ZARCH
1852 && !FP_REG_P (operands[0])"
1853 "larl\t%0,%1"
1854 [(set_attr "op_type" "RIL")
1855 (set_attr "type" "larl")
1856 (set_attr "z10prop" "z10_fwd_A1")])
1857
1858 (define_insn "*movsi_zarch"
1859 [(set (match_operand:SI 0 "nonimmediate_operand"
1860 "=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")
1861 (match_operand:SI 1 "general_operand"
1862 " 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"))]
1863 "TARGET_ZARCH"
1864 "@
1865 lhi\t%0,%h1
1866 llilh\t%0,%i1
1867 llill\t%0,%i1
1868 iilf\t%0,%o1
1869 lay\t%0,%a1
1870 lrl\t%0,%1
1871 lr\t%0,%1
1872 l\t%0,%1
1873 ly\t%0,%1
1874 st\t%1,%0
1875 sty\t%1,%0
1876 lder\t%0,%1
1877 ler\t%0,%1
1878 lde\t%0,%1
1879 le\t%0,%1
1880 ley\t%0,%1
1881 ste\t%1,%0
1882 stey\t%1,%0
1883 ear\t%0,%1
1884 sar\t%0,%1
1885 stam\t%1,%1,%S0
1886 strl\t%1,%0
1887 mvhi\t%0,%1
1888 lam\t%0,%0,%S1
1889 vleif\t%v0,%h1,0
1890 vlr\t%v0,%v1
1891 vlvgf\t%v0,%1,0
1892 vlgvf\t%0,%v1,0
1893 vlef\t%v0,%1,0
1894 vstef\t%v1,%0,0"
1895 [(set_attr "op_type" "RI,RI,RI,RIL,RXY,RIL,RR,RX,RXY,RX,RXY,
1896 RRE,RR,RXE,RX,RXY,RX,RXY,RRE,RRE,RS,RIL,SIL,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1897 (set_attr "type" "*,
1898 *,
1899 *,
1900 *,
1901 la,
1902 larl,
1903 lr,
1904 load,
1905 load,
1906 store,
1907 store,
1908 floadsf,
1909 floadsf,
1910 floadsf,
1911 floadsf,
1912 floadsf,
1913 fstoresf,
1914 fstoresf,
1915 *,
1916 *,
1917 *,
1918 larl,
1919 *,
1920 *,*,*,*,*,*,*")
1921 (set_attr "cpu_facility" "*,*,*,extimm,longdisp,z10,*,*,longdisp,*,longdisp,
1922 vec,*,vec,*,longdisp,*,longdisp,*,*,*,z10,z10,*,vec,vec,vec,vec,vec,vec")
1923 (set_attr "z10prop" "z10_fwd_A1,
1924 z10_fwd_E1,
1925 z10_fwd_E1,
1926 z10_fwd_A1,
1927 z10_fwd_A1,
1928 z10_fwd_A3,
1929 z10_fr_E1,
1930 z10_fwd_A3,
1931 z10_fwd_A3,
1932 z10_rec,
1933 z10_rec,
1934 *,
1935 *,
1936 *,
1937 *,
1938 *,
1939 *,
1940 *,
1941 z10_super_E1,
1942 z10_super,
1943 *,
1944 z10_rec,
1945 z10_super,
1946 *,*,*,*,*,*,*")])
1947
1948 (define_insn "*movsi_esa"
1949 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,R,!*f,!*f,!*f,!*f,!R,d,t,Q,t")
1950 (match_operand:SI 1 "general_operand" "K,d,R,d, *f, *f, R, R,*f,t,d,t,Q"))]
1951 "!TARGET_ZARCH"
1952 "@
1953 lhi\t%0,%h1
1954 lr\t%0,%1
1955 l\t%0,%1
1956 st\t%1,%0
1957 lder\t%0,%1
1958 ler\t%0,%1
1959 lde\t%0,%1
1960 le\t%0,%1
1961 ste\t%1,%0
1962 ear\t%0,%1
1963 sar\t%0,%1
1964 stam\t%1,%1,%S0
1965 lam\t%0,%0,%S1"
1966 [(set_attr "op_type" "RI,RR,RX,RX,RRE,RR,RXE,RX,RX,RRE,RRE,RS,RS")
1967 (set_attr "type" "*,lr,load,store,floadsf,floadsf,floadsf,floadsf,fstoresf,*,*,*,*")
1968 (set_attr "z10prop" "z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_rec,*,*,*,*,*,z10_super_E1,
1969 z10_super,*,*")
1970 (set_attr "cpu_facility" "*,*,*,*,vec,*,vec,*,*,*,*,*,*")
1971 ])
1972
1973 (define_peephole2
1974 [(set (match_operand:SI 0 "register_operand" "")
1975 (mem:SI (match_operand 1 "address_operand" "")))]
1976 "!FP_REG_P (operands[0])
1977 && GET_CODE (operands[1]) == SYMBOL_REF
1978 && CONSTANT_POOL_ADDRESS_P (operands[1])
1979 && get_pool_mode (operands[1]) == SImode
1980 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1981 [(set (match_dup 0) (match_dup 2))]
1982 "operands[2] = get_pool_constant (operands[1]);")
1983
1984 (define_insn "*la_31"
1985 [(set (match_operand:SI 0 "register_operand" "=d,d")
1986 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))]
1987 "!TARGET_64BIT && legitimate_la_operand_p (operands[1])"
1988 "@
1989 la\t%0,%a1
1990 lay\t%0,%a1"
1991 [(set_attr "op_type" "RX,RXY")
1992 (set_attr "type" "la")
1993 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
1994
1995 (define_peephole2
1996 [(parallel
1997 [(set (match_operand:SI 0 "register_operand" "")
1998 (match_operand:QI 1 "address_operand" ""))
1999 (clobber (reg:CC CC_REGNUM))])]
2000 "!TARGET_64BIT
2001 && preferred_la_operand_p (operands[1], const0_rtx)"
2002 [(set (match_dup 0) (match_dup 1))]
2003 "")
2004
2005 (define_peephole2
2006 [(set (match_operand:SI 0 "register_operand" "")
2007 (match_operand:SI 1 "register_operand" ""))
2008 (parallel
2009 [(set (match_dup 0)
2010 (plus:SI (match_dup 0)
2011 (match_operand:SI 2 "nonmemory_operand" "")))
2012 (clobber (reg:CC CC_REGNUM))])]
2013 "!TARGET_64BIT
2014 && !reg_overlap_mentioned_p (operands[0], operands[2])
2015 && preferred_la_operand_p (operands[1], operands[2])"
2016 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2017 "")
2018
2019 (define_insn "*la_31_and"
2020 [(set (match_operand:SI 0 "register_operand" "=d,d")
2021 (and:SI (match_operand:QI 1 "address_operand" "ZQZR,ZSZT")
2022 (const_int 2147483647)))]
2023 "!TARGET_64BIT"
2024 "@
2025 la\t%0,%a1
2026 lay\t%0,%a1"
2027 [(set_attr "op_type" "RX,RXY")
2028 (set_attr "type" "la")
2029 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2030
2031 (define_insn_and_split "*la_31_and_cc"
2032 [(set (match_operand:SI 0 "register_operand" "=d")
2033 (and:SI (match_operand:QI 1 "address_operand" "p")
2034 (const_int 2147483647)))
2035 (clobber (reg:CC CC_REGNUM))]
2036 "!TARGET_64BIT"
2037 "#"
2038 "&& reload_completed"
2039 [(set (match_dup 0)
2040 (and:SI (match_dup 1) (const_int 2147483647)))]
2041 ""
2042 [(set_attr "op_type" "RX")
2043 (set_attr "type" "la")])
2044
2045 (define_insn "force_la_31"
2046 [(set (match_operand:SI 0 "register_operand" "=d,d")
2047 (match_operand:QI 1 "address_operand" "ZQZR,ZSZT"))
2048 (use (const_int 0))]
2049 "!TARGET_64BIT"
2050 "@
2051 la\t%0,%a1
2052 lay\t%0,%a1"
2053 [(set_attr "op_type" "RX")
2054 (set_attr "type" "la")
2055 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2056
2057 ;
2058 ; movhi instruction pattern(s).
2059 ;
2060
2061 (define_expand "movhi"
2062 [(set (match_operand:HI 0 "nonimmediate_operand" "")
2063 (match_operand:HI 1 "general_operand" ""))]
2064 ""
2065 {
2066 /* Make it explicit that loading a register from memory
2067 always sign-extends (at least) to SImode. */
2068 if (optimize && can_create_pseudo_p ()
2069 && register_operand (operands[0], VOIDmode)
2070 && GET_CODE (operands[1]) == MEM)
2071 {
2072 rtx tmp = gen_reg_rtx (SImode);
2073 rtx ext = gen_rtx_SIGN_EXTEND (SImode, operands[1]);
2074 emit_insn (gen_rtx_SET (tmp, ext));
2075 operands[1] = gen_lowpart (HImode, tmp);
2076 }
2077 })
2078
2079 (define_insn "*movhi"
2080 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,d,R,T,b,Q,v,v,v,d, v,QR")
2081 (match_operand:HI 1 "general_operand" " d,n,R,T,b,d,d,d,K,K,v,d,v,QR, v"))]
2082 ""
2083 "@
2084 lr\t%0,%1
2085 lhi\t%0,%h1
2086 lh\t%0,%1
2087 lhy\t%0,%1
2088 lhrl\t%0,%1
2089 sth\t%1,%0
2090 sthy\t%1,%0
2091 sthrl\t%1,%0
2092 mvhhi\t%0,%1
2093 vleih\t%v0,%h1,0
2094 vlr\t%v0,%v1
2095 vlvgh\t%v0,%1,0
2096 vlgvh\t%0,%v1,0
2097 vleh\t%v0,%1,0
2098 vsteh\t%v1,%0,0"
2099 [(set_attr "op_type" "RR,RI,RX,RXY,RIL,RX,RXY,RIL,SIL,VRI,VRR,VRS,VRS,VRX,VRX")
2100 (set_attr "type" "lr,*,*,*,larl,store,store,store,*,*,*,*,*,*,*")
2101 (set_attr "cpu_facility" "*,*,*,*,z10,*,*,z10,z10,vec,vec,vec,vec,vec,vec")
2102 (set_attr "z10prop" "z10_fr_E1,
2103 z10_fwd_A1,
2104 z10_super_E1,
2105 z10_super_E1,
2106 z10_super_E1,
2107 z10_rec,
2108 z10_rec,
2109 z10_rec,
2110 z10_super,*,*,*,*,*,*")])
2111
2112 (define_peephole2
2113 [(set (match_operand:HI 0 "register_operand" "")
2114 (mem:HI (match_operand 1 "address_operand" "")))]
2115 "GET_CODE (operands[1]) == SYMBOL_REF
2116 && CONSTANT_POOL_ADDRESS_P (operands[1])
2117 && get_pool_mode (operands[1]) == HImode
2118 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2119 [(set (match_dup 0) (match_dup 2))]
2120 "operands[2] = get_pool_constant (operands[1]);")
2121
2122 ;
2123 ; movqi instruction pattern(s).
2124 ;
2125
2126 (define_expand "movqi"
2127 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2128 (match_operand:QI 1 "general_operand" ""))]
2129 ""
2130 {
2131 /* On z/Architecture, zero-extending from memory to register
2132 is just as fast as a QImode load. */
2133 if (TARGET_ZARCH && optimize && can_create_pseudo_p ()
2134 && register_operand (operands[0], VOIDmode)
2135 && GET_CODE (operands[1]) == MEM)
2136 {
2137 rtx tmp = gen_reg_rtx (DImode);
2138 rtx ext = gen_rtx_ZERO_EXTEND (DImode, operands[1]);
2139 emit_insn (gen_rtx_SET (tmp, ext));
2140 operands[1] = gen_lowpart (QImode, tmp);
2141 }
2142 })
2143
2144 (define_insn "*movqi"
2145 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,T,Q,S,?Q,v,v,v,d, v,QR")
2146 (match_operand:QI 1 "general_operand" " d,n,R,T,d,d,n,n,?Q,K,v,d,v,QR, v"))]
2147 ""
2148 "@
2149 lr\t%0,%1
2150 lhi\t%0,%b1
2151 ic\t%0,%1
2152 icy\t%0,%1
2153 stc\t%1,%0
2154 stcy\t%1,%0
2155 mvi\t%S0,%b1
2156 mviy\t%S0,%b1
2157 #
2158 vleib\t%v0,%b1,0
2159 vlr\t%v0,%v1
2160 vlvgb\t%v0,%1,0
2161 vlgvb\t%0,%v1,0
2162 vleb\t%v0,%1,0
2163 vsteb\t%v1,%0,0"
2164 [(set_attr "op_type" "RR,RI,RX,RXY,RX,RXY,SI,SIY,SS,VRI,VRR,VRS,VRS,VRX,VRX")
2165 (set_attr "type" "lr,*,*,*,store,store,store,store,*,*,*,*,*,*,*")
2166 (set_attr "cpu_facility" "*,*,*,*,*,*,*,*,*,vec,vec,vec,vec,vec,vec")
2167 (set_attr "z10prop" "z10_fr_E1,
2168 z10_fwd_A1,
2169 z10_super_E1,
2170 z10_super_E1,
2171 z10_rec,
2172 z10_rec,
2173 z10_super,
2174 z10_super,
2175 *,*,*,*,*,*,*")])
2176
2177 (define_peephole2
2178 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2179 (mem:QI (match_operand 1 "address_operand" "")))]
2180 "GET_CODE (operands[1]) == SYMBOL_REF
2181 && CONSTANT_POOL_ADDRESS_P (operands[1])
2182 && get_pool_mode (operands[1]) == QImode
2183 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2184 [(set (match_dup 0) (match_dup 2))]
2185 "operands[2] = get_pool_constant (operands[1]);")
2186
2187 ;
2188 ; movstrictqi instruction pattern(s).
2189 ;
2190
2191 (define_insn "*movstrictqi"
2192 [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d,d"))
2193 (match_operand:QI 1 "memory_operand" "R,T"))]
2194 ""
2195 "@
2196 ic\t%0,%1
2197 icy\t%0,%1"
2198 [(set_attr "op_type" "RX,RXY")
2199 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2200
2201 ;
2202 ; movstricthi instruction pattern(s).
2203 ;
2204
2205 (define_insn "*movstricthi"
2206 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d,d"))
2207 (match_operand:HI 1 "memory_operand" "Q,S"))
2208 (clobber (reg:CC CC_REGNUM))]
2209 ""
2210 "@
2211 icm\t%0,3,%S1
2212 icmy\t%0,3,%S1"
2213 [(set_attr "op_type" "RS,RSY")
2214 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2215
2216 ;
2217 ; movstrictsi instruction pattern(s).
2218 ;
2219
2220 (define_insn "movstrictsi"
2221 [(set (strict_low_part (match_operand:SI 0 "register_operand" "+d,d,d,d"))
2222 (match_operand:SI 1 "general_operand" "d,R,T,t"))]
2223 "TARGET_ZARCH"
2224 "@
2225 lr\t%0,%1
2226 l\t%0,%1
2227 ly\t%0,%1
2228 ear\t%0,%1"
2229 [(set_attr "op_type" "RR,RX,RXY,RRE")
2230 (set_attr "type" "lr,load,load,*")
2231 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_super_E1")])
2232
2233 ;
2234 ; mov(tf|td) instruction pattern(s).
2235 ;
2236
2237 (define_expand "mov<mode>"
2238 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2239 (match_operand:TD_TF 1 "general_operand" ""))]
2240 ""
2241 "")
2242
2243 (define_insn "*mov<mode>_64"
2244 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o, d,QS, d,o")
2245 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,QS, d,dRT,d"))]
2246 "TARGET_ZARCH"
2247 "@
2248 lzxr\t%0
2249 lxr\t%0,%1
2250 #
2251 #
2252 lmg\t%0,%N0,%S1
2253 stmg\t%1,%N1,%S0
2254 #
2255 #"
2256 [(set_attr "op_type" "RRE,RRE,*,*,RSY,RSY,*,*")
2257 (set_attr "type" "fsimptf,fsimptf,*,*,lm,stm,*,*")
2258 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*")])
2259
2260 (define_insn "*mov<mode>_31"
2261 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o")
2262 (match_operand:TD_TF 1 "general_operand" " G,f,o,f"))]
2263 "!TARGET_ZARCH"
2264 "@
2265 lzxr\t%0
2266 lxr\t%0,%1
2267 #
2268 #"
2269 [(set_attr "op_type" "RRE,RRE,*,*")
2270 (set_attr "type" "fsimptf,fsimptf,*,*")
2271 (set_attr "cpu_facility" "z196,*,*,*")])
2272
2273 ; TFmode in GPRs splitters
2274
2275 (define_split
2276 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2277 (match_operand:TD_TF 1 "general_operand" ""))]
2278 "TARGET_ZARCH && reload_completed
2279 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2280 [(set (match_dup 2) (match_dup 4))
2281 (set (match_dup 3) (match_dup 5))]
2282 {
2283 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2284 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2285 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2286 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2287 })
2288
2289 (define_split
2290 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2291 (match_operand:TD_TF 1 "general_operand" ""))]
2292 "TARGET_ZARCH && reload_completed
2293 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2294 [(set (match_dup 2) (match_dup 4))
2295 (set (match_dup 3) (match_dup 5))]
2296 {
2297 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2298 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2299 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2300 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2301 })
2302
2303 (define_split
2304 [(set (match_operand:TD_TF 0 "register_operand" "")
2305 (match_operand:TD_TF 1 "memory_operand" ""))]
2306 "TARGET_ZARCH && reload_completed
2307 && GENERAL_REG_P (operands[0])
2308 && !s_operand (operands[1], VOIDmode)"
2309 [(set (match_dup 0) (match_dup 1))]
2310 {
2311 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2312 addr = gen_lowpart (Pmode, addr);
2313 s390_load_address (addr, XEXP (operands[1], 0));
2314 operands[1] = replace_equiv_address (operands[1], addr);
2315 })
2316
2317 ; TFmode in BFPs splitters
2318
2319 (define_split
2320 [(set (match_operand:TD_TF 0 "register_operand" "")
2321 (match_operand:TD_TF 1 "memory_operand" ""))]
2322 "reload_completed && offsettable_memref_p (operands[1])
2323 && FP_REG_P (operands[0])"
2324 [(set (match_dup 2) (match_dup 4))
2325 (set (match_dup 3) (match_dup 5))]
2326 {
2327 operands[2] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2328 <MODE>mode, 0);
2329 operands[3] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2330 <MODE>mode, 8);
2331 operands[4] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 0);
2332 operands[5] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 8);
2333 })
2334
2335 (define_split
2336 [(set (match_operand:TD_TF 0 "memory_operand" "")
2337 (match_operand:TD_TF 1 "register_operand" ""))]
2338 "reload_completed && offsettable_memref_p (operands[0])
2339 && FP_REG_P (operands[1])"
2340 [(set (match_dup 2) (match_dup 4))
2341 (set (match_dup 3) (match_dup 5))]
2342 {
2343 operands[2] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 0);
2344 operands[3] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 8);
2345 operands[4] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2346 <MODE>mode, 0);
2347 operands[5] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2348 <MODE>mode, 8);
2349 })
2350
2351 ;
2352 ; mov(df|dd) instruction pattern(s).
2353 ;
2354
2355 (define_expand "mov<mode>"
2356 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2357 (match_operand:DD_DF 1 "general_operand" ""))]
2358 ""
2359 "")
2360
2361 (define_insn "*mov<mode>_64dfp"
2362 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2363 "=f,f,f,d,f,f,R,T,d,d,d, d,b,RT,v,v,d,v,QR")
2364 (match_operand:DD_DF 1 "general_operand"
2365 " G,f,d,f,R,T,f,f,G,d,b,RT,d, d,v,d,v,QR,v"))]
2366 "TARGET_DFP"
2367 "@
2368 lzdr\t%0
2369 ldr\t%0,%1
2370 ldgr\t%0,%1
2371 lgdr\t%0,%1
2372 ld\t%0,%1
2373 ldy\t%0,%1
2374 std\t%1,%0
2375 stdy\t%1,%0
2376 lghi\t%0,0
2377 lgr\t%0,%1
2378 lgrl\t%0,%1
2379 lg\t%0,%1
2380 stgrl\t%1,%0
2381 stg\t%1,%0
2382 vlr\t%v0,%v1
2383 vlvgg\t%v0,%1,0
2384 vlgvg\t%0,%v1,0
2385 vleg\t%0,%1,0
2386 vsteg\t%1,%0,0"
2387 [(set_attr "op_type" "RRE,RR,RRE,RRE,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRS,VRS,VRX,VRX")
2388 (set_attr "type" "fsimpdf,floaddf,floaddf,floaddf,floaddf,floaddf,
2389 fstoredf,fstoredf,*,lr,load,load,store,store,*,*,*,load,store")
2390 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*,*,*")
2391 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,*,*,z10,*,z10,*,vec,vec,vec,vec,vec")])
2392
2393 (define_insn "*mov<mode>_64"
2394 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "=f,f,f,f,R,T,d,d,d, d,b,RT,v,v,QR")
2395 (match_operand:DD_DF 1 "general_operand" " G,f,R,T,f,f,G,d,b,RT,d, d,v,QR,v"))]
2396 "TARGET_ZARCH"
2397 "@
2398 lzdr\t%0
2399 ldr\t%0,%1
2400 ld\t%0,%1
2401 ldy\t%0,%1
2402 std\t%1,%0
2403 stdy\t%1,%0
2404 lghi\t%0,0
2405 lgr\t%0,%1
2406 lgrl\t%0,%1
2407 lg\t%0,%1
2408 stgrl\t%1,%0
2409 stg\t%1,%0
2410 vlr\t%v0,%v1
2411 vleg\t%v0,%1,0
2412 vsteg\t%v1,%0,0"
2413 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRX,VRX")
2414 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2415 fstore<mode>,fstore<mode>,*,lr,load,load,store,store,*,load,store")
2416 (set_attr "z10prop" "*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*")
2417 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,z10,*,z10,*,vec,vec,vec")])
2418
2419 (define_insn "*mov<mode>_31"
2420 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2421 "=f,f,f,f,R,T,d,d,Q,S, d,o")
2422 (match_operand:DD_DF 1 "general_operand"
2423 " G,f,R,T,f,f,Q,S,d,d,dPRT,d"))]
2424 "!TARGET_ZARCH"
2425 "@
2426 lzdr\t%0
2427 ldr\t%0,%1
2428 ld\t%0,%1
2429 ldy\t%0,%1
2430 std\t%1,%0
2431 stdy\t%1,%0
2432 lm\t%0,%N0,%S1
2433 lmy\t%0,%N0,%S1
2434 stm\t%1,%N1,%S0
2435 stmy\t%1,%N1,%S0
2436 #
2437 #"
2438 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RS,RSY,RS,RSY,*,*")
2439 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2440 fstore<mode>,fstore<mode>,lm,lm,stm,stm,*,*")
2441 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*,*,*,*,*")])
2442
2443 (define_split
2444 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2445 (match_operand:DD_DF 1 "general_operand" ""))]
2446 "!TARGET_ZARCH && reload_completed
2447 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2448 [(set (match_dup 2) (match_dup 4))
2449 (set (match_dup 3) (match_dup 5))]
2450 {
2451 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2452 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2453 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2454 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2455 })
2456
2457 (define_split
2458 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2459 (match_operand:DD_DF 1 "general_operand" ""))]
2460 "!TARGET_ZARCH && reload_completed
2461 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2462 [(set (match_dup 2) (match_dup 4))
2463 (set (match_dup 3) (match_dup 5))]
2464 {
2465 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2466 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2467 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2468 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2469 })
2470
2471 (define_split
2472 [(set (match_operand:DD_DF 0 "register_operand" "")
2473 (match_operand:DD_DF 1 "memory_operand" ""))]
2474 "!TARGET_ZARCH && reload_completed
2475 && !FP_REG_P (operands[0])
2476 && !s_operand (operands[1], VOIDmode)"
2477 [(set (match_dup 0) (match_dup 1))]
2478 {
2479 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2480 s390_load_address (addr, XEXP (operands[1], 0));
2481 operands[1] = replace_equiv_address (operands[1], addr);
2482 })
2483
2484 ;
2485 ; mov(sf|sd) instruction pattern(s).
2486 ;
2487
2488 (define_insn "mov<mode>"
2489 [(set (match_operand:SD_SF 0 "nonimmediate_operand"
2490 "=f,f,f,f,f,f,R,T,d,d,d,d,d,b,R,T,v,v,v,d,v,QR")
2491 (match_operand:SD_SF 1 "general_operand"
2492 " G,f,f,R,R,T,f,f,G,d,b,R,T,d,d,d,v,G,d,v,QR,v"))]
2493 ""
2494 "@
2495 lzer\t%0
2496 lder\t%0,%1
2497 ler\t%0,%1
2498 lde\t%0,%1
2499 le\t%0,%1
2500 ley\t%0,%1
2501 ste\t%1,%0
2502 stey\t%1,%0
2503 lhi\t%0,0
2504 lr\t%0,%1
2505 lrl\t%0,%1
2506 l\t%0,%1
2507 ly\t%0,%1
2508 strl\t%1,%0
2509 st\t%1,%0
2510 sty\t%1,%0
2511 vlr\t%v0,%v1
2512 vleif\t%v0,0
2513 vlvgf\t%v0,%1,0
2514 vlgvf\t%0,%v1,0
2515 vleg\t%0,%1,0
2516 vsteg\t%1,%0,0"
2517 [(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")
2518 (set_attr "type" "fsimpsf,fsimpsf,fload<mode>,fload<mode>,fload<mode>,fload<mode>,
2519 fstore<mode>,fstore<mode>,*,lr,load,load,load,store,store,store,*,*,*,*,load,store")
2520 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,z10_rec,*,*,*,*,*,*")
2521 (set_attr "cpu_facility" "z196,vec,*,vec,*,*,*,*,*,*,z10,*,*,z10,*,*,vec,vec,vec,vec,vec,vec")])
2522
2523 ;
2524 ; movcc instruction pattern
2525 ;
2526
2527 (define_insn "movcc"
2528 [(set (match_operand:CC 0 "nonimmediate_operand" "=d,c,d,d,d,R,T")
2529 (match_operand:CC 1 "nonimmediate_operand" " d,d,c,R,T,d,d"))]
2530 ""
2531 "@
2532 lr\t%0,%1
2533 tmh\t%1,12288
2534 ipm\t%0
2535 l\t%0,%1
2536 ly\t%0,%1
2537 st\t%1,%0
2538 sty\t%1,%0"
2539 [(set_attr "op_type" "RR,RI,RRE,RX,RXY,RX,RXY")
2540 (set_attr "type" "lr,*,*,load,load,store,store")
2541 (set_attr "z10prop" "z10_fr_E1,z10_super,*,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec")
2542 (set_attr "z196prop" "*,*,z196_ends,*,*,*,*")])
2543
2544 ;
2545 ; Block move (MVC) patterns.
2546 ;
2547
2548 (define_insn "*mvc"
2549 [(set (match_operand:BLK 0 "memory_operand" "=Q")
2550 (match_operand:BLK 1 "memory_operand" "Q"))
2551 (use (match_operand 2 "const_int_operand" "n"))]
2552 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
2553 "mvc\t%O0(%2,%R0),%S1"
2554 [(set_attr "op_type" "SS")])
2555
2556 ; This splitter converts a QI to QI mode copy into a BLK mode copy in
2557 ; order to have it implemented with mvc.
2558
2559 (define_split
2560 [(set (match_operand:QI 0 "memory_operand" "")
2561 (match_operand:QI 1 "memory_operand" ""))]
2562 "reload_completed"
2563 [(parallel
2564 [(set (match_dup 0) (match_dup 1))
2565 (use (const_int 1))])]
2566 {
2567 operands[0] = adjust_address (operands[0], BLKmode, 0);
2568 operands[1] = adjust_address (operands[1], BLKmode, 0);
2569 })
2570
2571
2572 (define_peephole2
2573 [(parallel
2574 [(set (match_operand:BLK 0 "memory_operand" "")
2575 (match_operand:BLK 1 "memory_operand" ""))
2576 (use (match_operand 2 "const_int_operand" ""))])
2577 (parallel
2578 [(set (match_operand:BLK 3 "memory_operand" "")
2579 (match_operand:BLK 4 "memory_operand" ""))
2580 (use (match_operand 5 "const_int_operand" ""))])]
2581 "s390_offset_p (operands[0], operands[3], operands[2])
2582 && s390_offset_p (operands[1], operands[4], operands[2])
2583 && !s390_overlap_p (operands[0], operands[1],
2584 INTVAL (operands[2]) + INTVAL (operands[5]))
2585 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
2586 [(parallel
2587 [(set (match_dup 6) (match_dup 7))
2588 (use (match_dup 8))])]
2589 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
2590 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
2591 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
2592
2593
2594 ;
2595 ; load_multiple pattern(s).
2596 ;
2597 ; ??? Due to reload problems with replacing registers inside match_parallel
2598 ; we currently support load_multiple/store_multiple only after reload.
2599 ;
2600
2601 (define_expand "load_multiple"
2602 [(match_par_dup 3 [(set (match_operand 0 "" "")
2603 (match_operand 1 "" ""))
2604 (use (match_operand 2 "" ""))])]
2605 "reload_completed"
2606 {
2607 machine_mode mode;
2608 int regno;
2609 int count;
2610 rtx from;
2611 int i, off;
2612
2613 /* Support only loading a constant number of fixed-point registers from
2614 memory and only bother with this if more than two */
2615 if (GET_CODE (operands[2]) != CONST_INT
2616 || INTVAL (operands[2]) < 2
2617 || INTVAL (operands[2]) > 16
2618 || GET_CODE (operands[1]) != MEM
2619 || GET_CODE (operands[0]) != REG
2620 || REGNO (operands[0]) >= 16)
2621 FAIL;
2622
2623 count = INTVAL (operands[2]);
2624 regno = REGNO (operands[0]);
2625 mode = GET_MODE (operands[0]);
2626 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2627 FAIL;
2628
2629 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2630 if (!can_create_pseudo_p ())
2631 {
2632 if (GET_CODE (XEXP (operands[1], 0)) == REG)
2633 {
2634 from = XEXP (operands[1], 0);
2635 off = 0;
2636 }
2637 else if (GET_CODE (XEXP (operands[1], 0)) == PLUS
2638 && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == REG
2639 && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == CONST_INT)
2640 {
2641 from = XEXP (XEXP (operands[1], 0), 0);
2642 off = INTVAL (XEXP (XEXP (operands[1], 0), 1));
2643 }
2644 else
2645 FAIL;
2646 }
2647 else
2648 {
2649 from = force_reg (Pmode, XEXP (operands[1], 0));
2650 off = 0;
2651 }
2652
2653 for (i = 0; i < count; i++)
2654 XVECEXP (operands[3], 0, i)
2655 = gen_rtx_SET (gen_rtx_REG (mode, regno + i),
2656 change_address (operands[1], mode,
2657 plus_constant (Pmode, from,
2658 off + i * GET_MODE_SIZE (mode))));
2659 })
2660
2661 (define_insn "*load_multiple_di"
2662 [(match_parallel 0 "load_multiple_operation"
2663 [(set (match_operand:DI 1 "register_operand" "=r")
2664 (match_operand:DI 2 "s_operand" "QS"))])]
2665 "reload_completed && TARGET_ZARCH"
2666 {
2667 int words = XVECLEN (operands[0], 0);
2668 operands[0] = gen_rtx_REG (DImode, REGNO (operands[1]) + words - 1);
2669 return "lmg\t%1,%0,%S2";
2670 }
2671 [(set_attr "op_type" "RSY")
2672 (set_attr "type" "lm")])
2673
2674 (define_insn "*load_multiple_si"
2675 [(match_parallel 0 "load_multiple_operation"
2676 [(set (match_operand:SI 1 "register_operand" "=r,r")
2677 (match_operand:SI 2 "s_operand" "Q,S"))])]
2678 "reload_completed"
2679 {
2680 int words = XVECLEN (operands[0], 0);
2681 operands[0] = gen_rtx_REG (SImode, REGNO (operands[1]) + words - 1);
2682 return which_alternative == 0 ? "lm\t%1,%0,%S2" : "lmy\t%1,%0,%S2";
2683 }
2684 [(set_attr "op_type" "RS,RSY")
2685 (set_attr "type" "lm")])
2686
2687 ;
2688 ; store multiple pattern(s).
2689 ;
2690
2691 (define_expand "store_multiple"
2692 [(match_par_dup 3 [(set (match_operand 0 "" "")
2693 (match_operand 1 "" ""))
2694 (use (match_operand 2 "" ""))])]
2695 "reload_completed"
2696 {
2697 machine_mode mode;
2698 int regno;
2699 int count;
2700 rtx to;
2701 int i, off;
2702
2703 /* Support only storing a constant number of fixed-point registers to
2704 memory and only bother with this if more than two. */
2705 if (GET_CODE (operands[2]) != CONST_INT
2706 || INTVAL (operands[2]) < 2
2707 || INTVAL (operands[2]) > 16
2708 || GET_CODE (operands[0]) != MEM
2709 || GET_CODE (operands[1]) != REG
2710 || REGNO (operands[1]) >= 16)
2711 FAIL;
2712
2713 count = INTVAL (operands[2]);
2714 regno = REGNO (operands[1]);
2715 mode = GET_MODE (operands[1]);
2716 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2717 FAIL;
2718
2719 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2720
2721 if (!can_create_pseudo_p ())
2722 {
2723 if (GET_CODE (XEXP (operands[0], 0)) == REG)
2724 {
2725 to = XEXP (operands[0], 0);
2726 off = 0;
2727 }
2728 else if (GET_CODE (XEXP (operands[0], 0)) == PLUS
2729 && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
2730 && GET_CODE (XEXP (XEXP (operands[0], 0), 1)) == CONST_INT)
2731 {
2732 to = XEXP (XEXP (operands[0], 0), 0);
2733 off = INTVAL (XEXP (XEXP (operands[0], 0), 1));
2734 }
2735 else
2736 FAIL;
2737 }
2738 else
2739 {
2740 to = force_reg (Pmode, XEXP (operands[0], 0));
2741 off = 0;
2742 }
2743
2744 for (i = 0; i < count; i++)
2745 XVECEXP (operands[3], 0, i)
2746 = gen_rtx_SET (change_address (operands[0], mode,
2747 plus_constant (Pmode, to,
2748 off + i * GET_MODE_SIZE (mode))),
2749 gen_rtx_REG (mode, regno + i));
2750 })
2751
2752 (define_insn "*store_multiple_di"
2753 [(match_parallel 0 "store_multiple_operation"
2754 [(set (match_operand:DI 1 "s_operand" "=QS")
2755 (match_operand:DI 2 "register_operand" "r"))])]
2756 "reload_completed && TARGET_ZARCH"
2757 {
2758 int words = XVECLEN (operands[0], 0);
2759 operands[0] = gen_rtx_REG (DImode, REGNO (operands[2]) + words - 1);
2760 return "stmg\t%2,%0,%S1";
2761 }
2762 [(set_attr "op_type" "RSY")
2763 (set_attr "type" "stm")])
2764
2765
2766 (define_insn "*store_multiple_si"
2767 [(match_parallel 0 "store_multiple_operation"
2768 [(set (match_operand:SI 1 "s_operand" "=Q,S")
2769 (match_operand:SI 2 "register_operand" "r,r"))])]
2770 "reload_completed"
2771 {
2772 int words = XVECLEN (operands[0], 0);
2773 operands[0] = gen_rtx_REG (SImode, REGNO (operands[2]) + words - 1);
2774 return which_alternative == 0 ? "stm\t%2,%0,%S1" : "stmy\t%2,%0,%S1";
2775 }
2776 [(set_attr "op_type" "RS,RSY")
2777 (set_attr "type" "stm")])
2778
2779 ;;
2780 ;; String instructions.
2781 ;;
2782
2783 (define_insn "*execute_rl"
2784 [(match_parallel 0 "execute_operation"
2785 [(unspec [(match_operand 1 "register_operand" "a")
2786 (match_operand 2 "" "")
2787 (match_operand:SI 3 "larl_operand" "X")] UNSPEC_EXECUTE)])]
2788 "TARGET_Z10 && GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2789 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2790 "exrl\t%1,%3"
2791 [(set_attr "op_type" "RIL")
2792 (set_attr "type" "cs")])
2793
2794 (define_insn "*execute"
2795 [(match_parallel 0 "execute_operation"
2796 [(unspec [(match_operand 1 "register_operand" "a")
2797 (match_operand:BLK 2 "memory_operand" "R")
2798 (match_operand 3 "" "")] UNSPEC_EXECUTE)])]
2799 "GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2800 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2801 "ex\t%1,%2"
2802 [(set_attr "op_type" "RX")
2803 (set_attr "type" "cs")])
2804
2805
2806 ;
2807 ; strlenM instruction pattern(s).
2808 ;
2809
2810 (define_expand "strlen<mode>"
2811 [(match_operand:P 0 "register_operand" "") ; result
2812 (match_operand:BLK 1 "memory_operand" "") ; input string
2813 (match_operand:SI 2 "immediate_operand" "") ; search character
2814 (match_operand:SI 3 "immediate_operand" "")] ; known alignment
2815 ""
2816 {
2817 if (!TARGET_VX || operands[2] != const0_rtx)
2818 emit_insn (gen_strlen_srst<mode> (operands[0], operands[1],
2819 operands[2], operands[3]));
2820 else
2821 s390_expand_vec_strlen (operands[0], operands[1], operands[3]);
2822
2823 DONE;
2824 })
2825
2826 (define_expand "strlen_srst<mode>"
2827 [(set (reg:SI 0) (match_operand:SI 2 "immediate_operand" ""))
2828 (parallel
2829 [(set (match_dup 4)
2830 (unspec:P [(const_int 0)
2831 (match_operand:BLK 1 "memory_operand" "")
2832 (reg:SI 0)
2833 (match_operand 3 "immediate_operand" "")] UNSPEC_SRST))
2834 (clobber (scratch:P))
2835 (clobber (reg:CC CC_REGNUM))])
2836 (parallel
2837 [(set (match_operand:P 0 "register_operand" "")
2838 (minus:P (match_dup 4) (match_dup 5)))
2839 (clobber (reg:CC CC_REGNUM))])]
2840 ""
2841 {
2842 operands[4] = gen_reg_rtx (Pmode);
2843 operands[5] = gen_reg_rtx (Pmode);
2844 emit_move_insn (operands[5], force_operand (XEXP (operands[1], 0), NULL_RTX));
2845 operands[1] = replace_equiv_address (operands[1], operands[5]);
2846 })
2847
2848 (define_insn "*strlen<mode>"
2849 [(set (match_operand:P 0 "register_operand" "=a")
2850 (unspec:P [(match_operand:P 2 "general_operand" "0")
2851 (mem:BLK (match_operand:P 3 "register_operand" "1"))
2852 (reg:SI 0)
2853 (match_operand 4 "immediate_operand" "")] UNSPEC_SRST))
2854 (clobber (match_scratch:P 1 "=a"))
2855 (clobber (reg:CC CC_REGNUM))]
2856 ""
2857 "srst\t%0,%1\;jo\t.-4"
2858 [(set_attr "length" "8")
2859 (set_attr "type" "vs")])
2860
2861 ;
2862 ; cmpstrM instruction pattern(s).
2863 ;
2864
2865 (define_expand "cmpstrsi"
2866 [(set (reg:SI 0) (const_int 0))
2867 (parallel
2868 [(clobber (match_operand 3 "" ""))
2869 (clobber (match_dup 4))
2870 (set (reg:CCU CC_REGNUM)
2871 (compare:CCU (match_operand:BLK 1 "memory_operand" "")
2872 (match_operand:BLK 2 "memory_operand" "")))
2873 (use (reg:SI 0))])
2874 (parallel
2875 [(set (match_operand:SI 0 "register_operand" "=d")
2876 (unspec:SI [(reg:CCU CC_REGNUM)] UNSPEC_STRCMPCC_TO_INT))
2877 (clobber (reg:CC CC_REGNUM))])]
2878 ""
2879 {
2880 /* As the result of CMPINT is inverted compared to what we need,
2881 we have to swap the operands. */
2882 rtx op1 = operands[2];
2883 rtx op2 = operands[1];
2884 rtx addr1 = gen_reg_rtx (Pmode);
2885 rtx addr2 = gen_reg_rtx (Pmode);
2886
2887 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
2888 emit_move_insn (addr2, force_operand (XEXP (op2, 0), NULL_RTX));
2889 operands[1] = replace_equiv_address_nv (op1, addr1);
2890 operands[2] = replace_equiv_address_nv (op2, addr2);
2891 operands[3] = addr1;
2892 operands[4] = addr2;
2893 })
2894
2895 (define_insn "*cmpstr<mode>"
2896 [(clobber (match_operand:P 0 "register_operand" "=d"))
2897 (clobber (match_operand:P 1 "register_operand" "=d"))
2898 (set (reg:CCU CC_REGNUM)
2899 (compare:CCU (mem:BLK (match_operand:P 2 "register_operand" "0"))
2900 (mem:BLK (match_operand:P 3 "register_operand" "1"))))
2901 (use (reg:SI 0))]
2902 ""
2903 "clst\t%0,%1\;jo\t.-4"
2904 [(set_attr "length" "8")
2905 (set_attr "type" "vs")])
2906
2907 ;
2908 ; movstr instruction pattern.
2909 ;
2910
2911 (define_expand "movstr"
2912 [(set (reg:SI 0) (const_int 0))
2913 (parallel
2914 [(clobber (match_dup 3))
2915 (set (match_operand:BLK 1 "memory_operand" "")
2916 (match_operand:BLK 2 "memory_operand" ""))
2917 (set (match_operand 0 "register_operand" "")
2918 (unspec [(match_dup 1)
2919 (match_dup 2)
2920 (reg:SI 0)] UNSPEC_MVST))
2921 (clobber (reg:CC CC_REGNUM))])]
2922 ""
2923 {
2924 rtx addr1 = gen_reg_rtx (Pmode);
2925 rtx addr2 = gen_reg_rtx (Pmode);
2926
2927 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
2928 emit_move_insn (addr2, force_operand (XEXP (operands[2], 0), NULL_RTX));
2929 operands[1] = replace_equiv_address_nv (operands[1], addr1);
2930 operands[2] = replace_equiv_address_nv (operands[2], addr2);
2931 operands[3] = addr2;
2932 })
2933
2934 (define_insn "*movstr"
2935 [(clobber (match_operand:P 2 "register_operand" "=d"))
2936 (set (mem:BLK (match_operand:P 1 "register_operand" "0"))
2937 (mem:BLK (match_operand:P 3 "register_operand" "2")))
2938 (set (match_operand:P 0 "register_operand" "=d")
2939 (unspec [(mem:BLK (match_dup 1))
2940 (mem:BLK (match_dup 3))
2941 (reg:SI 0)] UNSPEC_MVST))
2942 (clobber (reg:CC CC_REGNUM))]
2943 ""
2944 "mvst\t%1,%2\;jo\t.-4"
2945 [(set_attr "length" "8")
2946 (set_attr "type" "vs")])
2947
2948
2949 ;
2950 ; movmemM instruction pattern(s).
2951 ;
2952
2953 (define_expand "movmem<mode>"
2954 [(set (match_operand:BLK 0 "memory_operand" "") ; destination
2955 (match_operand:BLK 1 "memory_operand" "")) ; source
2956 (use (match_operand:GPR 2 "general_operand" "")) ; count
2957 (match_operand 3 "" "")]
2958 ""
2959 {
2960 if (s390_expand_movmem (operands[0], operands[1], operands[2]))
2961 DONE;
2962 else
2963 FAIL;
2964 })
2965
2966 ; Move a block that is up to 256 bytes in length.
2967 ; The block length is taken as (operands[2] % 256) + 1.
2968
2969 (define_expand "movmem_short"
2970 [(parallel
2971 [(set (match_operand:BLK 0 "memory_operand" "")
2972 (match_operand:BLK 1 "memory_operand" ""))
2973 (use (match_operand 2 "nonmemory_operand" ""))
2974 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2975 (clobber (match_dup 3))])]
2976 ""
2977 "operands[3] = gen_rtx_SCRATCH (Pmode);")
2978
2979 (define_insn "*movmem_short"
2980 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
2981 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q"))
2982 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
2983 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
2984 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
2985 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
2986 "#"
2987 [(set_attr "type" "cs")
2988 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
2989
2990 (define_split
2991 [(set (match_operand:BLK 0 "memory_operand" "")
2992 (match_operand:BLK 1 "memory_operand" ""))
2993 (use (match_operand 2 "const_int_operand" ""))
2994 (use (match_operand 3 "immediate_operand" ""))
2995 (clobber (scratch))]
2996 "reload_completed"
2997 [(parallel
2998 [(set (match_dup 0) (match_dup 1))
2999 (use (match_dup 2))])]
3000 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3001
3002 (define_split
3003 [(set (match_operand:BLK 0 "memory_operand" "")
3004 (match_operand:BLK 1 "memory_operand" ""))
3005 (use (match_operand 2 "register_operand" ""))
3006 (use (match_operand 3 "memory_operand" ""))
3007 (clobber (scratch))]
3008 "reload_completed"
3009 [(parallel
3010 [(unspec [(match_dup 2) (match_dup 3)
3011 (const_int 0)] UNSPEC_EXECUTE)
3012 (set (match_dup 0) (match_dup 1))
3013 (use (const_int 1))])]
3014 "")
3015
3016 (define_split
3017 [(set (match_operand:BLK 0 "memory_operand" "")
3018 (match_operand:BLK 1 "memory_operand" ""))
3019 (use (match_operand 2 "register_operand" ""))
3020 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3021 (clobber (scratch))]
3022 "TARGET_Z10 && reload_completed"
3023 [(parallel
3024 [(unspec [(match_dup 2) (const_int 0)
3025 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3026 (set (match_dup 0) (match_dup 1))
3027 (use (const_int 1))])]
3028 "operands[3] = gen_label_rtx ();")
3029
3030 (define_split
3031 [(set (match_operand:BLK 0 "memory_operand" "")
3032 (match_operand:BLK 1 "memory_operand" ""))
3033 (use (match_operand 2 "register_operand" ""))
3034 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3035 (clobber (match_operand 3 "register_operand" ""))]
3036 "reload_completed && TARGET_CPU_ZARCH"
3037 [(set (match_dup 3) (label_ref (match_dup 4)))
3038 (parallel
3039 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3040 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3041 (set (match_dup 0) (match_dup 1))
3042 (use (const_int 1))])]
3043 "operands[4] = gen_label_rtx ();")
3044
3045 ; Move a block of arbitrary length.
3046
3047 (define_expand "movmem_long"
3048 [(parallel
3049 [(clobber (match_dup 2))
3050 (clobber (match_dup 3))
3051 (set (match_operand:BLK 0 "memory_operand" "")
3052 (match_operand:BLK 1 "memory_operand" ""))
3053 (use (match_operand 2 "general_operand" ""))
3054 (use (match_dup 3))
3055 (clobber (reg:CC CC_REGNUM))])]
3056 ""
3057 {
3058 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3059 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3060 rtx reg0 = gen_reg_rtx (dreg_mode);
3061 rtx reg1 = gen_reg_rtx (dreg_mode);
3062 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3063 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3064 rtx len0 = gen_lowpart (Pmode, reg0);
3065 rtx len1 = gen_lowpart (Pmode, reg1);
3066
3067 emit_clobber (reg0);
3068 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3069 emit_move_insn (len0, operands[2]);
3070
3071 emit_clobber (reg1);
3072 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3073 emit_move_insn (len1, operands[2]);
3074
3075 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3076 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3077 operands[2] = reg0;
3078 operands[3] = reg1;
3079 })
3080
3081 (define_insn "*movmem_long"
3082 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3083 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3084 (set (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3085 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0)))
3086 (use (match_dup 2))
3087 (use (match_dup 3))
3088 (clobber (reg:CC CC_REGNUM))]
3089 "TARGET_64BIT || !TARGET_ZARCH"
3090 "mvcle\t%0,%1,0\;jo\t.-4"
3091 [(set_attr "length" "8")
3092 (set_attr "type" "vs")])
3093
3094 (define_insn "*movmem_long_31z"
3095 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3096 (clobber (match_operand:TI 1 "register_operand" "=d"))
3097 (set (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3098 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4)))
3099 (use (match_dup 2))
3100 (use (match_dup 3))
3101 (clobber (reg:CC CC_REGNUM))]
3102 "!TARGET_64BIT && TARGET_ZARCH"
3103 "mvcle\t%0,%1,0\;jo\t.-4"
3104 [(set_attr "length" "8")
3105 (set_attr "type" "vs")])
3106
3107
3108 ;
3109 ; Test data class.
3110 ;
3111
3112 (define_expand "signbit<mode>2"
3113 [(set (reg:CCZ CC_REGNUM)
3114 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3115 (match_dup 2)]
3116 UNSPEC_TDC_INSN))
3117 (set (match_operand:SI 0 "register_operand" "=d")
3118 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3119 "TARGET_HARD_FLOAT"
3120 {
3121 operands[2] = GEN_INT (S390_TDC_SIGNBIT_SET);
3122 })
3123
3124 (define_expand "isinf<mode>2"
3125 [(set (reg:CCZ CC_REGNUM)
3126 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3127 (match_dup 2)]
3128 UNSPEC_TDC_INSN))
3129 (set (match_operand:SI 0 "register_operand" "=d")
3130 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3131 "TARGET_HARD_FLOAT"
3132 {
3133 operands[2] = GEN_INT (S390_TDC_INFINITY);
3134 })
3135
3136 ; This extracts CC into a GPR properly shifted. The actual IPM
3137 ; instruction will be issued by reload. The constraint of operand 1
3138 ; forces reload to use a GPR. So reload will issue a movcc insn for
3139 ; copying CC into a GPR first.
3140 (define_insn_and_split "*cc_to_int"
3141 [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3142 (unspec:SI [(match_operand 1 "register_operand" "0")]
3143 UNSPEC_CC_TO_INT))]
3144 "operands != NULL"
3145 "#"
3146 "reload_completed"
3147 [(set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 28)))])
3148
3149 ; This insn is used to generate all variants of the Test Data Class
3150 ; instruction, namely tcxb, tcdb, and tceb. The insn's first operand
3151 ; is the register to be tested and the second one is the bit mask
3152 ; specifying the required test(s).
3153 ;
3154 ; tcxb, tcdb, tceb, tdcxt, tdcdt, tdcet
3155 (define_insn "*TDC_insn_<mode>"
3156 [(set (reg:CCZ CC_REGNUM)
3157 (unspec:CCZ [(match_operand:FP_ALL 0 "register_operand" "f")
3158 (match_operand:SI 1 "const_int_operand")] UNSPEC_TDC_INSN))]
3159 "TARGET_HARD_FLOAT"
3160 "t<_d>c<xde><bt>\t%0,%1"
3161 [(set_attr "op_type" "RXE")
3162 (set_attr "type" "fsimp<mode>")])
3163
3164
3165
3166 ;
3167 ; setmemM instruction pattern(s).
3168 ;
3169
3170 (define_expand "setmem<mode>"
3171 [(set (match_operand:BLK 0 "memory_operand" "")
3172 (match_operand:QI 2 "general_operand" ""))
3173 (use (match_operand:GPR 1 "general_operand" ""))
3174 (match_operand 3 "" "")]
3175 ""
3176 "s390_expand_setmem (operands[0], operands[1], operands[2]); DONE;")
3177
3178 ; Clear a block that is up to 256 bytes in length.
3179 ; The block length is taken as (operands[1] % 256) + 1.
3180
3181 (define_expand "clrmem_short"
3182 [(parallel
3183 [(set (match_operand:BLK 0 "memory_operand" "")
3184 (const_int 0))
3185 (use (match_operand 1 "nonmemory_operand" ""))
3186 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3187 (clobber (match_dup 2))
3188 (clobber (reg:CC CC_REGNUM))])]
3189 ""
3190 "operands[2] = gen_rtx_SCRATCH (Pmode);")
3191
3192 (define_insn "*clrmem_short"
3193 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3194 (const_int 0))
3195 (use (match_operand 1 "nonmemory_operand" "n,a,a,a"))
3196 (use (match_operand 2 "immediate_operand" "X,R,X,X"))
3197 (clobber (match_scratch:P 3 "=X,X,X,&a"))
3198 (clobber (reg:CC CC_REGNUM))]
3199 "(GET_MODE (operands[1]) == Pmode || GET_MODE (operands[1]) == VOIDmode)"
3200 "#"
3201 [(set_attr "type" "cs")
3202 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3203
3204 (define_split
3205 [(set (match_operand:BLK 0 "memory_operand" "")
3206 (const_int 0))
3207 (use (match_operand 1 "const_int_operand" ""))
3208 (use (match_operand 2 "immediate_operand" ""))
3209 (clobber (scratch))
3210 (clobber (reg:CC CC_REGNUM))]
3211 "reload_completed"
3212 [(parallel
3213 [(set (match_dup 0) (const_int 0))
3214 (use (match_dup 1))
3215 (clobber (reg:CC CC_REGNUM))])]
3216 "operands[1] = GEN_INT ((INTVAL (operands[1]) & 0xff) + 1);")
3217
3218 (define_split
3219 [(set (match_operand:BLK 0 "memory_operand" "")
3220 (const_int 0))
3221 (use (match_operand 1 "register_operand" ""))
3222 (use (match_operand 2 "memory_operand" ""))
3223 (clobber (scratch))
3224 (clobber (reg:CC CC_REGNUM))]
3225 "reload_completed"
3226 [(parallel
3227 [(unspec [(match_dup 1) (match_dup 2)
3228 (const_int 0)] UNSPEC_EXECUTE)
3229 (set (match_dup 0) (const_int 0))
3230 (use (const_int 1))
3231 (clobber (reg:CC CC_REGNUM))])]
3232 "")
3233
3234 (define_split
3235 [(set (match_operand:BLK 0 "memory_operand" "")
3236 (const_int 0))
3237 (use (match_operand 1 "register_operand" ""))
3238 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3239 (clobber (scratch))
3240 (clobber (reg:CC CC_REGNUM))]
3241 "TARGET_Z10 && reload_completed"
3242 [(parallel
3243 [(unspec [(match_dup 1) (const_int 0)
3244 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3245 (set (match_dup 0) (const_int 0))
3246 (use (const_int 1))
3247 (clobber (reg:CC CC_REGNUM))])]
3248 "operands[3] = gen_label_rtx ();")
3249
3250 (define_split
3251 [(set (match_operand:BLK 0 "memory_operand" "")
3252 (const_int 0))
3253 (use (match_operand 1 "register_operand" ""))
3254 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3255 (clobber (match_operand 2 "register_operand" ""))
3256 (clobber (reg:CC CC_REGNUM))]
3257 "reload_completed && TARGET_CPU_ZARCH"
3258 [(set (match_dup 2) (label_ref (match_dup 3)))
3259 (parallel
3260 [(unspec [(match_dup 1) (mem:BLK (match_dup 2))
3261 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3262 (set (match_dup 0) (const_int 0))
3263 (use (const_int 1))
3264 (clobber (reg:CC CC_REGNUM))])]
3265 "operands[3] = gen_label_rtx ();")
3266
3267 ; Initialize a block of arbitrary length with (operands[2] % 256).
3268
3269 (define_expand "setmem_long"
3270 [(parallel
3271 [(clobber (match_dup 1))
3272 (set (match_operand:BLK 0 "memory_operand" "")
3273 (match_operand 2 "shift_count_or_setmem_operand" ""))
3274 (use (match_operand 1 "general_operand" ""))
3275 (use (match_dup 3))
3276 (clobber (reg:CC CC_REGNUM))])]
3277 ""
3278 {
3279 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3280 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3281 rtx reg0 = gen_reg_rtx (dreg_mode);
3282 rtx reg1 = gen_reg_rtx (dreg_mode);
3283 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3284 rtx len0 = gen_lowpart (Pmode, reg0);
3285
3286 emit_clobber (reg0);
3287 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3288 emit_move_insn (len0, operands[1]);
3289
3290 emit_move_insn (reg1, const0_rtx);
3291
3292 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3293 operands[1] = reg0;
3294 operands[3] = reg1;
3295 })
3296
3297 (define_insn "*setmem_long"
3298 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3299 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3300 (match_operand 2 "shift_count_or_setmem_operand" "Y"))
3301 (use (match_dup 3))
3302 (use (match_operand:<DBL> 1 "register_operand" "d"))
3303 (clobber (reg:CC CC_REGNUM))]
3304 "TARGET_64BIT || !TARGET_ZARCH"
3305 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3306 [(set_attr "length" "8")
3307 (set_attr "type" "vs")])
3308
3309 (define_insn "*setmem_long_and"
3310 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3311 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3312 (and (match_operand 2 "shift_count_or_setmem_operand" "Y")
3313 (match_operand 4 "const_int_operand" "n")))
3314 (use (match_dup 3))
3315 (use (match_operand:<DBL> 1 "register_operand" "d"))
3316 (clobber (reg:CC CC_REGNUM))]
3317 "(TARGET_64BIT || !TARGET_ZARCH) &&
3318 (INTVAL (operands[4]) & 255) == 255"
3319 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3320 [(set_attr "length" "8")
3321 (set_attr "type" "vs")])
3322
3323 (define_insn "*setmem_long_31z"
3324 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3325 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3326 (match_operand 2 "shift_count_or_setmem_operand" "Y"))
3327 (use (match_dup 3))
3328 (use (match_operand:TI 1 "register_operand" "d"))
3329 (clobber (reg:CC CC_REGNUM))]
3330 "!TARGET_64BIT && TARGET_ZARCH"
3331 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3332 [(set_attr "length" "8")
3333 (set_attr "type" "vs")])
3334
3335 ;
3336 ; cmpmemM instruction pattern(s).
3337 ;
3338
3339 (define_expand "cmpmemsi"
3340 [(set (match_operand:SI 0 "register_operand" "")
3341 (compare:SI (match_operand:BLK 1 "memory_operand" "")
3342 (match_operand:BLK 2 "memory_operand" "") ) )
3343 (use (match_operand:SI 3 "general_operand" ""))
3344 (use (match_operand:SI 4 "" ""))]
3345 ""
3346 {
3347 if (s390_expand_cmpmem (operands[0], operands[1],
3348 operands[2], operands[3]))
3349 DONE;
3350 else
3351 FAIL;
3352 })
3353
3354 ; Compare a block that is up to 256 bytes in length.
3355 ; The block length is taken as (operands[2] % 256) + 1.
3356
3357 (define_expand "cmpmem_short"
3358 [(parallel
3359 [(set (reg:CCU CC_REGNUM)
3360 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3361 (match_operand:BLK 1 "memory_operand" "")))
3362 (use (match_operand 2 "nonmemory_operand" ""))
3363 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3364 (clobber (match_dup 3))])]
3365 ""
3366 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3367
3368 (define_insn "*cmpmem_short"
3369 [(set (reg:CCU CC_REGNUM)
3370 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
3371 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
3372 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3373 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3374 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3375 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3376 "#"
3377 [(set_attr "type" "cs")
3378 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3379
3380 (define_split
3381 [(set (reg:CCU CC_REGNUM)
3382 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3383 (match_operand:BLK 1 "memory_operand" "")))
3384 (use (match_operand 2 "const_int_operand" ""))
3385 (use (match_operand 3 "immediate_operand" ""))
3386 (clobber (scratch))]
3387 "reload_completed"
3388 [(parallel
3389 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3390 (use (match_dup 2))])]
3391 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3392
3393 (define_split
3394 [(set (reg:CCU CC_REGNUM)
3395 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3396 (match_operand:BLK 1 "memory_operand" "")))
3397 (use (match_operand 2 "register_operand" ""))
3398 (use (match_operand 3 "memory_operand" ""))
3399 (clobber (scratch))]
3400 "reload_completed"
3401 [(parallel
3402 [(unspec [(match_dup 2) (match_dup 3)
3403 (const_int 0)] UNSPEC_EXECUTE)
3404 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3405 (use (const_int 1))])]
3406 "")
3407
3408 (define_split
3409 [(set (reg:CCU CC_REGNUM)
3410 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3411 (match_operand:BLK 1 "memory_operand" "")))
3412 (use (match_operand 2 "register_operand" ""))
3413 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3414 (clobber (scratch))]
3415 "TARGET_Z10 && reload_completed"
3416 [(parallel
3417 [(unspec [(match_dup 2) (const_int 0)
3418 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3419 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3420 (use (const_int 1))])]
3421 "operands[4] = gen_label_rtx ();")
3422
3423 (define_split
3424 [(set (reg:CCU CC_REGNUM)
3425 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3426 (match_operand:BLK 1 "memory_operand" "")))
3427 (use (match_operand 2 "register_operand" ""))
3428 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3429 (clobber (match_operand 3 "register_operand" ""))]
3430 "reload_completed && TARGET_CPU_ZARCH"
3431 [(set (match_dup 3) (label_ref (match_dup 4)))
3432 (parallel
3433 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3434 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3435 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3436 (use (const_int 1))])]
3437 "operands[4] = gen_label_rtx ();")
3438
3439 ; Compare a block of arbitrary length.
3440
3441 (define_expand "cmpmem_long"
3442 [(parallel
3443 [(clobber (match_dup 2))
3444 (clobber (match_dup 3))
3445 (set (reg:CCU CC_REGNUM)
3446 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3447 (match_operand:BLK 1 "memory_operand" "")))
3448 (use (match_operand 2 "general_operand" ""))
3449 (use (match_dup 3))])]
3450 ""
3451 {
3452 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3453 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3454 rtx reg0 = gen_reg_rtx (dreg_mode);
3455 rtx reg1 = gen_reg_rtx (dreg_mode);
3456 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3457 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3458 rtx len0 = gen_lowpart (Pmode, reg0);
3459 rtx len1 = gen_lowpart (Pmode, reg1);
3460
3461 emit_clobber (reg0);
3462 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3463 emit_move_insn (len0, operands[2]);
3464
3465 emit_clobber (reg1);
3466 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3467 emit_move_insn (len1, operands[2]);
3468
3469 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3470 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3471 operands[2] = reg0;
3472 operands[3] = reg1;
3473 })
3474
3475 (define_insn "*cmpmem_long"
3476 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3477 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3478 (set (reg:CCU CC_REGNUM)
3479 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3480 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
3481 (use (match_dup 2))
3482 (use (match_dup 3))]
3483 "TARGET_64BIT || !TARGET_ZARCH"
3484 "clcle\t%0,%1,0\;jo\t.-4"
3485 [(set_attr "length" "8")
3486 (set_attr "type" "vs")])
3487
3488 (define_insn "*cmpmem_long_31z"
3489 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3490 (clobber (match_operand:TI 1 "register_operand" "=d"))
3491 (set (reg:CCU CC_REGNUM)
3492 (compare:CCU (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3493 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4))))
3494 (use (match_dup 2))
3495 (use (match_dup 3))]
3496 "!TARGET_64BIT && TARGET_ZARCH"
3497 "clcle\t%0,%1,0\;jo\t.-4"
3498 [(set_attr "op_type" "NN")
3499 (set_attr "type" "vs")
3500 (set_attr "length" "8")])
3501
3502 ; Convert CCUmode condition code to integer.
3503 ; Result is zero if EQ, positive if LTU, negative if GTU.
3504
3505 (define_insn_and_split "cmpint"
3506 [(set (match_operand:SI 0 "register_operand" "=d")
3507 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3508 UNSPEC_STRCMPCC_TO_INT))
3509 (clobber (reg:CC CC_REGNUM))]
3510 ""
3511 "#"
3512 "reload_completed"
3513 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3514 (parallel
3515 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
3516 (clobber (reg:CC CC_REGNUM))])])
3517
3518 (define_insn_and_split "*cmpint_cc"
3519 [(set (reg CC_REGNUM)
3520 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3521 UNSPEC_STRCMPCC_TO_INT)
3522 (const_int 0)))
3523 (set (match_operand:SI 0 "register_operand" "=d")
3524 (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT))]
3525 "s390_match_ccmode (insn, CCSmode)"
3526 "#"
3527 "&& reload_completed"
3528 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3529 (parallel
3530 [(set (match_dup 2) (match_dup 3))
3531 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
3532 {
3533 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
3534 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3535 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3536 })
3537
3538 (define_insn_and_split "*cmpint_sign"
3539 [(set (match_operand:DI 0 "register_operand" "=d")
3540 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3541 UNSPEC_STRCMPCC_TO_INT)))
3542 (clobber (reg:CC CC_REGNUM))]
3543 "TARGET_ZARCH"
3544 "#"
3545 "&& reload_completed"
3546 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3547 (parallel
3548 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
3549 (clobber (reg:CC CC_REGNUM))])])
3550
3551 (define_insn_and_split "*cmpint_sign_cc"
3552 [(set (reg CC_REGNUM)
3553 (compare (ashiftrt:DI (ashift:DI (subreg:DI
3554 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3555 UNSPEC_STRCMPCC_TO_INT) 0)
3556 (const_int 32)) (const_int 32))
3557 (const_int 0)))
3558 (set (match_operand:DI 0 "register_operand" "=d")
3559 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT)))]
3560 "s390_match_ccmode (insn, CCSmode) && TARGET_ZARCH"
3561 "#"
3562 "&& reload_completed"
3563 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3564 (parallel
3565 [(set (match_dup 2) (match_dup 3))
3566 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
3567 {
3568 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
3569 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3570 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3571 })
3572
3573
3574 ;;
3575 ;;- Conversion instructions.
3576 ;;
3577
3578 (define_insn "*sethighpartsi"
3579 [(set (match_operand:SI 0 "register_operand" "=d,d")
3580 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
3581 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3582 (clobber (reg:CC CC_REGNUM))]
3583 ""
3584 "@
3585 icm\t%0,%2,%S1
3586 icmy\t%0,%2,%S1"
3587 [(set_attr "op_type" "RS,RSY")
3588 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3589
3590 (define_insn "*sethighpartdi_64"
3591 [(set (match_operand:DI 0 "register_operand" "=d")
3592 (unspec:DI [(match_operand:BLK 1 "s_operand" "QS")
3593 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
3594 (clobber (reg:CC CC_REGNUM))]
3595 "TARGET_ZARCH"
3596 "icmh\t%0,%2,%S1"
3597 [(set_attr "op_type" "RSY")
3598 (set_attr "z10prop" "z10_super")])
3599
3600 (define_insn "*sethighpartdi_31"
3601 [(set (match_operand:DI 0 "register_operand" "=d,d")
3602 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
3603 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3604 (clobber (reg:CC CC_REGNUM))]
3605 "!TARGET_ZARCH"
3606 "@
3607 icm\t%0,%2,%S1
3608 icmy\t%0,%2,%S1"
3609 [(set_attr "op_type" "RS,RSY")
3610 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3611
3612 ;
3613 ; extv instruction patterns
3614 ;
3615
3616 ; FIXME: This expander needs to be converted from DI to GPR as well
3617 ; after resolving some issues with it.
3618
3619 (define_expand "extzv"
3620 [(parallel
3621 [(set (match_operand:DI 0 "register_operand" "=d")
3622 (zero_extract:DI
3623 (match_operand:DI 1 "register_operand" "d")
3624 (match_operand 2 "const_int_operand" "") ; size
3625 (match_operand 3 "const_int_operand" ""))) ; start
3626 (clobber (reg:CC CC_REGNUM))])]
3627 "TARGET_Z10"
3628 {
3629 /* Starting with zEC12 there is risbgn not clobbering CC. */
3630 if (TARGET_ZEC12)
3631 {
3632 emit_move_insn (operands[0],
3633 gen_rtx_ZERO_EXTRACT (DImode,
3634 operands[1],
3635 operands[2],
3636 operands[3]));
3637 DONE;
3638 }
3639 })
3640
3641 (define_insn "*extzv<mode>_zEC12"
3642 [(set (match_operand:GPR 0 "register_operand" "=d")
3643 (zero_extract:GPR
3644 (match_operand:GPR 1 "register_operand" "d")
3645 (match_operand 2 "const_int_operand" "") ; size
3646 (match_operand 3 "const_int_operand" "")))] ; start]
3647 "TARGET_ZEC12"
3648 "risbgn\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3649 [(set_attr "op_type" "RIE")])
3650
3651 (define_insn "*extzv<mode>_z10"
3652 [(set (match_operand:GPR 0 "register_operand" "=d")
3653 (zero_extract:GPR
3654 (match_operand:GPR 1 "register_operand" "d")
3655 (match_operand 2 "const_int_operand" "") ; size
3656 (match_operand 3 "const_int_operand" ""))) ; start
3657 (clobber (reg:CC CC_REGNUM))]
3658 "TARGET_Z10"
3659 "risbg\t%0,%1,64-%2,128+63,<bitsize>+%3+%2" ; dst, src, start, end, shift
3660 [(set_attr "op_type" "RIE")
3661 (set_attr "z10prop" "z10_super_E1")])
3662
3663 (define_insn_and_split "*pre_z10_extzv<mode>"
3664 [(set (match_operand:GPR 0 "register_operand" "=d")
3665 (zero_extract:GPR (match_operand:QI 1 "s_operand" "QS")
3666 (match_operand 2 "nonzero_shift_count_operand" "")
3667 (const_int 0)))
3668 (clobber (reg:CC CC_REGNUM))]
3669 "!TARGET_Z10"
3670 "#"
3671 "&& reload_completed"
3672 [(parallel
3673 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3674 (clobber (reg:CC CC_REGNUM))])
3675 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3676 {
3677 int bitsize = INTVAL (operands[2]);
3678 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3679 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3680
3681 operands[1] = adjust_address (operands[1], BLKmode, 0);
3682 set_mem_size (operands[1], size);
3683 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3684 operands[3] = GEN_INT (mask);
3685 })
3686
3687 (define_insn_and_split "*pre_z10_extv<mode>"
3688 [(set (match_operand:GPR 0 "register_operand" "=d")
3689 (sign_extract:GPR (match_operand:QI 1 "s_operand" "QS")
3690 (match_operand 2 "nonzero_shift_count_operand" "")
3691 (const_int 0)))
3692 (clobber (reg:CC CC_REGNUM))]
3693 ""
3694 "#"
3695 "&& reload_completed"
3696 [(parallel
3697 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3698 (clobber (reg:CC CC_REGNUM))])
3699 (parallel
3700 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3701 (clobber (reg:CC CC_REGNUM))])]
3702 {
3703 int bitsize = INTVAL (operands[2]);
3704 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3705 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3706
3707 operands[1] = adjust_address (operands[1], BLKmode, 0);
3708 set_mem_size (operands[1], size);
3709 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3710 operands[3] = GEN_INT (mask);
3711 })
3712
3713 ;
3714 ; insv instruction patterns
3715 ;
3716
3717 (define_expand "insv"
3718 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3719 (match_operand 1 "const_int_operand" "")
3720 (match_operand 2 "const_int_operand" ""))
3721 (match_operand 3 "general_operand" ""))]
3722 ""
3723 {
3724 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3725 DONE;
3726 FAIL;
3727 })
3728
3729
3730 ; The normal RTL expansion will never generate a zero_extract where
3731 ; the location operand isn't word mode. However, we do this in the
3732 ; back-end when generating atomic operations. See s390_two_part_insv.
3733 (define_insn "*insv<mode>_zEC12"
3734 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3735 (match_operand 1 "const_int_operand" "I") ; size
3736 (match_operand 2 "const_int_operand" "I")) ; pos
3737 (match_operand:GPR 3 "nonimmediate_operand" "d"))]
3738 "TARGET_ZEC12
3739 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3740 "risbgn\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3741 [(set_attr "op_type" "RIE")])
3742
3743 (define_insn "*insv<mode>_z10"
3744 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3745 (match_operand 1 "const_int_operand" "I") ; size
3746 (match_operand 2 "const_int_operand" "I")) ; pos
3747 (match_operand:GPR 3 "nonimmediate_operand" "d"))
3748 (clobber (reg:CC CC_REGNUM))]
3749 "TARGET_Z10
3750 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3751 "risbg\t%0,%3,64-<bitsize>+%2,64-<bitsize>+%2+%1-1,<bitsize>-%2-%1"
3752 [(set_attr "op_type" "RIE")
3753 (set_attr "z10prop" "z10_super_E1")])
3754
3755 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3756 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3757 (define_insn "*insv<mode>_zEC12_noshift"
3758 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3759 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3760 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3761 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3762 (match_operand:GPR 4 "const_int_operand" ""))))]
3763 "TARGET_ZEC12 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3764 "risbgn\t%0,%1,%<bfstart>2,%<bfend>2,0"
3765 [(set_attr "op_type" "RIE")])
3766
3767 (define_insn "*insv<mode>_z10_noshift"
3768 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3769 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3770 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3771 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3772 (match_operand:GPR 4 "const_int_operand" ""))))
3773 (clobber (reg:CC CC_REGNUM))]
3774 "TARGET_Z10 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3775 "risbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3776 [(set_attr "op_type" "RIE")
3777 (set_attr "z10prop" "z10_super_E1")])
3778
3779 (define_insn "*r<noxa>sbg_<mode>_noshift"
3780 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3781 (IXOR:GPR
3782 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3783 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3784 (match_operand:GPR 3 "nonimmediate_operand" "0")))
3785 (clobber (reg:CC CC_REGNUM))]
3786 "TARGET_Z10"
3787 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
3788 [(set_attr "op_type" "RIE")])
3789
3790 (define_insn "*r<noxa>sbg_di_rotl"
3791 [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
3792 (IXOR:DI
3793 (and:DI
3794 (rotate:DI
3795 (match_operand:DI 1 "nonimmediate_operand" "d")
3796 (match_operand:DI 3 "const_int_operand" ""))
3797 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3798 (match_operand:DI 4 "nonimmediate_operand" "0")))
3799 (clobber (reg:CC CC_REGNUM))]
3800 "TARGET_Z10"
3801 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%b3"
3802 [(set_attr "op_type" "RIE")])
3803
3804 (define_insn "*r<noxa>sbg_<mode>_srl"
3805 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3806 (IXOR:GPR
3807 (and:GPR
3808 (lshiftrt:GPR
3809 (match_operand:GPR 1 "nonimmediate_operand" "d")
3810 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
3811 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3812 (match_operand:GPR 4 "nonimmediate_operand" "0")))
3813 (clobber (reg:CC CC_REGNUM))]
3814 "TARGET_Z10
3815 && s390_extzv_shift_ok (<bitsize>, 64 - INTVAL (operands[3]),
3816 INTVAL (operands[2]))"
3817 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,64-%3"
3818 [(set_attr "op_type" "RIE")])
3819
3820 (define_insn "*r<noxa>sbg_<mode>_sll"
3821 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3822 (IXOR:GPR
3823 (and:GPR
3824 (ashift:GPR
3825 (match_operand:GPR 1 "nonimmediate_operand" "d")
3826 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
3827 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3828 (match_operand:GPR 4 "nonimmediate_operand" "0")))
3829 (clobber (reg:CC CC_REGNUM))]
3830 "TARGET_Z10
3831 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[3]),
3832 INTVAL (operands[2]))"
3833 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%3"
3834 [(set_attr "op_type" "RIE")])
3835
3836 ;; These two are generated by combine for s.bf &= val.
3837 ;; ??? For bitfields smaller than 32-bits, we wind up with SImode
3838 ;; shifts and ands, which results in some truly awful patterns
3839 ;; including subregs of operations. Rather unnecessisarily, IMO.
3840 ;; Instead of
3841 ;;
3842 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
3843 ;; (const_int 24 [0x18])
3844 ;; (const_int 0 [0]))
3845 ;; (subreg:DI (and:SI (subreg:SI (lshiftrt:DI (reg/v:DI 50 [ s ])
3846 ;; (const_int 40 [0x28])) 4)
3847 ;; (reg:SI 4 %r4 [ y+4 ])) 0))
3848 ;;
3849 ;; we should instead generate
3850 ;;
3851 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
3852 ;; (const_int 24 [0x18])
3853 ;; (const_int 0 [0]))
3854 ;; (and:DI (lshiftrt:DI (reg/v:DI 50 [ s ])
3855 ;; (const_int 40 [0x28]))
3856 ;; (subreg:DI (reg:SI 4 %r4 [ y+4 ]) 0)))
3857 ;;
3858 ;; by noticing that we can push down the outer paradoxical subreg
3859 ;; into the operation.
3860
3861 (define_insn "*insv_rnsbg_noshift"
3862 [(set (zero_extract:DI
3863 (match_operand:DI 0 "nonimmediate_operand" "+d")
3864 (match_operand 1 "const_int_operand" "")
3865 (match_operand 2 "const_int_operand" ""))
3866 (and:DI
3867 (match_dup 0)
3868 (match_operand:DI 3 "nonimmediate_operand" "d")))
3869 (clobber (reg:CC CC_REGNUM))]
3870 "TARGET_Z10
3871 && INTVAL (operands[1]) + INTVAL (operands[2]) == 64"
3872 "rnsbg\t%0,%3,%2,63,0"
3873 [(set_attr "op_type" "RIE")])
3874
3875 (define_insn "*insv_rnsbg_srl"
3876 [(set (zero_extract:DI
3877 (match_operand:DI 0 "nonimmediate_operand" "+d")
3878 (match_operand 1 "const_int_operand" "")
3879 (match_operand 2 "const_int_operand" ""))
3880 (and:DI
3881 (lshiftrt:DI
3882 (match_dup 0)
3883 (match_operand 3 "const_int_operand" ""))
3884 (match_operand:DI 4 "nonimmediate_operand" "d")))
3885 (clobber (reg:CC CC_REGNUM))]
3886 "TARGET_Z10
3887 && INTVAL (operands[3]) == 64 - INTVAL (operands[1]) - INTVAL (operands[2])"
3888 "rnsbg\t%0,%4,%2,%2+%1-1,%3"
3889 [(set_attr "op_type" "RIE")])
3890
3891 (define_insn "*insv<mode>_mem_reg"
3892 [(set (zero_extract:W (match_operand:QI 0 "memory_operand" "+Q,S")
3893 (match_operand 1 "const_int_operand" "n,n")
3894 (const_int 0))
3895 (match_operand:W 2 "register_operand" "d,d"))]
3896 "INTVAL (operands[1]) > 0
3897 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
3898 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
3899 {
3900 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
3901
3902 operands[1] = GEN_INT ((1ul << size) - 1);
3903 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
3904 : "stcmy\t%2,%1,%S0";
3905 }
3906 [(set_attr "op_type" "RS,RSY")
3907 (set_attr "z10prop" "z10_super,z10_super")])
3908
3909 (define_insn "*insvdi_mem_reghigh"
3910 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+QS")
3911 (match_operand 1 "const_int_operand" "n")
3912 (const_int 0))
3913 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
3914 (const_int 32)))]
3915 "TARGET_ZARCH
3916 && INTVAL (operands[1]) > 0
3917 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
3918 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
3919 {
3920 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
3921
3922 operands[1] = GEN_INT ((1ul << size) - 1);
3923 return "stcmh\t%2,%1,%S0";
3924 }
3925 [(set_attr "op_type" "RSY")
3926 (set_attr "z10prop" "z10_super")])
3927
3928 (define_insn "*insvdi_reg_imm"
3929 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
3930 (const_int 16)
3931 (match_operand 1 "const_int_operand" "n"))
3932 (match_operand:DI 2 "const_int_operand" "n"))]
3933 "TARGET_ZARCH
3934 && INTVAL (operands[1]) >= 0
3935 && INTVAL (operands[1]) < BITS_PER_WORD
3936 && INTVAL (operands[1]) % 16 == 0"
3937 {
3938 switch (BITS_PER_WORD - INTVAL (operands[1]))
3939 {
3940 case 64: return "iihh\t%0,%x2"; break;
3941 case 48: return "iihl\t%0,%x2"; break;
3942 case 32: return "iilh\t%0,%x2"; break;
3943 case 16: return "iill\t%0,%x2"; break;
3944 default: gcc_unreachable();
3945 }
3946 }
3947 [(set_attr "op_type" "RI")
3948 (set_attr "z10prop" "z10_super_E1")])
3949
3950 ; Update the left-most 32 bit of a DI.
3951 (define_insn "*insv_h_di_reg_extimm"
3952 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
3953 (const_int 32)
3954 (const_int 0))
3955 (match_operand:DI 1 "const_int_operand" "n"))]
3956 "TARGET_EXTIMM"
3957 "iihf\t%0,%o1"
3958 [(set_attr "op_type" "RIL")
3959 (set_attr "z10prop" "z10_fwd_E1")])
3960
3961 ; Update the right-most 32 bit of a DI.
3962 (define_insn "*insv_l_di_reg_extimm"
3963 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
3964 (const_int 32)
3965 (const_int 32))
3966 (match_operand:DI 1 "const_int_operand" "n"))]
3967 "TARGET_EXTIMM"
3968 "iilf\t%0,%o1"
3969 [(set_attr "op_type" "RIL")
3970 (set_attr "z10prop" "z10_fwd_A1")])
3971
3972 ;
3973 ; extendsidi2 instruction pattern(s).
3974 ;
3975
3976 (define_expand "extendsidi2"
3977 [(set (match_operand:DI 0 "register_operand" "")
3978 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3979 ""
3980 {
3981 if (!TARGET_ZARCH)
3982 {
3983 emit_clobber (operands[0]);
3984 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
3985 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
3986 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
3987 DONE;
3988 }
3989 })
3990
3991 (define_insn "*extendsidi2"
3992 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
3993 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
3994 "TARGET_ZARCH"
3995 "@
3996 lgfr\t%0,%1
3997 lgf\t%0,%1
3998 lgfrl\t%0,%1"
3999 [(set_attr "op_type" "RRE,RXY,RIL")
4000 (set_attr "type" "*,*,larl")
4001 (set_attr "cpu_facility" "*,*,z10")
4002 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4003
4004 ;
4005 ; extend(hi|qi)(si|di)2 instruction pattern(s).
4006 ;
4007
4008 (define_expand "extend<HQI:mode><DSI:mode>2"
4009 [(set (match_operand:DSI 0 "register_operand" "")
4010 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4011 ""
4012 {
4013 if (<DSI:MODE>mode == DImode && !TARGET_ZARCH)
4014 {
4015 rtx tmp = gen_reg_rtx (SImode);
4016 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
4017 emit_insn (gen_extendsidi2 (operands[0], tmp));
4018 DONE;
4019 }
4020 else if (!TARGET_EXTIMM)
4021 {
4022 rtx bitcount = GEN_INT (<DSI:bitsize> - <HQI:bitsize>);
4023
4024 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
4025 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
4026 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
4027 DONE;
4028 }
4029 })
4030
4031 ;
4032 ; extendhidi2 instruction pattern(s).
4033 ;
4034
4035 (define_insn "*extendhidi2_extimm"
4036 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4037 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,RT,b")))]
4038 "TARGET_ZARCH && TARGET_EXTIMM"
4039 "@
4040 lghr\t%0,%1
4041 lgh\t%0,%1
4042 lghrl\t%0,%1"
4043 [(set_attr "op_type" "RRE,RXY,RIL")
4044 (set_attr "type" "*,*,larl")
4045 (set_attr "cpu_facility" "extimm,extimm,z10")
4046 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4047
4048 (define_insn "*extendhidi2"
4049 [(set (match_operand:DI 0 "register_operand" "=d")
4050 (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT")))]
4051 "TARGET_ZARCH"
4052 "lgh\t%0,%1"
4053 [(set_attr "op_type" "RXY")
4054 (set_attr "z10prop" "z10_super_E1")])
4055
4056 ;
4057 ; extendhisi2 instruction pattern(s).
4058 ;
4059
4060 (define_insn "*extendhisi2_extimm"
4061 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
4062 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
4063 "TARGET_EXTIMM"
4064 "@
4065 lhr\t%0,%1
4066 lh\t%0,%1
4067 lhy\t%0,%1
4068 lhrl\t%0,%1"
4069 [(set_attr "op_type" "RRE,RX,RXY,RIL")
4070 (set_attr "type" "*,*,*,larl")
4071 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")
4072 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,z10_super_E1")])
4073
4074 (define_insn "*extendhisi2"
4075 [(set (match_operand:SI 0 "register_operand" "=d,d")
4076 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
4077 "!TARGET_EXTIMM"
4078 "@
4079 lh\t%0,%1
4080 lhy\t%0,%1"
4081 [(set_attr "op_type" "RX,RXY")
4082 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4083
4084 ;
4085 ; extendqi(si|di)2 instruction pattern(s).
4086 ;
4087
4088 ; lbr, lgbr, lb, lgb
4089 (define_insn "*extendqi<mode>2_extimm"
4090 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4091 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,RT")))]
4092 "TARGET_EXTIMM"
4093 "@
4094 l<g>br\t%0,%1
4095 l<g>b\t%0,%1"
4096 [(set_attr "op_type" "RRE,RXY")
4097 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4098
4099 ; lb, lgb
4100 (define_insn "*extendqi<mode>2"
4101 [(set (match_operand:GPR 0 "register_operand" "=d")
4102 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "RT")))]
4103 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
4104 "l<g>b\t%0,%1"
4105 [(set_attr "op_type" "RXY")
4106 (set_attr "z10prop" "z10_super_E1")])
4107
4108 (define_insn_and_split "*extendqi<mode>2_short_displ"
4109 [(set (match_operand:GPR 0 "register_operand" "=d")
4110 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
4111 (clobber (reg:CC CC_REGNUM))]
4112 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
4113 "#"
4114 "&& reload_completed"
4115 [(parallel
4116 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
4117 (clobber (reg:CC CC_REGNUM))])
4118 (parallel
4119 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
4120 (clobber (reg:CC CC_REGNUM))])]
4121 {
4122 operands[1] = adjust_address (operands[1], BLKmode, 0);
4123 set_mem_size (operands[1], GET_MODE_SIZE (QImode));
4124 operands[2] = GEN_INT (<GPR:bitsize> - BITS_PER_UNIT);
4125 })
4126
4127 ;
4128 ; zero_extendsidi2 instruction pattern(s).
4129 ;
4130
4131 (define_expand "zero_extendsidi2"
4132 [(set (match_operand:DI 0 "register_operand" "")
4133 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4134 ""
4135 {
4136 if (!TARGET_ZARCH)
4137 {
4138 emit_clobber (operands[0]);
4139 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
4140 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
4141 DONE;
4142 }
4143 })
4144
4145 (define_insn "*zero_extendsidi2"
4146 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4147 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
4148 "TARGET_ZARCH"
4149 "@
4150 llgfr\t%0,%1
4151 llgf\t%0,%1
4152 llgfrl\t%0,%1"
4153 [(set_attr "op_type" "RRE,RXY,RIL")
4154 (set_attr "type" "*,*,larl")
4155 (set_attr "cpu_facility" "*,*,z10")
4156 (set_attr "z10prop" "z10_fwd_E1,z10_fwd_A3,z10_fwd_A3")])
4157
4158 ;
4159 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
4160 ;
4161
4162 (define_insn "*llgt_sidi"
4163 [(set (match_operand:DI 0 "register_operand" "=d")
4164 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
4165 (const_int 2147483647)))]
4166 "TARGET_ZARCH"
4167 "llgt\t%0,%1"
4168 [(set_attr "op_type" "RXE")
4169 (set_attr "z10prop" "z10_super_E1")])
4170
4171 (define_insn_and_split "*llgt_sidi_split"
4172 [(set (match_operand:DI 0 "register_operand" "=d")
4173 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
4174 (const_int 2147483647)))
4175 (clobber (reg:CC CC_REGNUM))]
4176 "TARGET_ZARCH"
4177 "#"
4178 "&& reload_completed"
4179 [(set (match_dup 0)
4180 (and:DI (subreg:DI (match_dup 1) 0)
4181 (const_int 2147483647)))]
4182 "")
4183
4184 (define_insn "*llgt_sisi"
4185 [(set (match_operand:SI 0 "register_operand" "=d,d")
4186 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,RT")
4187 (const_int 2147483647)))]
4188 "TARGET_ZARCH"
4189 "@
4190 llgtr\t%0,%1
4191 llgt\t%0,%1"
4192 [(set_attr "op_type" "RRE,RXE")
4193 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4194
4195 (define_insn "*llgt_didi"
4196 [(set (match_operand:DI 0 "register_operand" "=d,d")
4197 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
4198 (const_int 2147483647)))]
4199 "TARGET_ZARCH"
4200 "@
4201 llgtr\t%0,%1
4202 llgt\t%0,%N1"
4203 [(set_attr "op_type" "RRE,RXE")
4204 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4205
4206 (define_split
4207 [(set (match_operand:DSI 0 "register_operand" "")
4208 (and:DSI (match_operand:DSI 1 "nonimmediate_operand" "")
4209 (const_int 2147483647)))
4210 (clobber (reg:CC CC_REGNUM))]
4211 "TARGET_ZARCH && reload_completed"
4212 [(set (match_dup 0)
4213 (and:DSI (match_dup 1)
4214 (const_int 2147483647)))]
4215 "")
4216
4217 ;
4218 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
4219 ;
4220
4221 (define_expand "zero_extend<mode>di2"
4222 [(set (match_operand:DI 0 "register_operand" "")
4223 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4224 ""
4225 {
4226 if (!TARGET_ZARCH)
4227 {
4228 rtx tmp = gen_reg_rtx (SImode);
4229 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
4230 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
4231 DONE;
4232 }
4233 else if (!TARGET_EXTIMM)
4234 {
4235 rtx bitcount = GEN_INT (64 - <HQI:bitsize>);
4236 operands[1] = gen_lowpart (DImode, operands[1]);
4237 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
4238 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
4239 DONE;
4240 }
4241 })
4242
4243 (define_expand "zero_extend<mode>si2"
4244 [(set (match_operand:SI 0 "register_operand" "")
4245 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4246 ""
4247 {
4248 if (!TARGET_EXTIMM)
4249 {
4250 operands[1] = gen_lowpart (SImode, operands[1]);
4251 emit_insn (gen_andsi3 (operands[0], operands[1],
4252 GEN_INT ((1 << <HQI:bitsize>) - 1)));
4253 DONE;
4254 }
4255 })
4256
4257 ; llhrl, llghrl
4258 (define_insn "*zero_extendhi<mode>2_z10"
4259 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4260 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,RT,b")))]
4261 "TARGET_Z10"
4262 "@
4263 ll<g>hr\t%0,%1
4264 ll<g>h\t%0,%1
4265 ll<g>hrl\t%0,%1"
4266 [(set_attr "op_type" "RXY,RRE,RIL")
4267 (set_attr "type" "*,*,larl")
4268 (set_attr "cpu_facility" "*,*,z10")
4269 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3,z10_fwd_A3")])
4270
4271 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
4272 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
4273 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4274 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,RT")))]
4275 "TARGET_EXTIMM"
4276 "@
4277 ll<g><hc>r\t%0,%1
4278 ll<g><hc>\t%0,%1"
4279 [(set_attr "op_type" "RRE,RXY")
4280 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3")])
4281
4282 ; llgh, llgc
4283 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
4284 [(set (match_operand:GPR 0 "register_operand" "=d")
4285 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "RT")))]
4286 "TARGET_ZARCH && !TARGET_EXTIMM"
4287 "llg<hc>\t%0,%1"
4288 [(set_attr "op_type" "RXY")
4289 (set_attr "z10prop" "z10_fwd_A3")])
4290
4291 (define_insn_and_split "*zero_extendhisi2_31"
4292 [(set (match_operand:SI 0 "register_operand" "=&d")
4293 (zero_extend:SI (match_operand:HI 1 "s_operand" "QS")))
4294 (clobber (reg:CC CC_REGNUM))]
4295 "!TARGET_ZARCH"
4296 "#"
4297 "&& reload_completed"
4298 [(set (match_dup 0) (const_int 0))
4299 (parallel
4300 [(set (strict_low_part (match_dup 2)) (match_dup 1))
4301 (clobber (reg:CC CC_REGNUM))])]
4302 "operands[2] = gen_lowpart (HImode, operands[0]);")
4303
4304 (define_insn_and_split "*zero_extendqisi2_31"
4305 [(set (match_operand:SI 0 "register_operand" "=&d")
4306 (zero_extend:SI (match_operand:QI 1 "memory_operand" "RT")))]
4307 "!TARGET_ZARCH"
4308 "#"
4309 "&& reload_completed"
4310 [(set (match_dup 0) (const_int 0))
4311 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4312 "operands[2] = gen_lowpart (QImode, operands[0]);")
4313
4314 ;
4315 ; zero_extendqihi2 instruction pattern(s).
4316 ;
4317
4318 (define_expand "zero_extendqihi2"
4319 [(set (match_operand:HI 0 "register_operand" "")
4320 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4321 "TARGET_ZARCH && !TARGET_EXTIMM"
4322 {
4323 operands[1] = gen_lowpart (HImode, operands[1]);
4324 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
4325 DONE;
4326 })
4327
4328 (define_insn "*zero_extendqihi2_64"
4329 [(set (match_operand:HI 0 "register_operand" "=d")
4330 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
4331 "TARGET_ZARCH && !TARGET_EXTIMM"
4332 "llgc\t%0,%1"
4333 [(set_attr "op_type" "RXY")
4334 (set_attr "z10prop" "z10_fwd_A3")])
4335
4336 (define_insn_and_split "*zero_extendqihi2_31"
4337 [(set (match_operand:HI 0 "register_operand" "=&d")
4338 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
4339 "!TARGET_ZARCH"
4340 "#"
4341 "&& reload_completed"
4342 [(set (match_dup 0) (const_int 0))
4343 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4344 "operands[2] = gen_lowpart (QImode, operands[0]);")
4345
4346 ;
4347 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
4348 ;
4349
4350 (define_expand "fixuns_truncdddi2"
4351 [(parallel
4352 [(set (match_operand:DI 0 "register_operand" "")
4353 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
4354 (unspec:DI [(const_int 5)] UNSPEC_ROUND)
4355 (clobber (reg:CC CC_REGNUM))])]
4356
4357 "TARGET_HARD_DFP"
4358 {
4359 if (!TARGET_Z196)
4360 {
4361 rtx_code_label *label1 = gen_label_rtx ();
4362 rtx_code_label *label2 = gen_label_rtx ();
4363 rtx temp = gen_reg_rtx (TDmode);
4364 REAL_VALUE_TYPE cmp, sub;
4365
4366 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4367 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4368
4369 /* 2^63 can't be represented as 64bit DFP number with full precision. The
4370 solution is doing the check and the subtraction in TD mode and using a
4371 TD -> DI convert afterwards. */
4372 emit_insn (gen_extendddtd2 (temp, operands[1]));
4373 temp = force_reg (TDmode, temp);
4374 emit_cmp_and_jump_insns (temp,
4375 CONST_DOUBLE_FROM_REAL_VALUE (cmp, TDmode),
4376 LT, NULL_RTX, VOIDmode, 0, label1);
4377 emit_insn (gen_subtd3 (temp, temp,
4378 CONST_DOUBLE_FROM_REAL_VALUE (sub, TDmode)));
4379 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
4380 emit_jump (label2);
4381
4382 emit_label (label1);
4383 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1], GEN_INT (9)));
4384 emit_label (label2);
4385 DONE;
4386 }
4387 })
4388
4389 (define_expand "fixuns_trunctddi2"
4390 [(parallel
4391 [(set (match_operand:DI 0 "register_operand" "")
4392 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))
4393 (unspec:DI [(const_int 5)] UNSPEC_ROUND)
4394 (clobber (reg:CC CC_REGNUM))])]
4395
4396 "TARGET_HARD_DFP"
4397 {
4398 if (!TARGET_Z196)
4399 {
4400 rtx_code_label *label1 = gen_label_rtx ();
4401 rtx_code_label *label2 = gen_label_rtx ();
4402 rtx temp = gen_reg_rtx (TDmode);
4403 REAL_VALUE_TYPE cmp, sub;
4404
4405 operands[1] = force_reg (TDmode, operands[1]);
4406 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4407 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4408
4409 emit_cmp_and_jump_insns (operands[1],
4410 CONST_DOUBLE_FROM_REAL_VALUE (cmp, TDmode),
4411 LT, NULL_RTX, VOIDmode, 0, label1);
4412 emit_insn (gen_subtd3 (temp, operands[1],
4413 CONST_DOUBLE_FROM_REAL_VALUE (sub, TDmode)));
4414 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
4415 emit_jump (label2);
4416
4417 emit_label (label1);
4418 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1], GEN_INT (9)));
4419 emit_label (label2);
4420 DONE;
4421 }
4422 })
4423
4424 ;
4425 ; fixuns_trunc(sf|df|tf)(si|di)2 and fix_trunc(sf|df|tf)(si|di)2
4426 ; instruction pattern(s).
4427 ;
4428
4429 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
4430 [(parallel
4431 [(set (match_operand:GPR 0 "register_operand" "")
4432 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))
4433 (unspec:GPR [(const_int 5)] UNSPEC_ROUND)
4434 (clobber (reg:CC CC_REGNUM))])]
4435 "TARGET_HARD_FLOAT"
4436 {
4437 if (!TARGET_Z196)
4438 {
4439 rtx_code_label *label1 = gen_label_rtx ();
4440 rtx_code_label *label2 = gen_label_rtx ();
4441 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
4442 REAL_VALUE_TYPE cmp, sub;
4443
4444 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
4445 real_2expN (&cmp, <GPR:bitsize> - 1, <BFP:MODE>mode);
4446 real_2expN (&sub, <GPR:bitsize>, <BFP:MODE>mode);
4447
4448 emit_cmp_and_jump_insns (operands[1],
4449 CONST_DOUBLE_FROM_REAL_VALUE (cmp, <BFP:MODE>mode),
4450 LT, NULL_RTX, VOIDmode, 0, label1);
4451 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
4452 CONST_DOUBLE_FROM_REAL_VALUE (sub, <BFP:MODE>mode)));
4453 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
4454 GEN_INT (7)));
4455 emit_jump (label2);
4456
4457 emit_label (label1);
4458 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
4459 operands[1], GEN_INT (5)));
4460 emit_label (label2);
4461 DONE;
4462 }
4463 })
4464
4465 ; fixuns_trunc(td|dd)si2 expander
4466 (define_expand "fixuns_trunc<mode>si2"
4467 [(parallel
4468 [(set (match_operand:SI 0 "register_operand" "")
4469 (unsigned_fix:SI (match_operand:DFP 1 "register_operand" "")))
4470 (unspec:SI [(const_int 5)] UNSPEC_ROUND)
4471 (clobber (reg:CC CC_REGNUM))])]
4472 "TARGET_Z196 && TARGET_HARD_DFP"
4473 "")
4474
4475 ; fixuns_trunc(tf|df|sf|td|dd)(di|si)2 instruction patterns.
4476
4477 (define_insn "*fixuns_truncdfdi2_z13"
4478 [(set (match_operand:DI 0 "register_operand" "=d,v")
4479 (unsigned_fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4480 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4481 (clobber (reg:CC CC_REGNUM))]
4482 "TARGET_Z13 && TARGET_HARD_FLOAT"
4483 "@
4484 clgdbr\t%0,%h2,%1,0
4485 wclgdb\t%v0,%v1,0,%h2"
4486 [(set_attr "op_type" "RRF,VRR")
4487 (set_attr "type" "ftoi")])
4488
4489 ; clfebr, clfdbr, clfxbr, clgebr, clgdbr, clgxbr
4490 ; clfdtr, clfxtr, clgdtr, clgxtr
4491 (define_insn "*fixuns_trunc<FP:mode><GPR:mode>2_z196"
4492 [(set (match_operand:GPR 0 "register_operand" "=d")
4493 (unsigned_fix:GPR (match_operand:FP 1 "register_operand" "f")))
4494 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4495 (clobber (reg:CC CC_REGNUM))]
4496 "TARGET_Z196 && TARGET_HARD_FLOAT
4497 && (!TARGET_Z13 || <GPR:MODE>mode != DImode || <FP:MODE>mode != DFmode)"
4498 "cl<GPR:gf><FP:xde><FP:bt>r\t%0,%h2,%1,0"
4499 [(set_attr "op_type" "RRF")
4500 (set_attr "type" "ftoi")])
4501
4502 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
4503 [(set (match_operand:GPR 0 "register_operand" "")
4504 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
4505 "TARGET_HARD_FLOAT"
4506 {
4507 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
4508 GEN_INT (5)));
4509 DONE;
4510 })
4511
4512 (define_insn "*fix_truncdfdi2_bfp_z13"
4513 [(set (match_operand:DI 0 "register_operand" "=d,v")
4514 (fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4515 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4516 (clobber (reg:CC CC_REGNUM))]
4517 "TARGET_Z13 && TARGET_HARD_FLOAT"
4518 "@
4519 cgdbr\t%0,%h2,%1
4520 wcgdb\t%v0,%v1,0,%h2"
4521 [(set_attr "op_type" "RRE,VRR")
4522 (set_attr "type" "ftoi")])
4523
4524 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
4525 (define_insn "*fix_trunc<BFP:mode><GPR:mode>2_bfp"
4526 [(set (match_operand:GPR 0 "register_operand" "=d")
4527 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4528 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4529 (clobber (reg:CC CC_REGNUM))]
4530 "TARGET_HARD_FLOAT
4531 && (!TARGET_VX || <GPR:MODE>mode != DImode || <BFP:MODE>mode != DFmode)"
4532 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
4533 [(set_attr "op_type" "RRE")
4534 (set_attr "type" "ftoi")])
4535
4536 (define_expand "fix_trunc<BFP:mode><GPR:mode>2_bfp"
4537 [(parallel
4538 [(set (match_operand:GPR 0 "register_operand" "=d")
4539 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4540 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4541 (clobber (reg:CC CC_REGNUM))])]
4542 "TARGET_HARD_FLOAT")
4543 ;
4544 ; fix_trunc(td|dd)di2 instruction pattern(s).
4545 ;
4546
4547 (define_expand "fix_trunc<mode>di2"
4548 [(set (match_operand:DI 0 "register_operand" "")
4549 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
4550 "TARGET_ZARCH && TARGET_HARD_DFP"
4551 {
4552 operands[1] = force_reg (<MODE>mode, operands[1]);
4553 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
4554 GEN_INT (9)));
4555 DONE;
4556 })
4557
4558 ; cgxtr, cgdtr
4559 (define_insn "fix_trunc<DFP:mode>di2_dfp"
4560 [(set (match_operand:DI 0 "register_operand" "=d")
4561 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
4562 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
4563 (clobber (reg:CC CC_REGNUM))]
4564 "TARGET_ZARCH && TARGET_HARD_DFP"
4565 "cg<DFP:xde>tr\t%0,%h2,%1"
4566 [(set_attr "op_type" "RRF")
4567 (set_attr "type" "ftoidfp")])
4568
4569
4570 ;
4571 ; fix_trunctf(si|di)2 instruction pattern(s).
4572 ;
4573
4574 (define_expand "fix_trunctf<mode>2"
4575 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
4576 (fix:GPR (match_operand:TF 1 "register_operand" "")))
4577 (unspec:GPR [(const_int 5)] UNSPEC_ROUND)
4578 (clobber (reg:CC CC_REGNUM))])]
4579 "TARGET_HARD_FLOAT"
4580 "")
4581
4582
4583 ;
4584 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4585 ;
4586
4587 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
4588 (define_insn "floatdi<mode>2"
4589 [(set (match_operand:FP 0 "register_operand" "=f,<vf>")
4590 (float:FP (match_operand:DI 1 "register_operand" "d,<vd>")))]
4591 "TARGET_ZARCH && TARGET_HARD_FLOAT"
4592 "@
4593 c<xde>g<bt>r\t%0,%1
4594 wcdgb\t%v0,%v1,0,0"
4595 [(set_attr "op_type" "RRE,VRR")
4596 (set_attr "type" "itof<mode>" )
4597 (set_attr "cpu_facility" "*,vec")])
4598
4599 ; cxfbr, cdfbr, cefbr
4600 (define_insn "floatsi<mode>2"
4601 [(set (match_operand:BFP 0 "register_operand" "=f")
4602 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
4603 "TARGET_HARD_FLOAT"
4604 "c<xde>fbr\t%0,%1"
4605 [(set_attr "op_type" "RRE")
4606 (set_attr "type" "itof<mode>" )])
4607
4608 ; cxftr, cdftr
4609 (define_insn "floatsi<mode>2"
4610 [(set (match_operand:DFP 0 "register_operand" "=f")
4611 (float:DFP (match_operand:SI 1 "register_operand" "d")))]
4612 "TARGET_Z196 && TARGET_HARD_FLOAT"
4613 "c<xde>ftr\t%0,0,%1,0"
4614 [(set_attr "op_type" "RRE")
4615 (set_attr "type" "itof<mode>" )])
4616
4617 ;
4618 ; floatuns(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4619 ;
4620
4621 (define_insn "*floatunsdidf2_z13"
4622 [(set (match_operand:DF 0 "register_operand" "=f,v")
4623 (unsigned_float:DF (match_operand:DI 1 "register_operand" "d,v")))]
4624 "TARGET_Z13 && TARGET_HARD_FLOAT"
4625 "@
4626 cdlgbr\t%0,0,%1,0
4627 wcdlgb\t%v0,%v1,0,0"
4628 [(set_attr "op_type" "RRE,VRR")
4629 (set_attr "type" "itofdf")])
4630
4631 ; cxlgbr, cdlgbr, celgbr, cxlgtr, cdlgtr
4632 ; cxlfbr, cdlfbr, celfbr, cxlftr, cdlftr
4633 (define_insn "*floatuns<GPR:mode><FP:mode>2"
4634 [(set (match_operand:FP 0 "register_operand" "=f")
4635 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "d")))]
4636 "TARGET_Z196 && TARGET_HARD_FLOAT
4637 && (!TARGET_VX || <FP:MODE>mode != DFmode || <GPR:MODE>mode != DImode)"
4638 "c<FP:xde>l<GPR:gf><FP:bt>r\t%0,0,%1,0"
4639 [(set_attr "op_type" "RRE")
4640 (set_attr "type" "itof<FP:mode>")])
4641
4642 (define_expand "floatuns<GPR:mode><FP:mode>2"
4643 [(set (match_operand:FP 0 "register_operand" "")
4644 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "")))]
4645 "TARGET_Z196 && TARGET_HARD_FLOAT")
4646
4647 ;
4648 ; truncdfsf2 instruction pattern(s).
4649 ;
4650
4651 (define_insn "truncdfsf2"
4652 [(set (match_operand:SF 0 "register_operand" "=f,v")
4653 (float_truncate:SF (match_operand:DF 1 "register_operand" "f,v")))]
4654 "TARGET_HARD_FLOAT"
4655 "@
4656 ledbr\t%0,%1
4657 wledb\t%v0,%v1,0,0" ; IEEE inexact exception not suppressed
4658 ; According to BFP rounding mode
4659 [(set_attr "op_type" "RRE,VRR")
4660 (set_attr "type" "ftruncdf")
4661 (set_attr "cpu_facility" "*,vec")])
4662
4663 ;
4664 ; trunctf(df|sf)2 instruction pattern(s).
4665 ;
4666
4667 ; ldxbr, lexbr
4668 (define_insn "trunctf<mode>2"
4669 [(set (match_operand:DSF 0 "register_operand" "=f")
4670 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
4671 (clobber (match_scratch:TF 2 "=f"))]
4672 "TARGET_HARD_FLOAT"
4673 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
4674 [(set_attr "length" "6")
4675 (set_attr "type" "ftrunctf")])
4676
4677 ;
4678 ; trunctddd2 and truncddsd2 instruction pattern(s).
4679 ;
4680
4681 (define_insn "trunctddd2"
4682 [(set (match_operand:DD 0 "register_operand" "=f")
4683 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
4684 (clobber (match_scratch:TD 2 "=f"))]
4685 "TARGET_HARD_DFP"
4686 "ldxtr\t%2,0,%1,0\;ldr\t%0,%2"
4687 [(set_attr "length" "6")
4688 (set_attr "type" "ftruncdd")])
4689
4690 (define_insn "truncddsd2"
4691 [(set (match_operand:SD 0 "register_operand" "=f")
4692 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
4693 "TARGET_HARD_DFP"
4694 "ledtr\t%0,0,%1,0"
4695 [(set_attr "op_type" "RRF")
4696 (set_attr "type" "ftruncsd")])
4697
4698 (define_expand "trunctdsd2"
4699 [(parallel
4700 [(set (match_dup 3)
4701 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
4702 (clobber (match_scratch:TD 2 ""))])
4703 (set (match_operand:SD 0 "register_operand" "")
4704 (float_truncate:SD (match_dup 3)))]
4705 "TARGET_HARD_DFP"
4706 {
4707 operands[3] = gen_reg_rtx (DDmode);
4708 })
4709
4710 ;
4711 ; extend(sf|df)(df|tf)2 instruction pattern(s).
4712 ;
4713
4714 (define_insn "*extendsfdf2_z13"
4715 [(set (match_operand:DF 0 "register_operand" "=f,f,v")
4716 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,R,v")))]
4717 "TARGET_Z13 && TARGET_HARD_FLOAT"
4718 "@
4719 ldebr\t%0,%1
4720 ldeb\t%0,%1
4721 wldeb\t%v0,%v1"
4722 [(set_attr "op_type" "RRE,RXE,VRR")
4723 (set_attr "type" "fsimpdf, floaddf,fsimpdf")])
4724
4725 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
4726 (define_insn "*extend<DSF:mode><BFP:mode>2"
4727 [(set (match_operand:BFP 0 "register_operand" "=f,f")
4728 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
4729 "TARGET_HARD_FLOAT
4730 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)
4731 && (!TARGET_VX || <BFP:MODE>mode != DFmode || <DSF:MODE>mode != SFmode)"
4732 "@
4733 l<BFP:xde><DSF:xde>br\t%0,%1
4734 l<BFP:xde><DSF:xde>b\t%0,%1"
4735 [(set_attr "op_type" "RRE,RXE")
4736 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
4737
4738 (define_expand "extend<DSF:mode><BFP:mode>2"
4739 [(set (match_operand:BFP 0 "register_operand" "")
4740 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "")))]
4741 "TARGET_HARD_FLOAT
4742 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)")
4743
4744 ;
4745 ; extendddtd2 and extendsddd2 instruction pattern(s).
4746 ;
4747
4748 (define_insn "extendddtd2"
4749 [(set (match_operand:TD 0 "register_operand" "=f")
4750 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
4751 "TARGET_HARD_DFP"
4752 "lxdtr\t%0,%1,0"
4753 [(set_attr "op_type" "RRF")
4754 (set_attr "type" "fsimptf")])
4755
4756 (define_insn "extendsddd2"
4757 [(set (match_operand:DD 0 "register_operand" "=f")
4758 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
4759 "TARGET_HARD_DFP"
4760 "ldetr\t%0,%1,0"
4761 [(set_attr "op_type" "RRF")
4762 (set_attr "type" "fsimptf")])
4763
4764 (define_expand "extendsdtd2"
4765 [(set (match_dup 2)
4766 (float_extend:DD (match_operand:SD 1 "register_operand" "")))
4767 (set (match_operand:TD 0 "register_operand" "")
4768 (float_extend:TD (match_dup 2)))]
4769 "TARGET_HARD_DFP"
4770 {
4771 operands[2] = gen_reg_rtx (DDmode);
4772 })
4773
4774 ; Binary Floating Point - load fp integer
4775
4776 ; Expanders for: floor, btrunc, round, ceil, and nearbyint
4777 ; For all of them the inexact exceptions are suppressed.
4778
4779 ; fiebra, fidbra, fixbra
4780 (define_insn "<FPINT:fpint_name><BFP:mode>2"
4781 [(set (match_operand:BFP 0 "register_operand" "=f")
4782 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
4783 FPINT))]
4784 "TARGET_Z196"
4785 "fi<BFP:xde>bra\t%0,<FPINT:fpint_roundingmode>,%1,4"
4786 [(set_attr "op_type" "RRF")
4787 (set_attr "type" "fsimp<BFP:mode>")])
4788
4789 ; rint is supposed to raise an inexact exception so we can use the
4790 ; older instructions.
4791
4792 ; fiebr, fidbr, fixbr
4793 (define_insn "rint<BFP:mode>2"
4794 [(set (match_operand:BFP 0 "register_operand" "=f")
4795 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
4796 UNSPEC_FPINT_RINT))]
4797 ""
4798 "fi<BFP:xde>br\t%0,0,%1"
4799 [(set_attr "op_type" "RRF")
4800 (set_attr "type" "fsimp<BFP:mode>")])
4801
4802
4803 ; Decimal Floating Point - load fp integer
4804
4805 ; fidtr, fixtr
4806 (define_insn "<FPINT:fpint_name><DFP:mode>2"
4807 [(set (match_operand:DFP 0 "register_operand" "=f")
4808 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
4809 FPINT))]
4810 "TARGET_HARD_DFP"
4811 "fi<DFP:xde>tr\t%0,<FPINT:fpint_roundingmode>,%1,4"
4812 [(set_attr "op_type" "RRF")
4813 (set_attr "type" "fsimp<DFP:mode>")])
4814
4815 ; fidtr, fixtr
4816 (define_insn "rint<DFP:mode>2"
4817 [(set (match_operand:DFP 0 "register_operand" "=f")
4818 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
4819 UNSPEC_FPINT_RINT))]
4820 "TARGET_HARD_DFP"
4821 "fi<DFP:xde>tr\t%0,0,%1,0"
4822 [(set_attr "op_type" "RRF")
4823 (set_attr "type" "fsimp<DFP:mode>")])
4824
4825 ;
4826 ; Binary <-> Decimal floating point trunc patterns
4827 ;
4828
4829 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
4830 [(set (reg:DFP_ALL FPR0_REGNUM)
4831 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
4832 (use (reg:SI GPR0_REGNUM))
4833 (clobber (reg:CC CC_REGNUM))]
4834 "TARGET_HARD_DFP"
4835 "pfpo")
4836
4837 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
4838 [(set (reg:BFP FPR0_REGNUM)
4839 (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
4840 (use (reg:SI GPR0_REGNUM))
4841 (clobber (reg:CC CC_REGNUM))]
4842 "TARGET_HARD_DFP"
4843 "pfpo")
4844
4845 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
4846 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
4847 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4848 (parallel
4849 [(set (reg:DFP_ALL FPR0_REGNUM)
4850 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
4851 (use (reg:SI GPR0_REGNUM))
4852 (clobber (reg:CC CC_REGNUM))])
4853 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
4854 (reg:DFP_ALL FPR0_REGNUM))]
4855 "TARGET_HARD_DFP
4856 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
4857 {
4858 HOST_WIDE_INT flags;
4859
4860 flags = (PFPO_CONVERT |
4861 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
4862 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
4863
4864 operands[2] = GEN_INT (flags);
4865 })
4866
4867 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
4868 [(set (reg:DFP_ALL FPR4_REGNUM)
4869 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
4870 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4871 (parallel
4872 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
4873 (use (reg:SI GPR0_REGNUM))
4874 (clobber (reg:CC CC_REGNUM))])
4875 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
4876 "TARGET_HARD_DFP
4877 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
4878 {
4879 HOST_WIDE_INT flags;
4880
4881 flags = (PFPO_CONVERT |
4882 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
4883 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
4884
4885 operands[2] = GEN_INT (flags);
4886 })
4887
4888 ;
4889 ; Binary <-> Decimal floating point extend patterns
4890 ;
4891
4892 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
4893 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
4894 (use (reg:SI GPR0_REGNUM))
4895 (clobber (reg:CC CC_REGNUM))]
4896 "TARGET_HARD_DFP"
4897 "pfpo")
4898
4899 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
4900 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
4901 (use (reg:SI GPR0_REGNUM))
4902 (clobber (reg:CC CC_REGNUM))]
4903 "TARGET_HARD_DFP"
4904 "pfpo")
4905
4906 (define_expand "extend<BFP:mode><DFP_ALL:mode>2"
4907 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
4908 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4909 (parallel
4910 [(set (reg:DFP_ALL FPR0_REGNUM)
4911 (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
4912 (use (reg:SI GPR0_REGNUM))
4913 (clobber (reg:CC CC_REGNUM))])
4914 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
4915 (reg:DFP_ALL FPR0_REGNUM))]
4916 "TARGET_HARD_DFP
4917 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
4918 {
4919 HOST_WIDE_INT flags;
4920
4921 flags = (PFPO_CONVERT |
4922 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
4923 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
4924
4925 operands[2] = GEN_INT (flags);
4926 })
4927
4928 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
4929 [(set (reg:DFP_ALL FPR4_REGNUM)
4930 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
4931 (set (reg:SI GPR0_REGNUM) (match_dup 2))
4932 (parallel
4933 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
4934 (use (reg:SI GPR0_REGNUM))
4935 (clobber (reg:CC CC_REGNUM))])
4936 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
4937 "TARGET_HARD_DFP
4938 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
4939 {
4940 HOST_WIDE_INT flags;
4941
4942 flags = (PFPO_CONVERT |
4943 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
4944 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
4945
4946 operands[2] = GEN_INT (flags);
4947 })
4948
4949
4950 ;;
4951 ;; ARITHMETIC OPERATIONS
4952 ;;
4953 ; arithmetic operations set the ConditionCode,
4954 ; because of unpredictable Bits in Register for Halfword and Byte
4955 ; the ConditionCode can be set wrong in operations for Halfword and Byte
4956
4957 ;;
4958 ;;- Add instructions.
4959 ;;
4960
4961 ;
4962 ; addti3 instruction pattern(s).
4963 ;
4964
4965 (define_expand "addti3"
4966 [(parallel
4967 [(set (match_operand:TI 0 "register_operand" "")
4968 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
4969 (match_operand:TI 2 "general_operand" "") ) )
4970 (clobber (reg:CC CC_REGNUM))])]
4971 "TARGET_ZARCH"
4972 {
4973 /* For z13 we have vaq which doesn't set CC. */
4974 if (TARGET_VX)
4975 {
4976 emit_insn (gen_rtx_SET (operands[0],
4977 gen_rtx_PLUS (TImode,
4978 copy_to_mode_reg (TImode, operands[1]),
4979 copy_to_mode_reg (TImode, operands[2]))));
4980 DONE;
4981 }
4982 })
4983
4984 (define_insn_and_split "*addti3"
4985 [(set (match_operand:TI 0 "register_operand" "=&d")
4986 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
4987 (match_operand:TI 2 "general_operand" "do") ) )
4988 (clobber (reg:CC CC_REGNUM))]
4989 "TARGET_ZARCH"
4990 "#"
4991 "&& reload_completed"
4992 [(parallel
4993 [(set (reg:CCL1 CC_REGNUM)
4994 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
4995 (match_dup 7)))
4996 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
4997 (parallel
4998 [(set (match_dup 3) (plus:DI
4999 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
5000 (match_dup 4)) (match_dup 5)))
5001 (clobber (reg:CC CC_REGNUM))])]
5002 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5003 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5004 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5005 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5006 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5007 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5008 [(set_attr "op_type" "*")
5009 (set_attr "cpu_facility" "*")])
5010
5011 ;
5012 ; adddi3 instruction pattern(s).
5013 ;
5014
5015 (define_expand "adddi3"
5016 [(parallel
5017 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5018 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5019 (match_operand:DI 2 "general_operand" "")))
5020 (clobber (reg:CC CC_REGNUM))])]
5021 ""
5022 "")
5023
5024 (define_insn "*adddi3_sign"
5025 [(set (match_operand:DI 0 "register_operand" "=d,d")
5026 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5027 (match_operand:DI 1 "register_operand" "0,0")))
5028 (clobber (reg:CC CC_REGNUM))]
5029 "TARGET_ZARCH"
5030 "@
5031 agfr\t%0,%2
5032 agf\t%0,%2"
5033 [(set_attr "op_type" "RRE,RXY")
5034 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5035
5036 (define_insn "*adddi3_zero_cc"
5037 [(set (reg CC_REGNUM)
5038 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5039 (match_operand:DI 1 "register_operand" "0,0"))
5040 (const_int 0)))
5041 (set (match_operand:DI 0 "register_operand" "=d,d")
5042 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
5043 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5044 "@
5045 algfr\t%0,%2
5046 algf\t%0,%2"
5047 [(set_attr "op_type" "RRE,RXY")
5048 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5049
5050 (define_insn "*adddi3_zero_cconly"
5051 [(set (reg CC_REGNUM)
5052 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5053 (match_operand:DI 1 "register_operand" "0,0"))
5054 (const_int 0)))
5055 (clobber (match_scratch:DI 0 "=d,d"))]
5056 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5057 "@
5058 algfr\t%0,%2
5059 algf\t%0,%2"
5060 [(set_attr "op_type" "RRE,RXY")
5061 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5062
5063 (define_insn "*adddi3_zero"
5064 [(set (match_operand:DI 0 "register_operand" "=d,d")
5065 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
5066 (match_operand:DI 1 "register_operand" "0,0")))
5067 (clobber (reg:CC CC_REGNUM))]
5068 "TARGET_ZARCH"
5069 "@
5070 algfr\t%0,%2
5071 algf\t%0,%2"
5072 [(set_attr "op_type" "RRE,RXY")
5073 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5074
5075 (define_insn_and_split "*adddi3_31z"
5076 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5077 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5078 (match_operand:DI 2 "general_operand" "do") ) )
5079 (clobber (reg:CC CC_REGNUM))]
5080 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5081 "#"
5082 "&& reload_completed"
5083 [(parallel
5084 [(set (reg:CCL1 CC_REGNUM)
5085 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5086 (match_dup 7)))
5087 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5088 (parallel
5089 [(set (match_dup 3) (plus:SI
5090 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
5091 (match_dup 4)) (match_dup 5)))
5092 (clobber (reg:CC CC_REGNUM))])]
5093 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5094 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5095 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5096 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5097 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5098 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5099
5100 (define_insn_and_split "*adddi3_31"
5101 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5102 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5103 (match_operand:DI 2 "general_operand" "do") ) )
5104 (clobber (reg:CC CC_REGNUM))]
5105 "!TARGET_CPU_ZARCH"
5106 "#"
5107 "&& reload_completed"
5108 [(parallel
5109 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
5110 (clobber (reg:CC CC_REGNUM))])
5111 (parallel
5112 [(set (reg:CCL1 CC_REGNUM)
5113 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5114 (match_dup 7)))
5115 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5116 (set (pc)
5117 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
5118 (pc)
5119 (label_ref (match_dup 9))))
5120 (parallel
5121 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
5122 (clobber (reg:CC CC_REGNUM))])
5123 (match_dup 9)]
5124 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5125 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5126 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5127 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5128 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5129 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5130 operands[9] = gen_label_rtx ();")
5131
5132 ;
5133 ; addsi3 instruction pattern(s).
5134 ;
5135
5136 (define_expand "addsi3"
5137 [(parallel
5138 [(set (match_operand:SI 0 "nonimmediate_operand" "")
5139 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5140 (match_operand:SI 2 "general_operand" "")))
5141 (clobber (reg:CC CC_REGNUM))])]
5142 ""
5143 "")
5144
5145 (define_insn "*addsi3_sign"
5146 [(set (match_operand:SI 0 "register_operand" "=d,d")
5147 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
5148 (match_operand:SI 1 "register_operand" "0,0")))
5149 (clobber (reg:CC CC_REGNUM))]
5150 ""
5151 "@
5152 ah\t%0,%2
5153 ahy\t%0,%2"
5154 [(set_attr "op_type" "RX,RXY")
5155 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5156
5157 ;
5158 ; add(di|si)3 instruction pattern(s).
5159 ;
5160
5161 ; ark, agrk, ar, ahi, ahik, aghik, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
5162 (define_insn "*add<mode>3"
5163 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d, d, d,d,d,QS")
5164 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,d, 0, 0,0,0, 0")
5165 (match_operand:GPR 2 "general_operand" " d,d,K,K,Op,On,R,T, C") ) )
5166 (clobber (reg:CC CC_REGNUM))]
5167 ""
5168 "@
5169 a<g>r\t%0,%2
5170 a<g>rk\t%0,%1,%2
5171 a<g>hi\t%0,%h2
5172 a<g>hik\t%0,%1,%h2
5173 al<g>fi\t%0,%2
5174 sl<g>fi\t%0,%n2
5175 a<g>\t%0,%2
5176 a<y>\t%0,%2
5177 a<g>si\t%0,%c2"
5178 [(set_attr "op_type" "RR<E>,RRF,RI,RIE,RIL,RIL,RX<Y>,RXY,SIY")
5179 (set_attr "cpu_facility" "*,z196,*,z196,extimm,extimm,*,*,z10")
5180 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,z10_super_E1,z10_super_E1,
5181 z10_super_E1,z10_super_E1,z10_super_E1")])
5182
5183 ; alr, alfi, slfi, al, aly, alrk, alhsik, algr, algfi, slgfi, alg, alsi, algsi, algrk, alghsik
5184 (define_insn "*add<mode>3_carry1_cc"
5185 [(set (reg CC_REGNUM)
5186 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5187 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5188 (match_dup 1)))
5189 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,d")
5190 (plus:GPR (match_dup 1) (match_dup 2)))]
5191 "s390_match_ccmode (insn, CCL1mode)"
5192 "@
5193 al<g>r\t%0,%2
5194 al<g>rk\t%0,%1,%2
5195 al<g>fi\t%0,%2
5196 sl<g>fi\t%0,%n2
5197 al<g>hsik\t%0,%1,%h2
5198 al<g>\t%0,%2
5199 al<y>\t%0,%2
5200 al<g>si\t%0,%c2"
5201 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5202 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5203 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5204 z10_super_E1,z10_super_E1,z10_super_E1")])
5205
5206 ; alr, al, aly, algr, alg, alrk, algrk
5207 (define_insn "*add<mode>3_carry1_cconly"
5208 [(set (reg CC_REGNUM)
5209 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5210 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5211 (match_dup 1)))
5212 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5213 "s390_match_ccmode (insn, CCL1mode)"
5214 "@
5215 al<g>r\t%0,%2
5216 al<g>rk\t%0,%1,%2
5217 al<g>\t%0,%2
5218 al<y>\t%0,%2"
5219 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5220 (set_attr "cpu_facility" "*,z196,*,*")
5221 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5222
5223 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5224 (define_insn "*add<mode>3_carry2_cc"
5225 [(set (reg CC_REGNUM)
5226 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0, 0")
5227 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T, C"))
5228 (match_dup 2)))
5229 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,RS")
5230 (plus:GPR (match_dup 1) (match_dup 2)))]
5231 "s390_match_ccmode (insn, CCL1mode)"
5232 "@
5233 al<g>r\t%0,%2
5234 al<g>rk\t%0,%1,%2
5235 al<g>fi\t%0,%2
5236 sl<g>fi\t%0,%n2
5237 al<g>hsik\t%0,%1,%h2
5238 al<g>\t%0,%2
5239 al<y>\t%0,%2
5240 al<g>si\t%0,%c2"
5241 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5242 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5243 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5244 z10_super_E1,z10_super_E1,z10_super_E1")])
5245
5246 ; alr, al, aly, algr, alg, alrk, algrk
5247 (define_insn "*add<mode>3_carry2_cconly"
5248 [(set (reg CC_REGNUM)
5249 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5250 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5251 (match_dup 2)))
5252 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5253 "s390_match_ccmode (insn, CCL1mode)"
5254 "@
5255 al<g>r\t%0,%2
5256 al<g>rk\t%0,%1,%2
5257 al<g>\t%0,%2
5258 al<y>\t%0,%2"
5259 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5260 (set_attr "cpu_facility" "*,z196,*,*")
5261 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5262
5263 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5264 (define_insn "*add<mode>3_cc"
5265 [(set (reg CC_REGNUM)
5266 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0, 0")
5267 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T, C"))
5268 (const_int 0)))
5269 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,RS")
5270 (plus:GPR (match_dup 1) (match_dup 2)))]
5271 "s390_match_ccmode (insn, CCLmode)"
5272 "@
5273 al<g>r\t%0,%2
5274 al<g>rk\t%0,%1,%2
5275 al<g>fi\t%0,%2
5276 sl<g>fi\t%0,%n2
5277 al<g>hsik\t%0,%1,%h2
5278 al<g>\t%0,%2
5279 al<y>\t%0,%2
5280 al<g>si\t%0,%c2"
5281 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5282 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,*,z10")
5283 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,
5284 *,z10_super_E1,z10_super_E1,z10_super_E1")])
5285
5286 ; alr, al, aly, algr, alg, alrk, algrk
5287 (define_insn "*add<mode>3_cconly"
5288 [(set (reg CC_REGNUM)
5289 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5290 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5291 (const_int 0)))
5292 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5293 "s390_match_ccmode (insn, CCLmode)"
5294 "@
5295 al<g>r\t%0,%2
5296 al<g>rk\t%0,%1,%2
5297 al<g>\t%0,%2
5298 al<y>\t%0,%2"
5299 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5300 (set_attr "cpu_facility" "*,z196,*,*")
5301 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5302
5303 ; alr, al, aly, algr, alg, alrk, algrk
5304 (define_insn "*add<mode>3_cconly2"
5305 [(set (reg CC_REGNUM)
5306 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5307 (neg:GPR (match_operand:GPR 2 "general_operand" "d,d,R,T"))))
5308 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5309 "s390_match_ccmode(insn, CCLmode)"
5310 "@
5311 al<g>r\t%0,%2
5312 al<g>rk\t%0,%1,%2
5313 al<g>\t%0,%2
5314 al<y>\t%0,%2"
5315 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5316 (set_attr "cpu_facility" "*,z196,*,*")
5317 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5318
5319 ; ahi, afi, aghi, agfi, asi, agsi
5320 (define_insn "*add<mode>3_imm_cc"
5321 [(set (reg CC_REGNUM)
5322 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" " 0, d,0, 0")
5323 (match_operand:GPR 2 "const_int_operand" " K, K,Os, C"))
5324 (const_int 0)))
5325 (set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,d,QS")
5326 (plus:GPR (match_dup 1) (match_dup 2)))]
5327 "s390_match_ccmode (insn, CCAmode)
5328 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
5329 || (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
5330 /* Avoid INT32_MIN on 32 bit. */
5331 && (!TARGET_ZARCH || INTVAL (operands[2]) != -0x7fffffff - 1)))"
5332 "@
5333 a<g>hi\t%0,%h2
5334 a<g>hik\t%0,%1,%h2
5335 a<g>fi\t%0,%2
5336 a<g>si\t%0,%c2"
5337 [(set_attr "op_type" "RI,RIE,RIL,SIY")
5338 (set_attr "cpu_facility" "*,z196,extimm,z10")
5339 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5340
5341 ;
5342 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
5343 ;
5344
5345 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5346 ; FIXME: wfadb does not clobber cc
5347 (define_insn "add<mode>3"
5348 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
5349 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>, 0,<v0>")
5350 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))
5351 (clobber (reg:CC CC_REGNUM))]
5352 "TARGET_HARD_FLOAT"
5353 "@
5354 a<xde><bt>r\t%0,<op1>%2
5355 a<xde>b\t%0,%2
5356 wfadb\t%v0,%v1,%v2"
5357 [(set_attr "op_type" "<RRer>,RXE,VRR")
5358 (set_attr "type" "fsimp<mode>")
5359 (set_attr "cpu_facility" "*,*,vec")])
5360
5361 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5362 (define_insn "*add<mode>3_cc"
5363 [(set (reg CC_REGNUM)
5364 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
5365 (match_operand:FP 2 "general_operand" " f,<Rf>"))
5366 (match_operand:FP 3 "const0_operand" "")))
5367 (set (match_operand:FP 0 "register_operand" "=f,f")
5368 (plus:FP (match_dup 1) (match_dup 2)))]
5369 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5370 "@
5371 a<xde><bt>r\t%0,<op1>%2
5372 a<xde>b\t%0,%2"
5373 [(set_attr "op_type" "<RRer>,RXE")
5374 (set_attr "type" "fsimp<mode>")])
5375
5376 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5377 (define_insn "*add<mode>3_cconly"
5378 [(set (reg CC_REGNUM)
5379 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
5380 (match_operand:FP 2 "general_operand" " f,<Rf>"))
5381 (match_operand:FP 3 "const0_operand" "")))
5382 (clobber (match_scratch:FP 0 "=f,f"))]
5383 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5384 "@
5385 a<xde><bt>r\t%0,<op1>%2
5386 a<xde>b\t%0,%2"
5387 [(set_attr "op_type" "<RRer>,RXE")
5388 (set_attr "type" "fsimp<mode>")])
5389
5390 ;
5391 ; Pointer add instruction patterns
5392 ;
5393
5394 ; This will match "*la_64"
5395 (define_expand "addptrdi3"
5396 [(set (match_operand:DI 0 "register_operand" "")
5397 (plus:DI (match_operand:DI 1 "register_operand" "")
5398 (match_operand:DI 2 "nonmemory_operand" "")))]
5399 "TARGET_64BIT"
5400 {
5401 if (GET_CODE (operands[2]) == CONST_INT)
5402 {
5403 HOST_WIDE_INT c = INTVAL (operands[2]);
5404
5405 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5406 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5407 {
5408 operands[2] = force_const_mem (DImode, operands[2]);
5409 operands[2] = force_reg (DImode, operands[2]);
5410 }
5411 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5412 operands[2] = force_reg (DImode, operands[2]);
5413 }
5414 })
5415
5416 ; For 31 bit we have to prevent the generated pattern from matching
5417 ; normal ADDs since la only does a 31 bit add. This is supposed to
5418 ; match "force_la_31".
5419 (define_expand "addptrsi3"
5420 [(parallel
5421 [(set (match_operand:SI 0 "register_operand" "")
5422 (plus:SI (match_operand:SI 1 "register_operand" "")
5423 (match_operand:SI 2 "nonmemory_operand" "")))
5424 (use (const_int 0))])]
5425 "!TARGET_64BIT"
5426 {
5427 if (GET_CODE (operands[2]) == CONST_INT)
5428 {
5429 HOST_WIDE_INT c = INTVAL (operands[2]);
5430
5431 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5432 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5433 {
5434 operands[2] = force_const_mem (SImode, operands[2]);
5435 operands[2] = force_reg (SImode, operands[2]);
5436 }
5437 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5438 operands[2] = force_reg (SImode, operands[2]);
5439 }
5440 })
5441
5442 ;;
5443 ;;- Subtract instructions.
5444 ;;
5445
5446 ;
5447 ; subti3 instruction pattern(s).
5448 ;
5449
5450 (define_expand "subti3"
5451 [(parallel
5452 [(set (match_operand:TI 0 "register_operand" "")
5453 (minus:TI (match_operand:TI 1 "register_operand" "")
5454 (match_operand:TI 2 "general_operand" "") ) )
5455 (clobber (reg:CC CC_REGNUM))])]
5456 "TARGET_ZARCH"
5457 {
5458 /* For z13 we have vaq which doesn't set CC. */
5459 if (TARGET_VX)
5460 {
5461 emit_insn (gen_rtx_SET (operands[0],
5462 gen_rtx_MINUS (TImode,
5463 operands[1],
5464 copy_to_mode_reg (TImode, operands[2]))));
5465 DONE;
5466 }
5467 })
5468
5469 (define_insn_and_split "*subti3"
5470 [(set (match_operand:TI 0 "register_operand" "=&d")
5471 (minus:TI (match_operand:TI 1 "register_operand" "0")
5472 (match_operand:TI 2 "general_operand" "do") ) )
5473 (clobber (reg:CC CC_REGNUM))]
5474 "TARGET_ZARCH"
5475 "#"
5476 "&& reload_completed"
5477 [(parallel
5478 [(set (reg:CCL2 CC_REGNUM)
5479 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
5480 (match_dup 7)))
5481 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
5482 (parallel
5483 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
5484 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
5485 (clobber (reg:CC CC_REGNUM))])]
5486 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5487 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5488 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5489 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5490 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5491 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5492 [(set_attr "op_type" "*")
5493 (set_attr "cpu_facility" "*")])
5494
5495 ;
5496 ; subdi3 instruction pattern(s).
5497 ;
5498
5499 (define_expand "subdi3"
5500 [(parallel
5501 [(set (match_operand:DI 0 "register_operand" "")
5502 (minus:DI (match_operand:DI 1 "register_operand" "")
5503 (match_operand:DI 2 "general_operand" "")))
5504 (clobber (reg:CC CC_REGNUM))])]
5505 ""
5506 "")
5507
5508 (define_insn "*subdi3_sign"
5509 [(set (match_operand:DI 0 "register_operand" "=d,d")
5510 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5511 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
5512 (clobber (reg:CC CC_REGNUM))]
5513 "TARGET_ZARCH"
5514 "@
5515 sgfr\t%0,%2
5516 sgf\t%0,%2"
5517 [(set_attr "op_type" "RRE,RXY")
5518 (set_attr "z10prop" "z10_c,*")
5519 (set_attr "z196prop" "z196_cracked")])
5520
5521 (define_insn "*subdi3_zero_cc"
5522 [(set (reg CC_REGNUM)
5523 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5524 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
5525 (const_int 0)))
5526 (set (match_operand:DI 0 "register_operand" "=d,d")
5527 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
5528 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5529 "@
5530 slgfr\t%0,%2
5531 slgf\t%0,%2"
5532 [(set_attr "op_type" "RRE,RXY")
5533 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5534
5535 (define_insn "*subdi3_zero_cconly"
5536 [(set (reg CC_REGNUM)
5537 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5538 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
5539 (const_int 0)))
5540 (clobber (match_scratch:DI 0 "=d,d"))]
5541 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5542 "@
5543 slgfr\t%0,%2
5544 slgf\t%0,%2"
5545 [(set_attr "op_type" "RRE,RXY")
5546 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5547
5548 (define_insn "*subdi3_zero"
5549 [(set (match_operand:DI 0 "register_operand" "=d,d")
5550 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5551 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
5552 (clobber (reg:CC CC_REGNUM))]
5553 "TARGET_ZARCH"
5554 "@
5555 slgfr\t%0,%2
5556 slgf\t%0,%2"
5557 [(set_attr "op_type" "RRE,RXY")
5558 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5559
5560 (define_insn_and_split "*subdi3_31z"
5561 [(set (match_operand:DI 0 "register_operand" "=&d")
5562 (minus:DI (match_operand:DI 1 "register_operand" "0")
5563 (match_operand:DI 2 "general_operand" "do") ) )
5564 (clobber (reg:CC CC_REGNUM))]
5565 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5566 "#"
5567 "&& reload_completed"
5568 [(parallel
5569 [(set (reg:CCL2 CC_REGNUM)
5570 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5571 (match_dup 7)))
5572 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5573 (parallel
5574 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
5575 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
5576 (clobber (reg:CC CC_REGNUM))])]
5577 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5578 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5579 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5580 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5581 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5582 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5583
5584 (define_insn_and_split "*subdi3_31"
5585 [(set (match_operand:DI 0 "register_operand" "=&d")
5586 (minus:DI (match_operand:DI 1 "register_operand" "0")
5587 (match_operand:DI 2 "general_operand" "do") ) )
5588 (clobber (reg:CC CC_REGNUM))]
5589 "!TARGET_CPU_ZARCH"
5590 "#"
5591 "&& reload_completed"
5592 [(parallel
5593 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
5594 (clobber (reg:CC CC_REGNUM))])
5595 (parallel
5596 [(set (reg:CCL2 CC_REGNUM)
5597 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5598 (match_dup 7)))
5599 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5600 (set (pc)
5601 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
5602 (pc)
5603 (label_ref (match_dup 9))))
5604 (parallel
5605 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
5606 (clobber (reg:CC CC_REGNUM))])
5607 (match_dup 9)]
5608 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5609 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5610 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5611 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5612 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5613 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5614 operands[9] = gen_label_rtx ();")
5615
5616 ;
5617 ; subsi3 instruction pattern(s).
5618 ;
5619
5620 (define_expand "subsi3"
5621 [(parallel
5622 [(set (match_operand:SI 0 "register_operand" "")
5623 (minus:SI (match_operand:SI 1 "register_operand" "")
5624 (match_operand:SI 2 "general_operand" "")))
5625 (clobber (reg:CC CC_REGNUM))])]
5626 ""
5627 "")
5628
5629 (define_insn "*subsi3_sign"
5630 [(set (match_operand:SI 0 "register_operand" "=d,d")
5631 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
5632 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
5633 (clobber (reg:CC CC_REGNUM))]
5634 ""
5635 "@
5636 sh\t%0,%2
5637 shy\t%0,%2"
5638 [(set_attr "op_type" "RX,RXY")
5639 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5640
5641 ;
5642 ; sub(di|si)3 instruction pattern(s).
5643 ;
5644
5645 ; sr, s, sy, sgr, sg, srk, sgrk
5646 (define_insn "*sub<mode>3"
5647 [(set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5648 (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5649 (match_operand:GPR 2 "general_operand" "d,d,R,T") ) )
5650 (clobber (reg:CC CC_REGNUM))]
5651 ""
5652 "@
5653 s<g>r\t%0,%2
5654 s<g>rk\t%0,%1,%2
5655 s<g>\t%0,%2
5656 s<y>\t%0,%2"
5657 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5658 (set_attr "cpu_facility" "*,z196,*,*")
5659 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5660
5661 ; slr, sl, sly, slgr, slg, slrk, slgrk
5662 (define_insn "*sub<mode>3_borrow_cc"
5663 [(set (reg CC_REGNUM)
5664 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5665 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5666 (match_dup 1)))
5667 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5668 (minus:GPR (match_dup 1) (match_dup 2)))]
5669 "s390_match_ccmode (insn, CCL2mode)"
5670 "@
5671 sl<g>r\t%0,%2
5672 sl<g>rk\t%0,%1,%2
5673 sl<g>\t%0,%2
5674 sl<y>\t%0,%2"
5675 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5676 (set_attr "cpu_facility" "*,z196,*,*")
5677 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5678
5679 ; slr, sl, sly, slgr, slg, slrk, slgrk
5680 (define_insn "*sub<mode>3_borrow_cconly"
5681 [(set (reg CC_REGNUM)
5682 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5683 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5684 (match_dup 1)))
5685 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5686 "s390_match_ccmode (insn, CCL2mode)"
5687 "@
5688 sl<g>r\t%0,%2
5689 sl<g>rk\t%0,%1,%2
5690 sl<g>\t%0,%2
5691 sl<y>\t%0,%2"
5692 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5693 (set_attr "cpu_facility" "*,z196,*,*")
5694 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5695
5696 ; slr, sl, sly, slgr, slg, slrk, slgrk
5697 (define_insn "*sub<mode>3_cc"
5698 [(set (reg CC_REGNUM)
5699 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5700 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5701 (const_int 0)))
5702 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5703 (minus:GPR (match_dup 1) (match_dup 2)))]
5704 "s390_match_ccmode (insn, CCLmode)"
5705 "@
5706 sl<g>r\t%0,%2
5707 sl<g>rk\t%0,%1,%2
5708 sl<g>\t%0,%2
5709 sl<y>\t%0,%2"
5710 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5711 (set_attr "cpu_facility" "*,z196,*,*")
5712 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5713
5714 ; slr, sl, sly, slgr, slg, slrk, slgrk
5715 (define_insn "*sub<mode>3_cc2"
5716 [(set (reg CC_REGNUM)
5717 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
5718 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
5719 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
5720 (minus:GPR (match_dup 1) (match_dup 2)))]
5721 "s390_match_ccmode (insn, CCL3mode)"
5722 "@
5723 sl<g>r\t%0,%2
5724 sl<g>rk\t%0,%1,%2
5725 sl<g>\t%0,%2
5726 sl<y>\t%0,%2"
5727 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5728 (set_attr "cpu_facility" "*,z196,*,*")
5729 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5730
5731 ; slr, sl, sly, slgr, slg, slrk, slgrk
5732 (define_insn "*sub<mode>3_cconly"
5733 [(set (reg CC_REGNUM)
5734 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
5735 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5736 (const_int 0)))
5737 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5738 "s390_match_ccmode (insn, CCLmode)"
5739 "@
5740 sl<g>r\t%0,%2
5741 sl<g>rk\t%0,%1,%2
5742 sl<g>\t%0,%2
5743 sl<y>\t%0,%2"
5744 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5745 (set_attr "cpu_facility" "*,z196,*,*")
5746 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5747
5748
5749 ; slr, sl, sly, slgr, slg, slrk, slgrk
5750 (define_insn "*sub<mode>3_cconly2"
5751 [(set (reg CC_REGNUM)
5752 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
5753 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
5754 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5755 "s390_match_ccmode (insn, CCL3mode)"
5756 "@
5757 sl<g>r\t%0,%2
5758 sl<g>rk\t%0,%1,%2
5759 sl<g>\t%0,%2
5760 sl<y>\t%0,%2"
5761 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5762 (set_attr "cpu_facility" "*,z196,*,*")
5763 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
5764
5765
5766 ;
5767 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
5768 ;
5769
5770 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5771 (define_insn "sub<mode>3"
5772 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
5773 (minus:FP (match_operand:FP 1 "register_operand" "<f0>, 0,<v0>")
5774 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))
5775 (clobber (reg:CC CC_REGNUM))]
5776 "TARGET_HARD_FLOAT"
5777 "@
5778 s<xde><bt>r\t%0,<op1>%2
5779 s<xde>b\t%0,%2
5780 wfsdb\t%v0,%v1,%v2"
5781 [(set_attr "op_type" "<RRer>,RXE,VRR")
5782 (set_attr "type" "fsimp<mode>")
5783 (set_attr "cpu_facility" "*,*,vec")])
5784
5785 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5786 (define_insn "*sub<mode>3_cc"
5787 [(set (reg CC_REGNUM)
5788 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
5789 (match_operand:FP 2 "general_operand" "f,<Rf>"))
5790 (match_operand:FP 3 "const0_operand" "")))
5791 (set (match_operand:FP 0 "register_operand" "=f,f")
5792 (minus:FP (match_dup 1) (match_dup 2)))]
5793 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5794 "@
5795 s<xde><bt>r\t%0,<op1>%2
5796 s<xde>b\t%0,%2"
5797 [(set_attr "op_type" "<RRer>,RXE")
5798 (set_attr "type" "fsimp<mode>")])
5799
5800 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
5801 (define_insn "*sub<mode>3_cconly"
5802 [(set (reg CC_REGNUM)
5803 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
5804 (match_operand:FP 2 "general_operand" "f,<Rf>"))
5805 (match_operand:FP 3 "const0_operand" "")))
5806 (clobber (match_scratch:FP 0 "=f,f"))]
5807 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5808 "@
5809 s<xde><bt>r\t%0,<op1>%2
5810 s<xde>b\t%0,%2"
5811 [(set_attr "op_type" "<RRer>,RXE")
5812 (set_attr "type" "fsimp<mode>")])
5813
5814
5815 ;;
5816 ;;- Conditional add/subtract instructions.
5817 ;;
5818
5819 ;
5820 ; add(di|si)cc instruction pattern(s).
5821 ;
5822
5823 ; the following 4 patterns are used when the result of an add with
5824 ; carry is checked for an overflow condition
5825
5826 ; op1 + op2 + c < op1
5827
5828 ; alcr, alc, alcgr, alcg
5829 (define_insn "*add<mode>3_alc_carry1_cc"
5830 [(set (reg CC_REGNUM)
5831 (compare
5832 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5833 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5834 (match_operand:GPR 2 "general_operand" "d,RT"))
5835 (match_dup 1)))
5836 (set (match_operand:GPR 0 "register_operand" "=d,d")
5837 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
5838 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5839 "@
5840 alc<g>r\t%0,%2
5841 alc<g>\t%0,%2"
5842 [(set_attr "op_type" "RRE,RXY")
5843 (set_attr "z196prop" "z196_alone,z196_alone")])
5844
5845 ; alcr, alc, alcgr, alcg
5846 (define_insn "*add<mode>3_alc_carry1_cconly"
5847 [(set (reg CC_REGNUM)
5848 (compare
5849 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5850 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5851 (match_operand:GPR 2 "general_operand" "d,RT"))
5852 (match_dup 1)))
5853 (clobber (match_scratch:GPR 0 "=d,d"))]
5854 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5855 "@
5856 alc<g>r\t%0,%2
5857 alc<g>\t%0,%2"
5858 [(set_attr "op_type" "RRE,RXY")
5859 (set_attr "z196prop" "z196_alone,z196_alone")])
5860
5861 ; op1 + op2 + c < op2
5862
5863 ; alcr, alc, alcgr, alcg
5864 (define_insn "*add<mode>3_alc_carry2_cc"
5865 [(set (reg CC_REGNUM)
5866 (compare
5867 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5868 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5869 (match_operand:GPR 2 "general_operand" "d,RT"))
5870 (match_dup 2)))
5871 (set (match_operand:GPR 0 "register_operand" "=d,d")
5872 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
5873 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5874 "@
5875 alc<g>r\t%0,%2
5876 alc<g>\t%0,%2"
5877 [(set_attr "op_type" "RRE,RXY")])
5878
5879 ; alcr, alc, alcgr, alcg
5880 (define_insn "*add<mode>3_alc_carry2_cconly"
5881 [(set (reg CC_REGNUM)
5882 (compare
5883 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5884 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5885 (match_operand:GPR 2 "general_operand" "d,RT"))
5886 (match_dup 2)))
5887 (clobber (match_scratch:GPR 0 "=d,d"))]
5888 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
5889 "@
5890 alc<g>r\t%0,%2
5891 alc<g>\t%0,%2"
5892 [(set_attr "op_type" "RRE,RXY")])
5893
5894 ; alcr, alc, alcgr, alcg
5895 (define_insn "*add<mode>3_alc_cc"
5896 [(set (reg CC_REGNUM)
5897 (compare
5898 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5899 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5900 (match_operand:GPR 2 "general_operand" "d,RT"))
5901 (const_int 0)))
5902 (set (match_operand:GPR 0 "register_operand" "=d,d")
5903 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
5904 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
5905 "@
5906 alc<g>r\t%0,%2
5907 alc<g>\t%0,%2"
5908 [(set_attr "op_type" "RRE,RXY")])
5909
5910 ; alcr, alc, alcgr, alcg
5911 (define_insn "*add<mode>3_alc"
5912 [(set (match_operand:GPR 0 "register_operand" "=d,d")
5913 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
5914 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
5915 (match_operand:GPR 2 "general_operand" "d,RT")))
5916 (clobber (reg:CC CC_REGNUM))]
5917 "TARGET_CPU_ZARCH"
5918 "@
5919 alc<g>r\t%0,%2
5920 alc<g>\t%0,%2"
5921 [(set_attr "op_type" "RRE,RXY")])
5922
5923 ; slbr, slb, slbgr, slbg
5924 (define_insn "*sub<mode>3_slb_cc"
5925 [(set (reg CC_REGNUM)
5926 (compare
5927 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
5928 (match_operand:GPR 2 "general_operand" "d,RT"))
5929 (match_operand:GPR 3 "s390_slb_comparison" ""))
5930 (const_int 0)))
5931 (set (match_operand:GPR 0 "register_operand" "=d,d")
5932 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
5933 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
5934 "@
5935 slb<g>r\t%0,%2
5936 slb<g>\t%0,%2"
5937 [(set_attr "op_type" "RRE,RXY")
5938 (set_attr "z10prop" "z10_c,*")])
5939
5940 ; slbr, slb, slbgr, slbg
5941 (define_insn "*sub<mode>3_slb"
5942 [(set (match_operand:GPR 0 "register_operand" "=d,d")
5943 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
5944 (match_operand:GPR 2 "general_operand" "d,RT"))
5945 (match_operand:GPR 3 "s390_slb_comparison" "")))
5946 (clobber (reg:CC CC_REGNUM))]
5947 "TARGET_CPU_ZARCH"
5948 "@
5949 slb<g>r\t%0,%2
5950 slb<g>\t%0,%2"
5951 [(set_attr "op_type" "RRE,RXY")
5952 (set_attr "z10prop" "z10_c,*")])
5953
5954 (define_expand "add<mode>cc"
5955 [(match_operand:GPR 0 "register_operand" "")
5956 (match_operand 1 "comparison_operator" "")
5957 (match_operand:GPR 2 "register_operand" "")
5958 (match_operand:GPR 3 "const_int_operand" "")]
5959 "TARGET_CPU_ZARCH"
5960 "if (!s390_expand_addcc (GET_CODE (operands[1]),
5961 XEXP (operands[1], 0), XEXP (operands[1], 1),
5962 operands[0], operands[2],
5963 operands[3])) FAIL; DONE;")
5964
5965 ;
5966 ; scond instruction pattern(s).
5967 ;
5968
5969 (define_insn_and_split "*scond<mode>"
5970 [(set (match_operand:GPR 0 "register_operand" "=&d")
5971 (match_operand:GPR 1 "s390_alc_comparison" ""))
5972 (clobber (reg:CC CC_REGNUM))]
5973 "TARGET_CPU_ZARCH"
5974 "#"
5975 "&& reload_completed"
5976 [(set (match_dup 0) (const_int 0))
5977 (parallel
5978 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
5979 (match_dup 0)))
5980 (clobber (reg:CC CC_REGNUM))])]
5981 "")
5982
5983 (define_insn_and_split "*scond<mode>_neg"
5984 [(set (match_operand:GPR 0 "register_operand" "=&d")
5985 (match_operand:GPR 1 "s390_slb_comparison" ""))
5986 (clobber (reg:CC CC_REGNUM))]
5987 "TARGET_CPU_ZARCH"
5988 "#"
5989 "&& reload_completed"
5990 [(set (match_dup 0) (const_int 0))
5991 (parallel
5992 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
5993 (match_dup 1)))
5994 (clobber (reg:CC CC_REGNUM))])
5995 (parallel
5996 [(set (match_dup 0) (neg:GPR (match_dup 0)))
5997 (clobber (reg:CC CC_REGNUM))])]
5998 "")
5999
6000
6001 (define_expand "cstore<mode>4"
6002 [(set (match_operand:SI 0 "register_operand" "")
6003 (match_operator:SI 1 "s390_scond_operator"
6004 [(match_operand:GPR 2 "register_operand" "")
6005 (match_operand:GPR 3 "general_operand" "")]))]
6006 "TARGET_CPU_ZARCH"
6007 "if (!s390_expand_addcc (GET_CODE (operands[1]), operands[2], operands[3],
6008 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
6009
6010 (define_expand "cstorecc4"
6011 [(parallel
6012 [(set (match_operand:SI 0 "register_operand" "")
6013 (match_operator:SI 1 "s390_eqne_operator"
6014 [(match_operand:CCZ1 2 "register_operand")
6015 (match_operand 3 "const0_operand")]))
6016 (clobber (reg:CC CC_REGNUM))])]
6017 ""
6018 "emit_insn (gen_sne (operands[0], operands[2]));
6019 if (GET_CODE (operands[1]) == EQ)
6020 emit_insn (gen_xorsi3 (operands[0], operands[0], const1_rtx));
6021 DONE;")
6022
6023 (define_insn_and_split "sne"
6024 [(set (match_operand:SI 0 "register_operand" "=d")
6025 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
6026 (const_int 0)))
6027 (clobber (reg:CC CC_REGNUM))]
6028 ""
6029 "#"
6030 "reload_completed"
6031 [(parallel
6032 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
6033 (clobber (reg:CC CC_REGNUM))])])
6034
6035
6036 ;;
6037 ;; - Conditional move instructions (introduced with z196)
6038 ;;
6039
6040 (define_expand "mov<mode>cc"
6041 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
6042 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
6043 (match_operand:GPR 2 "nonimmediate_operand" "")
6044 (match_operand:GPR 3 "nonimmediate_operand" "")))]
6045 "TARGET_Z196"
6046 "operands[1] = s390_emit_compare (GET_CODE (operands[1]),
6047 XEXP (operands[1], 0), XEXP (operands[1], 1));")
6048
6049 ; locr, loc, stoc, locgr, locg, stocg
6050 (define_insn_and_split "*mov<mode>cc"
6051 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,QS,QS,&d")
6052 (if_then_else:GPR
6053 (match_operator 1 "s390_comparison"
6054 [(match_operand 2 "cc_reg_operand" " c,c, c, c, c, c, c")
6055 (match_operand 5 "const_int_operand" "")])
6056 (match_operand:GPR 3 "nonimmediate_operand" " d,0,QS, 0, d, 0,QS")
6057 (match_operand:GPR 4 "nonimmediate_operand" " 0,d, 0,QS, 0, d,QS")))]
6058 "TARGET_Z196"
6059 "@
6060 loc<g>r%C1\t%0,%3
6061 loc<g>r%D1\t%0,%4
6062 loc<g>%C1\t%0,%3
6063 loc<g>%D1\t%0,%4
6064 stoc<g>%C1\t%3,%0
6065 stoc<g>%D1\t%4,%0
6066 #"
6067 "&& reload_completed
6068 && MEM_P (operands[3]) && MEM_P (operands[4])"
6069 [(set (match_dup 0)
6070 (if_then_else:GPR
6071 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6072 (match_dup 3)
6073 (match_dup 0)))
6074 (set (match_dup 0)
6075 (if_then_else:GPR
6076 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6077 (match_dup 0)
6078 (match_dup 4)))]
6079 ""
6080 [(set_attr "op_type" "RRF,RRF,RSY,RSY,RSY,RSY,*")])
6081
6082 ;;
6083 ;;- Multiply instructions.
6084 ;;
6085
6086 ;
6087 ; muldi3 instruction pattern(s).
6088 ;
6089
6090 (define_insn "*muldi3_sign"
6091 [(set (match_operand:DI 0 "register_operand" "=d,d")
6092 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
6093 (match_operand:DI 1 "register_operand" "0,0")))]
6094 "TARGET_ZARCH"
6095 "@
6096 msgfr\t%0,%2
6097 msgf\t%0,%2"
6098 [(set_attr "op_type" "RRE,RXY")
6099 (set_attr "type" "imuldi")])
6100
6101 (define_insn "muldi3"
6102 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
6103 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
6104 (match_operand:DI 2 "general_operand" "d,K,RT,Os")))]
6105 "TARGET_ZARCH"
6106 "@
6107 msgr\t%0,%2
6108 mghi\t%0,%h2
6109 msg\t%0,%2
6110 msgfi\t%0,%2"
6111 [(set_attr "op_type" "RRE,RI,RXY,RIL")
6112 (set_attr "type" "imuldi")
6113 (set_attr "cpu_facility" "*,*,*,z10")])
6114
6115 ;
6116 ; mulsi3 instruction pattern(s).
6117 ;
6118
6119 (define_insn "*mulsi3_sign"
6120 [(set (match_operand:SI 0 "register_operand" "=d,d")
6121 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
6122 (match_operand:SI 1 "register_operand" "0,0")))]
6123 ""
6124 "@
6125 mh\t%0,%2
6126 mhy\t%0,%2"
6127 [(set_attr "op_type" "RX,RXY")
6128 (set_attr "type" "imulhi")
6129 (set_attr "cpu_facility" "*,z10")])
6130
6131 (define_insn "mulsi3"
6132 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
6133 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
6134 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
6135 ""
6136 "@
6137 msr\t%0,%2
6138 mhi\t%0,%h2
6139 ms\t%0,%2
6140 msy\t%0,%2
6141 msfi\t%0,%2"
6142 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
6143 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
6144 (set_attr "cpu_facility" "*,*,*,*,z10")])
6145
6146 ;
6147 ; mulsidi3 instruction pattern(s).
6148 ;
6149
6150 (define_insn "mulsidi3"
6151 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
6152 (mult:DI (sign_extend:DI
6153 (match_operand:SI 1 "register_operand" "%0,0,0"))
6154 (sign_extend:DI
6155 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
6156 "!TARGET_ZARCH"
6157 "@
6158 mr\t%0,%2
6159 m\t%0,%2
6160 mfy\t%0,%2"
6161 [(set_attr "op_type" "RR,RX,RXY")
6162 (set_attr "type" "imulsi")
6163 (set_attr "cpu_facility" "*,*,z10")])
6164
6165 ;
6166 ; umul instruction pattern(s).
6167 ;
6168
6169 ; mlr, ml, mlgr, mlg
6170 (define_insn "umul<dwh><mode>3"
6171 [(set (match_operand:DW 0 "register_operand" "=d, d")
6172 (mult:DW (zero_extend:DW
6173 (match_operand:<DWH> 1 "register_operand" "%0, 0"))
6174 (zero_extend:DW
6175 (match_operand:<DWH> 2 "nonimmediate_operand" " d,RT"))))]
6176 "TARGET_CPU_ZARCH"
6177 "@
6178 ml<tg>r\t%0,%2
6179 ml<tg>\t%0,%2"
6180 [(set_attr "op_type" "RRE,RXY")
6181 (set_attr "type" "imul<dwh>")])
6182
6183 ;
6184 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
6185 ;
6186
6187 ; mxbr, mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
6188 (define_insn "mul<mode>3"
6189 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
6190 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>, 0,<v0>")
6191 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))]
6192 "TARGET_HARD_FLOAT"
6193 "@
6194 m<xdee><bt>r\t%0,<op1>%2
6195 m<xdee>b\t%0,%2
6196 wfmdb\t%v0,%v1,%v2"
6197 [(set_attr "op_type" "<RRer>,RXE,VRR")
6198 (set_attr "type" "fmul<mode>")
6199 (set_attr "cpu_facility" "*,*,vec")])
6200
6201 ; madbr, maebr, maxb, madb, maeb
6202 (define_insn "fma<mode>4"
6203 [(set (match_operand:DSF 0 "register_operand" "=f,f,<vf>")
6204 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,<vf>")
6205 (match_operand:DSF 2 "nonimmediate_operand" "f,R,<vf>")
6206 (match_operand:DSF 3 "register_operand" "0,0,<v0>")))]
6207 "TARGET_HARD_FLOAT"
6208 "@
6209 ma<xde>br\t%0,%1,%2
6210 ma<xde>b\t%0,%1,%2
6211 wfmadb\t%v0,%v1,%v2,%v3"
6212 [(set_attr "op_type" "RRE,RXE,VRR")
6213 (set_attr "type" "fmadd<mode>")
6214 (set_attr "cpu_facility" "*,*,vec")])
6215
6216 ; msxbr, msdbr, msebr, msxb, msdb, mseb
6217 (define_insn "fms<mode>4"
6218 [(set (match_operand:DSF 0 "register_operand" "=f,f,<vf>")
6219 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,<vf>")
6220 (match_operand:DSF 2 "nonimmediate_operand" "f,R,<vf>")
6221 (neg:DSF (match_operand:DSF 3 "register_operand" "0,0,<v0>"))))]
6222 "TARGET_HARD_FLOAT"
6223 "@
6224 ms<xde>br\t%0,%1,%2
6225 ms<xde>b\t%0,%1,%2
6226 wfmsdb\t%v0,%v1,%v2,%v3"
6227 [(set_attr "op_type" "RRE,RXE,VRR")
6228 (set_attr "type" "fmadd<mode>")
6229 (set_attr "cpu_facility" "*,*,vec")])
6230
6231 ;;
6232 ;;- Divide and modulo instructions.
6233 ;;
6234
6235 ;
6236 ; divmoddi4 instruction pattern(s).
6237 ;
6238
6239 (define_expand "divmoddi4"
6240 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6241 (div:DI (match_operand:DI 1 "register_operand" "")
6242 (match_operand:DI 2 "general_operand" "")))
6243 (set (match_operand:DI 3 "general_operand" "")
6244 (mod:DI (match_dup 1) (match_dup 2)))])
6245 (clobber (match_dup 4))]
6246 "TARGET_ZARCH"
6247 {
6248 rtx insn, div_equal, mod_equal;
6249
6250 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
6251 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
6252
6253 operands[4] = gen_reg_rtx(TImode);
6254 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
6255
6256 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6257 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6258
6259 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6260 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6261
6262 DONE;
6263 })
6264
6265 (define_insn "divmodtidi3"
6266 [(set (match_operand:TI 0 "register_operand" "=d,d")
6267 (ior:TI
6268 (ashift:TI
6269 (zero_extend:TI
6270 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6271 (match_operand:DI 2 "general_operand" "d,RT")))
6272 (const_int 64))
6273 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
6274 "TARGET_ZARCH"
6275 "@
6276 dsgr\t%0,%2
6277 dsg\t%0,%2"
6278 [(set_attr "op_type" "RRE,RXY")
6279 (set_attr "type" "idiv")])
6280
6281 (define_insn "divmodtisi3"
6282 [(set (match_operand:TI 0 "register_operand" "=d,d")
6283 (ior:TI
6284 (ashift:TI
6285 (zero_extend:TI
6286 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6287 (sign_extend:DI
6288 (match_operand:SI 2 "nonimmediate_operand" "d,RT"))))
6289 (const_int 64))
6290 (zero_extend:TI
6291 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
6292 "TARGET_ZARCH"
6293 "@
6294 dsgfr\t%0,%2
6295 dsgf\t%0,%2"
6296 [(set_attr "op_type" "RRE,RXY")
6297 (set_attr "type" "idiv")])
6298
6299 ;
6300 ; udivmoddi4 instruction pattern(s).
6301 ;
6302
6303 (define_expand "udivmoddi4"
6304 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6305 (udiv:DI (match_operand:DI 1 "general_operand" "")
6306 (match_operand:DI 2 "nonimmediate_operand" "")))
6307 (set (match_operand:DI 3 "general_operand" "")
6308 (umod:DI (match_dup 1) (match_dup 2)))])
6309 (clobber (match_dup 4))]
6310 "TARGET_ZARCH"
6311 {
6312 rtx insn, div_equal, mod_equal, equal;
6313
6314 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
6315 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
6316 equal = gen_rtx_IOR (TImode,
6317 gen_rtx_ASHIFT (TImode,
6318 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
6319 GEN_INT (64)),
6320 gen_rtx_ZERO_EXTEND (TImode, div_equal));
6321
6322 operands[4] = gen_reg_rtx(TImode);
6323 emit_clobber (operands[4]);
6324 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
6325 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
6326
6327 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
6328 set_unique_reg_note (insn, REG_EQUAL, equal);
6329
6330 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6331 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6332
6333 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6334 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6335
6336 DONE;
6337 })
6338
6339 (define_insn "udivmodtidi3"
6340 [(set (match_operand:TI 0 "register_operand" "=d,d")
6341 (ior:TI
6342 (ashift:TI
6343 (zero_extend:TI
6344 (truncate:DI
6345 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
6346 (zero_extend:TI
6347 (match_operand:DI 2 "nonimmediate_operand" "d,RT")))))
6348 (const_int 64))
6349 (zero_extend:TI
6350 (truncate:DI
6351 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
6352 "TARGET_ZARCH"
6353 "@
6354 dlgr\t%0,%2
6355 dlg\t%0,%2"
6356 [(set_attr "op_type" "RRE,RXY")
6357 (set_attr "type" "idiv")])
6358
6359 ;
6360 ; divmodsi4 instruction pattern(s).
6361 ;
6362
6363 (define_expand "divmodsi4"
6364 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6365 (div:SI (match_operand:SI 1 "general_operand" "")
6366 (match_operand:SI 2 "nonimmediate_operand" "")))
6367 (set (match_operand:SI 3 "general_operand" "")
6368 (mod:SI (match_dup 1) (match_dup 2)))])
6369 (clobber (match_dup 4))]
6370 "!TARGET_ZARCH"
6371 {
6372 rtx insn, div_equal, mod_equal, equal;
6373
6374 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
6375 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
6376 equal = gen_rtx_IOR (DImode,
6377 gen_rtx_ASHIFT (DImode,
6378 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6379 GEN_INT (32)),
6380 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6381
6382 operands[4] = gen_reg_rtx(DImode);
6383 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
6384
6385 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
6386 set_unique_reg_note (insn, REG_EQUAL, equal);
6387
6388 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6389 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6390
6391 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6392 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6393
6394 DONE;
6395 })
6396
6397 (define_insn "divmoddisi3"
6398 [(set (match_operand:DI 0 "register_operand" "=d,d")
6399 (ior:DI
6400 (ashift:DI
6401 (zero_extend:DI
6402 (truncate:SI
6403 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6404 (sign_extend:DI
6405 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
6406 (const_int 32))
6407 (zero_extend:DI
6408 (truncate:SI
6409 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
6410 "!TARGET_ZARCH"
6411 "@
6412 dr\t%0,%2
6413 d\t%0,%2"
6414 [(set_attr "op_type" "RR,RX")
6415 (set_attr "type" "idiv")])
6416
6417 ;
6418 ; udivsi3 and umodsi3 instruction pattern(s).
6419 ;
6420
6421 (define_expand "udivmodsi4"
6422 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6423 (udiv:SI (match_operand:SI 1 "general_operand" "")
6424 (match_operand:SI 2 "nonimmediate_operand" "")))
6425 (set (match_operand:SI 3 "general_operand" "")
6426 (umod:SI (match_dup 1) (match_dup 2)))])
6427 (clobber (match_dup 4))]
6428 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6429 {
6430 rtx insn, div_equal, mod_equal, equal;
6431
6432 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6433 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6434 equal = gen_rtx_IOR (DImode,
6435 gen_rtx_ASHIFT (DImode,
6436 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6437 GEN_INT (32)),
6438 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6439
6440 operands[4] = gen_reg_rtx(DImode);
6441 emit_clobber (operands[4]);
6442 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
6443 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
6444
6445 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
6446 set_unique_reg_note (insn, REG_EQUAL, equal);
6447
6448 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6449 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6450
6451 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6452 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6453
6454 DONE;
6455 })
6456
6457 (define_insn "udivmoddisi3"
6458 [(set (match_operand:DI 0 "register_operand" "=d,d")
6459 (ior:DI
6460 (ashift:DI
6461 (zero_extend:DI
6462 (truncate:SI
6463 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
6464 (zero_extend:DI
6465 (match_operand:SI 2 "nonimmediate_operand" "d,RT")))))
6466 (const_int 32))
6467 (zero_extend:DI
6468 (truncate:SI
6469 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
6470 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6471 "@
6472 dlr\t%0,%2
6473 dl\t%0,%2"
6474 [(set_attr "op_type" "RRE,RXY")
6475 (set_attr "type" "idiv")])
6476
6477 (define_expand "udivsi3"
6478 [(set (match_operand:SI 0 "register_operand" "=d")
6479 (udiv:SI (match_operand:SI 1 "general_operand" "")
6480 (match_operand:SI 2 "general_operand" "")))
6481 (clobber (match_dup 3))]
6482 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6483 {
6484 rtx insn, udiv_equal, umod_equal, equal;
6485
6486 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6487 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6488 equal = gen_rtx_IOR (DImode,
6489 gen_rtx_ASHIFT (DImode,
6490 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6491 GEN_INT (32)),
6492 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6493
6494 operands[3] = gen_reg_rtx (DImode);
6495
6496 if (CONSTANT_P (operands[2]))
6497 {
6498 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
6499 {
6500 rtx_code_label *label1 = gen_label_rtx ();
6501
6502 operands[1] = make_safe_from (operands[1], operands[0]);
6503 emit_move_insn (operands[0], const0_rtx);
6504 emit_cmp_and_jump_insns (operands[1], operands[2], LT, NULL_RTX,
6505 SImode, 1, label1);
6506 emit_move_insn (operands[0], const1_rtx);
6507 emit_label (label1);
6508 }
6509 else
6510 {
6511 operands[2] = force_reg (SImode, operands[2]);
6512 operands[2] = make_safe_from (operands[2], operands[0]);
6513
6514 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6515 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6516 operands[2]));
6517 set_unique_reg_note (insn, REG_EQUAL, equal);
6518
6519 insn = emit_move_insn (operands[0],
6520 gen_lowpart (SImode, operands[3]));
6521 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6522 }
6523 }
6524 else
6525 {
6526 rtx_code_label *label1 = gen_label_rtx ();
6527 rtx_code_label *label2 = gen_label_rtx ();
6528 rtx_code_label *label3 = gen_label_rtx ();
6529
6530 operands[1] = force_reg (SImode, operands[1]);
6531 operands[1] = make_safe_from (operands[1], operands[0]);
6532 operands[2] = force_reg (SImode, operands[2]);
6533 operands[2] = make_safe_from (operands[2], operands[0]);
6534
6535 emit_move_insn (operands[0], const0_rtx);
6536 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6537 SImode, 1, label3);
6538 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6539 SImode, 0, label2);
6540 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6541 SImode, 0, label1);
6542 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6543 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6544 operands[2]));
6545 set_unique_reg_note (insn, REG_EQUAL, equal);
6546
6547 insn = emit_move_insn (operands[0],
6548 gen_lowpart (SImode, operands[3]));
6549 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6550
6551 emit_jump (label3);
6552 emit_label (label1);
6553 emit_move_insn (operands[0], operands[1]);
6554 emit_jump (label3);
6555 emit_label (label2);
6556 emit_move_insn (operands[0], const1_rtx);
6557 emit_label (label3);
6558 }
6559 emit_move_insn (operands[0], operands[0]);
6560 DONE;
6561 })
6562
6563 (define_expand "umodsi3"
6564 [(set (match_operand:SI 0 "register_operand" "=d")
6565 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
6566 (match_operand:SI 2 "nonimmediate_operand" "")))
6567 (clobber (match_dup 3))]
6568 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6569 {
6570 rtx insn, udiv_equal, umod_equal, equal;
6571
6572 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6573 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6574 equal = gen_rtx_IOR (DImode,
6575 gen_rtx_ASHIFT (DImode,
6576 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6577 GEN_INT (32)),
6578 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6579
6580 operands[3] = gen_reg_rtx (DImode);
6581
6582 if (CONSTANT_P (operands[2]))
6583 {
6584 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
6585 {
6586 rtx_code_label *label1 = gen_label_rtx ();
6587
6588 operands[1] = make_safe_from (operands[1], operands[0]);
6589 emit_move_insn (operands[0], operands[1]);
6590 emit_cmp_and_jump_insns (operands[0], operands[2], LT, NULL_RTX,
6591 SImode, 1, label1);
6592 emit_insn (gen_abssi2 (operands[0], operands[2]));
6593 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
6594 emit_label (label1);
6595 }
6596 else
6597 {
6598 operands[2] = force_reg (SImode, operands[2]);
6599 operands[2] = make_safe_from (operands[2], operands[0]);
6600
6601 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6602 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6603 operands[2]));
6604 set_unique_reg_note (insn, REG_EQUAL, equal);
6605
6606 insn = emit_move_insn (operands[0],
6607 gen_highpart (SImode, operands[3]));
6608 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6609 }
6610 }
6611 else
6612 {
6613 rtx_code_label *label1 = gen_label_rtx ();
6614 rtx_code_label *label2 = gen_label_rtx ();
6615 rtx_code_label *label3 = gen_label_rtx ();
6616
6617 operands[1] = force_reg (SImode, operands[1]);
6618 operands[1] = make_safe_from (operands[1], operands[0]);
6619 operands[2] = force_reg (SImode, operands[2]);
6620 operands[2] = make_safe_from (operands[2], operands[0]);
6621
6622 emit_move_insn(operands[0], operands[1]);
6623 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6624 SImode, 1, label3);
6625 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6626 SImode, 0, label2);
6627 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6628 SImode, 0, label1);
6629 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6630 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6631 operands[2]));
6632 set_unique_reg_note (insn, REG_EQUAL, equal);
6633
6634 insn = emit_move_insn (operands[0],
6635 gen_highpart (SImode, operands[3]));
6636 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
6637
6638 emit_jump (label3);
6639 emit_label (label1);
6640 emit_move_insn (operands[0], const0_rtx);
6641 emit_jump (label3);
6642 emit_label (label2);
6643 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
6644 emit_label (label3);
6645 }
6646 DONE;
6647 })
6648
6649 ;
6650 ; div(df|sf)3 instruction pattern(s).
6651 ;
6652
6653 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
6654 (define_insn "div<mode>3"
6655 [(set (match_operand:FP 0 "register_operand" "=f, f,<vf>")
6656 (div:FP (match_operand:FP 1 "register_operand" "<f0>, 0,<v0>")
6657 (match_operand:FP 2 "general_operand" "f,<Rf>,<vf>")))]
6658 "TARGET_HARD_FLOAT"
6659 "@
6660 d<xde><bt>r\t%0,<op1>%2
6661 d<xde>b\t%0,%2
6662 wfddb\t%v0,%v1,%v2"
6663 [(set_attr "op_type" "<RRer>,RXE,VRR")
6664 (set_attr "type" "fdiv<mode>")
6665 (set_attr "cpu_facility" "*,*,vec")])
6666
6667
6668 ;;
6669 ;;- And instructions.
6670 ;;
6671
6672 (define_expand "and<mode>3"
6673 [(set (match_operand:INT 0 "nonimmediate_operand" "")
6674 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
6675 (match_operand:INT 2 "general_operand" "")))
6676 (clobber (reg:CC CC_REGNUM))]
6677 ""
6678 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
6679
6680 ;
6681 ; anddi3 instruction pattern(s).
6682 ;
6683
6684 (define_insn "*anddi3_cc"
6685 [(set (reg CC_REGNUM)
6686 (compare
6687 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0, d")
6688 (match_operand:DI 2 "general_operand" " d,d,RT,NxxDq"))
6689 (const_int 0)))
6690 (set (match_operand:DI 0 "register_operand" "=d,d, d, d")
6691 (and:DI (match_dup 1) (match_dup 2)))]
6692 "TARGET_ZARCH && s390_match_ccmode(insn, CCTmode)"
6693 "@
6694 ngr\t%0,%2
6695 ngrk\t%0,%1,%2
6696 ng\t%0,%2
6697 risbg\t%0,%1,%s2,128+%e2,0"
6698 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6699 (set_attr "cpu_facility" "*,z196,*,z10")
6700 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6701
6702 (define_insn "*anddi3_cconly"
6703 [(set (reg CC_REGNUM)
6704 (compare
6705 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0, d")
6706 (match_operand:DI 2 "general_operand" " d,d,RT,NxxDq"))
6707 (const_int 0)))
6708 (clobber (match_scratch:DI 0 "=d,d, d, d"))]
6709 "TARGET_ZARCH
6710 && s390_match_ccmode(insn, CCTmode)
6711 /* Do not steal TM patterns. */
6712 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
6713 "@
6714 ngr\t%0,%2
6715 ngrk\t%0,%1,%2
6716 ng\t%0,%2
6717 risbg\t%0,%1,%s2,128+%e2,0"
6718 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
6719 (set_attr "cpu_facility" "*,z196,*,z10")
6720 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
6721
6722 (define_insn "*anddi3"
6723 [(set (match_operand:DI 0 "nonimmediate_operand"
6724 "=d,d, d, d, d, d, d, d,d,d, d, d, AQ,Q")
6725 (and:DI
6726 (match_operand:DI 1 "nonimmediate_operand"
6727 "%d,o, 0, 0, 0, 0, 0, 0,0,d, 0, d, 0,0")
6728 (match_operand:DI 2 "general_operand"
6729 "M, M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,d,RT,NxxDq,NxQDF,Q")))
6730 (clobber (reg:CC CC_REGNUM))]
6731 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6732 "@
6733 #
6734 #
6735 nihh\t%0,%j2
6736 nihl\t%0,%j2
6737 nilh\t%0,%j2
6738 nill\t%0,%j2
6739 nihf\t%0,%m2
6740 nilf\t%0,%m2
6741 ngr\t%0,%2
6742 ngrk\t%0,%1,%2
6743 ng\t%0,%2
6744 risbg\t%0,%1,%s2,128+%e2,0
6745 #
6746 #"
6747 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,RIE,SI,SS")
6748 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,z196,*,z10,*,*")
6749 (set_attr "z10prop" "*,
6750 *,
6751 z10_super_E1,
6752 z10_super_E1,
6753 z10_super_E1,
6754 z10_super_E1,
6755 z10_super_E1,
6756 z10_super_E1,
6757 z10_super_E1,
6758 *,
6759 z10_super_E1,
6760 z10_super_E1,
6761 *,
6762 *")])
6763
6764 (define_split
6765 [(set (match_operand:DI 0 "s_operand" "")
6766 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
6767 (clobber (reg:CC CC_REGNUM))]
6768 "reload_completed"
6769 [(parallel
6770 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
6771 (clobber (reg:CC CC_REGNUM))])]
6772 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
6773
6774 ;; These two are what combine generates for (ashift (zero_extract)).
6775 (define_insn "*extzv_<mode>_srl"
6776 [(set (match_operand:GPR 0 "register_operand" "=d")
6777 (and:GPR (lshiftrt:GPR
6778 (match_operand:GPR 1 "register_operand" "d")
6779 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
6780 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
6781 (clobber (reg:CC CC_REGNUM))]
6782 "TARGET_Z10
6783 /* Note that even for the SImode pattern, the rotate is always DImode. */
6784 && s390_extzv_shift_ok (<bitsize>, -INTVAL (operands[2]),
6785 INTVAL (operands[3]))"
6786 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,64-%2"
6787 [(set_attr "op_type" "RIE")
6788 (set_attr "z10prop" "z10_super_E1")])
6789
6790 (define_insn "*extzv_<mode>_sll"
6791 [(set (match_operand:GPR 0 "register_operand" "=d")
6792 (and:GPR (ashift:GPR
6793 (match_operand:GPR 1 "register_operand" "d")
6794 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
6795 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))
6796 (clobber (reg:CC CC_REGNUM))]
6797 "TARGET_Z10
6798 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[2]),
6799 INTVAL (operands[3]))"
6800 "risbg\t%0,%1,%<bfstart>3,128+%<bfend>3,%2"
6801 [(set_attr "op_type" "RIE")
6802 (set_attr "z10prop" "z10_super_E1")])
6803
6804
6805 ;
6806 ; andsi3 instruction pattern(s).
6807 ;
6808
6809 (define_insn "*andsi3_cc"
6810 [(set (reg CC_REGNUM)
6811 (compare
6812 (and:SI
6813 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
6814 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
6815 (const_int 0)))
6816 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d, d")
6817 (and:SI (match_dup 1) (match_dup 2)))]
6818 "s390_match_ccmode(insn, CCTmode)"
6819 "@
6820 nilf\t%0,%o2
6821 nr\t%0,%2
6822 nrk\t%0,%1,%2
6823 n\t%0,%2
6824 ny\t%0,%2
6825 risbg\t%0,%1,%t2,128+%f2,0"
6826 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
6827 (set_attr "cpu_facility" "*,*,z196,*,*,z10")
6828 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
6829 z10_super_E1,z10_super_E1,z10_super_E1")])
6830
6831 (define_insn "*andsi3_cconly"
6832 [(set (reg CC_REGNUM)
6833 (compare
6834 (and:SI
6835 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
6836 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
6837 (const_int 0)))
6838 (clobber (match_scratch:SI 0 "=d,d,d,d,d, d"))]
6839 "s390_match_ccmode(insn, CCTmode)
6840 /* Do not steal TM patterns. */
6841 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
6842 "@
6843 nilf\t%0,%o2
6844 nr\t%0,%2
6845 nrk\t%0,%1,%2
6846 n\t%0,%2
6847 ny\t%0,%2
6848 risbg\t%0,%1,%t2,128+%f2,0"
6849 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
6850 (set_attr "cpu_facility" "*,*,z196,*,*,z10")
6851 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
6852 z10_super_E1,z10_super_E1,z10_super_E1")])
6853
6854 (define_insn "*andsi3_zarch"
6855 [(set (match_operand:SI 0 "nonimmediate_operand"
6856 "=d,d, d, d, d,d,d,d,d, d, AQ,Q")
6857 (and:SI (match_operand:SI 1 "nonimmediate_operand"
6858 "%d,o, 0, 0, 0,0,d,0,0, d, 0,0")
6859 (match_operand:SI 2 "general_operand"
6860 " M,M,N0HSF,N1HSF,Os,d,d,R,T,NxxSq,NxQSF,Q")))
6861 (clobber (reg:CC CC_REGNUM))]
6862 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6863 "@
6864 #
6865 #
6866 nilh\t%0,%j2
6867 nill\t%0,%j2
6868 nilf\t%0,%o2
6869 nr\t%0,%2
6870 nrk\t%0,%1,%2
6871 n\t%0,%2
6872 ny\t%0,%2
6873 risbg\t%0,%1,%t2,128+%f2,0
6874 #
6875 #"
6876 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RRF,RX,RXY,RIE,SI,SS")
6877 (set_attr "cpu_facility" "*,*,*,*,*,*,z196,*,*,z10,*,*")
6878 (set_attr "z10prop" "*,
6879 *,
6880 z10_super_E1,
6881 z10_super_E1,
6882 z10_super_E1,
6883 z10_super_E1,
6884 *,
6885 z10_super_E1,
6886 z10_super_E1,
6887 z10_super_E1,
6888 *,
6889 *")])
6890
6891 (define_insn "*andsi3_esa"
6892 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d, AQ,Q")
6893 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0, 0,0")
6894 (match_operand:SI 2 "general_operand" " d,R,NxQSF,Q")))
6895 (clobber (reg:CC CC_REGNUM))]
6896 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6897 "@
6898 nr\t%0,%2
6899 n\t%0,%2
6900 #
6901 #"
6902 [(set_attr "op_type" "RR,RX,SI,SS")
6903 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
6904
6905
6906 (define_split
6907 [(set (match_operand:SI 0 "s_operand" "")
6908 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
6909 (clobber (reg:CC CC_REGNUM))]
6910 "reload_completed"
6911 [(parallel
6912 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
6913 (clobber (reg:CC CC_REGNUM))])]
6914 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
6915
6916 ;
6917 ; andhi3 instruction pattern(s).
6918 ;
6919
6920 (define_insn "*andhi3_zarch"
6921 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
6922 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
6923 (match_operand:HI 2 "general_operand" " d,d,n,NxQHF,Q")))
6924 (clobber (reg:CC CC_REGNUM))]
6925 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6926 "@
6927 nr\t%0,%2
6928 nrk\t%0,%1,%2
6929 nill\t%0,%x2
6930 #
6931 #"
6932 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
6933 (set_attr "cpu_facility" "*,z196,*,*,*")
6934 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")
6935 ])
6936
6937 (define_insn "*andhi3_esa"
6938 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
6939 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
6940 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
6941 (clobber (reg:CC CC_REGNUM))]
6942 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6943 "@
6944 nr\t%0,%2
6945 #
6946 #"
6947 [(set_attr "op_type" "RR,SI,SS")
6948 (set_attr "z10prop" "z10_super_E1,*,*")
6949 ])
6950
6951 (define_split
6952 [(set (match_operand:HI 0 "s_operand" "")
6953 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
6954 (clobber (reg:CC CC_REGNUM))]
6955 "reload_completed"
6956 [(parallel
6957 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
6958 (clobber (reg:CC CC_REGNUM))])]
6959 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
6960
6961 ;
6962 ; andqi3 instruction pattern(s).
6963 ;
6964
6965 (define_insn "*andqi3_zarch"
6966 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
6967 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
6968 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
6969 (clobber (reg:CC CC_REGNUM))]
6970 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6971 "@
6972 nr\t%0,%2
6973 nrk\t%0,%1,%2
6974 nill\t%0,%b2
6975 ni\t%S0,%b2
6976 niy\t%S0,%b2
6977 #"
6978 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
6979 (set_attr "cpu_facility" "*,z196,*,*,*,*")
6980 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super,z10_super,*")])
6981
6982 (define_insn "*andqi3_esa"
6983 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
6984 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6985 (match_operand:QI 2 "general_operand" "d,n,Q")))
6986 (clobber (reg:CC CC_REGNUM))]
6987 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
6988 "@
6989 nr\t%0,%2
6990 ni\t%S0,%b2
6991 #"
6992 [(set_attr "op_type" "RR,SI,SS")
6993 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
6994
6995 ;
6996 ; Block and (NC) patterns.
6997 ;
6998
6999 (define_insn "*nc"
7000 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7001 (and:BLK (match_dup 0)
7002 (match_operand:BLK 1 "memory_operand" "Q")))
7003 (use (match_operand 2 "const_int_operand" "n"))
7004 (clobber (reg:CC CC_REGNUM))]
7005 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7006 "nc\t%O0(%2,%R0),%S1"
7007 [(set_attr "op_type" "SS")
7008 (set_attr "z196prop" "z196_cracked")])
7009
7010 (define_split
7011 [(set (match_operand 0 "memory_operand" "")
7012 (and (match_dup 0)
7013 (match_operand 1 "memory_operand" "")))
7014 (clobber (reg:CC CC_REGNUM))]
7015 "reload_completed
7016 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7017 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7018 [(parallel
7019 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
7020 (use (match_dup 2))
7021 (clobber (reg:CC CC_REGNUM))])]
7022 {
7023 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7024 operands[0] = adjust_address (operands[0], BLKmode, 0);
7025 operands[1] = adjust_address (operands[1], BLKmode, 0);
7026 })
7027
7028 (define_peephole2
7029 [(parallel
7030 [(set (match_operand:BLK 0 "memory_operand" "")
7031 (and:BLK (match_dup 0)
7032 (match_operand:BLK 1 "memory_operand" "")))
7033 (use (match_operand 2 "const_int_operand" ""))
7034 (clobber (reg:CC CC_REGNUM))])
7035 (parallel
7036 [(set (match_operand:BLK 3 "memory_operand" "")
7037 (and:BLK (match_dup 3)
7038 (match_operand:BLK 4 "memory_operand" "")))
7039 (use (match_operand 5 "const_int_operand" ""))
7040 (clobber (reg:CC CC_REGNUM))])]
7041 "s390_offset_p (operands[0], operands[3], operands[2])
7042 && s390_offset_p (operands[1], operands[4], operands[2])
7043 && !s390_overlap_p (operands[0], operands[1],
7044 INTVAL (operands[2]) + INTVAL (operands[5]))
7045 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7046 [(parallel
7047 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
7048 (use (match_dup 8))
7049 (clobber (reg:CC CC_REGNUM))])]
7050 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7051 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7052 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7053
7054
7055 ;;
7056 ;;- Bit set (inclusive or) instructions.
7057 ;;
7058
7059 (define_expand "ior<mode>3"
7060 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7061 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
7062 (match_operand:INT 2 "general_operand" "")))
7063 (clobber (reg:CC CC_REGNUM))]
7064 ""
7065 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
7066
7067 ;
7068 ; iordi3 instruction pattern(s).
7069 ;
7070
7071 (define_insn "*iordi3_cc"
7072 [(set (reg CC_REGNUM)
7073 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7074 (match_operand:DI 2 "general_operand" " d,d,RT"))
7075 (const_int 0)))
7076 (set (match_operand:DI 0 "register_operand" "=d,d, d")
7077 (ior:DI (match_dup 1) (match_dup 2)))]
7078 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7079 "@
7080 ogr\t%0,%2
7081 ogrk\t%0,%1,%2
7082 og\t%0,%2"
7083 [(set_attr "op_type" "RRE,RRF,RXY")
7084 (set_attr "cpu_facility" "*,z196,*")
7085 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7086
7087 (define_insn "*iordi3_cconly"
7088 [(set (reg CC_REGNUM)
7089 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7090 (match_operand:DI 2 "general_operand" " d,d,RT"))
7091 (const_int 0)))
7092 (clobber (match_scratch:DI 0 "=d,d,d"))]
7093 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7094 "@
7095 ogr\t%0,%2
7096 ogrk\t%0,%1,%2
7097 og\t%0,%2"
7098 [(set_attr "op_type" "RRE,RRF,RXY")
7099 (set_attr "cpu_facility" "*,z196,*")
7100 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7101
7102 (define_insn "*iordi3"
7103 [(set (match_operand:DI 0 "nonimmediate_operand"
7104 "=d, d, d, d, d, d,d,d, d, AQ,Q")
7105 (ior:DI (match_operand:DI 1 "nonimmediate_operand"
7106 " %0, 0, 0, 0, 0, 0,0,d, 0, 0,0")
7107 (match_operand:DI 2 "general_operand"
7108 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,d,RT,NxQD0,Q")))
7109 (clobber (reg:CC CC_REGNUM))]
7110 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7111 "@
7112 oihh\t%0,%i2
7113 oihl\t%0,%i2
7114 oilh\t%0,%i2
7115 oill\t%0,%i2
7116 oihf\t%0,%k2
7117 oilf\t%0,%k2
7118 ogr\t%0,%2
7119 ogrk\t%0,%1,%2
7120 og\t%0,%2
7121 #
7122 #"
7123 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,SI,SS")
7124 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,z196,*,*,*")
7125 (set_attr "z10prop" "z10_super_E1,
7126 z10_super_E1,
7127 z10_super_E1,
7128 z10_super_E1,
7129 z10_super_E1,
7130 z10_super_E1,
7131 z10_super_E1,
7132 *,
7133 z10_super_E1,
7134 *,
7135 *")])
7136
7137 (define_split
7138 [(set (match_operand:DI 0 "s_operand" "")
7139 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7140 (clobber (reg:CC CC_REGNUM))]
7141 "reload_completed"
7142 [(parallel
7143 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7144 (clobber (reg:CC CC_REGNUM))])]
7145 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7146
7147 ;
7148 ; iorsi3 instruction pattern(s).
7149 ;
7150
7151 (define_insn "*iorsi3_cc"
7152 [(set (reg CC_REGNUM)
7153 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7154 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7155 (const_int 0)))
7156 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7157 (ior:SI (match_dup 1) (match_dup 2)))]
7158 "s390_match_ccmode(insn, CCTmode)"
7159 "@
7160 oilf\t%0,%o2
7161 or\t%0,%2
7162 ork\t%0,%1,%2
7163 o\t%0,%2
7164 oy\t%0,%2"
7165 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7166 (set_attr "cpu_facility" "*,*,z196,*,*")
7167 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7168
7169 (define_insn "*iorsi3_cconly"
7170 [(set (reg CC_REGNUM)
7171 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7172 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7173 (const_int 0)))
7174 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7175 "s390_match_ccmode(insn, CCTmode)"
7176 "@
7177 oilf\t%0,%o2
7178 or\t%0,%2
7179 ork\t%0,%1,%2
7180 o\t%0,%2
7181 oy\t%0,%2"
7182 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7183 (set_attr "cpu_facility" "*,*,z196,*,*")
7184 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7185
7186 (define_insn "*iorsi3_zarch"
7187 [(set (match_operand:SI 0 "nonimmediate_operand" "=d, d, d,d,d,d,d, AQ,Q")
7188 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0, 0, 0,0,d,0,0, 0,0")
7189 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,d,R,T,NxQS0,Q")))
7190 (clobber (reg:CC CC_REGNUM))]
7191 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7192 "@
7193 oilh\t%0,%i2
7194 oill\t%0,%i2
7195 oilf\t%0,%o2
7196 or\t%0,%2
7197 ork\t%0,%1,%2
7198 o\t%0,%2
7199 oy\t%0,%2
7200 #
7201 #"
7202 [(set_attr "op_type" "RI,RI,RIL,RR,RRF,RX,RXY,SI,SS")
7203 (set_attr "cpu_facility" "*,*,*,*,z196,*,*,*,*")
7204 (set_attr "z10prop" "z10_super_E1,
7205 z10_super_E1,
7206 z10_super_E1,
7207 z10_super_E1,
7208 *,
7209 z10_super_E1,
7210 z10_super_E1,
7211 *,
7212 *")])
7213
7214 (define_insn "*iorsi3_esa"
7215 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
7216 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
7217 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
7218 (clobber (reg:CC CC_REGNUM))]
7219 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7220 "@
7221 or\t%0,%2
7222 o\t%0,%2
7223 #
7224 #"
7225 [(set_attr "op_type" "RR,RX,SI,SS")
7226 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7227
7228 (define_split
7229 [(set (match_operand:SI 0 "s_operand" "")
7230 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7231 (clobber (reg:CC CC_REGNUM))]
7232 "reload_completed"
7233 [(parallel
7234 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7235 (clobber (reg:CC CC_REGNUM))])]
7236 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7237
7238 ;
7239 ; iorhi3 instruction pattern(s).
7240 ;
7241
7242 (define_insn "*iorhi3_zarch"
7243 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7244 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7245 (match_operand:HI 2 "general_operand" " d,d,n,NxQH0,Q")))
7246 (clobber (reg:CC CC_REGNUM))]
7247 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7248 "@
7249 or\t%0,%2
7250 ork\t%0,%1,%2
7251 oill\t%0,%x2
7252 #
7253 #"
7254 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7255 (set_attr "cpu_facility" "*,z196,*,*,*")
7256 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")])
7257
7258 (define_insn "*iorhi3_esa"
7259 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7260 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7261 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
7262 (clobber (reg:CC CC_REGNUM))]
7263 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7264 "@
7265 or\t%0,%2
7266 #
7267 #"
7268 [(set_attr "op_type" "RR,SI,SS")
7269 (set_attr "z10prop" "z10_super_E1,*,*")])
7270
7271 (define_split
7272 [(set (match_operand:HI 0 "s_operand" "")
7273 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7274 (clobber (reg:CC CC_REGNUM))]
7275 "reload_completed"
7276 [(parallel
7277 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7278 (clobber (reg:CC CC_REGNUM))])]
7279 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7280
7281 ;
7282 ; iorqi3 instruction pattern(s).
7283 ;
7284
7285 (define_insn "*iorqi3_zarch"
7286 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7287 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7288 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7289 (clobber (reg:CC CC_REGNUM))]
7290 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7291 "@
7292 or\t%0,%2
7293 ork\t%0,%1,%2
7294 oill\t%0,%b2
7295 oi\t%S0,%b2
7296 oiy\t%S0,%b2
7297 #"
7298 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7299 (set_attr "cpu_facility" "*,z196,*,*,*,*")
7300 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,
7301 z10_super,z10_super,*")])
7302
7303 (define_insn "*iorqi3_esa"
7304 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7305 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7306 (match_operand:QI 2 "general_operand" "d,n,Q")))
7307 (clobber (reg:CC CC_REGNUM))]
7308 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7309 "@
7310 or\t%0,%2
7311 oi\t%S0,%b2
7312 #"
7313 [(set_attr "op_type" "RR,SI,SS")
7314 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7315
7316 ;
7317 ; Block inclusive or (OC) patterns.
7318 ;
7319
7320 (define_insn "*oc"
7321 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7322 (ior:BLK (match_dup 0)
7323 (match_operand:BLK 1 "memory_operand" "Q")))
7324 (use (match_operand 2 "const_int_operand" "n"))
7325 (clobber (reg:CC CC_REGNUM))]
7326 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7327 "oc\t%O0(%2,%R0),%S1"
7328 [(set_attr "op_type" "SS")
7329 (set_attr "z196prop" "z196_cracked")])
7330
7331 (define_split
7332 [(set (match_operand 0 "memory_operand" "")
7333 (ior (match_dup 0)
7334 (match_operand 1 "memory_operand" "")))
7335 (clobber (reg:CC CC_REGNUM))]
7336 "reload_completed
7337 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7338 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7339 [(parallel
7340 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
7341 (use (match_dup 2))
7342 (clobber (reg:CC CC_REGNUM))])]
7343 {
7344 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7345 operands[0] = adjust_address (operands[0], BLKmode, 0);
7346 operands[1] = adjust_address (operands[1], BLKmode, 0);
7347 })
7348
7349 (define_peephole2
7350 [(parallel
7351 [(set (match_operand:BLK 0 "memory_operand" "")
7352 (ior:BLK (match_dup 0)
7353 (match_operand:BLK 1 "memory_operand" "")))
7354 (use (match_operand 2 "const_int_operand" ""))
7355 (clobber (reg:CC CC_REGNUM))])
7356 (parallel
7357 [(set (match_operand:BLK 3 "memory_operand" "")
7358 (ior:BLK (match_dup 3)
7359 (match_operand:BLK 4 "memory_operand" "")))
7360 (use (match_operand 5 "const_int_operand" ""))
7361 (clobber (reg:CC CC_REGNUM))])]
7362 "s390_offset_p (operands[0], operands[3], operands[2])
7363 && s390_offset_p (operands[1], operands[4], operands[2])
7364 && !s390_overlap_p (operands[0], operands[1],
7365 INTVAL (operands[2]) + INTVAL (operands[5]))
7366 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7367 [(parallel
7368 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
7369 (use (match_dup 8))
7370 (clobber (reg:CC CC_REGNUM))])]
7371 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7372 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7373 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7374
7375
7376 ;;
7377 ;;- Xor instructions.
7378 ;;
7379
7380 (define_expand "xor<mode>3"
7381 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7382 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
7383 (match_operand:INT 2 "general_operand" "")))
7384 (clobber (reg:CC CC_REGNUM))]
7385 ""
7386 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
7387
7388 ; Combine replaces (xor (x) (const_int -1)) with (not (x)) when doing
7389 ; simplifications. So its better to have something matching.
7390 (define_split
7391 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7392 (not:INT (match_operand:INT 1 "nonimmediate_operand" "")))]
7393 ""
7394 [(parallel
7395 [(set (match_dup 0) (xor:INT (match_dup 1) (match_dup 2)))
7396 (clobber (reg:CC CC_REGNUM))])]
7397 {
7398 operands[2] = constm1_rtx;
7399 if (!s390_logical_operator_ok_p (operands))
7400 FAIL;
7401 })
7402
7403 ;
7404 ; xordi3 instruction pattern(s).
7405 ;
7406
7407 (define_insn "*xordi3_cc"
7408 [(set (reg CC_REGNUM)
7409 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7410 (match_operand:DI 2 "general_operand" " d,d,RT"))
7411 (const_int 0)))
7412 (set (match_operand:DI 0 "register_operand" "=d,d, d")
7413 (xor:DI (match_dup 1) (match_dup 2)))]
7414 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7415 "@
7416 xgr\t%0,%2
7417 xgrk\t%0,%1,%2
7418 xg\t%0,%2"
7419 [(set_attr "op_type" "RRE,RRF,RXY")
7420 (set_attr "cpu_facility" "*,z196,*")
7421 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7422
7423 (define_insn "*xordi3_cconly"
7424 [(set (reg CC_REGNUM)
7425 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d, 0")
7426 (match_operand:DI 2 "general_operand" " d,d,RT"))
7427 (const_int 0)))
7428 (clobber (match_scratch:DI 0 "=d,d, d"))]
7429 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7430 "@
7431 xgr\t%0,%2
7432 xgrk\t%0,%1,%2
7433 xg\t%0,%2"
7434 [(set_attr "op_type" "RRE,RRF,RXY")
7435 (set_attr "cpu_facility" "*,z196,*")
7436 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7437
7438 (define_insn "*xordi3"
7439 [(set (match_operand:DI 0 "nonimmediate_operand" "=d, d,d,d, d, AQ,Q")
7440 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0, 0,0,d, 0, 0,0")
7441 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,d,RT,NxQD0,Q")))
7442 (clobber (reg:CC CC_REGNUM))]
7443 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7444 "@
7445 xihf\t%0,%k2
7446 xilf\t%0,%k2
7447 xgr\t%0,%2
7448 xgrk\t%0,%1,%2
7449 xg\t%0,%2
7450 #
7451 #"
7452 [(set_attr "op_type" "RIL,RIL,RRE,RRF,RXY,SI,SS")
7453 (set_attr "cpu_facility" "extimm,extimm,*,z196,*,*,*")
7454 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,
7455 *,z10_super_E1,*,*")])
7456
7457 (define_split
7458 [(set (match_operand:DI 0 "s_operand" "")
7459 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7460 (clobber (reg:CC CC_REGNUM))]
7461 "reload_completed"
7462 [(parallel
7463 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7464 (clobber (reg:CC CC_REGNUM))])]
7465 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7466
7467 ;
7468 ; xorsi3 instruction pattern(s).
7469 ;
7470
7471 (define_insn "*xorsi3_cc"
7472 [(set (reg CC_REGNUM)
7473 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7474 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7475 (const_int 0)))
7476 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7477 (xor:SI (match_dup 1) (match_dup 2)))]
7478 "s390_match_ccmode(insn, CCTmode)"
7479 "@
7480 xilf\t%0,%o2
7481 xr\t%0,%2
7482 xrk\t%0,%1,%2
7483 x\t%0,%2
7484 xy\t%0,%2"
7485 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7486 (set_attr "cpu_facility" "*,*,z196,*,*")
7487 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7488 z10_super_E1,z10_super_E1")])
7489
7490 (define_insn "*xorsi3_cconly"
7491 [(set (reg CC_REGNUM)
7492 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7493 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7494 (const_int 0)))
7495 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7496 "s390_match_ccmode(insn, CCTmode)"
7497 "@
7498 xilf\t%0,%o2
7499 xr\t%0,%2
7500 xrk\t%0,%1,%2
7501 x\t%0,%2
7502 xy\t%0,%2"
7503 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7504 (set_attr "cpu_facility" "*,*,z196,*,*")
7505 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7506 z10_super_E1,z10_super_E1")])
7507
7508 (define_insn "*xorsi3"
7509 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d, AQ,Q")
7510 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, 0,0")
7511 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxQS0,Q")))
7512 (clobber (reg:CC CC_REGNUM))]
7513 "s390_logical_operator_ok_p (operands)"
7514 "@
7515 xilf\t%0,%o2
7516 xr\t%0,%2
7517 xrk\t%0,%1,%2
7518 x\t%0,%2
7519 xy\t%0,%2
7520 #
7521 #"
7522 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,SI,SS")
7523 (set_attr "cpu_facility" "*,*,z196,*,*,*,*")
7524 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7525 z10_super_E1,z10_super_E1,*,*")])
7526
7527 (define_split
7528 [(set (match_operand:SI 0 "s_operand" "")
7529 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7530 (clobber (reg:CC CC_REGNUM))]
7531 "reload_completed"
7532 [(parallel
7533 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7534 (clobber (reg:CC CC_REGNUM))])]
7535 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7536
7537 ;
7538 ; xorhi3 instruction pattern(s).
7539 ;
7540
7541 (define_insn "*xorhi3"
7542 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7543 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,d, 0,0")
7544 (match_operand:HI 2 "general_operand" "Os,d,d,NxQH0,Q")))
7545 (clobber (reg:CC CC_REGNUM))]
7546 "s390_logical_operator_ok_p (operands)"
7547 "@
7548 xilf\t%0,%x2
7549 xr\t%0,%2
7550 xrk\t%0,%1,%2
7551 #
7552 #"
7553 [(set_attr "op_type" "RIL,RR,RRF,SI,SS")
7554 (set_attr "cpu_facility" "*,*,z196,*,*")
7555 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*,*")])
7556
7557 (define_split
7558 [(set (match_operand:HI 0 "s_operand" "")
7559 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7560 (clobber (reg:CC CC_REGNUM))]
7561 "reload_completed"
7562 [(parallel
7563 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7564 (clobber (reg:CC CC_REGNUM))])]
7565 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7566
7567 ;
7568 ; xorqi3 instruction pattern(s).
7569 ;
7570
7571 (define_insn "*xorqi3"
7572 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7573 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,d,0,0,0")
7574 (match_operand:QI 2 "general_operand" "Os,d,d,n,n,Q")))
7575 (clobber (reg:CC CC_REGNUM))]
7576 "s390_logical_operator_ok_p (operands)"
7577 "@
7578 xilf\t%0,%b2
7579 xr\t%0,%2
7580 xrk\t%0,%1,%2
7581 xi\t%S0,%b2
7582 xiy\t%S0,%b2
7583 #"
7584 [(set_attr "op_type" "RIL,RR,RRF,SI,SIY,SS")
7585 (set_attr "cpu_facility" "*,*,z196,*,*,*")
7586 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super,z10_super,*")])
7587
7588
7589 ;
7590 ; Block exclusive or (XC) patterns.
7591 ;
7592
7593 (define_insn "*xc"
7594 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7595 (xor:BLK (match_dup 0)
7596 (match_operand:BLK 1 "memory_operand" "Q")))
7597 (use (match_operand 2 "const_int_operand" "n"))
7598 (clobber (reg:CC CC_REGNUM))]
7599 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7600 "xc\t%O0(%2,%R0),%S1"
7601 [(set_attr "op_type" "SS")])
7602
7603 (define_split
7604 [(set (match_operand 0 "memory_operand" "")
7605 (xor (match_dup 0)
7606 (match_operand 1 "memory_operand" "")))
7607 (clobber (reg:CC CC_REGNUM))]
7608 "reload_completed
7609 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7610 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7611 [(parallel
7612 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
7613 (use (match_dup 2))
7614 (clobber (reg:CC CC_REGNUM))])]
7615 {
7616 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7617 operands[0] = adjust_address (operands[0], BLKmode, 0);
7618 operands[1] = adjust_address (operands[1], BLKmode, 0);
7619 })
7620
7621 (define_peephole2
7622 [(parallel
7623 [(set (match_operand:BLK 0 "memory_operand" "")
7624 (xor:BLK (match_dup 0)
7625 (match_operand:BLK 1 "memory_operand" "")))
7626 (use (match_operand 2 "const_int_operand" ""))
7627 (clobber (reg:CC CC_REGNUM))])
7628 (parallel
7629 [(set (match_operand:BLK 3 "memory_operand" "")
7630 (xor:BLK (match_dup 3)
7631 (match_operand:BLK 4 "memory_operand" "")))
7632 (use (match_operand 5 "const_int_operand" ""))
7633 (clobber (reg:CC CC_REGNUM))])]
7634 "s390_offset_p (operands[0], operands[3], operands[2])
7635 && s390_offset_p (operands[1], operands[4], operands[2])
7636 && !s390_overlap_p (operands[0], operands[1],
7637 INTVAL (operands[2]) + INTVAL (operands[5]))
7638 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7639 [(parallel
7640 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
7641 (use (match_dup 8))
7642 (clobber (reg:CC CC_REGNUM))])]
7643 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7644 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7645 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7646
7647 ;
7648 ; Block xor (XC) patterns with src == dest.
7649 ;
7650
7651 (define_insn "*xc_zero"
7652 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7653 (const_int 0))
7654 (use (match_operand 1 "const_int_operand" "n"))
7655 (clobber (reg:CC CC_REGNUM))]
7656 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
7657 "xc\t%O0(%1,%R0),%S0"
7658 [(set_attr "op_type" "SS")
7659 (set_attr "z196prop" "z196_cracked")])
7660
7661 (define_peephole2
7662 [(parallel
7663 [(set (match_operand:BLK 0 "memory_operand" "")
7664 (const_int 0))
7665 (use (match_operand 1 "const_int_operand" ""))
7666 (clobber (reg:CC CC_REGNUM))])
7667 (parallel
7668 [(set (match_operand:BLK 2 "memory_operand" "")
7669 (const_int 0))
7670 (use (match_operand 3 "const_int_operand" ""))
7671 (clobber (reg:CC CC_REGNUM))])]
7672 "s390_offset_p (operands[0], operands[2], operands[1])
7673 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
7674 [(parallel
7675 [(set (match_dup 4) (const_int 0))
7676 (use (match_dup 5))
7677 (clobber (reg:CC CC_REGNUM))])]
7678 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7679 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
7680
7681
7682 ;;
7683 ;;- Negate instructions.
7684 ;;
7685
7686 ;
7687 ; neg(di|si)2 instruction pattern(s).
7688 ;
7689
7690 (define_expand "neg<mode>2"
7691 [(parallel
7692 [(set (match_operand:DSI 0 "register_operand" "=d")
7693 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
7694 (clobber (reg:CC CC_REGNUM))])]
7695 ""
7696 "")
7697
7698 (define_insn "*negdi2_sign_cc"
7699 [(set (reg CC_REGNUM)
7700 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
7701 (match_operand:SI 1 "register_operand" "d") 0)
7702 (const_int 32)) (const_int 32)))
7703 (const_int 0)))
7704 (set (match_operand:DI 0 "register_operand" "=d")
7705 (neg:DI (sign_extend:DI (match_dup 1))))]
7706 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
7707 "lcgfr\t%0,%1"
7708 [(set_attr "op_type" "RRE")
7709 (set_attr "z10prop" "z10_c")])
7710
7711 (define_insn "*negdi2_sign"
7712 [(set (match_operand:DI 0 "register_operand" "=d")
7713 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
7714 (clobber (reg:CC CC_REGNUM))]
7715 "TARGET_ZARCH"
7716 "lcgfr\t%0,%1"
7717 [(set_attr "op_type" "RRE")
7718 (set_attr "z10prop" "z10_c")])
7719
7720 ; lcr, lcgr
7721 (define_insn "*neg<mode>2_cc"
7722 [(set (reg CC_REGNUM)
7723 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
7724 (const_int 0)))
7725 (set (match_operand:GPR 0 "register_operand" "=d")
7726 (neg:GPR (match_dup 1)))]
7727 "s390_match_ccmode (insn, CCAmode)"
7728 "lc<g>r\t%0,%1"
7729 [(set_attr "op_type" "RR<E>")
7730 (set_attr "z10prop" "z10_super_c_E1")])
7731
7732 ; lcr, lcgr
7733 (define_insn "*neg<mode>2_cconly"
7734 [(set (reg CC_REGNUM)
7735 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
7736 (const_int 0)))
7737 (clobber (match_scratch:GPR 0 "=d"))]
7738 "s390_match_ccmode (insn, CCAmode)"
7739 "lc<g>r\t%0,%1"
7740 [(set_attr "op_type" "RR<E>")
7741 (set_attr "z10prop" "z10_super_c_E1")])
7742
7743 ; lcr, lcgr
7744 (define_insn "*neg<mode>2"
7745 [(set (match_operand:GPR 0 "register_operand" "=d")
7746 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
7747 (clobber (reg:CC CC_REGNUM))]
7748 ""
7749 "lc<g>r\t%0,%1"
7750 [(set_attr "op_type" "RR<E>")
7751 (set_attr "z10prop" "z10_super_c_E1")])
7752
7753 (define_insn "*negdi2_31"
7754 [(set (match_operand:DI 0 "register_operand" "=d")
7755 (neg:DI (match_operand:DI 1 "register_operand" "d")))
7756 (clobber (reg:CC CC_REGNUM))]
7757 "!TARGET_ZARCH"
7758 "#")
7759
7760 ; Split a DImode NEG on 31bit into 2 SImode NEGs
7761
7762 ; Doing the twos complement separately on the SImode parts does an
7763 ; unwanted +1 on the high part which needs to be subtracted afterwards
7764 ; ... unless the +1 on the low part created an overflow.
7765
7766 (define_split
7767 [(set (match_operand:DI 0 "register_operand" "")
7768 (neg:DI (match_operand:DI 1 "register_operand" "")))
7769 (clobber (reg:CC CC_REGNUM))]
7770 "!TARGET_ZARCH
7771 && (REGNO (operands[0]) == REGNO (operands[1])
7772 || s390_split_ok_p (operands[0], operands[1], DImode, 0))
7773 && reload_completed"
7774 [(parallel
7775 [(set (match_dup 2) (neg:SI (match_dup 3)))
7776 (clobber (reg:CC CC_REGNUM))])
7777 (parallel
7778 [(set (reg:CCAP CC_REGNUM)
7779 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
7780 (set (match_dup 4) (neg:SI (match_dup 5)))])
7781 (set (pc)
7782 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
7783 (pc)
7784 (label_ref (match_dup 6))))
7785 (parallel
7786 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
7787 (clobber (reg:CC CC_REGNUM))])
7788 (match_dup 6)]
7789 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
7790 operands[3] = operand_subword (operands[1], 0, 0, DImode);
7791 operands[4] = operand_subword (operands[0], 1, 0, DImode);
7792 operands[5] = operand_subword (operands[1], 1, 0, DImode);
7793 operands[6] = gen_label_rtx ();")
7794
7795 ; Like above but first make a copy of the low part of the src operand
7796 ; since it might overlap with the high part of the destination.
7797
7798 (define_split
7799 [(set (match_operand:DI 0 "register_operand" "")
7800 (neg:DI (match_operand:DI 1 "register_operand" "")))
7801 (clobber (reg:CC CC_REGNUM))]
7802 "!TARGET_ZARCH
7803 && s390_split_ok_p (operands[0], operands[1], DImode, 1)
7804 && reload_completed"
7805 [; Make a backup of op5 first
7806 (set (match_dup 4) (match_dup 5))
7807 ; Setting op2 here might clobber op5
7808 (parallel
7809 [(set (match_dup 2) (neg:SI (match_dup 3)))
7810 (clobber (reg:CC CC_REGNUM))])
7811 (parallel
7812 [(set (reg:CCAP CC_REGNUM)
7813 (compare:CCAP (neg:SI (match_dup 4)) (const_int 0)))
7814 (set (match_dup 4) (neg:SI (match_dup 4)))])
7815 (set (pc)
7816 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
7817 (pc)
7818 (label_ref (match_dup 6))))
7819 (parallel
7820 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
7821 (clobber (reg:CC CC_REGNUM))])
7822 (match_dup 6)]
7823 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
7824 operands[3] = operand_subword (operands[1], 0, 0, DImode);
7825 operands[4] = operand_subword (operands[0], 1, 0, DImode);
7826 operands[5] = operand_subword (operands[1], 1, 0, DImode);
7827 operands[6] = gen_label_rtx ();")
7828
7829 ;
7830 ; neg(df|sf)2 instruction pattern(s).
7831 ;
7832
7833 (define_expand "neg<mode>2"
7834 [(parallel
7835 [(set (match_operand:BFP 0 "register_operand" "=f")
7836 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
7837 (clobber (reg:CC CC_REGNUM))])]
7838 "TARGET_HARD_FLOAT"
7839 "")
7840
7841 ; lcxbr, lcdbr, lcebr
7842 (define_insn "*neg<mode>2_cc"
7843 [(set (reg CC_REGNUM)
7844 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
7845 (match_operand:BFP 2 "const0_operand" "")))
7846 (set (match_operand:BFP 0 "register_operand" "=f")
7847 (neg:BFP (match_dup 1)))]
7848 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7849 "lc<xde>br\t%0,%1"
7850 [(set_attr "op_type" "RRE")
7851 (set_attr "type" "fsimp<mode>")])
7852
7853 ; lcxbr, lcdbr, lcebr
7854 (define_insn "*neg<mode>2_cconly"
7855 [(set (reg CC_REGNUM)
7856 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
7857 (match_operand:BFP 2 "const0_operand" "")))
7858 (clobber (match_scratch:BFP 0 "=f"))]
7859 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7860 "lc<xde>br\t%0,%1"
7861 [(set_attr "op_type" "RRE")
7862 (set_attr "type" "fsimp<mode>")])
7863
7864 ; lcdfr
7865 (define_insn "*neg<mode>2_nocc"
7866 [(set (match_operand:FP 0 "register_operand" "=f")
7867 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
7868 "TARGET_DFP"
7869 "lcdfr\t%0,%1"
7870 [(set_attr "op_type" "RRE")
7871 (set_attr "type" "fsimp<mode>")])
7872
7873 ; lcxbr, lcdbr, lcebr
7874 ; FIXME: wflcdb does not clobber cc
7875 (define_insn "*neg<mode>2"
7876 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
7877 (neg:BFP (match_operand:BFP 1 "register_operand" "f,<vf>")))
7878 (clobber (reg:CC CC_REGNUM))]
7879 "TARGET_HARD_FLOAT"
7880 "@
7881 lc<xde>br\t%0,%1
7882 wflcdb\t%0,%1"
7883 [(set_attr "op_type" "RRE,VRR")
7884 (set_attr "cpu_facility" "*,vec")
7885 (set_attr "type" "fsimp<mode>,*")])
7886
7887
7888 ;;
7889 ;;- Absolute value instructions.
7890 ;;
7891
7892 ;
7893 ; abs(di|si)2 instruction pattern(s).
7894 ;
7895
7896 (define_insn "*absdi2_sign_cc"
7897 [(set (reg CC_REGNUM)
7898 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
7899 (match_operand:SI 1 "register_operand" "d") 0)
7900 (const_int 32)) (const_int 32)))
7901 (const_int 0)))
7902 (set (match_operand:DI 0 "register_operand" "=d")
7903 (abs:DI (sign_extend:DI (match_dup 1))))]
7904 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
7905 "lpgfr\t%0,%1"
7906 [(set_attr "op_type" "RRE")
7907 (set_attr "z10prop" "z10_c")])
7908
7909 (define_insn "*absdi2_sign"
7910 [(set (match_operand:DI 0 "register_operand" "=d")
7911 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
7912 (clobber (reg:CC CC_REGNUM))]
7913 "TARGET_ZARCH"
7914 "lpgfr\t%0,%1"
7915 [(set_attr "op_type" "RRE")
7916 (set_attr "z10prop" "z10_c")])
7917
7918 ; lpr, lpgr
7919 (define_insn "*abs<mode>2_cc"
7920 [(set (reg CC_REGNUM)
7921 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
7922 (const_int 0)))
7923 (set (match_operand:GPR 0 "register_operand" "=d")
7924 (abs:GPR (match_dup 1)))]
7925 "s390_match_ccmode (insn, CCAmode)"
7926 "lp<g>r\t%0,%1"
7927 [(set_attr "op_type" "RR<E>")
7928 (set_attr "z10prop" "z10_c")])
7929
7930 ; lpr, lpgr
7931 (define_insn "*abs<mode>2_cconly"
7932 [(set (reg CC_REGNUM)
7933 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
7934 (const_int 0)))
7935 (clobber (match_scratch:GPR 0 "=d"))]
7936 "s390_match_ccmode (insn, CCAmode)"
7937 "lp<g>r\t%0,%1"
7938 [(set_attr "op_type" "RR<E>")
7939 (set_attr "z10prop" "z10_c")])
7940
7941 ; lpr, lpgr
7942 (define_insn "abs<mode>2"
7943 [(set (match_operand:GPR 0 "register_operand" "=d")
7944 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
7945 (clobber (reg:CC CC_REGNUM))]
7946 ""
7947 "lp<g>r\t%0,%1"
7948 [(set_attr "op_type" "RR<E>")
7949 (set_attr "z10prop" "z10_c")])
7950
7951 ;
7952 ; abs(df|sf)2 instruction pattern(s).
7953 ;
7954
7955 (define_expand "abs<mode>2"
7956 [(parallel
7957 [(set (match_operand:BFP 0 "register_operand" "=f")
7958 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
7959 (clobber (reg:CC CC_REGNUM))])]
7960 "TARGET_HARD_FLOAT"
7961 "")
7962
7963 ; lpxbr, lpdbr, lpebr
7964 (define_insn "*abs<mode>2_cc"
7965 [(set (reg CC_REGNUM)
7966 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
7967 (match_operand:BFP 2 "const0_operand" "")))
7968 (set (match_operand:BFP 0 "register_operand" "=f")
7969 (abs:BFP (match_dup 1)))]
7970 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7971 "lp<xde>br\t%0,%1"
7972 [(set_attr "op_type" "RRE")
7973 (set_attr "type" "fsimp<mode>")])
7974
7975 ; lpxbr, lpdbr, lpebr
7976 (define_insn "*abs<mode>2_cconly"
7977 [(set (reg CC_REGNUM)
7978 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
7979 (match_operand:BFP 2 "const0_operand" "")))
7980 (clobber (match_scratch:BFP 0 "=f"))]
7981 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
7982 "lp<xde>br\t%0,%1"
7983 [(set_attr "op_type" "RRE")
7984 (set_attr "type" "fsimp<mode>")])
7985
7986 ; lpdfr
7987 (define_insn "*abs<mode>2_nocc"
7988 [(set (match_operand:FP 0 "register_operand" "=f")
7989 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
7990 "TARGET_DFP"
7991 "lpdfr\t%0,%1"
7992 [(set_attr "op_type" "RRE")
7993 (set_attr "type" "fsimp<mode>")])
7994
7995 ; lpxbr, lpdbr, lpebr
7996 ; FIXME: wflpdb does not clobber cc
7997 (define_insn "*abs<mode>2"
7998 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
7999 (abs:BFP (match_operand:BFP 1 "register_operand" "f,<vf>")))
8000 (clobber (reg:CC CC_REGNUM))]
8001 "TARGET_HARD_FLOAT"
8002 "@
8003 lp<xde>br\t%0,%1
8004 wflpdb\t%0,%1"
8005 [(set_attr "op_type" "RRE,VRR")
8006 (set_attr "cpu_facility" "*,vec")
8007 (set_attr "type" "fsimp<mode>,*")])
8008
8009
8010 ;;
8011 ;;- Negated absolute value instructions
8012 ;;
8013
8014 ;
8015 ; Integer
8016 ;
8017
8018 (define_insn "*negabsdi2_sign_cc"
8019 [(set (reg CC_REGNUM)
8020 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8021 (match_operand:SI 1 "register_operand" "d") 0)
8022 (const_int 32)) (const_int 32))))
8023 (const_int 0)))
8024 (set (match_operand:DI 0 "register_operand" "=d")
8025 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
8026 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8027 "lngfr\t%0,%1"
8028 [(set_attr "op_type" "RRE")
8029 (set_attr "z10prop" "z10_c")])
8030
8031 (define_insn "*negabsdi2_sign"
8032 [(set (match_operand:DI 0 "register_operand" "=d")
8033 (neg:DI (abs:DI (sign_extend:DI
8034 (match_operand:SI 1 "register_operand" "d")))))
8035 (clobber (reg:CC CC_REGNUM))]
8036 "TARGET_ZARCH"
8037 "lngfr\t%0,%1"
8038 [(set_attr "op_type" "RRE")
8039 (set_attr "z10prop" "z10_c")])
8040
8041 ; lnr, lngr
8042 (define_insn "*negabs<mode>2_cc"
8043 [(set (reg CC_REGNUM)
8044 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8045 (const_int 0)))
8046 (set (match_operand:GPR 0 "register_operand" "=d")
8047 (neg:GPR (abs:GPR (match_dup 1))))]
8048 "s390_match_ccmode (insn, CCAmode)"
8049 "ln<g>r\t%0,%1"
8050 [(set_attr "op_type" "RR<E>")
8051 (set_attr "z10prop" "z10_c")])
8052
8053 ; lnr, lngr
8054 (define_insn "*negabs<mode>2_cconly"
8055 [(set (reg CC_REGNUM)
8056 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8057 (const_int 0)))
8058 (clobber (match_scratch:GPR 0 "=d"))]
8059 "s390_match_ccmode (insn, CCAmode)"
8060 "ln<g>r\t%0,%1"
8061 [(set_attr "op_type" "RR<E>")
8062 (set_attr "z10prop" "z10_c")])
8063
8064 ; lnr, lngr
8065 (define_insn "*negabs<mode>2"
8066 [(set (match_operand:GPR 0 "register_operand" "=d")
8067 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
8068 (clobber (reg:CC CC_REGNUM))]
8069 ""
8070 "ln<g>r\t%0,%1"
8071 [(set_attr "op_type" "RR<E>")
8072 (set_attr "z10prop" "z10_c")])
8073
8074 ;
8075 ; Floating point
8076 ;
8077
8078 ; lnxbr, lndbr, lnebr
8079 (define_insn "*negabs<mode>2_cc"
8080 [(set (reg CC_REGNUM)
8081 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8082 (match_operand:BFP 2 "const0_operand" "")))
8083 (set (match_operand:BFP 0 "register_operand" "=f")
8084 (neg:BFP (abs:BFP (match_dup 1))))]
8085 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8086 "ln<xde>br\t%0,%1"
8087 [(set_attr "op_type" "RRE")
8088 (set_attr "type" "fsimp<mode>")])
8089
8090 ; lnxbr, lndbr, lnebr
8091 (define_insn "*negabs<mode>2_cconly"
8092 [(set (reg CC_REGNUM)
8093 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8094 (match_operand:BFP 2 "const0_operand" "")))
8095 (clobber (match_scratch:BFP 0 "=f"))]
8096 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8097 "ln<xde>br\t%0,%1"
8098 [(set_attr "op_type" "RRE")
8099 (set_attr "type" "fsimp<mode>")])
8100
8101 ; lndfr
8102 (define_insn "*negabs<mode>2_nocc"
8103 [(set (match_operand:FP 0 "register_operand" "=f")
8104 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
8105 "TARGET_DFP"
8106 "lndfr\t%0,%1"
8107 [(set_attr "op_type" "RRE")
8108 (set_attr "type" "fsimp<mode>")])
8109
8110 ; lnxbr, lndbr, lnebr
8111 ; FIXME: wflndb does not clobber cc
8112 (define_insn "*negabs<mode>2"
8113 [(set (match_operand:BFP 0 "register_operand" "=f,<vf>")
8114 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f,<vf>"))))
8115 (clobber (reg:CC CC_REGNUM))]
8116 "TARGET_HARD_FLOAT"
8117 "@
8118 ln<xde>br\t%0,%1
8119 wflndb\t%0,%1"
8120 [(set_attr "op_type" "RRE,VRR")
8121 (set_attr "cpu_facility" "*,vec")
8122 (set_attr "type" "fsimp<mode>,*")])
8123
8124 ;;
8125 ;;- Square root instructions.
8126 ;;
8127
8128 ;
8129 ; sqrt(df|sf)2 instruction pattern(s).
8130 ;
8131
8132 ; sqxbr, sqdbr, sqebr, sqdb, sqeb
8133 (define_insn "sqrt<mode>2"
8134 [(set (match_operand:BFP 0 "register_operand" "=f, f,<vf>")
8135 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,<Rf>,<vf>")))]
8136 "TARGET_HARD_FLOAT"
8137 "@
8138 sq<xde>br\t%0,%1
8139 sq<xde>b\t%0,%1
8140 wfsqdb\t%v0,%v1"
8141 [(set_attr "op_type" "RRE,RXE,VRR")
8142 (set_attr "type" "fsqrt<mode>")
8143 (set_attr "cpu_facility" "*,*,vec")])
8144
8145
8146 ;;
8147 ;;- One complement instructions.
8148 ;;
8149
8150 ;
8151 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
8152 ;
8153
8154 (define_expand "one_cmpl<mode>2"
8155 [(parallel
8156 [(set (match_operand:INT 0 "register_operand" "")
8157 (xor:INT (match_operand:INT 1 "register_operand" "")
8158 (const_int -1)))
8159 (clobber (reg:CC CC_REGNUM))])]
8160 ""
8161 "")
8162
8163
8164 ;;
8165 ;; Find leftmost bit instructions.
8166 ;;
8167
8168 (define_expand "clzdi2"
8169 [(set (match_operand:DI 0 "register_operand" "=d")
8170 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
8171 "TARGET_EXTIMM && TARGET_ZARCH"
8172 {
8173 rtx insn, clz_equal;
8174 rtx wide_reg = gen_reg_rtx (TImode);
8175 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
8176
8177 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
8178
8179 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
8180
8181 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
8182 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
8183
8184 DONE;
8185 })
8186
8187 (define_insn "clztidi2"
8188 [(set (match_operand:TI 0 "register_operand" "=d")
8189 (ior:TI
8190 (ashift:TI
8191 (zero_extend:TI
8192 (xor:DI (match_operand:DI 1 "register_operand" "d")
8193 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
8194 (subreg:SI (clz:DI (match_dup 1)) 4))))
8195
8196 (const_int 64))
8197 (zero_extend:TI (clz:DI (match_dup 1)))))
8198 (clobber (reg:CC CC_REGNUM))]
8199 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
8200 == (unsigned HOST_WIDE_INT) 1 << 63
8201 && TARGET_EXTIMM && TARGET_ZARCH"
8202 "flogr\t%0,%1"
8203 [(set_attr "op_type" "RRE")])
8204
8205
8206 ;;
8207 ;;- Rotate instructions.
8208 ;;
8209
8210 ;
8211 ; rotl(di|si)3 instruction pattern(s).
8212 ;
8213
8214 ; rll, rllg
8215 (define_insn "rotl<mode>3"
8216 [(set (match_operand:GPR 0 "register_operand" "=d")
8217 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8218 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
8219 "TARGET_CPU_ZARCH"
8220 "rll<g>\t%0,%1,%Y2"
8221 [(set_attr "op_type" "RSE")
8222 (set_attr "atype" "reg")
8223 (set_attr "z10prop" "z10_super_E1")])
8224
8225 ; rll, rllg
8226 (define_insn "*rotl<mode>3_and"
8227 [(set (match_operand:GPR 0 "register_operand" "=d")
8228 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8229 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8230 (match_operand:SI 3 "const_int_operand" "n"))))]
8231 "TARGET_CPU_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8232 "rll<g>\t%0,%1,%Y2"
8233 [(set_attr "op_type" "RSE")
8234 (set_attr "atype" "reg")
8235 (set_attr "z10prop" "z10_super_E1")])
8236
8237
8238 ;;
8239 ;;- Shift instructions.
8240 ;;
8241
8242 ;
8243 ; (ashl|lshr)(di|si)3 instruction pattern(s).
8244 ; Left shifts and logical right shifts
8245
8246 (define_expand "<shift><mode>3"
8247 [(set (match_operand:DSI 0 "register_operand" "")
8248 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
8249 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))]
8250 ""
8251 "")
8252
8253 ; sldl, srdl
8254 (define_insn "*<shift>di3_31"
8255 [(set (match_operand:DI 0 "register_operand" "=d")
8256 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8257 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
8258 "!TARGET_ZARCH"
8259 "s<lr>dl\t%0,%Y2"
8260 [(set_attr "op_type" "RS")
8261 (set_attr "atype" "reg")
8262 (set_attr "z196prop" "z196_cracked")])
8263
8264 ; sll, srl, sllg, srlg, sllk, srlk
8265 (define_insn "*<shift><mode>3"
8266 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8267 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8268 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")))]
8269 ""
8270 "@
8271 s<lr>l<g>\t%0,<1>%Y2
8272 s<lr>l<gk>\t%0,%1,%Y2"
8273 [(set_attr "op_type" "RS<E>,RSY")
8274 (set_attr "atype" "reg,reg")
8275 (set_attr "cpu_facility" "*,z196")
8276 (set_attr "z10prop" "z10_super_E1,*")])
8277
8278 ; sldl, srdl
8279 (define_insn "*<shift>di3_31_and"
8280 [(set (match_operand:DI 0 "register_operand" "=d")
8281 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8282 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8283 (match_operand:SI 3 "const_int_operand" "n"))))]
8284 "!TARGET_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8285 "s<lr>dl\t%0,%Y2"
8286 [(set_attr "op_type" "RS")
8287 (set_attr "atype" "reg")])
8288
8289 ; sll, srl, sllg, srlg, sllk, srlk
8290 (define_insn "*<shift><mode>3_and"
8291 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8292 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8293 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8294 (match_operand:SI 3 "const_int_operand" "n,n"))))]
8295 "(INTVAL (operands[3]) & 63) == 63"
8296 "@
8297 s<lr>l<g>\t%0,<1>%Y2
8298 s<lr>l<gk>\t%0,%1,%Y2"
8299 [(set_attr "op_type" "RS<E>,RSY")
8300 (set_attr "atype" "reg,reg")
8301 (set_attr "cpu_facility" "*,z196")
8302 (set_attr "z10prop" "z10_super_E1,*")])
8303
8304 ;
8305 ; ashr(di|si)3 instruction pattern(s).
8306 ; Arithmetic right shifts
8307
8308 (define_expand "ashr<mode>3"
8309 [(parallel
8310 [(set (match_operand:DSI 0 "register_operand" "")
8311 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
8312 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))
8313 (clobber (reg:CC CC_REGNUM))])]
8314 ""
8315 "")
8316
8317 (define_insn "*ashrdi3_cc_31"
8318 [(set (reg CC_REGNUM)
8319 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8320 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
8321 (const_int 0)))
8322 (set (match_operand:DI 0 "register_operand" "=d")
8323 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
8324 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)"
8325 "srda\t%0,%Y2"
8326 [(set_attr "op_type" "RS")
8327 (set_attr "atype" "reg")])
8328
8329 (define_insn "*ashrdi3_cconly_31"
8330 [(set (reg CC_REGNUM)
8331 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8332 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
8333 (const_int 0)))
8334 (clobber (match_scratch:DI 0 "=d"))]
8335 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)"
8336 "srda\t%0,%Y2"
8337 [(set_attr "op_type" "RS")
8338 (set_attr "atype" "reg")])
8339
8340 (define_insn "*ashrdi3_31"
8341 [(set (match_operand:DI 0 "register_operand" "=d")
8342 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8343 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))
8344 (clobber (reg:CC CC_REGNUM))]
8345 "!TARGET_ZARCH"
8346 "srda\t%0,%Y2"
8347 [(set_attr "op_type" "RS")
8348 (set_attr "atype" "reg")])
8349
8350 ; sra, srag, srak
8351 (define_insn "*ashr<mode>3_cc"
8352 [(set (reg CC_REGNUM)
8353 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8354 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y"))
8355 (const_int 0)))
8356 (set (match_operand:GPR 0 "register_operand" "=d,d")
8357 (ashiftrt:GPR (match_dup 1) (match_dup 2)))]
8358 "s390_match_ccmode(insn, CCSmode)"
8359 "@
8360 sra<g>\t%0,<1>%Y2
8361 sra<gk>\t%0,%1,%Y2"
8362 [(set_attr "op_type" "RS<E>,RSY")
8363 (set_attr "atype" "reg,reg")
8364 (set_attr "cpu_facility" "*,z196")
8365 (set_attr "z10prop" "z10_super_E1,*")])
8366
8367 ; sra, srag, srak
8368 (define_insn "*ashr<mode>3_cconly"
8369 [(set (reg CC_REGNUM)
8370 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8371 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y"))
8372 (const_int 0)))
8373 (clobber (match_scratch:GPR 0 "=d,d"))]
8374 "s390_match_ccmode(insn, CCSmode)"
8375 "@
8376 sra<g>\t%0,<1>%Y2
8377 sra<gk>\t%0,%1,%Y2"
8378 [(set_attr "op_type" "RS<E>,RSY")
8379 (set_attr "atype" "reg,reg")
8380 (set_attr "cpu_facility" "*,z196")
8381 (set_attr "z10prop" "z10_super_E1,*")])
8382
8383 ; sra, srag
8384 (define_insn "*ashr<mode>3"
8385 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8386 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8387 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")))
8388 (clobber (reg:CC CC_REGNUM))]
8389 ""
8390 "@
8391 sra<g>\t%0,<1>%Y2
8392 sra<gk>\t%0,%1,%Y2"
8393 [(set_attr "op_type" "RS<E>,RSY")
8394 (set_attr "atype" "reg,reg")
8395 (set_attr "cpu_facility" "*,z196")
8396 (set_attr "z10prop" "z10_super_E1,*")])
8397
8398
8399 ; shift pattern with implicit ANDs
8400
8401 (define_insn "*ashrdi3_cc_31_and"
8402 [(set (reg CC_REGNUM)
8403 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8404 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8405 (match_operand:SI 3 "const_int_operand" "n")))
8406 (const_int 0)))
8407 (set (match_operand:DI 0 "register_operand" "=d")
8408 (ashiftrt:DI (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
8409 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)
8410 && (INTVAL (operands[3]) & 63) == 63"
8411 "srda\t%0,%Y2"
8412 [(set_attr "op_type" "RS")
8413 (set_attr "atype" "reg")])
8414
8415 (define_insn "*ashrdi3_cconly_31_and"
8416 [(set (reg CC_REGNUM)
8417 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8418 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8419 (match_operand:SI 3 "const_int_operand" "n")))
8420 (const_int 0)))
8421 (clobber (match_scratch:DI 0 "=d"))]
8422 "!TARGET_ZARCH && s390_match_ccmode(insn, CCSmode)
8423 && (INTVAL (operands[3]) & 63) == 63"
8424 "srda\t%0,%Y2"
8425 [(set_attr "op_type" "RS")
8426 (set_attr "atype" "reg")])
8427
8428 (define_insn "*ashrdi3_31_and"
8429 [(set (match_operand:DI 0 "register_operand" "=d")
8430 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
8431 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
8432 (match_operand:SI 3 "const_int_operand" "n"))))
8433 (clobber (reg:CC CC_REGNUM))]
8434 "!TARGET_ZARCH && (INTVAL (operands[3]) & 63) == 63"
8435 "srda\t%0,%Y2"
8436 [(set_attr "op_type" "RS")
8437 (set_attr "atype" "reg")])
8438
8439 ; sra, srag, srak
8440 (define_insn "*ashr<mode>3_cc_and"
8441 [(set (reg CC_REGNUM)
8442 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8443 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8444 (match_operand:SI 3 "const_int_operand" "n,n")))
8445 (const_int 0)))
8446 (set (match_operand:GPR 0 "register_operand" "=d,d")
8447 (ashiftrt:GPR (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
8448 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
8449 "@
8450 sra<g>\t%0,<1>%Y2
8451 sra<gk>\t%0,%1,%Y2"
8452 [(set_attr "op_type" "RS<E>,RSY")
8453 (set_attr "atype" "reg,reg")
8454 (set_attr "cpu_facility" "*,z196")
8455 (set_attr "z10prop" "z10_super_E1,*")])
8456
8457 ; sra, srag, srak
8458 (define_insn "*ashr<mode>3_cconly_and"
8459 [(set (reg CC_REGNUM)
8460 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8461 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8462 (match_operand:SI 3 "const_int_operand" "n,n")))
8463 (const_int 0)))
8464 (clobber (match_scratch:GPR 0 "=d,d"))]
8465 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
8466 "@
8467 sra<g>\t%0,<1>%Y2
8468 sra<gk>\t%0,%1,%Y2"
8469 [(set_attr "op_type" "RS<E>,RSY")
8470 (set_attr "atype" "reg,reg")
8471 (set_attr "cpu_facility" "*,z196")
8472 (set_attr "z10prop" "z10_super_E1,*")])
8473
8474 ; sra, srag, srak
8475 (define_insn "*ashr<mode>3_and"
8476 [(set (match_operand:GPR 0 "register_operand" "=d,d")
8477 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>,d")
8478 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y,Y")
8479 (match_operand:SI 3 "const_int_operand" "n,n"))))
8480 (clobber (reg:CC CC_REGNUM))]
8481 "(INTVAL (operands[3]) & 63) == 63"
8482 "@
8483 sra<g>\t%0,<1>%Y2
8484 sra<gk>\t%0,%1,%Y2"
8485 [(set_attr "op_type" "RS<E>,RSY")
8486 (set_attr "atype" "reg,reg")
8487 (set_attr "cpu_facility" "*,z196")
8488 (set_attr "z10prop" "z10_super_E1,*")])
8489
8490
8491 ;;
8492 ;; Branch instruction patterns.
8493 ;;
8494
8495 (define_expand "cbranch<mode>4"
8496 [(set (pc)
8497 (if_then_else (match_operator 0 "comparison_operator"
8498 [(match_operand:GPR 1 "register_operand" "")
8499 (match_operand:GPR 2 "general_operand" "")])
8500 (label_ref (match_operand 3 "" ""))
8501 (pc)))]
8502 ""
8503 "s390_emit_jump (operands[3],
8504 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8505 DONE;")
8506
8507 (define_expand "cbranch<mode>4"
8508 [(set (pc)
8509 (if_then_else (match_operator 0 "comparison_operator"
8510 [(match_operand:FP 1 "register_operand" "")
8511 (match_operand:FP 2 "general_operand" "")])
8512 (label_ref (match_operand 3 "" ""))
8513 (pc)))]
8514 "TARGET_HARD_FLOAT"
8515 "s390_emit_jump (operands[3],
8516 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8517 DONE;")
8518
8519 (define_expand "cbranchcc4"
8520 [(set (pc)
8521 (if_then_else (match_operator 0 "s390_comparison"
8522 [(match_operand 1 "cc_reg_operand" "")
8523 (match_operand 2 "const_int_operand" "")])
8524 (label_ref (match_operand 3 "" ""))
8525 (pc)))]
8526 ""
8527 "")
8528
8529
8530 ;;
8531 ;;- Conditional jump instructions.
8532 ;;
8533
8534 (define_insn "*cjump_64"
8535 [(set (pc)
8536 (if_then_else
8537 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8538 (match_operand 2 "const_int_operand" "")])
8539 (label_ref (match_operand 0 "" ""))
8540 (pc)))]
8541 "TARGET_CPU_ZARCH"
8542 {
8543 if (get_attr_length (insn) == 4)
8544 return "j%C1\t%l0";
8545 else
8546 return "jg%C1\t%l0";
8547 }
8548 [(set_attr "op_type" "RI")
8549 (set_attr "type" "branch")
8550 (set (attr "length")
8551 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8552 (const_int 4) (const_int 6)))])
8553
8554 (define_insn "*cjump_31"
8555 [(set (pc)
8556 (if_then_else
8557 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8558 (match_operand 2 "const_int_operand" "")])
8559 (label_ref (match_operand 0 "" ""))
8560 (pc)))]
8561 "!TARGET_CPU_ZARCH"
8562 {
8563 gcc_assert (get_attr_length (insn) == 4);
8564 return "j%C1\t%l0";
8565 }
8566 [(set_attr "op_type" "RI")
8567 (set_attr "type" "branch")
8568 (set (attr "length")
8569 (if_then_else (not (match_test "flag_pic"))
8570 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8571 (const_int 4) (const_int 6))
8572 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8573 (const_int 4) (const_int 8))))])
8574
8575 (define_insn "*cjump_long"
8576 [(set (pc)
8577 (if_then_else
8578 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8579 (match_operand 0 "address_operand" "ZQZR")
8580 (pc)))]
8581 ""
8582 {
8583 if (get_attr_op_type (insn) == OP_TYPE_RR)
8584 return "b%C1r\t%0";
8585 else
8586 return "b%C1\t%a0";
8587 }
8588 [(set (attr "op_type")
8589 (if_then_else (match_operand 0 "register_operand" "")
8590 (const_string "RR") (const_string "RX")))
8591 (set_attr "type" "branch")
8592 (set_attr "atype" "agen")])
8593
8594 ;; A conditional return instruction.
8595 (define_insn "*c<code>"
8596 [(set (pc)
8597 (if_then_else
8598 (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8599 (ANY_RETURN)
8600 (pc)))]
8601 "s390_can_use_<code>_insn ()"
8602 "b%C0r\t%%r14"
8603 [(set_attr "op_type" "RR")
8604 (set_attr "type" "jsr")
8605 (set_attr "atype" "agen")])
8606
8607 ;;
8608 ;;- Negated conditional jump instructions.
8609 ;;
8610
8611 (define_insn "*icjump_64"
8612 [(set (pc)
8613 (if_then_else
8614 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8615 (pc)
8616 (label_ref (match_operand 0 "" ""))))]
8617 "TARGET_CPU_ZARCH"
8618 {
8619 if (get_attr_length (insn) == 4)
8620 return "j%D1\t%l0";
8621 else
8622 return "jg%D1\t%l0";
8623 }
8624 [(set_attr "op_type" "RI")
8625 (set_attr "type" "branch")
8626 (set (attr "length")
8627 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8628 (const_int 4) (const_int 6)))])
8629
8630 (define_insn "*icjump_31"
8631 [(set (pc)
8632 (if_then_else
8633 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8634 (pc)
8635 (label_ref (match_operand 0 "" ""))))]
8636 "!TARGET_CPU_ZARCH"
8637 {
8638 gcc_assert (get_attr_length (insn) == 4);
8639 return "j%D1\t%l0";
8640 }
8641 [(set_attr "op_type" "RI")
8642 (set_attr "type" "branch")
8643 (set (attr "length")
8644 (if_then_else (not (match_test "flag_pic"))
8645 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8646 (const_int 4) (const_int 6))
8647 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8648 (const_int 4) (const_int 8))))])
8649
8650 (define_insn "*icjump_long"
8651 [(set (pc)
8652 (if_then_else
8653 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8654 (pc)
8655 (match_operand 0 "address_operand" "ZQZR")))]
8656 ""
8657 {
8658 if (get_attr_op_type (insn) == OP_TYPE_RR)
8659 return "b%D1r\t%0";
8660 else
8661 return "b%D1\t%a0";
8662 }
8663 [(set (attr "op_type")
8664 (if_then_else (match_operand 0 "register_operand" "")
8665 (const_string "RR") (const_string "RX")))
8666 (set_attr "type" "branch")
8667 (set_attr "atype" "agen")])
8668
8669 ;;
8670 ;;- Trap instructions.
8671 ;;
8672
8673 (define_insn "trap"
8674 [(trap_if (const_int 1) (const_int 0))]
8675 ""
8676 "j\t.+2"
8677 [(set_attr "op_type" "RI")
8678 (set_attr "type" "branch")])
8679
8680 (define_expand "ctrap<mode>4"
8681 [(trap_if (match_operator 0 "comparison_operator"
8682 [(match_operand:GPR 1 "register_operand" "")
8683 (match_operand:GPR 2 "general_operand" "")])
8684 (match_operand 3 "const0_operand" ""))]
8685 ""
8686 {
8687 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8688 operands[1], operands[2]);
8689 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8690 DONE;
8691 })
8692
8693 (define_expand "ctrap<mode>4"
8694 [(trap_if (match_operator 0 "comparison_operator"
8695 [(match_operand:FP 1 "register_operand" "")
8696 (match_operand:FP 2 "general_operand" "")])
8697 (match_operand 3 "const0_operand" ""))]
8698 ""
8699 {
8700 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8701 operands[1], operands[2]);
8702 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8703 DONE;
8704 })
8705
8706 (define_insn "condtrap"
8707 [(trap_if (match_operator 0 "s390_comparison"
8708 [(match_operand 1 "cc_reg_operand" "c")
8709 (const_int 0)])
8710 (const_int 0))]
8711 ""
8712 "j%C0\t.+2";
8713 [(set_attr "op_type" "RI")
8714 (set_attr "type" "branch")])
8715
8716 ; crt, cgrt, cit, cgit
8717 (define_insn "*cmp_and_trap_signed_int<mode>"
8718 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
8719 [(match_operand:GPR 1 "register_operand" "d,d")
8720 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
8721 (const_int 0))]
8722 "TARGET_Z10"
8723 "@
8724 c<g>rt%C0\t%1,%2
8725 c<g>it%C0\t%1,%h2"
8726 [(set_attr "op_type" "RRF,RIE")
8727 (set_attr "type" "branch")
8728 (set_attr "z10prop" "z10_super_c,z10_super")])
8729
8730 ; clrt, clgrt, clfit, clgit, clt, clgt
8731 (define_insn "*cmp_and_trap_unsigned_int<mode>"
8732 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
8733 [(match_operand:GPR 1 "register_operand" "d,d, d")
8734 (match_operand:GPR 2 "general_operand" "d,D,RT")])
8735 (const_int 0))]
8736 "TARGET_Z10"
8737 "@
8738 cl<g>rt%C0\t%1,%2
8739 cl<gf>it%C0\t%1,%x2
8740 cl<g>t%C0\t%1,%2"
8741 [(set_attr "op_type" "RRF,RIE,RSY")
8742 (set_attr "type" "branch")
8743 (set_attr "z10prop" "z10_super_c,z10_super,*")
8744 (set_attr "cpu_facility" "z10,z10,zEC12")])
8745
8746 ; lat, lgat
8747 (define_insn "*load_and_trap<mode>"
8748 [(trap_if (eq (match_operand:GPR 0 "memory_operand" "RT")
8749 (const_int 0))
8750 (const_int 0))
8751 (set (match_operand:GPR 1 "register_operand" "=d")
8752 (match_dup 0))]
8753 "TARGET_ZEC12"
8754 "l<g>at\t%1,%0"
8755 [(set_attr "op_type" "RXY")])
8756
8757
8758 ;;
8759 ;;- Loop instructions.
8760 ;;
8761 ;; This is all complicated by the fact that since this is a jump insn
8762 ;; we must handle our own output reloads.
8763
8764 ;; branch on index
8765
8766 ; This splitter will be matched by combine and has to add the 2 moves
8767 ; necessary to load the compare and the increment values into a
8768 ; register pair as needed by brxle.
8769
8770 (define_insn_and_split "*brx_stage1_<GPR:mode>"
8771 [(set (pc)
8772 (if_then_else
8773 (match_operator 6 "s390_brx_operator"
8774 [(plus:GPR (match_operand:GPR 1 "register_operand" "")
8775 (match_operand:GPR 2 "general_operand" ""))
8776 (match_operand:GPR 3 "register_operand" "")])
8777 (label_ref (match_operand 0 "" ""))
8778 (pc)))
8779 (set (match_operand:GPR 4 "nonimmediate_operand" "")
8780 (plus:GPR (match_dup 1) (match_dup 2)))
8781 (clobber (match_scratch:GPR 5 ""))]
8782 "TARGET_CPU_ZARCH"
8783 "#"
8784 "!reload_completed && !reload_in_progress"
8785 [(set (match_dup 7) (match_dup 2)) ; the increment
8786 (set (match_dup 8) (match_dup 3)) ; the comparison value
8787 (parallel [(set (pc)
8788 (if_then_else
8789 (match_op_dup 6
8790 [(plus:GPR (match_dup 1) (match_dup 7))
8791 (match_dup 8)])
8792 (label_ref (match_dup 0))
8793 (pc)))
8794 (set (match_dup 4)
8795 (plus:GPR (match_dup 1) (match_dup 7)))
8796 (clobber (match_dup 5))
8797 (clobber (reg:CC CC_REGNUM))])]
8798 {
8799 rtx dreg = gen_reg_rtx (word_mode == DImode ? TImode : DImode);
8800 operands[7] = gen_lowpart (<GPR:MODE>mode,
8801 gen_highpart (word_mode, dreg));
8802 operands[8] = gen_lowpart (<GPR:MODE>mode,
8803 gen_lowpart (word_mode, dreg));
8804 })
8805
8806 ; brxlg, brxhg
8807
8808 (define_insn_and_split "*brxg_64bit"
8809 [(set (pc)
8810 (if_then_else
8811 (match_operator 5 "s390_brx_operator"
8812 [(plus:DI (match_operand:DI 1 "register_operand" "d,d,d")
8813 (subreg:DI (match_operand:TI 2 "register_operand" "d,d,d") 0))
8814 (subreg:DI (match_dup 2) 8)])
8815 (label_ref (match_operand 0 "" ""))
8816 (pc)))
8817 (set (match_operand:DI 3 "nonimmediate_operand" "=1,?X,?X")
8818 (plus:DI (match_dup 1)
8819 (subreg:DI (match_dup 2) 0)))
8820 (clobber (match_scratch:DI 4 "=X,&1,&?d"))
8821 (clobber (reg:CC CC_REGNUM))]
8822 "TARGET_ZARCH"
8823 {
8824 if (which_alternative != 0)
8825 return "#";
8826 else if (get_attr_length (insn) == 6)
8827 return "brx%E5g\t%1,%2,%l0";
8828 else
8829 return "agr\t%1,%2\;cgr\t%1,%M2\;jg%C5\t%l0";
8830 }
8831 "&& reload_completed
8832 && (!REG_P (operands[3])
8833 || !rtx_equal_p (operands[1], operands[3]))"
8834 [(set (match_dup 4) (match_dup 1))
8835 (parallel [(set (match_dup 4) (plus:DI (match_dup 4) (subreg:DI (match_dup 2) 0)))
8836 (clobber (reg:CC CC_REGNUM))])
8837 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:DI (match_dup 2) 8)))
8838 (set (match_dup 3) (match_dup 4))
8839 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8840 (label_ref (match_dup 0))
8841 (pc)))]
8842 ""
8843 [(set_attr "op_type" "RIE")
8844 (set_attr "type" "branch")
8845 (set (attr "length")
8846 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8847 (const_int 6) (const_int 16)))])
8848
8849 ; brxle, brxh
8850
8851 (define_insn_and_split "*brx_64bit"
8852 [(set (pc)
8853 (if_then_else
8854 (match_operator 5 "s390_brx_operator"
8855 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
8856 (subreg:SI (match_operand:TI 2 "register_operand" "d,d,d") 4))
8857 (subreg:SI (match_dup 2) 12)])
8858 (label_ref (match_operand 0 "" ""))
8859 (pc)))
8860 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
8861 (plus:SI (match_dup 1)
8862 (subreg:SI (match_dup 2) 4)))
8863 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
8864 (clobber (reg:CC CC_REGNUM))]
8865 "TARGET_ZARCH"
8866 {
8867 if (which_alternative != 0)
8868 return "#";
8869 else if (get_attr_length (insn) == 6)
8870 return "brx%C5\t%1,%2,%l0";
8871 else
8872 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
8873 }
8874 "&& reload_completed
8875 && (!REG_P (operands[3])
8876 || !rtx_equal_p (operands[1], operands[3]))"
8877 [(set (match_dup 4) (match_dup 1))
8878 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 4)))
8879 (clobber (reg:CC CC_REGNUM))])
8880 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 12)))
8881 (set (match_dup 3) (match_dup 4))
8882 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8883 (label_ref (match_dup 0))
8884 (pc)))]
8885 ""
8886 [(set_attr "op_type" "RSI")
8887 (set_attr "type" "branch")
8888 (set (attr "length")
8889 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8890 (const_int 6) (const_int 14)))])
8891
8892 ; brxle, brxh
8893
8894 (define_insn_and_split "*brx_31bit"
8895 [(set (pc)
8896 (if_then_else
8897 (match_operator 5 "s390_brx_operator"
8898 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
8899 (subreg:SI (match_operand:DI 2 "register_operand" "d,d,d") 0))
8900 (subreg:SI (match_dup 2) 4)])
8901 (label_ref (match_operand 0 "" ""))
8902 (pc)))
8903 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
8904 (plus:SI (match_dup 1)
8905 (subreg:SI (match_dup 2) 0)))
8906 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
8907 (clobber (reg:CC CC_REGNUM))]
8908 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
8909 {
8910 if (which_alternative != 0)
8911 return "#";
8912 else if (get_attr_length (insn) == 6)
8913 return "brx%C5\t%1,%2,%l0";
8914 else
8915 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
8916 }
8917 "&& reload_completed
8918 && (!REG_P (operands[3])
8919 || !rtx_equal_p (operands[1], operands[3]))"
8920 [(set (match_dup 4) (match_dup 1))
8921 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 0)))
8922 (clobber (reg:CC CC_REGNUM))])
8923 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 4)))
8924 (set (match_dup 3) (match_dup 4))
8925 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
8926 (label_ref (match_dup 0))
8927 (pc)))]
8928 ""
8929 [(set_attr "op_type" "RSI")
8930 (set_attr "type" "branch")
8931 (set (attr "length")
8932 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8933 (const_int 6) (const_int 14)))])
8934
8935
8936 ;; branch on count
8937
8938 (define_expand "doloop_end"
8939 [(use (match_operand 0 "" "")) ; loop pseudo
8940 (use (match_operand 1 "" ""))] ; label
8941 ""
8942 {
8943 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
8944 emit_jump_insn (gen_doloop_si31 (operands[1], operands[0], operands[0]));
8945 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
8946 emit_jump_insn (gen_doloop_si64 (operands[1], operands[0], operands[0]));
8947 else if (GET_MODE (operands[0]) == DImode && TARGET_ZARCH)
8948 emit_jump_insn (gen_doloop_di (operands[1], operands[0], operands[0]));
8949 else
8950 FAIL;
8951
8952 DONE;
8953 })
8954
8955 (define_insn_and_split "doloop_si64"
8956 [(set (pc)
8957 (if_then_else
8958 (ne (match_operand:SI 1 "register_operand" "d,d,d")
8959 (const_int 1))
8960 (label_ref (match_operand 0 "" ""))
8961 (pc)))
8962 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
8963 (plus:SI (match_dup 1) (const_int -1)))
8964 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
8965 (clobber (reg:CC CC_REGNUM))]
8966 "TARGET_CPU_ZARCH"
8967 {
8968 if (which_alternative != 0)
8969 return "#";
8970 else if (get_attr_length (insn) == 4)
8971 return "brct\t%1,%l0";
8972 else
8973 return "ahi\t%1,-1\;jgne\t%l0";
8974 }
8975 "&& reload_completed
8976 && (! REG_P (operands[2])
8977 || ! rtx_equal_p (operands[1], operands[2]))"
8978 [(set (match_dup 3) (match_dup 1))
8979 (parallel [(set (reg:CCAN CC_REGNUM)
8980 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
8981 (const_int 0)))
8982 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
8983 (set (match_dup 2) (match_dup 3))
8984 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
8985 (label_ref (match_dup 0))
8986 (pc)))]
8987 ""
8988 [(set_attr "op_type" "RI")
8989 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
8990 ; hurt us in the (rare) case of ahi.
8991 (set_attr "z10prop" "z10_super_E1")
8992 (set_attr "type" "branch")
8993 (set (attr "length")
8994 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8995 (const_int 4) (const_int 10)))])
8996
8997 (define_insn_and_split "doloop_si31"
8998 [(set (pc)
8999 (if_then_else
9000 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9001 (const_int 1))
9002 (label_ref (match_operand 0 "" ""))
9003 (pc)))
9004 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9005 (plus:SI (match_dup 1) (const_int -1)))
9006 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9007 (clobber (reg:CC CC_REGNUM))]
9008 "!TARGET_CPU_ZARCH"
9009 {
9010 if (which_alternative != 0)
9011 return "#";
9012 else if (get_attr_length (insn) == 4)
9013 return "brct\t%1,%l0";
9014 else
9015 gcc_unreachable ();
9016 }
9017 "&& reload_completed
9018 && (! REG_P (operands[2])
9019 || ! rtx_equal_p (operands[1], operands[2]))"
9020 [(set (match_dup 3) (match_dup 1))
9021 (parallel [(set (reg:CCAN CC_REGNUM)
9022 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9023 (const_int 0)))
9024 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9025 (set (match_dup 2) (match_dup 3))
9026 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9027 (label_ref (match_dup 0))
9028 (pc)))]
9029 ""
9030 [(set_attr "op_type" "RI")
9031 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9032 ; hurt us in the (rare) case of ahi.
9033 (set_attr "z10prop" "z10_super_E1")
9034 (set_attr "type" "branch")
9035 (set (attr "length")
9036 (if_then_else (not (match_test "flag_pic"))
9037 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9038 (const_int 4) (const_int 6))
9039 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9040 (const_int 4) (const_int 8))))])
9041
9042 (define_insn "*doloop_si_long"
9043 [(set (pc)
9044 (if_then_else
9045 (ne (match_operand:SI 1 "register_operand" "d")
9046 (const_int 1))
9047 (match_operand 0 "address_operand" "ZQZR")
9048 (pc)))
9049 (set (match_operand:SI 2 "register_operand" "=1")
9050 (plus:SI (match_dup 1) (const_int -1)))
9051 (clobber (match_scratch:SI 3 "=X"))
9052 (clobber (reg:CC CC_REGNUM))]
9053 "!TARGET_CPU_ZARCH"
9054 {
9055 if (get_attr_op_type (insn) == OP_TYPE_RR)
9056 return "bctr\t%1,%0";
9057 else
9058 return "bct\t%1,%a0";
9059 }
9060 [(set (attr "op_type")
9061 (if_then_else (match_operand 0 "register_operand" "")
9062 (const_string "RR") (const_string "RX")))
9063 (set_attr "type" "branch")
9064 (set_attr "atype" "agen")
9065 (set_attr "z10prop" "z10_c")
9066 (set_attr "z196prop" "z196_cracked")])
9067
9068 (define_insn_and_split "doloop_di"
9069 [(set (pc)
9070 (if_then_else
9071 (ne (match_operand:DI 1 "register_operand" "d,d,d")
9072 (const_int 1))
9073 (label_ref (match_operand 0 "" ""))
9074 (pc)))
9075 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
9076 (plus:DI (match_dup 1) (const_int -1)))
9077 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
9078 (clobber (reg:CC CC_REGNUM))]
9079 "TARGET_ZARCH"
9080 {
9081 if (which_alternative != 0)
9082 return "#";
9083 else if (get_attr_length (insn) == 4)
9084 return "brctg\t%1,%l0";
9085 else
9086 return "aghi\t%1,-1\;jgne\t%l0";
9087 }
9088 "&& reload_completed
9089 && (! REG_P (operands[2])
9090 || ! rtx_equal_p (operands[1], operands[2]))"
9091 [(set (match_dup 3) (match_dup 1))
9092 (parallel [(set (reg:CCAN CC_REGNUM)
9093 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
9094 (const_int 0)))
9095 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
9096 (set (match_dup 2) (match_dup 3))
9097 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9098 (label_ref (match_dup 0))
9099 (pc)))]
9100 ""
9101 [(set_attr "op_type" "RI")
9102 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9103 ; hurt us in the (rare) case of ahi.
9104 (set_attr "z10prop" "z10_super_E1")
9105 (set_attr "type" "branch")
9106 (set (attr "length")
9107 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9108 (const_int 4) (const_int 10)))])
9109
9110 ;;
9111 ;;- Unconditional jump instructions.
9112 ;;
9113
9114 ;
9115 ; jump instruction pattern(s).
9116 ;
9117
9118 (define_expand "jump"
9119 [(match_operand 0 "" "")]
9120 ""
9121 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
9122
9123 (define_insn "*jump64"
9124 [(set (pc) (label_ref (match_operand 0 "" "")))]
9125 "TARGET_CPU_ZARCH"
9126 {
9127 if (get_attr_length (insn) == 4)
9128 return "j\t%l0";
9129 else
9130 return "jg\t%l0";
9131 }
9132 [(set_attr "op_type" "RI")
9133 (set_attr "type" "branch")
9134 (set (attr "length")
9135 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9136 (const_int 4) (const_int 6)))])
9137
9138 (define_insn "*jump31"
9139 [(set (pc) (label_ref (match_operand 0 "" "")))]
9140 "!TARGET_CPU_ZARCH"
9141 {
9142 gcc_assert (get_attr_length (insn) == 4);
9143 return "j\t%l0";
9144 }
9145 [(set_attr "op_type" "RI")
9146 (set_attr "type" "branch")
9147 (set (attr "length")
9148 (if_then_else (not (match_test "flag_pic"))
9149 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9150 (const_int 4) (const_int 6))
9151 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9152 (const_int 4) (const_int 8))))])
9153
9154 ;
9155 ; indirect-jump instruction pattern(s).
9156 ;
9157
9158 (define_insn "indirect_jump"
9159 [(set (pc) (match_operand 0 "address_operand" "ZQZR"))]
9160 ""
9161 {
9162 if (get_attr_op_type (insn) == OP_TYPE_RR)
9163 return "br\t%0";
9164 else
9165 return "b\t%a0";
9166 }
9167 [(set (attr "op_type")
9168 (if_then_else (match_operand 0 "register_operand" "")
9169 (const_string "RR") (const_string "RX")))
9170 (set_attr "type" "branch")
9171 (set_attr "atype" "agen")])
9172
9173 ;
9174 ; casesi instruction pattern(s).
9175 ;
9176
9177 (define_insn "casesi_jump"
9178 [(set (pc) (match_operand 0 "address_operand" "ZQZR"))
9179 (use (label_ref (match_operand 1 "" "")))]
9180 ""
9181 {
9182 if (get_attr_op_type (insn) == OP_TYPE_RR)
9183 return "br\t%0";
9184 else
9185 return "b\t%a0";
9186 }
9187 [(set (attr "op_type")
9188 (if_then_else (match_operand 0 "register_operand" "")
9189 (const_string "RR") (const_string "RX")))
9190 (set_attr "type" "branch")
9191 (set_attr "atype" "agen")])
9192
9193 (define_expand "casesi"
9194 [(match_operand:SI 0 "general_operand" "")
9195 (match_operand:SI 1 "general_operand" "")
9196 (match_operand:SI 2 "general_operand" "")
9197 (label_ref (match_operand 3 "" ""))
9198 (label_ref (match_operand 4 "" ""))]
9199 ""
9200 {
9201 rtx index = gen_reg_rtx (SImode);
9202 rtx base = gen_reg_rtx (Pmode);
9203 rtx target = gen_reg_rtx (Pmode);
9204
9205 emit_move_insn (index, operands[0]);
9206 emit_insn (gen_subsi3 (index, index, operands[1]));
9207 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
9208 operands[4]);
9209
9210 if (Pmode != SImode)
9211 index = convert_to_mode (Pmode, index, 1);
9212 if (GET_CODE (index) != REG)
9213 index = copy_to_mode_reg (Pmode, index);
9214
9215 if (TARGET_64BIT)
9216 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
9217 else
9218 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
9219
9220 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
9221
9222 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
9223 emit_move_insn (target, index);
9224
9225 if (flag_pic)
9226 target = gen_rtx_PLUS (Pmode, base, target);
9227 emit_jump_insn (gen_casesi_jump (target, operands[3]));
9228
9229 DONE;
9230 })
9231
9232
9233 ;;
9234 ;;- Jump to subroutine.
9235 ;;
9236 ;;
9237
9238 ;
9239 ; untyped call instruction pattern(s).
9240 ;
9241
9242 ;; Call subroutine returning any type.
9243 (define_expand "untyped_call"
9244 [(parallel [(call (match_operand 0 "" "")
9245 (const_int 0))
9246 (match_operand 1 "" "")
9247 (match_operand 2 "" "")])]
9248 ""
9249 {
9250 int i;
9251
9252 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
9253
9254 for (i = 0; i < XVECLEN (operands[2], 0); i++)
9255 {
9256 rtx set = XVECEXP (operands[2], 0, i);
9257 emit_move_insn (SET_DEST (set), SET_SRC (set));
9258 }
9259
9260 /* The optimizer does not know that the call sets the function value
9261 registers we stored in the result block. We avoid problems by
9262 claiming that all hard registers are used and clobbered at this
9263 point. */
9264 emit_insn (gen_blockage ());
9265
9266 DONE;
9267 })
9268
9269 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
9270 ;; all of memory. This blocks insns from being moved across this point.
9271
9272 (define_insn "blockage"
9273 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
9274 ""
9275 ""
9276 [(set_attr "type" "none")
9277 (set_attr "length" "0")])
9278
9279 ;
9280 ; sibcall patterns
9281 ;
9282
9283 (define_expand "sibcall"
9284 [(call (match_operand 0 "" "")
9285 (match_operand 1 "" ""))]
9286 ""
9287 {
9288 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
9289 DONE;
9290 })
9291
9292 (define_insn "*sibcall_br"
9293 [(call (mem:QI (reg SIBCALL_REGNUM))
9294 (match_operand 0 "const_int_operand" "n"))]
9295 "SIBLING_CALL_P (insn)
9296 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
9297 "br\t%%r1"
9298 [(set_attr "op_type" "RR")
9299 (set_attr "type" "branch")
9300 (set_attr "atype" "agen")])
9301
9302 (define_insn "*sibcall_brc"
9303 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9304 (match_operand 1 "const_int_operand" "n"))]
9305 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9306 "j\t%0"
9307 [(set_attr "op_type" "RI")
9308 (set_attr "type" "branch")])
9309
9310 (define_insn "*sibcall_brcl"
9311 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9312 (match_operand 1 "const_int_operand" "n"))]
9313 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9314 "jg\t%0"
9315 [(set_attr "op_type" "RIL")
9316 (set_attr "type" "branch")])
9317
9318 ;
9319 ; sibcall_value patterns
9320 ;
9321
9322 (define_expand "sibcall_value"
9323 [(set (match_operand 0 "" "")
9324 (call (match_operand 1 "" "")
9325 (match_operand 2 "" "")))]
9326 ""
9327 {
9328 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
9329 DONE;
9330 })
9331
9332 (define_insn "*sibcall_value_br"
9333 [(set (match_operand 0 "" "")
9334 (call (mem:QI (reg SIBCALL_REGNUM))
9335 (match_operand 1 "const_int_operand" "n")))]
9336 "SIBLING_CALL_P (insn)
9337 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
9338 "br\t%%r1"
9339 [(set_attr "op_type" "RR")
9340 (set_attr "type" "branch")
9341 (set_attr "atype" "agen")])
9342
9343 (define_insn "*sibcall_value_brc"
9344 [(set (match_operand 0 "" "")
9345 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9346 (match_operand 2 "const_int_operand" "n")))]
9347 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9348 "j\t%1"
9349 [(set_attr "op_type" "RI")
9350 (set_attr "type" "branch")])
9351
9352 (define_insn "*sibcall_value_brcl"
9353 [(set (match_operand 0 "" "")
9354 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9355 (match_operand 2 "const_int_operand" "n")))]
9356 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9357 "jg\t%1"
9358 [(set_attr "op_type" "RIL")
9359 (set_attr "type" "branch")])
9360
9361
9362 ;
9363 ; call instruction pattern(s).
9364 ;
9365
9366 (define_expand "call"
9367 [(call (match_operand 0 "" "")
9368 (match_operand 1 "" ""))
9369 (use (match_operand 2 "" ""))]
9370 ""
9371 {
9372 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
9373 gen_rtx_REG (Pmode, RETURN_REGNUM));
9374 DONE;
9375 })
9376
9377 (define_insn "*bras"
9378 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9379 (match_operand 1 "const_int_operand" "n"))
9380 (clobber (match_operand 2 "register_operand" "=r"))]
9381 "!SIBLING_CALL_P (insn)
9382 && TARGET_SMALL_EXEC
9383 && GET_MODE (operands[2]) == Pmode"
9384 "bras\t%2,%0"
9385 [(set_attr "op_type" "RI")
9386 (set_attr "type" "jsr")
9387 (set_attr "z196prop" "z196_cracked")])
9388
9389 (define_insn "*brasl"
9390 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9391 (match_operand 1 "const_int_operand" "n"))
9392 (clobber (match_operand 2 "register_operand" "=r"))]
9393 "!SIBLING_CALL_P (insn)
9394 && TARGET_CPU_ZARCH
9395 && GET_MODE (operands[2]) == Pmode"
9396 "brasl\t%2,%0"
9397 [(set_attr "op_type" "RIL")
9398 (set_attr "type" "jsr")
9399 (set_attr "z196prop" "z196_cracked")])
9400
9401 (define_insn "*basr"
9402 [(call (mem:QI (match_operand 0 "address_operand" "ZQZR"))
9403 (match_operand 1 "const_int_operand" "n"))
9404 (clobber (match_operand 2 "register_operand" "=r"))]
9405 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
9406 {
9407 if (get_attr_op_type (insn) == OP_TYPE_RR)
9408 return "basr\t%2,%0";
9409 else
9410 return "bas\t%2,%a0";
9411 }
9412 [(set (attr "op_type")
9413 (if_then_else (match_operand 0 "register_operand" "")
9414 (const_string "RR") (const_string "RX")))
9415 (set_attr "type" "jsr")
9416 (set_attr "atype" "agen")
9417 (set_attr "z196prop" "z196_cracked")])
9418
9419 ;
9420 ; call_value instruction pattern(s).
9421 ;
9422
9423 (define_expand "call_value"
9424 [(set (match_operand 0 "" "")
9425 (call (match_operand 1 "" "")
9426 (match_operand 2 "" "")))
9427 (use (match_operand 3 "" ""))]
9428 ""
9429 {
9430 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
9431 gen_rtx_REG (Pmode, RETURN_REGNUM));
9432 DONE;
9433 })
9434
9435 (define_insn "*bras_r"
9436 [(set (match_operand 0 "" "")
9437 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9438 (match_operand:SI 2 "const_int_operand" "n")))
9439 (clobber (match_operand 3 "register_operand" "=r"))]
9440 "!SIBLING_CALL_P (insn)
9441 && TARGET_SMALL_EXEC
9442 && GET_MODE (operands[3]) == Pmode"
9443 "bras\t%3,%1"
9444 [(set_attr "op_type" "RI")
9445 (set_attr "type" "jsr")
9446 (set_attr "z196prop" "z196_cracked")])
9447
9448 (define_insn "*brasl_r"
9449 [(set (match_operand 0 "" "")
9450 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9451 (match_operand 2 "const_int_operand" "n")))
9452 (clobber (match_operand 3 "register_operand" "=r"))]
9453 "!SIBLING_CALL_P (insn)
9454 && TARGET_CPU_ZARCH
9455 && GET_MODE (operands[3]) == Pmode"
9456 "brasl\t%3,%1"
9457 [(set_attr "op_type" "RIL")
9458 (set_attr "type" "jsr")
9459 (set_attr "z196prop" "z196_cracked")])
9460
9461 (define_insn "*basr_r"
9462 [(set (match_operand 0 "" "")
9463 (call (mem:QI (match_operand 1 "address_operand" "ZQZR"))
9464 (match_operand 2 "const_int_operand" "n")))
9465 (clobber (match_operand 3 "register_operand" "=r"))]
9466 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9467 {
9468 if (get_attr_op_type (insn) == OP_TYPE_RR)
9469 return "basr\t%3,%1";
9470 else
9471 return "bas\t%3,%a1";
9472 }
9473 [(set (attr "op_type")
9474 (if_then_else (match_operand 1 "register_operand" "")
9475 (const_string "RR") (const_string "RX")))
9476 (set_attr "type" "jsr")
9477 (set_attr "atype" "agen")
9478 (set_attr "z196prop" "z196_cracked")])
9479
9480 ;;
9481 ;;- Thread-local storage support.
9482 ;;
9483
9484 (define_expand "get_thread_pointer<mode>"
9485 [(set (match_operand:P 0 "nonimmediate_operand" "") (reg:P TP_REGNUM))]
9486 ""
9487 "")
9488
9489 (define_expand "set_thread_pointer<mode>"
9490 [(set (reg:P TP_REGNUM) (match_operand:P 0 "nonimmediate_operand" ""))
9491 (set (reg:P TP_REGNUM) (unspec_volatile:P [(reg:P TP_REGNUM)] UNSPECV_SET_TP))]
9492 ""
9493 "")
9494
9495 (define_insn "*set_tp"
9496 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
9497 ""
9498 ""
9499 [(set_attr "type" "none")
9500 (set_attr "length" "0")])
9501
9502 (define_insn "*tls_load_64"
9503 [(set (match_operand:DI 0 "register_operand" "=d")
9504 (unspec:DI [(match_operand:DI 1 "memory_operand" "RT")
9505 (match_operand:DI 2 "" "")]
9506 UNSPEC_TLS_LOAD))]
9507 "TARGET_64BIT"
9508 "lg\t%0,%1%J2"
9509 [(set_attr "op_type" "RXE")
9510 (set_attr "z10prop" "z10_fwd_A3")])
9511
9512 (define_insn "*tls_load_31"
9513 [(set (match_operand:SI 0 "register_operand" "=d,d")
9514 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
9515 (match_operand:SI 2 "" "")]
9516 UNSPEC_TLS_LOAD))]
9517 "!TARGET_64BIT"
9518 "@
9519 l\t%0,%1%J2
9520 ly\t%0,%1%J2"
9521 [(set_attr "op_type" "RX,RXY")
9522 (set_attr "type" "load")
9523 (set_attr "z10prop" "z10_fwd_A3,z10_fwd_A3")])
9524
9525 (define_insn "*bras_tls"
9526 [(set (match_operand 0 "" "")
9527 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9528 (match_operand 2 "const_int_operand" "n")))
9529 (clobber (match_operand 3 "register_operand" "=r"))
9530 (use (match_operand 4 "" ""))]
9531 "!SIBLING_CALL_P (insn)
9532 && TARGET_SMALL_EXEC
9533 && GET_MODE (operands[3]) == Pmode"
9534 "bras\t%3,%1%J4"
9535 [(set_attr "op_type" "RI")
9536 (set_attr "type" "jsr")
9537 (set_attr "z196prop" "z196_cracked")])
9538
9539 (define_insn "*brasl_tls"
9540 [(set (match_operand 0 "" "")
9541 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9542 (match_operand 2 "const_int_operand" "n")))
9543 (clobber (match_operand 3 "register_operand" "=r"))
9544 (use (match_operand 4 "" ""))]
9545 "!SIBLING_CALL_P (insn)
9546 && TARGET_CPU_ZARCH
9547 && GET_MODE (operands[3]) == Pmode"
9548 "brasl\t%3,%1%J4"
9549 [(set_attr "op_type" "RIL")
9550 (set_attr "type" "jsr")
9551 (set_attr "z196prop" "z196_cracked")])
9552
9553 (define_insn "*basr_tls"
9554 [(set (match_operand 0 "" "")
9555 (call (mem:QI (match_operand 1 "address_operand" "ZQZR"))
9556 (match_operand 2 "const_int_operand" "n")))
9557 (clobber (match_operand 3 "register_operand" "=r"))
9558 (use (match_operand 4 "" ""))]
9559 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9560 {
9561 if (get_attr_op_type (insn) == OP_TYPE_RR)
9562 return "basr\t%3,%1%J4";
9563 else
9564 return "bas\t%3,%a1%J4";
9565 }
9566 [(set (attr "op_type")
9567 (if_then_else (match_operand 1 "register_operand" "")
9568 (const_string "RR") (const_string "RX")))
9569 (set_attr "type" "jsr")
9570 (set_attr "atype" "agen")
9571 (set_attr "z196prop" "z196_cracked")])
9572
9573 ;;
9574 ;;- Atomic operations
9575 ;;
9576
9577 ;
9578 ; memory barrier patterns.
9579 ;
9580
9581 (define_expand "mem_signal_fence"
9582 [(match_operand:SI 0 "const_int_operand")] ;; model
9583 ""
9584 {
9585 /* The s390 memory model is strong enough not to require any
9586 barrier in order to synchronize a thread with itself. */
9587 DONE;
9588 })
9589
9590 (define_expand "mem_thread_fence"
9591 [(match_operand:SI 0 "const_int_operand")] ;; model
9592 ""
9593 {
9594 /* Unless this is a SEQ_CST fence, the s390 memory model is strong
9595 enough not to require barriers of any kind. */
9596 if (is_mm_seq_cst (memmodel_from_int (INTVAL (operands[0]))))
9597 {
9598 rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
9599 MEM_VOLATILE_P (mem) = 1;
9600 emit_insn (gen_mem_thread_fence_1 (mem));
9601 }
9602 DONE;
9603 })
9604
9605 ; Although bcr is superscalar on Z10, this variant will never
9606 ; become part of an execution group.
9607 ; With z196 we can make use of the fast-BCR-serialization facility.
9608 ; This allows for a slightly faster sync which is sufficient for our
9609 ; purposes.
9610 (define_insn "mem_thread_fence_1"
9611 [(set (match_operand:BLK 0 "" "")
9612 (unspec:BLK [(match_dup 0)] UNSPEC_MB))]
9613 ""
9614 {
9615 if (TARGET_Z196)
9616 return "bcr\t14,0";
9617 else
9618 return "bcr\t15,0";
9619 }
9620 [(set_attr "op_type" "RR")
9621 (set_attr "mnemonic" "bcr_flush")
9622 (set_attr "z196prop" "z196_alone")])
9623
9624 ;
9625 ; atomic load/store operations
9626 ;
9627
9628 ; Atomic loads need not examine the memory model at all.
9629 (define_expand "atomic_load<mode>"
9630 [(match_operand:DINT 0 "register_operand") ;; output
9631 (match_operand:DINT 1 "memory_operand") ;; memory
9632 (match_operand:SI 2 "const_int_operand")] ;; model
9633 ""
9634 {
9635 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9636 FAIL;
9637
9638 if (<MODE>mode == TImode)
9639 emit_insn (gen_atomic_loadti_1 (operands[0], operands[1]));
9640 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9641 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1]));
9642 else
9643 emit_move_insn (operands[0], operands[1]);
9644 DONE;
9645 })
9646
9647 ; Different from movdi_31 in that we want no splitters.
9648 (define_insn "atomic_loaddi_1"
9649 [(set (match_operand:DI 0 "register_operand" "=d,d,!*f,!*f")
9650 (unspec:DI [(match_operand:DI 1 "memory_operand" "Q,S,R,T")]
9651 UNSPEC_MOVA))]
9652 "!TARGET_ZARCH"
9653 "@
9654 lm\t%0,%M0,%S1
9655 lmy\t%0,%M0,%S1
9656 ld\t%0,%1
9657 ldy\t%0,%1"
9658 [(set_attr "op_type" "RS,RSY,RS,RSY")
9659 (set_attr "type" "lm,lm,floaddf,floaddf")])
9660
9661 (define_insn "atomic_loadti_1"
9662 [(set (match_operand:TI 0 "register_operand" "=r")
9663 (unspec:TI [(match_operand:TI 1 "memory_operand" "RT")]
9664 UNSPEC_MOVA))]
9665 "TARGET_ZARCH"
9666 "lpq\t%0,%1"
9667 [(set_attr "op_type" "RXY")
9668 (set_attr "type" "other")])
9669
9670 ; Atomic stores must(?) enforce sequential consistency.
9671 (define_expand "atomic_store<mode>"
9672 [(match_operand:DINT 0 "memory_operand") ;; memory
9673 (match_operand:DINT 1 "register_operand") ;; input
9674 (match_operand:SI 2 "const_int_operand")] ;; model
9675 ""
9676 {
9677 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
9678
9679 if (MEM_ALIGN (operands[0]) < GET_MODE_BITSIZE (GET_MODE (operands[0])))
9680 FAIL;
9681
9682 if (<MODE>mode == TImode)
9683 emit_insn (gen_atomic_storeti_1 (operands[0], operands[1]));
9684 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9685 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1]));
9686 else
9687 emit_move_insn (operands[0], operands[1]);
9688 if (is_mm_seq_cst (model))
9689 emit_insn (gen_mem_thread_fence (operands[2]));
9690 DONE;
9691 })
9692
9693 ; Different from movdi_31 in that we want no splitters.
9694 (define_insn "atomic_storedi_1"
9695 [(set (match_operand:DI 0 "memory_operand" "=Q,S,R,T")
9696 (unspec:DI [(match_operand:DI 1 "register_operand" "d,d,!*f,!*f")]
9697 UNSPEC_MOVA))]
9698 "!TARGET_ZARCH"
9699 "@
9700 stm\t%1,%N1,%S0
9701 stmy\t%1,%N1,%S0
9702 std %1,%0
9703 stdy %1,%0"
9704 [(set_attr "op_type" "RS,RSY,RS,RSY")
9705 (set_attr "type" "stm,stm,fstoredf,fstoredf")])
9706
9707 (define_insn "atomic_storeti_1"
9708 [(set (match_operand:TI 0 "memory_operand" "=RT")
9709 (unspec:TI [(match_operand:TI 1 "register_operand" "r")]
9710 UNSPEC_MOVA))]
9711 "TARGET_ZARCH"
9712 "stpq\t%1,%0"
9713 [(set_attr "op_type" "RXY")
9714 (set_attr "type" "other")])
9715
9716 ;
9717 ; compare and swap patterns.
9718 ;
9719
9720 (define_expand "atomic_compare_and_swap<mode>"
9721 [(match_operand:SI 0 "register_operand") ;; bool success output
9722 (match_operand:DGPR 1 "nonimmediate_operand");; oldval output
9723 (match_operand:DGPR 2 "memory_operand") ;; memory
9724 (match_operand:DGPR 3 "register_operand") ;; expected intput
9725 (match_operand:DGPR 4 "register_operand") ;; newval intput
9726 (match_operand:SI 5 "const_int_operand") ;; is_weak
9727 (match_operand:SI 6 "const_int_operand") ;; success model
9728 (match_operand:SI 7 "const_int_operand")] ;; failure model
9729 ""
9730 {
9731 rtx cc, cmp, output = operands[1];
9732
9733 if (!register_operand (output, <MODE>mode))
9734 output = gen_reg_rtx (<MODE>mode);
9735
9736 if (MEM_ALIGN (operands[2]) < GET_MODE_BITSIZE (GET_MODE (operands[2])))
9737 FAIL;
9738
9739 emit_insn (gen_atomic_compare_and_swap<mode>_internal
9740 (output, operands[2], operands[3], operands[4]));
9741
9742 /* We deliberately accept non-register operands in the predicate
9743 to ensure the write back to the output operand happens *before*
9744 the store-flags code below. This makes it easier for combine
9745 to merge the store-flags code with a potential test-and-branch
9746 pattern following (immediately!) afterwards. */
9747 if (output != operands[1])
9748 emit_move_insn (operands[1], output);
9749
9750 cc = gen_rtx_REG (CCZ1mode, CC_REGNUM);
9751 cmp = gen_rtx_EQ (SImode, cc, const0_rtx);
9752 emit_insn (gen_cstorecc4 (operands[0], cmp, cc, const0_rtx));
9753 DONE;
9754 })
9755
9756 (define_expand "atomic_compare_and_swap<mode>"
9757 [(match_operand:SI 0 "register_operand") ;; bool success output
9758 (match_operand:HQI 1 "nonimmediate_operand") ;; oldval output
9759 (match_operand:HQI 2 "memory_operand") ;; memory
9760 (match_operand:HQI 3 "general_operand") ;; expected intput
9761 (match_operand:HQI 4 "general_operand") ;; newval intput
9762 (match_operand:SI 5 "const_int_operand") ;; is_weak
9763 (match_operand:SI 6 "const_int_operand") ;; success model
9764 (match_operand:SI 7 "const_int_operand")] ;; failure model
9765 ""
9766 {
9767 s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1], operands[2],
9768 operands[3], operands[4], INTVAL (operands[5]));
9769 DONE;
9770 })
9771
9772 (define_expand "atomic_compare_and_swap<mode>_internal"
9773 [(parallel
9774 [(set (match_operand:DGPR 0 "register_operand")
9775 (match_operand:DGPR 1 "memory_operand"))
9776 (set (match_dup 1)
9777 (unspec_volatile:DGPR
9778 [(match_dup 1)
9779 (match_operand:DGPR 2 "register_operand")
9780 (match_operand:DGPR 3 "register_operand")]
9781 UNSPECV_CAS))
9782 (set (reg:CCZ1 CC_REGNUM)
9783 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
9784 "")
9785
9786 ; cdsg, csg
9787 (define_insn "*atomic_compare_and_swap<mode>_1"
9788 [(set (match_operand:TDI 0 "register_operand" "=r")
9789 (match_operand:TDI 1 "memory_operand" "+QS"))
9790 (set (match_dup 1)
9791 (unspec_volatile:TDI
9792 [(match_dup 1)
9793 (match_operand:TDI 2 "register_operand" "0")
9794 (match_operand:TDI 3 "register_operand" "r")]
9795 UNSPECV_CAS))
9796 (set (reg:CCZ1 CC_REGNUM)
9797 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9798 "TARGET_ZARCH"
9799 "c<td>sg\t%0,%3,%S1"
9800 [(set_attr "op_type" "RSY")
9801 (set_attr "type" "sem")])
9802
9803 ; cds, cdsy
9804 (define_insn "*atomic_compare_and_swapdi_2"
9805 [(set (match_operand:DI 0 "register_operand" "=r,r")
9806 (match_operand:DI 1 "memory_operand" "+Q,S"))
9807 (set (match_dup 1)
9808 (unspec_volatile:DI
9809 [(match_dup 1)
9810 (match_operand:DI 2 "register_operand" "0,0")
9811 (match_operand:DI 3 "register_operand" "r,r")]
9812 UNSPECV_CAS))
9813 (set (reg:CCZ1 CC_REGNUM)
9814 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9815 "!TARGET_ZARCH"
9816 "@
9817 cds\t%0,%3,%S1
9818 cdsy\t%0,%3,%S1"
9819 [(set_attr "op_type" "RS,RSY")
9820 (set_attr "type" "sem")])
9821
9822 ; cs, csy
9823 (define_insn "*atomic_compare_and_swapsi_3"
9824 [(set (match_operand:SI 0 "register_operand" "=r,r")
9825 (match_operand:SI 1 "memory_operand" "+Q,S"))
9826 (set (match_dup 1)
9827 (unspec_volatile:SI
9828 [(match_dup 1)
9829 (match_operand:SI 2 "register_operand" "0,0")
9830 (match_operand:SI 3 "register_operand" "r,r")]
9831 UNSPECV_CAS))
9832 (set (reg:CCZ1 CC_REGNUM)
9833 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
9834 ""
9835 "@
9836 cs\t%0,%3,%S1
9837 csy\t%0,%3,%S1"
9838 [(set_attr "op_type" "RS,RSY")
9839 (set_attr "type" "sem")])
9840
9841 ;
9842 ; Other atomic instruction patterns.
9843 ;
9844
9845 ; z196 load and add, xor, or and and instructions
9846
9847 (define_expand "atomic_fetch_<atomic><mode>"
9848 [(match_operand:GPR 0 "register_operand") ;; val out
9849 (ATOMIC_Z196:GPR
9850 (match_operand:GPR 1 "memory_operand") ;; memory
9851 (match_operand:GPR 2 "register_operand")) ;; val in
9852 (match_operand:SI 3 "const_int_operand")] ;; model
9853 "TARGET_Z196"
9854 {
9855 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9856 FAIL;
9857
9858 emit_insn (gen_atomic_fetch_<atomic><mode>_iaf
9859 (operands[0], operands[1], operands[2]));
9860 DONE;
9861 })
9862
9863 ; lan, lang, lao, laog, lax, laxg, laa, laag
9864 (define_insn "atomic_fetch_<atomic><mode>_iaf"
9865 [(set (match_operand:GPR 0 "register_operand" "=d")
9866 (match_operand:GPR 1 "memory_operand" "+QS"))
9867 (set (match_dup 1)
9868 (unspec_volatile:GPR
9869 [(ATOMIC_Z196:GPR (match_dup 1)
9870 (match_operand:GPR 2 "general_operand" "d"))]
9871 UNSPECV_ATOMIC_OP))
9872 (clobber (reg:CC CC_REGNUM))]
9873 "TARGET_Z196"
9874 "la<noxa><g>\t%0,%2,%1"
9875 [(set_attr "op_type" "RSY")
9876 (set_attr "type" "sem")])
9877
9878 ;; For SImode and larger, the optabs.c code will do just fine in
9879 ;; expanding a compare-and-swap loop. For QI/HImode, we can do
9880 ;; better by expanding our own loop.
9881
9882 (define_expand "atomic_<atomic><mode>"
9883 [(ATOMIC:HQI
9884 (match_operand:HQI 0 "memory_operand") ;; memory
9885 (match_operand:HQI 1 "general_operand")) ;; val in
9886 (match_operand:SI 2 "const_int_operand")] ;; model
9887 ""
9888 {
9889 s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
9890 operands[1], false);
9891 DONE;
9892 })
9893
9894 (define_expand "atomic_fetch_<atomic><mode>"
9895 [(match_operand:HQI 0 "register_operand") ;; val out
9896 (ATOMIC:HQI
9897 (match_operand:HQI 1 "memory_operand") ;; memory
9898 (match_operand:HQI 2 "general_operand")) ;; val in
9899 (match_operand:SI 3 "const_int_operand")] ;; model
9900 ""
9901 {
9902 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
9903 operands[2], false);
9904 DONE;
9905 })
9906
9907 (define_expand "atomic_<atomic>_fetch<mode>"
9908 [(match_operand:HQI 0 "register_operand") ;; val out
9909 (ATOMIC:HQI
9910 (match_operand:HQI 1 "memory_operand") ;; memory
9911 (match_operand:HQI 2 "general_operand")) ;; val in
9912 (match_operand:SI 3 "const_int_operand")] ;; model
9913 ""
9914 {
9915 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
9916 operands[2], true);
9917 DONE;
9918 })
9919
9920 (define_expand "atomic_exchange<mode>"
9921 [(match_operand:HQI 0 "register_operand") ;; val out
9922 (match_operand:HQI 1 "memory_operand") ;; memory
9923 (match_operand:HQI 2 "general_operand") ;; val in
9924 (match_operand:SI 3 "const_int_operand")] ;; model
9925 ""
9926 {
9927 s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
9928 operands[2], false);
9929 DONE;
9930 })
9931
9932 ;;
9933 ;;- Miscellaneous instructions.
9934 ;;
9935
9936 ;
9937 ; allocate stack instruction pattern(s).
9938 ;
9939
9940 (define_expand "allocate_stack"
9941 [(match_operand 0 "general_operand" "")
9942 (match_operand 1 "general_operand" "")]
9943 "TARGET_BACKCHAIN"
9944 {
9945 rtx temp = gen_reg_rtx (Pmode);
9946
9947 emit_move_insn (temp, s390_back_chain_rtx ());
9948 anti_adjust_stack (operands[1]);
9949 emit_move_insn (s390_back_chain_rtx (), temp);
9950
9951 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
9952 DONE;
9953 })
9954
9955
9956 ;
9957 ; setjmp instruction pattern.
9958 ;
9959
9960 (define_expand "builtin_setjmp_receiver"
9961 [(match_operand 0 "" "")]
9962 "flag_pic"
9963 {
9964 emit_insn (s390_load_got ());
9965 emit_use (pic_offset_table_rtx);
9966 DONE;
9967 })
9968
9969 ;; These patterns say how to save and restore the stack pointer. We need not
9970 ;; save the stack pointer at function level since we are careful to
9971 ;; preserve the backchain. At block level, we have to restore the backchain
9972 ;; when we restore the stack pointer.
9973 ;;
9974 ;; For nonlocal gotos, we must save both the stack pointer and its
9975 ;; backchain and restore both. Note that in the nonlocal case, the
9976 ;; save area is a memory location.
9977
9978 (define_expand "save_stack_function"
9979 [(match_operand 0 "general_operand" "")
9980 (match_operand 1 "general_operand" "")]
9981 ""
9982 "DONE;")
9983
9984 (define_expand "restore_stack_function"
9985 [(match_operand 0 "general_operand" "")
9986 (match_operand 1 "general_operand" "")]
9987 ""
9988 "DONE;")
9989
9990 (define_expand "restore_stack_block"
9991 [(match_operand 0 "register_operand" "")
9992 (match_operand 1 "register_operand" "")]
9993 "TARGET_BACKCHAIN"
9994 {
9995 rtx temp = gen_reg_rtx (Pmode);
9996
9997 emit_move_insn (temp, s390_back_chain_rtx ());
9998 emit_move_insn (operands[0], operands[1]);
9999 emit_move_insn (s390_back_chain_rtx (), temp);
10000
10001 DONE;
10002 })
10003
10004 (define_expand "save_stack_nonlocal"
10005 [(match_operand 0 "memory_operand" "")
10006 (match_operand 1 "register_operand" "")]
10007 ""
10008 {
10009 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10010
10011 /* Copy the backchain to the first word, sp to the second and the
10012 literal pool base to the third. */
10013
10014 rtx save_bc = adjust_address (operands[0], Pmode, 0);
10015 rtx save_sp = adjust_address (operands[0], Pmode, GET_MODE_SIZE (Pmode));
10016 rtx save_bp = adjust_address (operands[0], Pmode, 2 * GET_MODE_SIZE (Pmode));
10017
10018 if (TARGET_BACKCHAIN)
10019 emit_move_insn (save_bc, force_reg (Pmode, s390_back_chain_rtx ()));
10020
10021 emit_move_insn (save_sp, operands[1]);
10022 emit_move_insn (save_bp, base);
10023
10024 DONE;
10025 })
10026
10027 (define_expand "restore_stack_nonlocal"
10028 [(match_operand 0 "register_operand" "")
10029 (match_operand 1 "memory_operand" "")]
10030 ""
10031 {
10032 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10033 rtx temp = NULL_RTX;
10034
10035 /* Restore the backchain from the first word, sp from the second and the
10036 literal pool base from the third. */
10037
10038 rtx save_bc = adjust_address (operands[1], Pmode, 0);
10039 rtx save_sp = adjust_address (operands[1], Pmode, GET_MODE_SIZE (Pmode));
10040 rtx save_bp = adjust_address (operands[1], Pmode, 2 * GET_MODE_SIZE (Pmode));
10041
10042 if (TARGET_BACKCHAIN)
10043 temp = force_reg (Pmode, save_bc);
10044
10045 emit_move_insn (base, save_bp);
10046 emit_move_insn (operands[0], save_sp);
10047
10048 if (temp)
10049 emit_move_insn (s390_back_chain_rtx (), temp);
10050
10051 emit_use (base);
10052 DONE;
10053 })
10054
10055 (define_expand "exception_receiver"
10056 [(const_int 0)]
10057 ""
10058 {
10059 s390_set_has_landing_pad_p (true);
10060 DONE;
10061 })
10062
10063 ;
10064 ; nop instruction pattern(s).
10065 ;
10066
10067 (define_insn "nop"
10068 [(const_int 0)]
10069 ""
10070 "lr\t0,0"
10071 [(set_attr "op_type" "RR")
10072 (set_attr "z10prop" "z10_fr_E1")])
10073
10074 (define_insn "nop1"
10075 [(const_int 1)]
10076 ""
10077 "lr\t1,1"
10078 [(set_attr "op_type" "RR")])
10079
10080 ;;- Undeletable nops (used for hotpatching)
10081
10082 (define_insn "nop_2_byte"
10083 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_2_BYTE)]
10084 ""
10085 "nopr\t%%r7"
10086 [(set_attr "op_type" "RR")])
10087
10088 (define_insn "nop_4_byte"
10089 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_4_BYTE)]
10090 ""
10091 "nop\t0"
10092 [(set_attr "op_type" "RX")])
10093
10094 (define_insn "nop_6_byte"
10095 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_6_BYTE)]
10096 "TARGET_CPU_ZARCH"
10097 "brcl\t0, 0"
10098 [(set_attr "op_type" "RIL")])
10099
10100
10101 ;
10102 ; Special literal pool access instruction pattern(s).
10103 ;
10104
10105 (define_insn "*pool_entry"
10106 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
10107 UNSPECV_POOL_ENTRY)]
10108 ""
10109 {
10110 machine_mode mode = GET_MODE (PATTERN (insn));
10111 unsigned int align = GET_MODE_BITSIZE (mode);
10112 s390_output_pool_entry (operands[0], mode, align);
10113 return "";
10114 }
10115 [(set (attr "length")
10116 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
10117
10118 (define_insn "pool_align"
10119 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
10120 UNSPECV_POOL_ALIGN)]
10121 ""
10122 ".align\t%0"
10123 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10124
10125 (define_insn "pool_section_start"
10126 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
10127 ""
10128 ".section\t.rodata"
10129 [(set_attr "length" "0")])
10130
10131 (define_insn "pool_section_end"
10132 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
10133 ""
10134 ".previous"
10135 [(set_attr "length" "0")])
10136
10137 (define_insn "main_base_31_small"
10138 [(set (match_operand 0 "register_operand" "=a")
10139 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10140 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10141 "basr\t%0,0"
10142 [(set_attr "op_type" "RR")
10143 (set_attr "type" "la")
10144 (set_attr "z196prop" "z196_cracked")])
10145
10146 (define_insn "main_base_31_large"
10147 [(set (match_operand 0 "register_operand" "=a")
10148 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
10149 (set (pc) (label_ref (match_operand 2 "" "")))]
10150 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10151 "bras\t%0,%2"
10152 [(set_attr "op_type" "RI")
10153 (set_attr "z196prop" "z196_cracked")])
10154
10155 (define_insn "main_base_64"
10156 [(set (match_operand 0 "register_operand" "=a")
10157 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10158 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10159 "larl\t%0,%1"
10160 [(set_attr "op_type" "RIL")
10161 (set_attr "type" "larl")
10162 (set_attr "z10prop" "z10_fwd_A1")])
10163
10164 (define_insn "main_pool"
10165 [(set (match_operand 0 "register_operand" "=a")
10166 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
10167 "GET_MODE (operands[0]) == Pmode"
10168 {
10169 gcc_unreachable ();
10170 }
10171 [(set (attr "type")
10172 (if_then_else (match_test "TARGET_CPU_ZARCH")
10173 (const_string "larl") (const_string "la")))])
10174
10175 (define_insn "reload_base_31"
10176 [(set (match_operand 0 "register_operand" "=a")
10177 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10178 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10179 "basr\t%0,0\;la\t%0,%1-.(%0)"
10180 [(set_attr "length" "6")
10181 (set_attr "type" "la")
10182 (set_attr "z196prop" "z196_cracked")])
10183
10184 (define_insn "reload_base_64"
10185 [(set (match_operand 0 "register_operand" "=a")
10186 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10187 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10188 "larl\t%0,%1"
10189 [(set_attr "op_type" "RIL")
10190 (set_attr "type" "larl")
10191 (set_attr "z10prop" "z10_fwd_A1")])
10192
10193 (define_insn "pool"
10194 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
10195 ""
10196 {
10197 gcc_unreachable ();
10198 }
10199 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10200
10201 ;;
10202 ;; Insns related to generating the function prologue and epilogue.
10203 ;;
10204
10205
10206 (define_expand "prologue"
10207 [(use (const_int 0))]
10208 ""
10209 "s390_emit_prologue (); DONE;")
10210
10211 (define_expand "epilogue"
10212 [(use (const_int 1))]
10213 ""
10214 "s390_emit_epilogue (false); DONE;")
10215
10216 (define_expand "sibcall_epilogue"
10217 [(use (const_int 0))]
10218 ""
10219 "s390_emit_epilogue (true); DONE;")
10220
10221 ;; A direct return instruction, without using an epilogue.
10222 (define_insn "<code>"
10223 [(ANY_RETURN)]
10224 "s390_can_use_<code>_insn ()"
10225 "br\t%%r14"
10226 [(set_attr "op_type" "RR")
10227 (set_attr "type" "jsr")
10228 (set_attr "atype" "agen")])
10229
10230 (define_insn "*return"
10231 [(return)
10232 (use (match_operand 0 "register_operand" "a"))]
10233 "GET_MODE (operands[0]) == Pmode"
10234 "br\t%0"
10235 [(set_attr "op_type" "RR")
10236 (set_attr "type" "jsr")
10237 (set_attr "atype" "agen")])
10238
10239
10240 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
10241 ;; pointer. This is used for compatibility.
10242
10243 (define_expand "ptr_extend"
10244 [(set (match_operand:DI 0 "register_operand" "=r")
10245 (match_operand:SI 1 "register_operand" "r"))]
10246 "TARGET_64BIT"
10247 {
10248 emit_insn (gen_anddi3 (operands[0],
10249 gen_lowpart (DImode, operands[1]),
10250 GEN_INT (0x7fffffff)));
10251 DONE;
10252 })
10253
10254 ;; Instruction definition to expand eh_return macro to support
10255 ;; swapping in special linkage return addresses.
10256
10257 (define_expand "eh_return"
10258 [(use (match_operand 0 "register_operand" ""))]
10259 "TARGET_TPF"
10260 {
10261 s390_emit_tpf_eh_return (operands[0]);
10262 DONE;
10263 })
10264
10265 ;
10266 ; Stack Protector Patterns
10267 ;
10268
10269 (define_expand "stack_protect_set"
10270 [(set (match_operand 0 "memory_operand" "")
10271 (match_operand 1 "memory_operand" ""))]
10272 ""
10273 {
10274 #ifdef TARGET_THREAD_SSP_OFFSET
10275 operands[1]
10276 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10277 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10278 #endif
10279 if (TARGET_64BIT)
10280 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
10281 else
10282 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
10283
10284 DONE;
10285 })
10286
10287 (define_insn "stack_protect_set<mode>"
10288 [(set (match_operand:DSI 0 "memory_operand" "=Q")
10289 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
10290 ""
10291 "mvc\t%O0(%G0,%R0),%S1"
10292 [(set_attr "op_type" "SS")])
10293
10294 (define_expand "stack_protect_test"
10295 [(set (reg:CC CC_REGNUM)
10296 (compare (match_operand 0 "memory_operand" "")
10297 (match_operand 1 "memory_operand" "")))
10298 (match_operand 2 "" "")]
10299 ""
10300 {
10301 rtx cc_reg, test;
10302 #ifdef TARGET_THREAD_SSP_OFFSET
10303 operands[1]
10304 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10305 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10306 #endif
10307 if (TARGET_64BIT)
10308 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
10309 else
10310 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
10311
10312 cc_reg = gen_rtx_REG (CCZmode, CC_REGNUM);
10313 test = gen_rtx_EQ (VOIDmode, cc_reg, const0_rtx);
10314 emit_jump_insn (gen_cbranchcc4 (test, cc_reg, const0_rtx, operands[2]));
10315 DONE;
10316 })
10317
10318 (define_insn "stack_protect_test<mode>"
10319 [(set (reg:CCZ CC_REGNUM)
10320 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
10321 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
10322 ""
10323 "clc\t%O0(%G0,%R0),%S1"
10324 [(set_attr "op_type" "SS")])
10325
10326 ; This is used in s390_emit_prologue in order to prevent insns
10327 ; adjusting the stack pointer to be moved over insns writing stack
10328 ; slots using a copy of the stack pointer in a different register.
10329 (define_insn "stack_tie"
10330 [(set (match_operand:BLK 0 "memory_operand" "+m")
10331 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
10332 ""
10333 ""
10334 [(set_attr "length" "0")])
10335
10336
10337 ;
10338 ; Data prefetch patterns
10339 ;
10340
10341 (define_insn "prefetch"
10342 [(prefetch (match_operand 0 "address_operand" "ZQZRZSZT,X")
10343 (match_operand:SI 1 "const_int_operand" " n,n")
10344 (match_operand:SI 2 "const_int_operand" " n,n"))]
10345 "TARGET_Z10"
10346 {
10347 switch (which_alternative)
10348 {
10349 case 0:
10350 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
10351 case 1:
10352 if (larl_operand (operands[0], Pmode))
10353 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
10354 default:
10355
10356 /* This might be reached for symbolic operands with an odd
10357 addend. We simply omit the prefetch for such rare cases. */
10358
10359 return "";
10360 }
10361 }
10362 [(set_attr "type" "load,larl")
10363 (set_attr "op_type" "RXY,RIL")
10364 (set_attr "z10prop" "z10_super")
10365 (set_attr "z196prop" "z196_alone")])
10366
10367
10368 ;
10369 ; Byte swap instructions
10370 ;
10371
10372 (define_insn "bswap<mode>2"
10373 [(set (match_operand:GPR 0 "register_operand" "=d, d")
10374 (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,RT")))]
10375 "TARGET_CPU_ZARCH"
10376 "@
10377 lrv<g>r\t%0,%1
10378 lrv<g>\t%0,%1"
10379 [(set_attr "type" "*,load")
10380 (set_attr "op_type" "RRE,RXY")
10381 (set_attr "z10prop" "z10_super")])
10382
10383
10384 ;
10385 ; Population count instruction
10386 ;
10387
10388 ; The S/390 popcount instruction counts the bits of op1 in 8 byte
10389 ; portions and stores the result in the corresponding bytes in op0.
10390 (define_insn "*popcount<mode>"
10391 [(set (match_operand:INT 0 "register_operand" "=d")
10392 (unspec:INT [(match_operand:INT 1 "register_operand" "d")] UNSPEC_POPCNT))
10393 (clobber (reg:CC CC_REGNUM))]
10394 "TARGET_Z196"
10395 "popcnt\t%0,%1"
10396 [(set_attr "op_type" "RRE")])
10397
10398 (define_expand "popcountdi2"
10399 [; popcnt op0, op1
10400 (parallel [(set (match_operand:DI 0 "register_operand" "")
10401 (unspec:DI [(match_operand:DI 1 "register_operand")]
10402 UNSPEC_POPCNT))
10403 (clobber (reg:CC CC_REGNUM))])
10404 ; sllg op2, op0, 32
10405 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 32)))
10406 ; agr op0, op2
10407 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10408 (clobber (reg:CC CC_REGNUM))])
10409 ; sllg op2, op0, 16
10410 (set (match_dup 2)
10411 (ashift:DI (match_dup 0) (const_int 16)))
10412 ; agr op0, op2
10413 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10414 (clobber (reg:CC CC_REGNUM))])
10415 ; sllg op2, op0, 8
10416 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 8)))
10417 ; agr op0, op2
10418 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10419 (clobber (reg:CC CC_REGNUM))])
10420 ; srlg op0, op0, 56
10421 (set (match_dup 0) (lshiftrt:DI (match_dup 0) (const_int 56)))]
10422 "TARGET_Z196 && TARGET_64BIT"
10423 "operands[2] = gen_reg_rtx (DImode);")
10424
10425 (define_expand "popcountsi2"
10426 [; popcnt op0, op1
10427 (parallel [(set (match_operand:SI 0 "register_operand" "")
10428 (unspec:SI [(match_operand:SI 1 "register_operand")]
10429 UNSPEC_POPCNT))
10430 (clobber (reg:CC CC_REGNUM))])
10431 ; sllk op2, op0, 16
10432 (set (match_dup 2)
10433 (ashift:SI (match_dup 0) (const_int 16)))
10434 ; ar op0, op2
10435 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10436 (clobber (reg:CC CC_REGNUM))])
10437 ; sllk op2, op0, 8
10438 (set (match_dup 2) (ashift:SI (match_dup 0) (const_int 8)))
10439 ; ar op0, op2
10440 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10441 (clobber (reg:CC CC_REGNUM))])
10442 ; srl op0, op0, 24
10443 (set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 24)))]
10444 "TARGET_Z196"
10445 "operands[2] = gen_reg_rtx (SImode);")
10446
10447 (define_expand "popcounthi2"
10448 [; popcnt op0, op1
10449 (parallel [(set (match_operand:HI 0 "register_operand" "")
10450 (unspec:HI [(match_operand:HI 1 "register_operand")]
10451 UNSPEC_POPCNT))
10452 (clobber (reg:CC CC_REGNUM))])
10453 ; sllk op2, op0, 8
10454 (set (match_dup 2)
10455 (ashift:SI (match_dup 0) (const_int 8)))
10456 ; ar op0, op2
10457 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10458 (clobber (reg:CC CC_REGNUM))])
10459 ; srl op0, op0, 8
10460 (set (match_dup 0) (lshiftrt:HI (match_dup 0) (const_int 8)))]
10461 "TARGET_Z196"
10462 "operands[2] = gen_reg_rtx (SImode);")
10463
10464 (define_expand "popcountqi2"
10465 [; popcnt op0, op1
10466 (parallel [(set (match_operand:QI 0 "register_operand" "")
10467 (unspec:QI [(match_operand:QI 1 "register_operand")]
10468 UNSPEC_POPCNT))
10469 (clobber (reg:CC CC_REGNUM))])]
10470 "TARGET_Z196"
10471 "")
10472
10473 ;;
10474 ;;- Copy sign instructions
10475 ;;
10476
10477 (define_insn "copysign<mode>3"
10478 [(set (match_operand:FP 0 "register_operand" "=f")
10479 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
10480 (match_operand:FP 2 "register_operand" "f")]
10481 UNSPEC_COPYSIGN))]
10482 "TARGET_Z196"
10483 "cpsdr\t%0,%2,%1"
10484 [(set_attr "op_type" "RRF")
10485 (set_attr "type" "fsimp<mode>")])
10486
10487
10488 ;;
10489 ;;- Transactional execution instructions
10490 ;;
10491
10492 ; This splitter helps combine to make use of CC directly when
10493 ; comparing the integer result of a tbegin builtin with a constant.
10494 ; The unspec is already removed by canonicalize_comparison. So this
10495 ; splitters only job is to turn the PARALLEL into separate insns
10496 ; again. Unfortunately this only works with the very first cc/int
10497 ; compare since combine is not able to deal with data flow across
10498 ; basic block boundaries.
10499
10500 ; It needs to be an insn pattern as well since combine does not apply
10501 ; the splitter directly. Combine would only use it if it actually
10502 ; would reduce the number of instructions.
10503 (define_insn_and_split "*ccraw_to_int"
10504 [(set (pc)
10505 (if_then_else
10506 (match_operator 0 "s390_eqne_operator"
10507 [(reg:CCRAW CC_REGNUM)
10508 (match_operand 1 "const_int_operand" "")])
10509 (label_ref (match_operand 2 "" ""))
10510 (pc)))
10511 (set (match_operand:SI 3 "register_operand" "=d")
10512 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10513 ""
10514 "#"
10515 ""
10516 [(set (match_dup 3)
10517 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))
10518 (set (pc)
10519 (if_then_else (match_op_dup 0 [(reg:CCRAW CC_REGNUM) (match_dup 1)])
10520 (label_ref (match_dup 2))
10521 (pc)))]
10522 "")
10523
10524 ; Non-constrained transaction begin
10525
10526 (define_expand "tbegin"
10527 [(match_operand:SI 0 "register_operand" "")
10528 (match_operand:BLK 1 "memory_operand" "")]
10529 "TARGET_HTM"
10530 {
10531 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, true);
10532 DONE;
10533 })
10534
10535 (define_expand "tbegin_nofloat"
10536 [(match_operand:SI 0 "register_operand" "")
10537 (match_operand:BLK 1 "memory_operand" "")]
10538 "TARGET_HTM"
10539 {
10540 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, false);
10541 DONE;
10542 })
10543
10544 (define_expand "tbegin_retry"
10545 [(match_operand:SI 0 "register_operand" "")
10546 (match_operand:BLK 1 "memory_operand" "")
10547 (match_operand:SI 2 "general_operand" "")]
10548 "TARGET_HTM"
10549 {
10550 s390_expand_tbegin (operands[0], operands[1], operands[2], true);
10551 DONE;
10552 })
10553
10554 (define_expand "tbegin_retry_nofloat"
10555 [(match_operand:SI 0 "register_operand" "")
10556 (match_operand:BLK 1 "memory_operand" "")
10557 (match_operand:SI 2 "general_operand" "")]
10558 "TARGET_HTM"
10559 {
10560 s390_expand_tbegin (operands[0], operands[1], operands[2], false);
10561 DONE;
10562 })
10563
10564 (define_insn "tbegin_1"
10565 [(set (reg:CCRAW CC_REGNUM)
10566 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10567 UNSPECV_TBEGIN))
10568 (set (match_operand:BLK 1 "memory_operand" "=Q")
10569 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10570 (clobber (reg:DF 16))
10571 (clobber (reg:DF 17))
10572 (clobber (reg:DF 18))
10573 (clobber (reg:DF 19))
10574 (clobber (reg:DF 20))
10575 (clobber (reg:DF 21))
10576 (clobber (reg:DF 22))
10577 (clobber (reg:DF 23))
10578 (clobber (reg:DF 24))
10579 (clobber (reg:DF 25))
10580 (clobber (reg:DF 26))
10581 (clobber (reg:DF 27))
10582 (clobber (reg:DF 28))
10583 (clobber (reg:DF 29))
10584 (clobber (reg:DF 30))
10585 (clobber (reg:DF 31))]
10586 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10587 ; not supposed to be used for immediates (see genpreds.c).
10588 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10589 "tbegin\t%1,%x0"
10590 [(set_attr "op_type" "SIL")])
10591
10592 ; Same as above but without the FPR clobbers
10593 (define_insn "tbegin_nofloat_1"
10594 [(set (reg:CCRAW CC_REGNUM)
10595 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10596 UNSPECV_TBEGIN))
10597 (set (match_operand:BLK 1 "memory_operand" "=Q")
10598 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))]
10599 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10600 "tbegin\t%1,%x0"
10601 [(set_attr "op_type" "SIL")])
10602
10603
10604 ; Constrained transaction begin
10605
10606 (define_expand "tbeginc"
10607 [(set (reg:CCRAW CC_REGNUM)
10608 (unspec_volatile:CCRAW [(const_int TBEGINC_MASK)]
10609 UNSPECV_TBEGINC))]
10610 "TARGET_HTM"
10611 "")
10612
10613 (define_insn "*tbeginc_1"
10614 [(set (reg:CCRAW CC_REGNUM)
10615 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" " D")]
10616 UNSPECV_TBEGINC))]
10617 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10618 "tbeginc\t0,%x0"
10619 [(set_attr "op_type" "SIL")])
10620
10621 ; Transaction end
10622
10623 (define_expand "tend"
10624 [(set (reg:CCRAW CC_REGNUM)
10625 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))
10626 (set (match_operand:SI 0 "register_operand" "")
10627 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10628 "TARGET_HTM"
10629 "")
10630
10631 (define_insn "*tend_1"
10632 [(set (reg:CCRAW CC_REGNUM)
10633 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))]
10634 "TARGET_HTM"
10635 "tend"
10636 [(set_attr "op_type" "S")])
10637
10638 ; Transaction abort
10639
10640 (define_expand "tabort"
10641 [(unspec_volatile [(match_operand:SI 0 "shift_count_or_setmem_operand" "")]
10642 UNSPECV_TABORT)]
10643 "TARGET_HTM && operands != NULL"
10644 {
10645 if (CONST_INT_P (operands[0])
10646 && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 255)
10647 {
10648 error ("Invalid transaction abort code: " HOST_WIDE_INT_PRINT_DEC
10649 ". Values in range 0 through 255 are reserved.",
10650 INTVAL (operands[0]));
10651 FAIL;
10652 }
10653 })
10654
10655 (define_insn "*tabort_1"
10656 [(unspec_volatile [(match_operand:SI 0 "shift_count_or_setmem_operand" "Y")]
10657 UNSPECV_TABORT)]
10658 "TARGET_HTM && operands != NULL"
10659 "tabort\t%Y0"
10660 [(set_attr "op_type" "S")])
10661
10662 ; Transaction extract nesting depth
10663
10664 (define_insn "etnd"
10665 [(set (match_operand:SI 0 "register_operand" "=d")
10666 (unspec_volatile:SI [(const_int 0)] UNSPECV_ETND))]
10667 "TARGET_HTM"
10668 "etnd\t%0"
10669 [(set_attr "op_type" "RRE")])
10670
10671 ; Non-transactional store
10672
10673 (define_insn "ntstg"
10674 [(set (match_operand:DI 0 "memory_operand" "=RT")
10675 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "d")]
10676 UNSPECV_NTSTG))]
10677 "TARGET_HTM"
10678 "ntstg\t%1,%0"
10679 [(set_attr "op_type" "RXY")])
10680
10681 ; Transaction perform processor assist
10682
10683 (define_expand "tx_assist"
10684 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")
10685 (reg:SI GPR0_REGNUM)
10686 (const_int 1)]
10687 UNSPECV_PPA)]
10688 "TARGET_HTM"
10689 "")
10690
10691 (define_insn "*ppa"
10692 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")
10693 (match_operand:SI 1 "register_operand" "d")
10694 (match_operand 2 "const_int_operand" "I")]
10695 UNSPECV_PPA)]
10696 "TARGET_HTM && INTVAL (operands[2]) < 16"
10697 "ppa\t%0,%1,%2"
10698 [(set_attr "op_type" "RRF")])
10699
10700
10701 ; Set and get floating point control register
10702
10703 (define_insn "sfpc"
10704 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")]
10705 UNSPECV_SFPC)]
10706 "TARGET_HARD_FLOAT"
10707 "sfpc\t%0")
10708
10709 (define_insn "efpc"
10710 [(set (match_operand:SI 0 "register_operand" "=d")
10711 (unspec_volatile:SI [(const_int 0)] UNSPECV_EFPC))]
10712 "TARGET_HARD_FLOAT"
10713 "efpc\t%0")
10714
10715
10716 ; Load count to block boundary
10717
10718 (define_insn "lcbb"
10719 [(set (match_operand:SI 0 "register_operand" "=d")
10720 (unspec:SI [(match_operand:SI 1 "address_operand" "ZQZR")
10721 (match_operand:SI 2 "immediate_operand" "C")] UNSPEC_LCBB))
10722 (clobber (reg:CC CC_REGNUM))]
10723 "TARGET_Z13"
10724 "lcbb\t%0,%1,%b2"
10725 [(set_attr "op_type" "VRX")])