]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/config/i370/i370.md
PR c++/17413
[thirdparty/gcc.git] / gcc / config / i370 / i370.md
CommitLineData
8e5578ea 1;;- Machine description for GNU compiler -- System/370 version.
2;; Copyright (C) 1989, 1993, 1994, 1995, 1997, 1998, 1999, 2000, 2002
3;; Free Software Foundation, Inc.
4;; Contributed by Jan Stein (jan@cd.chalmers.se).
5;; Modified for OS/390 LanguageEnvironment C by Dave Pitts (dpitts@cozx.com)
6;; Lots of Bug Fixes & Enhancements by Linas Vepstas (linas@linas.org)
7
8;; This file is part of GCC.
9
10;; GCC is free software; you can redistribute it and/or modify
11;; it under the terms of the GNU General Public License as published by
12;; the Free Software Foundation; either version 2, or (at your option)
13;; any later version.
14
15;; GCC is distributed in the hope that it will be useful,
16;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18;; GNU General Public License for more details.
19
20;; You should have received a copy of the GNU General Public License
21;; along with GCC; see the file COPYING. If not, write to
22;; the Free Software Foundation, 59 Temple Place - Suite 330,
23;; Boston, MA 02111-1307, USA.
24
25;; =======================================================================
26;; Condition codes for some of the instructions (in particular, for
27;; add, sub, shift, abs, etc. are handled with the cpp macro NOTICE_UPDATE_CC
28;;
29;; Special constraints for 370 machine description:
30;;
31;; a -- Any address register from 1 to 15.
32;; d -- Any register from 0 to 15.
33;; I -- An 8-bit constant (0..255).
34;; J -- A 12-bit constant (0..4095).
35;; K -- A 16-bit constant (-32768..32767).
36;; R -- a valid S operand in an RS, SI or SS instruction, or register
37;; S -- a valid S operand in an RS, SI or SS instruction
38;;
39;; Note this well:
40;; When defining an instruction, e.g. the movsi pattern:
41;;
42;; (define_insn ""
43;; [(set (match_operand:SI 0 "r_or_s_operand" "=dm,d,dm")
44;; (match_operand:SI 1 "r_or_s_operand" "diR,dim,*fF"))]
45;;
46;; The "r_or_s_operand" predicate is used to recognize the instruction;
47;; however, it is not further used to enforce a constraint at later stages.
48;; Thus, for example, although "r_or_s_operand" bars operands of the form
49;; base+index+displacement, such operands can none-the-less show up during
50;; post-instruction-recog processing: thus, for example, garbage like
51;; MVC 152(4,r13),0(r5,r13) might be generated if both op0 and op1 are
52;; mem operands. To avoid this, use the S constraint.
53;;
54;;
55;; Special formats used for outputting 370 instructions.
56;;
57;; %B -- Print a constant byte integer.
58;; %H -- Print a signed 16-bit constant.
59;; %K -- Print a signed 16-bit constant signed-extended to 32-bits.
60;; %L -- Print least significant word of a CONST_DOUBLE.
61;; %M -- Print most significant word of a CONST_DOUBLE.
62;; %N -- Print next register (second word of a DImode reg).
63;; %O -- Print the offset of a memory reference (PLUS (REG) (CONST_INT)).
64;; %R -- Print the register of a memory reference (PLUS (REG) (CONST_INT)).
65;; %X -- Print a constant byte integer in hex.
66;; %W -- Print a signed 32-bit int sign-extended to 64-bits.
67;;
68;; We have a special constraint for pattern matching.
69;;
70;; s_operand -- Matches a valid S operand in a RS, SI or SS type instruction.
71;;
72;; r_or_s_operand -- Matches a register or a valid S operand in a RS, SI
73;; or SS type instruction or a register
74;;
75;; For MVS C/370 we use the following stack locations for:
76;;
77;; 136 - internal function result buffer
78;; 140 - numeric conversion buffer
79;; 144 - pointer to internal function result buffer
80;; 148 - start of automatic variables and function arguments
81;;
82;; To support programs larger than a page, 4096 bytes, PAGE_REGISTER points
83;; to a page origin table, all internal labels are generated to reload the
84;; BASE_REGISTER knowing what page it is on and all branch instructions go
85;; directly to the target if it is known that the target is on the current
86;; page (essentially backward references). All forward references and off
87;; page references are handled by loading the address of target into a
88;; register and branching indirectly.
89;;
90;; Some *di patterns have been commented out per advice from RMS, as gcc
91;; will generate the right things to do.
92;;
93;; See the note in i370.h about register 14, clobbering it, and optimization.
94;; Basically, using clobber in egcs-1.1.1 will ruin ability to optimize around
95;; branches, so don't do it.
96;;
97;; We use the "length" attirbute to store the max possible code size of an
98;; insn. We use this length to estimate the length of forward branches, to
99;; determine if they're on page or off.
100
101(define_attr "length" "" (const_int 0))
102
103;;
104;;- Test instructions.
105;;
106
107;
108; tstdi instruction pattern(s).
109;
110
111(define_insn "tstdi"
112 [(set (cc0)
113 (match_operand:DI 0 "register_operand" "d"))]
114 ""
115 "*
116{
117 check_label_emit ();
118 mvs_check_page (0, 4, 0);
119 return \"SRDA %0,0\";
120}"
121 [(set_attr "length" "4")]
122)
123
124;
125; tstsi instruction pattern(s).
126;
127
128(define_insn "tstsi"
129 [(set (cc0)
130 (match_operand:SI 0 "register_operand" "d"))]
131 ""
132 "*
133{
134 check_label_emit ();
135 mvs_check_page (0, 2, 0);
136 return \"LTR %0,%0\";
137}"
138 [(set_attr "length" "2")]
139)
140
141;
142; tsthi instruction pattern(s).
143;
144
145(define_insn "tsthi"
146 [(set (cc0)
147 (match_operand:HI 0 "register_operand" "d"))]
148 ""
149 "*
150{
151 check_label_emit ();
152 mvs_check_page (0, 4, 2);
153 return \"CH %0,=H'0'\";
154}"
155 [(set_attr "length" "4")]
156)
157
158;
159; tstqi instruction pattern(s).
160;
161
162(define_insn ""
163 [(set (cc0)
164 (match_operand:QI 0 "r_or_s_operand" "dm"))]
165 "unsigned_jump_follows_p (insn)"
166 "*
167{
168 check_label_emit ();
169 if (REG_P (operands[0]))
170 {
171 /* an unsigned compare to zero is always zero/not-zero... */
172 mvs_check_page (0, 4, 4);
173 return \"N %0,=XL4'000000FF'\";
174 }
175 mvs_check_page (0, 4, 0);
176 return \"CLI %0,0\";
177}"
178 [(set_attr "length" "4")]
179)
180
181(define_insn "tstqi"
182 [(set (cc0)
183 (match_operand:QI 0 "register_operand" "d"))]
184 ""
185 "*
186{
187 check_label_emit ();
188 if (unsigned_jump_follows_p (insn))
189 {
190 /* an unsigned compare to zero is always zero/not-zero... */
191 mvs_check_page (0, 4, 4);
192 return \"N %0,=XL4'000000FF'\";
193 }
194 mvs_check_page (0, 8, 0);
195 return \"SLL %0,24\;SRA %0,24\";
196}"
197 [(set_attr "length" "8")]
198)
199
200;
201; tstdf instruction pattern(s).
202;
203
204(define_insn "tstdf"
205 [(set (cc0)
206 (match_operand:DF 0 "general_operand" "f"))]
207 ""
208 "*
209{
210 check_label_emit ();
211 mvs_check_page (0, 2, 0);
212 return \"LTDR %0,%0\";
213}"
214 [(set_attr "length" "2")]
215)
216
217;
218; tstsf instruction pattern(s).
219;
220
221(define_insn "tstsf"
222 [(set (cc0)
223 (match_operand:SF 0 "general_operand" "f"))]
224 ""
225 "*
226{
227 check_label_emit ();
228 mvs_check_page (0, 2, 0);
229 return \"LTER %0,%0\";
230}"
231 [(set_attr "length" "2")]
232)
233
234;;
235;;- Compare instructions.
236;;
237
238;
239; cmpdi instruction pattern(s).
240;
241
242;(define_insn "cmpdi"
243; [(set (cc0)
244; (compare (match_operand:DI 0 "register_operand" "d")
245; (match_operand:DI 1 "general_operand" "")))]
246; ""
247; "*
248;{
249; check_label_emit ();
250; if (REG_P (operands[1]))
251; {
252; mvs_check_page (0, 8, 0);
253; if (unsigned_jump_follows_p (insn))
254; return \"CLR %0,%1\;BNE *+6\;CLR %N0,%N1\";
255; return \"CR %0,%1\;BNE *+6\;CLR %N0,%N1\";
256; }
257; mvs_check_page (0, 12, 0);
258; if (unsigned_jump_follows_p (insn))
259; return \"CL %0,%M1\;BNE *+8\;CL %N0,%L1\";
260; return \"C %0,%M1\;BNE *+8\;CL %N0,%L1\";
261;}")
262
263;
264; cmpsi instruction pattern(s).
265;
266
267(define_insn "cmpsi"
268 [(set (cc0)
269 (compare (match_operand:SI 0 "register_operand" "d")
270 (match_operand:SI 1 "general_operand" "md")))]
271 ""
272 "*
273{
274 check_label_emit ();
275 if (REG_P (operands[1]))
276 {
277 mvs_check_page (0, 2, 0);
278 if (unsigned_jump_follows_p (insn))
279 return \"CLR %0,%1\";
280 return \"CR %0,%1\";
281 }
282 if (GET_CODE (operands[1]) == CONST_INT)
283 {
284 mvs_check_page (0, 4, 4);
285 if (unsigned_jump_follows_p (insn))
286 return \"CL %0,=F'%c1'\";
287 return \"C %0,=F'%c1'\";
288 }
289 mvs_check_page (0, 4, 0);
290 if (unsigned_jump_follows_p (insn))
291 return \"CL %0,%1\";
292 return \"C %0,%1\";
293}"
294 [(set_attr "length" "4")]
295)
296
297;
298; cmphi instruction pattern(s).
299;
300
301; deprecate constraint d because it takes multiple instructions
302; and a memeory access ...
303(define_insn "cmphi"
304 [(set (cc0)
305 (compare (match_operand:HI 0 "register_operand" "d")
306 (match_operand:HI 1 "general_operand" "???dim")))]
307 ""
308 "*
309{
310 check_label_emit ();
311 if (REG_P (operands[1]))
312 {
313 mvs_check_page (0, 8, 0);
314 if (unsigned_jump_follows_p (insn))
315 return \"STH %1,140(,13)\;CLM %0,3,140(13)\";
316 return \"STH %1,140(,13)\;CH %0,140(,13)\";
317 }
318 if (GET_CODE (operands[1]) == CONST_INT)
319 {
320 mvs_check_page (0, 4, 0);
321 return \"CH %0,%H1\";
322 }
323 mvs_check_page (0, 4, 0);
324 return \"CH %0,%1\";
325}"
326 [(set_attr "length" "8")]
327)
328
329;
330; cmpqi instruction pattern(s).
331;
332
333(define_insn ""
334 [(set (cc0)
335 (compare (match_operand:QI 0 "r_or_s_operand" "dS")
336 (match_operand:QI 1 "r_or_s_operand" "diS")))]
337 "unsigned_jump_follows_p (insn)"
338 "*
339{
340 check_label_emit ();
341 if (REG_P (operands[0]))
342 {
343 if (REG_P (operands[1]))
344 {
345 mvs_check_page (0, 8, 0);
346 return \"STC %1,140(,13)\;CLM %0,1,140(13)\";
347 }
348 if (GET_CODE (operands[1]) == CONST_INT)
349 {
350 mvs_check_page (0, 4, 1);
351 return \"CLM %0,1,=XL1'%X1'\";
352 }
353 mvs_check_page (0, 4, 0);
354 return \"CLM %0,1,%1\";
355 }
356 else if (GET_CODE (operands[0]) == CONST_INT)
357 {
358 cc_status.flags |= CC_REVERSED;
359 if (REG_P (operands[1]))
360 {
361 mvs_check_page (0, 4, 1);
362 return \"CLM %1,1,=XL1'%X0'\";
363 }
364 mvs_check_page (0, 4, 0);
365 return \"CLI %1,%B0\";
366 }
367 if (GET_CODE (operands[1]) == CONST_INT)
368 {
369 mvs_check_page (0, 4, 0);
370 return \"CLI %0,%B1\";
371 }
372 if (GET_CODE (operands[1]) == MEM)
373 {
374 mvs_check_page (0, 6, 0);
375 return \"CLC %O0(1,%R0),%1\";
376 }
377 cc_status.flags |= CC_REVERSED;
378 mvs_check_page (0, 4, 0);
379 return \"CLM %1,1,%0\";
380}"
381 [(set_attr "length" "8")]
382)
383
384(define_insn "cmpqi"
385 [(set (cc0)
386 (compare (match_operand:QI 0 "register_operand" "d")
387 (match_operand:QI 1 "general_operand" "di")))]
388 ""
389 "*
390{
391 check_label_emit ();
392 if (unsigned_jump_follows_p (insn))
393 {
394 if (GET_CODE (operands[1]) == CONST_INT)
395 {
396 mvs_check_page (0, 4, 1);
397 return \"CLM %0,1,=XL1'%X1'\";
398 }
399 if (!(REG_P (operands[1])))
400 {
401 mvs_check_page (0, 4, 0);
402 return \"CLM %0,1,%1\";
403 }
404 mvs_check_page (0, 8, 0);
405 return \"STC %1,140(,13)\;CLM %0,1,140(13)\";
406 }
407 if (REG_P (operands[1]))
408 {
409 mvs_check_page (0, 18, 0);
410 return \"SLL %0,24\;SRA %0,24\;SLL %1,24\;SRA %1,24\;CR %0,%1\";
411 }
412 mvs_check_page (0, 12, 0);
413 return \"SLL %0,24\;SRA %0,24\;C %0,%1\";
414}"
415 [(set_attr "length" "18")]
416)
417
418;
419; cmpdf instruction pattern(s).
420;
421
422(define_insn "cmpdf"
423 [(set (cc0)
424 (compare (match_operand:DF 0 "general_operand" "f,mF")
425 (match_operand:DF 1 "general_operand" "fmF,f")))]
426 ""
427 "*
428{
429 check_label_emit ();
430 if (FP_REG_P (operands[0]))
431 {
432 if (FP_REG_P (operands[1]))
433 {
434 mvs_check_page (0, 2, 0);
435 return \"CDR %0,%1\";
436 }
437 mvs_check_page (0, 4, 0);
438 return \"CD %0,%1\";
439 }
440 cc_status.flags |= CC_REVERSED;
441 mvs_check_page (0, 4, 0);
442 return \"CD %1,%0\";
443}"
444 [(set_attr "length" "4")]
445)
446
447;
448; cmpsf instruction pattern(s).
449;
450
451(define_insn "cmpsf"
452 [(set (cc0)
453 (compare (match_operand:SF 0 "general_operand" "f,mF")
454 (match_operand:SF 1 "general_operand" "fmF,f")))]
455 ""
456 "*
457{
458check_label_emit ();
459 if (FP_REG_P (operands[0]))
460 {
461 if (FP_REG_P (operands[1]))
462 {
463 mvs_check_page (0, 2, 0);
464 return \"CER %0,%1\";
465 }
466 mvs_check_page (0, 4, 0);
467 return \"CE %0,%1\";
468 }
469 cc_status.flags |= CC_REVERSED;
470 mvs_check_page (0, 4, 0);
471 return \"CE %1,%0\";
472}"
473 [(set_attr "length" "4")]
474)
475
476;
477; cmpmemsi instruction pattern(s).
478;
479
480(define_expand "cmpmemsi"
481 [(set (match_operand:SI 0 "general_operand" "")
482 (compare (match_operand:BLK 1 "general_operand" "")
483 (match_operand:BLK 2 "general_operand" "")))
484 (use (match_operand:SI 3 "general_operand" ""))
485 (use (match_operand:SI 4 "" ""))]
486 ""
487 "
488{
489 rtx op1, op2;
490
491 op1 = XEXP (operands[1], 0);
492 if (GET_CODE (op1) == REG
493 || (GET_CODE (op1) == PLUS && GET_CODE (XEXP (op1, 0)) == REG
494 && GET_CODE (XEXP (op1, 1)) == CONST_INT
495 && (unsigned) INTVAL (XEXP (op1, 1)) < 4096))
496 {
497 op1 = operands[1];
498 }
499 else
500 {
501 op1 = gen_rtx_MEM (BLKmode, copy_to_mode_reg (SImode, op1));
502 }
503
504 op2 = XEXP (operands[2], 0);
505 if (GET_CODE (op2) == REG
506 || (GET_CODE (op2) == PLUS && GET_CODE (XEXP (op2, 0)) == REG
507 && GET_CODE (XEXP (op2, 1)) == CONST_INT
508 && (unsigned) INTVAL (XEXP (op2, 1)) < 4096))
509 {
510 op2 = operands[2];
511 }
512 else
513 {
514 op2 = gen_rtx_MEM (BLKmode, copy_to_mode_reg (SImode, op2));
515 }
516
517 if (GET_CODE (operands[3]) == CONST_INT && INTVAL (operands[3]) < 256)
518 {
519 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
520 gen_rtx_SET (VOIDmode, operands[0],
521 gen_rtx_COMPARE (VOIDmode, op1, op2)),
522 gen_rtx_USE (VOIDmode, operands[3]))));
523 }
524 else
525 {
526 /* implementation suggested by Richard Henderson <rth@cygnus.com> */
527 rtx reg1 = gen_reg_rtx (DImode);
528 rtx reg2 = gen_reg_rtx (DImode);
529 rtx result = operands[0];
530 rtx mem1 = operands[1];
531 rtx mem2 = operands[2];
532 rtx len = operands[3];
533 if (!CONSTANT_P (len))
534 len = force_reg (SImode, len);
535
536 /* Load up the address+length pairs. */
537 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg1));
538 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, 0),
539 force_operand (XEXP (mem1, 0), NULL_RTX));
540 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, GET_MODE_SIZE (SImode)), len);
541
542 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg2));
543 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, 0),
544 force_operand (XEXP (mem2, 0), NULL_RTX));
545 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, GET_MODE_SIZE (SImode)), len);
546
547 /* Compare! */
548 emit_insn (gen_cmpmemsi_1 (result, reg1, reg2));
549 }
550 DONE;
551}")
552
553; Compare a block that is less than 256 bytes in length.
554
555(define_insn ""
556 [(set (match_operand:SI 0 "register_operand" "=d")
557 (compare (match_operand:BLK 1 "s_operand" "m")
558 (match_operand:BLK 2 "s_operand" "m")))
559 (use (match_operand:QI 3 "immediate_operand" "I"))]
560 "((unsigned) INTVAL (operands[3]) < 256)"
561 "*
562{
563 check_label_emit ();
564 mvs_check_page (0, 22, 0);
565 return \"LA %0,%1\;CLC %O1(%c3,%R1),%2\;BH *+12\;BL *+6\;SLR %0,%0\;LNR %0,%0\";
566}"
567 [(set_attr "length" "22")]
568)
569
570; Compare a block that is larger than 255 bytes in length.
571
572(define_insn "cmpmemsi_1"
573 [(set (match_operand:SI 0 "register_operand" "+d")
574 (compare
575 (mem:BLK (subreg:SI (match_operand:DI 1 "register_operand" "+d") 0))
576 (mem:BLK (subreg:SI (match_operand:DI 2 "register_operand" "+d") 0))))
577 (use (match_dup 1))
578 (use (match_dup 2))
579 (clobber (match_dup 1))
580 (clobber (match_dup 2))]
581 ""
582 "*
583{
584 check_label_emit ();
585 mvs_check_page (0, 18, 0);
586 return \"LA %0,1(0,0)\;CLCL %1,%2\;BH *+12\;BL *+6\;SLR %0,%0\;LNR %0,%0\";
587}"
588 [(set_attr "length" "18")]
589)
590
591;;
592;;- Move instructions.
593;;
594
595;
596; movdi instruction pattern(s).
597;
598
599(define_insn ""
600;; [(set (match_operand:DI 0 "r_or_s_operand" "=dm")
601;; (match_operand:DI 1 "r_or_s_operand" "dim*fF"))]
602 [(set (match_operand:DI 0 "r_or_s_operand" "=dS,m")
603 (match_operand:DI 1 "r_or_s_operand" "diS*fF,d*fF"))]
604
605 "TARGET_CHAR_INSTRUCTIONS"
606 "*
607{
608 check_label_emit ();
609 if (REG_P (operands[0]))
610 {
611 if (FP_REG_P (operands[1]))
612 {
613 mvs_check_page (0, 8, 0);
614 return \"STD %1,140(,13)\;LM %0,%N0,140(13)\";
615 }
616 if (REG_P (operands[1]))
617 {
618 mvs_check_page (0, 4, 0);
619 return \"LR %0,%1\;LR %N0,%N1\";
620 }
621 if (operands[1] == const0_rtx)
622 {
623 CC_STATUS_INIT;
624 mvs_check_page (0, 4, 0);
625 return \"SLR %0,%0\;SLR %N0,%N0\";
626 }
627 if (GET_CODE (operands[1]) == CONST_INT
628 && (unsigned) INTVAL (operands[1]) < 4096)
629 {
630 CC_STATUS_INIT;
631 mvs_check_page (0, 6, 0);
632 return \"SLR %0,%0\;LA %N0,%c1(0,0)\";
633 }
634 if (GET_CODE (operands[1]) == CONST_INT)
635 {
636 CC_STATUS_SET (operands[0], operands[1]);
637 mvs_check_page (0, 8, 0);
638 return \"L %0,%1\;SRDA %0,32\";
639 }
640 mvs_check_page (0, 4, 0);
641 return \"LM %0,%N0,%1\";
642 }
643 else if (FP_REG_P (operands[1]))
644 {
645 mvs_check_page (0, 4, 0);
646 return \"STD %1,%0\";
647 }
648 else if (REG_P (operands[1]))
649 {
650 mvs_check_page (0, 4, 0);
651 return \"STM %1,%N1,%0\";
652 }
653 mvs_check_page (0, 6, 0);
654 return \"MVC %O0(8,%R0),%W1\";
655}"
656 [(set_attr "length" "8")]
657)
658
659(define_insn "movdi"
660;; [(set (match_operand:DI 0 "general_operand" "=d,dm")
661;; (match_operand:DI 1 "general_operand" "dimF,*fd"))]
662 [(set (match_operand:DI 0 "general_operand" "=d,dm")
663 (match_operand:DI 1 "r_or_s_operand" "diSF,*fd"))]
664 ""
665 "*
666{
667 check_label_emit ();
668 if (REG_P (operands[0]))
669 {
670 if (FP_REG_P (operands[1]))
671 {
672 mvs_check_page (0, 8, 0);
673 return \"STD %1,140(,13)\;LM %0,%N0,140(13)\";
674 }
675 if (REG_P (operands[1]))
676 {
677 mvs_check_page (0, 4, 0);
678 return \"LR %0,%1\;LR %N0,%N1\";
679 }
680 if (operands[1] == const0_rtx)
681 {
682 CC_STATUS_INIT;
683 mvs_check_page (0, 4, 0);
684 return \"SLR %0,%0\;SLR %N0,%N0\";
685 }
686 if (GET_CODE (operands[1]) == CONST_INT
687 && (unsigned) INTVAL (operands[1]) < 4096)
688 {
689 CC_STATUS_INIT;
690 mvs_check_page (0, 6, 0);
691 return \"SLR %0,%0\;LA %N0,%c1(0,0)\";
692 }
693 if (GET_CODE (operands[1]) == CONST_INT)
694 {
695 CC_STATUS_SET (operands[0], operands[1]);
696 mvs_check_page (0, 8, 0);
697 return \"L %0,%1\;SRDA %0,32\";
698 }
699 mvs_check_page (0, 4, 0);
700 return \"LM %0,%N0,%1\";
701 }
702 else if (FP_REG_P (operands[1]))
703 {
704 mvs_check_page (0, 4, 0);
705 return \"STD %1,%0\";
706 }
707 mvs_check_page (0, 4, 0);
708 return \"STM %1,%N1,%0\";
709}"
710 [(set_attr "length" "8")]
711)
712
713;; we have got to provide a movdi alternative that will go from
714;; register to memory & back in its full glory. However, we try to
715;; discourage its use by listing this alternative last.
716;; The problem is that the instructions above only provide
717;; S-form style (base + displacement) mem access, while the
718;; below provvides the full (base+index+displacement) RX-form.
719;; These are rarely needed, but when needed they're needed.
720
721(define_insn ""
722 [(set (match_operand:DI 0 "general_operand" "=d,???m")
723 (match_operand:DI 1 "general_operand" "???m,d"))]
724
725 ""
726 "*
727{
728 check_label_emit ();
729 if (REG_P (operands[0]))
730 {
731 mvs_check_page (0, 8, 0);
732 return \"LM %0,%N0,%1\";
733 }
734 else if (REG_P (operands[1]))
735 {
736 mvs_check_page (0, 8, 0);
737 return \"STM %1,%N1,%0\";
738 }
739 mvs_check_page (0, 6, 0);
740 return \"MVC %O0(8,%R0),%1\";
741}"
742 [(set_attr "length" "8")]
743)
744
745;
746; movsi instruction pattern(s).
747;
748
749(define_insn ""
750;; [(set (match_operand:SI 0 "r_or_s_operand" "=dm,d,dm")
751;; (match_operand:SI 1 "r_or_s_operand" "diR,dim,*fF"))]
752 [(set (match_operand:SI 0 "r_or_s_operand" "=d,dS,dm")
753 (match_operand:SI 1 "general_operand" "dim,diS,di*fF"))]
754
755 "TARGET_CHAR_INSTRUCTIONS"
756 "*
757{
758 check_label_emit ();
759 if (REG_P (operands[0]))
760 {
761 if (FP_REG_P (operands[1]))
762 {
763 mvs_check_page (0, 8, 0);
764 return \"STE %1,140(,13)\;L %0,140(,13)\";
765 }
766 if (REG_P (operands[1]))
767 {
768 mvs_check_page (0, 2, 0);
769 return \"LR %0,%1\";
770 }
771 if (operands[1] == const0_rtx)
772 {
773 CC_STATUS_INIT;
774 mvs_check_page (0, 2, 0);
775 return \"SLR %0,%0\";
776 }
777 if (GET_CODE (operands[1]) == CONST_INT
778 && (unsigned) INTVAL (operands[1]) < 4096)
779 {
780 mvs_check_page (0, 4, 0);
781 return \"LA %0,%c1(0,0)\";
782 }
783 mvs_check_page (0, 4, 0);
784 return \"L %0,%1\";
785 }
786 else if (FP_REG_P (operands[1]))
787 {
788 mvs_check_page (0, 4, 0);
789 return \"STE %1,%0\";
790 }
791 else if (REG_P (operands[1]))
792 {
793 mvs_check_page (0, 4, 0);
794 return \"ST %1,%0\";
795 }
796 mvs_check_page (0, 6, 0);
797 return \"MVC %O0(4,%R0),%1\";
798}"
799 [(set_attr "length" "8")]
800)
801
802(define_insn "movsi"
803 [(set (match_operand:SI 0 "general_operand" "=d,dm")
804 (match_operand:SI 1 "general_operand" "dimF,*fd"))]
805 ""
806 "*
807{
808 check_label_emit ();
809 if (REG_P (operands[0]))
810 {
811 if (FP_REG_P (operands[1]))
812 {
813 mvs_check_page (0, 8, 0);
814 return \"STE %1,140(,13)\;L %0,140(,13)\";
815 }
816 if (REG_P (operands[1]))
817 {
818 mvs_check_page (0, 2, 0);
819 return \"LR %0,%1\";
820 }
821 if (operands[1] == const0_rtx)
822 {
823 CC_STATUS_INIT;
824 mvs_check_page (0, 2, 0);
825 return \"SLR %0,%0\";
826 }
827 if (GET_CODE (operands[1]) == CONST_INT
828 && (unsigned) INTVAL (operands[1]) < 4096)
829 {
830 mvs_check_page (0, 4, 0);
831 return \"LA %0,%c1(0,0)\";
832 }
833 mvs_check_page (0, 4, 0);
834 return \"L %0,%1\";
835 }
836 else if (FP_REG_P (operands[1]))
837 {
838 mvs_check_page (0, 4, 0);
839 return \"STE %1,%0\";
840 }
841 mvs_check_page (0, 4, 0);
842 return \"ST %1,%0\";
843}"
844 [(set_attr "length" "8")]
845)
846
847;(define_expand "movsi"
848; [(set (match_operand:SI 0 "general_operand" "=d,dm")
849; (match_operand:SI 1 "general_operand" "dimF,*fd"))]
850; ""
851; "
852;{
853; rtx op0, op1;
854;
855; op0 = operands[0];
856; if (GET_CODE (op0) == CONST
857; && GET_CODE (XEXP (XEXP (op0, 0), 0)) == SYMBOL_REF
858; && SYMBOL_REF_EXTERNAL_P (XEXP (XEXP (op0, 0), 0)))
859; {
860; op0 = gen_rtx_MEM (SImode, copy_to_mode_reg (SImode, XEXP (op0, 0)));
861; }
862;
863; op1 = operands[1];
864; if (GET_CODE (op1) == CONST
865; && GET_CODE (XEXP (XEXP (op1, 0), 0)) == SYMBOL_REF
866; && SYMBOL_REF_EXTERNAL_P (XEXP (XEXP (op1, 0), 0)))
867; {
868; op1 = gen_rtx_MEM (SImode, copy_to_mode_reg (SImode, XEXP (op1, 0)));
869; }
870;
871; emit_insn (gen_rtx_SET (VOIDmode, op0, op1));
872; DONE;
873;}")
874
875;
876; movhi instruction pattern(s).
877;
878
879(define_insn ""
880 [(set (match_operand:HI 0 "r_or_s_operand" "=g")
881 (match_operand:HI 1 "r_or_s_operand" "g"))]
882 "TARGET_CHAR_INSTRUCTIONS"
883 "*
884{
885 check_label_emit ();
886 if (REG_P (operands[0]))
887 {
888 if (REG_P (operands[1]))
889 {
890 mvs_check_page (0, 2, 0);
891 return \"LR %0,%1\";
892 }
893 if (operands[1] == const0_rtx)
894 {
895 CC_STATUS_INIT;
896 mvs_check_page (0, 2, 0);
897 return \"SLR %0,%0\";
898 }
899 if (GET_CODE (operands[1]) == CONST_INT
900 && (unsigned) INTVAL (operands[1]) < 4096)
901 {
902 mvs_check_page (0, 4, 0);
903 return \"LA %0,%c1(0,0)\";
904 }
905 if (GET_CODE (operands[1]) == CONST_INT)
906 {
907 mvs_check_page (0, 4, 0);
908 return \"LH %0,%H1\";
909 }
910 mvs_check_page (0, 4, 0);
911 return \"LH %0,%1\";
912 }
913 else if (REG_P (operands[1]))
914 {
915 mvs_check_page (0, 4, 0);
916 return \"STH %1,%0\";
917 }
918 if (GET_CODE (operands[1]) == CONST_INT)
919 {
920 mvs_check_page (0, 6, 0);
921 return \"MVC %O0(2,%R0),%H1\";
922 }
923 mvs_check_page (0, 6, 0);
924 return \"MVC %O0(2,%R0),%1\";
925}"
926 [(set_attr "length" "6")]
927)
928
929(define_insn "movhi"
930 [(set (match_operand:HI 0 "general_operand" "=d,m")
931 (match_operand:HI 1 "general_operand" "g,d"))]
932 ""
933 "*
934{
935 check_label_emit ();
936 if (REG_P (operands[0]))
937 {
938 if (REG_P (operands[1]))
939 {
940 mvs_check_page (0, 2, 0);
941 return \"LR %0,%1\";
942 }
943 if (operands[1] == const0_rtx)
944 {
945 CC_STATUS_INIT;
946 mvs_check_page (0, 2, 0);
947 return \"SLR %0,%0\";
948 }
949 if (GET_CODE (operands[1]) == CONST_INT
950 && (unsigned) INTVAL (operands[1]) < 4096)
951 {
952 mvs_check_page (0, 4, 0);
953 return \"LA %0,%c1(0,0)\";
954 }
955 if (GET_CODE (operands[1]) == CONST_INT)
956 {
957 mvs_check_page (0, 4, 0);
958 return \"LH %0,%H1\";
959 }
960 mvs_check_page (0, 4, 0);
961 return \"LH %0,%1\";
962 }
963 mvs_check_page (0, 4, 0);
964 return \"STH %1,%0\";
965}"
966 [(set_attr "length" "4")]
967)
968
969;
970; movqi instruction pattern(s).
971;
972
973(define_insn ""
974 [(set (match_operand:QI 0 "r_or_s_operand" "=g")
975 (match_operand:QI 1 "r_or_s_operand" "g"))]
976 "TARGET_CHAR_INSTRUCTIONS"
977 "*
978{
979 check_label_emit ();
980 if (REG_P (operands[0]))
981 {
982 if (REG_P (operands[1]))
983 {
984 mvs_check_page (0, 2, 0);
985 return \"LR %0,%1\";
986 }
987 if (operands[1] == const0_rtx)
988 {
989 CC_STATUS_INIT;
990 mvs_check_page (0, 2, 0);
991 return \"SLR %0,%0\";
992 }
993 if (GET_CODE (operands[1]) == CONST_INT)
994 {
995 if ((INTVAL (operands[1]) >= 0)
996 && (unsigned) INTVAL (operands[1]) < 4096)
997 {
998 mvs_check_page (0, 4, 0);
999 return \"LA %0,%c1(0,0)\";
1000 }
1001 mvs_check_page (0, 4, 0);
1002 return \"L %0,=F'%c1'\";
1003 }
1004 mvs_check_page (0, 4, 0);
1005 return \"IC %0,%1\";
1006 }
1007 else if (REG_P (operands[1]))
1008 {
1009 mvs_check_page (0, 4, 0);
1010 return \"STC %1,%0\";
1011 }
1012 else if (GET_CODE (operands[1]) == CONST_INT)
1013 {
1014 mvs_check_page (0, 4, 0);
1015 return \"MVI %0,%B1\";
1016 }
1017 mvs_check_page (0, 6, 0);
1018 return \"MVC %O0(1,%R0),%1\";
1019}"
1020 [(set_attr "length" "6")]
1021)
1022
1023(define_insn "movqi"
1024 [(set (match_operand:QI 0 "general_operand" "=d,m")
1025 (match_operand:QI 1 "general_operand" "g,d"))]
1026 ""
1027 "*
1028{
1029 check_label_emit ();
1030 if (REG_P (operands[0]))
1031 {
1032 if (REG_P (operands[1]))
1033 {
1034 mvs_check_page (0, 2, 0);
1035 return \"LR %0,%1\";
1036 }
1037 if (operands[1] == const0_rtx)
1038 {
1039 CC_STATUS_INIT;
1040 mvs_check_page (0, 2, 0);
1041 return \"SLR %0,%0\";
1042 }
1043 if (GET_CODE (operands[1]) == CONST_INT)
1044 {
1045 if ((INTVAL (operands[1]) >= 0)
1046 && (unsigned) INTVAL (operands[1]) < 4096)
1047 {
1048 mvs_check_page (0, 4, 0);
1049 return \"LA %0,%c1(0,0)\";
1050 }
1051 mvs_check_page (0, 4, 0);
1052 return \"L %0,=F'%c1'\";
1053 }
1054 mvs_check_page (0, 4, 0);
1055 return \"IC %0,%1\";
1056 }
1057 mvs_check_page (0, 4, 0);
1058 return \"STC %1,%0\";
1059}"
1060 [(set_attr "length" "4")]
1061)
1062
1063;
1064; movstrictqi instruction pattern(s).
1065;
1066
1067(define_insn "movstrictqi"
1068 [(set (strict_low_part (match_operand:QI 0 "general_operand" "+d"))
1069 (match_operand:QI 1 "general_operand" "g"))]
1070 ""
1071 "*
1072{
1073 check_label_emit ();
1074 if (REG_P (operands[1]))
1075 {
1076 mvs_check_page (0, 8, 0);
1077 return \"STC %1,140(,13)\;IC %0,140(,13)\";
1078 }
1079 mvs_check_page (0, 4, 0);
1080 return \"IC %0,%1\";
1081}"
1082 [(set_attr "length" "8")]
1083)
1084
1085;
1086; movstricthi instruction pattern(s).
1087;
1088
1089(define_insn ""
1090 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+d"))
1091 (match_operand:HI 1 "r_or_s_operand" "g"))]
1092 ""
1093 "*
1094{
1095 check_label_emit ();
1096 if (REG_P (operands[1]))
1097 {
1098 mvs_check_page (0, 8, 0);
1099 return \"STH %1,140(,13)\;ICM %0,3,140(13)\";
1100 }
1101 else if (GET_CODE (operands[1]) == CONST_INT)
1102 {
1103 mvs_check_page (0, 4, 0);
1104 return \"ICM %0,3,%H1\";
1105 }
1106 mvs_check_page (0, 4, 0);
1107 return \"ICM %0,3,%1\";
1108}"
1109 [(set_attr "length" "8")]
1110)
1111
1112(define_insn "movstricthi"
1113 [(set (strict_low_part (match_operand:HI 0 "general_operand" "+dm"))
1114 (match_operand:HI 1 "general_operand" "d"))]
1115 ""
1116 "*
1117{
1118 check_label_emit ();
1119 if (REG_P (operands[0]))
1120 {
1121 mvs_check_page (0, 8, 0);
1122 return \"STH %1,140(,13)\;ICM %0,3,140(13)\";
1123 }
1124 mvs_check_page (0, 4, 0);
1125 return \"STH %1,%0\";
1126}"
1127 [(set_attr "length" "8")]
1128)
1129
1130;
1131; movdf instruction pattern(s).
1132;
1133
1134(define_insn ""
1135;; [(set (match_operand:DF 0 "r_or_s_operand" "=fm,fm,*dm")
1136;; (match_operand:DF 1 "r_or_s_operand" "fmF,*dm,fmF"))]
1137 [(set (match_operand:DF 0 "general_operand" "=f,m,fS,*dS,???d")
1138 (match_operand:DF 1 "general_operand" "fmF,fF,*dS,fSF,???d"))]
1139
1140 "TARGET_CHAR_INSTRUCTIONS"
1141 "*
1142{
1143 check_label_emit ();
1144 if (FP_REG_P (operands[0]))
1145 {
1146 if (FP_REG_P (operands[1]))
1147 {
1148 mvs_check_page (0, 2, 0);
1149 return \"LDR %0,%1\";
1150 }
1151 if (REG_P (operands[1]))
1152 {
1153 mvs_check_page (0, 8, 0);
1154 return \"STM %1,%N1,140(13)\;LD %0,140(,13)\";
1155 }
1156 if (operands[1] == const0_rtx)
1157 {
1158 CC_STATUS_SET (operands[0], operands[1]);
1159 mvs_check_page (0, 2, 0);
1160 return \"SDR %0,%0\";
1161 }
1162 mvs_check_page (0, 4, 0);
1163 return \"LD %0,%1\";
1164 }
1165 if (REG_P (operands[0]))
1166 {
1167 if (FP_REG_P (operands[1]))
1168 {
1169 mvs_check_page (0, 12, 0);
1170 return \"STD %1,140(,13)\;LM %0,%N0,140(13)\";
1171 }
1172 if (REG_P (operands[1]))
1173 {
1174 mvs_check_page (0, 4, 0);
1175 return \"LR %0,%1\;LR %N0,%N1\";
1176 }
1177 mvs_check_page (0, 4, 0);
1178 return \"LM %0,%N0,%1\";
1179 }
1180 else if (FP_REG_P (operands[1]))
1181 {
1182 mvs_check_page (0, 4, 0);
1183 return \"STD %1,%0\";
1184 }
1185 else if (REG_P (operands[1]))
1186 {
1187 mvs_check_page (0, 4, 0);
1188 return \"STM %1,%N1,%0\";
1189 }
1190 mvs_check_page (0, 6, 0);
1191 return \"MVC %O0(8,%R0),%1\";
1192}"
1193 [(set_attr "length" "12")]
1194)
1195
1196(define_insn "movdf"
1197;; [(set (match_operand:DF 0 "general_operand" "=f,fm,m,*d")
1198;; (match_operand:DF 1 "general_operand" "fmF,*d,f,fmF"))]
1199 [(set (match_operand:DF 0 "general_operand" "=f,m,fS,*d,???d")
1200 (match_operand:DF 1 "general_operand" "fmF,f,*d,SfF,???d"))]
1201
1202 ""
1203 "*
1204{
1205 check_label_emit ();
1206 if (FP_REG_P (operands[0]))
1207 {
1208 if (FP_REG_P (operands[1]))
1209 {
1210 mvs_check_page (0, 2, 0);
1211 return \"LDR %0,%1\";
1212 }
1213 if (REG_P (operands[1]))
1214 {
1215 mvs_check_page (0, 8, 0);
1216 return \"STM %1,%N1,140(13)\;LD %0,140(,13)\";
1217 }
1218 if (operands[1] == const0_rtx)
1219 {
1220 CC_STATUS_SET (operands[0], operands[1]);
1221 mvs_check_page (0, 2, 0);
1222 return \"SDR %0,%0\";
1223 }
1224 mvs_check_page (0, 4, 0);
1225 return \"LD %0,%1\";
1226 }
1227 else if (REG_P (operands[0]))
1228 {
1229 if (FP_REG_P (operands[1]))
1230 {
1231 mvs_check_page (0, 12, 0);
1232 return \"STD %1,140(,13)\;LM %0,%N0,140(13)\";
1233 }
1234 if (REG_P (operands[1]))
1235 {
1236 mvs_check_page (0, 4, 0);
1237 return \"LR %0,%1\;LR %N0,%N1\";
1238 }
1239 mvs_check_page (0, 4, 0);
1240 return \"LM %0,%N0,%1\";
1241 }
1242 else if (FP_REG_P (operands[1]))
1243 {
1244 mvs_check_page (0, 4, 0);
1245 return \"STD %1,%0\";
1246 }
1247 mvs_check_page (0, 4, 0);
1248 return \"STM %1,%N1,%0\";
1249}"
1250 [(set_attr "length" "12")]
1251)
1252
1253;
1254; movsf instruction pattern(s).
1255;
1256
1257(define_insn ""
1258;; [(set (match_operand:SF 0 "r_or_s_operand" "=fm,fm,*dm")
1259;; (match_operand:SF 1 "r_or_s_operand" "fmF,*dm,fmF"))]
1260;; [(set (match_operand:SF 0 "general_operand" "=f,m,fm,*d,S")
1261;; (match_operand:SF 1 "general_operand" "fmF,fF,*d,fmF,S"))]
1262 [(set (match_operand:SF 0 "general_operand" "=f*d,fm,S,???d")
1263 (match_operand:SF 1 "general_operand" "fmF,fF*d,S,???d"))]
1264
1265 "TARGET_CHAR_INSTRUCTIONS"
1266 "*
1267{
1268 check_label_emit ();
1269 if (FP_REG_P (operands[0]))
1270 {
1271 if (FP_REG_P (operands[1]))
1272 {
1273 mvs_check_page (0, 2, 0);
1274 return \"LER %0,%1\";
1275 }
1276 if (REG_P (operands[1]))
1277 {
1278 mvs_check_page (0, 8, 0);
1279 return \"ST %1,140(,13)\;LE %0,140(,13)\";
1280 }
1281 if (operands[1] == const0_rtx)
1282 {
1283 CC_STATUS_SET (operands[0], operands[1]);
1284 mvs_check_page (0, 2, 0);
1285 return \"SER %0,%0\";
1286 }
1287 mvs_check_page (0, 4, 0);
1288 return \"LE %0,%1\";
1289 }
1290 else if (REG_P (operands[0]))
1291 {
1292 if (FP_REG_P (operands[1]))
1293 {
1294 mvs_check_page (0, 8, 0);
1295 return \"STE %1,140(,13)\;L %0,140(,13)\";
1296 }
1297 if (REG_P (operands[1]))
1298 {
1299 mvs_check_page (0, 2, 0);
1300 return \"LR %0,%1\";
1301 }
1302 mvs_check_page (0, 4, 0);
1303 return \"L %0,%1\";
1304 }
1305 else if (FP_REG_P (operands[1]))
1306 {
1307 mvs_check_page (0, 4, 0);
1308 return \"STE %1,%0\";
1309 }
1310 else if (REG_P (operands[1]))
1311 {
1312 mvs_check_page (0, 4, 0);
1313 return \"ST %1,%0\";
1314 }
1315 mvs_check_page (0, 6, 0);
1316 return \"MVC %O0(4,%R0),%1\";
1317}"
1318 [(set_attr "length" "8")]
1319)
1320
1321(define_insn "movsf"
1322 [(set (match_operand:SF 0 "general_operand" "=f,fm,m,*d")
1323 (match_operand:SF 1 "general_operand" "fmF,*d,f,fmF"))]
1324 ""
1325 "*
1326{
1327 check_label_emit ();
1328 if (FP_REG_P (operands[0]))
1329 {
1330 if (FP_REG_P (operands[1]))
1331 {
1332 mvs_check_page (0, 2, 0);
1333 return \"LER %0,%1\";
1334 }
1335 if (REG_P (operands[1]))
1336 {
1337 mvs_check_page (0, 8, 0);
1338 return \"ST %1,140(,13)\;LE %0,140(,13)\";
1339 }
1340 if (operands[1] == const0_rtx)
1341 {
1342 CC_STATUS_SET (operands[0], operands[1]);
1343 mvs_check_page (0, 2, 0);
1344 return \"SER %0,%0\";
1345 }
1346 mvs_check_page (0, 4, 0);
1347 return \"LE %0,%1\";
1348 }
1349 else if (REG_P (operands[0]))
1350 {
1351 if (FP_REG_P (operands[1]))
1352 {
1353 mvs_check_page (0, 8, 0);
1354 return \"STE %1,140(,13)\;L %0,140(,13)\";
1355 }
1356 mvs_check_page (0, 4, 0);
1357 return \"L %0,%1\";
1358 }
1359 else if (FP_REG_P (operands[1]))
1360 {
1361 mvs_check_page (0, 4, 0);
1362 return \"STE %1,%0\";
1363 }
1364 mvs_check_page (0, 4, 0);
1365 return \"ST %1,%0\";
1366}"
1367 [(set_attr "length" "8")]
1368)
1369
1370;
1371; clrstrsi instruction pattern(s).
1372; memset a block of bytes to zero.
1373; block must be less than 16M (24 bits) in length
1374;
1375(define_expand "clrstrsi"
1376 [(set (match_operand:BLK 0 "general_operand" "g")
1377 (const_int 0))
1378 (use (match_operand:SI 1 "general_operand" ""))
1379 (match_operand 2 "" "")]
1380 ""
1381 "
1382{
1383 {
1384 /* implementation suggested by Richard Henderson <rth@cygnus.com> */
1385 rtx reg1 = gen_reg_rtx (DImode);
1386 rtx reg2 = gen_reg_rtx (DImode);
1387 rtx mem1 = operands[0];
1388 rtx zippo = gen_rtx_CONST_INT (SImode, 0);
1389 rtx len = operands[1];
1390 if (!CONSTANT_P (len))
1391 len = force_reg (SImode, len);
1392
1393 /* Load up the address+length pairs. */
1394 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg1));
1395 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, 0),
1396 force_operand (XEXP (mem1, 0), NULL_RTX));
1397 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, GET_MODE_SIZE (SImode)), len);
1398
1399 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg2));
1400 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, 0), zippo);
1401 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, GET_MODE_SIZE (SImode)), zippo);
1402
1403 /* Copy! */
1404 emit_insn (gen_movstrsi_1 (reg1, reg2));
1405 }
1406 DONE;
1407}")
1408
1409;
1410; movstrsi instruction pattern(s).
1411; block must be less than 16M (24 bits) in length
1412
1413(define_expand "movstrsi"
1414 [(set (match_operand:BLK 0 "general_operand" "")
1415 (match_operand:BLK 1 "general_operand" ""))
1416 (use (match_operand:SI 2 "general_operand" ""))
1417 (match_operand 3 "" "")]
1418 ""
1419 "
1420{
1421 rtx op0, op1;
1422
1423 op0 = XEXP (operands[0], 0);
1424 if (GET_CODE (op0) == REG
1425 || (GET_CODE (op0) == PLUS && GET_CODE (XEXP (op0, 0)) == REG
1426 && GET_CODE (XEXP (op0, 1)) == CONST_INT
1427 && (unsigned) INTVAL (XEXP (op0, 1)) < 4096))
1428 op0 = operands[0];
1429 else
1430 op0 = replace_equiv_address (operands[0], copy_to_mode_reg (SImode, op0));
1431
1432 op1 = XEXP (operands[1], 0);
1433 if (GET_CODE (op1) == REG
1434 || (GET_CODE (op1) == PLUS && GET_CODE (XEXP (op1, 0)) == REG
1435 && GET_CODE (XEXP (op1, 1)) == CONST_INT
1436 && (unsigned) INTVAL (XEXP (op1, 1)) < 4096))
1437 op1 = operands[1];
1438 else
1439 op1 = replace_equiv_address (operands[1], copy_to_mode_reg (SImode, op1));
1440
1441 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 256)
1442 emit_insn (gen_rtx_PARALLEL (VOIDmode,
1443 gen_rtvec (2,
1444 gen_rtx_SET (VOIDmode, op0, op1),
1445 gen_rtx_USE (VOIDmode, operands[2]))));
1446
1447 else
1448 {
1449 /* implementation provided by Richard Henderson <rth@cygnus.com> */
1450 rtx reg1 = gen_reg_rtx (DImode);
1451 rtx reg2 = gen_reg_rtx (DImode);
1452 rtx mem1 = operands[0];
1453 rtx mem2 = operands[1];
1454 rtx len = operands[2];
1455 if (!CONSTANT_P (len))
1456 len = force_reg (SImode, len);
1457
1458 /* Load up the address+length pairs. */
1459 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg1));
1460 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, 0),
1461 force_operand (XEXP (mem1, 0), NULL_RTX));
1462 emit_move_insn (gen_rtx_SUBREG (SImode, reg1, GET_MODE_SIZE (SImode)), len);
1463
1464 emit_insn (gen_rtx_CLOBBER (VOIDmode, reg2));
1465 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, 0),
1466 force_operand (XEXP (mem2, 0), NULL_RTX));
1467 emit_move_insn (gen_rtx_SUBREG (SImode, reg2, GET_MODE_SIZE (SImode)), len);
1468
1469 /* Copy! */
1470 emit_insn (gen_movstrsi_1 (reg1, reg2));
1471 }
1472 DONE;
1473}")
1474
1475; Move a block that is less than 256 bytes in length.
1476
1477(define_insn ""
1478 [(set (match_operand:BLK 0 "s_operand" "=m")
1479 (match_operand:BLK 1 "s_operand" "m"))
1480 (use (match_operand 2 "immediate_operand" "I"))]
1481 "((unsigned) INTVAL (operands[2]) < 256)"
1482 "*
1483{
1484 check_label_emit ();
1485 mvs_check_page (0, 6, 0);
1486 return \"MVC %O0(%c2,%R0),%1\";
1487}"
1488 [(set_attr "length" "6")]
1489)
1490
1491; Move a block that is larger than 255 bytes in length.
1492
1493(define_insn "movstrsi_1"
1494 [(set (mem:BLK (subreg:SI (match_operand:DI 0 "register_operand" "+d") 0))
1495 (mem:BLK (subreg:SI (match_operand:DI 1 "register_operand" "+d") 0)))
1496 (use (match_dup 0))
1497 (use (match_dup 1))
1498 (clobber (match_dup 0))
1499 (clobber (match_dup 1))]
1500 ""
1501 "*
1502{
1503 check_label_emit ();
1504 mvs_check_page (0, 2, 0);
1505 return \"MVCL %0,%1\";
1506}"
1507 [(set_attr "length" "2")]
1508)
1509
1510;;
1511;;- Conversion instructions.
1512;;
1513
1514;
1515; extendsidi2 instruction pattern(s).
1516;
1517
1518(define_expand "extendsidi2"
1519 [(set (match_operand:DI 0 "register_operand" "=d")
1520 (sign_extend:DI (match_operand:SI 1 "general_operand" "")))]
1521 ""
1522 "
1523{
1524 if (GET_CODE (operands[1]) != CONST_INT)
1525 {
1526 emit_insn (gen_rtx_SET (VOIDmode,
1527 operand_subword (operands[0], 0, 1, DImode), operands[1]));
1528 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
1529 gen_rtx_ASHIFTRT (DImode, operands[0],
1530 gen_rtx_CONST_INT (SImode, 32))));
1531 }
1532 else
1533 {
1534 if (INTVAL (operands[1]) < 0)
1535 {
1536 emit_insn (gen_rtx_SET (VOIDmode,
1537 operand_subword (operands[0], 0, 1, DImode),
1538 gen_rtx_CONST_INT (SImode, -1)));
1539 }
1540 else
1541 {
1542 emit_insn (gen_rtx_SET (VOIDmode,
1543 operand_subword (operands[0], 0, 1, DImode),
1544 gen_rtx_CONST_INT (SImode, 0)));
1545 }
1546 emit_insn (gen_rtx_SET (VOIDmode, gen_lowpart (SImode, operands[0]),
1547 operands[1]));
1548 }
1549 DONE;
1550}")
1551
1552;
1553; extendhisi2 instruction pattern(s).
1554;
1555
1556(define_insn "extendhisi2"
1557 [(set (match_operand:SI 0 "general_operand" "=d,m")
1558 (sign_extend:SI (match_operand:HI 1 "general_operand" "g,d")))]
1559 ""
1560 "*
1561{
1562 check_label_emit ();
1563 if (REG_P (operands[0]))
1564 {
1565 if (REG_P (operands[1]))
1566 {
1567 if (REGNO (operands[0]) != REGNO (operands[1]))
1568 {
1569 mvs_check_page (0, 10, 0);
1570 return \"LR %0,%1\;SLL %0,16\;SRA %0,16\";
1571 }
1572 else
1573 return \"\"; /* Should be empty. 16-bits regs are always 32-bits. */
1574 }
1575 if (operands[1] == const0_rtx)
1576 {
1577 CC_STATUS_INIT;
1578 mvs_check_page (0, 2, 0);
1579 return \"SLR %0,%0\";
1580 }
1581 if (GET_CODE (operands[1]) == CONST_INT
1582 && (unsigned) INTVAL (operands[1]) < 4096)
1583 {
1584 mvs_check_page (0, 4, 0);
1585 return \"LA %0,%c1(0,0)\";
1586 }
1587 if (GET_CODE (operands[1]) == CONST_INT)
1588 {
1589 mvs_check_page (0, 4, 0);
1590 return \"LH %0,%H1\";
1591 }
1592 mvs_check_page (0, 4, 0);
1593 return \"LH %0,%1\";
1594 }
1595 mvs_check_page (0, 12, 0);
1596 return \"SLL %1,16\;SRA %1,16\;ST %1,%0\";
1597}"
1598 [(set_attr "length" "12")]
1599)
1600
1601;
1602; extendqisi2 instruction pattern(s).
1603;
1604
1605(define_insn "extendqisi2"
1606 [(set (match_operand:SI 0 "general_operand" "=d")
1607 (sign_extend:SI (match_operand:QI 1 "general_operand" "0mi")))]
1608 ""
1609 "*
1610{
1611 check_label_emit ();
1612 CC_STATUS_SET (operands[0], operands[1]);
1613 if (REG_P (operands[1]))
1614 {
1615 mvs_check_page (0, 8, 0);
1616 return \"SLL %0,24\;SRA %0,24\";
1617 }
1618 if (s_operand (operands[1], GET_MODE (operands[1])))
1619 {
1620 mvs_check_page (0, 8, 0);
1621 return \"ICM %0,8,%1\;SRA %0,24\";
1622 }
1623 mvs_check_page (0, 12, 0);
1624 return \"IC %0,%1\;SLL %0,24\;SRA %0,24\";
1625}"
1626 [(set_attr "length" "12")]
1627)
1628
1629;
1630; extendqihi2 instruction pattern(s).
1631;
1632
1633(define_insn "extendqihi2"
1634 [(set (match_operand:HI 0 "general_operand" "=d")
1635 (sign_extend:HI (match_operand:QI 1 "general_operand" "0m")))]
1636 ""
1637 "*
1638{
1639 check_label_emit ();
1640 CC_STATUS_SET (operands[0], operands[1]);
1641 if (REG_P (operands[1]))
1642 {
1643 mvs_check_page (0, 8, 0);
1644 return \"SLL %0,24\;SRA %0,24\";
1645 }
1646 if (s_operand (operands[1], GET_MODE (operands[1])))
1647 {
1648 mvs_check_page (0, 8, 0);
1649 return \"ICM %0,8,%1\;SRA %0,24\";
1650 }
1651 mvs_check_page (0, 12, 0);
1652 return \"IC %0,%1\;SLL %0,24\;SRA %0,24\";
1653}"
1654 [(set_attr "length" "12")]
1655)
1656
1657;
1658; zero_extendsidi2 instruction pattern(s).
1659;
1660
1661(define_expand "zero_extendsidi2"
1662 [(set (match_operand:DI 0 "register_operand" "=d")
1663 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))]
1664 ""
1665 "
1666{
1667 emit_insn (gen_rtx_SET (VOIDmode,
1668 operand_subword (operands[0], 0, 1, DImode), operands[1]));
1669 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
1670 gen_rtx_LSHIFTRT (DImode, operands[0],
1671 gen_rtx_CONST_INT (SImode, 32))));
1672 DONE;
1673}")
1674
1675;
1676; zero_extendhisi2 instruction pattern(s).
1677;
1678
1679(define_insn "zero_extendhisi2"
1680 [(set (match_operand:SI 0 "general_operand" "=d")
1681 (zero_extend:SI (match_operand:HI 1 "general_operand" "0")))]
1682 ""
1683 "*
1684{
1685 check_label_emit ();
1686 /* AND only sets zero/not-zero bits not the arithmetic bits ... */
1687 CC_STATUS_INIT;
1688 mvs_check_page (0, 4, 4);
1689 return \"N %1,=XL4'0000FFFF'\";
1690}"
1691 [(set_attr "length" "4")]
1692)
1693
1694;
1695; zero_extendqisi2 instruction pattern(s).
1696;
1697
1698(define_insn "zero_extendqisi2"
1699 [(set (match_operand:SI 0 "general_operand" "=d,&d")
1700 (zero_extend:SI (match_operand:QI 1 "general_operand" "0i,m")))]
1701 ""
1702 "*
1703{
1704 check_label_emit ();
1705 if (REG_P (operands[1]))
1706 {
1707 /* AND only sets zero/not-zero bits not the arithmetic bits ... */
1708 CC_STATUS_INIT;
1709 mvs_check_page (0, 4, 4);
1710 return \"N %0,=XL4'000000FF'\";
1711 }
1712 if (GET_CODE (operands[1]) == CONST_INT)
1713 {
1714 mvs_check_page (0, 4, 0);
1715 return \"LA %0,%c1(0,0)\";
1716 }
1717 CC_STATUS_INIT;
1718 mvs_check_page (0, 8, 0);
1719 return \"SLR %0,%0\;IC %0,%1\";
1720}"
1721 [(set_attr "length" "8")]
1722)
1723
1724;
1725; zero_extendqihi2 instruction pattern(s).
1726;
1727
1728(define_insn "zero_extendqihi2"
1729 [(set (match_operand:HI 0 "general_operand" "=d,&d")
1730 (zero_extend:HI (match_operand:QI 1 "general_operand" "0i,m")))]
1731 ""
1732 "*
1733{
1734 check_label_emit ();
1735 if (REG_P (operands[1]))
1736 {
1737 /* AND only sets zero/not-zero bits not the arithmetic bits ... */
1738 CC_STATUS_INIT;
1739 mvs_check_page (0, 4, 4);
1740 return \"N %0,=XL4'000000FF'\";
1741 }
1742 if (GET_CODE (operands[1]) == CONST_INT)
1743 {
1744 mvs_check_page (0, 4, 0);
1745 return \"LA %0,%c1(0,0)\";
1746 }
1747 CC_STATUS_INIT;
1748 mvs_check_page (0, 8, 0);
1749 return \"SLR %0,%0\;IC %0,%1\";
1750}"
1751 [(set_attr "length" "8")]
1752)
1753
1754;
1755; truncsihi2 instruction pattern(s).
1756;
1757
1758(define_insn "truncsihi2"
1759 [(set (match_operand:HI 0 "general_operand" "=d,m")
1760 (truncate:HI (match_operand:SI 1 "general_operand" "0,d")))]
1761 ""
1762 "*
1763{
1764 check_label_emit ();
1765 if (REG_P (operands[0]))
1766 {
1767 CC_STATUS_SET (operands[0], operands[1]);
1768 mvs_check_page (0, 8, 0);
1769 return \"SLL %0,16\;SRA %0,16\";
1770 }
1771 mvs_check_page (0, 4, 0);
1772 return \"STH %1,%0\";
1773}"
1774 [(set_attr "length" "8")]
1775)
1776
1777;
1778; fix_truncdfsi2 instruction pattern(s).
1779;
1780
1781(define_insn "fix_truncdfsi2"
1782 [(set (match_operand:SI 0 "general_operand" "=d")
1783 (fix:SI (truncate:DF (match_operand:DF 1 "general_operand" "+f"))))
1784 (clobber (reg:DF 16))]
1785 ""
1786 "*
1787{
1788 check_label_emit ();
1789 CC_STATUS_INIT;
1790 if (REGNO (operands[1]) == 16)
1791 {
1792 mvs_check_page (0, 12, 8);
1793 return \"AD 0,=XL8'4F08000000000000'\;STD 0,140(,13)\;L %0,144(,13)\";
1794 }
1795 mvs_check_page (0, 14, 8);
1796 return \"LDR 0,%1\;AD 0,=XL8'4F08000000000000'\;STD 0,140(,13)\;L %0,144(,13)\";
1797}"
1798 [(set_attr "length" "14")]
1799)
1800
1801;
1802; floatsidf2 instruction pattern(s).
1803;
1804; LE/370 mode uses the float field of the TCA.
1805;
1806
1807(define_insn "floatsidf2"
1808 [(set (match_operand:DF 0 "general_operand" "=f")
1809 (float:DF (match_operand:SI 1 "general_operand" "d")))]
1810 ""
1811 "*
1812{
1813 check_label_emit ();
1814 CC_STATUS_INIT;
1815#ifdef TARGET_ELF_ABI
1816 mvs_check_page (0, 22, 12);
1817 return \"MVC 140(4,13),=XL4'4E000000'\;ST %1,144(,13)\;XI 144(13),128\;LD %0,140(,13)\;SD %0,=XL8'4E00000080000000'\";
1818#else
1819 mvs_check_page (0, 16, 8);
1820 return \"ST %1,508(,12)\;XI 508(12),128\;LD %0,504(,12)\;SD %0,=XL8'4E00000080000000'\";
1821#endif
1822}"
1823 [(set_attr "length" "22")]
1824)
1825
1826;
1827; truncdfsf2 instruction pattern(s).
1828;
1829
1830(define_insn "truncdfsf2"
1831 [(set (match_operand:SF 0 "general_operand" "=f")
1832 (float_truncate:SF (match_operand:DF 1 "general_operand" "f")))]
1833 ""
1834 "*
1835{
1836 check_label_emit ();
1837 mvs_check_page (0, 2, 0);
1838 return \"LRER %0,%1\";
1839}"
1840 [(set_attr "length" "2")]
1841)
1842
1843;
1844; extendsfdf2 instruction pattern(s).
1845;
1846
1847(define_insn "extendsfdf2"
1848 [(set (match_operand:DF 0 "general_operand" "=f")
1849 (float_extend:DF (match_operand:SF 1 "general_operand" "fmF")))]
1850 ""
1851 "*
1852{
1853 check_label_emit ();
1854 CC_STATUS_SET (0, const0_rtx);
1855 if (FP_REG_P (operands[1]))
1856 {
1857 if (REGNO (operands[0]) == REGNO (operands[1]))
1858 {
1859 mvs_check_page (0, 10, 0);
1860 return \"STE %1,140(,13)\;SDR %0,%0\;LE %0,140(,13)\";
1861 }
1862 mvs_check_page (0, 4, 0);
1863 return \"SDR %0,%0\;LER %0,%1\";
1864 }
1865 mvs_check_page (0, 6, 0);
1866 return \"SDR %0,%0\;LE %0,%1\";
1867}"
1868 [(set_attr "length" "10")]
1869)
1870
1871;;
1872;;- Add instructions.
1873;;
1874
1875;
1876; adddi3 instruction pattern(s).
1877;
1878;
1879;(define_expand "adddi3"
1880; [(set (match_operand:DI 0 "general_operand" "")
1881; (plus:DI (match_operand:DI 1 "general_operand" "")
1882; (match_operand:DI 2 "general_operand" "")))]
1883; ""
1884; "
1885;{
1886; rtx label = gen_label_rtx ();
1887; rtx op0_high = operand_subword (operands[0], 0, 1, DImode);
1888; rtx op0_low = gen_lowpart (SImode, operands[0]);
1889;
1890; emit_insn (gen_rtx_SET (VOIDmode, op0_high,
1891; gen_rtx_PLUS (SImode,
1892; operand_subword (operands[1], 0, 1, DImode),
1893; operand_subword (operands[2], 0, 1, DImode))));
1894; emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
1895; gen_rtx_SET (VOIDmode, op0_low,
1896; gen_rtx_PLUS (SImode, gen_lowpart (SImode, operands[1]),
1897; gen_lowpart (SImode, operands[2]))),
1898; gen_rtx_USE (VOIDmode, gen_rtx_LABEL_REF (VOIDmode, label)))));
1899; emit_insn (gen_rtx_SET (VOIDmode, op0_high,
1900; gen_rtx_PLUS (SImode, op0_high,
1901; gen_rtx_CONST_INT (SImode, 1))));
1902; emit_label (label);
1903; DONE;
1904;}")
1905
1906(define_insn ""
1907 [(set (match_operand:SI 0 "general_operand" "=d")
1908 (plus:SI (match_operand:SI 1 "general_operand" "%0")
1909 (match_operand:SI 2 "general_operand" "g")))
1910 (use (label_ref (match_operand 3 "" "")))
1911; (clobber (reg:SI 14))
1912 ]
1913 ""
1914 "*
1915{
1916 int onpage;
1917
1918 check_label_emit ();
1919 onpage = mvs_check_label (CODE_LABEL_NUMBER (operands[3]));
1920 if (REG_P (operands[2]))
1921 {
1922 if (!onpage)
1923 {
1924 mvs_check_page (0, 8, 4);
1925 return \"ALR %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
1926 }
1927 if (mvs_check_page (0, 6, 0))
1928 {
1929 mvs_check_page (0, 2, 4);
1930 return \"ALR %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
1931 }
1932 return \"ALR %0,%2\;BC 12,%l3\";
1933 }
1934 if (!onpage)
1935 {
1936 mvs_check_page (0, 10, 4);
1937 return \"AL %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
1938 }
1939 if (mvs_check_page (0, 8 ,0))
1940 {
1941 mvs_check_page (0, 2, 4);
1942 return \"AL %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
1943 }
1944 return \"AL %0,%2\;BC 12,%l3\";
1945}"
1946 [(set_attr "length" "10")]
1947)
1948
1949;
1950; addsi3 instruction pattern(s).
1951;
1952; The following insn is used when it is known that operand one is an address,
1953; frame, stack or argument pointer, and operand two is a constant that is
1954; small enough to fit in the displacement field.
1955; Notice that we can't allow the frame pointer to used as a normal register
1956; because of this insn.
1957;
1958
1959(define_insn ""
1960 [(set (match_operand:SI 0 "register_operand" "=d")
1961 (plus:SI (match_operand:SI 1 "general_operand" "%a")
1962 (match_operand:SI 2 "immediate_operand" "J")))]
1963 "((REGNO (operands[1]) == FRAME_POINTER_REGNUM || REGNO (operands[1]) == ARG_POINTER_REGNUM || REGNO (operands[1]) == STACK_POINTER_REGNUM) && (unsigned) INTVAL (operands[2]) < 4096)"
1964 "*
1965{
1966 check_label_emit ();
1967 CC_STATUS_INIT; /* add assumes CC but LA doesn't set CC */
1968 mvs_check_page (0, 4, 0);
1969 return \"LA %0,%c2(,%1)\";
1970}"
1971 [(set_attr "length" "4")]
1972)
1973
1974; This insn handles additions that are relative to the frame pointer.
1975
1976(define_insn ""
1977 [(set (match_operand:SI 0 "register_operand" "=d")
1978 (plus:SI (match_operand:SI 1 "register_operand" "%a")
1979 (match_operand:SI 2 "immediate_operand" "i")))]
1980 "REGNO (operands[1]) == FRAME_POINTER_REGNUM"
1981 "*
1982{
1983 check_label_emit ();
1984 if ((unsigned) INTVAL (operands[2]) < 4096)
1985 {
1986 CC_STATUS_INIT; /* add assumes CC but LA doesn't set CC */
1987 mvs_check_page (0, 4, 0);
1988 return \"LA %0,%c2(,%1)\";
1989 }
1990 if (REGNO (operands[1]) == REGNO (operands[0]))
1991 {
1992 CC_STATUS_INIT;
1993 mvs_check_page (0, 4, 0);
1994 return \"A %0,%2\";
1995 }
1996 mvs_check_page (0, 6, 0);
1997 return \"L %0,%2\;AR %0,%1\";
1998}"
1999 [(set_attr "length" "6")]
2000)
2001
2002;;
2003;; The CC status bits for the arithmetic instructions are handled
2004;; in the NOTICE_UPDATE_CC macro (yeah???) and so they do not need
2005;; to be set below. They only need to be invalidated if *not* set
2006;; (e.g. by BCTR) ... yeah I think that's right ...
2007;;
2008
2009(define_insn "addsi3"
2010 [(set (match_operand:SI 0 "general_operand" "=d")
2011 (plus:SI (match_operand:SI 1 "general_operand" "%0")
2012 (match_operand:SI 2 "general_operand" "g")))]
2013 ""
2014 "*
2015{
2016 check_label_emit ();
2017 if (REG_P (operands[2]))
2018 {
2019 mvs_check_page (0, 2, 0);
2020 return \"AR %0,%2\";
2021 }
2022 if (GET_CODE (operands[2]) == CONST_INT)
2023 {
2024 if (INTVAL (operands[2]) == -1)
2025 {
2026 CC_STATUS_INIT; /* add assumes CC but BCTR doesn't set CC */
2027 mvs_check_page (0, 2, 0);
2028 return \"BCTR %0,0\";
2029 }
2030 }
2031 mvs_check_page (0, 4, 0);
2032 return \"A %0,%2\";
2033}"
2034 [(set_attr "length" "4")]
2035)
2036
2037;
2038; addhi3 instruction pattern(s).
2039;
2040
2041(define_insn "addhi3"
2042 [(set (match_operand:HI 0 "general_operand" "=d")
2043 (plus:HI (match_operand:HI 1 "general_operand" "%0")
2044 (match_operand:HI 2 "general_operand" "dmi")))]
2045 ""
2046 "*
2047{
2048 check_label_emit ();
2049 if (REG_P (operands[2]))
2050 {
2051 mvs_check_page (0, 8, 0);
2052 return \"STH %2,140(,13)\;AH %0,140(,13)\";
2053 }
2054 if (GET_CODE (operands[2]) == CONST_INT)
2055 {
2056 if (INTVAL (operands[2]) == -1)
2057 {
2058 CC_STATUS_INIT; /* add assumes CC but BCTR doesn't set CC */
2059 mvs_check_page (0, 2, 0);
2060 return \"BCTR %0,0\";
2061 }
2062 mvs_check_page (0, 4, 0);
2063 return \"AH %0,%H2\";
2064 }
2065 mvs_check_page (0, 4, 0);
2066 return \"AH %0,%2\";
2067}"
2068 [(set_attr "length" "8")]
2069)
2070
2071;
2072; addqi3 instruction pattern(s).
2073;
2074
2075(define_insn "addqi3"
2076 [(set (match_operand:QI 0 "general_operand" "=d")
2077 (plus:QI (match_operand:QI 1 "general_operand" "%a")
2078 (match_operand:QI 2 "general_operand" "ai")))]
2079 ""
2080 "*
2081{
2082 check_label_emit ();
2083 CC_STATUS_INIT; /* add assumes CC but LA doesn't set CC */
2084 mvs_check_page (0, 4, 0);
2085 if (REG_P (operands[2]))
2086 return \"LA %0,0(%1,%2)\";
2087 return \"LA %0,%B2(,%1)\";
2088}"
2089 [(set_attr "length" "4")]
2090)
2091
2092;
2093; adddf3 instruction pattern(s).
2094;
2095
2096(define_insn "adddf3"
2097 [(set (match_operand:DF 0 "general_operand" "=f")
2098 (plus:DF (match_operand:DF 1 "general_operand" "%0")
2099 (match_operand:DF 2 "general_operand" "fmF")))]
2100 ""
2101 "*
2102{
2103 check_label_emit ();
2104 if (FP_REG_P (operands[2]))
2105 {
2106 mvs_check_page (0, 2, 0);
2107 return \"ADR %0,%2\";
2108 }
2109 mvs_check_page (0, 4, 0);
2110 return \"AD %0,%2\";
2111}"
2112 [(set_attr "length" "4")]
2113)
2114
2115;
2116; addsf3 instruction pattern(s).
2117;
2118
2119(define_insn "addsf3"
2120 [(set (match_operand:SF 0 "general_operand" "=f")
2121 (plus:SF (match_operand:SF 1 "general_operand" "%0")
2122 (match_operand:SF 2 "general_operand" "fmF")))]
2123 ""
2124 "*
2125{
2126 check_label_emit ();
2127 if (FP_REG_P (operands[2]))
2128 {
2129 mvs_check_page (0, 2, 0);
2130 return \"AER %0,%2\";
2131 }
2132 mvs_check_page (0, 4, 0);
2133 return \"AE %0,%2\";
2134}"
2135 [(set_attr "length" "4")]
2136)
2137
2138;;
2139;;- Subtract instructions.
2140;;
2141
2142;
2143; subdi3 instruction pattern(s).
2144;
2145;
2146;(define_expand "subdi3"
2147; [(set (match_operand:DI 0 "general_operand" "")
2148; (minus:DI (match_operand:DI 1 "general_operand" "")
2149; (match_operand:DI 2 "general_operand" "")))]
2150; ""
2151; "
2152;{
2153; rtx label = gen_label_rtx ();
2154; rtx op0_high = operand_subword (operands[0], 0, 1, DImode);
2155; rtx op0_low = gen_lowpart (SImode, operands[0]);
2156;
2157; emit_insn (gen_rtx_SET (VOIDmode, op0_high,
2158; gen_rtx_MINUS (SImode,
2159; operand_subword (operands[1], 0, 1, DImode),
2160; operand_subword (operands[2], 0, 1, DImode))));
2161; emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
2162; gen_rtx_SET (VOIDmode, op0_low,
2163; gen_rtx_MINUS (SImode,
2164; gen_lowpart (SImode, operands[1]),
2165; gen_lowpart (SImode, operands[2]))),
2166; gen_rtx_USE (VOIDmode,
2167; gen_rtx_LABEL_REF (VOIDmode, label)))));
2168; emit_insn (gen_rtx_SET (VOIDmode, op0_high,
2169; gen_rtx_MINUS (SImode, op0_high,
2170; gen_rtx_CONST_INT (SImode, 1))));
2171; emit_label (label);
2172; DONE;
2173;}")
2174
2175(define_insn ""
2176 [(set (match_operand:SI 0 "general_operand" "=d")
2177 (minus:SI (match_operand:SI 1 "general_operand" "0")
2178 (match_operand:SI 2 "general_operand" "g")))
2179 (use (label_ref (match_operand 3 "" "")))
2180; (clobber (reg:SI 14))
2181 ]
2182 ""
2183 "*
2184{
2185 int onpage;
2186
2187 check_label_emit ();
2188 CC_STATUS_INIT;
2189 onpage = mvs_check_label (CODE_LABEL_NUMBER (operands[3]));
2190 if (REG_P (operands[2]))
2191 {
2192 if (!onpage)
2193 {
2194 mvs_check_page (0, 8, 4);
2195 return \"SLR %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
2196 }
2197 if (mvs_check_page (0, 6, 0))
2198 {
2199 mvs_check_page (0, 2, 4);
2200 return \"SLR %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
2201 }
2202 return \"SLR %0,%2\;BC 12,%l3\";
2203 }
2204 if (!onpage)
2205 {
2206 mvs_check_page (0, 10, 4);
2207 return \"SL %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
2208 }
2209 if (mvs_check_page (0, 8, 0))
2210 {
2211 mvs_check_page (0, 2, 4);
2212 return \"SL %0,%2\;L 14,=A(%l3)\;BCR 12,14\";
2213 }
2214 return \"SL %0,%2\;BC 12,%l3\";
2215}"
2216 [(set_attr "length" "10")]
2217)
2218
2219;
2220; subsi3 instruction pattern(s).
2221;
2222
2223(define_insn "subsi3"
2224 [(set (match_operand:SI 0 "general_operand" "=d")
2225 (minus:SI (match_operand:SI 1 "general_operand" "0")
2226 (match_operand:SI 2 "general_operand" "g")))]
2227 ""
2228 "*
2229{
2230 check_label_emit ();
2231 if (REG_P (operands[2]))
2232 {
2233 mvs_check_page (0, 2, 0);
2234 return \"SR %0,%2\";
2235 }
2236 if (operands[2] == const1_rtx)
2237 {
2238 CC_STATUS_INIT; /* subtract assumes CC but BCTR doesn't set CC */
2239 mvs_check_page (0, 2, 0);
2240 return \"BCTR %0,0\";
2241 }
2242 mvs_check_page (0, 4, 0);
2243 return \"S %0,%2\";
2244}"
2245 [(set_attr "length" "4")]
2246)
2247
2248;
2249; subhi3 instruction pattern(s).
2250;
2251
2252(define_insn "subhi3"
2253 [(set (match_operand:HI 0 "general_operand" "=d")
2254 (minus:HI (match_operand:HI 1 "general_operand" "0")
2255 (match_operand:HI 2 "general_operand" "g")))]
2256 ""
2257 "*
2258{
2259 check_label_emit ();
2260 if (REG_P (operands[2]))
2261 {
2262 mvs_check_page (0, 8, 0);
2263 return \"STH %2,140(,13)\;SH %0,140(,13)\";
2264 }
2265 if (operands[2] == const1_rtx)
2266 {
2267 CC_STATUS_INIT; /* subtract assumes CC but BCTR doesn't set CC */
2268 mvs_check_page (0, 2, 0);
2269 return \"BCTR %0,0\";
2270 }
2271 if (GET_CODE (operands[2]) == CONST_INT)
2272 {
2273 mvs_check_page (0, 4, 0);
2274 return \"SH %0,%H2\";
2275 }
2276 mvs_check_page (0, 4, 0);
2277 return \"SH %0,%2\";
2278}"
2279 [(set_attr "length" "8")]
2280)
2281
2282;
2283; subqi3 instruction pattern(s).
2284;
2285
2286(define_expand "subqi3"
2287 [(set (match_operand:QI 0 "general_operand" "=d")
2288 (minus:QI (match_operand:QI 1 "general_operand" "0")
2289 (match_operand:QI 2 "general_operand" "di")))]
2290 ""
2291 "
2292{
2293 if (REG_P (operands[2]))
2294 {
2295 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2296 gen_rtx_MINUS (QImode, operands[1], operands[2])));
2297 }
2298 else
2299 {
2300 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2301 gen_rtx_PLUS (QImode, operands[1],
2302 negate_rtx (QImode, operands[2]))));
2303 }
2304 DONE;
2305}")
2306
2307(define_insn ""
2308 [(set (match_operand:QI 0 "register_operand" "=d")
2309 (minus:QI (match_operand:QI 1 "register_operand" "0")
2310 (match_operand:QI 2 "register_operand" "d")))]
2311 ""
2312 "*
2313{
2314 check_label_emit ();
2315 mvs_check_page (0, 2, 0);
2316 return \"SR %0,%2\";
2317}"
2318 [(set_attr "length" "2")]
2319)
2320
2321;
2322; subdf3 instruction pattern(s).
2323;
2324
2325(define_insn "subdf3"
2326 [(set (match_operand:DF 0 "general_operand" "=f")
2327 (minus:DF (match_operand:DF 1 "general_operand" "0")
2328 (match_operand:DF 2 "general_operand" "fmF")))]
2329 ""
2330 "*
2331{
2332 check_label_emit ();
2333 if (FP_REG_P (operands[2]))
2334 {
2335 mvs_check_page (0, 2, 0);
2336 return \"SDR %0,%2\";
2337 }
2338 mvs_check_page (0, 4, 0);
2339 return \"SD %0,%2\";
2340}"
2341 [(set_attr "length" "4")]
2342)
2343
2344;
2345; subsf3 instruction pattern(s).
2346;
2347
2348(define_insn "subsf3"
2349 [(set (match_operand:SF 0 "general_operand" "=f")
2350 (minus:SF (match_operand:SF 1 "general_operand" "0")
2351 (match_operand:SF 2 "general_operand" "fmF")))]
2352 ""
2353 "*
2354{
2355 check_label_emit ();
2356 if (FP_REG_P (operands[2]))
2357 {
2358 mvs_check_page (0, 2, 0);
2359 return \"SER %0,%2\";
2360 }
2361 mvs_check_page (0, 4, 0);
2362 return \"SE %0,%2\";
2363}"
2364 [(set_attr "length" "4")]
2365)
2366
2367;;
2368;;- Multiply instructions.
2369;;
2370
2371;
2372; mulsi3 instruction pattern(s).
2373;
2374
2375(define_expand "mulsi3"
2376 [(set (match_operand:SI 0 "general_operand" "")
2377 (mult:SI (match_operand:SI 1 "general_operand" "")
2378 (match_operand:SI 2 "general_operand" "")))]
2379 ""
2380 "
2381{
2382 if (GET_CODE (operands[1]) == CONST_INT
2383 && CONST_OK_FOR_LETTER_P (INTVAL (operands[1]), 'K'))
2384 {
2385 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2386 gen_rtx_MULT (SImode, operands[2], operands[1])));
2387 }
2388 else if (GET_CODE (operands[2]) == CONST_INT
2389 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))
2390 {
2391 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2392 gen_rtx_MULT (SImode, operands[1], operands[2])));
2393 }
2394 else
2395 {
2396 rtx r = gen_reg_rtx (DImode);
2397
2398 /* XXX trouble. Below we generate some rtx's that model what
2399 * is really supposed to happen with multiply on the 370/390
2400 * hardware, and that is all well & good. However, during optimization
2401 * it can happen that the two operands are exchanged (after all,
2402 * multiplication is commutitive), in which case the doubleword
2403 * ends up in memory and everything is hosed. The gen_reg_rtx
2404 * should have kept it in a reg ... We hack around this
2405 * below, in the M/MR isntruction pattern, and constrain it to
2406 * \"di\" instead of \"g\". But this still ends up with lots & lots of
2407 * movement between registers & memory and is an awful waste.
2408 * Dunno how to untwist it elegantly; but it seems to work for now.
2409 */
2410 emit_insn (gen_rtx_SET (VOIDmode,
2411 gen_rtx_SUBREG (SImode, r, GET_MODE_SIZE (SImode)),
2412 operands[1]));
2413 emit_insn (gen_rtx_SET (VOIDmode, r,
2414 gen_rtx_MULT (DImode, r, operands[2])));
2415 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2416 gen_rtx_SUBREG (SImode, r, GET_MODE_SIZE (SImode))));
2417 }
2418 DONE;
2419}")
2420
2421(define_insn ""
2422 [(set (match_operand:SI 0 "general_operand" "=d")
2423 (mult:SI (match_operand:SI 1 "general_operand" "%0")
2424 (match_operand:SI 2 "immediate_operand" "K")))]
2425 ""
2426 "*
2427{
2428 check_label_emit ();
2429 mvs_check_page (0, 4, 0);
2430 return \"MH %0,%H2\";
2431}"
2432 [(set_attr "length" "4")]
2433)
2434
2435(define_insn ""
2436 [(set (match_operand:DI 0 "register_operand" "=d")
2437 (mult:DI (match_operand:DI 1 "general_operand" "%0")
2438 (match_operand:SI 2 "general_operand" "di")))]
2439 ""
2440 "*
2441{
2442 check_label_emit ();
2443 if (REG_P (operands[2]))
2444 {
2445 mvs_check_page (0, 2, 0);
2446 return \"MR %0,%2\";
2447 }
2448 mvs_check_page (0, 4, 0);
2449 return \"M %0,%2\";
2450}"
2451 [(set_attr "length" "4")]
2452)
2453
2454;
2455; muldf3 instruction pattern(s).
2456;
2457
2458(define_insn "muldf3"
2459 [(set (match_operand:DF 0 "general_operand" "=f")
2460 (mult:DF (match_operand:DF 1 "general_operand" "%0")
2461 (match_operand:DF 2 "general_operand" "fmF")))]
2462 ""
2463 "*
2464{
2465 check_label_emit ();
2466 if (FP_REG_P (operands[2]))
2467 {
2468 mvs_check_page (0, 2, 0);
2469 return \"MDR %0,%2\";
2470 }
2471 mvs_check_page (0, 4, 0);
2472 return \"MD %0,%2\";
2473}"
2474 [(set_attr "length" "4")]
2475)
2476
2477;
2478; mulsf3 instruction pattern(s).
2479;
2480
2481(define_insn "mulsf3"
2482 [(set (match_operand:SF 0 "general_operand" "=f")
2483 (mult:SF (match_operand:SF 1 "general_operand" "%0")
2484 (match_operand:SF 2 "general_operand" "fmF")))]
2485 ""
2486 "*
2487{
2488 check_label_emit ();
2489 if (FP_REG_P (operands[2]))
2490 {
2491 mvs_check_page (0, 2, 0);
2492 return \"MER %0,%2\";
2493 }
2494 mvs_check_page (0, 4, 0);
2495 return \"ME %0,%2\";
2496}"
2497 [(set_attr "length" "4")]
2498)
2499
2500;;
2501;;- Divide instructions.
2502;;
2503
2504;
2505; divsi3 instruction pattern(s).
2506;
2507
2508(define_expand "divsi3"
2509 [(set (match_operand:SI 0 "general_operand" "")
2510 (div:SI (match_operand:SI 1 "general_operand" "")
2511 (match_operand:SI 2 "general_operand" "")))]
2512 ""
2513 "
2514{
2515 rtx r = gen_reg_rtx (DImode);
2516
2517 emit_insn (gen_extendsidi2 (r, operands[1]));
2518 emit_insn (gen_rtx_SET (VOIDmode, r,
2519 gen_rtx_DIV (DImode, r, operands[2])));
2520 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2521 gen_rtx_SUBREG (SImode, r, GET_MODE_SIZE (SImode))));
2522 DONE;
2523}")
2524
2525
2526;
2527; udivsi3 instruction pattern(s).
2528;
2529
2530(define_expand "udivsi3"
2531 [(set (match_operand:SI 0 "general_operand" "")
2532 (udiv:SI (match_operand:SI 1 "general_operand" "")
2533 (match_operand:SI 2 "general_operand" "")))]
2534 ""
2535 "
2536{
2537 rtx dr = gen_reg_rtx (DImode);
2538 rtx dr_0 = gen_rtx_SUBREG (SImode, dr, 0);
2539 rtx dr_1 = gen_rtx_SUBREG (SImode, dr, GET_MODE_SIZE (SImode));
2540
2541
2542 if (GET_CODE (operands[2]) == CONST_INT)
2543 {
2544 if (INTVAL (operands[2]) > 0)
2545 {
2546 emit_insn (gen_zero_extendsidi2 (dr, operands[1]));
2547 emit_insn (gen_rtx_SET (VOIDmode, dr,
2548 gen_rtx_DIV (DImode, dr, operands[2])));
2549 }
2550 else
2551 {
2552 rtx label1 = gen_label_rtx ();
2553
2554 emit_insn (gen_rtx_SET (VOIDmode, dr_0, operands[1]));
2555 emit_insn (gen_rtx_SET (VOIDmode, dr_1, const0_rtx));
2556 emit_insn (gen_cmpsi (dr_0, operands[2]));
2557 emit_jump_insn (gen_bltu (label1));
2558 emit_insn (gen_rtx_SET (VOIDmode, dr_1, const1_rtx));
2559 emit_label (label1);
2560 }
2561 }
2562 else
2563 {
2564 rtx label1 = gen_label_rtx ();
2565 rtx label2 = gen_label_rtx ();
2566 rtx label3 = gen_label_rtx ();
2567 rtx sr = gen_reg_rtx (SImode);
2568
2569 emit_insn (gen_rtx_SET (VOIDmode, dr_0, operands[1]));
2570 emit_insn (gen_rtx_SET (VOIDmode, sr, operands[2]));
2571 emit_insn (gen_rtx_SET (VOIDmode, dr_1, const0_rtx));
2572 emit_insn (gen_cmpsi (sr, dr_0));
2573 emit_jump_insn (gen_bgtu (label3));
2574 emit_insn (gen_cmpsi (sr, const1_rtx));
2575 emit_jump_insn (gen_blt (label2));
2576 emit_insn (gen_cmpsi (sr, const1_rtx));
2577 emit_jump_insn (gen_beq (label1));
2578 emit_insn (gen_rtx_SET (VOIDmode, dr,
2579 gen_rtx_LSHIFTRT (DImode, dr,
2580 gen_rtx_CONST_INT (SImode, 32))));
2581 emit_insn (gen_rtx_SET (VOIDmode, dr,
2582 gen_rtx_DIV (DImode, dr, sr)));
2583 emit_jump_insn (gen_jump (label3));
2584 emit_label (label1);
2585 emit_insn (gen_rtx_SET (VOIDmode, dr_1, dr_0));
2586 emit_jump_insn (gen_jump (label3));
2587 emit_label (label2);
2588 emit_insn (gen_rtx_SET (VOIDmode, dr_1, const1_rtx));
2589 emit_label (label3);
2590 }
2591 emit_insn (gen_rtx_SET (VOIDmode, operands[0], dr_1));
2592
2593 DONE;
2594}")
2595
2596; This is used by divsi3 & udivsi3.
2597
2598(define_insn ""
2599 [(set (match_operand:DI 0 "register_operand" "=d")
2600 (div:DI (match_operand:DI 1 "register_operand" "0")
2601 (match_operand:SI 2 "general_operand" "dm")))]
2602 ""
2603 "*
2604{
2605 check_label_emit ();
2606 if (REG_P (operands[2]))
2607 {
2608 mvs_check_page (0, 2, 0);
2609 return \"DR %0,%2\";
2610 }
2611 mvs_check_page (0, 4, 0);
2612 return \"D %0,%2\";
2613}"
2614 [(set_attr "length" "4")]
2615)
2616
2617;
2618; divdf3 instruction pattern(s).
2619;
2620
2621(define_insn "divdf3"
2622 [(set (match_operand:DF 0 "general_operand" "=f")
2623 (div:DF (match_operand:DF 1 "general_operand" "0")
2624 (match_operand:DF 2 "general_operand" "fmF")))]
2625 ""
2626 "*
2627{
2628 check_label_emit ();
2629 if (FP_REG_P (operands[2]))
2630 {
2631 mvs_check_page (0, 2, 0);
2632 return \"DDR %0,%2\";
2633 }
2634 mvs_check_page (0, 4, 0);
2635 return \"DD %0,%2\";
2636}"
2637 [(set_attr "length" "4")]
2638)
2639
2640;
2641; divsf3 instruction pattern(s).
2642;
2643
2644(define_insn "divsf3"
2645 [(set (match_operand:SF 0 "general_operand" "=f")
2646 (div:SF (match_operand:SF 1 "general_operand" "0")
2647 (match_operand:SF 2 "general_operand" "fmF")))]
2648 ""
2649 "*
2650{
2651 check_label_emit ();
2652 if (FP_REG_P (operands[2]))
2653 {
2654 mvs_check_page (0, 2, 0);
2655 return \"DER %0,%2\";
2656 }
2657 mvs_check_page (0, 4, 0);
2658 return \"DE %0,%2\";
2659}"
2660 [(set_attr "length" "4")]
2661)
2662
2663;;
2664;;- Modulo instructions.
2665;;
2666
2667;
2668; modsi3 instruction pattern(s).
2669;
2670
2671(define_expand "modsi3"
2672 [(set (match_operand:SI 0 "general_operand" "")
2673 (mod:SI (match_operand:SI 1 "general_operand" "")
2674 (match_operand:SI 2 "general_operand" "")))]
2675 ""
2676 "
2677{
2678 rtx r = gen_reg_rtx (DImode);
2679
2680 emit_insn (gen_extendsidi2 (r, operands[1]));
2681 emit_insn (gen_rtx_SET (VOIDmode, r,
2682 gen_rtx_MOD (DImode, r, operands[2])));
2683 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
2684 gen_rtx_SUBREG (SImode, r, 0)));
2685 DONE;
2686}")
2687
2688;
2689; umodsi3 instruction pattern(s).
2690;
2691
2692(define_expand "umodsi3"
2693 [(set (match_operand:SI 0 "general_operand" "")
2694 (umod:SI (match_operand:SI 1 "general_operand" "")
2695 (match_operand:SI 2 "general_operand" "")))]
2696 ""
2697 "
2698{
2699 rtx dr = gen_reg_rtx (DImode);
2700 rtx dr_0 = gen_rtx_SUBREG (SImode, dr, 0);
2701
2702 emit_insn (gen_rtx_SET (VOIDmode, dr_0, operands[1]));
2703
2704 if (GET_CODE (operands[2]) == CONST_INT)
2705 {
2706 if (INTVAL (operands[2]) > 0)
2707 {
2708 emit_insn (gen_rtx_SET (VOIDmode, dr,
2709 gen_rtx_LSHIFTRT (DImode, dr,
2710 gen_rtx_CONST_INT (SImode, 32))));
2711 emit_insn (gen_rtx_SET (VOIDmode, dr,
2712 gen_rtx_MOD (DImode, dr, operands[2])));
2713 }
2714 else
2715 {
2716 rtx label1 = gen_label_rtx ();
2717 rtx sr = gen_reg_rtx (SImode);
2718
2719 emit_insn (gen_rtx_SET (VOIDmode, sr, operands[2]));
2720 emit_insn (gen_cmpsi (dr_0, sr));
2721 emit_jump_insn (gen_bltu (label1));
2722 emit_insn (gen_rtx_SET (VOIDmode, sr, gen_rtx_ABS (SImode, sr)));
2723 emit_insn (gen_rtx_SET (VOIDmode, dr_0,
2724 gen_rtx_PLUS (SImode, dr_0, sr)));
2725 emit_label (label1);
2726 }
2727 }
2728 else
2729 {
2730 rtx label1 = gen_label_rtx ();
2731 rtx label2 = gen_label_rtx ();
2732 rtx label3 = gen_label_rtx ();
2733 rtx sr = gen_reg_rtx (SImode);
2734
2735 emit_insn (gen_rtx_SET (VOIDmode, dr_0, operands[1]));
2736 emit_insn (gen_rtx_SET (VOIDmode, sr, operands[2]));
2737 emit_insn (gen_cmpsi (sr, dr_0));
2738 emit_jump_insn (gen_bgtu (label3));
2739 emit_insn (gen_cmpsi (sr, const1_rtx));
2740 emit_jump_insn (gen_blt (label2));
2741 emit_jump_insn (gen_beq (label1));
2742 emit_insn (gen_rtx_SET (VOIDmode, dr,
2743 gen_rtx_LSHIFTRT (DImode, dr,
2744 gen_rtx_CONST_INT (SImode, 32))));
2745 emit_insn (gen_rtx_SET (VOIDmode, dr, gen_rtx_MOD (DImode, dr, sr)));
2746 emit_jump_insn (gen_jump (label3));
2747 emit_label (label1);
2748 emit_insn (gen_rtx_SET (VOIDmode, dr_0, const0_rtx));
2749 emit_jump_insn (gen_jump (label3));
2750 emit_label (label2);
2751 emit_insn (gen_rtx_SET (VOIDmode, dr_0,
2752 gen_rtx_MINUS (SImode, dr_0, sr)));
2753 emit_label (label3);
2754
2755 }
2756 emit_insn (gen_rtx_SET (VOIDmode, operands[0], dr_0));
2757
2758 DONE;
2759}")
2760
2761; This is used by modsi3 & umodsi3.
2762
2763(define_insn ""
2764 [(set (match_operand:DI 0 "register_operand" "=d")
2765 (mod:DI (match_operand:DI 1 "register_operand" "0")
2766 (match_operand:SI 2 "general_operand" "dm")))]
2767 ""
2768 "*
2769{
2770 check_label_emit ();
2771 if (REG_P (operands[2]))
2772 {
2773 mvs_check_page (0, 2, 0);
2774 return \"DR %0,%2\";
2775 }
2776 mvs_check_page (0, 4, 0);
2777 return \"D %0,%2\";
2778}"
2779 [(set_attr "length" "4")]
2780)
2781
2782;;
2783;;- And instructions.
2784;;
2785
2786;
2787; anddi3 instruction pattern(s).
2788;
2789
2790;(define_expand "anddi3"
2791; [(set (match_operand:DI 0 "general_operand" "")
2792; (and:DI (match_operand:DI 1 "general_operand" "")
2793; (match_operand:DI 2 "general_operand" "")))]
2794; ""
2795; "
2796;{
2797; rtx gen_andsi3();
2798;
2799; emit_insn (gen_andsi3 (operand_subword (operands[0], 0, 1, DImode),
2800; operand_subword (operands[1], 0, 1, DImode),
2801; operand_subword (operands[2], 0, 1, DImode)));
2802; emit_insn (gen_andsi3 (gen_lowpart (SImode, operands[0]),
2803; gen_lowpart (SImode, operands[1]),
2804; gen_lowpart (SImode, operands[2])));
2805; DONE;
2806;}")
2807
2808;
2809; andsi3 instruction pattern(s).
2810;
2811
2812(define_insn ""
2813 [(set (match_operand:SI 0 "r_or_s_operand" "=d,m")
2814 (and:SI (match_operand:SI 1 "r_or_s_operand" "%0,0")
2815 (match_operand:SI 2 "r_or_s_operand" "g,mi")))]
2816 "TARGET_CHAR_INSTRUCTIONS"
2817 "*
2818{
2819 check_label_emit ();
2820 CC_STATUS_INIT; /* and sets CC but not how we want it */
2821 if (REG_P (operands[2]))
2822 {
2823 mvs_check_page (0, 2, 0);
2824 return \"NR %0,%2\";
2825 }
2826 if (REG_P (operands[0]))
2827 {
2828 mvs_check_page (0, 4, 0);
2829 return \"N %0,%2\";
2830 }
2831 mvs_check_page (0, 6, 0);
2832 return \"NC %O0(4,%R0),%2\";
2833}"
2834 [(set_attr "length" "6")]
2835)
2836
2837(define_insn "andsi3"
2838 [(set (match_operand:SI 0 "general_operand" "=d")
2839 (and:SI (match_operand:SI 1 "general_operand" "%0")
2840 (match_operand:SI 2 "general_operand" "g")))]
2841 ""
2842 "*
2843{
2844 check_label_emit ();
2845 CC_STATUS_INIT; /* and sets CC but not how we want it */
2846 if (REG_P (operands[2]))
2847 {
2848 mvs_check_page (0, 2, 0);
2849 return \"NR %0,%2\";
2850 }
2851 mvs_check_page (0, 4, 0);
2852 return \"N %0,%2\";
2853}"
2854 [(set_attr "length" "4")]
2855)
2856
2857;
2858; andhi3 instruction pattern(s).
2859;
2860
2861(define_insn ""
2862 [(set (match_operand:HI 0 "r_or_s_operand" "=d,m")
2863 (and:HI (match_operand:HI 1 "r_or_s_operand" "%0,0")
2864 (match_operand:HI 2 "r_or_s_operand" "di,mi")))]
2865 "TARGET_CHAR_INSTRUCTIONS"
2866 "*
2867{
2868 check_label_emit ();
2869 CC_STATUS_INIT; /* and sets CC but not how we want it */
2870 if (REG_P (operands[2]))
2871 {
2872 mvs_check_page (0, 2, 0);
2873 return \"NR %0,%2\";
2874 }
2875 if (REG_P (operands[0]))
2876 {
2877 /* %K2 == sign extend operand to 32 bits so that CH works */
2878 mvs_check_page (0, 4, 0);
2879 if (GET_CODE (operands[2]) == CONST_INT)
2880 return \"N %0,%K2\";
2881 return \"N %0,%2\";
2882 }
2883 if (GET_CODE (operands[2]) == CONST_INT)
2884 {
2885 mvs_check_page (0, 6, 0);
2886 return \"NC %O0(2,%R0),%H2\";
2887 }
2888 mvs_check_page (0, 6, 0);
2889 return \"NC %O0(2,%R0),%2\";
2890}"
2891 [(set_attr "length" "6")]
2892)
2893
2894(define_insn "andhi3"
2895 [(set (match_operand:HI 0 "general_operand" "=d")
2896 (and:HI (match_operand:HI 1 "general_operand" "%0")
2897 (match_operand:HI 2 "general_operand" "di")))]
2898 ""
2899 "*
2900{
2901 check_label_emit ();
2902 CC_STATUS_INIT; /* and sets CC but not how we want it */
2903 if (GET_CODE (operands[2]) == CONST_INT)
2904 {
2905 /* %K2 == sign extend operand to 32 bits so that CH works */
2906 mvs_check_page (0, 4, 0);
2907 return \"N %0,%K2\";
2908 }
2909 mvs_check_page (0, 2, 0);
2910 return \"NR %0,%2\";
2911}"
2912 [(set_attr "length" "4")]
2913)
2914
2915;
2916; andqi3 instruction pattern(s).
2917;
2918
2919(define_insn ""
2920 [(set (match_operand:QI 0 "r_or_s_operand" "=d,m")
2921 (and:QI (match_operand:QI 1 "r_or_s_operand" "%0,0")
2922 (match_operand:QI 2 "r_or_s_operand" "di,mi")))]
2923 "TARGET_CHAR_INSTRUCTIONS"
2924 "*
2925{
2926 check_label_emit ();
2927 CC_STATUS_INIT; /* and sets CC but not how we want it */
2928 if (REG_P (operands[2]))
2929 {
2930 mvs_check_page (0, 2, 0);
2931 return \"NR %0,%2\";
2932 }
2933 if (REG_P (operands[0]))
2934 {
2935 mvs_check_page (0, 4, 0);
2936 return \"N %0,%2\";
2937 }
2938 if (GET_CODE (operands[2]) == CONST_INT)
2939 {
2940 mvs_check_page (0, 4, 0);
2941 return \"NI %0,%B2\";
2942 }
2943 mvs_check_page (0, 6, 0);
2944 return \"NC %O0(1,%R0),%2\";
2945}"
2946 [(set_attr "length" "6")]
2947)
2948
2949(define_insn "andqi3"
2950 [(set (match_operand:QI 0 "general_operand" "=d")
2951 (and:QI (match_operand:QI 1 "general_operand" "%0")
2952 (match_operand:QI 2 "general_operand" "di")))]
2953 ""
2954 "*
2955{
2956 check_label_emit ();
2957 CC_STATUS_INIT; /* and sets CC but not how we want it */
2958 if (GET_CODE (operands[2]) == CONST_INT)
2959 {
2960 mvs_check_page (0, 4, 0);
2961 return \"N %0,%2\";
2962 }
2963 mvs_check_page (0, 2, 0);
2964 return \"NR %0,%2\";
2965}"
2966 [(set_attr "length" "4")]
2967)
2968
2969;;
2970;;- Bit set (inclusive or) instructions.
2971;;
2972
2973;
2974; iordi3 instruction pattern(s).
2975;
2976
2977;(define_expand "iordi3"
2978; [(set (match_operand:DI 0 "general_operand" "")
2979; (ior:DI (match_operand:DI 1 "general_operand" "")
2980; (match_operand:DI 2 "general_operand" "")))]
2981; ""
2982; "
2983;{
2984; rtx gen_iorsi3();
2985;
2986; emit_insn (gen_iorsi3 (operand_subword (operands[0], 0, 1, DImode),
2987; operand_subword (operands[1], 0, 1, DImode),
2988; operand_subword (operands[2], 0, 1, DImode)));
2989; emit_insn (gen_iorsi3 (gen_lowpart (SImode, operands[0]),
2990; gen_lowpart (SImode, operands[1]),
2991; gen_lowpart (SImode, operands[2])));
2992; DONE;
2993;}")
2994
2995;
2996; iorsi3 instruction pattern(s).
2997;
2998
2999(define_insn ""
3000 [(set (match_operand:SI 0 "r_or_s_operand" "=d,m")
3001 (ior:SI (match_operand:SI 1 "r_or_s_operand" "%0,0")
3002 (match_operand:SI 2 "r_or_s_operand" "g,Si")))]
3003 "TARGET_CHAR_INSTRUCTIONS"
3004 "*
3005{
3006 check_label_emit ();
3007 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3008 if (REG_P (operands[2]))
3009 {
3010 mvs_check_page (0, 2, 0);
3011 return \"OR %0,%2\";
3012 }
3013 if (REG_P (operands[0]))
3014 {
3015 mvs_check_page (0, 4, 0);
3016 return \"O %0,%2\";
3017 }
3018 mvs_check_page (0, 6, 0);
3019 return \"OC %O0(4,%R0),%2\";
3020}"
3021 [(set_attr "length" "6")]
3022)
3023
3024(define_insn "iorsi3"
3025 [(set (match_operand:SI 0 "general_operand" "=d")
3026 (ior:SI (match_operand:SI 1 "general_operand" "%0")
3027 (match_operand:SI 2 "general_operand" "g")))]
3028 ""
3029 "*
3030{
3031 check_label_emit ();
3032 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3033 if (REG_P (operands[2]))
3034 {
3035 mvs_check_page (0, 2, 0);
3036 return \"OR %0,%2\";
3037 }
3038 mvs_check_page (0, 4, 0);
3039 return \"O %0,%2\";
3040}"
3041 [(set_attr "length" "4")]
3042)
3043
3044;
3045; iorhi3 instruction pattern(s).
3046;
3047
3048(define_insn ""
3049 [(set (match_operand:HI 0 "r_or_s_operand" "=d,m")
3050 (ior:HI (match_operand:HI 1 "r_or_s_operand" "%0,0")
3051 (match_operand:HI 2 "r_or_s_operand" "di,mi")))]
3052 "TARGET_CHAR_INSTRUCTIONS"
3053 "*
3054{
3055 check_label_emit ();
3056 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3057 if (REG_P (operands[2]))
3058 {
3059 mvs_check_page (0, 2, 0);
3060 return \"OR %0,%2\";
3061 }
3062 if (REG_P (operands[0]))
3063 {
3064 mvs_check_page (0, 4, 0);
3065 return \"O %0,%2\";
3066 }
3067 if (GET_CODE (operands[2]) == CONST_INT)
3068 {
3069 mvs_check_page (0, 6, 2);
3070 return \"OC %O0(2,%R0),%H2\";
3071 }
3072 mvs_check_page (0, 6, 0);
3073 return \"OC %O0(2,%R0),%2\";
3074}"
3075 [(set_attr "length" "6")]
3076)
3077
3078(define_insn "iorhi3"
3079 [(set (match_operand:HI 0 "general_operand" "=d")
3080 (ior:HI (match_operand:HI 1 "general_operand" "%0")
3081 (match_operand:HI 2 "general_operand" "di")))]
3082 ""
3083 "*
3084{
3085 check_label_emit ();
3086 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3087 if (GET_CODE (operands[2]) == CONST_INT)
3088 {
3089 mvs_check_page (0, 4, 0);
3090 return \"O %0,%2\";
3091 }
3092 mvs_check_page (0, 2, 0);
3093 return \"OR %0,%2\";
3094}"
3095 [(set_attr "length" "4")]
3096)
3097
3098;
3099; iorqi3 instruction pattern(s).
3100;
3101
3102(define_insn ""
3103 [(set (match_operand:QI 0 "r_or_s_operand" "=d,m")
3104 (ior:QI (match_operand:QI 1 "r_or_s_operand" "%0,0")
3105 (match_operand:QI 2 "r_or_s_operand" "di,mi")))]
3106 "TARGET_CHAR_INSTRUCTIONS"
3107 "*
3108{
3109 check_label_emit ();
3110 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3111 if (REG_P (operands[2]))
3112 {
3113 mvs_check_page (0, 2, 0);
3114 return \"OR %0,%2\";
3115 }
3116 if (REG_P (operands[0]))
3117 {
3118 mvs_check_page (0, 4, 0);
3119 return \"O %0,%2\";
3120 }
3121 if (GET_CODE (operands[2]) == CONST_INT)
3122 {
3123 mvs_check_page (0, 4, 0);
3124 return \"OI %0,%B2\";
3125 }
3126 mvs_check_page (0, 6, 0);
3127 return \"OC %O0(1,%R0),%2\";
3128}"
3129 [(set_attr "length" "6")]
3130)
3131
3132(define_insn "iorqi3"
3133 [(set (match_operand:QI 0 "general_operand" "=d")
3134 (ior:QI (match_operand:QI 1 "general_operand" "%0")
3135 (match_operand:QI 2 "general_operand" "di")))]
3136 ""
3137 "*
3138{
3139 check_label_emit ();
3140 CC_STATUS_INIT; /* OR sets CC but not how we want it */
3141 if (GET_CODE (operands[2]) == CONST_INT)
3142 {
3143 mvs_check_page (0, 4, 0);
3144 return \"O %0,%2\";
3145 }
3146 mvs_check_page (0, 2, 0);
3147 return \"OR %0,%2\";
3148}"
3149 [(set_attr "length" "4")]
3150)
3151
3152;;
3153;;- Xor instructions.
3154;;
3155
3156;
3157; xordi3 instruction pattern(s).
3158;
3159
3160;(define_expand "xordi3"
3161; [(set (match_operand:DI 0 "general_operand" "")
3162; (xor:DI (match_operand:DI 1 "general_operand" "")
3163; (match_operand:DI 2 "general_operand" "")))]
3164; ""
3165; "
3166;{
3167; rtx gen_xorsi3();
3168;
3169; emit_insn (gen_xorsi3 (operand_subword (operands[0], 0, 1, DImode),
3170; operand_subword (operands[1], 0, 1, DImode),
3171; operand_subword (operands[2], 0, 1, DImode)));
3172; emit_insn (gen_xorsi3 (gen_lowpart (SImode, operands[0]),
3173; gen_lowpart (SImode, operands[1]),
3174; gen_lowpart (SImode, operands[2])));
3175; DONE;
3176;}")
3177
3178;
3179; xorsi3 instruction pattern(s).
3180;
3181
3182(define_insn ""
3183 [(set (match_operand:SI 0 "r_or_s_operand" "=d,m")
3184 (xor:SI (match_operand:SI 1 "r_or_s_operand" "%0,0")
3185 (match_operand:SI 2 "r_or_s_operand" "g,mi")))]
3186 "TARGET_CHAR_INSTRUCTIONS"
3187 "*
3188{
3189 check_label_emit ();
3190 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3191 if (REG_P (operands[2]))
3192 {
3193 mvs_check_page (0, 2, 0);
3194 return \"XR %0,%2\";
3195 }
3196 if (REG_P (operands[0]))
3197 {
3198 mvs_check_page (0, 4, 0);
3199 return \"X %0,%2\";
3200 }
3201 mvs_check_page (0, 6, 0);
3202 return \"XC %O0(4,%R0),%2\";
3203}"
3204 [(set_attr "length" "6")]
3205)
3206
3207(define_insn "xorsi3"
3208 [(set (match_operand:SI 0 "general_operand" "=d")
3209 (xor:SI (match_operand:SI 1 "general_operand" "%0")
3210 (match_operand:SI 2 "general_operand" "g")))]
3211 ""
3212 "*
3213{
3214 check_label_emit ();
3215 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3216 if (REG_P (operands[2]))
3217 {
3218 mvs_check_page (0, 2, 0);
3219 return \"XR %0,%2\";
3220 }
3221 mvs_check_page (0, 4, 0);
3222 return \"X %0,%2\";
3223}"
3224 [(set_attr "length" "4")]
3225)
3226
3227;
3228; xorhi3 instruction pattern(s).
3229;
3230
3231(define_insn ""
3232 [(set (match_operand:HI 0 "r_or_s_operand" "=d,m")
3233 (xor:HI (match_operand:HI 1 "r_or_s_operand" "%0,0")
3234 (match_operand:HI 2 "r_or_s_operand" "di,mi")))]
3235 "TARGET_CHAR_INSTRUCTIONS"
3236 "*
3237{
3238 check_label_emit ();
3239 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3240 if (REG_P (operands[2]))
3241 {
3242 mvs_check_page (0, 2, 0);
3243 return \"XR %0,%2\";
3244 }
3245 if (REG_P (operands[0]))
3246 {
3247 mvs_check_page (0, 4, 0);
3248 return \"X %0,%H2\";
3249 }
3250 if (GET_CODE (operands[2]) == CONST_INT)
3251 {
3252 mvs_check_page (0, 6, 0);
3253 return \"XC %O0(2,%R0),%H2\";
3254 }
3255 mvs_check_page (0, 6, 0);
3256 return \"XC %O0(2,%R0),%2\";
3257}"
3258 [(set_attr "length" "6")]
3259)
3260
3261(define_insn "xorhi3"
3262 [(set (match_operand:HI 0 "general_operand" "=d")
3263 (xor:HI (match_operand:HI 1 "general_operand" "%0")
3264 (match_operand:HI 2 "general_operand" "di")))]
3265 ""
3266 "*
3267{
3268 check_label_emit ();
3269 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3270 if (GET_CODE (operands[2]) == CONST_INT)
3271 {
3272 mvs_check_page (0, 4, 0);
3273 return \"X %0,%H2\";
3274 }
3275 mvs_check_page (0, 2, 0);
3276 return \"XR %0,%2\";
3277}"
3278 [(set_attr "length" "4")]
3279)
3280
3281;
3282; xorqi3 instruction pattern(s).
3283;
3284
3285(define_insn ""
3286 [(set (match_operand:QI 0 "r_or_s_operand" "=d,m")
3287 (xor:QI (match_operand:QI 1 "r_or_s_operand" "%0,0")
3288 (match_operand:QI 2 "r_or_s_operand" "di,mi")))]
3289 "TARGET_CHAR_INSTRUCTIONS"
3290 "*
3291{
3292 check_label_emit ();
3293 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3294 if (REG_P (operands[2]))
3295 {
3296 mvs_check_page (0, 2, 0);
3297 return \"XR %0,%2\";
3298 }
3299 if (REG_P (operands[0]))
3300 {
3301 mvs_check_page (0, 4, 0);
3302 return \"X %0,%2\";
3303 }
3304 if (GET_CODE (operands[2]) == CONST_INT)
3305 {
3306 mvs_check_page (0, 4, 0);
3307 return \"XI %0,%B2\";
3308 }
3309 mvs_check_page (0, 6, 0);
3310 return \"XC %O0(1,%R0),%2\";
3311}"
3312 [(set_attr "length" "6")]
3313)
3314
3315(define_insn "xorqi3"
3316 [(set (match_operand:QI 0 "general_operand" "=d")
3317 (xor:QI (match_operand:QI 1 "general_operand" "%0")
3318 (match_operand:QI 2 "general_operand" "di")))]
3319 ""
3320 "*
3321{
3322 check_label_emit ();
3323 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3324 if (GET_CODE (operands[2]) == CONST_INT)
3325 {
3326 mvs_check_page (0, 4, 0);
3327 return \"X %0,%2\";
3328 }
3329 mvs_check_page (0, 2, 0);
3330 return \"XR %0,%2\";
3331}"
3332 [(set_attr "length" "4")]
3333)
3334
3335;;
3336;;- Negate instructions.
3337;;
3338
3339;
3340; negsi2 instruction pattern(s).
3341;
3342
3343(define_insn "negsi2"
3344 [(set (match_operand:SI 0 "general_operand" "=d")
3345 (neg:SI (match_operand:SI 1 "general_operand" "d")))]
3346 ""
3347 "*
3348{
3349 check_label_emit ();
3350 mvs_check_page (0, 2, 0);
3351 return \"LCR %0,%1\";
3352}"
3353 [(set_attr "length" "2")]
3354)
3355
3356;
3357; neghi2 instruction pattern(s).
3358;
3359
3360(define_insn "neghi2"
3361 [(set (match_operand:HI 0 "general_operand" "=d")
3362 (neg:HI (match_operand:HI 1 "general_operand" "d")))]
3363 ""
3364 "*
3365{
3366 check_label_emit ();
3367 mvs_check_page (0, 10, 0);
3368 return \"SLL %1,16\;SRA %1,16\;LCR %0,%1\";
3369}"
3370 [(set_attr "length" "10")]
3371)
3372
3373;
3374; negdf2 instruction pattern(s).
3375;
3376
3377(define_insn "negdf2"
3378 [(set (match_operand:DF 0 "general_operand" "=f")
3379 (neg:DF (match_operand:DF 1 "general_operand" "f")))]
3380 ""
3381 "*
3382{
3383 check_label_emit ();
3384 mvs_check_page (0, 2, 0);
3385 return \"LCDR %0,%1\";
3386}"
3387 [(set_attr "length" "2")]
3388)
3389
3390;
3391; negsf2 instruction pattern(s).
3392;
3393
3394(define_insn "negsf2"
3395 [(set (match_operand:SF 0 "general_operand" "=f")
3396 (neg:SF (match_operand:SF 1 "general_operand" "f")))]
3397 ""
3398 "*
3399{
3400 check_label_emit ();
3401 mvs_check_page (0, 2, 0);
3402 return \"LCER %0,%1\";
3403}"
3404 [(set_attr "length" "2")]
3405)
3406
3407;;
3408;;- Absolute value instructions.
3409;;
3410
3411;
3412; abssi2 instruction pattern(s).
3413;
3414
3415(define_insn "abssi2"
3416 [(set (match_operand:SI 0 "general_operand" "=d")
3417 (abs:SI (match_operand:SI 1 "general_operand" "d")))]
3418 ""
3419 "*
3420{
3421 check_label_emit ();
3422 mvs_check_page (0, 2, 0);
3423 return \"LPR %0,%1\";
3424}"
3425 [(set_attr "length" "2")]
3426)
3427
3428;
3429; abshi2 instruction pattern(s).
3430;
3431
3432(define_insn "abshi2"
3433 [(set (match_operand:HI 0 "general_operand" "=d")
3434 (abs:HI (match_operand:HI 1 "general_operand" "d")))]
3435 ""
3436 "*
3437{
3438 check_label_emit ();
3439 mvs_check_page (0, 10, 0);
3440 return \"SLL %1,16\;SRA %1,16\;LPR %0,%1\";
3441}"
3442 [(set_attr "length" "10")]
3443)
3444
3445;
3446; absdf2 instruction pattern(s).
3447;
3448
3449(define_insn "absdf2"
3450 [(set (match_operand:DF 0 "general_operand" "=f")
3451 (abs:DF (match_operand:DF 1 "general_operand" "f")))]
3452 ""
3453 "*
3454{
3455 check_label_emit ();
3456 mvs_check_page (0, 2, 0);
3457 return \"LPDR %0,%1\";
3458}"
3459 [(set_attr "length" "2")]
3460)
3461
3462;
3463; abssf2 instruction pattern(s).
3464;
3465
3466(define_insn "abssf2"
3467 [(set (match_operand:SF 0 "general_operand" "=f")
3468 (abs:SF (match_operand:SF 1 "general_operand" "f")))]
3469 ""
3470 "*
3471{
3472 check_label_emit ();
3473 mvs_check_page (0, 2, 0);
3474 return \"LPER %0,%1\";
3475}"
3476 [(set_attr "length" "2")]
3477)
3478
3479;;
3480;;- One complement instructions.
3481;;
3482
3483;
3484; one_cmpldi2 instruction pattern(s).
3485;
3486
3487;(define_expand "one_cmpldi2"
3488; [(set (match_operand:DI 0 "general_operand" "")
3489; (not:DI (match_operand:DI 1 "general_operand" "")))]
3490; ""
3491; "
3492;{
3493; rtx gen_one_cmplsi2();
3494;
3495; emit_insn (gen_one_cmplsi2 (operand_subword (operands[0], 0, 1, DImode),
3496; operand_subword (operands[1], 0, 1, DImode)));
3497; emit_insn (gen_one_cmplsi2 (gen_lowpart (SImode, operands[0]),
3498; gen_lowpart (SImode, operands[1])));
3499; DONE;
3500;}")
3501
3502;
3503; one_cmplsi2 instruction pattern(s).
3504;
3505
3506(define_insn ""
3507 [(set (match_operand:SI 0 "r_or_s_operand" "=dm")
3508 (not:SI (match_operand:SI 1 "r_or_s_operand" "0")))]
3509 "TARGET_CHAR_INSTRUCTIONS"
3510 "*
3511{
3512 check_label_emit ();
3513 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3514 if (REG_P (operands[0]))
3515 {
3516 mvs_check_page (0, 4, 4);
3517 return \"X %0,=F'-1'\";
3518 }
3519 CC_STATUS_INIT;
3520 mvs_check_page (0, 6, 4);
3521 return \"XC %O0(4,%R0),=F'-1'\";
3522}"
3523 [(set_attr "length" "6")]
3524)
3525
3526(define_insn "one_cmplsi2"
3527 [(set (match_operand:SI 0 "general_operand" "=d")
3528 (not:SI (match_operand:SI 1 "general_operand" "0")))]
3529 ""
3530 "*
3531{
3532 check_label_emit ();
3533 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3534 mvs_check_page (0, 4, 4);
3535 return \"X %0,=F'-1'\";
3536}"
3537 [(set_attr "length" "4")]
3538)
3539
3540;
3541; one_cmplhi2 instruction pattern(s).
3542;
3543
3544(define_insn ""
3545 [(set (match_operand:HI 0 "r_or_s_operand" "=dm")
3546 (not:HI (match_operand:HI 1 "r_or_s_operand" "0")))]
3547 "TARGET_CHAR_INSTRUCTIONS"
3548 "*
3549{
3550 check_label_emit ();
3551 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3552 if (REG_P (operands[0]))
3553 {
3554 mvs_check_page (0, 4, 4);
3555 return \"X %0,=F'-1'\";
3556 }
3557 mvs_check_page (0, 6, 4);
3558 return \"XC %O0(2,%R0),=XL4'FFFF'\";
3559}"
3560 [(set_attr "length" "6")]
3561)
3562
3563(define_insn "one_cmplhi2"
3564 [(set (match_operand:HI 0 "general_operand" "=d")
3565 (not:HI (match_operand:HI 1 "general_operand" "0")))]
3566 ""
3567 "*
3568{
3569 check_label_emit ();
3570 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3571 mvs_check_page (0, 4, 4);
3572 return \"X %0,=F'-1'\";
3573}"
3574 [(set_attr "length" "4")]
3575)
3576
3577;
3578; one_cmplqi2 instruction pattern(s).
3579;
3580
3581(define_insn ""
3582 [(set (match_operand:QI 0 "r_or_s_operand" "=dm")
3583 (not:QI (match_operand:QI 1 "r_or_s_operand" "0")))]
3584 "TARGET_CHAR_INSTRUCTIONS"
3585 "*
3586{
3587 check_label_emit ();
3588 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3589 if (REG_P (operands[0]))
3590 {
3591 mvs_check_page (0, 4, 4);
3592 return \"X %0,=F'-1'\";
3593 }
3594 mvs_check_page (0, 4, 0);
3595 return \"XI %0,255\";
3596}"
3597 [(set_attr "length" "4")]
3598)
3599
3600(define_insn "one_cmplqi2"
3601 [(set (match_operand:QI 0 "general_operand" "=d")
3602 (not:QI (match_operand:QI 1 "general_operand" "0")))]
3603 ""
3604 "*
3605{
3606 check_label_emit ();
3607 CC_STATUS_INIT; /* XOR sets CC but not how we want it */
3608 mvs_check_page (0, 4, 4);
3609 return \"X %0,=F'-1'\";
3610}"
3611 [(set_attr "length" "4")]
3612)
3613
3614;;
3615;;- Arithmetic shift instructions.
3616;;
3617
3618;
3619; ashldi3 instruction pattern(s).
3620;
3621
3622(define_insn "ashldi3"
3623 [(set (match_operand:DI 0 "general_operand" "=d")
3624 (ashift:DI (match_operand:DI 1 "general_operand" "0")
3625 (match_operand:SI 2 "general_operand" "Ja")))]
3626 ""
3627 "*
3628{
3629 check_label_emit ();
3630 /* this status set seems not have the desired effect,
3631 * proably because the 64-bit long-long test is emulated ?! */
3632 CC_STATUS_SET (operands[0], operands[1]);
3633 mvs_check_page (0, 4, 0);
3634 if (REG_P (operands[2]))
3635 return \"SLDA %0,0(%2)\";
3636 return \"SLDA %0,%c2\";
3637}"
3638 [(set_attr "length" "4")]
3639)
3640
3641;
3642; ashrdi3 instruction pattern(s).
3643;
3644
3645(define_insn "ashrdi3"
3646 [(set (match_operand:DI 0 "register_operand" "=d")
3647 (ashiftrt:DI (match_operand:DI 1 "general_operand" "0")
3648 (match_operand:SI 2 "general_operand" "Ja")))]
3649 ""
3650 "*
3651{
3652 check_label_emit ();
3653 /* this status set seems not have the desired effect,
3654 * proably because the 64-bit long-long test is emulated ?! */
3655 CC_STATUS_SET (operands[0], operands[1]);
3656 mvs_check_page (0, 4, 0);
3657 if (REG_P (operands[2]))
3658 return \"SRDA %0,0(%2)\";
3659 return \"SRDA %0,%c2\";
3660}"
3661 [(set_attr "length" "4")]
3662)
3663
3664;
3665; ashlsi3 instruction pattern(s).
3666;
3667
3668(define_insn "ashlsi3"
3669 [(set (match_operand:SI 0 "general_operand" "=d")
3670 (ashift:SI (match_operand:SI 1 "general_operand" "0")
3671 (match_operand:SI 2 "general_operand" "Ja")))]
3672 ""
3673 "*
3674{
3675 check_label_emit ();
3676 mvs_check_page (0, 4, 0);
3677 if (REG_P (operands[2]))
3678 return \"SLL %0,0(%2)\";
3679 return \"SLL %0,%c2\";
3680}"
3681 [(set_attr "length" "4")]
3682)
3683
3684;
3685; ashrsi3 instruction pattern(s).
3686;
3687
3688(define_insn "ashrsi3"
3689 [(set (match_operand:SI 0 "general_operand" "=d")
3690 (ashiftrt:SI (match_operand:SI 1 "general_operand" "0")
3691 (match_operand:SI 2 "general_operand" "Ja")))]
3692 ""
3693 "*
3694{
3695 check_label_emit ();
3696 CC_STATUS_SET (operands[0], operands[1]);
3697 mvs_check_page (0, 4, 0);
3698 if (REG_P (operands[2]))
3699 return \"SRA %0,0(%2)\";
3700 return \"SRA %0,%c2\";
3701}"
3702 [(set_attr "length" "4")]
3703)
3704
3705;
3706; ashlhi3 instruction pattern(s).
3707;
3708
3709(define_insn "ashlhi3"
3710 [(set (match_operand:HI 0 "general_operand" "=d")
3711 (ashift:HI (match_operand:HI 1 "general_operand" "0")
3712 (match_operand:SI 2 "general_operand" "Ja")))]
3713 ""
3714 "*
3715{
3716 check_label_emit ();
3717 mvs_check_page (0, 8, 0);
3718 if (REG_P (operands[2]))
3719 return \"SLL %0,16(%2)\;SRA %0,16\";
3720 return \"SLL %0,16+%c2\;SRA %0,16\";
3721}"
3722 [(set_attr "length" "8")]
3723)
3724
3725;
3726; ashrhi3 instruction pattern(s).
3727;
3728
3729(define_insn "ashrhi3"
3730 [(set (match_operand:HI 0 "general_operand" "=d")
3731 (ashiftrt:HI (match_operand:HI 1 "general_operand" "0")
3732 (match_operand:SI 2 "general_operand" "Ja")))]
3733 ""
3734 "*
3735{
3736 check_label_emit ();
3737 mvs_check_page (0, 8, 0);
3738 if (REG_P (operands[2]))
3739 return \"SLL %0,16\;SRA %0,16(%2)\";
3740 return \"SLL %0,16\;SRA %0,16+%c2\";
3741}"
3742 [(set_attr "length" "8")]
3743)
3744
3745;
3746; ashlqi3 instruction pattern(s).
3747;
3748
3749(define_insn "ashlqi3"
3750 [(set (match_operand:QI 0 "general_operand" "=d")
3751 (ashift:QI (match_operand:QI 1 "general_operand" "0")
3752 (match_operand:SI 2 "general_operand" "Ja")))]
3753 ""
3754 "*
3755{
3756 check_label_emit ();
3757 mvs_check_page (0, 4, 0);
3758 if (REG_P (operands[2]))
3759 return \"SLL %0,0(%2)\";
3760 return \"SLL %0,%c2\";
3761}"
3762 [(set_attr "length" "4")]
3763)
3764
3765;
3766; ashrqi3 instruction pattern(s).
3767;
3768
3769(define_insn "ashrqi3"
3770 [(set (match_operand:QI 0 "general_operand" "=d")
3771 (ashiftrt:QI (match_operand:QI 1 "general_operand" "0")
3772 (match_operand:SI 2 "general_operand" "Ja")))]
3773 ""
3774 "*
3775{
3776 check_label_emit ();
3777 mvs_check_page (0, 8, 0);
3778 if (REG_P (operands[2]))
3779 return \"SLL %0,24\;SRA %0,24(%2)\";
3780 return \"SLL %0,24\;SRA %0,24+%c2\";
3781}"
3782 [(set_attr "length" "8")]
3783)
3784
3785;;
3786;;- Logical shift instructions.
3787;;
3788
3789;
3790; lshrdi3 instruction pattern(s).
3791;
3792
3793(define_insn "lshrdi3"
3794 [(set (match_operand:DI 0 "general_operand" "=d")
3795 (lshiftrt:DI (match_operand:DI 1 "general_operand" "0")
3796 (match_operand:SI 2 "general_operand" "Ja")))]
3797 ""
3798 "*
3799{
3800 check_label_emit ();
3801 mvs_check_page (0, 4, 0);
3802 if (REG_P (operands[2]))
3803 return \"SRDL %0,0(%2)\";
3804 return \"SRDL %0,%c2\";
3805}"
3806 [(set_attr "length" "4")]
3807)
3808
3809
3810;
3811; lshrsi3 instruction pattern(s).
3812;
3813
3814(define_insn "lshrsi3"
3815 [(set (match_operand:SI 0 "general_operand" "=d")
3816 (lshiftrt:SI (match_operand:SI 1 "general_operand" "0")
3817 (match_operand:SI 2 "general_operand" "Ja")))]
3818 ""
3819 "*
3820{
3821 check_label_emit ();
3822 mvs_check_page (0, 4, 0);
3823 if (REG_P (operands[2]))
3824 return \"SRL %0,0(%2)\";
3825 return \"SRL %0,%c2\";
3826}"
3827 [(set_attr "length" "4")]
3828)
3829
3830;
3831; lshrhi3 instruction pattern(s).
3832;
3833
3834(define_insn "lshrhi3"
3835 [(set (match_operand:HI 0 "general_operand" "=d")
3836 (lshiftrt:HI (match_operand:HI 1 "general_operand" "0")
3837 (match_operand:SI 2 "general_operand" "Ja")))]
3838 ""
3839 "*
3840{
3841 check_label_emit ();
3842 CC_STATUS_INIT; /* AND sets the CC but not how we want it */
3843 if (REG_P (operands[2]))
3844 {
3845 mvs_check_page (0, 8, 4);
3846 return \"N %0,=XL4'0000FFFF'\;SRL %0,0(%2)\";
3847 }
3848 mvs_check_page (0, 8, 4);
3849 return \"N %0,=XL4'0000FFFF'\;SRL %0,%c2\";
3850}"
3851 [(set_attr "length" "8")]
3852)
3853
3854;
3855; lshrqi3 instruction pattern(s).
3856;
3857
3858(define_insn "lshrqi3"
3859 [(set (match_operand:QI 0 "general_operand" "=d")
3860 (lshiftrt:QI (match_operand:QI 1 "general_operand" "0")
3861 (match_operand:SI 2 "general_operand" "Ja")))]
3862 ""
3863 "*
3864{
3865 check_label_emit ();
3866 CC_STATUS_INIT; /* AND sets the CC but not how we want it */
3867 mvs_check_page (0, 8, 4);
3868 if (REG_P (operands[2]))
3869 return \"N %0,=XL4'000000FF'\;SRL %0,0(%2)\";
3870 return \"N %0,=XL4'000000FF'\;SRL %0,%c2\";
3871}"
3872 [(set_attr "length" "8")]
3873)
3874
3875;; =======================================================================
3876;;- Conditional jump instructions.
3877;; =======================================================================
3878
3879;
3880; beq instruction pattern(s).
3881;
3882
3883(define_insn "beq"
3884 [(set (pc)
3885 (if_then_else (eq (cc0)
3886 (const_int 0))
3887 (label_ref (match_operand 0 "" ""))
3888 (pc)))
3889; (clobber (reg:SI 14))
3890 ]
3891 ""
3892 "*
3893{
3894 check_label_emit ();
3895 mvs_check_page (0, 4, 0);
3896 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
3897 {
3898 return \"BE %l0\";
3899 }
3900 mvs_check_page (0, 2, 4);
3901 return \"L 14,=A(%l0)\;BER 14\";
3902}"
3903 [(set_attr "length" "6")]
3904)
3905
3906;
3907; bne instruction pattern(s).
3908;
3909
3910(define_insn "bne"
3911 [(set (pc)
3912 (if_then_else (ne (cc0)
3913 (const_int 0))
3914 (label_ref (match_operand 0 "" ""))
3915 (pc)))
3916; (clobber (reg:SI 14))
3917 ]
3918 ""
3919 "*
3920{
3921 check_label_emit ();
3922 mvs_check_page (0, 4, 0);
3923 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
3924 {
3925 return \"BNE %l0\";
3926 }
3927 mvs_check_page (0, 2, 4);
3928 return \"L 14,=A(%l0)\;BNER 14\";
3929}"
3930 [(set_attr "length" "6")]
3931)
3932
3933;
3934; bgt instruction pattern(s).
3935;
3936
3937(define_insn "bgt"
3938 [(set (pc)
3939 (if_then_else (gt (cc0)
3940 (const_int 0))
3941 (label_ref (match_operand 0 "" ""))
3942 (pc)))
3943; (clobber (reg:SI 14))
3944 ]
3945 ""
3946 "*
3947{
3948 check_label_emit ();
3949 mvs_check_page (0, 4, 0);
3950 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
3951 {
3952 return \"BH %l0\";
3953 }
3954 mvs_check_page (0, 2, 4);
3955 return \"L 14,=A(%l0)\;BHR 14\";
3956}"
3957 [(set_attr "length" "6")]
3958)
3959
3960;
3961; bgtu instruction pattern(s).
3962;
3963
3964(define_insn "bgtu"
3965 [(set (pc)
3966 (if_then_else (gtu (cc0)
3967 (const_int 0))
3968 (label_ref (match_operand 0 "" ""))
3969 (pc)))
3970; (clobber (reg:SI 14))
3971 ]
3972 ""
3973 "*
3974{
3975 check_label_emit ();
3976 mvs_check_page (0, 4, 0);
3977 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
3978 {
3979 return \"BH %l0\";
3980 }
3981 mvs_check_page (0, 2, 4);
3982 return \"L 14,=A(%l0)\;BHR 14\";
3983}"
3984 [(set_attr "length" "6")]
3985)
3986
3987;
3988; blt instruction pattern(s).
3989;
3990
3991(define_insn "blt"
3992 [(set (pc)
3993 (if_then_else (lt (cc0)
3994 (const_int 0))
3995 (label_ref (match_operand 0 "" ""))
3996 (pc)))
3997; (clobber (reg:SI 14))
3998 ]
3999 ""
4000 "*
4001{
4002 check_label_emit ();
4003 mvs_check_page (0, 4, 0);
4004 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4005 {
4006 return \"BL %l0\";
4007 }
4008 mvs_check_page (0, 2, 4);
4009 return \"L 14,=A(%l0)\;BLR 14\";
4010}"
4011 [(set_attr "length" "6")]
4012)
4013
4014;
4015; bltu instruction pattern(s).
4016;
4017
4018(define_insn "bltu"
4019 [(set (pc)
4020 (if_then_else (ltu (cc0)
4021 (const_int 0))
4022 (label_ref (match_operand 0 "" ""))
4023 (pc)))
4024; (clobber (reg:SI 14))
4025 ]
4026 ""
4027 "*
4028{
4029 check_label_emit ();
4030 mvs_check_page (0, 4, 0);
4031 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4032 {
4033 return \"BL %l0\";
4034 }
4035 mvs_check_page (0, 2, 4);
4036 return \"L 14,=A(%l0)\;BLR 14\";
4037}"
4038 [(set_attr "length" "6")]
4039)
4040
4041;
4042; bge instruction pattern(s).
4043;
4044
4045(define_insn "bge"
4046 [(set (pc)
4047 (if_then_else (ge (cc0)
4048 (const_int 0))
4049 (label_ref (match_operand 0 "" ""))
4050 (pc)))
4051; (clobber (reg:SI 14))
4052 ]
4053 ""
4054 "*
4055{
4056 check_label_emit ();
4057 mvs_check_page (0, 4, 0);
4058 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4059 {
4060 return \"BNL %l0\";
4061 }
4062 mvs_check_page (0, 2, 4);
4063 return \"L 14,=A(%l0)\;BNLR 14\";
4064}"
4065 [(set_attr "length" "6")]
4066)
4067
4068;
4069; bgeu instruction pattern(s).
4070;
4071
4072(define_insn "bgeu"
4073 [(set (pc)
4074 (if_then_else (geu (cc0)
4075 (const_int 0))
4076 (label_ref (match_operand 0 "" ""))
4077 (pc)))
4078; (clobber (reg:SI 14))
4079 ]
4080 ""
4081 "*
4082{
4083 check_label_emit ();
4084 mvs_check_page (0, 4, 0);
4085 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4086 {
4087 return \"BNL %l0\";
4088 }
4089 mvs_check_page (0, 2, 4);
4090 return \"L 14,=A(%l0)\;BNLR 14\";
4091}"
4092 [(set_attr "length" "6")]
4093)
4094
4095;
4096; ble instruction pattern(s).
4097;
4098
4099(define_insn "ble"
4100 [(set (pc)
4101 (if_then_else (le (cc0)
4102 (const_int 0))
4103 (label_ref (match_operand 0 "" ""))
4104 (pc)))
4105; (clobber (reg:SI 14))
4106 ]
4107 ""
4108 "*
4109{
4110 check_label_emit ();
4111 mvs_check_page (0, 4, 0);
4112 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4113 {
4114 return \"BNH %l0\";
4115 }
4116 mvs_check_page (0, 2, 4);
4117 return \"L 14,=A(%l0)\;BNHR 14\";
4118}"
4119 [(set_attr "length" "6")]
4120)
4121
4122;
4123; bleu instruction pattern(s).
4124;
4125
4126(define_insn "bleu"
4127 [(set (pc)
4128 (if_then_else (leu (cc0)
4129 (const_int 0))
4130 (label_ref (match_operand 0 "" ""))
4131 (pc)))
4132; (clobber (reg:SI 14))
4133 ]
4134 ""
4135 "*
4136{
4137 check_label_emit ();
4138 mvs_check_page (0, 4, 0);
4139 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4140 {
4141 return \"BNH %l0\";
4142 }
4143 mvs_check_page (0, 2, 4);
4144 return \"L 14,=A(%l0)\;BNHR 14\";
4145}"
4146 [(set_attr "length" "6")]
4147)
4148
4149;;
4150;;- Negated conditional jump instructions.
4151;;
4152
4153(define_insn ""
4154 [(set (pc)
4155 (if_then_else (eq (cc0)
4156 (const_int 0))
4157 (pc)
4158 (label_ref (match_operand 0 "" ""))))
4159; (clobber (reg:SI 14))
4160 ]
4161 ""
4162 "*
4163{
4164 check_label_emit ();
4165 mvs_check_page (0, 4, 0);
4166 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4167 {
4168 return \"BNE %l0\";
4169 }
4170 mvs_check_page (0, 2, 4);
4171 return \"L 14,=A(%l0)\;BNER 14\";
4172}"
4173 [(set_attr "length" "6")]
4174)
4175
4176(define_insn ""
4177 [(set (pc)
4178 (if_then_else (ne (cc0)
4179 (const_int 0))
4180 (pc)
4181 (label_ref (match_operand 0 "" ""))))
4182; (clobber (reg:SI 14))
4183 ]
4184 ""
4185 "*
4186{
4187 check_label_emit ();
4188 mvs_check_page (0, 4, 0);
4189 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4190 {
4191 return \"BE %l0\";
4192 }
4193 mvs_check_page (0, 2, 4);
4194 return \"L 14,=A(%l0)\;BER 14\";
4195}"
4196 [(set_attr "length" "6")]
4197)
4198
4199(define_insn ""
4200 [(set (pc)
4201 (if_then_else (gt (cc0)
4202 (const_int 0))
4203 (pc)
4204 (label_ref (match_operand 0 "" ""))))
4205; (clobber (reg:SI 14))
4206 ]
4207 ""
4208 "*
4209{
4210 check_label_emit ();
4211 mvs_check_page (0, 4, 0);
4212 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4213 {
4214 return \"BNH %l0\";
4215 }
4216 mvs_check_page (0, 2, 4);
4217 return \"L 14,=A(%l0)\;BNHR 14\";
4218}"
4219 [(set_attr "length" "6")]
4220)
4221
4222(define_insn ""
4223 [(set (pc)
4224 (if_then_else (gtu (cc0)
4225 (const_int 0))
4226 (pc)
4227 (label_ref (match_operand 0 "" ""))))
4228; (clobber (reg:SI 14))
4229 ]
4230 ""
4231 "*
4232{
4233 check_label_emit ();
4234 mvs_check_page (0, 4, 0);
4235 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4236 {
4237 return \"BNH %l0\";
4238 }
4239 mvs_check_page (0, 2, 4);
4240 return \"L 14,=A(%l0)\;BNHR 14\";
4241}"
4242 [(set_attr "length" "6")]
4243)
4244
4245(define_insn ""
4246 [(set (pc)
4247 (if_then_else (lt (cc0)
4248 (const_int 0))
4249 (pc)
4250 (label_ref (match_operand 0 "" ""))))
4251; (clobber (reg:SI 14))
4252 ]
4253 ""
4254 "*
4255{
4256 check_label_emit ();
4257 mvs_check_page (0, 4, 0);
4258 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4259 {
4260 return \"BNL %l0\";
4261 }
4262 mvs_check_page (0, 2, 4);
4263 return \"L 14,=A(%l0)\;BNLR 14\";
4264}"
4265 [(set_attr "length" "6")]
4266)
4267
4268(define_insn ""
4269 [(set (pc)
4270 (if_then_else (ltu (cc0)
4271 (const_int 0))
4272 (pc)
4273 (label_ref (match_operand 0 "" ""))))
4274; (clobber (reg:SI 14))
4275 ]
4276 ""
4277 "*
4278{
4279 check_label_emit ();
4280 mvs_check_page (0, 4, 0);
4281 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4282 {
4283 return \"BNL %l0\";
4284 }
4285 mvs_check_page (0, 2, 4);
4286 return \"L 14,=A(%l0)\;BNLR 14\";
4287}"
4288 [(set_attr "length" "6")]
4289)
4290
4291(define_insn ""
4292 [(set (pc)
4293 (if_then_else (ge (cc0)
4294 (const_int 0))
4295 (pc)
4296 (label_ref (match_operand 0 "" ""))))
4297; (clobber (reg:SI 14))
4298 ]
4299 ""
4300 "*
4301{
4302 check_label_emit ();
4303 mvs_check_page (0, 4, 0);
4304 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4305 {
4306 return \"BL %l0\";
4307 }
4308 mvs_check_page (0, 2, 4);
4309 return \"L 14,=A(%l0)\;BLR 14\";
4310}"
4311 [(set_attr "length" "6")]
4312)
4313
4314(define_insn ""
4315 [(set (pc)
4316 (if_then_else (geu (cc0)
4317 (const_int 0))
4318 (pc)
4319 (label_ref (match_operand 0 "" ""))))
4320; (clobber (reg:SI 14))
4321 ]
4322 ""
4323 "*
4324{
4325 check_label_emit ();
4326 mvs_check_page (0, 4, 0);
4327 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4328 {
4329 return \"BL %l0\";
4330 }
4331 mvs_check_page (0, 2, 4);
4332 return \"L 14,=A(%l0)\;BLR 14\";
4333}"
4334 [(set_attr "length" "6")]
4335)
4336
4337(define_insn ""
4338 [(set (pc)
4339 (if_then_else (le (cc0)
4340 (const_int 0))
4341 (pc)
4342 (label_ref (match_operand 0 "" ""))))
4343; (clobber (reg:SI 14))
4344 ]
4345 ""
4346 "*
4347{
4348 check_label_emit ();
4349 mvs_check_page (0, 4, 0);
4350 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4351 {
4352 return \"BH %l0\";
4353 }
4354 mvs_check_page (0, 2, 4);
4355 return \"L 14,=A(%l0)\;BHR 14\";
4356}"
4357 [(set_attr "length" "6")]
4358)
4359
4360(define_insn ""
4361 [(set (pc)
4362 (if_then_else (leu (cc0)
4363 (const_int 0))
4364 (pc)
4365 (label_ref (match_operand 0 "" ""))))
4366; (clobber (reg:SI 14))
4367 ]
4368 ""
4369 "*
4370{
4371 check_label_emit ();
4372 mvs_check_page (0, 4, 0);
4373 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4374 {
4375 return \"BH %l0\";
4376 }
4377 mvs_check_page (0, 2, 4);
4378 return \"L 14,=A(%l0)\;BHR 14\";
4379}"
4380 [(set_attr "length" "6")]
4381)
4382
4383;; ==============================================================
4384;;- Subtract one and jump if not zero.
4385;; These insns seem to not be getting matched ...
4386;; XXX should fix this, as it would improve for loops
4387
4388(define_insn ""
4389 [(set (pc)
4390 (if_then_else
4391 (ne (plus:SI (match_operand:SI 0 "register_operand" "+d")
4392 (const_int -1))
4393 (const_int 0))
4394 (label_ref (match_operand 1 "" ""))
4395 (pc)))
4396 (set (match_dup 0)
4397 (plus:SI (match_dup 0)
4398 (const_int -1)))
4399; (clobber (reg:SI 14))
4400 ]
4401 ""
4402 "*
4403{
4404 check_label_emit ();
4405 mvs_check_page (0, 4, 0);
4406 if (mvs_check_label (CODE_LABEL_NUMBER (operands[1])))
4407 {
4408 return \"BCT %0,%l1\";
4409 }
4410 mvs_check_page (0, 2, 4);
4411 return \"L 14,=A(%l1)\;BCTR %0,14\";
4412}"
4413 [(set_attr "length" "6")]
4414)
4415
4416(define_insn ""
4417 [(set (pc)
4418 (if_then_else
4419 (eq (plus:SI (match_operand:SI 0 "register_operand" "+d")
4420 (const_int -1))
4421 (const_int 0))
4422 (pc)
4423 (label_ref (match_operand 1 "" ""))))
4424 (set (match_dup 0)
4425 (plus:SI (match_dup 0)
4426 (const_int -1)))
4427; (clobber (reg:SI 14))
4428 ]
4429 ""
4430 "*
4431{
4432 check_label_emit ();
4433 mvs_check_page (0, 4, 0);
4434 if (mvs_check_label (CODE_LABEL_NUMBER (operands[1])))
4435 {
4436 return \"BCT %0,%l1\";
4437 }
4438 mvs_check_page (0, 2, 4);
4439 return \"L 14,=A(%l1)\;BCTR %0,14\";
4440}"
4441 [(set_attr "length" "6")]
4442)
4443
4444;; =============================================================
4445;;- Unconditional jump instructions.
4446;;
4447
4448;
4449; jump instruction pattern(s).
4450;
4451
4452(define_insn "jump"
4453 [(set (pc)
4454 (label_ref (match_operand 0 "" "")))
4455; (clobber (reg:SI 14))
4456 ]
4457 ""
4458 "*
4459{
4460 check_label_emit ();
4461 mvs_check_page (0, 4, 0);
4462 if (i370_short_branch(insn) || mvs_check_label (CODE_LABEL_NUMBER (operands[0])))
4463 {
4464 return \"B %l0\";
4465 }
4466 mvs_check_page (0, 2, 4);
4467 return \"L 14,=A(%l0)\;BR 14\";
4468}"
4469 [(set_attr "length" "6")]
4470)
4471
4472;
4473; indirect-jump instruction pattern(s).
4474; hack alert -- should check that displacement is < 4096
4475
4476(define_insn "indirect_jump"
4477 [(set (pc) (match_operand:SI 0 "general_operand" "rm"))]
4478 ""
4479 "*
4480{
4481 check_label_emit ();
4482 if (REG_P (operands[0]))
4483 {
4484 mvs_check_page (0, 2, 0);
4485 return \"BR %0\";
4486 }
4487 mvs_check_page (0, 4, 0);
4488 return \"B %0\";
4489}"
4490 [(set_attr "length" "4")]
4491)
4492
4493;
4494; tablejump instruction pattern(s).
4495;
4496
4497(define_insn "tablejump"
4498 [(set (pc)
4499 (match_operand:SI 0 "general_operand" "am"))
4500 (use (label_ref (match_operand 1 "" "")))
4501; (clobber (reg:SI 14))
4502 ]
4503 ""
4504 "*
4505{
4506 check_label_emit ();
4507 if (REG_P (operands[0]))
4508 {
4509 mvs_check_page (0, 6, 0);
4510 return \"BR %0\;DS 0F\";
4511 }
4512 mvs_check_page (0, 10, 0);
4513 return \"L 14,%0\;BR 14\;DS 0F\";
4514}"
4515 [(set_attr "length" "10")]
4516)
4517
4518;;
4519;;- Jump to subroutine.
4520;;
4521;; For the C/370 environment the internal functions, ie. sqrt, are called with
4522;; a non-standard form. So, we must fix it here. There's no BM like IBM.
4523;;
4524;; The ELF ABI is different from the C/370 ABI because we have a simpler,
4525;; more powerful way of dealing with structure-value returns. Basically,
4526;; we use R1 to point at structure returns (64-bit and larger returns)
4527;; and R11 to point at the args. Note that this handles double-precision
4528;; (64-bit) values just fine, in a less-kludged manner than the C/370 ABI.
4529;; Since R1 is used, we use R2 to pass the argument pointer to the routine.
4530
4531;
4532; call instruction pattern(s).
4533;
4534; We define four call instruction patterns below. The first two patterns,
4535; although general, end up matching (only?) calls through function pointers.
4536; The last two, which require a symbol-ref to match, get used for all
4537; ordinary subroutine calls.
4538
4539(define_insn "call"
4540 [(call (match_operand:QI 0 "memory_operand" "m")
4541 (match_operand:SI 1 "immediate_operand" "i"))
4542 (clobber (reg:SI 2))
4543 ]
4544 ""
4545 "*
4546{
4547 static char temp[128];
4548 int i = STACK_POINTER_OFFSET;
4549 CC_STATUS_INIT;
4550
4551 check_label_emit ();
4552#ifdef TARGET_ELF_ABI
4553 mvs_check_page (0, 10, 4);
4554 sprintf ( temp, \"LA r2,%d(,sp)\;LA 15,%%0\;BASR 14,15\", i );
4555 return temp;
4556#else
4557 if (mvs_function_check (XSTR (operands[0], 0)))
4558 {
4559 mvs_check_page (0, 22, 4);
4560 sprintf ( temp, \"LA 1,136(,13)\;ST 1,%d(,13)\;LA 1,%d(,13)\;LA 15,%%0\;BALR 14,15\;LD 0,136(,13)\",
4561 i - 4, i - 4 );
4562 }
4563 else
4564 {
4565 mvs_check_page (0, 10, 4);
4566 sprintf ( temp, \"LA 1,%d(,13)\;LA 15,%%0\;BALR 14,15\", i );
4567 }
4568 return temp;
4569#endif
4570}"
4571 [(set_attr "length" "22")]
4572)
4573
4574;
4575; call_value instruction pattern(s).
4576;
4577
4578(define_insn "call_value"
4579 [(set (match_operand 0 "" "=rf")
4580 (call (match_operand:QI 1 "memory_operand" "m")
4581 (match_operand:SI 2 "general_operand" "i")))
4582 (clobber (reg:SI 2))
4583 ]
4584 ""
4585 "*
4586{
4587 static char temp[128];
4588 int i = STACK_POINTER_OFFSET;
4589 CC_STATUS_INIT;
4590
4591 check_label_emit ();
4592#ifdef TARGET_ELF_ABI
4593 mvs_check_page (0, 10, 4);
4594 sprintf ( temp, \"LA r2,%d(,sp)\;LA 15,%%1\;BASR 14,15\", i );
4595 return temp;
4596#else
4597 if (mvs_function_check (XSTR (operands[1], 0)))
4598 {
4599 mvs_check_page (0, 22, 4);
4600 sprintf ( temp, \"LA 1,136(,13)\;ST 1,%d(,13)\;LA 1,%d(,13)\;LA 15,%%1\;BALR 14,15\;LD 0,136(,13)\",
4601 i - 4, i - 4 );
4602 }
4603 else
4604 {
4605 mvs_check_page (0, 10, 4);
4606 sprintf ( temp, \"LA 1,%d(,13)\;LA 15,%%1\;BALR 14,15\", i );
4607 }
4608 return temp;
4609#endif
4610}"
4611 [(set_attr "length" "22")]
4612)
4613
4614(define_insn ""
4615 [(call (mem:QI (match_operand:SI 0 "" "i"))
4616 (match_operand:SI 1 "general_operand" "g"))
4617 (clobber (reg:SI 2))
4618 ]
4619 "GET_CODE (operands[0]) == SYMBOL_REF"
4620 "*
4621{
4622 static char temp[128];
4623 int i = STACK_POINTER_OFFSET;
4624 CC_STATUS_INIT;
4625
4626 check_label_emit ();
4627#ifdef TARGET_ELF_ABI
4628 mvs_check_page (0, 10, 4);
4629 sprintf ( temp, \"LA r2,%d(,sp)\;L 15,%%0\;BASR 14,15\", i );
4630 return temp;
4631#else
4632 if (mvs_function_check (XSTR (operands[0], 0)))
4633 {
4634 mvs_check_page (0, 22, 4);
4635 sprintf ( temp, \"LA 1,136(,13)\;ST 1,%d(,13)\;LA 1,%d(,13)\;L 15,%%0\;BALR 14,15\;LD 0,136(,13)\",
4636 i - 4, i - 4 );
4637 }
4638 else
4639 {
4640 mvs_check_page (0, 10, 4);
4641 sprintf ( temp, \"LA 1,%d(,13)\;L 15,%%0\;BALR 14,15\", i );
4642 }
4643 return temp;
4644#endif
4645}"
4646 [(set_attr "length" "22")]
4647)
4648
4649(define_insn ""
4650 [(set (match_operand 0 "" "=rf")
4651 (call (mem:QI (match_operand:SI 1 "" "i"))
4652 (match_operand:SI 2 "general_operand" "g")))
4653 (clobber (reg:SI 2))
4654 ]
4655 "GET_CODE (operands[1]) == SYMBOL_REF"
4656 "*
4657{
4658 static char temp[128];
4659 int i = STACK_POINTER_OFFSET;
4660 CC_STATUS_INIT;
4661
4662 check_label_emit ();
4663#ifdef TARGET_ELF_ABI
4664 mvs_check_page (0, 10, 4);
4665 sprintf ( temp, \"LA r2,%d(,sp)\;L 15,%%1\;BASR 14,15\", i );
4666 return temp;
4667#else
4668 if (mvs_function_check (XSTR (operands[1], 0)))
4669 {
4670 mvs_check_page (0, 22, 4);
4671 sprintf ( temp, \"LA 1,136(,13)\;ST 1,%d(,13)\;LA 1,%d(,13)\;L 15,%%1\;BALR 14,15\;LD 0,136(,13)\",
4672 i - 4, i - 4 );
4673 }
4674 else
4675 {
4676 mvs_check_page (0, 10, 4);
4677 sprintf ( temp, \"LA 1,%d(,13)\;L 15,%%1\;BALR 14,15\", i );
4678 }
4679 return temp;
4680#endif
4681}"
4682 [(set_attr "length" "22")]
4683)
4684
4685;;
4686;; Call subroutine returning any type.
4687;; This instruction pattern appears to be used only by the
4688;; expand_builtin_apply definition for __builtin_apply. It is needed
4689;; since call_value might return an int in r15 or a float in fpr0 (r16)
4690;; and the builtin code calls abort since the reg is ambiguous. Well,
4691;; the below is probably broken anyway, we just want to go for now.
4692;;
4693(define_expand "untyped_call"
4694[(parallel [(call (match_operand 0 "" "")
4695 (const_int 0))
4696 (match_operand 1 "" "")
4697 (match_operand 2 "" "")])]
4698 ""
4699 "
4700{
4701 int i;
4702
4703 emit_call_insn (GEN_CALL (operands[0], const0_rtx, const0_rtx, const0_rtx));
4704
4705 for (i = 0; i < XVECLEN (operands[2], 0); i++)
4706 {
4707 rtx set = XVECEXP (operands[2], 0, i);
4708 emit_move_insn (SET_DEST (set), SET_SRC (set));
4709 }
4710
4711 /* The optimizer does not know that the call sets the function value
4712 registers we stored in the result block. We avoid problems by
4713 claiming that all hard registers are used and clobbered at this
4714 point. */
4715 /* emit_insn (gen_blockage ()); */
4716
4717 DONE;
4718}")
4719
4720
4721;;
4722;;- Miscellaneous instructions.
4723;;
4724
4725;
4726; nop instruction pattern(s).
4727;
4728
4729(define_insn "nop"
4730 [(const_int 0)]
4731 ""
4732 "*
4733{
4734 check_label_emit ();
4735 mvs_check_page (0, 2, 0);
4736 return \"LR 0,0\";
4737}"
4738 [(set_attr "length" "2")]
4739)