S/390: Add static OSC breaker if necessary.
[gcc.git] / gcc / config / s390 / s390.md
1 ;;- Machine description for GNU compiler -- S/390 / zSeries version.
2 ;; Copyright (C) 1999-2016 Free Software Foundation, Inc.
3 ;; Contributed by Hartmut Penner (hpenner@de.ibm.com) and
4 ;; Ulrich Weigand (uweigand@de.ibm.com) and
5 ;; Andreas Krebbel (Andreas.Krebbel@de.ibm.com)
6
7 ;; This file is part of GCC.
8
9 ;; GCC is free software; you can redistribute it and/or modify it under
10 ;; the terms of the GNU General Public License as published by the Free
11 ;; Software Foundation; either version 3, or (at your option) any later
12 ;; version.
13
14 ;; GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 ;; WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 ;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17 ;; for more details.
18
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GCC; see the file COPYING3. If not see
21 ;; <http://www.gnu.org/licenses/>.
22
23 ;;
24 ;; See constraints.md for a description of constraints specific to s390.
25 ;;
26
27 ;; Special formats used for outputting 390 instructions.
28 ;;
29 ;; %C: print opcode suffix for branch condition.
30 ;; %D: print opcode suffix for inverse branch condition.
31 ;; %J: print tls_load/tls_gdcall/tls_ldcall suffix
32 ;; %G: print the size of the operand in bytes.
33 ;; %O: print only the displacement of a memory reference.
34 ;; %R: print only the base register of a memory reference.
35 ;; %S: print S-type memory reference (base+displacement).
36 ;; %N: print the second word of a DImode operand.
37 ;; %M: print the second word of a TImode operand.
38 ;; %Y: print shift count operand.
39 ;;
40 ;; %b: print integer X as if it's an unsigned byte.
41 ;; %c: print integer X as if it's an signed byte.
42 ;; %x: print integer X as if it's an unsigned halfword.
43 ;; %h: print integer X as if it's a signed halfword.
44 ;; %i: print the first nonzero HImode part of X.
45 ;; %j: print the first HImode part unequal to -1 of X.
46 ;; %k: print the first nonzero SImode part of X.
47 ;; %m: print the first SImode part unequal to -1 of X.
48 ;; %o: print integer X as if it's an unsigned 32bit word.
49 ;;
50 ;; We have a special constraint for pattern matching.
51 ;;
52 ;; s_operand -- Matches a valid S operand in a RS, SI or SS type instruction.
53 ;;
54
55 ;;
56 ;; UNSPEC usage
57 ;;
58
59 (define_c_enum "unspec" [
60 ; Miscellaneous
61 UNSPEC_ROUND
62 UNSPEC_ICM
63 UNSPEC_TIE
64
65 ; Convert CC into a str comparison result and copy it into an
66 ; integer register
67 ; cc0->0, cc1->1, cc2->-1, (cc3->-1)
68 UNSPEC_STRCMPCC_TO_INT
69
70 ; Copy CC as is into the lower 2 bits of an integer register
71 UNSPEC_CC_TO_INT
72
73 ; The right hand side of an setmem
74 UNSPEC_REPLICATE_BYTE
75
76 ; GOT/PLT and lt-relative accesses
77 UNSPEC_LTREL_OFFSET
78 UNSPEC_LTREL_BASE
79 UNSPEC_POOL_OFFSET
80 UNSPEC_GOTENT
81 UNSPEC_GOT
82 UNSPEC_GOTOFF
83 UNSPEC_PLT
84 UNSPEC_PLTOFF
85
86 ; Literal pool
87 UNSPEC_RELOAD_BASE
88 UNSPEC_MAIN_BASE
89 UNSPEC_LTREF
90 UNSPEC_INSN
91 UNSPEC_EXECUTE
92
93 ; Atomic Support
94 UNSPEC_MB
95 UNSPEC_MOVA
96
97 ; TLS relocation specifiers
98 UNSPEC_TLSGD
99 UNSPEC_TLSLDM
100 UNSPEC_NTPOFF
101 UNSPEC_DTPOFF
102 UNSPEC_GOTNTPOFF
103 UNSPEC_INDNTPOFF
104
105 ; TLS support
106 UNSPEC_TLSLDM_NTPOFF
107 UNSPEC_TLS_LOAD
108
109 ; String Functions
110 UNSPEC_SRST
111 UNSPEC_MVST
112
113 ; Stack Smashing Protector
114 UNSPEC_SP_SET
115 UNSPEC_SP_TEST
116
117 ; Split stack support
118 UNSPEC_STACK_CHECK
119
120 ; Test Data Class (TDC)
121 UNSPEC_TDC_INSN
122
123 ; Population Count
124 UNSPEC_POPCNT
125 UNSPEC_COPYSIGN
126
127 ; Load FP Integer
128 UNSPEC_FPINT_FLOOR
129 UNSPEC_FPINT_BTRUNC
130 UNSPEC_FPINT_ROUND
131 UNSPEC_FPINT_CEIL
132 UNSPEC_FPINT_NEARBYINT
133 UNSPEC_FPINT_RINT
134
135 UNSPEC_LCBB
136
137 ; Vector
138 UNSPEC_VEC_SMULT_HI
139 UNSPEC_VEC_UMULT_HI
140 UNSPEC_VEC_SMULT_LO
141 UNSPEC_VEC_SMULT_EVEN
142 UNSPEC_VEC_UMULT_EVEN
143 UNSPEC_VEC_SMULT_ODD
144 UNSPEC_VEC_UMULT_ODD
145
146 UNSPEC_VEC_VMAL
147 UNSPEC_VEC_VMAH
148 UNSPEC_VEC_VMALH
149 UNSPEC_VEC_VMAE
150 UNSPEC_VEC_VMALE
151 UNSPEC_VEC_VMAO
152 UNSPEC_VEC_VMALO
153
154 UNSPEC_VEC_GATHER
155 UNSPEC_VEC_EXTRACT
156 UNSPEC_VEC_INSERT_AND_ZERO
157 UNSPEC_VEC_LOAD_BNDRY
158 UNSPEC_VEC_LOAD_LEN
159 UNSPEC_VEC_MERGEH
160 UNSPEC_VEC_MERGEL
161 UNSPEC_VEC_PACK
162 UNSPEC_VEC_PACK_SATURATE
163 UNSPEC_VEC_PACK_SATURATE_CC
164 UNSPEC_VEC_PACK_SATURATE_GENCC
165 UNSPEC_VEC_PACK_UNSIGNED_SATURATE
166 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC
167 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC
168 UNSPEC_VEC_PERM
169 UNSPEC_VEC_PERMI
170 UNSPEC_VEC_EXTEND
171 UNSPEC_VEC_STORE_LEN
172 UNSPEC_VEC_UNPACKH
173 UNSPEC_VEC_UNPACKH_L
174 UNSPEC_VEC_UNPACKL
175 UNSPEC_VEC_UNPACKL_L
176 UNSPEC_VEC_ADDC
177 UNSPEC_VEC_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") (CCVH "h") (CCVHU "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 [(and:P
3406 (match_operand:P 2 "setmem_operand" "Y")
3407 (match_operand:P 4 "const_int_operand" "n"))
3408 (subreg:P (match_dup 3) <modesize>)]
3409 UNSPEC_REPLICATE_BYTE))
3410 (use (match_operand:<DBL> 1 "register_operand" "d"))
3411 (clobber (reg:CC CC_REGNUM))]
3412 "(TARGET_64BIT || !TARGET_ZARCH) &&
3413 (INTVAL (operands[4]) & 255) == 255"
3414 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3415 [(set_attr "length" "8")
3416 (set_attr "type" "vs")])
3417
3418 ; Variants for 31 bit + Zarch, necessary because of the odd in-register offsets
3419 ; of the SImode subregs.
3420
3421 (define_insn "*setmem_long_31z"
3422 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3423 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3424 (unspec:BLK [(match_operand:SI 2 "setmem_operand" "Y")
3425 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3426 (use (match_operand:TI 1 "register_operand" "d"))
3427 (clobber (reg:CC CC_REGNUM))]
3428 "!TARGET_64BIT && TARGET_ZARCH"
3429 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3430 [(set_attr "length" "8")
3431 (set_attr "type" "vs")])
3432
3433 (define_insn "*setmem_long_and_31z"
3434 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3435 (set (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "0") 4))
3436 (unspec:BLK [(and:SI
3437 (match_operand:SI 2 "setmem_operand" "Y")
3438 (match_operand:SI 4 "const_int_operand" "n"))
3439 (subreg:SI (match_dup 3) 12)] UNSPEC_REPLICATE_BYTE))
3440 (use (match_operand:TI 1 "register_operand" "d"))
3441 (clobber (reg:CC CC_REGNUM))]
3442 "(!TARGET_64BIT && TARGET_ZARCH) &&
3443 (INTVAL (operands[4]) & 255) == 255"
3444 "mvcle\t%0,%1,%Y2\;jo\t.-4"
3445 [(set_attr "length" "8")
3446 (set_attr "type" "vs")])
3447
3448 ;
3449 ; cmpmemM instruction pattern(s).
3450 ;
3451
3452 (define_expand "cmpmemsi"
3453 [(set (match_operand:SI 0 "register_operand" "")
3454 (compare:SI (match_operand:BLK 1 "memory_operand" "")
3455 (match_operand:BLK 2 "memory_operand" "") ) )
3456 (use (match_operand:SI 3 "general_operand" ""))
3457 (use (match_operand:SI 4 "" ""))]
3458 ""
3459 {
3460 if (s390_expand_cmpmem (operands[0], operands[1],
3461 operands[2], operands[3]))
3462 DONE;
3463 else
3464 FAIL;
3465 })
3466
3467 ; Compare a block that is up to 256 bytes in length.
3468 ; The block length is taken as (operands[2] % 256) + 1.
3469
3470 (define_expand "cmpmem_short"
3471 [(parallel
3472 [(set (reg:CCU CC_REGNUM)
3473 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3474 (match_operand:BLK 1 "memory_operand" "")))
3475 (use (match_operand 2 "nonmemory_operand" ""))
3476 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3477 (clobber (match_dup 3))])]
3478 ""
3479 "operands[3] = gen_rtx_SCRATCH (Pmode);")
3480
3481 (define_insn "*cmpmem_short"
3482 [(set (reg:CCU CC_REGNUM)
3483 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
3484 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
3485 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
3486 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
3487 (clobber (match_scratch:P 4 "=X,X,X,&a"))]
3488 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)"
3489 "#"
3490 [(set_attr "type" "cs")
3491 (set_attr "cpu_facility" "*,*,z10,cpu_zarch")])
3492
3493 (define_split
3494 [(set (reg:CCU CC_REGNUM)
3495 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3496 (match_operand:BLK 1 "memory_operand" "")))
3497 (use (match_operand 2 "const_int_operand" ""))
3498 (use (match_operand 3 "immediate_operand" ""))
3499 (clobber (scratch))]
3500 "reload_completed"
3501 [(parallel
3502 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3503 (use (match_dup 2))])]
3504 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
3505
3506 (define_split
3507 [(set (reg:CCU CC_REGNUM)
3508 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3509 (match_operand:BLK 1 "memory_operand" "")))
3510 (use (match_operand 2 "register_operand" ""))
3511 (use (match_operand 3 "memory_operand" ""))
3512 (clobber (scratch))]
3513 "reload_completed"
3514 [(parallel
3515 [(unspec [(match_dup 2) (match_dup 3)
3516 (const_int 0)] UNSPEC_EXECUTE)
3517 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3518 (use (const_int 1))])]
3519 "")
3520
3521 (define_split
3522 [(set (reg:CCU CC_REGNUM)
3523 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3524 (match_operand:BLK 1 "memory_operand" "")))
3525 (use (match_operand 2 "register_operand" ""))
3526 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3527 (clobber (scratch))]
3528 "TARGET_Z10 && reload_completed"
3529 [(parallel
3530 [(unspec [(match_dup 2) (const_int 0)
3531 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3532 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3533 (use (const_int 1))])]
3534 "operands[4] = gen_label_rtx ();")
3535
3536 (define_split
3537 [(set (reg:CCU CC_REGNUM)
3538 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3539 (match_operand:BLK 1 "memory_operand" "")))
3540 (use (match_operand 2 "register_operand" ""))
3541 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
3542 (clobber (match_operand 3 "register_operand" ""))]
3543 "reload_completed && TARGET_CPU_ZARCH"
3544 [(set (match_dup 3) (label_ref (match_dup 4)))
3545 (parallel
3546 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
3547 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
3548 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
3549 (use (const_int 1))])]
3550 "operands[4] = gen_label_rtx ();")
3551
3552 ; Compare a block of arbitrary length.
3553
3554 (define_expand "cmpmem_long"
3555 [(parallel
3556 [(clobber (match_dup 2))
3557 (clobber (match_dup 3))
3558 (set (reg:CCU CC_REGNUM)
3559 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
3560 (match_operand:BLK 1 "memory_operand" "")))
3561 (use (match_operand 2 "general_operand" ""))
3562 (use (match_dup 3))])]
3563 ""
3564 {
3565 machine_mode sreg_mode = TARGET_ZARCH ? DImode : SImode;
3566 machine_mode dreg_mode = TARGET_ZARCH ? TImode : DImode;
3567 rtx reg0 = gen_reg_rtx (dreg_mode);
3568 rtx reg1 = gen_reg_rtx (dreg_mode);
3569 rtx addr0 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg0));
3570 rtx addr1 = gen_lowpart (Pmode, gen_highpart (sreg_mode, reg1));
3571 rtx len0 = gen_lowpart (Pmode, reg0);
3572 rtx len1 = gen_lowpart (Pmode, reg1);
3573
3574 emit_clobber (reg0);
3575 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
3576 emit_move_insn (len0, operands[2]);
3577
3578 emit_clobber (reg1);
3579 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
3580 emit_move_insn (len1, operands[2]);
3581
3582 operands[0] = replace_equiv_address_nv (operands[0], addr0);
3583 operands[1] = replace_equiv_address_nv (operands[1], addr1);
3584 operands[2] = reg0;
3585 operands[3] = reg1;
3586 })
3587
3588 (define_insn "*cmpmem_long"
3589 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
3590 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
3591 (set (reg:CCU CC_REGNUM)
3592 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
3593 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
3594 (use (match_dup 2))
3595 (use (match_dup 3))]
3596 "TARGET_64BIT || !TARGET_ZARCH"
3597 "clcle\t%0,%1,0\;jo\t.-4"
3598 [(set_attr "length" "8")
3599 (set_attr "type" "vs")])
3600
3601 (define_insn "*cmpmem_long_31z"
3602 [(clobber (match_operand:TI 0 "register_operand" "=d"))
3603 (clobber (match_operand:TI 1 "register_operand" "=d"))
3604 (set (reg:CCU CC_REGNUM)
3605 (compare:CCU (mem:BLK (subreg:SI (match_operand:TI 2 "register_operand" "0") 4))
3606 (mem:BLK (subreg:SI (match_operand:TI 3 "register_operand" "1") 4))))
3607 (use (match_dup 2))
3608 (use (match_dup 3))]
3609 "!TARGET_64BIT && TARGET_ZARCH"
3610 "clcle\t%0,%1,0\;jo\t.-4"
3611 [(set_attr "op_type" "NN")
3612 (set_attr "type" "vs")
3613 (set_attr "length" "8")])
3614
3615 ; Convert CCUmode condition code to integer.
3616 ; Result is zero if EQ, positive if LTU, negative if GTU.
3617
3618 (define_insn_and_split "cmpint"
3619 [(set (match_operand:SI 0 "register_operand" "=d")
3620 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3621 UNSPEC_STRCMPCC_TO_INT))
3622 (clobber (reg:CC CC_REGNUM))]
3623 ""
3624 "#"
3625 "reload_completed"
3626 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3627 (parallel
3628 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
3629 (clobber (reg:CC CC_REGNUM))])])
3630
3631 (define_insn_and_split "*cmpint_cc"
3632 [(set (reg CC_REGNUM)
3633 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3634 UNSPEC_STRCMPCC_TO_INT)
3635 (const_int 0)))
3636 (set (match_operand:SI 0 "register_operand" "=d")
3637 (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT))]
3638 "s390_match_ccmode (insn, CCSmode)"
3639 "#"
3640 "&& reload_completed"
3641 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
3642 (parallel
3643 [(set (match_dup 2) (match_dup 3))
3644 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
3645 {
3646 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
3647 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3648 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3649 })
3650
3651 (define_insn_and_split "*cmpint_sign"
3652 [(set (match_operand:DI 0 "register_operand" "=d")
3653 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3654 UNSPEC_STRCMPCC_TO_INT)))
3655 (clobber (reg:CC CC_REGNUM))]
3656 "TARGET_ZARCH"
3657 "#"
3658 "&& reload_completed"
3659 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3660 (parallel
3661 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
3662 (clobber (reg:CC CC_REGNUM))])])
3663
3664 (define_insn_and_split "*cmpint_sign_cc"
3665 [(set (reg CC_REGNUM)
3666 (compare (ashiftrt:DI (ashift:DI (subreg:DI
3667 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
3668 UNSPEC_STRCMPCC_TO_INT) 0)
3669 (const_int 32)) (const_int 32))
3670 (const_int 0)))
3671 (set (match_operand:DI 0 "register_operand" "=d")
3672 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_STRCMPCC_TO_INT)))]
3673 "s390_match_ccmode (insn, CCSmode) && TARGET_ZARCH"
3674 "#"
3675 "&& reload_completed"
3676 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
3677 (parallel
3678 [(set (match_dup 2) (match_dup 3))
3679 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
3680 {
3681 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
3682 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
3683 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
3684 })
3685
3686
3687 ;;
3688 ;;- Conversion instructions.
3689 ;;
3690
3691 (define_insn "*sethighpartsi"
3692 [(set (match_operand:SI 0 "register_operand" "=d,d")
3693 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
3694 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3695 (clobber (reg:CC CC_REGNUM))]
3696 ""
3697 "@
3698 icm\t%0,%2,%S1
3699 icmy\t%0,%2,%S1"
3700 [(set_attr "op_type" "RS,RSY")
3701 (set_attr "cpu_facility" "*,longdisp")
3702 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3703
3704 (define_insn "*sethighpartdi_64"
3705 [(set (match_operand:DI 0 "register_operand" "=d")
3706 (unspec:DI [(match_operand:BLK 1 "s_operand" "S")
3707 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
3708 (clobber (reg:CC CC_REGNUM))]
3709 "TARGET_ZARCH"
3710 "icmh\t%0,%2,%S1"
3711 [(set_attr "op_type" "RSY")
3712 (set_attr "z10prop" "z10_super")])
3713
3714 (define_insn "*sethighpartdi_31"
3715 [(set (match_operand:DI 0 "register_operand" "=d,d")
3716 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
3717 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
3718 (clobber (reg:CC CC_REGNUM))]
3719 "!TARGET_ZARCH"
3720 "@
3721 icm\t%0,%2,%S1
3722 icmy\t%0,%2,%S1"
3723 [(set_attr "op_type" "RS,RSY")
3724 (set_attr "cpu_facility" "*,longdisp")
3725 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
3726
3727 ;
3728 ; extv instruction patterns
3729 ;
3730
3731 ; FIXME: This expander needs to be converted from DI to GPR as well
3732 ; after resolving some issues with it.
3733
3734 (define_expand "extzv"
3735 [(parallel
3736 [(set (match_operand:DI 0 "register_operand" "=d")
3737 (zero_extract:DI
3738 (match_operand:DI 1 "register_operand" "d")
3739 (match_operand 2 "const_int_operand" "") ; size
3740 (match_operand 3 "const_int_operand" ""))) ; start
3741 (clobber (reg:CC CC_REGNUM))])]
3742 "TARGET_Z10"
3743 {
3744 /* Starting with zEC12 there is risbgn not clobbering CC. */
3745 if (TARGET_ZEC12)
3746 {
3747 emit_move_insn (operands[0],
3748 gen_rtx_ZERO_EXTRACT (DImode,
3749 operands[1],
3750 operands[2],
3751 operands[3]));
3752 DONE;
3753 }
3754 })
3755
3756 (define_insn "*extzv<mode><clobbercc_or_nocc>"
3757 [(set (match_operand:GPR 0 "register_operand" "=d")
3758 (zero_extract:GPR
3759 (match_operand:GPR 1 "register_operand" "d")
3760 (match_operand 2 "const_int_operand" "") ; size
3761 (match_operand 3 "const_int_operand" ""))) ; start
3762 ]
3763 "<z10_or_zEC12_cond>"
3764 "<risbg_n>\t%0,%1,64-%2,128+63,<bitoff_plus>%3+%2" ; dst, src, start, end, shift
3765 [(set_attr "op_type" "RIE")
3766 (set_attr "z10prop" "z10_super_E1")])
3767
3768 ; 64 bit: (a & -16) | ((b >> 8) & 15)
3769 (define_insn "*extzvdi<clobbercc_or_nocc>_lshiftrt"
3770 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
3771 (match_operand 1 "const_int_operand" "") ; size
3772 (match_operand 2 "const_int_operand" "")) ; start
3773 (lshiftrt:DI (match_operand:DI 3 "register_operand" "d")
3774 (match_operand:DI 4 "nonzero_shift_count_operand" "")))]
3775 "<z10_or_zEC12_cond>
3776 && 64 - UINTVAL (operands[4]) >= UINTVAL (operands[1])"
3777 "<risbg_n>\t%0,%3,%2,%2+%1-1,128-%2-%1-%4"
3778 [(set_attr "op_type" "RIE")
3779 (set_attr "z10prop" "z10_super_E1")])
3780
3781 ; 32 bit: (a & -16) | ((b >> 8) & 15)
3782 (define_insn "*<risbg_n>_ior_and_sr_ze"
3783 [(set (match_operand:SI 0 "register_operand" "=d")
3784 (ior:SI (and:SI
3785 (match_operand:SI 1 "register_operand" "0")
3786 (match_operand:SI 2 "const_int_operand" ""))
3787 (subreg:SI
3788 (zero_extract:DI
3789 (match_operand:DI 3 "register_operand" "d")
3790 (match_operand 4 "const_int_operand" "") ; size
3791 (match_operand 5 "const_int_operand" "")) ; start
3792 4)))]
3793 "<z10_or_zEC12_cond>
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 "<risbg_n>\t%0,%1,64-1,128+63,%2+1" ; dst, src, start, end, shift
3809 [(set_attr "op_type" "RIE")
3810 (set_attr "z10prop" "z10_super_E1")])
3811
3812 (define_insn "*<risbg_n>_and_subregdi_rotr"
3813 [(set (match_operand:DI 0 "register_operand" "=d")
3814 (and:DI (subreg:DI
3815 (rotate:SINT (match_operand:SINT 1 "register_operand" "d")
3816 (match_operand:SINT 2 "const_int_operand" "")) 0)
3817 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3818 "<z10_or_zEC12_cond>
3819 && UINTVAL (operands[3]) < (1ULL << (UINTVAL (operands[2]) & 0x3f))"
3820 "<risbg_n>\t%0,%1,%s3,128+%e3,<bitoff_plus>%2" ; dst, src, start, end, shift
3821 [(set_attr "op_type" "RIE")
3822 (set_attr "z10prop" "z10_super_E1")])
3823
3824 (define_insn "*<risbg_n>_and_subregdi_rotl"
3825 [(set (match_operand:DI 0 "register_operand" "=d")
3826 (and:DI (subreg:DI
3827 (rotate:SINT (match_operand:SINT 1 "register_operand" "d")
3828 (match_operand:SINT 2 "const_int_operand" "")) 0)
3829 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3830 "<z10_or_zEC12_cond>
3831 && !(UINTVAL (operands[3]) & ((1ULL << (UINTVAL (operands[2]) & 0x3f)) - 1))"
3832 "<risbg_n>\t%0,%1,%s3,128+%e3,%2" ; dst, src, start, end, shift
3833 [(set_attr "op_type" "RIE")
3834 (set_attr "z10prop" "z10_super_E1")])
3835
3836 (define_insn "*<risbg_n>_di_and_rot"
3837 [(set (match_operand:DI 0 "register_operand" "=d")
3838 (and:DI (rotate:DI (match_operand:DI 1 "register_operand" "d")
3839 (match_operand:DI 2 "const_int_operand" ""))
3840 (match_operand:DI 3 "contiguous_bitmask_operand" "")))]
3841 "<z10_or_zEC12_cond>"
3842 "<risbg_n>\t%0,%1,%s3,128+%e3,%2" ; dst, src, start, end, shift
3843 [(set_attr "op_type" "RIE")
3844 (set_attr "z10prop" "z10_super_E1")])
3845
3846 (define_insn_and_split "*pre_z10_extzv<mode>"
3847 [(set (match_operand:GPR 0 "register_operand" "=d")
3848 (zero_extract:GPR (match_operand:QI 1 "s_operand" "S")
3849 (match_operand 2 "nonzero_shift_count_operand" "")
3850 (const_int 0)))
3851 (clobber (reg:CC CC_REGNUM))]
3852 "!TARGET_Z10"
3853 "#"
3854 "&& reload_completed"
3855 [(parallel
3856 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3857 (clobber (reg:CC CC_REGNUM))])
3858 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3859 {
3860 int bitsize = INTVAL (operands[2]);
3861 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3862 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3863
3864 operands[1] = adjust_address (operands[1], BLKmode, 0);
3865 set_mem_size (operands[1], size);
3866 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3867 operands[3] = GEN_INT (mask);
3868 })
3869
3870 (define_insn_and_split "*pre_z10_extv<mode>"
3871 [(set (match_operand:GPR 0 "register_operand" "=d")
3872 (sign_extract:GPR (match_operand:QI 1 "s_operand" "S")
3873 (match_operand 2 "nonzero_shift_count_operand" "")
3874 (const_int 0)))
3875 (clobber (reg:CC CC_REGNUM))]
3876 ""
3877 "#"
3878 "&& reload_completed"
3879 [(parallel
3880 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3881 (clobber (reg:CC CC_REGNUM))])
3882 (parallel
3883 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3884 (clobber (reg:CC CC_REGNUM))])]
3885 {
3886 int bitsize = INTVAL (operands[2]);
3887 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3888 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3889
3890 operands[1] = adjust_address (operands[1], BLKmode, 0);
3891 set_mem_size (operands[1], size);
3892 operands[2] = GEN_INT (<GPR:bitsize> - bitsize);
3893 operands[3] = GEN_INT (mask);
3894 })
3895
3896 ;
3897 ; insv instruction patterns
3898 ;
3899
3900 (define_expand "insv"
3901 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3902 (match_operand 1 "const_int_operand" "")
3903 (match_operand 2 "const_int_operand" ""))
3904 (match_operand 3 "general_operand" ""))]
3905 ""
3906 {
3907 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3908 DONE;
3909 FAIL;
3910 })
3911
3912
3913 ; The normal RTL expansion will never generate a zero_extract where
3914 ; the location operand isn't word mode. However, we do this in the
3915 ; back-end when generating atomic operations. See s390_two_part_insv.
3916 (define_insn "*insv<mode><clobbercc_or_nocc>"
3917 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3918 (match_operand 1 "const_int_operand" "I") ; size
3919 (match_operand 2 "const_int_operand" "I")) ; pos
3920 (match_operand:GPR 3 "nonimmediate_operand" "d"))]
3921 "<z10_or_zEC12_cond>
3922 && (INTVAL (operands[1]) + INTVAL (operands[2])) <= <bitsize>"
3923 "<risbg_n>\t%0,%3,<bitoff_plus>%2,<bitoff_plus>%2+%1-1,<bitsize>-%2-%1"
3924 [(set_attr "op_type" "RIE")
3925 (set_attr "z10prop" "z10_super_E1")])
3926
3927 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3928 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3929 (define_insn "*insv<mode><clobbercc_or_nocc>_noshift"
3930 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d")
3931 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d,0")
3932 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
3933 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0,d")
3934 (match_operand:GPR 4 "const_int_operand" ""))))]
3935 "<z10_or_zEC12_cond> && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3936 "@
3937 <risbg_n>\t%0,%1,%<bfstart>2,%<bfend>2,0
3938 <risbg_n>\t%0,%3,%<bfstart>4,%<bfend>4,0"
3939 [(set_attr "op_type" "RIE")
3940 (set_attr "z10prop" "z10_super_E1")])
3941
3942 (define_insn "*insv_z10_noshift_cc"
3943 [(set (reg CC_REGNUM)
3944 (compare
3945 (ior:DI
3946 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,0")
3947 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3948 (and:DI (match_operand:DI 3 "nonimmediate_operand" "0,d")
3949 (match_operand:DI 4 "const_int_operand" "")))
3950 (const_int 0)))
3951 (set (match_operand:DI 0 "nonimmediate_operand" "=d,d")
3952 (ior:DI (and:DI (match_dup 1) (match_dup 2))
3953 (and:DI (match_dup 3) (match_dup 4))))]
3954 "TARGET_Z10 && s390_match_ccmode (insn, CCSmode)
3955 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3956 "@
3957 risbg\t%0,%1,%s2,%e2,0
3958 risbg\t%0,%3,%s4,%e4,0"
3959 [(set_attr "op_type" "RIE")
3960 (set_attr "z10prop" "z10_super_E1")])
3961
3962 (define_insn "*insv_z10_noshift_cconly"
3963 [(set
3964 (reg CC_REGNUM)
3965 (compare
3966 (ior:DI
3967 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,0")
3968 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
3969 (and:DI (match_operand:DI 3 "nonimmediate_operand" "0,d")
3970 (match_operand:DI 4 "const_int_operand" "")))
3971 (const_int 0)))
3972 (clobber (match_scratch:DI 0 "=d,d"))]
3973 "TARGET_Z10 && s390_match_ccmode (insn, CCSmode)
3974 && INTVAL (operands[2]) == ~INTVAL (operands[4])"
3975 "@
3976 risbg\t%0,%1,%s2,%e2,0
3977 risbg\t%0,%3,%s4,%e4,0"
3978 [(set_attr "op_type" "RIE")
3979 (set_attr "z10prop" "z10_super_E1")])
3980
3981 ; Implement appending Y on the left of S bits of X
3982 ; x = (y << s) | (x & ((1 << s) - 1))
3983 (define_insn "*insv<mode><clobbercc_or_nocc>_appendbitsleft"
3984 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3985 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "0")
3986 (match_operand:GPR 2 "immediate_operand" ""))
3987 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "d")
3988 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
3989 "<z10_or_zEC12_cond>
3990 && UINTVAL (operands[2]) == (1UL << UINTVAL (operands[4])) - 1"
3991 "<risbg_n>\t%0,%3,<bitoff>,64-%4-1,%4"
3992 [(set_attr "op_type" "RIE")
3993 (set_attr "z10prop" "z10_super_E1")])
3994
3995 ; a = ((i32)a & -16777216) | (((ui32)b) >> 8)
3996 (define_insn "*<risbg_n>_<mode>_ior_and_lshiftrt"
3997 [(set (match_operand:GPR 0 "register_operand" "=d")
3998 (ior:GPR (and:GPR
3999 (match_operand:GPR 1 "register_operand" "0")
4000 (match_operand:GPR 2 "const_int_operand" ""))
4001 (lshiftrt:GPR
4002 (match_operand:GPR 3 "register_operand" "d")
4003 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
4004 "<z10_or_zEC12_cond> && UINTVAL (operands[2])
4005 == (~(0ULL) << (GET_MODE_BITSIZE (<MODE>mode) - UINTVAL (operands[4])))"
4006 "<risbg_n>\t%0,%3,<bitoff_plus>%4,63,64-%4"
4007 [(set_attr "op_type" "RIE")
4008 (set_attr "z10prop" "z10_super_E1")])
4009
4010 ; (ui32)(((ui64)x) >> 48) | ((i32)y & -65536);
4011 (define_insn "*<risbg_n>_sidi_ior_and_lshiftrt"
4012 [(set (match_operand:SI 0 "register_operand" "=d")
4013 (ior:SI (and:SI
4014 (match_operand:SI 1 "register_operand" "0")
4015 (match_operand:SI 2 "const_int_operand" ""))
4016 (subreg:SI
4017 (lshiftrt:DI
4018 (match_operand:DI 3 "register_operand" "d")
4019 (match_operand:DI 4 "nonzero_shift_count_operand" "")) 4)))]
4020 "<z10_or_zEC12_cond>
4021 && UINTVAL (operands[2]) == ~(~(0ULL) >> UINTVAL (operands[4]))"
4022 "<risbg_n>\t%0,%3,%4,63,64-%4"
4023 [(set_attr "op_type" "RIE")
4024 (set_attr "z10prop" "z10_super_E1")])
4025
4026 ; (ui32)(((ui64)x) >> 12) & -4
4027 (define_insn "*trunc_sidi_and_subreg_lshrt<clobbercc_or_nocc>"
4028 [(set (match_operand:SI 0 "register_operand" "=d")
4029 (and:SI
4030 (subreg:SI (lshiftrt:DI
4031 (match_operand:DI 1 "register_operand" "d")
4032 (match_operand:DI 2 "nonzero_shift_count_operand" "")) 4)
4033 (match_operand:SI 3 "contiguous_bitmask_nowrap_operand" "")))]
4034 "<z10_or_zEC12_cond>"
4035 "<risbg_n>\t%0,%1,%t3,128+%f3,64-%2"
4036 [(set_attr "op_type" "RIE")
4037 (set_attr "z10prop" "z10_super_E1")])
4038
4039 ; z = (x << c) | (y >> d) with (x << c) and (y >> d) not overlapping after shifting
4040 ; -> z = y >> d; z = (x << c) | (z & ((1 << c) - 1))
4041 ; -> z = y >> d; z = risbg;
4042
4043 (define_split
4044 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
4045 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
4046 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4047 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
4048 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))]
4049 "TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
4050 [(set (match_dup 6)
4051 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
4052 (set (match_dup 0)
4053 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
4054 (ashift:GPR (match_dup 3) (match_dup 4))))]
4055 {
4056 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
4057 if (reg_overlap_mentioned_p (operands[0], operands[3]))
4058 {
4059 if (!can_create_pseudo_p ())
4060 FAIL;
4061 operands[6] = gen_reg_rtx (<MODE>mode);
4062 }
4063 else
4064 operands[6] = operands[0];
4065 })
4066
4067 (define_split
4068 [(parallel
4069 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
4070 (ior:GPR (lshiftrt:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
4071 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4072 (ashift:GPR (match_operand:GPR 3 "nonimmediate_operand" "")
4073 (match_operand:GPR 4 "nonzero_shift_count_operand" ""))))
4074 (clobber (reg:CC CC_REGNUM))])]
4075 "TARGET_Z10 && !TARGET_ZEC12 && UINTVAL (operands[2]) + UINTVAL (operands[4]) >= <bitsize>"
4076 [(set (match_dup 6)
4077 (lshiftrt:GPR (match_dup 1) (match_dup 2)))
4078 (parallel
4079 [(set (match_dup 0)
4080 (ior:GPR (and:GPR (match_dup 6) (match_dup 5))
4081 (ashift:GPR (match_dup 3) (match_dup 4))))
4082 (clobber (reg:CC CC_REGNUM))])]
4083 {
4084 operands[5] = GEN_INT ((1UL << UINTVAL (operands[4])) - 1);
4085 if (reg_overlap_mentioned_p (operands[0], operands[3]))
4086 {
4087 if (!can_create_pseudo_p ())
4088 FAIL;
4089 operands[6] = gen_reg_rtx (<MODE>mode);
4090 }
4091 else
4092 operands[6] = operands[0];
4093 })
4094
4095 (define_insn "*r<noxa>sbg_<mode>_noshift"
4096 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4097 (IXOR:GPR
4098 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
4099 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4100 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4101 (clobber (reg:CC CC_REGNUM))]
4102 "TARGET_Z10"
4103 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,0"
4104 [(set_attr "op_type" "RIE")])
4105
4106 (define_insn "*r<noxa>sbg_di_rotl"
4107 [(set (match_operand:DI 0 "nonimmediate_operand" "=d")
4108 (IXOR:DI
4109 (and:DI
4110 (rotate:DI
4111 (match_operand:DI 1 "nonimmediate_operand" "d")
4112 (match_operand:DI 3 "const_int_operand" ""))
4113 (match_operand:DI 2 "contiguous_bitmask_operand" ""))
4114 (match_operand:DI 4 "nonimmediate_operand" "0")))
4115 (clobber (reg:CC CC_REGNUM))]
4116 "TARGET_Z10"
4117 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%b3"
4118 [(set_attr "op_type" "RIE")])
4119
4120 (define_insn "*r<noxa>sbg_<mode>_srl_bitmask"
4121 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4122 (IXOR:GPR
4123 (and:GPR
4124 (lshiftrt:GPR
4125 (match_operand:GPR 1 "nonimmediate_operand" "d")
4126 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4127 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4128 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4129 (clobber (reg:CC CC_REGNUM))]
4130 "TARGET_Z10
4131 && s390_extzv_shift_ok (<bitsize>, 64 - INTVAL (operands[3]),
4132 INTVAL (operands[2]))"
4133 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,64-%3"
4134 [(set_attr "op_type" "RIE")])
4135
4136 (define_insn "*r<noxa>sbg_<mode>_sll_bitmask"
4137 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4138 (IXOR:GPR
4139 (and:GPR
4140 (ashift:GPR
4141 (match_operand:GPR 1 "nonimmediate_operand" "d")
4142 (match_operand:GPR 3 "nonzero_shift_count_operand" ""))
4143 (match_operand:GPR 2 "contiguous_bitmask_operand" ""))
4144 (match_operand:GPR 4 "nonimmediate_operand" "0")))
4145 (clobber (reg:CC CC_REGNUM))]
4146 "TARGET_Z10
4147 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[3]),
4148 INTVAL (operands[2]))"
4149 "r<noxa>sbg\t%0,%1,%<bfstart>2,%<bfend>2,%3"
4150 [(set_attr "op_type" "RIE")])
4151
4152 ;; unsigned {int,long} a, b
4153 ;; a = a | (b << const_int)
4154 ;; a = a ^ (b << const_int)
4155 (define_insn "*r<noxa>sbg_<mode>_sll"
4156 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4157 (IXOR:GPR
4158 (ashift:GPR
4159 (match_operand:GPR 1 "nonimmediate_operand" "d")
4160 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4161 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4162 (clobber (reg:CC CC_REGNUM))]
4163 "TARGET_Z10"
4164 "r<noxa>sbg\t%0,%1,<bitoff>,63-%2,%2"
4165 [(set_attr "op_type" "RIE")])
4166
4167 ;; unsigned {int,long} a, b
4168 ;; a = a | (b >> const_int)
4169 ;; a = a ^ (b >> const_int)
4170 (define_insn "*r<noxa>sbg_<mode>_srl"
4171 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
4172 (IXOR:GPR
4173 (lshiftrt:GPR
4174 (match_operand:GPR 1 "nonimmediate_operand" "d")
4175 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
4176 (match_operand:GPR 3 "nonimmediate_operand" "0")))
4177 (clobber (reg:CC CC_REGNUM))]
4178 "TARGET_Z10"
4179 "r<noxa>sbg\t%0,%1,<bitoff_plus>%2,63,64-%2"
4180 [(set_attr "op_type" "RIE")])
4181
4182 ;; These two are generated by combine for s.bf &= val.
4183 ;; ??? For bitfields smaller than 32-bits, we wind up with SImode
4184 ;; shifts and ands, which results in some truly awful patterns
4185 ;; including subregs of operations. Rather unnecessisarily, IMO.
4186 ;; Instead of
4187 ;;
4188 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4189 ;; (const_int 24 [0x18])
4190 ;; (const_int 0 [0]))
4191 ;; (subreg:DI (and:SI (subreg:SI (lshiftrt:DI (reg/v:DI 50 [ s ])
4192 ;; (const_int 40 [0x28])) 4)
4193 ;; (reg:SI 4 %r4 [ y+4 ])) 0))
4194 ;;
4195 ;; we should instead generate
4196 ;;
4197 ;; (set (zero_extract:DI (reg/v:DI 50 [ s ])
4198 ;; (const_int 24 [0x18])
4199 ;; (const_int 0 [0]))
4200 ;; (and:DI (lshiftrt:DI (reg/v:DI 50 [ s ])
4201 ;; (const_int 40 [0x28]))
4202 ;; (subreg:DI (reg:SI 4 %r4 [ y+4 ]) 0)))
4203 ;;
4204 ;; by noticing that we can push down the outer paradoxical subreg
4205 ;; into the operation.
4206
4207 (define_insn "*insv_rnsbg_noshift"
4208 [(set (zero_extract:DI
4209 (match_operand:DI 0 "nonimmediate_operand" "+d")
4210 (match_operand 1 "const_int_operand" "")
4211 (match_operand 2 "const_int_operand" ""))
4212 (and:DI
4213 (match_dup 0)
4214 (match_operand:DI 3 "nonimmediate_operand" "d")))
4215 (clobber (reg:CC CC_REGNUM))]
4216 "TARGET_Z10
4217 && INTVAL (operands[1]) + INTVAL (operands[2]) == 64"
4218 "rnsbg\t%0,%3,%2,63,0"
4219 [(set_attr "op_type" "RIE")])
4220
4221 (define_insn "*insv_rnsbg_srl"
4222 [(set (zero_extract:DI
4223 (match_operand:DI 0 "nonimmediate_operand" "+d")
4224 (match_operand 1 "const_int_operand" "")
4225 (match_operand 2 "const_int_operand" ""))
4226 (and:DI
4227 (lshiftrt:DI
4228 (match_dup 0)
4229 (match_operand 3 "const_int_operand" ""))
4230 (match_operand:DI 4 "nonimmediate_operand" "d")))
4231 (clobber (reg:CC CC_REGNUM))]
4232 "TARGET_Z10
4233 && INTVAL (operands[3]) == 64 - INTVAL (operands[1]) - INTVAL (operands[2])"
4234 "rnsbg\t%0,%4,%2,%2+%1-1,%3"
4235 [(set_attr "op_type" "RIE")])
4236
4237 (define_insn "*insv<mode>_mem_reg"
4238 [(set (zero_extract:W (match_operand:QI 0 "memory_operand" "+Q,S")
4239 (match_operand 1 "const_int_operand" "n,n")
4240 (const_int 0))
4241 (match_operand:W 2 "register_operand" "d,d"))]
4242 "INTVAL (operands[1]) > 0
4243 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4244 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4245 {
4246 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4247
4248 operands[1] = GEN_INT ((1ul << size) - 1);
4249 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
4250 : "stcmy\t%2,%1,%S0";
4251 }
4252 [(set_attr "op_type" "RS,RSY")
4253 (set_attr "cpu_facility" "*,longdisp")
4254 (set_attr "z10prop" "z10_super,z10_super")])
4255
4256 (define_insn "*insvdi_mem_reghigh"
4257 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+S")
4258 (match_operand 1 "const_int_operand" "n")
4259 (const_int 0))
4260 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
4261 (const_int 32)))]
4262 "TARGET_ZARCH
4263 && INTVAL (operands[1]) > 0
4264 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
4265 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
4266 {
4267 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
4268
4269 operands[1] = GEN_INT ((1ul << size) - 1);
4270 return "stcmh\t%2,%1,%S0";
4271 }
4272 [(set_attr "op_type" "RSY")
4273 (set_attr "z10prop" "z10_super")])
4274
4275 (define_insn "*insvdi_reg_imm"
4276 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4277 (const_int 16)
4278 (match_operand 1 "const_int_operand" "n"))
4279 (match_operand:DI 2 "const_int_operand" "n"))]
4280 "TARGET_ZARCH
4281 && INTVAL (operands[1]) >= 0
4282 && INTVAL (operands[1]) < BITS_PER_WORD
4283 && INTVAL (operands[1]) % 16 == 0"
4284 {
4285 switch (BITS_PER_WORD - INTVAL (operands[1]))
4286 {
4287 case 64: return "iihh\t%0,%x2"; break;
4288 case 48: return "iihl\t%0,%x2"; break;
4289 case 32: return "iilh\t%0,%x2"; break;
4290 case 16: return "iill\t%0,%x2"; break;
4291 default: gcc_unreachable();
4292 }
4293 }
4294 [(set_attr "op_type" "RI")
4295 (set_attr "z10prop" "z10_super_E1")])
4296
4297 ; Update the left-most 32 bit of a DI.
4298 (define_insn "*insv_h_di_reg_extimm"
4299 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4300 (const_int 32)
4301 (const_int 0))
4302 (match_operand:DI 1 "const_int_operand" "n"))]
4303 "TARGET_EXTIMM"
4304 "iihf\t%0,%o1"
4305 [(set_attr "op_type" "RIL")
4306 (set_attr "z10prop" "z10_fwd_E1")])
4307
4308 ; Update the right-most 32 bit of a DI.
4309 (define_insn "*insv_l_di_reg_extimm"
4310 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+d")
4311 (const_int 32)
4312 (const_int 32))
4313 (match_operand:DI 1 "const_int_operand" "n"))]
4314 "TARGET_EXTIMM"
4315 "iilf\t%0,%o1"
4316 [(set_attr "op_type" "RIL")
4317 (set_attr "z10prop" "z10_fwd_A1")])
4318
4319 ;
4320 ; extendsidi2 instruction pattern(s).
4321 ;
4322
4323 (define_expand "extendsidi2"
4324 [(set (match_operand:DI 0 "register_operand" "")
4325 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4326 ""
4327 {
4328 if (!TARGET_ZARCH)
4329 {
4330 emit_clobber (operands[0]);
4331 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
4332 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
4333 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
4334 DONE;
4335 }
4336 })
4337
4338 (define_insn "*extendsidi2"
4339 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4340 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4341 "TARGET_ZARCH"
4342 "@
4343 lgfr\t%0,%1
4344 lgf\t%0,%1
4345 lgfrl\t%0,%1"
4346 [(set_attr "op_type" "RRE,RXY,RIL")
4347 (set_attr "type" "*,*,larl")
4348 (set_attr "cpu_facility" "*,*,z10")
4349 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4350
4351 ;
4352 ; extend(hi|qi)(si|di)2 instruction pattern(s).
4353 ;
4354
4355 (define_expand "extend<HQI:mode><DSI:mode>2"
4356 [(set (match_operand:DSI 0 "register_operand" "")
4357 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4358 ""
4359 {
4360 if (<DSI:MODE>mode == DImode && !TARGET_ZARCH)
4361 {
4362 rtx tmp = gen_reg_rtx (SImode);
4363 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
4364 emit_insn (gen_extendsidi2 (operands[0], tmp));
4365 DONE;
4366 }
4367 else if (!TARGET_EXTIMM)
4368 {
4369 rtx bitcount = GEN_INT (<DSI:bitsize> - <HQI:bitsize>);
4370
4371 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
4372 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
4373 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
4374 DONE;
4375 }
4376 })
4377
4378 ;
4379 ; extendhidi2 instruction pattern(s).
4380 ;
4381
4382 (define_insn "*extendhidi2_extimm"
4383 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4384 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,T,b")))]
4385 "TARGET_ZARCH && TARGET_EXTIMM"
4386 "@
4387 lghr\t%0,%1
4388 lgh\t%0,%1
4389 lghrl\t%0,%1"
4390 [(set_attr "op_type" "RRE,RXY,RIL")
4391 (set_attr "type" "*,*,larl")
4392 (set_attr "cpu_facility" "extimm,extimm,z10")
4393 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1")])
4394
4395 (define_insn "*extendhidi2"
4396 [(set (match_operand:DI 0 "register_operand" "=d")
4397 (sign_extend:DI (match_operand:HI 1 "memory_operand" "T")))]
4398 "TARGET_ZARCH"
4399 "lgh\t%0,%1"
4400 [(set_attr "op_type" "RXY")
4401 (set_attr "z10prop" "z10_super_E1")])
4402
4403 ;
4404 ; extendhisi2 instruction pattern(s).
4405 ;
4406
4407 (define_insn "*extendhisi2_extimm"
4408 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
4409 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
4410 "TARGET_EXTIMM"
4411 "@
4412 lhr\t%0,%1
4413 lh\t%0,%1
4414 lhy\t%0,%1
4415 lhrl\t%0,%1"
4416 [(set_attr "op_type" "RRE,RX,RXY,RIL")
4417 (set_attr "type" "*,*,*,larl")
4418 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")
4419 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,z10_super_E1")])
4420
4421 (define_insn "*extendhisi2"
4422 [(set (match_operand:SI 0 "register_operand" "=d,d")
4423 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
4424 "!TARGET_EXTIMM"
4425 "@
4426 lh\t%0,%1
4427 lhy\t%0,%1"
4428 [(set_attr "op_type" "RX,RXY")
4429 (set_attr "cpu_facility" "*,longdisp")
4430 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4431
4432 ;
4433 ; extendqi(si|di)2 instruction pattern(s).
4434 ;
4435
4436 ; lbr, lgbr, lb, lgb
4437 (define_insn "*extendqi<mode>2_extimm"
4438 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4439 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,T")))]
4440 "TARGET_EXTIMM"
4441 "@
4442 l<g>br\t%0,%1
4443 l<g>b\t%0,%1"
4444 [(set_attr "op_type" "RRE,RXY")
4445 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4446
4447 ; lb, lgb
4448 (define_insn "*extendqi<mode>2"
4449 [(set (match_operand:GPR 0 "register_operand" "=d")
4450 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "T")))]
4451 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
4452 "l<g>b\t%0,%1"
4453 [(set_attr "op_type" "RXY")
4454 (set_attr "z10prop" "z10_super_E1")])
4455
4456 (define_insn_and_split "*extendqi<mode>2_short_displ"
4457 [(set (match_operand:GPR 0 "register_operand" "=d")
4458 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
4459 (clobber (reg:CC CC_REGNUM))]
4460 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
4461 "#"
4462 "&& reload_completed"
4463 [(parallel
4464 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
4465 (clobber (reg:CC CC_REGNUM))])
4466 (parallel
4467 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
4468 (clobber (reg:CC CC_REGNUM))])]
4469 {
4470 operands[1] = adjust_address (operands[1], BLKmode, 0);
4471 set_mem_size (operands[1], GET_MODE_SIZE (QImode));
4472 operands[2] = GEN_INT (<GPR:bitsize> - BITS_PER_UNIT);
4473 })
4474
4475 ;
4476 ; zero_extendsidi2 instruction pattern(s).
4477 ;
4478
4479 (define_expand "zero_extendsidi2"
4480 [(set (match_operand:DI 0 "register_operand" "")
4481 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
4482 ""
4483 {
4484 if (!TARGET_ZARCH)
4485 {
4486 emit_clobber (operands[0]);
4487 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
4488 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
4489 DONE;
4490 }
4491 })
4492
4493 (define_insn "*zero_extendsidi2"
4494 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4495 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,T,b")))]
4496 "TARGET_ZARCH"
4497 "@
4498 llgfr\t%0,%1
4499 llgf\t%0,%1
4500 llgfrl\t%0,%1"
4501 [(set_attr "op_type" "RRE,RXY,RIL")
4502 (set_attr "type" "*,*,larl")
4503 (set_attr "cpu_facility" "*,*,z10")
4504 (set_attr "z10prop" "z10_fwd_E1,z10_fwd_A3,z10_fwd_A3")])
4505
4506 ;
4507 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
4508 ;
4509
4510 (define_insn "*llgt_sidi"
4511 [(set (match_operand:DI 0 "register_operand" "=d")
4512 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4513 (const_int 2147483647)))]
4514 "TARGET_ZARCH"
4515 "llgt\t%0,%1"
4516 [(set_attr "op_type" "RXE")
4517 (set_attr "z10prop" "z10_super_E1")])
4518
4519 (define_insn_and_split "*llgt_sidi_split"
4520 [(set (match_operand:DI 0 "register_operand" "=d")
4521 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "T") 0)
4522 (const_int 2147483647)))
4523 (clobber (reg:CC CC_REGNUM))]
4524 "TARGET_ZARCH"
4525 "#"
4526 "&& reload_completed"
4527 [(set (match_dup 0)
4528 (and:DI (subreg:DI (match_dup 1) 0)
4529 (const_int 2147483647)))]
4530 "")
4531
4532 (define_insn "*llgt_sisi"
4533 [(set (match_operand:SI 0 "register_operand" "=d,d")
4534 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,T")
4535 (const_int 2147483647)))]
4536 "TARGET_ZARCH"
4537 "@
4538 llgtr\t%0,%1
4539 llgt\t%0,%1"
4540 [(set_attr "op_type" "RRE,RXE")
4541 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4542
4543 (define_insn "*llgt_didi"
4544 [(set (match_operand:DI 0 "register_operand" "=d,d")
4545 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
4546 (const_int 2147483647)))]
4547 "TARGET_ZARCH"
4548 "@
4549 llgtr\t%0,%1
4550 llgt\t%0,%N1"
4551 [(set_attr "op_type" "RRE,RXE")
4552 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
4553
4554 (define_split
4555 [(set (match_operand:DSI 0 "register_operand" "")
4556 (and:DSI (match_operand:DSI 1 "nonimmediate_operand" "")
4557 (const_int 2147483647)))
4558 (clobber (reg:CC CC_REGNUM))]
4559 "TARGET_ZARCH && reload_completed"
4560 [(set (match_dup 0)
4561 (and:DSI (match_dup 1)
4562 (const_int 2147483647)))]
4563 "")
4564
4565 ;
4566 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
4567 ;
4568
4569 (define_expand "zero_extend<mode>di2"
4570 [(set (match_operand:DI 0 "register_operand" "")
4571 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4572 ""
4573 {
4574 if (!TARGET_ZARCH)
4575 {
4576 rtx tmp = gen_reg_rtx (SImode);
4577 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
4578 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
4579 DONE;
4580 }
4581 else if (!TARGET_EXTIMM)
4582 {
4583 rtx bitcount = GEN_INT (64 - <HQI:bitsize>);
4584 operands[1] = gen_lowpart (DImode, operands[1]);
4585 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
4586 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
4587 DONE;
4588 }
4589 })
4590
4591 (define_expand "zero_extend<mode>si2"
4592 [(set (match_operand:SI 0 "register_operand" "")
4593 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
4594 ""
4595 {
4596 if (!TARGET_EXTIMM)
4597 {
4598 operands[1] = gen_lowpart (SImode, operands[1]);
4599 emit_insn (gen_andsi3 (operands[0], operands[1],
4600 GEN_INT ((1 << <HQI:bitsize>) - 1)));
4601 DONE;
4602 }
4603 })
4604
4605 ; llhrl, llghrl
4606 (define_insn "*zero_extendhi<mode>2_z10"
4607 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4608 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,T,b")))]
4609 "TARGET_Z10"
4610 "@
4611 ll<g>hr\t%0,%1
4612 ll<g>h\t%0,%1
4613 ll<g>hrl\t%0,%1"
4614 [(set_attr "op_type" "RXY,RRE,RIL")
4615 (set_attr "type" "*,*,larl")
4616 (set_attr "cpu_facility" "*,*,z10")
4617 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3,z10_fwd_A3")])
4618
4619 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
4620 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
4621 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4622 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,T")))]
4623 "TARGET_EXTIMM"
4624 "@
4625 ll<g><hc>r\t%0,%1
4626 ll<g><hc>\t%0,%1"
4627 [(set_attr "op_type" "RRE,RXY")
4628 (set_attr "z10prop" "z10_super_E1,z10_fwd_A3")])
4629
4630 ; llgh, llgc
4631 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
4632 [(set (match_operand:GPR 0 "register_operand" "=d")
4633 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "T")))]
4634 "TARGET_ZARCH && !TARGET_EXTIMM"
4635 "llg<hc>\t%0,%1"
4636 [(set_attr "op_type" "RXY")
4637 (set_attr "z10prop" "z10_fwd_A3")])
4638
4639 (define_insn_and_split "*zero_extendhisi2_31"
4640 [(set (match_operand:SI 0 "register_operand" "=&d")
4641 (zero_extend:SI (match_operand:HI 1 "s_operand" "S")))
4642 (clobber (reg:CC CC_REGNUM))]
4643 "!TARGET_ZARCH"
4644 "#"
4645 "&& reload_completed"
4646 [(set (match_dup 0) (const_int 0))
4647 (parallel
4648 [(set (strict_low_part (match_dup 2)) (match_dup 1))
4649 (clobber (reg:CC CC_REGNUM))])]
4650 "operands[2] = gen_lowpart (HImode, operands[0]);")
4651
4652 (define_insn_and_split "*zero_extendqisi2_31"
4653 [(set (match_operand:SI 0 "register_operand" "=&d")
4654 (zero_extend:SI (match_operand:QI 1 "memory_operand" "T")))]
4655 "!TARGET_ZARCH"
4656 "#"
4657 "&& reload_completed"
4658 [(set (match_dup 0) (const_int 0))
4659 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4660 "operands[2] = gen_lowpart (QImode, operands[0]);")
4661
4662 ;
4663 ; zero_extendqihi2 instruction pattern(s).
4664 ;
4665
4666 (define_expand "zero_extendqihi2"
4667 [(set (match_operand:HI 0 "register_operand" "")
4668 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4669 "TARGET_ZARCH && !TARGET_EXTIMM"
4670 {
4671 operands[1] = gen_lowpart (HImode, operands[1]);
4672 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
4673 DONE;
4674 })
4675
4676 (define_insn "*zero_extendqihi2_64"
4677 [(set (match_operand:HI 0 "register_operand" "=d")
4678 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4679 "TARGET_ZARCH && !TARGET_EXTIMM"
4680 "llgc\t%0,%1"
4681 [(set_attr "op_type" "RXY")
4682 (set_attr "z10prop" "z10_fwd_A3")])
4683
4684 (define_insn_and_split "*zero_extendqihi2_31"
4685 [(set (match_operand:HI 0 "register_operand" "=&d")
4686 (zero_extend:HI (match_operand:QI 1 "memory_operand" "T")))]
4687 "!TARGET_ZARCH"
4688 "#"
4689 "&& reload_completed"
4690 [(set (match_dup 0) (const_int 0))
4691 (set (strict_low_part (match_dup 2)) (match_dup 1))]
4692 "operands[2] = gen_lowpart (QImode, operands[0]);")
4693
4694 ;
4695 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
4696 ;
4697
4698 (define_expand "fixuns_truncdddi2"
4699 [(parallel
4700 [(set (match_operand:DI 0 "register_operand" "")
4701 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
4702 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4703 (clobber (reg:CC CC_REGNUM))])]
4704
4705 "TARGET_HARD_DFP"
4706 {
4707 if (!TARGET_Z196)
4708 {
4709 rtx_code_label *label1 = gen_label_rtx ();
4710 rtx_code_label *label2 = gen_label_rtx ();
4711 rtx temp = gen_reg_rtx (TDmode);
4712 REAL_VALUE_TYPE cmp, sub;
4713
4714 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4715 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4716
4717 /* 2^63 can't be represented as 64bit DFP number with full precision. The
4718 solution is doing the check and the subtraction in TD mode and using a
4719 TD -> DI convert afterwards. */
4720 emit_insn (gen_extendddtd2 (temp, operands[1]));
4721 temp = force_reg (TDmode, temp);
4722 emit_cmp_and_jump_insns (temp,
4723 const_double_from_real_value (cmp, TDmode),
4724 LT, NULL_RTX, VOIDmode, 0, label1);
4725 emit_insn (gen_subtd3 (temp, temp,
4726 const_double_from_real_value (sub, TDmode)));
4727 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4728 GEN_INT (DFP_RND_TOWARD_MINF)));
4729 emit_jump (label2);
4730
4731 emit_label (label1);
4732 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1],
4733 GEN_INT (DFP_RND_TOWARD_0)));
4734 emit_label (label2);
4735 DONE;
4736 }
4737 })
4738
4739 (define_expand "fixuns_trunctddi2"
4740 [(parallel
4741 [(set (match_operand:DI 0 "register_operand" "")
4742 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))
4743 (unspec:DI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4744 (clobber (reg:CC CC_REGNUM))])]
4745
4746 "TARGET_HARD_DFP"
4747 {
4748 if (!TARGET_Z196)
4749 {
4750 rtx_code_label *label1 = gen_label_rtx ();
4751 rtx_code_label *label2 = gen_label_rtx ();
4752 rtx temp = gen_reg_rtx (TDmode);
4753 REAL_VALUE_TYPE cmp, sub;
4754
4755 operands[1] = force_reg (TDmode, operands[1]);
4756 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
4757 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
4758
4759 emit_cmp_and_jump_insns (operands[1],
4760 const_double_from_real_value (cmp, TDmode),
4761 LT, NULL_RTX, VOIDmode, 0, label1);
4762 emit_insn (gen_subtd3 (temp, operands[1],
4763 const_double_from_real_value (sub, TDmode)));
4764 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp,
4765 GEN_INT (DFP_RND_TOWARD_MINF)));
4766 emit_jump (label2);
4767
4768 emit_label (label1);
4769 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1],
4770 GEN_INT (DFP_RND_TOWARD_0)));
4771 emit_label (label2);
4772 DONE;
4773 }
4774 })
4775
4776 ;
4777 ; fixuns_trunc(sf|df|tf)(si|di)2 and fix_trunc(sf|df|tf)(si|di)2
4778 ; instruction pattern(s).
4779 ;
4780
4781 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
4782 [(parallel
4783 [(set (match_operand:GPR 0 "register_operand" "")
4784 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))
4785 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4786 (clobber (reg:CC CC_REGNUM))])]
4787 "TARGET_HARD_FLOAT"
4788 {
4789 if (!TARGET_Z196)
4790 {
4791 rtx_code_label *label1 = gen_label_rtx ();
4792 rtx_code_label *label2 = gen_label_rtx ();
4793 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
4794 REAL_VALUE_TYPE cmp, sub;
4795
4796 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
4797 real_2expN (&cmp, <GPR:bitsize> - 1, <BFP:MODE>mode);
4798 real_2expN (&sub, <GPR:bitsize>, <BFP:MODE>mode);
4799
4800 emit_cmp_and_jump_insns (operands[1],
4801 const_double_from_real_value (cmp, <BFP:MODE>mode),
4802 LT, NULL_RTX, VOIDmode, 0, label1);
4803 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
4804 const_double_from_real_value (sub, <BFP:MODE>mode)));
4805 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
4806 GEN_INT (BFP_RND_TOWARD_MINF)));
4807 emit_jump (label2);
4808
4809 emit_label (label1);
4810 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
4811 operands[1], GEN_INT (BFP_RND_TOWARD_0)));
4812 emit_label (label2);
4813 DONE;
4814 }
4815 })
4816
4817 ; fixuns_trunc(td|dd)si2 expander
4818 (define_expand "fixuns_trunc<mode>si2"
4819 [(parallel
4820 [(set (match_operand:SI 0 "register_operand" "")
4821 (unsigned_fix:SI (match_operand:DFP 1 "register_operand" "")))
4822 (unspec:SI [(const_int DFP_RND_TOWARD_0)] UNSPEC_ROUND)
4823 (clobber (reg:CC CC_REGNUM))])]
4824 "TARGET_Z196 && TARGET_HARD_DFP"
4825 "")
4826
4827 ; fixuns_trunc(tf|df|sf|td|dd)(di|si)2 instruction patterns.
4828
4829 (define_insn "*fixuns_truncdfdi2_z13"
4830 [(set (match_operand:DI 0 "register_operand" "=d,v")
4831 (unsigned_fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4832 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4833 (clobber (reg:CC CC_REGNUM))]
4834 "TARGET_VX && TARGET_HARD_FLOAT"
4835 "@
4836 clgdbr\t%0,%h2,%1,0
4837 wclgdb\t%v0,%v1,0,%h2"
4838 [(set_attr "op_type" "RRF,VRR")
4839 (set_attr "type" "ftoi")])
4840
4841 ; clfebr, clfdbr, clfxbr, clgebr, clgdbr, clgxbr
4842 ; clfdtr, clfxtr, clgdtr, clgxtr
4843 (define_insn "*fixuns_trunc<FP:mode><GPR:mode>2_z196"
4844 [(set (match_operand:GPR 0 "register_operand" "=d")
4845 (unsigned_fix:GPR (match_operand:FP 1 "register_operand" "f")))
4846 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4847 (clobber (reg:CC CC_REGNUM))]
4848 "TARGET_Z196 && TARGET_HARD_FLOAT
4849 && (!TARGET_VX || <GPR:MODE>mode != DImode || <FP:MODE>mode != DFmode)"
4850 "cl<GPR:gf><FP:xde><FP:bt>r\t%0,%h2,%1,0"
4851 [(set_attr "op_type" "RRF")
4852 (set_attr "type" "ftoi")])
4853
4854 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
4855 [(set (match_operand:GPR 0 "register_operand" "")
4856 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
4857 "TARGET_HARD_FLOAT"
4858 {
4859 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
4860 GEN_INT (BFP_RND_TOWARD_0)));
4861 DONE;
4862 })
4863
4864 (define_insn "*fix_truncdfdi2_bfp_z13"
4865 [(set (match_operand:DI 0 "register_operand" "=d,v")
4866 (fix:DI (match_operand:DF 1 "register_operand" "f,v")))
4867 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K,K")] UNSPEC_ROUND)
4868 (clobber (reg:CC CC_REGNUM))]
4869 "TARGET_VX && TARGET_HARD_FLOAT"
4870 "@
4871 cgdbr\t%0,%h2,%1
4872 wcgdb\t%v0,%v1,0,%h2"
4873 [(set_attr "op_type" "RRE,VRR")
4874 (set_attr "type" "ftoi")])
4875
4876 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
4877 (define_insn "*fix_trunc<BFP:mode><GPR:mode>2_bfp"
4878 [(set (match_operand:GPR 0 "register_operand" "=d")
4879 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4880 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4881 (clobber (reg:CC CC_REGNUM))]
4882 "TARGET_HARD_FLOAT
4883 && (!TARGET_VX || <GPR:MODE>mode != DImode || <BFP:MODE>mode != DFmode)"
4884 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
4885 [(set_attr "op_type" "RRE")
4886 (set_attr "type" "ftoi")])
4887
4888 (define_expand "fix_trunc<BFP:mode><GPR:mode>2_bfp"
4889 [(parallel
4890 [(set (match_operand:GPR 0 "register_operand" "=d")
4891 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
4892 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
4893 (clobber (reg:CC CC_REGNUM))])]
4894 "TARGET_HARD_FLOAT")
4895 ;
4896 ; fix_trunc(td|dd)di2 instruction pattern(s).
4897 ;
4898
4899 (define_expand "fix_trunc<mode>di2"
4900 [(set (match_operand:DI 0 "register_operand" "")
4901 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
4902 "TARGET_ZARCH && TARGET_HARD_DFP"
4903 {
4904 operands[1] = force_reg (<MODE>mode, operands[1]);
4905 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
4906 GEN_INT (DFP_RND_TOWARD_0)));
4907 DONE;
4908 })
4909
4910 ; cgxtr, cgdtr
4911 (define_insn "fix_trunc<DFP:mode>di2_dfp"
4912 [(set (match_operand:DI 0 "register_operand" "=d")
4913 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
4914 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
4915 (clobber (reg:CC CC_REGNUM))]
4916 "TARGET_ZARCH && TARGET_HARD_DFP"
4917 "cg<DFP:xde>tr\t%0,%h2,%1"
4918 [(set_attr "op_type" "RRF")
4919 (set_attr "type" "ftoidfp")])
4920
4921
4922 ;
4923 ; fix_trunctf(si|di)2 instruction pattern(s).
4924 ;
4925
4926 (define_expand "fix_trunctf<mode>2"
4927 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
4928 (fix:GPR (match_operand:TF 1 "register_operand" "")))
4929 (unspec:GPR [(const_int BFP_RND_TOWARD_0)] UNSPEC_ROUND)
4930 (clobber (reg:CC CC_REGNUM))])]
4931 "TARGET_HARD_FLOAT"
4932 "")
4933
4934
4935 ;
4936 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4937 ;
4938
4939 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
4940 (define_insn "floatdi<mode>2"
4941 [(set (match_operand:FP 0 "register_operand" "=f,v")
4942 (float:FP (match_operand:DI 1 "register_operand" "d,v")))]
4943 "TARGET_ZARCH && TARGET_HARD_FLOAT"
4944 "@
4945 c<xde>g<bt>r\t%0,%1
4946 wcdgb\t%v0,%v1,0,0"
4947 [(set_attr "op_type" "RRE,VRR")
4948 (set_attr "type" "itof<mode>" )
4949 (set_attr "cpu_facility" "*,vec")
4950 (set_attr "enabled" "*,<DFDI>")])
4951
4952 ; cxfbr, cdfbr, cefbr
4953 (define_insn "floatsi<mode>2"
4954 [(set (match_operand:BFP 0 "register_operand" "=f")
4955 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
4956 "TARGET_HARD_FLOAT"
4957 "c<xde>fbr\t%0,%1"
4958 [(set_attr "op_type" "RRE")
4959 (set_attr "type" "itof<mode>" )])
4960
4961 ; cxftr, cdftr
4962 (define_insn "floatsi<mode>2"
4963 [(set (match_operand:DFP 0 "register_operand" "=f")
4964 (float:DFP (match_operand:SI 1 "register_operand" "d")))]
4965 "TARGET_Z196 && TARGET_HARD_FLOAT"
4966 "c<xde>ftr\t%0,0,%1,0"
4967 [(set_attr "op_type" "RRE")
4968 (set_attr "type" "itof<mode>" )])
4969
4970 ;
4971 ; floatuns(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
4972 ;
4973
4974 (define_insn "*floatunsdidf2_z13"
4975 [(set (match_operand:DF 0 "register_operand" "=f,v")
4976 (unsigned_float:DF (match_operand:DI 1 "register_operand" "d,v")))]
4977 "TARGET_VX && TARGET_HARD_FLOAT"
4978 "@
4979 cdlgbr\t%0,0,%1,0
4980 wcdlgb\t%v0,%v1,0,0"
4981 [(set_attr "op_type" "RRE,VRR")
4982 (set_attr "type" "itofdf")])
4983
4984 ; cxlgbr, cdlgbr, celgbr, cxlgtr, cdlgtr
4985 ; cxlfbr, cdlfbr, celfbr, cxlftr, cdlftr
4986 (define_insn "*floatuns<GPR:mode><FP:mode>2"
4987 [(set (match_operand:FP 0 "register_operand" "=f")
4988 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "d")))]
4989 "TARGET_Z196 && TARGET_HARD_FLOAT
4990 && (!TARGET_VX || <FP:MODE>mode != DFmode || <GPR:MODE>mode != DImode)"
4991 "c<FP:xde>l<GPR:gf><FP:bt>r\t%0,0,%1,0"
4992 [(set_attr "op_type" "RRE")
4993 (set_attr "type" "itof<FP:mode>")])
4994
4995 (define_expand "floatuns<GPR:mode><FP:mode>2"
4996 [(set (match_operand:FP 0 "register_operand" "")
4997 (unsigned_float:FP (match_operand:GPR 1 "register_operand" "")))]
4998 "TARGET_Z196 && TARGET_HARD_FLOAT")
4999
5000 ;
5001 ; truncdfsf2 instruction pattern(s).
5002 ;
5003
5004 (define_insn "truncdfsf2"
5005 [(set (match_operand:SF 0 "register_operand" "=f,v")
5006 (float_truncate:SF (match_operand:DF 1 "register_operand" "f,v")))]
5007 "TARGET_HARD_FLOAT"
5008 "@
5009 ledbr\t%0,%1
5010 wledb\t%v0,%v1,0,0" ; IEEE inexact exception not suppressed
5011 ; According to BFP rounding mode
5012 [(set_attr "op_type" "RRE,VRR")
5013 (set_attr "type" "ftruncdf")
5014 (set_attr "cpu_facility" "*,vec")])
5015
5016 ;
5017 ; trunctf(df|sf)2 instruction pattern(s).
5018 ;
5019
5020 ; ldxbr, lexbr
5021 (define_insn "trunctf<mode>2"
5022 [(set (match_operand:DSF 0 "register_operand" "=f")
5023 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
5024 (clobber (match_scratch:TF 2 "=f"))]
5025 "TARGET_HARD_FLOAT"
5026 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
5027 [(set_attr "length" "6")
5028 (set_attr "type" "ftrunctf")])
5029
5030 ;
5031 ; trunctddd2 and truncddsd2 instruction pattern(s).
5032 ;
5033
5034
5035 (define_expand "trunctddd2"
5036 [(parallel
5037 [(set (match_operand:DD 0 "register_operand" "")
5038 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
5039 (unspec:DI [(const_int DFP_RND_CURRENT)] UNSPEC_ROUND)
5040 (clobber (scratch:TD))])]
5041 "TARGET_HARD_DFP")
5042
5043 (define_insn "*trunctddd2"
5044 [(set (match_operand:DD 0 "register_operand" "=f")
5045 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
5046 (unspec:DI [(match_operand:DI 2 "const_mask_operand" "I")] UNSPEC_ROUND)
5047 (clobber (match_scratch:TD 3 "=f"))]
5048 "TARGET_HARD_DFP"
5049 "ldxtr\t%3,%2,%1,0\;ldr\t%0,%3"
5050 [(set_attr "length" "6")
5051 (set_attr "type" "ftruncdd")])
5052
5053 (define_insn "truncddsd2"
5054 [(set (match_operand:SD 0 "register_operand" "=f")
5055 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
5056 "TARGET_HARD_DFP"
5057 "ledtr\t%0,0,%1,0"
5058 [(set_attr "op_type" "RRF")
5059 (set_attr "type" "ftruncsd")])
5060
5061 (define_expand "trunctdsd2"
5062 [(parallel
5063 [(set (match_dup 3)
5064 (float_truncate:DD (match_operand:TD 1 "register_operand" "")))
5065 (unspec:DI [(const_int DFP_RND_PREP_FOR_SHORT_PREC)] UNSPEC_ROUND)
5066 (clobber (match_scratch:TD 2 ""))])
5067 (set (match_operand:SD 0 "register_operand" "")
5068 (float_truncate:SD (match_dup 3)))]
5069 "TARGET_HARD_DFP"
5070 {
5071 operands[3] = gen_reg_rtx (DDmode);
5072 })
5073
5074 ;
5075 ; extend(sf|df)(df|tf)2 instruction pattern(s).
5076 ;
5077
5078 (define_insn "*extendsfdf2_z13"
5079 [(set (match_operand:DF 0 "register_operand" "=f,f,v")
5080 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,R,v")))]
5081 "TARGET_VX && TARGET_HARD_FLOAT"
5082 "@
5083 ldebr\t%0,%1
5084 ldeb\t%0,%1
5085 wldeb\t%v0,%v1"
5086 [(set_attr "op_type" "RRE,RXE,VRR")
5087 (set_attr "type" "fsimpdf, floaddf,fsimpdf")])
5088
5089 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
5090 (define_insn "*extend<DSF:mode><BFP:mode>2"
5091 [(set (match_operand:BFP 0 "register_operand" "=f,f")
5092 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
5093 "TARGET_HARD_FLOAT
5094 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)
5095 && (!TARGET_VX || <BFP:MODE>mode != DFmode || <DSF:MODE>mode != SFmode)"
5096 "@
5097 l<BFP:xde><DSF:xde>br\t%0,%1
5098 l<BFP:xde><DSF:xde>b\t%0,%1"
5099 [(set_attr "op_type" "RRE,RXE")
5100 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
5101
5102 (define_expand "extend<DSF:mode><BFP:mode>2"
5103 [(set (match_operand:BFP 0 "register_operand" "")
5104 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "")))]
5105 "TARGET_HARD_FLOAT
5106 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)")
5107
5108 ;
5109 ; extendddtd2 and extendsddd2 instruction pattern(s).
5110 ;
5111
5112 (define_insn "extendddtd2"
5113 [(set (match_operand:TD 0 "register_operand" "=f")
5114 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
5115 "TARGET_HARD_DFP"
5116 "lxdtr\t%0,%1,0"
5117 [(set_attr "op_type" "RRF")
5118 (set_attr "type" "fsimptf")])
5119
5120 (define_insn "extendsddd2"
5121 [(set (match_operand:DD 0 "register_operand" "=f")
5122 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
5123 "TARGET_HARD_DFP"
5124 "ldetr\t%0,%1,0"
5125 [(set_attr "op_type" "RRF")
5126 (set_attr "type" "fsimptf")])
5127
5128 (define_expand "extendsdtd2"
5129 [(set (match_dup 2)
5130 (float_extend:DD (match_operand:SD 1 "register_operand" "")))
5131 (set (match_operand:TD 0 "register_operand" "")
5132 (float_extend:TD (match_dup 2)))]
5133 "TARGET_HARD_DFP"
5134 {
5135 operands[2] = gen_reg_rtx (DDmode);
5136 })
5137
5138 ; Binary Floating Point - load fp integer
5139
5140 ; Expanders for: floor, btrunc, round, ceil, and nearbyint
5141 ; For all of them the inexact exceptions are suppressed.
5142
5143 ; fiebra, fidbra, fixbra
5144 (define_insn "<FPINT:fpint_name><BFP:mode>2"
5145 [(set (match_operand:BFP 0 "register_operand" "=f")
5146 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5147 FPINT))]
5148 "TARGET_Z196"
5149 "fi<BFP:xde>bra\t%0,<FPINT:fpint_roundingmode>,%1,4"
5150 [(set_attr "op_type" "RRF")
5151 (set_attr "type" "fsimp<BFP:mode>")])
5152
5153 ; rint is supposed to raise an inexact exception so we can use the
5154 ; older instructions.
5155
5156 ; fiebr, fidbr, fixbr
5157 (define_insn "rint<BFP:mode>2"
5158 [(set (match_operand:BFP 0 "register_operand" "=f")
5159 (unspec:BFP [(match_operand:BFP 1 "register_operand" "f")]
5160 UNSPEC_FPINT_RINT))]
5161 ""
5162 "fi<BFP:xde>br\t%0,0,%1"
5163 [(set_attr "op_type" "RRF")
5164 (set_attr "type" "fsimp<BFP:mode>")])
5165
5166
5167 ; Decimal Floating Point - load fp integer
5168
5169 ; fidtr, fixtr
5170 (define_insn "<FPINT:fpint_name><DFP:mode>2"
5171 [(set (match_operand:DFP 0 "register_operand" "=f")
5172 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5173 FPINT))]
5174 "TARGET_HARD_DFP"
5175 "fi<DFP:xde>tr\t%0,<FPINT:fpint_roundingmode>,%1,4"
5176 [(set_attr "op_type" "RRF")
5177 (set_attr "type" "fsimp<DFP:mode>")])
5178
5179 ; fidtr, fixtr
5180 (define_insn "rint<DFP:mode>2"
5181 [(set (match_operand:DFP 0 "register_operand" "=f")
5182 (unspec:DFP [(match_operand:DFP 1 "register_operand" "f")]
5183 UNSPEC_FPINT_RINT))]
5184 "TARGET_HARD_DFP"
5185 "fi<DFP:xde>tr\t%0,0,%1,0"
5186 [(set_attr "op_type" "RRF")
5187 (set_attr "type" "fsimp<DFP:mode>")])
5188
5189 ;
5190 ; Binary <-> Decimal floating point trunc patterns
5191 ;
5192
5193 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
5194 [(set (reg:DFP_ALL FPR0_REGNUM)
5195 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5196 (use (reg:SI GPR0_REGNUM))
5197 (clobber (reg:CC CC_REGNUM))
5198 (clobber (reg:SI GPR1_REGNUM))]
5199 "TARGET_HARD_DFP"
5200 "pfpo")
5201
5202 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
5203 [(set (reg:BFP FPR0_REGNUM)
5204 (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5205 (use (reg:SI GPR0_REGNUM))
5206 (clobber (reg:CC CC_REGNUM))
5207 (clobber (reg:SI GPR1_REGNUM))]
5208 "TARGET_HARD_DFP"
5209 "pfpo")
5210
5211 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
5212 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5213 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5214 (parallel
5215 [(set (reg:DFP_ALL FPR0_REGNUM)
5216 (float_truncate:DFP_ALL (reg:BFP FPR4_REGNUM)))
5217 (use (reg:SI GPR0_REGNUM))
5218 (clobber (reg:CC CC_REGNUM))
5219 (clobber (reg:SI GPR1_REGNUM))])
5220 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5221 (reg:DFP_ALL FPR0_REGNUM))]
5222 "TARGET_HARD_DFP
5223 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5224 {
5225 HOST_WIDE_INT flags;
5226
5227 flags = (PFPO_CONVERT |
5228 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5229 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5230
5231 operands[2] = GEN_INT (flags);
5232 })
5233
5234 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
5235 [(set (reg:DFP_ALL FPR4_REGNUM)
5236 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5237 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5238 (parallel
5239 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR4_REGNUM)))
5240 (use (reg:SI GPR0_REGNUM))
5241 (clobber (reg:CC CC_REGNUM))
5242 (clobber (reg:SI GPR1_REGNUM))])
5243 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5244 "TARGET_HARD_DFP
5245 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
5246 {
5247 HOST_WIDE_INT flags;
5248
5249 flags = (PFPO_CONVERT |
5250 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5251 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5252
5253 operands[2] = GEN_INT (flags);
5254 })
5255
5256 ;
5257 ; Binary <-> Decimal floating point extend patterns
5258 ;
5259
5260 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
5261 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5262 (use (reg:SI GPR0_REGNUM))
5263 (clobber (reg:CC CC_REGNUM))
5264 (clobber (reg:SI GPR1_REGNUM))]
5265 "TARGET_HARD_DFP"
5266 "pfpo")
5267
5268 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
5269 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL 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_expand "extend<BFP:mode><DFP_ALL:mode>2"
5277 [(set (reg:BFP FPR4_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
5278 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5279 (parallel
5280 [(set (reg:DFP_ALL FPR0_REGNUM)
5281 (float_extend:DFP_ALL (reg:BFP FPR4_REGNUM)))
5282 (use (reg:SI GPR0_REGNUM))
5283 (clobber (reg:CC CC_REGNUM))
5284 (clobber (reg:SI GPR1_REGNUM))])
5285 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
5286 (reg:DFP_ALL FPR0_REGNUM))]
5287 "TARGET_HARD_DFP
5288 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
5289 {
5290 HOST_WIDE_INT flags;
5291
5292 flags = (PFPO_CONVERT |
5293 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
5294 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
5295
5296 operands[2] = GEN_INT (flags);
5297 })
5298
5299 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
5300 [(set (reg:DFP_ALL FPR4_REGNUM)
5301 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
5302 (set (reg:SI GPR0_REGNUM) (match_dup 2))
5303 (parallel
5304 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR4_REGNUM)))
5305 (use (reg:SI GPR0_REGNUM))
5306 (clobber (reg:CC CC_REGNUM))
5307 (clobber (reg:SI GPR1_REGNUM))])
5308 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
5309 "TARGET_HARD_DFP
5310 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
5311 {
5312 HOST_WIDE_INT flags;
5313
5314 flags = (PFPO_CONVERT |
5315 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
5316 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
5317
5318 operands[2] = GEN_INT (flags);
5319 })
5320
5321
5322 ;;
5323 ;; ARITHMETIC OPERATIONS
5324 ;;
5325 ; arithmetic operations set the ConditionCode,
5326 ; because of unpredictable Bits in Register for Halfword and Byte
5327 ; the ConditionCode can be set wrong in operations for Halfword and Byte
5328
5329 ;;
5330 ;;- Add instructions.
5331 ;;
5332
5333 ;
5334 ; addti3 instruction pattern(s).
5335 ;
5336
5337 (define_expand "addti3"
5338 [(parallel
5339 [(set (match_operand:TI 0 "register_operand" "")
5340 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5341 (match_operand:TI 2 "general_operand" "") ) )
5342 (clobber (reg:CC CC_REGNUM))])]
5343 "TARGET_ZARCH"
5344 {
5345 /* For z13 we have vaq which doesn't set CC. */
5346 if (TARGET_VX)
5347 {
5348 emit_insn (gen_rtx_SET (operands[0],
5349 gen_rtx_PLUS (TImode,
5350 copy_to_mode_reg (TImode, operands[1]),
5351 copy_to_mode_reg (TImode, operands[2]))));
5352 DONE;
5353 }
5354 })
5355
5356 (define_insn_and_split "*addti3"
5357 [(set (match_operand:TI 0 "register_operand" "=&d")
5358 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
5359 (match_operand:TI 2 "general_operand" "do") ) )
5360 (clobber (reg:CC CC_REGNUM))]
5361 "TARGET_ZARCH"
5362 "#"
5363 "&& reload_completed"
5364 [(parallel
5365 [(set (reg:CCL1 CC_REGNUM)
5366 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
5367 (match_dup 7)))
5368 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
5369 (parallel
5370 [(set (match_dup 3) (plus:DI
5371 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
5372 (match_dup 4)) (match_dup 5)))
5373 (clobber (reg:CC CC_REGNUM))])]
5374 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5375 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5376 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5377 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5378 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5379 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5380 [(set_attr "op_type" "*")
5381 (set_attr "cpu_facility" "*")])
5382
5383 ;
5384 ; adddi3 instruction pattern(s).
5385 ;
5386
5387 (define_expand "adddi3"
5388 [(parallel
5389 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5390 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5391 (match_operand:DI 2 "general_operand" "")))
5392 (clobber (reg:CC CC_REGNUM))])]
5393 ""
5394 "")
5395
5396 (define_insn "*adddi3_sign"
5397 [(set (match_operand:DI 0 "register_operand" "=d,d")
5398 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5399 (match_operand:DI 1 "register_operand" "0,0")))
5400 (clobber (reg:CC CC_REGNUM))]
5401 "TARGET_ZARCH"
5402 "@
5403 agfr\t%0,%2
5404 agf\t%0,%2"
5405 [(set_attr "op_type" "RRE,RXY")
5406 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5407
5408 (define_insn "*adddi3_zero_cc"
5409 [(set (reg CC_REGNUM)
5410 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5411 (match_operand:DI 1 "register_operand" "0,0"))
5412 (const_int 0)))
5413 (set (match_operand:DI 0 "register_operand" "=d,d")
5414 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
5415 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5416 "@
5417 algfr\t%0,%2
5418 algf\t%0,%2"
5419 [(set_attr "op_type" "RRE,RXY")
5420 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5421
5422 (define_insn "*adddi3_zero_cconly"
5423 [(set (reg CC_REGNUM)
5424 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5425 (match_operand:DI 1 "register_operand" "0,0"))
5426 (const_int 0)))
5427 (clobber (match_scratch:DI 0 "=d,d"))]
5428 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5429 "@
5430 algfr\t%0,%2
5431 algf\t%0,%2"
5432 [(set_attr "op_type" "RRE,RXY")
5433 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5434
5435 (define_insn "*adddi3_zero"
5436 [(set (match_operand:DI 0 "register_operand" "=d,d")
5437 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
5438 (match_operand:DI 1 "register_operand" "0,0")))
5439 (clobber (reg:CC CC_REGNUM))]
5440 "TARGET_ZARCH"
5441 "@
5442 algfr\t%0,%2
5443 algf\t%0,%2"
5444 [(set_attr "op_type" "RRE,RXY")
5445 (set_attr "z10prop" "z10_super_E1,z10_super_E1")])
5446
5447 (define_insn_and_split "*adddi3_31z"
5448 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5449 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5450 (match_operand:DI 2 "general_operand" "do") ) )
5451 (clobber (reg:CC CC_REGNUM))]
5452 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5453 "#"
5454 "&& reload_completed"
5455 [(parallel
5456 [(set (reg:CCL1 CC_REGNUM)
5457 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5458 (match_dup 7)))
5459 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5460 (parallel
5461 [(set (match_dup 3) (plus:SI
5462 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
5463 (match_dup 4)) (match_dup 5)))
5464 (clobber (reg:CC CC_REGNUM))])]
5465 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5466 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5467 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5468 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5469 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5470 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5471
5472 (define_insn_and_split "*adddi3_31"
5473 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
5474 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5475 (match_operand:DI 2 "general_operand" "do") ) )
5476 (clobber (reg:CC CC_REGNUM))]
5477 "!TARGET_CPU_ZARCH"
5478 "#"
5479 "&& reload_completed"
5480 [(parallel
5481 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
5482 (clobber (reg:CC CC_REGNUM))])
5483 (parallel
5484 [(set (reg:CCL1 CC_REGNUM)
5485 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
5486 (match_dup 7)))
5487 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
5488 (set (pc)
5489 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
5490 (pc)
5491 (label_ref (match_dup 9))))
5492 (parallel
5493 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
5494 (clobber (reg:CC CC_REGNUM))])
5495 (match_dup 9)]
5496 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5497 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5498 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5499 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5500 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5501 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5502 operands[9] = gen_label_rtx ();")
5503
5504 ;
5505 ; addsi3 instruction pattern(s).
5506 ;
5507
5508 (define_expand "addsi3"
5509 [(parallel
5510 [(set (match_operand:SI 0 "nonimmediate_operand" "")
5511 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5512 (match_operand:SI 2 "general_operand" "")))
5513 (clobber (reg:CC CC_REGNUM))])]
5514 ""
5515 "")
5516
5517 (define_insn "*addsi3_sign"
5518 [(set (match_operand:SI 0 "register_operand" "=d,d")
5519 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
5520 (match_operand:SI 1 "register_operand" "0,0")))
5521 (clobber (reg:CC CC_REGNUM))]
5522 ""
5523 "@
5524 ah\t%0,%2
5525 ahy\t%0,%2"
5526 [(set_attr "op_type" "RX,RXY")
5527 (set_attr "cpu_facility" "*,longdisp")
5528 (set_attr "z196prop" "z196_cracked,z196_cracked")])
5529
5530 ;
5531 ; add(di|si)3 instruction pattern(s).
5532 ;
5533
5534 ; ark, agrk, ar, ahi, ahik, aghik, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
5535 (define_insn "*add<mode>3"
5536 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d, d, d,d,d,S")
5537 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,d, 0, 0,0,0,0")
5538 (match_operand:GPR 2 "general_operand" " d,d,K,K,Op,On,R,T,C") ) )
5539 (clobber (reg:CC CC_REGNUM))]
5540 ""
5541 "@
5542 a<g>r\t%0,%2
5543 a<g>rk\t%0,%1,%2
5544 a<g>hi\t%0,%h2
5545 a<g>hik\t%0,%1,%h2
5546 al<g>fi\t%0,%2
5547 sl<g>fi\t%0,%n2
5548 a<g>\t%0,%2
5549 a<y>\t%0,%2
5550 a<g>si\t%0,%c2"
5551 [(set_attr "op_type" "RR<E>,RRF,RI,RIE,RIL,RIL,RX<Y>,RXY,SIY")
5552 (set_attr "cpu_facility" "*,z196,*,z196,extimm,extimm,*,longdisp,z10")
5553 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,z10_super_E1,z10_super_E1,
5554 z10_super_E1,z10_super_E1,z10_super_E1")])
5555
5556 ; alr, alfi, slfi, al, aly, alrk, alhsik, algr, algfi, slgfi, alg, alsi, algsi, algrk, alghsik
5557 (define_insn "*add<mode>3_carry1_cc"
5558 [(set (reg CC_REGNUM)
5559 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5560 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5561 (match_dup 1)))
5562 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,d")
5563 (plus:GPR (match_dup 1) (match_dup 2)))]
5564 "s390_match_ccmode (insn, CCL1mode)"
5565 "@
5566 al<g>r\t%0,%2
5567 al<g>rk\t%0,%1,%2
5568 al<g>fi\t%0,%2
5569 sl<g>fi\t%0,%n2
5570 al<g>hsik\t%0,%1,%h2
5571 al<g>\t%0,%2
5572 al<y>\t%0,%2
5573 al<g>si\t%0,%c2"
5574 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5575 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5576 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5577 z10_super_E1,z10_super_E1,z10_super_E1")])
5578
5579 ; alr, al, aly, algr, alg, alrk, algrk
5580 (define_insn "*add<mode>3_carry1_cconly"
5581 [(set (reg CC_REGNUM)
5582 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5583 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5584 (match_dup 1)))
5585 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5586 "s390_match_ccmode (insn, CCL1mode)"
5587 "@
5588 al<g>r\t%0,%2
5589 al<g>rk\t%0,%1,%2
5590 al<g>\t%0,%2
5591 al<y>\t%0,%2"
5592 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5593 (set_attr "cpu_facility" "*,z196,*,longdisp")
5594 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5595
5596 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5597 (define_insn "*add<mode>3_carry2_cc"
5598 [(set (reg CC_REGNUM)
5599 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5600 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5601 (match_dup 2)))
5602 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5603 (plus:GPR (match_dup 1) (match_dup 2)))]
5604 "s390_match_ccmode (insn, CCL1mode)"
5605 "@
5606 al<g>r\t%0,%2
5607 al<g>rk\t%0,%1,%2
5608 al<g>fi\t%0,%2
5609 sl<g>fi\t%0,%n2
5610 al<g>hsik\t%0,%1,%h2
5611 al<g>\t%0,%2
5612 al<y>\t%0,%2
5613 al<g>si\t%0,%c2"
5614 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5615 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5616 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,*,
5617 z10_super_E1,z10_super_E1,z10_super_E1")])
5618
5619 ; alr, al, aly, algr, alg, alrk, algrk
5620 (define_insn "*add<mode>3_carry2_cconly"
5621 [(set (reg CC_REGNUM)
5622 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5623 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5624 (match_dup 2)))
5625 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5626 "s390_match_ccmode (insn, CCL1mode)"
5627 "@
5628 al<g>r\t%0,%2
5629 al<g>rk\t%0,%1,%2
5630 al<g>\t%0,%2
5631 al<y>\t%0,%2"
5632 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5633 (set_attr "cpu_facility" "*,z196,*,longdisp")
5634 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5635
5636 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi, alrk, algrk, alhsik, alghsik
5637 (define_insn "*add<mode>3_cc"
5638 [(set (reg CC_REGNUM)
5639 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d, 0, 0,d,0,0,0")
5640 (match_operand:GPR 2 "general_operand" " d,d,Op,On,K,R,T,C"))
5641 (const_int 0)))
5642 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d, d, d,d,d,d,S")
5643 (plus:GPR (match_dup 1) (match_dup 2)))]
5644 "s390_match_ccmode (insn, CCLmode)"
5645 "@
5646 al<g>r\t%0,%2
5647 al<g>rk\t%0,%1,%2
5648 al<g>fi\t%0,%2
5649 sl<g>fi\t%0,%n2
5650 al<g>hsik\t%0,%1,%h2
5651 al<g>\t%0,%2
5652 al<y>\t%0,%2
5653 al<g>si\t%0,%c2"
5654 [(set_attr "op_type" "RR<E>,RRF,RIL,RIL,RIE,RX<Y>,RXY,SIY")
5655 (set_attr "cpu_facility" "*,z196,extimm,extimm,z196,*,longdisp,z10")
5656 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1,
5657 *,z10_super_E1,z10_super_E1,z10_super_E1")])
5658
5659 ; alr, al, aly, algr, alg, alrk, algrk
5660 (define_insn "*add<mode>3_cconly"
5661 [(set (reg CC_REGNUM)
5662 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5663 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
5664 (const_int 0)))
5665 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5666 "s390_match_ccmode (insn, CCLmode)"
5667 "@
5668 al<g>r\t%0,%2
5669 al<g>rk\t%0,%1,%2
5670 al<g>\t%0,%2
5671 al<y>\t%0,%2"
5672 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5673 (set_attr "cpu_facility" "*,z196,*,longdisp")
5674 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5675
5676 ; alr, al, aly, algr, alg, alrk, algrk
5677 (define_insn "*add<mode>3_cconly2"
5678 [(set (reg CC_REGNUM)
5679 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,d,0,0")
5680 (neg:GPR (match_operand:GPR 2 "general_operand" "d,d,R,T"))))
5681 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
5682 "s390_match_ccmode(insn, CCLmode)"
5683 "@
5684 al<g>r\t%0,%2
5685 al<g>rk\t%0,%1,%2
5686 al<g>\t%0,%2
5687 al<y>\t%0,%2"
5688 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
5689 (set_attr "cpu_facility" "*,z196,*,longdisp")
5690 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5691
5692 ; ahi, afi, aghi, agfi, asi, agsi
5693 (define_insn "*add<mode>3_imm_cc"
5694 [(set (reg CC_REGNUM)
5695 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" " 0, d,0, 0")
5696 (match_operand:GPR 2 "const_int_operand" " K, K,Os,C"))
5697 (const_int 0)))
5698 (set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,d, S")
5699 (plus:GPR (match_dup 1) (match_dup 2)))]
5700 "s390_match_ccmode (insn, CCAmode)
5701 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
5702 || (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
5703 /* Avoid INT32_MIN on 32 bit. */
5704 && (!TARGET_ZARCH || INTVAL (operands[2]) != -0x7fffffff - 1)))"
5705 "@
5706 a<g>hi\t%0,%h2
5707 a<g>hik\t%0,%1,%h2
5708 a<g>fi\t%0,%2
5709 a<g>si\t%0,%c2"
5710 [(set_attr "op_type" "RI,RIE,RIL,SIY")
5711 (set_attr "cpu_facility" "*,z196,extimm,z10")
5712 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
5713
5714 ;
5715 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
5716 ;
5717
5718 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5719 ; FIXME: wfadb does not clobber cc
5720 (define_insn "add<mode>3"
5721 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
5722 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
5723 (match_operand:FP 2 "general_operand" "f,f,R,v")))
5724 (clobber (reg:CC CC_REGNUM))]
5725 "TARGET_HARD_FLOAT"
5726 "@
5727 a<xde>tr\t%0,%1,%2
5728 a<xde>br\t%0,%2
5729 a<xde>b\t%0,%2
5730 wfadb\t%v0,%v1,%v2"
5731 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
5732 (set_attr "type" "fsimp<mode>")
5733 (set_attr "cpu_facility" "*,*,*,vec")
5734 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
5735
5736 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5737 (define_insn "*add<mode>3_cc"
5738 [(set (reg CC_REGNUM)
5739 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5740 (match_operand:FP 2 "general_operand" "f,f,R"))
5741 (match_operand:FP 3 "const0_operand" "")))
5742 (set (match_operand:FP 0 "register_operand" "=f,f,f")
5743 (plus:FP (match_dup 1) (match_dup 2)))]
5744 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5745 "@
5746 a<xde>tr\t%0,%1,%2
5747 a<xde>br\t%0,%2
5748 a<xde>b\t%0,%2"
5749 [(set_attr "op_type" "RRF,RRE,RXE")
5750 (set_attr "type" "fsimp<mode>")
5751 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5752
5753 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
5754 (define_insn "*add<mode>3_cconly"
5755 [(set (reg CC_REGNUM)
5756 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0")
5757 (match_operand:FP 2 "general_operand" "f,f,R"))
5758 (match_operand:FP 3 "const0_operand" "")))
5759 (clobber (match_scratch:FP 0 "=f,f,f"))]
5760 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
5761 "@
5762 a<xde>tr\t%0,%1,%2
5763 a<xde>br\t%0,%2
5764 a<xde>b\t%0,%2"
5765 [(set_attr "op_type" "RRF,RRE,RXE")
5766 (set_attr "type" "fsimp<mode>")
5767 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
5768
5769 ;
5770 ; Pointer add instruction patterns
5771 ;
5772
5773 ; This will match "*la_64"
5774 (define_expand "addptrdi3"
5775 [(set (match_operand:DI 0 "register_operand" "")
5776 (plus:DI (match_operand:DI 1 "register_operand" "")
5777 (match_operand:DI 2 "nonmemory_operand" "")))]
5778 "TARGET_64BIT"
5779 {
5780 if (GET_CODE (operands[2]) == CONST_INT)
5781 {
5782 HOST_WIDE_INT c = INTVAL (operands[2]);
5783
5784 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5785 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5786 {
5787 operands[2] = force_const_mem (DImode, operands[2]);
5788 operands[2] = force_reg (DImode, operands[2]);
5789 }
5790 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5791 operands[2] = force_reg (DImode, operands[2]);
5792 }
5793 })
5794
5795 ; For 31 bit we have to prevent the generated pattern from matching
5796 ; normal ADDs since la only does a 31 bit add. This is supposed to
5797 ; match "force_la_31".
5798 (define_expand "addptrsi3"
5799 [(parallel
5800 [(set (match_operand:SI 0 "register_operand" "")
5801 (plus:SI (match_operand:SI 1 "register_operand" "")
5802 (match_operand:SI 2 "nonmemory_operand" "")))
5803 (use (const_int 0))])]
5804 "!TARGET_64BIT"
5805 {
5806 if (GET_CODE (operands[2]) == CONST_INT)
5807 {
5808 HOST_WIDE_INT c = INTVAL (operands[2]);
5809
5810 if (!CONST_OK_FOR_CONSTRAINT_P (c, 'K', "K")
5811 && !CONST_OK_FOR_CONSTRAINT_P (c, 'O', "Os"))
5812 {
5813 operands[2] = force_const_mem (SImode, operands[2]);
5814 operands[2] = force_reg (SImode, operands[2]);
5815 }
5816 else if (!DISP_IN_RANGE (INTVAL (operands[2])))
5817 operands[2] = force_reg (SImode, operands[2]);
5818 }
5819 })
5820
5821 ;;
5822 ;;- Subtract instructions.
5823 ;;
5824
5825 ;
5826 ; subti3 instruction pattern(s).
5827 ;
5828
5829 (define_expand "subti3"
5830 [(parallel
5831 [(set (match_operand:TI 0 "register_operand" "")
5832 (minus:TI (match_operand:TI 1 "register_operand" "")
5833 (match_operand:TI 2 "general_operand" "") ) )
5834 (clobber (reg:CC CC_REGNUM))])]
5835 "TARGET_ZARCH"
5836 {
5837 /* For z13 we have vsq which doesn't set CC. */
5838 if (TARGET_VX)
5839 {
5840 emit_insn (gen_rtx_SET (operands[0],
5841 gen_rtx_MINUS (TImode,
5842 operands[1],
5843 copy_to_mode_reg (TImode, operands[2]))));
5844 DONE;
5845 }
5846 })
5847
5848 (define_insn_and_split "*subti3"
5849 [(set (match_operand:TI 0 "register_operand" "=&d")
5850 (minus:TI (match_operand:TI 1 "register_operand" "0")
5851 (match_operand:TI 2 "general_operand" "do") ) )
5852 (clobber (reg:CC CC_REGNUM))]
5853 "TARGET_ZARCH"
5854 "#"
5855 "&& reload_completed"
5856 [(parallel
5857 [(set (reg:CCL2 CC_REGNUM)
5858 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
5859 (match_dup 7)))
5860 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
5861 (parallel
5862 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
5863 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
5864 (clobber (reg:CC CC_REGNUM))])]
5865 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
5866 operands[4] = operand_subword (operands[1], 0, 0, TImode);
5867 operands[5] = operand_subword (operands[2], 0, 0, TImode);
5868 operands[6] = operand_subword (operands[0], 1, 0, TImode);
5869 operands[7] = operand_subword (operands[1], 1, 0, TImode);
5870 operands[8] = operand_subword (operands[2], 1, 0, TImode);"
5871 [(set_attr "op_type" "*")
5872 (set_attr "cpu_facility" "*")])
5873
5874 ;
5875 ; subdi3 instruction pattern(s).
5876 ;
5877
5878 (define_expand "subdi3"
5879 [(parallel
5880 [(set (match_operand:DI 0 "register_operand" "")
5881 (minus:DI (match_operand:DI 1 "register_operand" "")
5882 (match_operand:DI 2 "general_operand" "")))
5883 (clobber (reg:CC CC_REGNUM))])]
5884 ""
5885 "")
5886
5887 (define_insn "*subdi3_sign"
5888 [(set (match_operand:DI 0 "register_operand" "=d,d")
5889 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5890 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5891 (clobber (reg:CC CC_REGNUM))]
5892 "TARGET_ZARCH"
5893 "@
5894 sgfr\t%0,%2
5895 sgf\t%0,%2"
5896 [(set_attr "op_type" "RRE,RXY")
5897 (set_attr "z10prop" "z10_c,*")
5898 (set_attr "z196prop" "z196_cracked")])
5899
5900 (define_insn "*subdi3_zero_cc"
5901 [(set (reg CC_REGNUM)
5902 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5903 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5904 (const_int 0)))
5905 (set (match_operand:DI 0 "register_operand" "=d,d")
5906 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
5907 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5908 "@
5909 slgfr\t%0,%2
5910 slgf\t%0,%2"
5911 [(set_attr "op_type" "RRE,RXY")
5912 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5913
5914 (define_insn "*subdi3_zero_cconly"
5915 [(set (reg CC_REGNUM)
5916 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5917 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T")))
5918 (const_int 0)))
5919 (clobber (match_scratch:DI 0 "=d,d"))]
5920 "s390_match_ccmode (insn, CCLmode) && TARGET_ZARCH"
5921 "@
5922 slgfr\t%0,%2
5923 slgf\t%0,%2"
5924 [(set_attr "op_type" "RRE,RXY")
5925 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5926
5927 (define_insn "*subdi3_zero"
5928 [(set (match_operand:DI 0 "register_operand" "=d,d")
5929 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
5930 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,T"))))
5931 (clobber (reg:CC CC_REGNUM))]
5932 "TARGET_ZARCH"
5933 "@
5934 slgfr\t%0,%2
5935 slgf\t%0,%2"
5936 [(set_attr "op_type" "RRE,RXY")
5937 (set_attr "z10prop" "z10_super_c_E1,z10_super_E1")])
5938
5939 (define_insn_and_split "*subdi3_31z"
5940 [(set (match_operand:DI 0 "register_operand" "=&d")
5941 (minus:DI (match_operand:DI 1 "register_operand" "0")
5942 (match_operand:DI 2 "general_operand" "do") ) )
5943 (clobber (reg:CC CC_REGNUM))]
5944 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
5945 "#"
5946 "&& reload_completed"
5947 [(parallel
5948 [(set (reg:CCL2 CC_REGNUM)
5949 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5950 (match_dup 7)))
5951 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5952 (parallel
5953 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
5954 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
5955 (clobber (reg:CC CC_REGNUM))])]
5956 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5957 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5958 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5959 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5960 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5961 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
5962
5963 (define_insn_and_split "*subdi3_31"
5964 [(set (match_operand:DI 0 "register_operand" "=&d")
5965 (minus:DI (match_operand:DI 1 "register_operand" "0")
5966 (match_operand:DI 2 "general_operand" "do") ) )
5967 (clobber (reg:CC CC_REGNUM))]
5968 "!TARGET_CPU_ZARCH"
5969 "#"
5970 "&& reload_completed"
5971 [(parallel
5972 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
5973 (clobber (reg:CC CC_REGNUM))])
5974 (parallel
5975 [(set (reg:CCL2 CC_REGNUM)
5976 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
5977 (match_dup 7)))
5978 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
5979 (set (pc)
5980 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
5981 (pc)
5982 (label_ref (match_dup 9))))
5983 (parallel
5984 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
5985 (clobber (reg:CC CC_REGNUM))])
5986 (match_dup 9)]
5987 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
5988 operands[4] = operand_subword (operands[1], 0, 0, DImode);
5989 operands[5] = operand_subword (operands[2], 0, 0, DImode);
5990 operands[6] = operand_subword (operands[0], 1, 0, DImode);
5991 operands[7] = operand_subword (operands[1], 1, 0, DImode);
5992 operands[8] = operand_subword (operands[2], 1, 0, DImode);
5993 operands[9] = gen_label_rtx ();")
5994
5995 ;
5996 ; subsi3 instruction pattern(s).
5997 ;
5998
5999 (define_expand "subsi3"
6000 [(parallel
6001 [(set (match_operand:SI 0 "register_operand" "")
6002 (minus:SI (match_operand:SI 1 "register_operand" "")
6003 (match_operand:SI 2 "general_operand" "")))
6004 (clobber (reg:CC CC_REGNUM))])]
6005 ""
6006 "")
6007
6008 (define_insn "*subsi3_sign"
6009 [(set (match_operand:SI 0 "register_operand" "=d,d")
6010 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6011 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
6012 (clobber (reg:CC CC_REGNUM))]
6013 ""
6014 "@
6015 sh\t%0,%2
6016 shy\t%0,%2"
6017 [(set_attr "op_type" "RX,RXY")
6018 (set_attr "cpu_facility" "*,longdisp")
6019 (set_attr "z196prop" "z196_cracked,z196_cracked")])
6020
6021 ;
6022 ; sub(di|si)3 instruction pattern(s).
6023 ;
6024
6025 ; sr, s, sy, sgr, sg, srk, sgrk
6026 (define_insn "*sub<mode>3"
6027 [(set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6028 (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6029 (match_operand:GPR 2 "general_operand" "d,d,R,T") ) )
6030 (clobber (reg:CC CC_REGNUM))]
6031 ""
6032 "@
6033 s<g>r\t%0,%2
6034 s<g>rk\t%0,%1,%2
6035 s<g>\t%0,%2
6036 s<y>\t%0,%2"
6037 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6038 (set_attr "cpu_facility" "*,z196,*,longdisp")
6039 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6040
6041 ; slr, sl, sly, slgr, slg, slrk, slgrk
6042 (define_insn "*sub<mode>3_borrow_cc"
6043 [(set (reg CC_REGNUM)
6044 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6045 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6046 (match_dup 1)))
6047 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6048 (minus:GPR (match_dup 1) (match_dup 2)))]
6049 "s390_match_ccmode (insn, CCL2mode)"
6050 "@
6051 sl<g>r\t%0,%2
6052 sl<g>rk\t%0,%1,%2
6053 sl<g>\t%0,%2
6054 sl<y>\t%0,%2"
6055 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6056 (set_attr "cpu_facility" "*,z196,*,longdisp")
6057 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6058
6059 ; slr, sl, sly, slgr, slg, slrk, slgrk
6060 (define_insn "*sub<mode>3_borrow_cconly"
6061 [(set (reg CC_REGNUM)
6062 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6063 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6064 (match_dup 1)))
6065 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6066 "s390_match_ccmode (insn, CCL2mode)"
6067 "@
6068 sl<g>r\t%0,%2
6069 sl<g>rk\t%0,%1,%2
6070 sl<g>\t%0,%2
6071 sl<y>\t%0,%2"
6072 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6073 (set_attr "cpu_facility" "*,z196,*,longdisp")
6074 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6075
6076 ; slr, sl, sly, slgr, slg, slrk, slgrk
6077 (define_insn "*sub<mode>3_cc"
6078 [(set (reg CC_REGNUM)
6079 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6080 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6081 (const_int 0)))
6082 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6083 (minus:GPR (match_dup 1) (match_dup 2)))]
6084 "s390_match_ccmode (insn, CCLmode)"
6085 "@
6086 sl<g>r\t%0,%2
6087 sl<g>rk\t%0,%1,%2
6088 sl<g>\t%0,%2
6089 sl<y>\t%0,%2"
6090 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6091 (set_attr "cpu_facility" "*,z196,*,longdisp")
6092 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6093
6094 ; slr, sl, sly, slgr, slg, slrk, slgrk
6095 (define_insn "*sub<mode>3_cc2"
6096 [(set (reg CC_REGNUM)
6097 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
6098 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
6099 (set (match_operand:GPR 0 "register_operand" "=d,d,d,d")
6100 (minus:GPR (match_dup 1) (match_dup 2)))]
6101 "s390_match_ccmode (insn, CCL3mode)"
6102 "@
6103 sl<g>r\t%0,%2
6104 sl<g>rk\t%0,%1,%2
6105 sl<g>\t%0,%2
6106 sl<y>\t%0,%2"
6107 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6108 (set_attr "cpu_facility" "*,z196,*,longdisp")
6109 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6110
6111 ; slr, sl, sly, slgr, slg, slrk, slgrk
6112 (define_insn "*sub<mode>3_cconly"
6113 [(set (reg CC_REGNUM)
6114 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,d,0,0")
6115 (match_operand:GPR 2 "general_operand" "d,d,R,T"))
6116 (const_int 0)))
6117 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6118 "s390_match_ccmode (insn, CCLmode)"
6119 "@
6120 sl<g>r\t%0,%2
6121 sl<g>rk\t%0,%1,%2
6122 sl<g>\t%0,%2
6123 sl<y>\t%0,%2"
6124 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6125 (set_attr "cpu_facility" "*,z196,*,longdisp")
6126 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6127
6128
6129 ; slr, sl, sly, slgr, slg, slrk, slgrk
6130 (define_insn "*sub<mode>3_cconly2"
6131 [(set (reg CC_REGNUM)
6132 (compare (match_operand:GPR 1 "register_operand" "0,d,0,0")
6133 (match_operand:GPR 2 "general_operand" "d,d,R,T")))
6134 (clobber (match_scratch:GPR 0 "=d,d,d,d"))]
6135 "s390_match_ccmode (insn, CCL3mode)"
6136 "@
6137 sl<g>r\t%0,%2
6138 sl<g>rk\t%0,%1,%2
6139 sl<g>\t%0,%2
6140 sl<y>\t%0,%2"
6141 [(set_attr "op_type" "RR<E>,RRF,RX<Y>,RXY")
6142 (set_attr "cpu_facility" "*,z196,*,longdisp")
6143 (set_attr "z10prop" "z10_super_c_E1,*,z10_super_E1,z10_super_E1")])
6144
6145
6146 ;
6147 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
6148 ;
6149
6150 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6151 (define_insn "sub<mode>3"
6152 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6153 (minus:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
6154 (match_operand:FP 2 "general_operand" "f,f,R,v")))
6155 (clobber (reg:CC CC_REGNUM))]
6156 "TARGET_HARD_FLOAT"
6157 "@
6158 s<xde>tr\t%0,%1,%2
6159 s<xde>br\t%0,%2
6160 s<xde>b\t%0,%2
6161 wfsdb\t%v0,%v1,%v2"
6162 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6163 (set_attr "type" "fsimp<mode>")
6164 (set_attr "cpu_facility" "*,*,*,vec")
6165 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6166
6167 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6168 (define_insn "*sub<mode>3_cc"
6169 [(set (reg CC_REGNUM)
6170 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6171 (match_operand:FP 2 "general_operand" "f,f,R"))
6172 (match_operand:FP 3 "const0_operand" "")))
6173 (set (match_operand:FP 0 "register_operand" "=f,f,f")
6174 (minus:FP (match_dup 1) (match_dup 2)))]
6175 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6176 "@
6177 s<xde>tr\t%0,%1,%2
6178 s<xde>br\t%0,%2
6179 s<xde>b\t%0,%2"
6180 [(set_attr "op_type" "RRF,RRE,RXE")
6181 (set_attr "type" "fsimp<mode>")
6182 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6183
6184 ; sxbr, sdbr, sebr, sdb, seb, sxtr, sdtr
6185 (define_insn "*sub<mode>3_cconly"
6186 [(set (reg CC_REGNUM)
6187 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "f,0,0")
6188 (match_operand:FP 2 "general_operand" "f,f,R"))
6189 (match_operand:FP 3 "const0_operand" "")))
6190 (clobber (match_scratch:FP 0 "=f,f,f"))]
6191 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6192 "@
6193 s<xde>tr\t%0,%1,%2
6194 s<xde>br\t%0,%2
6195 s<xde>b\t%0,%2"
6196 [(set_attr "op_type" "RRF,RRE,RXE")
6197 (set_attr "type" "fsimp<mode>")
6198 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>")])
6199
6200
6201 ;;
6202 ;;- Conditional add/subtract instructions.
6203 ;;
6204
6205 ;
6206 ; add(di|si)cc instruction pattern(s).
6207 ;
6208
6209 ; the following 4 patterns are used when the result of an add with
6210 ; carry is checked for an overflow condition
6211
6212 ; op1 + op2 + c < op1
6213
6214 ; alcr, alc, alcgr, alcg
6215 (define_insn "*add<mode>3_alc_carry1_cc"
6216 [(set (reg CC_REGNUM)
6217 (compare
6218 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6219 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6220 (match_operand:GPR 2 "general_operand" "d,T"))
6221 (match_dup 1)))
6222 (set (match_operand:GPR 0 "register_operand" "=d,d")
6223 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6224 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6225 "@
6226 alc<g>r\t%0,%2
6227 alc<g>\t%0,%2"
6228 [(set_attr "op_type" "RRE,RXY")
6229 (set_attr "z196prop" "z196_alone,z196_alone")])
6230
6231 ; alcr, alc, alcgr, alcg
6232 (define_insn "*add<mode>3_alc_carry1_cconly"
6233 [(set (reg CC_REGNUM)
6234 (compare
6235 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6236 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6237 (match_operand:GPR 2 "general_operand" "d,T"))
6238 (match_dup 1)))
6239 (clobber (match_scratch:GPR 0 "=d,d"))]
6240 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6241 "@
6242 alc<g>r\t%0,%2
6243 alc<g>\t%0,%2"
6244 [(set_attr "op_type" "RRE,RXY")
6245 (set_attr "z196prop" "z196_alone,z196_alone")])
6246
6247 ; op1 + op2 + c < op2
6248
6249 ; alcr, alc, alcgr, alcg
6250 (define_insn "*add<mode>3_alc_carry2_cc"
6251 [(set (reg CC_REGNUM)
6252 (compare
6253 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6254 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6255 (match_operand:GPR 2 "general_operand" "d,T"))
6256 (match_dup 2)))
6257 (set (match_operand:GPR 0 "register_operand" "=d,d")
6258 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6259 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6260 "@
6261 alc<g>r\t%0,%2
6262 alc<g>\t%0,%2"
6263 [(set_attr "op_type" "RRE,RXY")])
6264
6265 ; alcr, alc, alcgr, alcg
6266 (define_insn "*add<mode>3_alc_carry2_cconly"
6267 [(set (reg CC_REGNUM)
6268 (compare
6269 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6270 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6271 (match_operand:GPR 2 "general_operand" "d,T"))
6272 (match_dup 2)))
6273 (clobber (match_scratch:GPR 0 "=d,d"))]
6274 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
6275 "@
6276 alc<g>r\t%0,%2
6277 alc<g>\t%0,%2"
6278 [(set_attr "op_type" "RRE,RXY")])
6279
6280 ; alcr, alc, alcgr, alcg
6281 (define_insn "*add<mode>3_alc_cc"
6282 [(set (reg CC_REGNUM)
6283 (compare
6284 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6285 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6286 (match_operand:GPR 2 "general_operand" "d,T"))
6287 (const_int 0)))
6288 (set (match_operand:GPR 0 "register_operand" "=d,d")
6289 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
6290 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6291 "@
6292 alc<g>r\t%0,%2
6293 alc<g>\t%0,%2"
6294 [(set_attr "op_type" "RRE,RXY")])
6295
6296 ; alcr, alc, alcgr, alcg
6297 (define_insn "*add<mode>3_alc"
6298 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6299 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
6300 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
6301 (match_operand:GPR 2 "general_operand" "d,T")))
6302 (clobber (reg:CC CC_REGNUM))]
6303 "TARGET_CPU_ZARCH"
6304 "@
6305 alc<g>r\t%0,%2
6306 alc<g>\t%0,%2"
6307 [(set_attr "op_type" "RRE,RXY")])
6308
6309 ; slbr, slb, slbgr, slbg
6310 (define_insn "*sub<mode>3_slb_cc"
6311 [(set (reg CC_REGNUM)
6312 (compare
6313 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6314 (match_operand:GPR 2 "general_operand" "d,T"))
6315 (match_operand:GPR 3 "s390_slb_comparison" ""))
6316 (const_int 0)))
6317 (set (match_operand:GPR 0 "register_operand" "=d,d")
6318 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
6319 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
6320 "@
6321 slb<g>r\t%0,%2
6322 slb<g>\t%0,%2"
6323 [(set_attr "op_type" "RRE,RXY")
6324 (set_attr "z10prop" "z10_c,*")])
6325
6326 ; slbr, slb, slbgr, slbg
6327 (define_insn "*sub<mode>3_slb"
6328 [(set (match_operand:GPR 0 "register_operand" "=d,d")
6329 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
6330 (match_operand:GPR 2 "general_operand" "d,T"))
6331 (match_operand:GPR 3 "s390_slb_comparison" "")))
6332 (clobber (reg:CC CC_REGNUM))]
6333 "TARGET_CPU_ZARCH"
6334 "@
6335 slb<g>r\t%0,%2
6336 slb<g>\t%0,%2"
6337 [(set_attr "op_type" "RRE,RXY")
6338 (set_attr "z10prop" "z10_c,*")])
6339
6340 (define_expand "add<mode>cc"
6341 [(match_operand:GPR 0 "register_operand" "")
6342 (match_operand 1 "comparison_operator" "")
6343 (match_operand:GPR 2 "register_operand" "")
6344 (match_operand:GPR 3 "const_int_operand" "")]
6345 "TARGET_CPU_ZARCH"
6346 "if (!s390_expand_addcc (GET_CODE (operands[1]),
6347 XEXP (operands[1], 0), XEXP (operands[1], 1),
6348 operands[0], operands[2],
6349 operands[3])) FAIL; DONE;")
6350
6351 ;
6352 ; scond instruction pattern(s).
6353 ;
6354
6355 (define_insn_and_split "*scond<mode>"
6356 [(set (match_operand:GPR 0 "register_operand" "=&d")
6357 (match_operand:GPR 1 "s390_alc_comparison" ""))
6358 (clobber (reg:CC CC_REGNUM))]
6359 "TARGET_CPU_ZARCH"
6360 "#"
6361 "&& reload_completed"
6362 [(set (match_dup 0) (const_int 0))
6363 (parallel
6364 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
6365 (match_dup 0)))
6366 (clobber (reg:CC CC_REGNUM))])]
6367 "")
6368
6369 (define_insn_and_split "*scond<mode>_neg"
6370 [(set (match_operand:GPR 0 "register_operand" "=&d")
6371 (match_operand:GPR 1 "s390_slb_comparison" ""))
6372 (clobber (reg:CC CC_REGNUM))]
6373 "TARGET_CPU_ZARCH"
6374 "#"
6375 "&& reload_completed"
6376 [(set (match_dup 0) (const_int 0))
6377 (parallel
6378 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
6379 (match_dup 1)))
6380 (clobber (reg:CC CC_REGNUM))])
6381 (parallel
6382 [(set (match_dup 0) (neg:GPR (match_dup 0)))
6383 (clobber (reg:CC CC_REGNUM))])]
6384 "")
6385
6386
6387 (define_expand "cstore<mode>4"
6388 [(set (match_operand:SI 0 "register_operand" "")
6389 (match_operator:SI 1 "s390_scond_operator"
6390 [(match_operand:GPR 2 "register_operand" "")
6391 (match_operand:GPR 3 "general_operand" "")]))]
6392 "TARGET_CPU_ZARCH"
6393 "if (!s390_expand_addcc (GET_CODE (operands[1]), operands[2], operands[3],
6394 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
6395
6396 (define_expand "cstorecc4"
6397 [(parallel
6398 [(set (match_operand:SI 0 "register_operand" "")
6399 (match_operator:SI 1 "s390_eqne_operator"
6400 [(match_operand:CCZ1 2 "register_operand")
6401 (match_operand 3 "const0_operand")]))
6402 (clobber (reg:CC CC_REGNUM))])]
6403 ""
6404 "emit_insn (gen_sne (operands[0], operands[2]));
6405 if (GET_CODE (operands[1]) == EQ)
6406 emit_insn (gen_xorsi3 (operands[0], operands[0], const1_rtx));
6407 DONE;")
6408
6409 (define_insn_and_split "sne"
6410 [(set (match_operand:SI 0 "register_operand" "=d")
6411 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
6412 (const_int 0)))
6413 (clobber (reg:CC CC_REGNUM))]
6414 ""
6415 "#"
6416 "reload_completed"
6417 [(parallel
6418 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
6419 (clobber (reg:CC CC_REGNUM))])])
6420
6421
6422 ;;
6423 ;; - Conditional move instructions (introduced with z196)
6424 ;;
6425
6426 (define_expand "mov<mode>cc"
6427 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
6428 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
6429 (match_operand:GPR 2 "nonimmediate_operand" "")
6430 (match_operand:GPR 3 "nonimmediate_operand" "")))]
6431 "TARGET_Z196"
6432 {
6433 /* Emit the comparison insn in case we do not already have a comparison result. */
6434 if (!s390_comparison (operands[1], VOIDmode))
6435 operands[1] = s390_emit_compare (GET_CODE (operands[1]),
6436 XEXP (operands[1], 0),
6437 XEXP (operands[1], 1));
6438 })
6439
6440 ; locr, loc, stoc, locgr, locg, stocg, lochi, locghi
6441 (define_insn_and_split "*mov<mode>cc"
6442 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,d,S,S,&d")
6443 (if_then_else:GPR
6444 (match_operator 1 "s390_comparison"
6445 [(match_operand 2 "cc_reg_operand" " c,c,c,c,c,c,c,c,c")
6446 (match_operand 5 "const_int_operand" "")])
6447 (match_operand:GPR 3 "loc_operand" " d,0,S,0,K,0,d,0,S")
6448 (match_operand:GPR 4 "loc_operand" " 0,d,0,S,0,K,0,d,S")))]
6449 "TARGET_Z196"
6450 "@
6451 loc<g>r%C1\t%0,%3
6452 loc<g>r%D1\t%0,%4
6453 loc<g>%C1\t%0,%3
6454 loc<g>%D1\t%0,%4
6455 loc<g>hi%C1\t%0,%h3
6456 loc<g>hi%D1\t%0,%h4
6457 stoc<g>%C1\t%3,%0
6458 stoc<g>%D1\t%4,%0
6459 #"
6460 "&& reload_completed
6461 && MEM_P (operands[3]) && MEM_P (operands[4])"
6462 [(set (match_dup 0)
6463 (if_then_else:GPR
6464 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6465 (match_dup 3)
6466 (match_dup 0)))
6467 (set (match_dup 0)
6468 (if_then_else:GPR
6469 (match_op_dup 1 [(match_dup 2) (const_int 0)])
6470 (match_dup 0)
6471 (match_dup 4)))]
6472 ""
6473 [(set_attr "op_type" "RRF,RRF,RSY,RSY,RIE,RIE,RSY,RSY,*")
6474 (set_attr "cpu_facility" "*,*,*,*,z13,z13,*,*,*")])
6475
6476 ;;
6477 ;;- Multiply instructions.
6478 ;;
6479
6480 ;
6481 ; muldi3 instruction pattern(s).
6482 ;
6483
6484 (define_insn "*muldi3_sign"
6485 [(set (match_operand:DI 0 "register_operand" "=d,d")
6486 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,T"))
6487 (match_operand:DI 1 "register_operand" "0,0")))]
6488 "TARGET_ZARCH"
6489 "@
6490 msgfr\t%0,%2
6491 msgf\t%0,%2"
6492 [(set_attr "op_type" "RRE,RXY")
6493 (set_attr "type" "imuldi")])
6494
6495 (define_insn "muldi3"
6496 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
6497 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
6498 (match_operand:DI 2 "general_operand" "d,K,T,Os")))]
6499 "TARGET_ZARCH"
6500 "@
6501 msgr\t%0,%2
6502 mghi\t%0,%h2
6503 msg\t%0,%2
6504 msgfi\t%0,%2"
6505 [(set_attr "op_type" "RRE,RI,RXY,RIL")
6506 (set_attr "type" "imuldi")
6507 (set_attr "cpu_facility" "*,*,*,z10")])
6508
6509 ;
6510 ; mulsi3 instruction pattern(s).
6511 ;
6512
6513 (define_insn "*mulsi3_sign"
6514 [(set (match_operand:SI 0 "register_operand" "=d,d")
6515 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
6516 (match_operand:SI 1 "register_operand" "0,0")))]
6517 ""
6518 "@
6519 mh\t%0,%2
6520 mhy\t%0,%2"
6521 [(set_attr "op_type" "RX,RXY")
6522 (set_attr "type" "imulhi")
6523 (set_attr "cpu_facility" "*,z10")])
6524
6525 (define_insn "mulsi3"
6526 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
6527 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
6528 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
6529 ""
6530 "@
6531 msr\t%0,%2
6532 mhi\t%0,%h2
6533 ms\t%0,%2
6534 msy\t%0,%2
6535 msfi\t%0,%2"
6536 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
6537 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
6538 (set_attr "cpu_facility" "*,*,*,longdisp,z10")])
6539
6540 ;
6541 ; mulsidi3 instruction pattern(s).
6542 ;
6543
6544 (define_insn "mulsidi3"
6545 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
6546 (mult:DI (sign_extend:DI
6547 (match_operand:SI 1 "register_operand" "%0,0,0"))
6548 (sign_extend:DI
6549 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
6550 "!TARGET_ZARCH"
6551 "@
6552 mr\t%0,%2
6553 m\t%0,%2
6554 mfy\t%0,%2"
6555 [(set_attr "op_type" "RR,RX,RXY")
6556 (set_attr "type" "imulsi")
6557 (set_attr "cpu_facility" "*,*,z10")])
6558
6559 ;
6560 ; umul instruction pattern(s).
6561 ;
6562
6563 ; mlr, ml, mlgr, mlg
6564 (define_insn "umul<dwh><mode>3"
6565 [(set (match_operand:DW 0 "register_operand" "=d,d")
6566 (mult:DW (zero_extend:DW
6567 (match_operand:<DWH> 1 "register_operand" "%0,0"))
6568 (zero_extend:DW
6569 (match_operand:<DWH> 2 "nonimmediate_operand" " d,T"))))]
6570 "TARGET_CPU_ZARCH"
6571 "@
6572 ml<tg>r\t%0,%2
6573 ml<tg>\t%0,%2"
6574 [(set_attr "op_type" "RRE,RXY")
6575 (set_attr "type" "imul<dwh>")])
6576
6577 ;
6578 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
6579 ;
6580
6581 ; mxbr, mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
6582 (define_insn "mul<mode>3"
6583 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
6584 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%f,0,0,v")
6585 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
6586 "TARGET_HARD_FLOAT"
6587 "@
6588 m<xdee>tr\t%0,%1,%2
6589 m<xdee>br\t%0,%2
6590 m<xdee>b\t%0,%2
6591 wfmdb\t%v0,%v1,%v2"
6592 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
6593 (set_attr "type" "fmul<mode>")
6594 (set_attr "cpu_facility" "*,*,*,vec")
6595 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
6596
6597 ; madbr, maebr, maxb, madb, maeb
6598 (define_insn "fma<mode>4"
6599 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6600 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6601 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6602 (match_operand:DSF 3 "register_operand" "0,0,v")))]
6603 "TARGET_HARD_FLOAT"
6604 "@
6605 ma<xde>br\t%0,%1,%2
6606 ma<xde>b\t%0,%1,%2
6607 wfmadb\t%v0,%v1,%v2,%v3"
6608 [(set_attr "op_type" "RRE,RXE,VRR")
6609 (set_attr "type" "fmadd<mode>")
6610 (set_attr "cpu_facility" "*,*,vec")
6611 (set_attr "enabled" "*,*,<DFDI>")])
6612
6613 ; msxbr, msdbr, msebr, msxb, msdb, mseb
6614 (define_insn "fms<mode>4"
6615 [(set (match_operand:DSF 0 "register_operand" "=f,f,v")
6616 (fma:DSF (match_operand:DSF 1 "nonimmediate_operand" "%f,f,v")
6617 (match_operand:DSF 2 "nonimmediate_operand" "f,R,v")
6618 (neg:DSF (match_operand:DSF 3 "register_operand" "0,0,v"))))]
6619 "TARGET_HARD_FLOAT"
6620 "@
6621 ms<xde>br\t%0,%1,%2
6622 ms<xde>b\t%0,%1,%2
6623 wfmsdb\t%v0,%v1,%v2,%v3"
6624 [(set_attr "op_type" "RRE,RXE,VRR")
6625 (set_attr "type" "fmadd<mode>")
6626 (set_attr "cpu_facility" "*,*,vec")
6627 (set_attr "enabled" "*,*,<DFDI>")])
6628
6629 ;;
6630 ;;- Divide and modulo instructions.
6631 ;;
6632
6633 ;
6634 ; divmoddi4 instruction pattern(s).
6635 ;
6636
6637 (define_expand "divmoddi4"
6638 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6639 (div:DI (match_operand:DI 1 "register_operand" "")
6640 (match_operand:DI 2 "general_operand" "")))
6641 (set (match_operand:DI 3 "general_operand" "")
6642 (mod:DI (match_dup 1) (match_dup 2)))])
6643 (clobber (match_dup 4))]
6644 "TARGET_ZARCH"
6645 {
6646 rtx insn, div_equal, mod_equal;
6647
6648 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
6649 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
6650
6651 operands[4] = gen_reg_rtx(TImode);
6652 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
6653
6654 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6655 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6656
6657 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6658 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6659
6660 DONE;
6661 })
6662
6663 (define_insn "divmodtidi3"
6664 [(set (match_operand:TI 0 "register_operand" "=d,d")
6665 (ior:TI
6666 (ashift:TI
6667 (zero_extend:TI
6668 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6669 (match_operand:DI 2 "general_operand" "d,T")))
6670 (const_int 64))
6671 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
6672 "TARGET_ZARCH"
6673 "@
6674 dsgr\t%0,%2
6675 dsg\t%0,%2"
6676 [(set_attr "op_type" "RRE,RXY")
6677 (set_attr "type" "idiv")])
6678
6679 (define_insn "divmodtisi3"
6680 [(set (match_operand:TI 0 "register_operand" "=d,d")
6681 (ior:TI
6682 (ashift:TI
6683 (zero_extend:TI
6684 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6685 (sign_extend:DI
6686 (match_operand:SI 2 "nonimmediate_operand" "d,T"))))
6687 (const_int 64))
6688 (zero_extend:TI
6689 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
6690 "TARGET_ZARCH"
6691 "@
6692 dsgfr\t%0,%2
6693 dsgf\t%0,%2"
6694 [(set_attr "op_type" "RRE,RXY")
6695 (set_attr "type" "idiv")])
6696
6697 ;
6698 ; udivmoddi4 instruction pattern(s).
6699 ;
6700
6701 (define_expand "udivmoddi4"
6702 [(parallel [(set (match_operand:DI 0 "general_operand" "")
6703 (udiv:DI (match_operand:DI 1 "general_operand" "")
6704 (match_operand:DI 2 "nonimmediate_operand" "")))
6705 (set (match_operand:DI 3 "general_operand" "")
6706 (umod:DI (match_dup 1) (match_dup 2)))])
6707 (clobber (match_dup 4))]
6708 "TARGET_ZARCH"
6709 {
6710 rtx insn, div_equal, mod_equal, equal;
6711
6712 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
6713 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
6714 equal = gen_rtx_IOR (TImode,
6715 gen_rtx_ASHIFT (TImode,
6716 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
6717 GEN_INT (64)),
6718 gen_rtx_ZERO_EXTEND (TImode, div_equal));
6719
6720 operands[4] = gen_reg_rtx(TImode);
6721 emit_clobber (operands[4]);
6722 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
6723 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
6724
6725 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
6726 set_unique_reg_note (insn, REG_EQUAL, equal);
6727
6728 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
6729 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6730
6731 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
6732 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6733
6734 DONE;
6735 })
6736
6737 (define_insn "udivmodtidi3"
6738 [(set (match_operand:TI 0 "register_operand" "=d,d")
6739 (ior:TI
6740 (ashift:TI
6741 (zero_extend:TI
6742 (truncate:DI
6743 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
6744 (zero_extend:TI
6745 (match_operand:DI 2 "nonimmediate_operand" "d,T")))))
6746 (const_int 64))
6747 (zero_extend:TI
6748 (truncate:DI
6749 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
6750 "TARGET_ZARCH"
6751 "@
6752 dlgr\t%0,%2
6753 dlg\t%0,%2"
6754 [(set_attr "op_type" "RRE,RXY")
6755 (set_attr "type" "idiv")])
6756
6757 ;
6758 ; divmodsi4 instruction pattern(s).
6759 ;
6760
6761 (define_expand "divmodsi4"
6762 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6763 (div:SI (match_operand:SI 1 "general_operand" "")
6764 (match_operand:SI 2 "nonimmediate_operand" "")))
6765 (set (match_operand:SI 3 "general_operand" "")
6766 (mod:SI (match_dup 1) (match_dup 2)))])
6767 (clobber (match_dup 4))]
6768 "!TARGET_ZARCH"
6769 {
6770 rtx insn, div_equal, mod_equal, equal;
6771
6772 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
6773 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
6774 equal = gen_rtx_IOR (DImode,
6775 gen_rtx_ASHIFT (DImode,
6776 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6777 GEN_INT (32)),
6778 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6779
6780 operands[4] = gen_reg_rtx(DImode);
6781 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
6782
6783 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
6784 set_unique_reg_note (insn, REG_EQUAL, equal);
6785
6786 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6787 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6788
6789 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6790 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6791
6792 DONE;
6793 })
6794
6795 (define_insn "divmoddisi3"
6796 [(set (match_operand:DI 0 "register_operand" "=d,d")
6797 (ior:DI
6798 (ashift:DI
6799 (zero_extend:DI
6800 (truncate:SI
6801 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
6802 (sign_extend:DI
6803 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
6804 (const_int 32))
6805 (zero_extend:DI
6806 (truncate:SI
6807 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
6808 "!TARGET_ZARCH"
6809 "@
6810 dr\t%0,%2
6811 d\t%0,%2"
6812 [(set_attr "op_type" "RR,RX")
6813 (set_attr "type" "idiv")])
6814
6815 ;
6816 ; udivsi3 and umodsi3 instruction pattern(s).
6817 ;
6818
6819 (define_expand "udivmodsi4"
6820 [(parallel [(set (match_operand:SI 0 "general_operand" "")
6821 (udiv:SI (match_operand:SI 1 "general_operand" "")
6822 (match_operand:SI 2 "nonimmediate_operand" "")))
6823 (set (match_operand:SI 3 "general_operand" "")
6824 (umod:SI (match_dup 1) (match_dup 2)))])
6825 (clobber (match_dup 4))]
6826 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6827 {
6828 rtx insn, div_equal, mod_equal, equal;
6829
6830 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6831 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6832 equal = gen_rtx_IOR (DImode,
6833 gen_rtx_ASHIFT (DImode,
6834 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
6835 GEN_INT (32)),
6836 gen_rtx_ZERO_EXTEND (DImode, div_equal));
6837
6838 operands[4] = gen_reg_rtx(DImode);
6839 emit_clobber (operands[4]);
6840 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
6841 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
6842
6843 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
6844 set_unique_reg_note (insn, REG_EQUAL, equal);
6845
6846 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
6847 set_unique_reg_note (insn, REG_EQUAL, div_equal);
6848
6849 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
6850 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
6851
6852 DONE;
6853 })
6854
6855 (define_insn "udivmoddisi3"
6856 [(set (match_operand:DI 0 "register_operand" "=d,d")
6857 (ior:DI
6858 (ashift:DI
6859 (zero_extend:DI
6860 (truncate:SI
6861 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
6862 (zero_extend:DI
6863 (match_operand:SI 2 "nonimmediate_operand" "d,T")))))
6864 (const_int 32))
6865 (zero_extend:DI
6866 (truncate:SI
6867 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
6868 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
6869 "@
6870 dlr\t%0,%2
6871 dl\t%0,%2"
6872 [(set_attr "op_type" "RRE,RXY")
6873 (set_attr "type" "idiv")])
6874
6875 (define_expand "udivsi3"
6876 [(set (match_operand:SI 0 "register_operand" "=d")
6877 (udiv:SI (match_operand:SI 1 "general_operand" "")
6878 (match_operand:SI 2 "general_operand" "")))
6879 (clobber (match_dup 3))]
6880 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6881 {
6882 rtx insn, udiv_equal, umod_equal, equal;
6883
6884 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6885 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6886 equal = gen_rtx_IOR (DImode,
6887 gen_rtx_ASHIFT (DImode,
6888 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6889 GEN_INT (32)),
6890 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6891
6892 operands[3] = gen_reg_rtx (DImode);
6893
6894 if (CONSTANT_P (operands[2]))
6895 {
6896 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
6897 {
6898 rtx_code_label *label1 = gen_label_rtx ();
6899
6900 operands[1] = make_safe_from (operands[1], operands[0]);
6901 emit_move_insn (operands[0], const0_rtx);
6902 emit_cmp_and_jump_insns (operands[1], operands[2], LT, NULL_RTX,
6903 SImode, 1, label1);
6904 emit_move_insn (operands[0], const1_rtx);
6905 emit_label (label1);
6906 }
6907 else
6908 {
6909 operands[2] = force_reg (SImode, operands[2]);
6910 operands[2] = make_safe_from (operands[2], operands[0]);
6911
6912 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6913 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6914 operands[2]));
6915 set_unique_reg_note (insn, REG_EQUAL, equal);
6916
6917 insn = emit_move_insn (operands[0],
6918 gen_lowpart (SImode, operands[3]));
6919 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6920 }
6921 }
6922 else
6923 {
6924 rtx_code_label *label1 = gen_label_rtx ();
6925 rtx_code_label *label2 = gen_label_rtx ();
6926 rtx_code_label *label3 = gen_label_rtx ();
6927
6928 operands[1] = force_reg (SImode, operands[1]);
6929 operands[1] = make_safe_from (operands[1], operands[0]);
6930 operands[2] = force_reg (SImode, operands[2]);
6931 operands[2] = make_safe_from (operands[2], operands[0]);
6932
6933 emit_move_insn (operands[0], const0_rtx);
6934 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
6935 SImode, 1, label3);
6936 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
6937 SImode, 0, label2);
6938 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
6939 SImode, 0, label1);
6940 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
6941 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
6942 operands[2]));
6943 set_unique_reg_note (insn, REG_EQUAL, equal);
6944
6945 insn = emit_move_insn (operands[0],
6946 gen_lowpart (SImode, operands[3]));
6947 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
6948
6949 emit_jump (label3);
6950 emit_label (label1);
6951 emit_move_insn (operands[0], operands[1]);
6952 emit_jump (label3);
6953 emit_label (label2);
6954 emit_move_insn (operands[0], const1_rtx);
6955 emit_label (label3);
6956 }
6957 emit_move_insn (operands[0], operands[0]);
6958 DONE;
6959 })
6960
6961 (define_expand "umodsi3"
6962 [(set (match_operand:SI 0 "register_operand" "=d")
6963 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
6964 (match_operand:SI 2 "nonimmediate_operand" "")))
6965 (clobber (match_dup 3))]
6966 "!TARGET_ZARCH && !TARGET_CPU_ZARCH"
6967 {
6968 rtx insn, udiv_equal, umod_equal, equal;
6969
6970 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
6971 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
6972 equal = gen_rtx_IOR (DImode,
6973 gen_rtx_ASHIFT (DImode,
6974 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
6975 GEN_INT (32)),
6976 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
6977
6978 operands[3] = gen_reg_rtx (DImode);
6979
6980 if (CONSTANT_P (operands[2]))
6981 {
6982 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
6983 {
6984 rtx_code_label *label1 = gen_label_rtx ();
6985
6986 operands[1] = make_safe_from (operands[1], operands[0]);
6987 emit_move_insn (operands[0], operands[1]);
6988 emit_cmp_and_jump_insns (operands[0], operands[2], LT, NULL_RTX,
6989 SImode, 1, label1);
6990 emit_insn (gen_abssi2 (operands[0], operands[2]));
6991 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
6992 emit_label (label1);
6993 }
6994 else
6995 {
6996 operands[2] = force_reg (SImode, operands[2]);
6997 operands[2] = make_safe_from (operands[2], operands[0]);
6998
6999 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
7000 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
7001 operands[2]));
7002 set_unique_reg_note (insn, REG_EQUAL, equal);
7003
7004 insn = emit_move_insn (operands[0],
7005 gen_highpart (SImode, operands[3]));
7006 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
7007 }
7008 }
7009 else
7010 {
7011 rtx_code_label *label1 = gen_label_rtx ();
7012 rtx_code_label *label2 = gen_label_rtx ();
7013 rtx_code_label *label3 = gen_label_rtx ();
7014
7015 operands[1] = force_reg (SImode, operands[1]);
7016 operands[1] = make_safe_from (operands[1], operands[0]);
7017 operands[2] = force_reg (SImode, operands[2]);
7018 operands[2] = make_safe_from (operands[2], operands[0]);
7019
7020 emit_move_insn(operands[0], operands[1]);
7021 emit_cmp_and_jump_insns (operands[2], operands[1], GT, NULL_RTX,
7022 SImode, 1, label3);
7023 emit_cmp_and_jump_insns (operands[2], const0_rtx, LT, NULL_RTX,
7024 SImode, 0, label2);
7025 emit_cmp_and_jump_insns (operands[2], const1_rtx, EQ, NULL_RTX,
7026 SImode, 0, label1);
7027 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
7028 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
7029 operands[2]));
7030 set_unique_reg_note (insn, REG_EQUAL, equal);
7031
7032 insn = emit_move_insn (operands[0],
7033 gen_highpart (SImode, operands[3]));
7034 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
7035
7036 emit_jump (label3);
7037 emit_label (label1);
7038 emit_move_insn (operands[0], const0_rtx);
7039 emit_jump (label3);
7040 emit_label (label2);
7041 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
7042 emit_label (label3);
7043 }
7044 DONE;
7045 })
7046
7047 ;
7048 ; div(df|sf)3 instruction pattern(s).
7049 ;
7050
7051 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
7052 (define_insn "div<mode>3"
7053 [(set (match_operand:FP 0 "register_operand" "=f,f,f,v")
7054 (div:FP (match_operand:FP 1 "register_operand" "f,0,0,v")
7055 (match_operand:FP 2 "general_operand" "f,f,R,v")))]
7056 "TARGET_HARD_FLOAT"
7057 "@
7058 d<xde>tr\t%0,%1,%2
7059 d<xde>br\t%0,%2
7060 d<xde>b\t%0,%2
7061 wfddb\t%v0,%v1,%v2"
7062 [(set_attr "op_type" "RRF,RRE,RXE,VRR")
7063 (set_attr "type" "fdiv<mode>")
7064 (set_attr "cpu_facility" "*,*,*,vec")
7065 (set_attr "enabled" "<nBFP>,<nDFP>,<DSF>,<DFDI>")])
7066
7067
7068 ;;
7069 ;;- And instructions.
7070 ;;
7071
7072 (define_expand "and<mode>3"
7073 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7074 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
7075 (match_operand:INT 2 "general_operand" "")))
7076 (clobber (reg:CC CC_REGNUM))]
7077 ""
7078 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
7079
7080 ;
7081 ; anddi3 instruction pattern(s).
7082 ;
7083
7084 (define_insn "*anddi3_cc"
7085 [(set (reg CC_REGNUM)
7086 (compare
7087 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
7088 (match_operand:DI 2 "general_operand" " d,d,T,NxxDw"))
7089 (const_int 0)))
7090 (set (match_operand:DI 0 "register_operand" "=d,d,d, d")
7091 (and:DI (match_dup 1) (match_dup 2)))]
7092 "TARGET_ZARCH && s390_match_ccmode(insn, CCTmode)"
7093 "@
7094 ngr\t%0,%2
7095 ngrk\t%0,%1,%2
7096 ng\t%0,%2
7097 risbg\t%0,%1,%s2,128+%e2,0"
7098 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
7099 (set_attr "cpu_facility" "*,z196,*,z10")
7100 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
7101
7102 (define_insn "*anddi3_cconly"
7103 [(set (reg CC_REGNUM)
7104 (compare
7105 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0, d")
7106 (match_operand:DI 2 "general_operand" " d,d,T,NxxDw"))
7107 (const_int 0)))
7108 (clobber (match_scratch:DI 0 "=d,d,d, d"))]
7109 "TARGET_ZARCH
7110 && s390_match_ccmode(insn, CCTmode)
7111 /* Do not steal TM patterns. */
7112 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
7113 "@
7114 ngr\t%0,%2
7115 ngrk\t%0,%1,%2
7116 ng\t%0,%2
7117 risbg\t%0,%1,%s2,128+%e2,0"
7118 [(set_attr "op_type" "RRE,RRF,RXY,RIE")
7119 (set_attr "cpu_facility" "*,z196,*,z10")
7120 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super_E1")])
7121
7122 (define_insn "*anddi3"
7123 [(set (match_operand:DI 0 "nonimmediate_operand"
7124 "=d,d, d, d, d, d, d, d,d,d,d, d, AQ,Q")
7125 (and:DI
7126 (match_operand:DI 1 "nonimmediate_operand"
7127 "%d,o, 0, 0, 0, 0, 0, 0,0,d,0, d, 0,0")
7128 (match_operand:DI 2 "general_operand"
7129 "M, M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,d,T,NxxDw,NxQDF,Q")))
7130 (clobber (reg:CC CC_REGNUM))]
7131 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7132 "@
7133 #
7134 #
7135 nihh\t%0,%j2
7136 nihl\t%0,%j2
7137 nilh\t%0,%j2
7138 nill\t%0,%j2
7139 nihf\t%0,%m2
7140 nilf\t%0,%m2
7141 ngr\t%0,%2
7142 ngrk\t%0,%1,%2
7143 ng\t%0,%2
7144 risbg\t%0,%1,%s2,128+%e2,0
7145 #
7146 #"
7147 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,RIE,SI,SS")
7148 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,z196,*,z10,*,*")
7149 (set_attr "z10prop" "*,
7150 *,
7151 z10_super_E1,
7152 z10_super_E1,
7153 z10_super_E1,
7154 z10_super_E1,
7155 z10_super_E1,
7156 z10_super_E1,
7157 z10_super_E1,
7158 *,
7159 z10_super_E1,
7160 z10_super_E1,
7161 *,
7162 *")])
7163
7164 (define_split
7165 [(set (match_operand:DI 0 "s_operand" "")
7166 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7167 (clobber (reg:CC CC_REGNUM))]
7168 "reload_completed"
7169 [(parallel
7170 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7171 (clobber (reg:CC CC_REGNUM))])]
7172 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7173
7174 ;; These two are what combine generates for (ashift (zero_extract)).
7175 (define_insn "*extzv_<mode>_srl<clobbercc_or_nocc>"
7176 [(set (match_operand:GPR 0 "register_operand" "=d")
7177 (and:GPR (lshiftrt:GPR
7178 (match_operand:GPR 1 "register_operand" "d")
7179 (match_operand:GPR 2 "nonzero_shift_count_operand" ""))
7180 (match_operand:GPR 3 "contiguous_bitmask_operand" "")))]
7181 "<z10_or_zEC12_cond>
7182 /* Note that even for the SImode pattern, the rotate is always DImode. */
7183 && s390_extzv_shift_ok (<bitsize>, -INTVAL (operands[2]),
7184 INTVAL (operands[3]))"
7185 "<risbg_n>\t%0,%1,%<bfstart>3,128+%<bfend>3,64-%2"
7186 [(set_attr "op_type" "RIE")
7187 (set_attr "z10prop" "z10_super_E1")])
7188
7189 (define_insn "*extzv_<mode>_sll<clobbercc_or_nocc>"
7190 [(set (match_operand:GPR 0 "register_operand" "=d")
7191 (and:GPR (ashift: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 && s390_extzv_shift_ok (<bitsize>, INTVAL (operands[2]),
7197 INTVAL (operands[3]))"
7198 "<risbg_n>\t%0,%1,%<bfstart>3,128+%<bfend>3,%2"
7199 [(set_attr "op_type" "RIE")
7200 (set_attr "z10prop" "z10_super_E1")])
7201
7202
7203 ;
7204 ; andsi3 instruction pattern(s).
7205 ;
7206
7207 (define_insn "*andsi3_cc"
7208 [(set (reg CC_REGNUM)
7209 (compare
7210 (and:SI
7211 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7212 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7213 (const_int 0)))
7214 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d, d")
7215 (and:SI (match_dup 1) (match_dup 2)))]
7216 "s390_match_ccmode(insn, CCTmode)"
7217 "@
7218 nilf\t%0,%o2
7219 nr\t%0,%2
7220 nrk\t%0,%1,%2
7221 n\t%0,%2
7222 ny\t%0,%2
7223 risbg\t%0,%1,%t2,128+%f2,0"
7224 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7225 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7226 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7227 z10_super_E1,z10_super_E1,z10_super_E1")])
7228
7229 (define_insn "*andsi3_cconly"
7230 [(set (reg CC_REGNUM)
7231 (compare
7232 (and:SI
7233 (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, d")
7234 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxxSq"))
7235 (const_int 0)))
7236 (clobber (match_scratch:SI 0 "=d,d,d,d,d, d"))]
7237 "s390_match_ccmode(insn, CCTmode)
7238 /* Do not steal TM patterns. */
7239 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
7240 "@
7241 nilf\t%0,%o2
7242 nr\t%0,%2
7243 nrk\t%0,%1,%2
7244 n\t%0,%2
7245 ny\t%0,%2
7246 risbg\t%0,%1,%t2,128+%f2,0"
7247 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,RIE")
7248 (set_attr "cpu_facility" "*,*,z196,*,longdisp,z10")
7249 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7250 z10_super_E1,z10_super_E1,z10_super_E1")])
7251
7252 (define_insn "*andsi3_zarch"
7253 [(set (match_operand:SI 0 "nonimmediate_operand"
7254 "=d,d, d, d, d,d,d,d,d, d, AQ,Q")
7255 (and:SI (match_operand:SI 1 "nonimmediate_operand"
7256 "%d,o, 0, 0, 0,0,d,0,0, d, 0,0")
7257 (match_operand:SI 2 "general_operand"
7258 " M,M,N0HSF,N1HSF,Os,d,d,R,T,NxxSw,NxQSF,Q")))
7259 (clobber (reg:CC CC_REGNUM))]
7260 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7261 "@
7262 #
7263 #
7264 nilh\t%0,%j2
7265 nill\t%0,%j2
7266 nilf\t%0,%o2
7267 nr\t%0,%2
7268 nrk\t%0,%1,%2
7269 n\t%0,%2
7270 ny\t%0,%2
7271 risbg\t%0,%1,%t2,128+%f2,0
7272 #
7273 #"
7274 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RRF,RX,RXY,RIE,SI,SS")
7275 (set_attr "cpu_facility" "*,*,*,*,*,*,z196,*,longdisp,z10,*,*")
7276 (set_attr "z10prop" "*,
7277 *,
7278 z10_super_E1,
7279 z10_super_E1,
7280 z10_super_E1,
7281 z10_super_E1,
7282 *,
7283 z10_super_E1,
7284 z10_super_E1,
7285 z10_super_E1,
7286 *,
7287 *")])
7288
7289 (define_insn "*andsi3_esa"
7290 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d, AQ,Q")
7291 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0, 0,0")
7292 (match_operand:SI 2 "general_operand" " d,R,NxQSF,Q")))
7293 (clobber (reg:CC CC_REGNUM))]
7294 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7295 "@
7296 nr\t%0,%2
7297 n\t%0,%2
7298 #
7299 #"
7300 [(set_attr "op_type" "RR,RX,SI,SS")
7301 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7302
7303
7304 (define_split
7305 [(set (match_operand:SI 0 "s_operand" "")
7306 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7307 (clobber (reg:CC CC_REGNUM))]
7308 "reload_completed"
7309 [(parallel
7310 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7311 (clobber (reg:CC CC_REGNUM))])]
7312 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7313
7314 ;
7315 ; andhi3 instruction pattern(s).
7316 ;
7317
7318 (define_insn "*andhi3_zarch"
7319 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7320 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7321 (match_operand:HI 2 "general_operand" " d,d,n,NxQHF,Q")))
7322 (clobber (reg:CC CC_REGNUM))]
7323 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7324 "@
7325 nr\t%0,%2
7326 nrk\t%0,%1,%2
7327 nill\t%0,%x2
7328 #
7329 #"
7330 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7331 (set_attr "cpu_facility" "*,z196,*,*,*")
7332 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")
7333 ])
7334
7335 (define_insn "*andhi3_esa"
7336 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7337 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7338 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
7339 (clobber (reg:CC CC_REGNUM))]
7340 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7341 "@
7342 nr\t%0,%2
7343 #
7344 #"
7345 [(set_attr "op_type" "RR,SI,SS")
7346 (set_attr "z10prop" "z10_super_E1,*,*")
7347 ])
7348
7349 (define_split
7350 [(set (match_operand:HI 0 "s_operand" "")
7351 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7352 (clobber (reg:CC CC_REGNUM))]
7353 "reload_completed"
7354 [(parallel
7355 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
7356 (clobber (reg:CC CC_REGNUM))])]
7357 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
7358
7359 ;
7360 ; andqi3 instruction pattern(s).
7361 ;
7362
7363 (define_insn "*andqi3_zarch"
7364 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7365 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7366 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7367 (clobber (reg:CC CC_REGNUM))]
7368 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7369 "@
7370 nr\t%0,%2
7371 nrk\t%0,%1,%2
7372 nill\t%0,%b2
7373 ni\t%S0,%b2
7374 niy\t%S0,%b2
7375 #"
7376 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7377 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7378 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,z10_super,z10_super,*")])
7379
7380 (define_insn "*andqi3_esa"
7381 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7382 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7383 (match_operand:QI 2 "general_operand" "d,n,Q")))
7384 (clobber (reg:CC CC_REGNUM))]
7385 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7386 "@
7387 nr\t%0,%2
7388 ni\t%S0,%b2
7389 #"
7390 [(set_attr "op_type" "RR,SI,SS")
7391 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7392
7393 ;
7394 ; And with complement
7395 ;
7396 ; c = ~b & a = (b & a) ^ a
7397
7398 (define_insn_and_split "*andc_split_<mode>"
7399 [(set (match_operand:GPR 0 "nonimmediate_operand" "")
7400 (and:GPR (not:GPR (match_operand:GPR 1 "nonimmediate_operand" ""))
7401 (match_operand:GPR 2 "general_operand" "")))
7402 (clobber (reg:CC CC_REGNUM))]
7403 "! reload_completed && s390_logical_operator_ok_p (operands)"
7404 "#"
7405 "&& 1"
7406 [
7407 (parallel
7408 [(set (match_dup 3) (and:GPR (match_dup 1) (match_dup 2)))
7409 (clobber (reg:CC CC_REGNUM))])
7410 (parallel
7411 [(set (match_dup 0) (xor:GPR (match_dup 3) (match_dup 2)))
7412 (clobber (reg:CC CC_REGNUM))])]
7413 {
7414 if (reg_overlap_mentioned_p (operands[0], operands[2]))
7415 operands[3] = gen_reg_rtx (<MODE>mode);
7416 else
7417 operands[3] = operands[0];
7418 })
7419
7420 ;
7421 ; Block and (NC) patterns.
7422 ;
7423
7424 (define_insn "*nc"
7425 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7426 (and:BLK (match_dup 0)
7427 (match_operand:BLK 1 "memory_operand" "Q")))
7428 (use (match_operand 2 "const_int_operand" "n"))
7429 (clobber (reg:CC CC_REGNUM))]
7430 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7431 "nc\t%O0(%2,%R0),%S1"
7432 [(set_attr "op_type" "SS")
7433 (set_attr "z196prop" "z196_cracked")])
7434
7435 (define_split
7436 [(set (match_operand 0 "memory_operand" "")
7437 (and (match_dup 0)
7438 (match_operand 1 "memory_operand" "")))
7439 (clobber (reg:CC CC_REGNUM))]
7440 "reload_completed
7441 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7442 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7443 [(parallel
7444 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
7445 (use (match_dup 2))
7446 (clobber (reg:CC CC_REGNUM))])]
7447 {
7448 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7449 operands[0] = adjust_address (operands[0], BLKmode, 0);
7450 operands[1] = adjust_address (operands[1], BLKmode, 0);
7451 })
7452
7453 (define_peephole2
7454 [(parallel
7455 [(set (match_operand:BLK 0 "memory_operand" "")
7456 (and:BLK (match_dup 0)
7457 (match_operand:BLK 1 "memory_operand" "")))
7458 (use (match_operand 2 "const_int_operand" ""))
7459 (clobber (reg:CC CC_REGNUM))])
7460 (parallel
7461 [(set (match_operand:BLK 3 "memory_operand" "")
7462 (and:BLK (match_dup 3)
7463 (match_operand:BLK 4 "memory_operand" "")))
7464 (use (match_operand 5 "const_int_operand" ""))
7465 (clobber (reg:CC CC_REGNUM))])]
7466 "s390_offset_p (operands[0], operands[3], operands[2])
7467 && s390_offset_p (operands[1], operands[4], operands[2])
7468 && !s390_overlap_p (operands[0], operands[1],
7469 INTVAL (operands[2]) + INTVAL (operands[5]))
7470 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7471 [(parallel
7472 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
7473 (use (match_dup 8))
7474 (clobber (reg:CC CC_REGNUM))])]
7475 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7476 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7477 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7478
7479
7480 ;;
7481 ;;- Bit set (inclusive or) instructions.
7482 ;;
7483
7484 (define_expand "ior<mode>3"
7485 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7486 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
7487 (match_operand:INT 2 "general_operand" "")))
7488 (clobber (reg:CC CC_REGNUM))]
7489 ""
7490 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
7491
7492 ;
7493 ; iordi3 instruction pattern(s).
7494 ;
7495
7496 (define_insn "*iordi3_cc"
7497 [(set (reg CC_REGNUM)
7498 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7499 (match_operand:DI 2 "general_operand" " d,d,T"))
7500 (const_int 0)))
7501 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7502 (ior:DI (match_dup 1) (match_dup 2)))]
7503 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7504 "@
7505 ogr\t%0,%2
7506 ogrk\t%0,%1,%2
7507 og\t%0,%2"
7508 [(set_attr "op_type" "RRE,RRF,RXY")
7509 (set_attr "cpu_facility" "*,z196,*")
7510 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7511
7512 (define_insn "*iordi3_cconly"
7513 [(set (reg CC_REGNUM)
7514 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7515 (match_operand:DI 2 "general_operand" " d,d,T"))
7516 (const_int 0)))
7517 (clobber (match_scratch:DI 0 "=d,d,d"))]
7518 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7519 "@
7520 ogr\t%0,%2
7521 ogrk\t%0,%1,%2
7522 og\t%0,%2"
7523 [(set_attr "op_type" "RRE,RRF,RXY")
7524 (set_attr "cpu_facility" "*,z196,*")
7525 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7526
7527 (define_insn "*iordi3"
7528 [(set (match_operand:DI 0 "nonimmediate_operand"
7529 "=d, d, d, d, d, d,d,d,d, AQ,Q")
7530 (ior:DI (match_operand:DI 1 "nonimmediate_operand"
7531 " %0, 0, 0, 0, 0, 0,0,d,0, 0,0")
7532 (match_operand:DI 2 "general_operand"
7533 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7534 (clobber (reg:CC CC_REGNUM))]
7535 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7536 "@
7537 oihh\t%0,%i2
7538 oihl\t%0,%i2
7539 oilh\t%0,%i2
7540 oill\t%0,%i2
7541 oihf\t%0,%k2
7542 oilf\t%0,%k2
7543 ogr\t%0,%2
7544 ogrk\t%0,%1,%2
7545 og\t%0,%2
7546 #
7547 #"
7548 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RRF,RXY,SI,SS")
7549 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,z196,*,*,*")
7550 (set_attr "z10prop" "z10_super_E1,
7551 z10_super_E1,
7552 z10_super_E1,
7553 z10_super_E1,
7554 z10_super_E1,
7555 z10_super_E1,
7556 z10_super_E1,
7557 *,
7558 z10_super_E1,
7559 *,
7560 *")])
7561
7562 (define_split
7563 [(set (match_operand:DI 0 "s_operand" "")
7564 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7565 (clobber (reg:CC CC_REGNUM))]
7566 "reload_completed"
7567 [(parallel
7568 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7569 (clobber (reg:CC CC_REGNUM))])]
7570 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7571
7572 ;
7573 ; iorsi3 instruction pattern(s).
7574 ;
7575
7576 (define_insn "*iorsi3_cc"
7577 [(set (reg CC_REGNUM)
7578 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7579 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7580 (const_int 0)))
7581 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7582 (ior:SI (match_dup 1) (match_dup 2)))]
7583 "s390_match_ccmode(insn, CCTmode)"
7584 "@
7585 oilf\t%0,%o2
7586 or\t%0,%2
7587 ork\t%0,%1,%2
7588 o\t%0,%2
7589 oy\t%0,%2"
7590 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7591 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7592 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7593
7594 (define_insn "*iorsi3_cconly"
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 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
7600 "s390_match_ccmode(insn, CCTmode)"
7601 "@
7602 oilf\t%0,%o2
7603 or\t%0,%2
7604 ork\t%0,%1,%2
7605 o\t%0,%2
7606 oy\t%0,%2"
7607 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7608 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7609 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super_E1,z10_super_E1")])
7610
7611 (define_insn "*iorsi3_zarch"
7612 [(set (match_operand:SI 0 "nonimmediate_operand" "=d, d, d,d,d,d,d, AQ,Q")
7613 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0, 0, 0,0,d,0,0, 0,0")
7614 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,d,R,T,NxQS0,Q")))
7615 (clobber (reg:CC CC_REGNUM))]
7616 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7617 "@
7618 oilh\t%0,%i2
7619 oill\t%0,%i2
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 #
7626 #"
7627 [(set_attr "op_type" "RI,RI,RIL,RR,RRF,RX,RXY,SI,SS")
7628 (set_attr "cpu_facility" "*,*,*,*,z196,*,longdisp,*,*")
7629 (set_attr "z10prop" "z10_super_E1,
7630 z10_super_E1,
7631 z10_super_E1,
7632 z10_super_E1,
7633 *,
7634 z10_super_E1,
7635 z10_super_E1,
7636 *,
7637 *")])
7638
7639 (define_insn "*iorsi3_esa"
7640 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
7641 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
7642 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
7643 (clobber (reg:CC CC_REGNUM))]
7644 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7645 "@
7646 or\t%0,%2
7647 o\t%0,%2
7648 #
7649 #"
7650 [(set_attr "op_type" "RR,RX,SI,SS")
7651 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*")])
7652
7653 (define_split
7654 [(set (match_operand:SI 0 "s_operand" "")
7655 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7656 (clobber (reg:CC CC_REGNUM))]
7657 "reload_completed"
7658 [(parallel
7659 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7660 (clobber (reg:CC CC_REGNUM))])]
7661 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7662
7663 ;
7664 ; iorhi3 instruction pattern(s).
7665 ;
7666
7667 (define_insn "*iorhi3_zarch"
7668 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7669 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,d,0, 0,0")
7670 (match_operand:HI 2 "general_operand" " d,d,n,NxQH0,Q")))
7671 (clobber (reg:CC CC_REGNUM))]
7672 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7673 "@
7674 or\t%0,%2
7675 ork\t%0,%1,%2
7676 oill\t%0,%x2
7677 #
7678 #"
7679 [(set_attr "op_type" "RR,RRF,RI,SI,SS")
7680 (set_attr "cpu_facility" "*,z196,*,*,*")
7681 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,*,*")])
7682
7683 (define_insn "*iorhi3_esa"
7684 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
7685 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
7686 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
7687 (clobber (reg:CC CC_REGNUM))]
7688 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7689 "@
7690 or\t%0,%2
7691 #
7692 #"
7693 [(set_attr "op_type" "RR,SI,SS")
7694 (set_attr "z10prop" "z10_super_E1,*,*")])
7695
7696 (define_split
7697 [(set (match_operand:HI 0 "s_operand" "")
7698 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7699 (clobber (reg:CC CC_REGNUM))]
7700 "reload_completed"
7701 [(parallel
7702 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
7703 (clobber (reg:CC CC_REGNUM))])]
7704 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
7705
7706 ;
7707 ; iorqi3 instruction pattern(s).
7708 ;
7709
7710 (define_insn "*iorqi3_zarch"
7711 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7712 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,d,0,0,0,0")
7713 (match_operand:QI 2 "general_operand" " d,d,n,n,n,Q")))
7714 (clobber (reg:CC CC_REGNUM))]
7715 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7716 "@
7717 or\t%0,%2
7718 ork\t%0,%1,%2
7719 oill\t%0,%b2
7720 oi\t%S0,%b2
7721 oiy\t%S0,%b2
7722 #"
7723 [(set_attr "op_type" "RR,RRF,RI,SI,SIY,SS")
7724 (set_attr "cpu_facility" "*,z196,*,*,longdisp,*")
7725 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1,
7726 z10_super,z10_super,*")])
7727
7728 (define_insn "*iorqi3_esa"
7729 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
7730 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7731 (match_operand:QI 2 "general_operand" "d,n,Q")))
7732 (clobber (reg:CC CC_REGNUM))]
7733 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7734 "@
7735 or\t%0,%2
7736 oi\t%S0,%b2
7737 #"
7738 [(set_attr "op_type" "RR,SI,SS")
7739 (set_attr "z10prop" "z10_super_E1,z10_super,*")])
7740
7741 ;
7742 ; Block inclusive or (OC) patterns.
7743 ;
7744
7745 (define_insn "*oc"
7746 [(set (match_operand:BLK 0 "memory_operand" "=Q")
7747 (ior:BLK (match_dup 0)
7748 (match_operand:BLK 1 "memory_operand" "Q")))
7749 (use (match_operand 2 "const_int_operand" "n"))
7750 (clobber (reg:CC CC_REGNUM))]
7751 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
7752 "oc\t%O0(%2,%R0),%S1"
7753 [(set_attr "op_type" "SS")
7754 (set_attr "z196prop" "z196_cracked")])
7755
7756 (define_split
7757 [(set (match_operand 0 "memory_operand" "")
7758 (ior (match_dup 0)
7759 (match_operand 1 "memory_operand" "")))
7760 (clobber (reg:CC CC_REGNUM))]
7761 "reload_completed
7762 && GET_MODE (operands[0]) == GET_MODE (operands[1])
7763 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
7764 [(parallel
7765 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
7766 (use (match_dup 2))
7767 (clobber (reg:CC CC_REGNUM))])]
7768 {
7769 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
7770 operands[0] = adjust_address (operands[0], BLKmode, 0);
7771 operands[1] = adjust_address (operands[1], BLKmode, 0);
7772 })
7773
7774 (define_peephole2
7775 [(parallel
7776 [(set (match_operand:BLK 0 "memory_operand" "")
7777 (ior:BLK (match_dup 0)
7778 (match_operand:BLK 1 "memory_operand" "")))
7779 (use (match_operand 2 "const_int_operand" ""))
7780 (clobber (reg:CC CC_REGNUM))])
7781 (parallel
7782 [(set (match_operand:BLK 3 "memory_operand" "")
7783 (ior:BLK (match_dup 3)
7784 (match_operand:BLK 4 "memory_operand" "")))
7785 (use (match_operand 5 "const_int_operand" ""))
7786 (clobber (reg:CC CC_REGNUM))])]
7787 "s390_offset_p (operands[0], operands[3], operands[2])
7788 && s390_offset_p (operands[1], operands[4], operands[2])
7789 && !s390_overlap_p (operands[0], operands[1],
7790 INTVAL (operands[2]) + INTVAL (operands[5]))
7791 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
7792 [(parallel
7793 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
7794 (use (match_dup 8))
7795 (clobber (reg:CC CC_REGNUM))])]
7796 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
7797 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
7798 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
7799
7800
7801 ;;
7802 ;;- Xor instructions.
7803 ;;
7804
7805 (define_expand "xor<mode>3"
7806 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7807 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
7808 (match_operand:INT 2 "general_operand" "")))
7809 (clobber (reg:CC CC_REGNUM))]
7810 ""
7811 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
7812
7813 ; Combine replaces (xor (x) (const_int -1)) with (not (x)) when doing
7814 ; simplifications. So its better to have something matching.
7815 (define_split
7816 [(set (match_operand:INT 0 "nonimmediate_operand" "")
7817 (not:INT (match_operand:INT 1 "nonimmediate_operand" "")))]
7818 ""
7819 [(parallel
7820 [(set (match_dup 0) (xor:INT (match_dup 1) (match_dup 2)))
7821 (clobber (reg:CC CC_REGNUM))])]
7822 {
7823 operands[2] = constm1_rtx;
7824 if (!s390_logical_operator_ok_p (operands))
7825 FAIL;
7826 })
7827
7828 ;
7829 ; xordi3 instruction pattern(s).
7830 ;
7831
7832 (define_insn "*xordi3_cc"
7833 [(set (reg CC_REGNUM)
7834 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7835 (match_operand:DI 2 "general_operand" " d,d,T"))
7836 (const_int 0)))
7837 (set (match_operand:DI 0 "register_operand" "=d,d,d")
7838 (xor:DI (match_dup 1) (match_dup 2)))]
7839 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7840 "@
7841 xgr\t%0,%2
7842 xgrk\t%0,%1,%2
7843 xg\t%0,%2"
7844 [(set_attr "op_type" "RRE,RRF,RXY")
7845 (set_attr "cpu_facility" "*,z196,*")
7846 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7847
7848 (define_insn "*xordi3_cconly"
7849 [(set (reg CC_REGNUM)
7850 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,d,0")
7851 (match_operand:DI 2 "general_operand" " d,d,T"))
7852 (const_int 0)))
7853 (clobber (match_scratch:DI 0 "=d,d,d"))]
7854 "s390_match_ccmode(insn, CCTmode) && TARGET_ZARCH"
7855 "@
7856 xgr\t%0,%2
7857 xgrk\t%0,%1,%2
7858 xg\t%0,%2"
7859 [(set_attr "op_type" "RRE,RRF,RXY")
7860 (set_attr "cpu_facility" "*,z196,*")
7861 (set_attr "z10prop" "z10_super_E1,*,z10_super_E1")])
7862
7863 (define_insn "*xordi3"
7864 [(set (match_operand:DI 0 "nonimmediate_operand" "=d, d,d,d,d, AQ,Q")
7865 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0, 0,0,d,0, 0,0")
7866 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,d,T,NxQD0,Q")))
7867 (clobber (reg:CC CC_REGNUM))]
7868 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
7869 "@
7870 xihf\t%0,%k2
7871 xilf\t%0,%k2
7872 xgr\t%0,%2
7873 xgrk\t%0,%1,%2
7874 xg\t%0,%2
7875 #
7876 #"
7877 [(set_attr "op_type" "RIL,RIL,RRE,RRF,RXY,SI,SS")
7878 (set_attr "cpu_facility" "extimm,extimm,*,z196,*,*,*")
7879 (set_attr "z10prop" "z10_super_E1,z10_super_E1,z10_super_E1,
7880 *,z10_super_E1,*,*")])
7881
7882 (define_split
7883 [(set (match_operand:DI 0 "s_operand" "")
7884 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
7885 (clobber (reg:CC CC_REGNUM))]
7886 "reload_completed"
7887 [(parallel
7888 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7889 (clobber (reg:CC CC_REGNUM))])]
7890 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7891
7892 ;
7893 ; xorsi3 instruction pattern(s).
7894 ;
7895
7896 (define_insn "*xorsi3_cc"
7897 [(set (reg CC_REGNUM)
7898 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7899 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7900 (const_int 0)))
7901 (set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
7902 (xor:SI (match_dup 1) (match_dup 2)))]
7903 "s390_match_ccmode(insn, CCTmode)"
7904 "@
7905 xilf\t%0,%o2
7906 xr\t%0,%2
7907 xrk\t%0,%1,%2
7908 x\t%0,%2
7909 xy\t%0,%2"
7910 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY")
7911 (set_attr "cpu_facility" "*,*,z196,*,longdisp")
7912 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7913 z10_super_E1,z10_super_E1")])
7914
7915 (define_insn "*xorsi3_cconly"
7916 [(set (reg CC_REGNUM)
7917 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0")
7918 (match_operand:SI 2 "general_operand" "Os,d,d,R,T"))
7919 (const_int 0)))
7920 (clobber (match_scratch:SI 0 "=d,d,d,d,d"))]
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"
7934 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d, AQ,Q")
7935 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,d,0,0, 0,0")
7936 (match_operand:SI 2 "general_operand" "Os,d,d,R,T,NxQS0,Q")))
7937 (clobber (reg:CC CC_REGNUM))]
7938 "s390_logical_operator_ok_p (operands)"
7939 "@
7940 xilf\t%0,%o2
7941 xr\t%0,%2
7942 xrk\t%0,%1,%2
7943 x\t%0,%2
7944 xy\t%0,%2
7945 #
7946 #"
7947 [(set_attr "op_type" "RIL,RR,RRF,RX,RXY,SI,SS")
7948 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*,*")
7949 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,
7950 z10_super_E1,z10_super_E1,*,*")])
7951
7952 (define_split
7953 [(set (match_operand:SI 0 "s_operand" "")
7954 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
7955 (clobber (reg:CC CC_REGNUM))]
7956 "reload_completed"
7957 [(parallel
7958 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7959 (clobber (reg:CC CC_REGNUM))])]
7960 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7961
7962 ;
7963 ; xorhi3 instruction pattern(s).
7964 ;
7965
7966 (define_insn "*xorhi3"
7967 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d, AQ,Q")
7968 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,d, 0,0")
7969 (match_operand:HI 2 "general_operand" "Os,d,d,NxQH0,Q")))
7970 (clobber (reg:CC CC_REGNUM))]
7971 "s390_logical_operator_ok_p (operands)"
7972 "@
7973 xilf\t%0,%x2
7974 xr\t%0,%2
7975 xrk\t%0,%1,%2
7976 #
7977 #"
7978 [(set_attr "op_type" "RIL,RR,RRF,SI,SS")
7979 (set_attr "cpu_facility" "*,*,z196,*,*")
7980 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,*,*")])
7981
7982 (define_split
7983 [(set (match_operand:HI 0 "s_operand" "")
7984 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
7985 (clobber (reg:CC CC_REGNUM))]
7986 "reload_completed"
7987 [(parallel
7988 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7989 (clobber (reg:CC CC_REGNUM))])]
7990 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
7991
7992 ;
7993 ; xorqi3 instruction pattern(s).
7994 ;
7995
7996 (define_insn "*xorqi3"
7997 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,Q,S,Q")
7998 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,d,0,0,0")
7999 (match_operand:QI 2 "general_operand" "Os,d,d,n,n,Q")))
8000 (clobber (reg:CC CC_REGNUM))]
8001 "s390_logical_operator_ok_p (operands)"
8002 "@
8003 xilf\t%0,%b2
8004 xr\t%0,%2
8005 xrk\t%0,%1,%2
8006 xi\t%S0,%b2
8007 xiy\t%S0,%b2
8008 #"
8009 [(set_attr "op_type" "RIL,RR,RRF,SI,SIY,SS")
8010 (set_attr "cpu_facility" "*,*,z196,*,longdisp,*")
8011 (set_attr "z10prop" "z10_super_E1,z10_super_E1,*,z10_super,z10_super,*")])
8012
8013
8014 ;
8015 ; Block exclusive or (XC) patterns.
8016 ;
8017
8018 (define_insn "*xc"
8019 [(set (match_operand:BLK 0 "memory_operand" "=Q")
8020 (xor:BLK (match_dup 0)
8021 (match_operand:BLK 1 "memory_operand" "Q")))
8022 (use (match_operand 2 "const_int_operand" "n"))
8023 (clobber (reg:CC CC_REGNUM))]
8024 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
8025 "xc\t%O0(%2,%R0),%S1"
8026 [(set_attr "op_type" "SS")])
8027
8028 (define_split
8029 [(set (match_operand 0 "memory_operand" "")
8030 (xor (match_dup 0)
8031 (match_operand 1 "memory_operand" "")))
8032 (clobber (reg:CC CC_REGNUM))]
8033 "reload_completed
8034 && GET_MODE (operands[0]) == GET_MODE (operands[1])
8035 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
8036 [(parallel
8037 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
8038 (use (match_dup 2))
8039 (clobber (reg:CC CC_REGNUM))])]
8040 {
8041 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
8042 operands[0] = adjust_address (operands[0], BLKmode, 0);
8043 operands[1] = adjust_address (operands[1], BLKmode, 0);
8044 })
8045
8046 (define_peephole2
8047 [(parallel
8048 [(set (match_operand:BLK 0 "memory_operand" "")
8049 (xor:BLK (match_dup 0)
8050 (match_operand:BLK 1 "memory_operand" "")))
8051 (use (match_operand 2 "const_int_operand" ""))
8052 (clobber (reg:CC CC_REGNUM))])
8053 (parallel
8054 [(set (match_operand:BLK 3 "memory_operand" "")
8055 (xor:BLK (match_dup 3)
8056 (match_operand:BLK 4 "memory_operand" "")))
8057 (use (match_operand 5 "const_int_operand" ""))
8058 (clobber (reg:CC CC_REGNUM))])]
8059 "s390_offset_p (operands[0], operands[3], operands[2])
8060 && s390_offset_p (operands[1], operands[4], operands[2])
8061 && !s390_overlap_p (operands[0], operands[1],
8062 INTVAL (operands[2]) + INTVAL (operands[5]))
8063 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
8064 [(parallel
8065 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
8066 (use (match_dup 8))
8067 (clobber (reg:CC CC_REGNUM))])]
8068 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
8069 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
8070 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
8071
8072 ;
8073 ; Block xor (XC) patterns with src == dest.
8074 ;
8075
8076 (define_insn "*xc_zero"
8077 [(set (match_operand:BLK 0 "memory_operand" "=Q")
8078 (const_int 0))
8079 (use (match_operand 1 "const_int_operand" "n"))
8080 (clobber (reg:CC CC_REGNUM))]
8081 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
8082 "xc\t%O0(%1,%R0),%S0"
8083 [(set_attr "op_type" "SS")
8084 (set_attr "z196prop" "z196_cracked")])
8085
8086 (define_peephole2
8087 [(parallel
8088 [(set (match_operand:BLK 0 "memory_operand" "")
8089 (const_int 0))
8090 (use (match_operand 1 "const_int_operand" ""))
8091 (clobber (reg:CC CC_REGNUM))])
8092 (parallel
8093 [(set (match_operand:BLK 2 "memory_operand" "")
8094 (const_int 0))
8095 (use (match_operand 3 "const_int_operand" ""))
8096 (clobber (reg:CC CC_REGNUM))])]
8097 "s390_offset_p (operands[0], operands[2], operands[1])
8098 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
8099 [(parallel
8100 [(set (match_dup 4) (const_int 0))
8101 (use (match_dup 5))
8102 (clobber (reg:CC CC_REGNUM))])]
8103 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
8104 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
8105
8106
8107 ;;
8108 ;;- Negate instructions.
8109 ;;
8110
8111 ;
8112 ; neg(di|si)2 instruction pattern(s).
8113 ;
8114
8115 (define_expand "neg<mode>2"
8116 [(parallel
8117 [(set (match_operand:DSI 0 "register_operand" "=d")
8118 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
8119 (clobber (reg:CC CC_REGNUM))])]
8120 ""
8121 "")
8122
8123 (define_insn "*negdi2_sign_cc"
8124 [(set (reg CC_REGNUM)
8125 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
8126 (match_operand:SI 1 "register_operand" "d") 0)
8127 (const_int 32)) (const_int 32)))
8128 (const_int 0)))
8129 (set (match_operand:DI 0 "register_operand" "=d")
8130 (neg:DI (sign_extend:DI (match_dup 1))))]
8131 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8132 "lcgfr\t%0,%1"
8133 [(set_attr "op_type" "RRE")
8134 (set_attr "z10prop" "z10_c")])
8135
8136 (define_insn "*negdi2_sign"
8137 [(set (match_operand:DI 0 "register_operand" "=d")
8138 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8139 (clobber (reg:CC CC_REGNUM))]
8140 "TARGET_ZARCH"
8141 "lcgfr\t%0,%1"
8142 [(set_attr "op_type" "RRE")
8143 (set_attr "z10prop" "z10_c")])
8144
8145 ; lcr, lcgr
8146 (define_insn "*neg<mode>2_cc"
8147 [(set (reg CC_REGNUM)
8148 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8149 (const_int 0)))
8150 (set (match_operand:GPR 0 "register_operand" "=d")
8151 (neg:GPR (match_dup 1)))]
8152 "s390_match_ccmode (insn, CCAmode)"
8153 "lc<g>r\t%0,%1"
8154 [(set_attr "op_type" "RR<E>")
8155 (set_attr "z10prop" "z10_super_c_E1")])
8156
8157 ; lcr, lcgr
8158 (define_insn "*neg<mode>2_cconly"
8159 [(set (reg CC_REGNUM)
8160 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
8161 (const_int 0)))
8162 (clobber (match_scratch:GPR 0 "=d"))]
8163 "s390_match_ccmode (insn, CCAmode)"
8164 "lc<g>r\t%0,%1"
8165 [(set_attr "op_type" "RR<E>")
8166 (set_attr "z10prop" "z10_super_c_E1")])
8167
8168 ; lcr, lcgr
8169 (define_insn "*neg<mode>2"
8170 [(set (match_operand:GPR 0 "register_operand" "=d")
8171 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
8172 (clobber (reg:CC CC_REGNUM))]
8173 ""
8174 "lc<g>r\t%0,%1"
8175 [(set_attr "op_type" "RR<E>")
8176 (set_attr "z10prop" "z10_super_c_E1")])
8177
8178 (define_insn "*negdi2_31"
8179 [(set (match_operand:DI 0 "register_operand" "=d")
8180 (neg:DI (match_operand:DI 1 "register_operand" "d")))
8181 (clobber (reg:CC CC_REGNUM))]
8182 "!TARGET_ZARCH"
8183 "#")
8184
8185 ; Split a DImode NEG on 31bit into 2 SImode NEGs
8186
8187 ; Doing the twos complement separately on the SImode parts does an
8188 ; unwanted +1 on the high part which needs to be subtracted afterwards
8189 ; ... unless the +1 on the low part created an overflow.
8190
8191 (define_split
8192 [(set (match_operand:DI 0 "register_operand" "")
8193 (neg:DI (match_operand:DI 1 "register_operand" "")))
8194 (clobber (reg:CC CC_REGNUM))]
8195 "!TARGET_ZARCH
8196 && (REGNO (operands[0]) == REGNO (operands[1])
8197 || s390_split_ok_p (operands[0], operands[1], DImode, 0))
8198 && reload_completed"
8199 [(parallel
8200 [(set (match_dup 2) (neg:SI (match_dup 3)))
8201 (clobber (reg:CC CC_REGNUM))])
8202 (parallel
8203 [(set (reg:CCAP CC_REGNUM)
8204 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
8205 (set (match_dup 4) (neg:SI (match_dup 5)))])
8206 (set (pc)
8207 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8208 (pc)
8209 (label_ref (match_dup 6))))
8210 (parallel
8211 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8212 (clobber (reg:CC CC_REGNUM))])
8213 (match_dup 6)]
8214 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8215 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8216 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8217 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8218 operands[6] = gen_label_rtx ();")
8219
8220 ; Like above but first make a copy of the low part of the src operand
8221 ; since it might overlap with the high part of the destination.
8222
8223 (define_split
8224 [(set (match_operand:DI 0 "register_operand" "")
8225 (neg:DI (match_operand:DI 1 "register_operand" "")))
8226 (clobber (reg:CC CC_REGNUM))]
8227 "!TARGET_ZARCH
8228 && s390_split_ok_p (operands[0], operands[1], DImode, 1)
8229 && reload_completed"
8230 [; Make a backup of op5 first
8231 (set (match_dup 4) (match_dup 5))
8232 ; Setting op2 here might clobber op5
8233 (parallel
8234 [(set (match_dup 2) (neg:SI (match_dup 3)))
8235 (clobber (reg:CC CC_REGNUM))])
8236 (parallel
8237 [(set (reg:CCAP CC_REGNUM)
8238 (compare:CCAP (neg:SI (match_dup 4)) (const_int 0)))
8239 (set (match_dup 4) (neg:SI (match_dup 4)))])
8240 (set (pc)
8241 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
8242 (pc)
8243 (label_ref (match_dup 6))))
8244 (parallel
8245 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
8246 (clobber (reg:CC CC_REGNUM))])
8247 (match_dup 6)]
8248 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
8249 operands[3] = operand_subword (operands[1], 0, 0, DImode);
8250 operands[4] = operand_subword (operands[0], 1, 0, DImode);
8251 operands[5] = operand_subword (operands[1], 1, 0, DImode);
8252 operands[6] = gen_label_rtx ();")
8253
8254 ;
8255 ; neg(df|sf)2 instruction pattern(s).
8256 ;
8257
8258 (define_expand "neg<mode>2"
8259 [(parallel
8260 [(set (match_operand:BFP 0 "register_operand" "=f")
8261 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
8262 (clobber (reg:CC CC_REGNUM))])]
8263 "TARGET_HARD_FLOAT"
8264 "")
8265
8266 ; lcxbr, lcdbr, lcebr
8267 (define_insn "*neg<mode>2_cc"
8268 [(set (reg CC_REGNUM)
8269 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8270 (match_operand:BFP 2 "const0_operand" "")))
8271 (set (match_operand:BFP 0 "register_operand" "=f")
8272 (neg:BFP (match_dup 1)))]
8273 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8274 "lc<xde>br\t%0,%1"
8275 [(set_attr "op_type" "RRE")
8276 (set_attr "type" "fsimp<mode>")])
8277
8278 ; lcxbr, lcdbr, lcebr
8279 (define_insn "*neg<mode>2_cconly"
8280 [(set (reg CC_REGNUM)
8281 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
8282 (match_operand:BFP 2 "const0_operand" "")))
8283 (clobber (match_scratch:BFP 0 "=f"))]
8284 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8285 "lc<xde>br\t%0,%1"
8286 [(set_attr "op_type" "RRE")
8287 (set_attr "type" "fsimp<mode>")])
8288
8289 ; lcdfr
8290 (define_insn "*neg<mode>2_nocc"
8291 [(set (match_operand:FP 0 "register_operand" "=f")
8292 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8293 "TARGET_DFP"
8294 "lcdfr\t%0,%1"
8295 [(set_attr "op_type" "RRE")
8296 (set_attr "type" "fsimp<mode>")])
8297
8298 ; lcxbr, lcdbr, lcebr
8299 ; FIXME: wflcdb does not clobber cc
8300 (define_insn "*neg<mode>2"
8301 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8302 (neg:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8303 (clobber (reg:CC CC_REGNUM))]
8304 "TARGET_HARD_FLOAT"
8305 "@
8306 lc<xde>br\t%0,%1
8307 wflcdb\t%0,%1"
8308 [(set_attr "op_type" "RRE,VRR")
8309 (set_attr "cpu_facility" "*,vec")
8310 (set_attr "type" "fsimp<mode>,*")
8311 (set_attr "enabled" "*,<DFDI>")])
8312
8313
8314 ;;
8315 ;;- Absolute value instructions.
8316 ;;
8317
8318 ;
8319 ; abs(di|si)2 instruction pattern(s).
8320 ;
8321
8322 (define_insn "*absdi2_sign_cc"
8323 [(set (reg CC_REGNUM)
8324 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8325 (match_operand:SI 1 "register_operand" "d") 0)
8326 (const_int 32)) (const_int 32)))
8327 (const_int 0)))
8328 (set (match_operand:DI 0 "register_operand" "=d")
8329 (abs:DI (sign_extend:DI (match_dup 1))))]
8330 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8331 "lpgfr\t%0,%1"
8332 [(set_attr "op_type" "RRE")
8333 (set_attr "z10prop" "z10_c")])
8334
8335 (define_insn "*absdi2_sign"
8336 [(set (match_operand:DI 0 "register_operand" "=d")
8337 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
8338 (clobber (reg:CC CC_REGNUM))]
8339 "TARGET_ZARCH"
8340 "lpgfr\t%0,%1"
8341 [(set_attr "op_type" "RRE")
8342 (set_attr "z10prop" "z10_c")])
8343
8344 ; lpr, lpgr
8345 (define_insn "*abs<mode>2_cc"
8346 [(set (reg CC_REGNUM)
8347 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
8348 (const_int 0)))
8349 (set (match_operand:GPR 0 "register_operand" "=d")
8350 (abs:GPR (match_dup 1)))]
8351 "s390_match_ccmode (insn, CCAmode)"
8352 "lp<g>r\t%0,%1"
8353 [(set_attr "op_type" "RR<E>")
8354 (set_attr "z10prop" "z10_c")])
8355
8356 ; lpr, lpgr
8357 (define_insn "*abs<mode>2_cconly"
8358 [(set (reg CC_REGNUM)
8359 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
8360 (const_int 0)))
8361 (clobber (match_scratch:GPR 0 "=d"))]
8362 "s390_match_ccmode (insn, CCAmode)"
8363 "lp<g>r\t%0,%1"
8364 [(set_attr "op_type" "RR<E>")
8365 (set_attr "z10prop" "z10_c")])
8366
8367 ; lpr, lpgr
8368 (define_insn "abs<mode>2"
8369 [(set (match_operand:GPR 0 "register_operand" "=d")
8370 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8371 (clobber (reg:CC CC_REGNUM))]
8372 ""
8373 "lp<g>r\t%0,%1"
8374 [(set_attr "op_type" "RR<E>")
8375 (set_attr "z10prop" "z10_c")])
8376
8377 ;
8378 ; abs(df|sf)2 instruction pattern(s).
8379 ;
8380
8381 (define_expand "abs<mode>2"
8382 [(parallel
8383 [(set (match_operand:BFP 0 "register_operand" "=f")
8384 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8385 (clobber (reg:CC CC_REGNUM))])]
8386 "TARGET_HARD_FLOAT"
8387 "")
8388
8389 ; lpxbr, lpdbr, lpebr
8390 (define_insn "*abs<mode>2_cc"
8391 [(set (reg CC_REGNUM)
8392 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8393 (match_operand:BFP 2 "const0_operand" "")))
8394 (set (match_operand:BFP 0 "register_operand" "=f")
8395 (abs:BFP (match_dup 1)))]
8396 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8397 "lp<xde>br\t%0,%1"
8398 [(set_attr "op_type" "RRE")
8399 (set_attr "type" "fsimp<mode>")])
8400
8401 ; lpxbr, lpdbr, lpebr
8402 (define_insn "*abs<mode>2_cconly"
8403 [(set (reg CC_REGNUM)
8404 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
8405 (match_operand:BFP 2 "const0_operand" "")))
8406 (clobber (match_scratch:BFP 0 "=f"))]
8407 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8408 "lp<xde>br\t%0,%1"
8409 [(set_attr "op_type" "RRE")
8410 (set_attr "type" "fsimp<mode>")])
8411
8412 ; lpdfr
8413 (define_insn "*abs<mode>2_nocc"
8414 [(set (match_operand:FP 0 "register_operand" "=f")
8415 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
8416 "TARGET_DFP"
8417 "lpdfr\t%0,%1"
8418 [(set_attr "op_type" "RRE")
8419 (set_attr "type" "fsimp<mode>")])
8420
8421 ; lpxbr, lpdbr, lpebr
8422 ; FIXME: wflpdb does not clobber cc
8423 (define_insn "*abs<mode>2"
8424 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8425 (abs:BFP (match_operand:BFP 1 "register_operand" "f,v")))
8426 (clobber (reg:CC CC_REGNUM))]
8427 "TARGET_HARD_FLOAT"
8428 "@
8429 lp<xde>br\t%0,%1
8430 wflpdb\t%0,%1"
8431 [(set_attr "op_type" "RRE,VRR")
8432 (set_attr "cpu_facility" "*,vec")
8433 (set_attr "type" "fsimp<mode>,*")
8434 (set_attr "enabled" "*,<DFDI>")])
8435
8436
8437 ;;
8438 ;;- Negated absolute value instructions
8439 ;;
8440
8441 ;
8442 ; Integer
8443 ;
8444
8445 (define_insn "*negabsdi2_sign_cc"
8446 [(set (reg CC_REGNUM)
8447 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
8448 (match_operand:SI 1 "register_operand" "d") 0)
8449 (const_int 32)) (const_int 32))))
8450 (const_int 0)))
8451 (set (match_operand:DI 0 "register_operand" "=d")
8452 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
8453 "TARGET_ZARCH && s390_match_ccmode (insn, CCAmode)"
8454 "lngfr\t%0,%1"
8455 [(set_attr "op_type" "RRE")
8456 (set_attr "z10prop" "z10_c")])
8457
8458 (define_insn "*negabsdi2_sign"
8459 [(set (match_operand:DI 0 "register_operand" "=d")
8460 (neg:DI (abs:DI (sign_extend:DI
8461 (match_operand:SI 1 "register_operand" "d")))))
8462 (clobber (reg:CC CC_REGNUM))]
8463 "TARGET_ZARCH"
8464 "lngfr\t%0,%1"
8465 [(set_attr "op_type" "RRE")
8466 (set_attr "z10prop" "z10_c")])
8467
8468 ; lnr, lngr
8469 (define_insn "*negabs<mode>2_cc"
8470 [(set (reg CC_REGNUM)
8471 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8472 (const_int 0)))
8473 (set (match_operand:GPR 0 "register_operand" "=d")
8474 (neg:GPR (abs:GPR (match_dup 1))))]
8475 "s390_match_ccmode (insn, CCAmode)"
8476 "ln<g>r\t%0,%1"
8477 [(set_attr "op_type" "RR<E>")
8478 (set_attr "z10prop" "z10_c")])
8479
8480 ; lnr, lngr
8481 (define_insn "*negabs<mode>2_cconly"
8482 [(set (reg CC_REGNUM)
8483 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
8484 (const_int 0)))
8485 (clobber (match_scratch:GPR 0 "=d"))]
8486 "s390_match_ccmode (insn, CCAmode)"
8487 "ln<g>r\t%0,%1"
8488 [(set_attr "op_type" "RR<E>")
8489 (set_attr "z10prop" "z10_c")])
8490
8491 ; lnr, lngr
8492 (define_insn "*negabs<mode>2"
8493 [(set (match_operand:GPR 0 "register_operand" "=d")
8494 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
8495 (clobber (reg:CC CC_REGNUM))]
8496 ""
8497 "ln<g>r\t%0,%1"
8498 [(set_attr "op_type" "RR<E>")
8499 (set_attr "z10prop" "z10_c")])
8500
8501 ;
8502 ; Floating point
8503 ;
8504
8505 ; lnxbr, lndbr, lnebr
8506 (define_insn "*negabs<mode>2_cc"
8507 [(set (reg CC_REGNUM)
8508 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8509 (match_operand:BFP 2 "const0_operand" "")))
8510 (set (match_operand:BFP 0 "register_operand" "=f")
8511 (neg:BFP (abs:BFP (match_dup 1))))]
8512 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8513 "ln<xde>br\t%0,%1"
8514 [(set_attr "op_type" "RRE")
8515 (set_attr "type" "fsimp<mode>")])
8516
8517 ; lnxbr, lndbr, lnebr
8518 (define_insn "*negabs<mode>2_cconly"
8519 [(set (reg CC_REGNUM)
8520 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
8521 (match_operand:BFP 2 "const0_operand" "")))
8522 (clobber (match_scratch:BFP 0 "=f"))]
8523 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
8524 "ln<xde>br\t%0,%1"
8525 [(set_attr "op_type" "RRE")
8526 (set_attr "type" "fsimp<mode>")])
8527
8528 ; lndfr
8529 (define_insn "*negabs<mode>2_nocc"
8530 [(set (match_operand:FP 0 "register_operand" "=f")
8531 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
8532 "TARGET_DFP"
8533 "lndfr\t%0,%1"
8534 [(set_attr "op_type" "RRE")
8535 (set_attr "type" "fsimp<mode>")])
8536
8537 ; lnxbr, lndbr, lnebr
8538 ; FIXME: wflndb does not clobber cc
8539 (define_insn "*negabs<mode>2"
8540 [(set (match_operand:BFP 0 "register_operand" "=f,v")
8541 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f,v"))))
8542 (clobber (reg:CC CC_REGNUM))]
8543 "TARGET_HARD_FLOAT"
8544 "@
8545 ln<xde>br\t%0,%1
8546 wflndb\t%0,%1"
8547 [(set_attr "op_type" "RRE,VRR")
8548 (set_attr "cpu_facility" "*,vec")
8549 (set_attr "type" "fsimp<mode>,*")
8550 (set_attr "enabled" "*,<DFDI>")])
8551
8552 ;;
8553 ;;- Square root instructions.
8554 ;;
8555
8556 ;
8557 ; sqrt(df|sf)2 instruction pattern(s).
8558 ;
8559
8560 ; sqxbr, sqdbr, sqebr, sqdb, sqeb
8561 (define_insn "sqrt<mode>2"
8562 [(set (match_operand:BFP 0 "register_operand" "=f,f,v")
8563 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,R,v")))]
8564 "TARGET_HARD_FLOAT"
8565 "@
8566 sq<xde>br\t%0,%1
8567 sq<xde>b\t%0,%1
8568 wfsqdb\t%v0,%v1"
8569 [(set_attr "op_type" "RRE,RXE,VRR")
8570 (set_attr "type" "fsqrt<mode>")
8571 (set_attr "cpu_facility" "*,*,vec")
8572 (set_attr "enabled" "*,<DSF>,<DFDI>")])
8573
8574
8575 ;;
8576 ;;- One complement instructions.
8577 ;;
8578
8579 ;
8580 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
8581 ;
8582
8583 (define_expand "one_cmpl<mode>2"
8584 [(parallel
8585 [(set (match_operand:INT 0 "register_operand" "")
8586 (xor:INT (match_operand:INT 1 "register_operand" "")
8587 (const_int -1)))
8588 (clobber (reg:CC CC_REGNUM))])]
8589 ""
8590 "")
8591
8592
8593 ;;
8594 ;; Find leftmost bit instructions.
8595 ;;
8596
8597 (define_expand "clzdi2"
8598 [(set (match_operand:DI 0 "register_operand" "=d")
8599 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
8600 "TARGET_EXTIMM && TARGET_ZARCH"
8601 {
8602 rtx insn, clz_equal;
8603 rtx wide_reg = gen_reg_rtx (TImode);
8604 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
8605
8606 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
8607
8608 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
8609
8610 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
8611 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
8612
8613 DONE;
8614 })
8615
8616 (define_insn "clztidi2"
8617 [(set (match_operand:TI 0 "register_operand" "=d")
8618 (ior:TI
8619 (ashift:TI
8620 (zero_extend:TI
8621 (xor:DI (match_operand:DI 1 "register_operand" "d")
8622 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
8623 (subreg:SI (clz:DI (match_dup 1)) 4))))
8624
8625 (const_int 64))
8626 (zero_extend:TI (clz:DI (match_dup 1)))))
8627 (clobber (reg:CC CC_REGNUM))]
8628 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
8629 == (unsigned HOST_WIDE_INT) 1 << 63
8630 && TARGET_EXTIMM && TARGET_ZARCH"
8631 "flogr\t%0,%1"
8632 [(set_attr "op_type" "RRE")])
8633
8634
8635 ;;
8636 ;;- Rotate instructions.
8637 ;;
8638
8639 ;
8640 ; rotl(di|si)3 instruction pattern(s).
8641 ;
8642
8643 (define_expand "rotl<mode>3"
8644 [(set (match_operand:GPR 0 "register_operand" "")
8645 (rotate:GPR (match_operand:GPR 1 "register_operand" "")
8646 (match_operand:SI 2 "nonmemory_operand" "")))]
8647 "TARGET_CPU_ZARCH"
8648 "")
8649
8650 ; rll, rllg
8651 (define_insn "*rotl<mode>3<addr_style_op><masked_op>"
8652 [(set (match_operand:GPR 0 "register_operand" "=d")
8653 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
8654 (match_operand:SI 2 "nonmemory_operand" "an")))]
8655 "TARGET_CPU_ZARCH"
8656 "rll<g>\t%0,%1,<addr_style_op_ops>"
8657 [(set_attr "op_type" "RSE")
8658 (set_attr "atype" "reg")
8659 (set_attr "z10prop" "z10_super_E1")])
8660
8661
8662 ;;
8663 ;;- Shift instructions.
8664 ;;
8665
8666 ;
8667 ; (ashl|lshr)(di|si)3 instruction pattern(s).
8668 ; Left shifts and logical right shifts
8669
8670 (define_expand "<shift><mode>3"
8671 [(set (match_operand:DSI 0 "register_operand" "")
8672 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
8673 (match_operand:SI 2 "nonmemory_operand" "")))]
8674 ""
8675 "")
8676
8677 ; ESA 64 bit register pair shift with reg or imm shift count
8678 ; sldl, srdl
8679 (define_insn "*<shift>di3_31<addr_style_op><masked_op>"
8680 [(set (match_operand:DI 0 "register_operand" "=d")
8681 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
8682 (match_operand:SI 2 "nonmemory_operand" "an")))]
8683 "!TARGET_ZARCH"
8684 "s<lr>dl\t%0,<addr_style_op_ops>"
8685 [(set_attr "op_type" "RS")
8686 (set_attr "atype" "reg")
8687 (set_attr "z196prop" "z196_cracked")])
8688
8689
8690 ; 64 bit register shift with reg or imm shift count
8691 ; sll, srl, sllg, srlg, sllk, srlk
8692 (define_insn "*<shift><mode>3<addr_style_op><masked_op>"
8693 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8694 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8695 (match_operand:SI 2 "nonmemory_operand" "an,an")))]
8696 ""
8697 "@
8698 s<lr>l<g>\t%0,<1><addr_style_op_ops>
8699 s<lr>l<gk>\t%0,%1,<addr_style_op_ops>"
8700 [(set_attr "op_type" "RS<E>,RSY")
8701 (set_attr "atype" "reg,reg")
8702 (set_attr "cpu_facility" "*,z196")
8703 (set_attr "z10prop" "z10_super_E1,*")])
8704
8705 ;
8706 ; ashr(di|si)3 instruction pattern(s).
8707 ; Arithmetic right shifts
8708
8709 (define_expand "ashr<mode>3"
8710 [(parallel
8711 [(set (match_operand:DSI 0 "register_operand" "")
8712 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
8713 (match_operand:SI 2 "nonmemory_operand" "")))
8714 (clobber (reg:CC CC_REGNUM))])]
8715 ""
8716 "")
8717
8718 ; FIXME: The number of alternatives is doubled here to match the fix
8719 ; number of 2 in the subst pattern for the (clobber (match_scratch...
8720 ; The right fix should be to support match_scratch in the output
8721 ; pattern of a define_subst.
8722 (define_insn "*ashrdi3_31<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8723 [(set (match_operand:DI 0 "register_operand" "=d, d")
8724 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0, 0")
8725 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8726 (clobber (reg:CC CC_REGNUM))]
8727 "!TARGET_ZARCH"
8728 "@
8729 srda\t%0,<addr_style_op_cc_ops>
8730 srda\t%0,<addr_style_op_cc_ops>"
8731 [(set_attr "op_type" "RS")
8732 (set_attr "atype" "reg")])
8733
8734
8735 ; sra, srag
8736 (define_insn "*ashr<mode>3<addr_style_op_cc><masked_op_cc><setcc><cconly>"
8737 [(set (match_operand:GPR 0 "register_operand" "=d, d")
8738 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>, d")
8739 (match_operand:SI 2 "nonmemory_operand" "an,an")))
8740 (clobber (reg:CC CC_REGNUM))]
8741 ""
8742 "@
8743 sra<g>\t%0,<1><addr_style_op_cc_ops>
8744 sra<gk>\t%0,%1,<addr_style_op_cc_ops>"
8745 [(set_attr "op_type" "RS<E>,RSY")
8746 (set_attr "atype" "reg")
8747 (set_attr "cpu_facility" "*,z196")
8748 (set_attr "z10prop" "z10_super_E1,*")])
8749
8750
8751 ;;
8752 ;; Branch instruction patterns.
8753 ;;
8754
8755 (define_expand "cbranch<mode>4"
8756 [(set (pc)
8757 (if_then_else (match_operator 0 "comparison_operator"
8758 [(match_operand:GPR 1 "register_operand" "")
8759 (match_operand:GPR 2 "general_operand" "")])
8760 (label_ref (match_operand 3 "" ""))
8761 (pc)))]
8762 ""
8763 "s390_emit_jump (operands[3],
8764 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8765 DONE;")
8766
8767 (define_expand "cbranch<mode>4"
8768 [(set (pc)
8769 (if_then_else (match_operator 0 "comparison_operator"
8770 [(match_operand:FP 1 "register_operand" "")
8771 (match_operand:FP 2 "general_operand" "")])
8772 (label_ref (match_operand 3 "" ""))
8773 (pc)))]
8774 "TARGET_HARD_FLOAT"
8775 "s390_emit_jump (operands[3],
8776 s390_emit_compare (GET_CODE (operands[0]), operands[1], operands[2]));
8777 DONE;")
8778
8779 (define_expand "cbranchcc4"
8780 [(set (pc)
8781 (if_then_else (match_operator 0 "s390_comparison"
8782 [(match_operand 1 "cc_reg_operand" "")
8783 (match_operand 2 "const_int_operand" "")])
8784 (label_ref (match_operand 3 "" ""))
8785 (pc)))]
8786 ""
8787 "")
8788
8789
8790 ;;
8791 ;;- Conditional jump instructions.
8792 ;;
8793
8794 (define_insn "*cjump_64"
8795 [(set (pc)
8796 (if_then_else
8797 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8798 (match_operand 2 "const_int_operand" "")])
8799 (label_ref (match_operand 0 "" ""))
8800 (pc)))]
8801 "TARGET_CPU_ZARCH"
8802 {
8803 if (get_attr_length (insn) == 4)
8804 return "j%C1\t%l0";
8805 else
8806 return "jg%C1\t%l0";
8807 }
8808 [(set_attr "op_type" "RI")
8809 (set_attr "type" "branch")
8810 (set (attr "length")
8811 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8812 (const_int 4) (const_int 6)))])
8813
8814 (define_insn "*cjump_31"
8815 [(set (pc)
8816 (if_then_else
8817 (match_operator 1 "s390_comparison" [(reg CC_REGNUM)
8818 (match_operand 2 "const_int_operand" "")])
8819 (label_ref (match_operand 0 "" ""))
8820 (pc)))]
8821 "!TARGET_CPU_ZARCH"
8822 {
8823 gcc_assert (get_attr_length (insn) == 4);
8824 return "j%C1\t%l0";
8825 }
8826 [(set_attr "op_type" "RI")
8827 (set_attr "type" "branch")
8828 (set (attr "length")
8829 (if_then_else (not (match_test "flag_pic"))
8830 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8831 (const_int 4) (const_int 6))
8832 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8833 (const_int 4) (const_int 8))))])
8834
8835 (define_insn "*cjump_long"
8836 [(set (pc)
8837 (if_then_else
8838 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8839 (match_operand 0 "address_operand" "ZQZR")
8840 (pc)))]
8841 ""
8842 {
8843 if (get_attr_op_type (insn) == OP_TYPE_RR)
8844 return "b%C1r\t%0";
8845 else
8846 return "b%C1\t%a0";
8847 }
8848 [(set (attr "op_type")
8849 (if_then_else (match_operand 0 "register_operand" "")
8850 (const_string "RR") (const_string "RX")))
8851 (set_attr "type" "branch")
8852 (set_attr "atype" "agen")])
8853
8854 ;; A conditional return instruction.
8855 (define_insn "*c<code>"
8856 [(set (pc)
8857 (if_then_else
8858 (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8859 (ANY_RETURN)
8860 (pc)))]
8861 "s390_can_use_<code>_insn ()"
8862 "b%C0r\t%%r14"
8863 [(set_attr "op_type" "RR")
8864 (set_attr "type" "jsr")
8865 (set_attr "atype" "agen")])
8866
8867 ;;
8868 ;;- Negated conditional jump instructions.
8869 ;;
8870
8871 (define_insn "*icjump_64"
8872 [(set (pc)
8873 (if_then_else
8874 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8875 (pc)
8876 (label_ref (match_operand 0 "" ""))))]
8877 "TARGET_CPU_ZARCH"
8878 {
8879 if (get_attr_length (insn) == 4)
8880 return "j%D1\t%l0";
8881 else
8882 return "jg%D1\t%l0";
8883 }
8884 [(set_attr "op_type" "RI")
8885 (set_attr "type" "branch")
8886 (set (attr "length")
8887 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8888 (const_int 4) (const_int 6)))])
8889
8890 (define_insn "*icjump_31"
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 gcc_assert (get_attr_length (insn) == 4);
8899 return "j%D1\t%l0";
8900 }
8901 [(set_attr "op_type" "RI")
8902 (set_attr "type" "branch")
8903 (set (attr "length")
8904 (if_then_else (not (match_test "flag_pic"))
8905 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8906 (const_int 4) (const_int 6))
8907 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
8908 (const_int 4) (const_int 8))))])
8909
8910 (define_insn "*icjump_long"
8911 [(set (pc)
8912 (if_then_else
8913 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
8914 (pc)
8915 (match_operand 0 "address_operand" "ZQZR")))]
8916 ""
8917 {
8918 if (get_attr_op_type (insn) == OP_TYPE_RR)
8919 return "b%D1r\t%0";
8920 else
8921 return "b%D1\t%a0";
8922 }
8923 [(set (attr "op_type")
8924 (if_then_else (match_operand 0 "register_operand" "")
8925 (const_string "RR") (const_string "RX")))
8926 (set_attr "type" "branch")
8927 (set_attr "atype" "agen")])
8928
8929 ;;
8930 ;;- Trap instructions.
8931 ;;
8932
8933 (define_insn "trap"
8934 [(trap_if (const_int 1) (const_int 0))]
8935 ""
8936 "j\t.+2"
8937 [(set_attr "op_type" "RI")
8938 (set_attr "type" "branch")])
8939
8940 (define_expand "ctrap<mode>4"
8941 [(trap_if (match_operator 0 "comparison_operator"
8942 [(match_operand:GPR 1 "register_operand" "")
8943 (match_operand:GPR 2 "general_operand" "")])
8944 (match_operand 3 "const0_operand" ""))]
8945 ""
8946 {
8947 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8948 operands[1], operands[2]);
8949 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8950 DONE;
8951 })
8952
8953 (define_expand "ctrap<mode>4"
8954 [(trap_if (match_operator 0 "comparison_operator"
8955 [(match_operand:FP 1 "register_operand" "")
8956 (match_operand:FP 2 "general_operand" "")])
8957 (match_operand 3 "const0_operand" ""))]
8958 ""
8959 {
8960 rtx cond = s390_emit_compare (GET_CODE (operands[0]),
8961 operands[1], operands[2]);
8962 emit_insn (gen_condtrap (cond, XEXP (cond, 0)));
8963 DONE;
8964 })
8965
8966 (define_insn "condtrap"
8967 [(trap_if (match_operator 0 "s390_comparison"
8968 [(match_operand 1 "cc_reg_operand" "c")
8969 (const_int 0)])
8970 (const_int 0))]
8971 ""
8972 "j%C0\t.+2";
8973 [(set_attr "op_type" "RI")
8974 (set_attr "type" "branch")])
8975
8976 ; crt, cgrt, cit, cgit
8977 (define_insn "*cmp_and_trap_signed_int<mode>"
8978 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
8979 [(match_operand:GPR 1 "register_operand" "d,d")
8980 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
8981 (const_int 0))]
8982 "TARGET_Z10"
8983 "@
8984 c<g>rt%C0\t%1,%2
8985 c<g>it%C0\t%1,%h2"
8986 [(set_attr "op_type" "RRF,RIE")
8987 (set_attr "type" "branch")
8988 (set_attr "z10prop" "z10_super_c,z10_super")])
8989
8990 ; clrt, clgrt, clfit, clgit, clt, clgt
8991 (define_insn "*cmp_and_trap_unsigned_int<mode>"
8992 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
8993 [(match_operand:GPR 1 "register_operand" "d,d,d")
8994 (match_operand:GPR 2 "general_operand" "d,D,T")])
8995 (const_int 0))]
8996 "TARGET_Z10"
8997 "@
8998 cl<g>rt%C0\t%1,%2
8999 cl<gf>it%C0\t%1,%x2
9000 cl<g>t%C0\t%1,%2"
9001 [(set_attr "op_type" "RRF,RIE,RSY")
9002 (set_attr "type" "branch")
9003 (set_attr "z10prop" "z10_super_c,z10_super,*")
9004 (set_attr "cpu_facility" "z10,z10,zEC12")])
9005
9006 ; lat, lgat
9007 (define_insn "*load_and_trap<mode>"
9008 [(trap_if (eq (match_operand:GPR 0 "memory_operand" "T")
9009 (const_int 0))
9010 (const_int 0))
9011 (set (match_operand:GPR 1 "register_operand" "=d")
9012 (match_dup 0))]
9013 "TARGET_ZEC12"
9014 "l<g>at\t%1,%0"
9015 [(set_attr "op_type" "RXY")])
9016
9017
9018 ;;
9019 ;;- Loop instructions.
9020 ;;
9021 ;; This is all complicated by the fact that since this is a jump insn
9022 ;; we must handle our own output reloads.
9023
9024 ;; branch on index
9025
9026 ; This splitter will be matched by combine and has to add the 2 moves
9027 ; necessary to load the compare and the increment values into a
9028 ; register pair as needed by brxle.
9029
9030 (define_insn_and_split "*brx_stage1_<GPR:mode>"
9031 [(set (pc)
9032 (if_then_else
9033 (match_operator 6 "s390_brx_operator"
9034 [(plus:GPR (match_operand:GPR 1 "register_operand" "")
9035 (match_operand:GPR 2 "general_operand" ""))
9036 (match_operand:GPR 3 "register_operand" "")])
9037 (label_ref (match_operand 0 "" ""))
9038 (pc)))
9039 (set (match_operand:GPR 4 "nonimmediate_operand" "")
9040 (plus:GPR (match_dup 1) (match_dup 2)))
9041 (clobber (match_scratch:GPR 5 ""))]
9042 "TARGET_CPU_ZARCH"
9043 "#"
9044 "!reload_completed && !reload_in_progress"
9045 [(set (match_dup 7) (match_dup 2)) ; the increment
9046 (set (match_dup 8) (match_dup 3)) ; the comparison value
9047 (parallel [(set (pc)
9048 (if_then_else
9049 (match_op_dup 6
9050 [(plus:GPR (match_dup 1) (match_dup 7))
9051 (match_dup 8)])
9052 (label_ref (match_dup 0))
9053 (pc)))
9054 (set (match_dup 4)
9055 (plus:GPR (match_dup 1) (match_dup 7)))
9056 (clobber (match_dup 5))
9057 (clobber (reg:CC CC_REGNUM))])]
9058 {
9059 rtx dreg = gen_reg_rtx (word_mode == DImode ? TImode : DImode);
9060 operands[7] = gen_lowpart (<GPR:MODE>mode,
9061 gen_highpart (word_mode, dreg));
9062 operands[8] = gen_lowpart (<GPR:MODE>mode,
9063 gen_lowpart (word_mode, dreg));
9064 })
9065
9066 ; brxlg, brxhg
9067
9068 (define_insn_and_split "*brxg_64bit"
9069 [(set (pc)
9070 (if_then_else
9071 (match_operator 5 "s390_brx_operator"
9072 [(plus:DI (match_operand:DI 1 "register_operand" "d,d,d")
9073 (subreg:DI (match_operand:TI 2 "register_operand" "d,d,d") 0))
9074 (subreg:DI (match_dup 2) 8)])
9075 (label_ref (match_operand 0 "" ""))
9076 (pc)))
9077 (set (match_operand:DI 3 "nonimmediate_operand" "=1,?X,?X")
9078 (plus:DI (match_dup 1)
9079 (subreg:DI (match_dup 2) 0)))
9080 (clobber (match_scratch:DI 4 "=X,&1,&?d"))
9081 (clobber (reg:CC CC_REGNUM))]
9082 "TARGET_ZARCH"
9083 {
9084 if (which_alternative != 0)
9085 return "#";
9086 else if (get_attr_length (insn) == 6)
9087 return "brx%E5g\t%1,%2,%l0";
9088 else
9089 return "agr\t%1,%2\;cgr\t%1,%M2\;jg%C5\t%l0";
9090 }
9091 "&& reload_completed
9092 && (!REG_P (operands[3])
9093 || !rtx_equal_p (operands[1], operands[3]))"
9094 [(set (match_dup 4) (match_dup 1))
9095 (parallel [(set (match_dup 4) (plus:DI (match_dup 4) (subreg:DI (match_dup 2) 0)))
9096 (clobber (reg:CC CC_REGNUM))])
9097 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:DI (match_dup 2) 8)))
9098 (set (match_dup 3) (match_dup 4))
9099 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9100 (label_ref (match_dup 0))
9101 (pc)))]
9102 ""
9103 [(set_attr "op_type" "RIE")
9104 (set_attr "type" "branch")
9105 (set (attr "length")
9106 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9107 (const_int 6) (const_int 16)))])
9108
9109 ; brxle, brxh
9110
9111 (define_insn_and_split "*brx_64bit"
9112 [(set (pc)
9113 (if_then_else
9114 (match_operator 5 "s390_brx_operator"
9115 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9116 (subreg:SI (match_operand:TI 2 "register_operand" "d,d,d") 4))
9117 (subreg:SI (match_dup 2) 12)])
9118 (label_ref (match_operand 0 "" ""))
9119 (pc)))
9120 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9121 (plus:SI (match_dup 1)
9122 (subreg:SI (match_dup 2) 4)))
9123 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9124 (clobber (reg:CC CC_REGNUM))]
9125 "TARGET_ZARCH"
9126 {
9127 if (which_alternative != 0)
9128 return "#";
9129 else if (get_attr_length (insn) == 6)
9130 return "brx%C5\t%1,%2,%l0";
9131 else
9132 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9133 }
9134 "&& reload_completed
9135 && (!REG_P (operands[3])
9136 || !rtx_equal_p (operands[1], operands[3]))"
9137 [(set (match_dup 4) (match_dup 1))
9138 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 4)))
9139 (clobber (reg:CC CC_REGNUM))])
9140 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 12)))
9141 (set (match_dup 3) (match_dup 4))
9142 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9143 (label_ref (match_dup 0))
9144 (pc)))]
9145 ""
9146 [(set_attr "op_type" "RSI")
9147 (set_attr "type" "branch")
9148 (set (attr "length")
9149 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9150 (const_int 6) (const_int 14)))])
9151
9152 ; brxle, brxh
9153
9154 (define_insn_and_split "*brx_31bit"
9155 [(set (pc)
9156 (if_then_else
9157 (match_operator 5 "s390_brx_operator"
9158 [(plus:SI (match_operand:SI 1 "register_operand" "d,d,d")
9159 (subreg:SI (match_operand:DI 2 "register_operand" "d,d,d") 0))
9160 (subreg:SI (match_dup 2) 4)])
9161 (label_ref (match_operand 0 "" ""))
9162 (pc)))
9163 (set (match_operand:SI 3 "nonimmediate_operand" "=1,?X,?X")
9164 (plus:SI (match_dup 1)
9165 (subreg:SI (match_dup 2) 0)))
9166 (clobber (match_scratch:SI 4 "=X,&1,&?d"))
9167 (clobber (reg:CC CC_REGNUM))]
9168 "!TARGET_ZARCH && TARGET_CPU_ZARCH"
9169 {
9170 if (which_alternative != 0)
9171 return "#";
9172 else if (get_attr_length (insn) == 6)
9173 return "brx%C5\t%1,%2,%l0";
9174 else
9175 return "ar\t%1,%2\;cr\t%1,%M2\;jg%C5\t%l0";
9176 }
9177 "&& reload_completed
9178 && (!REG_P (operands[3])
9179 || !rtx_equal_p (operands[1], operands[3]))"
9180 [(set (match_dup 4) (match_dup 1))
9181 (parallel [(set (match_dup 4) (plus:SI (match_dup 4) (subreg:SI (match_dup 2) 0)))
9182 (clobber (reg:CC CC_REGNUM))])
9183 (set (reg:CCS CC_REGNUM) (compare:CCS (match_dup 4) (subreg:SI (match_dup 2) 4)))
9184 (set (match_dup 3) (match_dup 4))
9185 (set (pc) (if_then_else (match_op_dup 5 [(reg:CCS CC_REGNUM) (const_int 0)])
9186 (label_ref (match_dup 0))
9187 (pc)))]
9188 ""
9189 [(set_attr "op_type" "RSI")
9190 (set_attr "type" "branch")
9191 (set (attr "length")
9192 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9193 (const_int 6) (const_int 14)))])
9194
9195
9196 ;; branch on count
9197
9198 (define_expand "doloop_end"
9199 [(use (match_operand 0 "" "")) ; loop pseudo
9200 (use (match_operand 1 "" ""))] ; label
9201 ""
9202 {
9203 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
9204 emit_jump_insn (gen_doloop_si31 (operands[1], operands[0], operands[0]));
9205 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
9206 emit_jump_insn (gen_doloop_si64 (operands[1], operands[0], operands[0]));
9207 else if (GET_MODE (operands[0]) == DImode && TARGET_ZARCH)
9208 emit_jump_insn (gen_doloop_di (operands[1], operands[0], operands[0]));
9209 else
9210 FAIL;
9211
9212 DONE;
9213 })
9214
9215 (define_insn_and_split "doloop_si64"
9216 [(set (pc)
9217 (if_then_else
9218 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9219 (const_int 1))
9220 (label_ref (match_operand 0 "" ""))
9221 (pc)))
9222 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9223 (plus:SI (match_dup 1) (const_int -1)))
9224 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9225 (clobber (reg:CC CC_REGNUM))]
9226 "TARGET_CPU_ZARCH"
9227 {
9228 if (which_alternative != 0)
9229 return "#";
9230 else if (get_attr_length (insn) == 4)
9231 return "brct\t%1,%l0";
9232 else
9233 return "ahi\t%1,-1\;jgne\t%l0";
9234 }
9235 "&& reload_completed
9236 && (! REG_P (operands[2])
9237 || ! rtx_equal_p (operands[1], operands[2]))"
9238 [(set (match_dup 3) (match_dup 1))
9239 (parallel [(set (reg:CCAN CC_REGNUM)
9240 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9241 (const_int 0)))
9242 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9243 (set (match_dup 2) (match_dup 3))
9244 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9245 (label_ref (match_dup 0))
9246 (pc)))]
9247 ""
9248 [(set_attr "op_type" "RI")
9249 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9250 ; hurt us in the (rare) case of ahi.
9251 (set_attr "z10prop" "z10_super_E1")
9252 (set_attr "type" "branch")
9253 (set (attr "length")
9254 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9255 (const_int 4) (const_int 10)))])
9256
9257 (define_insn_and_split "doloop_si31"
9258 [(set (pc)
9259 (if_then_else
9260 (ne (match_operand:SI 1 "register_operand" "d,d,d")
9261 (const_int 1))
9262 (label_ref (match_operand 0 "" ""))
9263 (pc)))
9264 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
9265 (plus:SI (match_dup 1) (const_int -1)))
9266 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
9267 (clobber (reg:CC CC_REGNUM))]
9268 "!TARGET_CPU_ZARCH"
9269 {
9270 if (which_alternative != 0)
9271 return "#";
9272 else if (get_attr_length (insn) == 4)
9273 return "brct\t%1,%l0";
9274 else
9275 gcc_unreachable ();
9276 }
9277 "&& reload_completed
9278 && (! REG_P (operands[2])
9279 || ! rtx_equal_p (operands[1], operands[2]))"
9280 [(set (match_dup 3) (match_dup 1))
9281 (parallel [(set (reg:CCAN CC_REGNUM)
9282 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
9283 (const_int 0)))
9284 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
9285 (set (match_dup 2) (match_dup 3))
9286 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9287 (label_ref (match_dup 0))
9288 (pc)))]
9289 ""
9290 [(set_attr "op_type" "RI")
9291 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9292 ; hurt us in the (rare) case of ahi.
9293 (set_attr "z10prop" "z10_super_E1")
9294 (set_attr "type" "branch")
9295 (set (attr "length")
9296 (if_then_else (not (match_test "flag_pic"))
9297 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9298 (const_int 4) (const_int 6))
9299 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9300 (const_int 4) (const_int 8))))])
9301
9302 (define_insn "*doloop_si_long"
9303 [(set (pc)
9304 (if_then_else
9305 (ne (match_operand:SI 1 "register_operand" "d")
9306 (const_int 1))
9307 (match_operand 0 "address_operand" "ZR")
9308 (pc)))
9309 (set (match_operand:SI 2 "register_operand" "=1")
9310 (plus:SI (match_dup 1) (const_int -1)))
9311 (clobber (match_scratch:SI 3 "=X"))
9312 (clobber (reg:CC CC_REGNUM))]
9313 "!TARGET_CPU_ZARCH"
9314 {
9315 if (get_attr_op_type (insn) == OP_TYPE_RR)
9316 return "bctr\t%1,%0";
9317 else
9318 return "bct\t%1,%a0";
9319 }
9320 [(set (attr "op_type")
9321 (if_then_else (match_operand 0 "register_operand" "")
9322 (const_string "RR") (const_string "RX")))
9323 (set_attr "type" "branch")
9324 (set_attr "atype" "agen")
9325 (set_attr "z10prop" "z10_c")
9326 (set_attr "z196prop" "z196_cracked")])
9327
9328 (define_insn_and_split "doloop_di"
9329 [(set (pc)
9330 (if_then_else
9331 (ne (match_operand:DI 1 "register_operand" "d,d,d")
9332 (const_int 1))
9333 (label_ref (match_operand 0 "" ""))
9334 (pc)))
9335 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
9336 (plus:DI (match_dup 1) (const_int -1)))
9337 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
9338 (clobber (reg:CC CC_REGNUM))]
9339 "TARGET_ZARCH"
9340 {
9341 if (which_alternative != 0)
9342 return "#";
9343 else if (get_attr_length (insn) == 4)
9344 return "brctg\t%1,%l0";
9345 else
9346 return "aghi\t%1,-1\;jgne\t%l0";
9347 }
9348 "&& reload_completed
9349 && (! REG_P (operands[2])
9350 || ! rtx_equal_p (operands[1], operands[2]))"
9351 [(set (match_dup 3) (match_dup 1))
9352 (parallel [(set (reg:CCAN CC_REGNUM)
9353 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
9354 (const_int 0)))
9355 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
9356 (set (match_dup 2) (match_dup 3))
9357 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
9358 (label_ref (match_dup 0))
9359 (pc)))]
9360 ""
9361 [(set_attr "op_type" "RI")
9362 ; Strictly speaking, the z10 properties are valid for brct only, however, it does not
9363 ; hurt us in the (rare) case of ahi.
9364 (set_attr "z10prop" "z10_super_E1")
9365 (set_attr "type" "branch")
9366 (set (attr "length")
9367 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9368 (const_int 4) (const_int 10)))])
9369
9370 ;;
9371 ;;- Unconditional jump instructions.
9372 ;;
9373
9374 ;
9375 ; jump instruction pattern(s).
9376 ;
9377
9378 (define_expand "jump"
9379 [(match_operand 0 "" "")]
9380 ""
9381 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
9382
9383 (define_insn "*jump64"
9384 [(set (pc) (label_ref (match_operand 0 "" "")))]
9385 "TARGET_CPU_ZARCH"
9386 {
9387 if (get_attr_length (insn) == 4)
9388 return "j\t%l0";
9389 else
9390 return "jg\t%l0";
9391 }
9392 [(set_attr "op_type" "RI")
9393 (set_attr "type" "branch")
9394 (set (attr "length")
9395 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9396 (const_int 4) (const_int 6)))])
9397
9398 (define_insn "*jump31"
9399 [(set (pc) (label_ref (match_operand 0 "" "")))]
9400 "!TARGET_CPU_ZARCH"
9401 {
9402 gcc_assert (get_attr_length (insn) == 4);
9403 return "j\t%l0";
9404 }
9405 [(set_attr "op_type" "RI")
9406 (set_attr "type" "branch")
9407 (set (attr "length")
9408 (if_then_else (not (match_test "flag_pic"))
9409 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9410 (const_int 4) (const_int 6))
9411 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
9412 (const_int 4) (const_int 8))))])
9413
9414 ;
9415 ; indirect-jump instruction pattern(s).
9416 ;
9417
9418 (define_insn "indirect_jump"
9419 [(set (pc) (match_operand 0 "address_operand" "ZR"))]
9420 ""
9421 {
9422 if (get_attr_op_type (insn) == OP_TYPE_RR)
9423 return "br\t%0";
9424 else
9425 return "b\t%a0";
9426 }
9427 [(set (attr "op_type")
9428 (if_then_else (match_operand 0 "register_operand" "")
9429 (const_string "RR") (const_string "RX")))
9430 (set_attr "type" "branch")
9431 (set_attr "atype" "agen")])
9432
9433 ;
9434 ; casesi instruction pattern(s).
9435 ;
9436
9437 (define_insn "casesi_jump"
9438 [(set (pc) (match_operand 0 "address_operand" "ZR"))
9439 (use (label_ref (match_operand 1 "" "")))]
9440 ""
9441 {
9442 if (get_attr_op_type (insn) == OP_TYPE_RR)
9443 return "br\t%0";
9444 else
9445 return "b\t%a0";
9446 }
9447 [(set (attr "op_type")
9448 (if_then_else (match_operand 0 "register_operand" "")
9449 (const_string "RR") (const_string "RX")))
9450 (set_attr "type" "branch")
9451 (set_attr "atype" "agen")])
9452
9453 (define_expand "casesi"
9454 [(match_operand:SI 0 "general_operand" "")
9455 (match_operand:SI 1 "general_operand" "")
9456 (match_operand:SI 2 "general_operand" "")
9457 (label_ref (match_operand 3 "" ""))
9458 (label_ref (match_operand 4 "" ""))]
9459 ""
9460 {
9461 rtx index = gen_reg_rtx (SImode);
9462 rtx base = gen_reg_rtx (Pmode);
9463 rtx target = gen_reg_rtx (Pmode);
9464
9465 emit_move_insn (index, operands[0]);
9466 emit_insn (gen_subsi3 (index, index, operands[1]));
9467 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
9468 operands[4]);
9469
9470 if (Pmode != SImode)
9471 index = convert_to_mode (Pmode, index, 1);
9472 if (GET_CODE (index) != REG)
9473 index = copy_to_mode_reg (Pmode, index);
9474
9475 if (TARGET_64BIT)
9476 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
9477 else
9478 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
9479
9480 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
9481
9482 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
9483 emit_move_insn (target, index);
9484
9485 if (flag_pic)
9486 target = gen_rtx_PLUS (Pmode, base, target);
9487 emit_jump_insn (gen_casesi_jump (target, operands[3]));
9488
9489 DONE;
9490 })
9491
9492
9493 ;;
9494 ;;- Jump to subroutine.
9495 ;;
9496 ;;
9497
9498 ;
9499 ; untyped call instruction pattern(s).
9500 ;
9501
9502 ;; Call subroutine returning any type.
9503 (define_expand "untyped_call"
9504 [(parallel [(call (match_operand 0 "" "")
9505 (const_int 0))
9506 (match_operand 1 "" "")
9507 (match_operand 2 "" "")])]
9508 ""
9509 {
9510 int i;
9511
9512 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
9513
9514 for (i = 0; i < XVECLEN (operands[2], 0); i++)
9515 {
9516 rtx set = XVECEXP (operands[2], 0, i);
9517 emit_move_insn (SET_DEST (set), SET_SRC (set));
9518 }
9519
9520 /* The optimizer does not know that the call sets the function value
9521 registers we stored in the result block. We avoid problems by
9522 claiming that all hard registers are used and clobbered at this
9523 point. */
9524 emit_insn (gen_blockage ());
9525
9526 DONE;
9527 })
9528
9529 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
9530 ;; all of memory. This blocks insns from being moved across this point.
9531
9532 (define_insn "blockage"
9533 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
9534 ""
9535 ""
9536 [(set_attr "type" "none")
9537 (set_attr "length" "0")])
9538
9539 ;
9540 ; sibcall patterns
9541 ;
9542
9543 (define_expand "sibcall"
9544 [(call (match_operand 0 "" "")
9545 (match_operand 1 "" ""))]
9546 ""
9547 {
9548 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
9549 DONE;
9550 })
9551
9552 (define_insn "*sibcall_br"
9553 [(call (mem:QI (reg SIBCALL_REGNUM))
9554 (match_operand 0 "const_int_operand" "n"))]
9555 "SIBLING_CALL_P (insn)
9556 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
9557 "br\t%%r1"
9558 [(set_attr "op_type" "RR")
9559 (set_attr "type" "branch")
9560 (set_attr "atype" "agen")])
9561
9562 (define_insn "*sibcall_brc"
9563 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9564 (match_operand 1 "const_int_operand" "n"))]
9565 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9566 "j\t%0"
9567 [(set_attr "op_type" "RI")
9568 (set_attr "type" "branch")])
9569
9570 (define_insn "*sibcall_brcl"
9571 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9572 (match_operand 1 "const_int_operand" "n"))]
9573 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9574 "jg\t%0"
9575 [(set_attr "op_type" "RIL")
9576 (set_attr "type" "branch")])
9577
9578 ;
9579 ; sibcall_value patterns
9580 ;
9581
9582 (define_expand "sibcall_value"
9583 [(set (match_operand 0 "" "")
9584 (call (match_operand 1 "" "")
9585 (match_operand 2 "" "")))]
9586 ""
9587 {
9588 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
9589 DONE;
9590 })
9591
9592 (define_insn "*sibcall_value_br"
9593 [(set (match_operand 0 "" "")
9594 (call (mem:QI (reg SIBCALL_REGNUM))
9595 (match_operand 1 "const_int_operand" "n")))]
9596 "SIBLING_CALL_P (insn)
9597 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
9598 "br\t%%r1"
9599 [(set_attr "op_type" "RR")
9600 (set_attr "type" "branch")
9601 (set_attr "atype" "agen")])
9602
9603 (define_insn "*sibcall_value_brc"
9604 [(set (match_operand 0 "" "")
9605 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9606 (match_operand 2 "const_int_operand" "n")))]
9607 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
9608 "j\t%1"
9609 [(set_attr "op_type" "RI")
9610 (set_attr "type" "branch")])
9611
9612 (define_insn "*sibcall_value_brcl"
9613 [(set (match_operand 0 "" "")
9614 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9615 (match_operand 2 "const_int_operand" "n")))]
9616 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
9617 "jg\t%1"
9618 [(set_attr "op_type" "RIL")
9619 (set_attr "type" "branch")])
9620
9621
9622 ;
9623 ; call instruction pattern(s).
9624 ;
9625
9626 (define_expand "call"
9627 [(call (match_operand 0 "" "")
9628 (match_operand 1 "" ""))
9629 (use (match_operand 2 "" ""))]
9630 ""
9631 {
9632 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
9633 gen_rtx_REG (Pmode, RETURN_REGNUM));
9634 DONE;
9635 })
9636
9637 (define_insn "*bras"
9638 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9639 (match_operand 1 "const_int_operand" "n"))
9640 (clobber (match_operand 2 "register_operand" "=r"))]
9641 "!SIBLING_CALL_P (insn)
9642 && TARGET_SMALL_EXEC
9643 && GET_MODE (operands[2]) == Pmode"
9644 "bras\t%2,%0"
9645 [(set_attr "op_type" "RI")
9646 (set_attr "type" "jsr")
9647 (set_attr "z196prop" "z196_cracked")])
9648
9649 (define_insn "*brasl"
9650 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
9651 (match_operand 1 "const_int_operand" "n"))
9652 (clobber (match_operand 2 "register_operand" "=r"))]
9653 "!SIBLING_CALL_P (insn)
9654 && TARGET_CPU_ZARCH
9655 && GET_MODE (operands[2]) == Pmode"
9656 "brasl\t%2,%0"
9657 [(set_attr "op_type" "RIL")
9658 (set_attr "type" "jsr")
9659 (set_attr "z196prop" "z196_cracked")])
9660
9661 (define_insn "*basr"
9662 [(call (mem:QI (match_operand 0 "address_operand" "ZR"))
9663 (match_operand 1 "const_int_operand" "n"))
9664 (clobber (match_operand 2 "register_operand" "=r"))]
9665 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
9666 {
9667 if (get_attr_op_type (insn) == OP_TYPE_RR)
9668 return "basr\t%2,%0";
9669 else
9670 return "bas\t%2,%a0";
9671 }
9672 [(set (attr "op_type")
9673 (if_then_else (match_operand 0 "register_operand" "")
9674 (const_string "RR") (const_string "RX")))
9675 (set_attr "type" "jsr")
9676 (set_attr "atype" "agen")
9677 (set_attr "z196prop" "z196_cracked")])
9678
9679 ;
9680 ; call_value instruction pattern(s).
9681 ;
9682
9683 (define_expand "call_value"
9684 [(set (match_operand 0 "" "")
9685 (call (match_operand 1 "" "")
9686 (match_operand 2 "" "")))
9687 (use (match_operand 3 "" ""))]
9688 ""
9689 {
9690 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
9691 gen_rtx_REG (Pmode, RETURN_REGNUM));
9692 DONE;
9693 })
9694
9695 (define_insn "*bras_r"
9696 [(set (match_operand 0 "" "")
9697 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9698 (match_operand:SI 2 "const_int_operand" "n")))
9699 (clobber (match_operand 3 "register_operand" "=r"))]
9700 "!SIBLING_CALL_P (insn)
9701 && TARGET_SMALL_EXEC
9702 && GET_MODE (operands[3]) == Pmode"
9703 "bras\t%3,%1"
9704 [(set_attr "op_type" "RI")
9705 (set_attr "type" "jsr")
9706 (set_attr "z196prop" "z196_cracked")])
9707
9708 (define_insn "*brasl_r"
9709 [(set (match_operand 0 "" "")
9710 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9711 (match_operand 2 "const_int_operand" "n")))
9712 (clobber (match_operand 3 "register_operand" "=r"))]
9713 "!SIBLING_CALL_P (insn)
9714 && TARGET_CPU_ZARCH
9715 && GET_MODE (operands[3]) == Pmode"
9716 "brasl\t%3,%1"
9717 [(set_attr "op_type" "RIL")
9718 (set_attr "type" "jsr")
9719 (set_attr "z196prop" "z196_cracked")])
9720
9721 (define_insn "*basr_r"
9722 [(set (match_operand 0 "" "")
9723 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9724 (match_operand 2 "const_int_operand" "n")))
9725 (clobber (match_operand 3 "register_operand" "=r"))]
9726 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9727 {
9728 if (get_attr_op_type (insn) == OP_TYPE_RR)
9729 return "basr\t%3,%1";
9730 else
9731 return "bas\t%3,%a1";
9732 }
9733 [(set (attr "op_type")
9734 (if_then_else (match_operand 1 "register_operand" "")
9735 (const_string "RR") (const_string "RX")))
9736 (set_attr "type" "jsr")
9737 (set_attr "atype" "agen")
9738 (set_attr "z196prop" "z196_cracked")])
9739
9740 ;;
9741 ;;- Thread-local storage support.
9742 ;;
9743
9744 (define_expand "get_thread_pointer<mode>"
9745 [(set (match_operand:P 0 "nonimmediate_operand" "") (reg:P TP_REGNUM))]
9746 ""
9747 "")
9748
9749 (define_expand "set_thread_pointer<mode>"
9750 [(set (reg:P TP_REGNUM) (match_operand:P 0 "nonimmediate_operand" ""))
9751 (set (reg:P TP_REGNUM) (unspec_volatile:P [(reg:P TP_REGNUM)] UNSPECV_SET_TP))]
9752 ""
9753 "")
9754
9755 (define_insn "*set_tp"
9756 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
9757 ""
9758 ""
9759 [(set_attr "type" "none")
9760 (set_attr "length" "0")])
9761
9762 (define_insn "*tls_load_64"
9763 [(set (match_operand:DI 0 "register_operand" "=d")
9764 (unspec:DI [(match_operand:DI 1 "memory_operand" "T")
9765 (match_operand:DI 2 "" "")]
9766 UNSPEC_TLS_LOAD))]
9767 "TARGET_64BIT"
9768 "lg\t%0,%1%J2"
9769 [(set_attr "op_type" "RXE")
9770 (set_attr "z10prop" "z10_fwd_A3")])
9771
9772 (define_insn "*tls_load_31"
9773 [(set (match_operand:SI 0 "register_operand" "=d,d")
9774 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
9775 (match_operand:SI 2 "" "")]
9776 UNSPEC_TLS_LOAD))]
9777 "!TARGET_64BIT"
9778 "@
9779 l\t%0,%1%J2
9780 ly\t%0,%1%J2"
9781 [(set_attr "op_type" "RX,RXY")
9782 (set_attr "type" "load")
9783 (set_attr "cpu_facility" "*,longdisp")
9784 (set_attr "z10prop" "z10_fwd_A3,z10_fwd_A3")])
9785
9786 (define_insn "*bras_tls"
9787 [(set (match_operand 0 "" "")
9788 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9789 (match_operand 2 "const_int_operand" "n")))
9790 (clobber (match_operand 3 "register_operand" "=r"))
9791 (use (match_operand 4 "" ""))]
9792 "!SIBLING_CALL_P (insn)
9793 && TARGET_SMALL_EXEC
9794 && GET_MODE (operands[3]) == Pmode"
9795 "bras\t%3,%1%J4"
9796 [(set_attr "op_type" "RI")
9797 (set_attr "type" "jsr")
9798 (set_attr "z196prop" "z196_cracked")])
9799
9800 (define_insn "*brasl_tls"
9801 [(set (match_operand 0 "" "")
9802 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
9803 (match_operand 2 "const_int_operand" "n")))
9804 (clobber (match_operand 3 "register_operand" "=r"))
9805 (use (match_operand 4 "" ""))]
9806 "!SIBLING_CALL_P (insn)
9807 && TARGET_CPU_ZARCH
9808 && GET_MODE (operands[3]) == Pmode"
9809 "brasl\t%3,%1%J4"
9810 [(set_attr "op_type" "RIL")
9811 (set_attr "type" "jsr")
9812 (set_attr "z196prop" "z196_cracked")])
9813
9814 (define_insn "*basr_tls"
9815 [(set (match_operand 0 "" "")
9816 (call (mem:QI (match_operand 1 "address_operand" "ZR"))
9817 (match_operand 2 "const_int_operand" "n")))
9818 (clobber (match_operand 3 "register_operand" "=r"))
9819 (use (match_operand 4 "" ""))]
9820 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
9821 {
9822 if (get_attr_op_type (insn) == OP_TYPE_RR)
9823 return "basr\t%3,%1%J4";
9824 else
9825 return "bas\t%3,%a1%J4";
9826 }
9827 [(set (attr "op_type")
9828 (if_then_else (match_operand 1 "register_operand" "")
9829 (const_string "RR") (const_string "RX")))
9830 (set_attr "type" "jsr")
9831 (set_attr "atype" "agen")
9832 (set_attr "z196prop" "z196_cracked")])
9833
9834 ;;
9835 ;;- Atomic operations
9836 ;;
9837
9838 ;
9839 ; memory barrier patterns.
9840 ;
9841
9842 (define_expand "mem_signal_fence"
9843 [(match_operand:SI 0 "const_int_operand")] ;; model
9844 ""
9845 {
9846 /* The s390 memory model is strong enough not to require any
9847 barrier in order to synchronize a thread with itself. */
9848 DONE;
9849 })
9850
9851 (define_expand "mem_thread_fence"
9852 [(match_operand:SI 0 "const_int_operand")] ;; model
9853 ""
9854 {
9855 /* Unless this is a SEQ_CST fence, the s390 memory model is strong
9856 enough not to require barriers of any kind. */
9857 if (is_mm_seq_cst (memmodel_from_int (INTVAL (operands[0]))))
9858 {
9859 rtx mem = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
9860 MEM_VOLATILE_P (mem) = 1;
9861 emit_insn (gen_mem_thread_fence_1 (mem));
9862 }
9863 DONE;
9864 })
9865
9866 ; Although bcr is superscalar on Z10, this variant will never
9867 ; become part of an execution group.
9868 ; With z196 we can make use of the fast-BCR-serialization facility.
9869 ; This allows for a slightly faster sync which is sufficient for our
9870 ; purposes.
9871 (define_insn "mem_thread_fence_1"
9872 [(set (match_operand:BLK 0 "" "")
9873 (unspec:BLK [(match_dup 0)] UNSPEC_MB))]
9874 ""
9875 {
9876 if (TARGET_Z196)
9877 return "bcr\t14,0";
9878 else
9879 return "bcr\t15,0";
9880 }
9881 [(set_attr "op_type" "RR")
9882 (set_attr "mnemonic" "bcr_flush")
9883 (set_attr "z196prop" "z196_alone")])
9884
9885 ;
9886 ; atomic load/store operations
9887 ;
9888
9889 ; Atomic loads need not examine the memory model at all.
9890 (define_expand "atomic_load<mode>"
9891 [(match_operand:DINT 0 "register_operand") ;; output
9892 (match_operand:DINT 1 "memory_operand") ;; memory
9893 (match_operand:SI 2 "const_int_operand")] ;; model
9894 ""
9895 {
9896 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
9897 FAIL;
9898
9899 if (<MODE>mode == TImode)
9900 emit_insn (gen_atomic_loadti_1 (operands[0], operands[1]));
9901 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9902 emit_insn (gen_atomic_loaddi_1 (operands[0], operands[1]));
9903 else
9904 emit_move_insn (operands[0], operands[1]);
9905 DONE;
9906 })
9907
9908 ; Different from movdi_31 in that we want no splitters.
9909 (define_insn "atomic_loaddi_1"
9910 [(set (match_operand:DI 0 "register_operand" "=d,d,!*f,!*f")
9911 (unspec:DI [(match_operand:DI 1 "memory_operand" "Q,S,R,T")]
9912 UNSPEC_MOVA))]
9913 "!TARGET_ZARCH"
9914 "@
9915 lm\t%0,%M0,%S1
9916 lmy\t%0,%M0,%S1
9917 ld\t%0,%1
9918 ldy\t%0,%1"
9919 [(set_attr "op_type" "RS,RSY,RS,RSY")
9920 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9921 (set_attr "type" "lm,lm,floaddf,floaddf")])
9922
9923 (define_insn "atomic_loadti_1"
9924 [(set (match_operand:TI 0 "register_operand" "=r")
9925 (unspec:TI [(match_operand:TI 1 "memory_operand" "T")]
9926 UNSPEC_MOVA))]
9927 "TARGET_ZARCH"
9928 "lpq\t%0,%1"
9929 [(set_attr "op_type" "RXY")
9930 (set_attr "type" "other")])
9931
9932 ; Atomic stores must(?) enforce sequential consistency.
9933 (define_expand "atomic_store<mode>"
9934 [(match_operand:DINT 0 "memory_operand") ;; memory
9935 (match_operand:DINT 1 "register_operand") ;; input
9936 (match_operand:SI 2 "const_int_operand")] ;; model
9937 ""
9938 {
9939 enum memmodel model = memmodel_from_int (INTVAL (operands[2]));
9940
9941 if (MEM_ALIGN (operands[0]) < GET_MODE_BITSIZE (GET_MODE (operands[0])))
9942 FAIL;
9943
9944 if (<MODE>mode == TImode)
9945 emit_insn (gen_atomic_storeti_1 (operands[0], operands[1]));
9946 else if (<MODE>mode == DImode && !TARGET_ZARCH)
9947 emit_insn (gen_atomic_storedi_1 (operands[0], operands[1]));
9948 else
9949 emit_move_insn (operands[0], operands[1]);
9950 if (is_mm_seq_cst (model))
9951 emit_insn (gen_mem_thread_fence (operands[2]));
9952 DONE;
9953 })
9954
9955 ; Different from movdi_31 in that we want no splitters.
9956 (define_insn "atomic_storedi_1"
9957 [(set (match_operand:DI 0 "memory_operand" "=Q,S,R,T")
9958 (unspec:DI [(match_operand:DI 1 "register_operand" "d,d,!*f,!*f")]
9959 UNSPEC_MOVA))]
9960 "!TARGET_ZARCH"
9961 "@
9962 stm\t%1,%N1,%S0
9963 stmy\t%1,%N1,%S0
9964 std %1,%0
9965 stdy %1,%0"
9966 [(set_attr "op_type" "RS,RSY,RS,RSY")
9967 (set_attr "cpu_facility" "*,longdisp,*,longdisp")
9968 (set_attr "type" "stm,stm,fstoredf,fstoredf")])
9969
9970 (define_insn "atomic_storeti_1"
9971 [(set (match_operand:TI 0 "memory_operand" "=T")
9972 (unspec:TI [(match_operand:TI 1 "register_operand" "r")]
9973 UNSPEC_MOVA))]
9974 "TARGET_ZARCH"
9975 "stpq\t%1,%0"
9976 [(set_attr "op_type" "RXY")
9977 (set_attr "type" "other")])
9978
9979 ;
9980 ; compare and swap patterns.
9981 ;
9982
9983 (define_expand "atomic_compare_and_swap<mode>"
9984 [(match_operand:SI 0 "register_operand") ;; bool success output
9985 (match_operand:DGPR 1 "nonimmediate_operand");; oldval output
9986 (match_operand:DGPR 2 "memory_operand") ;; memory
9987 (match_operand:DGPR 3 "register_operand") ;; expected intput
9988 (match_operand:DGPR 4 "register_operand") ;; newval intput
9989 (match_operand:SI 5 "const_int_operand") ;; is_weak
9990 (match_operand:SI 6 "const_int_operand") ;; success model
9991 (match_operand:SI 7 "const_int_operand")] ;; failure model
9992 ""
9993 {
9994 rtx cc, cmp, output = operands[1];
9995
9996 if (!register_operand (output, <MODE>mode))
9997 output = gen_reg_rtx (<MODE>mode);
9998
9999 if (MEM_ALIGN (operands[2]) < GET_MODE_BITSIZE (GET_MODE (operands[2])))
10000 FAIL;
10001
10002 emit_insn (gen_atomic_compare_and_swap<mode>_internal
10003 (output, operands[2], operands[3], operands[4]));
10004
10005 /* We deliberately accept non-register operands in the predicate
10006 to ensure the write back to the output operand happens *before*
10007 the store-flags code below. This makes it easier for combine
10008 to merge the store-flags code with a potential test-and-branch
10009 pattern following (immediately!) afterwards. */
10010 if (output != operands[1])
10011 emit_move_insn (operands[1], output);
10012
10013 cc = gen_rtx_REG (CCZ1mode, CC_REGNUM);
10014 cmp = gen_rtx_EQ (SImode, cc, const0_rtx);
10015 emit_insn (gen_cstorecc4 (operands[0], cmp, cc, const0_rtx));
10016 DONE;
10017 })
10018
10019 (define_expand "atomic_compare_and_swap<mode>"
10020 [(match_operand:SI 0 "register_operand") ;; bool success output
10021 (match_operand:HQI 1 "nonimmediate_operand") ;; oldval output
10022 (match_operand:HQI 2 "memory_operand") ;; memory
10023 (match_operand:HQI 3 "general_operand") ;; expected intput
10024 (match_operand:HQI 4 "general_operand") ;; newval intput
10025 (match_operand:SI 5 "const_int_operand") ;; is_weak
10026 (match_operand:SI 6 "const_int_operand") ;; success model
10027 (match_operand:SI 7 "const_int_operand")] ;; failure model
10028 ""
10029 {
10030 s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1], operands[2],
10031 operands[3], operands[4], INTVAL (operands[5]));
10032 DONE;
10033 })
10034
10035 (define_expand "atomic_compare_and_swap<mode>_internal"
10036 [(parallel
10037 [(set (match_operand:DGPR 0 "register_operand")
10038 (match_operand:DGPR 1 "memory_operand"))
10039 (set (match_dup 1)
10040 (unspec_volatile:DGPR
10041 [(match_dup 1)
10042 (match_operand:DGPR 2 "register_operand")
10043 (match_operand:DGPR 3 "register_operand")]
10044 UNSPECV_CAS))
10045 (set (reg:CCZ1 CC_REGNUM)
10046 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
10047 "")
10048
10049 ; cdsg, csg
10050 (define_insn "*atomic_compare_and_swap<mode>_1"
10051 [(set (match_operand:TDI 0 "register_operand" "=r")
10052 (match_operand:TDI 1 "memory_operand" "+S"))
10053 (set (match_dup 1)
10054 (unspec_volatile:TDI
10055 [(match_dup 1)
10056 (match_operand:TDI 2 "register_operand" "0")
10057 (match_operand:TDI 3 "register_operand" "r")]
10058 UNSPECV_CAS))
10059 (set (reg:CCZ1 CC_REGNUM)
10060 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10061 "TARGET_ZARCH"
10062 "c<td>sg\t%0,%3,%S1"
10063 [(set_attr "op_type" "RSY")
10064 (set_attr "type" "sem")])
10065
10066 ; cds, cdsy
10067 (define_insn "*atomic_compare_and_swapdi_2"
10068 [(set (match_operand:DI 0 "register_operand" "=r,r")
10069 (match_operand:DI 1 "memory_operand" "+Q,S"))
10070 (set (match_dup 1)
10071 (unspec_volatile:DI
10072 [(match_dup 1)
10073 (match_operand:DI 2 "register_operand" "0,0")
10074 (match_operand:DI 3 "register_operand" "r,r")]
10075 UNSPECV_CAS))
10076 (set (reg:CCZ1 CC_REGNUM)
10077 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10078 "!TARGET_ZARCH"
10079 "@
10080 cds\t%0,%3,%S1
10081 cdsy\t%0,%3,%S1"
10082 [(set_attr "op_type" "RS,RSY")
10083 (set_attr "cpu_facility" "*,longdisp")
10084 (set_attr "type" "sem")])
10085
10086 ; cs, csy
10087 (define_insn "*atomic_compare_and_swapsi_3"
10088 [(set (match_operand:SI 0 "register_operand" "=r,r")
10089 (match_operand:SI 1 "memory_operand" "+Q,S"))
10090 (set (match_dup 1)
10091 (unspec_volatile:SI
10092 [(match_dup 1)
10093 (match_operand:SI 2 "register_operand" "0,0")
10094 (match_operand:SI 3 "register_operand" "r,r")]
10095 UNSPECV_CAS))
10096 (set (reg:CCZ1 CC_REGNUM)
10097 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
10098 ""
10099 "@
10100 cs\t%0,%3,%S1
10101 csy\t%0,%3,%S1"
10102 [(set_attr "op_type" "RS,RSY")
10103 (set_attr "cpu_facility" "*,longdisp")
10104 (set_attr "type" "sem")])
10105
10106 ;
10107 ; Other atomic instruction patterns.
10108 ;
10109
10110 ; z196 load and add, xor, or and and instructions
10111
10112 (define_expand "atomic_fetch_<atomic><mode>"
10113 [(match_operand:GPR 0 "register_operand") ;; val out
10114 (ATOMIC_Z196:GPR
10115 (match_operand:GPR 1 "memory_operand") ;; memory
10116 (match_operand:GPR 2 "register_operand")) ;; val in
10117 (match_operand:SI 3 "const_int_operand")] ;; model
10118 "TARGET_Z196"
10119 {
10120 if (MEM_ALIGN (operands[1]) < GET_MODE_BITSIZE (GET_MODE (operands[1])))
10121 FAIL;
10122
10123 emit_insn (gen_atomic_fetch_<atomic><mode>_iaf
10124 (operands[0], operands[1], operands[2]));
10125 DONE;
10126 })
10127
10128 ; lan, lang, lao, laog, lax, laxg, laa, laag
10129 (define_insn "atomic_fetch_<atomic><mode>_iaf"
10130 [(set (match_operand:GPR 0 "register_operand" "=d")
10131 (match_operand:GPR 1 "memory_operand" "+S"))
10132 (set (match_dup 1)
10133 (unspec_volatile:GPR
10134 [(ATOMIC_Z196:GPR (match_dup 1)
10135 (match_operand:GPR 2 "general_operand" "d"))]
10136 UNSPECV_ATOMIC_OP))
10137 (clobber (reg:CC CC_REGNUM))]
10138 "TARGET_Z196"
10139 "la<noxa><g>\t%0,%2,%1"
10140 [(set_attr "op_type" "RSY")
10141 (set_attr "type" "sem")])
10142
10143 ;; For SImode and larger, the optabs.c code will do just fine in
10144 ;; expanding a compare-and-swap loop. For QI/HImode, we can do
10145 ;; better by expanding our own loop.
10146
10147 (define_expand "atomic_<atomic><mode>"
10148 [(ATOMIC:HQI
10149 (match_operand:HQI 0 "memory_operand") ;; memory
10150 (match_operand:HQI 1 "general_operand")) ;; val in
10151 (match_operand:SI 2 "const_int_operand")] ;; model
10152 ""
10153 {
10154 s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
10155 operands[1], false);
10156 DONE;
10157 })
10158
10159 (define_expand "atomic_fetch_<atomic><mode>"
10160 [(match_operand:HQI 0 "register_operand") ;; val out
10161 (ATOMIC:HQI
10162 (match_operand:HQI 1 "memory_operand") ;; memory
10163 (match_operand:HQI 2 "general_operand")) ;; val in
10164 (match_operand:SI 3 "const_int_operand")] ;; model
10165 ""
10166 {
10167 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10168 operands[2], false);
10169 DONE;
10170 })
10171
10172 (define_expand "atomic_<atomic>_fetch<mode>"
10173 [(match_operand:HQI 0 "register_operand") ;; val out
10174 (ATOMIC:HQI
10175 (match_operand:HQI 1 "memory_operand") ;; memory
10176 (match_operand:HQI 2 "general_operand")) ;; val in
10177 (match_operand:SI 3 "const_int_operand")] ;; model
10178 ""
10179 {
10180 s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
10181 operands[2], true);
10182 DONE;
10183 })
10184
10185 (define_expand "atomic_exchange<mode>"
10186 [(match_operand:HQI 0 "register_operand") ;; val out
10187 (match_operand:HQI 1 "memory_operand") ;; memory
10188 (match_operand:HQI 2 "general_operand") ;; val in
10189 (match_operand:SI 3 "const_int_operand")] ;; model
10190 ""
10191 {
10192 s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
10193 operands[2], false);
10194 DONE;
10195 })
10196
10197 ;;
10198 ;;- Miscellaneous instructions.
10199 ;;
10200
10201 ;
10202 ; allocate stack instruction pattern(s).
10203 ;
10204
10205 (define_expand "allocate_stack"
10206 [(match_operand 0 "general_operand" "")
10207 (match_operand 1 "general_operand" "")]
10208 "TARGET_BACKCHAIN"
10209 {
10210 rtx temp = gen_reg_rtx (Pmode);
10211
10212 emit_move_insn (temp, s390_back_chain_rtx ());
10213 anti_adjust_stack (operands[1]);
10214 emit_move_insn (s390_back_chain_rtx (), temp);
10215
10216 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
10217 DONE;
10218 })
10219
10220
10221 ;
10222 ; setjmp instruction pattern.
10223 ;
10224
10225 (define_expand "builtin_setjmp_receiver"
10226 [(match_operand 0 "" "")]
10227 "flag_pic"
10228 {
10229 emit_insn (s390_load_got ());
10230 emit_use (pic_offset_table_rtx);
10231 DONE;
10232 })
10233
10234 ;; These patterns say how to save and restore the stack pointer. We need not
10235 ;; save the stack pointer at function level since we are careful to
10236 ;; preserve the backchain. At block level, we have to restore the backchain
10237 ;; when we restore the stack pointer.
10238 ;;
10239 ;; For nonlocal gotos, we must save both the stack pointer and its
10240 ;; backchain and restore both. Note that in the nonlocal case, the
10241 ;; save area is a memory location.
10242
10243 (define_expand "save_stack_function"
10244 [(match_operand 0 "general_operand" "")
10245 (match_operand 1 "general_operand" "")]
10246 ""
10247 "DONE;")
10248
10249 (define_expand "restore_stack_function"
10250 [(match_operand 0 "general_operand" "")
10251 (match_operand 1 "general_operand" "")]
10252 ""
10253 "DONE;")
10254
10255 (define_expand "restore_stack_block"
10256 [(match_operand 0 "register_operand" "")
10257 (match_operand 1 "register_operand" "")]
10258 "TARGET_BACKCHAIN"
10259 {
10260 rtx temp = gen_reg_rtx (Pmode);
10261
10262 emit_move_insn (temp, s390_back_chain_rtx ());
10263 emit_move_insn (operands[0], operands[1]);
10264 emit_move_insn (s390_back_chain_rtx (), temp);
10265
10266 DONE;
10267 })
10268
10269 (define_expand "save_stack_nonlocal"
10270 [(match_operand 0 "memory_operand" "")
10271 (match_operand 1 "register_operand" "")]
10272 ""
10273 {
10274 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10275
10276 /* Copy the backchain to the first word, sp to the second and the
10277 literal pool base to the third. */
10278
10279 rtx save_bc = adjust_address (operands[0], Pmode, 0);
10280 rtx save_sp = adjust_address (operands[0], Pmode, GET_MODE_SIZE (Pmode));
10281 rtx save_bp = adjust_address (operands[0], Pmode, 2 * GET_MODE_SIZE (Pmode));
10282
10283 if (TARGET_BACKCHAIN)
10284 emit_move_insn (save_bc, force_reg (Pmode, s390_back_chain_rtx ()));
10285
10286 emit_move_insn (save_sp, operands[1]);
10287 emit_move_insn (save_bp, base);
10288
10289 DONE;
10290 })
10291
10292 (define_expand "restore_stack_nonlocal"
10293 [(match_operand 0 "register_operand" "")
10294 (match_operand 1 "memory_operand" "")]
10295 ""
10296 {
10297 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
10298 rtx temp = NULL_RTX;
10299
10300 /* Restore the backchain from the first word, sp from the second and the
10301 literal pool base from the third. */
10302
10303 rtx save_bc = adjust_address (operands[1], Pmode, 0);
10304 rtx save_sp = adjust_address (operands[1], Pmode, GET_MODE_SIZE (Pmode));
10305 rtx save_bp = adjust_address (operands[1], Pmode, 2 * GET_MODE_SIZE (Pmode));
10306
10307 if (TARGET_BACKCHAIN)
10308 temp = force_reg (Pmode, save_bc);
10309
10310 emit_move_insn (base, save_bp);
10311 emit_move_insn (operands[0], save_sp);
10312
10313 if (temp)
10314 emit_move_insn (s390_back_chain_rtx (), temp);
10315
10316 emit_use (base);
10317 DONE;
10318 })
10319
10320 (define_expand "exception_receiver"
10321 [(const_int 0)]
10322 ""
10323 {
10324 s390_set_has_landing_pad_p (true);
10325 DONE;
10326 })
10327
10328 ;
10329 ; nop instruction pattern(s).
10330 ;
10331
10332 (define_insn "nop"
10333 [(const_int 0)]
10334 ""
10335 "lr\t0,0"
10336 [(set_attr "op_type" "RR")
10337 (set_attr "z10prop" "z10_fr_E1")])
10338
10339 (define_insn "nop1"
10340 [(const_int 1)]
10341 ""
10342 "lr\t1,1"
10343 [(set_attr "op_type" "RR")])
10344
10345 ;;- Undeletable nops (used for hotpatching)
10346
10347 (define_insn "nop_2_byte"
10348 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_2_BYTE)]
10349 ""
10350 "nopr\t%%r7"
10351 [(set_attr "op_type" "RR")])
10352
10353 (define_insn "nop_4_byte"
10354 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_4_BYTE)]
10355 ""
10356 "nop\t0"
10357 [(set_attr "op_type" "RX")])
10358
10359 (define_insn "nop_6_byte"
10360 [(unspec_volatile [(const_int 0)] UNSPECV_NOP_6_BYTE)]
10361 "TARGET_CPU_ZARCH"
10362 "brcl\t0, 0"
10363 [(set_attr "op_type" "RIL")])
10364
10365
10366 ;
10367 ; Special literal pool access instruction pattern(s).
10368 ;
10369
10370 (define_insn "*pool_entry"
10371 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
10372 UNSPECV_POOL_ENTRY)]
10373 ""
10374 {
10375 machine_mode mode = GET_MODE (PATTERN (insn));
10376 unsigned int align = GET_MODE_BITSIZE (mode);
10377 s390_output_pool_entry (operands[0], mode, align);
10378 return "";
10379 }
10380 [(set (attr "length")
10381 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
10382
10383 (define_insn "pool_align"
10384 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
10385 UNSPECV_POOL_ALIGN)]
10386 ""
10387 ".align\t%0"
10388 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10389
10390 (define_insn "pool_section_start"
10391 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
10392 ""
10393 {
10394 switch_to_section (targetm.asm_out.function_rodata_section
10395 (current_function_decl));
10396 return "";
10397 }
10398 [(set_attr "length" "0")])
10399
10400 (define_insn "pool_section_end"
10401 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
10402 ""
10403 {
10404 switch_to_section (current_function_section ());
10405 return "";
10406 }
10407 [(set_attr "length" "0")])
10408
10409 (define_insn "main_base_31_small"
10410 [(set (match_operand 0 "register_operand" "=a")
10411 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10412 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10413 "basr\t%0,0"
10414 [(set_attr "op_type" "RR")
10415 (set_attr "type" "la")
10416 (set_attr "z196prop" "z196_cracked")])
10417
10418 (define_insn "main_base_31_large"
10419 [(set (match_operand 0 "register_operand" "=a")
10420 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
10421 (set (pc) (label_ref (match_operand 2 "" "")))]
10422 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10423 "bras\t%0,%2"
10424 [(set_attr "op_type" "RI")
10425 (set_attr "z196prop" "z196_cracked")])
10426
10427 (define_insn "main_base_64"
10428 [(set (match_operand 0 "register_operand" "=a")
10429 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
10430 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10431 "larl\t%0,%1"
10432 [(set_attr "op_type" "RIL")
10433 (set_attr "type" "larl")
10434 (set_attr "z10prop" "z10_fwd_A1")])
10435
10436 (define_insn "main_pool"
10437 [(set (match_operand 0 "register_operand" "=a")
10438 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
10439 "GET_MODE (operands[0]) == Pmode"
10440 {
10441 gcc_unreachable ();
10442 }
10443 [(set (attr "type")
10444 (if_then_else (match_test "TARGET_CPU_ZARCH")
10445 (const_string "larl") (const_string "la")))])
10446
10447 (define_insn "reload_base_31"
10448 [(set (match_operand 0 "register_operand" "=a")
10449 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10450 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10451 "basr\t%0,0\;la\t%0,%1-.(%0)"
10452 [(set_attr "length" "6")
10453 (set_attr "type" "la")
10454 (set_attr "z196prop" "z196_cracked")])
10455
10456 (define_insn "reload_base_64"
10457 [(set (match_operand 0 "register_operand" "=a")
10458 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
10459 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
10460 "larl\t%0,%1"
10461 [(set_attr "op_type" "RIL")
10462 (set_attr "type" "larl")
10463 (set_attr "z10prop" "z10_fwd_A1")])
10464
10465 (define_insn "pool"
10466 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
10467 ""
10468 {
10469 gcc_unreachable ();
10470 }
10471 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
10472
10473 ;;
10474 ;; Insns related to generating the function prologue and epilogue.
10475 ;;
10476
10477
10478 (define_expand "prologue"
10479 [(use (const_int 0))]
10480 ""
10481 "s390_emit_prologue (); DONE;")
10482
10483 (define_expand "epilogue"
10484 [(use (const_int 1))]
10485 ""
10486 "s390_emit_epilogue (false); DONE;")
10487
10488 (define_expand "sibcall_epilogue"
10489 [(use (const_int 0))]
10490 ""
10491 "s390_emit_epilogue (true); DONE;")
10492
10493 ;; A direct return instruction, without using an epilogue.
10494 (define_insn "<code>"
10495 [(ANY_RETURN)]
10496 "s390_can_use_<code>_insn ()"
10497 "br\t%%r14"
10498 [(set_attr "op_type" "RR")
10499 (set_attr "type" "jsr")
10500 (set_attr "atype" "agen")])
10501
10502 (define_insn "*return"
10503 [(return)
10504 (use (match_operand 0 "register_operand" "a"))]
10505 "GET_MODE (operands[0]) == Pmode"
10506 "br\t%0"
10507 [(set_attr "op_type" "RR")
10508 (set_attr "type" "jsr")
10509 (set_attr "atype" "agen")])
10510
10511
10512 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
10513 ;; pointer. This is used for compatibility.
10514
10515 (define_expand "ptr_extend"
10516 [(set (match_operand:DI 0 "register_operand" "=r")
10517 (match_operand:SI 1 "register_operand" "r"))]
10518 "TARGET_64BIT"
10519 {
10520 emit_insn (gen_anddi3 (operands[0],
10521 gen_lowpart (DImode, operands[1]),
10522 GEN_INT (0x7fffffff)));
10523 DONE;
10524 })
10525
10526 ;; Instruction definition to expand eh_return macro to support
10527 ;; swapping in special linkage return addresses.
10528
10529 (define_expand "eh_return"
10530 [(use (match_operand 0 "register_operand" ""))]
10531 "TARGET_TPF"
10532 {
10533 s390_emit_tpf_eh_return (operands[0]);
10534 DONE;
10535 })
10536
10537 ;
10538 ; Stack Protector Patterns
10539 ;
10540
10541 (define_expand "stack_protect_set"
10542 [(set (match_operand 0 "memory_operand" "")
10543 (match_operand 1 "memory_operand" ""))]
10544 ""
10545 {
10546 #ifdef TARGET_THREAD_SSP_OFFSET
10547 operands[1]
10548 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10549 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10550 #endif
10551 if (TARGET_64BIT)
10552 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
10553 else
10554 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
10555
10556 DONE;
10557 })
10558
10559 (define_insn "stack_protect_set<mode>"
10560 [(set (match_operand:DSI 0 "memory_operand" "=Q")
10561 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
10562 ""
10563 "mvc\t%O0(%G0,%R0),%S1"
10564 [(set_attr "op_type" "SS")])
10565
10566 (define_expand "stack_protect_test"
10567 [(set (reg:CC CC_REGNUM)
10568 (compare (match_operand 0 "memory_operand" "")
10569 (match_operand 1 "memory_operand" "")))
10570 (match_operand 2 "" "")]
10571 ""
10572 {
10573 rtx cc_reg, test;
10574 #ifdef TARGET_THREAD_SSP_OFFSET
10575 operands[1]
10576 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
10577 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
10578 #endif
10579 if (TARGET_64BIT)
10580 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
10581 else
10582 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
10583
10584 cc_reg = gen_rtx_REG (CCZmode, CC_REGNUM);
10585 test = gen_rtx_EQ (VOIDmode, cc_reg, const0_rtx);
10586 emit_jump_insn (gen_cbranchcc4 (test, cc_reg, const0_rtx, operands[2]));
10587 DONE;
10588 })
10589
10590 (define_insn "stack_protect_test<mode>"
10591 [(set (reg:CCZ CC_REGNUM)
10592 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
10593 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
10594 ""
10595 "clc\t%O0(%G0,%R0),%S1"
10596 [(set_attr "op_type" "SS")])
10597
10598 ; This is used in s390_emit_prologue in order to prevent insns
10599 ; adjusting the stack pointer to be moved over insns writing stack
10600 ; slots using a copy of the stack pointer in a different register.
10601 (define_insn "stack_tie"
10602 [(set (match_operand:BLK 0 "memory_operand" "+m")
10603 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
10604 ""
10605 ""
10606 [(set_attr "length" "0")])
10607
10608
10609 (define_insn "stack_restore_from_fpr"
10610 [(set (reg:DI STACK_REGNUM)
10611 (match_operand:DI 0 "register_operand" "f"))
10612 (clobber (mem:BLK (scratch)))]
10613 "TARGET_Z10"
10614 "lgdr\t%%r15,%0"
10615 [(set_attr "op_type" "RRE")])
10616
10617 ;
10618 ; Data prefetch patterns
10619 ;
10620
10621 (define_insn "prefetch"
10622 [(prefetch (match_operand 0 "address_operand" "ZT,X")
10623 (match_operand:SI 1 "const_int_operand" " n,n")
10624 (match_operand:SI 2 "const_int_operand" " n,n"))]
10625 "TARGET_Z10"
10626 {
10627 switch (which_alternative)
10628 {
10629 case 0:
10630 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
10631 case 1:
10632 if (larl_operand (operands[0], Pmode))
10633 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
10634 /* fallthrough */
10635 default:
10636
10637 /* This might be reached for symbolic operands with an odd
10638 addend. We simply omit the prefetch for such rare cases. */
10639
10640 return "";
10641 }
10642 }
10643 [(set_attr "type" "load,larl")
10644 (set_attr "op_type" "RXY,RIL")
10645 (set_attr "z10prop" "z10_super")
10646 (set_attr "z196prop" "z196_alone")])
10647
10648
10649 ;
10650 ; Byte swap instructions
10651 ;
10652
10653 ; FIXME: There is also mvcin but we cannot use it since src and target
10654 ; may overlap.
10655 (define_insn "bswap<mode>2"
10656 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,T")
10657 (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,T,d")))]
10658 "TARGET_CPU_ZARCH"
10659 "@
10660 lrv<g>r\t%0,%1
10661 lrv<g>\t%0,%1
10662 strv<g>\t%1,%0"
10663 [(set_attr "type" "*,load,store")
10664 (set_attr "op_type" "RRE,RXY,RXY")
10665 (set_attr "z10prop" "z10_super")])
10666
10667 (define_insn "bswaphi2"
10668 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,T")
10669 (bswap:HI (match_operand:HI 1 "nonimmediate_operand" " d,T,d")))]
10670 "TARGET_CPU_ZARCH"
10671 "@
10672 #
10673 lrvh\t%0,%1
10674 strvh\t%1,%0"
10675 [(set_attr "type" "*,load,store")
10676 (set_attr "op_type" "RRE,RXY,RXY")
10677 (set_attr "z10prop" "z10_super")])
10678
10679 (define_split
10680 [(set (match_operand:HI 0 "register_operand" "")
10681 (bswap:HI (match_operand:HI 1 "register_operand" "")))]
10682 "TARGET_CPU_ZARCH"
10683 [(set (match_dup 2) (bswap:SI (match_dup 3)))
10684 (set (match_dup 2) (lshiftrt:SI (match_dup 2) (const_int 16)))]
10685 {
10686 operands[2] = simplify_gen_subreg (SImode, operands[0], HImode, 0);
10687 operands[3] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
10688 })
10689
10690
10691 ;
10692 ; Population count instruction
10693 ;
10694
10695 ; The S/390 popcount instruction counts the bits of op1 in 8 byte
10696 ; portions and stores the result in the corresponding bytes in op0.
10697 (define_insn "*popcount<mode>"
10698 [(set (match_operand:INT 0 "register_operand" "=d")
10699 (unspec:INT [(match_operand:INT 1 "register_operand" "d")] UNSPEC_POPCNT))
10700 (clobber (reg:CC CC_REGNUM))]
10701 "TARGET_Z196"
10702 "popcnt\t%0,%1"
10703 [(set_attr "op_type" "RRE")])
10704
10705 (define_expand "popcountdi2"
10706 [; popcnt op0, op1
10707 (parallel [(set (match_operand:DI 0 "register_operand" "")
10708 (unspec:DI [(match_operand:DI 1 "register_operand")]
10709 UNSPEC_POPCNT))
10710 (clobber (reg:CC CC_REGNUM))])
10711 ; sllg op2, op0, 32
10712 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 32)))
10713 ; agr op0, op2
10714 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10715 (clobber (reg:CC CC_REGNUM))])
10716 ; sllg op2, op0, 16
10717 (set (match_dup 2)
10718 (ashift:DI (match_dup 0) (const_int 16)))
10719 ; agr op0, op2
10720 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10721 (clobber (reg:CC CC_REGNUM))])
10722 ; sllg op2, op0, 8
10723 (set (match_dup 2) (ashift:DI (match_dup 0) (const_int 8)))
10724 ; agr op0, op2
10725 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 2)))
10726 (clobber (reg:CC CC_REGNUM))])
10727 ; srlg op0, op0, 56
10728 (set (match_dup 0) (lshiftrt:DI (match_dup 0) (const_int 56)))]
10729 "TARGET_Z196 && TARGET_64BIT"
10730 "operands[2] = gen_reg_rtx (DImode);")
10731
10732 (define_expand "popcountsi2"
10733 [; popcnt op0, op1
10734 (parallel [(set (match_operand:SI 0 "register_operand" "")
10735 (unspec:SI [(match_operand:SI 1 "register_operand")]
10736 UNSPEC_POPCNT))
10737 (clobber (reg:CC CC_REGNUM))])
10738 ; sllk op2, op0, 16
10739 (set (match_dup 2)
10740 (ashift:SI (match_dup 0) (const_int 16)))
10741 ; ar op0, op2
10742 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10743 (clobber (reg:CC CC_REGNUM))])
10744 ; sllk op2, op0, 8
10745 (set (match_dup 2) (ashift:SI (match_dup 0) (const_int 8)))
10746 ; ar op0, op2
10747 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10748 (clobber (reg:CC CC_REGNUM))])
10749 ; srl op0, op0, 24
10750 (set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 24)))]
10751 "TARGET_Z196"
10752 "operands[2] = gen_reg_rtx (SImode);")
10753
10754 (define_expand "popcounthi2"
10755 [; popcnt op0, op1
10756 (parallel [(set (match_operand:HI 0 "register_operand" "")
10757 (unspec:HI [(match_operand:HI 1 "register_operand")]
10758 UNSPEC_POPCNT))
10759 (clobber (reg:CC CC_REGNUM))])
10760 ; sllk op2, op0, 8
10761 (set (match_dup 2)
10762 (ashift:SI (match_dup 0) (const_int 8)))
10763 ; ar op0, op2
10764 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
10765 (clobber (reg:CC CC_REGNUM))])
10766 ; srl op0, op0, 8
10767 (set (match_dup 0) (lshiftrt:HI (match_dup 0) (const_int 8)))]
10768 "TARGET_Z196"
10769 "operands[2] = gen_reg_rtx (SImode);")
10770
10771 (define_expand "popcountqi2"
10772 [; popcnt op0, op1
10773 (parallel [(set (match_operand:QI 0 "register_operand" "")
10774 (unspec:QI [(match_operand:QI 1 "register_operand")]
10775 UNSPEC_POPCNT))
10776 (clobber (reg:CC CC_REGNUM))])]
10777 "TARGET_Z196"
10778 "")
10779
10780 ;;
10781 ;;- Copy sign instructions
10782 ;;
10783
10784 (define_insn "copysign<mode>3"
10785 [(set (match_operand:FP 0 "register_operand" "=f")
10786 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
10787 (match_operand:FP 2 "register_operand" "f")]
10788 UNSPEC_COPYSIGN))]
10789 "TARGET_Z196"
10790 "cpsdr\t%0,%2,%1"
10791 [(set_attr "op_type" "RRF")
10792 (set_attr "type" "fsimp<mode>")])
10793
10794
10795 ;;
10796 ;;- Transactional execution instructions
10797 ;;
10798
10799 ; This splitter helps combine to make use of CC directly when
10800 ; comparing the integer result of a tbegin builtin with a constant.
10801 ; The unspec is already removed by canonicalize_comparison. So this
10802 ; splitters only job is to turn the PARALLEL into separate insns
10803 ; again. Unfortunately this only works with the very first cc/int
10804 ; compare since combine is not able to deal with data flow across
10805 ; basic block boundaries.
10806
10807 ; It needs to be an insn pattern as well since combine does not apply
10808 ; the splitter directly. Combine would only use it if it actually
10809 ; would reduce the number of instructions.
10810 (define_insn_and_split "*ccraw_to_int"
10811 [(set (pc)
10812 (if_then_else
10813 (match_operator 0 "s390_eqne_operator"
10814 [(reg:CCRAW CC_REGNUM)
10815 (match_operand 1 "const_int_operand" "")])
10816 (label_ref (match_operand 2 "" ""))
10817 (pc)))
10818 (set (match_operand:SI 3 "register_operand" "=d")
10819 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10820 ""
10821 "#"
10822 ""
10823 [(set (match_dup 3)
10824 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))
10825 (set (pc)
10826 (if_then_else (match_op_dup 0 [(reg:CCRAW CC_REGNUM) (match_dup 1)])
10827 (label_ref (match_dup 2))
10828 (pc)))]
10829 "")
10830
10831 ; Non-constrained transaction begin
10832
10833 (define_expand "tbegin"
10834 [(match_operand:SI 0 "register_operand" "")
10835 (match_operand:BLK 1 "memory_operand" "")]
10836 "TARGET_HTM"
10837 {
10838 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, true);
10839 DONE;
10840 })
10841
10842 (define_expand "tbegin_nofloat"
10843 [(match_operand:SI 0 "register_operand" "")
10844 (match_operand:BLK 1 "memory_operand" "")]
10845 "TARGET_HTM"
10846 {
10847 s390_expand_tbegin (operands[0], operands[1], NULL_RTX, false);
10848 DONE;
10849 })
10850
10851 (define_expand "tbegin_retry"
10852 [(match_operand:SI 0 "register_operand" "")
10853 (match_operand:BLK 1 "memory_operand" "")
10854 (match_operand:SI 2 "general_operand" "")]
10855 "TARGET_HTM"
10856 {
10857 s390_expand_tbegin (operands[0], operands[1], operands[2], true);
10858 DONE;
10859 })
10860
10861 (define_expand "tbegin_retry_nofloat"
10862 [(match_operand:SI 0 "register_operand" "")
10863 (match_operand:BLK 1 "memory_operand" "")
10864 (match_operand:SI 2 "general_operand" "")]
10865 "TARGET_HTM"
10866 {
10867 s390_expand_tbegin (operands[0], operands[1], operands[2], false);
10868 DONE;
10869 })
10870
10871 ; Clobber VRs since they don't get restored
10872 (define_insn "tbegin_1_z13"
10873 [(set (reg:CCRAW CC_REGNUM)
10874 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10875 UNSPECV_TBEGIN))
10876 (set (match_operand:BLK 1 "memory_operand" "=Q")
10877 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10878 (clobber (reg:TI 16)) (clobber (reg:TI 38))
10879 (clobber (reg:TI 17)) (clobber (reg:TI 39))
10880 (clobber (reg:TI 18)) (clobber (reg:TI 40))
10881 (clobber (reg:TI 19)) (clobber (reg:TI 41))
10882 (clobber (reg:TI 20)) (clobber (reg:TI 42))
10883 (clobber (reg:TI 21)) (clobber (reg:TI 43))
10884 (clobber (reg:TI 22)) (clobber (reg:TI 44))
10885 (clobber (reg:TI 23)) (clobber (reg:TI 45))
10886 (clobber (reg:TI 24)) (clobber (reg:TI 46))
10887 (clobber (reg:TI 25)) (clobber (reg:TI 47))
10888 (clobber (reg:TI 26)) (clobber (reg:TI 48))
10889 (clobber (reg:TI 27)) (clobber (reg:TI 49))
10890 (clobber (reg:TI 28)) (clobber (reg:TI 50))
10891 (clobber (reg:TI 29)) (clobber (reg:TI 51))
10892 (clobber (reg:TI 30)) (clobber (reg:TI 52))
10893 (clobber (reg:TI 31)) (clobber (reg:TI 53))]
10894 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10895 ; not supposed to be used for immediates (see genpreds.c).
10896 "TARGET_VX && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10897 "tbegin\t%1,%x0"
10898 [(set_attr "op_type" "SIL")])
10899
10900 (define_insn "tbegin_1"
10901 [(set (reg:CCRAW CC_REGNUM)
10902 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10903 UNSPECV_TBEGIN))
10904 (set (match_operand:BLK 1 "memory_operand" "=Q")
10905 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))
10906 (clobber (reg:DF 16))
10907 (clobber (reg:DF 17))
10908 (clobber (reg:DF 18))
10909 (clobber (reg:DF 19))
10910 (clobber (reg:DF 20))
10911 (clobber (reg:DF 21))
10912 (clobber (reg:DF 22))
10913 (clobber (reg:DF 23))
10914 (clobber (reg:DF 24))
10915 (clobber (reg:DF 25))
10916 (clobber (reg:DF 26))
10917 (clobber (reg:DF 27))
10918 (clobber (reg:DF 28))
10919 (clobber (reg:DF 29))
10920 (clobber (reg:DF 30))
10921 (clobber (reg:DF 31))]
10922 ; CONST_OK_FOR_CONSTRAINT_P does not work with D constraint since D is
10923 ; not supposed to be used for immediates (see genpreds.c).
10924 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10925 "tbegin\t%1,%x0"
10926 [(set_attr "op_type" "SIL")])
10927
10928 ; Same as above but without the FPR clobbers
10929 (define_insn "tbegin_nofloat_1"
10930 [(set (reg:CCRAW CC_REGNUM)
10931 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" "D")]
10932 UNSPECV_TBEGIN))
10933 (set (match_operand:BLK 1 "memory_operand" "=Q")
10934 (unspec_volatile:BLK [(match_dup 0)] UNSPECV_TBEGIN_TDB))]
10935 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10936 "tbegin\t%1,%x0"
10937 [(set_attr "op_type" "SIL")])
10938
10939
10940 ; Constrained transaction begin
10941
10942 (define_expand "tbeginc"
10943 [(set (reg:CCRAW CC_REGNUM)
10944 (unspec_volatile:CCRAW [(const_int TBEGINC_MASK)]
10945 UNSPECV_TBEGINC))]
10946 "TARGET_HTM"
10947 "")
10948
10949 (define_insn "*tbeginc_1"
10950 [(set (reg:CCRAW CC_REGNUM)
10951 (unspec_volatile:CCRAW [(match_operand 0 "const_int_operand" " D")]
10952 UNSPECV_TBEGINC))]
10953 "TARGET_HTM && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 0xffff"
10954 "tbeginc\t0,%x0"
10955 [(set_attr "op_type" "SIL")])
10956
10957 ; Transaction end
10958
10959 (define_expand "tend"
10960 [(set (reg:CCRAW CC_REGNUM)
10961 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))
10962 (set (match_operand:SI 0 "register_operand" "")
10963 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
10964 "TARGET_HTM"
10965 "")
10966
10967 (define_insn "*tend_1"
10968 [(set (reg:CCRAW CC_REGNUM)
10969 (unspec_volatile:CCRAW [(const_int 0)] UNSPECV_TEND))]
10970 "TARGET_HTM"
10971 "tend"
10972 [(set_attr "op_type" "S")])
10973
10974 ; Transaction abort
10975
10976 (define_expand "tabort"
10977 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "")]
10978 UNSPECV_TABORT)]
10979 "TARGET_HTM && operands != NULL"
10980 {
10981 if (CONST_INT_P (operands[0])
10982 && INTVAL (operands[0]) >= 0 && INTVAL (operands[0]) <= 255)
10983 {
10984 error ("Invalid transaction abort code: " HOST_WIDE_INT_PRINT_DEC
10985 ". Values in range 0 through 255 are reserved.",
10986 INTVAL (operands[0]));
10987 FAIL;
10988 }
10989 })
10990
10991 (define_insn "*tabort_1"
10992 [(unspec_volatile [(match_operand:SI 0 "nonmemory_operand" "aJ")]
10993 UNSPECV_TABORT)]
10994 "TARGET_HTM && operands != NULL"
10995 "tabort\t%Y0"
10996 [(set_attr "op_type" "S")])
10997
10998 (define_insn "*tabort_1_plus"
10999 [(unspec_volatile [(plus:SI (match_operand:SI 0 "register_operand" "a")
11000 (match_operand:SI 1 "const_int_operand" "J"))]
11001 UNSPECV_TABORT)]
11002 "TARGET_HTM && operands != NULL
11003 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[1]), 'J', \"J\")"
11004 "tabort\t%1(%0)"
11005 [(set_attr "op_type" "S")])
11006
11007 ; Transaction extract nesting depth
11008
11009 (define_insn "etnd"
11010 [(set (match_operand:SI 0 "register_operand" "=d")
11011 (unspec_volatile:SI [(const_int 0)] UNSPECV_ETND))]
11012 "TARGET_HTM"
11013 "etnd\t%0"
11014 [(set_attr "op_type" "RRE")])
11015
11016 ; Non-transactional store
11017
11018 (define_insn "ntstg"
11019 [(set (match_operand:DI 0 "memory_operand" "=T")
11020 (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "d")]
11021 UNSPECV_NTSTG))]
11022 "TARGET_HTM"
11023 "ntstg\t%1,%0"
11024 [(set_attr "op_type" "RXY")])
11025
11026 ; Transaction perform processor assist
11027
11028 (define_expand "tx_assist"
11029 [(unspec_volatile [(match_operand:SI 0 "register_operand" "")
11030 (reg:SI GPR0_REGNUM)
11031 (const_int 1)]
11032 UNSPECV_PPA)]
11033 "TARGET_HTM"
11034 "")
11035
11036 (define_insn "*ppa"
11037 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")
11038 (match_operand:SI 1 "register_operand" "d")
11039 (match_operand 2 "const_int_operand" "I")]
11040 UNSPECV_PPA)]
11041 "TARGET_HTM && INTVAL (operands[2]) < 16"
11042 "ppa\t%0,%1,%2"
11043 [(set_attr "op_type" "RRF")])
11044
11045
11046 ; Set and get floating point control register
11047
11048 (define_insn "sfpc"
11049 [(unspec_volatile [(match_operand:SI 0 "register_operand" "d")]
11050 UNSPECV_SFPC)]
11051 "TARGET_HARD_FLOAT"
11052 "sfpc\t%0")
11053
11054 (define_insn "efpc"
11055 [(set (match_operand:SI 0 "register_operand" "=d")
11056 (unspec_volatile:SI [(const_int 0)] UNSPECV_EFPC))]
11057 "TARGET_HARD_FLOAT"
11058 "efpc\t%0")
11059
11060
11061 ; Load count to block boundary
11062
11063 (define_insn "lcbb"
11064 [(set (match_operand:SI 0 "register_operand" "=d")
11065 (unspec:SI [(match_operand 1 "address_operand" "ZR")
11066 (match_operand:SI 2 "immediate_operand" "C")] UNSPEC_LCBB))
11067 (clobber (reg:CC CC_REGNUM))]
11068 "TARGET_Z13"
11069 "lcbb\t%0,%a1,%b2"
11070 [(set_attr "op_type" "VRX")])
11071
11072 ; Handle -fsplit-stack.
11073
11074 (define_expand "split_stack_prologue"
11075 [(const_int 0)]
11076 ""
11077 {
11078 s390_expand_split_stack_prologue ();
11079 DONE;
11080 })
11081
11082 ;; If there are operand 0 bytes available on the stack, jump to
11083 ;; operand 1.
11084
11085 (define_expand "split_stack_space_check"
11086 [(set (pc) (if_then_else
11087 (ltu (minus (reg 15)
11088 (match_operand 0 "register_operand"))
11089 (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
11090 (label_ref (match_operand 1))
11091 (pc)))]
11092 ""
11093 {
11094 /* Offset from thread pointer to __private_ss. */
11095 int psso = TARGET_64BIT ? 0x38 : 0x20;
11096 rtx tp = s390_get_thread_pointer ();
11097 rtx guard = gen_rtx_MEM (Pmode, plus_constant (Pmode, tp, psso));
11098 rtx reg = gen_reg_rtx (Pmode);
11099 rtx cc;
11100 if (TARGET_64BIT)
11101 emit_insn (gen_subdi3 (reg, stack_pointer_rtx, operands[0]));
11102 else
11103 emit_insn (gen_subsi3 (reg, stack_pointer_rtx, operands[0]));
11104 cc = s390_emit_compare (GT, reg, guard);
11105 s390_emit_jump (operands[1], cc);
11106
11107 DONE;
11108 })
11109
11110 ;; __morestack parameter block for split stack prologue. Parameters are:
11111 ;; parameter block label, label to be called by __morestack, frame size,
11112 ;; stack parameter size.
11113
11114 (define_insn "split_stack_data"
11115 [(unspec_volatile [(match_operand 0 "" "X")
11116 (match_operand 1 "" "X")
11117 (match_operand 2 "const_int_operand" "X")
11118 (match_operand 3 "const_int_operand" "X")]
11119 UNSPECV_SPLIT_STACK_DATA)]
11120 "TARGET_CPU_ZARCH"
11121 {
11122 switch_to_section (targetm.asm_out.function_rodata_section
11123 (current_function_decl));
11124
11125 if (TARGET_64BIT)
11126 output_asm_insn (".align\t8", operands);
11127 else
11128 output_asm_insn (".align\t4", operands);
11129 (*targetm.asm_out.internal_label) (asm_out_file, "L",
11130 CODE_LABEL_NUMBER (operands[0]));
11131 if (TARGET_64BIT)
11132 {
11133 output_asm_insn (".quad\t%2", operands);
11134 output_asm_insn (".quad\t%3", operands);
11135 output_asm_insn (".quad\t%1-%0", operands);
11136 }
11137 else
11138 {
11139 output_asm_insn (".long\t%2", operands);
11140 output_asm_insn (".long\t%3", operands);
11141 output_asm_insn (".long\t%1-%0", operands);
11142 }
11143
11144 switch_to_section (current_function_section ());
11145 return "";
11146 }
11147 [(set_attr "length" "0")])
11148
11149
11150 ;; A jg with minimal fuss for use in split stack prologue.
11151
11152 (define_expand "split_stack_call"
11153 [(match_operand 0 "bras_sym_operand" "X")
11154 (match_operand 1 "" "")]
11155 "TARGET_CPU_ZARCH"
11156 {
11157 if (TARGET_64BIT)
11158 emit_jump_insn (gen_split_stack_call_di (operands[0], operands[1]));
11159 else
11160 emit_jump_insn (gen_split_stack_call_si (operands[0], operands[1]));
11161 DONE;
11162 })
11163
11164 (define_insn "split_stack_call_<mode>"
11165 [(set (pc) (label_ref (match_operand 1 "" "")))
11166 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11167 (reg:P 1)]
11168 UNSPECV_SPLIT_STACK_CALL))]
11169 "TARGET_CPU_ZARCH"
11170 "jg\t%0"
11171 [(set_attr "op_type" "RIL")
11172 (set_attr "type" "branch")])
11173
11174 ;; Also a conditional one.
11175
11176 (define_expand "split_stack_cond_call"
11177 [(match_operand 0 "bras_sym_operand" "X")
11178 (match_operand 1 "" "")
11179 (match_operand 2 "" "")]
11180 "TARGET_CPU_ZARCH"
11181 {
11182 if (TARGET_64BIT)
11183 emit_jump_insn (gen_split_stack_cond_call_di (operands[0], operands[1], operands[2]));
11184 else
11185 emit_jump_insn (gen_split_stack_cond_call_si (operands[0], operands[1], operands[2]));
11186 DONE;
11187 })
11188
11189 (define_insn "split_stack_cond_call_<mode>"
11190 [(set (pc)
11191 (if_then_else
11192 (match_operand 1 "" "")
11193 (label_ref (match_operand 2 "" ""))
11194 (pc)))
11195 (set (reg:P 1) (unspec_volatile [(match_operand 0 "bras_sym_operand" "X")
11196 (reg:P 1)]
11197 UNSPECV_SPLIT_STACK_CALL))]
11198 "TARGET_CPU_ZARCH"
11199 "jg%C1\t%0"
11200 [(set_attr "op_type" "RIL")
11201 (set_attr "type" "branch")])
11202
11203 (define_insn "osc_break"
11204 [(unspec_volatile [(const_int 0)] UNSPECV_OSC_BREAK)]
11205 ""
11206 "bcr\t7,%%r0"
11207 [(set_attr "op_type" "RR")])