rtl.h (emit_clobber, [...]): Declare.
[gcc.git] / gcc / config / s390 / s390.md
1 ;;- Machine description for GNU compiler -- S/390 / zSeries version.
2 ;; Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008
3 ;; Free Software Foundation, Inc.
4 ;; Contributed by Hartmut Penner (hpenner@de.ibm.com) and
5 ;; Ulrich Weigand (uweigand@de.ibm.com) and
6 ;; Andreas Krebbel (Andreas.Krebbel@de.ibm.com)
7
8 ;; This file is part of GCC.
9
10 ;; GCC is free software; you can redistribute it and/or modify it under
11 ;; the terms of the GNU General Public License as published by the Free
12 ;; Software Foundation; either version 3, or (at your option) any later
13 ;; version.
14
15 ;; GCC is distributed in the hope that it will be useful, but WITHOUT ANY
16 ;; WARRANTY; without even the implied warranty of MERCHANTABILITY or
17 ;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
18 ;; for more details.
19
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING3. If not see
22 ;; <http://www.gnu.org/licenses/>.
23
24 ;;
25 ;; See constraints.md for a description of constraints specific to s390.
26 ;;
27
28 ;; Special formats used for outputting 390 instructions.
29 ;;
30 ;; %C: print opcode suffix for branch condition.
31 ;; %D: print opcode suffix for inverse branch condition.
32 ;; %J: print tls_load/tls_gdcall/tls_ldcall suffix
33 ;; %G: print the size of the operand in bytes.
34 ;; %O: print only the displacement of a memory reference.
35 ;; %R: print only the base register of a memory reference.
36 ;; %S: print S-type memory reference (base+displacement).
37 ;; %N: print the second word of a DImode operand.
38 ;; %M: print the second word of a TImode operand.
39 ;; %Y: print shift count operand.
40 ;;
41 ;; %b: print integer X as if it's an unsigned byte.
42 ;; %c: print integer X as if it's an signed byte.
43 ;; %x: print integer X as if it's an unsigned halfword.
44 ;; %h: print integer X as if it's a signed halfword.
45 ;; %i: print the first nonzero HImode part of X.
46 ;; %j: print the first HImode part unequal to -1 of X.
47 ;; %k: print the first nonzero SImode part of X.
48 ;; %m: print the first SImode part unequal to -1 of X.
49 ;; %o: print integer X as if it's an unsigned 32bit word.
50 ;;
51 ;; We have a special constraint for pattern matching.
52 ;;
53 ;; s_operand -- Matches a valid S operand in a RS, SI or SS type instruction.
54 ;;
55
56 ;;
57 ;; UNSPEC usage
58 ;;
59
60 (define_constants
61 [; Miscellaneous
62 (UNSPEC_ROUND 1)
63 (UNSPEC_CCU_TO_INT 2)
64 (UNSPEC_CCZ_TO_INT 3)
65 (UNSPEC_ICM 10)
66 (UNSPEC_TIE 11)
67
68 ; GOT/PLT and lt-relative accesses
69 (UNSPEC_LTREL_OFFSET 100)
70 (UNSPEC_LTREL_BASE 101)
71 (UNSPEC_GOTENT 110)
72 (UNSPEC_GOT 111)
73 (UNSPEC_GOTOFF 112)
74 (UNSPEC_PLT 113)
75 (UNSPEC_PLTOFF 114)
76
77 ; Literal pool
78 (UNSPEC_RELOAD_BASE 210)
79 (UNSPEC_MAIN_BASE 211)
80 (UNSPEC_LTREF 212)
81 (UNSPEC_INSN 213)
82 (UNSPEC_EXECUTE 214)
83
84 ; TLS relocation specifiers
85 (UNSPEC_TLSGD 500)
86 (UNSPEC_TLSLDM 501)
87 (UNSPEC_NTPOFF 502)
88 (UNSPEC_DTPOFF 503)
89 (UNSPEC_GOTNTPOFF 504)
90 (UNSPEC_INDNTPOFF 505)
91
92 ; TLS support
93 (UNSPEC_TLSLDM_NTPOFF 511)
94 (UNSPEC_TLS_LOAD 512)
95
96 ; String Functions
97 (UNSPEC_SRST 600)
98 (UNSPEC_MVST 601)
99
100 ; Stack Smashing Protector
101 (UNSPEC_SP_SET 700)
102 (UNSPEC_SP_TEST 701)
103
104 ; Copy sign instructions
105 (UNSPEC_COPYSIGN 800)
106
107 ; Test Data Class (TDC)
108 (UNSPEC_TDC_INSN 900)
109 ])
110
111 ;;
112 ;; UNSPEC_VOLATILE usage
113 ;;
114
115 (define_constants
116 [; Blockage
117 (UNSPECV_BLOCKAGE 0)
118
119 ; TPF Support
120 (UNSPECV_TPF_PROLOGUE 20)
121 (UNSPECV_TPF_EPILOGUE 21)
122
123 ; Literal pool
124 (UNSPECV_POOL 200)
125 (UNSPECV_POOL_SECTION 201)
126 (UNSPECV_POOL_ALIGN 202)
127 (UNSPECV_POOL_ENTRY 203)
128 (UNSPECV_MAIN_POOL 300)
129
130 ; TLS support
131 (UNSPECV_SET_TP 500)
132
133 ; Atomic Support
134 (UNSPECV_MB 700)
135 (UNSPECV_CAS 701)
136 ])
137
138 ;;
139 ;; Registers
140 ;;
141
142 ; Registers with special meaning
143
144 (define_constants
145 [
146 ; Sibling call register.
147 (SIBCALL_REGNUM 1)
148 ; Literal pool base register.
149 (BASE_REGNUM 13)
150 ; Return address register.
151 (RETURN_REGNUM 14)
152 ; Condition code register.
153 (CC_REGNUM 33)
154 ; Thread local storage pointer register.
155 (TP_REGNUM 36)
156 ])
157
158 ; Hardware register names
159
160 (define_constants
161 [
162 ; General purpose registers
163 (GPR0_REGNUM 0)
164 ; Floating point registers.
165 (FPR0_REGNUM 16)
166 (FPR2_REGNUM 18)
167 ])
168
169 ;;
170 ;; PFPO GPR0 argument format
171 ;;
172
173 (define_constants
174 [
175 ; PFPO operation type
176 (PFPO_CONVERT 0x1000000)
177 ; PFPO operand types
178 (PFPO_OP_TYPE_SF 0x5)
179 (PFPO_OP_TYPE_DF 0x6)
180 (PFPO_OP_TYPE_TF 0x7)
181 (PFPO_OP_TYPE_SD 0x8)
182 (PFPO_OP_TYPE_DD 0x9)
183 (PFPO_OP_TYPE_TD 0xa)
184 ; Bitposition of operand types
185 (PFPO_OP0_TYPE_SHIFT 16)
186 (PFPO_OP1_TYPE_SHIFT 8)
187 ])
188
189
190 ;; Instruction operand type as used in the Principles of Operation.
191 ;; Used to determine defaults for length and other attribute values.
192
193 (define_attr "op_type"
194 "NN,E,RR,RRE,RX,RS,RSI,RI,SI,S,SS,SSE,RXE,RSE,RIL,RIE,RXY,RSY,SIY,RRF,RRR,SIL,RRS,RIS"
195 (const_string "NN"))
196
197 ;; Instruction type attribute used for scheduling.
198
199 (define_attr "type" "none,integer,load,lr,la,larl,lm,stm,
200 cs,vs,store,sem,idiv,
201 imulhi,imulsi,imuldi,
202 branch,jsr,fsimptf,fsimpdf,fsimpsf,
203 floadtf,floaddf,floadsf,fstoredf,fstoresf,
204 fmultf,fmuldf,fmulsf,fdivtf,fdivdf,fdivsf,
205 ftoi,itof,fsqrttf,fsqrtdf,fsqrtsf,
206 ftrunctf,ftruncdf,other"
207 (cond [(eq_attr "op_type" "NN") (const_string "other")
208 (eq_attr "op_type" "SS") (const_string "cs")]
209 (const_string "integer")))
210
211 ;; Another attribute used for scheduling purposes:
212 ;; agen: Instruction uses the address generation unit
213 ;; reg: Instruction does not use the agen unit
214
215 (define_attr "atype" "agen,reg"
216 (if_then_else (eq_attr "op_type" "E,RR,RI,RRE")
217 (const_string "reg")
218 (const_string "agen")))
219
220 ;; Length in bytes.
221
222 (define_attr "length" ""
223 (cond [(eq_attr "op_type" "E,RR") (const_int 2)
224 (eq_attr "op_type" "RX,RI,RRE,RS,RSI,S,SI,RRF,RRR") (const_int 4)]
225 (const_int 6)))
226
227
228 ;; Processor type. This attribute must exactly match the processor_type
229 ;; enumeration in s390.h. The current machine description does not
230 ;; distinguish between g5 and g6, but there are differences between the two
231 ;; CPUs could in theory be modeled.
232
233 (define_attr "cpu" "g5,g6,z900,z990,z9_109,z10"
234 (const (symbol_ref "s390_tune")))
235
236 (define_attr "cpu_facility" "standard,ieee,zarch,longdisp,extimm,dfp,z10"
237 (const_string "standard"))
238
239 (define_attr "enabled" ""
240 (cond [(eq_attr "cpu_facility" "standard")
241 (const_int 1)
242
243 (and (eq_attr "cpu_facility" "ieee")
244 (ne (symbol_ref "TARGET_CPU_IEEE_FLOAT") (const_int 0)))
245 (const_int 1)
246
247 (and (eq_attr "cpu_facility" "zarch")
248 (ne (symbol_ref "TARGET_ZARCH") (const_int 0)))
249 (const_int 1)
250
251 (and (eq_attr "cpu_facility" "longdisp")
252 (ne (symbol_ref "TARGET_LONG_DISPLACEMENT") (const_int 0)))
253 (const_int 1)
254
255 (and (eq_attr "cpu_facility" "extimm")
256 (ne (symbol_ref "TARGET_EXTIMM") (const_int 0)))
257 (const_int 1)
258
259 (and (eq_attr "cpu_facility" "dfp")
260 (ne (symbol_ref "TARGET_DFP") (const_int 0)))
261 (const_int 1)
262
263 (and (eq_attr "cpu_facility" "z10")
264 (ne (symbol_ref "TARGET_Z10") (const_int 0)))
265 (const_int 1)]
266 (const_int 0)))
267
268 ;; Pipeline description for z900. For lack of anything better,
269 ;; this description is also used for the g5 and g6.
270 (include "2064.md")
271
272 ;; Pipeline description for z990, z9-109 and z9-ec.
273 (include "2084.md")
274
275 ;; Predicates
276 (include "predicates.md")
277
278 ;; Constraint definitions
279 (include "constraints.md")
280
281 ;; Other includes
282 (include "tpf.md")
283
284 ;; Iterators
285
286 ;; These mode iterators allow floating point patterns to be generated from the
287 ;; same template.
288 (define_mode_iterator FP_ALL [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")
289 (SD "TARGET_HARD_DFP")])
290 (define_mode_iterator FP [TF DF SF (TD "TARGET_HARD_DFP") (DD "TARGET_HARD_DFP")])
291 (define_mode_iterator FPALL [TF DF SF TD DD SD])
292 (define_mode_iterator BFP [TF DF SF])
293 (define_mode_iterator DFP [TD DD])
294 (define_mode_iterator DFP_ALL [TD DD SD])
295 (define_mode_iterator DSF [DF SF])
296 (define_mode_iterator SD_SF [SF SD])
297 (define_mode_iterator DD_DF [DF DD])
298 (define_mode_iterator TD_TF [TF TD])
299
300 ;; This mode iterator allows 31-bit and 64-bit TDSI patterns to be generated
301 ;; from the same template.
302 (define_mode_iterator TDSI [(TI "TARGET_64BIT") DI SI])
303
304 ;; These mode iterators allow 31-bit and 64-bit GPR patterns to be generated
305 ;; from the same template.
306 (define_mode_iterator GPR [(DI "TARGET_64BIT") SI])
307 (define_mode_iterator DSI [DI SI])
308
309 ;; These mode iterators allow :P to be used for patterns that operate on
310 ;; pointer-sized quantities. Exactly one of the two alternatives will match.
311 (define_mode_iterator DP [(TI "TARGET_64BIT") (DI "!TARGET_64BIT")])
312 (define_mode_iterator P [(DI "TARGET_64BIT") (SI "!TARGET_64BIT")])
313
314 ;; This mode iterator allows the QI and HI patterns to be defined from
315 ;; the same template.
316 (define_mode_iterator HQI [HI QI])
317
318 ;; This mode iterator allows the integer patterns to be defined from the
319 ;; same template.
320 (define_mode_iterator INT [(DI "TARGET_64BIT") SI HI QI])
321 (define_mode_iterator INTALL [TI DI SI HI QI])
322
323 ;; This iterator allows to unify all 'bCOND' expander patterns.
324 (define_code_iterator COMPARE [eq ne gt gtu lt ltu ge geu le leu unordered
325 ordered uneq unlt ungt unle unge ltgt])
326
327 ;; This iterator allows to unify all 'sCOND' patterns.
328 (define_code_iterator SCOND [ltu gtu leu geu])
329
330 ;; This iterator allows some 'ashift' and 'lshiftrt' pattern to be defined from
331 ;; the same template.
332 (define_code_iterator SHIFT [ashift lshiftrt])
333
334 ;; This iterator and attribute allow to combine most atomic operations.
335 (define_code_iterator ATOMIC [and ior xor plus minus mult])
336 (define_code_attr atomic [(and "and") (ior "ior") (xor "xor")
337 (plus "add") (minus "sub") (mult "nand")])
338
339 ;; In FP templates, a string like "lt<de>br" will expand to "ltxbr" in
340 ;; TF/TDmode, "ltdbr" in DF/DDmode, and "ltebr" in SF/SDmode.
341 (define_mode_attr xde [(TF "x") (DF "d") (SF "e") (TD "x") (DD "d") (SD "e")])
342
343 ;; In FP templates, a <dee> in "m<dee><bt>r" will expand to "mx<bt>r" in
344 ;; TF/TDmode, "md<bt>r" in DF/DDmode, "mee<bt>r" in SFmode and "me<bt>r in
345 ;; SDmode.
346 (define_mode_attr xdee [(TF "x") (DF "d") (SF "ee") (TD "x") (DD "d") (SD "e")])
347
348 ;; In FP templates, "<RRe>" will expand to "RRE" in TFmode and "RR" otherwise.
349 ;; Likewise for "<RXe>".
350 (define_mode_attr RRe [(TF "RRE") (DF "RR") (SF "RR")])
351 (define_mode_attr RXe [(TF "RXE") (DF "RX") (SF "RX")])
352
353 ;; The decimal floating point variants of add, sub, div and mul support 3
354 ;; fp register operands. The following attributes allow to merge the bfp and
355 ;; dfp variants in a single insn definition.
356
357 ;; This attribute is used to set op_type accordingly.
358 (define_mode_attr RRer [(TF "RRE") (DF "RRE") (SF "RRE") (TD "RRR")
359 (DD "RRR") (SD "RRR")])
360
361 ;; This attribute is used in the operand constraint list in order to have the
362 ;; first and the second operand match for bfp modes.
363 (define_mode_attr f0 [(TF "0") (DF "0") (SF "0") (TD "f") (DD "f") (DD "f")])
364
365 ;; This attribute is used in the operand list of the instruction to have an
366 ;; additional operand for the dfp instructions.
367 (define_mode_attr op1 [(TF "") (DF "") (SF "")
368 (TD "%1,") (DD "%1,") (SD "%1,")])
369
370
371 ;; This attribute is used in the operand constraint list
372 ;; for instructions dealing with the sign bit of 32 or 64bit fp values.
373 ;; TFmode values are represented by a fp register pair. Since the
374 ;; sign bit instructions only handle single source and target fp registers
375 ;; these instructions can only be used for TFmode values if the source and
376 ;; target operand uses the same fp register.
377 (define_mode_attr fT0 [(TF "0") (DF "f") (SF "f")])
378
379 ;; In FP templates, "<Rf>" will expand to "f" in TFmode and "R" otherwise.
380 ;; This is used to disable the memory alternative in TFmode patterns.
381 (define_mode_attr Rf [(TF "f") (DF "R") (SF "R") (TD "f") (DD "f") (SD "f")])
382
383 ;; This attribute adds b for bfp instructions and t for dfp instructions and is used
384 ;; within instruction mnemonics.
385 (define_mode_attr bt [(TF "b") (DF "b") (SF "b") (TD "t") (DD "t") (SD "t")])
386
387 ;; This attribute is used within instruction mnemonics. It evaluates to d for dfp
388 ;; modes and to an empty string for bfp modes.
389 (define_mode_attr _d [(TF "") (DF "") (SF "") (TD "d") (DD "d") (SD "d")])
390
391 ;; Although it is imprecise for z9-ec we handle all dfp instructions like
392 ;; bfp regarding the pipeline description.
393 (define_mode_attr bfp [(TF "tf") (DF "df") (SF "sf")
394 (TD "tf") (DD "df") (SD "sf")])
395
396
397 ;; In GPR and P templates, a constraint like "<d0>" will expand to "d" in DImode
398 ;; and "0" in SImode. This allows to combine instructions of which the 31bit
399 ;; version only operates on one register.
400 (define_mode_attr d0 [(DI "d") (SI "0")])
401
402 ;; In combination with d0 this allows to combine instructions of which the 31bit
403 ;; version only operates on one register. The DImode version needs an additional
404 ;; register for the assembler output.
405 (define_mode_attr 1 [(DI "%1,") (SI "")])
406
407 ;; In SHIFT templates, a string like "s<lr>dl" will expand to "sldl" in
408 ;; 'ashift' and "srdl" in 'lshiftrt'.
409 (define_code_attr lr [(ashift "l") (lshiftrt "r")])
410
411 ;; In SHIFT templates, this attribute holds the correct standard name for the
412 ;; pattern itself and the corresponding function calls.
413 (define_code_attr shift [(ashift "ashl") (lshiftrt "lshr")])
414
415 ;; This attribute handles differences in the instruction 'type' and will result
416 ;; in "RRE" for DImode and "RR" for SImode.
417 (define_mode_attr E [(DI "E") (SI "")])
418
419 ;; This attribute handles differences in the instruction 'type' and makes RX<Y>
420 ;; to result in "RXY" for DImode and "RX" for SImode.
421 (define_mode_attr Y [(DI "Y") (SI "")])
422
423 ;; This attribute handles differences in the instruction 'type' and will result
424 ;; in "RSE" for TImode and "RS" for DImode.
425 (define_mode_attr TE [(TI "E") (DI "")])
426
427 ;; In GPR templates, a string like "lc<g>r" will expand to "lcgr" in DImode
428 ;; and "lcr" in SImode.
429 (define_mode_attr g [(DI "g") (SI "")])
430
431 ;; In GPR templates, a string like "sl<y>" will expand to "slg" in DImode
432 ;; and "sly" in SImode. This is useful because on 64bit the ..g instructions
433 ;; were enhanced with long displacements whereas 31bit instructions got a ..y
434 ;; variant for long displacements.
435 (define_mode_attr y [(DI "g") (SI "y")])
436
437 ;; In DP templates, a string like "cds<g>" will expand to "cdsg" in TImode
438 ;; and "cds" in DImode.
439 (define_mode_attr tg [(TI "g") (DI "")])
440
441 ;; In GPR templates, a string like "c<gf>dbr" will expand to "cgdbr" in DImode
442 ;; and "cfdbr" in SImode.
443 (define_mode_attr gf [(DI "g") (SI "f")])
444
445 ;; ICM mask required to load MODE value into the lowest subreg
446 ;; of a SImode register.
447 (define_mode_attr icm_lo [(HI "3") (QI "1")])
448
449 ;; In HQI templates, a string like "llg<hc>" will expand to "llgh" in
450 ;; HImode and "llgc" in QImode.
451 (define_mode_attr hc [(HI "h") (QI "c")])
452
453 ;; In P templates, the mode <DBL> will expand to "TI" in DImode and "DI"
454 ;; in SImode.
455 (define_mode_attr DBL [(DI "TI") (SI "DI")])
456
457 ;; This attribute expands to DF for TFmode and to DD for TDmode . It is
458 ;; used for Txmode splitters splitting a Txmode copy into 2 Dxmode copies.
459 (define_mode_attr HALF_TMODE [(TF "DF") (TD "DD")])
460
461 ;; Maximum unsigned integer that fits in MODE.
462 (define_mode_attr max_uint [(HI "65535") (QI "255")])
463
464 ;;
465 ;;- Compare instructions.
466 ;;
467
468 (define_expand "cmp<mode>"
469 [(set (reg:CC CC_REGNUM)
470 (compare:CC (match_operand:GPR 0 "register_operand" "")
471 (match_operand:GPR 1 "general_operand" "")))]
472 ""
473 {
474 s390_compare_op0 = operands[0];
475 s390_compare_op1 = operands[1];
476 DONE;
477 })
478
479 (define_expand "cmp<mode>"
480 [(set (reg:CC CC_REGNUM)
481 (compare:CC (match_operand:FP 0 "register_operand" "")
482 (match_operand:FP 1 "general_operand" "")))]
483 "TARGET_HARD_FLOAT"
484 {
485 s390_compare_op0 = operands[0];
486 s390_compare_op1 = operands[1];
487 DONE;
488 })
489
490
491 ; Test-under-Mask instructions
492
493 (define_insn "*tmqi_mem"
494 [(set (reg CC_REGNUM)
495 (compare (and:QI (match_operand:QI 0 "memory_operand" "Q,S")
496 (match_operand:QI 1 "immediate_operand" "n,n"))
497 (match_operand:QI 2 "immediate_operand" "n,n")))]
498 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], false))"
499 "@
500 tm\t%S0,%b1
501 tmy\t%S0,%b1"
502 [(set_attr "op_type" "SI,SIY")])
503
504 (define_insn "*tmdi_reg"
505 [(set (reg CC_REGNUM)
506 (compare (and:DI (match_operand:DI 0 "nonimmediate_operand" "d,d,d,d")
507 (match_operand:DI 1 "immediate_operand"
508 "N0HD0,N1HD0,N2HD0,N3HD0"))
509 (match_operand:DI 2 "immediate_operand" "n,n,n,n")))]
510 "TARGET_64BIT
511 && s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
512 && s390_single_part (operands[1], DImode, HImode, 0) >= 0"
513 "@
514 tmhh\t%0,%i1
515 tmhl\t%0,%i1
516 tmlh\t%0,%i1
517 tmll\t%0,%i1"
518 [(set_attr "op_type" "RI")])
519
520 (define_insn "*tmsi_reg"
521 [(set (reg CC_REGNUM)
522 (compare (and:SI (match_operand:SI 0 "nonimmediate_operand" "d,d")
523 (match_operand:SI 1 "immediate_operand" "N0HS0,N1HS0"))
524 (match_operand:SI 2 "immediate_operand" "n,n")))]
525 "s390_match_ccmode (insn, s390_tm_ccmode (operands[1], operands[2], true))
526 && s390_single_part (operands[1], SImode, HImode, 0) >= 0"
527 "@
528 tmh\t%0,%i1
529 tml\t%0,%i1"
530 [(set_attr "op_type" "RI")])
531
532 (define_insn "*tm<mode>_full"
533 [(set (reg CC_REGNUM)
534 (compare (match_operand:HQI 0 "register_operand" "d")
535 (match_operand:HQI 1 "immediate_operand" "n")))]
536 "s390_match_ccmode (insn, s390_tm_ccmode (constm1_rtx, operands[1], true))"
537 "tml\t%0,<max_uint>"
538 [(set_attr "op_type" "RI")])
539
540
541 ;
542 ; Load-and-Test instructions
543 ;
544
545 ; tst(di|si) instruction pattern(s).
546
547 (define_insn "*tstdi_sign"
548 [(set (reg CC_REGNUM)
549 (compare
550 (ashiftrt:DI
551 (ashift:DI
552 (subreg:DI (match_operand:SI 0 "nonimmediate_operand" "d,RT") 0)
553 (const_int 32)) (const_int 32))
554 (match_operand:DI 1 "const0_operand" "")))
555 (set (match_operand:DI 2 "register_operand" "=d,d")
556 (sign_extend:DI (match_dup 0)))]
557 "s390_match_ccmode(insn, CCSmode) && TARGET_64BIT"
558 "ltgfr\t%2,%0
559 ltgf\t%2,%0"
560 [(set_attr "op_type" "RRE,RXY")
561 (set_attr "cpu_facility" "*,z10")])
562
563 ; ltr, lt, ltgr, ltg
564 (define_insn "*tst<mode>_extimm"
565 [(set (reg CC_REGNUM)
566 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
567 (match_operand:GPR 1 "const0_operand" "")))
568 (set (match_operand:GPR 2 "register_operand" "=d,d")
569 (match_dup 0))]
570 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
571 "@
572 lt<g>r\t%2,%0
573 lt<g>\t%2,%0"
574 [(set_attr "op_type" "RR<E>,RXY")])
575
576 ; ltr, lt, ltgr, ltg
577 (define_insn "*tst<mode>_cconly_extimm"
578 [(set (reg CC_REGNUM)
579 (compare (match_operand:GPR 0 "nonimmediate_operand" "d,RT")
580 (match_operand:GPR 1 "const0_operand" "")))
581 (clobber (match_scratch:GPR 2 "=X,d"))]
582 "s390_match_ccmode(insn, CCSmode) && TARGET_EXTIMM"
583 "@
584 lt<g>r\t%0,%0
585 lt<g>\t%2,%0"
586 [(set_attr "op_type" "RR<E>,RXY")])
587
588 (define_insn "*tstdi"
589 [(set (reg CC_REGNUM)
590 (compare (match_operand:DI 0 "register_operand" "d")
591 (match_operand:DI 1 "const0_operand" "")))
592 (set (match_operand:DI 2 "register_operand" "=d")
593 (match_dup 0))]
594 "s390_match_ccmode(insn, CCSmode) && TARGET_64BIT && !TARGET_EXTIMM"
595 "ltgr\t%2,%0"
596 [(set_attr "op_type" "RRE")])
597
598 (define_insn "*tstsi"
599 [(set (reg CC_REGNUM)
600 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
601 (match_operand:SI 1 "const0_operand" "")))
602 (set (match_operand:SI 2 "register_operand" "=d,d,d")
603 (match_dup 0))]
604 "s390_match_ccmode(insn, CCSmode) && !TARGET_EXTIMM"
605 "@
606 ltr\t%2,%0
607 icm\t%2,15,%S0
608 icmy\t%2,15,%S0"
609 [(set_attr "op_type" "RR,RS,RSY")])
610
611 (define_insn "*tstsi_cconly"
612 [(set (reg CC_REGNUM)
613 (compare (match_operand:SI 0 "nonimmediate_operand" "d,Q,S")
614 (match_operand:SI 1 "const0_operand" "")))
615 (clobber (match_scratch:SI 2 "=X,d,d"))]
616 "s390_match_ccmode(insn, CCSmode)"
617 "@
618 ltr\t%0,%0
619 icm\t%2,15,%S0
620 icmy\t%2,15,%S0"
621 [(set_attr "op_type" "RR,RS,RSY")])
622
623 (define_insn "*tstdi_cconly_31"
624 [(set (reg CC_REGNUM)
625 (compare (match_operand:DI 0 "register_operand" "d")
626 (match_operand:DI 1 "const0_operand" "")))]
627 "s390_match_ccmode(insn, CCSmode) && !TARGET_64BIT"
628 "srda\t%0,0"
629 [(set_attr "op_type" "RS")
630 (set_attr "atype" "reg")])
631
632 ; ltr, ltgr
633 (define_insn "*tst<mode>_cconly2"
634 [(set (reg CC_REGNUM)
635 (compare (match_operand:GPR 0 "register_operand" "d")
636 (match_operand:GPR 1 "const0_operand" "")))]
637 "s390_match_ccmode(insn, CCSmode)"
638 "lt<g>r\t%0,%0"
639 [(set_attr "op_type" "RR<E>")])
640
641 ; tst(hi|qi) instruction pattern(s).
642
643 (define_insn "*tst<mode>CCT"
644 [(set (reg CC_REGNUM)
645 (compare (match_operand:HQI 0 "nonimmediate_operand" "?Q,?S,d")
646 (match_operand:HQI 1 "const0_operand" "")))
647 (set (match_operand:HQI 2 "register_operand" "=d,d,0")
648 (match_dup 0))]
649 "s390_match_ccmode(insn, CCTmode)"
650 "@
651 icm\t%2,<icm_lo>,%S0
652 icmy\t%2,<icm_lo>,%S0
653 tml\t%0,<max_uint>"
654 [(set_attr "op_type" "RS,RSY,RI")])
655
656 (define_insn "*tsthiCCT_cconly"
657 [(set (reg CC_REGNUM)
658 (compare (match_operand:HI 0 "nonimmediate_operand" "Q,S,d")
659 (match_operand:HI 1 "const0_operand" "")))
660 (clobber (match_scratch:HI 2 "=d,d,X"))]
661 "s390_match_ccmode(insn, CCTmode)"
662 "@
663 icm\t%2,3,%S0
664 icmy\t%2,3,%S0
665 tml\t%0,65535"
666 [(set_attr "op_type" "RS,RSY,RI")])
667
668 (define_insn "*tstqiCCT_cconly"
669 [(set (reg CC_REGNUM)
670 (compare (match_operand:QI 0 "nonimmediate_operand" "?Q,?S,d")
671 (match_operand:QI 1 "const0_operand" "")))]
672 "s390_match_ccmode(insn, CCTmode)"
673 "@
674 cli\t%S0,0
675 cliy\t%S0,0
676 tml\t%0,255"
677 [(set_attr "op_type" "SI,SIY,RI")])
678
679 (define_insn "*tst<mode>"
680 [(set (reg CC_REGNUM)
681 (compare (match_operand:HQI 0 "s_operand" "Q,S")
682 (match_operand:HQI 1 "const0_operand" "")))
683 (set (match_operand:HQI 2 "register_operand" "=d,d")
684 (match_dup 0))]
685 "s390_match_ccmode(insn, CCSmode)"
686 "@
687 icm\t%2,<icm_lo>,%S0
688 icmy\t%2,<icm_lo>,%S0"
689 [(set_attr "op_type" "RS,RSY")])
690
691 (define_insn "*tst<mode>_cconly"
692 [(set (reg CC_REGNUM)
693 (compare (match_operand:HQI 0 "s_operand" "Q,S")
694 (match_operand:HQI 1 "const0_operand" "")))
695 (clobber (match_scratch:HQI 2 "=d,d"))]
696 "s390_match_ccmode(insn, CCSmode)"
697 "@
698 icm\t%2,<icm_lo>,%S0
699 icmy\t%2,<icm_lo>,%S0"
700 [(set_attr "op_type" "RS,RSY")])
701
702
703 ; Compare (equality) instructions
704
705 (define_insn "*cmpdi_cct"
706 [(set (reg CC_REGNUM)
707 (compare (match_operand:DI 0 "nonimmediate_operand" "%d,d,d,d,Q")
708 (match_operand:DI 1 "general_operand" "d,K,Os,RT,BQ")))]
709 "s390_match_ccmode (insn, CCTmode) && TARGET_64BIT"
710 "@
711 cgr\t%0,%1
712 cghi\t%0,%h1
713 cgfi\t%0,%1
714 cg\t%0,%1
715 #"
716 [(set_attr "op_type" "RRE,RI,RIL,RXY,SS")])
717
718 (define_insn "*cmpsi_cct"
719 [(set (reg CC_REGNUM)
720 (compare (match_operand:SI 0 "nonimmediate_operand" "%d,d,d,d,d,Q")
721 (match_operand:SI 1 "general_operand" "d,K,Os,R,T,BQ")))]
722 "s390_match_ccmode (insn, CCTmode)"
723 "@
724 cr\t%0,%1
725 chi\t%0,%h1
726 cfi\t%0,%1
727 c\t%0,%1
728 cy\t%0,%1
729 #"
730 [(set_attr "op_type" "RR,RI,RIL,RX,RXY,SS")])
731
732
733 ; Compare (signed) instructions
734
735 (define_insn "*cmpdi_ccs_sign"
736 [(set (reg CC_REGNUM)
737 (compare (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand"
738 "d,RT,b"))
739 (match_operand:DI 0 "register_operand" "d, d,d")))]
740 "s390_match_ccmode(insn, CCSRmode) && TARGET_64BIT"
741 "@
742 cgfr\t%0,%1
743 cgf\t%0,%1
744 cgfrl\t%0,%1"
745 [(set_attr "op_type" "RRE,RXY,RIL")
746 (set_attr "cpu_facility" "*,*,z10")
747 (set_attr "type" "*,*,larl")])
748
749 (define_insn "*cmpsi_ccs_sign"
750 [(set (reg CC_REGNUM)
751 (compare (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T,b"))
752 (match_operand:SI 0 "register_operand" "d,d,d")))]
753 "s390_match_ccmode(insn, CCSRmode)"
754 "@
755 ch\t%0,%1
756 chy\t%0,%1
757 chrl\t%0,%1"
758 [(set_attr "op_type" "RX,RXY,RIL")
759 (set_attr "cpu_facility" "*,*,z10")
760 (set_attr "type" "*,*,larl")])
761
762 (define_insn "*cmphi_ccs_z10"
763 [(set (reg CC_REGNUM)
764 (compare (match_operand:HI 0 "s_operand" "Q")
765 (match_operand:HI 1 "immediate_operand" "K")))]
766 "s390_match_ccmode(insn, CCSmode) && TARGET_Z10"
767 "chhsi\t%0,%1"
768 [(set_attr "op_type" "SIL")])
769
770 (define_insn "*cmpdi_ccs_signhi_rl"
771 [(set (reg CC_REGNUM)
772 (compare (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT,b"))
773 (match_operand:GPR 0 "register_operand" "d,d")))]
774 "s390_match_ccmode(insn, CCSRmode) && TARGET_Z10"
775 "@
776 cgh\t%0,%1
777 cghrl\t%0,%1"
778 [(set_attr "op_type" "RXY,RIL")
779 (set_attr "type" "*,larl")])
780
781 ; cr, chi, cfi, c, cy, cgr, cghi, cgfi, cg, chsi, cghsi, crl, cgrl
782 (define_insn "*cmp<mode>_ccs"
783 [(set (reg CC_REGNUM)
784 (compare (match_operand:GPR 0 "nonimmediate_operand"
785 "d,d,Q, d,d,d,d")
786 (match_operand:GPR 1 "general_operand"
787 "d,K,K,Os,R,T,b")))]
788 "s390_match_ccmode(insn, CCSmode)"
789 "@
790 c<g>r\t%0,%1
791 c<g>hi\t%0,%h1
792 c<g>hsi\t%0,%h1
793 c<g>fi\t%0,%1
794 c<g>\t%0,%1
795 c<y>\t%0,%1
796 c<g>rl\t%0,%1"
797 [(set_attr "op_type" "RR<E>,RI,SIL,RIL,RX<Y>,RXY,RIL")
798 (set_attr "cpu_facility" "*,*,z10,extimm,*,*,z10")
799 (set_attr "type" "*,*,*,*,*,*,larl")])
800
801
802 ; Compare (unsigned) instructions
803
804 (define_insn "*cmpsi_ccu_zerohi_rlsi"
805 [(set (reg CC_REGNUM)
806 (compare (zero_extend:SI (mem:HI (match_operand:SI 1
807 "larl_operand" "X")))
808 (match_operand:SI 0 "register_operand" "d")))]
809 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
810 "clhrl\t%0,%1"
811 [(set_attr "op_type" "RIL")
812 (set_attr "type" "larl")])
813
814 ; clhrl, clghrl
815 (define_insn "*cmp<GPR:mode>_ccu_zerohi_rldi"
816 [(set (reg CC_REGNUM)
817 (compare (zero_extend:GPR (mem:HI (match_operand:DI 1
818 "larl_operand" "X")))
819 (match_operand:GPR 0 "register_operand" "d")))]
820 "s390_match_ccmode(insn, CCURmode) && TARGET_Z10"
821 "cl<g>hrl\t%0,%1"
822 [(set_attr "op_type" "RIL")
823 (set_attr "type" "larl")])
824
825 (define_insn "*cmpdi_ccu_zero"
826 [(set (reg CC_REGNUM)
827 (compare (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand"
828 "d,RT,b"))
829 (match_operand:DI 0 "register_operand" "d, d,d")))]
830 "s390_match_ccmode (insn, CCURmode) && TARGET_64BIT"
831 "@
832 clgfr\t%0,%1
833 clgf\t%0,%1
834 clgfrl\t%0,%1"
835 [(set_attr "op_type" "RRE,RXY,RIL")
836 (set_attr "cpu_facility" "*,*,z10")
837 (set_attr "type" "*,*,larl")])
838
839 (define_insn "*cmpdi_ccu"
840 [(set (reg CC_REGNUM)
841 (compare (match_operand:DI 0 "nonimmediate_operand"
842 "d, d,d,Q, d, Q,BQ")
843 (match_operand:DI 1 "general_operand"
844 "d,Op,b,D,RT,BQ,Q")))]
845 "s390_match_ccmode (insn, CCUmode) && TARGET_64BIT"
846 "@
847 clgr\t%0,%1
848 clgfi\t%0,%1
849 clgrl\t%0,%1
850 clghsi\t%0,%x1
851 clg\t%0,%1
852 #
853 #"
854 [(set_attr "op_type" "RRE,RIL,RIL,SIL,RXY,SS,SS")
855 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*")
856 (set_attr "type" "*,*,larl,*,*,*,*")])
857
858 (define_insn "*cmpsi_ccu"
859 [(set (reg CC_REGNUM)
860 (compare (match_operand:SI 0 "nonimmediate_operand" "d, d,d,Q,d,d, Q,BQ")
861 (match_operand:SI 1 "general_operand" "d,Os,b,D,R,T,BQ, Q")))]
862 "s390_match_ccmode (insn, CCUmode)"
863 "@
864 clr\t%0,%1
865 clfi\t%0,%o1
866 clrl\t%0,%1
867 clfhsi\t%0,%x1
868 cl\t%0,%1
869 cly\t%0,%1
870 #
871 #"
872 [(set_attr "op_type" "RR,RIL,RIL,SIL,RX,RXY,SS,SS")
873 (set_attr "cpu_facility" "*,extimm,z10,z10,*,*,*,*")
874 (set_attr "type" "*,*,larl,*,*,*,*,*")])
875
876 (define_insn "*cmphi_ccu"
877 [(set (reg CC_REGNUM)
878 (compare (match_operand:HI 0 "nonimmediate_operand" "d,d,Q,Q,BQ")
879 (match_operand:HI 1 "general_operand" "Q,S,D,BQ,Q")))]
880 "s390_match_ccmode (insn, CCUmode)
881 && !register_operand (operands[1], HImode)"
882 "@
883 clm\t%0,3,%S1
884 clmy\t%0,3,%S1
885 clhhsi\t%0,%1
886 #
887 #"
888 [(set_attr "op_type" "RS,RSY,SIL,SS,SS")
889 (set_attr "cpu_facility" "*,*,z10,*,*")])
890
891 (define_insn "*cmpqi_ccu"
892 [(set (reg CC_REGNUM)
893 (compare (match_operand:QI 0 "nonimmediate_operand" "d,d,Q,S,Q,BQ")
894 (match_operand:QI 1 "general_operand" "Q,S,n,n,BQ,Q")))]
895 "s390_match_ccmode (insn, CCUmode)
896 && !register_operand (operands[1], QImode)"
897 "@
898 clm\t%0,1,%S1
899 clmy\t%0,1,%S1
900 cli\t%S0,%b1
901 cliy\t%S0,%b1
902 #
903 #"
904 [(set_attr "op_type" "RS,RSY,SI,SIY,SS,SS")])
905
906
907 ; Block compare (CLC) instruction patterns.
908
909 (define_insn "*clc"
910 [(set (reg CC_REGNUM)
911 (compare (match_operand:BLK 0 "memory_operand" "Q")
912 (match_operand:BLK 1 "memory_operand" "Q")))
913 (use (match_operand 2 "const_int_operand" "n"))]
914 "s390_match_ccmode (insn, CCUmode)
915 && INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
916 "clc\t%O0(%2,%R0),%S1"
917 [(set_attr "op_type" "SS")])
918
919 (define_split
920 [(set (reg CC_REGNUM)
921 (compare (match_operand 0 "memory_operand" "")
922 (match_operand 1 "memory_operand" "")))]
923 "reload_completed
924 && s390_match_ccmode (insn, CCUmode)
925 && GET_MODE (operands[0]) == GET_MODE (operands[1])
926 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
927 [(parallel
928 [(set (match_dup 0) (match_dup 1))
929 (use (match_dup 2))])]
930 {
931 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
932 operands[0] = adjust_address (operands[0], BLKmode, 0);
933 operands[1] = adjust_address (operands[1], BLKmode, 0);
934
935 operands[1] = gen_rtx_COMPARE (GET_MODE (SET_DEST (PATTERN (curr_insn))),
936 operands[0], operands[1]);
937 operands[0] = SET_DEST (PATTERN (curr_insn));
938 })
939
940
941 ; (TF|DF|SF|TD|DD|SD) instructions
942
943 ; ltxbr, ltdbr, ltebr, ltxtr, ltdtr
944 (define_insn "*cmp<mode>_ccs_0"
945 [(set (reg CC_REGNUM)
946 (compare (match_operand:FP 0 "register_operand" "f")
947 (match_operand:FP 1 "const0_operand" "")))]
948 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
949 "lt<xde><bt>r\t%0,%0"
950 [(set_attr "op_type" "RRE")
951 (set_attr "type" "fsimp<bfp>")])
952
953 ; cxtr, cxbr, cdbr, cebr, cxb, cdb, ceb, cxbtr, cdbtr
954 (define_insn "*cmp<mode>_ccs"
955 [(set (reg CC_REGNUM)
956 (compare (match_operand:FP 0 "register_operand" "f,f")
957 (match_operand:FP 1 "general_operand" "f,<Rf>")))]
958 "s390_match_ccmode(insn, CCSmode) && TARGET_HARD_FLOAT"
959 "@
960 c<xde><bt>r\t%0,%1
961 c<xde>b\t%0,%1"
962 [(set_attr "op_type" "RRE,RXE")
963 (set_attr "type" "fsimp<bfp>")])
964
965
966 ; Compare and Branch instructions
967
968 ; cij, cgij, crj, cgrj, cfi, cgfi, cr, cgr
969 (define_insn "*cmp_and_br_signed_<mode>"
970 [(set (pc)
971 (if_then_else (match_operator 0 "s390_signed_integer_comparison"
972 [(match_operand:GPR 1 "register_operand" "d,d")
973 (match_operand:GPR 2 "nonmemory_operand" "d,C")])
974 (label_ref (match_operand 3 "" ""))
975 (pc)))
976 (clobber (reg:CC CC_REGNUM))]
977 "TARGET_Z10"
978 {
979 if (get_attr_length (insn) == 6)
980 return which_alternative ?
981 "c<g>ij%C0\t%1,%c2,%l3" : "c<g>rj%C0\t%1,%2,%l3";
982 else
983 return which_alternative ?
984 "c<g>fi\t%1,%c2\;jg%C0\t%l3" : "c<g>r\t%1,%2\;jg%C0\t%l3";
985 }
986 [(set_attr "op_type" "RIE")
987 (set_attr "type" "branch")
988 (set (attr "length")
989 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
990 (const_int 6) (const_int 12)))]) ; 8 byte for cr/jg
991 ; 10 byte for cgr/jg
992
993 ; clij, clgij, clrj, clgrj, clfi, clgfi, clr, clgr
994 (define_insn "*cmp_and_br_unsigned_<mode>"
995 [(set (pc)
996 (if_then_else (match_operator 0 "s390_unsigned_integer_comparison"
997 [(match_operand:GPR 1 "register_operand" "d,d")
998 (match_operand:GPR 2 "nonmemory_operand" "d,I")])
999 (label_ref (match_operand 3 "" ""))
1000 (pc)))
1001 (clobber (reg:CC CC_REGNUM))]
1002 "TARGET_Z10"
1003 {
1004 if (get_attr_length (insn) == 6)
1005 return which_alternative ?
1006 "cl<g>ij%C0\t%1,%b2,%l3" : "cl<g>rj%C0\t%1,%2,%l3";
1007 else
1008 return which_alternative ?
1009 "cl<g>fi\t%1,%b2\;jg%C0\t%l3" : "cl<g>r\t%1,%2\;jg%C0\t%l3";
1010 }
1011 [(set_attr "op_type" "RIE")
1012 (set_attr "type" "branch")
1013 (set (attr "length")
1014 (if_then_else (lt (abs (minus (pc) (match_dup 3))) (const_int 60000))
1015 (const_int 6) (const_int 12)))]) ; 8 byte for clr/jg
1016 ; 10 byte for clgr/jg
1017
1018 ;;
1019 ;;- Move instructions.
1020 ;;
1021
1022 ;
1023 ; movti instruction pattern(s).
1024 ;
1025
1026 (define_insn "movti"
1027 [(set (match_operand:TI 0 "nonimmediate_operand" "=d,QS,d,o,Q")
1028 (match_operand:TI 1 "general_operand" "QS,d,dPRT,d,Q"))]
1029 "TARGET_64BIT"
1030 "@
1031 lmg\t%0,%N0,%S1
1032 stmg\t%1,%N1,%S0
1033 #
1034 #
1035 #"
1036 [(set_attr "op_type" "RSY,RSY,*,*,SS")
1037 (set_attr "type" "lm,stm,*,*,*")])
1038
1039 (define_split
1040 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1041 (match_operand:TI 1 "general_operand" ""))]
1042 "TARGET_64BIT && reload_completed
1043 && s390_split_ok_p (operands[0], operands[1], TImode, 0)"
1044 [(set (match_dup 2) (match_dup 4))
1045 (set (match_dup 3) (match_dup 5))]
1046 {
1047 operands[2] = operand_subword (operands[0], 0, 0, TImode);
1048 operands[3] = operand_subword (operands[0], 1, 0, TImode);
1049 operands[4] = operand_subword (operands[1], 0, 0, TImode);
1050 operands[5] = operand_subword (operands[1], 1, 0, TImode);
1051 })
1052
1053 (define_split
1054 [(set (match_operand:TI 0 "nonimmediate_operand" "")
1055 (match_operand:TI 1 "general_operand" ""))]
1056 "TARGET_64BIT && reload_completed
1057 && s390_split_ok_p (operands[0], operands[1], TImode, 1)"
1058 [(set (match_dup 2) (match_dup 4))
1059 (set (match_dup 3) (match_dup 5))]
1060 {
1061 operands[2] = operand_subword (operands[0], 1, 0, TImode);
1062 operands[3] = operand_subword (operands[0], 0, 0, TImode);
1063 operands[4] = operand_subword (operands[1], 1, 0, TImode);
1064 operands[5] = operand_subword (operands[1], 0, 0, TImode);
1065 })
1066
1067 (define_split
1068 [(set (match_operand:TI 0 "register_operand" "")
1069 (match_operand:TI 1 "memory_operand" ""))]
1070 "TARGET_64BIT && reload_completed
1071 && !s_operand (operands[1], VOIDmode)"
1072 [(set (match_dup 0) (match_dup 1))]
1073 {
1074 rtx addr = operand_subword (operands[0], 1, 0, TImode);
1075 s390_load_address (addr, XEXP (operands[1], 0));
1076 operands[1] = replace_equiv_address (operands[1], addr);
1077 })
1078
1079
1080 ;
1081 ; Patterns used for secondary reloads
1082 ;
1083
1084 ; z10 provides move instructions accepting larl memory operands.
1085 ; Unfortunately there is no such variant for QI, TI and FP mode moves.
1086 ; These patterns are also used for unaligned SI and DI accesses.
1087
1088 (define_expand "reload<INTALL:mode><P:mode>_tomem_z10"
1089 [(parallel [(match_operand:INTALL 0 "memory_operand" "")
1090 (match_operand:INTALL 1 "register_operand" "=d")
1091 (match_operand:P 2 "register_operand" "=&a")])]
1092 "TARGET_Z10"
1093 {
1094 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1095 DONE;
1096 })
1097
1098 (define_expand "reload<INTALL:mode><P:mode>_toreg_z10"
1099 [(parallel [(match_operand:INTALL 0 "register_operand" "=d")
1100 (match_operand:INTALL 1 "memory_operand" "")
1101 (match_operand:P 2 "register_operand" "=a")])]
1102 "TARGET_Z10"
1103 {
1104 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1105 DONE;
1106 })
1107
1108 (define_expand "reload<FPALL:mode><P:mode>_tomem_z10"
1109 [(parallel [(match_operand:FPALL 0 "memory_operand" "")
1110 (match_operand:FPALL 1 "register_operand" "=d")
1111 (match_operand:P 2 "register_operand" "=&a")])]
1112 "TARGET_Z10"
1113 {
1114 s390_reload_symref_address (operands[1], operands[0], operands[2], 1);
1115 DONE;
1116 })
1117
1118 (define_expand "reload<FPALL:mode><P:mode>_toreg_z10"
1119 [(parallel [(match_operand:FPALL 0 "register_operand" "=d")
1120 (match_operand:FPALL 1 "memory_operand" "")
1121 (match_operand:P 2 "register_operand" "=a")])]
1122 "TARGET_Z10"
1123 {
1124 s390_reload_symref_address (operands[0], operands[1], operands[2], 0);
1125 DONE;
1126 })
1127
1128 (define_expand "reload<P:mode>_larl_odd_addend_z10"
1129 [(parallel [(match_operand:P 0 "register_operand" "=d")
1130 (match_operand:P 1 "larl_operand" "")
1131 (match_operand:P 2 "register_operand" "=a")])]
1132 "TARGET_Z10"
1133 {
1134 s390_reload_larl_operand (operands[0], operands[1], operands[2]);
1135 DONE;
1136 })
1137
1138 ; Handles loading a PLUS (load address) expression
1139
1140 (define_expand "reload<mode>_plus"
1141 [(parallel [(match_operand:P 0 "register_operand" "=a")
1142 (match_operand:P 1 "s390_plus_operand" "")
1143 (match_operand:P 2 "register_operand" "=&a")])]
1144 ""
1145 {
1146 s390_expand_plus_operand (operands[0], operands[1], operands[2]);
1147 DONE;
1148 })
1149
1150 ; Handles assessing a non-offsetable memory address
1151
1152 (define_expand "reload<mode>_nonoffmem_in"
1153 [(parallel [(match_operand 0 "register_operand" "")
1154 (match_operand 1 "" "")
1155 (match_operand:P 2 "register_operand" "=&a")])]
1156 ""
1157 {
1158 gcc_assert (MEM_P (operands[1]));
1159 s390_load_address (operands[2], find_replacement (&XEXP (operands[1], 0)));
1160 operands[1] = replace_equiv_address (operands[1], operands[2]);
1161 emit_move_insn (operands[0], operands[1]);
1162 DONE;
1163 })
1164
1165 (define_expand "reload<mode>_nonoffmem_out"
1166 [(parallel [(match_operand 0 "" "")
1167 (match_operand 1 "register_operand" "")
1168 (match_operand:P 2 "register_operand" "=&a")])]
1169 ""
1170 {
1171 gcc_assert (MEM_P (operands[0]));
1172 s390_load_address (operands[2], find_replacement (&XEXP (operands[0], 0)));
1173 operands[0] = replace_equiv_address (operands[0], operands[2]);
1174 emit_move_insn (operands[0], operands[1]);
1175 DONE;
1176 })
1177
1178 ;
1179 ; movdi instruction pattern(s).
1180 ;
1181
1182 (define_expand "movdi"
1183 [(set (match_operand:DI 0 "general_operand" "")
1184 (match_operand:DI 1 "general_operand" ""))]
1185 ""
1186 {
1187 /* Handle symbolic constants. */
1188 if (TARGET_64BIT
1189 && (SYMBOLIC_CONST (operands[1])
1190 || (GET_CODE (operands[1]) == PLUS
1191 && XEXP (operands[1], 0) == pic_offset_table_rtx
1192 && SYMBOLIC_CONST (XEXP (operands[1], 1)))))
1193 emit_symbolic_move (operands);
1194 })
1195
1196 (define_insn "*movdi_larl"
1197 [(set (match_operand:DI 0 "register_operand" "=d")
1198 (match_operand:DI 1 "larl_operand" "X"))]
1199 "TARGET_64BIT
1200 && !FP_REG_P (operands[0])"
1201 "larl\t%0,%1"
1202 [(set_attr "op_type" "RIL")
1203 (set_attr "type" "larl")])
1204
1205 (define_insn "*movdi_64"
1206 [(set (match_operand:DI 0 "nonimmediate_operand"
1207 "=d,d,d,d,d,d,d,d,f,d,d,d,d,d,
1208 RT,!*f,!*f,!*f,!R,!T,b,Q,d,t,Q,t,?Q")
1209 (match_operand:DI 1 "general_operand"
1210 "K,N0HD0,N1HD0,N2HD0,N3HD0,Os,N0SD0,N1SD0,d,f,L,b,d,RT,
1211 d,*f,R,T,*f,*f,d,K,t,d,t,Q,?Q"))]
1212 "TARGET_64BIT"
1213 "@
1214 lghi\t%0,%h1
1215 llihh\t%0,%i1
1216 llihl\t%0,%i1
1217 llilh\t%0,%i1
1218 llill\t%0,%i1
1219 lgfi\t%0,%1
1220 llihf\t%0,%k1
1221 llilf\t%0,%k1
1222 ldgr\t%0,%1
1223 lgdr\t%0,%1
1224 lay\t%0,%a1
1225 lgrl\t%0,%1
1226 lgr\t%0,%1
1227 lg\t%0,%1
1228 stg\t%1,%0
1229 ldr\t%0,%1
1230 ld\t%0,%1
1231 ldy\t%0,%1
1232 std\t%1,%0
1233 stdy\t%1,%0
1234 stgrl\t%1,%0
1235 mvghi\t%0,%1
1236 #
1237 #
1238 stam\t%1,%N1,%S0
1239 lam\t%0,%N0,%S1
1240 #"
1241 [(set_attr "op_type" "RI,RI,RI,RI,RI,RIL,RIL,RIL,RRE,RRE,RXY,RIL,RRE,RXY,
1242 RXY,RR,RX,RXY,RX,RXY,RIL,SIL,*,*,RS,RS,SS")
1243 (set_attr "type" "*,*,*,*,*,*,*,*,floaddf,floaddf,la,larl,lr,load,store,
1244 floaddf,floaddf,floaddf,fstoredf,fstoredf,larl,*,*,*,
1245 *,*,*")
1246 (set_attr "cpu_facility" "*,*,*,*,*,extimm,extimm,extimm,dfp,dfp,longdisp,
1247 z10,*,*,*,*,*,longdisp,*,longdisp,
1248 z10,z10,*,*,*,*,*")])
1249
1250 (define_split
1251 [(set (match_operand:DI 0 "register_operand" "")
1252 (match_operand:DI 1 "register_operand" ""))]
1253 "TARGET_64BIT && ACCESS_REG_P (operands[1])"
1254 [(set (match_dup 2) (match_dup 3))
1255 (set (match_dup 0) (ashift:DI (match_dup 0) (const_int 32)))
1256 (set (strict_low_part (match_dup 2)) (match_dup 4))]
1257 "operands[2] = gen_lowpart (SImode, operands[0]);
1258 s390_split_access_reg (operands[1], &operands[4], &operands[3]);")
1259
1260 (define_split
1261 [(set (match_operand:DI 0 "register_operand" "")
1262 (match_operand:DI 1 "register_operand" ""))]
1263 "TARGET_64BIT && ACCESS_REG_P (operands[0])
1264 && dead_or_set_p (insn, operands[1])"
1265 [(set (match_dup 3) (match_dup 2))
1266 (set (match_dup 1) (lshiftrt:DI (match_dup 1) (const_int 32)))
1267 (set (match_dup 4) (match_dup 2))]
1268 "operands[2] = gen_lowpart (SImode, operands[1]);
1269 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1270
1271 (define_split
1272 [(set (match_operand:DI 0 "register_operand" "")
1273 (match_operand:DI 1 "register_operand" ""))]
1274 "TARGET_64BIT && ACCESS_REG_P (operands[0])
1275 && !dead_or_set_p (insn, operands[1])"
1276 [(set (match_dup 3) (match_dup 2))
1277 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))
1278 (set (match_dup 4) (match_dup 2))
1279 (set (match_dup 1) (rotate:DI (match_dup 1) (const_int 32)))]
1280 "operands[2] = gen_lowpart (SImode, operands[1]);
1281 s390_split_access_reg (operands[0], &operands[3], &operands[4]);")
1282
1283 (define_insn "*movdi_31"
1284 [(set (match_operand:DI 0 "nonimmediate_operand"
1285 "=d,d,Q,S,d ,o,!*f,!*f,!*f,!R,!T,Q,d")
1286 (match_operand:DI 1 "general_operand"
1287 " Q,S,d,d,dPRT,d, *f, R, T,*f,*f,Q,b"))]
1288 "!TARGET_64BIT"
1289 "@
1290 lm\t%0,%N0,%S1
1291 lmy\t%0,%N0,%S1
1292 stm\t%1,%N1,%S0
1293 stmy\t%1,%N1,%S0
1294 #
1295 #
1296 ldr\t%0,%1
1297 ld\t%0,%1
1298 ldy\t%0,%1
1299 std\t%1,%0
1300 stdy\t%1,%0
1301 #
1302 #"
1303 [(set_attr "op_type" "RS,RSY,RS,RSY,*,*,RR,RX,RXY,RX,RXY,SS,*")
1304 (set_attr "type" "lm,lm,stm,stm,*,*,floaddf,floaddf,floaddf,fstoredf,fstoredf,*,*")
1305 (set_attr "cpu_facility" "*,*,*,*,*,*,*,*,*,*,*,*,z10")])
1306
1307 ; For a load from a symbol ref we can use one of the target registers
1308 ; together with larl to load the address.
1309 (define_split
1310 [(set (match_operand:DI 0 "register_operand" "")
1311 (match_operand:DI 1 "memory_operand" ""))]
1312 "!TARGET_64BIT && reload_completed && TARGET_Z10
1313 && larl_operand (XEXP (operands[1], 0), SImode)"
1314 [(set (match_dup 2) (match_dup 3))
1315 (set (match_dup 0) (match_dup 1))]
1316 {
1317 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1318 operands[3] = XEXP (operands[1], 0);
1319 operands[1] = replace_equiv_address (operands[1], operands[2]);
1320 })
1321
1322 (define_split
1323 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1324 (match_operand:DI 1 "general_operand" ""))]
1325 "!TARGET_64BIT && reload_completed
1326 && s390_split_ok_p (operands[0], operands[1], DImode, 0)"
1327 [(set (match_dup 2) (match_dup 4))
1328 (set (match_dup 3) (match_dup 5))]
1329 {
1330 operands[2] = operand_subword (operands[0], 0, 0, DImode);
1331 operands[3] = operand_subword (operands[0], 1, 0, DImode);
1332 operands[4] = operand_subword (operands[1], 0, 0, DImode);
1333 operands[5] = operand_subword (operands[1], 1, 0, DImode);
1334 })
1335
1336 (define_split
1337 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1338 (match_operand:DI 1 "general_operand" ""))]
1339 "!TARGET_64BIT && reload_completed
1340 && s390_split_ok_p (operands[0], operands[1], DImode, 1)"
1341 [(set (match_dup 2) (match_dup 4))
1342 (set (match_dup 3) (match_dup 5))]
1343 {
1344 operands[2] = operand_subword (operands[0], 1, 0, DImode);
1345 operands[3] = operand_subword (operands[0], 0, 0, DImode);
1346 operands[4] = operand_subword (operands[1], 1, 0, DImode);
1347 operands[5] = operand_subword (operands[1], 0, 0, DImode);
1348 })
1349
1350 (define_split
1351 [(set (match_operand:DI 0 "register_operand" "")
1352 (match_operand:DI 1 "memory_operand" ""))]
1353 "!TARGET_64BIT && reload_completed
1354 && !FP_REG_P (operands[0])
1355 && !s_operand (operands[1], VOIDmode)"
1356 [(set (match_dup 0) (match_dup 1))]
1357 {
1358 rtx addr = operand_subword (operands[0], 1, 0, DImode);
1359 s390_load_address (addr, XEXP (operands[1], 0));
1360 operands[1] = replace_equiv_address (operands[1], addr);
1361 })
1362
1363 (define_peephole2
1364 [(set (match_operand:DI 0 "register_operand" "")
1365 (mem:DI (match_operand 1 "address_operand" "")))]
1366 "TARGET_64BIT
1367 && !FP_REG_P (operands[0])
1368 && GET_CODE (operands[1]) == SYMBOL_REF
1369 && CONSTANT_POOL_ADDRESS_P (operands[1])
1370 && get_pool_mode (operands[1]) == DImode
1371 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1372 [(set (match_dup 0) (match_dup 2))]
1373 "operands[2] = get_pool_constant (operands[1]);")
1374
1375 (define_insn "*la_64"
1376 [(set (match_operand:DI 0 "register_operand" "=d,d")
1377 (match_operand:QI 1 "address_operand" "U,W"))]
1378 "TARGET_64BIT"
1379 "@
1380 la\t%0,%a1
1381 lay\t%0,%a1"
1382 [(set_attr "op_type" "RX,RXY")
1383 (set_attr "type" "la")])
1384
1385 (define_peephole2
1386 [(parallel
1387 [(set (match_operand:DI 0 "register_operand" "")
1388 (match_operand:QI 1 "address_operand" ""))
1389 (clobber (reg:CC CC_REGNUM))])]
1390 "TARGET_64BIT
1391 && preferred_la_operand_p (operands[1], const0_rtx)"
1392 [(set (match_dup 0) (match_dup 1))]
1393 "")
1394
1395 (define_peephole2
1396 [(set (match_operand:DI 0 "register_operand" "")
1397 (match_operand:DI 1 "register_operand" ""))
1398 (parallel
1399 [(set (match_dup 0)
1400 (plus:DI (match_dup 0)
1401 (match_operand:DI 2 "nonmemory_operand" "")))
1402 (clobber (reg:CC CC_REGNUM))])]
1403 "TARGET_64BIT
1404 && !reg_overlap_mentioned_p (operands[0], operands[2])
1405 && preferred_la_operand_p (operands[1], operands[2])"
1406 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))]
1407 "")
1408
1409 ;
1410 ; movsi instruction pattern(s).
1411 ;
1412
1413 (define_expand "movsi"
1414 [(set (match_operand:SI 0 "general_operand" "")
1415 (match_operand:SI 1 "general_operand" ""))]
1416 ""
1417 {
1418 /* Handle symbolic constants. */
1419 if (!TARGET_64BIT
1420 && (SYMBOLIC_CONST (operands[1])
1421 || (GET_CODE (operands[1]) == PLUS
1422 && XEXP (operands[1], 0) == pic_offset_table_rtx
1423 && SYMBOLIC_CONST (XEXP(operands[1], 1)))))
1424 emit_symbolic_move (operands);
1425 })
1426
1427 (define_insn "*movsi_larl"
1428 [(set (match_operand:SI 0 "register_operand" "=d")
1429 (match_operand:SI 1 "larl_operand" "X"))]
1430 "!TARGET_64BIT && TARGET_CPU_ZARCH
1431 && !FP_REG_P (operands[0])"
1432 "larl\t%0,%1"
1433 [(set_attr "op_type" "RIL")
1434 (set_attr "type" "larl")])
1435
1436 (define_insn "*movsi_zarch"
1437 [(set (match_operand:SI 0 "nonimmediate_operand"
1438 "=d,d,d,d,d,d,d,d,d,R,T,!*f,!*f,!*f,!R,!T,d,t,Q,b,Q,t,?Q")
1439 (match_operand:SI 1 "general_operand"
1440 "K,N0HS0,N1HS0,Os,L,b,d,R,T,d,d,*f,R,T,*f,*f,t,d,t,d,K,Q,?Q"))]
1441 "TARGET_ZARCH"
1442 "@
1443 lhi\t%0,%h1
1444 llilh\t%0,%i1
1445 llill\t%0,%i1
1446 iilf\t%0,%o1
1447 lay\t%0,%a1
1448 lrl\t%0,%1
1449 lr\t%0,%1
1450 l\t%0,%1
1451 ly\t%0,%1
1452 st\t%1,%0
1453 sty\t%1,%0
1454 ler\t%0,%1
1455 le\t%0,%1
1456 ley\t%0,%1
1457 ste\t%1,%0
1458 stey\t%1,%0
1459 ear\t%0,%1
1460 sar\t%0,%1
1461 stam\t%1,%1,%S0
1462 strl\t%1,%0
1463 mvhi\t%0,%1
1464 lam\t%0,%0,%S1
1465 #"
1466 [(set_attr "op_type" "RI,RI,RI,RIL,RXY,RIL,RR,RX,RXY,RX,RXY,
1467 RR,RX,RXY,RX,RXY,RRE,RRE,RS,RIL,SIL,RS,SS")
1468 (set_attr "type" "*,*,*,*,la,larl,lr,load,load,store,store,
1469 floadsf,floadsf,floadsf,fstoresf,fstoresf,*,*,*,larl,*,*,*")
1470 (set_attr "cpu_facility" "*,*,*,extimm,longdisp,z10,*,*,longdisp,*,longdisp,
1471 *,*,longdisp,*,longdisp,*,*,*,z10,z10,*,*")])
1472
1473 (define_insn "*movsi_esa"
1474 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,R,!*f,!*f,!R,d,t,Q,t,?Q")
1475 (match_operand:SI 1 "general_operand" "K,d,R,d,*f,R,*f,t,d,t,Q,?Q"))]
1476 "!TARGET_ZARCH"
1477 "@
1478 lhi\t%0,%h1
1479 lr\t%0,%1
1480 l\t%0,%1
1481 st\t%1,%0
1482 ler\t%0,%1
1483 le\t%0,%1
1484 ste\t%1,%0
1485 ear\t%0,%1
1486 sar\t%0,%1
1487 stam\t%1,%1,%S0
1488 lam\t%0,%0,%S1
1489 #"
1490 [(set_attr "op_type" "RI,RR,RX,RX,RR,RX,RX,RRE,RRE,RS,RS,SS")
1491 (set_attr "type" "*,lr,load,store,floadsf,floadsf,fstoresf,*,*,*,*,*")])
1492
1493 (define_peephole2
1494 [(set (match_operand:SI 0 "register_operand" "")
1495 (mem:SI (match_operand 1 "address_operand" "")))]
1496 "!FP_REG_P (operands[0])
1497 && GET_CODE (operands[1]) == SYMBOL_REF
1498 && CONSTANT_POOL_ADDRESS_P (operands[1])
1499 && get_pool_mode (operands[1]) == SImode
1500 && legitimate_reload_constant_p (get_pool_constant (operands[1]))"
1501 [(set (match_dup 0) (match_dup 2))]
1502 "operands[2] = get_pool_constant (operands[1]);")
1503
1504 (define_insn "*la_31"
1505 [(set (match_operand:SI 0 "register_operand" "=d,d")
1506 (match_operand:QI 1 "address_operand" "U,W"))]
1507 "!TARGET_64BIT && legitimate_la_operand_p (operands[1])"
1508 "@
1509 la\t%0,%a1
1510 lay\t%0,%a1"
1511 [(set_attr "op_type" "RX,RXY")
1512 (set_attr "type" "la")])
1513
1514 (define_peephole2
1515 [(parallel
1516 [(set (match_operand:SI 0 "register_operand" "")
1517 (match_operand:QI 1 "address_operand" ""))
1518 (clobber (reg:CC CC_REGNUM))])]
1519 "!TARGET_64BIT
1520 && preferred_la_operand_p (operands[1], const0_rtx)"
1521 [(set (match_dup 0) (match_dup 1))]
1522 "")
1523
1524 (define_peephole2
1525 [(set (match_operand:SI 0 "register_operand" "")
1526 (match_operand:SI 1 "register_operand" ""))
1527 (parallel
1528 [(set (match_dup 0)
1529 (plus:SI (match_dup 0)
1530 (match_operand:SI 2 "nonmemory_operand" "")))
1531 (clobber (reg:CC CC_REGNUM))])]
1532 "!TARGET_64BIT
1533 && !reg_overlap_mentioned_p (operands[0], operands[2])
1534 && preferred_la_operand_p (operands[1], operands[2])"
1535 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))]
1536 "")
1537
1538 (define_insn "*la_31_and"
1539 [(set (match_operand:SI 0 "register_operand" "=d,d")
1540 (and:SI (match_operand:QI 1 "address_operand" "U,W")
1541 (const_int 2147483647)))]
1542 "!TARGET_64BIT"
1543 "@
1544 la\t%0,%a1
1545 lay\t%0,%a1"
1546 [(set_attr "op_type" "RX,RXY")
1547 (set_attr "type" "la")])
1548
1549 (define_insn_and_split "*la_31_and_cc"
1550 [(set (match_operand:SI 0 "register_operand" "=d")
1551 (and:SI (match_operand:QI 1 "address_operand" "p")
1552 (const_int 2147483647)))
1553 (clobber (reg:CC CC_REGNUM))]
1554 "!TARGET_64BIT"
1555 "#"
1556 "&& reload_completed"
1557 [(set (match_dup 0)
1558 (and:SI (match_dup 1) (const_int 2147483647)))]
1559 ""
1560 [(set_attr "op_type" "RX")
1561 (set_attr "type" "la")])
1562
1563 (define_insn "force_la_31"
1564 [(set (match_operand:SI 0 "register_operand" "=d,d")
1565 (match_operand:QI 1 "address_operand" "U,W"))
1566 (use (const_int 0))]
1567 "!TARGET_64BIT"
1568 "@
1569 la\t%0,%a1
1570 lay\t%0,%a1"
1571 [(set_attr "op_type" "RX")
1572 (set_attr "type" "la")])
1573
1574 ;
1575 ; movhi instruction pattern(s).
1576 ;
1577
1578 (define_expand "movhi"
1579 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1580 (match_operand:HI 1 "general_operand" ""))]
1581 ""
1582 {
1583 /* Make it explicit that loading a register from memory
1584 always sign-extends (at least) to SImode. */
1585 if (optimize && can_create_pseudo_p ()
1586 && register_operand (operands[0], VOIDmode)
1587 && GET_CODE (operands[1]) == MEM)
1588 {
1589 rtx tmp = gen_reg_rtx (SImode);
1590 rtx ext = gen_rtx_SIGN_EXTEND (SImode, operands[1]);
1591 emit_insn (gen_rtx_SET (VOIDmode, tmp, ext));
1592 operands[1] = gen_lowpart (HImode, tmp);
1593 }
1594 })
1595
1596 (define_insn "*movhi"
1597 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,d,R,T,b,Q,?Q")
1598 (match_operand:HI 1 "general_operand" " d,n,R,T,b,d,d,d,K,?Q"))]
1599 ""
1600 "@
1601 lr\t%0,%1
1602 lhi\t%0,%h1
1603 lh\t%0,%1
1604 lhy\t%0,%1
1605 lhrl\t%0,%1
1606 sth\t%1,%0
1607 sthy\t%1,%0
1608 sthrl\t%1,%0
1609 mvhhi\t%0,%1
1610 #"
1611 [(set_attr "op_type" "RR,RI,RX,RXY,RIL,RX,RXY,RIL,SIL,SS")
1612 (set_attr "type" "lr,*,*,*,larl,store,store,store,*,*")
1613 (set_attr "cpu_facility" "*,*,*,*,z10,*,*,z10,z10,*")])
1614
1615 (define_peephole2
1616 [(set (match_operand:HI 0 "register_operand" "")
1617 (mem:HI (match_operand 1 "address_operand" "")))]
1618 "GET_CODE (operands[1]) == SYMBOL_REF
1619 && CONSTANT_POOL_ADDRESS_P (operands[1])
1620 && get_pool_mode (operands[1]) == HImode
1621 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
1622 [(set (match_dup 0) (match_dup 2))]
1623 "operands[2] = get_pool_constant (operands[1]);")
1624
1625 ;
1626 ; movqi instruction pattern(s).
1627 ;
1628
1629 (define_expand "movqi"
1630 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1631 (match_operand:QI 1 "general_operand" ""))]
1632 ""
1633 {
1634 /* On z/Architecture, zero-extending from memory to register
1635 is just as fast as a QImode load. */
1636 if (TARGET_ZARCH && optimize && can_create_pseudo_p ()
1637 && register_operand (operands[0], VOIDmode)
1638 && GET_CODE (operands[1]) == MEM)
1639 {
1640 rtx tmp = gen_reg_rtx (word_mode);
1641 rtx ext = gen_rtx_ZERO_EXTEND (word_mode, operands[1]);
1642 emit_insn (gen_rtx_SET (VOIDmode, tmp, ext));
1643 operands[1] = gen_lowpart (QImode, tmp);
1644 }
1645 })
1646
1647 (define_insn "*movqi"
1648 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,T,Q,S,?Q")
1649 (match_operand:QI 1 "general_operand" "d,n,R,T,d,d,n,n,?Q"))]
1650 ""
1651 "@
1652 lr\t%0,%1
1653 lhi\t%0,%b1
1654 ic\t%0,%1
1655 icy\t%0,%1
1656 stc\t%1,%0
1657 stcy\t%1,%0
1658 mvi\t%S0,%b1
1659 mviy\t%S0,%b1
1660 #"
1661 [(set_attr "op_type" "RR,RI,RX,RXY,RX,RXY,SI,SIY,SS")
1662 (set_attr "type" "lr,*,*,*,store,store,store,store,*")])
1663
1664 (define_peephole2
1665 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1666 (mem:QI (match_operand 1 "address_operand" "")))]
1667 "GET_CODE (operands[1]) == SYMBOL_REF
1668 && CONSTANT_POOL_ADDRESS_P (operands[1])
1669 && get_pool_mode (operands[1]) == QImode
1670 && GET_CODE (get_pool_constant (operands[1])) == CONST_INT"
1671 [(set (match_dup 0) (match_dup 2))]
1672 "operands[2] = get_pool_constant (operands[1]);")
1673
1674 ;
1675 ; movstrictqi instruction pattern(s).
1676 ;
1677
1678 (define_insn "*movstrictqi"
1679 [(set (strict_low_part (match_operand:QI 0 "register_operand" "+d,d"))
1680 (match_operand:QI 1 "memory_operand" "R,T"))]
1681 ""
1682 "@
1683 ic\t%0,%1
1684 icy\t%0,%1"
1685 [(set_attr "op_type" "RX,RXY")])
1686
1687 ;
1688 ; movstricthi instruction pattern(s).
1689 ;
1690
1691 (define_insn "*movstricthi"
1692 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d,d"))
1693 (match_operand:HI 1 "memory_operand" "Q,S"))
1694 (clobber (reg:CC CC_REGNUM))]
1695 ""
1696 "@
1697 icm\t%0,3,%S1
1698 icmy\t%0,3,%S1"
1699 [(set_attr "op_type" "RS,RSY")])
1700
1701 ;
1702 ; movstrictsi instruction pattern(s).
1703 ;
1704
1705 (define_insn "movstrictsi"
1706 [(set (strict_low_part (match_operand:SI 0 "register_operand" "+d,d,d,d"))
1707 (match_operand:SI 1 "general_operand" "d,R,T,t"))]
1708 "TARGET_64BIT"
1709 "@
1710 lr\t%0,%1
1711 l\t%0,%1
1712 ly\t%0,%1
1713 ear\t%0,%1"
1714 [(set_attr "op_type" "RR,RX,RXY,RRE")
1715 (set_attr "type" "lr,load,load,*")])
1716
1717 ;
1718 ; mov(tf|td) instruction pattern(s).
1719 ;
1720
1721 (define_expand "mov<mode>"
1722 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
1723 (match_operand:TD_TF 1 "general_operand" ""))]
1724 ""
1725 "")
1726
1727 (define_insn "*mov<mode>_64"
1728 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o, d,QS, d,o,Q")
1729 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,QS, d,dRT,d,Q"))]
1730 "TARGET_64BIT"
1731 "@
1732 lzxr\t%0
1733 lxr\t%0,%1
1734 #
1735 #
1736 lmg\t%0,%N0,%S1
1737 stmg\t%1,%N1,%S0
1738 #
1739 #
1740 #"
1741 [(set_attr "op_type" "RRE,RRE,*,*,RSY,RSY,*,*,*")
1742 (set_attr "type" "fsimptf,fsimptf,*,*,lm,stm,*,*,*")])
1743
1744 (define_insn "*mov<mode>_31"
1745 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "=f,f,f,o,Q")
1746 (match_operand:TD_TF 1 "general_operand" " G,f,o,f,Q"))]
1747 "!TARGET_64BIT"
1748 "@
1749 lzxr\t%0
1750 lxr\t%0,%1
1751 #
1752 #
1753 #"
1754 [(set_attr "op_type" "RRE,RRE,*,*,*")
1755 (set_attr "type" "fsimptf,fsimptf,*,*,*")])
1756
1757 ; TFmode in GPRs splitters
1758
1759 (define_split
1760 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
1761 (match_operand:TD_TF 1 "general_operand" ""))]
1762 "TARGET_64BIT && reload_completed
1763 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
1764 [(set (match_dup 2) (match_dup 4))
1765 (set (match_dup 3) (match_dup 5))]
1766 {
1767 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
1768 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
1769 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
1770 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
1771 })
1772
1773 (define_split
1774 [(set (match_operand:TD_TF 0 "nonimmediate_operand" "")
1775 (match_operand:TD_TF 1 "general_operand" ""))]
1776 "TARGET_64BIT && reload_completed
1777 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
1778 [(set (match_dup 2) (match_dup 4))
1779 (set (match_dup 3) (match_dup 5))]
1780 {
1781 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
1782 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
1783 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
1784 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
1785 })
1786
1787 (define_split
1788 [(set (match_operand:TD_TF 0 "register_operand" "")
1789 (match_operand:TD_TF 1 "memory_operand" ""))]
1790 "TARGET_64BIT && reload_completed
1791 && !FP_REG_P (operands[0])
1792 && !s_operand (operands[1], VOIDmode)"
1793 [(set (match_dup 0) (match_dup 1))]
1794 {
1795 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
1796 s390_load_address (addr, XEXP (operands[1], 0));
1797 operands[1] = replace_equiv_address (operands[1], addr);
1798 })
1799
1800 ; TFmode in BFPs splitters
1801
1802 (define_split
1803 [(set (match_operand:TD_TF 0 "register_operand" "")
1804 (match_operand:TD_TF 1 "memory_operand" ""))]
1805 "reload_completed && offsettable_memref_p (operands[1])
1806 && FP_REG_P (operands[0])"
1807 [(set (match_dup 2) (match_dup 4))
1808 (set (match_dup 3) (match_dup 5))]
1809 {
1810 operands[2] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
1811 <MODE>mode, 0);
1812 operands[3] = simplify_gen_subreg (<HALF_TMODE>mode, operands[0],
1813 <MODE>mode, 8);
1814 operands[4] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 0);
1815 operands[5] = adjust_address_nv (operands[1], <HALF_TMODE>mode, 8);
1816 })
1817
1818 (define_split
1819 [(set (match_operand:TD_TF 0 "memory_operand" "")
1820 (match_operand:TD_TF 1 "register_operand" ""))]
1821 "reload_completed && offsettable_memref_p (operands[0])
1822 && FP_REG_P (operands[1])"
1823 [(set (match_dup 2) (match_dup 4))
1824 (set (match_dup 3) (match_dup 5))]
1825 {
1826 operands[2] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 0);
1827 operands[3] = adjust_address_nv (operands[0], <HALF_TMODE>mode, 8);
1828 operands[4] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
1829 <MODE>mode, 0);
1830 operands[5] = simplify_gen_subreg (<HALF_TMODE>mode, operands[1],
1831 <MODE>mode, 8);
1832 })
1833
1834 ;
1835 ; mov(df|dd) instruction pattern(s).
1836 ;
1837
1838 (define_expand "mov<mode>"
1839 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
1840 (match_operand:DD_DF 1 "general_operand" ""))]
1841 ""
1842 "")
1843
1844 (define_insn "*mov<mode>_64dfp"
1845 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
1846 "=f,f,f,d,f,f,R,T,d,d,RT,?Q")
1847 (match_operand:DD_DF 1 "general_operand"
1848 "G,f,d,f,R,T,f,f,d,RT,d,?Q"))]
1849 "TARGET_64BIT && TARGET_DFP"
1850 "@
1851 lzdr\t%0
1852 ldr\t%0,%1
1853 ldgr\t%0,%1
1854 lgdr\t%0,%1
1855 ld\t%0,%1
1856 ldy\t%0,%1
1857 std\t%1,%0
1858 stdy\t%1,%0
1859 lgr\t%0,%1
1860 lg\t%0,%1
1861 stg\t%1,%0
1862 #"
1863 [(set_attr "op_type" "RRE,RR,RRE,RRE,RX,RXY,RX,RXY,RRE,RXY,RXY,SS")
1864 (set_attr "type" "fsimpdf,floaddf,floaddf,floaddf,floaddf,floaddf,
1865 fstoredf,fstoredf,lr,load,store,*")])
1866
1867 (define_insn "*mov<mode>_64"
1868 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "=f,f,f,f,R,T,d, d,RT,?Q")
1869 (match_operand:DD_DF 1 "general_operand" "G,f,R,T,f,f,d,RT, d,?Q"))]
1870 "TARGET_64BIT"
1871 "@
1872 lzdr\t%0
1873 ldr\t%0,%1
1874 ld\t%0,%1
1875 ldy\t%0,%1
1876 std\t%1,%0
1877 stdy\t%1,%0
1878 lgr\t%0,%1
1879 lg\t%0,%1
1880 stg\t%1,%0
1881 #"
1882 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RRE,RXY,RXY,SS")
1883 (set_attr "type" "fsimp<bfp>,fload<bfp>,fload<bfp>,fload<bfp>,
1884 fstore<bfp>,fstore<bfp>,lr,load,store,*")])
1885
1886 (define_insn "*mov<mode>_31"
1887 [(set (match_operand:DD_DF 0 "nonimmediate_operand"
1888 "=f,f,f,f,R,T,d,d,Q,S, d,o,Q")
1889 (match_operand:DD_DF 1 "general_operand"
1890 " G,f,R,T,f,f,Q,S,d,d,dPRT,d,Q"))]
1891 "!TARGET_64BIT"
1892 "@
1893 lzdr\t%0
1894 ldr\t%0,%1
1895 ld\t%0,%1
1896 ldy\t%0,%1
1897 std\t%1,%0
1898 stdy\t%1,%0
1899 lm\t%0,%N0,%S1
1900 lmy\t%0,%N0,%S1
1901 stm\t%1,%N1,%S0
1902 stmy\t%1,%N1,%S0
1903 #
1904 #
1905 #"
1906 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RS,RSY,RS,RSY,*,*,SS")
1907 (set_attr "type" "fsimp<bfp>,fload<bfp>,fload<bfp>,fload<bfp>,
1908 fstore<bfp>,fstore<bfp>,lm,lm,stm,stm,*,*,*")])
1909
1910 (define_split
1911 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
1912 (match_operand:DD_DF 1 "general_operand" ""))]
1913 "!TARGET_64BIT && reload_completed
1914 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 0)"
1915 [(set (match_dup 2) (match_dup 4))
1916 (set (match_dup 3) (match_dup 5))]
1917 {
1918 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
1919 operands[3] = operand_subword (operands[0], 1, 0, <MODE>mode);
1920 operands[4] = operand_subword (operands[1], 0, 0, <MODE>mode);
1921 operands[5] = operand_subword (operands[1], 1, 0, <MODE>mode);
1922 })
1923
1924 (define_split
1925 [(set (match_operand:DD_DF 0 "nonimmediate_operand" "")
1926 (match_operand:DD_DF 1 "general_operand" ""))]
1927 "!TARGET_64BIT && reload_completed
1928 && s390_split_ok_p (operands[0], operands[1], <MODE>mode, 1)"
1929 [(set (match_dup 2) (match_dup 4))
1930 (set (match_dup 3) (match_dup 5))]
1931 {
1932 operands[2] = operand_subword (operands[0], 1, 0, <MODE>mode);
1933 operands[3] = operand_subword (operands[0], 0, 0, <MODE>mode);
1934 operands[4] = operand_subword (operands[1], 1, 0, <MODE>mode);
1935 operands[5] = operand_subword (operands[1], 0, 0, <MODE>mode);
1936 })
1937
1938 (define_split
1939 [(set (match_operand:DD_DF 0 "register_operand" "")
1940 (match_operand:DD_DF 1 "memory_operand" ""))]
1941 "!TARGET_64BIT && reload_completed
1942 && !FP_REG_P (operands[0])
1943 && !s_operand (operands[1], VOIDmode)"
1944 [(set (match_dup 0) (match_dup 1))]
1945 {
1946 rtx addr = operand_subword (operands[0], 1, 0, <MODE>mode);
1947 s390_load_address (addr, XEXP (operands[1], 0));
1948 operands[1] = replace_equiv_address (operands[1], addr);
1949 })
1950
1951 ;
1952 ; mov(sf|sd) instruction pattern(s).
1953 ;
1954
1955 (define_insn "mov<mode>"
1956 [(set (match_operand:SD_SF 0 "nonimmediate_operand"
1957 "=f,f,f,f,R,T,d,d,d,R,T,?Q")
1958 (match_operand:SD_SF 1 "general_operand"
1959 " G,f,R,T,f,f,d,R,T,d,d,?Q"))]
1960 ""
1961 "@
1962 lzer\t%0
1963 ler\t%0,%1
1964 le\t%0,%1
1965 ley\t%0,%1
1966 ste\t%1,%0
1967 stey\t%1,%0
1968 lr\t%0,%1
1969 l\t%0,%1
1970 ly\t%0,%1
1971 st\t%1,%0
1972 sty\t%1,%0
1973 #"
1974 [(set_attr "op_type" "RRE,RR,RX,RXY,RX,RXY,RR,RX,RXY,RX,RXY,SS")
1975 (set_attr "type" "fsimp<bfp>,fload<bfp>,fload<bfp>,fload<bfp>,
1976 fstore<bfp>,fstore<bfp>,lr,load,load,store,store,*")])
1977
1978 ;
1979 ; movcc instruction pattern
1980 ;
1981
1982 (define_insn "movcc"
1983 [(set (match_operand:CC 0 "nonimmediate_operand" "=d,c,d,d,d,R,T")
1984 (match_operand:CC 1 "nonimmediate_operand" "d,d,c,R,T,d,d"))]
1985 ""
1986 "@
1987 lr\t%0,%1
1988 tmh\t%1,12288
1989 ipm\t%0
1990 st\t%0,%1
1991 sty\t%0,%1
1992 l\t%1,%0
1993 ly\t%1,%0"
1994 [(set_attr "op_type" "RR,RI,RRE,RX,RXY,RX,RXY")
1995 (set_attr "type" "lr,*,*,store,store,load,load")])
1996
1997 ;
1998 ; Block move (MVC) patterns.
1999 ;
2000
2001 (define_insn "*mvc"
2002 [(set (match_operand:BLK 0 "memory_operand" "=Q")
2003 (match_operand:BLK 1 "memory_operand" "Q"))
2004 (use (match_operand 2 "const_int_operand" "n"))]
2005 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
2006 "mvc\t%O0(%2,%R0),%S1"
2007 [(set_attr "op_type" "SS")])
2008
2009 (define_split
2010 [(set (match_operand 0 "memory_operand" "")
2011 (match_operand 1 "memory_operand" ""))]
2012 "reload_completed
2013 && GET_MODE (operands[0]) == GET_MODE (operands[1])
2014 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
2015 [(parallel
2016 [(set (match_dup 0) (match_dup 1))
2017 (use (match_dup 2))])]
2018 {
2019 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
2020 operands[0] = adjust_address (operands[0], BLKmode, 0);
2021 operands[1] = adjust_address (operands[1], BLKmode, 0);
2022 })
2023
2024 (define_peephole2
2025 [(parallel
2026 [(set (match_operand:BLK 0 "memory_operand" "")
2027 (match_operand:BLK 1 "memory_operand" ""))
2028 (use (match_operand 2 "const_int_operand" ""))])
2029 (parallel
2030 [(set (match_operand:BLK 3 "memory_operand" "")
2031 (match_operand:BLK 4 "memory_operand" ""))
2032 (use (match_operand 5 "const_int_operand" ""))])]
2033 "s390_offset_p (operands[0], operands[3], operands[2])
2034 && s390_offset_p (operands[1], operands[4], operands[2])
2035 && !s390_overlap_p (operands[0], operands[1],
2036 INTVAL (operands[2]) + INTVAL (operands[5]))
2037 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
2038 [(parallel
2039 [(set (match_dup 6) (match_dup 7))
2040 (use (match_dup 8))])]
2041 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
2042 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
2043 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
2044
2045
2046 ;
2047 ; load_multiple pattern(s).
2048 ;
2049 ; ??? Due to reload problems with replacing registers inside match_parallel
2050 ; we currently support load_multiple/store_multiple only after reload.
2051 ;
2052
2053 (define_expand "load_multiple"
2054 [(match_par_dup 3 [(set (match_operand 0 "" "")
2055 (match_operand 1 "" ""))
2056 (use (match_operand 2 "" ""))])]
2057 "reload_completed"
2058 {
2059 enum machine_mode mode;
2060 int regno;
2061 int count;
2062 rtx from;
2063 int i, off;
2064
2065 /* Support only loading a constant number of fixed-point registers from
2066 memory and only bother with this if more than two */
2067 if (GET_CODE (operands[2]) != CONST_INT
2068 || INTVAL (operands[2]) < 2
2069 || INTVAL (operands[2]) > 16
2070 || GET_CODE (operands[1]) != MEM
2071 || GET_CODE (operands[0]) != REG
2072 || REGNO (operands[0]) >= 16)
2073 FAIL;
2074
2075 count = INTVAL (operands[2]);
2076 regno = REGNO (operands[0]);
2077 mode = GET_MODE (operands[0]);
2078 if (mode != SImode && mode != word_mode)
2079 FAIL;
2080
2081 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2082 if (!can_create_pseudo_p ())
2083 {
2084 if (GET_CODE (XEXP (operands[1], 0)) == REG)
2085 {
2086 from = XEXP (operands[1], 0);
2087 off = 0;
2088 }
2089 else if (GET_CODE (XEXP (operands[1], 0)) == PLUS
2090 && GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == REG
2091 && GET_CODE (XEXP (XEXP (operands[1], 0), 1)) == CONST_INT)
2092 {
2093 from = XEXP (XEXP (operands[1], 0), 0);
2094 off = INTVAL (XEXP (XEXP (operands[1], 0), 1));
2095 }
2096 else
2097 FAIL;
2098 }
2099 else
2100 {
2101 from = force_reg (Pmode, XEXP (operands[1], 0));
2102 off = 0;
2103 }
2104
2105 for (i = 0; i < count; i++)
2106 XVECEXP (operands[3], 0, i)
2107 = gen_rtx_SET (VOIDmode, gen_rtx_REG (mode, regno + i),
2108 change_address (operands[1], mode,
2109 plus_constant (from, off + i * GET_MODE_SIZE (mode))));
2110 })
2111
2112 (define_insn "*load_multiple_di"
2113 [(match_parallel 0 "load_multiple_operation"
2114 [(set (match_operand:DI 1 "register_operand" "=r")
2115 (match_operand:DI 2 "s_operand" "QS"))])]
2116 "reload_completed && word_mode == DImode"
2117 {
2118 int words = XVECLEN (operands[0], 0);
2119 operands[0] = gen_rtx_REG (DImode, REGNO (operands[1]) + words - 1);
2120 return "lmg\t%1,%0,%S2";
2121 }
2122 [(set_attr "op_type" "RSY")
2123 (set_attr "type" "lm")])
2124
2125 (define_insn "*load_multiple_si"
2126 [(match_parallel 0 "load_multiple_operation"
2127 [(set (match_operand:SI 1 "register_operand" "=r,r")
2128 (match_operand:SI 2 "s_operand" "Q,S"))])]
2129 "reload_completed"
2130 {
2131 int words = XVECLEN (operands[0], 0);
2132 operands[0] = gen_rtx_REG (SImode, REGNO (operands[1]) + words - 1);
2133 return which_alternative == 0 ? "lm\t%1,%0,%S2" : "lmy\t%1,%0,%S2";
2134 }
2135 [(set_attr "op_type" "RS,RSY")
2136 (set_attr "type" "lm")])
2137
2138 ;
2139 ; store multiple pattern(s).
2140 ;
2141
2142 (define_expand "store_multiple"
2143 [(match_par_dup 3 [(set (match_operand 0 "" "")
2144 (match_operand 1 "" ""))
2145 (use (match_operand 2 "" ""))])]
2146 "reload_completed"
2147 {
2148 enum machine_mode mode;
2149 int regno;
2150 int count;
2151 rtx to;
2152 int i, off;
2153
2154 /* Support only storing a constant number of fixed-point registers to
2155 memory and only bother with this if more than two. */
2156 if (GET_CODE (operands[2]) != CONST_INT
2157 || INTVAL (operands[2]) < 2
2158 || INTVAL (operands[2]) > 16
2159 || GET_CODE (operands[0]) != MEM
2160 || GET_CODE (operands[1]) != REG
2161 || REGNO (operands[1]) >= 16)
2162 FAIL;
2163
2164 count = INTVAL (operands[2]);
2165 regno = REGNO (operands[1]);
2166 mode = GET_MODE (operands[1]);
2167 if (mode != SImode && mode != word_mode)
2168 FAIL;
2169
2170 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
2171
2172 if (!can_create_pseudo_p ())
2173 {
2174 if (GET_CODE (XEXP (operands[0], 0)) == REG)
2175 {
2176 to = XEXP (operands[0], 0);
2177 off = 0;
2178 }
2179 else if (GET_CODE (XEXP (operands[0], 0)) == PLUS
2180 && GET_CODE (XEXP (XEXP (operands[0], 0), 0)) == REG
2181 && GET_CODE (XEXP (XEXP (operands[0], 0), 1)) == CONST_INT)
2182 {
2183 to = XEXP (XEXP (operands[0], 0), 0);
2184 off = INTVAL (XEXP (XEXP (operands[0], 0), 1));
2185 }
2186 else
2187 FAIL;
2188 }
2189 else
2190 {
2191 to = force_reg (Pmode, XEXP (operands[0], 0));
2192 off = 0;
2193 }
2194
2195 for (i = 0; i < count; i++)
2196 XVECEXP (operands[3], 0, i)
2197 = gen_rtx_SET (VOIDmode,
2198 change_address (operands[0], mode,
2199 plus_constant (to, off + i * GET_MODE_SIZE (mode))),
2200 gen_rtx_REG (mode, regno + i));
2201 })
2202
2203 (define_insn "*store_multiple_di"
2204 [(match_parallel 0 "store_multiple_operation"
2205 [(set (match_operand:DI 1 "s_operand" "=QS")
2206 (match_operand:DI 2 "register_operand" "r"))])]
2207 "reload_completed && word_mode == DImode"
2208 {
2209 int words = XVECLEN (operands[0], 0);
2210 operands[0] = gen_rtx_REG (DImode, REGNO (operands[2]) + words - 1);
2211 return "stmg\t%2,%0,%S1";
2212 }
2213 [(set_attr "op_type" "RSY")
2214 (set_attr "type" "stm")])
2215
2216
2217 (define_insn "*store_multiple_si"
2218 [(match_parallel 0 "store_multiple_operation"
2219 [(set (match_operand:SI 1 "s_operand" "=Q,S")
2220 (match_operand:SI 2 "register_operand" "r,r"))])]
2221 "reload_completed"
2222 {
2223 int words = XVECLEN (operands[0], 0);
2224 operands[0] = gen_rtx_REG (SImode, REGNO (operands[2]) + words - 1);
2225 return which_alternative == 0 ? "stm\t%2,%0,%S1" : "stmy\t%2,%0,%S1";
2226 }
2227 [(set_attr "op_type" "RS,RSY")
2228 (set_attr "type" "stm")])
2229
2230 ;;
2231 ;; String instructions.
2232 ;;
2233
2234 (define_insn "*execute_rl"
2235 [(match_parallel 0 ""
2236 [(unspec [(match_operand 1 "register_operand" "a")
2237 (match_operand 2 "" "")
2238 (match_operand:SI 3 "larl_operand" "X")] UNSPEC_EXECUTE)])]
2239 "TARGET_Z10 && GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2240 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2241 "exrl\t%1,%3"
2242 [(set_attr "op_type" "RIL")
2243 (set_attr "type" "cs")])
2244
2245 (define_insn "*execute"
2246 [(match_parallel 0 ""
2247 [(unspec [(match_operand 1 "register_operand" "a")
2248 (match_operand:BLK 2 "memory_operand" "R")
2249 (match_operand 3 "" "")] UNSPEC_EXECUTE)])]
2250 "GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
2251 && GET_MODE_SIZE (GET_MODE (operands[1])) <= UNITS_PER_WORD"
2252 "ex\t%1,%2"
2253 [(set_attr "op_type" "RX")
2254 (set_attr "type" "cs")])
2255
2256
2257 ;
2258 ; strlenM instruction pattern(s).
2259 ;
2260
2261 (define_expand "strlen<mode>"
2262 [(set (reg:SI 0) (match_operand:SI 2 "immediate_operand" ""))
2263 (parallel
2264 [(set (match_dup 4)
2265 (unspec:P [(const_int 0)
2266 (match_operand:BLK 1 "memory_operand" "")
2267 (reg:SI 0)
2268 (match_operand 3 "immediate_operand" "")] UNSPEC_SRST))
2269 (clobber (scratch:P))
2270 (clobber (reg:CC CC_REGNUM))])
2271 (parallel
2272 [(set (match_operand:P 0 "register_operand" "")
2273 (minus:P (match_dup 4) (match_dup 5)))
2274 (clobber (reg:CC CC_REGNUM))])]
2275 ""
2276 {
2277 operands[4] = gen_reg_rtx (Pmode);
2278 operands[5] = gen_reg_rtx (Pmode);
2279 emit_move_insn (operands[5], force_operand (XEXP (operands[1], 0), NULL_RTX));
2280 operands[1] = replace_equiv_address (operands[1], operands[5]);
2281 })
2282
2283 (define_insn "*strlen<mode>"
2284 [(set (match_operand:P 0 "register_operand" "=a")
2285 (unspec:P [(match_operand:P 2 "general_operand" "0")
2286 (mem:BLK (match_operand:P 3 "register_operand" "1"))
2287 (reg:SI 0)
2288 (match_operand 4 "immediate_operand" "")] UNSPEC_SRST))
2289 (clobber (match_scratch:P 1 "=a"))
2290 (clobber (reg:CC CC_REGNUM))]
2291 ""
2292 "srst\t%0,%1\;jo\t.-4"
2293 [(set_attr "length" "8")
2294 (set_attr "type" "vs")])
2295
2296 ;
2297 ; cmpstrM instruction pattern(s).
2298 ;
2299
2300 (define_expand "cmpstrsi"
2301 [(set (reg:SI 0) (const_int 0))
2302 (parallel
2303 [(clobber (match_operand 3 "" ""))
2304 (clobber (match_dup 4))
2305 (set (reg:CCU CC_REGNUM)
2306 (compare:CCU (match_operand:BLK 1 "memory_operand" "")
2307 (match_operand:BLK 2 "memory_operand" "")))
2308 (use (reg:SI 0))])
2309 (parallel
2310 [(set (match_operand:SI 0 "register_operand" "=d")
2311 (unspec:SI [(reg:CCU CC_REGNUM)] UNSPEC_CCU_TO_INT))
2312 (clobber (reg:CC CC_REGNUM))])]
2313 ""
2314 {
2315 /* As the result of CMPINT is inverted compared to what we need,
2316 we have to swap the operands. */
2317 rtx op1 = operands[2];
2318 rtx op2 = operands[1];
2319 rtx addr1 = gen_reg_rtx (Pmode);
2320 rtx addr2 = gen_reg_rtx (Pmode);
2321
2322 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
2323 emit_move_insn (addr2, force_operand (XEXP (op2, 0), NULL_RTX));
2324 operands[1] = replace_equiv_address_nv (op1, addr1);
2325 operands[2] = replace_equiv_address_nv (op2, addr2);
2326 operands[3] = addr1;
2327 operands[4] = addr2;
2328 })
2329
2330 (define_insn "*cmpstr<mode>"
2331 [(clobber (match_operand:P 0 "register_operand" "=d"))
2332 (clobber (match_operand:P 1 "register_operand" "=d"))
2333 (set (reg:CCU CC_REGNUM)
2334 (compare:CCU (mem:BLK (match_operand:P 2 "register_operand" "0"))
2335 (mem:BLK (match_operand:P 3 "register_operand" "1"))))
2336 (use (reg:SI 0))]
2337 ""
2338 "clst\t%0,%1\;jo\t.-4"
2339 [(set_attr "length" "8")
2340 (set_attr "type" "vs")])
2341
2342 ;
2343 ; movstr instruction pattern.
2344 ;
2345
2346 (define_expand "movstr"
2347 [(set (reg:SI 0) (const_int 0))
2348 (parallel
2349 [(clobber (match_dup 3))
2350 (set (match_operand:BLK 1 "memory_operand" "")
2351 (match_operand:BLK 2 "memory_operand" ""))
2352 (set (match_operand 0 "register_operand" "")
2353 (unspec [(match_dup 1)
2354 (match_dup 2)
2355 (reg:SI 0)] UNSPEC_MVST))
2356 (clobber (reg:CC CC_REGNUM))])]
2357 ""
2358 {
2359 rtx addr1 = gen_reg_rtx (Pmode);
2360 rtx addr2 = gen_reg_rtx (Pmode);
2361
2362 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
2363 emit_move_insn (addr2, force_operand (XEXP (operands[2], 0), NULL_RTX));
2364 operands[1] = replace_equiv_address_nv (operands[1], addr1);
2365 operands[2] = replace_equiv_address_nv (operands[2], addr2);
2366 operands[3] = addr2;
2367 })
2368
2369 (define_insn "*movstr"
2370 [(clobber (match_operand:P 2 "register_operand" "=d"))
2371 (set (mem:BLK (match_operand:P 1 "register_operand" "0"))
2372 (mem:BLK (match_operand:P 3 "register_operand" "2")))
2373 (set (match_operand:P 0 "register_operand" "=d")
2374 (unspec [(mem:BLK (match_dup 1))
2375 (mem:BLK (match_dup 3))
2376 (reg:SI 0)] UNSPEC_MVST))
2377 (clobber (reg:CC CC_REGNUM))]
2378 ""
2379 "mvst\t%1,%2\;jo\t.-4"
2380 [(set_attr "length" "8")
2381 (set_attr "type" "vs")])
2382
2383
2384 ;
2385 ; movmemM instruction pattern(s).
2386 ;
2387
2388 (define_expand "movmem<mode>"
2389 [(set (match_operand:BLK 0 "memory_operand" "") ; destination
2390 (match_operand:BLK 1 "memory_operand" "")) ; source
2391 (use (match_operand:GPR 2 "general_operand" "")) ; count
2392 (match_operand 3 "" "")]
2393 ""
2394 "s390_expand_movmem (operands[0], operands[1], operands[2]); DONE;")
2395
2396 ; Move a block that is up to 256 bytes in length.
2397 ; The block length is taken as (operands[2] % 256) + 1.
2398
2399 (define_expand "movmem_short"
2400 [(parallel
2401 [(set (match_operand:BLK 0 "memory_operand" "")
2402 (match_operand:BLK 1 "memory_operand" ""))
2403 (use (match_operand 2 "nonmemory_operand" ""))
2404 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2405 (clobber (match_dup 3))])]
2406 ""
2407 "operands[3] = gen_rtx_SCRATCH (Pmode);")
2408
2409 (define_insn "*movmem_short"
2410 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
2411 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q"))
2412 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
2413 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
2414 (clobber (match_scratch 4 "=X,X,X,&a"))]
2415 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)
2416 && GET_MODE (operands[4]) == Pmode"
2417 "#"
2418 [(set_attr "type" "cs")
2419 (set_attr "cpu_facility" "*,*,z10,*")])
2420
2421 (define_split
2422 [(set (match_operand:BLK 0 "memory_operand" "")
2423 (match_operand:BLK 1 "memory_operand" ""))
2424 (use (match_operand 2 "const_int_operand" ""))
2425 (use (match_operand 3 "immediate_operand" ""))
2426 (clobber (scratch))]
2427 "reload_completed"
2428 [(parallel
2429 [(set (match_dup 0) (match_dup 1))
2430 (use (match_dup 2))])]
2431 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
2432
2433 (define_split
2434 [(set (match_operand:BLK 0 "memory_operand" "")
2435 (match_operand:BLK 1 "memory_operand" ""))
2436 (use (match_operand 2 "register_operand" ""))
2437 (use (match_operand 3 "memory_operand" ""))
2438 (clobber (scratch))]
2439 "reload_completed"
2440 [(parallel
2441 [(unspec [(match_dup 2) (match_dup 3)
2442 (const_int 0)] UNSPEC_EXECUTE)
2443 (set (match_dup 0) (match_dup 1))
2444 (use (const_int 1))])]
2445 "")
2446
2447 (define_split
2448 [(set (match_operand:BLK 0 "memory_operand" "")
2449 (match_operand:BLK 1 "memory_operand" ""))
2450 (use (match_operand 2 "register_operand" ""))
2451 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2452 (clobber (scratch))]
2453 "TARGET_Z10 && reload_completed"
2454 [(parallel
2455 [(unspec [(match_dup 2) (const_int 0)
2456 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
2457 (set (match_dup 0) (match_dup 1))
2458 (use (const_int 1))])]
2459 "operands[3] = gen_label_rtx ();")
2460
2461 (define_split
2462 [(set (match_operand:BLK 0 "memory_operand" "")
2463 (match_operand:BLK 1 "memory_operand" ""))
2464 (use (match_operand 2 "register_operand" ""))
2465 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2466 (clobber (match_operand 3 "register_operand" ""))]
2467 "reload_completed && TARGET_CPU_ZARCH"
2468 [(set (match_dup 3) (label_ref (match_dup 4)))
2469 (parallel
2470 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
2471 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
2472 (set (match_dup 0) (match_dup 1))
2473 (use (const_int 1))])]
2474 "operands[4] = gen_label_rtx ();")
2475
2476 ; Move a block of arbitrary length.
2477
2478 (define_expand "movmem_long"
2479 [(parallel
2480 [(clobber (match_dup 2))
2481 (clobber (match_dup 3))
2482 (set (match_operand:BLK 0 "memory_operand" "")
2483 (match_operand:BLK 1 "memory_operand" ""))
2484 (use (match_operand 2 "general_operand" ""))
2485 (use (match_dup 3))
2486 (clobber (reg:CC CC_REGNUM))])]
2487 ""
2488 {
2489 enum machine_mode dword_mode = word_mode == DImode ? TImode : DImode;
2490 rtx reg0 = gen_reg_rtx (dword_mode);
2491 rtx reg1 = gen_reg_rtx (dword_mode);
2492 rtx addr0 = gen_lowpart (Pmode, gen_highpart (word_mode, reg0));
2493 rtx addr1 = gen_lowpart (Pmode, gen_highpart (word_mode, reg1));
2494 rtx len0 = gen_lowpart (Pmode, reg0);
2495 rtx len1 = gen_lowpart (Pmode, reg1);
2496
2497 emit_clobber (reg0);
2498 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
2499 emit_move_insn (len0, operands[2]);
2500
2501 emit_clobber (reg1);
2502 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
2503 emit_move_insn (len1, operands[2]);
2504
2505 operands[0] = replace_equiv_address_nv (operands[0], addr0);
2506 operands[1] = replace_equiv_address_nv (operands[1], addr1);
2507 operands[2] = reg0;
2508 operands[3] = reg1;
2509 })
2510
2511 (define_insn "*movmem_long"
2512 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
2513 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
2514 (set (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
2515 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0)))
2516 (use (match_dup 2))
2517 (use (match_dup 3))
2518 (clobber (reg:CC CC_REGNUM))]
2519 ""
2520 "mvcle\t%0,%1,0\;jo\t.-4"
2521 [(set_attr "length" "8")
2522 (set_attr "type" "vs")])
2523
2524
2525 ;
2526 ; Test data class.
2527 ;
2528
2529 (define_expand "signbit<mode>2"
2530 [(set (reg:CCZ CC_REGNUM)
2531 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
2532 (match_dup 2)]
2533 UNSPEC_TDC_INSN))
2534 (set (match_operand:SI 0 "register_operand" "=d")
2535 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CCZ_TO_INT))]
2536 "TARGET_HARD_FLOAT"
2537 {
2538 operands[2] = GEN_INT (S390_TDC_SIGNBIT_SET);
2539 })
2540
2541 (define_expand "isinf<mode>2"
2542 [(set (reg:CCZ CC_REGNUM)
2543 (unspec:CCZ [(match_operand:FP_ALL 1 "register_operand" "f")
2544 (match_dup 2)]
2545 UNSPEC_TDC_INSN))
2546 (set (match_operand:SI 0 "register_operand" "=d")
2547 (unspec:SI [(reg:CCZ CC_REGNUM)] UNSPEC_CCZ_TO_INT))]
2548 "TARGET_HARD_FLOAT"
2549 {
2550 operands[2] = GEN_INT (S390_TDC_INFINITY);
2551 })
2552
2553 ; This insn is used to generate all variants of the Test Data Class
2554 ; instruction, namely tcxb, tcdb, and tceb. The insn's first operand
2555 ; is the register to be tested and the second one is the bit mask
2556 ; specifying the required test(s).
2557 ;
2558 (define_insn "*TDC_insn_<mode>"
2559 [(set (reg:CCZ CC_REGNUM)
2560 (unspec:CCZ [(match_operand:FP_ALL 0 "register_operand" "f")
2561 (match_operand:SI 1 "const_int_operand")] UNSPEC_TDC_INSN))]
2562 "TARGET_HARD_FLOAT"
2563 "t<_d>c<xde><bt>\t%0,%1"
2564 [(set_attr "op_type" "RXE")
2565 (set_attr "type" "fsimp<bfp>")])
2566
2567 (define_insn_and_split "*ccz_to_int"
2568 [(set (match_operand:SI 0 "register_operand" "=d")
2569 (unspec:SI [(match_operand:CCZ 1 "register_operand" "0")]
2570 UNSPEC_CCZ_TO_INT))]
2571 ""
2572 "#"
2573 "reload_completed"
2574 [(set (match_dup 0) (lshiftrt:SI (match_dup 0) (const_int 28)))])
2575
2576
2577 ;
2578 ; setmemM instruction pattern(s).
2579 ;
2580
2581 (define_expand "setmem<mode>"
2582 [(set (match_operand:BLK 0 "memory_operand" "")
2583 (match_operand:QI 2 "general_operand" ""))
2584 (use (match_operand:GPR 1 "general_operand" ""))
2585 (match_operand 3 "" "")]
2586 ""
2587 "s390_expand_setmem (operands[0], operands[1], operands[2]); DONE;")
2588
2589 ; Clear a block that is up to 256 bytes in length.
2590 ; The block length is taken as (operands[1] % 256) + 1.
2591
2592 (define_expand "clrmem_short"
2593 [(parallel
2594 [(set (match_operand:BLK 0 "memory_operand" "")
2595 (const_int 0))
2596 (use (match_operand 1 "nonmemory_operand" ""))
2597 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2598 (clobber (match_dup 2))
2599 (clobber (reg:CC CC_REGNUM))])]
2600 ""
2601 "operands[2] = gen_rtx_SCRATCH (Pmode);")
2602
2603 (define_insn "*clrmem_short"
2604 [(set (match_operand:BLK 0 "memory_operand" "=Q,Q,Q,Q")
2605 (const_int 0))
2606 (use (match_operand 1 "nonmemory_operand" "n,a,a,a"))
2607 (use (match_operand 2 "immediate_operand" "X,R,X,X"))
2608 (clobber (match_scratch 3 "=X,X,X,&a"))
2609 (clobber (reg:CC CC_REGNUM))]
2610 "(GET_MODE (operands[1]) == Pmode || GET_MODE (operands[1]) == VOIDmode)
2611 && GET_MODE (operands[3]) == Pmode"
2612 "#"
2613 [(set_attr "type" "cs")
2614 (set_attr "cpu_facility" "*,*,z10,*")])
2615
2616 (define_split
2617 [(set (match_operand:BLK 0 "memory_operand" "")
2618 (const_int 0))
2619 (use (match_operand 1 "const_int_operand" ""))
2620 (use (match_operand 2 "immediate_operand" ""))
2621 (clobber (scratch))
2622 (clobber (reg:CC CC_REGNUM))]
2623 "reload_completed"
2624 [(parallel
2625 [(set (match_dup 0) (const_int 0))
2626 (use (match_dup 1))
2627 (clobber (reg:CC CC_REGNUM))])]
2628 "operands[1] = GEN_INT ((INTVAL (operands[1]) & 0xff) + 1);")
2629
2630 (define_split
2631 [(set (match_operand:BLK 0 "memory_operand" "")
2632 (const_int 0))
2633 (use (match_operand 1 "register_operand" ""))
2634 (use (match_operand 2 "memory_operand" ""))
2635 (clobber (scratch))
2636 (clobber (reg:CC CC_REGNUM))]
2637 "reload_completed"
2638 [(parallel
2639 [(unspec [(match_dup 1) (match_dup 2)
2640 (const_int 0)] UNSPEC_EXECUTE)
2641 (set (match_dup 0) (const_int 0))
2642 (use (const_int 1))
2643 (clobber (reg:CC CC_REGNUM))])]
2644 "")
2645
2646 (define_split
2647 [(set (match_operand:BLK 0 "memory_operand" "")
2648 (const_int 0))
2649 (use (match_operand 1 "register_operand" ""))
2650 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2651 (clobber (scratch))
2652 (clobber (reg:CC CC_REGNUM))]
2653 "TARGET_Z10 && reload_completed"
2654 [(parallel
2655 [(unspec [(match_dup 1) (const_int 0)
2656 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
2657 (set (match_dup 0) (const_int 0))
2658 (use (const_int 1))
2659 (clobber (reg:CC CC_REGNUM))])]
2660 "operands[3] = gen_label_rtx ();")
2661
2662 (define_split
2663 [(set (match_operand:BLK 0 "memory_operand" "")
2664 (const_int 0))
2665 (use (match_operand 1 "register_operand" ""))
2666 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2667 (clobber (match_operand 2 "register_operand" ""))
2668 (clobber (reg:CC CC_REGNUM))]
2669 "reload_completed && TARGET_CPU_ZARCH"
2670 [(set (match_dup 2) (label_ref (match_dup 3)))
2671 (parallel
2672 [(unspec [(match_dup 1) (mem:BLK (match_dup 2))
2673 (label_ref (match_dup 3))] UNSPEC_EXECUTE)
2674 (set (match_dup 0) (const_int 0))
2675 (use (const_int 1))
2676 (clobber (reg:CC CC_REGNUM))])]
2677 "operands[3] = gen_label_rtx ();")
2678
2679 ; Initialize a block of arbitrary length with (operands[2] % 256).
2680
2681 (define_expand "setmem_long"
2682 [(parallel
2683 [(clobber (match_dup 1))
2684 (set (match_operand:BLK 0 "memory_operand" "")
2685 (match_operand 2 "shift_count_or_setmem_operand" ""))
2686 (use (match_operand 1 "general_operand" ""))
2687 (use (match_dup 3))
2688 (clobber (reg:CC CC_REGNUM))])]
2689 ""
2690 {
2691 enum machine_mode dword_mode = word_mode == DImode ? TImode : DImode;
2692 rtx reg0 = gen_reg_rtx (dword_mode);
2693 rtx reg1 = gen_reg_rtx (dword_mode);
2694 rtx addr0 = gen_lowpart (Pmode, gen_highpart (word_mode, reg0));
2695 rtx len0 = gen_lowpart (Pmode, reg0);
2696
2697 emit_clobber (reg0);
2698 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
2699 emit_move_insn (len0, operands[1]);
2700
2701 emit_move_insn (reg1, const0_rtx);
2702
2703 operands[0] = replace_equiv_address_nv (operands[0], addr0);
2704 operands[1] = reg0;
2705 operands[3] = reg1;
2706 })
2707
2708 (define_insn "*setmem_long"
2709 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
2710 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
2711 (match_operand 2 "shift_count_or_setmem_operand" "Y"))
2712 (use (match_dup 3))
2713 (use (match_operand:<DBL> 1 "register_operand" "d"))
2714 (clobber (reg:CC CC_REGNUM))]
2715 ""
2716 "mvcle\t%0,%1,%Y2\;jo\t.-4"
2717 [(set_attr "length" "8")
2718 (set_attr "type" "vs")])
2719
2720 (define_insn "*setmem_long_and"
2721 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
2722 (set (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "0") 0))
2723 (and (match_operand 2 "shift_count_or_setmem_operand" "Y")
2724 (match_operand 4 "const_int_operand" "n")))
2725 (use (match_dup 3))
2726 (use (match_operand:<DBL> 1 "register_operand" "d"))
2727 (clobber (reg:CC CC_REGNUM))]
2728 "(INTVAL (operands[4]) & 255) == 255"
2729 "mvcle\t%0,%1,%Y2\;jo\t.-4"
2730 [(set_attr "length" "8")
2731 (set_attr "type" "vs")])
2732 ;
2733 ; cmpmemM instruction pattern(s).
2734 ;
2735
2736 (define_expand "cmpmemsi"
2737 [(set (match_operand:SI 0 "register_operand" "")
2738 (compare:SI (match_operand:BLK 1 "memory_operand" "")
2739 (match_operand:BLK 2 "memory_operand" "") ) )
2740 (use (match_operand:SI 3 "general_operand" ""))
2741 (use (match_operand:SI 4 "" ""))]
2742 ""
2743 "s390_expand_cmpmem (operands[0], operands[1],
2744 operands[2], operands[3]); DONE;")
2745
2746 ; Compare a block that is up to 256 bytes in length.
2747 ; The block length is taken as (operands[2] % 256) + 1.
2748
2749 (define_expand "cmpmem_short"
2750 [(parallel
2751 [(set (reg:CCU CC_REGNUM)
2752 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2753 (match_operand:BLK 1 "memory_operand" "")))
2754 (use (match_operand 2 "nonmemory_operand" ""))
2755 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2756 (clobber (match_dup 3))])]
2757 ""
2758 "operands[3] = gen_rtx_SCRATCH (Pmode);")
2759
2760 (define_insn "*cmpmem_short"
2761 [(set (reg:CCU CC_REGNUM)
2762 (compare:CCU (match_operand:BLK 0 "memory_operand" "Q,Q,Q,Q")
2763 (match_operand:BLK 1 "memory_operand" "Q,Q,Q,Q")))
2764 (use (match_operand 2 "nonmemory_operand" "n,a,a,a"))
2765 (use (match_operand 3 "immediate_operand" "X,R,X,X"))
2766 (clobber (match_scratch 4 "=X,X,X,&a"))]
2767 "(GET_MODE (operands[2]) == Pmode || GET_MODE (operands[2]) == VOIDmode)
2768 && GET_MODE (operands[4]) == Pmode"
2769 "#"
2770 [(set_attr "type" "cs")
2771 (set_attr "cpu_facility" "*,*,z10,*")])
2772
2773 (define_split
2774 [(set (reg:CCU CC_REGNUM)
2775 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2776 (match_operand:BLK 1 "memory_operand" "")))
2777 (use (match_operand 2 "const_int_operand" ""))
2778 (use (match_operand 3 "immediate_operand" ""))
2779 (clobber (scratch))]
2780 "reload_completed"
2781 [(parallel
2782 [(set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
2783 (use (match_dup 2))])]
2784 "operands[2] = GEN_INT ((INTVAL (operands[2]) & 0xff) + 1);")
2785
2786 (define_split
2787 [(set (reg:CCU CC_REGNUM)
2788 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2789 (match_operand:BLK 1 "memory_operand" "")))
2790 (use (match_operand 2 "register_operand" ""))
2791 (use (match_operand 3 "memory_operand" ""))
2792 (clobber (scratch))]
2793 "reload_completed"
2794 [(parallel
2795 [(unspec [(match_dup 2) (match_dup 3)
2796 (const_int 0)] UNSPEC_EXECUTE)
2797 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
2798 (use (const_int 1))])]
2799 "")
2800
2801 (define_split
2802 [(set (reg:CCU CC_REGNUM)
2803 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2804 (match_operand:BLK 1 "memory_operand" "")))
2805 (use (match_operand 2 "register_operand" ""))
2806 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2807 (clobber (scratch))]
2808 "TARGET_Z10 && reload_completed"
2809 [(parallel
2810 [(unspec [(match_dup 2) (const_int 0)
2811 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
2812 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
2813 (use (const_int 1))])]
2814 "operands[4] = gen_label_rtx ();")
2815
2816 (define_split
2817 [(set (reg:CCU CC_REGNUM)
2818 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2819 (match_operand:BLK 1 "memory_operand" "")))
2820 (use (match_operand 2 "register_operand" ""))
2821 (use (const:BLK (unspec:BLK [(const_int 0)] UNSPEC_INSN)))
2822 (clobber (match_operand 3 "register_operand" ""))]
2823 "reload_completed && TARGET_CPU_ZARCH"
2824 [(set (match_dup 3) (label_ref (match_dup 4)))
2825 (parallel
2826 [(unspec [(match_dup 2) (mem:BLK (match_dup 3))
2827 (label_ref (match_dup 4))] UNSPEC_EXECUTE)
2828 (set (reg:CCU CC_REGNUM) (compare:CCU (match_dup 0) (match_dup 1)))
2829 (use (const_int 1))])]
2830 "operands[4] = gen_label_rtx ();")
2831
2832 ; Compare a block of arbitrary length.
2833
2834 (define_expand "cmpmem_long"
2835 [(parallel
2836 [(clobber (match_dup 2))
2837 (clobber (match_dup 3))
2838 (set (reg:CCU CC_REGNUM)
2839 (compare:CCU (match_operand:BLK 0 "memory_operand" "")
2840 (match_operand:BLK 1 "memory_operand" "")))
2841 (use (match_operand 2 "general_operand" ""))
2842 (use (match_dup 3))])]
2843 ""
2844 {
2845 enum machine_mode dword_mode = word_mode == DImode ? TImode : DImode;
2846 rtx reg0 = gen_reg_rtx (dword_mode);
2847 rtx reg1 = gen_reg_rtx (dword_mode);
2848 rtx addr0 = gen_lowpart (Pmode, gen_highpart (word_mode, reg0));
2849 rtx addr1 = gen_lowpart (Pmode, gen_highpart (word_mode, reg1));
2850 rtx len0 = gen_lowpart (Pmode, reg0);
2851 rtx len1 = gen_lowpart (Pmode, reg1);
2852
2853 emit_clobber (reg0);
2854 emit_move_insn (addr0, force_operand (XEXP (operands[0], 0), NULL_RTX));
2855 emit_move_insn (len0, operands[2]);
2856
2857 emit_clobber (reg1);
2858 emit_move_insn (addr1, force_operand (XEXP (operands[1], 0), NULL_RTX));
2859 emit_move_insn (len1, operands[2]);
2860
2861 operands[0] = replace_equiv_address_nv (operands[0], addr0);
2862 operands[1] = replace_equiv_address_nv (operands[1], addr1);
2863 operands[2] = reg0;
2864 operands[3] = reg1;
2865 })
2866
2867 (define_insn "*cmpmem_long"
2868 [(clobber (match_operand:<DBL> 0 "register_operand" "=d"))
2869 (clobber (match_operand:<DBL> 1 "register_operand" "=d"))
2870 (set (reg:CCU CC_REGNUM)
2871 (compare:CCU (mem:BLK (subreg:P (match_operand:<DBL> 2 "register_operand" "0") 0))
2872 (mem:BLK (subreg:P (match_operand:<DBL> 3 "register_operand" "1") 0))))
2873 (use (match_dup 2))
2874 (use (match_dup 3))]
2875 ""
2876 "clcle\t%0,%1,0\;jo\t.-4"
2877 [(set_attr "length" "8")
2878 (set_attr "type" "vs")])
2879
2880 ; Convert CCUmode condition code to integer.
2881 ; Result is zero if EQ, positive if LTU, negative if GTU.
2882
2883 (define_insn_and_split "cmpint"
2884 [(set (match_operand:SI 0 "register_operand" "=d")
2885 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
2886 UNSPEC_CCU_TO_INT))
2887 (clobber (reg:CC CC_REGNUM))]
2888 ""
2889 "#"
2890 "reload_completed"
2891 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
2892 (parallel
2893 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))
2894 (clobber (reg:CC CC_REGNUM))])])
2895
2896 (define_insn_and_split "*cmpint_cc"
2897 [(set (reg CC_REGNUM)
2898 (compare (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
2899 UNSPEC_CCU_TO_INT)
2900 (const_int 0)))
2901 (set (match_operand:SI 0 "register_operand" "=d")
2902 (unspec:SI [(match_dup 1)] UNSPEC_CCU_TO_INT))]
2903 "s390_match_ccmode (insn, CCSmode)"
2904 "#"
2905 "&& reload_completed"
2906 [(set (match_dup 0) (ashift:SI (match_dup 0) (const_int 2)))
2907 (parallel
2908 [(set (match_dup 2) (match_dup 3))
2909 (set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 30)))])]
2910 {
2911 rtx result = gen_rtx_ASHIFTRT (SImode, operands[0], GEN_INT (30));
2912 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
2913 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
2914 })
2915
2916 (define_insn_and_split "*cmpint_sign"
2917 [(set (match_operand:DI 0 "register_operand" "=d")
2918 (sign_extend:DI (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
2919 UNSPEC_CCU_TO_INT)))
2920 (clobber (reg:CC CC_REGNUM))]
2921 "TARGET_64BIT"
2922 "#"
2923 "&& reload_completed"
2924 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
2925 (parallel
2926 [(set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))
2927 (clobber (reg:CC CC_REGNUM))])])
2928
2929 (define_insn_and_split "*cmpint_sign_cc"
2930 [(set (reg CC_REGNUM)
2931 (compare (ashiftrt:DI (ashift:DI (subreg:DI
2932 (unspec:SI [(match_operand:CCU 1 "register_operand" "0")]
2933 UNSPEC_CCU_TO_INT) 0)
2934 (const_int 32)) (const_int 32))
2935 (const_int 0)))
2936 (set (match_operand:DI 0 "register_operand" "=d")
2937 (sign_extend:DI (unspec:SI [(match_dup 1)] UNSPEC_CCU_TO_INT)))]
2938 "s390_match_ccmode (insn, CCSmode) && TARGET_64BIT"
2939 "#"
2940 "&& reload_completed"
2941 [(set (match_dup 0) (ashift:DI (match_dup 0) (const_int 34)))
2942 (parallel
2943 [(set (match_dup 2) (match_dup 3))
2944 (set (match_dup 0) (ashiftrt:DI (match_dup 0) (const_int 62)))])]
2945 {
2946 rtx result = gen_rtx_ASHIFTRT (DImode, operands[0], GEN_INT (62));
2947 operands[2] = SET_DEST (XVECEXP (PATTERN (curr_insn), 0, 0));
2948 operands[3] = gen_rtx_COMPARE (GET_MODE (operands[2]), result, const0_rtx);
2949 })
2950
2951
2952 ;;
2953 ;;- Conversion instructions.
2954 ;;
2955
2956 (define_insn "*sethighpartsi"
2957 [(set (match_operand:SI 0 "register_operand" "=d,d")
2958 (unspec:SI [(match_operand:BLK 1 "s_operand" "Q,S")
2959 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
2960 (clobber (reg:CC CC_REGNUM))]
2961 ""
2962 "@
2963 icm\t%0,%2,%S1
2964 icmy\t%0,%2,%S1"
2965 [(set_attr "op_type" "RS,RSY")])
2966
2967 (define_insn "*sethighpartdi_64"
2968 [(set (match_operand:DI 0 "register_operand" "=d")
2969 (unspec:DI [(match_operand:BLK 1 "s_operand" "QS")
2970 (match_operand 2 "const_int_operand" "n")] UNSPEC_ICM))
2971 (clobber (reg:CC CC_REGNUM))]
2972 "TARGET_64BIT"
2973 "icmh\t%0,%2,%S1"
2974 [(set_attr "op_type" "RSY")])
2975
2976 (define_insn "*sethighpartdi_31"
2977 [(set (match_operand:DI 0 "register_operand" "=d,d")
2978 (unspec:DI [(match_operand:BLK 1 "s_operand" "Q,S")
2979 (match_operand 2 "const_int_operand" "n,n")] UNSPEC_ICM))
2980 (clobber (reg:CC CC_REGNUM))]
2981 "!TARGET_64BIT"
2982 "@
2983 icm\t%0,%2,%S1
2984 icmy\t%0,%2,%S1"
2985 [(set_attr "op_type" "RS,RSY")])
2986
2987 (define_insn_and_split "*extzv<mode>"
2988 [(set (match_operand:GPR 0 "register_operand" "=d")
2989 (zero_extract:GPR (match_operand:QI 1 "s_operand" "QS")
2990 (match_operand 2 "const_int_operand" "n")
2991 (const_int 0)))
2992 (clobber (reg:CC CC_REGNUM))]
2993 "INTVAL (operands[2]) > 0
2994 && INTVAL (operands[2]) <= GET_MODE_BITSIZE (SImode)"
2995 "#"
2996 "&& reload_completed"
2997 [(parallel
2998 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
2999 (clobber (reg:CC CC_REGNUM))])
3000 (set (match_dup 0) (lshiftrt:GPR (match_dup 0) (match_dup 2)))]
3001 {
3002 int bitsize = INTVAL (operands[2]);
3003 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3004 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3005
3006 operands[1] = adjust_address (operands[1], BLKmode, 0);
3007 set_mem_size (operands[1], GEN_INT (size));
3008 operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - bitsize);
3009 operands[3] = GEN_INT (mask);
3010 })
3011
3012 (define_insn_and_split "*extv<mode>"
3013 [(set (match_operand:GPR 0 "register_operand" "=d")
3014 (sign_extract:GPR (match_operand:QI 1 "s_operand" "QS")
3015 (match_operand 2 "const_int_operand" "n")
3016 (const_int 0)))
3017 (clobber (reg:CC CC_REGNUM))]
3018 "INTVAL (operands[2]) > 0
3019 && INTVAL (operands[2]) <= GET_MODE_BITSIZE (SImode)"
3020 "#"
3021 "&& reload_completed"
3022 [(parallel
3023 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (match_dup 3)] UNSPEC_ICM))
3024 (clobber (reg:CC CC_REGNUM))])
3025 (parallel
3026 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3027 (clobber (reg:CC CC_REGNUM))])]
3028 {
3029 int bitsize = INTVAL (operands[2]);
3030 int size = (bitsize - 1) / BITS_PER_UNIT + 1; /* round up */
3031 int mask = ((1ul << size) - 1) << (GET_MODE_SIZE (SImode) - size);
3032
3033 operands[1] = adjust_address (operands[1], BLKmode, 0);
3034 set_mem_size (operands[1], GEN_INT (size));
3035 operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - bitsize);
3036 operands[3] = GEN_INT (mask);
3037 })
3038
3039 ;
3040 ; insv instruction patterns
3041 ;
3042
3043 (define_expand "insv"
3044 [(set (zero_extract (match_operand 0 "nonimmediate_operand" "")
3045 (match_operand 1 "const_int_operand" "")
3046 (match_operand 2 "const_int_operand" ""))
3047 (match_operand 3 "general_operand" ""))]
3048 ""
3049 {
3050 if (s390_expand_insv (operands[0], operands[1], operands[2], operands[3]))
3051 DONE;
3052 FAIL;
3053 })
3054
3055 (define_insn "*insv<mode>_z10"
3056 [(set (zero_extract:GPR (match_operand:GPR 0 "nonimmediate_operand" "+d")
3057 (match_operand 1 "const_int_operand" "I")
3058 (match_operand 2 "const_int_operand" "I"))
3059 (match_operand:GPR 3 "nonimmediate_operand" "d"))
3060 (clobber (reg:CC CC_REGNUM))]
3061 "TARGET_Z10
3062 && (INTVAL (operands[1]) + INTVAL (operands[2])) <=
3063 GET_MODE_BITSIZE (<MODE>mode)"
3064 {
3065 int start = INTVAL (operands[2]);
3066 int size = INTVAL (operands[1]);
3067 int offset = 64 - GET_MODE_BITSIZE (<MODE>mode);
3068
3069 operands[2] = GEN_INT (offset + start); /* start bit position */
3070 operands[1] = GEN_INT (offset + start + size - 1); /* end bit position */
3071 operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) -
3072 start - size); /* left shift count */
3073
3074 return "risbg\t%0,%3,%b2,%b1,%b4";
3075 }
3076 [(set_attr "op_type" "RIE")])
3077
3078 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3079 ; and op3=op0 with a mask being 0 for the selected bits and 1 for the rest
3080 (define_insn "*insv<mode>_z10_noshift"
3081 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3082 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3083 (match_operand 2 "const_int_operand" "n"))
3084 (and:GPR (match_operand:GPR 3 "nonimmediate_operand" "0")
3085 (match_operand 4 "const_int_operand" "n"))))
3086 (clobber (reg:CC CC_REGNUM))]
3087 "TARGET_Z10
3088 && s390_contiguous_bitmask_p (INTVAL (operands[2]),
3089 GET_MODE_BITSIZE (<MODE>mode), NULL, NULL)
3090 && INTVAL (operands[2]) == ~(INTVAL (operands[4]))"
3091
3092 {
3093 int start;
3094 int size;
3095
3096 s390_contiguous_bitmask_p (INTVAL (operands[2]),
3097 GET_MODE_BITSIZE (<MODE>mode), &start, &size);
3098
3099 operands[5] = GEN_INT (64 - start - size); /* start bit position */
3100 operands[6] = GEN_INT (64 - 1 - start); /* end bit position */
3101 operands[7] = const0_rtx; /* left shift count */
3102
3103 return "risbg\t%0,%1,%b5,%b6,%b7";
3104 }
3105 [(set_attr "op_type" "RIE")])
3106
3107 ; and op1 with a mask being 1 for the selected bits and 0 for the rest
3108 (define_insn "*insv<mode>_or_z10_noshift"
3109 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d")
3110 (ior:GPR (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "d")
3111 (match_operand 2 "const_int_operand" "n"))
3112 (match_operand:GPR 3 "nonimmediate_operand" "0")))
3113 (clobber (reg:CC CC_REGNUM))]
3114 "TARGET_Z10
3115 && s390_contiguous_bitmask_p (INTVAL (operands[2]),
3116 GET_MODE_BITSIZE (<MODE>mode), NULL, NULL)"
3117 {
3118 int start;
3119 int size;
3120
3121 s390_contiguous_bitmask_p (INTVAL (operands[2]),
3122 GET_MODE_BITSIZE (<MODE>mode), &start, &size);
3123
3124 operands[4] = GEN_INT (64 - start - size); /* start bit position */
3125 operands[5] = GEN_INT (64 - 1 - start); /* end bit position */
3126 operands[6] = const0_rtx; /* left shift count */
3127
3128 return "rosbg\t%0,%1,%b4,%b5,%b6";
3129 }
3130 [(set_attr "op_type" "RIE")])
3131
3132 (define_insn "*insv<mode>_mem_reg"
3133 [(set (zero_extract:P (match_operand:QI 0 "memory_operand" "+Q,S")
3134 (match_operand 1 "const_int_operand" "n,n")
3135 (const_int 0))
3136 (match_operand:P 2 "register_operand" "d,d"))]
3137 "INTVAL (operands[1]) > 0
3138 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
3139 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
3140 {
3141 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
3142
3143 operands[1] = GEN_INT ((1ul << size) - 1);
3144 return (which_alternative == 0) ? "stcm\t%2,%1,%S0"
3145 : "stcmy\t%2,%1,%S0";
3146 }
3147 [(set_attr "op_type" "RS,RSY")])
3148
3149 (define_insn "*insvdi_mem_reghigh"
3150 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "+QS")
3151 (match_operand 1 "const_int_operand" "n")
3152 (const_int 0))
3153 (lshiftrt:DI (match_operand:DI 2 "register_operand" "d")
3154 (const_int 32)))]
3155 "TARGET_64BIT
3156 && INTVAL (operands[1]) > 0
3157 && INTVAL (operands[1]) <= GET_MODE_BITSIZE (SImode)
3158 && INTVAL (operands[1]) % BITS_PER_UNIT == 0"
3159 {
3160 int size = INTVAL (operands[1]) / BITS_PER_UNIT;
3161
3162 operands[1] = GEN_INT ((1ul << size) - 1);
3163 return "stcmh\t%2,%1,%S0";
3164 }
3165 [(set_attr "op_type" "RSY")])
3166
3167 (define_insn "*insv<mode>_reg_imm"
3168 [(set (zero_extract:P (match_operand:P 0 "register_operand" "+d")
3169 (const_int 16)
3170 (match_operand 1 "const_int_operand" "n"))
3171 (match_operand:P 2 "const_int_operand" "n"))]
3172 "TARGET_ZARCH
3173 && INTVAL (operands[1]) >= 0
3174 && INTVAL (operands[1]) < BITS_PER_WORD
3175 && INTVAL (operands[1]) % 16 == 0"
3176 {
3177 switch (BITS_PER_WORD - INTVAL (operands[1]))
3178 {
3179 case 64: return "iihh\t%0,%x2"; break;
3180 case 48: return "iihl\t%0,%x2"; break;
3181 case 32: return "iilh\t%0,%x2"; break;
3182 case 16: return "iill\t%0,%x2"; break;
3183 default: gcc_unreachable();
3184 }
3185 }
3186 [(set_attr "op_type" "RI")])
3187
3188 (define_insn "*insv<mode>_reg_extimm"
3189 [(set (zero_extract:P (match_operand:P 0 "register_operand" "+d")
3190 (const_int 32)
3191 (match_operand 1 "const_int_operand" "n"))
3192 (match_operand:P 2 "const_int_operand" "n"))]
3193 "TARGET_EXTIMM
3194 && INTVAL (operands[1]) >= 0
3195 && INTVAL (operands[1]) < BITS_PER_WORD
3196 && INTVAL (operands[1]) % 32 == 0"
3197 {
3198 switch (BITS_PER_WORD - INTVAL (operands[1]))
3199 {
3200 case 64: return "iihf\t%0,%o2"; break;
3201 case 32: return "iilf\t%0,%o2"; break;
3202 default: gcc_unreachable();
3203 }
3204 }
3205 [(set_attr "op_type" "RIL")])
3206
3207 ;
3208 ; extendsidi2 instruction pattern(s).
3209 ;
3210
3211 (define_expand "extendsidi2"
3212 [(set (match_operand:DI 0 "register_operand" "")
3213 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3214 ""
3215 {
3216 if (!TARGET_64BIT)
3217 {
3218 emit_clobber (operands[0]);
3219 emit_move_insn (gen_highpart (SImode, operands[0]), operands[1]);
3220 emit_move_insn (gen_lowpart (SImode, operands[0]), const0_rtx);
3221 emit_insn (gen_ashrdi3 (operands[0], operands[0], GEN_INT (32)));
3222 DONE;
3223 }
3224 })
3225
3226 (define_insn "*extendsidi2"
3227 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
3228 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
3229 "TARGET_64BIT"
3230 "@
3231 lgfr\t%0,%1
3232 lgf\t%0,%1
3233 lgfrl\t%0,%1"
3234 [(set_attr "op_type" "RRE,RXY,RIL")
3235 (set_attr "type" "*,*,larl")
3236 (set_attr "cpu_facility" "*,*,z10")])
3237
3238 ;
3239 ; extend(hi|qi)(si|di)2 instruction pattern(s).
3240 ;
3241
3242 (define_expand "extend<HQI:mode><DSI:mode>2"
3243 [(set (match_operand:DSI 0 "register_operand" "")
3244 (sign_extend:DSI (match_operand:HQI 1 "nonimmediate_operand" "")))]
3245 ""
3246 {
3247 if (<DSI:MODE>mode == DImode && !TARGET_64BIT)
3248 {
3249 rtx tmp = gen_reg_rtx (SImode);
3250 emit_insn (gen_extend<HQI:mode>si2 (tmp, operands[1]));
3251 emit_insn (gen_extendsidi2 (operands[0], tmp));
3252 DONE;
3253 }
3254 else if (!TARGET_EXTIMM)
3255 {
3256 rtx bitcount = GEN_INT (GET_MODE_BITSIZE (<DSI:MODE>mode) -
3257 GET_MODE_BITSIZE (<HQI:MODE>mode));
3258
3259 operands[1] = gen_lowpart (<DSI:MODE>mode, operands[1]);
3260 emit_insn (gen_ashl<DSI:mode>3 (operands[0], operands[1], bitcount));
3261 emit_insn (gen_ashr<DSI:mode>3 (operands[0], operands[0], bitcount));
3262 DONE;
3263 }
3264 })
3265
3266 ;
3267 ; extendhidi2 instruction pattern(s).
3268 ;
3269
3270 (define_insn "*extendhidi2_extimm"
3271 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
3272 (sign_extend:DI (match_operand:HI 1 "general_operand" "d,RT,b")))]
3273 "TARGET_64BIT && TARGET_EXTIMM"
3274 "@
3275 lghr\t%0,%1
3276 lgh\t%0,%1
3277 lghrl\t%0,%1"
3278 [(set_attr "op_type" "RRE,RXY,RIL")
3279 (set_attr "type" "*,*,larl")
3280 (set_attr "cpu_facility" "extimm,extimm,z10")])
3281
3282 (define_insn "*extendhidi2"
3283 [(set (match_operand:DI 0 "register_operand" "=d")
3284 (sign_extend:DI (match_operand:HI 1 "memory_operand" "RT")))]
3285 "TARGET_64BIT"
3286 "lgh\t%0,%1"
3287 [(set_attr "op_type" "RXY")])
3288
3289 ;
3290 ; extendhisi2 instruction pattern(s).
3291 ;
3292
3293 (define_insn "*extendhisi2_extimm"
3294 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d")
3295 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" " d,R,T,b")))]
3296 "TARGET_EXTIMM"
3297 "@
3298 lhr\t%0,%1
3299 lh\t%0,%1
3300 lhy\t%0,%1
3301 lhrl\t%0,%1"
3302 [(set_attr "op_type" "RRE,RX,RXY,RIL")
3303 (set_attr "type" "*,*,*,larl")
3304 (set_attr "cpu_facility" "extimm,extimm,extimm,z10")])
3305
3306 (define_insn "*extendhisi2"
3307 [(set (match_operand:SI 0 "register_operand" "=d,d")
3308 (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,T")))]
3309 "!TARGET_EXTIMM"
3310 "@
3311 lh\t%0,%1
3312 lhy\t%0,%1"
3313 [(set_attr "op_type" "RX,RXY")])
3314
3315 ;
3316 ; extendqi(si|di)2 instruction pattern(s).
3317 ;
3318
3319 ; lbr, lgbr, lb, lgb
3320 (define_insn "*extendqi<mode>2_extimm"
3321 [(set (match_operand:GPR 0 "register_operand" "=d,d")
3322 (sign_extend:GPR (match_operand:QI 1 "nonimmediate_operand" "d,RT")))]
3323 "TARGET_EXTIMM"
3324 "@
3325 l<g>br\t%0,%1
3326 l<g>b\t%0,%1"
3327 [(set_attr "op_type" "RRE,RXY")])
3328
3329 ; lb, lgb
3330 (define_insn "*extendqi<mode>2"
3331 [(set (match_operand:GPR 0 "register_operand" "=d")
3332 (sign_extend:GPR (match_operand:QI 1 "memory_operand" "RT")))]
3333 "!TARGET_EXTIMM && TARGET_LONG_DISPLACEMENT"
3334 "l<g>b\t%0,%1"
3335 [(set_attr "op_type" "RXY")])
3336
3337 (define_insn_and_split "*extendqi<mode>2_short_displ"
3338 [(set (match_operand:GPR 0 "register_operand" "=d")
3339 (sign_extend:GPR (match_operand:QI 1 "s_operand" "Q")))
3340 (clobber (reg:CC CC_REGNUM))]
3341 "!TARGET_EXTIMM && !TARGET_LONG_DISPLACEMENT"
3342 "#"
3343 "&& reload_completed"
3344 [(parallel
3345 [(set (match_dup 0) (unspec:GPR [(match_dup 1) (const_int 8)] UNSPEC_ICM))
3346 (clobber (reg:CC CC_REGNUM))])
3347 (parallel
3348 [(set (match_dup 0) (ashiftrt:GPR (match_dup 0) (match_dup 2)))
3349 (clobber (reg:CC CC_REGNUM))])]
3350 {
3351 operands[1] = adjust_address (operands[1], BLKmode, 0);
3352 set_mem_size (operands[1], GEN_INT (GET_MODE_SIZE (QImode)));
3353 operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)
3354 - GET_MODE_BITSIZE (QImode));
3355 })
3356
3357 ;
3358 ; zero_extendsidi2 instruction pattern(s).
3359 ;
3360
3361 (define_expand "zero_extendsidi2"
3362 [(set (match_operand:DI 0 "register_operand" "")
3363 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3364 ""
3365 {
3366 if (!TARGET_64BIT)
3367 {
3368 emit_clobber (operands[0]);
3369 emit_move_insn (gen_lowpart (SImode, operands[0]), operands[1]);
3370 emit_move_insn (gen_highpart (SImode, operands[0]), const0_rtx);
3371 DONE;
3372 }
3373 })
3374
3375 (define_insn "*zero_extendsidi2"
3376 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
3377 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "d,RT,b")))]
3378 "TARGET_64BIT"
3379 "@
3380 llgfr\t%0,%1
3381 llgf\t%0,%1
3382 llgfrl\t%0,%1"
3383 [(set_attr "op_type" "RRE,RXY,RIL")
3384 (set_attr "type" "*,*,larl")
3385 (set_attr "cpu_facility" "*,*,z10")])
3386
3387 ;
3388 ; LLGT-type instructions (zero-extend from 31 bit to 64 bit).
3389 ;
3390
3391 (define_insn "*llgt_sidi"
3392 [(set (match_operand:DI 0 "register_operand" "=d")
3393 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
3394 (const_int 2147483647)))]
3395 "TARGET_64BIT"
3396 "llgt\t%0,%1"
3397 [(set_attr "op_type" "RXE")])
3398
3399 (define_insn_and_split "*llgt_sidi_split"
3400 [(set (match_operand:DI 0 "register_operand" "=d")
3401 (and:DI (subreg:DI (match_operand:SI 1 "memory_operand" "RT") 0)
3402 (const_int 2147483647)))
3403 (clobber (reg:CC CC_REGNUM))]
3404 "TARGET_64BIT"
3405 "#"
3406 "&& reload_completed"
3407 [(set (match_dup 0)
3408 (and:DI (subreg:DI (match_dup 1) 0)
3409 (const_int 2147483647)))]
3410 "")
3411
3412 (define_insn "*llgt_sisi"
3413 [(set (match_operand:SI 0 "register_operand" "=d,d")
3414 (and:SI (match_operand:SI 1 "nonimmediate_operand" "d,RT")
3415 (const_int 2147483647)))]
3416 "TARGET_ZARCH"
3417 "@
3418 llgtr\t%0,%1
3419 llgt\t%0,%1"
3420 [(set_attr "op_type" "RRE,RXE")])
3421
3422 (define_insn "*llgt_didi"
3423 [(set (match_operand:DI 0 "register_operand" "=d,d")
3424 (and:DI (match_operand:DI 1 "nonimmediate_operand" "d,o")
3425 (const_int 2147483647)))]
3426 "TARGET_64BIT"
3427 "@
3428 llgtr\t%0,%1
3429 llgt\t%0,%N1"
3430 [(set_attr "op_type" "RRE,RXE")])
3431
3432 (define_split
3433 [(set (match_operand:GPR 0 "register_operand" "")
3434 (and:GPR (match_operand:GPR 1 "nonimmediate_operand" "")
3435 (const_int 2147483647)))
3436 (clobber (reg:CC CC_REGNUM))]
3437 "TARGET_ZARCH && reload_completed"
3438 [(set (match_dup 0)
3439 (and:GPR (match_dup 1)
3440 (const_int 2147483647)))]
3441 "")
3442
3443 ;
3444 ; zero_extend(hi|qi)(si|di)2 instruction pattern(s).
3445 ;
3446
3447 (define_expand "zero_extend<mode>di2"
3448 [(set (match_operand:DI 0 "register_operand" "")
3449 (zero_extend:DI (match_operand:HQI 1 "nonimmediate_operand" "")))]
3450 ""
3451 {
3452 if (!TARGET_64BIT)
3453 {
3454 rtx tmp = gen_reg_rtx (SImode);
3455 emit_insn (gen_zero_extend<mode>si2 (tmp, operands[1]));
3456 emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
3457 DONE;
3458 }
3459 else if (!TARGET_EXTIMM)
3460 {
3461 rtx bitcount = GEN_INT (GET_MODE_BITSIZE(DImode) -
3462 GET_MODE_BITSIZE(<MODE>mode));
3463 operands[1] = gen_lowpart (DImode, operands[1]);
3464 emit_insn (gen_ashldi3 (operands[0], operands[1], bitcount));
3465 emit_insn (gen_lshrdi3 (operands[0], operands[0], bitcount));
3466 DONE;
3467 }
3468 })
3469
3470 (define_expand "zero_extend<mode>si2"
3471 [(set (match_operand:SI 0 "register_operand" "")
3472 (zero_extend:SI (match_operand:HQI 1 "nonimmediate_operand" "")))]
3473 ""
3474 {
3475 if (!TARGET_EXTIMM)
3476 {
3477 operands[1] = gen_lowpart (SImode, operands[1]);
3478 emit_insn (gen_andsi3 (operands[0], operands[1],
3479 GEN_INT ((1 << GET_MODE_BITSIZE(<MODE>mode)) - 1)));
3480 DONE;
3481 }
3482 })
3483
3484 ; llhrl, llghrl
3485 (define_insn "*zero_extendhi<mode>2_z10"
3486 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
3487 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "d,RT,b")))]
3488 "TARGET_Z10"
3489 "@
3490 ll<g>hr\t%0,%1
3491 ll<g>h\t%0,%1
3492 ll<g>hrl\t%0,%1"
3493 [(set_attr "op_type" "RXY,RRE,RIL")
3494 (set_attr "type" "*,*,larl")
3495 (set_attr "cpu_facility" "*,*,z10")])
3496
3497 ; llhr, llcr, llghr, llgcr, llh, llc, llgh, llgc
3498 (define_insn "*zero_extend<HQI:mode><GPR:mode>2_extimm"
3499 [(set (match_operand:GPR 0 "register_operand" "=d,d")
3500 (zero_extend:GPR (match_operand:HQI 1 "nonimmediate_operand" "d,RT")))]
3501 "TARGET_EXTIMM"
3502 "@
3503 ll<g><hc>r\t%0,%1
3504 ll<g><hc>\t%0,%1"
3505 [(set_attr "op_type" "RRE,RXY")])
3506
3507 ; llgh, llgc
3508 (define_insn "*zero_extend<HQI:mode><GPR:mode>2"
3509 [(set (match_operand:GPR 0 "register_operand" "=d")
3510 (zero_extend:GPR (match_operand:HQI 1 "memory_operand" "RT")))]
3511 "TARGET_ZARCH && !TARGET_EXTIMM"
3512 "llg<hc>\t%0,%1"
3513 [(set_attr "op_type" "RXY")])
3514
3515 (define_insn_and_split "*zero_extendhisi2_31"
3516 [(set (match_operand:SI 0 "register_operand" "=&d")
3517 (zero_extend:SI (match_operand:HI 1 "s_operand" "QS")))
3518 (clobber (reg:CC CC_REGNUM))]
3519 "!TARGET_ZARCH"
3520 "#"
3521 "&& reload_completed"
3522 [(set (match_dup 0) (const_int 0))
3523 (parallel
3524 [(set (strict_low_part (match_dup 2)) (match_dup 1))
3525 (clobber (reg:CC CC_REGNUM))])]
3526 "operands[2] = gen_lowpart (HImode, operands[0]);")
3527
3528 (define_insn_and_split "*zero_extendqisi2_31"
3529 [(set (match_operand:SI 0 "register_operand" "=&d")
3530 (zero_extend:SI (match_operand:QI 1 "memory_operand" "RT")))]
3531 "!TARGET_ZARCH"
3532 "#"
3533 "&& reload_completed"
3534 [(set (match_dup 0) (const_int 0))
3535 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3536 "operands[2] = gen_lowpart (QImode, operands[0]);")
3537
3538 ;
3539 ; zero_extendqihi2 instruction pattern(s).
3540 ;
3541
3542 (define_expand "zero_extendqihi2"
3543 [(set (match_operand:HI 0 "register_operand" "")
3544 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
3545 "TARGET_ZARCH && !TARGET_EXTIMM"
3546 {
3547 operands[1] = gen_lowpart (HImode, operands[1]);
3548 emit_insn (gen_andhi3 (operands[0], operands[1], GEN_INT (0xff)));
3549 DONE;
3550 })
3551
3552 (define_insn "*zero_extendqihi2_64"
3553 [(set (match_operand:HI 0 "register_operand" "=d")
3554 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
3555 "TARGET_ZARCH && !TARGET_EXTIMM"
3556 "llgc\t%0,%1"
3557 [(set_attr "op_type" "RXY")])
3558
3559 (define_insn_and_split "*zero_extendqihi2_31"
3560 [(set (match_operand:HI 0 "register_operand" "=&d")
3561 (zero_extend:HI (match_operand:QI 1 "memory_operand" "RT")))]
3562 "!TARGET_ZARCH"
3563 "#"
3564 "&& reload_completed"
3565 [(set (match_dup 0) (const_int 0))
3566 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3567 "operands[2] = gen_lowpart (QImode, operands[0]);")
3568
3569 ;
3570 ; fixuns_trunc(dd|td)di2 instruction pattern(s).
3571 ;
3572
3573 (define_expand "fixuns_truncdddi2"
3574 [(parallel
3575 [(set (match_operand:DI 0 "register_operand" "")
3576 (unsigned_fix:DI (match_operand:DD 1 "register_operand" "")))
3577 (clobber (match_scratch:TD 2 "=f"))])]
3578
3579 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3580 {
3581 rtx label1 = gen_label_rtx ();
3582 rtx label2 = gen_label_rtx ();
3583 rtx temp = gen_reg_rtx (TDmode);
3584 REAL_VALUE_TYPE cmp, sub;
3585
3586 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
3587 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
3588
3589 /* 2^63 can't be represented as 64bit DFP number with full precision. The
3590 solution is doing the check and the subtraction in TD mode and using a
3591 TD -> DI convert afterwards. */
3592 emit_insn (gen_extendddtd2 (temp, operands[1]));
3593 temp = force_reg (TDmode, temp);
3594 emit_insn (gen_cmptd (temp,
3595 CONST_DOUBLE_FROM_REAL_VALUE (cmp, TDmode)));
3596 emit_jump_insn (gen_blt (label1));
3597 emit_insn (gen_subtd3 (temp, temp,
3598 CONST_DOUBLE_FROM_REAL_VALUE (sub, TDmode)));
3599 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
3600 emit_jump (label2);
3601
3602 emit_label (label1);
3603 emit_insn (gen_fix_truncdddi2_dfp (operands[0], operands[1], GEN_INT (9)));
3604 emit_label (label2);
3605 DONE;
3606 })
3607
3608 (define_expand "fixuns_trunctddi2"
3609 [(set (match_operand:DI 0 "register_operand" "")
3610 (unsigned_fix:DI (match_operand:TD 1 "register_operand" "")))]
3611 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3612 {
3613 rtx label1 = gen_label_rtx ();
3614 rtx label2 = gen_label_rtx ();
3615 rtx temp = gen_reg_rtx (TDmode);
3616 REAL_VALUE_TYPE cmp, sub;
3617
3618 operands[1] = force_reg (TDmode, operands[1]);
3619 decimal_real_from_string (&cmp, "9223372036854775808.0"); /* 2^63 */
3620 decimal_real_from_string (&sub, "18446744073709551616.0"); /* 2^64 */
3621
3622 emit_insn (gen_cmptd (operands[1],
3623 CONST_DOUBLE_FROM_REAL_VALUE (cmp, TDmode)));
3624 emit_jump_insn (gen_blt (label1));
3625 emit_insn (gen_subtd3 (temp, operands[1],
3626 CONST_DOUBLE_FROM_REAL_VALUE (sub, TDmode)));
3627 emit_insn (gen_fix_trunctddi2_dfp (operands[0], temp, GEN_INT (11)));
3628 emit_jump (label2);
3629
3630 emit_label (label1);
3631 emit_insn (gen_fix_trunctddi2_dfp (operands[0], operands[1], GEN_INT (9)));
3632 emit_label (label2);
3633 DONE;
3634 })
3635
3636 ;
3637 ; fixuns_trunc(sf|df)(si|di)2 and fix_trunc(sf|df)(si|di)2
3638 ; instruction pattern(s).
3639 ;
3640
3641 (define_expand "fixuns_trunc<BFP:mode><GPR:mode>2"
3642 [(set (match_operand:GPR 0 "register_operand" "")
3643 (unsigned_fix:GPR (match_operand:BFP 1 "register_operand" "")))]
3644 "TARGET_HARD_FLOAT"
3645 {
3646 rtx label1 = gen_label_rtx ();
3647 rtx label2 = gen_label_rtx ();
3648 rtx temp = gen_reg_rtx (<BFP:MODE>mode);
3649 REAL_VALUE_TYPE cmp, sub;
3650
3651 operands[1] = force_reg (<BFP:MODE>mode, operands[1]);
3652 real_2expN (&cmp, GET_MODE_BITSIZE(<GPR:MODE>mode) - 1, <BFP:MODE>mode);
3653 real_2expN (&sub, GET_MODE_BITSIZE(<GPR:MODE>mode), <BFP:MODE>mode);
3654
3655 emit_insn (gen_cmp<BFP:mode> (operands[1],
3656 CONST_DOUBLE_FROM_REAL_VALUE (cmp, <BFP:MODE>mode)));
3657 emit_jump_insn (gen_blt (label1));
3658 emit_insn (gen_sub<BFP:mode>3 (temp, operands[1],
3659 CONST_DOUBLE_FROM_REAL_VALUE (sub, <BFP:MODE>mode)));
3660 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0], temp,
3661 GEN_INT (7)));
3662 emit_jump (label2);
3663
3664 emit_label (label1);
3665 emit_insn (gen_fix_trunc<BFP:mode><GPR:mode>2_bfp (operands[0],
3666 operands[1], GEN_INT (5)));
3667 emit_label (label2);
3668 DONE;
3669 })
3670
3671 (define_expand "fix_trunc<DSF:mode><GPR:mode>2"
3672 [(set (match_operand:GPR 0 "register_operand" "")
3673 (fix:GPR (match_operand:DSF 1 "register_operand" "")))]
3674 "TARGET_HARD_FLOAT"
3675 {
3676 emit_insn (gen_fix_trunc<DSF:mode><GPR:mode>2_bfp (operands[0], operands[1],
3677 GEN_INT (5)));
3678 DONE;
3679 })
3680
3681 ; cgxbr, cgdbr, cgebr, cfxbr, cfdbr, cfebr
3682 (define_insn "fix_trunc<BFP:mode><GPR:mode>2_bfp"
3683 [(set (match_operand:GPR 0 "register_operand" "=d")
3684 (fix:GPR (match_operand:BFP 1 "register_operand" "f")))
3685 (unspec:GPR [(match_operand:GPR 2 "immediate_operand" "K")] UNSPEC_ROUND)
3686 (clobber (reg:CC CC_REGNUM))]
3687 "TARGET_HARD_FLOAT"
3688 "c<GPR:gf><BFP:xde>br\t%0,%h2,%1"
3689 [(set_attr "op_type" "RRE")
3690 (set_attr "type" "ftoi")])
3691
3692
3693 ;
3694 ; fix_trunc(td|dd)di2 instruction pattern(s).
3695 ;
3696
3697 (define_expand "fix_trunc<mode>di2"
3698 [(set (match_operand:DI 0 "register_operand" "")
3699 (fix:DI (match_operand:DFP 1 "nonimmediate_operand" "")))]
3700 "TARGET_64BIT && TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3701 {
3702 operands[1] = force_reg (<MODE>mode, operands[1]);
3703 emit_insn (gen_fix_trunc<mode>di2_dfp (operands[0], operands[1],
3704 GEN_INT (9)));
3705 DONE;
3706 })
3707
3708 ; cgxtr, cgdtr
3709 (define_insn "fix_trunc<DFP:mode>di2_dfp"
3710 [(set (match_operand:DI 0 "register_operand" "=d")
3711 (fix:DI (match_operand:DFP 1 "register_operand" "f")))
3712 (unspec:DI [(match_operand:DI 2 "immediate_operand" "K")] UNSPEC_ROUND)
3713 (clobber (reg:CC CC_REGNUM))]
3714 "TARGET_64BIT && TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3715 "cg<DFP:xde>tr\t%0,%h2,%1"
3716 [(set_attr "op_type" "RRF")
3717 (set_attr "type" "ftoi")])
3718
3719
3720 ;
3721 ; fix_trunctf(si|di)2 instruction pattern(s).
3722 ;
3723
3724 (define_expand "fix_trunctf<mode>2"
3725 [(parallel [(set (match_operand:GPR 0 "register_operand" "")
3726 (fix:GPR (match_operand:TF 1 "register_operand" "")))
3727 (unspec:GPR [(const_int 5)] UNSPEC_ROUND)
3728 (clobber (reg:CC CC_REGNUM))])]
3729 "TARGET_HARD_FLOAT"
3730 "")
3731
3732
3733 ;
3734 ; float(si|di)(tf|df|sf|td|dd)2 instruction pattern(s).
3735 ;
3736
3737 ; cxgbr, cdgbr, cegbr, cxgtr, cdgtr
3738 (define_insn "floatdi<mode>2"
3739 [(set (match_operand:FP 0 "register_operand" "=f")
3740 (float:FP (match_operand:DI 1 "register_operand" "d")))]
3741 "TARGET_64BIT && TARGET_HARD_FLOAT"
3742 "c<xde>g<bt>r\t%0,%1"
3743 [(set_attr "op_type" "RRE")
3744 (set_attr "type" "itof" )])
3745
3746 ; cxfbr, cdfbr, cefbr
3747 (define_insn "floatsi<mode>2"
3748 [(set (match_operand:BFP 0 "register_operand" "=f")
3749 (float:BFP (match_operand:SI 1 "register_operand" "d")))]
3750 "TARGET_HARD_FLOAT"
3751 "c<xde>fbr\t%0,%1"
3752 [(set_attr "op_type" "RRE")
3753 (set_attr "type" "itof" )])
3754
3755
3756 ;
3757 ; truncdfsf2 instruction pattern(s).
3758 ;
3759
3760 (define_insn "truncdfsf2"
3761 [(set (match_operand:SF 0 "register_operand" "=f")
3762 (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))]
3763 "TARGET_HARD_FLOAT"
3764 "ledbr\t%0,%1"
3765 [(set_attr "op_type" "RRE")
3766 (set_attr "type" "ftruncdf")])
3767
3768 ;
3769 ; trunctf(df|sf)2 instruction pattern(s).
3770 ;
3771
3772 ; ldxbr, lexbr
3773 (define_insn "trunctf<mode>2"
3774 [(set (match_operand:DSF 0 "register_operand" "=f")
3775 (float_truncate:DSF (match_operand:TF 1 "register_operand" "f")))
3776 (clobber (match_scratch:TF 2 "=f"))]
3777 "TARGET_HARD_FLOAT"
3778 "l<xde>xbr\t%2,%1\;l<xde>r\t%0,%2"
3779 [(set_attr "length" "6")
3780 (set_attr "type" "ftrunctf")])
3781
3782 ;
3783 ; trunctddd2 and truncddsd2 instruction pattern(s).
3784 ;
3785
3786 (define_insn "trunctddd2"
3787 [(set (match_operand:DD 0 "register_operand" "=f")
3788 (float_truncate:DD (match_operand:TD 1 "register_operand" "f")))
3789 (clobber (match_scratch:TD 2 "=f"))]
3790 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3791 "ldxtr\t%2,0,%1,0\;ldr\t%0,%2"
3792 [(set_attr "length" "6")
3793 (set_attr "type" "ftrunctf")])
3794
3795 (define_insn "truncddsd2"
3796 [(set (match_operand:SD 0 "register_operand" "=f")
3797 (float_truncate:SD (match_operand:DD 1 "register_operand" "f")))]
3798 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3799 "ledtr\t%0,0,%1,0"
3800 [(set_attr "op_type" "RRF")
3801 (set_attr "type" "fsimptf")])
3802
3803 ;
3804 ; extend(sf|df)(df|tf)2 instruction pattern(s).
3805 ;
3806
3807 ; ldebr, ldeb, lxdbr, lxdb, lxebr, lxeb
3808 (define_insn "extend<DSF:mode><BFP:mode>2"
3809 [(set (match_operand:BFP 0 "register_operand" "=f,f")
3810 (float_extend:BFP (match_operand:DSF 1 "nonimmediate_operand" "f,R")))]
3811 "TARGET_HARD_FLOAT
3812 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DSF:MODE>mode)"
3813 "@
3814 l<BFP:xde><DSF:xde>br\t%0,%1
3815 l<BFP:xde><DSF:xde>b\t%0,%1"
3816 [(set_attr "op_type" "RRE,RXE")
3817 (set_attr "type" "fsimp<BFP:mode>, fload<BFP:mode>")])
3818
3819 ;
3820 ; extendddtd2 and extendsddd2 instruction pattern(s).
3821 ;
3822
3823 (define_insn "extendddtd2"
3824 [(set (match_operand:TD 0 "register_operand" "=f")
3825 (float_extend:TD (match_operand:DD 1 "register_operand" "f")))]
3826 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3827 "lxdtr\t%0,%1,0"
3828 [(set_attr "op_type" "RRF")
3829 (set_attr "type" "fsimptf")])
3830
3831 (define_insn "extendsddd2"
3832 [(set (match_operand:DD 0 "register_operand" "=f")
3833 (float_extend:DD (match_operand:SD 1 "register_operand" "f")))]
3834 "TARGET_HARD_FLOAT && TARGET_HARD_DFP"
3835 "ldetr\t%0,%1,0"
3836 [(set_attr "op_type" "RRF")
3837 (set_attr "type" "fsimptf")])
3838
3839 ; Binary <-> Decimal floating point trunc patterns
3840 ;
3841
3842 (define_insn "*trunc<BFP:mode><DFP_ALL:mode>2"
3843 [(set (reg:DFP_ALL FPR0_REGNUM)
3844 (float_truncate:DFP_ALL (reg:BFP FPR2_REGNUM)))
3845 (use (reg:SI GPR0_REGNUM))
3846 (clobber (reg:CC CC_REGNUM))]
3847 "TARGET_HARD_FLOAT && TARGET_DFP"
3848 "pfpo")
3849
3850 (define_insn "*trunc<DFP_ALL:mode><BFP:mode>2"
3851 [(set (reg:BFP FPR0_REGNUM)
3852 (float_truncate:BFP (reg:DFP_ALL FPR2_REGNUM)))
3853 (use (reg:SI GPR0_REGNUM))
3854 (clobber (reg:CC CC_REGNUM))]
3855 "TARGET_HARD_FLOAT && TARGET_DFP"
3856 "pfpo")
3857
3858 (define_expand "trunc<BFP:mode><DFP_ALL:mode>2"
3859 [(set (reg:BFP FPR2_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
3860 (set (reg:SI GPR0_REGNUM) (match_dup 2))
3861 (parallel
3862 [(set (reg:DFP_ALL FPR0_REGNUM)
3863 (float_truncate:DFP_ALL (reg:BFP FPR2_REGNUM)))
3864 (use (reg:SI GPR0_REGNUM))
3865 (clobber (reg:CC CC_REGNUM))])
3866 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
3867 (reg:DFP_ALL FPR0_REGNUM))]
3868 "TARGET_HARD_FLOAT && TARGET_DFP
3869 && GET_MODE_SIZE (<BFP:MODE>mode) > GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
3870 {
3871 HOST_WIDE_INT flags;
3872
3873 flags = (PFPO_CONVERT |
3874 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
3875 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
3876
3877 operands[2] = GEN_INT (flags);
3878 })
3879
3880 (define_expand "trunc<DFP_ALL:mode><BFP:mode>2"
3881 [(set (reg:DFP_ALL FPR2_REGNUM)
3882 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
3883 (set (reg:SI GPR0_REGNUM) (match_dup 2))
3884 (parallel
3885 [(set (reg:BFP FPR0_REGNUM) (float_truncate:BFP (reg:DFP_ALL FPR2_REGNUM)))
3886 (use (reg:SI GPR0_REGNUM))
3887 (clobber (reg:CC CC_REGNUM))])
3888 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
3889 "TARGET_HARD_FLOAT && TARGET_DFP
3890 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) >= GET_MODE_SIZE (<BFP:MODE>mode)"
3891 {
3892 HOST_WIDE_INT flags;
3893
3894 flags = (PFPO_CONVERT |
3895 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
3896 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
3897
3898 operands[2] = GEN_INT (flags);
3899 })
3900
3901 ;
3902 ; Binary <-> Decimal floating point extend patterns
3903 ;
3904
3905 (define_insn "*extend<BFP:mode><DFP_ALL:mode>2"
3906 [(set (reg:DFP_ALL FPR0_REGNUM) (float_extend:DFP_ALL (reg:BFP FPR2_REGNUM)))
3907 (use (reg:SI GPR0_REGNUM))
3908 (clobber (reg:CC CC_REGNUM))]
3909 "TARGET_HARD_FLOAT && TARGET_DFP"
3910 "pfpo")
3911
3912 (define_insn "*extend<DFP_ALL:mode><BFP:mode>2"
3913 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR2_REGNUM)))
3914 (use (reg:SI GPR0_REGNUM))
3915 (clobber (reg:CC CC_REGNUM))]
3916 "TARGET_HARD_FLOAT && TARGET_DFP"
3917 "pfpo")
3918
3919 (define_expand "extend<BFP:mode><DFP_ALL:mode>2"
3920 [(set (reg:BFP FPR2_REGNUM) (match_operand:BFP 1 "nonimmediate_operand" ""))
3921 (set (reg:SI GPR0_REGNUM) (match_dup 2))
3922 (parallel
3923 [(set (reg:DFP_ALL FPR0_REGNUM)
3924 (float_extend:DFP_ALL (reg:BFP FPR2_REGNUM)))
3925 (use (reg:SI GPR0_REGNUM))
3926 (clobber (reg:CC CC_REGNUM))])
3927 (set (match_operand:DFP_ALL 0 "nonimmediate_operand" "")
3928 (reg:DFP_ALL FPR0_REGNUM))]
3929 "TARGET_HARD_FLOAT && TARGET_DFP
3930 && GET_MODE_SIZE (<BFP:MODE>mode) <= GET_MODE_SIZE (<DFP_ALL:MODE>mode)"
3931 {
3932 HOST_WIDE_INT flags;
3933
3934 flags = (PFPO_CONVERT |
3935 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP0_TYPE_SHIFT |
3936 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP1_TYPE_SHIFT);
3937
3938 operands[2] = GEN_INT (flags);
3939 })
3940
3941 (define_expand "extend<DFP_ALL:mode><BFP:mode>2"
3942 [(set (reg:DFP_ALL FPR2_REGNUM)
3943 (match_operand:DFP_ALL 1 "nonimmediate_operand" ""))
3944 (set (reg:SI GPR0_REGNUM) (match_dup 2))
3945 (parallel
3946 [(set (reg:BFP FPR0_REGNUM) (float_extend:BFP (reg:DFP_ALL FPR2_REGNUM)))
3947 (use (reg:SI GPR0_REGNUM))
3948 (clobber (reg:CC CC_REGNUM))])
3949 (set (match_operand:BFP 0 "nonimmediate_operand" "") (reg:BFP FPR0_REGNUM))]
3950 "TARGET_HARD_FLOAT && TARGET_DFP
3951 && GET_MODE_SIZE (<DFP_ALL:MODE>mode) < GET_MODE_SIZE (<BFP:MODE>mode)"
3952 {
3953 HOST_WIDE_INT flags;
3954
3955 flags = (PFPO_CONVERT |
3956 PFPO_OP_TYPE_<BFP:MODE> << PFPO_OP0_TYPE_SHIFT |
3957 PFPO_OP_TYPE_<DFP_ALL:MODE> << PFPO_OP1_TYPE_SHIFT);
3958
3959 operands[2] = GEN_INT (flags);
3960 })
3961
3962
3963 ;;
3964 ;; ARITHMETIC OPERATIONS
3965 ;;
3966 ; arithmetic operations set the ConditionCode,
3967 ; because of unpredictable Bits in Register for Halfword and Byte
3968 ; the ConditionCode can be set wrong in operations for Halfword and Byte
3969
3970 ;;
3971 ;;- Add instructions.
3972 ;;
3973
3974 ;
3975 ; addti3 instruction pattern(s).
3976 ;
3977
3978 (define_insn_and_split "addti3"
3979 [(set (match_operand:TI 0 "register_operand" "=&d")
3980 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
3981 (match_operand:TI 2 "general_operand" "do") ) )
3982 (clobber (reg:CC CC_REGNUM))]
3983 "TARGET_64BIT"
3984 "#"
3985 "&& reload_completed"
3986 [(parallel
3987 [(set (reg:CCL1 CC_REGNUM)
3988 (compare:CCL1 (plus:DI (match_dup 7) (match_dup 8))
3989 (match_dup 7)))
3990 (set (match_dup 6) (plus:DI (match_dup 7) (match_dup 8)))])
3991 (parallel
3992 [(set (match_dup 3) (plus:DI
3993 (plus:DI (ltu:DI (reg:CCL1 CC_REGNUM) (const_int 0))
3994 (match_dup 4)) (match_dup 5)))
3995 (clobber (reg:CC CC_REGNUM))])]
3996 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
3997 operands[4] = operand_subword (operands[1], 0, 0, TImode);
3998 operands[5] = operand_subword (operands[2], 0, 0, TImode);
3999 operands[6] = operand_subword (operands[0], 1, 0, TImode);
4000 operands[7] = operand_subword (operands[1], 1, 0, TImode);
4001 operands[8] = operand_subword (operands[2], 1, 0, TImode);")
4002
4003 ;
4004 ; adddi3 instruction pattern(s).
4005 ;
4006
4007 (define_expand "adddi3"
4008 [(parallel
4009 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4010 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4011 (match_operand:DI 2 "general_operand" "")))
4012 (clobber (reg:CC CC_REGNUM))])]
4013 ""
4014 "")
4015
4016 (define_insn "*adddi3_sign"
4017 [(set (match_operand:DI 0 "register_operand" "=d,d")
4018 (plus:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
4019 (match_operand:DI 1 "register_operand" "0,0")))
4020 (clobber (reg:CC CC_REGNUM))]
4021 "TARGET_64BIT"
4022 "@
4023 agfr\t%0,%2
4024 agf\t%0,%2"
4025 [(set_attr "op_type" "RRE,RXY")])
4026
4027 (define_insn "*adddi3_zero_cc"
4028 [(set (reg CC_REGNUM)
4029 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
4030 (match_operand:DI 1 "register_operand" "0,0"))
4031 (const_int 0)))
4032 (set (match_operand:DI 0 "register_operand" "=d,d")
4033 (plus:DI (zero_extend:DI (match_dup 2)) (match_dup 1)))]
4034 "s390_match_ccmode (insn, CCLmode) && TARGET_64BIT"
4035 "@
4036 algfr\t%0,%2
4037 algf\t%0,%2"
4038 [(set_attr "op_type" "RRE,RXY")])
4039
4040 (define_insn "*adddi3_zero_cconly"
4041 [(set (reg CC_REGNUM)
4042 (compare (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
4043 (match_operand:DI 1 "register_operand" "0,0"))
4044 (const_int 0)))
4045 (clobber (match_scratch:DI 0 "=d,d"))]
4046 "s390_match_ccmode (insn, CCLmode) && TARGET_64BIT"
4047 "@
4048 algfr\t%0,%2
4049 algf\t%0,%2"
4050 [(set_attr "op_type" "RRE,RXY")])
4051
4052 (define_insn "*adddi3_zero"
4053 [(set (match_operand:DI 0 "register_operand" "=d,d")
4054 (plus:DI (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
4055 (match_operand:DI 1 "register_operand" "0,0")))
4056 (clobber (reg:CC CC_REGNUM))]
4057 "TARGET_64BIT"
4058 "@
4059 algfr\t%0,%2
4060 algf\t%0,%2"
4061 [(set_attr "op_type" "RRE,RXY")])
4062
4063 (define_insn_and_split "*adddi3_31z"
4064 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
4065 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
4066 (match_operand:DI 2 "general_operand" "do") ) )
4067 (clobber (reg:CC CC_REGNUM))]
4068 "!TARGET_64BIT && TARGET_CPU_ZARCH"
4069 "#"
4070 "&& reload_completed"
4071 [(parallel
4072 [(set (reg:CCL1 CC_REGNUM)
4073 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
4074 (match_dup 7)))
4075 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
4076 (parallel
4077 [(set (match_dup 3) (plus:SI
4078 (plus:SI (ltu:SI (reg:CCL1 CC_REGNUM) (const_int 0))
4079 (match_dup 4)) (match_dup 5)))
4080 (clobber (reg:CC CC_REGNUM))])]
4081 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
4082 operands[4] = operand_subword (operands[1], 0, 0, DImode);
4083 operands[5] = operand_subword (operands[2], 0, 0, DImode);
4084 operands[6] = operand_subword (operands[0], 1, 0, DImode);
4085 operands[7] = operand_subword (operands[1], 1, 0, DImode);
4086 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
4087
4088 (define_insn_and_split "*adddi3_31"
4089 [(set (match_operand:DI 0 "nonimmediate_operand" "=&d")
4090 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
4091 (match_operand:DI 2 "general_operand" "do") ) )
4092 (clobber (reg:CC CC_REGNUM))]
4093 "!TARGET_CPU_ZARCH"
4094 "#"
4095 "&& reload_completed"
4096 [(parallel
4097 [(set (match_dup 3) (plus:SI (match_dup 4) (match_dup 5)))
4098 (clobber (reg:CC CC_REGNUM))])
4099 (parallel
4100 [(set (reg:CCL1 CC_REGNUM)
4101 (compare:CCL1 (plus:SI (match_dup 7) (match_dup 8))
4102 (match_dup 7)))
4103 (set (match_dup 6) (plus:SI (match_dup 7) (match_dup 8)))])
4104 (set (pc)
4105 (if_then_else (ltu (reg:CCL1 CC_REGNUM) (const_int 0))
4106 (pc)
4107 (label_ref (match_dup 9))))
4108 (parallel
4109 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int 1)))
4110 (clobber (reg:CC CC_REGNUM))])
4111 (match_dup 9)]
4112 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
4113 operands[4] = operand_subword (operands[1], 0, 0, DImode);
4114 operands[5] = operand_subword (operands[2], 0, 0, DImode);
4115 operands[6] = operand_subword (operands[0], 1, 0, DImode);
4116 operands[7] = operand_subword (operands[1], 1, 0, DImode);
4117 operands[8] = operand_subword (operands[2], 1, 0, DImode);
4118 operands[9] = gen_label_rtx ();")
4119
4120 ;
4121 ; addsi3 instruction pattern(s).
4122 ;
4123
4124 (define_expand "addsi3"
4125 [(parallel
4126 [(set (match_operand:SI 0 "nonimmediate_operand" "")
4127 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
4128 (match_operand:SI 2 "general_operand" "")))
4129 (clobber (reg:CC CC_REGNUM))])]
4130 ""
4131 "")
4132
4133 (define_insn "*addsi3_sign"
4134 [(set (match_operand:SI 0 "register_operand" "=d,d")
4135 (plus:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
4136 (match_operand:SI 1 "register_operand" "0,0")))
4137 (clobber (reg:CC CC_REGNUM))]
4138 ""
4139 "@
4140 ah\t%0,%2
4141 ahy\t%0,%2"
4142 [(set_attr "op_type" "RX,RXY")])
4143
4144 ;
4145 ; add(di|si)3 instruction pattern(s).
4146 ;
4147
4148 ; ar, ahi, alfi, slfi, a, ay, agr, aghi, algfi, slgfi, ag, asi, agsi
4149 (define_insn "*add<mode>3"
4150 [(set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,d,QS")
4151 (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0,0,0,0,0")
4152 (match_operand:GPR 2 "general_operand" "d,K,Op,On,R,T,C") ) )
4153 (clobber (reg:CC CC_REGNUM))]
4154 ""
4155 "@
4156 a<g>r\t%0,%2
4157 a<g>hi\t%0,%h2
4158 al<g>fi\t%0,%2
4159 sl<g>fi\t%0,%n2
4160 a<g>\t%0,%2
4161 a<y>\t%0,%2
4162 a<g>si\t%0,%c2"
4163 [(set_attr "op_type" "RR<E>,RI,RIL,RIL,RX<Y>,RXY,SIY")
4164 (set_attr "cpu_facility" "*,*,extimm,extimm,*,*,z10")])
4165
4166 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi
4167 (define_insn "*add<mode>3_carry1_cc"
4168 [(set (reg CC_REGNUM)
4169 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0,0,0,0")
4170 (match_operand:GPR 2 "general_operand" "d,Op,On,R,T,C"))
4171 (match_dup 1)))
4172 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,d")
4173 (plus:GPR (match_dup 1) (match_dup 2)))]
4174 "s390_match_ccmode (insn, CCL1mode)"
4175 "@
4176 al<g>r\t%0,%2
4177 al<g>fi\t%0,%2
4178 sl<g>fi\t%0,%n2
4179 al<g>\t%0,%2
4180 al<y>\t%0,%2
4181 al<g>si\t%0,%c2"
4182 [(set_attr "op_type" "RR<E>,RIL,RIL,RX<Y>,RXY,SIY")
4183 (set_attr "cpu_facility" "*,extimm,extimm,*,*,z10")])
4184
4185 ; alr, al, aly, algr, alg
4186 (define_insn "*add<mode>3_carry1_cconly"
4187 [(set (reg CC_REGNUM)
4188 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0")
4189 (match_operand:GPR 2 "general_operand" "d,R,T"))
4190 (match_dup 1)))
4191 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4192 "s390_match_ccmode (insn, CCL1mode)"
4193 "@
4194 al<g>r\t%0,%2
4195 al<g>\t%0,%2
4196 al<y>\t%0,%2"
4197 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4198
4199 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi
4200 (define_insn "*add<mode>3_carry2_cc"
4201 [(set (reg CC_REGNUM)
4202 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0,0,0,0")
4203 (match_operand:GPR 2 "general_operand" "d,Op,On,R,T,C"))
4204 (match_dup 2)))
4205 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,RS")
4206 (plus:GPR (match_dup 1) (match_dup 2)))]
4207 "s390_match_ccmode (insn, CCL1mode)"
4208 "@
4209 al<g>r\t%0,%2
4210 al<g>fi\t%0,%2
4211 sl<g>fi\t%0,%n2
4212 al<g>\t%0,%2
4213 al<y>\t%0,%2
4214 al<g>si\t%0,%c2"
4215 [(set_attr "op_type" "RR<E>,RIL,RIL,RX<Y>,RXY,SIY")
4216 (set_attr "cpu_facility" "*,extimm,extimm,*,*,z10")])
4217
4218 ; alr, al, aly, algr, alg
4219 (define_insn "*add<mode>3_carry2_cconly"
4220 [(set (reg CC_REGNUM)
4221 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0")
4222 (match_operand:GPR 2 "general_operand" "d,R,T"))
4223 (match_dup 2)))
4224 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4225 "s390_match_ccmode (insn, CCL1mode)"
4226 "@
4227 al<g>r\t%0,%2
4228 al<g>\t%0,%2
4229 al<y>\t%0,%2"
4230 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4231
4232 ; alr, alfi, slfi, al, aly, algr, algfi, slgfi, alg, alsi, algsi
4233 (define_insn "*add<mode>3_cc"
4234 [(set (reg CC_REGNUM)
4235 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0,0,0,0")
4236 (match_operand:GPR 2 "general_operand" "d,Op,On,R,T,C"))
4237 (const_int 0)))
4238 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,d,d,d,RS")
4239 (plus:GPR (match_dup 1) (match_dup 2)))]
4240 "s390_match_ccmode (insn, CCLmode)"
4241 "@
4242 al<g>r\t%0,%2
4243 al<g>fi\t%0,%2
4244 sl<g>fi\t%0,%n2
4245 al<g>\t%0,%2
4246 al<y>\t%0,%2
4247 al<g>si\t%0,%c2"
4248 [(set_attr "op_type" "RR<E>,RIL,RIL,RX<Y>,RXY,SIY")
4249 (set_attr "cpu_facility" "*,extimm,extimm,*,*,z10")])
4250
4251 ; alr, al, aly, algr, alg
4252 (define_insn "*add<mode>3_cconly"
4253 [(set (reg CC_REGNUM)
4254 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0")
4255 (match_operand:GPR 2 "general_operand" "d,R,T"))
4256 (const_int 0)))
4257 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4258 "s390_match_ccmode (insn, CCLmode)"
4259 "@
4260 al<g>r\t%0,%2
4261 al<g>\t%0,%2
4262 al<y>\t%0,%2"
4263 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4264
4265 ; alr, al, aly, algr, alg
4266 (define_insn "*add<mode>3_cconly2"
4267 [(set (reg CC_REGNUM)
4268 (compare (match_operand:GPR 1 "nonimmediate_operand" "%0,0,0")
4269 (neg:GPR (match_operand:GPR 2 "general_operand" "d,R,T"))))
4270 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4271 "s390_match_ccmode(insn, CCLmode)"
4272 "@
4273 al<g>r\t%0,%2
4274 al<g>\t%0,%2
4275 al<y>\t%0,%2"
4276 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4277
4278 ; ahi, afi, aghi, agfi, asi, agsi
4279 (define_insn "*add<mode>3_imm_cc"
4280 [(set (reg CC_REGNUM)
4281 (compare (plus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0,0")
4282 (match_operand:GPR 2 "const_int_operand" "K,Os,C"))
4283 (const_int 0)))
4284 (set (match_operand:GPR 0 "nonimmediate_operand" "=d,d,QS")
4285 (plus:GPR (match_dup 1) (match_dup 2)))]
4286 "s390_match_ccmode (insn, CCAmode)
4287 && (CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'K', \"K\")
4288 || CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'O', \"Os\")
4289 || CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'C', \"C\"))
4290 && INTVAL (operands[2]) != -((HOST_WIDE_INT)1 << (GET_MODE_BITSIZE(<MODE>mode) - 1))"
4291 "@
4292 a<g>hi\t%0,%h2
4293 a<g>fi\t%0,%2
4294 a<g>si\t%0,%c2"
4295 [(set_attr "op_type" "RI,RIL,SIY")
4296 (set_attr "cpu_facility" "*,extimm,z10")])
4297
4298 ;
4299 ; add(tf|df|sf|td|dd)3 instruction pattern(s).
4300 ;
4301
4302 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
4303 (define_insn "add<mode>3"
4304 [(set (match_operand:FP 0 "register_operand" "=f, f")
4305 (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
4306 (match_operand:FP 2 "general_operand" " f,<Rf>")))
4307 (clobber (reg:CC CC_REGNUM))]
4308 "TARGET_HARD_FLOAT"
4309 "@
4310 a<xde><bt>r\t%0,<op1>%2
4311 a<xde>b\t%0,%2"
4312 [(set_attr "op_type" "<RRer>,RXE")
4313 (set_attr "type" "fsimp<bfp>")])
4314
4315 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
4316 (define_insn "*add<mode>3_cc"
4317 [(set (reg CC_REGNUM)
4318 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
4319 (match_operand:FP 2 "general_operand" " f,<Rf>"))
4320 (match_operand:FP 3 "const0_operand" "")))
4321 (set (match_operand:FP 0 "register_operand" "=f,f")
4322 (plus:FP (match_dup 1) (match_dup 2)))]
4323 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
4324 "@
4325 a<xde><bt>r\t%0,<op1>%2
4326 a<xde>b\t%0,%2"
4327 [(set_attr "op_type" "<RRer>,RXE")
4328 (set_attr "type" "fsimp<bfp>")])
4329
4330 ; axbr, adbr, aebr, axb, adb, aeb, adtr, axtr
4331 (define_insn "*add<mode>3_cconly"
4332 [(set (reg CC_REGNUM)
4333 (compare (plus:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
4334 (match_operand:FP 2 "general_operand" " f,<Rf>"))
4335 (match_operand:FP 3 "const0_operand" "")))
4336 (clobber (match_scratch:FP 0 "=f,f"))]
4337 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
4338 "@
4339 a<xde><bt>r\t%0,<op1>%2
4340 a<xde>b\t%0,%2"
4341 [(set_attr "op_type" "<RRer>,RXE")
4342 (set_attr "type" "fsimp<bfp>")])
4343
4344
4345 ;;
4346 ;;- Subtract instructions.
4347 ;;
4348
4349 ;
4350 ; subti3 instruction pattern(s).
4351 ;
4352
4353 (define_insn_and_split "subti3"
4354 [(set (match_operand:TI 0 "register_operand" "=&d")
4355 (minus:TI (match_operand:TI 1 "register_operand" "0")
4356 (match_operand:TI 2 "general_operand" "do") ) )
4357 (clobber (reg:CC CC_REGNUM))]
4358 "TARGET_64BIT"
4359 "#"
4360 "&& reload_completed"
4361 [(parallel
4362 [(set (reg:CCL2 CC_REGNUM)
4363 (compare:CCL2 (minus:DI (match_dup 7) (match_dup 8))
4364 (match_dup 7)))
4365 (set (match_dup 6) (minus:DI (match_dup 7) (match_dup 8)))])
4366 (parallel
4367 [(set (match_dup 3) (minus:DI (minus:DI (match_dup 4) (match_dup 5))
4368 (gtu:DI (reg:CCL2 CC_REGNUM) (const_int 0))))
4369 (clobber (reg:CC CC_REGNUM))])]
4370 "operands[3] = operand_subword (operands[0], 0, 0, TImode);
4371 operands[4] = operand_subword (operands[1], 0, 0, TImode);
4372 operands[5] = operand_subword (operands[2], 0, 0, TImode);
4373 operands[6] = operand_subword (operands[0], 1, 0, TImode);
4374 operands[7] = operand_subword (operands[1], 1, 0, TImode);
4375 operands[8] = operand_subword (operands[2], 1, 0, TImode);")
4376
4377 ;
4378 ; subdi3 instruction pattern(s).
4379 ;
4380
4381 (define_expand "subdi3"
4382 [(parallel
4383 [(set (match_operand:DI 0 "register_operand" "")
4384 (minus:DI (match_operand:DI 1 "register_operand" "")
4385 (match_operand:DI 2 "general_operand" "")))
4386 (clobber (reg:CC CC_REGNUM))])]
4387 ""
4388 "")
4389
4390 (define_insn "*subdi3_sign"
4391 [(set (match_operand:DI 0 "register_operand" "=d,d")
4392 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
4393 (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
4394 (clobber (reg:CC CC_REGNUM))]
4395 "TARGET_64BIT"
4396 "@
4397 sgfr\t%0,%2
4398 sgf\t%0,%2"
4399 [(set_attr "op_type" "RRE,RXY")])
4400
4401 (define_insn "*subdi3_zero_cc"
4402 [(set (reg CC_REGNUM)
4403 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
4404 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
4405 (const_int 0)))
4406 (set (match_operand:DI 0 "register_operand" "=d,d")
4407 (minus:DI (match_dup 1) (zero_extend:DI (match_dup 2))))]
4408 "s390_match_ccmode (insn, CCLmode) && TARGET_64BIT"
4409 "@
4410 slgfr\t%0,%2
4411 slgf\t%0,%2"
4412 [(set_attr "op_type" "RRE,RXY")])
4413
4414 (define_insn "*subdi3_zero_cconly"
4415 [(set (reg CC_REGNUM)
4416 (compare (minus:DI (match_operand:DI 1 "register_operand" "0,0")
4417 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT")))
4418 (const_int 0)))
4419 (clobber (match_scratch:DI 0 "=d,d"))]
4420 "s390_match_ccmode (insn, CCLmode) && TARGET_64BIT"
4421 "@
4422 slgfr\t%0,%2
4423 slgf\t%0,%2"
4424 [(set_attr "op_type" "RRE,RXY")])
4425
4426 (define_insn "*subdi3_zero"
4427 [(set (match_operand:DI 0 "register_operand" "=d,d")
4428 (minus:DI (match_operand:DI 1 "register_operand" "0,0")
4429 (zero_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))))
4430 (clobber (reg:CC CC_REGNUM))]
4431 "TARGET_64BIT"
4432 "@
4433 slgfr\t%0,%2
4434 slgf\t%0,%2"
4435 [(set_attr "op_type" "RRE,RXY")])
4436
4437 (define_insn_and_split "*subdi3_31z"
4438 [(set (match_operand:DI 0 "register_operand" "=&d")
4439 (minus:DI (match_operand:DI 1 "register_operand" "0")
4440 (match_operand:DI 2 "general_operand" "do") ) )
4441 (clobber (reg:CC CC_REGNUM))]
4442 "!TARGET_64BIT && TARGET_CPU_ZARCH"
4443 "#"
4444 "&& reload_completed"
4445 [(parallel
4446 [(set (reg:CCL2 CC_REGNUM)
4447 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
4448 (match_dup 7)))
4449 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
4450 (parallel
4451 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 4) (match_dup 5))
4452 (gtu:SI (reg:CCL2 CC_REGNUM) (const_int 0))))
4453 (clobber (reg:CC CC_REGNUM))])]
4454 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
4455 operands[4] = operand_subword (operands[1], 0, 0, DImode);
4456 operands[5] = operand_subword (operands[2], 0, 0, DImode);
4457 operands[6] = operand_subword (operands[0], 1, 0, DImode);
4458 operands[7] = operand_subword (operands[1], 1, 0, DImode);
4459 operands[8] = operand_subword (operands[2], 1, 0, DImode);")
4460
4461 (define_insn_and_split "*subdi3_31"
4462 [(set (match_operand:DI 0 "register_operand" "=&d")
4463 (minus:DI (match_operand:DI 1 "register_operand" "0")
4464 (match_operand:DI 2 "general_operand" "do") ) )
4465 (clobber (reg:CC CC_REGNUM))]
4466 "!TARGET_CPU_ZARCH"
4467 "#"
4468 "&& reload_completed"
4469 [(parallel
4470 [(set (match_dup 3) (minus:SI (match_dup 4) (match_dup 5)))
4471 (clobber (reg:CC CC_REGNUM))])
4472 (parallel
4473 [(set (reg:CCL2 CC_REGNUM)
4474 (compare:CCL2 (minus:SI (match_dup 7) (match_dup 8))
4475 (match_dup 7)))
4476 (set (match_dup 6) (minus:SI (match_dup 7) (match_dup 8)))])
4477 (set (pc)
4478 (if_then_else (gtu (reg:CCL2 CC_REGNUM) (const_int 0))
4479 (pc)
4480 (label_ref (match_dup 9))))
4481 (parallel
4482 [(set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))
4483 (clobber (reg:CC CC_REGNUM))])
4484 (match_dup 9)]
4485 "operands[3] = operand_subword (operands[0], 0, 0, DImode);
4486 operands[4] = operand_subword (operands[1], 0, 0, DImode);
4487 operands[5] = operand_subword (operands[2], 0, 0, DImode);
4488 operands[6] = operand_subword (operands[0], 1, 0, DImode);
4489 operands[7] = operand_subword (operands[1], 1, 0, DImode);
4490 operands[8] = operand_subword (operands[2], 1, 0, DImode);
4491 operands[9] = gen_label_rtx ();")
4492
4493 ;
4494 ; subsi3 instruction pattern(s).
4495 ;
4496
4497 (define_expand "subsi3"
4498 [(parallel
4499 [(set (match_operand:SI 0 "register_operand" "")
4500 (minus:SI (match_operand:SI 1 "register_operand" "")
4501 (match_operand:SI 2 "general_operand" "")))
4502 (clobber (reg:CC CC_REGNUM))])]
4503 ""
4504 "")
4505
4506 (define_insn "*subsi3_sign"
4507 [(set (match_operand:SI 0 "register_operand" "=d,d")
4508 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
4509 (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))))
4510 (clobber (reg:CC CC_REGNUM))]
4511 ""
4512 "@
4513 sh\t%0,%2
4514 shy\t%0,%2"
4515 [(set_attr "op_type" "RX,RXY")])
4516
4517 ;
4518 ; sub(di|si)3 instruction pattern(s).
4519 ;
4520
4521 ; sr, s, sy, sgr, sg
4522 (define_insn "*sub<mode>3"
4523 [(set (match_operand:GPR 0 "register_operand" "=d,d,d")
4524 (minus:GPR (match_operand:GPR 1 "register_operand" "0,0,0")
4525 (match_operand:GPR 2 "general_operand" "d,R,T") ) )
4526 (clobber (reg:CC CC_REGNUM))]
4527 ""
4528 "@
4529 s<g>r\t%0,%2
4530 s<g>\t%0,%2
4531 s<y>\t%0,%2"
4532 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4533
4534 ; slr, sl, sly, slgr, slg
4535 (define_insn "*sub<mode>3_borrow_cc"
4536 [(set (reg CC_REGNUM)
4537 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,0,0")
4538 (match_operand:GPR 2 "general_operand" "d,R,T"))
4539 (match_dup 1)))
4540 (set (match_operand:GPR 0 "register_operand" "=d,d,d")
4541 (minus:GPR (match_dup 1) (match_dup 2)))]
4542 "s390_match_ccmode (insn, CCL2mode)"
4543 "@
4544 sl<g>r\t%0,%2
4545 sl<g>\t%0,%2
4546 sl<y>\t%0,%2"
4547 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4548
4549 ; slr, sl, sly, slgr, slg
4550 (define_insn "*sub<mode>3_borrow_cconly"
4551 [(set (reg CC_REGNUM)
4552 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,0,0")
4553 (match_operand:GPR 2 "general_operand" "d,R,T"))
4554 (match_dup 1)))
4555 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4556 "s390_match_ccmode (insn, CCL2mode)"
4557 "@
4558 sl<g>r\t%0,%2
4559 sl<g>\t%0,%2
4560 sl<y>\t%0,%2"
4561 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4562
4563 ; slr, sl, sly, slgr, slg
4564 (define_insn "*sub<mode>3_cc"
4565 [(set (reg CC_REGNUM)
4566 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,0,0")
4567 (match_operand:GPR 2 "general_operand" "d,R,T"))
4568 (const_int 0)))
4569 (set (match_operand:GPR 0 "register_operand" "=d,d,d")
4570 (minus:GPR (match_dup 1) (match_dup 2)))]
4571 "s390_match_ccmode (insn, CCLmode)"
4572 "@
4573 sl<g>r\t%0,%2
4574 sl<g>\t%0,%2
4575 sl<y>\t%0,%2"
4576 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4577
4578 ; slr, sl, sly, slgr, slg
4579 (define_insn "*sub<mode>3_cc2"
4580 [(set (reg CC_REGNUM)
4581 (compare (match_operand:GPR 1 "register_operand" "0,0,0")
4582 (match_operand:GPR 2 "general_operand" "d,R,T")))
4583 (set (match_operand:GPR 0 "register_operand" "=d,d,d")
4584 (minus:GPR (match_dup 1) (match_dup 2)))]
4585 "s390_match_ccmode (insn, CCL3mode)"
4586 "@
4587 sl<g>r\t%0,%2
4588 sl<g>\t%0,%2
4589 sl<y>\t%0,%2"
4590 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4591
4592 ; slr, sl, sly, slgr, slg
4593 (define_insn "*sub<mode>3_cconly"
4594 [(set (reg CC_REGNUM)
4595 (compare (minus:GPR (match_operand:GPR 1 "register_operand" "0,0,0")
4596 (match_operand:GPR 2 "general_operand" "d,R,T"))
4597 (const_int 0)))
4598 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4599 "s390_match_ccmode (insn, CCLmode)"
4600 "@
4601 sl<g>r\t%0,%2
4602 sl<g>\t%0,%2
4603 sl<y>\t%0,%2"
4604 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4605
4606 ; slr, sl, sly, slgr, slg
4607 (define_insn "*sub<mode>3_cconly2"
4608 [(set (reg CC_REGNUM)
4609 (compare (match_operand:GPR 1 "register_operand" "0,0,0")
4610 (match_operand:GPR 2 "general_operand" "d,R,T")))
4611 (clobber (match_scratch:GPR 0 "=d,d,d"))]
4612 "s390_match_ccmode (insn, CCL3mode)"
4613 "@
4614 sl<g>r\t%0,%2
4615 sl<g>\t%0,%2
4616 sl<y>\t%0,%2"
4617 [(set_attr "op_type" "RR<E>,RX<Y>,RXY")])
4618
4619 ;
4620 ; sub(tf|df|sf|td|dd)3 instruction pattern(s).
4621 ;
4622
4623 ; sxbr, sdbr, sebr, sxb, sdb, seb, sxtr, sdtr
4624 (define_insn "sub<mode>3"
4625 [(set (match_operand:FP 0 "register_operand" "=f, f")
4626 (minus:FP (match_operand:FP 1 "register_operand" "<f0>,0")
4627 (match_operand:FP 2 "general_operand" "f,<Rf>")))
4628 (clobber (reg:CC CC_REGNUM))]
4629 "TARGET_HARD_FLOAT"
4630 "@
4631 s<xde><bt>r\t%0,<op1>%2
4632 s<xde>b\t%0,%2"
4633 [(set_attr "op_type" "<RRer>,RXE")
4634 (set_attr "type" "fsimp<bfp>")])
4635
4636 ; sxbr, sdbr, sebr, sxb, sdb, seb, sxtr, sdtr
4637 (define_insn "*sub<mode>3_cc"
4638 [(set (reg CC_REGNUM)
4639 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
4640 (match_operand:FP 2 "general_operand" "f,<Rf>"))
4641 (match_operand:FP 3 "const0_operand" "")))
4642 (set (match_operand:FP 0 "register_operand" "=f,f")
4643 (minus:FP (match_dup 1) (match_dup 2)))]
4644 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
4645 "@
4646 s<xde><bt>r\t%0,<op1>%2
4647 s<xde>b\t%0,%2"
4648 [(set_attr "op_type" "<RRer>,RXE")
4649 (set_attr "type" "fsimp<bfp>")])
4650
4651 ; sxbr, sdbr, sebr, sxb, sdb, seb, sxtr, sdtr
4652 (define_insn "*sub<mode>3_cconly"
4653 [(set (reg CC_REGNUM)
4654 (compare (minus:FP (match_operand:FP 1 "nonimmediate_operand" "<f0>,0")
4655 (match_operand:FP 2 "general_operand" "f,<Rf>"))
4656 (match_operand:FP 3 "const0_operand" "")))
4657 (clobber (match_scratch:FP 0 "=f,f"))]
4658 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
4659 "@
4660 s<xde><bt>r\t%0,<op1>%2
4661 s<xde>b\t%0,%2"
4662 [(set_attr "op_type" "<RRer>,RXE")
4663 (set_attr "type" "fsimp<bfp>")])
4664
4665
4666 ;;
4667 ;;- Conditional add/subtract instructions.
4668 ;;
4669
4670 ;
4671 ; add(di|si)cc instruction pattern(s).
4672 ;
4673
4674 ; the following 4 patterns are used when the result of an add with
4675 ; carry is checked for an overflow condition
4676
4677 ; op1 + op2 + c < op1
4678
4679 ; alcr, alc, alcgr, alcg
4680 (define_insn "*add<mode>3_alc_carry1_cc"
4681 [(set (reg CC_REGNUM)
4682 (compare
4683 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4684 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4685 (match_operand:GPR 2 "general_operand" "d,RT"))
4686 (match_dup 1)))
4687 (set (match_operand:GPR 0 "register_operand" "=d,d")
4688 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
4689 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
4690 "@
4691 alc<g>r\t%0,%2
4692 alc<g>\t%0,%2"
4693 [(set_attr "op_type" "RRE,RXY")])
4694
4695 ; alcr, alc, alcgr, alcg
4696 (define_insn "*add<mode>3_alc_carry1_cconly"
4697 [(set (reg CC_REGNUM)
4698 (compare
4699 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4700 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4701 (match_operand:GPR 2 "general_operand" "d,RT"))
4702 (match_dup 1)))
4703 (clobber (match_scratch:GPR 0 "=d,d"))]
4704 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
4705 "@
4706 alc<g>r\t%0,%2
4707 alc<g>\t%0,%2"
4708 [(set_attr "op_type" "RRE,RXY")])
4709
4710 ; op1 + op2 + c < op2
4711
4712 ; alcr, alc, alcgr, alcg
4713 (define_insn "*add<mode>3_alc_carry2_cc"
4714 [(set (reg CC_REGNUM)
4715 (compare
4716 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4717 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4718 (match_operand:GPR 2 "general_operand" "d,RT"))
4719 (match_dup 2)))
4720 (set (match_operand:GPR 0 "register_operand" "=d,d")
4721 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
4722 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
4723 "@
4724 alc<g>r\t%0,%2
4725 alc<g>\t%0,%2"
4726 [(set_attr "op_type" "RRE,RXY")])
4727
4728 ; alcr, alc, alcgr, alcg
4729 (define_insn "*add<mode>3_alc_carry2_cconly"
4730 [(set (reg CC_REGNUM)
4731 (compare
4732 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4733 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4734 (match_operand:GPR 2 "general_operand" "d,RT"))
4735 (match_dup 2)))
4736 (clobber (match_scratch:GPR 0 "=d,d"))]
4737 "s390_match_ccmode (insn, CCL1mode) && TARGET_CPU_ZARCH"
4738 "@
4739 alc<g>r\t%0,%2
4740 alc<g>\t%0,%2"
4741 [(set_attr "op_type" "RRE,RXY")])
4742
4743 ; alcr, alc, alcgr, alcg
4744 (define_insn "*add<mode>3_alc_cc"
4745 [(set (reg CC_REGNUM)
4746 (compare
4747 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4748 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4749 (match_operand:GPR 2 "general_operand" "d,RT"))
4750 (const_int 0)))
4751 (set (match_operand:GPR 0 "register_operand" "=d,d")
4752 (plus:GPR (plus:GPR (match_dup 3) (match_dup 1)) (match_dup 2)))]
4753 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
4754 "@
4755 alc<g>r\t%0,%2
4756 alc<g>\t%0,%2"
4757 [(set_attr "op_type" "RRE,RXY")])
4758
4759 ; alcr, alc, alcgr, alcg
4760 (define_insn "*add<mode>3_alc"
4761 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4762 (plus:GPR (plus:GPR (match_operand:GPR 3 "s390_alc_comparison" "")
4763 (match_operand:GPR 1 "nonimmediate_operand" "%0,0"))
4764 (match_operand:GPR 2 "general_operand" "d,RT")))
4765 (clobber (reg:CC CC_REGNUM))]
4766 "TARGET_CPU_ZARCH"
4767 "@
4768 alc<g>r\t%0,%2
4769 alc<g>\t%0,%2"
4770 [(set_attr "op_type" "RRE,RXY")])
4771
4772 ; slbr, slb, slbgr, slbg
4773 (define_insn "*sub<mode>3_slb_cc"
4774 [(set (reg CC_REGNUM)
4775 (compare
4776 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
4777 (match_operand:GPR 2 "general_operand" "d,RT"))
4778 (match_operand:GPR 3 "s390_slb_comparison" ""))
4779 (const_int 0)))
4780 (set (match_operand:GPR 0 "register_operand" "=d,d")
4781 (minus:GPR (minus:GPR (match_dup 1) (match_dup 2)) (match_dup 3)))]
4782 "s390_match_ccmode (insn, CCLmode) && TARGET_CPU_ZARCH"
4783 "@
4784 slb<g>r\t%0,%2
4785 slb<g>\t%0,%2"
4786 [(set_attr "op_type" "RRE,RXY")])
4787
4788 ; slbr, slb, slbgr, slbg
4789 (define_insn "*sub<mode>3_slb"
4790 [(set (match_operand:GPR 0 "register_operand" "=d,d")
4791 (minus:GPR (minus:GPR (match_operand:GPR 1 "nonimmediate_operand" "0,0")
4792 (match_operand:GPR 2 "general_operand" "d,RT"))
4793 (match_operand:GPR 3 "s390_slb_comparison" "")))
4794 (clobber (reg:CC CC_REGNUM))]
4795 "TARGET_CPU_ZARCH"
4796 "@
4797 slb<g>r\t%0,%2
4798 slb<g>\t%0,%2"
4799 [(set_attr "op_type" "RRE,RXY")])
4800
4801 (define_expand "add<mode>cc"
4802 [(match_operand:GPR 0 "register_operand" "")
4803 (match_operand 1 "comparison_operator" "")
4804 (match_operand:GPR 2 "register_operand" "")
4805 (match_operand:GPR 3 "const_int_operand" "")]
4806 "TARGET_CPU_ZARCH"
4807 "if (!s390_expand_addcc (GET_CODE (operands[1]),
4808 s390_compare_op0, s390_compare_op1,
4809 operands[0], operands[2],
4810 operands[3])) FAIL; DONE;")
4811
4812 ;
4813 ; scond instruction pattern(s).
4814 ;
4815
4816 (define_insn_and_split "*scond<mode>"
4817 [(set (match_operand:GPR 0 "register_operand" "=&d")
4818 (match_operand:GPR 1 "s390_alc_comparison" ""))
4819 (clobber (reg:CC CC_REGNUM))]
4820 "TARGET_CPU_ZARCH"
4821 "#"
4822 "&& reload_completed"
4823 [(set (match_dup 0) (const_int 0))
4824 (parallel
4825 [(set (match_dup 0) (plus:GPR (plus:GPR (match_dup 1) (match_dup 0))
4826 (match_dup 0)))
4827 (clobber (reg:CC CC_REGNUM))])]
4828 "")
4829
4830 (define_insn_and_split "*scond<mode>_neg"
4831 [(set (match_operand:GPR 0 "register_operand" "=&d")
4832 (match_operand:GPR 1 "s390_slb_comparison" ""))
4833 (clobber (reg:CC CC_REGNUM))]
4834 "TARGET_CPU_ZARCH"
4835 "#"
4836 "&& reload_completed"
4837 [(set (match_dup 0) (const_int 0))
4838 (parallel
4839 [(set (match_dup 0) (minus:GPR (minus:GPR (match_dup 0) (match_dup 0))
4840 (match_dup 1)))
4841 (clobber (reg:CC CC_REGNUM))])
4842 (parallel
4843 [(set (match_dup 0) (neg:GPR (match_dup 0)))
4844 (clobber (reg:CC CC_REGNUM))])]
4845 "")
4846
4847
4848 (define_expand "s<code>"
4849 [(set (match_operand:SI 0 "register_operand" "")
4850 (SCOND (match_dup 0)
4851 (match_dup 0)))]
4852 "TARGET_CPU_ZARCH"
4853 "if (!s390_expand_addcc (<CODE>, s390_compare_op0, s390_compare_op1,
4854 operands[0], const0_rtx, const1_rtx)) FAIL; DONE;")
4855
4856 (define_expand "seq"
4857 [(parallel
4858 [(set (match_operand:SI 0 "register_operand" "=d")
4859 (match_dup 1))
4860 (clobber (reg:CC CC_REGNUM))])
4861 (parallel
4862 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 1)))
4863 (clobber (reg:CC CC_REGNUM))])]
4864 ""
4865 {
4866 if (!s390_compare_emitted || GET_MODE (s390_compare_emitted) != CCZ1mode)
4867 FAIL;
4868 operands[1] = s390_emit_compare (NE, s390_compare_op0, s390_compare_op1);
4869 PUT_MODE (operands[1], SImode);
4870 })
4871
4872 (define_insn_and_split "*sne"
4873 [(set (match_operand:SI 0 "register_operand" "=d")
4874 (ne:SI (match_operand:CCZ1 1 "register_operand" "0")
4875 (const_int 0)))
4876 (clobber (reg:CC CC_REGNUM))]
4877 ""
4878 "#"
4879 "reload_completed"
4880 [(parallel
4881 [(set (match_dup 0) (ashiftrt:SI (match_dup 0) (const_int 28)))
4882 (clobber (reg:CC CC_REGNUM))])])
4883
4884
4885 ;;
4886 ;;- Multiply instructions.
4887 ;;
4888
4889 ;
4890 ; muldi3 instruction pattern(s).
4891 ;
4892
4893 (define_insn "*muldi3_sign"
4894 [(set (match_operand:DI 0 "register_operand" "=d,d")
4895 (mult:DI (sign_extend:DI (match_operand:SI 2 "general_operand" "d,RT"))
4896 (match_operand:DI 1 "register_operand" "0,0")))]
4897 "TARGET_64BIT"
4898 "@
4899 msgfr\t%0,%2
4900 msgf\t%0,%2"
4901 [(set_attr "op_type" "RRE,RXY")
4902 (set_attr "type" "imuldi")])
4903
4904 (define_insn "muldi3"
4905 [(set (match_operand:DI 0 "register_operand" "=d,d,d,d")
4906 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0")
4907 (match_operand:DI 2 "general_operand" "d,K,RT,Os")))]
4908 "TARGET_64BIT"
4909 "@
4910 msgr\t%0,%2
4911 mghi\t%0,%h2
4912 msg\t%0,%2
4913 msgfi\t%0,%2"
4914 [(set_attr "op_type" "RRE,RI,RXY,RIL")
4915 (set_attr "type" "imuldi")
4916 (set_attr "cpu_facility" "*,*,*,z10")])
4917
4918 ;
4919 ; mulsi3 instruction pattern(s).
4920 ;
4921
4922 (define_insn "*mulsi3_sign"
4923 [(set (match_operand:SI 0 "register_operand" "=d,d")
4924 (mult:SI (sign_extend:SI (match_operand:HI 2 "memory_operand" "R,T"))
4925 (match_operand:SI 1 "register_operand" "0,0")))]
4926 ""
4927 "@
4928 mh\t%0,%2
4929 mhy\t%0,%2"
4930 [(set_attr "op_type" "RX,RXY")
4931 (set_attr "type" "imulhi")
4932 (set_attr "cpu_facility" "*,z10")])
4933
4934 (define_insn "mulsi3"
4935 [(set (match_operand:SI 0 "register_operand" "=d,d,d,d,d")
4936 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0")
4937 (match_operand:SI 2 "general_operand" "d,K,R,T,Os")))]
4938 ""
4939 "@
4940 msr\t%0,%2
4941 mhi\t%0,%h2
4942 ms\t%0,%2
4943 msy\t%0,%2
4944 msfi\t%0,%2"
4945 [(set_attr "op_type" "RRE,RI,RX,RXY,RIL")
4946 (set_attr "type" "imulsi,imulhi,imulsi,imulsi,imulsi")
4947 (set_attr "cpu_facility" "*,*,*,*,z10")])
4948
4949 ;
4950 ; mulsidi3 instruction pattern(s).
4951 ;
4952
4953 (define_insn "mulsidi3"
4954 [(set (match_operand:DI 0 "register_operand" "=d,d,d")
4955 (mult:DI (sign_extend:DI
4956 (match_operand:SI 1 "register_operand" "%0,0,0"))
4957 (sign_extend:DI
4958 (match_operand:SI 2 "nonimmediate_operand" "d,R,T"))))]
4959 "!TARGET_64BIT"
4960 "@
4961 mr\t%0,%2
4962 m\t%0,%2
4963 mfy\t%0,%2"
4964 [(set_attr "op_type" "RR,RX,RXY")
4965 (set_attr "type" "imulsi")
4966 (set_attr "cpu_facility" "*,*,z10")])
4967
4968 ;
4969 ; umulsidi3 instruction pattern(s).
4970 ;
4971
4972 (define_insn "umulsidi3"
4973 [(set (match_operand:DI 0 "register_operand" "=d,d")
4974 (mult:DI (zero_extend:DI
4975 (match_operand:SI 1 "register_operand" "%0,0"))
4976 (zero_extend:DI
4977 (match_operand:SI 2 "nonimmediate_operand" "d,RT"))))]
4978 "!TARGET_64BIT && TARGET_CPU_ZARCH"
4979 "@
4980 mlr\t%0,%2
4981 ml\t%0,%2"
4982 [(set_attr "op_type" "RRE,RXY")
4983 (set_attr "type" "imulsi")])
4984
4985 ;
4986 ; mul(tf|df|sf|td|dd)3 instruction pattern(s).
4987 ;
4988
4989 ; mxbr mdbr, meebr, mxb, mxb, meeb, mdtr, mxtr
4990 (define_insn "mul<mode>3"
4991 [(set (match_operand:FP 0 "register_operand" "=f,f")
4992 (mult:FP (match_operand:FP 1 "nonimmediate_operand" "%<f0>,0")
4993 (match_operand:FP 2 "general_operand" "f,<Rf>")))]
4994 "TARGET_HARD_FLOAT"
4995 "@
4996 m<xdee><bt>r\t%0,<op1>%2
4997 m<xdee>b\t%0,%2"
4998 [(set_attr "op_type" "<RRer>,RXE")
4999 (set_attr "type" "fmul<bfp>")])
5000
5001 ; maxbr, madbr, maebr, maxb, madb, maeb
5002 (define_insn "*fmadd<mode>"
5003 [(set (match_operand:DSF 0 "register_operand" "=f,f")
5004 (plus:DSF (mult:DSF (match_operand:DSF 1 "register_operand" "%f,f")
5005 (match_operand:DSF 2 "nonimmediate_operand" "f,R"))
5006 (match_operand:DSF 3 "register_operand" "0,0")))]
5007 "TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
5008 "@
5009 ma<xde>br\t%0,%1,%2
5010 ma<xde>b\t%0,%1,%2"
5011 [(set_attr "op_type" "RRE,RXE")
5012 (set_attr "type" "fmul<mode>")])
5013
5014 ; msxbr, msdbr, msebr, msxb, msdb, mseb
5015 (define_insn "*fmsub<mode>"
5016 [(set (match_operand:DSF 0 "register_operand" "=f,f")
5017 (minus:DSF (mult:DSF (match_operand:DSF 1 "register_operand" "f,f")
5018 (match_operand:DSF 2 "nonimmediate_operand" "f,R"))
5019 (match_operand:DSF 3 "register_operand" "0,0")))]
5020 "TARGET_HARD_FLOAT && TARGET_FUSED_MADD"
5021 "@
5022 ms<xde>br\t%0,%1,%2
5023 ms<xde>b\t%0,%1,%2"
5024 [(set_attr "op_type" "RRE,RXE")
5025 (set_attr "type" "fmul<mode>")])
5026
5027 ;;
5028 ;;- Divide and modulo instructions.
5029 ;;
5030
5031 ;
5032 ; divmoddi4 instruction pattern(s).
5033 ;
5034
5035 (define_expand "divmoddi4"
5036 [(parallel [(set (match_operand:DI 0 "general_operand" "")
5037 (div:DI (match_operand:DI 1 "register_operand" "")
5038 (match_operand:DI 2 "general_operand" "")))
5039 (set (match_operand:DI 3 "general_operand" "")
5040 (mod:DI (match_dup 1) (match_dup 2)))])
5041 (clobber (match_dup 4))]
5042 "TARGET_64BIT"
5043 {
5044 rtx insn, div_equal, mod_equal;
5045
5046 div_equal = gen_rtx_DIV (DImode, operands[1], operands[2]);
5047 mod_equal = gen_rtx_MOD (DImode, operands[1], operands[2]);
5048
5049 operands[4] = gen_reg_rtx(TImode);
5050 emit_insn (gen_divmodtidi3 (operands[4], operands[1], operands[2]));
5051
5052 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
5053 set_unique_reg_note (insn, REG_EQUAL, div_equal);
5054
5055 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
5056 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
5057
5058 DONE;
5059 })
5060
5061 (define_insn "divmodtidi3"
5062 [(set (match_operand:TI 0 "register_operand" "=d,d")
5063 (ior:TI
5064 (ashift:TI
5065 (zero_extend:TI
5066 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
5067 (match_operand:DI 2 "general_operand" "d,RT")))
5068 (const_int 64))
5069 (zero_extend:TI (div:DI (match_dup 1) (match_dup 2)))))]
5070 "TARGET_64BIT"
5071 "@
5072 dsgr\t%0,%2
5073 dsg\t%0,%2"
5074 [(set_attr "op_type" "RRE,RXY")
5075 (set_attr "type" "idiv")])
5076
5077 (define_insn "divmodtisi3"
5078 [(set (match_operand:TI 0 "register_operand" "=d,d")
5079 (ior:TI
5080 (ashift:TI
5081 (zero_extend:TI
5082 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
5083 (sign_extend:DI
5084 (match_operand:SI 2 "nonimmediate_operand" "d,RT"))))
5085 (const_int 64))
5086 (zero_extend:TI
5087 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2))))))]
5088 "TARGET_64BIT"
5089 "@
5090 dsgfr\t%0,%2
5091 dsgf\t%0,%2"
5092 [(set_attr "op_type" "RRE,RXY")
5093 (set_attr "type" "idiv")])
5094
5095 ;
5096 ; udivmoddi4 instruction pattern(s).
5097 ;
5098
5099 (define_expand "udivmoddi4"
5100 [(parallel [(set (match_operand:DI 0 "general_operand" "")
5101 (udiv:DI (match_operand:DI 1 "general_operand" "")
5102 (match_operand:DI 2 "nonimmediate_operand" "")))
5103 (set (match_operand:DI 3 "general_operand" "")
5104 (umod:DI (match_dup 1) (match_dup 2)))])
5105 (clobber (match_dup 4))]
5106 "TARGET_64BIT"
5107 {
5108 rtx insn, div_equal, mod_equal, equal;
5109
5110 div_equal = gen_rtx_UDIV (DImode, operands[1], operands[2]);
5111 mod_equal = gen_rtx_UMOD (DImode, operands[1], operands[2]);
5112 equal = gen_rtx_IOR (TImode,
5113 gen_rtx_ASHIFT (TImode,
5114 gen_rtx_ZERO_EXTEND (TImode, mod_equal),
5115 GEN_INT (64)),
5116 gen_rtx_ZERO_EXTEND (TImode, div_equal));
5117
5118 operands[4] = gen_reg_rtx(TImode);
5119 emit_clobber (operands[4]);
5120 emit_move_insn (gen_lowpart (DImode, operands[4]), operands[1]);
5121 emit_move_insn (gen_highpart (DImode, operands[4]), const0_rtx);
5122
5123 insn = emit_insn (gen_udivmodtidi3 (operands[4], operands[4], operands[2]));
5124 set_unique_reg_note (insn, REG_EQUAL, equal);
5125
5126 insn = emit_move_insn (operands[0], gen_lowpart (DImode, operands[4]));
5127 set_unique_reg_note (insn, REG_EQUAL, div_equal);
5128
5129 insn = emit_move_insn (operands[3], gen_highpart (DImode, operands[4]));
5130 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
5131
5132 DONE;
5133 })
5134
5135 (define_insn "udivmodtidi3"
5136 [(set (match_operand:TI 0 "register_operand" "=d,d")
5137 (ior:TI
5138 (ashift:TI
5139 (zero_extend:TI
5140 (truncate:DI
5141 (umod:TI (match_operand:TI 1 "register_operand" "0,0")
5142 (zero_extend:TI
5143 (match_operand:DI 2 "nonimmediate_operand" "d,RT")))))
5144 (const_int 64))
5145 (zero_extend:TI
5146 (truncate:DI
5147 (udiv:TI (match_dup 1) (zero_extend:TI (match_dup 2)))))))]
5148 "TARGET_64BIT"
5149 "@
5150 dlgr\t%0,%2
5151 dlg\t%0,%2"
5152 [(set_attr "op_type" "RRE,RXY")
5153 (set_attr "type" "idiv")])
5154
5155 ;
5156 ; divmodsi4 instruction pattern(s).
5157 ;
5158
5159 (define_expand "divmodsi4"
5160 [(parallel [(set (match_operand:SI 0 "general_operand" "")
5161 (div:SI (match_operand:SI 1 "general_operand" "")
5162 (match_operand:SI 2 "nonimmediate_operand" "")))
5163 (set (match_operand:SI 3 "general_operand" "")
5164 (mod:SI (match_dup 1) (match_dup 2)))])
5165 (clobber (match_dup 4))]
5166 "!TARGET_64BIT"
5167 {
5168 rtx insn, div_equal, mod_equal, equal;
5169
5170 div_equal = gen_rtx_DIV (SImode, operands[1], operands[2]);
5171 mod_equal = gen_rtx_MOD (SImode, operands[1], operands[2]);
5172 equal = gen_rtx_IOR (DImode,
5173 gen_rtx_ASHIFT (DImode,
5174 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
5175 GEN_INT (32)),
5176 gen_rtx_ZERO_EXTEND (DImode, div_equal));
5177
5178 operands[4] = gen_reg_rtx(DImode);
5179 emit_insn (gen_extendsidi2 (operands[4], operands[1]));
5180
5181 insn = emit_insn (gen_divmoddisi3 (operands[4], operands[4], operands[2]));
5182 set_unique_reg_note (insn, REG_EQUAL, equal);
5183
5184 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
5185 set_unique_reg_note (insn, REG_EQUAL, div_equal);
5186
5187 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
5188 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
5189
5190 DONE;
5191 })
5192
5193 (define_insn "divmoddisi3"
5194 [(set (match_operand:DI 0 "register_operand" "=d,d")
5195 (ior:DI
5196 (ashift:DI
5197 (zero_extend:DI
5198 (truncate:SI
5199 (mod:DI (match_operand:DI 1 "register_operand" "0,0")
5200 (sign_extend:DI
5201 (match_operand:SI 2 "nonimmediate_operand" "d,R")))))
5202 (const_int 32))
5203 (zero_extend:DI
5204 (truncate:SI
5205 (div:DI (match_dup 1) (sign_extend:DI (match_dup 2)))))))]
5206 "!TARGET_64BIT"
5207 "@
5208 dr\t%0,%2
5209 d\t%0,%2"
5210 [(set_attr "op_type" "RR,RX")
5211 (set_attr "type" "idiv")])
5212
5213 ;
5214 ; udivsi3 and umodsi3 instruction pattern(s).
5215 ;
5216
5217 (define_expand "udivmodsi4"
5218 [(parallel [(set (match_operand:SI 0 "general_operand" "")
5219 (udiv:SI (match_operand:SI 1 "general_operand" "")
5220 (match_operand:SI 2 "nonimmediate_operand" "")))
5221 (set (match_operand:SI 3 "general_operand" "")
5222 (umod:SI (match_dup 1) (match_dup 2)))])
5223 (clobber (match_dup 4))]
5224 "!TARGET_64BIT && TARGET_CPU_ZARCH"
5225 {
5226 rtx insn, div_equal, mod_equal, equal;
5227
5228 div_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
5229 mod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
5230 equal = gen_rtx_IOR (DImode,
5231 gen_rtx_ASHIFT (DImode,
5232 gen_rtx_ZERO_EXTEND (DImode, mod_equal),
5233 GEN_INT (32)),
5234 gen_rtx_ZERO_EXTEND (DImode, div_equal));
5235
5236 operands[4] = gen_reg_rtx(DImode);
5237 emit_clobber (operands[4]);
5238 emit_move_insn (gen_lowpart (SImode, operands[4]), operands[1]);
5239 emit_move_insn (gen_highpart (SImode, operands[4]), const0_rtx);
5240
5241 insn = emit_insn (gen_udivmoddisi3 (operands[4], operands[4], operands[2]));
5242 set_unique_reg_note (insn, REG_EQUAL, equal);
5243
5244 insn = emit_move_insn (operands[0], gen_lowpart (SImode, operands[4]));
5245 set_unique_reg_note (insn, REG_EQUAL, div_equal);
5246
5247 insn = emit_move_insn (operands[3], gen_highpart (SImode, operands[4]));
5248 set_unique_reg_note (insn, REG_EQUAL, mod_equal);
5249
5250 DONE;
5251 })
5252
5253 (define_insn "udivmoddisi3"
5254 [(set (match_operand:DI 0 "register_operand" "=d,d")
5255 (ior:DI
5256 (ashift:DI
5257 (zero_extend:DI
5258 (truncate:SI
5259 (umod:DI (match_operand:DI 1 "register_operand" "0,0")
5260 (zero_extend:DI
5261 (match_operand:SI 2 "nonimmediate_operand" "d,RT")))))
5262 (const_int 32))
5263 (zero_extend:DI
5264 (truncate:SI
5265 (udiv:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))))]
5266 "!TARGET_64BIT && TARGET_CPU_ZARCH"
5267 "@
5268 dlr\t%0,%2
5269 dl\t%0,%2"
5270 [(set_attr "op_type" "RRE,RXY")
5271 (set_attr "type" "idiv")])
5272
5273 (define_expand "udivsi3"
5274 [(set (match_operand:SI 0 "register_operand" "=d")
5275 (udiv:SI (match_operand:SI 1 "general_operand" "")
5276 (match_operand:SI 2 "general_operand" "")))
5277 (clobber (match_dup 3))]
5278 "!TARGET_64BIT && !TARGET_CPU_ZARCH"
5279 {
5280 rtx insn, udiv_equal, umod_equal, equal;
5281
5282 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
5283 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
5284 equal = gen_rtx_IOR (DImode,
5285 gen_rtx_ASHIFT (DImode,
5286 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
5287 GEN_INT (32)),
5288 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
5289
5290 operands[3] = gen_reg_rtx (DImode);
5291
5292 if (CONSTANT_P (operands[2]))
5293 {
5294 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
5295 {
5296 rtx label1 = gen_label_rtx ();
5297
5298 operands[1] = make_safe_from (operands[1], operands[0]);
5299 emit_move_insn (operands[0], const0_rtx);
5300 emit_insn (gen_cmpsi (operands[1], operands[2]));
5301 emit_jump_insn (gen_bltu (label1));
5302 emit_move_insn (operands[0], const1_rtx);
5303 emit_label (label1);
5304 }
5305 else
5306 {
5307 operands[2] = force_reg (SImode, operands[2]);
5308 operands[2] = make_safe_from (operands[2], operands[0]);
5309
5310 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
5311 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
5312 operands[2]));
5313 set_unique_reg_note (insn, REG_EQUAL, equal);
5314
5315 insn = emit_move_insn (operands[0],
5316 gen_lowpart (SImode, operands[3]));
5317 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
5318 }
5319 }
5320 else
5321 {
5322 rtx label1 = gen_label_rtx ();
5323 rtx label2 = gen_label_rtx ();
5324 rtx label3 = gen_label_rtx ();
5325
5326 operands[1] = force_reg (SImode, operands[1]);
5327 operands[1] = make_safe_from (operands[1], operands[0]);
5328 operands[2] = force_reg (SImode, operands[2]);
5329 operands[2] = make_safe_from (operands[2], operands[0]);
5330
5331 emit_move_insn (operands[0], const0_rtx);
5332 emit_insn (gen_cmpsi (operands[2], operands[1]));
5333 emit_jump_insn (gen_bgtu (label3));
5334 emit_insn (gen_cmpsi (operands[2], const0_rtx));
5335 emit_jump_insn (gen_blt (label2));
5336 emit_insn (gen_cmpsi (operands[2], const1_rtx));
5337 emit_jump_insn (gen_beq (label1));
5338 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
5339 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
5340 operands[2]));
5341 set_unique_reg_note (insn, REG_EQUAL, equal);
5342
5343 insn = emit_move_insn (operands[0],
5344 gen_lowpart (SImode, operands[3]));
5345 set_unique_reg_note (insn, REG_EQUAL, udiv_equal);
5346
5347 emit_jump (label3);
5348 emit_label (label1);
5349 emit_move_insn (operands[0], operands[1]);
5350 emit_jump (label3);
5351 emit_label (label2);
5352 emit_move_insn (operands[0], const1_rtx);
5353 emit_label (label3);
5354 }
5355 emit_move_insn (operands[0], operands[0]);
5356 DONE;
5357 })
5358
5359 (define_expand "umodsi3"
5360 [(set (match_operand:SI 0 "register_operand" "=d")
5361 (umod:SI (match_operand:SI 1 "nonimmediate_operand" "")
5362 (match_operand:SI 2 "nonimmediate_operand" "")))
5363 (clobber (match_dup 3))]
5364 "!TARGET_64BIT && !TARGET_CPU_ZARCH"
5365 {
5366 rtx insn, udiv_equal, umod_equal, equal;
5367
5368 udiv_equal = gen_rtx_UDIV (SImode, operands[1], operands[2]);
5369 umod_equal = gen_rtx_UMOD (SImode, operands[1], operands[2]);
5370 equal = gen_rtx_IOR (DImode,
5371 gen_rtx_ASHIFT (DImode,
5372 gen_rtx_ZERO_EXTEND (DImode, umod_equal),
5373 GEN_INT (32)),
5374 gen_rtx_ZERO_EXTEND (DImode, udiv_equal));
5375
5376 operands[3] = gen_reg_rtx (DImode);
5377
5378 if (CONSTANT_P (operands[2]))
5379 {
5380 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) <= 0)
5381 {
5382 rtx label1 = gen_label_rtx ();
5383
5384 operands[1] = make_safe_from (operands[1], operands[0]);
5385 emit_move_insn (operands[0], operands[1]);
5386 emit_insn (gen_cmpsi (operands[0], operands[2]));
5387 emit_jump_insn (gen_bltu (label1));
5388 emit_insn (gen_abssi2 (operands[0], operands[2]));
5389 emit_insn (gen_addsi3 (operands[0], operands[0], operands[1]));
5390 emit_label (label1);
5391 }
5392 else
5393 {
5394 operands[2] = force_reg (SImode, operands[2]);
5395 operands[2] = make_safe_from (operands[2], operands[0]);
5396
5397 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
5398 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
5399 operands[2]));
5400 set_unique_reg_note (insn, REG_EQUAL, equal);
5401
5402 insn = emit_move_insn (operands[0],
5403 gen_highpart (SImode, operands[3]));
5404 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
5405 }
5406 }
5407 else
5408 {
5409 rtx label1 = gen_label_rtx ();
5410 rtx label2 = gen_label_rtx ();
5411 rtx label3 = gen_label_rtx ();
5412
5413 operands[1] = force_reg (SImode, operands[1]);
5414 operands[1] = make_safe_from (operands[1], operands[0]);
5415 operands[2] = force_reg (SImode, operands[2]);
5416 operands[2] = make_safe_from (operands[2], operands[0]);
5417
5418 emit_move_insn(operands[0], operands[1]);
5419 emit_insn (gen_cmpsi (operands[2], operands[1]));
5420 emit_jump_insn (gen_bgtu (label3));
5421 emit_insn (gen_cmpsi (operands[2], const0_rtx));
5422 emit_jump_insn (gen_blt (label2));
5423 emit_insn (gen_cmpsi (operands[2], const1_rtx));
5424 emit_jump_insn (gen_beq (label1));
5425 emit_insn (gen_zero_extendsidi2 (operands[3], operands[1]));
5426 insn = emit_insn (gen_divmoddisi3 (operands[3], operands[3],
5427 operands[2]));
5428 set_unique_reg_note (insn, REG_EQUAL, equal);
5429
5430 insn = emit_move_insn (operands[0],
5431 gen_highpart (SImode, operands[3]));
5432 set_unique_reg_note (insn, REG_EQUAL, umod_equal);
5433
5434 emit_jump (label3);
5435 emit_label (label1);
5436 emit_move_insn (operands[0], const0_rtx);
5437 emit_jump (label3);
5438 emit_label (label2);
5439 emit_insn (gen_subsi3 (operands[0], operands[0], operands[2]));
5440 emit_label (label3);
5441 }
5442 DONE;
5443 })
5444
5445 ;
5446 ; div(df|sf)3 instruction pattern(s).
5447 ;
5448
5449 ; dxbr, ddbr, debr, dxb, ddb, deb, ddtr, dxtr
5450 (define_insn "div<mode>3"
5451 [(set (match_operand:FP 0 "register_operand" "=f,f")
5452 (div:FP (match_operand:FP 1 "register_operand" "<f0>,0")
5453 (match_operand:FP 2 "general_operand" "f,<Rf>")))]
5454 "TARGET_HARD_FLOAT"
5455 "@
5456 d<xde><bt>r\t%0,<op1>%2
5457 d<xde>b\t%0,%2"
5458 [(set_attr "op_type" "<RRer>,RXE")
5459 (set_attr "type" "fdiv<bfp>")])
5460
5461
5462 ;;
5463 ;;- And instructions.
5464 ;;
5465
5466 (define_expand "and<mode>3"
5467 [(set (match_operand:INT 0 "nonimmediate_operand" "")
5468 (and:INT (match_operand:INT 1 "nonimmediate_operand" "")
5469 (match_operand:INT 2 "general_operand" "")))
5470 (clobber (reg:CC CC_REGNUM))]
5471 ""
5472 "s390_expand_logical_operator (AND, <MODE>mode, operands); DONE;")
5473
5474 ;
5475 ; anddi3 instruction pattern(s).
5476 ;
5477
5478 (define_insn "*anddi3_cc"
5479 [(set (reg CC_REGNUM)
5480 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5481 (match_operand:DI 2 "general_operand" "d,RT"))
5482 (const_int 0)))
5483 (set (match_operand:DI 0 "register_operand" "=d,d")
5484 (and:DI (match_dup 1) (match_dup 2)))]
5485 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT"
5486 "@
5487 ngr\t%0,%2
5488 ng\t%0,%2"
5489 [(set_attr "op_type" "RRE,RXY")])
5490
5491 (define_insn "*anddi3_cconly"
5492 [(set (reg CC_REGNUM)
5493 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5494 (match_operand:DI 2 "general_operand" "d,RT"))
5495 (const_int 0)))
5496 (clobber (match_scratch:DI 0 "=d,d"))]
5497 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT
5498 /* Do not steal TM patterns. */
5499 && s390_single_part (operands[2], DImode, HImode, 0) < 0"
5500 "@
5501 ngr\t%0,%2
5502 ng\t%0,%2"
5503 [(set_attr "op_type" "RRE,RXY")])
5504
5505 (define_insn "*anddi3"
5506 [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,d,d,d,d,d,d,d,AQ,Q")
5507 (and:DI (match_operand:DI 1 "nonimmediate_operand"
5508 "%d,o,0,0,0,0,0,0,0,0,0,0")
5509 (match_operand:DI 2 "general_operand"
5510 "M,M,N0HDF,N1HDF,N2HDF,N3HDF,N0SDF,N1SDF,d,RT,NxQDF,Q")))
5511 (clobber (reg:CC CC_REGNUM))]
5512 "TARGET_64BIT && s390_logical_operator_ok_p (operands)"
5513 "@
5514 #
5515 #
5516 nihh\t%0,%j2
5517 nihl\t%0,%j2
5518 nilh\t%0,%j2
5519 nill\t%0,%j2
5520 nihf\t%0,%m2
5521 nilf\t%0,%m2
5522 ngr\t%0,%2
5523 ng\t%0,%2
5524 #
5525 #"
5526 [(set_attr "op_type" "RRE,RXE,RI,RI,RI,RI,RIL,RIL,RRE,RXY,SI,SS")
5527 (set_attr "cpu_facility" "*,*,*,*,*,*,extimm,extimm,*,*,*,*")])
5528
5529 (define_split
5530 [(set (match_operand:DI 0 "s_operand" "")
5531 (and:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
5532 (clobber (reg:CC CC_REGNUM))]
5533 "reload_completed"
5534 [(parallel
5535 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
5536 (clobber (reg:CC CC_REGNUM))])]
5537 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
5538
5539
5540 ;
5541 ; andsi3 instruction pattern(s).
5542 ;
5543
5544 (define_insn "*andsi3_cc"
5545 [(set (reg CC_REGNUM)
5546 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5547 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
5548 (const_int 0)))
5549 (set (match_operand:SI 0 "register_operand" "=d,d,d,d")
5550 (and:SI (match_dup 1) (match_dup 2)))]
5551 "s390_match_ccmode(insn, CCTmode)"
5552 "@
5553 nilf\t%0,%o2
5554 nr\t%0,%2
5555 n\t%0,%2
5556 ny\t%0,%2"
5557 [(set_attr "op_type" "RIL,RR,RX,RXY")])
5558
5559 (define_insn "*andsi3_cconly"
5560 [(set (reg CC_REGNUM)
5561 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5562 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
5563 (const_int 0)))
5564 (clobber (match_scratch:SI 0 "=d,d,d,d"))]
5565 "s390_match_ccmode(insn, CCTmode)
5566 /* Do not steal TM patterns. */
5567 && s390_single_part (operands[2], SImode, HImode, 0) < 0"
5568 "@
5569 nilf\t%0,%o2
5570 nr\t%0,%2
5571 n\t%0,%2
5572 ny\t%0,%2"
5573 [(set_attr "op_type" "RIL,RR,RX,RXY")])
5574
5575 (define_insn "*andsi3_zarch"
5576 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d,d,d,d,AQ,Q")
5577 (and:SI (match_operand:SI 1 "nonimmediate_operand"
5578 "%d,o,0,0,0,0,0,0,0,0")
5579 (match_operand:SI 2 "general_operand"
5580 "M,M,N0HSF,N1HSF,Os,d,R,T,NxQSF,Q")))
5581 (clobber (reg:CC CC_REGNUM))]
5582 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5583 "@
5584 #
5585 #
5586 nilh\t%0,%j2
5587 nill\t%0,%j2
5588 nilf\t%0,%o2
5589 nr\t%0,%2
5590 n\t%0,%2
5591 ny\t%0,%2
5592 #
5593 #"
5594 [(set_attr "op_type" "RRE,RXE,RI,RI,RIL,RR,RX,RXY,SI,SS")])
5595
5596 (define_insn "*andsi3_esa"
5597 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
5598 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5599 (match_operand:SI 2 "general_operand" "d,R,NxQSF,Q")))
5600 (clobber (reg:CC CC_REGNUM))]
5601 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5602 "@
5603 nr\t%0,%2
5604 n\t%0,%2
5605 #
5606 #"
5607 [(set_attr "op_type" "RR,RX,SI,SS")])
5608
5609 (define_split
5610 [(set (match_operand:SI 0 "s_operand" "")
5611 (and:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
5612 (clobber (reg:CC CC_REGNUM))]
5613 "reload_completed"
5614 [(parallel
5615 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
5616 (clobber (reg:CC CC_REGNUM))])]
5617 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
5618
5619 ;
5620 ; andhi3 instruction pattern(s).
5621 ;
5622
5623 (define_insn "*andhi3_zarch"
5624 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,AQ,Q")
5625 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0,0")
5626 (match_operand:HI 2 "general_operand" "d,n,NxQHF,Q")))
5627 (clobber (reg:CC CC_REGNUM))]
5628 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5629 "@
5630 nr\t%0,%2
5631 nill\t%0,%x2
5632 #
5633 #"
5634 [(set_attr "op_type" "RR,RI,SI,SS")])
5635
5636 (define_insn "*andhi3_esa"
5637 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
5638 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
5639 (match_operand:HI 2 "general_operand" "d,NxQHF,Q")))
5640 (clobber (reg:CC CC_REGNUM))]
5641 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5642 "@
5643 nr\t%0,%2
5644 #
5645 #"
5646 [(set_attr "op_type" "RR,SI,SS")])
5647
5648 (define_split
5649 [(set (match_operand:HI 0 "s_operand" "")
5650 (and:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
5651 (clobber (reg:CC CC_REGNUM))]
5652 "reload_completed"
5653 [(parallel
5654 [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
5655 (clobber (reg:CC CC_REGNUM))])]
5656 "s390_narrow_logical_operator (AND, &operands[0], &operands[1]);")
5657
5658 ;
5659 ; andqi3 instruction pattern(s).
5660 ;
5661
5662 (define_insn "*andqi3_zarch"
5663 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,Q,S,Q")
5664 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,0,0")
5665 (match_operand:QI 2 "general_operand" "d,n,n,n,Q")))
5666 (clobber (reg:CC CC_REGNUM))]
5667 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5668 "@
5669 nr\t%0,%2
5670 nill\t%0,%b2
5671 ni\t%S0,%b2
5672 niy\t%S0,%b2
5673 #"
5674 [(set_attr "op_type" "RR,RI,SI,SIY,SS")])
5675
5676 (define_insn "*andqi3_esa"
5677 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
5678 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
5679 (match_operand:QI 2 "general_operand" "d,n,Q")))
5680 (clobber (reg:CC CC_REGNUM))]
5681 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5682 "@
5683 nr\t%0,%2
5684 ni\t%S0,%b2
5685 #"
5686 [(set_attr "op_type" "RR,SI,SS")])
5687
5688 ;
5689 ; Block and (NC) patterns.
5690 ;
5691
5692 (define_insn "*nc"
5693 [(set (match_operand:BLK 0 "memory_operand" "=Q")
5694 (and:BLK (match_dup 0)
5695 (match_operand:BLK 1 "memory_operand" "Q")))
5696 (use (match_operand 2 "const_int_operand" "n"))
5697 (clobber (reg:CC CC_REGNUM))]
5698 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
5699 "nc\t%O0(%2,%R0),%S1"
5700 [(set_attr "op_type" "SS")])
5701
5702 (define_split
5703 [(set (match_operand 0 "memory_operand" "")
5704 (and (match_dup 0)
5705 (match_operand 1 "memory_operand" "")))
5706 (clobber (reg:CC CC_REGNUM))]
5707 "reload_completed
5708 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5709 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
5710 [(parallel
5711 [(set (match_dup 0) (and:BLK (match_dup 0) (match_dup 1)))
5712 (use (match_dup 2))
5713 (clobber (reg:CC CC_REGNUM))])]
5714 {
5715 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
5716 operands[0] = adjust_address (operands[0], BLKmode, 0);
5717 operands[1] = adjust_address (operands[1], BLKmode, 0);
5718 })
5719
5720 (define_peephole2
5721 [(parallel
5722 [(set (match_operand:BLK 0 "memory_operand" "")
5723 (and:BLK (match_dup 0)
5724 (match_operand:BLK 1 "memory_operand" "")))
5725 (use (match_operand 2 "const_int_operand" ""))
5726 (clobber (reg:CC CC_REGNUM))])
5727 (parallel
5728 [(set (match_operand:BLK 3 "memory_operand" "")
5729 (and:BLK (match_dup 3)
5730 (match_operand:BLK 4 "memory_operand" "")))
5731 (use (match_operand 5 "const_int_operand" ""))
5732 (clobber (reg:CC CC_REGNUM))])]
5733 "s390_offset_p (operands[0], operands[3], operands[2])
5734 && s390_offset_p (operands[1], operands[4], operands[2])
5735 && !s390_overlap_p (operands[0], operands[1],
5736 INTVAL (operands[2]) + INTVAL (operands[5]))
5737 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
5738 [(parallel
5739 [(set (match_dup 6) (and:BLK (match_dup 6) (match_dup 7)))
5740 (use (match_dup 8))
5741 (clobber (reg:CC CC_REGNUM))])]
5742 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
5743 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
5744 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
5745
5746
5747 ;;
5748 ;;- Bit set (inclusive or) instructions.
5749 ;;
5750
5751 (define_expand "ior<mode>3"
5752 [(set (match_operand:INT 0 "nonimmediate_operand" "")
5753 (ior:INT (match_operand:INT 1 "nonimmediate_operand" "")
5754 (match_operand:INT 2 "general_operand" "")))
5755 (clobber (reg:CC CC_REGNUM))]
5756 ""
5757 "s390_expand_logical_operator (IOR, <MODE>mode, operands); DONE;")
5758
5759 ;
5760 ; iordi3 instruction pattern(s).
5761 ;
5762
5763 (define_insn "*iordi3_cc"
5764 [(set (reg CC_REGNUM)
5765 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5766 (match_operand:DI 2 "general_operand" "d,RT"))
5767 (const_int 0)))
5768 (set (match_operand:DI 0 "register_operand" "=d,d")
5769 (ior:DI (match_dup 1) (match_dup 2)))]
5770 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT"
5771 "@
5772 ogr\t%0,%2
5773 og\t%0,%2"
5774 [(set_attr "op_type" "RRE,RXY")])
5775
5776 (define_insn "*iordi3_cconly"
5777 [(set (reg CC_REGNUM)
5778 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5779 (match_operand:DI 2 "general_operand" "d,RT"))
5780 (const_int 0)))
5781 (clobber (match_scratch:DI 0 "=d,d"))]
5782 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT"
5783 "@
5784 ogr\t%0,%2
5785 og\t%0,%2"
5786 [(set_attr "op_type" "RRE,RXY")])
5787
5788 (define_insn "*iordi3"
5789 [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,d,d,d,d,d,AQ,Q")
5790 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0,0,0,0,0,0,0")
5791 (match_operand:DI 2 "general_operand"
5792 "N0HD0,N1HD0,N2HD0,N3HD0,N0SD0,N1SD0,d,RT,NxQD0,Q")))
5793 (clobber (reg:CC CC_REGNUM))]
5794 "TARGET_64BIT && s390_logical_operator_ok_p (operands)"
5795 "@
5796 oihh\t%0,%i2
5797 oihl\t%0,%i2
5798 oilh\t%0,%i2
5799 oill\t%0,%i2
5800 oihf\t%0,%k2
5801 oilf\t%0,%k2
5802 ogr\t%0,%2
5803 og\t%0,%2
5804 #
5805 #"
5806 [(set_attr "op_type" "RI,RI,RI,RI,RIL,RIL,RRE,RXY,SI,SS")
5807 (set_attr "cpu_facility" "*,*,*,*,extimm,extimm,*,*,*,*")])
5808
5809 (define_split
5810 [(set (match_operand:DI 0 "s_operand" "")
5811 (ior:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
5812 (clobber (reg:CC CC_REGNUM))]
5813 "reload_completed"
5814 [(parallel
5815 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
5816 (clobber (reg:CC CC_REGNUM))])]
5817 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
5818
5819 ;
5820 ; iorsi3 instruction pattern(s).
5821 ;
5822
5823 (define_insn "*iorsi3_cc"
5824 [(set (reg CC_REGNUM)
5825 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5826 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
5827 (const_int 0)))
5828 (set (match_operand:SI 0 "register_operand" "=d,d,d,d")
5829 (ior:SI (match_dup 1) (match_dup 2)))]
5830 "s390_match_ccmode(insn, CCTmode)"
5831 "@
5832 oilf\t%0,%o2
5833 or\t%0,%2
5834 o\t%0,%2
5835 oy\t%0,%2"
5836 [(set_attr "op_type" "RIL,RR,RX,RXY")])
5837
5838 (define_insn "*iorsi3_cconly"
5839 [(set (reg CC_REGNUM)
5840 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5841 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
5842 (const_int 0)))
5843 (clobber (match_scratch:SI 0 "=d,d,d,d"))]
5844 "s390_match_ccmode(insn, CCTmode)"
5845 "@
5846 oilf\t%0,%o2
5847 or\t%0,%2
5848 o\t%0,%2
5849 oy\t%0,%2"
5850 [(set_attr "op_type" "RIL,RR,RX,RXY")])
5851
5852 (define_insn "*iorsi3_zarch"
5853 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d,d,AQ,Q")
5854 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0,0,0,0")
5855 (match_operand:SI 2 "general_operand" "N0HS0,N1HS0,Os,d,R,T,NxQS0,Q")))
5856 (clobber (reg:CC CC_REGNUM))]
5857 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5858 "@
5859 oilh\t%0,%i2
5860 oill\t%0,%i2
5861 oilf\t%0,%o2
5862 or\t%0,%2
5863 o\t%0,%2
5864 oy\t%0,%2
5865 #
5866 #"
5867 [(set_attr "op_type" "RI,RI,RIL,RR,RX,RXY,SI,SS")])
5868
5869 (define_insn "*iorsi3_esa"
5870 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,AQ,Q")
5871 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
5872 (match_operand:SI 2 "general_operand" "d,R,NxQS0,Q")))
5873 (clobber (reg:CC CC_REGNUM))]
5874 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5875 "@
5876 or\t%0,%2
5877 o\t%0,%2
5878 #
5879 #"
5880 [(set_attr "op_type" "RR,RX,SI,SS")])
5881
5882 (define_split
5883 [(set (match_operand:SI 0 "s_operand" "")
5884 (ior:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
5885 (clobber (reg:CC CC_REGNUM))]
5886 "reload_completed"
5887 [(parallel
5888 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
5889 (clobber (reg:CC CC_REGNUM))])]
5890 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
5891
5892 ;
5893 ; iorhi3 instruction pattern(s).
5894 ;
5895
5896 (define_insn "*iorhi3_zarch"
5897 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,AQ,Q")
5898 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0,0")
5899 (match_operand:HI 2 "general_operand" "d,n,NxQH0,Q")))
5900 (clobber (reg:CC CC_REGNUM))]
5901 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5902 "@
5903 or\t%0,%2
5904 oill\t%0,%x2
5905 #
5906 #"
5907 [(set_attr "op_type" "RR,RI,SI,SS")])
5908
5909 (define_insn "*iorhi3_esa"
5910 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,AQ,Q")
5911 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0")
5912 (match_operand:HI 2 "general_operand" "d,NxQH0,Q")))
5913 (clobber (reg:CC CC_REGNUM))]
5914 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5915 "@
5916 or\t%0,%2
5917 #
5918 #"
5919 [(set_attr "op_type" "RR,SI,SS")])
5920
5921 (define_split
5922 [(set (match_operand:HI 0 "s_operand" "")
5923 (ior:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
5924 (clobber (reg:CC CC_REGNUM))]
5925 "reload_completed"
5926 [(parallel
5927 [(set (match_dup 0) (ior:QI (match_dup 0) (match_dup 1)))
5928 (clobber (reg:CC CC_REGNUM))])]
5929 "s390_narrow_logical_operator (IOR, &operands[0], &operands[1]);")
5930
5931 ;
5932 ; iorqi3 instruction pattern(s).
5933 ;
5934
5935 (define_insn "*iorqi3_zarch"
5936 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,Q,S,Q")
5937 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,0,0")
5938 (match_operand:QI 2 "general_operand" "d,n,n,n,Q")))
5939 (clobber (reg:CC CC_REGNUM))]
5940 "TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5941 "@
5942 or\t%0,%2
5943 oill\t%0,%b2
5944 oi\t%S0,%b2
5945 oiy\t%S0,%b2
5946 #"
5947 [(set_attr "op_type" "RR,RI,SI,SIY,SS")])
5948
5949 (define_insn "*iorqi3_esa"
5950 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,Q,Q")
5951 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
5952 (match_operand:QI 2 "general_operand" "d,n,Q")))
5953 (clobber (reg:CC CC_REGNUM))]
5954 "!TARGET_ZARCH && s390_logical_operator_ok_p (operands)"
5955 "@
5956 or\t%0,%2
5957 oi\t%S0,%b2
5958 #"
5959 [(set_attr "op_type" "RR,SI,SS")])
5960
5961 ;
5962 ; Block inclusive or (OC) patterns.
5963 ;
5964
5965 (define_insn "*oc"
5966 [(set (match_operand:BLK 0 "memory_operand" "=Q")
5967 (ior:BLK (match_dup 0)
5968 (match_operand:BLK 1 "memory_operand" "Q")))
5969 (use (match_operand 2 "const_int_operand" "n"))
5970 (clobber (reg:CC CC_REGNUM))]
5971 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
5972 "oc\t%O0(%2,%R0),%S1"
5973 [(set_attr "op_type" "SS")])
5974
5975 (define_split
5976 [(set (match_operand 0 "memory_operand" "")
5977 (ior (match_dup 0)
5978 (match_operand 1 "memory_operand" "")))
5979 (clobber (reg:CC CC_REGNUM))]
5980 "reload_completed
5981 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5982 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
5983 [(parallel
5984 [(set (match_dup 0) (ior:BLK (match_dup 0) (match_dup 1)))
5985 (use (match_dup 2))
5986 (clobber (reg:CC CC_REGNUM))])]
5987 {
5988 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
5989 operands[0] = adjust_address (operands[0], BLKmode, 0);
5990 operands[1] = adjust_address (operands[1], BLKmode, 0);
5991 })
5992
5993 (define_peephole2
5994 [(parallel
5995 [(set (match_operand:BLK 0 "memory_operand" "")
5996 (ior:BLK (match_dup 0)
5997 (match_operand:BLK 1 "memory_operand" "")))
5998 (use (match_operand 2 "const_int_operand" ""))
5999 (clobber (reg:CC CC_REGNUM))])
6000 (parallel
6001 [(set (match_operand:BLK 3 "memory_operand" "")
6002 (ior:BLK (match_dup 3)
6003 (match_operand:BLK 4 "memory_operand" "")))
6004 (use (match_operand 5 "const_int_operand" ""))
6005 (clobber (reg:CC CC_REGNUM))])]
6006 "s390_offset_p (operands[0], operands[3], operands[2])
6007 && s390_offset_p (operands[1], operands[4], operands[2])
6008 && !s390_overlap_p (operands[0], operands[1],
6009 INTVAL (operands[2]) + INTVAL (operands[5]))
6010 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
6011 [(parallel
6012 [(set (match_dup 6) (ior:BLK (match_dup 6) (match_dup 7)))
6013 (use (match_dup 8))
6014 (clobber (reg:CC CC_REGNUM))])]
6015 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
6016 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
6017 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
6018
6019
6020 ;;
6021 ;;- Xor instructions.
6022 ;;
6023
6024 (define_expand "xor<mode>3"
6025 [(set (match_operand:INT 0 "nonimmediate_operand" "")
6026 (xor:INT (match_operand:INT 1 "nonimmediate_operand" "")
6027 (match_operand:INT 2 "general_operand" "")))
6028 (clobber (reg:CC CC_REGNUM))]
6029 ""
6030 "s390_expand_logical_operator (XOR, <MODE>mode, operands); DONE;")
6031
6032 ;
6033 ; xordi3 instruction pattern(s).
6034 ;
6035
6036 (define_insn "*xordi3_cc"
6037 [(set (reg CC_REGNUM)
6038 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
6039 (match_operand:DI 2 "general_operand" "d,RT"))
6040 (const_int 0)))
6041 (set (match_operand:DI 0 "register_operand" "=d,d")
6042 (xor:DI (match_dup 1) (match_dup 2)))]
6043 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT"
6044 "@
6045 xgr\t%0,%2
6046 xg\t%0,%2"
6047 [(set_attr "op_type" "RRE,RXY")])
6048
6049 (define_insn "*xordi3_cconly"
6050 [(set (reg CC_REGNUM)
6051 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
6052 (match_operand:DI 2 "general_operand" "d,RT"))
6053 (const_int 0)))
6054 (clobber (match_scratch:DI 0 "=d,d"))]
6055 "s390_match_ccmode(insn, CCTmode) && TARGET_64BIT"
6056 "@
6057 xgr\t%0,%2
6058 xg\t%0,%2"
6059 [(set_attr "op_type" "RRE,RXY")])
6060
6061 (define_insn "*xordi3"
6062 [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,d,AQ,Q")
6063 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,0,0,0")
6064 (match_operand:DI 2 "general_operand" "N0SD0,N1SD0,d,RT,NxQD0,Q")))
6065 (clobber (reg:CC CC_REGNUM))]
6066 "TARGET_64BIT && s390_logical_operator_ok_p (operands)"
6067 "@
6068 xihf\t%0,%k2
6069 xilf\t%0,%k2
6070 xgr\t%0,%2
6071 xg\t%0,%2
6072 #
6073 #"
6074 [(set_attr "op_type" "RIL,RIL,RRE,RXY,SI,SS")
6075 (set_attr "cpu_facility" "extimm,extimm,*,*,*,*")])
6076
6077 (define_split
6078 [(set (match_operand:DI 0 "s_operand" "")
6079 (xor:DI (match_dup 0) (match_operand:DI 1 "immediate_operand" "")))
6080 (clobber (reg:CC CC_REGNUM))]
6081 "reload_completed"
6082 [(parallel
6083 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
6084 (clobber (reg:CC CC_REGNUM))])]
6085 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
6086
6087 ;
6088 ; xorsi3 instruction pattern(s).
6089 ;
6090
6091 (define_insn "*xorsi3_cc"
6092 [(set (reg CC_REGNUM)
6093 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
6094 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
6095 (const_int 0)))
6096 (set (match_operand:SI 0 "register_operand" "=d,d,d,d")
6097 (xor:SI (match_dup 1) (match_dup 2)))]
6098 "s390_match_ccmode(insn, CCTmode)"
6099 "@
6100 xilf\t%0,%o2
6101 xr\t%0,%2
6102 x\t%0,%2
6103 xy\t%0,%2"
6104 [(set_attr "op_type" "RIL,RR,RX,RXY")])
6105
6106 (define_insn "*xorsi3_cconly"
6107 [(set (reg CC_REGNUM)
6108 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0")
6109 (match_operand:SI 2 "general_operand" "Os,d,R,T"))
6110 (const_int 0)))
6111 (clobber (match_scratch:SI 0 "=d,d,d,d"))]
6112 "s390_match_ccmode(insn, CCTmode)"
6113 "@
6114 xilf\t%0,%o2
6115 xr\t%0,%2
6116 x\t%0,%2
6117 xy\t%0,%2"
6118 [(set_attr "op_type" "RIL,RR,RX,RXY")])
6119
6120 (define_insn "*xorsi3"
6121 [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,AQ,Q")
6122 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,0,0,0,0")
6123 (match_operand:SI 2 "general_operand" "Os,d,R,T,NxQS0,Q")))
6124 (clobber (reg:CC CC_REGNUM))]
6125 "s390_logical_operator_ok_p (operands)"
6126 "@
6127 xilf\t%0,%o2
6128 xr\t%0,%2
6129 x\t%0,%2
6130 xy\t%0,%2
6131 #
6132 #"
6133 [(set_attr "op_type" "RIL,RR,RX,RXY,SI,SS")])
6134
6135 (define_split
6136 [(set (match_operand:SI 0 "s_operand" "")
6137 (xor:SI (match_dup 0) (match_operand:SI 1 "immediate_operand" "")))
6138 (clobber (reg:CC CC_REGNUM))]
6139 "reload_completed"
6140 [(parallel
6141 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
6142 (clobber (reg:CC CC_REGNUM))])]
6143 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
6144
6145 ;
6146 ; xorhi3 instruction pattern(s).
6147 ;
6148
6149 (define_insn "*xorhi3"
6150 [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,AQ,Q")
6151 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,0,0")
6152 (match_operand:HI 2 "general_operand" "Os,d,NxQH0,Q")))
6153 (clobber (reg:CC CC_REGNUM))]
6154 "s390_logical_operator_ok_p (operands)"
6155 "@
6156 xilf\t%0,%x2
6157 xr\t%0,%2
6158 #
6159 #"
6160 [(set_attr "op_type" "RIL,RR,SI,SS")])
6161
6162 (define_split
6163 [(set (match_operand:HI 0 "s_operand" "")
6164 (xor:HI (match_dup 0) (match_operand:HI 1 "immediate_operand" "")))
6165 (clobber (reg:CC CC_REGNUM))]
6166 "reload_completed"
6167 [(parallel
6168 [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
6169 (clobber (reg:CC CC_REGNUM))])]
6170 "s390_narrow_logical_operator (XOR, &operands[0], &operands[1]);")
6171
6172 ;
6173 ; xorqi3 instruction pattern(s).
6174 ;
6175
6176 (define_insn "*xorqi3"
6177 [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,Q,S,Q")
6178 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,0,0")
6179 (match_operand:QI 2 "general_operand" "Os,d,n,n,Q")))
6180 (clobber (reg:CC CC_REGNUM))]
6181 "s390_logical_operator_ok_p (operands)"
6182 "@
6183 xilf\t%0,%b2
6184 xr\t%0,%2
6185 xi\t%S0,%b2
6186 xiy\t%S0,%b2
6187 #"
6188 [(set_attr "op_type" "RIL,RR,SI,SIY,SS")])
6189
6190 ;
6191 ; Block exclusive or (XC) patterns.
6192 ;
6193
6194 (define_insn "*xc"
6195 [(set (match_operand:BLK 0 "memory_operand" "=Q")
6196 (xor:BLK (match_dup 0)
6197 (match_operand:BLK 1 "memory_operand" "Q")))
6198 (use (match_operand 2 "const_int_operand" "n"))
6199 (clobber (reg:CC CC_REGNUM))]
6200 "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 256"
6201 "xc\t%O0(%2,%R0),%S1"
6202 [(set_attr "op_type" "SS")])
6203
6204 (define_split
6205 [(set (match_operand 0 "memory_operand" "")
6206 (xor (match_dup 0)
6207 (match_operand 1 "memory_operand" "")))
6208 (clobber (reg:CC CC_REGNUM))]
6209 "reload_completed
6210 && GET_MODE (operands[0]) == GET_MODE (operands[1])
6211 && GET_MODE_SIZE (GET_MODE (operands[0])) > 0"
6212 [(parallel
6213 [(set (match_dup 0) (xor:BLK (match_dup 0) (match_dup 1)))
6214 (use (match_dup 2))
6215 (clobber (reg:CC CC_REGNUM))])]
6216 {
6217 operands[2] = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[0])));
6218 operands[0] = adjust_address (operands[0], BLKmode, 0);
6219 operands[1] = adjust_address (operands[1], BLKmode, 0);
6220 })
6221
6222 (define_peephole2
6223 [(parallel
6224 [(set (match_operand:BLK 0 "memory_operand" "")
6225 (xor:BLK (match_dup 0)
6226 (match_operand:BLK 1 "memory_operand" "")))
6227 (use (match_operand 2 "const_int_operand" ""))
6228 (clobber (reg:CC CC_REGNUM))])
6229 (parallel
6230 [(set (match_operand:BLK 3 "memory_operand" "")
6231 (xor:BLK (match_dup 3)
6232 (match_operand:BLK 4 "memory_operand" "")))
6233 (use (match_operand 5 "const_int_operand" ""))
6234 (clobber (reg:CC CC_REGNUM))])]
6235 "s390_offset_p (operands[0], operands[3], operands[2])
6236 && s390_offset_p (operands[1], operands[4], operands[2])
6237 && !s390_overlap_p (operands[0], operands[1],
6238 INTVAL (operands[2]) + INTVAL (operands[5]))
6239 && INTVAL (operands[2]) + INTVAL (operands[5]) <= 256"
6240 [(parallel
6241 [(set (match_dup 6) (xor:BLK (match_dup 6) (match_dup 7)))
6242 (use (match_dup 8))
6243 (clobber (reg:CC CC_REGNUM))])]
6244 "operands[6] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
6245 operands[7] = gen_rtx_MEM (BLKmode, XEXP (operands[1], 0));
6246 operands[8] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[5]));")
6247
6248 ;
6249 ; Block xor (XC) patterns with src == dest.
6250 ;
6251
6252 (define_insn "*xc_zero"
6253 [(set (match_operand:BLK 0 "memory_operand" "=Q")
6254 (const_int 0))
6255 (use (match_operand 1 "const_int_operand" "n"))
6256 (clobber (reg:CC CC_REGNUM))]
6257 "INTVAL (operands[1]) >= 1 && INTVAL (operands[1]) <= 256"
6258 "xc\t%O0(%1,%R0),%S0"
6259 [(set_attr "op_type" "SS")])
6260
6261 (define_peephole2
6262 [(parallel
6263 [(set (match_operand:BLK 0 "memory_operand" "")
6264 (const_int 0))
6265 (use (match_operand 1 "const_int_operand" ""))
6266 (clobber (reg:CC CC_REGNUM))])
6267 (parallel
6268 [(set (match_operand:BLK 2 "memory_operand" "")
6269 (const_int 0))
6270 (use (match_operand 3 "const_int_operand" ""))
6271 (clobber (reg:CC CC_REGNUM))])]
6272 "s390_offset_p (operands[0], operands[2], operands[1])
6273 && INTVAL (operands[1]) + INTVAL (operands[3]) <= 256"
6274 [(parallel
6275 [(set (match_dup 4) (const_int 0))
6276 (use (match_dup 5))
6277 (clobber (reg:CC CC_REGNUM))])]
6278 "operands[4] = gen_rtx_MEM (BLKmode, XEXP (operands[0], 0));
6279 operands[5] = GEN_INT (INTVAL (operands[1]) + INTVAL (operands[3]));")
6280
6281
6282 ;;
6283 ;;- Negate instructions.
6284 ;;
6285
6286 ;
6287 ; neg(di|si)2 instruction pattern(s).
6288 ;
6289
6290 (define_expand "neg<mode>2"
6291 [(parallel
6292 [(set (match_operand:DSI 0 "register_operand" "=d")
6293 (neg:DSI (match_operand:DSI 1 "register_operand" "d")))
6294 (clobber (reg:CC CC_REGNUM))])]
6295 ""
6296 "")
6297
6298 (define_insn "*negdi2_sign_cc"
6299 [(set (reg CC_REGNUM)
6300 (compare (neg:DI (ashiftrt:DI (ashift:DI (subreg:DI
6301 (match_operand:SI 1 "register_operand" "d") 0)
6302 (const_int 32)) (const_int 32)))
6303 (const_int 0)))
6304 (set (match_operand:DI 0 "register_operand" "=d")
6305 (neg:DI (sign_extend:DI (match_dup 1))))]
6306 "TARGET_64BIT && s390_match_ccmode (insn, CCAmode)"
6307 "lcgfr\t%0,%1"
6308 [(set_attr "op_type" "RRE")])
6309
6310 (define_insn "*negdi2_sign"
6311 [(set (match_operand:DI 0 "register_operand" "=d")
6312 (neg:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
6313 (clobber (reg:CC CC_REGNUM))]
6314 "TARGET_64BIT"
6315 "lcgfr\t%0,%1"
6316 [(set_attr "op_type" "RRE")])
6317
6318 ; lcr, lcgr
6319 (define_insn "*neg<mode>2_cc"
6320 [(set (reg CC_REGNUM)
6321 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
6322 (const_int 0)))
6323 (set (match_operand:GPR 0 "register_operand" "=d")
6324 (neg:GPR (match_dup 1)))]
6325 "s390_match_ccmode (insn, CCAmode)"
6326 "lc<g>r\t%0,%1"
6327 [(set_attr "op_type" "RR<E>")])
6328
6329 ; lcr, lcgr
6330 (define_insn "*neg<mode>2_cconly"
6331 [(set (reg CC_REGNUM)
6332 (compare (neg:GPR (match_operand:GPR 1 "register_operand" "d"))
6333 (const_int 0)))
6334 (clobber (match_scratch:GPR 0 "=d"))]
6335 "s390_match_ccmode (insn, CCAmode)"
6336 "lc<g>r\t%0,%1"
6337 [(set_attr "op_type" "RR<E>")])
6338
6339 ; lcr, lcgr
6340 (define_insn "*neg<mode>2"
6341 [(set (match_operand:GPR 0 "register_operand" "=d")
6342 (neg:GPR (match_operand:GPR 1 "register_operand" "d")))
6343 (clobber (reg:CC CC_REGNUM))]
6344 ""
6345 "lc<g>r\t%0,%1"
6346 [(set_attr "op_type" "RR<E>")])
6347
6348 (define_insn_and_split "*negdi2_31"
6349 [(set (match_operand:DI 0 "register_operand" "=d")
6350 (neg:DI (match_operand:DI 1 "register_operand" "d")))
6351 (clobber (reg:CC CC_REGNUM))]
6352 "!TARGET_64BIT"
6353 "#"
6354 "&& reload_completed"
6355 [(parallel
6356 [(set (match_dup 2) (neg:SI (match_dup 3)))
6357 (clobber (reg:CC CC_REGNUM))])
6358 (parallel
6359 [(set (reg:CCAP CC_REGNUM)
6360 (compare:CCAP (neg:SI (match_dup 5)) (const_int 0)))
6361 (set (match_dup 4) (neg:SI (match_dup 5)))])
6362 (set (pc)
6363 (if_then_else (ne (reg:CCAP CC_REGNUM) (const_int 0))
6364 (pc)
6365 (label_ref (match_dup 6))))
6366 (parallel
6367 [(set (match_dup 2) (plus:SI (match_dup 2) (const_int -1)))
6368 (clobber (reg:CC CC_REGNUM))])
6369 (match_dup 6)]
6370 "operands[2] = operand_subword (operands[0], 0, 0, DImode);
6371 operands[3] = operand_subword (operands[1], 0, 0, DImode);
6372 operands[4] = operand_subword (operands[0], 1, 0, DImode);
6373 operands[5] = operand_subword (operands[1], 1, 0, DImode);
6374 operands[6] = gen_label_rtx ();")
6375
6376 ;
6377 ; neg(df|sf)2 instruction pattern(s).
6378 ;
6379
6380 (define_expand "neg<mode>2"
6381 [(parallel
6382 [(set (match_operand:BFP 0 "register_operand" "=f")
6383 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
6384 (clobber (reg:CC CC_REGNUM))])]
6385 "TARGET_HARD_FLOAT"
6386 "")
6387
6388 ; lcxbr, lcdbr, lcebr
6389 (define_insn "*neg<mode>2_cc"
6390 [(set (reg CC_REGNUM)
6391 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
6392 (match_operand:BFP 2 "const0_operand" "")))
6393 (set (match_operand:BFP 0 "register_operand" "=f")
6394 (neg:BFP (match_dup 1)))]
6395 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6396 "lc<xde>br\t%0,%1"
6397 [(set_attr "op_type" "RRE")
6398 (set_attr "type" "fsimp<mode>")])
6399
6400 ; lcxbr, lcdbr, lcebr
6401 (define_insn "*neg<mode>2_cconly"
6402 [(set (reg CC_REGNUM)
6403 (compare (neg:BFP (match_operand:BFP 1 "register_operand" "f"))
6404 (match_operand:BFP 2 "const0_operand" "")))
6405 (clobber (match_scratch:BFP 0 "=f"))]
6406 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6407 "lc<xde>br\t%0,%1"
6408 [(set_attr "op_type" "RRE")
6409 (set_attr "type" "fsimp<mode>")])
6410
6411 ; lcdfr
6412 (define_insn "*neg<mode>2_nocc"
6413 [(set (match_operand:FP 0 "register_operand" "=f")
6414 (neg:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
6415 "TARGET_HARD_FLOAT && TARGET_DFP"
6416 "lcdfr\t%0,%1"
6417 [(set_attr "op_type" "RRE")
6418 (set_attr "type" "fsimp<bfp>")])
6419
6420 ; lcxbr, lcdbr, lcebr
6421 (define_insn "*neg<mode>2"
6422 [(set (match_operand:BFP 0 "register_operand" "=f")
6423 (neg:BFP (match_operand:BFP 1 "register_operand" "f")))
6424 (clobber (reg:CC CC_REGNUM))]
6425 "TARGET_HARD_FLOAT"
6426 "lc<xde>br\t%0,%1"
6427 [(set_attr "op_type" "RRE")
6428 (set_attr "type" "fsimp<mode>")])
6429
6430
6431 ;;
6432 ;;- Absolute value instructions.
6433 ;;
6434
6435 ;
6436 ; abs(di|si)2 instruction pattern(s).
6437 ;
6438
6439 (define_insn "*absdi2_sign_cc"
6440 [(set (reg CC_REGNUM)
6441 (compare (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
6442 (match_operand:SI 1 "register_operand" "d") 0)
6443 (const_int 32)) (const_int 32)))
6444 (const_int 0)))
6445 (set (match_operand:DI 0 "register_operand" "=d")
6446 (abs:DI (sign_extend:DI (match_dup 1))))]
6447 "TARGET_64BIT && s390_match_ccmode (insn, CCAmode)"
6448 "lpgfr\t%0,%1"
6449 [(set_attr "op_type" "RRE")])
6450
6451 (define_insn "*absdi2_sign"
6452 [(set (match_operand:DI 0 "register_operand" "=d")
6453 (abs:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))))
6454 (clobber (reg:CC CC_REGNUM))]
6455 "TARGET_64BIT"
6456 "lpgfr\t%0,%1"
6457 [(set_attr "op_type" "RRE")])
6458
6459 ; lpr, lpgr
6460 (define_insn "*abs<mode>2_cc"
6461 [(set (reg CC_REGNUM)
6462 (compare (abs:GPR (match_operand:DI 1 "register_operand" "d"))
6463 (const_int 0)))
6464 (set (match_operand:GPR 0 "register_operand" "=d")
6465 (abs:GPR (match_dup 1)))]
6466 "s390_match_ccmode (insn, CCAmode)"
6467 "lp<g>r\t%0,%1"
6468 [(set_attr "op_type" "RR<E>")])
6469
6470 ; lpr, lpgr
6471 (define_insn "*abs<mode>2_cconly"
6472 [(set (reg CC_REGNUM)
6473 (compare (abs:GPR (match_operand:GPR 1 "register_operand" "d"))
6474 (const_int 0)))
6475 (clobber (match_scratch:GPR 0 "=d"))]
6476 "s390_match_ccmode (insn, CCAmode)"
6477 "lp<g>r\t%0,%1"
6478 [(set_attr "op_type" "RR<E>")])
6479
6480 ; lpr, lpgr
6481 (define_insn "abs<mode>2"
6482 [(set (match_operand:GPR 0 "register_operand" "=d")
6483 (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
6484 (clobber (reg:CC CC_REGNUM))]
6485 ""
6486 "lp<g>r\t%0,%1"
6487 [(set_attr "op_type" "RR<E>")])
6488
6489 ;
6490 ; abs(df|sf)2 instruction pattern(s).
6491 ;
6492
6493 (define_expand "abs<mode>2"
6494 [(parallel
6495 [(set (match_operand:BFP 0 "register_operand" "=f")
6496 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
6497 (clobber (reg:CC CC_REGNUM))])]
6498 "TARGET_HARD_FLOAT"
6499 "")
6500
6501 ; lpxbr, lpdbr, lpebr
6502 (define_insn "*abs<mode>2_cc"
6503 [(set (reg CC_REGNUM)
6504 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
6505 (match_operand:BFP 2 "const0_operand" "")))
6506 (set (match_operand:BFP 0 "register_operand" "=f")
6507 (abs:BFP (match_dup 1)))]
6508 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6509 "lp<xde>br\t%0,%1"
6510 [(set_attr "op_type" "RRE")
6511 (set_attr "type" "fsimp<mode>")])
6512
6513 ; lpxbr, lpdbr, lpebr
6514 (define_insn "*abs<mode>2_cconly"
6515 [(set (reg CC_REGNUM)
6516 (compare (abs:BFP (match_operand:BFP 1 "register_operand" "f"))
6517 (match_operand:BFP 2 "const0_operand" "")))
6518 (clobber (match_scratch:BFP 0 "=f"))]
6519 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6520 "lp<xde>br\t%0,%1"
6521 [(set_attr "op_type" "RRE")
6522 (set_attr "type" "fsimp<mode>")])
6523
6524 ; lpdfr
6525 (define_insn "*abs<mode>2_nocc"
6526 [(set (match_operand:FP 0 "register_operand" "=f")
6527 (abs:FP (match_operand:FP 1 "register_operand" "<fT0>")))]
6528 "TARGET_HARD_FLOAT && TARGET_DFP"
6529 "lpdfr\t%0,%1"
6530 [(set_attr "op_type" "RRE")
6531 (set_attr "type" "fsimp<bfp>")])
6532
6533 ; lpxbr, lpdbr, lpebr
6534 (define_insn "*abs<mode>2"
6535 [(set (match_operand:BFP 0 "register_operand" "=f")
6536 (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
6537 (clobber (reg:CC CC_REGNUM))]
6538 "TARGET_HARD_FLOAT"
6539 "lp<xde>br\t%0,%1"
6540 [(set_attr "op_type" "RRE")
6541 (set_attr "type" "fsimp<mode>")])
6542
6543
6544 ;;
6545 ;;- Negated absolute value instructions
6546 ;;
6547
6548 ;
6549 ; Integer
6550 ;
6551
6552 (define_insn "*negabsdi2_sign_cc"
6553 [(set (reg CC_REGNUM)
6554 (compare (neg:DI (abs:DI (ashiftrt:DI (ashift:DI (subreg:DI
6555 (match_operand:SI 1 "register_operand" "d") 0)
6556 (const_int 32)) (const_int 32))))
6557 (const_int 0)))
6558 (set (match_operand:DI 0 "register_operand" "=d")
6559 (neg:DI (abs:DI (sign_extend:DI (match_dup 1)))))]
6560 "TARGET_64BIT && s390_match_ccmode (insn, CCAmode)"
6561 "lngfr\t%0,%1"
6562 [(set_attr "op_type" "RRE")])
6563
6564 (define_insn "*negabsdi2_sign"
6565 [(set (match_operand:DI 0 "register_operand" "=d")
6566 (neg:DI (abs:DI (sign_extend:DI
6567 (match_operand:SI 1 "register_operand" "d")))))
6568 (clobber (reg:CC CC_REGNUM))]
6569 "TARGET_64BIT"
6570 "lngfr\t%0,%1"
6571 [(set_attr "op_type" "RRE")])
6572
6573 ; lnr, lngr
6574 (define_insn "*negabs<mode>2_cc"
6575 [(set (reg CC_REGNUM)
6576 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
6577 (const_int 0)))
6578 (set (match_operand:GPR 0 "register_operand" "=d")
6579 (neg:GPR (abs:GPR (match_dup 1))))]
6580 "s390_match_ccmode (insn, CCAmode)"
6581 "ln<g>r\t%0,%1"
6582 [(set_attr "op_type" "RR<E>")])
6583
6584 ; lnr, lngr
6585 (define_insn "*negabs<mode>2_cconly"
6586 [(set (reg CC_REGNUM)
6587 (compare (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d")))
6588 (const_int 0)))
6589 (clobber (match_scratch:GPR 0 "=d"))]
6590 "s390_match_ccmode (insn, CCAmode)"
6591 "ln<g>r\t%0,%1"
6592 [(set_attr "op_type" "RR<E>")])
6593
6594 ; lnr, lngr
6595 (define_insn "*negabs<mode>2"
6596 [(set (match_operand:GPR 0 "register_operand" "=d")
6597 (neg:GPR (abs:GPR (match_operand:GPR 1 "register_operand" "d"))))
6598 (clobber (reg:CC CC_REGNUM))]
6599 ""
6600 "ln<g>r\t%0,%1"
6601 [(set_attr "op_type" "RR<E>")])
6602
6603 ;
6604 ; Floating point
6605 ;
6606
6607 ; lnxbr, lndbr, lnebr
6608 (define_insn "*negabs<mode>2_cc"
6609 [(set (reg CC_REGNUM)
6610 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
6611 (match_operand:BFP 2 "const0_operand" "")))
6612 (set (match_operand:BFP 0 "register_operand" "=f")
6613 (neg:BFP (abs:BFP (match_dup 1))))]
6614 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6615 "ln<xde>br\t%0,%1"
6616 [(set_attr "op_type" "RRE")
6617 (set_attr "type" "fsimp<mode>")])
6618
6619 ; lnxbr, lndbr, lnebr
6620 (define_insn "*negabs<mode>2_cconly"
6621 [(set (reg CC_REGNUM)
6622 (compare (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f")))
6623 (match_operand:BFP 2 "const0_operand" "")))
6624 (clobber (match_scratch:BFP 0 "=f"))]
6625 "s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT"
6626 "ln<xde>br\t%0,%1"
6627 [(set_attr "op_type" "RRE")
6628 (set_attr "type" "fsimp<mode>")])
6629
6630 ; lndfr
6631 (define_insn "*negabs<mode>2_nocc"
6632 [(set (match_operand:FP 0 "register_operand" "=f")
6633 (neg:FP (abs:FP (match_operand:BFP 1 "register_operand" "<fT0>"))))]
6634 "TARGET_HARD_FLOAT && TARGET_DFP"
6635 "lndfr\t%0,%1"
6636 [(set_attr "op_type" "RRE")
6637 (set_attr "type" "fsimp<bfp>")])
6638
6639 ; lnxbr, lndbr, lnebr
6640 (define_insn "*negabs<mode>2"
6641 [(set (match_operand:BFP 0 "register_operand" "=f")
6642 (neg:BFP (abs:BFP (match_operand:BFP 1 "register_operand" "f"))))
6643 (clobber (reg:CC CC_REGNUM))]
6644 "TARGET_HARD_FLOAT"
6645 "ln<xde>br\t%0,%1"
6646 [(set_attr "op_type" "RRE")
6647 (set_attr "type" "fsimp<mode>")])
6648
6649 ;;
6650 ;;- Copy sign instructions
6651 ;;
6652
6653 ; cpsdr
6654 (define_insn "copysign<mode>3"
6655 [(set (match_operand:FP 0 "register_operand" "=f")
6656 (unspec:FP [(match_operand:FP 1 "register_operand" "<fT0>")
6657 (match_operand:FP 2 "register_operand" "f")]
6658 UNSPEC_COPYSIGN))]
6659 "TARGET_HARD_FLOAT && TARGET_DFP"
6660 "cpsdr\t%0,%2,%1"
6661 [(set_attr "op_type" "RRF")
6662 (set_attr "type" "fsimp<bfp>")])
6663
6664 ;;
6665 ;;- Square root instructions.
6666 ;;
6667
6668 ;
6669 ; sqrt(df|sf)2 instruction pattern(s).
6670 ;
6671
6672 ; sqxbr, sqdbr, sqebr, sqxb, sqdb, sqeb
6673 (define_insn "sqrt<mode>2"
6674 [(set (match_operand:BFP 0 "register_operand" "=f,f")
6675 (sqrt:BFP (match_operand:BFP 1 "general_operand" "f,<Rf>")))]
6676 "TARGET_HARD_FLOAT"
6677 "@
6678 sq<xde>br\t%0,%1
6679 sq<xde>b\t%0,%1"
6680 [(set_attr "op_type" "RRE,RXE")
6681 (set_attr "type" "fsqrt<mode>")])
6682
6683
6684 ;;
6685 ;;- One complement instructions.
6686 ;;
6687
6688 ;
6689 ; one_cmpl(di|si|hi|qi)2 instruction pattern(s).
6690 ;
6691
6692 (define_expand "one_cmpl<mode>2"
6693 [(parallel
6694 [(set (match_operand:INT 0 "register_operand" "")
6695 (xor:INT (match_operand:INT 1 "register_operand" "")
6696 (const_int -1)))
6697 (clobber (reg:CC CC_REGNUM))])]
6698 ""
6699 "")
6700
6701
6702 ;;
6703 ;; Find leftmost bit instructions.
6704 ;;
6705
6706 (define_expand "clzdi2"
6707 [(set (match_operand:DI 0 "register_operand" "=d")
6708 (clz:DI (match_operand:DI 1 "register_operand" "d")))]
6709 "TARGET_EXTIMM && TARGET_64BIT"
6710 {
6711 rtx insn, clz_equal;
6712 rtx wide_reg = gen_reg_rtx (TImode);
6713 rtx msb = gen_rtx_CONST_INT (DImode, (unsigned HOST_WIDE_INT) 1 << 63);
6714
6715 clz_equal = gen_rtx_CLZ (DImode, operands[1]);
6716
6717 emit_insn (gen_clztidi2 (wide_reg, operands[1], msb));
6718
6719 insn = emit_move_insn (operands[0], gen_highpart (DImode, wide_reg));
6720 set_unique_reg_note (insn, REG_EQUAL, clz_equal);
6721
6722 DONE;
6723 })
6724
6725 (define_insn "clztidi2"
6726 [(set (match_operand:TI 0 "register_operand" "=d")
6727 (ior:TI
6728 (ashift:TI
6729 (zero_extend:TI
6730 (xor:DI (match_operand:DI 1 "register_operand" "d")
6731 (lshiftrt (match_operand:DI 2 "const_int_operand" "")
6732 (subreg:SI (clz:DI (match_dup 1)) 4))))
6733
6734 (const_int 64))
6735 (zero_extend:TI (clz:DI (match_dup 1)))))
6736 (clobber (reg:CC CC_REGNUM))]
6737 "(unsigned HOST_WIDE_INT) INTVAL (operands[2])
6738 == (unsigned HOST_WIDE_INT) 1 << 63
6739 && TARGET_EXTIMM && TARGET_64BIT"
6740 "flogr\t%0,%1"
6741 [(set_attr "op_type" "RRE")])
6742
6743
6744 ;;
6745 ;;- Rotate instructions.
6746 ;;
6747
6748 ;
6749 ; rotl(di|si)3 instruction pattern(s).
6750 ;
6751
6752 ; rll, rllg
6753 (define_insn "rotl<mode>3"
6754 [(set (match_operand:GPR 0 "register_operand" "=d")
6755 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
6756 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
6757 "TARGET_CPU_ZARCH"
6758 "rll<g>\t%0,%1,%Y2"
6759 [(set_attr "op_type" "RSE")
6760 (set_attr "atype" "reg")])
6761
6762 ; rll, rllg
6763 (define_insn "*rotl<mode>3_and"
6764 [(set (match_operand:GPR 0 "register_operand" "=d")
6765 (rotate:GPR (match_operand:GPR 1 "register_operand" "d")
6766 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6767 (match_operand:SI 3 "const_int_operand" "n"))))]
6768 "TARGET_CPU_ZARCH && (INTVAL (operands[3]) & 63) == 63"
6769 "rll<g>\t%0,%1,%Y2"
6770 [(set_attr "op_type" "RSE")
6771 (set_attr "atype" "reg")])
6772
6773
6774 ;;
6775 ;;- Shift instructions.
6776 ;;
6777
6778 ;
6779 ; (ashl|lshr)(di|si)3 instruction pattern(s).
6780 ;
6781
6782 (define_expand "<shift><mode>3"
6783 [(set (match_operand:DSI 0 "register_operand" "")
6784 (SHIFT:DSI (match_operand:DSI 1 "register_operand" "")
6785 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))]
6786 ""
6787 "")
6788
6789 ; sldl, srdl
6790 (define_insn "*<shift>di3_31"
6791 [(set (match_operand:DI 0 "register_operand" "=d")
6792 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
6793 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
6794 "!TARGET_64BIT"
6795 "s<lr>dl\t%0,%Y2"
6796 [(set_attr "op_type" "RS")
6797 (set_attr "atype" "reg")])
6798
6799 ; sll, srl, sllg, srlg
6800 (define_insn "*<shift><mode>3"
6801 [(set (match_operand:GPR 0 "register_operand" "=d")
6802 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6803 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))]
6804 ""
6805 "s<lr>l<g>\t%0,<1>%Y2"
6806 [(set_attr "op_type" "RS<E>")
6807 (set_attr "atype" "reg")])
6808
6809 ; sldl, srdl
6810 (define_insn "*<shift>di3_31_and"
6811 [(set (match_operand:DI 0 "register_operand" "=d")
6812 (SHIFT:DI (match_operand:DI 1 "register_operand" "0")
6813 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6814 (match_operand:SI 3 "const_int_operand" "n"))))]
6815 "!TARGET_64BIT && (INTVAL (operands[3]) & 63) == 63"
6816 "s<lr>dl\t%0,%Y2"
6817 [(set_attr "op_type" "RS")
6818 (set_attr "atype" "reg")])
6819
6820 ; sll, srl, sllg, srlg
6821 (define_insn "*<shift><mode>3_and"
6822 [(set (match_operand:GPR 0 "register_operand" "=d")
6823 (SHIFT:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6824 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6825 (match_operand:SI 3 "const_int_operand" "n"))))]
6826 "(INTVAL (operands[3]) & 63) == 63"
6827 "s<lr>l<g>\t%0,<1>%Y2"
6828 [(set_attr "op_type" "RS<E>")
6829 (set_attr "atype" "reg")])
6830
6831 ;
6832 ; ashr(di|si)3 instruction pattern(s).
6833 ;
6834
6835 (define_expand "ashr<mode>3"
6836 [(parallel
6837 [(set (match_operand:DSI 0 "register_operand" "")
6838 (ashiftrt:DSI (match_operand:DSI 1 "register_operand" "")
6839 (match_operand:SI 2 "shift_count_or_setmem_operand" "")))
6840 (clobber (reg:CC CC_REGNUM))])]
6841 ""
6842 "")
6843
6844 (define_insn "*ashrdi3_cc_31"
6845 [(set (reg CC_REGNUM)
6846 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6847 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
6848 (const_int 0)))
6849 (set (match_operand:DI 0 "register_operand" "=d")
6850 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
6851 "!TARGET_64BIT && s390_match_ccmode(insn, CCSmode)"
6852 "srda\t%0,%Y2"
6853 [(set_attr "op_type" "RS")
6854 (set_attr "atype" "reg")])
6855
6856 (define_insn "*ashrdi3_cconly_31"
6857 [(set (reg CC_REGNUM)
6858 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6859 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
6860 (const_int 0)))
6861 (clobber (match_scratch:DI 0 "=d"))]
6862 "!TARGET_64BIT && s390_match_ccmode(insn, CCSmode)"
6863 "srda\t%0,%Y2"
6864 [(set_attr "op_type" "RS")
6865 (set_attr "atype" "reg")])
6866
6867 (define_insn "*ashrdi3_31"
6868 [(set (match_operand:DI 0 "register_operand" "=d")
6869 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6870 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))
6871 (clobber (reg:CC CC_REGNUM))]
6872 "!TARGET_64BIT"
6873 "srda\t%0,%Y2"
6874 [(set_attr "op_type" "RS")
6875 (set_attr "atype" "reg")])
6876
6877 ; sra, srag
6878 (define_insn "*ashr<mode>3_cc"
6879 [(set (reg CC_REGNUM)
6880 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6881 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
6882 (const_int 0)))
6883 (set (match_operand:GPR 0 "register_operand" "=d")
6884 (ashiftrt:GPR (match_dup 1) (match_dup 2)))]
6885 "s390_match_ccmode(insn, CCSmode)"
6886 "sra<g>\t%0,<1>%Y2"
6887 [(set_attr "op_type" "RS<E>")
6888 (set_attr "atype" "reg")])
6889
6890 ; sra, srag
6891 (define_insn "*ashr<mode>3_cconly"
6892 [(set (reg CC_REGNUM)
6893 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6894 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y"))
6895 (const_int 0)))
6896 (clobber (match_scratch:GPR 0 "=d"))]
6897 "s390_match_ccmode(insn, CCSmode)"
6898 "sra<g>\t%0,<1>%Y2"
6899 [(set_attr "op_type" "RS<E>")
6900 (set_attr "atype" "reg")])
6901
6902 ; sra, srag
6903 (define_insn "*ashr<mode>3"
6904 [(set (match_operand:GPR 0 "register_operand" "=d")
6905 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6906 (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")))
6907 (clobber (reg:CC CC_REGNUM))]
6908 ""
6909 "sra<g>\t%0,<1>%Y2"
6910 [(set_attr "op_type" "RS<E>")
6911 (set_attr "atype" "reg")])
6912
6913
6914 ; shift pattern with implicit ANDs
6915
6916 (define_insn "*ashrdi3_cc_31_and"
6917 [(set (reg CC_REGNUM)
6918 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6919 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6920 (match_operand:SI 3 "const_int_operand" "n")))
6921 (const_int 0)))
6922 (set (match_operand:DI 0 "register_operand" "=d")
6923 (ashiftrt:DI (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
6924 "!TARGET_64BIT && s390_match_ccmode(insn, CCSmode)
6925 && (INTVAL (operands[3]) & 63) == 63"
6926 "srda\t%0,%Y2"
6927 [(set_attr "op_type" "RS")
6928 (set_attr "atype" "reg")])
6929
6930 (define_insn "*ashrdi3_cconly_31_and"
6931 [(set (reg CC_REGNUM)
6932 (compare (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6933 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6934 (match_operand:SI 3 "const_int_operand" "n")))
6935 (const_int 0)))
6936 (clobber (match_scratch:DI 0 "=d"))]
6937 "!TARGET_64BIT && s390_match_ccmode(insn, CCSmode)
6938 && (INTVAL (operands[3]) & 63) == 63"
6939 "srda\t%0,%Y2"
6940 [(set_attr "op_type" "RS")
6941 (set_attr "atype" "reg")])
6942
6943 (define_insn "*ashrdi3_31_and"
6944 [(set (match_operand:DI 0 "register_operand" "=d")
6945 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
6946 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6947 (match_operand:SI 3 "const_int_operand" "n"))))
6948 (clobber (reg:CC CC_REGNUM))]
6949 "!TARGET_64BIT && (INTVAL (operands[3]) & 63) == 63"
6950 "srda\t%0,%Y2"
6951 [(set_attr "op_type" "RS")
6952 (set_attr "atype" "reg")])
6953
6954 ; sra, srag
6955 (define_insn "*ashr<mode>3_cc_and"
6956 [(set (reg CC_REGNUM)
6957 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6958 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6959 (match_operand:SI 3 "const_int_operand" "n")))
6960 (const_int 0)))
6961 (set (match_operand:GPR 0 "register_operand" "=d")
6962 (ashiftrt:GPR (match_dup 1) (and:SI (match_dup 2) (match_dup 3))))]
6963 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
6964 "sra<g>\t%0,<1>%Y2"
6965 [(set_attr "op_type" "RS<E>")
6966 (set_attr "atype" "reg")])
6967
6968 ; sra, srag
6969 (define_insn "*ashr<mode>3_cconly_and"
6970 [(set (reg CC_REGNUM)
6971 (compare (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6972 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6973 (match_operand:SI 3 "const_int_operand" "n")))
6974 (const_int 0)))
6975 (clobber (match_scratch:GPR 0 "=d"))]
6976 "s390_match_ccmode(insn, CCSmode) && (INTVAL (operands[3]) & 63) == 63"
6977 "sra<g>\t%0,<1>%Y2"
6978 [(set_attr "op_type" "RS<E>")
6979 (set_attr "atype" "reg")])
6980
6981 ; sra, srag
6982 (define_insn "*ashr<mode>3_and"
6983 [(set (match_operand:GPR 0 "register_operand" "=d")
6984 (ashiftrt:GPR (match_operand:GPR 1 "register_operand" "<d0>")
6985 (and:SI (match_operand:SI 2 "shift_count_or_setmem_operand" "Y")
6986 (match_operand:SI 3 "const_int_operand" "n"))))
6987 (clobber (reg:CC CC_REGNUM))]
6988 "(INTVAL (operands[3]) & 63) == 63"
6989 "sra<g>\t%0,<1>%Y2"
6990 [(set_attr "op_type" "RS<E>")
6991 (set_attr "atype" "reg")])
6992
6993
6994 ;;
6995 ;; Branch instruction patterns.
6996 ;;
6997
6998 (define_expand "b<code>"
6999 [(set (pc)
7000 (if_then_else (COMPARE (match_operand 0 "" "")
7001 (const_int 0))
7002 (match_dup 0)
7003 (pc)))]
7004 ""
7005 "s390_emit_jump (operands[0],
7006 s390_emit_compare (<CODE>, s390_compare_op0, s390_compare_op1)); DONE;")
7007
7008
7009 ;;
7010 ;;- Conditional jump instructions.
7011 ;;
7012
7013 (define_insn "*cjump_64"
7014 [(set (pc)
7015 (if_then_else
7016 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7017 (label_ref (match_operand 0 "" ""))
7018 (pc)))]
7019 "TARGET_CPU_ZARCH"
7020 {
7021 if (get_attr_length (insn) == 4)
7022 return "j%C1\t%l0";
7023 else
7024 return "jg%C1\t%l0";
7025 }
7026 [(set_attr "op_type" "RI")
7027 (set_attr "type" "branch")
7028 (set (attr "length")
7029 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7030 (const_int 4) (const_int 6)))])
7031
7032 (define_insn "*cjump_31"
7033 [(set (pc)
7034 (if_then_else
7035 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7036 (label_ref (match_operand 0 "" ""))
7037 (pc)))]
7038 "!TARGET_CPU_ZARCH"
7039 {
7040 gcc_assert (get_attr_length (insn) == 4);
7041 return "j%C1\t%l0";
7042 }
7043 [(set_attr "op_type" "RI")
7044 (set_attr "type" "branch")
7045 (set (attr "length")
7046 (if_then_else (eq (symbol_ref "flag_pic") (const_int 0))
7047 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7048 (const_int 4) (const_int 6))
7049 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7050 (const_int 4) (const_int 8))))])
7051
7052 (define_insn "*cjump_long"
7053 [(set (pc)
7054 (if_then_else
7055 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7056 (match_operand 0 "address_operand" "U")
7057 (pc)))]
7058 ""
7059 {
7060 if (get_attr_op_type (insn) == OP_TYPE_RR)
7061 return "b%C1r\t%0";
7062 else
7063 return "b%C1\t%a0";
7064 }
7065 [(set (attr "op_type")
7066 (if_then_else (match_operand 0 "register_operand" "")
7067 (const_string "RR") (const_string "RX")))
7068 (set_attr "type" "branch")
7069 (set_attr "atype" "agen")])
7070
7071
7072 ;;
7073 ;;- Negated conditional jump instructions.
7074 ;;
7075
7076 (define_insn "*icjump_64"
7077 [(set (pc)
7078 (if_then_else
7079 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7080 (pc)
7081 (label_ref (match_operand 0 "" ""))))]
7082 "TARGET_CPU_ZARCH"
7083 {
7084 if (get_attr_length (insn) == 4)
7085 return "j%D1\t%l0";
7086 else
7087 return "jg%D1\t%l0";
7088 }
7089 [(set_attr "op_type" "RI")
7090 (set_attr "type" "branch")
7091 (set (attr "length")
7092 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7093 (const_int 4) (const_int 6)))])
7094
7095 (define_insn "*icjump_31"
7096 [(set (pc)
7097 (if_then_else
7098 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7099 (pc)
7100 (label_ref (match_operand 0 "" ""))))]
7101 "!TARGET_CPU_ZARCH"
7102 {
7103 gcc_assert (get_attr_length (insn) == 4);
7104 return "j%D1\t%l0";
7105 }
7106 [(set_attr "op_type" "RI")
7107 (set_attr "type" "branch")
7108 (set (attr "length")
7109 (if_then_else (eq (symbol_ref "flag_pic") (const_int 0))
7110 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7111 (const_int 4) (const_int 6))
7112 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7113 (const_int 4) (const_int 8))))])
7114
7115 (define_insn "*icjump_long"
7116 [(set (pc)
7117 (if_then_else
7118 (match_operator 1 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7119 (pc)
7120 (match_operand 0 "address_operand" "U")))]
7121 ""
7122 {
7123 if (get_attr_op_type (insn) == OP_TYPE_RR)
7124 return "b%D1r\t%0";
7125 else
7126 return "b%D1\t%a0";
7127 }
7128 [(set (attr "op_type")
7129 (if_then_else (match_operand 0 "register_operand" "")
7130 (const_string "RR") (const_string "RX")))
7131 (set_attr "type" "branch")
7132 (set_attr "atype" "agen")])
7133
7134 ;;
7135 ;;- Trap instructions.
7136 ;;
7137
7138 (define_insn "trap"
7139 [(trap_if (const_int 1) (const_int 0))]
7140 ""
7141 "j\t.+2"
7142 [(set_attr "op_type" "RI")
7143 (set_attr "type" "branch")])
7144
7145 (define_expand "conditional_trap"
7146 [(trap_if (match_operand 0 "comparison_operator" "")
7147 (match_operand 1 "general_operand" ""))]
7148 ""
7149 {
7150 if (operands[1] != const0_rtx) FAIL;
7151 operands[0] = s390_emit_compare (GET_CODE (operands[0]),
7152 s390_compare_op0, s390_compare_op1);
7153 })
7154
7155 (define_insn "*trap"
7156 [(trap_if (match_operator 0 "s390_comparison" [(reg CC_REGNUM) (const_int 0)])
7157 (const_int 0))]
7158 ""
7159 "j%C0\t.+2";
7160 [(set_attr "op_type" "RI")
7161 (set_attr "type" "branch")])
7162
7163 ; crt, cgrt, cit, cgit
7164 (define_insn "*cmp_and_trap_signed_int<mode>"
7165 [(trap_if (match_operator 0 "s390_signed_integer_comparison"
7166 [(match_operand:GPR 1 "register_operand" "d,d")
7167 (match_operand:GPR 2 "nonmemory_operand" "d,K")])
7168 (const_int 0))]
7169 "TARGET_Z10"
7170 "@
7171 c<g>rt%C0\t%1,%2
7172 c<g>it%C0\t%1,%h2"
7173 [(set_attr "op_type" "RRF,RIE")
7174 (set_attr "type" "branch")])
7175
7176 ; clrt, clgrt, clfit, clgit
7177 (define_insn "*cmp_and_trap_unsigned_int<mode>"
7178 [(trap_if (match_operator 0 "s390_unsigned_integer_comparison"
7179 [(match_operand:GPR 1 "register_operand" "d,d")
7180 (match_operand:GPR 2 "nonmemory_operand" "d,D")])
7181 (const_int 0))]
7182 "TARGET_Z10"
7183 "@
7184 cl<g>rt%C0\t%1,%2
7185 cl<gf>it%C0\t%1,%x2"
7186 [(set_attr "op_type" "RRF,RIE")
7187 (set_attr "type" "branch")])
7188
7189 ;;
7190 ;;- Loop instructions.
7191 ;;
7192 ;; This is all complicated by the fact that since this is a jump insn
7193 ;; we must handle our own output reloads.
7194
7195 (define_expand "doloop_end"
7196 [(use (match_operand 0 "" "")) ; loop pseudo
7197 (use (match_operand 1 "" "")) ; iterations; zero if unknown
7198 (use (match_operand 2 "" "")) ; max iterations
7199 (use (match_operand 3 "" "")) ; loop level
7200 (use (match_operand 4 "" ""))] ; label
7201 ""
7202 {
7203 if (GET_MODE (operands[0]) == SImode && !TARGET_CPU_ZARCH)
7204 emit_jump_insn (gen_doloop_si31 (operands[4], operands[0], operands[0]));
7205 else if (GET_MODE (operands[0]) == SImode && TARGET_CPU_ZARCH)
7206 emit_jump_insn (gen_doloop_si64 (operands[4], operands[0], operands[0]));
7207 else if (GET_MODE (operands[0]) == DImode && TARGET_64BIT)
7208 emit_jump_insn (gen_doloop_di (operands[4], operands[0], operands[0]));
7209 else
7210 FAIL;
7211
7212 DONE;
7213 })
7214
7215 (define_insn_and_split "doloop_si64"
7216 [(set (pc)
7217 (if_then_else
7218 (ne (match_operand:SI 1 "register_operand" "d,d,d")
7219 (const_int 1))
7220 (label_ref (match_operand 0 "" ""))
7221 (pc)))
7222 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
7223 (plus:SI (match_dup 1) (const_int -1)))
7224 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
7225 (clobber (reg:CC CC_REGNUM))]
7226 "TARGET_CPU_ZARCH"
7227 {
7228 if (which_alternative != 0)
7229 return "#";
7230 else if (get_attr_length (insn) == 4)
7231 return "brct\t%1,%l0";
7232 else
7233 return "ahi\t%1,-1\;jgne\t%l0";
7234 }
7235 "&& reload_completed
7236 && (! REG_P (operands[2])
7237 || ! rtx_equal_p (operands[1], operands[2]))"
7238 [(set (match_dup 3) (match_dup 1))
7239 (parallel [(set (reg:CCAN CC_REGNUM)
7240 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
7241 (const_int 0)))
7242 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
7243 (set (match_dup 2) (match_dup 3))
7244 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
7245 (label_ref (match_dup 0))
7246 (pc)))]
7247 ""
7248 [(set_attr "op_type" "RI")
7249 (set_attr "type" "branch")
7250 (set (attr "length")
7251 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7252 (const_int 4) (const_int 10)))])
7253
7254 (define_insn_and_split "doloop_si31"
7255 [(set (pc)
7256 (if_then_else
7257 (ne (match_operand:SI 1 "register_operand" "d,d,d")
7258 (const_int 1))
7259 (label_ref (match_operand 0 "" ""))
7260 (pc)))
7261 (set (match_operand:SI 2 "nonimmediate_operand" "=1,?X,?X")
7262 (plus:SI (match_dup 1) (const_int -1)))
7263 (clobber (match_scratch:SI 3 "=X,&1,&?d"))
7264 (clobber (reg:CC CC_REGNUM))]
7265 "!TARGET_CPU_ZARCH"
7266 {
7267 if (which_alternative != 0)
7268 return "#";
7269 else if (get_attr_length (insn) == 4)
7270 return "brct\t%1,%l0";
7271 else
7272 gcc_unreachable ();
7273 }
7274 "&& reload_completed
7275 && (! REG_P (operands[2])
7276 || ! rtx_equal_p (operands[1], operands[2]))"
7277 [(set (match_dup 3) (match_dup 1))
7278 (parallel [(set (reg:CCAN CC_REGNUM)
7279 (compare:CCAN (plus:SI (match_dup 3) (const_int -1))
7280 (const_int 0)))
7281 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
7282 (set (match_dup 2) (match_dup 3))
7283 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
7284 (label_ref (match_dup 0))
7285 (pc)))]
7286 ""
7287 [(set_attr "op_type" "RI")
7288 (set_attr "type" "branch")
7289 (set (attr "length")
7290 (if_then_else (eq (symbol_ref "flag_pic") (const_int 0))
7291 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7292 (const_int 4) (const_int 6))
7293 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7294 (const_int 4) (const_int 8))))])
7295
7296 (define_insn "*doloop_si_long"
7297 [(set (pc)
7298 (if_then_else
7299 (ne (match_operand:SI 1 "register_operand" "d")
7300 (const_int 1))
7301 (match_operand 0 "address_operand" "U")
7302 (pc)))
7303 (set (match_operand:SI 2 "register_operand" "=1")
7304 (plus:SI (match_dup 1) (const_int -1)))
7305 (clobber (match_scratch:SI 3 "=X"))
7306 (clobber (reg:CC CC_REGNUM))]
7307 "!TARGET_CPU_ZARCH"
7308 {
7309 if (get_attr_op_type (insn) == OP_TYPE_RR)
7310 return "bctr\t%1,%0";
7311 else
7312 return "bct\t%1,%a0";
7313 }
7314 [(set (attr "op_type")
7315 (if_then_else (match_operand 0 "register_operand" "")
7316 (const_string "RR") (const_string "RX")))
7317 (set_attr "type" "branch")
7318 (set_attr "atype" "agen")])
7319
7320 (define_insn_and_split "doloop_di"
7321 [(set (pc)
7322 (if_then_else
7323 (ne (match_operand:DI 1 "register_operand" "d,d,d")
7324 (const_int 1))
7325 (label_ref (match_operand 0 "" ""))
7326 (pc)))
7327 (set (match_operand:DI 2 "nonimmediate_operand" "=1,?X,?X")
7328 (plus:DI (match_dup 1) (const_int -1)))
7329 (clobber (match_scratch:DI 3 "=X,&1,&?d"))
7330 (clobber (reg:CC CC_REGNUM))]
7331 "TARGET_64BIT"
7332 {
7333 if (which_alternative != 0)
7334 return "#";
7335 else if (get_attr_length (insn) == 4)
7336 return "brctg\t%1,%l0";
7337 else
7338 return "aghi\t%1,-1\;jgne\t%l0";
7339 }
7340 "&& reload_completed
7341 && (! REG_P (operands[2])
7342 || ! rtx_equal_p (operands[1], operands[2]))"
7343 [(set (match_dup 3) (match_dup 1))
7344 (parallel [(set (reg:CCAN CC_REGNUM)
7345 (compare:CCAN (plus:DI (match_dup 3) (const_int -1))
7346 (const_int 0)))
7347 (set (match_dup 3) (plus:DI (match_dup 3) (const_int -1)))])
7348 (set (match_dup 2) (match_dup 3))
7349 (set (pc) (if_then_else (ne (reg:CCAN CC_REGNUM) (const_int 0))
7350 (label_ref (match_dup 0))
7351 (pc)))]
7352 ""
7353 [(set_attr "op_type" "RI")
7354 (set_attr "type" "branch")
7355 (set (attr "length")
7356 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7357 (const_int 4) (const_int 10)))])
7358
7359 ;;
7360 ;;- Unconditional jump instructions.
7361 ;;
7362
7363 ;
7364 ; jump instruction pattern(s).
7365 ;
7366
7367 (define_expand "jump"
7368 [(match_operand 0 "" "")]
7369 ""
7370 "s390_emit_jump (operands[0], NULL_RTX); DONE;")
7371
7372 (define_insn "*jump64"
7373 [(set (pc) (label_ref (match_operand 0 "" "")))]
7374 "TARGET_CPU_ZARCH"
7375 {
7376 if (get_attr_length (insn) == 4)
7377 return "j\t%l0";
7378 else
7379 return "jg\t%l0";
7380 }
7381 [(set_attr "op_type" "RI")
7382 (set_attr "type" "branch")
7383 (set (attr "length")
7384 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7385 (const_int 4) (const_int 6)))])
7386
7387 (define_insn "*jump31"
7388 [(set (pc) (label_ref (match_operand 0 "" "")))]
7389 "!TARGET_CPU_ZARCH"
7390 {
7391 gcc_assert (get_attr_length (insn) == 4);
7392 return "j\t%l0";
7393 }
7394 [(set_attr "op_type" "RI")
7395 (set_attr "type" "branch")
7396 (set (attr "length")
7397 (if_then_else (eq (symbol_ref "flag_pic") (const_int 0))
7398 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7399 (const_int 4) (const_int 6))
7400 (if_then_else (lt (abs (minus (pc) (match_dup 0))) (const_int 60000))
7401 (const_int 4) (const_int 8))))])
7402
7403 ;
7404 ; indirect-jump instruction pattern(s).
7405 ;
7406
7407 (define_insn "indirect_jump"
7408 [(set (pc) (match_operand 0 "address_operand" "U"))]
7409 ""
7410 {
7411 if (get_attr_op_type (insn) == OP_TYPE_RR)
7412 return "br\t%0";
7413 else
7414 return "b\t%a0";
7415 }
7416 [(set (attr "op_type")
7417 (if_then_else (match_operand 0 "register_operand" "")
7418 (const_string "RR") (const_string "RX")))
7419 (set_attr "type" "branch")
7420 (set_attr "atype" "agen")])
7421
7422 ;
7423 ; casesi instruction pattern(s).
7424 ;
7425
7426 (define_insn "casesi_jump"
7427 [(set (pc) (match_operand 0 "address_operand" "U"))
7428 (use (label_ref (match_operand 1 "" "")))]
7429 ""
7430 {
7431 if (get_attr_op_type (insn) == OP_TYPE_RR)
7432 return "br\t%0";
7433 else
7434 return "b\t%a0";
7435 }
7436 [(set (attr "op_type")
7437 (if_then_else (match_operand 0 "register_operand" "")
7438 (const_string "RR") (const_string "RX")))
7439 (set_attr "type" "branch")
7440 (set_attr "atype" "agen")])
7441
7442 (define_expand "casesi"
7443 [(match_operand:SI 0 "general_operand" "")
7444 (match_operand:SI 1 "general_operand" "")
7445 (match_operand:SI 2 "general_operand" "")
7446 (label_ref (match_operand 3 "" ""))
7447 (label_ref (match_operand 4 "" ""))]
7448 ""
7449 {
7450 rtx index = gen_reg_rtx (SImode);
7451 rtx base = gen_reg_rtx (Pmode);
7452 rtx target = gen_reg_rtx (Pmode);
7453
7454 emit_move_insn (index, operands[0]);
7455 emit_insn (gen_subsi3 (index, index, operands[1]));
7456 emit_cmp_and_jump_insns (index, operands[2], GTU, NULL_RTX, SImode, 1,
7457 operands[4]);
7458
7459 if (Pmode != SImode)
7460 index = convert_to_mode (Pmode, index, 1);
7461 if (GET_CODE (index) != REG)
7462 index = copy_to_mode_reg (Pmode, index);
7463
7464 if (TARGET_64BIT)
7465 emit_insn (gen_ashldi3 (index, index, GEN_INT (3)));
7466 else
7467 emit_insn (gen_ashlsi3 (index, index, const2_rtx));
7468
7469 emit_move_insn (base, gen_rtx_LABEL_REF (Pmode, operands[3]));
7470
7471 index = gen_const_mem (Pmode, gen_rtx_PLUS (Pmode, base, index));
7472 emit_move_insn (target, index);
7473
7474 if (flag_pic)
7475 target = gen_rtx_PLUS (Pmode, base, target);
7476 emit_jump_insn (gen_casesi_jump (target, operands[3]));
7477
7478 DONE;
7479 })
7480
7481
7482 ;;
7483 ;;- Jump to subroutine.
7484 ;;
7485 ;;
7486
7487 ;
7488 ; untyped call instruction pattern(s).
7489 ;
7490
7491 ;; Call subroutine returning any type.
7492 (define_expand "untyped_call"
7493 [(parallel [(call (match_operand 0 "" "")
7494 (const_int 0))
7495 (match_operand 1 "" "")
7496 (match_operand 2 "" "")])]
7497 ""
7498 {
7499 int i;
7500
7501 emit_call_insn (gen_call (operands[0], const0_rtx, const0_rtx));
7502
7503 for (i = 0; i < XVECLEN (operands[2], 0); i++)
7504 {
7505 rtx set = XVECEXP (operands[2], 0, i);
7506 emit_move_insn (SET_DEST (set), SET_SRC (set));
7507 }
7508
7509 /* The optimizer does not know that the call sets the function value
7510 registers we stored in the result block. We avoid problems by
7511 claiming that all hard registers are used and clobbered at this
7512 point. */
7513 emit_insn (gen_blockage ());
7514
7515 DONE;
7516 })
7517
7518 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
7519 ;; all of memory. This blocks insns from being moved across this point.
7520
7521 (define_insn "blockage"
7522 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
7523 ""
7524 ""
7525 [(set_attr "type" "none")
7526 (set_attr "length" "0")])
7527
7528 ;
7529 ; sibcall patterns
7530 ;
7531
7532 (define_expand "sibcall"
7533 [(call (match_operand 0 "" "")
7534 (match_operand 1 "" ""))]
7535 ""
7536 {
7537 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX, NULL_RTX);
7538 DONE;
7539 })
7540
7541 (define_insn "*sibcall_br"
7542 [(call (mem:QI (reg SIBCALL_REGNUM))
7543 (match_operand 0 "const_int_operand" "n"))]
7544 "SIBLING_CALL_P (insn)
7545 && GET_MODE (XEXP (XEXP (PATTERN (insn), 0), 0)) == Pmode"
7546 "br\t%%r1"
7547 [(set_attr "op_type" "RR")
7548 (set_attr "type" "branch")
7549 (set_attr "atype" "agen")])
7550
7551 (define_insn "*sibcall_brc"
7552 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
7553 (match_operand 1 "const_int_operand" "n"))]
7554 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
7555 "j\t%0"
7556 [(set_attr "op_type" "RI")
7557 (set_attr "type" "branch")])
7558
7559 (define_insn "*sibcall_brcl"
7560 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
7561 (match_operand 1 "const_int_operand" "n"))]
7562 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
7563 "jg\t%0"
7564 [(set_attr "op_type" "RIL")
7565 (set_attr "type" "branch")])
7566
7567 ;
7568 ; sibcall_value patterns
7569 ;
7570
7571 (define_expand "sibcall_value"
7572 [(set (match_operand 0 "" "")
7573 (call (match_operand 1 "" "")
7574 (match_operand 2 "" "")))]
7575 ""
7576 {
7577 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0], NULL_RTX);
7578 DONE;
7579 })
7580
7581 (define_insn "*sibcall_value_br"
7582 [(set (match_operand 0 "" "")
7583 (call (mem:QI (reg SIBCALL_REGNUM))
7584 (match_operand 1 "const_int_operand" "n")))]
7585 "SIBLING_CALL_P (insn)
7586 && GET_MODE (XEXP (XEXP (XEXP (PATTERN (insn), 1), 0), 0)) == Pmode"
7587 "br\t%%r1"
7588 [(set_attr "op_type" "RR")
7589 (set_attr "type" "branch")
7590 (set_attr "atype" "agen")])
7591
7592 (define_insn "*sibcall_value_brc"
7593 [(set (match_operand 0 "" "")
7594 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7595 (match_operand 2 "const_int_operand" "n")))]
7596 "SIBLING_CALL_P (insn) && TARGET_SMALL_EXEC"
7597 "j\t%1"
7598 [(set_attr "op_type" "RI")
7599 (set_attr "type" "branch")])
7600
7601 (define_insn "*sibcall_value_brcl"
7602 [(set (match_operand 0 "" "")
7603 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7604 (match_operand 2 "const_int_operand" "n")))]
7605 "SIBLING_CALL_P (insn) && TARGET_CPU_ZARCH"
7606 "jg\t%1"
7607 [(set_attr "op_type" "RIL")
7608 (set_attr "type" "branch")])
7609
7610
7611 ;
7612 ; call instruction pattern(s).
7613 ;
7614
7615 (define_expand "call"
7616 [(call (match_operand 0 "" "")
7617 (match_operand 1 "" ""))
7618 (use (match_operand 2 "" ""))]
7619 ""
7620 {
7621 s390_emit_call (XEXP (operands[0], 0), NULL_RTX, NULL_RTX,
7622 gen_rtx_REG (Pmode, RETURN_REGNUM));
7623 DONE;
7624 })
7625
7626 (define_insn "*bras"
7627 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
7628 (match_operand 1 "const_int_operand" "n"))
7629 (clobber (match_operand 2 "register_operand" "=r"))]
7630 "!SIBLING_CALL_P (insn)
7631 && TARGET_SMALL_EXEC
7632 && GET_MODE (operands[2]) == Pmode"
7633 "bras\t%2,%0"
7634 [(set_attr "op_type" "RI")
7635 (set_attr "type" "jsr")])
7636
7637 (define_insn "*brasl"
7638 [(call (mem:QI (match_operand 0 "bras_sym_operand" "X"))
7639 (match_operand 1 "const_int_operand" "n"))
7640 (clobber (match_operand 2 "register_operand" "=r"))]
7641 "!SIBLING_CALL_P (insn)
7642 && TARGET_CPU_ZARCH
7643 && GET_MODE (operands[2]) == Pmode"
7644 "brasl\t%2,%0"
7645 [(set_attr "op_type" "RIL")
7646 (set_attr "type" "jsr")])
7647
7648 (define_insn "*basr"
7649 [(call (mem:QI (match_operand 0 "address_operand" "U"))
7650 (match_operand 1 "const_int_operand" "n"))
7651 (clobber (match_operand 2 "register_operand" "=r"))]
7652 "!SIBLING_CALL_P (insn) && GET_MODE (operands[2]) == Pmode"
7653 {
7654 if (get_attr_op_type (insn) == OP_TYPE_RR)
7655 return "basr\t%2,%0";
7656 else
7657 return "bas\t%2,%a0";
7658 }
7659 [(set (attr "op_type")
7660 (if_then_else (match_operand 0 "register_operand" "")
7661 (const_string "RR") (const_string "RX")))
7662 (set_attr "type" "jsr")
7663 (set_attr "atype" "agen")])
7664
7665 ;
7666 ; call_value instruction pattern(s).
7667 ;
7668
7669 (define_expand "call_value"
7670 [(set (match_operand 0 "" "")
7671 (call (match_operand 1 "" "")
7672 (match_operand 2 "" "")))
7673 (use (match_operand 3 "" ""))]
7674 ""
7675 {
7676 s390_emit_call (XEXP (operands[1], 0), NULL_RTX, operands[0],
7677 gen_rtx_REG (Pmode, RETURN_REGNUM));
7678 DONE;
7679 })
7680
7681 (define_insn "*bras_r"
7682 [(set (match_operand 0 "" "")
7683 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7684 (match_operand:SI 2 "const_int_operand" "n")))
7685 (clobber (match_operand 3 "register_operand" "=r"))]
7686 "!SIBLING_CALL_P (insn)
7687 && TARGET_SMALL_EXEC
7688 && GET_MODE (operands[3]) == Pmode"
7689 "bras\t%3,%1"
7690 [(set_attr "op_type" "RI")
7691 (set_attr "type" "jsr")])
7692
7693 (define_insn "*brasl_r"
7694 [(set (match_operand 0 "" "")
7695 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7696 (match_operand 2 "const_int_operand" "n")))
7697 (clobber (match_operand 3 "register_operand" "=r"))]
7698 "!SIBLING_CALL_P (insn)
7699 && TARGET_CPU_ZARCH
7700 && GET_MODE (operands[3]) == Pmode"
7701 "brasl\t%3,%1"
7702 [(set_attr "op_type" "RIL")
7703 (set_attr "type" "jsr")])
7704
7705 (define_insn "*basr_r"
7706 [(set (match_operand 0 "" "")
7707 (call (mem:QI (match_operand 1 "address_operand" "U"))
7708 (match_operand 2 "const_int_operand" "n")))
7709 (clobber (match_operand 3 "register_operand" "=r"))]
7710 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
7711 {
7712 if (get_attr_op_type (insn) == OP_TYPE_RR)
7713 return "basr\t%3,%1";
7714 else
7715 return "bas\t%3,%a1";
7716 }
7717 [(set (attr "op_type")
7718 (if_then_else (match_operand 1 "register_operand" "")
7719 (const_string "RR") (const_string "RX")))
7720 (set_attr "type" "jsr")
7721 (set_attr "atype" "agen")])
7722
7723 ;;
7724 ;;- Thread-local storage support.
7725 ;;
7726
7727 (define_expand "get_tp_64"
7728 [(set (match_operand:DI 0 "nonimmediate_operand" "") (reg:DI TP_REGNUM))]
7729 "TARGET_64BIT"
7730 "")
7731
7732 (define_expand "get_tp_31"
7733 [(set (match_operand:SI 0 "nonimmediate_operand" "") (reg:SI TP_REGNUM))]
7734 "!TARGET_64BIT"
7735 "")
7736
7737 (define_expand "set_tp_64"
7738 [(set (reg:DI TP_REGNUM) (match_operand:DI 0 "nonimmediate_operand" ""))
7739 (set (reg:DI TP_REGNUM) (unspec_volatile:DI [(reg:DI TP_REGNUM)] UNSPECV_SET_TP))]
7740 "TARGET_64BIT"
7741 "")
7742
7743 (define_expand "set_tp_31"
7744 [(set (reg:SI TP_REGNUM) (match_operand:SI 0 "nonimmediate_operand" ""))
7745 (set (reg:SI TP_REGNUM) (unspec_volatile:SI [(reg:SI TP_REGNUM)] UNSPECV_SET_TP))]
7746 "!TARGET_64BIT"
7747 "")
7748
7749 (define_insn "*set_tp"
7750 [(set (reg TP_REGNUM) (unspec_volatile [(reg TP_REGNUM)] UNSPECV_SET_TP))]
7751 ""
7752 ""
7753 [(set_attr "type" "none")
7754 (set_attr "length" "0")])
7755
7756 (define_insn "*tls_load_64"
7757 [(set (match_operand:DI 0 "register_operand" "=d")
7758 (unspec:DI [(match_operand:DI 1 "memory_operand" "RT")
7759 (match_operand:DI 2 "" "")]
7760 UNSPEC_TLS_LOAD))]
7761 "TARGET_64BIT"
7762 "lg\t%0,%1%J2"
7763 [(set_attr "op_type" "RXE")])
7764
7765 (define_insn "*tls_load_31"
7766 [(set (match_operand:SI 0 "register_operand" "=d,d")
7767 (unspec:SI [(match_operand:SI 1 "memory_operand" "R,T")
7768 (match_operand:SI 2 "" "")]
7769 UNSPEC_TLS_LOAD))]
7770 "!TARGET_64BIT"
7771 "@
7772 l\t%0,%1%J2
7773 ly\t%0,%1%J2"
7774 [(set_attr "op_type" "RX,RXY")])
7775
7776 (define_insn "*bras_tls"
7777 [(set (match_operand 0 "" "")
7778 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7779 (match_operand 2 "const_int_operand" "n")))
7780 (clobber (match_operand 3 "register_operand" "=r"))
7781 (use (match_operand 4 "" ""))]
7782 "!SIBLING_CALL_P (insn)
7783 && TARGET_SMALL_EXEC
7784 && GET_MODE (operands[3]) == Pmode"
7785 "bras\t%3,%1%J4"
7786 [(set_attr "op_type" "RI")
7787 (set_attr "type" "jsr")])
7788
7789 (define_insn "*brasl_tls"
7790 [(set (match_operand 0 "" "")
7791 (call (mem:QI (match_operand 1 "bras_sym_operand" "X"))
7792 (match_operand 2 "const_int_operand" "n")))
7793 (clobber (match_operand 3 "register_operand" "=r"))
7794 (use (match_operand 4 "" ""))]
7795 "!SIBLING_CALL_P (insn)
7796 && TARGET_CPU_ZARCH
7797 && GET_MODE (operands[3]) == Pmode"
7798 "brasl\t%3,%1%J4"
7799 [(set_attr "op_type" "RIL")
7800 (set_attr "type" "jsr")])
7801
7802 (define_insn "*basr_tls"
7803 [(set (match_operand 0 "" "")
7804 (call (mem:QI (match_operand 1 "address_operand" "U"))
7805 (match_operand 2 "const_int_operand" "n")))
7806 (clobber (match_operand 3 "register_operand" "=r"))
7807 (use (match_operand 4 "" ""))]
7808 "!SIBLING_CALL_P (insn) && GET_MODE (operands[3]) == Pmode"
7809 {
7810 if (get_attr_op_type (insn) == OP_TYPE_RR)
7811 return "basr\t%3,%1%J4";
7812 else
7813 return "bas\t%3,%a1%J4";
7814 }
7815 [(set (attr "op_type")
7816 (if_then_else (match_operand 1 "register_operand" "")
7817 (const_string "RR") (const_string "RX")))
7818 (set_attr "type" "jsr")
7819 (set_attr "atype" "agen")])
7820
7821 ;;
7822 ;;- Atomic operations
7823 ;;
7824
7825 ;
7826 ; memory barrier pattern.
7827 ;
7828
7829 (define_expand "memory_barrier"
7830 [(set (mem:BLK (match_dup 0))
7831 (unspec_volatile:BLK [(mem:BLK (match_dup 0))] UNSPECV_MB))]
7832 ""
7833 {
7834 operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (DImode));
7835 MEM_VOLATILE_P (operands[0]) = 1;
7836 })
7837
7838 (define_insn "*memory_barrier"
7839 [(set (match_operand:BLK 0 "" "")
7840 (unspec_volatile:BLK [(match_operand:BLK 1 "" "")] UNSPECV_MB))]
7841 ""
7842 "bcr\t15,0"
7843 [(set_attr "op_type" "RR")])
7844
7845 ;
7846 ; compare and swap patterns.
7847 ;
7848
7849 (define_expand "sync_compare_and_swap<mode>"
7850 [(parallel
7851 [(set (match_operand:TDSI 0 "register_operand" "")
7852 (match_operand:TDSI 1 "memory_operand" ""))
7853 (set (match_dup 1)
7854 (unspec_volatile:TDSI
7855 [(match_dup 1)
7856 (match_operand:TDSI 2 "register_operand" "")
7857 (match_operand:TDSI 3 "register_operand" "")]
7858 UNSPECV_CAS))
7859 (set (reg:CCZ1 CC_REGNUM)
7860 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
7861 "")
7862
7863 (define_expand "sync_compare_and_swap<mode>"
7864 [(parallel
7865 [(set (match_operand:HQI 0 "register_operand" "")
7866 (match_operand:HQI 1 "memory_operand" ""))
7867 (set (match_dup 1)
7868 (unspec_volatile:HQI
7869 [(match_dup 1)
7870 (match_operand:HQI 2 "general_operand" "")
7871 (match_operand:HQI 3 "general_operand" "")]
7872 UNSPECV_CAS))
7873 (set (reg:CCZ1 CC_REGNUM)
7874 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
7875 ""
7876 "s390_expand_cs_hqi (<MODE>mode, operands[0], operands[1],
7877 operands[2], operands[3]); DONE;")
7878
7879 (define_expand "sync_compare_and_swap_cc<mode>"
7880 [(parallel
7881 [(set (match_operand:TDSI 0 "register_operand" "")
7882 (match_operand:TDSI 1 "memory_operand" ""))
7883 (set (match_dup 1)
7884 (unspec_volatile:TDSI
7885 [(match_dup 1)
7886 (match_operand:TDSI 2 "register_operand" "")
7887 (match_operand:TDSI 3 "register_operand" "")]
7888 UNSPECV_CAS))
7889 (set (match_dup 4)
7890 (compare:CCZ1 (match_dup 1) (match_dup 2)))])]
7891 ""
7892 {
7893 /* Emulate compare. */
7894 operands[4] = gen_rtx_REG (CCZ1mode, CC_REGNUM);
7895 s390_compare_op0 = operands[1];
7896 s390_compare_op1 = operands[2];
7897 s390_compare_emitted = operands[4];
7898 })
7899
7900 ; cds, cdsg
7901 (define_insn "*sync_compare_and_swap<mode>"
7902 [(set (match_operand:DP 0 "register_operand" "=r")
7903 (match_operand:DP 1 "memory_operand" "+Q"))
7904 (set (match_dup 1)
7905 (unspec_volatile:DP
7906 [(match_dup 1)
7907 (match_operand:DP 2 "register_operand" "0")
7908 (match_operand:DP 3 "register_operand" "r")]
7909 UNSPECV_CAS))
7910 (set (reg:CCZ1 CC_REGNUM)
7911 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
7912 ""
7913 "cds<tg>\t%0,%3,%S1"
7914 [(set_attr "op_type" "RS<TE>")
7915 (set_attr "type" "sem")])
7916
7917 ; cs, csg
7918 (define_insn "*sync_compare_and_swap<mode>"
7919 [(set (match_operand:GPR 0 "register_operand" "=r")
7920 (match_operand:GPR 1 "memory_operand" "+Q"))
7921 (set (match_dup 1)
7922 (unspec_volatile:GPR
7923 [(match_dup 1)
7924 (match_operand:GPR 2 "register_operand" "0")
7925 (match_operand:GPR 3 "register_operand" "r")]
7926 UNSPECV_CAS))
7927 (set (reg:CCZ1 CC_REGNUM)
7928 (compare:CCZ1 (match_dup 1) (match_dup 2)))]
7929 ""
7930 "cs<g>\t%0,%3,%S1"
7931 [(set_attr "op_type" "RS<E>")
7932 (set_attr "type" "sem")])
7933
7934
7935 ;
7936 ; Other atomic instruction patterns.
7937 ;
7938
7939 (define_expand "sync_lock_test_and_set<mode>"
7940 [(match_operand:HQI 0 "register_operand")
7941 (match_operand:HQI 1 "memory_operand")
7942 (match_operand:HQI 2 "general_operand")]
7943 ""
7944 "s390_expand_atomic (<MODE>mode, SET, operands[0], operands[1],
7945 operands[2], false); DONE;")
7946
7947 (define_expand "sync_<atomic><mode>"
7948 [(set (match_operand:HQI 0 "memory_operand")
7949 (ATOMIC:HQI (match_dup 0)
7950 (match_operand:HQI 1 "general_operand")))]
7951 ""
7952 "s390_expand_atomic (<MODE>mode, <CODE>, NULL_RTX, operands[0],
7953 operands[1], false); DONE;")
7954
7955 (define_expand "sync_old_<atomic><mode>"
7956 [(set (match_operand:HQI 0 "register_operand")
7957 (match_operand:HQI 1 "memory_operand"))
7958 (set (match_dup 1)
7959 (ATOMIC:HQI (match_dup 1)
7960 (match_operand:HQI 2 "general_operand")))]
7961 ""
7962 "s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
7963 operands[2], false); DONE;")
7964
7965 (define_expand "sync_new_<atomic><mode>"
7966 [(set (match_operand:HQI 0 "register_operand")
7967 (ATOMIC:HQI (match_operand:HQI 1 "memory_operand")
7968 (match_operand:HQI 2 "general_operand")))
7969 (set (match_dup 1) (ATOMIC:HQI (match_dup 1) (match_dup 2)))]
7970 ""
7971 "s390_expand_atomic (<MODE>mode, <CODE>, operands[0], operands[1],
7972 operands[2], true); DONE;")
7973
7974 ;;
7975 ;;- Miscellaneous instructions.
7976 ;;
7977
7978 ;
7979 ; allocate stack instruction pattern(s).
7980 ;
7981
7982 (define_expand "allocate_stack"
7983 [(match_operand 0 "general_operand" "")
7984 (match_operand 1 "general_operand" "")]
7985 "TARGET_BACKCHAIN"
7986 {
7987 rtx temp = gen_reg_rtx (Pmode);
7988
7989 emit_move_insn (temp, s390_back_chain_rtx ());
7990 anti_adjust_stack (operands[1]);
7991 emit_move_insn (s390_back_chain_rtx (), temp);
7992
7993 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
7994 DONE;
7995 })
7996
7997
7998 ;
7999 ; setjmp instruction pattern.
8000 ;
8001
8002 (define_expand "builtin_setjmp_receiver"
8003 [(match_operand 0 "" "")]
8004 "flag_pic"
8005 {
8006 emit_insn (s390_load_got ());
8007 emit_use (pic_offset_table_rtx);
8008 DONE;
8009 })
8010
8011 ;; These patterns say how to save and restore the stack pointer. We need not
8012 ;; save the stack pointer at function level since we are careful to
8013 ;; preserve the backchain. At block level, we have to restore the backchain
8014 ;; when we restore the stack pointer.
8015 ;;
8016 ;; For nonlocal gotos, we must save both the stack pointer and its
8017 ;; backchain and restore both. Note that in the nonlocal case, the
8018 ;; save area is a memory location.
8019
8020 (define_expand "save_stack_function"
8021 [(match_operand 0 "general_operand" "")
8022 (match_operand 1 "general_operand" "")]
8023 ""
8024 "DONE;")
8025
8026 (define_expand "restore_stack_function"
8027 [(match_operand 0 "general_operand" "")
8028 (match_operand 1 "general_operand" "")]
8029 ""
8030 "DONE;")
8031
8032 (define_expand "restore_stack_block"
8033 [(match_operand 0 "register_operand" "")
8034 (match_operand 1 "register_operand" "")]
8035 "TARGET_BACKCHAIN"
8036 {
8037 rtx temp = gen_reg_rtx (Pmode);
8038
8039 emit_move_insn (temp, s390_back_chain_rtx ());
8040 emit_move_insn (operands[0], operands[1]);
8041 emit_move_insn (s390_back_chain_rtx (), temp);
8042
8043 DONE;
8044 })
8045
8046 (define_expand "save_stack_nonlocal"
8047 [(match_operand 0 "memory_operand" "")
8048 (match_operand 1 "register_operand" "")]
8049 ""
8050 {
8051 enum machine_mode mode = TARGET_64BIT ? OImode : TImode;
8052 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
8053
8054 /* Copy the backchain to the first word, sp to the second and the
8055 literal pool base to the third. */
8056
8057 if (TARGET_BACKCHAIN)
8058 {
8059 rtx temp = force_reg (Pmode, s390_back_chain_rtx ());
8060 emit_move_insn (operand_subword (operands[0], 0, 0, mode), temp);
8061 }
8062
8063 emit_move_insn (operand_subword (operands[0], 1, 0, mode), operands[1]);
8064 emit_move_insn (operand_subword (operands[0], 2, 0, mode), base);
8065
8066 DONE;
8067 })
8068
8069 (define_expand "restore_stack_nonlocal"
8070 [(match_operand 0 "register_operand" "")
8071 (match_operand 1 "memory_operand" "")]
8072 ""
8073 {
8074 enum machine_mode mode = TARGET_64BIT ? OImode : TImode;
8075 rtx base = gen_rtx_REG (Pmode, BASE_REGNUM);
8076 rtx temp = NULL_RTX;
8077
8078 /* Restore the backchain from the first word, sp from the second and the
8079 literal pool base from the third. */
8080
8081 if (TARGET_BACKCHAIN)
8082 temp = force_reg (Pmode, operand_subword (operands[1], 0, 0, mode));
8083
8084 emit_move_insn (base, operand_subword (operands[1], 2, 0, mode));
8085 emit_move_insn (operands[0], operand_subword (operands[1], 1, 0, mode));
8086
8087 if (temp)
8088 emit_move_insn (s390_back_chain_rtx (), temp);
8089
8090 emit_use (base);
8091 DONE;
8092 })
8093
8094 (define_expand "exception_receiver"
8095 [(const_int 0)]
8096 ""
8097 {
8098 s390_set_has_landing_pad_p (true);
8099 DONE;
8100 })
8101
8102 ;
8103 ; nop instruction pattern(s).
8104 ;
8105
8106 (define_insn "nop"
8107 [(const_int 0)]
8108 ""
8109 "lr\t0,0"
8110 [(set_attr "op_type" "RR")])
8111
8112
8113 ;
8114 ; Special literal pool access instruction pattern(s).
8115 ;
8116
8117 (define_insn "*pool_entry"
8118 [(unspec_volatile [(match_operand 0 "consttable_operand" "X")]
8119 UNSPECV_POOL_ENTRY)]
8120 ""
8121 {
8122 enum machine_mode mode = GET_MODE (PATTERN (insn));
8123 unsigned int align = GET_MODE_BITSIZE (mode);
8124 s390_output_pool_entry (operands[0], mode, align);
8125 return "";
8126 }
8127 [(set (attr "length")
8128 (symbol_ref "GET_MODE_SIZE (GET_MODE (PATTERN (insn)))"))])
8129
8130 (define_insn "pool_align"
8131 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")]
8132 UNSPECV_POOL_ALIGN)]
8133 ""
8134 ".align\t%0"
8135 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
8136
8137 (define_insn "pool_section_start"
8138 [(unspec_volatile [(const_int 1)] UNSPECV_POOL_SECTION)]
8139 ""
8140 ".section\t.rodata"
8141 [(set_attr "length" "0")])
8142
8143 (define_insn "pool_section_end"
8144 [(unspec_volatile [(const_int 0)] UNSPECV_POOL_SECTION)]
8145 ""
8146 ".previous"
8147 [(set_attr "length" "0")])
8148
8149 (define_insn "main_base_31_small"
8150 [(set (match_operand 0 "register_operand" "=a")
8151 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
8152 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
8153 "basr\t%0,0"
8154 [(set_attr "op_type" "RR")
8155 (set_attr "type" "la")])
8156
8157 (define_insn "main_base_31_large"
8158 [(set (match_operand 0 "register_operand" "=a")
8159 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))
8160 (set (pc) (label_ref (match_operand 2 "" "")))]
8161 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
8162 "bras\t%0,%2"
8163 [(set_attr "op_type" "RI")])
8164
8165 (define_insn "main_base_64"
8166 [(set (match_operand 0 "register_operand" "=a")
8167 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_MAIN_BASE))]
8168 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
8169 "larl\t%0,%1"
8170 [(set_attr "op_type" "RIL")
8171 (set_attr "type" "larl")])
8172
8173 (define_insn "main_pool"
8174 [(set (match_operand 0 "register_operand" "=a")
8175 (unspec_volatile [(const_int 0)] UNSPECV_MAIN_POOL))]
8176 "GET_MODE (operands[0]) == Pmode"
8177 {
8178 gcc_unreachable ();
8179 }
8180 [(set (attr "type")
8181 (if_then_else (ne (symbol_ref "TARGET_CPU_ZARCH") (const_int 0))
8182 (const_string "larl") (const_string "la")))])
8183
8184 (define_insn "reload_base_31"
8185 [(set (match_operand 0 "register_operand" "=a")
8186 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
8187 "!TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
8188 "basr\t%0,0\;la\t%0,%1-.(%0)"
8189 [(set_attr "length" "6")
8190 (set_attr "type" "la")])
8191
8192 (define_insn "reload_base_64"
8193 [(set (match_operand 0 "register_operand" "=a")
8194 (unspec [(label_ref (match_operand 1 "" ""))] UNSPEC_RELOAD_BASE))]
8195 "TARGET_CPU_ZARCH && GET_MODE (operands[0]) == Pmode"
8196 "larl\t%0,%1"
8197 [(set_attr "op_type" "RIL")
8198 (set_attr "type" "larl")])
8199
8200 (define_insn "pool"
8201 [(unspec_volatile [(match_operand 0 "const_int_operand" "n")] UNSPECV_POOL)]
8202 ""
8203 {
8204 gcc_unreachable ();
8205 }
8206 [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))])
8207
8208 ;;
8209 ;; Insns related to generating the function prologue and epilogue.
8210 ;;
8211
8212
8213 (define_expand "prologue"
8214 [(use (const_int 0))]
8215 ""
8216 "s390_emit_prologue (); DONE;")
8217
8218 (define_expand "epilogue"
8219 [(use (const_int 1))]
8220 ""
8221 "s390_emit_epilogue (false); DONE;")
8222
8223 (define_expand "sibcall_epilogue"
8224 [(use (const_int 0))]
8225 ""
8226 "s390_emit_epilogue (true); DONE;")
8227
8228 (define_insn "*return"
8229 [(return)
8230 (use (match_operand 0 "register_operand" "a"))]
8231 "GET_MODE (operands[0]) == Pmode"
8232 "br\t%0"
8233 [(set_attr "op_type" "RR")
8234 (set_attr "type" "jsr")
8235 (set_attr "atype" "agen")])
8236
8237
8238 ;; Instruction definition to extend a 31-bit pointer into a 64-bit
8239 ;; pointer. This is used for compatibility.
8240
8241 (define_expand "ptr_extend"
8242 [(set (match_operand:DI 0 "register_operand" "=r")
8243 (match_operand:SI 1 "register_operand" "r"))]
8244 "TARGET_64BIT"
8245 {
8246 emit_insn (gen_anddi3 (operands[0],
8247 gen_lowpart (DImode, operands[1]),
8248 GEN_INT (0x7fffffff)));
8249 DONE;
8250 })
8251
8252 ;; Instruction definition to expand eh_return macro to support
8253 ;; swapping in special linkage return addresses.
8254
8255 (define_expand "eh_return"
8256 [(use (match_operand 0 "register_operand" ""))]
8257 "TARGET_TPF"
8258 {
8259 s390_emit_tpf_eh_return (operands[0]);
8260 DONE;
8261 })
8262
8263 ;
8264 ; Stack Protector Patterns
8265 ;
8266
8267 (define_expand "stack_protect_set"
8268 [(set (match_operand 0 "memory_operand" "")
8269 (match_operand 1 "memory_operand" ""))]
8270 ""
8271 {
8272 #ifdef TARGET_THREAD_SSP_OFFSET
8273 operands[1]
8274 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
8275 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
8276 #endif
8277 if (TARGET_64BIT)
8278 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
8279 else
8280 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
8281
8282 DONE;
8283 })
8284
8285 (define_insn "stack_protect_set<mode>"
8286 [(set (match_operand:DSI 0 "memory_operand" "=Q")
8287 (unspec:DSI [(match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_SET))]
8288 ""
8289 "mvc\t%O0(%G0,%R0),%S1"
8290 [(set_attr "op_type" "SS")])
8291
8292 (define_expand "stack_protect_test"
8293 [(set (reg:CC CC_REGNUM)
8294 (compare (match_operand 0 "memory_operand" "")
8295 (match_operand 1 "memory_operand" "")))
8296 (match_operand 2 "" "")]
8297 ""
8298 {
8299 #ifdef TARGET_THREAD_SSP_OFFSET
8300 operands[1]
8301 = gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, s390_get_thread_pointer (),
8302 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
8303 #endif
8304 s390_compare_op0 = operands[0];
8305 s390_compare_op1 = operands[1];
8306 s390_compare_emitted = gen_rtx_REG (CCZmode, CC_REGNUM);
8307
8308 if (TARGET_64BIT)
8309 emit_insn (gen_stack_protect_testdi (operands[0], operands[1]));
8310 else
8311 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
8312
8313 emit_jump_insn (gen_beq (operands[2]));
8314
8315 DONE;
8316 })
8317
8318 (define_insn "stack_protect_test<mode>"
8319 [(set (reg:CCZ CC_REGNUM)
8320 (unspec:CCZ [(match_operand:DSI 0 "memory_operand" "Q")
8321 (match_operand:DSI 1 "memory_operand" "Q")] UNSPEC_SP_TEST))]
8322 ""
8323 "clc\t%O0(%G0,%R0),%S1"
8324 [(set_attr "op_type" "SS")])
8325
8326 ; This is used in s390_emit_prologue in order to prevent insns
8327 ; adjusting the stack pointer to be moved over insns writing stack
8328 ; slots using a copy of the stack pointer in a different register.
8329 (define_insn "stack_tie"
8330 [(set (match_operand:BLK 0 "memory_operand" "+m")
8331 (unspec:BLK [(match_dup 0)] UNSPEC_TIE))]
8332 ""
8333 ""
8334 [(set_attr "length" "0")])
8335
8336
8337 ;
8338 ; Data prefetch patterns
8339 ;
8340
8341 (define_insn "prefetch"
8342 [(prefetch (match_operand 0 "address_operand" "UW,X")
8343 (match_operand:SI 1 "const_int_operand" "n,n")
8344 (match_operand:SI 2 "const_int_operand" "n,n"))]
8345 "TARGET_Z10"
8346 {
8347 if (larl_operand (operands[0], Pmode))
8348 return INTVAL (operands[1]) == 1 ? "pfdrl\t2,%a0" : "pfdrl\t1,%a0";
8349
8350 if (s390_mem_constraint ("W", operands[0])
8351 || s390_mem_constraint ("U", operands[0]))
8352 return INTVAL (operands[1]) == 1 ? "pfd\t2,%a0" : "pfd\t1,%a0";
8353
8354 /* This point might be reached if op0 is a larl operand with an
8355 uneven addend. In this case we simply omit issuing a prefetch
8356 instruction. */
8357
8358 return "";
8359
8360 } [(set_attr "type" "load,larl")
8361 (set_attr "op_type" "RXY,RIL")])