S/390: Fix matching setmem_long_and*.
[gcc.git] / gcc / config / s390 / s390.md
1 ;;- Machine description for GNU compiler -- S/390 / zSeries version.
2 ;; Copyright (C) 1999-2017 Free Software Foundation, Inc.
3 ;; Contributed by Hartmut Penner (hpenner@de.ibm.com) and
4 ;; Ulrich Weigand (uweigand@de.ibm.com) and
5 ;; Andreas Krebbel (Andreas.Krebbel@de.ibm.com)
6
7 ;; This file is part of GCC.
8
9 ;; GCC is free software; you can redistribute it and/or modify it under
10 ;; the terms of the GNU General Public License as published by the Free
11 ;; Software Foundation; either version 3, or (at your option) any later
12 ;; version.
13
14 ;; GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 ;; WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 ;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 ;; for more details.
18
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GCC; see the file COPYING3. If not see
21 ;; <http://www.gnu.org/licenses/>.
22
23 ;;
24 ;; See constraints.md for a description of constraints specific to s390.
25 ;;
26
27 ;; Special formats used for outputting 390 instructions.
28 ;;
29 ;; %C: print opcode suffix for branch condition.
30 ;; %D: print opcode suffix for inverse branch condition.
31 ;; %J: print tls_load/tls_gdcall/tls_ldcall suffix
32 ;; %G: print the size of the operand in bytes.
33 ;; %O: print only the displacement of a memory reference.
34 ;; %R: print only the base register of a memory reference.
35 ;; %S: print S-type memory reference (base+displacement).
36 ;; %N: print the second word of a DImode operand.
37 ;; %M: print the second word of a TImode operand.
38 ;; %Y: print shift count operand.
39 ;;
40 ;; %b: print integer X as if it's an unsigned byte.
41 ;; %c: print integer X as if it's an signed byte.
42 ;; %x: print integer X as if it's an unsigned halfword.
43 ;; %h: print integer X as if it's a signed halfword.
44 ;; %i: print the first nonzero HImode part of X.
45 ;; %j: print the first HImode part unequal to -1 of X.
46 ;; %k: print the first nonzero SImode part of X.
47 ;; %m: print the first SImode part unequal to -1 of X.
48 ;; %o: print integer X as if it's an unsigned 32bit word.
49 ;;
50 ;; We have a special constraint for pattern matching.
51 ;;
52 ;; s_operand -- Matches a valid S operand in a RS, SI or SS type instruction.
53 ;;
54
55 ;;
56 ;; UNSPEC usage
57 ;;
58
59 (define_c_enum "unspec" [
60 ; Miscellaneous
61 UNSPEC_ROUND
62 UNSPEC_ICM
63 UNSPEC_TIE
64
65 ; Convert CC into a str comparison result and copy it into an
66 ; integer register
67 ; cc0->0, cc1->1, cc2->-1, (cc3->-1)
68 UNSPEC_STRCMPCC_TO_INT
69
70 ; Copy CC as is into the lower 2 bits of an integer register
71 UNSPEC_CC_TO_INT
72
73 ; The right hand side of an setmem
74 UNSPEC_REPLICATE_BYTE
75
76 ; GOT/PLT and lt-relative accesses
77 UNSPEC_LTREL_OFFSET
78 UNSPEC_LTREL_BASE
79 UNSPEC_POOL_OFFSET
80 UNSPEC_GOTENT
81 UNSPEC_GOT
82 UNSPEC_GOTOFF
83 UNSPEC_PLT
84 UNSPEC_PLTOFF
85
86 ; Literal pool
87 UNSPEC_RELOAD_BASE
88 UNSPEC_MAIN_BASE
89 UNSPEC_LTREF
90 UNSPEC_INSN
91 UNSPEC_EXECUTE
92
93 ; Atomic Support
94 UNSPEC_MB
95 UNSPEC_MOVA
96
97 ; TLS relocation specifiers
98 UNSPEC_TLSGD
99 UNSPEC_TLSLDM
100 UNSPEC_NTPOFF
101 UNSPEC_DTPOFF
102 UNSPEC_GOTNTPOFF
103 UNSPEC_INDNTPOFF
104
105 ; TLS support
106 UNSPEC_TLSLDM_NTPOFF
107 UNSPEC_TLS_LOAD
108
109 ; String Functions
110 UNSPEC_SRST
111 UNSPEC_MVST
112
113 ; Stack Smashing Protector
114 UNSPEC_SP_SET
115 UNSPEC_SP_TEST
116
117 ; Split stack support
118 UNSPEC_STACK_CHECK
119
120 ; Test Data Class (TDC)
121 UNSPEC_TDC_INSN
122
123 ; Population Count
124 UNSPEC_POPCNT
125 UNSPEC_COPYSIGN
126
127 ; Load FP Integer
128 UNSPEC_FPINT_FLOOR
129 UNSPEC_FPINT_BTRUNC
130 UNSPEC_FPINT_ROUND
131 UNSPEC_FPINT_CEIL
132 UNSPEC_FPINT_NEARBYINT
133 UNSPEC_FPINT_RINT
134
135 UNSPEC_LCBB
136
137 ; Vector
138 UNSPEC_VEC_SMULT_HI
139 UNSPEC_VEC_UMULT_HI
140 UNSPEC_VEC_SMULT_LO
141 UNSPEC_VEC_SMULT_EVEN
142 UNSPEC_VEC_UMULT_EVEN
143 UNSPEC_VEC_SMULT_ODD
144 UNSPEC_VEC_UMULT_ODD
145
146 UNSPEC_VEC_VMAL
147 UNSPEC_VEC_VMAH
148 UNSPEC_VEC_VMALH
149 UNSPEC_VEC_VMAE
150 UNSPEC_VEC_VMALE
151 UNSPEC_VEC_VMAO
152 UNSPEC_VEC_VMALO
153
154 UNSPEC_VEC_GATHER
155 UNSPEC_VEC_EXTRACT
156 UNSPEC_VEC_INSERT_AND_ZERO
157 UNSPEC_VEC_LOAD_BNDRY
158 UNSPEC_VEC_LOAD_LEN
159 UNSPEC_VEC_MERGEH
160 UNSPEC_VEC_MERGEL
161 UNSPEC_VEC_PACK
162 UNSPEC_VEC_PACK_SATURATE
163 UNSPEC_VEC_PACK_SATURATE_CC
164 UNSPEC_VEC_PACK_SATURATE_GENCC
165 UNSPEC_VEC_PACK_UNSIGNED_SATURATE
166 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC
167 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC
168 UNSPEC_VEC_PERM
169 UNSPEC_VEC_PERMI
170 UNSPEC_VEC_EXTEND
171 UNSPEC_VEC_STORE_LEN
172 UNSPEC_VEC_UNPACKH
173 UNSPEC_VEC_UNPACKH_L
174 UNSPEC_VEC_UNPACKL
175 UNSPEC_VEC_UNPACKL_L
176 UNSPEC_VEC_ADDC
177 UNSPEC_VEC_ADDE_U128
178 UNSPEC_VEC_ADDEC_U128
179 UNSPEC_VEC_AVG
180 UNSPEC_VEC_AVGU
181 UNSPEC_VEC_CHECKSUM
182 UNSPEC_VEC_GFMSUM
183 UNSPEC_VEC_GFMSUM_128
184 UNSPEC_VEC_GFMSUM_ACCUM
185 UNSPEC_VEC_GFMSUM_ACCUM_128
186 UNSPEC_VEC_SET
187
188 UNSPEC_VEC_VSUMG
189 UNSPEC_VEC_VSUMQ
190 UNSPEC_VEC_VSUM
191 UNSPEC_VEC_RL_MASK
192 UNSPEC_VEC_SLL
193 UNSPEC_VEC_SLB
194 UNSPEC_VEC_SLDB
195 UNSPEC_VEC_SRAL
196 UNSPEC_VEC_SRAB
197 UNSPEC_VEC_SRL
198 UNSPEC_VEC_SRLB
199
200 UNSPEC_VEC_SUBC
201 UNSPEC_VEC_SUBE_U128
202 UNSPEC_VEC_SUBEC_U128
203
204 UNSPEC_VEC_TEST_MASK
205
206 UNSPEC_VEC_VFAE
207 UNSPEC_VEC_VFAECC
208
209 UNSPEC_VEC_VFEE
210 UNSPEC_VEC_VFEECC
211 UNSPEC_VEC_VFENE
212 UNSPEC_VEC_VFENECC
213
214 UNSPEC_VEC_VISTR
215 UNSPEC_VEC_VISTRCC
216
217 UNSPEC_VEC_VSTRC
218 UNSPEC_VEC_VSTRCCC
219
220 UNSPEC_VEC_VCDGB
221 UNSPEC_VEC_VCDLGB
222
223 UNSPEC_VEC_VCGDB
224 UNSPEC_VEC_VCLGDB
225
226 UNSPEC_VEC_VFIDB
227
228 UNSPEC_VEC_VLDEB
229 UNSPEC_VEC_VLEDB
230
231 UNSPEC_VEC_VFTCIDB
232 UNSPEC_VEC_VFTCIDBCC
233 ])
234
235 ;;
236 ;; UNSPEC_VOLATILE usage
237 ;;
238
239 (define_c_enum "unspecv" [
240 ; Blockage
241 UNSPECV_BLOCKAGE
242
243 ; TPF Support
244 UNSPECV_TPF_PROLOGUE
245 UNSPECV_TPF_EPILOGUE
246
247 ; Literal pool
248 UNSPECV_POOL
249 UNSPECV_POOL_SECTION
250 UNSPECV_POOL_ALIGN
251 UNSPECV_POOL_ENTRY
252 UNSPECV_MAIN_POOL
253
254 ; TLS support
255 UNSPECV_SET_TP
256
257 ; Atomic Support
258 UNSPECV_CAS
259 UNSPECV_ATOMIC_OP
260
261 ; Hotpatching (unremovable NOPs)
262 UNSPECV_NOP_2_BYTE
263 UNSPECV_NOP_4_BYTE
264 UNSPECV_NOP_6_BYTE
265
266 ; Transactional Execution support
267 UNSPECV_TBEGIN
268 UNSPECV_TBEGIN_TDB
269 UNSPECV_TBEGINC
270 UNSPECV_TEND
271 UNSPECV_TABORT
272 UNSPECV_ETND
273 UNSPECV_NTSTG
274 UNSPECV_PPA
275
276 ; Set and get floating point control register
277 UNSPECV_SFPC
278 UNSPECV_EFPC
279
280 ; Split stack support
281 UNSPECV_SPLIT_STACK_CALL
282 UNSPECV_SPLIT_STACK_DATA
283
284 UNSPECV_OSC_BREAK
285 ])
286
287 ;;
288 ;; Registers
289 ;;
290
291 ; Registers with special meaning
292
293 (define_constants
294 [
295 ; Sibling call register.
296 (SIBCALL_REGNUM 1)
297 ; Literal pool base register.
298 (BASE_REGNUM 13)
299 ; Return address register.
300 (RETURN_REGNUM 14)
301 ; Stack pointer register.
302 (STACK_REGNUM 15)
303 ; Condition code register.
304 (CC_REGNUM 33)
305 ; Thread local storage pointer register.
306 (TP_REGNUM 36)
307 ])
308
309 ; Hardware register names
310
311 (define_constants
312 [
313 ; General purpose registers
314 (GPR0_REGNUM 0)
315 (GPR1_REGNUM 1)
316 (GPR2_REGNUM 2)
317 (GPR6_REGNUM 6)
318 ; Floating point registers.
319 (FPR0_REGNUM 16)
320 (FPR1_REGNUM 20)
321 (FPR2_REGNUM 17)
322 (FPR3_REGNUM 21)
323 (FPR4_REGNUM 18)
324 (FPR5_REGNUM 22)
325 (FPR6_REGNUM 19)
326 (FPR7_REGNUM 23)
327 (FPR8_REGNUM 24)
328 (FPR9_REGNUM 28)
329 (FPR10_REGNUM 25)
330 (FPR11_REGNUM 29)
331 (FPR12_REGNUM 26)
332 (FPR13_REGNUM 30)
333 (FPR14_REGNUM 27)
334 (FPR15_REGNUM 31)
335 (VR0_REGNUM 16)
336 (VR16_REGNUM 38)
337 (VR23_REGNUM 45)
338 (VR24_REGNUM 46)
339 (VR31_REGNUM 53)
340 ])
341
342 ; Rounding modes for binary floating point numbers
343 (define_constants
344 [(BFP_RND_CURRENT 0)
345 (BFP_RND_NEAREST_TIE_AWAY_FROM_0 1)
346 (BFP_RND_PREP_FOR_SHORT_PREC 3)
347 (BFP_RND_NEAREST_TIE_TO_EVEN 4)
348 (BFP_RND_TOWARD_0 5)
349 (BFP_RND_TOWARD_INF 6)
350 (BFP_RND_TOWARD_MINF 7)])
351
352 ; Rounding modes for decimal floating point numbers
353 ; 1-7 were introduced with the floating point extension facility
354 ; available with z196
355 ; With these rounding modes (1-7) a quantum exception might occur
356 ; which is suppressed for the other modes.
357 (define_constants
358 [(DFP_RND_CURRENT 0)
359 (DFP_RND_NEAREST_TIE_AWAY_FROM_0_QUANTEXC 1)
360 (DFP_RND_CURRENT_QUANTEXC 2)
361 (DFP_RND_PREP_FOR_SHORT_PREC_QUANTEXC 3)
362 (DFP_RND_NEAREST_TIE_TO_EVEN_QUANTEXC 4)
363 (DFP_RND_TOWARD_0_QUANTEXC 5)
364 (DFP_RND_TOWARD_INF_QUANTEXC 6)
365 (DFP_RND_TOWARD_MINF_QUANTEXC 7)
366 (DFP_RND_NEAREST_TIE_TO_EVEN 8)
367 (DFP_RND_TOWARD_0 9)
368 (DFP_RND_TOWARD_INF 10)
369 (DFP_RND_TOWARD_MINF 11)
370 (DFP_RND_NEAREST_TIE_AWAY_FROM_0 12)
371 (DFP_RND_NEAREST_TIE_TO_0 13)
372 (DFP_RND_AWAY_FROM_0 14)
373 (DFP_RND_PREP_FOR_SHORT_PREC 15)])
374
375 ;;
376 ;; PFPO GPR0 argument format
377 ;;
378
379 (define_constants
380 [
381 ; PFPO operation type
382 (PFPO_CONVERT 0x1000000)
383 ; PFPO operand types
384 (PFPO_OP_TYPE_SF 0x5)
385 (PFPO_OP_TYPE_DF 0x6)
386 (PFPO_OP_TYPE_TF 0x7)
387 (PFPO_OP_TYPE_SD 0x8)
388 (PFPO_OP_TYPE_DD 0x9)
389 (PFPO_OP_TYPE_TD 0xa)
390 ; Bitposition of operand types
391 (PFPO_OP0_TYPE_SHIFT 16)
392 (PFPO_OP1_TYPE_SHIFT 8)
393 ])
394
395 ; Immediate operands for tbegin and tbeginc
396 (define_constants [(TBEGIN_MASK 65292)]) ; 0xff0c
397 (define_constants [(TBEGINC_MASK 65288)]) ; 0xff08
398
399 ;; Instruction operand type as used in the Principles of Operation.
400 ;; Used to determine defaults for length and other attribute values.
401
402 (define_attr "op_type"
403 "NN,E,RR,RRE,RX,RS,RSI,RI,SI,S,SS,SSE,RXE,RSE,RIL,RIE,RXY,RSY,SIY,RRF,SIL,RRS,RIS,VRI,VRR,VRS,VRV,VRX"
404 (const_string "NN"))
405
406 ;; Instruction type attribute used for scheduling.
407
408 (define_attr "type" "none,integer,load,lr,la,larl,lm,stm,
409 cs,vs,store,sem,idiv,
410 imulhi,imulsi,imuldi,
411 branch,jsr,fsimptf,fsimpdf,fsimpsf,fhex,
412 floadtf,floaddf,floadsf,fstoredf,fstoresf,
413 fmultf,fmuldf,fmulsf,fdivtf,fdivdf,fdivsf,
414 ftoi,fsqrttf,fsqrtdf,fsqrtsf,
415 fmadddf,fmaddsf,
416 ftrunctf,ftruncdf, ftruncsd, ftruncdd,
417 itoftf, itofdf, itofsf, itofdd, itoftd,
418 fdivdd, fdivtd, floaddd, floadsd, fmuldd, fmultd,
419 fsimpdd, fsimpsd, fsimptd, fstoredd, fstoresd,
420 ftoidfp, other"
421 (cond [(eq_attr "op_type" "NN") (const_string "other")
422 (eq_attr "op_type" "SS") (const_string "cs")]
423 (const_string "integer")))
424
425 ;; Another attribute used for scheduling purposes:
426 ;; agen: Instruction uses the address generation unit
427 ;; reg: Instruction does not use the agen unit
428
429 (define_attr "atype" "agen,reg"
430 (if_then_else (eq_attr "op_type" "E,RR,RI,RRE,RSI,RIL,RIE,RRF")
431 (const_string "reg")
432 (const_string "agen")))
433
434 ;; Properties concerning Z10 execution grouping and value forwarding.
435 ;; z10_super: instruction is superscalar.
436 ;; z10_super_c: instruction is superscalar and meets the condition of z10_c.
437 ;; z10_fwd: The instruction reads the value of an operand and stores it into a
438 ;; target register. It can forward this value to a second instruction that reads
439 ;; the same register if that second instruction is issued in the same group.
440 ;; z10_rec: The instruction is in the T pipeline and reads a register. If the
441 ;; instruction in the S pipe writes to the register, then the T instruction
442 ;; can immediately read the new value.
443 ;; z10_fr: union of Z10_fwd and z10_rec.
444 ;; z10_c: second operand of instruction is a register and read with complemented bits.
445 ;;
446 ;; An additional suffix A1, A3, or E1 indicates the respective AGI bypass.
447
448
449 (define_attr "z10prop" "none,
450 z10_super, z10_super_E1, z10_super_A1, z10_super_c, z10_super_c_E1,
451 z10_fwd, z10_fwd_A1, z10_fwd_A3, z10_fwd_E1,
452 z10_rec,
453 z10_fr, z10_fr_A3, z10_fr_E1,
454 z10_c"
455 (const_string "none"))
456
457 ;; Properties concerning Z196 decoding
458 ;; z196_alone: must group alone
459 ;; z196_end: ends a group
460 ;; z196_cracked: instruction is cracked or expanded
461 (define_attr "z196prop" "none,
462 z196_alone, z196_ends,
463 z196_cracked"
464 (const_string "none"))
465
466 (define_attr "mnemonic" "bcr_flush,unknown" (const_string "unknown"))
467
468 ;; Length in bytes.
469
470 (define_attr "length" ""
471 (cond [(eq_attr "op_type" "E,RR") (const_int 2)
472 (eq_attr "op_type" "RX,RI,RRE,RS,RSI,S,SI,RRF") (const_int 4)]
473 (const_int 6)))
474
475
476 ;; Processor type. This attribute must exactly match the processor_type
477 ;; enumeration in s390.h. The current machine description does not
478 ;; distinguish between g5 and g6, but there are differences between the two
479 ;; CPUs could in theory be modeled.
480
481 (define_attr "cpu" "g5,g6,z900,z990,z9_109,z9_ec,z10,z196,zEC12,z13"
482 (const (symbol_ref "s390_tune_attr")))
483
484 (define_attr "cpu_facility"
485 "standard,ieee,zarch,cpu_zarch,longdisp,extimm,dfp,z10,z196,zEC12,vec,z13"
486 (const_string "standard"))
487
488 (define_attr "enabled" ""
489 (cond [(eq_attr "cpu_facility" "standard")
490 (const_int 1)
491
492 (and (eq_attr "cpu_facility" "ieee")
493 (match_test "TARGET_CPU_IEEE_FLOAT"))
494 (const_int 1)
495
496 (and (eq_attr "cpu_facility" "zarch")
497 (match_test "TARGET_ZARCH"))
498 (const_int 1)
499
500 (and (eq_attr "cpu_facility" "longdisp")
501 (match_test "TARGET_LONG_DISPLACEMENT"))
502 (const_int 1)
503
504 (and (eq_attr "cpu_facility" "extimm")
505 (match_test "TARGET_EXTIMM"))
506 (const_int 1)
507
508 (and (eq_attr "cpu_facility" "dfp")
509 (match_test "TARGET_DFP"))
510 (const_int 1)
511
512 (and (eq_attr "cpu_facility" "cpu_zarch")
513 (match_test "TARGET_CPU_ZARCH"))
514 (const_int 1)
515
516 (and (eq_attr "cpu_facility" "z10")
517 (match_test "TARGET_Z10"))
518 (const_int 1)
519
520 (and (eq_attr "cpu_facility" "z196")
521 (match_test "TARGET_Z196"))
522 (const_int 1)
523
524 (and (eq_attr "cpu_facility" "zEC12")
525 (match_test "TARGET_ZEC12"))
526 (const_int 1)
527
528 (and (eq_attr "cpu_facility" "vec")
529 (match_test "TARGET_VX"))
530 (const_int 1)
531
532 (and (eq_attr "cpu_facility" "z13")
533 (match_test "TARGET_Z13"))
534 (const_int 1)
535 ]
536 (const_int 0)))
537
538 ;; Pipeline description for z900. For lack of anything better,
539 ;; this description is also used for the g5 and g6.
540 (include "2064.md")
541
542 ;; Pipeline description for z990, z9-109 and z9-ec.
543 (include "2084.md")
544
545 ;; Pipeline description for z10
546 (include "2097.md")
547
548 ;; Pipeline description for z196
549 (include "2817.md")
550
551 ;; Pipeline description for zEC12
552 (include "2827.md")
553
554 ;; Pipeline description for z13
555 (include "2964.md")
556
557 ;; Predicates
558 (include "predicates.md")
559
560 ;; Constraint definitions
561 (include "constraints.md")
562
563 ;; Other includes
564 (include "tpf.md")
565
566 ;; Iterators
567
568 (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])
569
570 ;; These mode iterators allow floating point patterns to be generated from the
571 ;; same template.
572 (define_mode_iterator FP_ALL [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")
573 (SD "TARGET_HARD_DFP")])
574 (define_mode_iterator FP [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")])
575 (define_mode_iterator BFP [TF DF SF])
576 (define_mode_iterator DFP [TD DD])
577 (define_mode_iterator DFP_ALL [TD DD SD])
578 (define_mode_iterator DSF [DF SF])
579 (define_mode_iterator SD_SF [SF SD])
580 (define_mode_iterator DD_DF [DF DD])
581 (define_mode_iterator TD_TF [TF TD])
582
583 ;; These mode iterators allow 31-bit and 64-bit GPR patterns to be generated
584 ;; from the same template.
585 (define_mode_iterator GPR [(DI "TARGET_ZARCH") SI])
586 (define_mode_iterator DGPR [(TI "TARGET_ZARCH") DI SI])
587 (define_mode_iterator DSI [DI SI])
588 (define_mode_iterator TDI [TI DI])
589
590 ;; These mode iterators allow :P to be used for patterns that operate on
591 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
592 (define_mode_iterator P [(DI "TARGET_64BIT") (SI "!TARGET_64BIT")])
593
594 ;; These macros refer to the actual word_mode of the configuration.
595 ;; This is equal to Pmode except on 31-bit machines in zarch mode.
596 (define_mode_iterator DW [(TI "TARGET_ZARCH") (DI "!TARGET_ZARCH")])
597 (define_mode_iterator W [(DI "TARGET_ZARCH") (SI "!TARGET_ZARCH")])
598
599 ;; Used by the umul pattern to express modes having half the size.
600 (define_mode_attr DWH [(TI "DI") (DI "SI")])
601 (define_mode_attr dwh [(TI "di") (DI "si")])
602
603 ;; This mode iterator allows the QI and HI patterns to be defined from
604 ;; the same template.
605 (define_mode_iterator HQI [HI QI])
606
607 ;; This mode iterator allows the integer patterns to be defined from the
608 ;; same template.
609 (define_mode_iterator INT [(DI "TARGET_ZARCH") SI HI QI])
610 (define_mode_iterator DINT [(TI "TARGET_ZARCH") DI SI HI QI])
611 (define_mode_iterator SINT [SI HI QI])
612
613 ;; This iterator allows some 'ashift' and 'lshiftrt' pattern to be defined from
614 ;; the same template.
615 (define_code_iterator SHIFT [ashift lshiftrt])
616
617 ;; This iterator allows r[ox]sbg to be defined with the same template
618 (define_code_iterator IXOR [ior xor])
619
620 ;; This iterator is used to expand the patterns for the nearest
621 ;; integer functions.
622 (define_int_iterator FPINT [UNSPEC_FPINT_FLOOR UNSPEC_FPINT_BTRUNC
623 UNSPEC_FPINT_ROUND UNSPEC_FPINT_CEIL
624 UNSPEC_FPINT_NEARBYINT])
625 (define_int_attr fpint_name [(UNSPEC_FPINT_FLOOR "floor")
626 (UNSPEC_FPINT_BTRUNC "btrunc")
627 (UNSPEC_FPINT_ROUND "round")
628 (UNSPEC_FPINT_CEIL "ceil")
629 (UNSPEC_FPINT_NEARBYINT "nearbyint")])
630 (define_int_attr fpint_roundingmode [(UNSPEC_FPINT_FLOOR "7")
631 (UNSPEC_FPINT_BTRUNC "5")
632 (UNSPEC_FPINT_ROUND "1")
633 (UNSPEC_FPINT_CEIL "6")
634 (UNSPEC_FPINT_NEARBYINT "0")])
635
636 ;; This iterator and attribute allow to combine most atomic operations.
637 (define_code_iterator ATOMIC [and ior xor plus minus mult])
638 (define_code_iterator ATOMIC_Z196 [and ior xor plus])
639 (define_code_attr atomic [(and "and") (ior "or") (xor "xor")
640 (plus "add") (minus "sub") (mult "nand")])
641 (define_code_attr noxa [(and "n") (ior "o") (xor "x") (plus "a")])
642
643 ;; In FP templates, a string like "lt<de>br" will expand to "ltxbr" in
644 ;; TF/TDmode, "ltdbr" in DF/DDmode, and "ltebr" in SF/SDmode.
645 (define_mode_attr xde [(TF "x") (DF "d") (SF "e") (TD "x") (DD "d") (SD "e")])
646
647 ;; In FP templates, a <dee> in "m<dee><bt>r" will expand to "mx<bt>r" in
648 ;; TF/TDmode, "md<bt>r" in DF/DDmode, "mee<bt>r" in SFmode and "me<bt>r in
649 ;; SDmode.
650 (define_mode_attr xdee [(TF "x") (DF "d") (SF "ee") (TD "x") (DD "d") (SD "e")])
651
652 ;; In FP templates, "<RRe>" will expand to "RRE" in TFmode and "RR" otherwise.
653 ;; Likewise for "<RXe>".
654 (define_mode_attr RRe [(TF "RRE") (DF "RR") (SF "RR")])
655 (define_mode_attr RXe [(TF "RXE") (DF "RX") (SF "RX")])
656
657 ;; The decimal floating point variants of add, sub, div and mul support 3
658 ;; fp register operands. The following attributes allow to merge the bfp and
659 ;; dfp variants in a single insn definition.
660
661 ;; These mode attributes are supposed to be used in the `enabled' insn
662 ;; attribute to disable certain alternatives for certain modes.
663 (define_mode_attr nBFP [(TF "0") (DF "0") (SF "0") (TD "*") (DD "*") (DD "*")])
664 (define_mode_attr nDFP [(TF "*") (DF "*") (SF "*") (TD "0") (DD "0") (DD "0")])
665 (define_mode_attr DSF [(TF "0") (DF "*") (SF "*") (TD "0") (DD "0") (SD "0")])
666 (define_mode_attr DFDI [(TF "0") (DF "*") (SF "0")
667 (TD "0") (DD "0") (DD "0")
668 (TI "0") (DI "*") (SI "0")])
669
670 ;; This attribute is used in the operand constraint list
671 ;; for instructions dealing with the sign bit of 32 or 64bit fp values.
672 ;; TFmode values are represented by a fp register pair. Since the
673 ;; sign bit instructions only handle single source and target fp registers
674 ;; these instructions can only be used for TFmode values if the source and
675 ;; target operand uses the same fp register.
676 (define_mode_attr fT0 [(TF "0") (DF "f") (SF "f")])
677
678 ;; This attribute adds b for bfp instructions and t for dfp instructions and is used
679 ;; within instruction mnemonics.
680 (define_mode_attr bt [(TF "b") (DF "b") (SF "b") (TD "t") (DD "t") (SD "t")])
681
682 ;; This attribute is used within instruction mnemonics. It evaluates to d for dfp
683 ;; modes and to an empty string for bfp modes.
684 (define_mode_attr _d [(TF "") (DF "") (SF "") (TD "d") (DD "d") (SD "d")])
685
686 ;; In GPR and P templates, a constraint like "<d0>" will expand to "d" in DImode
687 ;; and "0" in SImode. This allows to combine instructions of which the 31bit
688 ;; version only operates on one register.
689 (define_mode_attr d0 [(DI "d") (SI "0")])
690
691 ;; In combination with d0 this allows to combine instructions of which the 31bit
692 ;; version only operates on one register. The DImode version needs an additional
693 ;; register for the assembler output.
694 (define_mode_attr 1 [(DI "%1,") (SI "")])
695
696 ;; In SHIFT templates, a string like "s<lr>dl" will expand to "sldl" in
697 ;; 'ashift' and "srdl" in 'lshiftrt'.
698 (define_code_attr lr [(ashift "l") (lshiftrt "r")])
699
700 ;; In SHIFT templates, this attribute holds the correct standard name for the
701 ;; pattern itself and the corresponding function calls.
702 (define_code_attr shift [(ashift "ashl") (lshiftrt "lshr")])
703
704 ;; This attribute handles differences in the instruction 'type' and will result
705 ;; in "RRE" for DImode and "RR" for SImode.
706 (define_mode_attr E [(DI "E") (SI "")])
707
708 ;; This attribute handles differences in the instruction 'type' and makes RX<Y>
709 ;; to result in "RXY" for DImode and "RX" for SImode.
710 (define_mode_attr Y [(DI "Y") (SI "")])
711
712 ;; This attribute handles differences in the instruction 'type' and will result
713 ;; in "RSE" for TImode and "RS" for DImode.
714 (define_mode_attr TE [(TI "E") (DI "")])
715
716 ;; In GPR templates, a string like "lc<g>r" will expand to "lcgr" in DImode
717 ;; and "lcr" in SImode.
718 (define_mode_attr g [(DI "g") (SI "")])
719
720 ;; In GPR templates, a string like "sl<y>" will expand to "slg" in DImode
721 ;; and "sly" in SImode. This is useful because on 64bit the ..g instructions
722 ;; were enhanced with long displacements whereas 31bit instructions got a ..y
723 ;; variant for long displacements.
724 (define_mode_attr y [(DI "g") (SI "y")])
725
726 ;; In DW templates, a string like "cds<g>" will expand to "cdsg" in TImode
727 ;; and "cds" in DImode.
728 (define_mode_attr tg [(TI "g") (DI "")])
729
730 ;; In TDI templates, a string like "c<d>sg".
731 (define_mode_attr td [(TI "d") (DI "")])
732
733 ;; In GPR templates, a string like "c<gf>dbr" will expand to "cgdbr" in DImode
734 ;; and "cfdbr" in SImode.
735 (define_mode_attr gf [(DI "g") (SI "f")])
736
737 ;; In GPR templates, a string like sll<gk> will expand to sllg for DI
738 ;; and sllk for SI. This way it is possible to merge the new z196 SI
739 ;; 3 operands shift instructions into the existing patterns.
740 (define_mode_attr gk [(DI "g") (SI "k")])
741
742 ;; ICM mask required to load MODE value into the lowest subreg
743 ;; of a SImode register.
744 (define_mode_attr icm_lo [(HI "3") (QI "1")])
745
746 ;; In HQI templates, a string like "llg<hc>" will expand to "llgh" in
747 ;; HImode and "llgc" in QImode.
748 (define_mode_attr hc [(HI "h") (QI "c")])
749
750 ;; In P templates, the mode <DBL> will expand to "TI" in DImode and "DI"
751 ;; in SImode.
752 (define_mode_attr DBL [(DI "TI") (SI "DI")])
753
754 ;; This attribute expands to DF for TFmode and to DD for TDmode . It is
755 ;; used for Txmode splitters splitting a Txmode copy into 2 Dxmode copies.
756 (define_mode_attr HALF_TMODE [(TF "DF") (TD "DD")])
757
758 ;; Maximum unsigned integer that fits in MODE.
759 (define_mode_attr max_uint [(HI "65535") (QI "255")])
760
761 ;; Start and end field computations for RISBG et al.
762 (define_mode_attr bfstart [(DI "s") (SI "t")])
763 (define_mode_attr bfend [(DI "e") (SI "f")])
764
765 ;; In place of GET_MODE_BITSIZE (<MODE>mode)
766 (define_mode_attr bitsize [(DI "64") (SI "32") (HI "16") (QI "8")])
767 ;; 64 - bitsize
768 (define_mode_attr bitoff [(DI "0") (SI "32") (HI "48") (QI "56")])
769 (define_mode_attr bitoff_plus [(DI "") (SI "32+") (HI "48+") (QI "56+")])
770
771 ;; In place of GET_MODE_SIZE (<MODE>mode)
772 (define_mode_attr modesize [(DI "8") (SI "4")])
773
774 ;; Allow return and simple_return to be defined from a single template.
775 (define_code_iterator ANY_RETURN [return simple_return])
776
777
778
779 ; Condition code modes generated by vector fp comparisons. These will
780 ; be used also in single element mode.
781 (define_mode_iterator VFCMP [CCVEQ CCVFH CCVFHE])
782 ; Used with VFCMP to expand part of the mnemonic
783 ; For fp we have a mismatch: eq in the insn name - e in asm
784 (define_mode_attr asm_fcmp [(CCVEQ "e") (CCVFH "h") (CCVFHE "he")])
785 (define_mode_attr insn_cmp [(CCVEQ "eq") (CCVIH "h") (CCVIHU "hl") (CCVFH "h") (CCVFHE "he")])
786
787 ;; Subst pattern definitions
788 (include "subst.md")
789
790 (include "vector.md")
791
792 ;;
793 ;;- Compare instructions.
794 ;;
795
796 ; Test-under-Mask instructions
797
798 (define_insn "*tmqi_mem"
799 [(set (reg CC_REGNUM)
800 (compare (and:QI (match_operand:QI 0 "memory_operand" "Q,S")
801 (match_operand:QI 1 "immediate_operand" "n,n"))
802 (match_operand:QI 2 "immediate_operand" "n,n")))]
803 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], false))"
804 "@
805 tm\t%S0,%b1
806 tmy\t%S0,%b1"
807 [(set_attr "op_type" "SI,SIY")
808 (set_attr "cpu_facility" "*,longdisp")
809 (set_attr "z10prop" "z10_super,z10_super")])
810
811 (define_insn "*tmdi_reg"
812 [(set (reg CC_REGNUM)
813 (compare (and:DI (match_operand:DI 0 "nonimmediate_operand" "d,d,d,d")
814 (match_operand:DI 1 "immediate_operand"
815 "N0HD0,N1HD0,N2HD0,N3HD0"))
816 (match_operand:DI 2 "immediate_operand" "n,n,n,n")))]
817 "TARGET_ZARCH
818 && s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
819 && s390_single_part (operands[1], DImode, HImode, 0) >= 0"
820 "@
821 tmhh\t%0,%i1
822 tmhl\t%0,%i1
823 tmlh\t%0,%i1
824 tmll\t%0,%i1"
825 [(set_attr "op_type" "RI")
826 (set_attr "z10prop" "z10_super,z10_super,z10_super,z10_super")])
827
828 (define_insn "*tmsi_reg"
829 [(set (reg CC_REGNUM)
830 (compare (and:SI (match_operand:SI 0 "nonimmediate_operand" "d,d")
831 (match_operand:SI 1 "immediate_operand" "N0HS0,N1HS0"))
832 (match_operand:SI 2 "immediate_operand" "n,n")))]
833 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
834 && s390_single_part (operands[1], SImode, HImode, 0) >= 0"
835 "@
836 tmh\t%0,%i1
837 tml\t%0,%i1"
838 [(set_attr "op_type" "RI")
839 (set_attr "z10prop" "z10_super,z10_super")])
840
841 (define_insn "*tm<mode>_full"
842 [(set (reg CC_REGNUM)
843 (compare (match_operand:HQI 0 "register_operand" "d")
844 (match_operand:HQI 1 "immediate_operand" "n")))]
845 "s390_match_ccmode (insn, s390_tm_ccmode (constm1_rtx, operands[1], true))"
846 "tml\t%0,<max_uint>"
847 [(set_attr "op_type" "RI")
848 (set_attr "z10prop" "z10_super")])
849
850
851 ;
852 ; Load-and-Test instructions
853 ;
854
855 ; tst(di|si) instruction pattern(s).
856
857 (define_insn "*tstdi_sign"
858 [(set (reg CC_REGNUM)
859 (compare
860 (ashiftrt:DI
861 (ashift:DI
862 (subreg:DI (match_operand:SI 0 "nonimmediate_operand" "d,T") 0)
863 (const_int 32)) (const_int 32))
864 (match_operand:DI 1 "const0_operand" "")))
865 (set (match_operand:DI 2 "register_operand" "=d,d")
866 (sign_extend:DI (match_dup 0)))]
867 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH"
868 "ltgfr\t%2,%0
869 ltgf\t%2,%0"
870 [(set_attr "op_type" "RRE,RXY")
871 (set_attr "cpu_facility" "*,z10")
872 (set_attr "z10prop" "z10_super_E1,z10_super_E1") ])
873
874 ; ltr, lt, ltgr, ltg
875 (define_insn "*tst<mode>_extimm"
876 [(set (reg CC_REGNUM)
877 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,T")
878 (match_operand:GPR 1 "const0_operand" "")))
879 (set (match_operand:GPR 2 "register_operand" "=d,d")
880 (match_dup 0))]
881 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
882 "@
883 lt<g>r\t%2,%0
884 lt<g>\t%2,%0"
885 [(set_attr "op_type" "RR<E>,RXY")
886 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3") ])
887
888 ; ltr, lt, ltgr, ltg
889 (define_insn "*tst<mode>_cconly_extimm"
890 [(set (reg CC_REGNUM)
891 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,T")
892 (match_operand:GPR 1 "const0_operand" "")))
893 (clobber (match_scratch:GPR 2 "=X,d"))]
894 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
895 "@
896 lt<g>r\t%0,%0
897 lt<g>\t%2,%0"
898 [(set_attr "op_type" "RR<E>,RXY")
899 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3")])
900
901 (define_insn "*tstdi"
902 [(set (reg CC_REGNUM)
903 (compare (match_operand:DI 0 "register_operand" "d")
904 (match_operand:DI 1 "const0_operand" "")))
905 (set (match_operand:DI 2 "register_operand" "=d")
906 (match_dup 0))]
907 "s390_match_ccmode(insn, CCSmode) && TARGET_ZARCH && !TARGET_EXTIMM"
908 "ltgr\t%2,%0"
909 [(set_attr "op_type" "RRE")
910 (set_attr "z10prop" "z10_fr_E1")])
911
912 (define_insn "*tstsi"
913 [(set (reg CC_REGNUM)
914 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
915 (match_operand:SI 1 "const0_operand" "")))
916 (set (match_operand:SI 2 "register_operand" "=d,d,d")
917 (match_dup 0))]
918 "s390_match_ccmode(insn, CCSmode) && !TARGET_EXTIMM"
919 "@
920 ltr\t%2,%0
921 icm\t%2,15,%S0
922 icmy\t%2,15,%S0"
923 [(set_attr "op_type" "RR,RS,RSY")
924 (set_attr "cpu_facility" "*,*,longdisp")
925 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
926
927 (define_insn "*tstsi_cconly"
928 [(set (reg CC_REGNUM)
929 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
930 (match_operand:SI 1 "const0_operand" "")))
931 (clobber (match_scratch:SI 2 "=X,d,d"))]
932 "s390_match_ccmode(insn, CCSmode)"
933 "@
934 ltr\t%0,%0
935 icm\t%2,15,%S0
936 icmy\t%2,15,%S0"
937 [(set_attr "op_type" "RR,RS,RSY")
938 (set_attr "cpu_facility" "*,*,longdisp")
939 (set_attr "z10prop" "z10_fr_E1,z10_super_E1,z10_super_E1")])
940
941 (define_insn "*tstdi_cconly_31"
942 [(set (reg CC_REGNUM)
943 (compare (match_operand:DI 0 "register_operand" "d")
944 (match_operand:DI 1 "const0_operand" "")))]
945 "s390_match_ccmode(insn, CCSmode) && !TARGET_ZARCH"
946 "srda\t%0,0"
947 [(set_attr "op_type" "RS")
948 (set_attr "atype" "reg")])
949
950 ; ltr, ltgr
951 (define_insn "*tst<mode>_cconly2"
952 [(set (reg CC_REGNUM)
953 (compare (match_operand:GPR 0 "register_operand" "d")
954 (match_operand:GPR 1 "const0_operand" "")))]
955 "s390_match_ccmode(insn, CCSmode)"
956 "lt<g>r\t%0,%0"
957 [(set_attr "op_type" "RR<E>")
958 (set_attr "z10prop" "z10_fr_E1")])
959
960 ; tst(hi|qi) instruction pattern(s).
961
962 (define_insn "*tst<mode>CCT"
963 [(set (reg CC_REGNUM)
964 (compare (match_operand:HQI 0 "nonimmediate_operand" "?Q,?S,d")
965 (match_operand:HQI 1 "const0_operand" "")))
966 (set (match_operand:HQI 2 "register_operand" "=d,d,0")
967 (match_dup 0))]
968 "s390_match_ccmode(insn, CCTmode)"
969 "@
970 icm\t%2,<icm_lo>,%S0
971 icmy\t%2,<icm_lo>,%S0
972 tml\t%0,<max_uint>"
973 [(set_attr "op_type" "RS,RSY,RI")
974 (set_attr "cpu_facility" "*,longdisp,*")
975 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
976
977 (define_insn "*tsthiCCT_cconly"
978 [(set (reg CC_REGNUM)
979 (compare (match_operand:HI 0 "nonimmediate_operand" "Q,S,d")
980 (match_operand:HI 1 "const0_operand" "")))
981 (clobber (match_scratch:HI 2 "=d,d,X"))]
982 "s390_match_ccmode(insn, CCTmode)"
983 "@
984 icm\t%2,3,%S0
985 icmy\t%2,3,%S0
986 tml\t%0,65535"
987 [(set_attr "op_type" "RS,RSY,RI")
988 (set_attr "cpu_facility" "*,longdisp,*")
989 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super")])
990
991 (define_insn "*tstqiCCT_cconly"
992 [(set (reg CC_REGNUM)
993 (compare (match_operand:QI 0 "nonimmediate_operand" "?Q,?S,d")
994 (match_operand:QI 1 "const0_operand" "")))]
995 "s390_match_ccmode(insn, CCTmode)"
996 "@
997 cli\t%S0,0
998 cliy\t%S0,0
999 tml\t%0,255"
1000 [(set_attr "op_type" "SI,SIY,RI")
1001 (set_attr "cpu_facility" "*,longdisp,*")
1002 (set_attr "z10prop" "z10_super,z10_super,z10_super")])
1003
1004 (define_insn "*tst<mode>"
1005 [(set (reg CC_REGNUM)
1006 (compare (match_operand:HQI 0 "s_operand" "Q,S")
1007 (match_operand:HQI 1 "const0_operand" "")))
1008 (set (match_operand:HQI 2 "register_operand" "=d,d")
1009 (match_dup 0))]
1010 "s390_match_ccmode(insn, CCSmode)"
1011 "@
1012 icm\t%2,<icm_lo>,%S0
1013 icmy\t%2,<icm_lo>,%S0"
1014 [(set_attr "op_type" "RS,RSY")
1015 (set_attr "cpu_facility" "*,longdisp")
1016 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
1017
1018 (define_insn "*tst<mode>_cconly"
1019 [(set (reg CC_REGNUM)
1020 (compare (match_operand:HQI 0 "s_operand" "Q,S")
1021 (match_operand:HQI 1 "const0_operand" "")))
1022 (clobber (match_scratch:HQI 2 "=d,d"))]
1023 "s390_match_ccmode(insn, CCSmode)"
1024 "@
1025 icm\t%2,<icm_lo>,%S0
1026 icmy\t%2,<icm_lo>,%S0"
1027 [(set_attr "op_type" "RS,RSY")
1028 (set_attr "cpu_facility" "*,longdisp")
1029 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
1030
1031
1032 ; Compare (equality) instructions
1033
1034 (define_insn "*cmpdi_cct"
1035 [(set (reg CC_REGNUM)
1036 (compare (match_operand:DI 0 "nonimmediate_operand" "%d,d,d,d,Q")
1037 (match_operand:DI 1 "general_operand" "d,K,Os,T,BQ")))]
1038 "s390_match_ccmode (insn, CCTmode) && TARGET_ZARCH"
1039 "@
1040 cgr\t%0,%1
1041 cghi\t%0,%h1
1042 cgfi\t%0,%1
1043 cg\t%0,%1
1044 #"
1045 [(set_attr "op_type" "RRE,RI,RIL,RXY,SS")
1046 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,*")])
1047
1048 (define_insn "*cmpsi_cct"
1049 [(set (reg CC_REGNUM)
1050 (compare (match_operand:SI 0 "nonimmediate_operand" "%d,d,d,d,d,Q")
1051 (match_operand:SI 1 "general_operand" "d,K,Os,R,T,BQ")))]
1052 "s390_match_ccmode (insn, CCTmode)"
1053 "@
1054 cr\t%0,%1
1055 chi\t%0,%h1
1056 cfi\t%0,%1
1057 c\t%0,%1
1058 cy\t%0,%1
1059 #"
1060 [(set_attr "op_type" "RR,RI,RIL,RX,RXY,SS")
1061 (set_attr "cpu_facility" "*,*,*,*,longdisp,*")
1062 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*")])
1063
1064 ; Compare (signed) instructions
1065
1066 (define_insn "*cmpdi_ccs_sign"
1067 [(set (reg CC_REGNUM)
1068 (compare (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1069 "d,T,b"))
1070 (match_operand:DI 0 "register_operand" "d, d,d")))]
1071 "s390_match_ccmode(insn, CCSRmode) && TARGET_ZARCH"
1072 "@
1073 cgfr\t%0,%1
1074 cgf\t%0,%1
1075 cgfrl\t%0,%1"
1076 [(set_attr "op_type" "RRE,RXY,RIL")
1077 (set_attr "z10prop" "z10_c,*,*")
1078 (set_attr "type" "*,*,larl")])
1079
1080
1081
1082 (define_insn "*cmpsi_ccs_sign"
1083 [(set (reg CC_REGNUM)
1084 (compare (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T,b"))
1085 (match_operand:SI 0 "register_operand" "d,d,d")))]
1086 "s390_match_ccmode(insn, CCSRmode)"
1087 "@
1088 ch\t%0,%1
1089 chy\t%0,%1
1090 chrl\t%0,%1"
1091 [(set_attr "op_type" "RX,RXY,RIL")
1092 (set_attr "cpu_facility" "*,longdisp,z10")
1093 (set_attr "type" "*,*,larl")
1094 (set_attr "z196prop" "z196_cracked,z196_cracked,z196_cracked")])
1095
1096 (define_insn "*cmphi_ccs_z10"
1097 [(set (reg CC_REGNUM)
1098 (compare (match_operand:HI 0 "s_operand" "Q")
1099 (match_operand:HI 1 "immediate_operand" "K")))]
1100 "s390_match_ccmode(insn, CCSmode) && TARGET_Z10"
1101 "chhsi\t%0,%1"
1102 [(set_attr "op_type" "SIL")
1103 (set_attr "z196prop" "z196_cracked")])
1104
1105 (define_insn "*cmpdi_ccs_signhi_rl"
1106 [(set (reg CC_REGNUM)
1107 (compare (sign_extend:DI (match_operand:HI 1 "memory_operand" "T,b"))
1108 (match_operand:GPR 0 "register_operand" "d,d")))]
1109 "s390_match_ccmode(insn, CCSRmode) && TARGET_Z10"
1110 "@
1111 cgh\t%0,%1
1112 cghrl\t%0,%1"
1113 [(set_attr "op_type" "RXY,RIL")
1114 (set_attr "type" "*,larl")])
1115
1116 ; cr, chi, cfi, c, cy, cgr, cghi, cgfi, cg, chsi, cghsi, crl, cgrl
1117 (define_insn "*cmp<mode>_ccs"
1118 [(set (reg CC_REGNUM)
1119 (compare (match_operand:GPR 0 "nonimmediate_operand"
1120 "d,d,Q, d,d,d,d")
1121 (match_operand:GPR 1 "general_operand"
1122 "d,K,K,Os,R,T,b")))]
1123 "s390_match_ccmode(insn, CCSmode)"
1124 "@
1125 c<g>r\t%0,%1
1126 c<g>hi\t%0,%h1
1127 c<g>hsi\t%0,%h1
1128 c<g>fi\t%0,%1
1129 c<g>\t%0,%1
1130 c<y>\t%0,%1
1131 c<g>rl\t%0,%1"
1132 [(set_attr "op_type" "RR<E>,RI,SIL,RIL,RX<Y>,RXY,RIL")
1133 (set_attr "cpu_facility" "*,*,z10,extimm,*,longdisp,z10")
1134 (set_attr "type" "*,*,*,*,*,*,larl")
1135 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,z10_super")])
1136
1137
1138 ; Compare (unsigned) instructions
1139
1140 (define_insn "*cmpsi_ccu_zerohi_rlsi"
1141 [(set (reg CC_REGNUM)
1142 (compare (zero_extend:SI (mem:HI (match_operand:SI 1
1143 "larl_operand" "X")))
1144 (match_operand:SI 0 "register_operand" "d")))]
1145 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1146 "clhrl\t%0,%1"
1147 [(set_attr "op_type" "RIL")
1148 (set_attr "type" "larl")
1149 (set_attr "z10prop" "z10_super")])
1150
1151 ; clhrl, clghrl
1152 (define_insn "*cmp<GPR:mode>_ccu_zerohi_rldi"
1153 [(set (reg CC_REGNUM)
1154 (compare (zero_extend:GPR (mem:HI (match_operand:DI 1
1155 "larl_operand" "X")))
1156 (match_operand:GPR 0 "register_operand" "d")))]
1157 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
1158 "cl<g>hrl\t%0,%1"
1159 [(set_attr "op_type" "RIL")
1160 (set_attr "type" "larl")
1161 (set_attr "z10prop" "z10_super")])
1162
1163 (define_insn "*cmpdi_ccu_zero"
1164 [(set (reg CC_REGNUM)
1165 (compare (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand"
1166 "d,T,b"))
1167 (match_operand:DI 0 "register_operand" "d,d,d")))]
1168 "s390_match_ccmode (insn, CCURmode) && TARGET_ZARCH"
1169 "@
1170 clgfr\t%0,%1
1171 clgf\t%0,%1
1172 clgfrl\t%0,%1"
1173 [(set_attr "op_type" "RRE,RXY,RIL")
1174 (set_attr "cpu_facility" "*,*,z10")
1175 (set_attr "type" "*,*,larl")
1176 (set_attr "z10prop" "z10_super_c,z10_super_E1,z10_super")])
1177
1178 (define_insn "*cmpdi_ccu"
1179 [(set (reg CC_REGNUM)
1180 (compare (match_operand:DI 0 "nonimmediate_operand"
1181 "d, d,d,Q,d, Q,BQ")
1182 (match_operand:DI 1 "general_operand"
1183 "d,Op,b,D,T,BQ,Q")))]
1184 "s390_match_ccmode (insn, CCUmode) && TARGET_ZARCH"
1185 "@
1186 clgr\t%0,%1
1187 clgfi\t%0,%1
1188 clgrl\t%0,%1
1189 clghsi\t%0,%x1
1190 clg\t%0,%1
1191 #
1192 #"
1193 [(set_attr "op_type" "RRE,RIL,RIL,SIL,RXY,SS,SS")
1194 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*")
1195 (set_attr "type" "*,*,larl,*,*,*,*")
1196 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,*,*")])
1197
1198 (define_insn "*cmpsi_ccu"
1199 [(set (reg CC_REGNUM)
1200 (compare (match_operand:SI 0 "nonimmediate_operand" "d, d,d,Q,d,d, Q,BQ")
1201 (match_operand:SI 1 "general_operand" "d,Os,b,D,R,T,BQ, Q")))]
1202 "s390_match_ccmode (insn, CCUmode)"
1203 "@
1204 clr\t%0,%1
1205 clfi\t%0,%o1
1206 clrl\t%0,%1
1207 clfhsi\t%0,%x1
1208 cl\t%0,%1
1209 cly\t%0,%1
1210 #
1211 #"
1212 [(set_attr "op_type" "RR,RIL,RIL,SIL,RX,RXY,SS,SS")
1213 (set_attr "cpu_facility" "*,extimm,z10,z10,*,longdisp,*,*")
1214 (set_attr "type" "*,*,larl,*,*,*,*,*")
1215 (set_attr "z10prop" "z10_super_c,z10_super,z10_super,z10_super,z10_super,z10_super,*,*")])
1216
1217 (define_insn "*cmphi_ccu"
1218 [(set (reg CC_REGNUM)
1219 (compare (match_operand:HI 0 "nonimmediate_operand" "d,d,Q,Q,BQ")
1220 (match_operand:HI 1 "general_operand" "Q,S,D,BQ,Q")))]
1221 "s390_match_ccmode (insn, CCUmode)
1222 && !register_operand (operands[1], HImode)"
1223 "@
1224 clm\t%0,3,%S1
1225 clmy\t%0,3,%S1
1226 clhhsi\t%0,%1
1227 #
1228 #"
1229 [(set_attr "op_type" "RS,RSY,SIL,SS,SS")
1230 (set_attr "cpu_facility" "*,longdisp,z10,*,*")
1231 (set_attr "z10prop" "*,*,z10_super,*,*")])
1232
1233 (define_insn "*cmpqi_ccu"
1234 [(set (reg CC_REGNUM)
1235 (compare (match_operand:QI 0 "nonimmediate_operand" "d,d,Q,S,Q,BQ")
1236 (match_operand:QI 1 "general_operand" "Q,S,n,n,BQ,Q")))]
1237 "s390_match_ccmode (insn, CCUmode)
1238 && !register_operand (operands[1], QImode)"
1239 "@
1240 clm\t%0,1,%S1
1241 clmy\t%0,1,%S1
1242 cli\t%S0,%b1
1243 cliy\t%S0,%b1
1244 #
1245 #"
1246 [(set_attr "op_type" "RS,RSY,SI,SIY,SS,SS")
1247 (set_attr "cpu_facility" "*,longdisp,*,longdisp,*,*")
1248 (set_attr "z10prop" "*,*,z10_super,z10_super,*,*")])
1249
1250
1251 ; Block compare (CLC) instruction patterns.
1252
1253 (define_insn "*clc"
1254 [(set (reg CC_REGNUM)
1255 (compare (match_operand:BLK 0 "memory_operand" "Q")
1256 (match_operand:BLK 1 "memory_operand" "Q")))
1257 (use (match_operand 2 "const_int_operand" "n"))]
1258 "s390_match_ccmode (insn, CCUmode)
1259 && INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
1260 "clc\t%O0(%2,%R0),%S1"
1261 [(set_attr "op_type" "SS")])
1262
1263 (define_split
1264 [(set (reg CC_REGNUM)
1265 (compare (match_operand 0 "memory_operand" "")
1266 (match_operand 1 "memory_operand" "")))]
1267 "reload_completed
1268 && s390_match_ccmode (insn, CCUmode)
1269 && GET_MODE (operands[0]) == GET_MODE (operands[1])
1270 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
1271 [(parallel
1272 [(set (match_dup 0) (match_dup 1))
1273 (use (match_dup 2))])]
1274 {
1275 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
1276 operands[0] = adjust_address (operands[0], BLKmode, 0);
1277 operands[1] = adjust_address (operands[1], BLKmode, 0);
1278
1279 operands[1] = gen_rtx_COMPARE (GET_MODE (SET_DEST (PATTERN (curr_insn))),
1280 operands[0], operands[1]);
1281 operands[0] = SET_DEST (PATTERN (curr_insn));
1282 })
1283
1284
1285 ; (TF|DF|SF|TD|DD|SD) instructions
1286
1287 ; ltxbr, ltdbr, ltebr, ltxtr, ltdtr
1288 (define_insn "*cmp<mode>_ccs_0"
1289 [(set (reg CC_REGNUM)
1290 (compare (match_operand:FP 0 "register_operand" "f")
1291 (match_operand:FP 1 "const0_operand" "")))]
1292 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1293 "lt<xde><bt>r\t%0,%0"
1294 [(set_attr "op_type" "RRE")
1295 (set_attr "type" "fsimp<mode>")])
1296
1297 ; cxtr, cxbr, cdtr, cdbr, cebr, cdb, ceb
1298 (define_insn "*cmp<mode>_ccs"
1299 [(set (reg CC_REGNUM)
1300 (compare (match_operand:FP 0 "register_operand" "f,f")
1301 (match_operand:FP 1 "general_operand" "f,R")))]
1302 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
1303 "@
1304 c<xde><bt>r\t%0,%1
1305 c<xde>b\t%0,%1"
1306 [(set_attr "op_type" "RRE,RXE")
1307 (set_attr "type" "fsimp<mode>")
1308 (set_attr "enabled" "*,<DSF>")])
1309
1310 ; wfcedbs, wfchdbs, wfchedbs
1311 (define_insn "*vec_cmp<insn_cmp>df_cconly"
1312 [(set (reg:VFCMP CC_REGNUM)
1313 (compare:VFCMP (match_operand:DF 0 "register_operand" "v")
1314 (match_operand:DF 1 "register_operand" "v")))
1315 (clobber (match_scratch:V2DI 2 "=v"))]
1316 "TARGET_VX && TARGET_HARD_FLOAT"
1317 "wfc<asm_fcmp>dbs\t%v2,%v0,%v1"
1318 [(set_attr "op_type" "VRR")])
1319
1320 ; Compare and Branch instructions
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 "*cmp_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 (label_ref (match_operand 3 "" ""))
1331 (pc)))
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%C0\t%1,%c2,%l3" : "c<g>rj%C0\t%1,%2,%l3";
1338 else
1339 return which_alternative ?
1340 "c<g>fi\t%1,%c2\;jg%C0\t%l3" : "c<g>r\t%1,%2\;jg%C0\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 "*cmp_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 (label_ref (match_operand 3 "" ""))
1359 (pc)))
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%C0\t%1,%b2,%l3" : "cl<g>rj%C0\t%1,%2,%l3";
1366 else
1367 return which_alternative ?
1368 "cl<g>fi\t%1,%b2\;jg%C0\t%l3" : "cl<g>r\t%1,%2\;jg%C0\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 ; And now the same two patterns as above but with a negated CC mask.
1379
1380 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
1381 ; The following instructions do a complementary access of their second
1382 ; operand (z01 only): crj_c, cgrjc, cr, cgr
1383 (define_insn "*icmp_and_br_signed_<mode>"
1384 [(set (pc)
1385 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
1386 [(match_operand:GPR 1 "register_operand" "d,d")
1387 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
1388 (pc)
1389 (label_ref (match_operand 3 "" ""))))
1390 (clobber (reg:CC CC_REGNUM))]
1391 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1392 {
1393 if (get_attr_length (insn) == 6)
1394 return which_alternative ?
1395 "c<g>ij%D0\t%1,%c2,%l3" : "c<g>rj%D0\t%1,%2,%l3";
1396 else
1397 return which_alternative ?
1398 "c<g>fi\t%1,%c2\;jg%D0\t%l3" : "c<g>r\t%1,%2\;jg%D0\t%l3";
1399 }
1400 [(set_attr "op_type" "RIE")
1401 (set_attr "type" "branch")
1402 (set_attr "z10prop" "z10_super_c,z10_super")
1403 (set (attr "length")
1404 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1405 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
1406 ; 10 byte for cgr/jg
1407
1408 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
1409 ; The following instructions do a complementary access of their second
1410 ; operand (z10 only): clrj, clgrj, clr, clgr
1411 (define_insn "*icmp_and_br_unsigned_<mode>"
1412 [(set (pc)
1413 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
1414 [(match_operand:GPR 1 "register_operand" "d,d")
1415 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
1416 (pc)
1417 (label_ref (match_operand 3 "" ""))))
1418 (clobber (reg:CC CC_REGNUM))]
1419 "TARGET_Z10 && !TARGET_AVOID_CMP_AND_BRANCH"
1420 {
1421 if (get_attr_length (insn) == 6)
1422 return which_alternative ?
1423 "cl<g>ij%D0\t%1,%b2,%l3" : "cl<g>rj%D0\t%1,%2,%l3";
1424 else
1425 return which_alternative ?
1426 "cl<g>fi\t%1,%b2\;jg%D0\t%l3" : "cl<g>r\t%1,%2\;jg%D0\t%l3";
1427 }
1428 [(set_attr "op_type" "RIE")
1429 (set_attr "type" "branch")
1430 (set_attr "z10prop" "z10_super_c,z10_super")
1431 (set (attr "length")
1432 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1433 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1434 ; 10 byte for clgr/jg
1435
1436 ;;
1437 ;;- Move instructions.
1438 ;;
1439
1440 ;
1441 ; movti instruction pattern(s).
1442 ;
1443
1444 ; FIXME: More constants are possible by enabling jxx, jyy constraints
1445 ; for TImode (use double-int for the calculations)
1446 (define_insn "movti"
1447 [(set (match_operand:TI 0 "nonimmediate_operand" "=d,S,v, v, v,v,d,v,R, d,o")
1448 (match_operand:TI 1 "general_operand" " S,d,v,j00,jm1,d,v,R,v,dPT,d"))]
1449 "TARGET_ZARCH"
1450 "@
1451 lmg\t%0,%N0,%S1
1452 stmg\t%1,%N1,%S0
1453 vlr\t%v0,%v1
1454 vzero\t%v0
1455 vone\t%v0
1456 vlvgp\t%v0,%1,%N1
1457 #
1458 vl\t%v0,%1
1459 vst\t%v1,%0
1460 #
1461 #"
1462 [(set_attr "op_type" "RSY,RSY,VRR,VRI,VRI,VRR,*,VRX,VRX,*,*")
1463 (set_attr "type" "lm,stm,*,*,*,*,*,*,*,*,*")
1464 (set_attr "cpu_facility" "*,*,vec,vec,vec,vec,vec,vec,vec,*,*")])
1465
1466 (define_split
1467 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1468 (match_operand:TI 1 "general_operand" ""))]
1469 "TARGET_ZARCH && reload_completed
1470 && s390_split_ok_p (operands[0], operands[1], TImode, 0)"
1471 [(set (match_dup 2) (match_dup 4))
1472 (set (match_dup 3) (match_dup 5))]
1473 {
1474 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1475 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1476 operands[4] = operand_subword (operands[1], 0, 0, TImode);
1477 operands[5] = operand_subword (operands[1], 1, 0, TImode);
1478 })
1479
1480 (define_split
1481 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1482 (match_operand:TI 1 "general_operand" ""))]
1483 "TARGET_ZARCH && reload_completed
1484 && s390_split_ok_p (operands[0], operands[1], TImode, 1)"
1485 [(set (match_dup 2) (match_dup 4))
1486 (set (match_dup 3) (match_dup 5))]
1487 {
1488 operands[2] = operand_subword (operands[0], 1, 0, TImode);
1489 operands[3] = operand_subword (operands[0], 0, 0, TImode);
1490 operands[4] = operand_subword (operands[1], 1, 0, TImode);
1491 operands[5] = operand_subword (operands[1], 0, 0, TImode);
1492 })
1493
1494 ; Use part of the TImode target reg to perform the address
1495 ; calculation. If the TImode value is supposed to be copied into a VR
1496 ; this splitter is not necessary.
1497 (define_split
1498 [(set (match_operand:TI 0 "register_operand" "")
1499 (match_operand:TI 1 "memory_operand" ""))]
1500 "TARGET_ZARCH && reload_completed
1501 && !VECTOR_REG_P (operands[0])
1502 && !s_operand (operands[1], VOIDmode)"
1503 [(set (match_dup 0) (match_dup 1))]
1504 {
1505 rtx addr = operand_subword (operands[0], 1, 0, TImode);
1506 addr = gen_lowpart (Pmode, addr);
1507 s390_load_address (addr, XEXP (operands[1], 0));
1508 operands[1] = replace_equiv_address (operands[1], addr);
1509 })
1510
1511
1512 ; Split a VR -> GPR TImode move into 2 vector load GR from VR element.
1513 ; For the higher order bits we do simply a DImode move while the
1514 ; second part is done via vec extract. Both will end up as vlgvg.
1515 (define_split
1516 [(set (match_operand:TI 0 "register_operand" "")
1517 (match_operand:TI 1 "register_operand" ""))]
1518 "TARGET_VX && reload_completed
1519 && GENERAL_REG_P (operands[0])
1520 && VECTOR_REG_P (operands[1])"
1521 [(set (match_dup 2) (match_dup 4))
1522 (set (match_dup 3) (unspec:DI [(match_dup 5) (const_int 1)]
1523 UNSPEC_VEC_EXTRACT))]
1524 {
1525 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1526 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1527 operands[4] = gen_rtx_REG (DImode, REGNO (operands[1]));
1528 operands[5] = gen_rtx_REG (V2DImode, REGNO (operands[1]));
1529 })
1530
1531 ;
1532 ; Patterns used for secondary reloads
1533 ;
1534
1535 ; z10 provides move instructions accepting larl memory operands.
1536 ; Unfortunately there is no such variant for QI, TI and FP mode moves.
1537 ; These patterns are also used for unaligned SI and DI accesses.
1538
1539 (define_expand "reload<ALL:mode><P:mode>_tomem_z10"
1540 [(parallel [(match_operand:ALL 0 "memory_operand" "")
1541 (match_operand:ALL 1 "register_operand" "=d")
1542 (match_operand:P 2 "register_operand" "=&a")])]
1543 "TARGET_Z10"
1544 {
1545 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1546 DONE;
1547 })
1548
1549 (define_expand "reload<ALL:mode><P:mode>_toreg_z10"
1550 [(parallel [(match_operand:ALL 0 "register_operand" "=d")
1551 (match_operand:ALL 1 "memory_operand" "")
1552 (match_operand:P 2 "register_operand" "=a")])]
1553 "TARGET_Z10"
1554 {
1555 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1556 DONE;
1557 })
1558
1559 (define_expand "reload<P:mode>_larl_odd_addend_z10"
1560 [(parallel [(match_operand:P 0 "register_operand" "=d")
1561 (match_operand:P 1 "larl_operand" "")
1562 (match_operand:P 2 "register_operand" "=a")])]
1563 "TARGET_Z10"
1564 {
1565 s390_reload_larl_operand (operands[0], operands[1], operands[2]);
1566 DONE;
1567 })
1568
1569 ; Handles loading a PLUS (load address) expression
1570
1571 (define_expand "reload<mode>_plus"
1572 [(parallel [(match_operand:P 0 "register_operand" "=a")
1573 (match_operand:P 1 "s390_plus_operand" "")
1574 (match_operand:P 2 "register_operand" "=&a")])]
1575 ""
1576 {
1577 s390_expand_plus_operand (operands[0], operands[1], operands[2]);
1578 DONE;
1579 })
1580
1581 ; Not all the indirect memory access instructions support the full
1582 ; format (long disp + index + base). So whenever a move from/to such
1583 ; an address is required and the instruction cannot deal with it we do
1584 ; a load address into a scratch register first and use this as the new
1585 ; base register.
1586 ; This in particular is used for:
1587 ; - non-offsetable memory accesses for multiword moves
1588 ; - full vector reg moves with long displacements
1589
1590 (define_expand "reload<mode>_la_in"
1591 [(parallel [(match_operand 0 "register_operand" "")
1592 (match_operand 1 "" "")
1593 (match_operand:P 2 "register_operand" "=&a")])]
1594 ""
1595 {
1596 gcc_assert (MEM_P (operands[1]));
1597 s390_load_address (operands[2], find_replacement (&XEXP (operands[1], 0)));
1598 operands[1] = replace_equiv_address (operands[1], operands[2]);
1599 emit_move_insn (operands[0], operands[1]);
1600 DONE;
1601 })
1602
1603 (define_expand "reload<mode>_la_out"
1604 [(parallel [(match_operand 0 "" "")
1605 (match_operand 1 "register_operand" "")
1606 (match_operand:P 2 "register_operand" "=&a")])]
1607 ""
1608 {
1609 gcc_assert (MEM_P (operands[0]));
1610 s390_load_address (operands[2], find_replacement (&XEXP (operands[0], 0)));
1611 operands[0] = replace_equiv_address (operands[0], operands[2]);
1612 emit_move_insn (operands[0], operands[1]);
1613 DONE;
1614 })
1615
1616 (define_expand "reload<mode>_PIC_addr"
1617 [(parallel [(match_operand 0 "register_operand" "=d")
1618 (match_operand 1 "larl_operand" "")
1619 (match_operand:P 2 "register_operand" "=a")])]
1620 ""
1621 {
1622 rtx new_rtx = legitimize_pic_address (operands[1], operands[2]);
1623 emit_move_insn (operands[0], new_rtx);
1624 })
1625
1626 ;
1627 ; movdi instruction pattern(s).
1628 ;
1629
1630 (define_expand "movdi"
1631 [(set (match_operand:DI 0 "general_operand" "")
1632 (match_operand:DI 1 "general_operand" ""))]
1633 ""
1634 {
1635 /* Handle symbolic constants. */
1636 if (TARGET_64BIT
1637 && (SYMBOLIC_CONST (operands[1])
1638 || (GET_CODE (operands[1]) == PLUS
1639 && XEXP (operands[1], 0) == pic_offset_table_rtx
1640 && SYMBOLIC_CONST (XEXP (operands[1], 1)))))
1641 emit_symbolic_move (operands);
1642 })
1643
1644 (define_insn "*movdi_larl"
1645 [(set (match_operand:DI 0 "register_operand" "=d")
1646 (match_operand:DI 1 "larl_operand" "X"))]
1647 "TARGET_64BIT
1648 && !FP_REG_P (operands[0])"
1649 "larl\t%0,%1"
1650 [(set_attr "op_type" "RIL")
1651 (set_attr "type" "larl")
1652 (set_attr "z10prop" "z10_super_A1")])
1653
1654 (define_insn "*movdi_64"
1655 [(set (match_operand:DI 0 "nonimmediate_operand"
1656 "=d, d, d, d, d, d, d, d,f,d,d,d,d,d,T,!*f,!*f,!*f,!R,!T,b,Q,d,t,Q,t,v,v,v,d,v,R")
1657 (match_operand:DI 1 "general_operand"
1658 " K,N0HD0,N1HD0,N2HD0,N3HD0,Os,N0SD0,N1SD0,d,f,L,b,d,T,d, *f, R, T,*f,*f,d,K,t,d,t,Q,K,v,d,v,R,v"))]
1659 "TARGET_ZARCH"
1660 "@
1661 lghi\t%0,%h1
1662 llihh\t%0,%i1
1663 llihl\t%0,%i1
1664 llilh\t%0,%i1
1665 llill\t%0,%i1
1666 lgfi\t%0,%1
1667 llihf\t%0,%k1
1668 llilf\t%0,%k1
1669 ldgr\t%0,%1
1670 lgdr\t%0,%1
1671 lay\t%0,%a1
1672 lgrl\t%0,%1
1673 lgr\t%0,%1
1674 lg\t%0,%1
1675 stg\t%1,%0
1676 ldr\t%0,%1
1677 ld\t%0,%1
1678 ldy\t%0,%1
1679 std\t%1,%0
1680 stdy\t%1,%0
1681 stgrl\t%1,%0
1682 mvghi\t%0,%1
1683 #
1684 #
1685 stam\t%1,%N1,%S0
1686 lam\t%0,%N0,%S1
1687 vleig\t%v0,%h1,0
1688 vlr\t%v0,%v1
1689 vlvgg\t%v0,%1,0
1690 vlgvg\t%0,%v1,0
1691 vleg\t%v0,%1,0
1692 vsteg\t%v1,%0,0"
1693 [(set_attr "op_type" "RI,RI,RI,RI,RI,RIL,RIL,RIL,RRE,RRE,RXY,RIL,RRE,RXY,
1694 RXY,RR,RX,RXY,RX,RXY,RIL,SIL,*,*,RS,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1695 (set_attr "type" "*,*,*,*,*,*,*,*,floaddf,floaddf,la,larl,lr,load,store,
1696 floaddf,floaddf,floaddf,fstoredf,fstoredf,larl,*,*,*,*,
1697 *,*,*,*,*,*,*")
1698 (set_attr "cpu_facility" "*,*,*,*,*,extimm,extimm,extimm,dfp,dfp,longdisp,
1699 z10,*,*,*,*,*,longdisp,*,longdisp,
1700 z10,z10,*,*,*,*,vec,vec,vec,vec,vec,vec")
1701 (set_attr "z10prop" "z10_fwd_A1,
1702 z10_fwd_E1,
1703 z10_fwd_E1,
1704 z10_fwd_E1,
1705 z10_fwd_E1,
1706 z10_fwd_A1,
1707 z10_fwd_E1,
1708 z10_fwd_E1,
1709 *,
1710 *,
1711 z10_fwd_A1,
1712 z10_fwd_A3,
1713 z10_fr_E1,
1714 z10_fwd_A3,
1715 z10_rec,
1716 *,
1717 *,
1718 *,
1719 *,
1720 *,
1721 z10_rec,
1722 z10_super,
1723 *,
1724 *,
1725 *,
1726 *,*,*,*,*,*,*")
1727 ])
1728
1729 (define_split
1730 [(set (match_operand:DI 0 "register_operand" "")
1731 (match_operand:DI 1 "register_operand" ""))]
1732 "TARGET_ZARCH && ACCESS_REG_P (operands[1])"
1733 [(set (match_dup 2) (match_dup 3))
1734 (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
1735 (set (strict_low_part (match_dup 2)) (match_dup 4))]
1736 "operands[2] = gen_lowpart (SImode, operands[0]);
1737 s390_split_access_reg (operands[1], &operands[4], &operands[3]);")
1738
1739 (define_split
1740 [(set (match_operand:DI 0 "register_operand" "")
1741 (match_operand:DI 1 "register_operand" ""))]
1742 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1743 && dead_or_set_p (insn, operands[1])"
1744 [(set (match_dup 3) (match_dup 2))
1745 (set (match_dup 1) (lshiftrt:DI (match_dup 1) (const_int 32)))
1746 (set (match_dup 4) (match_dup 2))]
1747 "operands[2] = gen_lowpart (SImode, operands[1]);
1748 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1749
1750 (define_split
1751 [(set (match_operand:DI 0 "register_operand" "")
1752 (match_operand:DI 1 "register_operand" ""))]
1753 "TARGET_ZARCH && ACCESS_REG_P (operands[0])
1754 && !dead_or_set_p (insn, operands[1])"
1755 [(set (match_dup 3) (match_dup 2))
1756 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))
1757 (set (match_dup 4) (match_dup 2))
1758 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))]
1759 "operands[2] = gen_lowpart (SImode, operands[1]);
1760 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1761
1762 (define_insn "*movdi_31"
1763 [(set (match_operand:DI 0 "nonimmediate_operand"
1764 "=d,d,Q,S,d ,o,!*f,!*f,!*f,!R,!T,d")
1765 (match_operand:DI 1 "general_operand"
1766 " Q,S,d,d,dPT,d, *f, R, T,*f,*f,b"))]
1767 "!TARGET_ZARCH"
1768 "@
1769 lm\t%0,%N0,%S1
1770 lmy\t%0,%N0,%S1
1771 stm\t%1,%N1,%S0
1772 stmy\t%1,%N1,%S0
1773 #
1774 #
1775 ldr\t%0,%1
1776 ld\t%0,%1
1777 ldy\t%0,%1
1778 std\t%1,%0
1779 stdy\t%1,%0
1780 #"
1781 [(set_attr "op_type" "RS,RSY,RS,RSY,*,*,RR,RX,RXY,RX,RXY,*")
1782 (set_attr "type" "lm,lm,stm,stm,*,*,floaddf,floaddf,floaddf,fstoredf,fstoredf,*")
1783 (set_attr "cpu_facility" "*,longdisp,*,longdisp,*,*,*,*,longdisp,*,longdisp,z10")])
1784
1785 ; For a load from a symbol ref we can use one of the target registers
1786 ; together with larl to load the address.
1787 (define_split
1788 [(set (match_operand:DI 0 "register_operand" "")
1789 (match_operand:DI 1 "memory_operand" ""))]
1790 "!TARGET_ZARCH && reload_completed && TARGET_Z10
1791 && larl_operand (XEXP (operands[1], 0), SImode)"
1792 [(set (match_dup 2) (match_dup 3))
1793 (set (match_dup 0) (match_dup 1))]
1794 {
1795 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1796 operands[3] = XEXP (operands[1], 0);
1797 operands[1] = replace_equiv_address (operands[1], operands[2]);
1798 })
1799
1800 (define_split
1801 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1802 (match_operand:DI 1 "general_operand" ""))]
1803 "!TARGET_ZARCH && reload_completed
1804 && s390_split_ok_p (operands[0], operands[1], DImode, 0)"
1805 [(set (match_dup 2) (match_dup 4))
1806 (set (match_dup 3) (match_dup 5))]
1807 {
1808 operands[2] = operand_subword (operands[0], 0, 0, DImode);
1809 operands[3] = operand_subword (operands[0], 1, 0, DImode);
1810 operands[4] = operand_subword (operands[1], 0, 0, DImode);
1811 operands[5] = operand_subword (operands[1], 1, 0, DImode);
1812 })
1813
1814 (define_split
1815 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1816 (match_operand:DI 1 "general_operand" ""))]
1817 "!TARGET_ZARCH && reload_completed
1818 && s390_split_ok_p (operands[0], operands[1], DImode, 1)"
1819 [(set (match_dup 2) (match_dup 4))
1820 (set (match_dup 3) (match_dup 5))]
1821 {
1822 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1823 operands[3] = operand_subword (operands[0], 0, 0, DImode);
1824 operands[4] = operand_subword (operands[1], 1, 0, DImode);
1825 operands[5] = operand_subword (operands[1], 0, 0, DImode);
1826 })
1827
1828 (define_split
1829 [(set (match_operand:DI 0 "register_operand" "")
1830 (match_operand:DI 1 "memory_operand" ""))]
1831 "!TARGET_ZARCH && reload_completed
1832 && !FP_REG_P (operands[0])
1833 && !s_operand (operands[1], VOIDmode)"
1834 [(set (match_dup 0) (match_dup 1))]
1835 {
1836 rtx addr = operand_subword (operands[0], 1, 0, DImode);
1837 s390_load_address (addr, XEXP (operands[1], 0));
1838 operands[1] = replace_equiv_address (operands[1], addr);
1839 })
1840
1841 (define_peephole2
1842 [(set (match_operand:DI 0 "register_operand" "")
1843 (mem:DI (match_operand 1 "address_operand" "")))]
1844 "TARGET_ZARCH
1845 && !FP_REG_P (operands[0])
1846 && GET_CODE (operands[1]) == SYMBOL_REF
1847 && CONSTANT_POOL_ADDRESS_P (operands[1])
1848 && get_pool_mode (operands[1]) == DImode
1849 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1850 [(set (match_dup 0) (match_dup 2))]
1851 "operands[2] = get_pool_constant (operands[1]);")
1852
1853 (define_insn "*la_64"
1854 [(set (match_operand:DI 0 "register_operand" "=d,d")
1855 (match_operand:QI 1 "address_operand" "ZR,ZT"))]
1856 "TARGET_64BIT"
1857 "@
1858 la\t%0,%a1
1859 lay\t%0,%a1"
1860 [(set_attr "op_type" "RX,RXY")
1861 (set_attr "type" "la")
1862 (set_attr "cpu_facility" "*,longdisp")
1863 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
1864
1865 (define_peephole2
1866 [(parallel
1867 [(set (match_operand:DI 0 "register_operand" "")
1868 (match_operand:QI 1 "address_operand" ""))
1869 (clobber (reg:CC CC_REGNUM))])]
1870 "TARGET_64BIT
1871 && preferred_la_operand_p (operands[1], const0_rtx)"
1872 [(set (match_dup 0) (match_dup 1))]
1873 "")
1874
1875 (define_peephole2
1876 [(set (match_operand:DI 0 "register_operand" "")
1877 (match_operand:DI 1 "register_operand" ""))
1878 (parallel
1879 [(set (match_dup 0)
1880 (plus:DI (match_dup 0)
1881 (match_operand:DI 2 "nonmemory_operand" "")))
1882 (clobber (reg:CC CC_REGNUM))])]
1883 "TARGET_64BIT
1884 && !reg_overlap_mentioned_p (operands[0], operands[2])
1885 && preferred_la_operand_p (operands[1], operands[2])"
1886 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
1887 "")
1888
1889 ;
1890 ; movsi instruction pattern(s).
1891 ;
1892
1893 (define_expand "movsi"
1894 [(set (match_operand:SI 0 "general_operand" "")
1895 (match_operand:SI 1 "general_operand" ""))]
1896 ""
1897 {
1898 /* Handle symbolic constants. */
1899 if (!TARGET_64BIT
1900 && (SYMBOLIC_CONST (operands[1])
1901 || (GET_CODE (operands[1]) == PLUS
1902 && XEXP (operands[1], 0) == pic_offset_table_rtx
1903 && SYMBOLIC_CONST (XEXP(operands[1], 1)))))
1904 emit_symbolic_move (operands);
1905 })
1906
1907 (define_insn "*movsi_larl"
1908 [(set (match_operand:SI 0 "register_operand" "=d")
1909 (match_operand:SI 1 "larl_operand" "X"))]
1910 "!TARGET_64BIT && TARGET_CPU_ZARCH
1911 && !FP_REG_P (operands[0])"
1912 "larl\t%0,%1"
1913 [(set_attr "op_type" "RIL")
1914 (set_attr "type" "larl")
1915 (set_attr "z10prop" "z10_fwd_A1")])
1916
1917 (define_insn "*movsi_zarch"
1918 [(set (match_operand:SI 0 "nonimmediate_operand"
1919 "=d, d, d, d,d,d,d,d,d,R,T,!*f,!*f,!*f,!*f,!*f,!R,!T,d,t,Q,b,Q,t,v,v,v,d,v,R")
1920 (match_operand:SI 1 "general_operand"
1921 " K,N0HS0,N1HS0,Os,L,b,d,R,T,d,d, *f, *f, R, R, T,*f,*f,t,d,t,d,K,Q,K,v,d,v,R,v"))]
1922 "TARGET_ZARCH"
1923 "@
1924 lhi\t%0,%h1
1925 llilh\t%0,%i1
1926 llill\t%0,%i1
1927 iilf\t%0,%o1
1928 lay\t%0,%a1
1929 lrl\t%0,%1
1930 lr\t%0,%1
1931 l\t%0,%1
1932 ly\t%0,%1
1933 st\t%1,%0
1934 sty\t%1,%0
1935 ldr\t%0,%1
1936 ler\t%0,%1
1937 lde\t%0,%1
1938 le\t%0,%1
1939 ley\t%0,%1
1940 ste\t%1,%0
1941 stey\t%1,%0
1942 ear\t%0,%1
1943 sar\t%0,%1
1944 stam\t%1,%1,%S0
1945 strl\t%1,%0
1946 mvhi\t%0,%1
1947 lam\t%0,%0,%S1
1948 vleif\t%v0,%h1,0
1949 vlr\t%v0,%v1
1950 vlvgf\t%v0,%1,0
1951 vlgvf\t%0,%v1,0
1952 vlef\t%v0,%1,0
1953 vstef\t%v1,%0,0"
1954 [(set_attr "op_type" "RI,RI,RI,RIL,RXY,RIL,RR,RX,RXY,RX,RXY,
1955 RR,RR,RXE,RX,RXY,RX,RXY,RRE,RRE,RS,RIL,SIL,RS,VRI,VRR,VRS,VRS,VRX,VRX")
1956 (set_attr "type" "*,
1957 *,
1958 *,
1959 *,
1960 la,
1961 larl,
1962 lr,
1963 load,
1964 load,
1965 store,
1966 store,
1967 floadsf,
1968 floadsf,
1969 floadsf,
1970 floadsf,
1971 floadsf,
1972 fstoresf,
1973 fstoresf,
1974 *,
1975 *,
1976 *,
1977 larl,
1978 *,
1979 *,*,*,*,*,*,*")
1980 (set_attr "cpu_facility" "*,*,*,extimm,longdisp,z10,*,*,longdisp,*,longdisp,
1981 vec,*,vec,*,longdisp,*,longdisp,*,*,*,z10,z10,*,vec,vec,vec,vec,vec,vec")
1982 (set_attr "z10prop" "z10_fwd_A1,
1983 z10_fwd_E1,
1984 z10_fwd_E1,
1985 z10_fwd_A1,
1986 z10_fwd_A1,
1987 z10_fwd_A3,
1988 z10_fr_E1,
1989 z10_fwd_A3,
1990 z10_fwd_A3,
1991 z10_rec,
1992 z10_rec,
1993 *,
1994 *,
1995 *,
1996 *,
1997 *,
1998 *,
1999 *,
2000 z10_super_E1,
2001 z10_super,
2002 *,
2003 z10_rec,
2004 z10_super,
2005 *,*,*,*,*,*,*")])
2006
2007 (define_insn "*movsi_esa"
2008 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,R,!*f,!*f,!*f,!*f,!R,d,t,Q,t")
2009 (match_operand:SI 1 "general_operand" "K,d,R,d, *f, *f, R, R,*f,t,d,t,Q"))]
2010 "!TARGET_ZARCH"
2011 "@
2012 lhi\t%0,%h1
2013 lr\t%0,%1
2014 l\t%0,%1
2015 st\t%1,%0
2016 ldr\t%0,%1
2017 ler\t%0,%1
2018 lde\t%0,%1
2019 le\t%0,%1
2020 ste\t%1,%0
2021 ear\t%0,%1
2022 sar\t%0,%1
2023 stam\t%1,%1,%S0
2024 lam\t%0,%0,%S1"
2025 [(set_attr "op_type" "RI,RR,RX,RX,RR,RR,RXE,RX,RX,RRE,RRE,RS,RS")
2026 (set_attr "type" "*,lr,load,store,floadsf,floadsf,floadsf,floadsf,fstoresf,*,*,*,*")
2027 (set_attr "z10prop" "z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_rec,*,*,*,*,*,z10_super_E1,
2028 z10_super,*,*")
2029 (set_attr "cpu_facility" "*,*,*,*,vec,*,vec,*,*,*,*,*,*")
2030 ])
2031
2032 (define_peephole2
2033 [(set (match_operand:SI 0 "register_operand" "")
2034 (mem:SI (match_operand 1 "address_operand" "")))]
2035 "!FP_REG_P (operands[0])
2036 && GET_CODE (operands[1]) == SYMBOL_REF
2037 && CONSTANT_POOL_ADDRESS_P (operands[1])
2038 && get_pool_mode (operands[1]) == SImode
2039 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
2040 [(set (match_dup 0) (match_dup 2))]
2041 "operands[2] = get_pool_constant (operands[1]);")
2042
2043 (define_insn "*la_31"
2044 [(set (match_operand:SI 0 "register_operand" "=d,d")
2045 (match_operand:QI 1 "address_operand" "ZR,ZT"))]
2046 "!TARGET_64BIT && legitimate_la_operand_p (operands[1])"
2047 "@
2048 la\t%0,%a1
2049 lay\t%0,%a1"
2050 [(set_attr "op_type" "RX,RXY")
2051 (set_attr "type" "la")
2052 (set_attr "cpu_facility" "*,longdisp")
2053 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2054
2055 (define_peephole2
2056 [(parallel
2057 [(set (match_operand:SI 0 "register_operand" "")
2058 (match_operand:QI 1 "address_operand" ""))
2059 (clobber (reg:CC CC_REGNUM))])]
2060 "!TARGET_64BIT
2061 && preferred_la_operand_p (operands[1], const0_rtx)"
2062 [(set (match_dup 0) (match_dup 1))]
2063 "")
2064
2065 (define_peephole2
2066 [(set (match_operand:SI 0 "register_operand" "")
2067 (match_operand:SI 1 "register_operand" ""))
2068 (parallel
2069 [(set (match_dup 0)
2070 (plus:SI (match_dup 0)
2071 (match_operand:SI 2 "nonmemory_operand" "")))
2072 (clobber (reg:CC CC_REGNUM))])]
2073 "!TARGET_64BIT
2074 && !reg_overlap_mentioned_p (operands[0], operands[2])
2075 && preferred_la_operand_p (operands[1], operands[2])"
2076 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
2077 "")
2078
2079 (define_insn "*la_31_and"
2080 [(set (match_operand:SI 0 "register_operand" "=d,d")
2081 (and:SI (match_operand:QI 1 "address_operand" "ZR,ZT")
2082 (const_int 2147483647)))]
2083 "!TARGET_64BIT"
2084 "@
2085 la\t%0,%a1
2086 lay\t%0,%a1"
2087 [(set_attr "op_type" "RX,RXY")
2088 (set_attr "type" "la")
2089 (set_attr "cpu_facility" "*,longdisp")
2090 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2091
2092 (define_insn_and_split "*la_31_and_cc"
2093 [(set (match_operand:SI 0 "register_operand" "=d")
2094 (and:SI (match_operand:QI 1 "address_operand" "p")
2095 (const_int 2147483647)))
2096 (clobber (reg:CC CC_REGNUM))]
2097 "!TARGET_64BIT"
2098 "#"
2099 "&& reload_completed"
2100 [(set (match_dup 0)
2101 (and:SI (match_dup 1) (const_int 2147483647)))]
2102 ""
2103 [(set_attr "op_type" "RX")
2104 (set_attr "type" "la")])
2105
2106 (define_insn "force_la_31"
2107 [(set (match_operand:SI 0 "register_operand" "=d,d")
2108 (match_operand:QI 1 "address_operand" "ZR,ZT"))
2109 (use (const_int 0))]
2110 "!TARGET_64BIT"
2111 "@
2112 la\t%0,%a1
2113 lay\t%0,%a1"
2114 [(set_attr "op_type" "RX")
2115 (set_attr "type" "la")
2116 (set_attr "cpu_facility" "*,longdisp")
2117 (set_attr "z10prop" "z10_fwd_A1,z10_fwd_A1")])
2118
2119 ;
2120 ; movhi instruction pattern(s).
2121 ;
2122
2123 (define_expand "movhi"
2124 [(set (match_operand:HI 0 "nonimmediate_operand" "")
2125 (match_operand:HI 1 "general_operand" ""))]
2126 ""
2127 {
2128 /* Make it explicit that loading a register from memory
2129 always sign-extends (at least) to SImode. */
2130 if (optimize && can_create_pseudo_p ()
2131 && register_operand (operands[0], VOIDmode)
2132 && GET_CODE (operands[1]) == MEM)
2133 {
2134 rtx tmp = gen_reg_rtx (SImode);
2135 rtx ext = gen_rtx_SIGN_EXTEND (SImode, operands[1]);
2136 emit_insn (gen_rtx_SET (tmp, ext));
2137 operands[1] = gen_lowpart (HImode, tmp);
2138 }
2139 })
2140
2141 (define_insn "*movhi"
2142 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,d,R,T,b,Q,v,v,v,d,v,R")
2143 (match_operand:HI 1 "general_operand" " d,n,R,T,b,d,d,d,K,K,v,d,v,R,v"))]
2144 ""
2145 "@
2146 lr\t%0,%1
2147 lhi\t%0,%h1
2148 lh\t%0,%1
2149 lhy\t%0,%1
2150 lhrl\t%0,%1
2151 sth\t%1,%0
2152 sthy\t%1,%0
2153 sthrl\t%1,%0
2154 mvhhi\t%0,%1
2155 vleih\t%v0,%h1,0
2156 vlr\t%v0,%v1
2157 vlvgh\t%v0,%1,0
2158 vlgvh\t%0,%v1,0
2159 vleh\t%v0,%1,0
2160 vsteh\t%v1,%0,0"
2161 [(set_attr "op_type" "RR,RI,RX,RXY,RIL,RX,RXY,RIL,SIL,VRI,VRR,VRS,VRS,VRX,VRX")
2162 (set_attr "type" "lr,*,*,*,larl,store,store,store,*,*,*,*,*,*,*")
2163 (set_attr "cpu_facility" "*,*,*,longdisp,z10,*,longdisp,z10,z10,vec,vec,vec,vec,vec,vec")
2164 (set_attr "z10prop" "z10_fr_E1,
2165 z10_fwd_A1,
2166 z10_super_E1,
2167 z10_super_E1,
2168 z10_super_E1,
2169 z10_rec,
2170 z10_rec,
2171 z10_rec,
2172 z10_super,*,*,*,*,*,*")])
2173
2174 (define_peephole2
2175 [(set (match_operand:HI 0 "register_operand" "")
2176 (mem:HI (match_operand 1 "address_operand" "")))]
2177 "GET_CODE (operands[1]) == SYMBOL_REF
2178 && CONSTANT_POOL_ADDRESS_P (operands[1])
2179 && get_pool_mode (operands[1]) == HImode
2180 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2181 [(set (match_dup 0) (match_dup 2))]
2182 "operands[2] = get_pool_constant (operands[1]);")
2183
2184 ;
2185 ; movqi instruction pattern(s).
2186 ;
2187
2188 (define_expand "movqi"
2189 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2190 (match_operand:QI 1 "general_operand" ""))]
2191 ""
2192 {
2193 /* On z/Architecture, zero-extending from memory to register
2194 is just as fast as a QImode load. */
2195 if (TARGET_ZARCH && optimize && can_create_pseudo_p ()
2196 && register_operand (operands[0], VOIDmode)
2197 && GET_CODE (operands[1]) == MEM)
2198 {
2199 rtx tmp = gen_reg_rtx (DImode);
2200 rtx ext = gen_rtx_ZERO_EXTEND (DImode, operands[1]);
2201 emit_insn (gen_rtx_SET (tmp, ext));
2202 operands[1] = gen_lowpart (QImode, tmp);
2203 }
2204 })
2205
2206 (define_insn "*movqi"
2207 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,T,Q,S,?Q,v,v,v,d,v,R")
2208 (match_operand:QI 1 "general_operand" " d,n,R,T,d,d,n,n,?Q,K,v,d,v,R,v"))]
2209 ""
2210 "@
2211 lr\t%0,%1
2212 lhi\t%0,%b1
2213 ic\t%0,%1
2214 icy\t%0,%1
2215 stc\t%1,%0
2216 stcy\t%1,%0
2217 mvi\t%S0,%b1
2218 mviy\t%S0,%b1
2219 #
2220 vleib\t%v0,%b1,0
2221 vlr\t%v0,%v1
2222 vlvgb\t%v0,%1,0
2223 vlgvb\t%0,%v1,0
2224 vleb\t%v0,%1,0
2225 vsteb\t%v1,%0,0"
2226 [(set_attr "op_type" "RR,RI,RX,RXY,RX,RXY,SI,SIY,SS,VRI,VRR,VRS,VRS,VRX,VRX")
2227 (set_attr "type" "lr,*,*,*,store,store,store,store,*,*,*,*,*,*,*")
2228 (set_attr "cpu_facility" "*,*,*,longdisp,*,longdisp,*,longdisp,*,vec,vec,vec,vec,vec,vec")
2229 (set_attr "z10prop" "z10_fr_E1,
2230 z10_fwd_A1,
2231 z10_super_E1,
2232 z10_super_E1,
2233 z10_rec,
2234 z10_rec,
2235 z10_super,
2236 z10_super,
2237 *,*,*,*,*,*,*")])
2238
2239 (define_peephole2
2240 [(set (match_operand:QI 0 "nonimmediate_operand" "")
2241 (mem:QI (match_operand 1 "address_operand" "")))]
2242 "GET_CODE (operands[1]) == SYMBOL_REF
2243 && CONSTANT_POOL_ADDRESS_P (operands[1])
2244 && get_pool_mode (operands[1]) == QImode
2245 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
2246 [(set (match_dup 0) (match_dup 2))]
2247 "operands[2] = get_pool_constant (operands[1]);")
2248
2249 ;
2250 ; movstrictqi instruction pattern(s).
2251 ;
2252
2253 (define_insn "*movstrictqi"
2254 [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d,d"))
2255 (match_operand:QI 1 "memory_operand" "R,T"))]
2256 ""
2257 "@
2258 ic\t%0,%1
2259 icy\t%0,%1"
2260 [(set_attr "op_type" "RX,RXY")
2261 (set_attr "cpu_facility" "*,longdisp")
2262 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2263
2264 ;
2265 ; movstricthi instruction pattern(s).
2266 ;
2267
2268 (define_insn "*movstricthi"
2269 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d,d"))
2270 (match_operand:HI 1 "memory_operand" "Q,S"))
2271 (clobber (reg:CC CC_REGNUM))]
2272 ""
2273 "@
2274 icm\t%0,3,%S1
2275 icmy\t%0,3,%S1"
2276 [(set_attr "op_type" "RS,RSY")
2277 (set_attr "cpu_facility" "*,longdisp")
2278 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
2279
2280 ;
2281 ; movstrictsi instruction pattern(s).
2282 ;
2283
2284 (define_insn "movstrictsi"
2285 [(set (strict_low_part (match_operand:SI 0 "register_operand" "+d,d,d,d"))
2286 (match_operand:SI 1 "general_operand" "d,R,T,t"))]
2287 "TARGET_ZARCH"
2288 "@
2289 lr\t%0,%1
2290 l\t%0,%1
2291 ly\t%0,%1
2292 ear\t%0,%1"
2293 [(set_attr "op_type" "RR,RX,RXY,RRE")
2294 (set_attr "type" "lr,load,load,*")
2295 (set_attr "cpu_facility" "*,*,longdisp,*")
2296 (set_attr "z10prop" "z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_super_E1")])
2297
2298 ;
2299 ; mov(tf|td) instruction pattern(s).
2300 ;
2301
2302 (define_expand "mov<mode>"
2303 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2304 (match_operand:TD_TF 1 "general_operand" ""))]
2305 ""
2306 "")
2307
2308 (define_insn "*mov<mode>_64"
2309 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o,d,S, d,o")
2310 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,S,d,dT,d"))]
2311 "TARGET_ZARCH"
2312 "@
2313 lzxr\t%0
2314 lxr\t%0,%1
2315 #
2316 #
2317 lmg\t%0,%N0,%S1
2318 stmg\t%1,%N1,%S0
2319 #
2320 #"
2321 [(set_attr "op_type" "RRE,RRE,*,*,RSY,RSY,*,*")
2322 (set_attr "type" "fsimptf,fsimptf,*,*,lm,stm,*,*")
2323 (set_attr "cpu_facility" "z196,*,*,*,*,*,*,*")])
2324
2325 (define_insn "*mov<mode>_31"
2326 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o")
2327 (match_operand:TD_TF 1 "general_operand" " G,f,o,f"))]
2328 "!TARGET_ZARCH"
2329 "@
2330 lzxr\t%0
2331 lxr\t%0,%1
2332 #
2333 #"
2334 [(set_attr "op_type" "RRE,RRE,*,*")
2335 (set_attr "type" "fsimptf,fsimptf,*,*")
2336 (set_attr "cpu_facility" "z196,*,*,*")])
2337
2338 ; TFmode in GPRs splitters
2339
2340 (define_split
2341 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2342 (match_operand:TD_TF 1 "general_operand" ""))]
2343 "TARGET_ZARCH && reload_completed
2344 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2345 [(set (match_dup 2) (match_dup 4))
2346 (set (match_dup 3) (match_dup 5))]
2347 {
2348 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2349 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2350 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2351 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2352 })
2353
2354 (define_split
2355 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
2356 (match_operand:TD_TF 1 "general_operand" ""))]
2357 "TARGET_ZARCH && reload_completed
2358 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2359 [(set (match_dup 2) (match_dup 4))
2360 (set (match_dup 3) (match_dup 5))]
2361 {
2362 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2363 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2364 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2365 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2366 })
2367
2368 (define_split
2369 [(set (match_operand:TD_TF 0 "register_operand" "")
2370 (match_operand:TD_TF 1 "memory_operand" ""))]
2371 "TARGET_ZARCH && reload_completed
2372 && GENERAL_REG_P (operands[0])
2373 && !s_operand (operands[1], VOIDmode)"
2374 [(set (match_dup 0) (match_dup 1))]
2375 {
2376 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2377 addr = gen_lowpart (Pmode, addr);
2378 s390_load_address (addr, XEXP (operands[1], 0));
2379 operands[1] = replace_equiv_address (operands[1], addr);
2380 })
2381
2382 ; TFmode in BFPs splitters
2383
2384 (define_split
2385 [(set (match_operand:TD_TF 0 "register_operand" "")
2386 (match_operand:TD_TF 1 "memory_operand" ""))]
2387 "reload_completed && offsettable_memref_p (operands[1])
2388 && FP_REG_P (operands[0])"
2389 [(set (match_dup 2) (match_dup 4))
2390 (set (match_dup 3) (match_dup 5))]
2391 {
2392 operands[2] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2393 <MODE>mode, 0);
2394 operands[3] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
2395 <MODE>mode, 8);
2396 operands[4] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 0);
2397 operands[5] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 8);
2398 })
2399
2400 (define_split
2401 [(set (match_operand:TD_TF 0 "memory_operand" "")
2402 (match_operand:TD_TF 1 "register_operand" ""))]
2403 "reload_completed && offsettable_memref_p (operands[0])
2404 && FP_REG_P (operands[1])"
2405 [(set (match_dup 2) (match_dup 4))
2406 (set (match_dup 3) (match_dup 5))]
2407 {
2408 operands[2] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 0);
2409 operands[3] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 8);
2410 operands[4] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2411 <MODE>mode, 0);
2412 operands[5] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
2413 <MODE>mode, 8);
2414 })
2415
2416 ;
2417 ; mov(df|dd) instruction pattern(s).
2418 ;
2419
2420 (define_expand "mov<mode>"
2421 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2422 (match_operand:DD_DF 1 "general_operand" ""))]
2423 ""
2424 "")
2425
2426 (define_insn "*mov<mode>_64dfp"
2427 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2428 "=f,f,f,d,f,f,R,T,d,d,d,d,b,T,v,v,d,v,R")
2429 (match_operand:DD_DF 1 "general_operand"
2430 " G,f,d,f,R,T,f,f,G,d,b,T,d,d,v,d,v,R,v"))]
2431 "TARGET_DFP"
2432 "@
2433 lzdr\t%0
2434 ldr\t%0,%1
2435 ldgr\t%0,%1
2436 lgdr\t%0,%1
2437 ld\t%0,%1
2438 ldy\t%0,%1
2439 std\t%1,%0
2440 stdy\t%1,%0
2441 lghi\t%0,0
2442 lgr\t%0,%1
2443 lgrl\t%0,%1
2444 lg\t%0,%1
2445 stgrl\t%1,%0
2446 stg\t%1,%0
2447 vlr\t%v0,%v1
2448 vlvgg\t%v0,%1,0
2449 vlgvg\t%0,%v1,0
2450 vleg\t%0,%1,0
2451 vsteg\t%1,%0,0"
2452 [(set_attr "op_type" "RRE,RR,RRE,RRE,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRS,VRS,VRX,VRX")
2453 (set_attr "type" "fsimpdf,floaddf,floaddf,floaddf,floaddf,floaddf,
2454 fstoredf,fstoredf,*,lr,load,load,store,store,*,*,*,load,store")
2455 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*,*,*")
2456 (set_attr "cpu_facility" "z196,*,*,*,*,longdisp,*,longdisp,*,*,z10,*,z10,*,vec,vec,vec,vec,vec")])
2457
2458 (define_insn "*mov<mode>_64"
2459 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "=f,f,f,f,R,T,d,d,d,d,b,T,v,v,R")
2460 (match_operand:DD_DF 1 "general_operand" " G,f,R,T,f,f,G,d,b,T,d,d,v,R,v"))]
2461 "TARGET_ZARCH"
2462 "@
2463 lzdr\t%0
2464 ldr\t%0,%1
2465 ld\t%0,%1
2466 ldy\t%0,%1
2467 std\t%1,%0
2468 stdy\t%1,%0
2469 lghi\t%0,0
2470 lgr\t%0,%1
2471 lgrl\t%0,%1
2472 lg\t%0,%1
2473 stgrl\t%1,%0
2474 stg\t%1,%0
2475 vlr\t%v0,%v1
2476 vleg\t%v0,%1,0
2477 vsteg\t%v1,%0,0"
2478 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RI,RRE,RIL,RXY,RIL,RXY,VRR,VRX,VRX")
2479 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2480 fstore<mode>,fstore<mode>,*,lr,load,load,store,store,*,load,store")
2481 (set_attr "z10prop" "*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,*,*,*")
2482 (set_attr "cpu_facility" "z196,*,*,longdisp,*,longdisp,*,*,z10,*,z10,*,vec,vec,vec")])
2483
2484 (define_insn "*mov<mode>_31"
2485 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
2486 "=f,f,f,f,R,T,d,d,Q,S, d,o")
2487 (match_operand:DD_DF 1 "general_operand"
2488 " G,f,R,T,f,f,Q,S,d,d,dPT,d"))]
2489 "!TARGET_ZARCH"
2490 "@
2491 lzdr\t%0
2492 ldr\t%0,%1
2493 ld\t%0,%1
2494 ldy\t%0,%1
2495 std\t%1,%0
2496 stdy\t%1,%0
2497 lm\t%0,%N0,%S1
2498 lmy\t%0,%N0,%S1
2499 stm\t%1,%N1,%S0
2500 stmy\t%1,%N1,%S0
2501 #
2502 #"
2503 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RS,RSY,RS,RSY,*,*")
2504 (set_attr "type" "fsimpdf,fload<mode>,fload<mode>,fload<mode>,
2505 fstore<mode>,fstore<mode>,lm,lm,stm,stm,*,*")
2506 (set_attr "cpu_facility" "z196,*,*,longdisp,*,longdisp,*,longdisp,*,longdisp,*,*")])
2507
2508 (define_split
2509 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2510 (match_operand:DD_DF 1 "general_operand" ""))]
2511 "!TARGET_ZARCH && reload_completed
2512 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
2513 [(set (match_dup 2) (match_dup 4))
2514 (set (match_dup 3) (match_dup 5))]
2515 {
2516 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
2517 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
2518 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
2519 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
2520 })
2521
2522 (define_split
2523 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
2524 (match_operand:DD_DF 1 "general_operand" ""))]
2525 "!TARGET_ZARCH && reload_completed
2526 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
2527 [(set (match_dup 2) (match_dup 4))
2528 (set (match_dup 3) (match_dup 5))]
2529 {
2530 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
2531 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
2532 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
2533 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
2534 })
2535
2536 (define_split
2537 [(set (match_operand:DD_DF 0 "register_operand" "")
2538 (match_operand:DD_DF 1 "memory_operand" ""))]
2539 "!TARGET_ZARCH && reload_completed
2540 && !FP_REG_P (operands[0])
2541 && !s_operand (operands[1], VOIDmode)"
2542 [(set (match_dup 0) (match_dup 1))]
2543 {
2544 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
2545 s390_load_address (addr, XEXP (operands[1], 0));
2546 operands[1] = replace_equiv_address (operands[1], addr);
2547 })
2548
2549 ;
2550 ; mov(sf|sd) instruction pattern(s).
2551 ;
2552
2553 (define_insn "mov<mode>"
2554 [(set (match_operand:SD_SF 0 "nonimmediate_operand"
2555 "=f,f,f,f,f,f,R,T,d,d,d,d,d,b,R,T,v,v,v,d,v,R")
2556 (match_operand:SD_SF 1 "general_operand"
2557 " G,f,f,R,R,T,f,f,G,d,b,R,T,d,d,d,v,G,d,v,R,v"))]
2558 ""
2559 "@
2560 lzer\t%0
2561 ldr\t%0,%1
2562 ler\t%0,%1
2563 lde\t%0,%1
2564 le\t%0,%1
2565 ley\t%0,%1
2566 ste\t%1,%0
2567 stey\t%1,%0
2568 lhi\t%0,0
2569 lr\t%0,%1
2570 lrl\t%0,%1
2571 l\t%0,%1
2572 ly\t%0,%1
2573 strl\t%1,%0
2574 st\t%1,%0
2575 sty\t%1,%0
2576 vlr\t%v0,%v1
2577 vleif\t%v0,0
2578 vlvgf\t%v0,%1,0
2579 vlgvf\t%0,%v1,0
2580 vleg\t%0,%1,0
2581 vsteg\t%1,%0,0"
2582 [(set_attr "op_type" "RRE,RR,RR,RXE,RX,RXY,RX,RXY,RI,RR,RIL,RX,RXY,RIL,RX,RXY,VRR,VRI,VRS,VRS,VRX,VRX")
2583 (set_attr "type" "fsimpsf,fsimpsf,fload<mode>,fload<mode>,fload<mode>,fload<mode>,
2584 fstore<mode>,fstore<mode>,*,lr,load,load,load,store,store,store,*,*,*,*,load,store")
2585 (set_attr "z10prop" "*,*,*,*,*,*,*,*,z10_fwd_A1,z10_fr_E1,z10_fr_E1,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec,z10_rec,*,*,*,*,*,*")
2586 (set_attr "cpu_facility" "z196,vec,*,vec,*,longdisp,*,longdisp,*,*,z10,*,longdisp,z10,*,longdisp,vec,vec,vec,vec,vec,vec")])
2587
2588 ;
2589 ; movcc instruction pattern
2590 ;
2591
2592 (define_insn "movcc"
2593 [(set (match_operand:CC 0 "nonimmediate_operand" "=d,c,d,d,d,R,T")
2594 (match_operand:CC 1 "nonimmediate_operand" " d,d,c,R,T,d,d"))]
2595 ""
2596 "@
2597 lr\t%0,%1
2598 tmh\t%1,12288
2599 ipm\t%0
2600 l\t%0,%1
2601 ly\t%0,%1
2602 st\t%1,%0
2603 sty\t%1,%0"
2604 [(set_attr "op_type" "RR,RI,RRE,RX,RXY,RX,RXY")
2605 (set_attr "type" "lr,*,*,load,load,store,store")
2606 (set_attr "cpu_facility" "*,*,*,*,longdisp,*,longdisp")
2607 (set_attr "z10prop" "z10_fr_E1,z10_super,*,z10_fwd_A3,z10_fwd_A3,z10_rec,z10_rec")
2608 (set_attr "z196prop" "*,*,z196_ends,*,*,*,*")])
2609
2610 ;
2611 ; Block move (MVC) patterns.
2612 ;
2613
2614 (define_insn "*mvc"
2615 [(set (match_operand:BLK 0 "memory_operand" "=Q")
2616 (match_operand:BLK 1 "memory_operand" "Q"))
2617 (use (match_operand 2 "const_int_operand" "n"))]
2618 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
2619 "mvc\t%O0(%2,%R0),%S1"
2620 [(set_attr "op_type" "SS")])
2621
2622 ; This splitter converts a QI to QI mode copy into a BLK mode copy in
2623 ; order to have it implemented with mvc.
2624
2625 (define_split
2626 [(set (match_operand:QI 0 "memory_operand" "")
2627 (match_operand:QI 1 "memory_operand" ""))]
2628 "reload_completed"
2629 [(parallel
2630 [(set (match_dup 0) (match_dup 1))
2631 (use (const_int 1))])]
2632 {
2633 operands[0] = adjust_address (operands[0], BLKmode, 0);
2634 operands[1] = adjust_address (operands[1], BLKmode, 0);
2635 })
2636
2637
2638 (define_peephole2
2639 [(parallel
2640 [(set (match_operand:BLK 0 "memory_operand" "")
2641 (match_operand:BLK 1 "memory_operand" ""))
2642 (use (match_operand 2 "const_int_operand" ""))])
2643 (parallel
2644 [(set (match_operand:BLK 3 "memory_operand" "")
2645 (match_operand:BLK 4 "memory_operand" ""))
2646 (use (match_operand 5 "const_int_operand" ""))])]
2647 "s390_offset_p (operands[0], operands[3], operands[2])
2648 && s390_offset_p (operands[1], operands[4], operands[2])
2649 && !s390_overlap_p (operands[0], operands[1],
2650 INTVAL (operands[2]) + INTVAL (operands[5]))
2651 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
2652 [(parallel
2653 [(set (match_dup 6) (match_dup 7))
2654 (use (match_dup 8))])]
2655 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
2656 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
2657 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
2658
2659
2660 ;
2661 ; load_multiple pattern(s).
2662 ;
2663 ; ??? Due to reload problems with replacing registers inside match_parallel
2664 ; we currently support load_multiple/store_multiple only after reload.
2665 ;
2666
2667 (define_expand "load_multiple"
2668 [(match_par_dup 3 [(set (match_operand 0 "" "")
2669 (match_operand 1 "" ""))
2670 (use (match_operand 2 "" ""))])]
2671 "reload_completed"
2672 {
2673 machine_mode mode;
2674 int regno;
2675 int count;
2676 rtx from;
2677 int i, off;
2678
2679 /* Support only loading a constant number of fixed-point registers from
2680 memory and only bother with this if more than two */
2681 if (GET_CODE (operands[2]) != CONST_INT
2682 || INTVAL (operands[2]) < 2
2683 || INTVAL (operands[2]) > 16
2684 || GET_CODE (operands[1]) != MEM
2685 || GET_CODE (operands[0]) != REG
2686 || REGNO (operands[0]) >= 16)
2687 FAIL;
2688
2689 count = INTVAL (operands[2]);
2690 regno = REGNO (operands[0]);
2691 mode = GET_MODE (operands[0]);
2692 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2693 FAIL;
2694
2695 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2696 if (!can_create_pseudo_p ())
2697 {
2698 if (GET_CODE (XEXP (operands[1], 0)) == REG)
2699 {
2700 from = XEXP (operands[1], 0);
2701 off = 0;
2702 }
2703 else if (GET_CODE (XEXP (operands[1], 0)) == PLUS
2704 && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == REG
2705 && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == CONST_INT)
2706 {
2707 from = XEXP (XEXP (operands[1], 0), 0);
2708 off = INTVAL (XEXP (XEXP (operands[1], 0), 1));
2709 }
2710 else
2711 FAIL;
2712 }
2713 else
2714 {
2715 from = force_reg (Pmode, XEXP (operands[1], 0));
2716 off = 0;
2717 }
2718
2719 for (i = 0; i < count; i++)
2720 XVECEXP (operands[3], 0, i)
2721 = gen_rtx_SET (gen_rtx_REG (mode, regno + i),
2722 change_address (operands[1], mode,
2723 plus_constant (Pmode, from,
2724 off + i * GET_MODE_SIZE (mode))));
2725 })
2726
2727 (define_insn "*load_multiple_di"
2728 [(match_parallel 0 "load_multiple_operation"
2729 [(set (match_operand:DI 1 "register_operand" "=r")
2730 (match_operand:DI 2 "s_operand" "S"))])]
2731 "reload_completed && TARGET_ZARCH"
2732 {
2733 int words = XVECLEN (operands[0], 0);
2734 operands[0] = gen_rtx_REG (DImode, REGNO (operands[1]) + words - 1);
2735 return "lmg\t%1,%0,%S2";
2736 }
2737 [(set_attr "op_type" "RSY")
2738 (set_attr "type" "lm")])
2739
2740 (define_insn "*load_multiple_si"
2741 [(match_parallel 0 "load_multiple_operation"
2742 [(set (match_operand:SI 1 "register_operand" "=r,r")
2743 (match_operand:SI 2 "s_operand" "Q,S"))])]
2744 "reload_completed"
2745 {
2746 int words = XVECLEN (operands[0], 0);
2747 operands[0] = gen_rtx_REG (SImode, REGNO (operands[1]) + words - 1);
2748 return which_alternative == 0 ? "lm\t%1,%0,%S2" : "lmy\t%1,%0,%S2";
2749 }
2750 [(set_attr "op_type" "RS,RSY")
2751 (set_attr "cpu_facility" "*,longdisp")
2752 (set_attr "type" "lm")])
2753
2754 ;
2755 ; store multiple pattern(s).
2756 ;
2757
2758 (define_expand "store_multiple"
2759 [(match_par_dup 3 [(set (match_operand 0 "" "")
2760 (match_operand 1 "" ""))
2761 (use (match_operand 2 "" ""))])]
2762 "reload_completed"
2763 {
2764 machine_mode mode;
2765 int regno;
2766 int count;
2767 rtx to;
2768 int i, off;
2769
2770 /* Support only storing a constant number of fixed-point registers to
2771 memory and only bother with this if more than two. */
2772 if (GET_CODE (operands[2]) != CONST_INT
2773 || INTVAL (operands[2]) < 2
2774 || INTVAL (operands[2]) > 16
2775 || GET_CODE (operands[0]) != MEM
2776 || GET_CODE (operands[1]) != REG
2777 || REGNO (operands[1]) >= 16)
2778 FAIL;
2779
2780 count = INTVAL (operands[2]);
2781 regno = REGNO (operands[1]);
2782 mode = GET_MODE (operands[1]);
2783 if (mode != SImode && (!TARGET_ZARCH || mode != DImode))
2784 FAIL;
2785
2786 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2787
2788 if (!can_create_pseudo_p ())
2789 {
2790 if (GET_CODE (XEXP (operands[0], 0)) == REG)
2791 {
2792 to = XEXP (operands[0], 0);
2793 off = 0;
2794 }
2795 else if (GET_CODE (XEXP (operands[0], 0)) == PLUS
2796 && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
2797 && GET_CODE (XEXP (XEXP (operands[0], 0), 1)) == CONST_INT)
2798 {
2799 to = XEXP (XEXP (operands[0], 0), 0);
2800 off = INTVAL (XEXP (XEXP (operands[0], 0), 1));
2801 }
2802 else
2803 FAIL;
2804 }
2805 else
2806 {
2807 to = force_reg (Pmode, XEXP (operands[0], 0));
2808 off = 0;
2809 }
2810
2811 for (i = 0; i < count; i++)
2812 XVECEXP (operands[3], 0, i)
2813 = gen_rtx_SET (change_address (operands[0], mode,
2814 plus_constant (Pmode, to,
2815 off + i * GET_MODE_SIZE (mode))),
2816 gen_rtx_REG (mode, regno + i));
2817 })
2818
2819 (define_insn "*store_multiple_di"
2820 [(match_parallel 0 "store_multiple_operation"
2821 [(set (match_operand:DI 1 "s_operand" "=S")
2822 (match_operand:DI 2 "register_operand" "r"))])]
2823 "reload_completed && TARGET_ZARCH"
2824 {
2825 int words = XVECLEN (operands[0], 0);
2826 operands[0] = gen_rtx_REG (DImode, REGNO (operands[2]) + words - 1);
2827 return "stmg\t%2,%0,%S1";
2828 }
2829 [(set_attr "op_type" "RSY")
2830 (set_attr "type" "stm")])
2831
2832
2833 (define_insn "*store_multiple_si"
2834 [(match_parallel 0 "store_multiple_operation"
2835 [(set (match_operand:SI 1 "s_operand" "=Q,S")
2836 (match_operand:SI 2 "register_operand" "r,r"))])]
2837 "reload_completed"
2838 {
2839 int words = XVECLEN (operands[0], 0);
2840 operands[0] = gen_rtx_REG (SImode, REGNO (operands[2]) + words - 1);
2841 return which_alternative == 0 ? "stm\t%2,%0,%S1" : "stmy\t%2,%0,%S1";
2842 }
2843 [(set_attr "op_type" "RS,RSY")
2844 (set_attr "cpu_facility" "*,longdisp")
2845 (set_attr "type" "stm")])
2846
2847 ;;
2848 ;; String instructions.
2849 ;;
2850
2851 (define_insn "*execute_rl"
2852 [(match_parallel 0 "execute_operation"
2853 [(unspec [(match_operand 1 "register_operand" "a")
2854 (match_operand 2 "" "")
2855 (match_operand:SI 3 "larl_operand" "X")] UNSPEC_EXECUTE)])]
2856 "TARGET_Z10 && GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2857 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2858 "exrl\t%1,%3"
2859 [(set_attr "op_type" "RIL")
2860 (set_attr "type" "cs")])
2861
2862 (define_insn "*execute"
2863 [(match_parallel 0 "execute_operation"
2864 [(unspec [(match_operand 1 "register_operand" "a")
2865 (match_operand:BLK 2 "memory_operand" "R")
2866 (match_operand 3 "" "")] UNSPEC_EXECUTE)])]
2867 "GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2868 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2869 "ex\t%1,%2"
2870 [(set_attr "op_type" "RX")
2871 (set_attr "type" "cs")])
2872
2873
2874 ;
2875 ; strlenM instruction pattern(s).
2876 ;
2877
2878 (define_expand "strlen<mode>"
2879 [(match_operand:P 0 "register_operand" "") ; result
2880 (match_operand:BLK 1 "memory_operand" "") ; input string
2881 (match_operand:SI 2 "immediate_operand" "") ; search character
2882 (match_operand:SI 3 "immediate_operand" "")] ; known alignment
2883 ""
2884 {
2885 if (!TARGET_VX || operands[2] != const0_rtx)
2886 emit_insn (gen_strlen_srst<mode> (operands[0], operands[1],
2887 operands[2], operands[3]));
2888 else
2889 s390_expand_vec_strlen (operands[0], operands[1], operands[3]);
2890
2891 DONE;
2892 })
2893
2894 (define_expand "strlen_srst<mode>"
2895 [(set (reg:SI 0) (match_operand:SI 2 "immediate_operand" ""))
2896 (parallel
2897 [(set (match_dup 4)
2898 (unspec:P [(const_int 0)
2899 (match_operand:BLK 1 "memory_operand" "")
2900 (reg:SI 0)
2901 (match_operand 3 "immediate_operand" "")] UNSPEC_SRST))
2902 (clobber (scratch:P))
2903 (clobber (reg:CC CC_REGNUM))])
2904 (parallel
2905 [(set (match_operand:P 0 "register_operand" "")
2906 (minus:P (match_dup 4) (match_dup 5)))
2907 (clobber (reg:CC CC_REGNUM))])]
2908 ""
2909 {
2910 operands[4] = gen_reg_rtx (Pmode);
2911 operands[5] = gen_reg_rtx (Pmode);
2912 emit_move_insn (operands[5], force_operand (XEXP (operands[1], 0), NULL_RTX));
2913 operands[1] = replace_equiv_address (operands[1], operands[5]);
2914 })
2915
2916 (define_insn "*strlen<mode>"
2917 [(set (match_operand:P 0 "register_operand" "=a")
2918 (unspec:P [(match_operand:P 2 "general_operand" "0")
2919 (mem:BLK (match_operand:P 3 "register_operand" "1"))
2920 (reg:SI 0)
2921 (match_operand 4 "immediate_operand" "")] UNSPEC_SRST))
2922 (clobber (match_scratch:P 1 "=a"))
2923 (clobber (reg:CC CC_REGNUM))]
2924 ""
2925 "srst\t%0,%1\;jo\t.-4"
2926 [(set_attr "length" "8")
2927 (set_attr "type" "vs")])
2928
2929 ;
2930 ; cmpstrM instruction pattern(s).
2931 ;
2932
2933 (define_expand "cmpstrsi"
2934 [(set (reg:SI 0) (const_int 0))
2935 (parallel
2936 [(clobber (match_operand 3 "" ""))
2937 (clobber (match_dup 4))
2938 (set (reg:CCU CC_REGNUM)
2939 (compare:CCU (match_operand:BLK 1 "memory_operand" "")
2940 (match_operand:BLK 2 "memory_operand" "")))
2941 (use (reg:SI 0))])
2942 (parallel
2943 [(set (match_operand:SI 0 "register_operand" "=d")
2944 (unspec:SI [(reg:CCU CC_REGNUM)] UNSPEC_STRCMPCC_TO_INT))
2945 (clobber (reg:CC CC_REGNUM))])]
2946 ""
2947 {
2948 /* As the result of CMPINT is inverted compared to what we need,
2949 we have to swap the operands. */
2950 rtx op1 = operands[2];
2951 rtx op2 = operands[1];
2952 rtx addr1 = gen_reg_rtx (Pmode);
2953 rtx addr2 = gen_reg_rtx (Pmode);
2954
2955 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
2956 emit_move_insn (addr2, force_operand (XEXP (op2, 0), NULL_RTX));
2957 operands[1] = replace_equiv_address_nv (op1, addr1);
2958 operands[2] = replace_equiv_address_nv (op2, addr2);
2959 operands[3] = addr1;
2960 operands[4] = addr2;
2961 })
2962
2963 (define_insn "*cmpstr<mode>"
2964 [(clobber (match_operand:P 0 "register_operand" "=d"))
2965 (clobber (match_operand:P 1 "register_operand" "=d"))
2966 (set (reg:CCU CC_REGNUM)
2967 (compare:CCU (mem:BLK (match_operand:P 2 "register_operand" "0"))
2968 (mem:BLK (match_operand:P 3 "register_operand" "1"))))
2969 (use (reg:SI 0))]
2970 ""
2971 "clst\t%0,%1\;jo\t.-4"
2972 [(set_attr "length" "8")
2973 (set_attr "type" "vs")])
2974
2975 ;
2976 ; movstr instruction pattern.
2977 ;
2978
2979 (define_expand "movstr"
2980 [(match_operand 0 "register_operand" "")
2981 (match_operand 1 "memory_operand" "")
2982 (match_operand 2 "memory_operand" "")]
2983 ""
2984 {
2985 if (TARGET_64BIT)
2986 emit_insn (gen_movstrdi (operands[0], operands[1], operands[2]));
2987 else
2988 emit_insn (gen_movstrsi (operands[0], operands[1], operands[2]));
2989 DONE;
2990 })
2991
2992 (define_expand "movstr<P:mode>"
2993 [(set (reg:SI 0) (const_int 0))
2994 (parallel
2995 [(clobber (match_dup 3))
2996 (set (match_operand:BLK 1 "memory_operand" "")
2997 (match_operand:BLK 2 "memory_operand" ""))
2998 (set (match_operand:P 0 "register_operand" "")
2999 (unspec:P [(match_dup 1)
3000 (match_dup 2)
3001 (reg:SI 0)] UNSPEC_MVST))
3002 (clobber (reg:CC CC_REGNUM))])]
3003 ""
3004 {
3005 rtx addr1, addr2;
3006
3007 if (TARGET_VX && optimize_function_for_speed_p (cfun))
3008 {
3009 s390_expand_vec_movstr (operands[0], operands[1], operands[2]);
3010 DONE;
3011 }
3012
3013 addr1 = gen_reg_rtx (Pmode);
3014 addr2 = gen_reg_rtx (Pmode);
3015
3016 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3017 emit_move_insn (addr2, force_operand (XEXP (operands[2], 0), NULL_RTX));
3018 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3019 operands[2] = replace_equiv_address_nv (operands[2], addr2);
3020 operands[3] = addr2;
3021 })
3022
3023 (define_insn "*movstr"
3024 [(clobber (match_operand:P 2 "register_operand" "=d"))
3025 (set (mem:BLK (match_operand:P 1 "register_operand" "0"))
3026 (mem:BLK (match_operand:P 3 "register_operand" "2")))
3027 (set (match_operand:P 0 "register_operand" "=d")
3028 (unspec:P [(mem:BLK (match_dup 1))
3029 (mem:BLK (match_dup 3))
3030 (reg:SI 0)] UNSPEC_MVST))
3031 (clobber (reg:CC CC_REGNUM))]
3032 ""
3033 "mvst\t%1,%2\;jo\t.-4"
3034 [(set_attr "length" "8")
3035 (set_attr "type" "vs")])
3036
3037
3038 ;
3039 ; movmemM instruction pattern(s).
3040 ;
3041
3042 (define_expand "movmem<mode>"
3043 [(set (match_operand:BLK 0 "memory_operand" "") ; destination
3044 (match_operand:BLK 1 "memory_operand" "")) ; source
3045 (use (match_operand:GPR 2 "general_operand" "")) ; count
3046 (match_operand 3 "" "")]
3047 ""
3048 {
3049 if (s390_expand_movmem (operands[0], operands[1], operands[2]))
3050 DONE;
3051 else
3052 FAIL;
3053 })
3054
3055 ; Move a block that is up to 256 bytes in length.
3056 ; The block length is taken as (operands[2] % 256) + 1.
3057
3058 (define_expand "movmem_short"
3059 [(parallel
3060 [(set (match_operand:BLK 0 "memory_operand" "")
3061 (match_operand:BLK 1 "memory_operand" ""))
3062 (use (match_operand 2 "nonmemory_operand" ""))
3063 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3064 (clobber (match_dup 3))])]
3065 ""
3066 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3067
3068 (define_insn "*movmem_short"
3069 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3070 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q"))
3071 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3072 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3073 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3074 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3075 "#"
3076 [(set_attr "type" "cs")
3077 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3078
3079 (define_split
3080 [(set (match_operand:BLK 0 "memory_operand" "")
3081 (match_operand:BLK 1 "memory_operand" ""))
3082 (use (match_operand 2 "const_int_operand" ""))
3083 (use (match_operand 3 "immediate_operand" ""))
3084 (clobber (scratch))]
3085 "reload_completed"
3086 [(parallel
3087 [(set (match_dup 0) (match_dup 1))
3088 (use (match_dup 2))])]
3089 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3090
3091 (define_split
3092 [(set (match_operand:BLK 0 "memory_operand" "")
3093 (match_operand:BLK 1 "memory_operand" ""))
3094 (use (match_operand 2 "register_operand" ""))
3095 (use (match_operand 3 "memory_operand" ""))
3096 (clobber (scratch))]
3097 "reload_completed"
3098 [(parallel
3099 [(unspec [(match_dup 2) (match_dup 3)
3100 (const_int 0)] UNSPEC_EXECUTE)
3101 (set (match_dup 0) (match_dup 1))
3102 (use (const_int 1))])]
3103 "")
3104
3105 (define_split
3106 [(set (match_operand:BLK 0 "memory_operand" "")
3107 (match_operand:BLK 1 "memory_operand" ""))
3108 (use (match_operand 2 "register_operand" ""))
3109 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3110 (clobber (scratch))]
3111 "TARGET_Z10 && reload_completed"
3112 [(parallel
3113 [(unspec [(match_dup 2) (const_int 0)
3114 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3115 (set (match_dup 0) (match_dup 1))
3116 (use (const_int 1))])]
3117 "operands[3] = gen_label_rtx ();")
3118
3119 (define_split
3120 [(set (match_operand:BLK 0 "memory_operand" "")
3121 (match_operand:BLK 1 "memory_operand" ""))
3122 (use (match_operand 2 "register_operand" ""))
3123 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3124 (clobber (match_operand 3 "register_operand" ""))]
3125 "reload_completed && TARGET_CPU_ZARCH"
3126 [(set (match_dup 3) (label_ref (match_dup 4)))
3127 (parallel
3128 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3129 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3130 (set (match_dup 0) (match_dup 1))
3131 (use (const_int 1))])]
3132 "operands[4] = gen_label_rtx ();")
3133
3134 ; Move a block of arbitrary length.
3135
3136 (define_expand "movmem_long"
3137 [(parallel
3138 [(clobber (match_dup 2))
3139 (clobber (match_dup 3))
3140 (set (match_operand:BLK 0 "memory_operand" "")
3141 (match_operand:BLK 1 "memory_operand" ""))
3142 (use (match_operand 2 "general_operand" ""))
3143 (use (match_dup 3))
3144 (clobber (reg:CC CC_REGNUM))])]
3145 ""
3146 {
3147 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3148 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3149 rtx reg0 = gen_reg_rtx (dreg_mode);
3150 rtx reg1 = gen_reg_rtx (dreg_mode);
3151 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3152 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3153 rtx len0 = gen_lowpart (Pmode, reg0);
3154 rtx len1 = gen_lowpart (Pmode, reg1);
3155
3156 emit_clobber (reg0);
3157 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3158 emit_move_insn (len0, operands[2]);
3159
3160 emit_clobber (reg1);
3161 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3162 emit_move_insn (len1, operands[2]);
3163
3164 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3165 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3166 operands[2] = reg0;
3167 operands[3] = reg1;
3168 })
3169
3170 (define_insn "*movmem_long"
3171 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3172 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3173 (set (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3174 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0)))
3175 (use (match_dup 2))
3176 (use (match_dup 3))
3177 (clobber (reg:CC CC_REGNUM))]
3178 "TARGET_64BIT || !TARGET_ZARCH"
3179 "mvcle\t%0,%1,0\;jo\t.-4"
3180 [(set_attr "length" "8")
3181 (set_attr "type" "vs")])
3182
3183 (define_insn "*movmem_long_31z"
3184 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3185 (clobber (match_operand:TI 1 "register_operand" "=d"))
3186 (set (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3187 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4)))
3188 (use (match_dup 2))
3189 (use (match_dup 3))
3190 (clobber (reg:CC CC_REGNUM))]
3191 "!TARGET_64BIT && TARGET_ZARCH"
3192 "mvcle\t%0,%1,0\;jo\t.-4"
3193 [(set_attr "length" "8")
3194 (set_attr "type" "vs")])
3195
3196
3197 ;
3198 ; Test data class.
3199 ;
3200
3201 (define_expand "signbit<mode>2"
3202 [(set (reg:CCZ CC_REGNUM)
3203 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3204 (match_dup 2)]
3205 UNSPEC_TDC_INSN))
3206 (set (match_operand:SI 0 "register_operand" "=d")
3207 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3208 "TARGET_HARD_FLOAT"
3209 {
3210 operands[2] = GEN_INT (S390_TDC_SIGNBIT_SET);
3211 })
3212
3213 (define_expand "isinf<mode>2"
3214 [(set (reg:CCZ CC_REGNUM)
3215 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
3216 (match_dup 2)]
3217 UNSPEC_TDC_INSN))
3218 (set (match_operand:SI 0 "register_operand" "=d")
3219 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CC_TO_INT))]
3220 "TARGET_HARD_FLOAT"
3221 {
3222 operands[2] = GEN_INT (S390_TDC_INFINITY);
3223 })
3224
3225 ; This extracts CC into a GPR properly shifted. The actual IPM
3226 ; instruction will be issued by reload. The constraint of operand 1
3227 ; forces reload to use a GPR. So reload will issue a movcc insn for
3228 ; copying CC into a GPR first.
3229 (define_insn_and_split "*cc_to_int"
3230 [(set (match_operand:SI 0 "nonimmediate_operand" "=d")
3231 (unspec:SI [(match_operand 1 "register_operand" "0")]
3232 UNSPEC_CC_TO_INT))]
3233 "operands != NULL"
3234 "#"
3235 "reload_completed"
3236 [(set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 28)))])
3237
3238 ; This insn is used to generate all variants of the Test Data Class
3239 ; instruction, namely tcxb, tcdb, and tceb. The insn's first operand
3240 ; is the register to be tested and the second one is the bit mask
3241 ; specifying the required test(s).
3242 ;
3243 ; tcxb, tcdb, tceb, tdcxt, tdcdt, tdcet
3244 (define_insn "*TDC_insn_<mode>"
3245 [(set (reg:CCZ CC_REGNUM)
3246 (unspec:CCZ [(match_operand:FP_ALL 0 "register_operand" "f")
3247 (match_operand:SI 1 "const_int_operand")] UNSPEC_TDC_INSN))]
3248 "TARGET_HARD_FLOAT"
3249 "t<_d>c<xde><bt>\t%0,%1"
3250 [(set_attr "op_type" "RXE")
3251 (set_attr "type" "fsimp<mode>")])
3252
3253
3254
3255 ;
3256 ; setmemM instruction pattern(s).
3257 ;
3258
3259 (define_expand "setmem<mode>"
3260 [(set (match_operand:BLK 0 "memory_operand" "")
3261 (match_operand:QI 2 "general_operand" ""))
3262 (use (match_operand:GPR 1 "general_operand" ""))
3263 (match_operand 3 "" "")]
3264 ""
3265 "s390_expand_setmem (operands[0], operands[1], operands[2]); DONE;")
3266
3267 ; Clear a block that is up to 256 bytes in length.
3268 ; The block length is taken as (operands[1] % 256) + 1.
3269
3270 (define_expand "clrmem_short"
3271 [(parallel
3272 [(set (match_operand:BLK 0 "memory_operand" "")
3273 (const_int 0))
3274 (use (match_operand 1 "nonmemory_operand" ""))
3275 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3276 (clobber (match_dup 2))
3277 (clobber (reg:CC CC_REGNUM))])]
3278 ""
3279 "operands[2] = gen_rtx_SCRATCH (Pmode);")
3280
3281 (define_insn "*clrmem_short"
3282 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
3283 (const_int 0))
3284 (use (match_operand 1 "nonmemory_operand" "n,a,a,a"))
3285 (use (match_operand 2 "immediate_operand" "X,R,X,X"))
3286 (clobber (match_scratch:P 3 "=X,X,X,&a"))
3287 (clobber (reg:CC CC_REGNUM))]
3288 "(GET_MODE (operands[1]) == Pmode || GET_MODE (operands[1]) == VOIDmode)"
3289 "#"
3290 [(set_attr "type" "cs")
3291 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3292
3293 (define_split
3294 [(set (match_operand:BLK 0 "memory_operand" "")
3295 (const_int 0))
3296 (use (match_operand 1 "const_int_operand" ""))
3297 (use (match_operand 2 "immediate_operand" ""))
3298 (clobber (scratch))
3299 (clobber (reg:CC CC_REGNUM))]
3300 "reload_completed"
3301 [(parallel
3302 [(set (match_dup 0) (const_int 0))
3303 (use (match_dup 1))
3304 (clobber (reg:CC CC_REGNUM))])]
3305 "operands[1] = GEN_INT ((INTVAL (operands[1]) & 0xff) + 1);")
3306
3307 (define_split
3308 [(set (match_operand:BLK 0 "memory_operand" "")
3309 (const_int 0))
3310 (use (match_operand 1 "register_operand" ""))
3311 (use (match_operand 2 "memory_operand" ""))
3312 (clobber (scratch))
3313 (clobber (reg:CC CC_REGNUM))]
3314 "reload_completed"
3315 [(parallel
3316 [(unspec [(match_dup 1) (match_dup 2)
3317 (const_int 0)] UNSPEC_EXECUTE)
3318 (set (match_dup 0) (const_int 0))
3319 (use (const_int 1))
3320 (clobber (reg:CC CC_REGNUM))])]
3321 "")
3322
3323 (define_split
3324 [(set (match_operand:BLK 0 "memory_operand" "")
3325 (const_int 0))
3326 (use (match_operand 1 "register_operand" ""))
3327 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3328 (clobber (scratch))
3329 (clobber (reg:CC CC_REGNUM))]
3330 "TARGET_Z10 && reload_completed"
3331 [(parallel
3332 [(unspec [(match_dup 1) (const_int 0)
3333 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3334 (set (match_dup 0) (const_int 0))
3335 (use (const_int 1))
3336 (clobber (reg:CC CC_REGNUM))])]
3337 "operands[3] = gen_label_rtx ();")
3338
3339 (define_split
3340 [(set (match_operand:BLK 0 "memory_operand" "")
3341 (const_int 0))
3342 (use (match_operand 1 "register_operand" ""))
3343 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3344 (clobber (match_operand 2 "register_operand" ""))
3345 (clobber (reg:CC CC_REGNUM))]
3346 "reload_completed && TARGET_CPU_ZARCH"
3347 [(set (match_dup 2) (label_ref (match_dup 3)))
3348 (parallel
3349 [(unspec [(match_dup 1) (mem:BLK (match_dup 2))
3350 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
3351 (set (match_dup 0) (const_int 0))
3352 (use (const_int 1))
3353 (clobber (reg:CC CC_REGNUM))])]
3354 "operands[3] = gen_label_rtx ();")
3355
3356 ; Initialize a block of arbitrary length with (operands[2] % 256).
3357
3358 (define_expand "setmem_long_<P:mode>"
3359 [(parallel
3360 [(clobber (match_dup 1))
3361 (set (match_operand:BLK 0 "memory_operand" "")
3362 (unspec:BLK [(match_operand:P 2 "setmem_operand" "")
3363 (match_dup 4)] UNSPEC_REPLICATE_BYTE))
3364 (use (match_dup 3))
3365 (clobber (reg:CC CC_REGNUM))])]
3366 ""
3367 {
3368 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3369 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3370 rtx reg0 = gen_reg_rtx (dreg_mode);
3371 rtx reg1 = gen_reg_rtx (dreg_mode);
3372 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3373 rtx len0 = gen_lowpart (Pmode, reg0);
3374
3375 emit_clobber (reg0);
3376 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3377 emit_move_insn (len0, operands[1]);
3378
3379 emit_move_insn (reg1, const0_rtx);
3380
3381 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3382 operands[1] = reg0;
3383 operands[3] = reg1;
3384 operands[4] = gen_lowpart (Pmode, operands[1]);
3385 })
3386
3387 ; Patterns for 31 bit + Esa and 64 bit + Zarch.
3388
3389 (define_insn "*setmem_long"
3390 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3391 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3392 (unspec:BLK [(match_operand:P 2 "setmem_operand" "Y")
3393 (subreg:P (match_dup 3) <modesize>)]
3394 UNSPEC_REPLICATE_BYTE))
3395 (use (match_operand:<DBL> 1 "register_operand" "d"))
3396 (clobber (reg:CC CC_REGNUM))]
3397 "TARGET_64BIT || !TARGET_ZARCH"
3398 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3399 [(set_attr "length" "8")
3400 (set_attr "type" "vs")])
3401
3402 (define_insn "*setmem_long_and"
3403 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3404 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
3405 (unspec:BLK [(zero_extend:P (match_operand:QI 2 "setmem_operand" "Y"))
3406 (subreg:P (match_dup 3) <modesize>)]
3407 UNSPEC_REPLICATE_BYTE))
3408 (use (match_operand:<DBL> 1 "register_operand" "d"))
3409 (clobber (reg:CC CC_REGNUM))]
3410 "(TARGET_64BIT || !TARGET_ZARCH)"
3411 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3412 [(set_attr "length" "8")
3413 (set_attr "type" "vs")])
3414
3415 ; Variants for 31 bit + Zarch, necessary because of the odd in-register offsets
3416 ; of the SImode subregs.
3417
3418 (define_insn "*setmem_long_31z"
3419 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3420 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3421 (unspec:BLK [(match_operand:SI 2 "setmem_operand" "Y")
3422 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3423 (use (match_operand:TI 1 "register_operand" "d"))
3424 (clobber (reg:CC CC_REGNUM))]
3425 "!TARGET_64BIT && TARGET_ZARCH"
3426 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3427 [(set_attr "length" "8")
3428 (set_attr "type" "vs")])
3429
3430 (define_insn "*setmem_long_and_31z"
3431 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3432 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3433 (unspec:BLK [(zero_extend:SI (match_operand:QI 2 "setmem_operand" "Y"))
3434 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3435 (use (match_operand:TI 1 "register_operand" "d"))
3436 (clobber (reg:CC CC_REGNUM))]
3437 "(!TARGET_64BIT && TARGET_ZARCH)"
3438 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3439 [(set_attr "length" "8")
3440 (set_attr "type" "vs")])
3441
3442 ;
3443 ; cmpmemM instruction pattern(s).
3444 ;
3445
3446 (define_expand "cmpmemsi"
3447 [(set (match_operand:SI 0 "register_operand" "")
3448 (compare:SI (match_operand:BLK 1 "memory_operand" "")
3449 (match_operand:BLK 2 "memory_operand" "") ) )
3450 (use (match_operand:SI 3 "general_operand" ""))
3451 (use (match_operand:SI 4 "" ""))]
3452 ""
3453 {
3454 if (s390_expand_cmpmem (operands[0], operands[1],
3455 operands[2], operands[3]))
3456 DONE;
3457 else
3458 FAIL;
3459 })
3460
3461 ; Compare a block that is up to 256 bytes in length.
3462 ; The block length is taken as (operands[2] % 256) + 1.
3463
3464 (define_expand "cmpmem_short"
3465 [(parallel
3466 [(set (reg:CCU CC_REGNUM)
3467 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3468 (match_operand:BLK 1 "memory_operand" "")))
3469 (use (match_operand 2 "nonmemory_operand" ""))
3470 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3471 (clobber (match_dup 3))])]
3472 ""
3473 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3474
3475 (define_insn "*cmpmem_short"
3476 [(set (reg:CCU CC_REGNUM)
3477 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
3478 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
3479 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3480 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3481 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3482 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3483 "#"
3484 [(set_attr "type" "cs")
3485 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3486
3487 (define_split
3488 [(set (reg:CCU CC_REGNUM)
3489 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3490 (match_operand:BLK 1 "memory_operand" "")))
3491 (use (match_operand 2 "const_int_operand" ""))
3492 (use (match_operand 3 "immediate_operand" ""))
3493 (clobber (scratch))]
3494 "reload_completed"
3495 [(parallel
3496 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3497 (use (match_dup 2))])]
3498 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3499
3500 (define_split
3501 [(set (reg:CCU CC_REGNUM)
3502 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3503 (match_operand:BLK 1 "memory_operand" "")))
3504 (use (match_operand 2 "register_operand" ""))
3505 (use (match_operand 3 "memory_operand" ""))
3506 (clobber (scratch))]
3507 "reload_completed"
3508 [(parallel
3509 [(unspec [(match_dup 2) (match_dup 3)
3510 (const_int 0)] UNSPEC_EXECUTE)
3511 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3512 (use (const_int 1))])]
3513 "")
3514
3515 (define_split
3516 [(set (reg:CCU CC_REGNUM)
3517 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3518 (match_operand:BLK 1 "memory_operand" "")))
3519 (use (match_operand 2 "register_operand" ""))
3520 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3521 (clobber (scratch))]
3522 "TARGET_Z10 && reload_completed"
3523 [(parallel
3524 [(unspec [(match_dup 2) (const_int 0)
3525 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3526 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3527 (use (const_int 1))])]
3528 "operands[4] = gen_label_rtx ();")
3529
3530 (define_split
3531 [(set (reg:CCU CC_REGNUM)
3532 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3533 (match_operand:BLK 1 "memory_operand" "")))
3534 (use (match_operand 2 "register_operand" ""))
3535 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3536 (clobber (match_operand 3 "register_operand" ""))]
3537 "reload_completed && TARGET_CPU_ZARCH"
3538 [(set (match_dup 3) (label_ref (match_dup 4)))
3539 (parallel
3540 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3541 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3542 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3543 (use (const_int 1))])]
3544 "operands[4] = gen_label_rtx ();")
3545
3546 ; Compare a block of arbitrary length.
3547
3548 (define_expand "cmpmem_long"
3549 [(parallel
3550 [(clobber (match_dup 2))
3551 (clobber (match_dup 3))
3552 (set (reg:CCU CC_REGNUM)
3553 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3554 (match_operand:BLK 1 "memory_operand" "")))
3555 (use (match_operand 2 "general_operand" ""))
3556 (use (match_dup 3))])]
3557 ""
3558 {
3559 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3560 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3561 rtx reg0 = gen_reg_rtx (dreg_mode);
3562 rtx reg1 = gen_reg_rtx (dreg_mode);
3563 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3564 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3565 rtx len0 = gen_lowpart (Pmode, reg0);
3566 rtx len1 = gen_lowpart (Pmode, reg1);
3567
3568 emit_clobber (reg0);
3569 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3570 emit_move_insn (len0, operands[2]);
3571
3572 emit_clobber (reg1);
3573 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3574 emit_move_insn (len1, operands[2]);
3575
3576 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3577 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3578 operands[2] = reg0;
3579 operands[3] = reg1;
3580 })
3581
3582 (define_insn "*cmpmem_long"
3583 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3584 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3585 (set (reg:CCU CC_REGNUM)
3586 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3587 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
3588 (use (match_dup 2))
3589 (use (match_dup 3))]
3590 "TARGET_64BIT || !TARGET_ZARCH"
3591 "clcle\t%0,%1,0\;jo\t.-4"
3592 [(set_attr "length" "8")
3593 (set_attr "type" "vs")])
3594
3595 (define_insn "*cmpmem_long_31z"
3596 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3597 (clobber (match_operand:TI 1 "register_operand" "=d"))
3598 (set (reg:CCU CC_REGNUM)
3599 (compare:CCU (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3600 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4))))
3601 (use (match_dup 2))
3602 (use (match_dup 3))]
3603 "!TARGET_64BIT && TARGET_ZARCH"
3604 "clcle\t%0,%1,0\;jo\t.-4"
3605 [(set_attr "op_type" "NN")
3606 (set_attr "type" "vs")
3607 (set_attr "length" "8")])
3608
3609 ; Convert CCUmode condition code to integer.
3610 ; Result is zero if EQ, positive if LTU, negative if GTU.
3611
3612 (define_insn_and_split "cmpint"
3613 [(set (match_operand:SI 0 "register_operand" "=d")
3614 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3615 UNSPEC_STRCMPCC_TO_INT))
3616 (clobber (reg:CC CC_REGNUM))]
3617 ""
3618 "#"
3619 "reload_completed"
3620 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3621 (parallel
3622 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
3623 (clobber (reg:CC CC_REGNUM))])])
3624
3625 (define_insn_and_split "*cmpint_cc"
3626 [(set (reg CC_REGNUM)
3627 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3628 UNSPEC_STRCMPCC_TO_INT)
3629 (const_int 0)))
3630 (set (match_operand:SI 0 "register_operand" "=d")
3631 (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT))]
3632 "s390_match_ccmode (insn, CCSmode)"
3633 "#"
3634 "&& reload_completed"
3635 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3636 (parallel
3637 [(set (match_dup 2) (match_dup 3))
3638 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
3639 {
3640 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
3641 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3642 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3643 })
3644
3645 (define_insn_and_split "*cmpint_sign"
3646 [(set (match_operand:DI 0 "register_operand" "=d")
3647 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3648 UNSPEC_STRCMPCC_TO_INT)))
3649 (clobber (reg:CC CC_REGNUM))]
3650 "TARGET_ZARCH"
3651 "#"
3652 "&& reload_completed"
3653 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3654 (parallel
3655 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
3656 (clobber (reg:CC CC_REGNUM))])])
3657
3658 (define_insn_and_split "*cmpint_sign_cc"
3659 [(set (reg CC_REGNUM)
3660 (compare (ashiftrt:DI (ashift:DI (subreg:DI
3661 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3662 UNSPEC_STRCMPCC_TO_INT) 0)
3663 (const_int 32)) (const_int 32))
3664 (const_int 0)))
3665 (set (match_operand:DI 0 "register_operand" "=d")
3666 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT)))]
3667 "s390_match_ccmode (insn, CCSmode) && TARGET_ZARCH"
3668 "#"
3669 "&& reload_completed"
3670 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3671 (parallel
3672 [(set (match_dup 2) (match_dup 3))
3673 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
3674 {
3675 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
3676 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3677 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3678 })
3679
3680
3681 ;;
3682 ;;- Conversion instructions.
3683 ;;
3684
3685 (define_insn "*sethighpartsi"
3686 [(set (match_operand:SI 0 "register_operand" "=d,d")
3687 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
3688 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3689 (clobber (reg:CC CC_REGNUM))]
3690 ""
3691 "@
3692 icm\t%0,%2,%S1
3693 icmy\t%0,%2,%S1"
3694 [(set_attr "op_type" "RS,RSY")
3695 (set_attr "cpu_facility" "*,longdisp")
3696 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3697
3698 (define_insn "*sethighpartdi_64"
3699 [(set (match_operand:DI 0 "register_operand" "=d")
3700 (unspec:DI [(match_operand:BLK 1 "s_operand" "S")
3701 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
3702 (clobber (reg:CC CC_REGNUM))]
3703 "TARGET_ZARCH"
3704 "icmh\t%0,%2,%S1"
3705 [(set_attr "op_type" "RSY")
3706 (set_attr "z10prop" "z10_super")])
3707
3708 (define_insn "*sethighpartdi_31"
3709 [(set (match_operand:DI 0 "register_operand" "=d,d")
3710 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
3711 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3712 (clobber (reg:CC CC_REGNUM))]
3713 "!TARGET_ZARCH"
3714 "@
3715 icm\t%0,%2,%S1
3716 icmy\t%0,%2,%S1"
3717 [(set_attr "op_type" "RS,RSY")
3718 (set_attr "cpu_facility" "*,longdisp")
3719 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3720
3721 ;
3722 ; extv instruction patterns
3723 ;
3724
3725 ; FIXME: This expander needs to be converted from DI to GPR as well
3726 ; after resolving some issues with it.
3727
3728 (define_expand "extzv"
3729 [(parallel
3730 [(set (match_operand:DI 0 "register_operand" "=d")
3731 (zero_extract:DI
3732 (match_operand:DI 1 "register_operand" "d")
3733 (match_operand 2 "const_int_operand" "") ; size
3734 (match_operand 3 "const_int_operand" ""))) ; start
3735 (clobber (reg:CC CC_REGNUM))])]
3736 "TARGET_Z10"
3737 {
3738 if (! EXTRACT_ARGS_IN_RANGE (INTVAL (operands[2]), INTVAL (operands[3]), 64))
3739 FAIL;
3740 /* Starting with zEC12 there is risbgn not clobbering CC. */
3741 if (TARGET_ZEC12)
3742 {
3743 emit_move_insn (operands[0],
3744 gen_rtx_ZERO_EXTRACT (DImode,
3745 operands[1],
3746 operands[2],
3747 operands[3]));
3748 DONE;
3749 }
3750 })
3751
3752 (define_insn "*extzv<mode><clobbercc_or_nocc>"
3753 [(set (match_operand:GPR 0 "register_operand" "=d")
3754 (zero_extract:GPR
3755 (match_operand:GPR 1 "register_operand" "d")
3756 (match_operand 2 "const_int_operand" "") ; size
3757 (match_operand 3 "const_int_operand" ""))) ; start
3758 ]
3759 "<z10_or_zEC12_cond>
3760 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[2]), INTVAL (operands[3]),
3761 GET_MODE_BITSIZE (<MODE>mode))"
3762 "<risbg_n>\t%0,%1,64-%2,128+63,<bitoff_plus>%3+%2" ; dst, src, start, end, shift
3763 [(set_attr "op_type" "RIE")
3764 (set_attr "z10prop" "z10_super_E1")])
3765
3766 ; 64 bit: (a & -16) | ((b >> 8) & 15)
3767 (define_insn "*extzvdi<clobbercc_or_nocc>_lshiftrt"
3768 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
3769 (match_operand 1 "const_int_operand" "") ; size
3770 (match_operand 2 "const_int_operand" "")) ; start
3771 (lshiftrt:DI (match_operand:DI 3 "register_operand" "d")
3772 (match_operand:DI 4 "nonzero_shift_count_operand" "")))]
3773 "<z10_or_zEC12_cond>
3774 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), INTVAL (operands[2]), 64)
3775 && 64 - UINTVAL (operands[4]) >= UINTVAL (operands[1])"
3776 "<risbg_n>\t%0,%3,%2,%2+%1-1,128-%2-%1-%4"
3777 [(set_attr "op_type" "RIE")
3778 (set_attr "z10prop" "z10_super_E1")])
3779
3780 ; 32 bit: (a & -16) | ((b >> 8) & 15)
3781 (define_insn "*<risbg_n>_ior_and_sr_ze"
3782 [(set (match_operand:SI 0 "register_operand" "=d")
3783 (ior:SI (and:SI
3784 (match_operand:SI 1 "register_operand" "0")
3785 (match_operand:SI 2 "const_int_operand" ""))
3786 (subreg:SI
3787 (zero_extract:DI
3788 (match_operand:DI 3 "register_operand" "d")
3789 (match_operand 4 "const_int_operand" "") ; size
3790 (match_operand 5 "const_int_operand" "")) ; start
3791 4)))]
3792 "<z10_or_zEC12_cond>
3793 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[4]), INTVAL (operands[5]), 64)
3794 && UINTVAL (operands[2]) == (~(0ULL) << UINTVAL (operands[4]))"
3795 "<risbg_n>\t%0,%3,64-%4,63,%4+%5"
3796 [(set_attr "op_type" "RIE")
3797 (set_attr "z10prop" "z10_super_E1")])
3798
3799 ; ((int)foo >> 10) & 1;
3800 (define_insn "*extract1bitdi<clobbercc_or_nocc>"
3801 [(set (match_operand:DI 0 "register_operand" "=d")
3802 (ne:DI (zero_extract:DI
3803 (match_operand:DI 1 "register_operand" "d")
3804 (const_int 1) ; size
3805 (match_operand 2 "const_int_operand" "")) ; start
3806 (const_int 0)))]
3807 "<z10_or_zEC12_cond>
3808 && EXTRACT_ARGS_IN_RANGE (1, INTVAL (operands[2]), 64)"
3809 "<risbg_n>\t%0,%1,64-1,128+63,%2+1" ; dst, src, start, end, shift
3810 [(set_attr "op_type" "RIE")
3811 (set_attr "z10prop" "z10_super_E1")])
3812
3813 (define_insn "*<risbg_n>_and_subregdi_rotr"
3814 [(set (match_operand:DI 0 "register_operand" "=d")
3815 (and:DI (subreg:DI
3816 (rotate:SINT (match_operand:SINT 1 "register_operand" "d")
3817 (match_operand:SINT 2 "const_int_operand" "")) 0)
3818 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3819 "<z10_or_zEC12_cond>
3820 && UINTVAL (operands[3]) < (1ULL << (UINTVAL (operands[2]) & 0x3f))"
3821 "<risbg_n>\t%0,%1,%s3,128+%e3,<bitoff_plus>%2" ; dst, src, start, end, shift
3822 [(set_attr "op_type" "RIE")
3823 (set_attr "z10prop" "z10_super_E1")])
3824
3825 (define_insn "*<risbg_n>_and_subregdi_rotl"
3826 [(set (match_operand:DI 0 "register_operand" "=d")
3827 (and:DI (subreg:DI
3828 (rotate:SINT (match_operand:SINT 1 "register_operand" "d")
3829 (match_operand:SINT 2 "const_int_operand" "")) 0)
3830 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3831 "<z10_or_zEC12_cond>
3832 && !(UINTVAL (operands[3]) & ((1ULL << (UINTVAL (operands[2]) & 0x3f)) - 1))"
3833 "<risbg_n>\t%0,%1,%s3,128+%e3,%2" ; dst, src, start, end, shift
3834 [(set_attr "op_type" "RIE")
3835 (set_attr "z10prop" "z10_super_E1")])
3836
3837 (define_insn "*<risbg_n>_di_and_rot"
3838 [(set (match_operand:DI 0 "register_operand" "=d")
3839 (and:DI (rotate:DI (match_operand:DI 1 "register_operand" "d")
3840 (match_operand:DI 2 "const_int_operand" ""))
3841 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3842 "<z10_or_zEC12_cond>"
3843 "<risbg_n>\t%0,%1,%s3,128+%e3,%2" ; dst, src, start, end, shift
3844 [(set_attr "op_type" "RIE")
3845 (set_attr "z10prop" "z10_super_E1")])
3846
3847 (define_insn_and_split "*pre_z10_extzv<mode>"
3848 [(set (match_operand:GPR 0 "register_operand" "=d")
3849 (zero_extract:GPR (match_operand:QI 1 "s_operand" "S")
3850 (match_operand 2 "nonzero_shift_count_operand" "")
3851 (const_int 0)))
3852 (clobber (reg:CC CC_REGNUM))]
3853 "!TARGET_Z10"
3854 "#"
3855 "&& reload_completed"
3856 [(parallel
3857 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3858 (clobber (reg:CC CC_REGNUM))])
3859 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3860 {
3861 int bitsize = INTVAL (operands[2]);
3862 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3863 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3864
3865 operands[1] = adjust_address (operands[1], BLKmode, 0);
3866 set_mem_size (operands[1], size);
3867 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3868 operands[3] = GEN_INT (mask);
3869 })
3870
3871 (define_insn_and_split "*pre_z10_extv<mode>"
3872 [(set (match_operand:GPR 0 "register_operand" "=d")
3873 (sign_extract:GPR (match_operand:QI 1 "s_operand" "S")
3874 (match_operand 2 "nonzero_shift_count_operand" "")
3875 (const_int 0)))
3876 (clobber (reg:CC CC_REGNUM))]
3877 ""
3878 "#"
3879 "&& reload_completed"
3880 [(parallel
3881 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3882 (clobber (reg:CC CC_REGNUM))])
3883 (parallel
3884 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3885 (clobber (reg:CC CC_REGNUM))])]
3886 {
3887 int bitsize = INTVAL (operands[2]);
3888 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3889 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3890
3891 operands[1] = adjust_address (operands[1], BLKmode, 0);
3892 set_mem_size (operands[1], size);
3893 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3894 operands[3] = GEN_INT (mask);
3895 })
3896
3897 ;
3898 ; insv instruction patterns
3899 ;
3900
3901 (define_expand "insv"
3902 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3903 (match_operand 1 "const_int_operand" "")
3904 (match_operand 2 "const_int_operand" ""))
3905 (match_operand 3 "general_operand" ""))]
3906 ""
3907 {
3908 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3909 DONE;
3910 FAIL;
3911 })
3912
3913
3914 ; The normal RTL expansion will never generate a zero_extract where
3915 ; the location operand isn't word mode. However, we do this in the
3916 ; back-end when generating atomic operations. See s390_two_part_insv.
3917 (define_insn "*insv<mode><clobbercc_or_nocc>"
3918 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3919 (match_operand 1 "const_int_operand" "I") ; size
3920 (match_operand 2 "const_int_operand" "I")) ; pos
3921 (match_operand:GPR 3 "nonimmediate_operand" "d"))]
3922 "<z10_or_zEC12_cond>
3923 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), INTVAL (operands[2]),
3924 GET_MODE_BITSIZE (<MODE>mode))
3925 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3926 "<risbg_n>\t%0,%3,<bitoff_plus>%2,<bitoff_plus>%2+%1-1,<bitsize>-%2-%1"
3927 [(set_attr "op_type" "RIE")
3928 (set_attr "z10prop" "z10_super_E1")])
3929
3930 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3931 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3932 (define_insn "*insv<mode><clobbercc_or_nocc>_noshift"
3933 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d")
3934 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d,0")
3935 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3936 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0,d")
3937 (match_operand:GPR 4 "const_int_operand" ""))))]
3938 "<z10_or_zEC12_cond> && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3939 "@
3940 <risbg_n>\t%0,%1,%<bfstart>2,%<bfend>2,0
3941 <risbg_n>\t%0,%3,%<bfstart>4,%<bfend>4,0"
3942 [(set_attr "op_type" "RIE")
3943 (set_attr "z10prop" "z10_super_E1")])
3944
3945 (define_insn "*insv_z10_noshift_cc"
3946 [(set (reg CC_REGNUM)
3947 (compare
3948 (ior:DI
3949 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,0")
3950 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3951 (and:DI (match_operand:DI 3 "nonimmediate_operand" "0,d")
3952 (match_operand:DI 4 "const_int_operand" "")))
3953 (const_int 0)))
3954 (set (match_operand:DI 0 "nonimmediate_operand" "=d,d")
3955 (ior:DI (and:DI (match_dup 1) (match_dup 2))
3956 (and:DI (match_dup 3) (match_dup 4))))]
3957 "TARGET_Z10 && s390_match_ccmode (insn, CCSmode)
3958 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3959 "@
3960 risbg\t%0,%1,%s2,%e2,0
3961 risbg\t%0,%3,%s4,%e4,0"
3962 [(set_attr "op_type" "RIE")
3963 (set_attr "z10prop" "z10_super_E1")])
3964
3965 (define_insn "*insv_z10_noshift_cconly"
3966 [(set
3967 (reg CC_REGNUM)
3968 (compare
3969 (ior:DI
3970 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,0")
3971 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3972 (and:DI (match_operand:DI 3 "nonimmediate_operand" "0,d")
3973 (match_operand:DI 4 "const_int_operand" "")))
3974 (const_int 0)))
3975 (clobber (match_scratch:DI 0 "=d,d"))]
3976 "TARGET_Z10 && s390_match_ccmode (insn, CCSmode)
3977 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3978 "@
3979 risbg\t%0,%1,%s2,%e2,0
3980 risbg\t%0,%3,%s4,%e4,0"
3981 [(set_attr "op_type" "RIE")
3982 (set_attr "z10prop" "z10_super_E1")])
3983
3984 ; Implement appending Y on the left of S bits of X
3985 ; x = (y << s) | (x & ((1 << s) - 1))
3986 (define_insn "*insv<mode><clobbercc_or_nocc>_appendbitsleft"
3987 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3988 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3989 (match_operand:GPR 2 "immediate_operand" ""))
3990 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3991 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3992 "<z10_or_zEC12_cond>
3993 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3994 "<risbg_n>\t%0,%3,<bitoff>,64-%4-1,%4"
3995 [(set_attr "op_type" "RIE")
3996 (set_attr "z10prop" "z10_super_E1")])
3997
3998 ; a = ((i32)a & -16777216) | (((ui32)b) >> 8)
3999 (define_insn "*<risbg_n>_<mode>_ior_and_lshiftrt"
4000 [(set (match_operand:GPR 0 "register_operand" "=d")
4001 (ior:GPR (and:GPR
4002 (match_operand:GPR 1 "register_operand" "0")
4003 (match_operand:GPR 2 "const_int_operand" ""))
4004 (lshiftrt:GPR
4005 (match_operand:GPR 3 "register_operand" "d")
4006 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
4007 "<z10_or_zEC12_cond> && UINTVAL (operands[2])
4008 == (~(0ULL) << (GET_MODE_BITSIZE (<MODE>mode) - UINTVAL (operands[4])))"
4009 "<risbg_n>\t%0,%3,<bitoff_plus>%4,63,64-%4"
4010 [(set_attr "op_type" "RIE")
4011 (set_attr "z10prop" "z10_super_E1")])
4012
4013 ; (ui32)(((ui64)x) >> 48) | ((i32)y & -65536);
4014 (define_insn "*<risbg_n>_sidi_ior_and_lshiftrt"
4015 [(set (match_operand:SI 0 "register_operand" "=d")
4016 (ior:SI (and:SI
4017 (match_operand:SI 1 "register_operand" "0")
4018 (match_operand:SI 2 "const_int_operand" ""))
4019 (subreg:SI
4020 (lshiftrt:DI
4021 (match_operand:DI 3 "register_operand" "d")
4022 (match_operand:DI 4 "nonzero_shift_count_operand" "")) 4)))]
4023 "<z10_or_zEC12_cond>
4024 && UINTVAL (operands[2]) == ~(~(0ULL) >> UINTVAL (operands[4]))"
4025 "<risbg_n>\t%0,%3,%4,63,64-%4"
4026 [(set_attr "op_type" "RIE")
4027 (set_attr "z10prop" "z10_super_E1")])
4028
4029 ; (ui32)(((ui64)x) >> 12) & -4
4030 (define_insn "*trunc_sidi_and_subreg_lshrt<clobbercc_or_nocc>"
4031 [(set (match_operand:SI 0 "register_operand" "=d")
4032 (and:SI
4033 (subreg:SI (lshiftrt:DI
4034 (match_operand:DI 1 "register_operand" "d")
4035 (match_operand:DI 2 "nonzero_shift_count_operand" "")) 4)
4036 (match_operand:SI 3 "contiguous_bitmask_nowrap_operand" "")))]
4037 "<z10_or_zEC12_cond>"
4038 "<risbg_n>\t%0,%1,%t3,128+%f3,64-%2"
4039 [(set_attr "op_type" "RIE")
4040 (set_attr "z10prop" "z10_super_E1")])
4041
4042 ; z = (x << c) | (y >> d) with (x << c) and (y >> d) not overlapping after shifting
4043 ; -> z = y >> d; z = (x << c) | (z & ((1 << c) - 1))
4044 ; -> z = y >> d; z = risbg;
4045
4046 (define_split
4047 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
4048 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
4049 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4050 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
4051 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
4052 "TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
4053 [(set (match_dup 6)
4054 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
4055 (set (match_dup 0)
4056 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
4057 (ashift:GPR (match_dup 3) (match_dup 4))))]
4058 {
4059 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
4060 if (reg_overlap_mentioned_p (operands[0], operands[3]))
4061 {
4062 if (!can_create_pseudo_p ())
4063 FAIL;
4064 operands[6] = gen_reg_rtx (<MODE>mode);
4065 }
4066 else
4067 operands[6] = operands[0];
4068 })
4069
4070 (define_split
4071 [(parallel
4072 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
4073 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
4074 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4075 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
4076 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
4077 (clobber (reg:CC CC_REGNUM))])]
4078 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
4079 [(set (match_dup 6)
4080 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
4081 (parallel
4082 [(set (match_dup 0)
4083 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
4084 (ashift:GPR (match_dup 3) (match_dup 4))))
4085 (clobber (reg:CC CC_REGNUM))])]
4086 {
4087 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
4088 if (reg_overlap_mentioned_p (operands[0], operands[3]))
4089 {
4090 if (!can_create_pseudo_p ())
4091 FAIL;
4092 operands[6] = gen_reg_rtx (<MODE>mode);
4093 }
4094 else
4095 operands[6] = operands[0];
4096 })
4097
4098 (define_insn "*r<noxa>sbg_<mode>_noshift"
4099 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4100 (IXOR:GPR
4101 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
4102 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4103 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4104 (clobber (reg:CC CC_REGNUM))]
4105 "TARGET_Z10"
4106 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
4107 [(set_attr "op_type" "RIE")])
4108
4109 (define_insn "*r<noxa>sbg_di_rotl"
4110 [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
4111 (IXOR:DI
4112 (and:DI
4113 (rotate:DI
4114 (match_operand:DI 1 "nonimmediate_operand" "d")
4115 (match_operand:DI 3 "const_int_operand" ""))
4116 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
4117 (match_operand:DI 4 "nonimmediate_operand" "0")))
4118 (clobber (reg:CC CC_REGNUM))]
4119 "TARGET_Z10"
4120 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%b3"
4121 [(set_attr "op_type" "RIE")])
4122
4123 (define_insn "*r<noxa>sbg_<mode>_srl_bitmask"
4124 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4125 (IXOR:GPR
4126 (and:GPR
4127 (lshiftrt:GPR
4128 (match_operand:GPR 1 "nonimmediate_operand" "d")
4129 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4130 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4131 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4132 (clobber (reg:CC CC_REGNUM))]
4133 "TARGET_Z10
4134 && s390_extzv_shift_ok (<bitsize>, 64 - INTVAL (operands[3]),
4135 INTVAL (operands[2]))"
4136 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,64-%3"
4137 [(set_attr "op_type" "RIE")])
4138
4139 (define_insn "*r<noxa>sbg_<mode>_sll_bitmask"
4140 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4141 (IXOR:GPR
4142 (and:GPR
4143 (ashift:GPR
4144 (match_operand:GPR 1 "nonimmediate_operand" "d")
4145 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4146 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4147 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4148 (clobber (reg:CC CC_REGNUM))]
4149 "TARGET_Z10
4150 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[3]),
4151 INTVAL (operands[2]))"
4152 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%3"
4153 [(set_attr "op_type" "RIE")])
4154
4155 ;; unsigned {int,long} a, b
4156 ;; a = a | (b << const_int)
4157 ;; a = a ^ (b << const_int)
4158 (define_insn "*r<noxa>sbg_<mode>_sll"
4159 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4160 (IXOR:GPR
4161 (ashift:GPR
4162 (match_operand:GPR 1 "nonimmediate_operand" "d")
4163 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4164 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4165 (clobber (reg:CC CC_REGNUM))]
4166 "TARGET_Z10"
4167 "r<noxa>sbg\t%0,%1,<bitoff>,63-%2,%2"
4168 [(set_attr "op_type" "RIE")])
4169
4170 ;; unsigned {int,long} a, b
4171 ;; a = a | (b >> const_int)
4172 ;; a = a ^ (b >> const_int)
4173 (define_insn "*r<noxa>sbg_<mode>_srl"
4174 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4175 (IXOR:GPR
4176 (lshiftrt:GPR
4177 (match_operand:GPR 1 "nonimmediate_operand" "d")
4178 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4179 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4180 (clobber (reg:CC CC_REGNUM))]
4181 "TARGET_Z10"
4182 "r<noxa>sbg\t%0,%1,<bitoff_plus>%2,63,64-%2"
4183 [(set_attr "op_type" "RIE")])
4184
4185 ;; These two are generated by combine for s.bf &= val.
4186 ;; ??? For bitfields smaller than 32-bits, we wind up with SImode
4187 ;; shifts and ands, which results in some truly awful patterns
4188 ;; including subregs of operations. Rather unnecessisarily, IMO.
4189 ;; Instead of
4190 ;;
4191 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4192 ;; (const_int 24 [0x18])
4193 ;; (const_int 0 [0]))
4194 ;; (subreg:DI (and:SI (subreg:SI (lshiftrt:DI (reg/v:DI 50 [ s ])
4195 ;; (const_int 40 [0x28])) 4)
4196 ;; (reg:SI 4 %r4 [ y+4 ])) 0))
4197 ;;
4198 ;; we should instead generate
4199 ;;
4200 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4201 ;; (const_int 24 [0x18])
4202 ;; (const_int 0 [0]))
4203 ;; (and:DI (lshiftrt:DI (reg/v:DI 50 [ s ])
4204 ;; (const_int 40 [0x28]))
4205 ;; (subreg:DI (reg:SI 4 %r4 [ y+4 ]) 0)))
4206 ;;
4207 ;; by noticing that we can push down the outer paradoxical subreg
4208 ;; into the operation.
4209
4210 (define_insn "*insv_rnsbg_noshift"
4211 [(set (zero_extract:DI
4212 (match_operand:DI 0 "nonimmediate_operand" "+d")
4213 (match_operand 1 "const_int_operand" "")
4214 (match_operand 2 "const_int_operand" ""))
4215 (and:DI
4216 (match_dup 0)
4217 (match_operand:DI 3 "nonimmediate_operand" "d")))
4218 (clobber (reg:CC CC_REGNUM))]
4219 "TARGET_Z10
4220 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), INTVAL (operands[2]), 64)
4221 && INTVAL (operands[1]) + INTVAL (operands[2]) == 64"
4222 "rnsbg\t%0,%3,%2,63,0"
4223 [(set_attr "op_type" "RIE")])
4224
4225 (define_insn "*insv_rnsbg_srl"
4226 [(set (zero_extract:DI
4227 (match_operand:DI 0 "nonimmediate_operand" "+d")
4228 (match_operand 1 "const_int_operand" "")
4229 (match_operand 2 "const_int_operand" ""))
4230 (and:DI
4231 (lshiftrt:DI
4232 (match_dup 0)
4233 (match_operand 3 "const_int_operand" ""))
4234 (match_operand:DI 4 "nonimmediate_operand" "d")))
4235 (clobber (reg:CC CC_REGNUM))]
4236 "TARGET_Z10
4237 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), INTVAL (operands[2]), 64)
4238 && INTVAL (operands[3]) == 64 - INTVAL (operands[1]) - INTVAL (operands[2])"
4239 "rnsbg\t%0,%4,%2,%2+%1-1,%3"
4240 [(set_attr "op_type" "RIE")])
4241
4242 (define_insn "*insv<mode>_mem_reg"
4243 [(set (zero_extract:W (match_operand:QI 0 "memory_operand" "+Q,S")
4244 (match_operand 1 "const_int_operand" "n,n")
4245 (const_int 0))
4246 (match_operand:W 2 "register_operand" "d,d"))]
4247 "EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), 0, 64)
4248 && INTVAL (operands[1]) > 0
4249 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4250 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4251 {
4252 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4253
4254 operands[1] = GEN_INT ((1ul << size) - 1);
4255 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
4256 : "stcmy\t%2,%1,%S0";
4257 }
4258 [(set_attr "op_type" "RS,RSY")
4259 (set_attr "cpu_facility" "*,longdisp")
4260 (set_attr "z10prop" "z10_super,z10_super")])
4261
4262 (define_insn "*insvdi_mem_reghigh"
4263 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+S")
4264 (match_operand 1 "const_int_operand" "n")
4265 (const_int 0))
4266 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
4267 (const_int 32)))]
4268 "TARGET_ZARCH
4269 && EXTRACT_ARGS_IN_RANGE (INTVAL (operands[1]), 0, 64)
4270 && INTVAL (operands[1]) > 0
4271 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4272 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4273 {
4274 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4275
4276 operands[1] = GEN_INT ((1ul << size) - 1);
4277 return "stcmh\t%2,%1,%S0";
4278 }
4279 [(set_attr "op_type" "RSY")
4280 (set_attr "z10prop" "z10_super")])
4281
4282 (define_insn "*insvdi_reg_imm"
4283 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4284 (const_int 16)
4285 (match_operand 1 "const_int_operand" "n"))
4286 (match_operand:DI 2 "const_int_operand" "n"))]
4287 "TARGET_ZARCH
4288 && EXTRACT_ARGS_IN_RANGE (16, INTVAL (operands[1]), 64)
4289 && INTVAL (operands[1]) >= 0
4290 && INTVAL (operands[1]) < BITS_PER_WORD
4291 && INTVAL (operands[1]) % 16 == 0"
4292 {
4293 switch (BITS_PER_WORD - INTVAL (operands[1]))
4294 {
4295 case 64: return "iihh\t%0,%x2"; break;
4296 case 48: return "iihl\t%0,%x2"; break;
4297 case 32: return "iilh\t%0,%x2"; break;
4298 case 16: return "iill\t%0,%x2"; break;
4299 default: gcc_unreachable();
4300 }
4301 }
4302 [(set_attr "op_type" "RI")
4303 (set_attr "z10prop" "z10_super_E1")])
4304
4305 ; Update the left-most 32 bit of a DI.
4306 (define_insn "*insv_h_di_reg_extimm"
4307 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4308 (const_int 32)
4309 (const_int 0))
4310 (match_operand:DI 1 "const_int_operand" "n"))]
4311 "TARGET_EXTIMM"
4312 "iihf\t%0,%o1"
4313 [(set_attr "op_type" "RIL")
4314 (set_attr "z10prop" "z10_fwd_E1")])
4315
4316 ; Update the right-most 32 bit of a DI.
4317 (define_insn "*insv_l_di_reg_extimm"
4318 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4319 (const_int 32)
4320 (const_int 32))
4321 (match_operand:DI 1 "const_int_operand" "n"))]
4322 "TARGET_EXTIMM"
4323 "iilf\t%0,%o1"
4324 [(set_attr "op_type" "RIL")
4325 (set_attr "z10prop" "z10_fwd_A1")])
4326
4327 ;
4328 ; extendsidi2 instruction pattern(s).
4329 ;
4330
4331 (define_expand "extendsidi2"
4332 [(set (match_operand:DI 0 "register_operand" "")
4333 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4334 ""
4335 {
4336 if (!TARGET_ZARCH)
4337 {
4338 emit_clobber (operands[0]);
4339 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
4340 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
4341 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
4342 DONE;
4343 }
4344 })
4345
4346 (define_insn "*extendsidi2"
4347 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4348 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4349 "TARGET_ZARCH"
4350 "@
4351 lgfr\t%0,%1
4352 lgf\t%0,%1
4353 lgfrl\t%0,%1"
4354 [(set_attr "op_type" "RRE,RXY,RIL")
4355 (set_attr "type" "*,*,larl")
4356 (set_attr "cpu_facility" "*,*,z10")
4357 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4358
4359 ;
4360 ; extend(hi|qi)(si|di)2 instruction pattern(s).
4361 ;
4362
4363 (define_expand "extend<HQI:mode><DSI:mode>2"
4364 [(set (match_operand:DSI 0 "register_operand" "")
4365 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4366 ""
4367 {
4368 if (<DSI:MODE>mode == DImode && !TARGET_ZARCH)
4369 {
4370 rtx tmp = gen_reg_rtx (SImode);
4371 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
4372 emit_insn (gen_extendsidi2 (operands[0], tmp));
4373 DONE;
4374 }
4375 else if (!TARGET_EXTIMM)
4376 {
4377 rtx bitcount = GEN_INT (<DSI:bitsize> - <HQI:bitsize>);
4378
4379 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
4380 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
4381 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
4382 DONE;
4383 }
4384 })
4385
4386 ;
4387 ; extendhidi2 instruction pattern(s).
4388 ;
4389
4390 (define_insn "*extendhidi2_extimm"
4391 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4392 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,T,b")))]
4393 "TARGET_ZARCH && TARGET_EXTIMM"
4394 "@
4395 lghr\t%0,%1
4396 lgh\t%0,%1
4397 lghrl\t%0,%1"
4398 [(set_attr "op_type" "RRE,RXY,RIL")
4399 (set_attr "type" "*,*,larl")
4400 (set_attr "cpu_facility" "extimm,extimm,z10")
4401 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4402
4403 (define_insn "*extendhidi2"
4404 [(set (match_operand:DI 0 "register_operand" "=d")
4405 (sign_extend:DI (match_operand:HI 1 "memory_operand" "T")))]
4406 "TARGET_ZARCH"
4407 "lgh\t%0,%1"
4408 [(set_attr "op_type" "RXY")
4409 (set_attr "z10prop" "z10_super_E1")])
4410
4411 ;
4412 ; extendhisi2 instruction pattern(s).
4413 ;
4414
4415 (define_insn "*extendhisi2_extimm"
4416 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
4417 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
4418 "TARGET_EXTIMM"
4419 "@
4420 lhr\t%0,%1
4421 lh\t%0,%1
4422 lhy\t%0,%1
4423 lhrl\t%0,%1"
4424 [(set_attr "op_type" "RRE,RX,RXY,RIL")
4425 (set_attr "type" "*,*,*,larl")
4426 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")
4427 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,z10_super_E1")])
4428
4429 (define_insn "*extendhisi2"
4430 [(set (match_operand:SI 0 "register_operand" "=d,d")
4431 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
4432 "!TARGET_EXTIMM"
4433 "@
4434 lh\t%0,%1
4435 lhy\t%0,%1"
4436 [(set_attr "op_type" "RX,RXY")
4437 (set_attr "cpu_facility" "*,longdisp")
4438 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4439
4440 ;
4441 ; extendqi(si|di)2 instruction pattern(s).
4442 ;
4443
4444 ; lbr, lgbr, lb, lgb
4445 (define_insn "*extendqi<mode>2_extimm"
4446 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4447 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,T")))]
4448 "TARGET_EXTIMM"
4449 "@
4450 l<g>br\t%0,%1
4451 l<g>b\t%0,%1"
4452 [(set_attr "op_type" "RRE,RXY")
4453 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4454
4455 ; lb, lgb
4456 (define_insn "*extendqi<mode>2"
4457 [(set (match_operand:GPR 0 "register_operand" "=d")
4458 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "T")))]
4459 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
4460 "l<g>b\t%0,%1"
4461 [(set_attr "op_type" "RXY")
4462 (set_attr "z10prop" "z10_super_E1")])
4463
4464 (define_insn_and_split "*extendqi<mode>2_short_displ"
4465 [(set (match_operand:GPR 0 "register_operand" "=d")
4466 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
4467 (clobber (reg:CC CC_REGNUM))]
4468 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
4469 "#"
4470 "&& reload_completed"
4471 [(parallel
4472 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
4473 (clobber (reg:CC CC_REGNUM))])
4474 (parallel
4475 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
4476 (clobber (reg:CC CC_REGNUM))])]
4477 {
4478 operands[1] = adjust_address (operands[1], BLKmode, 0);
4479 set_mem_size (operands[1], GET_MODE_SIZE (QImode));
4480 operands[2] = GEN_INT (<GPR:bitsize> - BITS_PER_UNIT);
4481 })
4482
4483 ;
4484 ; zero_extendsidi2 instruction pattern(s).
4485 ;
4486
4487 (define_expand "zero_extendsidi2"
4488 [(set (match_operand:DI 0 "register_operand" "")
4489 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4490 ""
4491 {
4492 if (!TARGET_ZARCH)
4493 {
4494 emit_clobber (operands[0]);
4495 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
4496 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
4497 DONE;
4498 }
4499 })
4500
4501 (define_insn "*zero_extendsidi2"
4502 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4503 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4504 "TARGET_ZARCH"
4505 "@
4506 llgfr\t%0,%1
4507 llgf\t%0,%1
4508 llgfrl\t%0,%1"
4509 [(set_attr "op_type" "RRE,RXY,RIL")
4510 (set_attr "type" "*,*,larl")
4511 (set_attr "cpu_facility" "*,*,z10")
4512 (set_attr "z10prop" "z10_fwd_E1,z10_fwd_A3,z10_fwd_A3")])
4513
4514 ;
4515 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
4516 ;
4517
4518 (define_insn "*llgt_sidi"
4519 [(set (match_operand:DI 0 "register_operand" "=d")
4520 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4521 (const_int 2147483647)))]
4522 "TARGET_ZARCH"
4523 "llgt\t%0,%1"
4524 [(set_attr "op_type" "RXE")
4525 (set_attr "z10prop" "z10_super_E1")])
4526
4527 (define_insn_and_split "*llgt_sidi_split"
4528 [(set (match_operand:DI 0 "register_operand" "=d")
4529 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4530 (const_int 2147483647)))
4531 (clobber (reg:CC CC_REGNUM))]
4532 "TARGET_ZARCH"
4533 "#"
4534 "&& reload_completed"
4535 [(set (match_dup 0)
4536 (and:DI (subreg:DI (match_dup 1) 0)
4537 (const_int 2147483647)))]
4538 "")
4539
4540 (define_insn "*llgt_sisi"
4541 [(set (match_operand:SI 0 "register_operand" "=d,d")
4542 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,T")
4543 (const_int 2147483647)))]
4544 "TARGET_ZARCH"
4545 "@
4546 llgtr\t%0,%1
4547 llgt\t%0,%1"
4548 [(set_attr "op_type" "RRE,RXE")
4549 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4550
4551 (define_insn "*llgt_didi"
4552 [(set (match_operand:DI 0 "register_operand" "=d,d")
4553 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
4554 (const_int 2147483647)))]
4555 "TARGET_ZARCH"
4556 "@
4557 llgtr\t%0,%1
4558 llgt\t%0,%N1"
4559 [(set_attr "op_type" "RRE,RXE")
4560 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4561
4562 (define_split
4563 [(set (match_operand:DSI 0 "register_operand" "")
4564 (and:DSI (match_operand:DSI 1 "nonimmediate_operand" "")
4565 (const_int 2147483647)))
4566 (clobber (reg:CC CC_REGNUM))]
4567 "TARGET_ZARCH && reload_completed"
4568 [(set (match_dup 0)
4569 (and:DSI (match_dup 1)
4570 (const_int 2147483647)))]
4571 "")
4572
4573 ;
4574 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
4575 ;
4576
4577 (define_expand "zero_extend<mode>di2"
4578 [(set (match_operand:DI 0 "register_operand" "")
4579 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4580 ""
4581 {
4582 if (!TARGET_ZARCH)
4583 {
4584 rtx tmp = gen_reg_rtx (SImode);
4585 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
4586 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
4587 DONE;
4588 }
4589 else if (!TARGET_EXTIMM)
4590 {
4591 rtx bitcount = GEN_INT (64 - <HQI:bitsize>);
4592 operands[1] = gen_lowpart (DImode, operands[1]);
4593 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
4594 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
4595 DONE;
4596 }
4597 })
4598
4599 (define_expand "zero_extend<mode>si2"
4600 [(set (match_operand:SI 0 "register_operand" "")
4601 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4602 ""
4603 {
4604 if (!TARGET_EXTIMM)
4605 {
4606 operands[1] = gen_lowpart (SImode, operands[1]);
4607 emit_insn (gen_andsi3 (operands[0], operands[1],
4608 GEN_INT ((1 << <HQI:bitsize>) - 1)));
4609 DONE;
4610 }
4611 })
4612
4613 ; llhrl, llghrl
4614 (define_insn "*zero_extendhi<mode>2_z10"
4615 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4616 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,T,b")))]
4617 "TARGET_Z10"
4618 "@
4619 ll<g>hr\t%0,%1
4620 ll<g>h\t%0,%1
4621 ll<g>hrl\t%0,%1"
4622 [(set_attr "op_type" "RXY,RRE,RIL")
4623 (set_attr "type" "*,*,larl")
4624 (set_attr "cpu_facility" "*,*,z10")
4625 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3,z10_fwd_A3")])
4626
4627 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
4628 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
4629 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4630 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,T")))]
4631 "TARGET_EXTIMM"
4632 "@
4633 ll<g><hc>r\t%0,%1
4634 ll<g><hc>\t%0,%1"
4635 [(set_attr "op_type" "RRE,RXY")
4636 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3")])
4637
4638 ; llgh, llgc
4639 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
4640 [(set (match_operand:GPR 0 "register_operand" "=d")
4641 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "T")))]
4642 "TARGET_ZARCH && !TARGET_EXTIMM"
4643 "llg<hc>\t%0,%1"
4644 [(set_attr "op_type" "RXY")
4645 (set_attr "z10prop" "z10_fwd_A3")])
4646
4647 (define_insn_and_split "*zero_extendhisi2_31"
4648 [(set (match_operand:SI 0 "register_operand" "=&d")
4649 (zero_extend:SI (match_operand:HI 1 "s_operand" "S")))
4650 (clobber (reg:CC CC_REGNUM))]
4651 "!TARGET_ZARCH"
4652 "#"
4653 "&& reload_completed"
4654 [(set (match_dup 0) (const_int 0))
4655 (parallel
4656 [(set (strict_low_part (match_dup 2)) (match_dup 1))
4657 (clobber (reg:CC CC_REGNUM))])]
4658 "operands[2] = gen_lowpart (HImode, operands[0]);")
4659
4660 (define_insn_and_split "*zero_extendqisi2_31"
4661 [(set (match_operand:SI 0 "register_operand" "=&d")
4662 (zero_extend:SI (match_operand:QI 1 "memory_operand" "T")))]
4663 "!TARGET_ZARCH"
4664 "#"
4665 "&& reload_completed"
4666 [(set (match_dup 0) (const_int 0))
4667 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4668 "operands[2] = gen_lowpart (QImode, operands[0]);")
4669
4670 ;
4671 ; zero_extendqihi2 instruction pattern(s).
4672 ;
4673
4674 (define_expand "zero_extendqihi2"
4675 [(set (match_operand:HI 0 "register_operand" "")
4676 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4677 "TARGET_ZARCH && !TARGET_EXTIMM"
4678 {
4679 operands[1] = gen_lowpart (HImode, operands[1]);
4680 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
4681 DONE;
4682 })
4683
4684 (define_insn "*zero_extendqihi2_64"
4685 [(set (match_operand:HI 0 "register_operand" "=d")
4686 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4687 "TARGET_ZARCH && !TARGET_EXTIMM"
4688 "llgc\t%0,%1"
4689 [(set_attr "op_type" "RXY")
4690 (set_attr "z10prop" "z10_fwd_A3")])
4691
4692 (define_insn_and_split "*zero_extendqihi2_31"
4693 [(set (match_operand:HI 0 "register_operand" "=&d")
4694 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4695 "!TARGET_ZARCH"
4696 "#"
4697 "&& reload_completed"
4698 [(set (match_dup 0) (const_int 0))
4699 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4700 "operands[2] = gen_lowpart (QImode, operands[0]);")
4701
4702 ;
4703 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
4704 ;
4705
4706 (define_expand "fixuns_truncdddi2"
4707 [(parallel
4708 [(set (match_operand:DI 0 "register_operand" "")
4709 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
4710 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4711 (clobber (reg:CC CC_REGNUM))])]
4712
4713 "TARGET_HARD_DFP"
4714 {
4715 if (!TARGET_Z196)
4716 {
4717 rtx_code_label *label1 = gen_label_rtx ();
4718 rtx_code_label *label2 = gen_label_rtx ();
4719 rtx temp = gen_reg_rtx (TDmode);
4720 REAL_VALUE_TYPE cmp, sub;
4721
4722 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4723 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4724
4725 /* 2^63 can't be represented as 64bit DFP number with full precision. The
4726 solution is doing the check and the subtraction in TD mode and using a
4727 TD -> DI convert afterwards. */
4728 emit_insn (gen_extendddtd2 (temp, operands[1]));
4729 temp = force_reg (TDmode, temp);
4730 emit_cmp_and_jump_insns (temp,
4731 const_double_from_real_value (cmp, TDmode),
4732 LT, NULL_RTX, VOIDmode, 0, label1);
4733 emit_insn (gen_subtd3 (temp, temp,
4734 const_double_from_real_value (sub, TDmode)));
4735 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4736 GEN_INT (DFP_RND_TOWARD_MINF)));
4737 emit_jump (label2);
4738
4739 emit_label (label1);
4740 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1],
4741 GEN_INT (DFP_RND_TOWARD_0)));
4742 emit_label (label2);
4743 DONE;
4744 }
4745 })
4746
4747 (define_expand "fixuns_trunctddi2"
4748 [(parallel
4749 [(set (match_operand:DI 0 "register_operand" "")
4750 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))
4751 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4752 (clobber (reg:CC CC_REGNUM))])]
4753
4754 "TARGET_HARD_DFP"
4755 {
4756 if (!TARGET_Z196)
4757 {
4758 rtx_code_label *label1 = gen_label_rtx ();
4759 rtx_code_label *label2 = gen_label_rtx ();
4760 rtx temp = gen_reg_rtx (TDmode);
4761 REAL_VALUE_TYPE cmp, sub;
4762
4763 operands[1] = force_reg (TDmode, operands[1]);
4764 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4765 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4766
4767 emit_cmp_and_jump_insns (operands[1],
4768 const_double_from_real_value (cmp, TDmode),
4769 LT, NULL_RTX, VOIDmode, 0, label1);
4770 emit_insn (gen_subtd3 (temp, operands[1],
4771 const_double_from_real_value (sub, TDmode)));
4772 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4773 GEN_INT (DFP_RND_TOWARD_MINF)));
4774 emit_jump (label2);
4775
4776 emit_label (label1);
4777 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1],
4778 GEN_INT (DFP_RND_TOWARD_0)));
4779 emit_label (label2);
4780 DONE;
4781 }
4782 })
4783
4784 ;
4785 ; fixuns_trunc(sf|df|tf)(si|di)2 and fix_trunc(sf|df|tf)(si|di)2
4786 ; instruction pattern(s).
4787 ;
4788
4789 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
4790 [(parallel
4791 [(set (match_operand:GPR 0 "register_operand" "")
4792 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))
4793 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4794 (clobber (reg:CC CC_REGNUM))])]
4795 "TARGET_HARD_FLOAT"
4796 {
4797 if (!TARGET_Z196)
4798 {
4799 rtx_code_label *label1 = gen_label_rtx ();
4800 rtx_code_label *label2 = gen_label_rtx ();
4801 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
4802 REAL_VALUE_TYPE cmp, sub;
4803
4804 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
4805 real_2expN (&cmp, <GPR:bitsize> - 1, <BFP:MODE>mode);
4806 real_2expN (&sub, <GPR:bitsize>, <BFP:MODE>mode);
4807
4808 emit_cmp_and_jump_insns (operands[1],
4809 const_double_from_real_value (cmp, <BFP:MODE>mode),
4810 LT, NULL_RTX, VOIDmode, 0, label1);
4811 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
4812 const_double_from_real_value (sub, <BFP:MODE>mode)));
4813 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
4814 GEN_INT (BFP_RND_TOWARD_MINF)));
4815 emit_jump (label2);
4816
4817 emit_label (label1);
4818 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
4819 operands[1], GEN_INT (BFP_RND_TOWARD_0)));
4820 emit_label (label2);
4821 DONE;
4822 }
4823 })
4824
4825 ; fixuns_trunc(td|dd)si2 expander
4826 (define_expand "fixuns_trunc<mode>si2"
4827 [(parallel
4828 [(set (match_operand:SI 0 "register_operand" "")
4829 (unsigned_fix:SI (match_operand:DFP 1 "register_operand" "")))
4830 (unspec:SI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4831 (clobber (reg:CC CC_REGNUM))])]
4832 "TARGET_Z196 && TARGET_HARD_DFP"
4833 "")
4834
4835 ; fixuns_trunc(tf|df|sf|td|dd)(di|si)2 instruction patterns.
4836
4837 (define_insn "*fixuns_truncdfdi2_z13"
4838 [(set (match_operand:DI 0 "register_operand" "=d,v")
4839 (unsigned_fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4840 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4841 (clobber (reg:CC CC_REGNUM))]
4842 "TARGET_VX && TARGET_HARD_FLOAT"
4843 "@
4844 clgdbr\t%0,%h2,%1,0
4845 wclgdb\t%v0,%v1,0,%h2"
4846 [(set_attr "op_type" "RRF,VRR")
4847 (set_attr "type" "ftoi")])
4848
4849 ; clfebr, clfdbr, clfxbr, clgebr, clgdbr, clgxbr
4850 ; clfdtr, clfxtr, clgdtr, clgxtr
4851 (define_insn "*fixuns_trunc<FP:mode><GPR:mode>2_z196"
4852 [(set (match_operand:GPR 0 "register_operand" "=d")
4853 (unsigned_fix:GPR (match_operand:FP 1 "register_operand" "f")))
4854 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4855 (clobber (reg:CC CC_REGNUM))]
4856 "TARGET_Z196 && TARGET_HARD_FLOAT
4857 && (!TARGET_VX || <GPR:MODE>mode != DImode || <FP:MODE>mode != DFmode)"
4858 "cl<GPR:gf><FP:xde><FP:bt>r\t%0,%h2,%1,0"
4859 [(set_attr "op_type" "RRF")
4860 (set_attr "type" "ftoi")])
4861
4862 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
4863 [(set (match_operand:GPR 0 "register_operand" "")
4864 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
4865 "TARGET_HARD_FLOAT"
4866 {
4867 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
4868 GEN_INT (BFP_RND_TOWARD_0)));
4869 DONE;
4870 })
4871
4872 (define_insn "*fix_truncdfdi2_bfp_z13"
4873 [(set (match_operand:DI 0 "register_operand" "=d,v")
4874 (fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4875 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4876 (clobber (reg:CC CC_REGNUM))]
4877 "TARGET_VX && TARGET_HARD_FLOAT"
4878 "@
4879 cgdbr\t%0,%h2,%1
4880 wcgdb\t%v0,%v1,0,%h2"
4881 [(set_attr "op_type" "RRE,VRR")
4882 (set_attr "type" "ftoi")])
4883
4884 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
4885 (define_insn "*fix_trunc<BFP:mode><GPR:mode>2_bfp"
4886 [(set (match_operand:GPR 0 "register_operand" "=d")
4887 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4888 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4889 (clobber (reg:CC CC_REGNUM))]
4890 "TARGET_HARD_FLOAT
4891 && (!TARGET_VX || <GPR:MODE>mode != DImode || <BFP:MODE>mode != DFmode)"
4892 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
4893 [(set_attr "op_type" "RRE")
4894 (set_attr "type" "ftoi")])
4895
4896 (define_expand "fix_trunc<BFP:mode><GPR:mode>2_bfp"
4897 [(parallel
4898 [(set (match_operand:GPR 0 "register_operand" "=d")
4899 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4900 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4901 (clobber (reg:CC CC_REGNUM))])]
4902 "TARGET_HARD_FLOAT")
4903 ;
4904 ; fix_trunc(td|dd)di2 instruction pattern(s).
4905 ;
4906
4907 (define_expand "fix_trunc<mode>di2"
4908 [(set (match_operand:DI 0 "register_operand" "")
4909 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
4910 "TARGET_ZARCH && TARGET_HARD_DFP"
4911 {
4912 operands[1] = force_reg (<MODE>mode, operands[1]);
4913 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
4914 GEN_INT (DFP_RND_TOWARD_0)));
4915 DONE;
4916 })
4917
4918 ; cgxtr, cgdtr
4919 (define_insn "fix_trunc<DFP:mode>di2_dfp"
4920 [(set (match_operand:DI 0 "register_operand" "=d")
4921 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
4922 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
4923 (clobber (reg:CC CC_REGNUM))]
4924 "TARGET_ZARCH && TARGET_HARD_DFP"
4925 "cg<DFP:xde>tr\t%0,%h2,%1"
4926 [(set_attr "op_type" "RRF")
4927 (set_attr "type" "ftoidfp")])
4928
4929
4930 ;
4931 ; fix_trunctf(si|di)2 instruction pattern(s).
4932 ;
4933
4934 (define_expand "fix_trunctf<mode>2"
4935 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
4936 (fix:GPR (match_operand:TF 1 "register_operand" "")))
4937 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4938 (clobber (reg:CC CC_REGNUM))])]
4939 "TARGET_HARD_FLOAT"
4940 "")
4941
4942
4943 ;
4944 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4945 ;
4946
4947 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
4948 (define_insn "floatdi<mode>2"
4949 [(set (match_operand:FP 0 "register_operand" "=f,v")
4950 (float:FP (match_operand:DI 1 "register_operand" "d,v")))]
4951 "TARGET_ZARCH && TARGET_HARD_FLOAT"
4952 "@
4953 c<xde>g<bt>r\t%0,%1
4954 wcdgb\t%v0,%v1,0,0"
4955 [(set_attr "op_type" "RRE,VRR")
4956 (set_attr "type" "itof<mode>" )
4957 (set_attr "cpu_facility" "*,vec")
4958 (set_attr "enabled" "*,<DFDI>")])
4959
4960 ; cxfbr, cdfbr, cefbr
4961 (define_insn "floatsi<mode>2"
4962 [(set (match_operand:BFP 0 "register_operand" "=f")
4963 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
4964 "TARGET_HARD_FLOAT"
4965 "c<xde>fbr\t%0,%1"
4966 [(set_attr "op_type" "RRE")
4967 (set_attr "type" "itof<mode>" )])
4968
4969 ; cxftr, cdftr
4970 (define_insn "floatsi<mode>2"
4971 [(set (match_operand:DFP 0 "register_operand" "=f")
4972 (float:DFP (match_operand:SI 1 "register_operand" "d")))]
4973 "TARGET_Z196 && TARGET_HARD_FLOAT"
4974 "c<xde>ftr\t%0,0,%1,0"
4975 [(set_attr "op_type" "RRE")
4976 (set_attr "type" "itof<mode>" )])
4977
4978 ;
4979 ; floatuns(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4980 ;
4981
4982 (define_insn "*floatunsdidf2_z13"
4983 [(set (match_operand:DF 0 "register_operand" "=f,v")
4984 (unsigned_float:DF (match_operand:DI 1 "register_operand" "d,v")))]
4985 "TARGET_VX && TARGET_HARD_FLOAT"
4986 "@
4987 cdlgbr\t%0,0,%1,0
4988 wcdlgb\t%v0,%v1,0,0"
4989 [(set_attr "op_type" "RRE,VRR")
4990 (set_attr "type" "itofdf")])
4991
4992 ; cxlgbr, cdlgbr, celgbr, cxlgtr, cdlgtr
4993 ; cxlfbr, cdlfbr, celfbr, cxlftr, cdlftr
4994 (define_insn "*floatuns<GPR:mode><FP:mode>2"
4995 [(set (match_operand:FP 0 "register_operand" "=f")
4996 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "d")))]
4997 "TARGET_Z196 && TARGET_HARD_FLOAT
4998 && (!TARGET_VX || <FP:MODE>mode != DFmode || <GPR:MODE>mode != DImode)"
4999 "c<FP:xde>l<GPR:gf><FP:bt>r\t%0,0,%1,0"
5000 [(set_attr "op_type" "RRE")
5001 (set_attr "type" "itof<FP:mode>")])
5002
5003 (define_expand "floatuns<GPR:mode><FP:mode>2"
5004 [(set (match_operand:FP 0 "register_operand" "")
5005 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "")))]
5006 "TARGET_Z196 && TARGET_HARD_FLOAT")
5007
5008 ;
5009 ; truncdfsf2 instruction pattern(s).
5010 ;
5011
5012 (define_insn "truncdfsf2"
5013 [(set (match_operand:SF 0 "register_operand" "=f,v")
5014 (float_truncate:SF (match_operand:DF 1 "register_operand" "f,v")))]
5015 "TARGET_HARD_FLOAT"
5016 "@
5017 ledbr\t%0,%1
5018 wledb\t%v0,%v1,0,0" ; IEEE inexact exception not suppressed
5019 ; According to BFP rounding mode
5020 [(set_attr "op_type" "RRE,VRR")
5021 (set_attr "type" "ftruncdf")
5022 (set_attr "cpu_facility" "*,vec")])
5023
5024 ;
5025 ; trunctf(df|sf)2 instruction pattern(s).
5026 ;
5027
5028 ; ldxbr, lexbr
5029 (define_insn "trunctf<mode>2"
5030 [(set (match_operand:DSF 0 "register_operand" "=f")
5031 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
5032 (clobber (match_scratch:TF 2 "=f"))]
5033 "TARGET_HARD_FLOAT"
5034 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
5035 [(set_attr "length" "6")
5036 (set_attr "type" "ftrunctf")])
5037
5038 ;
5039 ; trunctddd2 and truncddsd2 instruction pattern(s).
5040 ;
5041
5042
5043 (define_expand "trunctddd2"
5044 [(parallel
5045 [(set (match_operand:DD 0 "register_operand" "")
5046 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
5047 (unspec:DI [(const_int DFP_RND_CURRENT)] UNSPEC_ROUND)
5048 (clobber (scratch:TD))])]
5049 "TARGET_HARD_DFP")
5050
5051 (define_insn "*trunctddd2"
5052 [(set (match_operand:DD 0 "register_operand" "=f")
5053 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
5054 (unspec:DI [(match_operand:DI 2 "const_mask_operand" "I")] UNSPEC_ROUND)
5055 (clobber (match_scratch:TD 3 "=f"))]
5056 "TARGET_HARD_DFP"
5057 "ldxtr\t%3,%2,%1,0\;ldr\t%0,%3"
5058 [(set_attr "length" "6")
5059 (set_attr "type" "ftruncdd")])
5060
5061 (define_insn "truncddsd2"
5062 [(set (match_operand:SD 0 "register_operand" "=f")
5063 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
5064 "TARGET_HARD_DFP"
5065 "ledtr\t%0,0,%1,0"
5066 [(set_attr "op_type" "RRF")
5067 (set_attr "type" "ftruncsd")])
5068
5069 (define_expand "trunctdsd2"
5070 [(parallel
5071 [(set (match_dup 3)
5072 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
5073 (unspec:DI [(const_int DFP_RND_PREP_FOR_SHORT_PREC)] UNSPEC_ROUND)
5074 (clobber (match_scratch:TD 2 ""))])
5075 (set (match_operand:SD 0 "register_operand" "")
5076 (float_truncate:SD (match_dup 3)))]
5077 "TARGET_HARD_DFP"
5078 {
5079 operands[3] = gen_reg_rtx (DDmode);
5080 })
5081
5082 ;
5083 ; extend(sf|df)(df|tf)2 instruction pattern(s).
5084 ;
5085
5086 (define_insn "*extendsfdf2_z13"
5087 [(set (match_operand:DF 0 "register_operand" "=f,f,v")
5088 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,R,v")))]
5089 "TARGET_VX && TARGET_HARD_FLOAT"
5090 "@
5091 ldebr\t%0,%1
5092 ldeb\t%0,%1
5093 wldeb\t%v0,%v1"
5094 [(set_attr "op_type" "RRE,RXE,VRR")
5095 (set_attr "type" "fsimpdf, floaddf,fsimpdf")])
5096
5097 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
5098 (define_insn "*extend<DSF:mode><BFP:mode>2"
5099 [(set (match_operand:BFP 0 "register_operand" "=f,f")
5100 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
5101 "TARGET_HARD_FLOAT
5102 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)
5103 && (!TARGET_VX || <BFP:MODE>mode != DFmode || <DSF:MODE>mode != SFmode)"
5104 "@
5105 l<BFP:xde><DSF:xde>br\t%0,%1
5106 l<BFP:xde><DSF:xde>b\t%0,%1"
5107 [(set_attr "op_type" "RRE,RXE")
5108 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
5109
5110 (define_expand "extend<DSF:mode><BFP:mode>2"
5111 [(set (match_operand:BFP 0 "register_operand" "")
5112 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "")))]
5113 "TARGET_HARD_FLOAT
5114 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)")
5115
5116 ;
5117 ; extendddtd2 and extendsddd2 instruction pattern(s).
5118 ;
5119
5120 (define_insn "extendddtd2"
5121 [(set (match_operand:TD 0 "register_operand" "=f")
5122 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
5123 "TARGET_HARD_DFP"
5124 "lxdtr\t%0,%1,0"
5125 [(set_attr "op_type" "RRF")
5126 (set_attr "type" "fsimptf")])
5127
5128 (define_insn "extendsddd2"
5129 [(set (match_operand:DD 0 "register_operand" "=f")
5130 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
5131 "TARGET_HARD_DFP"
5132 "ldetr\t%0,%1,0"
5133 [(set_attr "op_type" "RRF")
5134 (set_attr "type" "fsimptf")])
5135
5136 (define_expand "extendsdtd2"
5137 [(set (match_dup 2)
5138 (float_extend:DD (match_operand:SD 1 "register_operand" "")))
5139 (set (match_operand:TD 0 "register_operand" "")
5140 (float_extend:TD (match_dup 2)))]
5141 "TARGET_HARD_DFP"
5142 {
5143 operands[2] = gen_reg_rtx (DDmode);
5144 })
5145
5146 ; Binary Floating Point - load fp integer
5147
5148 ; Expanders for: floor, btrunc, round, ceil, and nearbyint
5149 ; For all of them the inexact exceptions are suppressed.
5150
5151 ; fiebra, fidbra, fixbra
5152 (define_insn "<FPINT:fpint_name><BFP:mode>2"
5153 [(set (match_operand:BFP 0 "register_operand" "=f")
5154 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5155 FPINT))]
5156 "TARGET_Z196"
5157 "fi<BFP:xde>bra\t%0,<FPINT:fpint_roundingmode>,%1,4"
5158 [(set_attr "op_type" "RRF")
5159 (set_attr "type" "fsimp<BFP:mode>")])
5160
5161 ; rint is supposed to raise an inexact exception so we can use the
5162 ; older instructions.
5163
5164 ; fiebr, fidbr, fixbr
5165 (define_insn "rint<BFP:mode>2"
5166 [(set (match_operand:BFP 0 "register_operand" "=f")
5167 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5168 UNSPEC_FPINT_RINT))]
5169 ""
5170 "fi<BFP:xde>br\t%0,0,%1"
5171 [(set_attr "op_type" "RRF")
5172 (set_attr "type" "fsimp<BFP:mode>")])
5173
5174
5175 ; Decimal Floating Point - load fp integer
5176
5177 ; fidtr, fixtr
5178 (define_insn "<FPINT:fpint_name><DFP:mode>2"
5179 [(set (match_operand:DFP 0 "register_operand" "=f")
5180 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5181 FPINT))]
5182 "TARGET_HARD_DFP"
5183 "fi<DFP:xde>tr\t%0,<FPINT:fpint_roundingmode>,%1,4"
5184 [(set_attr "op_type" "RRF")
5185 (set_attr "type" "fsimp<DFP:mode>")])
5186
5187 ; fidtr, fixtr
5188 (define_insn "rint<DFP:mode>2"
5189 [(set (match_operand:DFP 0 "register_operand" "=f")
5190 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5191 UNSPEC_FPINT_RINT))]
5192 "TARGET_HARD_DFP"
5193 "fi<DFP:xde>tr\t%0,0,%1,0"
5194 [(set_attr "op_type" "RRF")
5195 (set_attr "type" "fsimp<DFP:mode>")])
5196
5197 ;
5198 ; Binary <-> Decimal floating point trunc patterns
5199 ;
5200
5201 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
5202 [(set (reg:DFP_ALL FPR0_REGNUM)
5203 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5204 (use (reg:SI GPR0_REGNUM))
5205 (clobber (reg:CC CC_REGNUM))
5206 (clobber (reg:SI GPR1_REGNUM))]
5207 "TARGET_HARD_DFP"
5208 "pfpo")
5209
5210 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
5211 [(set (reg:BFP FPR0_REGNUM)
5212 (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5213 (use (reg:SI GPR0_REGNUM))
5214 (clobber (reg:CC CC_REGNUM))
5215 (clobber (reg:SI GPR1_REGNUM))]
5216 "TARGET_HARD_DFP"
5217 "pfpo")
5218
5219 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
5220 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5221 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5222 (parallel
5223 [(set (reg:DFP_ALL FPR0_REGNUM)
5224 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5225 (use (reg:SI GPR0_REGNUM))
5226 (clobber (reg:CC CC_REGNUM))
5227 (clobber (reg:SI GPR1_REGNUM))])
5228 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5229 (reg:DFP_ALL FPR0_REGNUM))]
5230 "TARGET_HARD_DFP
5231 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5232 {
5233 HOST_WIDE_INT flags;
5234
5235 flags = (PFPO_CONVERT |
5236 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5237 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5238
5239 operands[2] = GEN_INT (flags);
5240 })
5241
5242 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
5243 [(set (reg:DFP_ALL FPR4_REGNUM)
5244 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5245 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5246 (parallel
5247 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5248 (use (reg:SI GPR0_REGNUM))
5249 (clobber (reg:CC CC_REGNUM))
5250 (clobber (reg:SI GPR1_REGNUM))])
5251 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5252 "TARGET_HARD_DFP
5253 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
5254 {
5255 HOST_WIDE_INT flags;
5256
5257 flags = (PFPO_CONVERT |
5258 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5259 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5260
5261 operands[2] = GEN_INT (flags);
5262 })
5263
5264 ;
5265 ; Binary <-> Decimal floating point extend patterns
5266 ;
5267
5268 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
5269 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5270 (use (reg:SI GPR0_REGNUM))
5271 (clobber (reg:CC CC_REGNUM))
5272 (clobber (reg:SI GPR1_REGNUM))]
5273 "TARGET_HARD_DFP"
5274 "pfpo")
5275
5276 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
5277 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5278 (use (reg:SI GPR0_REGNUM))
5279 (clobber (reg:CC CC_REGNUM))
5280 (clobber (reg:SI GPR1_REGNUM))]
5281 "TARGET_HARD_DFP"
5282 "pfpo")
5283
5284 (define_expand "extend<BFP:mode><DFP_ALL:mode>2"
5285 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5286 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5287 (parallel
5288 [(set (reg:DFP_ALL FPR0_REGNUM)
5289 (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5290 (use (reg:SI GPR0_REGNUM))
5291 (clobber (reg:CC CC_REGNUM))
5292 (clobber (reg:SI GPR1_REGNUM))])
5293 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5294 (reg:DFP_ALL FPR0_REGNUM))]
5295 "TARGET_HARD_DFP
5296 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5297 {
5298 HOST_WIDE_INT flags;
5299
5300 flags = (PFPO_CONVERT |
5301 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5302 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5303
5304 operands[2] = GEN_INT (flags);
5305 })
5306
5307 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
5308 [(set (reg:DFP_ALL FPR4_REGNUM)
5309 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5310 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5311 (parallel
5312 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5313 (use (reg:SI GPR0_REGNUM))
5314 (clobber (reg:CC CC_REGNUM))
5315 (clobber (reg:SI GPR1_REGNUM))])
5316 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5317 "TARGET_HARD_DFP
5318 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
5319 {
5320 HOST_WIDE_INT flags;
5321
5322 flags = (PFPO_CONVERT |
5323 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5324 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5325
5326 operands[2] = GEN_INT (flags);
5327 })
5328
5329
5330 ;;
5331 ;; ARITHMETIC OPERATIONS
5332 ;;
5333 ; arithmetic operations set the ConditionCode,
5334 ; because of unpredictable Bits in Register for Halfword and Byte
5335 ; the ConditionCode can be set wrong in operations for Halfword and Byte
5336
5337 ;;
5338 ;;- Add instructions.
5339 ;;
5340
5341 ;
5342 ; addti3 instruction pattern(s).
5343 ;
5344
5345 (define_expand "addti3"
5346 [(parallel
5347 [(set (match_operand:TI 0 "register_operand" "")
5348 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5349 (match_operand:TI 2 "general_operand" "") ) )
5350 (clobber (reg:CC CC_REGNUM))])]
5351 "TARGET_ZARCH"
5352 {
5353 /* For z13 we have vaq which doesn't set CC. */
5354 if (TARGET_VX)
5355 {
5356 emit_insn (gen_rtx_SET (operands[0],
5357 gen_rtx_PLUS (TImode,
5358 copy_to_mode_reg (TImode, operands[1]),
5359 copy_to_mode_reg (TImode, operands[2]))));
5360 DONE;
5361 }
5362 })
5363
5364 (define_insn_and_split "*addti3"
5365 [(set (match_operand:TI 0 "register_operand" "=&d")
5366 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
5367 (match_operand:TI 2 "general_operand" "do") ) )
5368 (clobber (reg:CC CC_REGNUM))]
5369 "TARGET_ZARCH"
5370 "#"
5371 "&& reload_completed"
5372 [(parallel
5373 [(set (reg:CCL1 CC_REGNUM)
5374 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
5375 (match_dup 7)))
5376 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
5377 (parallel
5378 [(set (match_dup 3) (plus:DI
5379 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
5380 (match_dup 4)) (match_dup 5)))
5381 (clobber (reg:CC CC_REGNUM))])]
5382 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5383 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5384 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5385 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5386 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5387 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5388 [(set_attr "op_type" "*")
5389 (set_attr "cpu_facility" "*")])
5390
5391 ;
5392 ; adddi3 instruction pattern(s).
5393 ;
5394
5395 (define_expand "adddi3"
5396 [(parallel
5397 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5398 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5399 (match_operand:DI 2 "general_operand" "")))
5400 (clobber (reg:CC CC_REGNUM))])]
5401 ""
5402 "")
5403
5404 (define_insn "*adddi3_sign"
5405 [(set (match_operand:DI 0 "register_operand" "=d,d")
5406 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5407 (match_operand:DI 1 "register_operand" "0,0")))
5408 (clobber (reg:CC CC_REGNUM))]
5409 "TARGET_ZARCH"
5410 "@
5411 agfr\t%0,%2
5412 agf\t%0,%2"
5413 [(set_attr "op_type" "RRE,RXY")
5414 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5415
5416 (define_insn "*adddi3_zero_cc"
5417 [(set (reg CC_REGNUM)
5418 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5419 (match_operand:DI 1 "register_operand" "0,0"))
5420 (const_int 0)))
5421 (set (match_operand:DI 0 "register_operand" "=d,d")
5422 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
5423 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5424 "@
5425 algfr\t%0,%2
5426 algf\t%0,%2"
5427 [(set_attr "op_type" "RRE,RXY")
5428 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5429
5430 (define_insn "*adddi3_zero_cconly"
5431 [(set (reg CC_REGNUM)
5432 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5433 (match_operand:DI 1 "register_operand" "0,0"))
5434 (const_int 0)))
5435 (clobber (match_scratch:DI 0 "=d,d"))]
5436 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5437 "@
5438 algfr\t%0,%2
5439 algf\t%0,%2"
5440 [(set_attr "op_type" "RRE,RXY")
5441 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5442
5443 (define_insn "*adddi3_zero"
5444 [(set (match_operand:DI 0 "register_operand" "=d,d")
5445 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5446 (match_operand:DI 1 "register_operand" "0,0")))
5447 (clobber (reg:CC CC_REGNUM))]
5448 "TARGET_ZARCH"
5449 "@
5450 algfr\t%0,%2
5451 algf\t%0,%2"
5452 [(set_attr "op_type" "RRE,RXY")
5453 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5454
5455 (define_insn_and_split "*adddi3_31z"
5456 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5457 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5458 (match_operand:DI 2 "general_operand" "do") ) )
5459 (clobber (reg:CC CC_REGNUM))]
5460 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5461 "#"
5462 "&& reload_completed"
5463 [(parallel
5464 [(set (reg:CCL1 CC_REGNUM)
5465 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5466 (match_dup 7)))
5467 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5468 (parallel
5469 [(set (match_dup 3) (plus:SI
5470 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
5471 (match_dup 4)) (match_dup 5)))
5472 (clobber (reg:CC CC_REGNUM))])]
5473 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5474 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5475 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5476 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5477 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5478 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5479
5480 (define_insn_and_split "*adddi3_31"
5481 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5482 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5483 (match_operand:DI 2 "general_operand" "do") ) )
5484 (clobber (reg:CC CC_REGNUM))]
5485 "!TARGET_CPU_ZARCH"
5486 "#"
5487 "&& reload_completed"
5488 [(parallel
5489 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
5490 (clobber (reg:CC CC_REGNUM))])
5491 (parallel
5492 [(set (reg:CCL1 CC_REGNUM)
5493 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5494 (match_dup 7)))
5495 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5496 (set (pc)
5497 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
5498 (pc)
5499 (label_ref (match_dup 9))))
5500 (parallel
5501 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
5502 (clobber (reg:CC CC_REGNUM))])
5503 (match_dup 9)]
5504 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5505 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5506 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5507 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5508 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5509 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5510 operands[9] = gen_label_rtx ();")
5511
5512 ;
5513 ; addsi3 instruction pattern(s).
5514 ;
5515
5516 (define_expand "addsi3"
5517 [(parallel
5518 [(set (match_operand:SI 0 "nonimmediate_operand" "")
5519 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5520 (match_operand:SI 2 "general_operand" "")))
5521 (clobber (reg:CC CC_REGNUM))])]
5522 ""
5523 "")
5524
5525 (define_insn "*addsi3_sign"
5526 [(set (match_operand:SI 0 "register_operand" "=d,d")
5527 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
5528 (match_operand:SI 1 "register_operand" "0,0")))
5529 (clobber (reg:CC CC_REGNUM))]
5530 ""
5531 "@
5532 ah\t%0,%2
5533 ahy\t%0,%2"
5534 [(set_attr "op_type" "RX,RXY")
5535 (set_attr "cpu_facility" "*,longdisp")
5536 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5537
5538 ;
5539 ; add(di|si)3 instruction pattern(s).
5540 ;
5541
5542 ; ark, agrk, ar, ahi, ahik, aghik, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
5543 (define_insn "*add<mode>3"
5544 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d, d, d,d,d,S")
5545 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,d, 0, 0,0,0,0")
5546 (match_operand:GPR 2 "general_operand" " d,d,K,K,Op,On,R,T,C") ) )
5547 (clobber (reg:CC CC_REGNUM))]
5548 ""
5549 "@
5550 a<g>r\t%0,%2
5551 a<g>rk\t%0,%1,%2
5552 a<g>hi\t%0,%h2
5553 a<g>hik\t%0,%1,%h2
5554 al<g>fi\t%0,%2
5555 sl<g>fi\t%0,%n2
5556 a<g>\t%0,%2
5557 a<y>\t%0,%2
5558 a<g>si\t%0,%c2"
5559 [(set_attr "op_type" "RR<E>,RRF,RI,RIE,RIL,RIL,RX<Y>,RXY,SIY")
5560 (set_attr "cpu_facility" "*,z196,*,z196,extimm,extimm,*,longdisp,z10")
5561 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,z10_super_E1,z10_super_E1,
5562 z10_super_E1,z10_super_E1,z10_super_E1")])
5563
5564 ; alr, alfi, slfi, al, aly, alrk, alhsik, algr, algfi, slgfi, alg, alsi, algsi, algrk, alghsik
5565 (define_insn "*add<mode>3_carry1_cc"
5566 [(set (reg CC_REGNUM)
5567 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5568 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5569 (match_dup 1)))
5570 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,d")
5571 (plus:GPR (match_dup 1) (match_dup 2)))]
5572 "s390_match_ccmode (insn, CCL1mode)"
5573 "@
5574 al<g>r\t%0,%2
5575 al<g>rk\t%0,%1,%2
5576 al<g>fi\t%0,%2
5577 sl<g>fi\t%0,%n2
5578 al<g>hsik\t%0,%1,%h2
5579 al<g>\t%0,%2
5580 al<y>\t%0,%2
5581 al<g>si\t%0,%c2"
5582 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5583 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5584 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5585 z10_super_E1,z10_super_E1,z10_super_E1")])
5586
5587 ; alr, al, aly, algr, alg, alrk, algrk
5588 (define_insn "*add<mode>3_carry1_cconly"
5589 [(set (reg CC_REGNUM)
5590 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5591 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5592 (match_dup 1)))
5593 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5594 "s390_match_ccmode (insn, CCL1mode)"
5595 "@
5596 al<g>r\t%0,%2
5597 al<g>rk\t%0,%1,%2
5598 al<g>\t%0,%2
5599 al<y>\t%0,%2"
5600 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5601 (set_attr "cpu_facility" "*,z196,*,longdisp")
5602 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5603
5604 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5605 (define_insn "*add<mode>3_carry2_cc"
5606 [(set (reg CC_REGNUM)
5607 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5608 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5609 (match_dup 2)))
5610 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5611 (plus:GPR (match_dup 1) (match_dup 2)))]
5612 "s390_match_ccmode (insn, CCL1mode)"
5613 "@
5614 al<g>r\t%0,%2
5615 al<g>rk\t%0,%1,%2
5616 al<g>fi\t%0,%2
5617 sl<g>fi\t%0,%n2
5618 al<g>hsik\t%0,%1,%h2
5619 al<g>\t%0,%2
5620 al<y>\t%0,%2
5621 al<g>si\t%0,%c2"
5622 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5623 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5624 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5625 z10_super_E1,z10_super_E1,z10_super_E1")])
5626
5627 ; alr, al, aly, algr, alg, alrk, algrk
5628 (define_insn "*add<mode>3_carry2_cconly"
5629 [(set (reg CC_REGNUM)
5630 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5631 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5632 (match_dup 2)))
5633 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5634 "s390_match_ccmode (insn, CCL1mode)"
5635 "@
5636 al<g>r\t%0,%2
5637 al<g>rk\t%0,%1,%2
5638 al<g>\t%0,%2
5639 al<y>\t%0,%2"
5640 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5641 (set_attr "cpu_facility" "*,z196,*,longdisp")
5642 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5643
5644 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5645 (define_insn "*add<mode>3_cc"
5646 [(set (reg CC_REGNUM)
5647 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5648 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5649 (const_int 0)))
5650 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5651 (plus:GPR (match_dup 1) (match_dup 2)))]
5652 "s390_match_ccmode (insn, CCLmode)"
5653 "@
5654 al<g>r\t%0,%2
5655 al<g>rk\t%0,%1,%2
5656 al<g>fi\t%0,%2
5657 sl<g>fi\t%0,%n2
5658 al<g>hsik\t%0,%1,%h2
5659 al<g>\t%0,%2
5660 al<y>\t%0,%2
5661 al<g>si\t%0,%c2"
5662 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5663 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5664 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,
5665 *,z10_super_E1,z10_super_E1,z10_super_E1")])
5666
5667 ; alr, al, aly, algr, alg, alrk, algrk
5668 (define_insn "*add<mode>3_cconly"
5669 [(set (reg CC_REGNUM)
5670 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5671 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5672 (const_int 0)))
5673 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5674 "s390_match_ccmode (insn, CCLmode)"
5675 "@
5676 al<g>r\t%0,%2
5677 al<g>rk\t%0,%1,%2
5678 al<g>\t%0,%2
5679 al<y>\t%0,%2"
5680 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5681 (set_attr "cpu_facility" "*,z196,*,longdisp")
5682 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5683
5684 ; alr, al, aly, algr, alg, alrk, algrk
5685 (define_insn "*add<mode>3_cconly2"
5686 [(set (reg CC_REGNUM)
5687 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5688 (neg:GPR (match_operand:GPR 2 "general_operand" "d,d,R,T"))))
5689 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5690 "s390_match_ccmode(insn, CCLmode)"
5691 "@
5692 al<g>r\t%0,%2
5693 al<g>rk\t%0,%1,%2
5694 al<g>\t%0,%2
5695 al<y>\t%0,%2"
5696 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5697 (set_attr "cpu_facility" "*,z196,*,longdisp")
5698 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5699
5700 ; ahi, afi, aghi, agfi, asi, agsi
5701 (define_insn "*add<mode>3_imm_cc"
5702 [(set (reg CC_REGNUM)
5703 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" " 0, d,0, 0")
5704 (match_operand:GPR 2 "const_int_operand" " K, K,Os,C"))
5705 (const_int 0)))
5706 (set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,d, S")
5707 (plus:GPR (match_dup 1) (match_dup 2)))]
5708 "s390_match_ccmode (insn, CCAmode)
5709 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
5710 || (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
5711 /* Avoid INT32_MIN on 32 bit. */
5712 && (!TARGET_ZARCH || INTVAL (operands[2]) != -0x7fffffff - 1)))"
5713 "@
5714 a<g>hi\t%0,%h2
5715 a<g>hik\t%0,%1,%h2
5716 a<g>fi\t%0,%2
5717 a<g>si\t%0,%c2"
5718 [(set_attr "op_type" "RI,RIE,RIL,SIY")
5719 (set_attr "cpu_facility" "*,z196,extimm,z10")
5720 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5721
5722 ;
5723 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
5724 ;
5725
5726 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5727 ; FIXME: wfadb does not clobber cc
5728 (define_insn "add<mode>3"
5729 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
5730 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
5731 (match_operand:FP 2 "general_operand" "f,f,R,v")))
5732 (clobber (reg:CC CC_REGNUM))]
5733 "TARGET_HARD_FLOAT"
5734 "@
5735 a<xde>tr\t%0,%1,%2
5736 a<xde>br\t%0,%2
5737 a<xde>b\t%0,%2
5738 wfadb\t%v0,%v1,%v2"
5739 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
5740 (set_attr "type" "fsimp<mode>")
5741 (set_attr "cpu_facility" "*,*,*,vec")
5742 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
5743
5744 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5745 (define_insn "*add<mode>3_cc"
5746 [(set (reg CC_REGNUM)
5747 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5748 (match_operand:FP 2 "general_operand" "f,f,R"))
5749 (match_operand:FP 3 "const0_operand" "")))
5750 (set (match_operand:FP 0 "register_operand" "=f,f,f")
5751 (plus:FP (match_dup 1) (match_dup 2)))]
5752 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5753 "@
5754 a<xde>tr\t%0,%1,%2
5755 a<xde>br\t%0,%2
5756 a<xde>b\t%0,%2"
5757 [(set_attr "op_type" "RRF,RRE,RXE")
5758 (set_attr "type" "fsimp<mode>")
5759 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5760
5761 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5762 (define_insn "*add<mode>3_cconly"
5763 [(set (reg CC_REGNUM)
5764 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5765 (match_operand:FP 2 "general_operand" "f,f,R"))
5766 (match_operand:FP 3 "const0_operand" "")))
5767 (clobber (match_scratch:FP 0 "=f,f,f"))]
5768 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5769 "@
5770 a<xde>tr\t%0,%1,%2
5771 a<xde>br\t%0,%2
5772 a<xde>b\t%0,%2"
5773 [(set_attr "op_type" "RRF,RRE,RXE")
5774 (set_attr "type" "fsimp<mode>")
5775 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5776
5777 ;
5778 ; Pointer add instruction patterns
5779 ;
5780
5781 ; This will match "*la_64"
5782 (define_expand "addptrdi3"
5783 [(set (match_operand:DI 0 "register_operand" "")
5784 (plus:DI (match_operand:DI 1 "register_operand" "")
5785 (match_operand:DI 2 "nonmemory_operand" "")))]
5786 "TARGET_64BIT"
5787 {
5788 if (GET_CODE (operands[2]) == CONST_INT)
5789 {
5790 HOST_WIDE_INT c = INTVAL (operands[2]);
5791
5792 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5793 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5794 {
5795 operands[2] = force_const_mem (DImode, operands[2]);
5796 operands[2] = force_reg (DImode, operands[2]);
5797 }
5798 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5799 operands[2] = force_reg (DImode, operands[2]);
5800 }
5801 })
5802
5803 ; For 31 bit we have to prevent the generated pattern from matching
5804 ; normal ADDs since la only does a 31 bit add. This is supposed to
5805 ; match "force_la_31".
5806 (define_expand "addptrsi3"
5807 [(parallel
5808 [(set (match_operand:SI 0 "register_operand" "")
5809 (plus:SI (match_operand:SI 1 "register_operand" "")
5810 (match_operand:SI 2 "nonmemory_operand" "")))
5811 (use (const_int 0))])]
5812 "!TARGET_64BIT"
5813 {
5814 if (GET_CODE (operands[2]) == CONST_INT)
5815 {
5816 HOST_WIDE_INT c = INTVAL (operands[2]);
5817
5818 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5819 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5820 {
5821 operands[2] = force_const_mem (SImode, operands[2]);
5822 operands[2] = force_reg (SImode, operands[2]);
5823 }
5824 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5825 operands[2] = force_reg (SImode, operands[2]);
5826 }
5827 })
5828
5829 ;;
5830 ;;- Subtract instructions.
5831 ;;
5832
5833 ;
5834 ; subti3 instruction pattern(s).
5835 ;
5836
5837 (define_expand "subti3"
5838 [(parallel
5839 [(set (match_operand:TI 0 "register_operand" "")
5840 (minus:TI (match_operand:TI 1 "register_operand" "")
5841 (match_operand:TI 2 "general_operand" "") ) )
5842 (clobber (reg:CC CC_REGNUM))])]
5843 "TARGET_ZARCH"
5844 {
5845 /* For z13 we have vsq which doesn't set CC. */
5846 if (TARGET_VX)
5847 {
5848 emit_insn (gen_rtx_SET (operands[0],
5849 gen_rtx_MINUS (TImode,
5850 operands[1],
5851 copy_to_mode_reg (TImode, operands[2]))));
5852 DONE;
5853 }
5854 })
5855
5856 (define_insn_and_split "*subti3"
5857 [(set (match_operand:TI 0 "register_operand" "=&d")
5858 (minus:TI (match_operand:TI 1 "register_operand" "0")
5859 (match_operand:TI 2 "general_operand" "do") ) )
5860 (clobber (reg:CC CC_REGNUM))]
5861 "TARGET_ZARCH"
5862 "#"
5863 "&& reload_completed"
5864 [(parallel
5865 [(set (reg:CCL2 CC_REGNUM)
5866 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
5867 (match_dup 7)))
5868 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
5869 (parallel
5870 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
5871 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
5872 (clobber (reg:CC CC_REGNUM))])]
5873 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5874 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5875 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5876 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5877 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5878 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5879 [(set_attr "op_type" "*")
5880 (set_attr "cpu_facility" "*")])
5881
5882 ;
5883 ; subdi3 instruction pattern(s).
5884 ;
5885
5886 (define_expand "subdi3"
5887 [(parallel
5888 [(set (match_operand:DI 0 "register_operand" "")
5889 (minus:DI (match_operand:DI 1 "register_operand" "")
5890 (match_operand:DI 2 "general_operand" "")))
5891 (clobber (reg:CC CC_REGNUM))])]
5892 ""
5893 "")
5894
5895 (define_insn "*subdi3_sign"
5896 [(set (match_operand:DI 0 "register_operand" "=d,d")
5897 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5898 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5899 (clobber (reg:CC CC_REGNUM))]
5900 "TARGET_ZARCH"
5901 "@
5902 sgfr\t%0,%2
5903 sgf\t%0,%2"
5904 [(set_attr "op_type" "RRE,RXY")
5905 (set_attr "z10prop" "z10_c,*")
5906 (set_attr "z196prop" "z196_cracked")])
5907
5908 (define_insn "*subdi3_zero_cc"
5909 [(set (reg CC_REGNUM)
5910 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5911 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5912 (const_int 0)))
5913 (set (match_operand:DI 0 "register_operand" "=d,d")
5914 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
5915 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5916 "@
5917 slgfr\t%0,%2
5918 slgf\t%0,%2"
5919 [(set_attr "op_type" "RRE,RXY")
5920 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5921
5922 (define_insn "*subdi3_zero_cconly"
5923 [(set (reg CC_REGNUM)
5924 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5925 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5926 (const_int 0)))
5927 (clobber (match_scratch:DI 0 "=d,d"))]
5928 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5929 "@
5930 slgfr\t%0,%2
5931 slgf\t%0,%2"
5932 [(set_attr "op_type" "RRE,RXY")
5933 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5934
5935 (define_insn "*subdi3_zero"
5936 [(set (match_operand:DI 0 "register_operand" "=d,d")
5937 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5938 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5939 (clobber (reg:CC CC_REGNUM))]
5940 "TARGET_ZARCH"
5941 "@
5942 slgfr\t%0,%2
5943 slgf\t%0,%2"
5944 [(set_attr "op_type" "RRE,RXY")
5945 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5946
5947 (define_insn_and_split "*subdi3_31z"
5948 [(set (match_operand:DI 0 "register_operand" "=&d")
5949 (minus:DI (match_operand:DI 1 "register_operand" "0")
5950 (match_operand:DI 2 "general_operand" "do") ) )
5951 (clobber (reg:CC CC_REGNUM))]
5952 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5953 "#"
5954 "&& reload_completed"
5955 [(parallel
5956 [(set (reg:CCL2 CC_REGNUM)
5957 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5958 (match_dup 7)))
5959 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5960 (parallel
5961 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
5962 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
5963 (clobber (reg:CC CC_REGNUM))])]
5964 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5965 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5966 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5967 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5968 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5969 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5970
5971 (define_insn_and_split "*subdi3_31"
5972 [(set (match_operand:DI 0 "register_operand" "=&d")
5973 (minus:DI (match_operand:DI 1 "register_operand" "0")
5974 (match_operand:DI 2 "general_operand" "do") ) )
5975 (clobber (reg:CC CC_REGNUM))]
5976 "!TARGET_CPU_ZARCH"
5977 "#"
5978 "&& reload_completed"
5979 [(parallel
5980 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
5981 (clobber (reg:CC CC_REGNUM))])
5982 (parallel
5983 [(set (reg:CCL2 CC_REGNUM)
5984 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5985 (match_dup 7)))
5986 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5987 (set (pc)
5988 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
5989 (pc)
5990 (label_ref (match_dup 9))))
5991 (parallel
5992 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
5993 (clobber (reg:CC CC_REGNUM))])
5994 (match_dup 9)]
5995 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5996 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5997 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5998 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5999 operands[7] = operand_subword (operands[1], 1, 0, DImode);
6000 operands[8] = operand_subword (operands[2], 1, 0, DImode);
6001 operands[9] = gen_label_rtx ();")
6002
6003 ;
6004 ; subsi3 instruction pattern(s).
6005 ;
6006
6007 (define_expand "subsi3"
6008 [(parallel
6009 [(set (match_operand:SI 0 "register_operand" "")
6010 (minus:SI (match_operand:SI 1 "register_operand" "")
6011 (match_operand:SI 2 "general_operand" "")))
6012 (clobber (reg:CC CC_REGNUM))])]
6013 ""
6014 "")
6015
6016 (define_insn "*subsi3_sign"
6017 [(set (match_operand:SI 0 "register_operand" "=d,d")
6018 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6019 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
6020 (clobber (reg:CC CC_REGNUM))]
6021 ""
6022 "@
6023 sh\t%0,%2
6024 shy\t%0,%2"
6025 [(set_attr "op_type" "RX,RXY")
6026 (set_attr "cpu_facility" "*,longdisp")
6027 (set_attr "z196prop" "z196_cracked,z196_cracked")])
6028
6029 ;
6030 ; sub(di|si)3 instruction pattern(s).
6031 ;
6032
6033 ; sr, s, sy, sgr, sg, srk, sgrk
6034 (define_insn "*sub<mode>3"
6035 [(set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6036 (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6037 (match_operand:GPR 2 "general_operand" "d,d,R,T") ) )
6038 (clobber (reg:CC CC_REGNUM))]
6039 ""
6040 "@
6041 s<g>r\t%0,%2
6042 s<g>rk\t%0,%1,%2
6043 s<g>\t%0,%2
6044 s<y>\t%0,%2"
6045 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6046 (set_attr "cpu_facility" "*,z196,*,longdisp")
6047 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6048
6049 ; slr, sl, sly, slgr, slg, slrk, slgrk
6050 (define_insn "*sub<mode>3_borrow_cc"
6051 [(set (reg CC_REGNUM)
6052 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6053 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6054 (match_dup 1)))
6055 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6056 (minus:GPR (match_dup 1) (match_dup 2)))]
6057 "s390_match_ccmode (insn, CCL2mode)"
6058 "@
6059 sl<g>r\t%0,%2
6060 sl<g>rk\t%0,%1,%2
6061 sl<g>\t%0,%2
6062 sl<y>\t%0,%2"
6063 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6064 (set_attr "cpu_facility" "*,z196,*,longdisp")
6065 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6066
6067 ; slr, sl, sly, slgr, slg, slrk, slgrk
6068 (define_insn "*sub<mode>3_borrow_cconly"
6069 [(set (reg CC_REGNUM)
6070 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6071 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6072 (match_dup 1)))
6073 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6074 "s390_match_ccmode (insn, CCL2mode)"
6075 "@
6076 sl<g>r\t%0,%2
6077 sl<g>rk\t%0,%1,%2
6078 sl<g>\t%0,%2
6079 sl<y>\t%0,%2"
6080 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6081 (set_attr "cpu_facility" "*,z196,*,longdisp")
6082 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6083
6084 ; slr, sl, sly, slgr, slg, slrk, slgrk
6085 (define_insn "*sub<mode>3_cc"
6086 [(set (reg CC_REGNUM)
6087 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6088 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6089 (const_int 0)))
6090 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6091 (minus:GPR (match_dup 1) (match_dup 2)))]
6092 "s390_match_ccmode (insn, CCLmode)"
6093 "@
6094 sl<g>r\t%0,%2
6095 sl<g>rk\t%0,%1,%2
6096 sl<g>\t%0,%2
6097 sl<y>\t%0,%2"
6098 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6099 (set_attr "cpu_facility" "*,z196,*,longdisp")
6100 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6101
6102 ; slr, sl, sly, slgr, slg, slrk, slgrk
6103 (define_insn "*sub<mode>3_cc2"
6104 [(set (reg CC_REGNUM)
6105 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
6106 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
6107 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6108 (minus:GPR (match_dup 1) (match_dup 2)))]
6109 "s390_match_ccmode (insn, CCL3mode)"
6110 "@
6111 sl<g>r\t%0,%2
6112 sl<g>rk\t%0,%1,%2
6113 sl<g>\t%0,%2
6114 sl<y>\t%0,%2"
6115 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6116 (set_attr "cpu_facility" "*,z196,*,longdisp")
6117 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6118
6119 ; slr, sl, sly, slgr, slg, slrk, slgrk
6120 (define_insn "*sub<mode>3_cconly"
6121 [(set (reg CC_REGNUM)
6122 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6123 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6124 (const_int 0)))
6125 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6126 "s390_match_ccmode (insn, CCLmode)"
6127 "@
6128 sl<g>r\t%0,%2
6129 sl<g>rk\t%0,%1,%2
6130 sl<g>\t%0,%2
6131 sl<y>\t%0,%2"
6132 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6133 (set_attr "cpu_facility" "*,z196,*,longdisp")
6134 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6135
6136
6137 ; slr, sl, sly, slgr, slg, slrk, slgrk
6138 (define_insn "*sub<mode>3_cconly2"
6139 [(set (reg CC_REGNUM)
6140 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
6141 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
6142 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6143 "s390_match_ccmode (insn, CCL3mode)"
6144 "@
6145 sl<g>r\t%0,%2
6146 sl<g>rk\t%0,%1,%2
6147 sl<g>\t%0,%2
6148 sl<y>\t%0,%2"
6149 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6150 (set_attr "cpu_facility" "*,z196,*,longdisp")
6151 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6152
6153
6154 ;
6155 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
6156 ;
6157
6158 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6159 (define_insn "sub<mode>3"
6160 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6161 (minus:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
6162 (match_operand:FP 2 "general_operand" "f,f,R,v")))
6163 (clobber (reg:CC CC_REGNUM))]
6164 "TARGET_HARD_FLOAT"
6165 "@
6166 s<xde>tr\t%0,%1,%2
6167 s<xde>br\t%0,%2
6168 s<xde>b\t%0,%2
6169 wfsdb\t%v0,%v1,%v2"
6170 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6171 (set_attr "type" "fsimp<mode>")
6172 (set_attr "cpu_facility" "*,*,*,vec")
6173 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6174
6175 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6176 (define_insn "*sub<mode>3_cc"
6177 [(set (reg CC_REGNUM)
6178 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6179 (match_operand:FP 2 "general_operand" "f,f,R"))
6180 (match_operand:FP 3 "const0_operand" "")))
6181 (set (match_operand:FP 0 "register_operand" "=f,f,f")
6182 (minus:FP (match_dup 1) (match_dup 2)))]
6183 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6184 "@
6185 s<xde>tr\t%0,%1,%2
6186 s<xde>br\t%0,%2
6187 s<xde>b\t%0,%2"
6188 [(set_attr "op_type" "RRF,RRE,RXE")
6189 (set_attr "type" "fsimp<mode>")
6190 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6191
6192 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6193 (define_insn "*sub<mode>3_cconly"
6194 [(set (reg CC_REGNUM)
6195 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6196 (match_operand:FP 2 "general_operand" "f,f,R"))
6197 (match_operand:FP 3 "const0_operand" "")))
6198 (clobber (match_scratch:FP 0 "=f,f,f"))]
6199 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6200 "@
6201 s<xde>tr\t%0,%1,%2
6202 s<xde>br\t%0,%2
6203 s<xde>b\t%0,%2"
6204 [(set_attr "op_type" "RRF,RRE,RXE")
6205 (set_attr "type" "fsimp<mode>")
6206 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6207
6208
6209 ;;
6210 ;;- Conditional add/subtract instructions.
6211 ;;
6212
6213 ;
6214 ; add(di|si)cc instruction pattern(s).
6215 ;
6216
6217 ; the following 4 patterns are used when the result of an add with
6218 ; carry is checked for an overflow condition
6219
6220 ; op1 + op2 + c < op1
6221
6222 ; alcr, alc, alcgr, alcg
6223 (define_insn "*add<mode>3_alc_carry1_cc"
6224 [(set (reg CC_REGNUM)
6225 (compare
6226 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6227 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6228 (match_operand:GPR 2 "general_operand" "d,T"))
6229 (match_dup 1)))
6230 (set (match_operand:GPR 0 "register_operand" "=d,d")
6231 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6232 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6233 "@
6234 alc<g>r\t%0,%2
6235 alc<g>\t%0,%2"
6236 [(set_attr "op_type" "RRE,RXY")
6237 (set_attr "z196prop" "z196_alone,z196_alone")])
6238
6239 ; alcr, alc, alcgr, alcg
6240 (define_insn "*add<mode>3_alc_carry1_cconly"
6241 [(set (reg CC_REGNUM)
6242 (compare
6243 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6244 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6245 (match_operand:GPR 2 "general_operand" "d,T"))
6246 (match_dup 1)))
6247 (clobber (match_scratch:GPR 0 "=d,d"))]
6248 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6249 "@
6250 alc<g>r\t%0,%2
6251 alc<g>\t%0,%2"
6252 [(set_attr "op_type" "RRE,RXY")
6253 (set_attr "z196prop" "z196_alone,z196_alone")])
6254
6255 ; op1 + op2 + c < op2
6256
6257 ; alcr, alc, alcgr, alcg
6258 (define_insn "*add<mode>3_alc_carry2_cc"
6259 [(set (reg CC_REGNUM)
6260 (compare
6261 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6262 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6263 (match_operand:GPR 2 "general_operand" "d,T"))
6264 (match_dup 2)))
6265 (set (match_operand:GPR 0 "register_operand" "=d,d")
6266 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6267 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6268 "@
6269 alc<g>r\t%0,%2
6270 alc<g>\t%0,%2"
6271 [(set_attr "op_type" "RRE,RXY")])
6272
6273 ; alcr, alc, alcgr, alcg
6274 (define_insn "*add<mode>3_alc_carry2_cconly"
6275 [(set (reg CC_REGNUM)
6276 (compare
6277 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6278 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6279 (match_operand:GPR 2 "general_operand" "d,T"))
6280 (match_dup 2)))
6281 (clobber (match_scratch:GPR 0 "=d,d"))]
6282 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6283 "@
6284 alc<g>r\t%0,%2
6285 alc<g>\t%0,%2"
6286 [(set_attr "op_type" "RRE,RXY")])
6287
6288 ; alcr, alc, alcgr, alcg
6289 (define_insn "*add<mode>3_alc_cc"
6290 [(set (reg CC_REGNUM)
6291 (compare
6292 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6293 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6294 (match_operand:GPR 2 "general_operand" "d,T"))
6295 (const_int 0)))
6296 (set (match_operand:GPR 0 "register_operand" "=d,d")
6297 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6298 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6299 "@
6300 alc<g>r\t%0,%2
6301 alc<g>\t%0,%2"
6302 [(set_attr "op_type" "RRE,RXY")])
6303
6304 ; alcr, alc, alcgr, alcg
6305 (define_insn "*add<mode>3_alc"
6306 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6307 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6308 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6309 (match_operand:GPR 2 "general_operand" "d,T")))
6310 (clobber (reg:CC CC_REGNUM))]
6311 "TARGET_CPU_ZARCH"
6312 "@
6313 alc<g>r\t%0,%2
6314 alc<g>\t%0,%2"
6315 [(set_attr "op_type" "RRE,RXY")])
6316
6317 ; slbr, slb, slbgr, slbg
6318 (define_insn "*sub<mode>3_slb_cc"
6319 [(set (reg CC_REGNUM)
6320 (compare
6321 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6322 (match_operand:GPR 2 "general_operand" "d,T"))
6323 (match_operand:GPR 3 "s390_slb_comparison" ""))
6324 (const_int 0)))
6325 (set (match_operand:GPR 0 "register_operand" "=d,d")
6326 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
6327 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6328 "@
6329 slb<g>r\t%0,%2
6330 slb<g>\t%0,%2"
6331 [(set_attr "op_type" "RRE,RXY")
6332 (set_attr "z10prop" "z10_c,*")])
6333
6334 ; slbr, slb, slbgr, slbg
6335 (define_insn "*sub<mode>3_slb"
6336 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6337 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6338 (match_operand:GPR 2 "general_operand" "d,T"))
6339 (match_operand:GPR 3 "s390_slb_comparison" "")))
6340 (clobber (reg:CC CC_REGNUM))]
6341 "TARGET_CPU_ZARCH"
6342 "@
6343 slb<g>r\t%0,%2
6344 slb<g>\t%0,%2"
6345 [(set_attr "op_type" "RRE,RXY")
6346 (set_attr "z10prop" "z10_c,*")])
6347
6348 (define_expand "add<mode>cc"
6349 [(match_operand:GPR 0 "register_operand" "")
6350 (match_operand 1 "comparison_operator" "")
6351 (match_operand:GPR 2 "register_operand" "")
6352 (match_operand:GPR 3 "const_int_operand" "")]
6353 "TARGET_CPU_ZARCH"
6354 "if (!s390_expand_addcc (GET_CODE (operands[1]),
6355 XEXP (operands[1], 0), XEXP (operands[1], 1),
6356 operands[0], operands[2],
6357 operands[3])) FAIL; DONE;")
6358
6359 ;
6360 ; scond instruction pattern(s).
6361 ;
6362
6363 (define_insn_and_split "*scond<mode>"
6364 [(set (match_operand:GPR 0 "register_operand" "=&d")
6365 (match_operand:GPR 1 "s390_alc_comparison" ""))
6366 (clobber (reg:CC CC_REGNUM))]
6367 "TARGET_CPU_ZARCH"
6368 "#"
6369 "&& reload_completed"
6370 [(set (match_dup 0) (const_int 0))
6371 (parallel
6372 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
6373 (match_dup 0)))
6374 (clobber (reg:CC CC_REGNUM))])]
6375 "")
6376
6377 (define_insn_and_split "*scond<mode>_neg"
6378 [(set (match_operand:GPR 0 "register_operand" "=&d")
6379 (match_operand:GPR 1 "s390_slb_comparison" ""))
6380 (clobber (reg:CC CC_REGNUM))]
6381 "TARGET_CPU_ZARCH"
6382 "#"
6383 "&& reload_completed"
6384 [(set (match_dup 0) (const_int 0))
6385 (parallel
6386 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
6387 (match_dup 1)))
6388 (clobber (reg:CC CC_REGNUM))])
6389 (parallel
6390 [(set (match_dup 0) (neg:GPR (match_dup 0)))
6391 (clobber (reg:CC CC_REGNUM))])]
6392 "")
6393
6394
6395 (define_expand "cstore<mode>4"
6396 [(set (match_operand:SI 0 "register_operand" "")
6397 (match_operator:SI 1 "s390_scond_operator"
6398 [(match_operand:GPR 2 "register_operand" "")
6399 (match_operand:GPR 3 "general_operand" "")]))]
6400 "TARGET_CPU_ZARCH"
6401 "if (!s390_expand_addcc (GET_CODE (operands[1]), operands[2], operands[3],
6402 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
6403
6404 (define_expand "cstorecc4"
6405 [(parallel
6406 [(set (match_operand:SI 0 "register_operand" "")
6407 (match_operator:SI 1 "s390_eqne_operator"
6408 [(match_operand:CCZ1 2 "register_operand")
6409 (match_operand 3 "const0_operand")]))
6410 (clobber (reg:CC CC_REGNUM))])]
6411 ""
6412 "emit_insn (gen_sne (operands[0], operands[2]));
6413 if (GET_CODE (operands[1]) == EQ)
6414 emit_insn (gen_xorsi3 (operands[0], operands[0], const1_rtx));
6415 DONE;")
6416
6417 (define_insn_and_split "sne"
6418 [(set (match_operand:SI 0 "register_operand" "=d")
6419 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
6420 (const_int 0)))
6421 (clobber (reg:CC CC_REGNUM))]
6422 ""
6423 "#"
6424 "reload_completed"
6425 [(parallel
6426 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
6427 (clobber (reg:CC CC_REGNUM))])])
6428
6429
6430 ;;
6431 ;; - Conditional move instructions (introduced with z196)
6432 ;;
6433
6434 (define_expand "mov<mode>cc"
6435 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
6436 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
6437 (match_operand:GPR 2 "nonimmediate_operand" "")
6438 (match_operand:GPR 3 "nonimmediate_operand" "")))]
6439 "TARGET_Z196"
6440 {
6441 /* Emit the comparison insn in case we do not already have a comparison result. */
6442 if (!s390_comparison (operands[1], VOIDmode))
6443 operands[1] = s390_emit_compare (GET_CODE (operands[1]),
6444 XEXP (operands[1], 0),
6445 XEXP (operands[1], 1));
6446 })
6447
6448 ; locr, loc, stoc, locgr, locg, stocg, lochi, locghi
6449 (define_insn_and_split "*mov<mode>cc"
6450 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,d,S,S,&d")
6451 (if_then_else:GPR
6452 (match_operator 1 "s390_comparison"
6453 [(match_operand 2 "cc_reg_operand" " c,c,c,c,c,c,c,c,c")
6454 (match_operand 5 "const_int_operand" "")])
6455 (match_operand:GPR 3 "loc_operand" " d,0,S,0,K,0,d,0,S")
6456 (match_operand:GPR 4 "loc_operand" " 0,d,0,S,0,K,0,d,S")))]
6457 "TARGET_Z196"
6458 "@
6459 loc<g>r%C1\t%0,%3
6460 loc<g>r%D1\t%0,%4
6461 loc<g>%C1\t%0,%3
6462 loc<g>%D1\t%0,%4
6463 loc<g>hi%C1\t%0,%h3
6464 loc<g>hi%D1\t%0,%h4
6465 stoc<g>%C1\t%3,%0
6466 stoc<g>%D1\t%4,%0
6467 #"
6468 "&& reload_completed
6469 && MEM_P (operands[3]) && MEM_P (operands[4])"
6470 [(set (match_dup 0)
6471 (if_then_else:GPR
6472 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6473 (match_dup 3)
6474 (match_dup 0)))
6475 (set (match_dup 0)
6476 (if_then_else:GPR
6477 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6478 (match_dup 0)
6479 (match_dup 4)))]
6480 ""
6481 [(set_attr "op_type" "RRF,RRF,RSY,RSY,RIE,RIE,RSY,RSY,*")
6482 (set_attr "cpu_facility" "*,*,*,*,z13,z13,*,*,*")])
6483
6484 ;;
6485 ;;- Multiply instructions.
6486 ;;
6487
6488 ;
6489 ; muldi3 instruction pattern(s).
6490 ;
6491
6492 (define_insn "*muldi3_sign"
6493 [(set (match_operand:DI 0 "register_operand" "=d,d")
6494 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
6495 (match_operand:DI 1 "register_operand" "0,0")))]
6496 "TARGET_ZARCH"
6497 "@
6498 msgfr\t%0,%2
6499 msgf\t%0,%2"
6500 [(set_attr "op_type" "RRE,RXY")
6501 (set_attr "type" "imuldi")])
6502
6503 (define_insn "muldi3"
6504 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
6505 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
6506 (match_operand:DI 2 "general_operand" "d,K,T,Os")))]
6507 "TARGET_ZARCH"
6508 "@
6509 msgr\t%0,%2
6510 mghi\t%0,%h2
6511 msg\t%0,%2
6512 msgfi\t%0,%2"
6513 [(set_attr "op_type" "RRE,RI,RXY,RIL")
6514 (set_attr "type" "imuldi")
6515 (set_attr "cpu_facility" "*,*,*,z10")])
6516
6517 ;
6518 ; mulsi3 instruction pattern(s).
6519 ;
6520
6521 (define_insn "*mulsi3_sign"
6522 [(set (match_operand:SI 0 "register_operand" "=d,d")
6523 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
6524 (match_operand:SI 1 "register_operand" "0,0")))]
6525 ""
6526 "@
6527 mh\t%0,%2
6528 mhy\t%0,%2"
6529 [(set_attr "op_type" "RX,RXY")
6530 (set_attr "type" "imulhi")
6531 (set_attr "cpu_facility" "*,z10")])
6532
6533 (define_insn "mulsi3"
6534 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
6535 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
6536 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
6537 ""
6538 "@
6539 msr\t%0,%2
6540 mhi\t%0,%h2
6541 ms\t%0,%2
6542 msy\t%0,%2
6543 msfi\t%0,%2"
6544 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
6545 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
6546 (set_attr "cpu_facility" "*,*,*,longdisp,z10")])
6547
6548 ;
6549 ; mulsidi3 instruction pattern(s).
6550 ;
6551
6552 (define_insn "mulsidi3"
6553 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
6554 (mult:DI (sign_extend:DI
6555 (match_operand:SI 1 "register_operand" "%0,0,0"))
6556 (sign_extend:DI
6557 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
6558 "!TARGET_ZARCH"
6559 "@
6560 mr\t%0,%2
6561 m\t%0,%2
6562 mfy\t%0,%2"
6563 [(set_attr "op_type" "RR,RX,RXY")
6564 (set_attr "type" "imulsi")
6565 (set_attr "cpu_facility" "*,*,z10")])
6566
6567 ;
6568 ; umul instruction pattern(s).
6569 ;
6570
6571 ; mlr, ml, mlgr, mlg
6572 (define_insn "umul<dwh><mode>3"
6573 [(set (match_operand:DW 0 "register_operand" "=d,d")
6574 (mult:DW (zero_extend:DW
6575 (match_operand:<DWH> 1 "register_operand" "%0,0"))
6576 (zero_extend:DW
6577 (match_operand:<DWH> 2 "nonimmediate_operand" " d,T"))))]
6578 "TARGET_CPU_ZARCH"
6579 "@
6580 ml<tg>r\t%0,%2
6581 ml<tg>\t%0,%2"
6582 [(set_attr "op_type" "RRE,RXY")
6583 (set_attr "type" "imul<dwh>")])
6584
6585 ;
6586 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
6587 ;
6588
6589 ; mxbr, mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
6590 (define_insn "mul<mode>3"
6591 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6592 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
6593 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
6594 "TARGET_HARD_FLOAT"
6595 "@
6596 m<xdee>tr\t%0,%1,%2
6597 m<xdee>br\t%0,%2
6598 m<xdee>b\t%0,%2
6599 wfmdb\t%v0,%v1,%v2"
6600 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6601 (set_attr "type" "fmul<mode>")
6602 (set_attr "cpu_facility" "*,*,*,vec")
6603 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6604
6605 ; madbr, maebr, maxb, madb, maeb
6606 (define_insn "fma<mode>4"
6607 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6608 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6609 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6610 (match_operand:DSF 3 "register_operand" "0,0,v")))]
6611 "TARGET_HARD_FLOAT"
6612 "@
6613 ma<xde>br\t%0,%1,%2
6614 ma<xde>b\t%0,%1,%2
6615 wfmadb\t%v0,%v1,%v2,%v3"
6616 [(set_attr "op_type" "RRE,RXE,VRR")
6617 (set_attr "type" "fmadd<mode>")
6618 (set_attr "cpu_facility" "*,*,vec")
6619 (set_attr "enabled" "*,*,<DFDI>")])
6620
6621 ; msxbr, msdbr, msebr, msxb, msdb, mseb
6622 (define_insn "fms<mode>4"
6623 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6624 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6625 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6626 (neg:DSF (match_operand:DSF 3 "register_operand" "0,0,v"))))]
6627 "TARGET_HARD_FLOAT"
6628 "@
6629 ms<xde>br\t%0,%1,%2
6630 ms<xde>b\t%0,%1,%2
6631 wfmsdb\t%v0,%v1,%v2,%v3"
6632 [(set_attr "op_type" "RRE,RXE,VRR")
6633 (set_attr "type" "fmadd<mode>")
6634 (set_attr "cpu_facility" "*,*,vec")
6635 (set_attr "enabled" "*,*,<DFDI>")])
6636
6637 ;;
6638 ;;- Divide and modulo instructions.
6639 ;;
6640
6641 ;
6642 ; divmoddi4 instruction pattern(s).
6643 ;
6644
6645 (define_expand "divmoddi4"
6646 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6647 (div:DI (match_operand:DI 1 "register_operand" "")
6648 (match_operand:DI 2 "general_operand" "")))
6649 (set (match_operand:DI 3 "general_operand" "")
6650 (mod:DI (match_dup 1) (match_dup 2)))])
6651 (clobber (match_dup 4))]
6652 "TARGET_ZARCH"
6653 {
6654 rtx div_equal, mod_equal;
6655 rtx_insn *insn;
6656
6657 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
6658 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
6659
6660 operands[4] = gen_reg_rtx(TImode);
6661 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
6662
6663 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6664 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6665
6666 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6667 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6668
6669 DONE;
6670 })
6671
6672 (define_insn "divmodtidi3"
6673 [(set (match_operand:TI 0 "register_operand" "=d,d")
6674 (ior:TI
6675 (ashift:TI
6676 (zero_extend:TI
6677 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6678 (match_operand:DI 2 "general_operand" "d,T")))
6679 (const_int 64))
6680 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
6681 "TARGET_ZARCH"
6682 "@
6683 dsgr\t%0,%2
6684 dsg\t%0,%2"
6685 [(set_attr "op_type" "RRE,RXY")
6686 (set_attr "type" "idiv")])
6687
6688 (define_insn "divmodtisi3"
6689 [(set (match_operand:TI 0 "register_operand" "=d,d")
6690 (ior:TI
6691 (ashift:TI
6692 (zero_extend:TI
6693 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6694 (sign_extend:DI
6695 (match_operand:SI 2 "nonimmediate_operand" "d,T"))))
6696 (const_int 64))
6697 (zero_extend:TI
6698 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
6699 "TARGET_ZARCH"
6700 "@
6701 dsgfr\t%0,%2
6702 dsgf\t%0,%2"
6703 [(set_attr "op_type" "RRE,RXY")
6704 (set_attr "type" "idiv")])
6705
6706 ;
6707 ; udivmoddi4 instruction pattern(s).
6708 ;
6709
6710 (define_expand "udivmoddi4"
6711 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6712 (udiv:DI (match_operand:DI 1 "general_operand" "")
6713 (match_operand:DI 2 "nonimmediate_operand" "")))
6714 (set (match_operand:DI 3 "general_operand" "")
6715 (umod:DI (match_dup 1) (match_dup 2)))])
6716 (clobber (match_dup 4))]
6717 "TARGET_ZARCH"
6718 {
6719 rtx div_equal, mod_equal, equal;
6720 rtx_insn *insn;
6721
6722 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
6723 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
6724 equal = gen_rtx_IOR (TImode,
6725 gen_rtx_ASHIFT (TImode,
6726 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
6727 GEN_INT (64)),
6728 gen_rtx_ZERO_EXTEND (TImode, div_equal));
6729
6730 operands[4] = gen_reg_rtx(TImode);
6731 emit_clobber (operands[4]);
6732 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
6733 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
6734
6735 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
6736 set_unique_reg_note (insn, REG_EQUAL, equal);
6737
6738 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6739 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6740
6741 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6742 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6743
6744 DONE;
6745 })
6746
6747 (define_insn "udivmodtidi3"
6748 [(set (match_operand:TI 0 "register_operand" "=d,d")
6749 (ior:TI
6750 (ashift:TI
6751 (zero_extend:TI
6752 (truncate:DI
6753 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
6754 (zero_extend:TI
6755 (match_operand:DI 2 "nonimmediate_operand" "d,T")))))
6756 (const_int 64))
6757 (zero_extend:TI
6758 (truncate:DI
6759 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
6760 "TARGET_ZARCH"
6761 "@
6762 dlgr\t%0,%2
6763 dlg\t%0,%2"
6764 [(set_attr "op_type" "RRE,RXY")
6765 (set_attr "type" "idiv")])
6766
6767 ;
6768 ; divmodsi4 instruction pattern(s).
6769 ;
6770
6771 (define_expand "divmodsi4"
6772 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6773 (div:SI (match_operand:SI 1 "general_operand" "")
6774 (match_operand:SI 2 "nonimmediate_operand" "")))
6775 (set (match_operand:SI 3 "general_operand" "")
6776 (mod:SI (match_dup 1) (match_dup 2)))])
6777 (clobber (match_dup 4))]
6778 "!TARGET_ZARCH"
6779 {
6780 rtx div_equal, mod_equal, equal;
6781 rtx_insn *insn;
6782
6783 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
6784 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
6785 equal = gen_rtx_IOR (DImode,
6786 gen_rtx_ASHIFT (DImode,
6787 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6788 GEN_INT (32)),
6789 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6790
6791 operands[4] = gen_reg_rtx(DImode);
6792 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
6793
6794 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
6795 set_unique_reg_note (insn, REG_EQUAL, equal);
6796
6797 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6798 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6799
6800 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6801 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6802
6803 DONE;
6804 })
6805
6806 (define_insn "divmoddisi3"
6807 [(set (match_operand:DI 0 "register_operand" "=d,d")
6808 (ior:DI
6809 (ashift:DI
6810 (zero_extend:DI
6811 (truncate:SI
6812 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6813 (sign_extend:DI
6814 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
6815 (const_int 32))
6816 (zero_extend:DI
6817 (truncate:SI
6818 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
6819 "!TARGET_ZARCH"
6820 "@
6821 dr\t%0,%2
6822 d\t%0,%2"
6823 [(set_attr "op_type" "RR,RX")
6824 (set_attr "type" "idiv")])
6825
6826 ;
6827 ; udivsi3 and umodsi3 instruction pattern(s).
6828 ;
6829
6830 (define_expand "udivmodsi4"
6831 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6832 (udiv:SI (match_operand:SI 1 "general_operand" "")
6833 (match_operand:SI 2 "nonimmediate_operand" "")))
6834 (set (match_operand:SI 3 "general_operand" "")
6835 (umod:SI (match_dup 1) (match_dup 2)))])
6836 (clobber (match_dup 4))]
6837 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6838 {
6839 rtx div_equal, mod_equal, equal;
6840 rtx_insn *insn;
6841
6842 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6843 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6844 equal = gen_rtx_IOR (DImode,
6845 gen_rtx_ASHIFT (DImode,
6846 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6847 GEN_INT (32)),
6848 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6849
6850 operands[4] = gen_reg_rtx(DImode);
6851 emit_clobber (operands[4]);
6852 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
6853 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
6854
6855 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
6856 set_unique_reg_note (insn, REG_EQUAL, equal);
6857
6858 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6859 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6860
6861 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6862 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6863
6864 DONE;
6865 })
6866
6867 (define_insn "udivmoddisi3"
6868 [(set (match_operand:DI 0 "register_operand" "=d,d")
6869 (ior:DI
6870 (ashift:DI
6871 (zero_extend:DI
6872 (truncate:SI
6873 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
6874 (zero_extend:DI
6875 (match_operand:SI 2 "nonimmediate_operand" "d,T")))))
6876 (const_int 32))
6877 (zero_extend:DI
6878 (truncate:SI
6879 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
6880 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6881 "@
6882 dlr\t%0,%2
6883 dl\t%0,%2"
6884 [(set_attr "op_type" "RRE,RXY")
6885 (set_attr "type" "idiv")])
6886
6887 (define_expand "udivsi3"
6888 [(set (match_operand:SI 0 "register_operand" "=d")
6889 (udiv:SI (match_operand:SI 1 "general_operand" "")
6890 (match_operand:SI 2 "general_operand" "")))
6891 (clobber (match_dup 3))]
6892 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6893 {
6894 rtx udiv_equal, umod_equal, equal;
6895 rtx_insn *insn;
6896
6897 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6898 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6899 equal = gen_rtx_IOR (DImode,
6900 gen_rtx_ASHIFT (DImode,
6901 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6902 GEN_INT (32)),
6903 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6904
6905 operands[3] = gen_reg_rtx (DImode);
6906
6907 if (CONSTANT_P (operands[2]))
6908 {
6909 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
6910 {
6911 rtx_code_label *label1 = gen_label_rtx ();
6912
6913 operands[1] = make_safe_from (operands[1], operands[0]);
6914 emit_move_insn (operands[0], const0_rtx);
6915 emit_cmp_and_jump_insns (operands[1], operands[2], LT, NULL_RTX,
6916 SImode, 1, label1);
6917 emit_move_insn (operands[0], const1_rtx);
6918 emit_label (label1);
6919 }
6920 else
6921 {
6922 operands[2] = force_reg (SImode, operands[2]);
6923 operands[2] = make_safe_from (operands[2], operands[0]);
6924
6925 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6926 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6927 operands[2]));
6928 set_unique_reg_note (insn, REG_EQUAL, equal);
6929
6930 insn = emit_move_insn (operands[0],
6931 gen_lowpart (SImode, operands[3]));
6932 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6933 }
6934 }
6935 else
6936 {
6937 rtx_code_label *label1 = gen_label_rtx ();
6938 rtx_code_label *label2 = gen_label_rtx ();
6939 rtx_code_label *label3 = gen_label_rtx ();
6940
6941 operands[1] = force_reg (SImode, operands[1]);
6942 operands[1] = make_safe_from (operands[1], operands[0]);
6943 operands[2] = force_reg (SImode, operands[2]);
6944 operands[2] = make_safe_from (operands[2], operands[0]);
6945
6946 emit_move_insn (operands[0], const0_rtx);
6947 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6948 SImode, 1, label3);
6949 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6950 SImode, 0, label2);
6951 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6952 SImode, 0, label1);
6953 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6954 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6955 operands[2]));
6956 set_unique_reg_note (insn, REG_EQUAL, equal);
6957
6958 insn = emit_move_insn (operands[0],
6959 gen_lowpart (SImode, operands[3]));
6960 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6961
6962 emit_jump (label3);
6963 emit_label (label1);
6964 emit_move_insn (operands[0], operands[1]);
6965 emit_jump (label3);
6966 emit_label (label2);
6967 emit_move_insn (operands[0], const1_rtx);
6968 emit_label (label3);
6969 }
6970 emit_move_insn (operands[0], operands[0]);
6971 DONE;
6972 })
6973
6974 (define_expand "umodsi3"
6975 [(set (match_operand:SI 0 "register_operand" "=d")
6976 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
6977 (match_operand:SI 2 "nonimmediate_operand" "")))
6978 (clobber (match_dup 3))]
6979 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6980 {
6981 rtx udiv_equal, umod_equal, equal;
6982 rtx_insn *insn;
6983
6984 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6985 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6986 equal = gen_rtx_IOR (DImode,
6987 gen_rtx_ASHIFT (DImode,
6988 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6989 GEN_INT (32)),
6990 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6991
6992 operands[3] = gen_reg_rtx (DImode);
6993
6994 if (CONSTANT_P (operands[2]))
6995 {
6996 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
6997 {
6998 rtx_code_label *label1 = gen_label_rtx ();
6999
7000 operands[1] = make_safe_from (operands[1], operands[0]);
7001 emit_move_insn (operands[0], operands[1]);
7002 emit_cmp_and_jump_insns (operands[0], operands[2], LT, NULL_RTX,
7003 SImode, 1, label1);
7004 emit_insn (gen_abssi2 (operands[0], operands[2]));
7005 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
7006 emit_label (label1);
7007 }
7008 else
7009 {
7010 operands[2] = force_reg (SImode, operands[2]);
7011 operands[2] = make_safe_from (operands[2], operands[0]);
7012
7013 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
7014 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
7015 operands[2]));
7016 set_unique_reg_note (insn, REG_EQUAL, equal);
7017
7018 insn = emit_move_insn (operands[0],
7019 gen_highpart (SImode, operands[3]));
7020 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
7021 }
7022 }
7023 else
7024 {
7025 rtx_code_label *label1 = gen_label_rtx ();
7026 rtx_code_label *label2 = gen_label_rtx ();
7027 rtx_code_label *label3 = gen_label_rtx ();
7028
7029 operands[1] = force_reg (SImode, operands[1]);
7030 operands[1] = make_safe_from (operands[1], operands[0]);
7031 operands[2] = force_reg (SImode, operands[2]);
7032 operands[2] = make_safe_from (operands[2], operands[0]);
7033
7034 emit_move_insn(operands[0], operands[1]);
7035 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
7036 SImode, 1, label3);
7037 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
7038 SImode, 0, label2);
7039 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
7040 SImode, 0, label1);
7041 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
7042 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
7043 operands[2]));
7044 set_unique_reg_note (insn, REG_EQUAL, equal);
7045
7046 insn = emit_move_insn (operands[0],
7047 gen_highpart (SImode, operands[3]));
7048 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
7049
7050 emit_jump (label3);
7051 emit_label (label1);
7052 emit_move_insn (operands[0], const0_rtx);
7053 emit_jump (label3);
7054 emit_label (label2);
7055 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
7056 emit_label (label3);
7057 }
7058 DONE;
7059 })
7060
7061 ;
7062 ; div(df|sf)3 instruction pattern(s).
7063 ;
7064
7065 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
7066 (define_insn "div<mode>3"
7067 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
7068 (div:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
7069 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
7070 "TARGET_HARD_FLOAT"
7071 "@
7072 d<xde>tr\t%0,%1,%2
7073 d<xde>br\t%0,%2
7074 d<xde>b\t%0,%2
7075 wfddb\t%v0,%v1,%v2"
7076 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
7077 (set_attr "type" "fdiv<mode>")
7078 (set_attr "cpu_facility" "*,*,*,vec")
7079 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
7080
7081
7082 ;;
7083 ;;- And instructions.
7084 ;;
7085
7086 (define_expand "and<mode>3"
7087 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7088 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
7089 (match_operand:INT 2 "general_operand" "")))
7090 (clobber (reg:CC CC_REGNUM))]
7091 ""
7092 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
7093
7094 ;
7095 ; anddi3 instruction pattern(s).
7096 ;
7097
7098 (define_insn "*anddi3_cc"
7099 [(set (reg CC_REGNUM)
7100 (compare
7101 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
7102 (match_operand:DI 2 "general_operand" " d,d,T,NxxDw"))
7103 (const_int 0)))
7104 (set (match_operand:DI 0 "register_operand" "=d,d,d, d")
7105 (and:DI (match_dup 1) (match_dup 2)))]
7106 "TARGET_ZARCH && s390_match_ccmode(insn, CCTmode)"
7107 "@
7108 ngr\t%0,%2
7109 ngrk\t%0,%1,%2
7110 ng\t%0,%2
7111 risbg\t%0,%1,%s2,128+%e2,0"
7112 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
7113 (set_attr "cpu_facility" "*,z196,*,z10")
7114 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
7115
7116 (define_insn "*anddi3_cconly"
7117 [(set (reg CC_REGNUM)
7118 (compare
7119 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
7120 (match_operand:DI 2 "general_operand" " d,d,T,NxxDw"))
7121 (const_int 0)))
7122 (clobber (match_scratch:DI 0 "=d,d,d, d"))]
7123 "TARGET_ZARCH
7124 && s390_match_ccmode(insn, CCTmode)
7125 /* Do not steal TM patterns. */
7126 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
7127 "@
7128 ngr\t%0,%2
7129 ngrk\t%0,%1,%2
7130 ng\t%0,%2
7131 risbg\t%0,%1,%s2,128+%e2,0"
7132 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
7133 (set_attr "cpu_facility" "*,z196,*,z10")
7134 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
7135
7136 (define_insn "*anddi3"
7137 [(set (match_operand:DI 0 "nonimmediate_operand"
7138 "=d,d, d, d, d, d, d, d,d,d,d, d, AQ,Q")
7139 (and:DI
7140 (match_operand:DI 1 "nonimmediate_operand"
7141 "%d,o, 0, 0, 0, 0, 0, 0,0,d,0, d, 0,0")
7142 (match_operand:DI 2 "general_operand"
7143 "M, M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,d,T,NxxDw,NxQDF,Q")))
7144 (clobber (reg:CC CC_REGNUM))]
7145 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7146 "@
7147 #
7148 #
7149 nihh\t%0,%j2
7150 nihl\t%0,%j2
7151 nilh\t%0,%j2
7152 nill\t%0,%j2
7153 nihf\t%0,%m2
7154 nilf\t%0,%m2
7155 ngr\t%0,%2
7156 ngrk\t%0,%1,%2
7157 ng\t%0,%2
7158 risbg\t%0,%1,%s2,128+%e2,0
7159 #
7160 #"
7161 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,RIE,SI,SS")
7162 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,z196,*,z10,*,*")
7163 (set_attr "z10prop" "*,
7164 *,
7165 z10_super_E1,
7166 z10_super_E1,
7167 z10_super_E1,
7168 z10_super_E1,
7169 z10_super_E1,
7170 z10_super_E1,
7171 z10_super_E1,
7172 *,
7173 z10_super_E1,
7174 z10_super_E1,
7175 *,
7176 *")])
7177
7178 (define_split
7179 [(set (match_operand:DI 0 "s_operand" "")
7180 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7181 (clobber (reg:CC CC_REGNUM))]
7182 "reload_completed"
7183 [(parallel
7184 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7185 (clobber (reg:CC CC_REGNUM))])]
7186 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7187
7188 ;; These two are what combine generates for (ashift (zero_extract)).
7189 (define_insn "*extzv_<mode>_srl<clobbercc_or_nocc>"
7190 [(set (match_operand:GPR 0 "register_operand" "=d")
7191 (and:GPR (lshiftrt:GPR
7192 (match_operand:GPR 1 "register_operand" "d")
7193 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
7194 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))]
7195 "<z10_or_zEC12_cond>
7196 /* Note that even for the SImode pattern, the rotate is always DImode. */
7197 && s390_extzv_shift_ok (<bitsize>, -INTVAL (operands[2]),
7198 INTVAL (operands[3]))"
7199 "<risbg_n>\t%0,%1,%<bfstart>3,128+%<bfend>3,64-%2"
7200 [(set_attr "op_type" "RIE")
7201 (set_attr "z10prop" "z10_super_E1")])
7202
7203 (define_insn "*extzv_<mode>_sll<clobbercc_or_nocc>"
7204 [(set (match_operand:GPR 0 "register_operand" "=d")
7205 (and:GPR (ashift:GPR
7206 (match_operand:GPR 1 "register_operand" "d")
7207 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
7208 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))]
7209 "<z10_or_zEC12_cond>
7210 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[2]),
7211 INTVAL (operands[3]))"
7212 "<risbg_n>\t%0,%1,%<bfstart>3,128+%<bfend>3,%2"
7213 [(set_attr "op_type" "RIE")
7214 (set_attr "z10prop" "z10_super_E1")])
7215
7216
7217 ;
7218 ; andsi3 instruction pattern(s).
7219 ;
7220
7221 (define_insn "*andsi3_cc"
7222 [(set (reg CC_REGNUM)
7223 (compare
7224 (and:SI
7225 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7226 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7227 (const_int 0)))
7228 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d, d")
7229 (and:SI (match_dup 1) (match_dup 2)))]
7230 "s390_match_ccmode(insn, CCTmode)"
7231 "@
7232 nilf\t%0,%o2
7233 nr\t%0,%2
7234 nrk\t%0,%1,%2
7235 n\t%0,%2
7236 ny\t%0,%2
7237 risbg\t%0,%1,%t2,128+%f2,0"
7238 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7239 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7240 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7241 z10_super_E1,z10_super_E1,z10_super_E1")])
7242
7243 (define_insn "*andsi3_cconly"
7244 [(set (reg CC_REGNUM)
7245 (compare
7246 (and:SI
7247 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7248 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7249 (const_int 0)))
7250 (clobber (match_scratch:SI 0 "=d,d,d,d,d, d"))]
7251 "s390_match_ccmode(insn, CCTmode)
7252 /* Do not steal TM patterns. */
7253 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
7254 "@
7255 nilf\t%0,%o2
7256 nr\t%0,%2
7257 nrk\t%0,%1,%2
7258 n\t%0,%2
7259 ny\t%0,%2
7260 risbg\t%0,%1,%t2,128+%f2,0"
7261 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7262 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7263 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7264 z10_super_E1,z10_super_E1,z10_super_E1")])
7265
7266 (define_insn "*andsi3_zarch"
7267 [(set (match_operand:SI 0 "nonimmediate_operand"
7268 "=d,d, d, d, d,d,d,d,d, d, AQ,Q")
7269 (and:SI (match_operand:SI 1 "nonimmediate_operand"
7270 "%d,o, 0, 0, 0,0,d,0,0, d, 0,0")
7271 (match_operand:SI 2 "general_operand"
7272 " M,M,N0HSF,N1HSF,Os,d,d,R,T,NxxSw,NxQSF,Q")))
7273 (clobber (reg:CC CC_REGNUM))]
7274 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7275 "@
7276 #
7277 #
7278 nilh\t%0,%j2
7279 nill\t%0,%j2
7280 nilf\t%0,%o2
7281 nr\t%0,%2
7282 nrk\t%0,%1,%2
7283 n\t%0,%2
7284 ny\t%0,%2
7285 risbg\t%0,%1,%t2,128+%f2,0
7286 #
7287 #"
7288 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RRF,RX,RXY,RIE,SI,SS")
7289 (set_attr "cpu_facility" "*,*,*,*,*,*,z196,*,longdisp,z10,*,*")
7290 (set_attr "z10prop" "*,
7291 *,
7292 z10_super_E1,
7293 z10_super_E1,
7294 z10_super_E1,
7295 z10_super_E1,
7296 *,
7297 z10_super_E1,
7298 z10_super_E1,
7299 z10_super_E1,
7300 *,
7301 *")])
7302
7303 (define_insn "*andsi3_esa"
7304 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d, AQ,Q")
7305 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0, 0,0")
7306 (match_operand:SI 2 "general_operand" " d,R,NxQSF,Q")))
7307 (clobber (reg:CC CC_REGNUM))]
7308 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7309 "@
7310 nr\t%0,%2
7311 n\t%0,%2
7312 #
7313 #"
7314 [(set_attr "op_type" "RR,RX,SI,SS")
7315 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7316
7317
7318 (define_split
7319 [(set (match_operand:SI 0 "s_operand" "")
7320 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7321 (clobber (reg:CC CC_REGNUM))]
7322 "reload_completed"
7323 [(parallel
7324 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7325 (clobber (reg:CC CC_REGNUM))])]
7326 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7327
7328 ;
7329 ; andhi3 instruction pattern(s).
7330 ;
7331
7332 (define_insn "*andhi3_zarch"
7333 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7334 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7335 (match_operand:HI 2 "general_operand" " d,d,n,NxQHF,Q")))
7336 (clobber (reg:CC CC_REGNUM))]
7337 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7338 "@
7339 nr\t%0,%2
7340 nrk\t%0,%1,%2
7341 nill\t%0,%x2
7342 #
7343 #"
7344 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7345 (set_attr "cpu_facility" "*,z196,*,*,*")
7346 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")
7347 ])
7348
7349 (define_insn "*andhi3_esa"
7350 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7351 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7352 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
7353 (clobber (reg:CC CC_REGNUM))]
7354 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7355 "@
7356 nr\t%0,%2
7357 #
7358 #"
7359 [(set_attr "op_type" "RR,SI,SS")
7360 (set_attr "z10prop" "z10_super_E1,*,*")
7361 ])
7362
7363 (define_split
7364 [(set (match_operand:HI 0 "s_operand" "")
7365 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7366 (clobber (reg:CC CC_REGNUM))]
7367 "reload_completed"
7368 [(parallel
7369 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7370 (clobber (reg:CC CC_REGNUM))])]
7371 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7372
7373 ;
7374 ; andqi3 instruction pattern(s).
7375 ;
7376
7377 (define_insn "*andqi3_zarch"
7378 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7379 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7380 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7381 (clobber (reg:CC CC_REGNUM))]
7382 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7383 "@
7384 nr\t%0,%2
7385 nrk\t%0,%1,%2
7386 nill\t%0,%b2
7387 ni\t%S0,%b2
7388 niy\t%S0,%b2
7389 #"
7390 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7391 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7392 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super,z10_super,*")])
7393
7394 (define_insn "*andqi3_esa"
7395 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7396 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7397 (match_operand:QI 2 "general_operand" "d,n,Q")))
7398 (clobber (reg:CC CC_REGNUM))]
7399 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7400 "@
7401 nr\t%0,%2
7402 ni\t%S0,%b2
7403 #"
7404 [(set_attr "op_type" "RR,SI,SS")
7405 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7406
7407 ;
7408 ; And with complement
7409 ;
7410 ; c = ~b & a = (b & a) ^ a
7411
7412 (define_insn_and_split "*andc_split_<mode>"
7413 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
7414 (and:GPR (not:GPR (match_operand:GPR 1 "nonimmediate_operand" ""))
7415 (match_operand:GPR 2 "general_operand" "")))
7416 (clobber (reg:CC CC_REGNUM))]
7417 "! reload_completed
7418 && (GET_CODE (operands[0]) != MEM
7419 /* Ensure that s390_logical_operator_ok_p will succeed even
7420 on the split xor if (b & a) is stored into a pseudo. */
7421 || rtx_equal_p (operands[0], operands[2]))"
7422 "#"
7423 "&& 1"
7424 [
7425 (parallel
7426 [(set (match_dup 3) (and:GPR (match_dup 1) (match_dup 2)))
7427 (clobber (reg:CC CC_REGNUM))])
7428 (parallel
7429 [(set (match_dup 0) (xor:GPR (match_dup 3) (match_dup 2)))
7430 (clobber (reg:CC CC_REGNUM))])]
7431 {
7432 if (reg_overlap_mentioned_p (operands[0], operands[2]))
7433 operands[3] = gen_reg_rtx (<MODE>mode);
7434 else
7435 operands[3] = operands[0];
7436 })
7437
7438 ;
7439 ; Block and (NC) patterns.
7440 ;
7441
7442 (define_insn "*nc"
7443 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7444 (and:BLK (match_dup 0)
7445 (match_operand:BLK 1 "memory_operand" "Q")))
7446 (use (match_operand 2 "const_int_operand" "n"))
7447 (clobber (reg:CC CC_REGNUM))]
7448 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7449 "nc\t%O0(%2,%R0),%S1"
7450 [(set_attr "op_type" "SS")
7451 (set_attr "z196prop" "z196_cracked")])
7452
7453 (define_split
7454 [(set (match_operand 0 "memory_operand" "")
7455 (and (match_dup 0)
7456 (match_operand 1 "memory_operand" "")))
7457 (clobber (reg:CC CC_REGNUM))]
7458 "reload_completed
7459 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7460 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7461 [(parallel
7462 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
7463 (use (match_dup 2))
7464 (clobber (reg:CC CC_REGNUM))])]
7465 {
7466 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7467 operands[0] = adjust_address (operands[0], BLKmode, 0);
7468 operands[1] = adjust_address (operands[1], BLKmode, 0);
7469 })
7470
7471 (define_peephole2
7472 [(parallel
7473 [(set (match_operand:BLK 0 "memory_operand" "")
7474 (and:BLK (match_dup 0)
7475 (match_operand:BLK 1 "memory_operand" "")))
7476 (use (match_operand 2 "const_int_operand" ""))
7477 (clobber (reg:CC CC_REGNUM))])
7478 (parallel
7479 [(set (match_operand:BLK 3 "memory_operand" "")
7480 (and:BLK (match_dup 3)
7481 (match_operand:BLK 4 "memory_operand" "")))
7482 (use (match_operand 5 "const_int_operand" ""))
7483 (clobber (reg:CC CC_REGNUM))])]
7484 "s390_offset_p (operands[0], operands[3], operands[2])
7485 && s390_offset_p (operands[1], operands[4], operands[2])
7486 && !s390_overlap_p (operands[0], operands[1],
7487 INTVAL (operands[2]) + INTVAL (operands[5]))
7488 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7489 [(parallel
7490 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
7491 (use (match_dup 8))
7492 (clobber (reg:CC CC_REGNUM))])]
7493 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7494 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7495 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7496
7497
7498 ;;
7499 ;;- Bit set (inclusive or) instructions.
7500 ;;
7501
7502 (define_expand "ior<mode>3"
7503 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7504 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
7505 (match_operand:INT 2 "general_operand" "")))
7506 (clobber (reg:CC CC_REGNUM))]
7507 ""
7508 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
7509
7510 ;
7511 ; iordi3 instruction pattern(s).
7512 ;
7513
7514 (define_insn "*iordi3_cc"
7515 [(set (reg CC_REGNUM)
7516 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7517 (match_operand:DI 2 "general_operand" " d,d,T"))
7518 (const_int 0)))
7519 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7520 (ior:DI (match_dup 1) (match_dup 2)))]
7521 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7522 "@
7523 ogr\t%0,%2
7524 ogrk\t%0,%1,%2
7525 og\t%0,%2"
7526 [(set_attr "op_type" "RRE,RRF,RXY")
7527 (set_attr "cpu_facility" "*,z196,*")
7528 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7529
7530 (define_insn "*iordi3_cconly"
7531 [(set (reg CC_REGNUM)
7532 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7533 (match_operand:DI 2 "general_operand" " d,d,T"))
7534 (const_int 0)))
7535 (clobber (match_scratch:DI 0 "=d,d,d"))]
7536 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7537 "@
7538 ogr\t%0,%2
7539 ogrk\t%0,%1,%2
7540 og\t%0,%2"
7541 [(set_attr "op_type" "RRE,RRF,RXY")
7542 (set_attr "cpu_facility" "*,z196,*")
7543 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7544
7545 (define_insn "*iordi3"
7546 [(set (match_operand:DI 0 "nonimmediate_operand"
7547 "=d, d, d, d, d, d,d,d,d, AQ,Q")
7548 (ior:DI (match_operand:DI 1 "nonimmediate_operand"
7549 " %0, 0, 0, 0, 0, 0,0,d,0, 0,0")
7550 (match_operand:DI 2 "general_operand"
7551 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7552 (clobber (reg:CC CC_REGNUM))]
7553 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7554 "@
7555 oihh\t%0,%i2
7556 oihl\t%0,%i2
7557 oilh\t%0,%i2
7558 oill\t%0,%i2
7559 oihf\t%0,%k2
7560 oilf\t%0,%k2
7561 ogr\t%0,%2
7562 ogrk\t%0,%1,%2
7563 og\t%0,%2
7564 #
7565 #"
7566 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,SI,SS")
7567 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,z196,*,*,*")
7568 (set_attr "z10prop" "z10_super_E1,
7569 z10_super_E1,
7570 z10_super_E1,
7571 z10_super_E1,
7572 z10_super_E1,
7573 z10_super_E1,
7574 z10_super_E1,
7575 *,
7576 z10_super_E1,
7577 *,
7578 *")])
7579
7580 (define_split
7581 [(set (match_operand:DI 0 "s_operand" "")
7582 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7583 (clobber (reg:CC CC_REGNUM))]
7584 "reload_completed"
7585 [(parallel
7586 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7587 (clobber (reg:CC CC_REGNUM))])]
7588 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7589
7590 ;
7591 ; iorsi3 instruction pattern(s).
7592 ;
7593
7594 (define_insn "*iorsi3_cc"
7595 [(set (reg CC_REGNUM)
7596 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7597 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7598 (const_int 0)))
7599 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7600 (ior:SI (match_dup 1) (match_dup 2)))]
7601 "s390_match_ccmode(insn, CCTmode)"
7602 "@
7603 oilf\t%0,%o2
7604 or\t%0,%2
7605 ork\t%0,%1,%2
7606 o\t%0,%2
7607 oy\t%0,%2"
7608 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7609 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7610 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7611
7612 (define_insn "*iorsi3_cconly"
7613 [(set (reg CC_REGNUM)
7614 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7615 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7616 (const_int 0)))
7617 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7618 "s390_match_ccmode(insn, CCTmode)"
7619 "@
7620 oilf\t%0,%o2
7621 or\t%0,%2
7622 ork\t%0,%1,%2
7623 o\t%0,%2
7624 oy\t%0,%2"
7625 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7626 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7627 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7628
7629 (define_insn "*iorsi3_zarch"
7630 [(set (match_operand:SI 0 "nonimmediate_operand" "=d, d, d,d,d,d,d, AQ,Q")
7631 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0, 0, 0,0,d,0,0, 0,0")
7632 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,d,R,T,NxQS0,Q")))
7633 (clobber (reg:CC CC_REGNUM))]
7634 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7635 "@
7636 oilh\t%0,%i2
7637 oill\t%0,%i2
7638 oilf\t%0,%o2
7639 or\t%0,%2
7640 ork\t%0,%1,%2
7641 o\t%0,%2
7642 oy\t%0,%2
7643 #
7644 #"
7645 [(set_attr "op_type" "RI,RI,RIL,RR,RRF,RX,RXY,SI,SS")
7646 (set_attr "cpu_facility" "*,*,*,*,z196,*,longdisp,*,*")
7647 (set_attr "z10prop" "z10_super_E1,
7648 z10_super_E1,
7649 z10_super_E1,
7650 z10_super_E1,
7651 *,
7652 z10_super_E1,
7653 z10_super_E1,
7654 *,
7655 *")])
7656
7657 (define_insn "*iorsi3_esa"
7658 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
7659 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
7660 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
7661 (clobber (reg:CC CC_REGNUM))]
7662 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7663 "@
7664 or\t%0,%2
7665 o\t%0,%2
7666 #
7667 #"
7668 [(set_attr "op_type" "RR,RX,SI,SS")
7669 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7670
7671 (define_split
7672 [(set (match_operand:SI 0 "s_operand" "")
7673 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7674 (clobber (reg:CC CC_REGNUM))]
7675 "reload_completed"
7676 [(parallel
7677 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7678 (clobber (reg:CC CC_REGNUM))])]
7679 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7680
7681 ;
7682 ; iorhi3 instruction pattern(s).
7683 ;
7684
7685 (define_insn "*iorhi3_zarch"
7686 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7687 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7688 (match_operand:HI 2 "general_operand" " d,d,n,NxQH0,Q")))
7689 (clobber (reg:CC CC_REGNUM))]
7690 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7691 "@
7692 or\t%0,%2
7693 ork\t%0,%1,%2
7694 oill\t%0,%x2
7695 #
7696 #"
7697 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7698 (set_attr "cpu_facility" "*,z196,*,*,*")
7699 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")])
7700
7701 (define_insn "*iorhi3_esa"
7702 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7703 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7704 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
7705 (clobber (reg:CC CC_REGNUM))]
7706 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7707 "@
7708 or\t%0,%2
7709 #
7710 #"
7711 [(set_attr "op_type" "RR,SI,SS")
7712 (set_attr "z10prop" "z10_super_E1,*,*")])
7713
7714 (define_split
7715 [(set (match_operand:HI 0 "s_operand" "")
7716 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7717 (clobber (reg:CC CC_REGNUM))]
7718 "reload_completed"
7719 [(parallel
7720 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7721 (clobber (reg:CC CC_REGNUM))])]
7722 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7723
7724 ;
7725 ; iorqi3 instruction pattern(s).
7726 ;
7727
7728 (define_insn "*iorqi3_zarch"
7729 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7730 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7731 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7732 (clobber (reg:CC CC_REGNUM))]
7733 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7734 "@
7735 or\t%0,%2
7736 ork\t%0,%1,%2
7737 oill\t%0,%b2
7738 oi\t%S0,%b2
7739 oiy\t%S0,%b2
7740 #"
7741 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7742 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7743 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,
7744 z10_super,z10_super,*")])
7745
7746 (define_insn "*iorqi3_esa"
7747 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7748 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7749 (match_operand:QI 2 "general_operand" "d,n,Q")))
7750 (clobber (reg:CC CC_REGNUM))]
7751 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7752 "@
7753 or\t%0,%2
7754 oi\t%S0,%b2
7755 #"
7756 [(set_attr "op_type" "RR,SI,SS")
7757 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7758
7759 ;
7760 ; Block inclusive or (OC) patterns.
7761 ;
7762
7763 (define_insn "*oc"
7764 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7765 (ior:BLK (match_dup 0)
7766 (match_operand:BLK 1 "memory_operand" "Q")))
7767 (use (match_operand 2 "const_int_operand" "n"))
7768 (clobber (reg:CC CC_REGNUM))]
7769 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7770 "oc\t%O0(%2,%R0),%S1"
7771 [(set_attr "op_type" "SS")
7772 (set_attr "z196prop" "z196_cracked")])
7773
7774 (define_split
7775 [(set (match_operand 0 "memory_operand" "")
7776 (ior (match_dup 0)
7777 (match_operand 1 "memory_operand" "")))
7778 (clobber (reg:CC CC_REGNUM))]
7779 "reload_completed
7780 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7781 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7782 [(parallel
7783 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
7784 (use (match_dup 2))
7785 (clobber (reg:CC CC_REGNUM))])]
7786 {
7787 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7788 operands[0] = adjust_address (operands[0], BLKmode, 0);
7789 operands[1] = adjust_address (operands[1], BLKmode, 0);
7790 })
7791
7792 (define_peephole2
7793 [(parallel
7794 [(set (match_operand:BLK 0 "memory_operand" "")
7795 (ior:BLK (match_dup 0)
7796 (match_operand:BLK 1 "memory_operand" "")))
7797 (use (match_operand 2 "const_int_operand" ""))
7798 (clobber (reg:CC CC_REGNUM))])
7799 (parallel
7800 [(set (match_operand:BLK 3 "memory_operand" "")
7801 (ior:BLK (match_dup 3)
7802 (match_operand:BLK 4 "memory_operand" "")))
7803 (use (match_operand 5 "const_int_operand" ""))
7804 (clobber (reg:CC CC_REGNUM))])]
7805 "s390_offset_p (operands[0], operands[3], operands[2])
7806 && s390_offset_p (operands[1], operands[4], operands[2])
7807 && !s390_overlap_p (operands[0], operands[1],
7808 INTVAL (operands[2]) + INTVAL (operands[5]))
7809 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7810 [(parallel
7811 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
7812 (use (match_dup 8))
7813 (clobber (reg:CC CC_REGNUM))])]
7814 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7815 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7816 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7817
7818
7819 ;;
7820 ;;- Xor instructions.
7821 ;;
7822
7823 (define_expand "xor<mode>3"
7824 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7825 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
7826 (match_operand:INT 2 "general_operand" "")))
7827 (clobber (reg:CC CC_REGNUM))]
7828 ""
7829 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
7830
7831 ; Combine replaces (xor (x) (const_int -1)) with (not (x)) when doing
7832 ; simplifications. So its better to have something matching.
7833 (define_split
7834 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7835 (not:INT (match_operand:INT 1 "nonimmediate_operand" "")))]
7836 ""
7837 [(parallel
7838 [(set (match_dup 0) (xor:INT (match_dup 1) (match_dup 2)))
7839 (clobber (reg:CC CC_REGNUM))])]
7840 {
7841 operands[2] = constm1_rtx;
7842 if (!s390_logical_operator_ok_p (operands))
7843 FAIL;
7844 })
7845
7846 ;
7847 ; xordi3 instruction pattern(s).
7848 ;
7849
7850 (define_insn "*xordi3_cc"
7851 [(set (reg CC_REGNUM)
7852 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7853 (match_operand:DI 2 "general_operand" " d,d,T"))
7854 (const_int 0)))
7855 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7856 (xor:DI (match_dup 1) (match_dup 2)))]
7857 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7858 "@
7859 xgr\t%0,%2
7860 xgrk\t%0,%1,%2
7861 xg\t%0,%2"
7862 [(set_attr "op_type" "RRE,RRF,RXY")
7863 (set_attr "cpu_facility" "*,z196,*")
7864 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7865
7866 (define_insn "*xordi3_cconly"
7867 [(set (reg CC_REGNUM)
7868 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7869 (match_operand:DI 2 "general_operand" " d,d,T"))
7870 (const_int 0)))
7871 (clobber (match_scratch:DI 0 "=d,d,d"))]
7872 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7873 "@
7874 xgr\t%0,%2
7875 xgrk\t%0,%1,%2
7876 xg\t%0,%2"
7877 [(set_attr "op_type" "RRE,RRF,RXY")
7878 (set_attr "cpu_facility" "*,z196,*")
7879 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7880
7881 (define_insn "*xordi3"
7882 [(set (match_operand:DI 0 "nonimmediate_operand" "=d, d,d,d,d, AQ,Q")
7883 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0, 0,0,d,0, 0,0")
7884 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7885 (clobber (reg:CC CC_REGNUM))]
7886 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7887 "@
7888 xihf\t%0,%k2
7889 xilf\t%0,%k2
7890 xgr\t%0,%2
7891 xgrk\t%0,%1,%2
7892 xg\t%0,%2
7893 #
7894 #"
7895 [(set_attr "op_type" "RIL,RIL,RRE,RRF,RXY,SI,SS")
7896 (set_attr "cpu_facility" "extimm,extimm,*,z196,*,*,*")
7897 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,
7898 *,z10_super_E1,*,*")])
7899
7900 (define_split
7901 [(set (match_operand:DI 0 "s_operand" "")
7902 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7903 (clobber (reg:CC CC_REGNUM))]
7904 "reload_completed"
7905 [(parallel
7906 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7907 (clobber (reg:CC CC_REGNUM))])]
7908 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7909
7910 ;
7911 ; xorsi3 instruction pattern(s).
7912 ;
7913
7914 (define_insn "*xorsi3_cc"
7915 [(set (reg CC_REGNUM)
7916 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7917 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7918 (const_int 0)))
7919 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7920 (xor:SI (match_dup 1) (match_dup 2)))]
7921 "s390_match_ccmode(insn, CCTmode)"
7922 "@
7923 xilf\t%0,%o2
7924 xr\t%0,%2
7925 xrk\t%0,%1,%2
7926 x\t%0,%2
7927 xy\t%0,%2"
7928 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7929 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7930 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7931 z10_super_E1,z10_super_E1")])
7932
7933 (define_insn "*xorsi3_cconly"
7934 [(set (reg CC_REGNUM)
7935 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7936 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7937 (const_int 0)))
7938 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7939 "s390_match_ccmode(insn, CCTmode)"
7940 "@
7941 xilf\t%0,%o2
7942 xr\t%0,%2
7943 xrk\t%0,%1,%2
7944 x\t%0,%2
7945 xy\t%0,%2"
7946 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7947 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7948 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7949 z10_super_E1,z10_super_E1")])
7950
7951 (define_insn "*xorsi3"
7952 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d, AQ,Q")
7953 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, 0,0")
7954 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxQS0,Q")))
7955 (clobber (reg:CC CC_REGNUM))]
7956 "s390_logical_operator_ok_p (operands)"
7957 "@
7958 xilf\t%0,%o2
7959 xr\t%0,%2
7960 xrk\t%0,%1,%2
7961 x\t%0,%2
7962 xy\t%0,%2
7963 #
7964 #"
7965 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,SI,SS")
7966 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*,*")
7967 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7968 z10_super_E1,z10_super_E1,*,*")])
7969
7970 (define_split
7971 [(set (match_operand:SI 0 "s_operand" "")
7972 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7973 (clobber (reg:CC CC_REGNUM))]
7974 "reload_completed"
7975 [(parallel
7976 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7977 (clobber (reg:CC CC_REGNUM))])]
7978 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7979
7980 ;
7981 ; xorhi3 instruction pattern(s).
7982 ;
7983
7984 (define_insn "*xorhi3"
7985 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7986 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,d, 0,0")
7987 (match_operand:HI 2 "general_operand" "Os,d,d,NxQH0,Q")))
7988 (clobber (reg:CC CC_REGNUM))]
7989 "s390_logical_operator_ok_p (operands)"
7990 "@
7991 xilf\t%0,%x2
7992 xr\t%0,%2
7993 xrk\t%0,%1,%2
7994 #
7995 #"
7996 [(set_attr "op_type" "RIL,RR,RRF,SI,SS")
7997 (set_attr "cpu_facility" "*,*,z196,*,*")
7998 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*,*")])
7999
8000 (define_split
8001 [(set (match_operand:HI 0 "s_operand" "")
8002 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
8003 (clobber (reg:CC CC_REGNUM))]
8004 "reload_completed"
8005 [(parallel
8006 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
8007 (clobber (reg:CC CC_REGNUM))])]
8008 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
8009
8010 ;
8011 ; xorqi3 instruction pattern(s).
8012 ;
8013
8014 (define_insn "*xorqi3"
8015 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
8016 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,d,0,0,0")
8017 (match_operand:QI 2 "general_operand" "Os,d,d,n,n,Q")))
8018 (clobber (reg:CC CC_REGNUM))]
8019 "s390_logical_operator_ok_p (operands)"
8020 "@
8021 xilf\t%0,%b2
8022 xr\t%0,%2
8023 xrk\t%0,%1,%2
8024 xi\t%S0,%b2
8025 xiy\t%S0,%b2
8026 #"
8027 [(set_attr "op_type" "RIL,RR,RRF,SI,SIY,SS")
8028 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*")
8029 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super,z10_super,*")])
8030
8031
8032 ;
8033 ; Block exclusive or (XC) patterns.
8034 ;
8035
8036 (define_insn "*xc"
8037 [(set (match_operand:BLK 0 "memory_operand" "=Q")
8038 (xor:BLK (match_dup 0)
8039 (match_operand:BLK 1 "memory_operand" "Q")))
8040 (use (match_operand 2 "const_int_operand" "n"))
8041 (clobber (reg:CC CC_REGNUM))]
8042 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
8043 "xc\t%O0(%2,%R0),%S1"
8044 [(set_attr "op_type" "SS")])
8045
8046 (define_split
8047 [(set (match_operand 0 "memory_operand" "")
8048 (xor (match_dup 0)
8049 (match_operand 1 "memory_operand" "")))
8050 (clobber (reg:CC CC_REGNUM))]
8051 "reload_completed
8052 && GET_MODE (operands[0]) == GET_MODE (operands[1])
8053 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
8054 [(parallel
8055 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
8056 (use (match_dup 2))
8057 (clobber (reg:CC CC_REGNUM))])]
8058 {
8059 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
8060 operands[0] = adjust_address (operands[0], BLKmode, 0);
8061 operands[1] = adjust_address (operands[1], BLKmode, 0);
8062 })
8063
8064 (define_peephole2
8065 [(parallel
8066 [(set (match_operand:BLK 0 "memory_operand" "")
8067 (xor:BLK (match_dup 0)
8068 (match_operand:BLK 1 "memory_operand" "")))
8069 (use (match_operand 2 "const_int_operand" ""))
8070 (clobber (reg:CC CC_REGNUM))])
8071 (parallel
8072 [(set (match_operand:BLK 3 "memory_operand" "")
8073 (xor:BLK (match_dup 3)
8074 (match_operand:BLK 4 "memory_operand" "")))
8075 (use (match_operand 5 "const_int_operand" ""))
8076 (clobber (reg:CC CC_REGNUM))])]
8077 "s390_offset_p (operands[0], operands[3], operands[2])
8078 && s390_offset_p (operands[1], operands[4], operands[2])
8079 && !s390_overlap_p (operands[0], operands[1],
8080 INTVAL (operands[2]) + INTVAL (operands[5]))
8081 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
8082 [(parallel
8083 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
8084 (use (match_dup 8))
8085 (clobber (reg:CC CC_REGNUM))])]
8086 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
8087 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
8088 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
8089
8090 ;
8091 ; Block xor (XC) patterns with src == dest.
8092 ;
8093
8094 (define_insn "*xc_zero"
8095 [(set (match_operand:BLK 0 "memory_operand" "=Q")
8096 (const_int 0))
8097 (use (match_operand 1 "const_int_operand" "n"))
8098 (clobber (reg:CC CC_REGNUM))]
8099 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
8100 "xc\t%O0(%1,%R0),%S0"
8101 [(set_attr "op_type" "SS")
8102 (set_attr "z196prop" "z196_cracked")])
8103
8104 (define_peephole2
8105 [(parallel
8106 [(set (match_operand:BLK 0 "memory_operand" "")
8107 (const_int 0))
8108 (use (match_operand 1 "const_int_operand" ""))
8109 (clobber (reg:CC CC_REGNUM))])
8110 (parallel
8111 [(set (match_operand:BLK 2 "memory_operand" "")
8112 (const_int 0))
8113 (use (match_operand 3 "const_int_operand" ""))
8114 (clobber (reg:CC CC_REGNUM))])]
8115 "s390_offset_p (operands[0], operands[2], operands[1])
8116 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
8117 [(parallel
8118 [(set (match_dup 4) (const_int 0))
8119 (use (match_dup 5))
8120 (clobber (reg:CC CC_REGNUM))])]
8121 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
8122 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
8123
8124
8125 ;;
8126 ;;- Negate instructions.
8127 ;;
8128
8129 ;
8130 ; neg(di|si)2 instruction pattern(s).
8131 ;
8132
8133 (define_expand "neg<mode>2"
8134 [(parallel
8135 [(set (match_operand:DSI 0 "register_operand" "=d")
8136 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
8137 (clobber (reg:CC CC_REGNUM))])]
8138 ""
8139 "")
8140
8141 (define_insn "*negdi2_sign_cc"
8142 [(set (reg CC_REGNUM)
8143 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
8144 (match_operand:SI 1 "register_operand" "d") 0)
8145 (const_int 32)) (const_int 32)))
8146 (const_int 0)))
8147 (set (match_operand:DI 0 "register_operand" "=d")
8148 (neg:DI (sign_extend:DI (match_dup 1))))]
8149 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8150 "lcgfr\t%0,%1"
8151 [(set_attr "op_type" "RRE")
8152 (set_attr "z10prop" "z10_c")])
8153
8154 (define_insn "*negdi2_sign"
8155 [(set (match_operand:DI 0 "register_operand" "=d")
8156 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8157 (clobber (reg:CC CC_REGNUM))]
8158 "TARGET_ZARCH"
8159 "lcgfr\t%0,%1"
8160 [(set_attr "op_type" "RRE")
8161 (set_attr "z10prop" "z10_c")])
8162
8163 ; lcr, lcgr
8164 (define_insn "*neg<mode>2_cc"
8165 [(set (reg CC_REGNUM)
8166 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8167 (const_int 0)))
8168 (set (match_operand:GPR 0 "register_operand" "=d")
8169 (neg:GPR (match_dup 1)))]
8170 "s390_match_ccmode (insn, CCAmode)"
8171 "lc<g>r\t%0,%1"
8172 [(set_attr "op_type" "RR<E>")
8173 (set_attr "z10prop" "z10_super_c_E1")])
8174
8175 ; lcr, lcgr
8176 (define_insn "*neg<mode>2_cconly"
8177 [(set (reg CC_REGNUM)
8178 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8179 (const_int 0)))
8180 (clobber (match_scratch:GPR 0 "=d"))]
8181 "s390_match_ccmode (insn, CCAmode)"
8182 "lc<g>r\t%0,%1"
8183 [(set_attr "op_type" "RR<E>")
8184 (set_attr "z10prop" "z10_super_c_E1")])
8185
8186 ; lcr, lcgr
8187 (define_insn "*neg<mode>2"
8188 [(set (match_operand:GPR 0 "register_operand" "=d")
8189 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
8190 (clobber (reg:CC CC_REGNUM))]
8191 ""
8192 "lc<g>r\t%0,%1"
8193 [(set_attr "op_type" "RR<E>")
8194 (set_attr "z10prop" "z10_super_c_E1")])
8195
8196 (define_insn "*negdi2_31"
8197 [(set (match_operand:DI 0 "register_operand" "=d")
8198 (neg:DI (match_operand:DI 1 "register_operand" "d")))
8199 (clobber (reg:CC CC_REGNUM))]
8200 "!TARGET_ZARCH"
8201 "#")
8202
8203 ; Split a DImode NEG on 31bit into 2 SImode NEGs
8204
8205 ; Doing the twos complement separately on the SImode parts does an
8206 ; unwanted +1 on the high part which needs to be subtracted afterwards
8207 ; ... unless the +1 on the low part created an overflow.
8208
8209 (define_split
8210 [(set (match_operand:DI 0 "register_operand" "")
8211 (neg:DI (match_operand:DI 1 "register_operand" "")))
8212 (clobber (reg:CC CC_REGNUM))]
8213 "!TARGET_ZARCH
8214 && (REGNO (operands[0]) == REGNO (operands[1])
8215 || s390_split_ok_p (operands[0], operands[1], DImode, 0))
8216 && reload_completed"
8217 [(parallel
8218 [(set (match_dup 2) (neg:SI (match_dup 3)))
8219 (clobber (reg:CC CC_REGNUM))])
8220 (parallel
8221 [(set (reg:CCAP CC_REGNUM)
8222 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
8223 (set (match_dup 4) (neg:SI (match_dup 5)))])
8224 (set (pc)
8225 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8226 (pc)
8227 (label_ref (match_dup 6))))
8228 (parallel
8229 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8230 (clobber (reg:CC CC_REGNUM))])
8231 (match_dup 6)]
8232 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8233 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8234 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8235 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8236 operands[6] = gen_label_rtx ();")
8237
8238 ; Like above but first make a copy of the low part of the src operand
8239 ; since it might overlap with the high part of the destination.
8240
8241 (define_split
8242 [(set (match_operand:DI 0 "register_operand" "")
8243 (neg:DI (match_operand:DI 1 "register_operand" "")))
8244 (clobber (reg:CC CC_REGNUM))]
8245 "!TARGET_ZARCH
8246 && s390_split_ok_p (operands[0], operands[1], DImode, 1)
8247 && reload_completed"
8248 [; Make a backup of op5 first
8249 (set (match_dup 4) (match_dup 5))
8250 ; Setting op2 here might clobber op5
8251 (parallel
8252 [(set (match_dup 2) (neg:SI (match_dup 3)))
8253 (clobber (reg:CC CC_REGNUM))])
8254 (parallel
8255 [(set (reg:CCAP CC_REGNUM)
8256 (compare:CCAP (neg:SI (match_dup 4)) (const_int 0)))
8257 (set (match_dup 4) (neg:SI (match_dup 4)))])
8258 (set (pc)
8259 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8260 (pc)
8261 (label_ref (match_dup 6))))
8262 (parallel
8263 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8264 (clobber (reg:CC CC_REGNUM))])
8265 (match_dup 6)]
8266 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8267 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8268 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8269 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8270 operands[6] = gen_label_rtx ();")
8271
8272 ;
8273 ; neg(df|sf)2 instruction pattern(s).
8274 ;
8275
8276 (define_expand "neg<mode>2"
8277 [(parallel
8278 [(set (match_operand:BFP 0 "register_operand" "=f")
8279 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
8280 (clobber (reg:CC CC_REGNUM))])]
8281 "TARGET_HARD_FLOAT"
8282 "")
8283
8284 ; lcxbr, lcdbr, lcebr
8285 (define_insn "*neg<mode>2_cc"
8286 [(set (reg CC_REGNUM)
8287 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8288 (match_operand:BFP 2 "const0_operand" "")))
8289 (set (match_operand:BFP 0 "register_operand" "=f")
8290 (neg:BFP (match_dup 1)))]
8291 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8292 "lc<xde>br\t%0,%1"
8293 [(set_attr "op_type" "RRE")
8294 (set_attr "type" "fsimp<mode>")])
8295
8296 ; lcxbr, lcdbr, lcebr
8297 (define_insn "*neg<mode>2_cconly"
8298 [(set (reg CC_REGNUM)
8299 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8300 (match_operand:BFP 2 "const0_operand" "")))
8301 (clobber (match_scratch:BFP 0 "=f"))]
8302 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8303 "lc<xde>br\t%0,%1"
8304 [(set_attr "op_type" "RRE")
8305 (set_attr "type" "fsimp<mode>")])
8306
8307 ; lcdfr
8308 (define_insn "*neg<mode>2_nocc"
8309 [(set (match_operand:FP 0 "register_operand" "=f")
8310 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8311 "TARGET_DFP"
8312 "lcdfr\t%0,%1"
8313 [(set_attr "op_type" "RRE")
8314 (set_attr "type" "fsimp<mode>")])
8315
8316 ; lcxbr, lcdbr, lcebr
8317 ; FIXME: wflcdb does not clobber cc
8318 (define_insn "*neg<mode>2"
8319 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8320 (neg:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8321 (clobber (reg:CC CC_REGNUM))]
8322 "TARGET_HARD_FLOAT"
8323 "@
8324 lc<xde>br\t%0,%1
8325 wflcdb\t%0,%1"
8326 [(set_attr "op_type" "RRE,VRR")
8327 (set_attr "cpu_facility" "*,vec")
8328 (set_attr "type" "fsimp<mode>,*")
8329 (set_attr "enabled" "*,<DFDI>")])
8330
8331
8332 ;;
8333 ;;- Absolute value instructions.
8334 ;;
8335
8336 ;
8337 ; abs(di|si)2 instruction pattern(s).
8338 ;
8339
8340 (define_insn "*absdi2_sign_cc"
8341 [(set (reg CC_REGNUM)
8342 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8343 (match_operand:SI 1 "register_operand" "d") 0)
8344 (const_int 32)) (const_int 32)))
8345 (const_int 0)))
8346 (set (match_operand:DI 0 "register_operand" "=d")
8347 (abs:DI (sign_extend:DI (match_dup 1))))]
8348 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8349 "lpgfr\t%0,%1"
8350 [(set_attr "op_type" "RRE")
8351 (set_attr "z10prop" "z10_c")])
8352
8353 (define_insn "*absdi2_sign"
8354 [(set (match_operand:DI 0 "register_operand" "=d")
8355 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8356 (clobber (reg:CC CC_REGNUM))]
8357 "TARGET_ZARCH"
8358 "lpgfr\t%0,%1"
8359 [(set_attr "op_type" "RRE")
8360 (set_attr "z10prop" "z10_c")])
8361
8362 ; lpr, lpgr
8363 (define_insn "*abs<mode>2_cc"
8364 [(set (reg CC_REGNUM)
8365 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
8366 (const_int 0)))
8367 (set (match_operand:GPR 0 "register_operand" "=d")
8368 (abs:GPR (match_dup 1)))]
8369 "s390_match_ccmode (insn, CCAmode)"
8370 "lp<g>r\t%0,%1"
8371 [(set_attr "op_type" "RR<E>")
8372 (set_attr "z10prop" "z10_c")])
8373
8374 ; lpr, lpgr
8375 (define_insn "*abs<mode>2_cconly"
8376 [(set (reg CC_REGNUM)
8377 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
8378 (const_int 0)))
8379 (clobber (match_scratch:GPR 0 "=d"))]
8380 "s390_match_ccmode (insn, CCAmode)"
8381 "lp<g>r\t%0,%1"
8382 [(set_attr "op_type" "RR<E>")
8383 (set_attr "z10prop" "z10_c")])
8384
8385 ; lpr, lpgr
8386 (define_insn "abs<mode>2"
8387 [(set (match_operand:GPR 0 "register_operand" "=d")
8388 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8389 (clobber (reg:CC CC_REGNUM))]
8390 ""
8391 "lp<g>r\t%0,%1"
8392 [(set_attr "op_type" "RR<E>")
8393 (set_attr "z10prop" "z10_c")])
8394
8395 ;
8396 ; abs(df|sf)2 instruction pattern(s).
8397 ;
8398
8399 (define_expand "abs<mode>2"
8400 [(parallel
8401 [(set (match_operand:BFP 0 "register_operand" "=f")
8402 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8403 (clobber (reg:CC CC_REGNUM))])]
8404 "TARGET_HARD_FLOAT"
8405 "")
8406
8407 ; lpxbr, lpdbr, lpebr
8408 (define_insn "*abs<mode>2_cc"
8409 [(set (reg CC_REGNUM)
8410 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8411 (match_operand:BFP 2 "const0_operand" "")))
8412 (set (match_operand:BFP 0 "register_operand" "=f")
8413 (abs:BFP (match_dup 1)))]
8414 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8415 "lp<xde>br\t%0,%1"
8416 [(set_attr "op_type" "RRE")
8417 (set_attr "type" "fsimp<mode>")])
8418
8419 ; lpxbr, lpdbr, lpebr
8420 (define_insn "*abs<mode>2_cconly"
8421 [(set (reg CC_REGNUM)
8422 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8423 (match_operand:BFP 2 "const0_operand" "")))
8424 (clobber (match_scratch:BFP 0 "=f"))]
8425 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8426 "lp<xde>br\t%0,%1"
8427 [(set_attr "op_type" "RRE")
8428 (set_attr "type" "fsimp<mode>")])
8429
8430 ; lpdfr
8431 (define_insn "*abs<mode>2_nocc"
8432 [(set (match_operand:FP 0 "register_operand" "=f")
8433 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8434 "TARGET_DFP"
8435 "lpdfr\t%0,%1"
8436 [(set_attr "op_type" "RRE")
8437 (set_attr "type" "fsimp<mode>")])
8438
8439 ; lpxbr, lpdbr, lpebr
8440 ; FIXME: wflpdb does not clobber cc
8441 (define_insn "*abs<mode>2"
8442 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8443 (abs:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8444 (clobber (reg:CC CC_REGNUM))]
8445 "TARGET_HARD_FLOAT"
8446 "@
8447 lp<xde>br\t%0,%1
8448 wflpdb\t%0,%1"
8449 [(set_attr "op_type" "RRE,VRR")
8450 (set_attr "cpu_facility" "*,vec")
8451 (set_attr "type" "fsimp<mode>,*")
8452 (set_attr "enabled" "*,<DFDI>")])
8453
8454
8455 ;;
8456 ;;- Negated absolute value instructions
8457 ;;
8458
8459 ;
8460 ; Integer
8461 ;
8462
8463 (define_insn "*negabsdi2_sign_cc"
8464 [(set (reg CC_REGNUM)
8465 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8466 (match_operand:SI 1 "register_operand" "d") 0)
8467 (const_int 32)) (const_int 32))))
8468 (const_int 0)))
8469 (set (match_operand:DI 0 "register_operand" "=d")
8470 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
8471 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8472 "lngfr\t%0,%1"
8473 [(set_attr "op_type" "RRE")
8474 (set_attr "z10prop" "z10_c")])
8475
8476 (define_insn "*negabsdi2_sign"
8477 [(set (match_operand:DI 0 "register_operand" "=d")
8478 (neg:DI (abs:DI (sign_extend:DI
8479 (match_operand:SI 1 "register_operand" "d")))))
8480 (clobber (reg:CC CC_REGNUM))]
8481 "TARGET_ZARCH"
8482 "lngfr\t%0,%1"
8483 [(set_attr "op_type" "RRE")
8484 (set_attr "z10prop" "z10_c")])
8485
8486 ; lnr, lngr
8487 (define_insn "*negabs<mode>2_cc"
8488 [(set (reg CC_REGNUM)
8489 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8490 (const_int 0)))
8491 (set (match_operand:GPR 0 "register_operand" "=d")
8492 (neg:GPR (abs:GPR (match_dup 1))))]
8493 "s390_match_ccmode (insn, CCAmode)"
8494 "ln<g>r\t%0,%1"
8495 [(set_attr "op_type" "RR<E>")
8496 (set_attr "z10prop" "z10_c")])
8497
8498 ; lnr, lngr
8499 (define_insn "*negabs<mode>2_cconly"
8500 [(set (reg CC_REGNUM)
8501 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8502 (const_int 0)))
8503 (clobber (match_scratch:GPR 0 "=d"))]
8504 "s390_match_ccmode (insn, CCAmode)"
8505 "ln<g>r\t%0,%1"
8506 [(set_attr "op_type" "RR<E>")
8507 (set_attr "z10prop" "z10_c")])
8508
8509 ; lnr, lngr
8510 (define_insn "*negabs<mode>2"
8511 [(set (match_operand:GPR 0 "register_operand" "=d")
8512 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
8513 (clobber (reg:CC CC_REGNUM))]
8514 ""
8515 "ln<g>r\t%0,%1"
8516 [(set_attr "op_type" "RR<E>")
8517 (set_attr "z10prop" "z10_c")])
8518
8519 ;
8520 ; Floating point
8521 ;
8522
8523 ; lnxbr, lndbr, lnebr
8524 (define_insn "*negabs<mode>2_cc"
8525 [(set (reg CC_REGNUM)
8526 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8527 (match_operand:BFP 2 "const0_operand" "")))
8528 (set (match_operand:BFP 0 "register_operand" "=f")
8529 (neg:BFP (abs:BFP (match_dup 1))))]
8530 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8531 "ln<xde>br\t%0,%1"
8532 [(set_attr "op_type" "RRE")
8533 (set_attr "type" "fsimp<mode>")])
8534
8535 ; lnxbr, lndbr, lnebr
8536 (define_insn "*negabs<mode>2_cconly"
8537 [(set (reg CC_REGNUM)
8538 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8539 (match_operand:BFP 2 "const0_operand" "")))
8540 (clobber (match_scratch:BFP 0 "=f"))]
8541 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8542 "ln<xde>br\t%0,%1"
8543 [(set_attr "op_type" "RRE")
8544 (set_attr "type" "fsimp<mode>")])
8545
8546 ; lndfr
8547 (define_insn "*negabs<mode>2_nocc"
8548 [(set (match_operand:FP 0 "register_operand" "=f")
8549 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
8550 "TARGET_DFP"
8551 "lndfr\t%0,%1"
8552 [(set_attr "op_type" "RRE")
8553 (set_attr "type" "fsimp<mode>")])
8554
8555 ; lnxbr, lndbr, lnebr
8556 ; FIXME: wflndb does not clobber cc
8557 (define_insn "*negabs<mode>2"
8558 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8559 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f,v"))))
8560 (clobber (reg:CC CC_REGNUM))]
8561 "TARGET_HARD_FLOAT"
8562 "@
8563 ln<xde>br\t%0,%1
8564 wflndb\t%0,%1"
8565 [(set_attr "op_type" "RRE,VRR")
8566 (set_attr "cpu_facility" "*,vec")
8567 (set_attr "type" "fsimp<mode>,*")
8568 (set_attr "enabled" "*,<DFDI>")])
8569
8570 ;;
8571 ;;- Square root instructions.
8572 ;;
8573
8574 ;
8575 ; sqrt(df|sf)2 instruction pattern(s).
8576 ;
8577
8578 ; sqxbr, sqdbr, sqebr, sqdb, sqeb
8579 (define_insn "sqrt<mode>2"
8580 [(set (match_operand:BFP 0 "register_operand" "=f,f,v")
8581 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,R,v")))]
8582 "TARGET_HARD_FLOAT"
8583 "@
8584 sq<xde>br\t%0,%1
8585 sq<xde>b\t%0,%1
8586 wfsqdb\t%v0,%v1"
8587 [(set_attr "op_type" "RRE,RXE,VRR")
8588 (set_attr "type" "fsqrt<mode>")
8589 (set_attr "cpu_facility" "*,*,vec")
8590 (set_attr "enabled" "*,<DSF>,<DFDI>")])
8591
8592
8593 ;;
8594 ;;- One complement instructions.
8595 ;;
8596
8597 ;
8598 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
8599 ;
8600
8601 (define_expand "one_cmpl<mode>2"
8602 [(parallel
8603 [(set (match_operand:INT 0 "register_operand" "")
8604 (xor:INT (match_operand:INT 1 "register_operand" "")
8605 (const_int -1)))
8606 (clobber (reg:CC CC_REGNUM))])]
8607 ""
8608 "")
8609
8610
8611 ;;
8612 ;; Find leftmost bit instructions.
8613 ;;
8614
8615 (define_expand "clzdi2"
8616 [(set (match_operand:DI 0 "register_operand" "=d")
8617 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
8618 "TARGET_EXTIMM && TARGET_ZARCH"
8619 {
8620 rtx_insn *insn;
8621 rtx clz_equal;
8622 rtx wide_reg = gen_reg_rtx (TImode);
8623 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
8624
8625 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
8626
8627 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
8628
8629 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
8630 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
8631
8632 DONE;
8633 })
8634
8635 (define_insn "clztidi2"
8636 [(set (match_operand:TI 0 "register_operand" "=d")
8637 (ior:TI
8638 (ashift:TI
8639 (zero_extend:TI
8640 (xor:DI (match_operand:DI 1 "register_operand" "d")
8641 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
8642 (subreg:SI (clz:DI (match_dup 1)) 4))))
8643
8644 (const_int 64))
8645 (zero_extend:TI (clz:DI (match_dup 1)))))
8646 (clobber (reg:CC CC_REGNUM))]
8647 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
8648 == (unsigned HOST_WIDE_INT) 1 << 63
8649 && TARGET_EXTIMM && TARGET_ZARCH"
8650 "flogr\t%0,%1"
8651 [(set_attr "op_type" "RRE")])
8652
8653
8654 ;;
8655 ;;- Rotate instructions.
8656 ;;
8657
8658 ;
8659 ; rotl(di|si)3 instruction pattern(s).
8660 ;
8661
8662 (define_expand "rotl<mode>3"
8663 [(set (match_operand:GPR 0 "register_operand" "")
8664 (rotate:GPR (match_operand:GPR 1 "register_operand" "")
8665 (match_operand:SI 2 "nonmemory_operand" "")))]
8666 "TARGET_CPU_ZARCH"
8667 "")
8668
8669 ; rll, rllg
8670 (define_insn "*rotl<mode>3<addr_style_op><masked_op>"
8671 [(set (match_operand:GPR 0 "register_operand" "=d")
8672 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8673 (match_operand:SI 2 "nonmemory_operand" "an")))]
8674 "TARGET_CPU_ZARCH"
8675 "rll<g>\t%0,%1,<addr_style_op_ops>"
8676 [(set_attr "op_type" "RSE")
8677 (set_attr "atype" "reg")
8678 (set_attr "z10prop" "z10_super_E1")])
8679
8680
8681 ;;
8682 ;;- Shift instructions.
8683 ;;
8684
8685 ;
8686 ; (ashl|lshr)(di|si)3 instruction pattern(s).
8687 ; Left shifts and logical right shifts
8688
8689 (define_expand "<shift><mode>3"
8690 [(set (match_operand:DSI 0 "register_operand" "")
8691 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
8692 (match_operand:SI 2 "nonmemory_operand" "")))]
8693 ""
8694 "")
8695
8696 ; ESA 64 bit register pair shift with reg or imm shift count
8697 ; sldl, srdl
8698 (define_insn "*<shift>di3_31<addr_style_op><masked_op>"
8699 [(set (match_operand:DI 0 "register_operand" "=d")
8700 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8701 (match_operand:SI 2 "nonmemory_operand" "an")))]
8702 "!TARGET_ZARCH"
8703 "s<lr>dl\t%0,<addr_style_op_ops>"
8704 [(set_attr "op_type" "RS")
8705 (set_attr "atype" "reg")
8706 (set_attr "z196prop" "z196_cracked")])
8707
8708
8709 ; 64 bit register shift with reg or imm shift count
8710 ; sll, srl, sllg, srlg, sllk, srlk
8711 (define_insn "*<shift><mode>3<addr_style_op><masked_op>"
8712 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8713 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8714 (match_operand:SI 2 "nonmemory_operand" "an,an")))]
8715 ""
8716 "@
8717 s<lr>l<g>\t%0,<1><addr_style_op_ops>
8718 s<lr>l<gk>\t%0,%1,<addr_style_op_ops>"
8719 [(set_attr "op_type" "RS<E>,RSY")
8720 (set_attr "atype" "reg,reg")
8721 (set_attr "cpu_facility" "*,z196")
8722 (set_attr "z10prop" "z10_super_E1,*")])
8723
8724 ;
8725 ; ashr(di|si)3 instruction pattern(s).
8726 ; Arithmetic right shifts
8727
8728 (define_expand "ashr<mode>3"
8729 [(parallel
8730 [(set (match_operand:DSI 0 "register_operand" "")
8731 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
8732 (match_operand:SI 2 "nonmemory_operand" "")))
8733 (clobber (reg:CC CC_REGNUM))])]
8734 ""
8735 "")
8736
8737 ; FIXME: The number of alternatives is doubled here to match the fix
8738 ; number of 2 in the subst pattern for the (clobber (match_scratch...
8739 ; The right fix should be to support match_scratch in the output
8740 ; pattern of a define_subst.
8741 (define_insn "*ashrdi3_31<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8742 [(set (match_operand:DI 0 "register_operand" "=d, d")
8743 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0, 0")
8744 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8745 (clobber (reg:CC CC_REGNUM))]
8746 "!TARGET_ZARCH"
8747 "@
8748 srda\t%0,<addr_style_op_cc_ops>
8749 srda\t%0,<addr_style_op_cc_ops>"
8750 [(set_attr "op_type" "RS")
8751 (set_attr "atype" "reg")])
8752
8753
8754 ; sra, srag
8755 (define_insn "*ashr<mode>3<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8756 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8757 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8758 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8759 (clobber (reg:CC CC_REGNUM))]
8760 ""
8761 "@
8762 sra<g>\t%0,<1><addr_style_op_cc_ops>
8763 sra<gk>\t%0,%1,<addr_style_op_cc_ops>"
8764 [(set_attr "op_type" "RS<E>,RSY")
8765 (set_attr "atype" "reg")
8766 (set_attr "cpu_facility" "*,z196")
8767 (set_attr "z10prop" "z10_super_E1,*")])
8768
8769
8770 ;;
8771 ;; Branch instruction patterns.
8772 ;;
8773
8774 (define_expand "cbranch<mode>4"
8775 [(set (pc)
8776 (if_then_else (match_operator 0 "comparison_operator"
8777 [(match_operand:GPR 1 "register_operand" "")
8778 (match_operand:GPR 2 "general_operand" "")])
8779 (label_ref (match_operand 3 "" ""))
8780 (pc)))]
8781 ""
8782 "s390_emit_jump (operands[3],
8783 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8784 DONE;")
8785
8786 (define_expand "cbranch<mode>4"
8787 [(set (pc)
8788 (if_then_else (match_operator 0 "comparison_operator"
8789 [(match_operand:FP 1 "register_operand" "")
8790 (match_operand:FP 2 "general_operand" "")])
8791 (label_ref (match_operand 3 "" ""))
8792 (pc)))]
8793 "TARGET_HARD_FLOAT"
8794 "s390_emit_jump (operands[3],
8795 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8796 DONE;")
8797
8798 (define_expand "cbranchcc4"
8799 [(set (pc)
8800 (if_then_else (match_operator 0 "s390_comparison"
8801 [(match_operand 1 "cc_reg_operand" "")
8802 (match_operand 2 "const_int_operand" "")])
8803 (label_ref (match_operand 3 "" ""))
8804 (pc)))]
8805 ""
8806 "")
8807
8808
8809 ;;
8810 ;;- Conditional jump instructions.
8811 ;;
8812
8813 (define_insn "*cjump_64"
8814 [(set (pc)
8815 (if_then_else
8816 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8817 (match_operand 2 "const_int_operand" "")])
8818 (label_ref (match_operand 0 "" ""))
8819 (pc)))]
8820 "TARGET_CPU_ZARCH"
8821 {
8822 if (get_attr_length (insn) == 4)
8823 return "j%C1\t%l0";
8824 else
8825 return "jg%C1\t%l0";
8826 }
8827 [(set_attr "op_type" "RI")
8828 (set_attr "type" "branch")
8829 (set (attr "length")
8830 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8831 (const_int 4) (const_int 6)))])
8832
8833 (define_insn "*cjump_31"
8834 [(set (pc)
8835 (if_then_else
8836 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8837 (match_operand 2 "const_int_operand" "")])
8838 (label_ref (match_operand 0 "" ""))
8839 (pc)))]
8840 "!TARGET_CPU_ZARCH"
8841 {
8842 gcc_assert (get_attr_length (insn) == 4);
8843 return "j%C1\t%l0";
8844 }
8845 [(set_attr "op_type" "RI")
8846 (set_attr "type" "branch")
8847 (set (attr "length")
8848 (if_then_else (not (match_test "flag_pic"))
8849 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8850 (const_int 4) (const_int 6))
8851 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8852 (const_int 4) (const_int 8))))])
8853
8854 (define_insn "*cjump_long"
8855 [(set (pc)
8856 (if_then_else
8857 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8858 (match_operand 0 "address_operand" "ZQZR")
8859 (pc)))]
8860 ""
8861 {
8862 if (get_attr_op_type (insn) == OP_TYPE_RR)
8863 return "b%C1r\t%0";
8864 else
8865 return "b%C1\t%a0";
8866 }
8867 [(set (attr "op_type")
8868 (if_then_else (match_operand 0 "register_operand" "")
8869 (const_string "RR") (const_string "RX")))
8870 (set_attr "type" "branch")
8871 (set_attr "atype" "agen")])
8872
8873 ;; A conditional return instruction.
8874 (define_insn "*c<code>"
8875 [(set (pc)
8876 (if_then_else
8877 (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8878 (ANY_RETURN)
8879 (pc)))]
8880 "s390_can_use_<code>_insn ()"
8881 "b%C0r\t%%r14"
8882 [(set_attr "op_type" "RR")
8883 (set_attr "type" "jsr")
8884 (set_attr "atype" "agen")])
8885
8886 ;;
8887 ;;- Negated conditional jump instructions.
8888 ;;
8889
8890 (define_insn "*icjump_64"
8891 [(set (pc)
8892 (if_then_else
8893 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8894 (pc)
8895 (label_ref (match_operand 0 "" ""))))]
8896 "TARGET_CPU_ZARCH"
8897 {
8898 if (get_attr_length (insn) == 4)
8899 return "j%D1\t%l0";
8900 else
8901 return "jg%D1\t%l0";
8902 }
8903 [(set_attr "op_type" "RI")
8904 (set_attr "type" "branch")
8905 (set (attr "length")
8906 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8907 (const_int 4) (const_int 6)))])
8908
8909 (define_insn "*icjump_31"
8910 [(set (pc)
8911 (if_then_else
8912 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8913 (pc)
8914 (label_ref (match_operand 0 "" ""))))]
8915 "!TARGET_CPU_ZARCH"
8916 {
8917 gcc_assert (get_attr_length (insn) == 4);
8918 return "j%D1\t%l0";
8919 }
8920 [(set_attr "op_type" "RI")
8921 (set_attr "type" "branch")
8922 (set (attr "length")
8923 (if_then_else (not (match_test "flag_pic"))
8924 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8925 (const_int 4) (const_int 6))
8926 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8927 (const_int 4) (const_int 8))))])
8928
8929 (define_insn "*icjump_long"
8930 [(set (pc)
8931 (if_then_else
8932 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8933 (pc)
8934 (match_operand 0 "address_operand" "ZQZR")))]
8935 ""
8936 {
8937 if (get_attr_op_type (insn) == OP_TYPE_RR)
8938 return "b%D1r\t%0";
8939 else
8940 return "b%D1\t%a0";
8941 }
8942 [(set (attr "op_type")
8943 (if_then_else (match_operand 0 "register_operand" "")
8944 (const_string "RR") (const_string "RX")))
8945 (set_attr "type" "branch")
8946 (set_attr "atype" "agen")])
8947
8948 ;;
8949 ;;- Trap instructions.
8950 ;;
8951
8952 (define_insn "trap"
8953 [(trap_if (const_int 1) (const_int 0))]
8954 ""
8955 "j\t.+2"
8956 [(set_attr "op_type" "RI")
8957 (set_attr "type" "branch")])
8958
8959 (define_expand "ctrap<mode>4"
8960 [(trap_if (match_operator 0 "comparison_operator"
8961 [(match_operand:GPR 1 "register_operand" "")
8962 (match_operand:GPR 2 "general_operand" "")])
8963 (match_operand 3 "const0_operand" ""))]
8964 ""
8965 {
8966 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8967 operands[1], operands[2]);
8968 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8969 DONE;
8970 })
8971
8972 (define_expand "ctrap<mode>4"
8973 [(trap_if (match_operator 0 "comparison_operator"
8974 [(match_operand:FP 1 "register_operand" "")
8975 (match_operand:FP 2 "general_operand" "")])
8976 (match_operand 3 "const0_operand" ""))]
8977 ""
8978 {
8979 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8980 operands[1], operands[2]);
8981 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8982 DONE;
8983 })
8984
8985 (define_insn "condtrap"
8986 [(trap_if (match_operator 0 "s390_comparison"
8987 [(match_operand 1 "cc_reg_operand" "c")
8988 (const_int 0)])
8989 (const_int 0))]
8990 ""
8991 "j%C0\t.+2";
8992 [(set_attr "op_type" "RI")
8993 (set_attr "type" "branch")])
8994
8995 ; crt, cgrt, cit, cgit
8996 (define_insn "*cmp_and_trap_signed_int<mode>"
8997 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
8998 [(match_operand:GPR 1 "register_operand" "d,d")
8999 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
9000 (const_int 0))]
9001 "TARGET_Z10"
9002 "@
9003 c<g>rt%C0\t%1,%2
9004 c<g>it%C0\t%1,%h2"
9005 [(set_attr "op_type" "RRF,RIE")
9006 (set_attr "type" "branch")
9007 (set_attr "z10prop" "z10_super_c,z10_super")])
9008
9009 ; clrt, clgrt, clfit, clgit, clt, clgt
9010 (define_insn "*cmp_and_trap_unsigned_int<mode>"
9011 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
9012 [(match_operand:GPR 1 "register_operand" "d,d,d")
9013 (match_operand:GPR 2 "general_operand" "d,D,T")])
9014 (const_int 0))]
9015 "TARGET_Z10"
9016 "@
9017 cl<g>rt%C0\t%1,%2
9018 cl<gf>it%C0\t%1,%x2
9019 cl<g>t%C0\t%1,%2"
9020 [(set_attr "op_type" "RRF,RIE,RSY")
9021 (set_attr "type" "branch")
9022 (set_attr "z10prop" "z10_super_c,z10_super,*")
9023 (set_attr "cpu_facility" "z10,z10,zEC12")])
9024
9025 ; lat, lgat
9026 (define_insn "*load_and_trap<mode>"
9027 [(trap_if (eq (match_operand:GPR 0 "memory_operand" "T")
9028 (const_int 0))
9029 (const_int 0))
9030 (set (match_operand:GPR 1 "register_operand" "=d")
9031 (match_dup 0))]
9032 "TARGET_ZEC12"
9033 "l<g>at\t%1,%0"
9034 [(set_attr "op_type" "RXY")])
9035
9036
9037 ;;
9038 ;;- Loop instructions.
9039 ;;
9040 ;; This is all complicated by the fact that since this is a jump insn
9041 ;; we must handle our own output reloads.
9042
9043 ;; branch on index
9044
9045 ; This splitter will be matched by combine and has to add the 2 moves
9046 ; necessary to load the compare and the increment values into a
9047 ; register pair as needed by brxle.
9048
9049 (define_insn_and_split "*brx_stage1_<GPR:mode>"
9050 [(set (pc)
9051 (if_then_else
9052 (match_operator 6 "s390_brx_operator"
9053 [(plus:GPR (match_operand:GPR 1 "register_operand" "")
9054 (match_operand:GPR 2 "general_operand" ""))
9055 (match_operand:GPR 3 "register_operand" "")])
9056 (label_ref (match_operand 0 "" ""))
9057 (pc)))
9058 (set (match_operand:GPR 4 "nonimmediate_operand" "")
9059 (plus:GPR (match_dup 1) (match_dup 2)))
9060 (clobber (match_scratch:GPR 5 ""))]
9061 "TARGET_CPU_ZARCH"
9062 "#"
9063 "!reload_completed && !reload_in_progress"
9064 [(set (match_dup 7) (match_dup 2)) ; the increment
9065 (set (match_dup 8) (match_dup 3)) ; the comparison value
9066 (parallel [(set (pc)
9067 (if_then_else
9068 (match_op_dup 6
9069 [(plus:GPR (match_dup 1) (match_dup 7))
9070 (match_dup 8)])
9071 (label_ref (match_dup 0))
9072 (pc)))
9073 (set (match_dup 4)
9074 (plus:GPR (match_dup 1) (match_dup 7)))
9075 (clobber (match_dup 5))
9076 (clobber (reg:CC CC_REGNUM))])]
9077 {
9078 rtx dreg = gen_reg_rtx (word_mode == DImode ? TImode : DImode);
9079 operands[7] = gen_lowpart (<GPR:MODE>mode,
9080 gen_highpart (word_mode, dreg));
9081 operands[8] = gen_lowpart (<GPR:MODE>mode,
9082 gen_lowpart (word_mode, dreg));
9083 })
9084
9085 ; brxlg, brxhg
9086
9087 (define_insn_and_split "*brxg_64bit"
9088 [(set (pc)
9089 (if_then_else
9090 (match_operator 5 "s390_brx_operator"
9091 [(plus:DI (match_operand:DI 1 "register_operand" "d,d,d")
9092 (subreg:DI (match_operand:TI 2 "register_operand" "d,d,d") 0))
9093 (subreg:DI (match_dup 2) 8)])
9094 (label_ref (match_operand 0 "" ""))
9095 (pc)))
9096 (set (match_operand:DI 3 "nonimmediate_operand" "=1,?X,?X")
9097 (plus:DI (match_dup 1)
9098 (subreg:DI (match_dup 2) 0)))
9099 (clobber (match_scratch:DI 4 "=X,&1,&?d"))
9100 (clobber (reg:CC CC_REGNUM))]
9101 "TARGET_ZARCH"
9102 {
9103 if (which_alternative != 0)
9104 return "#";
9105 else if (get_attr_length (insn) == 6)
9106 return "brx%E5g\t%1,%2,%l0";
9107 else
9108 return "agr\t%1,%2\;cgr\t%1,%M2\;jg%C5\t%l0";
9109 }
9110 "&& reload_completed
9111 && (!REG_P (operands[3])
9112 || !rtx_equal_p (operands[1], operands[3]))"
9113 [(set (match_dup 4) (match_dup 1))
9114 (parallel [(set (match_dup 4) (plus:DI (match_dup 4) (subreg:DI (match_dup 2) 0)))
9115 (clobber (reg:CC CC_REGNUM))])
9116 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:DI (match_dup 2) 8)))
9117 (set (match_dup 3) (match_dup 4))
9118 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9119 (label_ref (match_dup 0))
9120 (pc)))]
9121 ""
9122 [(set_attr "op_type" "RIE")
9123 (set_attr "type" "branch")
9124 (set (attr "length")
9125 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9126 (const_int 6) (const_int 16)))])
9127
9128 ; brxle, brxh
9129
9130 (define_insn_and_split "*brx_64bit"
9131 [(set (pc)
9132 (if_then_else
9133 (match_operator 5 "s390_brx_operator"
9134 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9135 (subreg:SI (match_operand:TI 2 "register_operand" "d,d,d") 4))
9136 (subreg:SI (match_dup 2) 12)])
9137 (label_ref (match_operand 0 "" ""))
9138 (pc)))
9139 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9140 (plus:SI (match_dup 1)
9141 (subreg:SI (match_dup 2) 4)))
9142 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9143 (clobber (reg:CC CC_REGNUM))]
9144 "TARGET_ZARCH"
9145 {
9146 if (which_alternative != 0)
9147 return "#";
9148 else if (get_attr_length (insn) == 6)
9149 return "brx%C5\t%1,%2,%l0";
9150 else
9151 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9152 }
9153 "&& reload_completed
9154 && (!REG_P (operands[3])
9155 || !rtx_equal_p (operands[1], operands[3]))"
9156 [(set (match_dup 4) (match_dup 1))
9157 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 4)))
9158 (clobber (reg:CC CC_REGNUM))])
9159 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 12)))
9160 (set (match_dup 3) (match_dup 4))
9161 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9162 (label_ref (match_dup 0))
9163 (pc)))]
9164 ""
9165 [(set_attr "op_type" "RSI")
9166 (set_attr "type" "branch")
9167 (set (attr "length")
9168 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9169 (const_int 6) (const_int 14)))])
9170
9171 ; brxle, brxh
9172
9173 (define_insn_and_split "*brx_31bit"
9174 [(set (pc)
9175 (if_then_else
9176 (match_operator 5 "s390_brx_operator"
9177 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9178 (subreg:SI (match_operand:DI 2 "register_operand" "d,d,d") 0))
9179 (subreg:SI (match_dup 2) 4)])
9180 (label_ref (match_operand 0 "" ""))
9181 (pc)))
9182 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9183 (plus:SI (match_dup 1)
9184 (subreg:SI (match_dup 2) 0)))
9185 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9186 (clobber (reg:CC CC_REGNUM))]
9187 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
9188 {
9189 if (which_alternative != 0)
9190 return "#";
9191 else if (get_attr_length (insn) == 6)
9192 return "brx%C5\t%1,%2,%l0";
9193 else
9194 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9195 }
9196 "&& reload_completed
9197 && (!REG_P (operands[3])
9198 || !rtx_equal_p (operands[1], operands[3]))"
9199 [(set (match_dup 4) (match_dup 1))
9200 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 0)))
9201 (clobber (reg:CC CC_REGNUM))])
9202 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 4)))
9203 (set (match_dup 3) (match_dup 4))
9204 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9205 (label_ref (match_dup 0))
9206 (pc)))]
9207 ""
9208 [(set_attr "op_type" "RSI")
9209 (set_attr "type" "branch")
9210 (set (attr "length")
9211 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9212 (const_int 6) (const_int 14)))])
9213
9214
9215 ;; branch on count
9216
9217 (define_expand "doloop_end"
9218 [(use (match_operand 0 "" "")) ; loop pseudo
9219 (use (match_operand 1 "" ""))] ; label
9220 ""
9221 {
9222 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
9223 emit_jump_insn (gen_doloop_si31 (operands[1], operands[0], operands[0]));
9224 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
9225 emit_jump_insn (gen_doloop_si64 (operands[1], operands[0], operands[0]));
9226 else if (GET_MODE (operands[0]) == DImode && TARGET_ZARCH)
9227 emit_jump_insn (gen_doloop_di (operands[1], operands[0], operands[0]));
9228 else
9229 FAIL;
9230
9231 DONE;
9232 })
9233
9234 (define_insn_and_split "doloop_si64"
9235 [(set (pc)
9236 (if_then_else
9237 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9238 (const_int 1))
9239 (label_ref (match_operand 0 "" ""))
9240 (pc)))
9241 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9242 (plus:SI (match_dup 1) (const_int -1)))
9243 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9244 (clobber (reg:CC CC_REGNUM))]
9245 "TARGET_CPU_ZARCH"
9246 {
9247 if (which_alternative != 0)
9248 return "#";
9249 else if (get_attr_length (insn) == 4)
9250 return "brct\t%1,%l0";
9251 else
9252 return "ahi\t%1,-1\;jgne\t%l0";
9253 }
9254 "&& reload_completed
9255 && (! REG_P (operands[2])
9256 || ! rtx_equal_p (operands[1], operands[2]))"
9257 [(set (match_dup 3) (match_dup 1))
9258 (parallel [(set (reg:CCAN CC_REGNUM)
9259 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9260 (const_int 0)))
9261 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9262 (set (match_dup 2) (match_dup 3))
9263 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9264 (label_ref (match_dup 0))
9265 (pc)))]
9266 ""
9267 [(set_attr "op_type" "RI")
9268 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9269 ; hurt us in the (rare) case of ahi.
9270 (set_attr "z10prop" "z10_super_E1")
9271 (set_attr "type" "branch")
9272 (set (attr "length")
9273 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9274 (const_int 4) (const_int 10)))])
9275
9276 (define_insn_and_split "doloop_si31"
9277 [(set (pc)
9278 (if_then_else
9279 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9280 (const_int 1))
9281 (label_ref (match_operand 0 "" ""))
9282 (pc)))
9283 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9284 (plus:SI (match_dup 1) (const_int -1)))
9285 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9286 (clobber (reg:CC CC_REGNUM))]
9287 "!TARGET_CPU_ZARCH"
9288 {
9289 if (which_alternative != 0)
9290 return "#";
9291 else if (get_attr_length (insn) == 4)
9292 return "brct\t%1,%l0";
9293 else
9294 gcc_unreachable ();
9295 }
9296 "&& reload_completed
9297 && (! REG_P (operands[2])
9298 || ! rtx_equal_p (operands[1], operands[2]))"
9299 [(set (match_dup 3) (match_dup 1))
9300 (parallel [(set (reg:CCAN CC_REGNUM)
9301 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9302 (const_int 0)))
9303 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9304 (set (match_dup 2) (match_dup 3))
9305 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9306 (label_ref (match_dup 0))
9307 (pc)))]
9308 ""
9309 [(set_attr "op_type" "RI")
9310 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9311 ; hurt us in the (rare) case of ahi.
9312 (set_attr "z10prop" "z10_super_E1")
9313 (set_attr "type" "branch")
9314 (set (attr "length")
9315 (if_then_else (not (match_test "flag_pic"))
9316 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9317 (const_int 4) (const_int 6))
9318 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9319 (const_int 4) (const_int 8))))])
9320
9321 (define_insn "*doloop_si_long"
9322 [(set (pc)
9323 (if_then_else
9324 (ne (match_operand:SI 1 "register_operand" "d")
9325 (const_int 1))
9326 (match_operand 0 "address_operand" "ZR")
9327 (pc)))
9328 (set (match_operand:SI 2 "register_operand" "=1")
9329 (plus:SI (match_dup 1) (const_int -1)))
9330 (clobber (match_scratch:SI 3 "=X"))
9331 (clobber (reg:CC CC_REGNUM))]
9332 "!TARGET_CPU_ZARCH"
9333 {
9334 if (get_attr_op_type (insn) == OP_TYPE_RR)
9335 return "bctr\t%1,%0";
9336 else
9337 return "bct\t%1,%a0";
9338 }
9339 [(set (attr "op_type")
9340 (if_then_else (match_operand 0 "register_operand" "")
9341 (const_string "RR") (const_string "RX")))
9342 (set_attr "type" "branch")
9343 (set_attr "atype" "agen")
9344 (set_attr "z10prop" "z10_c")
9345 (set_attr "z196prop" "z196_cracked")])
9346
9347 (define_insn_and_split "doloop_di"
9348 [(set (pc)
9349 (if_then_else
9350 (ne (match_operand:DI 1 "register_operand" "d,d,d")
9351 (const_int 1))
9352 (label_ref (match_operand 0 "" ""))
9353 (pc)))
9354 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
9355 (plus:DI (match_dup 1) (const_int -1)))
9356 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
9357 (clobber (reg:CC CC_REGNUM))]
9358 "TARGET_ZARCH"
9359 {
9360 if (which_alternative != 0)
9361 return "#";
9362 else if (get_attr_length (insn) == 4)
9363 return "brctg\t%1,%l0";
9364 else
9365 return "aghi\t%1,-1\;jgne\t%l0";
9366 }
9367 "&& reload_completed
9368 && (! REG_P (operands[2])
9369 || ! rtx_equal_p (operands[1], operands[2]))"
9370 [(set (match_dup 3) (match_dup 1))
9371 (parallel [(set (reg:CCAN CC_REGNUM)
9372 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
9373 (const_int 0)))
9374 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
9375 (set (match_dup 2) (match_dup 3))
9376 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9377 (label_ref (match_dup 0))
9378 (pc)))]
9379 ""
9380 [(set_attr "op_type" "RI")
9381 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9382 ; hurt us in the (rare) case of ahi.
9383 (set_attr "z10prop" "z10_super_E1")
9384 (set_attr "type" "branch")
9385 (set (attr "length")
9386 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9387 (const_int 4) (const_int 10)))])
9388
9389 ;;
9390 ;;- Unconditional jump instructions.
9391 ;;
9392
9393 ;
9394 ; jump instruction pattern(s).
9395 ;
9396
9397 (define_expand "jump"
9398 [(match_operand 0 "" "")]
9399 ""
9400 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
9401
9402 (define_insn "*jump64"
9403 [(set (pc) (label_ref (match_operand 0 "" "")))]
9404 "TARGET_CPU_ZARCH"
9405 {
9406 if (get_attr_length (insn) == 4)
9407 return "j\t%l0";
9408 else
9409 return "jg\t%l0";
9410 }
9411 [(set_attr "op_type" "RI")
9412 (set_attr "type" "branch")
9413 (set (attr "length")
9414 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9415 (const_int 4) (const_int 6)))])
9416
9417 (define_insn "*jump31"
9418 [(set (pc) (label_ref (match_operand 0 "" "")))]
9419 "!TARGET_CPU_ZARCH"
9420 {
9421 gcc_assert (get_attr_length (insn) == 4);
9422 return "j\t%l0";
9423 }
9424 [(set_attr "op_type" "RI")
9425 (set_attr "type" "branch")
9426 (set (attr "length")
9427 (if_then_else (not (match_test "flag_pic"))
9428 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9429 (const_int 4) (const_int 6))
9430 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9431 (const_int 4) (const_int 8))))])
9432
9433 ;
9434 ; indirect-jump instruction pattern(s).
9435 ;
9436
9437 (define_insn "indirect_jump"
9438 [(set (pc) (match_operand 0 "address_operand" "ZR"))]
9439 ""
9440 {
9441 if (get_attr_op_type (insn) == OP_TYPE_RR)
9442 return "br\t%0";
9443 else
9444 return "b\t%a0";
9445 }
9446 [(set (attr "op_type")
9447 (if_then_else (match_operand 0 "register_operand" "")
9448 (const_string "RR") (const_string "RX")))
9449 (set_attr "type" "branch")
9450 (set_attr "atype" "agen")])
9451
9452 ;
9453 ; casesi instruction pattern(s).
9454 ;
9455
9456 (define_insn "casesi_jump"
9457 [(set (pc) (match_operand 0 "address_operand" "ZR"))
9458 (use (label_ref (match_operand 1 "" "")))]
9459 ""
9460 {
9461 if (get_attr_op_type (insn) == OP_TYPE_RR)
9462 return "br\t%0";
9463 else
9464 return "b\t%a0";
9465 }
9466 [(set (attr "op_type")
9467 (if_then_else (match_operand 0 "register_operand" "")
9468 (const_string "RR") (const_string "RX")))
9469 (set_attr "type" "branch")
9470 (set_attr "atype" "agen")])
9471
9472 (define_expand "casesi"
9473 [(match_operand:SI 0 "general_operand" "")
9474 (match_operand:SI 1 "general_operand" "")
9475 (match_operand:SI 2 "general_operand" "")
9476 (label_ref (match_operand 3 "" ""))
9477 (label_ref (match_operand 4 "" ""))]
9478 ""
9479 {
9480 rtx index = gen_reg_rtx (SImode);
9481 rtx base = gen_reg_rtx (Pmode);
9482 rtx target = gen_reg_rtx (Pmode);
9483
9484 emit_move_insn (index, operands[0]);
9485 emit_insn (gen_subsi3 (index, index, operands[1]));
9486 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
9487 operands[4]);
9488
9489 if (Pmode != SImode)
9490 index = convert_to_mode (Pmode, index, 1);
9491 if (GET_CODE (index) != REG)
9492 index = copy_to_mode_reg (Pmode, index);
9493
9494 if (TARGET_64BIT)
9495 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
9496 else
9497 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
9498
9499 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
9500
9501 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
9502 emit_move_insn (target, index);
9503
9504 if (flag_pic)
9505 target = gen_rtx_PLUS (Pmode, base, target);
9506 emit_jump_insn (gen_casesi_jump (target, operands[3]));
9507
9508 DONE;
9509 })
9510
9511
9512 ;;
9513 ;;- Jump to subroutine.
9514 ;;
9515 ;;
9516
9517 ;
9518 ; untyped call instruction pattern(s).
9519 ;
9520
9521 ;; Call subroutine returning any type.
9522 (define_expand "untyped_call"
9523 [(parallel [(call (match_operand 0 "" "")
9524 (const_int 0))
9525 (match_operand 1 "" "")
9526 (match_operand 2 "" "")])]
9527 ""
9528 {
9529 int i;
9530
9531 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
9532
9533 for (i = 0; i < XVECLEN (operands[2], 0); i++)
9534 {
9535 rtx set = XVECEXP (operands[2], 0, i);
9536 emit_move_insn (SET_DEST (set), SET_SRC (set));
9537 }
9538
9539 /* The optimizer does not know that the call sets the function value
9540 registers we stored in the result block. We avoid problems by
9541 claiming that all hard registers are used and clobbered at this
9542 point. */
9543 emit_insn (gen_blockage ());
9544
9545 DONE;
9546 })
9547
9548 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
9549 ;; all of memory. This blocks insns from being moved across this point.
9550
9551 (define_insn "blockage"
9552 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
9553 ""
9554 ""
9555 [(set_attr "type" "none")
9556 (set_attr "length" "0")])
9557
9558 ;
9559 ; sibcall patterns
9560 ;
9561
9562 (define_expand "sibcall"
9563 [(call (match_operand 0 "" "")
9564 (match_operand 1 "" ""))]
9565 ""
9566 {
9567 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
9568 DONE;
9569 })
9570
9571 (define_insn "*sibcall_br"
9572 [(call (mem:QI (reg SIBCALL_REGNUM))
9573 (match_operand 0 "const_int_operand" "n"))]
9574 "SIBLING_CALL_P (insn)
9575 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
9576 "br\t%%r1"
9577 [(set_attr "op_type" "RR")
9578 (set_attr "type" "branch")
9579 (set_attr "atype" "agen")])
9580
9581 (define_insn "*sibcall_brc"
9582 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9583 (match_operand 1 "const_int_operand" "n"))]
9584 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9585 "j\t%0"
9586 [(set_attr "op_type" "RI")
9587 (set_attr "type" "branch")])
9588
9589 (define_insn "*sibcall_brcl"
9590 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9591 (match_operand 1 "const_int_operand" "n"))]
9592 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9593 "jg\t%0"
9594 [(set_attr "op_type" "RIL")
9595 (set_attr "type" "branch")])
9596
9597 ;
9598 ; sibcall_value patterns
9599 ;
9600
9601 (define_expand "sibcall_value"
9602 [(set (match_operand 0 "" "")
9603 (call (match_operand 1 "" "")
9604 (match_operand 2 "" "")))]
9605 ""
9606 {
9607 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
9608 DONE;
9609 })
9610
9611 (define_insn "*sibcall_value_br"
9612 [(set (match_operand 0 "" "")
9613 (call (mem:QI (reg SIBCALL_REGNUM))
9614 (match_operand 1 "const_int_operand" "n")))]
9615 "SIBLING_CALL_P (insn)
9616 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
9617 "br\t%%r1"
9618 [(set_attr "op_type" "RR")
9619 (set_attr "type" "branch")
9620 (set_attr "atype" "agen")])
9621
9622 (define_insn "*sibcall_value_brc"
9623 [(set (match_operand 0 "" "")
9624 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9625 (match_operand 2 "const_int_operand" "n")))]
9626 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9627 "j\t%1"
9628 [(set_attr "op_type" "RI")
9629 (set_attr "type" "branch")])
9630
9631 (define_insn "*sibcall_value_brcl"
9632 [(set (match_operand 0 "" "")
9633 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9634 (match_operand 2 "const_int_operand" "n")))]
9635 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9636 "jg\t%1"
9637 [(set_attr "op_type" "RIL")
9638 (set_attr "type" "branch")])
9639
9640
9641 ;
9642 ; call instruction pattern(s).
9643 ;
9644
9645 (define_expand "call"
9646 [(call (match_operand 0 "" "")
9647 (match_operand 1 "" ""))
9648 (use (match_operand 2 "" ""))]
9649 ""
9650 {
9651 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
9652 gen_rtx_REG (Pmode, RETURN_REGNUM));
9653 DONE;
9654 })
9655
9656 (define_insn "*bras"
9657 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9658 (match_operand 1 "const_int_operand" "n"))
9659 (clobber (match_operand 2 "register_operand" "=r"))]
9660 "!SIBLING_CALL_P (insn)
9661 && TARGET_SMALL_EXEC
9662 && GET_MODE (operands[2]) == Pmode"
9663 "bras\t%2,%0"
9664 [(set_attr "op_type" "RI")
9665 (set_attr "type" "jsr")
9666 (set_attr "z196prop" "z196_cracked")])
9667
9668 (define_insn "*brasl"
9669 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9670 (match_operand 1 "const_int_operand" "n"))
9671 (clobber (match_operand 2 "register_operand" "=r"))]
9672 "!SIBLING_CALL_P (insn)
9673 && TARGET_CPU_ZARCH
9674 && GET_MODE (operands[2]) == Pmode"
9675 "brasl\t%2,%0"
9676 [(set_attr "op_type" "RIL")
9677 (set_attr "type" "jsr")
9678 (set_attr "z196prop" "z196_cracked")])
9679
9680 (define_insn "*basr"
9681 [(call (mem:QI (match_operand 0 "address_operand" "ZR"))
9682 (match_operand 1 "const_int_operand" "n"))
9683 (clobber (match_operand 2 "register_operand" "=r"))]
9684 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
9685 {
9686 if (get_attr_op_type (insn) == OP_TYPE_RR)
9687 return "basr\t%2,%0";
9688 else
9689 return "bas\t%2,%a0";
9690 }
9691 [(set (attr "op_type")
9692 (if_then_else (match_operand 0 "register_operand" "")
9693 (const_string "RR") (const_string "RX")))
9694 (set_attr "type" "jsr")
9695 (set_attr "atype" "agen")
9696 (set_attr "z196prop" "z196_cracked")])
9697
9698 ;
9699 ; call_value instruction pattern(s).
9700 ;
9701
9702 (define_expand "call_value"
9703 [(set (match_operand 0 "" "")
9704 (call (match_operand 1 "" "")
9705 (match_operand 2 "" "")))
9706 (use (match_operand 3 "" ""))]
9707 ""
9708 {
9709 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
9710 gen_rtx_REG (Pmode, RETURN_REGNUM));
9711 DONE;
9712 })
9713
9714 (define_insn "*bras_r"
9715 [(set (match_operand 0 "" "")
9716 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9717 (match_operand:SI 2 "const_int_operand" "n")))
9718 (clobber (match_operand 3 "register_operand" "=r"))]
9719 "!SIBLING_CALL_P (insn)
9720 && TARGET_SMALL_EXEC
9721 && GET_MODE (operands[3]) == Pmode"
9722 "bras\t%3,%1"
9723 [(set_attr "op_type" "RI")
9724 (set_attr "type" "jsr")
9725 (set_attr "z196prop" "z196_cracked")])
9726
9727 (define_insn "*brasl_r"
9728 [(set (match_operand 0 "" "")
9729 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9730 (match_operand 2 "const_int_operand" "n")))
9731 (clobber (match_operand 3 "register_operand" "=r"))]
9732 "!SIBLING_CALL_P (insn)
9733 && TARGET_CPU_ZARCH
9734 && GET_MODE (operands[3]) == Pmode"
9735 "brasl\t%3,%1"
9736 [(set_attr "op_type" "RIL")
9737 (set_attr "type" "jsr")
9738 (set_attr "z196prop" "z196_cracked")])
9739
9740 (define_insn "*basr_r"
9741 [(set (match_operand 0 "" "")
9742 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9743 (match_operand 2 "const_int_operand" "n")))
9744 (clobber (match_operand 3 "register_operand" "=r"))]
9745 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9746 {
9747 if (get_attr_op_type (insn) == OP_TYPE_RR)
9748 return "basr\t%3,%1";
9749 else
9750 return "bas\t%3,%a1";
9751 }
9752 [(set (attr "op_type")
9753 (if_then_else (match_operand 1 "register_operand" "")
9754 (const_string "RR") (const_string "RX")))
9755 (set_attr "type" "jsr")
9756 (set_attr "atype" "agen")
9757 (set_attr "z196prop" "z196_cracked")])
9758
9759 ;;
9760 ;;- Thread-local storage support.
9761 ;;
9762
9763 (define_expand "get_thread_pointer<mode>"
9764 [(set (match_operand:P 0 "nonimmediate_operand" "") (reg:P TP_REGNUM))]
9765 ""
9766 "")
9767
9768 (define_expand "set_thread_pointer<mode>"
9769 [(set (reg:P TP_REGNUM) (match_operand:P 0 "nonimmediate_operand" ""))
9770 (set (reg:P TP_REGNUM) (unspec_volatile:P [(reg:P TP_REGNUM)] UNSPECV_SET_TP))]
9771 ""
9772 "")
9773
9774 (define_insn "*set_tp"
9775 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
9776 ""
9777 ""
9778 [(set_attr "type" "none")
9779 (set_attr "length" "0")])
9780
9781 (define_insn "*tls_load_64"
9782 [(set (match_operand:DI 0 "register_operand" "=d")
9783 (unspec:DI [(match_operand:DI 1 "memory_operand" "T")
9784 (match_operand:DI 2 "" "")]
9785 UNSPEC_TLS_LOAD))]
9786 "TARGET_64BIT"
9787 "lg\t%0,%1%J2"
9788 [(set_attr "op_type" "RXE")
9789 (set_attr "z10prop" "z10_fwd_A3")])
9790
9791 (define_insn "*tls_load_31"
9792 [(set (match_operand:SI 0 "register_operand" "=d,d")
9793 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
9794 (match_operand:SI 2 "" "")]
9795 UNSPEC_TLS_LOAD))]
9796 "!TARGET_64BIT"
9797 "@
9798 l\t%0,%1%J2
9799 ly\t%0,%1%J2"
9800 [(set_attr "op_type" "RX,RXY")
9801 (set_attr "type" "load")
9802 (set_attr "cpu_facility" "*,longdisp")
9803 (set_attr "z10prop" "z10_fwd_A3,z10_fwd_A3")])
9804
9805 (define_insn "*bras_tls"
9806 [(set (match_operand 0 "" "")
9807 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9808 (match_operand 2 "const_int_operand" "n")))
9809 (clobber (match_operand 3 "register_operand" "=r"))
9810 (use (match_operand 4 "" ""))]
9811 "!SIBLING_CALL_P (insn)
9812 && TARGET_SMALL_EXEC
9813 && GET_MODE (operands[3]) == Pmode"
9814 "bras\t%3,%1%J4"
9815 [(set_attr "op_type" "RI")
9816 (set_attr "type" "jsr")
9817 (set_attr "z196prop" "z196_cracked")])
9818
9819 (define_insn "*brasl_tls"
9820 [(set (match_operand 0 "" "")
9821 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9822 (match_operand 2 "const_int_operand" "n")))
9823 (clobber (match_operand 3 "register_operand" "=r"))
9824 (use (match_operand 4 "" ""))]
9825 "!SIBLING_CALL_P (insn)
9826 && TARGET_CPU_ZARCH
9827 && GET_MODE (operands[3]) == Pmode"
9828 "brasl\t%3,%1%J4"
9829 [(set_attr "op_type" "RIL")
9830 (set_attr "type" "jsr")
9831 (set_attr "z196prop" "z196_cracked")])
9832
9833 (define_insn "*basr_tls"
9834 [(set (match_operand 0 "" "")
9835 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9836 (match_operand 2 "const_int_operand" "n")))
9837 (clobber (match_operand 3 "register_operand" "=r"))
9838 (use (match_operand 4 "" ""))]
9839 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9840 {
9841 if (get_attr_op_type (insn) == OP_TYPE_RR)
9842 return "basr\t%3,%1%J4";
9843 else
9844 return "bas\t%3,%a1%J4";
9845 }
9846 [(set (attr "op_type")
9847 (if_then_else (match_operand 1 "register_operand" "")
9848 (const_string "RR") (const_string "RX")))
9849 (set_attr "type" "jsr")
9850 (set_attr "atype" "agen")
9851 (set_attr "z196prop" "z196_cracked")])
9852
9853 ;;
9854 ;;- Atomic operations
9855 ;;
9856
9857 ;
9858 ; memory barrier patterns.
9859 ;
9860
9861 (define_expand "mem_signal_fence"
9862 [(match_operand:SI 0 "const_int_operand")] ;; model
9863 ""
9864 {
9865 /* The s390 memory model is strong enough not to require any
9866 barrier in order to synchronize a thread with itself. */
9867 DONE;
9868 })
9869
9870 (define_expand "mem_thread_fence"
9871 [(match_operand:SI 0 "const_int_operand")] ;; model
9872 ""
9873 {
9874 /* Unless this is a SEQ_CST fence, the s390 memory model is strong
9875 enough not to require barriers of any kind. */
9876 if (is_mm_seq_cst (memmodel_from_int (INTVAL (operands[0]))))
9877 {
9878 rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
9879 MEM_VOLATILE_P (mem) = 1;
9880 emit_insn (gen_mem_thread_fence_1 (mem));
9881 }
9882 DONE;
9883 })
9884
9885 ; Although bcr is superscalar on Z10, this variant will never
9886 ; become part of an execution group.
9887 ; With z196 we can make use of the fast-BCR-serialization facility.
9888 ; This allows for a slightly faster sync which is sufficient for our
9889 ; purposes.
9890 (define_insn "mem_thread_fence_1"
9891 [(set (match_operand:BLK 0 "" "")
9892 (unspec:BLK [(match_dup 0)] UNSPEC_MB))]
9893 ""
9894 {
9895 if (TARGET_Z196)
9896 return "bcr\t14,0";
9897 else
9898 return "bcr\t15,0";
9899 }
9900 [(set_attr "op_type" "RR")
9901 (set_attr "mnemonic" "bcr_flush")
9902 (set_attr "z196prop" "z196_alone")])
9903
9904 ;
9905 ; atomic load/store operations
9906 ;
9907
9908 ; Atomic loads need not examine the memory model at all.
9909 (define_expand "atomic_load<mode>"
9910 [(match_operand:DINT 0 "register_operand") ;; output
9911 (match_operand:DINT 1 "memory_operand") ;; memory
9912 (match_operand:SI 2 "const_int_operand")] ;; model
9913 ""
9914 {
9915 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9916 FAIL;
9917
9918 if (<MODE>mode == TImode)
9919 emit_insn (gen_atomic_loadti_1 (operands[0], operands[1]));
9920 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9921 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1]));
9922 else
9923 emit_move_insn (operands[0], operands[1]);
9924 DONE;
9925 })
9926
9927 ; Different from movdi_31 in that we want no splitters.
9928 (define_insn "atomic_loaddi_1"
9929 [(set (match_operand:DI 0 "register_operand" "=d,d,!*f,!*f")
9930 (unspec:DI [(match_operand:DI 1 "memory_operand" "Q,S,R,T")]
9931 UNSPEC_MOVA))]
9932 "!TARGET_ZARCH"
9933 "@
9934 lm\t%0,%M0,%S1
9935 lmy\t%0,%M0,%S1
9936 ld\t%0,%1
9937 ldy\t%0,%1"
9938 [(set_attr "op_type" "RS,RSY,RS,RSY")
9939 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9940 (set_attr "type" "lm,lm,floaddf,floaddf")])
9941
9942 (define_insn "atomic_loadti_1"
9943 [(set (match_operand:TI 0 "register_operand" "=r")
9944 (unspec:TI [(match_operand:TI 1 "memory_operand" "T")]
9945 UNSPEC_MOVA))]
9946 "TARGET_ZARCH"
9947 "lpq\t%0,%1"
9948 [(set_attr "op_type" "RXY")
9949 (set_attr "type" "other")])
9950
9951 ; Atomic stores must(?) enforce sequential consistency.
9952 (define_expand "atomic_store<mode>"
9953 [(match_operand:DINT 0 "memory_operand") ;; memory
9954 (match_operand:DINT 1 "register_operand") ;; input
9955 (match_operand:SI 2 "const_int_operand")] ;; model
9956 ""
9957 {
9958 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
9959
9960 if (MEM_ALIGN (operands[0]) < GET_MODE_BITSIZE (GET_MODE (operands[0])))
9961 FAIL;
9962
9963 if (<MODE>mode == TImode)
9964 emit_insn (gen_atomic_storeti_1 (operands[0], operands[1]));
9965 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9966 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1]));
9967 else
9968 emit_move_insn (operands[0], operands[1]);
9969 if (is_mm_seq_cst (model))
9970 emit_insn (gen_mem_thread_fence (operands[2]));
9971 DONE;
9972 })
9973
9974 ; Different from movdi_31 in that we want no splitters.
9975 (define_insn "atomic_storedi_1"
9976 [(set (match_operand:DI 0 "memory_operand" "=Q,S,R,T")
9977 (unspec:DI [(match_operand:DI 1 "register_operand" "d,d,!*f,!*f")]
9978 UNSPEC_MOVA))]
9979 "!TARGET_ZARCH"
9980 "@
9981 stm\t%1,%N1,%S0
9982 stmy\t%1,%N1,%S0
9983 std %1,%0
9984 stdy %1,%0"
9985 [(set_attr "op_type" "RS,RSY,RS,RSY")
9986 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9987 (set_attr "type" "stm,stm,fstoredf,fstoredf")])
9988
9989 (define_insn "atomic_storeti_1"
9990 [(set (match_operand:TI 0 "memory_operand" "=T")
9991 (unspec:TI [(match_operand:TI 1 "register_operand" "r")]
9992 UNSPEC_MOVA))]
9993 "TARGET_ZARCH"
9994 "stpq\t%1,%0"
9995 [(set_attr "op_type" "RXY")
9996 (set_attr "type" "other")])
9997
9998 ;
9999 ; compare and swap patterns.
10000 ;
10001
10002 (define_expand "atomic_compare_and_swap<mode>"
10003 [(match_operand:SI 0 "register_operand") ;; bool success output
10004 (match_operand:DGPR 1 "nonimmediate_operand");; oldval output
10005 (match_operand:DGPR 2 "memory_operand") ;; memory
10006 (match_operand:DGPR 3 "register_operand") ;; expected intput
10007 (match_operand:DGPR 4 "register_operand") ;; newval intput
10008 (match_operand:SI 5 "const_int_operand") ;; is_weak
10009 (match_operand:SI 6 "const_int_operand") ;; success model
10010 (match_operand:SI 7 "const_int_operand")] ;; failure model
10011 ""
10012 {
10013 rtx cc, cmp, output = operands[1];
10014
10015 if (!register_operand (output, <MODE>mode))
10016 output = gen_reg_rtx (<MODE>mode);
10017
10018 if (MEM_ALIGN (operands[2]) < GET_MODE_BITSIZE (GET_MODE (operands[2])))
10019 FAIL;
10020
10021 emit_insn (gen_atomic_compare_and_swap<mode>_internal
10022 (output, operands[2], operands[3], operands[4]));
10023
10024 /* We deliberately accept non-register operands in the predicate
10025 to ensure the write back to the output operand happens *before*
10026 the store-flags code below. This makes it easier for combine
10027 to merge the store-flags code with a potential test-and-branch
10028 pattern following (immediately!) afterwards. */
10029 if (output != operands[1])
10030 emit_move_insn (operands[1], output);
10031
10032 cc = gen_rtx_REG (CCZ1mode, CC_REGNUM);
10033 cmp = gen_rtx_EQ (SImode, cc, const0_rtx);
10034 emit_insn (gen_cstorecc4 (operands[0], cmp, cc, const0_rtx));
10035 DONE;
10036 })
10037
10038 (define_expand "atomic_compare_and_swap<mode>"
10039 [(match_operand:SI 0 "register_operand") ;; bool success output
10040 (match_operand:HQI 1 "nonimmediate_operand") ;; oldval output
10041 (match_operand:HQI 2 "memory_operand") ;; memory
10042 (match_operand:HQI 3 "general_operand") ;; expected intput
10043 (match_operand:HQI 4 "general_operand") ;; newval intput
10044 (match_operand:SI 5 "const_int_operand") ;; is_weak
10045 (match_operand:SI 6 "const_int_operand") ;; success model
10046 (match_operand:SI 7 "const_int_operand")] ;; failure model
10047 ""
10048 {
10049 s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1], operands[2],
10050 operands[3], operands[4], INTVAL (operands[5]));
10051 DONE;
10052 })
10053
10054 (define_expand "atomic_compare_and_swap<mode>_internal"
10055 [(parallel
10056 [(set (match_operand:DGPR 0 "register_operand")
10057 (match_operand:DGPR 1 "memory_operand"))
10058 (set (match_dup 1)
10059 (unspec_volatile:DGPR
10060 [(match_dup 1)
10061 (match_operand:DGPR 2 "register_operand")
10062 (match_operand:DGPR 3 "register_operand")]
10063 UNSPECV_CAS))
10064 (set (reg:CCZ1 CC_REGNUM)
10065 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
10066 "")
10067
10068 ; cdsg, csg
10069 (define_insn "*atomic_compare_and_swap<mode>_1"
10070 [(set (match_operand:TDI 0 "register_operand" "=r")
10071 (match_operand:TDI 1 "memory_operand" "+S"))
10072 (set (match_dup 1)
10073 (unspec_volatile:TDI
10074 [(match_dup 1)
10075 (match_operand:TDI 2 "register_operand" "0")
10076 (match_operand:TDI 3 "register_operand" "r")]
10077 UNSPECV_CAS))
10078 (set (reg:CCZ1 CC_REGNUM)
10079 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10080 "TARGET_ZARCH"
10081 "c<td>sg\t%0,%3,%S1"
10082 [(set_attr "op_type" "RSY")
10083 (set_attr "type" "sem")])
10084
10085 ; cds, cdsy
10086 (define_insn "*atomic_compare_and_swapdi_2"
10087 [(set (match_operand:DI 0 "register_operand" "=r,r")
10088 (match_operand:DI 1 "memory_operand" "+Q,S"))
10089 (set (match_dup 1)
10090 (unspec_volatile:DI
10091 [(match_dup 1)
10092 (match_operand:DI 2 "register_operand" "0,0")
10093 (match_operand:DI 3 "register_operand" "r,r")]
10094 UNSPECV_CAS))
10095 (set (reg:CCZ1 CC_REGNUM)
10096 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10097 "!TARGET_ZARCH"
10098 "@
10099 cds\t%0,%3,%S1
10100 cdsy\t%0,%3,%S1"
10101 [(set_attr "op_type" "RS,RSY")
10102 (set_attr "cpu_facility" "*,longdisp")
10103 (set_attr "type" "sem")])
10104
10105 ; cs, csy
10106 (define_insn "*atomic_compare_and_swapsi_3"
10107 [(set (match_operand:SI 0 "register_operand" "=r,r")
10108 (match_operand:SI 1 "memory_operand" "+Q,S"))
10109 (set (match_dup 1)
10110 (unspec_volatile:SI
10111 [(match_dup 1)
10112 (match_operand:SI 2 "register_operand" "0,0")
10113 (match_operand:SI 3 "register_operand" "r,r")]
10114 UNSPECV_CAS))
10115 (set (reg:CCZ1 CC_REGNUM)
10116 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10117 ""
10118 "@
10119 cs\t%0,%3,%S1
10120 csy\t%0,%3,%S1"
10121 [(set_attr "op_type" "RS,RSY")
10122 (set_attr "cpu_facility" "*,longdisp")
10123 (set_attr "type" "sem")])
10124
10125 ;
10126 ; Other atomic instruction patterns.
10127 ;
10128
10129 ; z196 load and add, xor, or and and instructions
10130
10131 (define_expand "atomic_fetch_<atomic><mode>"
10132 [(match_operand:GPR 0 "register_operand") ;; val out
10133 (ATOMIC_Z196:GPR
10134 (match_operand:GPR 1 "memory_operand") ;; memory
10135 (match_operand:GPR 2 "register_operand")) ;; val in
10136 (match_operand:SI 3 "const_int_operand")] ;; model
10137 "TARGET_Z196"
10138 {
10139 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
10140 FAIL;
10141
10142 emit_insn (gen_atomic_fetch_<atomic><mode>_iaf
10143 (operands[0], operands[1], operands[2]));
10144 DONE;
10145 })
10146
10147 ; lan, lang, lao, laog, lax, laxg, laa, laag
10148 (define_insn "atomic_fetch_<atomic><mode>_iaf"
10149 [(set (match_operand:GPR 0 "register_operand" "=d")
10150 (match_operand:GPR 1 "memory_operand" "+S"))
10151 (set (match_dup 1)
10152 (unspec_volatile:GPR
10153 [(ATOMIC_Z196:GPR (match_dup 1)
10154 (match_operand:GPR 2 "general_operand" "d"))]
10155 UNSPECV_ATOMIC_OP))
10156 (clobber (reg:CC CC_REGNUM))]
10157 "TARGET_Z196"
10158 "la<noxa><g>\t%0,%2,%1"
10159 [(set_attr "op_type" "RSY")
10160 (set_attr "type" "sem")])
10161
10162 ;; For SImode and larger, the optabs.c code will do just fine in
10163 ;; expanding a compare-and-swap loop. For QI/HImode, we can do
10164 ;; better by expanding our own loop.
10165
10166 (define_expand "atomic_<atomic><mode>"
10167 [(ATOMIC:HQI
10168 (match_operand:HQI 0 "memory_operand") ;; memory
10169 (match_operand:HQI 1 "general_operand")) ;; val in
10170 (match_operand:SI 2 "const_int_operand")] ;; model
10171 ""
10172 {
10173 s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
10174 operands[1], false);
10175 DONE;
10176 })
10177
10178 (define_expand "atomic_fetch_<atomic><mode>"
10179 [(match_operand:HQI 0 "register_operand") ;; val out
10180 (ATOMIC:HQI
10181 (match_operand:HQI 1 "memory_operand") ;; memory
10182 (match_operand:HQI 2 "general_operand")) ;; val in
10183 (match_operand:SI 3 "const_int_operand")] ;; model
10184 ""
10185 {
10186 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10187 operands[2], false);
10188 DONE;
10189 })
10190
10191 (define_expand "atomic_<atomic>_fetch<mode>"
10192 [(match_operand:HQI 0 "register_operand") ;; val out
10193 (ATOMIC:HQI
10194 (match_operand:HQI 1 "memory_operand") ;; memory
10195 (match_operand:HQI 2 "general_operand")) ;; val in
10196 (match_operand:SI 3 "const_int_operand")] ;; model
10197 ""
10198 {
10199 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10200 operands[2], true);
10201 DONE;
10202 })
10203
10204 (define_expand "atomic_exchange<mode>"
10205 [(match_operand:HQI 0 "register_operand") ;; val out
10206 (match_operand:HQI 1 "memory_operand") ;; memory
10207 (match_operand:HQI 2 "general_operand") ;; val in
10208 (match_operand:SI 3 "const_int_operand")] ;; model
10209 ""
10210 {
10211 s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
10212 operands[2], false);
10213 DONE;
10214 })
10215
10216 ;;
10217 ;;- Miscellaneous instructions.
10218 ;;
10219
10220 ;
10221 ; allocate stack instruction pattern(s).
10222 ;
10223
10224 (define_expand "allocate_stack"
10225 [(match_operand 0 "general_operand" "")
10226 (match_operand 1 "general_operand" "")]
10227 "TARGET_BACKCHAIN"
10228 {
10229 rtx temp = gen_reg_rtx (Pmode);
10230
10231 emit_move_insn (temp, s390_back_chain_rtx ());
10232 anti_adjust_stack (operands[1]);
10233 emit_move_insn (s390_back_chain_rtx (), temp);
10234
10235 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
10236 DONE;
10237 })
10238
10239
10240 ;
10241 ; setjmp instruction pattern.
10242 ;
10243
10244 (define_expand "builtin_setjmp_receiver"
10245 [(match_operand 0 "" "")]
10246 "flag_pic"
10247 {
10248 emit_insn (s390_load_got ());
10249 emit_use (pic_offset_table_rtx);
10250 DONE;
10251 })
10252
10253 ;; These patterns say how to save and restore the stack pointer. We need not
10254 ;; save the stack pointer at function level since we are careful to
10255 ;; preserve the backchain. At block level, we have to restore the backchain
10256 ;; when we restore the stack pointer.
10257 ;;
10258 ;; For nonlocal gotos, we must save both the stack pointer and its
10259 ;; backchain and restore both. Note that in the nonlocal case, the
10260 ;; save area is a memory location.
10261
10262 (define_expand "save_stack_function"
10263 [(match_operand 0 "general_operand" "")
10264 (match_operand 1 "general_operand" "")]
10265 ""
10266 "DONE;")
10267
10268 (define_expand "restore_stack_function"
10269 [(match_operand 0 "general_operand" "")
10270 (match_operand 1 "general_operand" "")]
10271 ""
10272 "DONE;")
10273
10274 (define_expand "restore_stack_block"
10275 [(match_operand 0 "register_operand" "")
10276 (match_operand 1 "register_operand" "")]
10277 "TARGET_BACKCHAIN"
10278 {
10279 rtx temp = gen_reg_rtx (Pmode);
10280
10281 emit_move_insn (temp, s390_back_chain_rtx ());
10282 emit_move_insn (operands[0], operands[1]);
10283 emit_move_insn (s390_back_chain_rtx (), temp);
10284
10285 DONE;
10286 })
10287
10288 (define_expand "save_stack_nonlocal"
10289 [(match_operand 0 "memory_operand" "")
10290 (match_operand 1 "register_operand" "")]
10291 ""
10292 {
10293 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10294
10295 /* Copy the backchain to the first word, sp to the second and the
10296 literal pool base to the third. */
10297
10298 rtx save_bc = adjust_address (operands[0], Pmode, 0);
10299 rtx save_sp = adjust_address (operands[0], Pmode, GET_MODE_SIZE (Pmode));
10300 rtx save_bp = adjust_address (operands[0], Pmode, 2 * GET_MODE_SIZE (Pmode));
10301
10302 if (TARGET_BACKCHAIN)
10303 emit_move_insn (save_bc, force_reg (Pmode, s390_back_chain_rtx ()));
10304
10305 emit_move_insn (save_sp, operands[1]);
10306 emit_move_insn (save_bp, base);
10307
10308 DONE;
10309 })
10310
10311 (define_expand "restore_stack_nonlocal"
10312 [(match_operand 0 "register_operand" "")
10313 (match_operand 1 "memory_operand" "")]
10314 ""
10315 {
10316 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10317 rtx temp = NULL_RTX;
10318
10319 /* Restore the backchain from the first word, sp from the second and the
10320 literal pool base from the third. */
10321
10322 rtx save_bc = adjust_address (operands[1], Pmode, 0);
10323 rtx save_sp = adjust_address (operands[1], Pmode, GET_MODE_SIZE (Pmode));
10324 rtx save_bp = adjust_address (operands[1], Pmode, 2 * GET_MODE_SIZE (Pmode));
10325
10326 if (TARGET_BACKCHAIN)
10327 temp = force_reg (Pmode, save_bc);
10328
10329 emit_move_insn (base, save_bp);
10330 emit_move_insn (operands[0], save_sp);
10331
10332 if (temp)
10333 emit_move_insn (s390_back_chain_rtx (), temp);
10334
10335 emit_use (base);
10336 DONE;
10337 })
10338
10339 (define_expand "exception_receiver"
10340 [(const_int 0)]
10341 ""
10342 {
10343 s390_set_has_landing_pad_p (true);
10344 DONE;
10345 })
10346
10347 ;
10348 ; nop instruction pattern(s).
10349 ;
10350
10351 (define_insn "nop"
10352 [(const_int 0)]
10353 ""
10354 "lr\t0,0"
10355 [(set_attr "op_type" "RR")
10356 (set_attr "z10prop" "z10_fr_E1")])
10357
10358 (define_insn "nop1"
10359 [(const_int 1)]
10360 ""
10361 "lr\t1,1"
10362 [(set_attr "op_type" "RR")])
10363
10364 ;;- Undeletable nops (used for hotpatching)
10365
10366 (define_insn "nop_2_byte"
10367 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_2_BYTE)]
10368 ""
10369 "nopr\t%%r7"
10370 [(set_attr "op_type" "RR")])
10371
10372 (define_insn "nop_4_byte"
10373 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_4_BYTE)]
10374 ""
10375 "nop\t0"
10376 [(set_attr "op_type" "RX")])
10377
10378 (define_insn "nop_6_byte"
10379 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_6_BYTE)]
10380 "TARGET_CPU_ZARCH"
10381 "brcl\t0, 0"
10382 [(set_attr "op_type" "RIL")])
10383
10384
10385 ;
10386 ; Special literal pool access instruction pattern(s).
10387 ;
10388
10389 (define_insn "*pool_entry"
10390 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
10391 UNSPECV_POOL_ENTRY)]
10392 ""
10393 {
10394 machine_mode mode = GET_MODE (PATTERN (insn));
10395 unsigned int align = GET_MODE_BITSIZE (mode);
10396 s390_output_pool_entry (operands[0], mode, align);
10397 return "";
10398 }
10399 [(set (attr "length")
10400 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
10401
10402 (define_insn "pool_align"
10403 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
10404 UNSPECV_POOL_ALIGN)]
10405 ""
10406 ".align\t%0"
10407 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10408
10409 (define_insn "pool_section_start"
10410 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
10411 ""
10412 {
10413 switch_to_section (targetm.asm_out.function_rodata_section
10414 (current_function_decl));
10415 return "";
10416 }
10417 [(set_attr "length" "0")])
10418
10419 (define_insn "pool_section_end"
10420 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
10421 ""
10422 {
10423 switch_to_section (current_function_section ());
10424 return "";
10425 }
10426 [(set_attr "length" "0")])
10427
10428 (define_insn "main_base_31_small"
10429 [(set (match_operand 0 "register_operand" "=a")
10430 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10431 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10432 "basr\t%0,0"
10433 [(set_attr "op_type" "RR")
10434 (set_attr "type" "la")
10435 (set_attr "z196prop" "z196_cracked")])
10436
10437 (define_insn "main_base_31_large"
10438 [(set (match_operand 0 "register_operand" "=a")
10439 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
10440 (set (pc) (label_ref (match_operand 2 "" "")))]
10441 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10442 "bras\t%0,%2"
10443 [(set_attr "op_type" "RI")
10444 (set_attr "z196prop" "z196_cracked")])
10445
10446 (define_insn "main_base_64"
10447 [(set (match_operand 0 "register_operand" "=a")
10448 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10449 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10450 "larl\t%0,%1"
10451 [(set_attr "op_type" "RIL")
10452 (set_attr "type" "larl")
10453 (set_attr "z10prop" "z10_fwd_A1")])
10454
10455 (define_insn "main_pool"
10456 [(set (match_operand 0 "register_operand" "=a")
10457 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
10458 "GET_MODE (operands[0]) == Pmode"
10459 {
10460 gcc_unreachable ();
10461 }
10462 [(set (attr "type")
10463 (if_then_else (match_test "TARGET_CPU_ZARCH")
10464 (const_string "larl") (const_string "la")))])
10465
10466 (define_insn "reload_base_31"
10467 [(set (match_operand 0 "register_operand" "=a")
10468 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10469 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10470 "basr\t%0,0\;la\t%0,%1-.(%0)"
10471 [(set_attr "length" "6")
10472 (set_attr "type" "la")
10473 (set_attr "z196prop" "z196_cracked")])
10474
10475 (define_insn "reload_base_64"
10476 [(set (match_operand 0 "register_operand" "=a")
10477 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10478 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10479 "larl\t%0,%1"
10480 [(set_attr "op_type" "RIL")
10481 (set_attr "type" "larl")
10482 (set_attr "z10prop" "z10_fwd_A1")])
10483
10484 (define_insn "pool"
10485 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
10486 ""
10487 {
10488 gcc_unreachable ();
10489 }
10490 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10491
10492 ;;
10493 ;; Insns related to generating the function prologue and epilogue.
10494 ;;
10495
10496
10497 (define_expand "prologue"
10498 [(use (const_int 0))]
10499 ""
10500 "s390_emit_prologue (); DONE;")
10501
10502 (define_expand "epilogue"
10503 [(use (const_int 1))]
10504 ""
10505 "s390_emit_epilogue (false); DONE;")
10506
10507 (define_expand "sibcall_epilogue"
10508 [(use (const_int 0))]
10509 ""
10510 "s390_emit_epilogue (true); DONE;")
10511
10512 ;; A direct return instruction, without using an epilogue.
10513 (define_insn "<code>"
10514 [(ANY_RETURN)]
10515 "s390_can_use_<code>_insn ()"
10516 "br\t%%r14"
10517 [(set_attr "op_type" "RR")
10518 (set_attr "type" "jsr")
10519 (set_attr "atype" "agen")])
10520
10521 (define_insn "*return"
10522 [(return)
10523 (use (match_operand 0 "register_operand" "a"))]
10524 "GET_MODE (operands[0]) == Pmode"
10525 "br\t%0"
10526 [(set_attr "op_type" "RR")
10527 (set_attr "type" "jsr")
10528 (set_attr "atype" "agen")])
10529
10530
10531 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
10532 ;; pointer. This is used for compatibility.
10533
10534 (define_expand "ptr_extend"
10535 [(set (match_operand:DI 0 "register_operand" "=r")
10536 (match_operand:SI 1 "register_operand" "r"))]
10537 "TARGET_64BIT"
10538 {
10539 emit_insn (gen_anddi3 (operands[0],
10540 gen_lowpart (DImode, operands[1]),
10541 GEN_INT (0x7fffffff)));
10542 DONE;
10543 })
10544
10545 ;; Instruction definition to expand eh_return macro to support
10546 ;; swapping in special linkage return addresses.
10547
10548 (define_expand "eh_return"
10549 [(use (match_operand 0 "register_operand" ""))]
10550 "TARGET_TPF"
10551 {
10552 s390_emit_tpf_eh_return (operands[0]);
10553 DONE;
10554 })
10555
10556 ;
10557 ; Stack Protector Patterns
10558 ;
10559
10560 (define_expand "stack_protect_set"
10561 [(set (match_operand 0 "memory_operand" "")
10562 (match_operand 1 "memory_operand" ""))]
10563 ""
10564 {
10565 #ifdef TARGET_THREAD_SSP_OFFSET
10566 operands[1]
10567 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10568 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10569 #endif
10570 if (TARGET_64BIT)
10571 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
10572 else
10573 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
10574
10575 DONE;
10576 })
10577
10578 (define_insn "stack_protect_set<mode>"
10579 [(set (match_operand:DSI 0 "memory_operand" "=Q")
10580 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
10581 ""
10582 "mvc\t%O0(%G0,%R0),%S1"
10583 [(set_attr "op_type" "SS")])
10584
10585 (define_expand "stack_protect_test"
10586 [(set (reg:CC CC_REGNUM)
10587 (compare (match_operand 0 "memory_operand" "")
10588 (match_operand 1 "memory_operand" "")))
10589 (match_operand 2 "" "")]
10590 ""
10591 {
10592 rtx cc_reg, test;
10593 #ifdef TARGET_THREAD_SSP_OFFSET
10594 operands[1]
10595 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10596 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10597 #endif
10598 if (TARGET_64BIT)
10599 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
10600 else
10601 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
10602
10603 cc_reg = gen_rtx_REG (CCZmode, CC_REGNUM);
10604 test = gen_rtx_EQ (VOIDmode, cc_reg, const0_rtx);
10605 emit_jump_insn (gen_cbranchcc4 (test, cc_reg, const0_rtx, operands[2]));
10606 DONE;
10607 })
10608
10609 (define_insn "stack_protect_test<mode>"
10610 [(set (reg:CCZ CC_REGNUM)
10611 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
10612 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
10613 ""
10614 "clc\t%O0(%G0,%R0),%S1"
10615 [(set_attr "op_type" "SS")])
10616
10617 ; This is used in s390_emit_prologue in order to prevent insns
10618 ; adjusting the stack pointer to be moved over insns writing stack
10619 ; slots using a copy of the stack pointer in a different register.
10620 (define_insn "stack_tie"
10621 [(set (match_operand:BLK 0 "memory_operand" "+m")
10622 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
10623 ""
10624 ""
10625 [(set_attr "length" "0")])
10626
10627
10628 (define_insn "stack_restore_from_fpr"
10629 [(set (reg:DI STACK_REGNUM)
10630 (match_operand:DI 0 "register_operand" "f"))
10631 (clobber (mem:BLK (scratch)))]
10632 "TARGET_Z10"
10633 "lgdr\t%%r15,%0"
10634 [(set_attr "op_type" "RRE")])
10635
10636 ;
10637 ; Data prefetch patterns
10638 ;
10639
10640 (define_insn "prefetch"
10641 [(prefetch (match_operand 0 "address_operand" "ZT,X")
10642 (match_operand:SI 1 "const_int_operand" " n,n")
10643 (match_operand:SI 2 "const_int_operand" " n,n"))]
10644 "TARGET_Z10"
10645 {
10646 switch (which_alternative)
10647 {
10648 case 0:
10649 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
10650 case 1:
10651 if (larl_operand (operands[0], Pmode))
10652 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
10653 /* fallthrough */
10654 default:
10655
10656 /* This might be reached for symbolic operands with an odd
10657 addend. We simply omit the prefetch for such rare cases. */
10658
10659 return "";
10660 }
10661 }
10662 [(set_attr "type" "load,larl")
10663 (set_attr "op_type" "RXY,RIL")
10664 (set_attr "z10prop" "z10_super")
10665 (set_attr "z196prop" "z196_alone")])
10666
10667
10668 ;
10669 ; Byte swap instructions
10670 ;
10671
10672 ; FIXME: There is also mvcin but we cannot use it since src and target
10673 ; may overlap.
10674 (define_insn "bswap<mode>2"
10675 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,T")
10676 (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,T,d")))]
10677 "TARGET_CPU_ZARCH"
10678 "@
10679 lrv<g>r\t%0,%1
10680 lrv<g>\t%0,%1
10681 strv<g>\t%1,%0"
10682 [(set_attr "type" "*,load,store")
10683 (set_attr "op_type" "RRE,RXY,RXY")
10684 (set_attr "z10prop" "z10_super")])
10685
10686 (define_insn "bswaphi2"
10687 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,T")
10688 (bswap:HI (match_operand:HI 1 "nonimmediate_operand" " d,T,d")))]
10689 "TARGET_CPU_ZARCH"
10690 "@
10691 #
10692 lrvh\t%0,%1
10693 strvh\t%1,%0"
10694 [(set_attr "type" "*,load,store")
10695 (set_attr "op_type" "RRE,RXY,RXY")
10696 (set_attr "z10prop" "z10_super")])
10697
10698 (define_split
10699 [(set (match_operand:HI 0 "register_operand" "")
10700 (bswap:HI (match_operand:HI 1 "register_operand" "")))]
10701 "TARGET_CPU_ZARCH"
10702 [(set (match_dup 2) (bswap:SI (match_dup 3)))
10703 (set (match_dup 2) (lshiftrt:SI (match_dup 2) (const_int 16)))]
10704 {
10705 operands[2] = simplify_gen_subreg (SImode, operands[0], HImode, 0);
10706 operands[3] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
10707 })
10708
10709
10710 ;
10711 ; Population count instruction
10712 ;
10713
10714 ; The S/390 popcount instruction counts the bits of op1 in 8 byte
10715 ; portions and stores the result in the corresponding bytes in op0.
10716 (define_insn "*popcount<mode>"
10717 [(set (match_operand:INT 0 "register_operand" "=d")
10718 (unspec:INT [(match_operand:INT 1 "register_operand" "d")] UNSPEC_POPCNT))
10719 (clobber (reg:CC CC_REGNUM))]
10720 "TARGET_Z196"
10721 "popcnt\t%0,%1"
10722 [(set_attr "op_type" "RRE")])
10723
10724 (define_expand "popcountdi2"
10725 [; popcnt op0, op1
10726 (parallel [(set (match_operand:DI 0 "register_operand" "")
10727 (unspec:DI [(match_operand:DI 1 "register_operand")]
10728 UNSPEC_POPCNT))
10729 (clobber (reg:CC CC_REGNUM))])
10730 ; sllg op2, op0, 32
10731 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 32)))
10732 ; agr op0, op2
10733 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10734 (clobber (reg:CC CC_REGNUM))])
10735 ; sllg op2, op0, 16
10736 (set (match_dup 2)
10737 (ashift:DI (match_dup 0) (const_int 16)))
10738 ; agr op0, op2
10739 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10740 (clobber (reg:CC CC_REGNUM))])
10741 ; sllg op2, op0, 8
10742 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 8)))
10743 ; agr op0, op2
10744 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10745 (clobber (reg:CC CC_REGNUM))])
10746 ; srlg op0, op0, 56
10747 (set (match_dup 0) (lshiftrt:DI (match_dup 0) (const_int 56)))]
10748 "TARGET_Z196 && TARGET_64BIT"
10749 "operands[2] = gen_reg_rtx (DImode);")
10750
10751 (define_expand "popcountsi2"
10752 [; popcnt op0, op1
10753 (parallel [(set (match_operand:SI 0 "register_operand" "")
10754 (unspec:SI [(match_operand:SI 1 "register_operand")]
10755 UNSPEC_POPCNT))
10756 (clobber (reg:CC CC_REGNUM))])
10757 ; sllk op2, op0, 16
10758 (set (match_dup 2)
10759 (ashift:SI (match_dup 0) (const_int 16)))
10760 ; ar op0, op2
10761 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10762 (clobber (reg:CC CC_REGNUM))])
10763 ; sllk op2, op0, 8
10764 (set (match_dup 2) (ashift:SI (match_dup 0) (const_int 8)))
10765 ; ar op0, op2
10766 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10767 (clobber (reg:CC CC_REGNUM))])
10768 ; srl op0, op0, 24
10769 (set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 24)))]
10770 "TARGET_Z196"
10771 "operands[2] = gen_reg_rtx (SImode);")
10772
10773 (define_expand "popcounthi2"
10774 [; popcnt op0, op1
10775 (parallel [(set (match_operand:HI 0 "register_operand" "")
10776 (unspec:HI [(match_operand:HI 1 "register_operand")]
10777 UNSPEC_POPCNT))
10778 (clobber (reg:CC CC_REGNUM))])
10779 ; sllk op2, op0, 8
10780 (set (match_dup 2)
10781 (ashift:SI (match_dup 0) (const_int 8)))
10782 ; ar op0, op2
10783 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10784 (clobber (reg:CC CC_REGNUM))])
10785 ; srl op0, op0, 8
10786 (set (match_dup 0) (lshiftrt:HI (match_dup 0) (const_int 8)))]
10787 "TARGET_Z196"
10788 "operands[2] = gen_reg_rtx (SImode);")
10789
10790 (define_expand "popcountqi2"
10791 [; popcnt op0, op1
10792 (parallel [(set (match_operand:QI 0 "register_operand" "")
10793 (unspec:QI [(match_operand:QI 1 "register_operand")]
10794 UNSPEC_POPCNT))
10795 (clobber (reg:CC CC_REGNUM))])]
10796 "TARGET_Z196"
10797 "")
10798
10799 ;;
10800 ;;- Copy sign instructions
10801 ;;
10802
10803 (define_insn "copysign<mode>3"
10804 [(set (match_operand:FP 0 "register_operand" "=f")
10805 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
10806 (match_operand:FP 2 "register_operand" "f")]
10807 UNSPEC_COPYSIGN))]
10808 "TARGET_Z196"
10809 "cpsdr\t%0,%2,%1"
10810 [(set_attr "op_type" "RRF")
10811 (set_attr "type" "fsimp<mode>")])
10812
10813
10814 ;;
10815 ;;- Transactional execution instructions
10816 ;;
10817
10818 ; This splitter helps combine to make use of CC directly when
10819 ; comparing the integer result of a tbegin builtin with a constant.
10820 ; The unspec is already removed by canonicalize_comparison. So this
10821 ; splitters only job is to turn the PARALLEL into separate insns
10822 ; again. Unfortunately this only works with the very first cc/int
10823 ; compare since combine is not able to deal with data flow across
10824 ; basic block boundaries.
10825
10826 ; It needs to be an insn pattern as well since combine does not apply
10827 ; the splitter directly. Combine would only use it if it actually
10828 ; would reduce the number of instructions.
10829 (define_insn_and_split "*ccraw_to_int"
10830 [(set (pc)
10831 (if_then_else
10832 (match_operator 0 "s390_eqne_operator"
10833 [(reg:CCRAW CC_REGNUM)
10834 (match_operand 1 "const_int_operand" "")])
10835 (label_ref (match_operand 2 "" ""))
10836 (pc)))
10837 (set (match_operand:SI 3 "register_operand" "=d")
10838 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10839 ""
10840 "#"
10841 ""
10842 [(set (match_dup 3)
10843 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))
10844 (set (pc)
10845 (if_then_else (match_op_dup 0 [(reg:CCRAW CC_REGNUM) (match_dup 1)])
10846 (label_ref (match_dup 2))
10847 (pc)))]
10848 "")
10849
10850 ; Non-constrained transaction begin
10851
10852 (define_expand "tbegin"
10853 [(match_operand:SI 0 "register_operand" "")
10854 (match_operand:BLK 1 "memory_operand" "")]
10855 "TARGET_HTM"
10856 {
10857 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, true);
10858 DONE;
10859 })
10860
10861 (define_expand "tbegin_nofloat"
10862 [(match_operand:SI 0 "register_operand" "")
10863 (match_operand:BLK 1 "memory_operand" "")]
10864 "TARGET_HTM"
10865 {
10866 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, false);
10867 DONE;
10868 })
10869
10870 (define_expand "tbegin_retry"
10871 [(match_operand:SI 0 "register_operand" "")
10872 (match_operand:BLK 1 "memory_operand" "")
10873 (match_operand:SI 2 "general_operand" "")]
10874 "TARGET_HTM"
10875 {
10876 s390_expand_tbegin (operands[0], operands[1], operands[2], true);
10877 DONE;
10878 })
10879
10880 (define_expand "tbegin_retry_nofloat"
10881 [(match_operand:SI 0 "register_operand" "")
10882 (match_operand:BLK 1 "memory_operand" "")
10883 (match_operand:SI 2 "general_operand" "")]
10884 "TARGET_HTM"
10885 {
10886 s390_expand_tbegin (operands[0], operands[1], operands[2], false);
10887 DONE;
10888 })
10889
10890 ; Clobber VRs since they don't get restored
10891 (define_insn "tbegin_1_z13"
10892 [(set (reg:CCRAW CC_REGNUM)
10893 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10894 UNSPECV_TBEGIN))
10895 (set (match_operand:BLK 1 "memory_operand" "=Q")
10896 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10897 (clobber (reg:TI 16)) (clobber (reg:TI 38))
10898 (clobber (reg:TI 17)) (clobber (reg:TI 39))
10899 (clobber (reg:TI 18)) (clobber (reg:TI 40))
10900 (clobber (reg:TI 19)) (clobber (reg:TI 41))
10901 (clobber (reg:TI 20)) (clobber (reg:TI 42))
10902 (clobber (reg:TI 21)) (clobber (reg:TI 43))
10903 (clobber (reg:TI 22)) (clobber (reg:TI 44))
10904 (clobber (reg:TI 23)) (clobber (reg:TI 45))
10905 (clobber (reg:TI 24)) (clobber (reg:TI 46))
10906 (clobber (reg:TI 25)) (clobber (reg:TI 47))
10907 (clobber (reg:TI 26)) (clobber (reg:TI 48))
10908 (clobber (reg:TI 27)) (clobber (reg:TI 49))
10909 (clobber (reg:TI 28)) (clobber (reg:TI 50))
10910 (clobber (reg:TI 29)) (clobber (reg:TI 51))
10911 (clobber (reg:TI 30)) (clobber (reg:TI 52))
10912 (clobber (reg:TI 31)) (clobber (reg:TI 53))]
10913 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10914 ; not supposed to be used for immediates (see genpreds.c).
10915 "TARGET_VX && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10916 "tbegin\t%1,%x0"
10917 [(set_attr "op_type" "SIL")])
10918
10919 (define_insn "tbegin_1"
10920 [(set (reg:CCRAW CC_REGNUM)
10921 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10922 UNSPECV_TBEGIN))
10923 (set (match_operand:BLK 1 "memory_operand" "=Q")
10924 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10925 (clobber (reg:DF 16))
10926 (clobber (reg:DF 17))
10927 (clobber (reg:DF 18))
10928 (clobber (reg:DF 19))
10929 (clobber (reg:DF 20))
10930 (clobber (reg:DF 21))
10931 (clobber (reg:DF 22))
10932 (clobber (reg:DF 23))
10933 (clobber (reg:DF 24))
10934 (clobber (reg:DF 25))
10935 (clobber (reg:DF 26))
10936 (clobber (reg:DF 27))
10937 (clobber (reg:DF 28))
10938 (clobber (reg:DF 29))
10939 (clobber (reg:DF 30))
10940 (clobber (reg:DF 31))]
10941 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10942 ; not supposed to be used for immediates (see genpreds.c).
10943 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10944 "tbegin\t%1,%x0"
10945 [(set_attr "op_type" "SIL")])
10946
10947 ; Same as above but without the FPR clobbers
10948 (define_insn "tbegin_nofloat_1"
10949 [(set (reg:CCRAW CC_REGNUM)
10950 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10951 UNSPECV_TBEGIN))
10952 (set (match_operand:BLK 1 "memory_operand" "=Q")
10953 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))]
10954 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10955 "tbegin\t%1,%x0"
10956 [(set_attr "op_type" "SIL")])
10957
10958
10959 ; Constrained transaction begin
10960
10961 (define_expand "tbeginc"
10962 [(set (reg:CCRAW CC_REGNUM)
10963 (unspec_volatile:CCRAW [(const_int TBEGINC_MASK)]
10964 UNSPECV_TBEGINC))]
10965 "TARGET_HTM"
10966 "")
10967
10968 (define_insn "*tbeginc_1"
10969 [(set (reg:CCRAW CC_REGNUM)
10970 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" " D")]
10971 UNSPECV_TBEGINC))]
10972 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10973 "tbeginc\t0,%x0"
10974 [(set_attr "op_type" "SIL")])
10975
10976 ; Transaction end
10977
10978 (define_expand "tend"
10979 [(set (reg:CCRAW CC_REGNUM)
10980 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))
10981 (set (match_operand:SI 0 "register_operand" "")
10982 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10983 "TARGET_HTM"
10984 "")
10985
10986 (define_insn "*tend_1"
10987 [(set (reg:CCRAW CC_REGNUM)
10988 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))]
10989 "TARGET_HTM"
10990 "tend"
10991 [(set_attr "op_type" "S")])
10992
10993 ; Transaction abort
10994
10995 (define_expand "tabort"
10996 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "")]
10997 UNSPECV_TABORT)]
10998 "TARGET_HTM && operands != NULL"
10999 {
11000 if (CONST_INT_P (operands[0])
11001 && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 255)
11002 {
11003 error ("invalid transaction abort code: " HOST_WIDE_INT_PRINT_DEC
11004 ". Values in range 0 through 255 are reserved.",
11005 INTVAL (operands[0]));
11006 FAIL;
11007 }
11008 })
11009
11010 (define_insn "*tabort_1"
11011 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "aJ")]
11012 UNSPECV_TABORT)]
11013 "TARGET_HTM && operands != NULL"
11014 "tabort\t%Y0"
11015 [(set_attr "op_type" "S")])
11016
11017 (define_insn "*tabort_1_plus"
11018 [(unspec_volatile [(plus:SI (match_operand:SI 0 "register_operand" "a")
11019 (match_operand:SI 1 "const_int_operand" "J"))]
11020 UNSPECV_TABORT)]
11021 "TARGET_HTM && operands != NULL
11022 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[1]), 'J', \"J\")"
11023 "tabort\t%1(%0)"
11024 [(set_attr "op_type" "S")])
11025
11026 ; Transaction extract nesting depth
11027
11028 (define_insn "etnd"
11029 [(set (match_operand:SI 0 "register_operand" "=d")
11030 (unspec_volatile:SI [(const_int 0)] UNSPECV_ETND))]
11031 "TARGET_HTM"
11032 "etnd\t%0"
11033 [(set_attr "op_type" "RRE")])
11034
11035 ; Non-transactional store
11036
11037 (define_insn "ntstg"
11038 [(set (match_operand:DI 0 "memory_operand" "=T")
11039 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "d")]
11040 UNSPECV_NTSTG))]
11041 "TARGET_HTM"
11042 "ntstg\t%1,%0"
11043 [(set_attr "op_type" "RXY")])
11044
11045 ; Transaction perform processor assist
11046
11047 (define_expand "tx_assist"
11048 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")
11049 (reg:SI GPR0_REGNUM)
11050 (const_int 1)]
11051 UNSPECV_PPA)]
11052 "TARGET_HTM"
11053 "")
11054
11055 (define_insn "*ppa"
11056 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")
11057 (match_operand:SI 1 "register_operand" "d")
11058 (match_operand 2 "const_int_operand" "I")]
11059 UNSPECV_PPA)]
11060 "TARGET_HTM && INTVAL (operands[2]) < 16"
11061 "ppa\t%0,%1,%2"
11062 [(set_attr "op_type" "RRF")])
11063
11064
11065 ; Set and get floating point control register
11066
11067 (define_insn "sfpc"
11068 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")]
11069 UNSPECV_SFPC)]
11070 "TARGET_HARD_FLOAT"
11071 "sfpc\t%0")
11072
11073 (define_insn "efpc"
11074 [(set (match_operand:SI 0 "register_operand" "=d")
11075 (unspec_volatile:SI [(const_int 0)] UNSPECV_EFPC))]
11076 "TARGET_HARD_FLOAT"
11077 "efpc\t%0")
11078
11079
11080 ; Load count to block boundary
11081
11082 (define_insn "lcbb"
11083 [(set (match_operand:SI 0 "register_operand" "=d")
11084 (unspec:SI [(match_operand 1 "address_operand" "ZR")
11085 (match_operand:SI 2 "immediate_operand" "C")] UNSPEC_LCBB))
11086 (clobber (reg:CC CC_REGNUM))]
11087 "TARGET_Z13"
11088 "lcbb\t%0,%a1,%b2"
11089 [(set_attr "op_type" "VRX")])
11090
11091 ; Handle -fsplit-stack.
11092
11093 (define_expand "split_stack_prologue"
11094 [(const_int 0)]
11095 ""
11096 {
11097 s390_expand_split_stack_prologue ();
11098 DONE;
11099 })
11100
11101 ;; If there are operand 0 bytes available on the stack, jump to
11102 ;; operand 1.
11103
11104 (define_expand "split_stack_space_check"
11105 [(set (pc) (if_then_else
11106 (ltu (minus (reg 15)
11107 (match_operand 0 "register_operand"))
11108 (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
11109 (label_ref (match_operand 1))
11110 (pc)))]
11111 ""
11112 {
11113 /* Offset from thread pointer to __private_ss. */
11114 int psso = TARGET_64BIT ? 0x38 : 0x20;
11115 rtx tp = s390_get_thread_pointer ();
11116 rtx guard = gen_rtx_MEM (Pmode, plus_constant (Pmode, tp, psso));
11117 rtx reg = gen_reg_rtx (Pmode);
11118 rtx cc;
11119 if (TARGET_64BIT)
11120 emit_insn (gen_subdi3 (reg, stack_pointer_rtx, operands[0]));
11121 else
11122 emit_insn (gen_subsi3 (reg, stack_pointer_rtx, operands[0]));
11123 cc = s390_emit_compare (GT, reg, guard);
11124 s390_emit_jump (operands[1], cc);
11125
11126 DONE;
11127 })
11128
11129 ;; __morestack parameter block for split stack prologue. Parameters are:
11130 ;; parameter block label, label to be called by __morestack, frame size,
11131 ;; stack parameter size.
11132
11133 (define_insn "split_stack_data"
11134 [(unspec_volatile [(match_operand 0 "" "X")
11135 (match_operand 1 "" "X")
11136 (match_operand 2 "const_int_operand" "X")
11137 (match_operand 3 "const_int_operand" "X")]
11138 UNSPECV_SPLIT_STACK_DATA)]
11139 "TARGET_CPU_ZARCH"
11140 {
11141 switch_to_section (targetm.asm_out.function_rodata_section
11142 (current_function_decl));
11143
11144 if (TARGET_64BIT)
11145 output_asm_insn (".align\t8", operands);
11146 else
11147 output_asm_insn (".align\t4", operands);
11148 (*targetm.asm_out.internal_label) (asm_out_file, "L",
11149 CODE_LABEL_NUMBER (operands[0]));
11150 if (TARGET_64BIT)
11151 {
11152 output_asm_insn (".quad\t%2", operands);
11153 output_asm_insn (".quad\t%3", operands);
11154 output_asm_insn (".quad\t%1-%0", operands);
11155 }
11156 else
11157 {
11158 output_asm_insn (".long\t%2", operands);
11159 output_asm_insn (".long\t%3", operands);
11160 output_asm_insn (".long\t%1-%0", operands);
11161 }
11162
11163 switch_to_section (current_function_section ());
11164 return "";
11165 }
11166 [(set_attr "length" "0")])
11167
11168
11169 ;; A jg with minimal fuss for use in split stack prologue.
11170
11171 (define_expand "split_stack_call"
11172 [(match_operand 0 "bras_sym_operand" "X")
11173 (match_operand 1 "" "")]
11174 "TARGET_CPU_ZARCH"
11175 {
11176 if (TARGET_64BIT)
11177 emit_jump_insn (gen_split_stack_call_di (operands[0], operands[1]));
11178 else
11179 emit_jump_insn (gen_split_stack_call_si (operands[0], operands[1]));
11180 DONE;
11181 })
11182
11183 (define_insn "split_stack_call_<mode>"
11184 [(set (pc) (label_ref (match_operand 1 "" "")))
11185 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11186 (reg:P 1)]
11187 UNSPECV_SPLIT_STACK_CALL))]
11188 "TARGET_CPU_ZARCH"
11189 "jg\t%0"
11190 [(set_attr "op_type" "RIL")
11191 (set_attr "type" "branch")])
11192
11193 ;; Also a conditional one.
11194
11195 (define_expand "split_stack_cond_call"
11196 [(match_operand 0 "bras_sym_operand" "X")
11197 (match_operand 1 "" "")
11198 (match_operand 2 "" "")]
11199 "TARGET_CPU_ZARCH"
11200 {
11201 if (TARGET_64BIT)
11202 emit_jump_insn (gen_split_stack_cond_call_di (operands[0], operands[1], operands[2]));
11203 else
11204 emit_jump_insn (gen_split_stack_cond_call_si (operands[0], operands[1], operands[2]));
11205 DONE;
11206 })
11207
11208 (define_insn "split_stack_cond_call_<mode>"
11209 [(set (pc)
11210 (if_then_else
11211 (match_operand 1 "" "")
11212 (label_ref (match_operand 2 "" ""))
11213 (pc)))
11214 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11215 (reg:P 1)]
11216 UNSPECV_SPLIT_STACK_CALL))]
11217 "TARGET_CPU_ZARCH"
11218 "jg%C1\t%0"
11219 [(set_attr "op_type" "RIL")
11220 (set_attr "type" "branch")])
11221
11222 (define_insn "osc_break"
11223 [(unspec_volatile [(const_int 0)] UNSPECV_OSC_BREAK)]
11224 ""
11225 "bcr\t7,%%r0"
11226 [(set_attr "op_type" "RR")])