]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/config/m32r/predicates.md
Update copyright years.
[thirdparty/gcc.git] / gcc / config / m32r / predicates.md
CommitLineData
22a14e0d 1;; Predicate definitions for Renesas M32R.
818ab71a 2;; Copyright (C) 2005-2016 Free Software Foundation, Inc.
22a14e0d
KH
3;;
4;; This file is part of GCC.
5;;
6;; GCC is free software; you can redistribute it and/or modify
7;; it under the terms of the GNU General Public License as published by
2f83c7d6 8;; the Free Software Foundation; either version 3, or (at your option)
22a14e0d
KH
9;; any later version.
10;;
11;; GCC is distributed in the hope that it will be useful,
12;; but WITHOUT ANY WARRANTY; without even the implied warranty of
13;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14;; GNU General Public License for more details.
15;;
16;; You should have received a copy of the GNU General Public License
2f83c7d6
NC
17;; along with GCC; see the file COPYING3. If not see
18;; <http://www.gnu.org/licenses/>.
22a14e0d
KH
19
20;; Return true if OP is a register or the constant 0.
21
22(define_predicate "reg_or_zero_operand"
23 (match_code "reg,subreg,const_int")
24{
d000f0d9 25 if (REG_P (op) || GET_CODE (op) == SUBREG)
22a14e0d
KH
26 return register_operand (op, mode);
27
d000f0d9 28 if (!CONST_INT_P (op))
22a14e0d
KH
29 return 0;
30
31 return INTVAL (op) == 0;
32})
33
34;; Return nonzero if the operand is suitable for use in a conditional
35;; move sequence.
36
37(define_predicate "conditional_move_operand"
38 (match_code "reg,subreg,const_int")
39{
40 /* Only defined for simple integers so far... */
41 if (mode != SImode && mode != HImode && mode != QImode)
42 return FALSE;
43
44 /* At the moment we can handle moving registers and loading constants. */
45 /* To be added: Addition/subtraction/bitops/multiplication of registers. */
46
47 switch (GET_CODE (op))
48 {
49 case REG:
50 return 1;
51
52 case CONST_INT:
fbaeb717 53 return satisfies_constraint_I (op);
22a14e0d
KH
54
55 default:
56#if 0
57 fprintf (stderr, "Test for cond move op of type: %s\n",
58 GET_RTX_NAME (GET_CODE (op)));
59#endif
60 return 0;
61 }
62})
63
64;; Return true if the code is a test of the carry bit.
65
66(define_predicate "carry_compare_operand"
67 (match_code "eq,ne")
68{
69 rtx x;
70
71 if (GET_MODE (op) != CCmode && GET_MODE (op) != VOIDmode)
72 return FALSE;
73
74 if (GET_CODE (op) != NE && GET_CODE (op) != EQ)
75 return FALSE;
76
77 x = XEXP (op, 0);
d000f0d9 78 if (!REG_P (x) || REGNO (x) != CARRY_REGNUM)
22a14e0d
KH
79 return FALSE;
80
81 x = XEXP (op, 1);
d000f0d9 82 if (!CONST_INT_P (x) || INTVAL (x) != 0)
22a14e0d
KH
83 return FALSE;
84
85 return TRUE;
86})
87
88;; Return 1 if OP is an EQ or NE comparison operator.
89
90(define_predicate "eqne_comparison_operator"
91 (match_code "eq,ne")
92{
93 enum rtx_code code = GET_CODE (op);
94
95 return (code == EQ || code == NE);
96})
97
98;; Return 1 if OP is a signed comparison operator.
99
100(define_predicate "signed_comparison_operator"
101 (match_code "eq,ne,lt,le,gt,ge")
102{
103 enum rtx_code code = GET_CODE (op);
104
105 return (COMPARISON_P (op)
106 && (code == EQ || code == NE
107 || code == LT || code == LE || code == GT || code == GE));
108})
109
110;; Return true if OP is an acceptable argument for a move destination.
111
112(define_predicate "move_dest_operand"
113 (match_code "reg,subreg,mem")
114{
115 switch (GET_CODE (op))
116 {
117 case REG :
118 return register_operand (op, mode);
119 case SUBREG :
120 /* (subreg (mem ...) ...) can occur here if the inner part was once a
121 pseudo-reg and is now a stack slot. */
d000f0d9 122 if (MEM_P (SUBREG_REG (op)))
22a14e0d
KH
123 return address_operand (XEXP (SUBREG_REG (op), 0), mode);
124 else
125 return register_operand (op, mode);
126 case MEM :
127 if (GET_CODE (XEXP (op, 0)) == POST_INC)
128 return 0; /* stores can't do post inc */
129 return address_operand (XEXP (op, 0), mode);
130 default :
131 return 0;
132 }
133})
134
135;; Return true if OP is an acceptable argument for a single word move
136;; source.
137
138(define_predicate "move_src_operand"
139 (match_code "reg,subreg,mem,const_int,const_double,label_ref,const,symbol_ref")
140{
141 switch (GET_CODE (op))
142 {
143 case LABEL_REF :
144 case SYMBOL_REF :
145 case CONST :
146 return addr24_operand (op, mode);
147 case CONST_INT :
148 /* ??? We allow more cse opportunities if we only allow constants
149 loadable with one insn, and split the rest into two. The instances
150 where this would help should be rare and the current way is
151 simpler. */
152 if (HOST_BITS_PER_WIDE_INT > 32)
153 {
154 HOST_WIDE_INT rest = INTVAL (op) >> 31;
155 return (rest == 0 || rest == -1);
156 }
157 else
158 return 1;
159 case CONST_DOUBLE :
160 if (mode == SFmode)
161 return 1;
162 else if (mode == SImode)
163 {
164 /* Large unsigned constants are represented as const_double's. */
165 unsigned HOST_WIDE_INT low, high;
166
167 low = CONST_DOUBLE_LOW (op);
168 high = CONST_DOUBLE_HIGH (op);
169 return high == 0 && low <= (unsigned) 0xffffffff;
170 }
171 else
172 return 0;
173 case REG :
174 return register_operand (op, mode);
175 case SUBREG :
176 /* (subreg (mem ...) ...) can occur here if the inner part was once a
177 pseudo-reg and is now a stack slot. */
d000f0d9 178 if (MEM_P (SUBREG_REG (op)))
22a14e0d
KH
179 return address_operand (XEXP (SUBREG_REG (op), 0), mode);
180 else
181 return register_operand (op, mode);
182 case MEM :
183 if (GET_CODE (XEXP (op, 0)) == PRE_INC
184 || GET_CODE (XEXP (op, 0)) == PRE_DEC)
185 return 0; /* loads can't do pre-{inc,dec} */
186 return address_operand (XEXP (op, 0), mode);
187 default :
188 return 0;
189 }
190})
191
192;; Return true if OP is an acceptable argument for a double word move
193;; source.
194
195(define_predicate "move_double_src_operand"
196 (match_code "reg,subreg,mem,const_int,const_double")
197{
198 switch (GET_CODE (op))
199 {
200 case CONST_INT :
201 case CONST_DOUBLE :
202 return 1;
203 case REG :
204 return register_operand (op, mode);
205 case SUBREG :
206 /* (subreg (mem ...) ...) can occur here if the inner part was once a
207 pseudo-reg and is now a stack slot. */
d000f0d9 208 if (MEM_P (SUBREG_REG (op)))
22a14e0d
KH
209 return move_double_src_operand (SUBREG_REG (op), mode);
210 else
211 return register_operand (op, mode);
212 case MEM :
213 /* Disallow auto inc/dec for now. */
214 if (GET_CODE (XEXP (op, 0)) == PRE_DEC
215 || GET_CODE (XEXP (op, 0)) == PRE_INC)
216 return 0;
217 return address_operand (XEXP (op, 0), mode);
218 default :
219 return 0;
220 }
221})
222
223;; Return true if OP is a const_int requiring two instructions to
224;; load.
225
226(define_predicate "two_insn_const_operand"
227 (match_code "const_int")
228{
d000f0d9 229 if (!CONST_INT_P (op))
22a14e0d 230 return 0;
fbaeb717
KK
231 if (satisfies_constraint_J (op)
232 || satisfies_constraint_M (op)
233 || satisfies_constraint_L (op))
22a14e0d
KH
234 return 0;
235 return 1;
236})
237
238;; Returns 1 if OP is a symbol reference.
239
240(define_predicate "symbolic_operand"
241 (match_code "symbol_ref,label_ref,const")
242{
243 switch (GET_CODE (op))
244 {
245 case SYMBOL_REF:
246 case LABEL_REF:
247 case CONST :
248 return 1;
249
250 default:
251 return 0;
252 }
253})
254
85f65093 255;; Return true if OP is a signed 8-bit immediate value.
22a14e0d
KH
256
257(define_predicate "int8_operand"
258 (match_code "const_int")
259{
d000f0d9 260 if (!CONST_INT_P (op))
22a14e0d 261 return 0;
fbaeb717 262 return satisfies_constraint_I (op);
22a14e0d
KH
263})
264
85f65093 265;; Return true if OP is an unsigned 16-bit immediate value.
22a14e0d
KH
266
267(define_predicate "uint16_operand"
268 (match_code "const_int")
269{
d000f0d9 270 if (!CONST_INT_P (op))
22a14e0d 271 return 0;
fbaeb717 272 return satisfies_constraint_K (op);
22a14e0d
KH
273})
274
85f65093 275;; Return true if OP is a register or signed 16-bit value.
22a14e0d
KH
276
277(define_predicate "reg_or_int16_operand"
278 (match_code "reg,subreg,const_int")
279{
d000f0d9 280 if (REG_P (op) || GET_CODE (op) == SUBREG)
22a14e0d 281 return register_operand (op, mode);
d000f0d9 282 if (!CONST_INT_P (op))
22a14e0d 283 return 0;
fbaeb717 284 return satisfies_constraint_J (op);
22a14e0d
KH
285})
286
85f65093 287;; Return true if OP is a register or an unsigned 16-bit value.
22a14e0d
KH
288
289(define_predicate "reg_or_uint16_operand"
290 (match_code "reg,subreg,const_int")
291{
d000f0d9 292 if (REG_P (op) || GET_CODE (op) == SUBREG)
22a14e0d 293 return register_operand (op, mode);
d000f0d9 294 if (!CONST_INT_P (op))
22a14e0d 295 return 0;
fbaeb717 296 return satisfies_constraint_K (op);
22a14e0d
KH
297})
298
85f65093 299;; Return true if OP is a register or signed 16-bit value for
22a14e0d
KH
300;; compares.
301
302(define_predicate "reg_or_cmp_int16_operand"
303 (match_code "reg,subreg,const_int")
304{
d000f0d9 305 if (REG_P (op) || GET_CODE (op) == SUBREG)
22a14e0d 306 return register_operand (op, mode);
d000f0d9 307 if (!CONST_INT_P (op))
22a14e0d 308 return 0;
fbaeb717 309 return satisfies_constraint_P (op);
22a14e0d
KH
310})
311
312;; Return true if OP is a register or an integer value that can be
313;; used is SEQ/SNE. We can use either XOR of the value or ADD of the
314;; negative of the value for the constant. Don't allow 0, because
315;; that is special cased.
316
317(define_predicate "reg_or_eq_int16_operand"
318 (match_code "reg,subreg,const_int")
319{
320 HOST_WIDE_INT value;
321
d000f0d9 322 if (REG_P (op) || GET_CODE (op) == SUBREG)
22a14e0d
KH
323 return register_operand (op, mode);
324
d000f0d9 325 if (!CONST_INT_P (op))
22a14e0d
KH
326 return 0;
327
328 value = INTVAL (op);
329 return (value != 0) && (UINT16_P (value) || CMP_INT16_P (-value));
330})
331
85f65093 332;; Return true if OP is a signed 16-bit immediate value useful in
22a14e0d
KH
333;; comparisons.
334
335(define_predicate "cmp_int16_operand"
336 (match_code "const_int")
337{
d000f0d9 338 if (!CONST_INT_P (op))
22a14e0d 339 return 0;
fbaeb717 340 return satisfies_constraint_P (op);
22a14e0d
KH
341})
342
343;; Acceptable arguments to the call insn.
344
345(define_predicate "call_address_operand"
346 (match_code "symbol_ref,label_ref,const")
347{
348 return symbolic_operand (op, mode);
349
350/* Constants and values in registers are not OK, because
351 the m32r BL instruction can only support PC relative branching. */
352})
353
354;; Return true if OP is an acceptable input argument for a zero/sign
355;; extend operation.
356
357(define_predicate "extend_operand"
358 (match_code "reg,subreg,mem")
359{
360 rtx addr;
361
362 switch (GET_CODE (op))
363 {
364 case REG :
365 case SUBREG :
366 return register_operand (op, mode);
367
368 case MEM :
369 addr = XEXP (op, 0);
370 if (GET_CODE (addr) == PRE_INC || GET_CODE (addr) == PRE_DEC)
371 return 0; /* loads can't do pre inc/pre dec */
372
373 return address_operand (addr, mode);
374
375 default :
376 return 0;
377 }
378})
379
380;; Return nonzero if the operand is an insn that is a small
381;; insn. Allow const_int 0 as well, which is a placeholder for NOP
382;; slots.
383
384(define_predicate "small_insn_p"
385 (match_code "insn,call_insn,jump_insn")
386{
d000f0d9 387 if (CONST_INT_P (op) && INTVAL (op) == 0)
22a14e0d
KH
388 return 1;
389
390 if (! INSN_P (op))
391 return 0;
392
84034c69 393 return get_attr_length (as_a <rtx_insn *> (op)) == 2;
22a14e0d
KH
394})
395
396;; Return true if op is an integer constant, less than or equal to
397;; MAX_MOVE_BYTES.
398
399(define_predicate "m32r_block_immediate_operand"
400 (match_code "const_int")
401{
d000f0d9 402 if (!CONST_INT_P (op)
22a14e0d
KH
403 || INTVAL (op) > MAX_MOVE_BYTES
404 || INTVAL (op) <= 0)
405 return 0;
406
407 return 1;
408})
409
410;; Return nonzero if the operand is an insn that is a large insn.
411
412(define_predicate "large_insn_p"
413 (match_code "insn,call_insn,jump_insn")
414{
415 if (! INSN_P (op))
416 return 0;
417
84034c69 418 return get_attr_length (as_a <rtx_insn *> (op)) != 2;
22a14e0d
KH
419})
420
421;; Returns 1 if OP is an acceptable operand for seth/add3.
422
423(define_predicate "seth_add3_operand"
424 (match_code "symbol_ref,label_ref,const")
425{
426 if (flag_pic)
427 return 0;
428
429 if (GET_CODE (op) == SYMBOL_REF
430 || GET_CODE (op) == LABEL_REF)
431 return 1;
432
433 if (GET_CODE (op) == CONST
434 && GET_CODE (XEXP (op, 0)) == PLUS
435 && GET_CODE (XEXP (XEXP (op, 0), 0)) == SYMBOL_REF
fbaeb717 436 && satisfies_constraint_J (XEXP (XEXP (op, 0), 1)))
22a14e0d
KH
437 return 1;
438
439 return 0;
440})